aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorBill Meier <wmeier@newsguy.com>2014-10-06 12:42:42 -0400
committerBill Meier <wmeier@newsguy.com>2014-10-06 17:10:35 +0000
commit2005fc6e780e2df78382a3c04dbdd574054eb6a5 (patch)
tree3d2f7165d21677ada41bde77cc065a545808a991
parent3377eca702cc0e8fe7b3f3409437f16b5b0b9b79 (diff)
Convert (what appear to be) "4 space tabs"; Adjust editor-modelines; Do some minor reformatting.
Change-Id: Ie078c826ed38a0d682f61fb3e95450b47a9d2c31 Reviewed-on: https://code.wireshark.org/review/4499 Reviewed-by: Bill Meier <wmeier@newsguy.com>
-rw-r--r--epan/dissectors/packet-icq.c2216
-rw-r--r--epan/dissectors/packet-rtpproxy.c2552
-rw-r--r--epan/dissectors/packet-ssh.c2234
3 files changed, 3505 insertions, 3497 deletions
diff --git a/epan/dissectors/packet-icq.c b/epan/dissectors/packet-icq.c
index 12c178b1eb..f57360f9f9 100644
--- a/epan/dissectors/packet-icq.c
+++ b/epan/dissectors/packet-icq.c
@@ -65,7 +65,7 @@ static expert_field ei_icq_unknown_meta_subcmd = EI_INIT;
static expert_field ei_icq_unknown_command = EI_INIT;
/* This is not IANA registered */
-#define UDP_PORT_ICQ 4000
+#define UDP_PORT_ICQ 4000
#define ICQ5_SERVER 0
#define ICQ5_CLIENT 1
@@ -74,289 +74,289 @@ const true_false_string tfs_client_server = { "Client", "Server" };
static void
dissect_icqv5Server(tvbuff_t *tvb, int offset, packet_info *pinfo,
- proto_tree *tree, int pktsize);
+ proto_tree *tree, int pktsize);
/* Offsets of fields in the ICQ headers */
/* Can be 0x0002 or 0x0005 */
-#define ICQ_VERSION 0x00
+#define ICQ_VERSION 0x00
/* Is either one (server) or four (client) bytes long */
/* Client header offsets */
-#define ICQ5_UNKNOWN 0x02
-#define ICQ5_CL_UIN 0x06
-#define ICQ5_CL_SESSIONID 0x0a
-#define ICQ5_CL_CMD 0x0e
-#define ICQ5_CL_SEQNUM1 0x10
-#define ICQ5_CL_SEQNUM2 0x12
-#define ICQ5_CL_CHECKCODE 0x14
-#define ICQ5_CL_PARAM 0x18
-#define ICQ5_CL_HDRSIZE 0x18
+#define ICQ5_UNKNOWN 0x02
+#define ICQ5_CL_UIN 0x06
+#define ICQ5_CL_SESSIONID 0x0a
+#define ICQ5_CL_CMD 0x0e
+#define ICQ5_CL_SEQNUM1 0x10
+#define ICQ5_CL_SEQNUM2 0x12
+#define ICQ5_CL_CHECKCODE 0x14
+#define ICQ5_CL_PARAM 0x18
+#define ICQ5_CL_HDRSIZE 0x18
/* Server header offsets */
-#define ICQ5_SRV_SESSIONID 0x03
-#define ICQ5_SRV_CMD 0x07
-#define ICQ5_SRV_SEQNUM1 0x09
-#define ICQ5_SRV_SEQNUM2 0x0b
-#define ICQ5_SRV_UIN 0x0d
-#define ICQ5_SRV_CHECKCODE 0x11
-#define ICQ5_SRV_PARAM 0x15
-#define ICQ5_SRV_HDRSIZE 0x15
+#define ICQ5_SRV_SESSIONID 0x03
+#define ICQ5_SRV_CMD 0x07
+#define ICQ5_SRV_SEQNUM1 0x09
+#define ICQ5_SRV_SEQNUM2 0x0b
+#define ICQ5_SRV_UIN 0x0d
+#define ICQ5_SRV_CHECKCODE 0x11
+#define ICQ5_SRV_PARAM 0x15
+#define ICQ5_SRV_HDRSIZE 0x15
-#define SRV_ACK 0x000a
+#define SRV_ACK 0x000a
-#define SRV_SILENT_TOO_LONG 0x001e
+#define SRV_SILENT_TOO_LONG 0x001e
-#define SRV_GO_AWAY 0x0028
+#define SRV_GO_AWAY 0x0028
-#define SRV_NEW_UIN 0x0046
+#define SRV_NEW_UIN 0x0046
/* LOGIN_REPLY is very scary. It has a lot of fields that are undocumented
* Only the IP field makes sense */
-#define SRV_LOGIN_REPLY 0x005a
-#define SRV_LOGIN_REPLY_IP 0x000c
+#define SRV_LOGIN_REPLY 0x005a
+#define SRV_LOGIN_REPLY_IP 0x000c
-#define SRV_BAD_PASS 0x0064
+#define SRV_BAD_PASS 0x0064
-#define SRV_USER_ONLINE 0x006e
-#define SRV_USER_ONL_UIN 0x0000
-#define SRV_USER_ONL_IP 0x0004
-#define SRV_USER_ONL_PORT 0x0008
-#define SRV_USER_ONL_REALIP 0x000c
-#define SRV_USER_ONL_X1 0x0010
-#define SRV_USER_ONL_STATUS 0x0013
-#define SRV_USER_ONL_X2 0x0015
+#define SRV_USER_ONLINE 0x006e
+#define SRV_USER_ONL_UIN 0x0000
+#define SRV_USER_ONL_IP 0x0004
+#define SRV_USER_ONL_PORT 0x0008
+#define SRV_USER_ONL_REALIP 0x000c
+#define SRV_USER_ONL_X1 0x0010
+#define SRV_USER_ONL_STATUS 0x0013
+#define SRV_USER_ONL_X2 0x0015
-#define SRV_USER_OFFLINE 0x0078
-#define SRV_USER_OFFLINE_UIN 0x0000
+#define SRV_USER_OFFLINE 0x0078
+#define SRV_USER_OFFLINE_UIN 0x0000
-#define SRV_MULTI 0x0212
-#define SRV_MULTI_NUM 0x0000
+#define SRV_MULTI 0x0212
+#define SRV_MULTI_NUM 0x0000
-#define SRV_META_USER 0x03de
-#define SRV_META_USER_SUBCMD 0x0000
-#define SRV_META_USER_RESULT 0x0002
-#define SRV_META_USER_DATA 0x0003
+#define SRV_META_USER 0x03de
+#define SRV_META_USER_SUBCMD 0x0000
+#define SRV_META_USER_RESULT 0x0002
+#define SRV_META_USER_DATA 0x0003
-#define SRV_UPDATE_SUCCESS 0x01e0
+#define SRV_UPDATE_SUCCESS 0x01e0
-#define SRV_UPDATE_FAIL 0x01ea
+#define SRV_UPDATE_FAIL 0x01ea
/*
* ICQv5 SRV_META_USER subcommands
*/
-#define META_EX_USER_FOUND 0x0190
-#define META_USER_FOUND 0x019a
-#define META_ABOUT 0x00e6
-#define META_USER_INFO 0x00c8
-
-#define SRV_RECV_MESSAGE 0x00dc
-#define SRV_RECV_MSG_UIN 0x0000
-#define SRV_RECV_MSG_YEAR 0x0004
-#define SRV_RECV_MSG_MONTH 0x0006
-#define SRV_RECV_MSG_DAY 0x0007
-#define SRV_RECV_MSG_HOUR 0x0008
-#define SRV_RECV_MSG_MINUTE 0x0009
+#define META_EX_USER_FOUND 0x0190
+#define META_USER_FOUND 0x019a
+#define META_ABOUT 0x00e6
+#define META_USER_INFO 0x00c8
+
+#define SRV_RECV_MESSAGE 0x00dc
+#define SRV_RECV_MSG_UIN 0x0000
+#define SRV_RECV_MSG_YEAR 0x0004
+#define SRV_RECV_MSG_MONTH 0x0006
+#define SRV_RECV_MSG_DAY 0x0007
+#define SRV_RECV_MSG_HOUR 0x0008
+#define SRV_RECV_MSG_MINUTE 0x0009
#define SRV_RECV_MSG_MSG_TYPE 0x000a
-#define SRV_RAND_USER 0x024e
-#define SRV_RAND_USER_UIN 0x0000
-#define SRV_RAND_USER_IP 0x0004
-#define SRV_RAND_USER_PORT 0x0008
+#define SRV_RAND_USER 0x024e
+#define SRV_RAND_USER_UIN 0x0000
+#define SRV_RAND_USER_IP 0x0004
+#define SRV_RAND_USER_PORT 0x0008
#define SRV_RAND_USER_REAL_IP 0x000c
-#define SRV_RAND_USER_CLASS 0x0010
-#define SRV_RAND_USER_X1 0x0011
-#define SRV_RAND_USER_STATUS 0x0015
+#define SRV_RAND_USER_CLASS 0x0010
+#define SRV_RAND_USER_X1 0x0011
+#define SRV_RAND_USER_STATUS 0x0015
#define SRV_RAND_USER_TCP_VER 0x0019
/* This message has the same structure as cmd_send_msg */
-#define SRV_SYS_DELIVERED_MESS 0x0104
+#define SRV_SYS_DELIVERED_MESS 0x0104
static const value_string serverMetaSubCmdCode[] = {
- { META_USER_FOUND, "META_USER_FOUND" },
- { META_EX_USER_FOUND, "META_EX_USER_FOUND" },
- { META_ABOUT, "META_ABOUT" },
- { META_USER_INFO, "META_USER_INFO" },
- { 0, NULL }
+ { META_USER_FOUND, "META_USER_FOUND" },
+ { META_EX_USER_FOUND, "META_EX_USER_FOUND" },
+ { META_ABOUT, "META_ABOUT" },
+ { META_USER_INFO, "META_USER_INFO" },
+ { 0, NULL }
};
static const value_string serverCmdCode[] = {
- { SRV_ACK, "SRV_ACK" },
- { SRV_SILENT_TOO_LONG, "SRV_SILENT_TOO_LONG" },
- { SRV_GO_AWAY, "SRV_GO_AWAY" },
- { SRV_NEW_UIN, "SRV_NEW_UIN" },
- { SRV_LOGIN_REPLY, "SRV_LOGIN_REPLY" },
- { SRV_BAD_PASS, "SRV_BAD_PASS" },
- { SRV_USER_ONLINE, "SRV_USER_ONLINE" },
- { SRV_USER_OFFLINE, "SRV_USER_OFFLINE" },
- { 130, "SRV_QUERY" },
- { 140, "SRV_USER_FOUND" },
- { 160, "SRV_END_OF_SEARCH" },
- { 180, "SRV_NEW_USER" },
- { 200, "SRV_UPDATE_EXT" },
- { SRV_RECV_MESSAGE, "SRV_RECV_MESSAGE" },
- { 230, "SRV_END_OFFLINE_MESSAGES" },
- { 240, "SRV_NOT_CONNECTED" },
- { 250, "SRV_TRY_AGAIN" },
- { SRV_SYS_DELIVERED_MESS, "SRV_SYS_DELIVERED_MESS" },
- { 280, "SRV_INFO_REPLY" },
- { 290, "SRV_EXT_INFO_REPLY" },
- { 420, "SRV_STATUS_UPDATE" },
- { 450, "SRV_SYSTEM_MESSAGE" },
- { SRV_UPDATE_SUCCESS, "SRV_UPDATE_SUCCESS" },
- { SRV_UPDATE_FAIL, "SRV_UPDATE_FAIL" },
- { 500, "SRV_AUTH_UPDATE" },
- { SRV_MULTI, "SRV_MULTI_PACKET" },
- { 540, "SRV_END_CONTACTLIST_STATUS" },
- { SRV_RAND_USER, "SRV_RAND_USER" },
- { SRV_META_USER, "SRV_META_USER" },
- { 0, NULL }
+ { SRV_ACK, "SRV_ACK" },
+ { SRV_SILENT_TOO_LONG, "SRV_SILENT_TOO_LONG" },
+ { SRV_GO_AWAY, "SRV_GO_AWAY" },
+ { SRV_NEW_UIN, "SRV_NEW_UIN" },
+ { SRV_LOGIN_REPLY, "SRV_LOGIN_REPLY" },
+ { SRV_BAD_PASS, "SRV_BAD_PASS" },
+ { SRV_USER_ONLINE, "SRV_USER_ONLINE" },
+ { SRV_USER_OFFLINE, "SRV_USER_OFFLINE" },
+ { 130, "SRV_QUERY" },
+ { 140, "SRV_USER_FOUND" },
+ { 160, "SRV_END_OF_SEARCH" },
+ { 180, "SRV_NEW_USER" },
+ { 200, "SRV_UPDATE_EXT" },
+ { SRV_RECV_MESSAGE, "SRV_RECV_MESSAGE" },
+ { 230, "SRV_END_OFFLINE_MESSAGES" },
+ { 240, "SRV_NOT_CONNECTED" },
+ { 250, "SRV_TRY_AGAIN" },
+ { SRV_SYS_DELIVERED_MESS, "SRV_SYS_DELIVERED_MESS" },
+ { 280, "SRV_INFO_REPLY" },
+ { 290, "SRV_EXT_INFO_REPLY" },
+ { 420, "SRV_STATUS_UPDATE" },
+ { 450, "SRV_SYSTEM_MESSAGE" },
+ { SRV_UPDATE_SUCCESS, "SRV_UPDATE_SUCCESS" },
+ { SRV_UPDATE_FAIL, "SRV_UPDATE_FAIL" },
+ { 500, "SRV_AUTH_UPDATE" },
+ { SRV_MULTI, "SRV_MULTI_PACKET" },
+ { 540, "SRV_END_CONTACTLIST_STATUS" },
+ { SRV_RAND_USER, "SRV_RAND_USER" },
+ { SRV_META_USER, "SRV_META_USER" },
+ { 0, NULL }
};
-#define MSG_TEXT 0x0001
-#define MSG_URL 0x0004
-#define MSG_AUTH_REQ 0x0006
-#define MSG_AUTH 0x0008
-#define MSG_USER_ADDED 0x000c
-#define MSG_EMAIL 0x000e
-#define MSG_CONTACTS 0x0013
-
-#define STATUS_ONLINE 0x00000000
-#define STATUS_AWAY 0x00000001
-#define STATUS_DND 0x00000013
-#define STATUS_INVISIBLE 0x00000100
-#define STATUS_OCCUPIED 0x00000010
-#define STATUS_NA 0x00000004
-#define STATUS_CHAT 0x00000020
+#define MSG_TEXT 0x0001
+#define MSG_URL 0x0004
+#define MSG_AUTH_REQ 0x0006
+#define MSG_AUTH 0x0008
+#define MSG_USER_ADDED 0x000c
+#define MSG_EMAIL 0x000e
+#define MSG_CONTACTS 0x0013
+
+#define STATUS_ONLINE 0x00000000
+#define STATUS_AWAY 0x00000001
+#define STATUS_DND 0x00000013
+#define STATUS_INVISIBLE 0x00000100
+#define STATUS_OCCUPIED 0x00000010
+#define STATUS_NA 0x00000004
+#define STATUS_CHAT 0x00000020
/* Offsets for all packets measured from the start of the payload; i.e.
* with the ICQ header removed
*/
-#define CMD_ACK 0x000a
-#define CMD_ACK_RANDOM 0x0000
-
-#define CMD_SEND_MSG 0x010E
-#define CMD_SEND_MSG_RECV_UIN 0x0000
-#define CMD_SEND_MSG_MSG_TYPE 0x0004
-#define CMD_SEND_MSG_MSG_LEN 0x0006
-#define CMD_SEND_MSG_MSG_TEXT 0x0008
+#define CMD_ACK 0x000a
+#define CMD_ACK_RANDOM 0x0000
+
+#define CMD_SEND_MSG 0x010E
+#define CMD_SEND_MSG_RECV_UIN 0x0000
+#define CMD_SEND_MSG_MSG_TYPE 0x0004
+#define CMD_SEND_MSG_MSG_LEN 0x0006
+#define CMD_SEND_MSG_MSG_TEXT 0x0008
/* The rest of the packet should be a null-term string */
-#define CMD_LOGIN 0x03E8
-#define CMD_LOGIN_TIME 0x0000
-#define CMD_LOGIN_PORT 0x0004
-#define CMD_LOGIN_PASSLEN 0x0008
-#define CMD_LOGIN_PASSWD 0x000A
+#define CMD_LOGIN 0x03E8
+#define CMD_LOGIN_TIME 0x0000
+#define CMD_LOGIN_PORT 0x0004
+#define CMD_LOGIN_PASSLEN 0x0008
+#define CMD_LOGIN_PASSWD 0x000A
/* The password is variable length; so when we've decoded the passwd,
* the structure starts counting at 0 again.
*/
-#define CMD_LOGIN_IP 0x0004
-#define CMD_LOGIN_STATUS 0x0009
+#define CMD_LOGIN_IP 0x0004
+#define CMD_LOGIN_STATUS 0x0009
-#define CMD_CONTACT_LIST 0x0406
-#define CMD_CONTACT_LIST_NUM 0x0000
+#define CMD_CONTACT_LIST 0x0406
+#define CMD_CONTACT_LIST_NUM 0x0000
-#define CMD_USER_META 0x064a
+#define CMD_USER_META 0x064a
-#define CMD_REG_NEW_USER 0x03fc
+#define CMD_REG_NEW_USER 0x03fc
-#define CMD_ACK_MESSAGES 0x0442
-#define CMD_ACK_MESSAGES_RANDOM 0x0000
+#define CMD_ACK_MESSAGES 0x0442
+#define CMD_ACK_MESSAGES_RANDOM 0x0000
-#define CMD_KEEP_ALIVE 0x042e
-#define CMD_KEEP_ALIVE_RANDOM 0x0000
+#define CMD_KEEP_ALIVE 0x042e
+#define CMD_KEEP_ALIVE_RANDOM 0x0000
-#define CMD_SEND_TEXT_CODE 0x0438
-#define CMD_SEND_TEXT_CODE_LEN 0x0000
-#define CMD_SEND_TEXT_CODE_TEXT 0x0002
+#define CMD_SEND_TEXT_CODE 0x0438
+#define CMD_SEND_TEXT_CODE_LEN 0x0000
+#define CMD_SEND_TEXT_CODE_TEXT 0x0002
-#define CMD_MSG_TO_NEW_USER 0x0456
+#define CMD_MSG_TO_NEW_USER 0x0456
-#define CMD_QUERY_SERVERS 0x04ba
+#define CMD_QUERY_SERVERS 0x04ba
-#define CMD_QUERY_ADDONS 0x04c4
+#define CMD_QUERY_ADDONS 0x04c4
-#define CMD_STATUS_CHANGE 0x04d8
+#define CMD_STATUS_CHANGE 0x04d8
#define CMD_STATUS_CHANGE_STATUS 0x0000
-#define CMD_ADD_TO_LIST 0x053c
-#define CMD_ADD_TO_LIST_UIN 0x0000
+#define CMD_ADD_TO_LIST 0x053c
+#define CMD_ADD_TO_LIST_UIN 0x0000
-#define CMD_RAND_SEARCH 0x056e
-#define CMD_RAND_SEARCH_GROUP 0x0000
+#define CMD_RAND_SEARCH 0x056e
+#define CMD_RAND_SEARCH_GROUP 0x0000
-#define CMD_META_USER 0x064a
+#define CMD_META_USER 0x064a
static const value_string msgTypeCode[] = {
- { MSG_TEXT, "MSG_TEXT" },
- { MSG_URL, "MSG_URL" },
- { MSG_AUTH_REQ, "MSG_AUTH_REQ" },
- { MSG_AUTH, "MSG_AUTH" },
- { MSG_USER_ADDED, "MSG_USER_ADDED" },
- { MSG_EMAIL, "MSG_EMAIL" },
- { MSG_CONTACTS, "MSG_CONTACTS" },
- { 0, NULL }
+ { MSG_TEXT, "MSG_TEXT" },
+ { MSG_URL, "MSG_URL" },
+ { MSG_AUTH_REQ, "MSG_AUTH_REQ" },
+ { MSG_AUTH, "MSG_AUTH" },
+ { MSG_USER_ADDED, "MSG_USER_ADDED" },
+ { MSG_EMAIL, "MSG_EMAIL" },
+ { MSG_CONTACTS, "MSG_CONTACTS" },
+ { 0, NULL }
};
static const value_string statusCode[] = {
- { STATUS_ONLINE, "ONLINE" },
- { STATUS_AWAY, "AWAY" },
- { STATUS_DND, "DND" },
- { STATUS_INVISIBLE, "INVISIBLE" },
- { STATUS_OCCUPIED, "OCCUPIED" },
- { STATUS_NA, "NA" },
- { STATUS_CHAT, "Free for Chat" },
- { 0, NULL }
+ { STATUS_ONLINE, "ONLINE" },
+ { STATUS_AWAY, "AWAY" },
+ { STATUS_DND, "DND" },
+ { STATUS_INVISIBLE, "INVISIBLE" },
+ { STATUS_OCCUPIED, "OCCUPIED" },
+ { STATUS_NA, "NA" },
+ { STATUS_CHAT, "Free for Chat" },
+ { 0, NULL }
};
static const value_string clientCmdCode[] = {
- { CMD_ACK, "CMD_ACK" },
- { CMD_SEND_MSG, "CMD_SEND_MESSAGE" },
- { CMD_LOGIN, "CMD_LOGIN" },
- { CMD_REG_NEW_USER, "CMD_REG_NEW_USER" },
- { 1030, "CMD_CONTACT_LIST" },
- { 1050, "CMD_SEARCH_UIN" },
- { 1060, "CMD_SEARCH_USER" },
- { 1070, "CMD_KEEP_ALIVE" },
- { CMD_SEND_TEXT_CODE, "CMD_SEND_TEXT_CODE" },
- { CMD_ACK_MESSAGES, "CMD_ACK_MESSAGES" },
- { 1100, "CMD_LOGIN_1" },
- { CMD_MSG_TO_NEW_USER, "CMD_MSG_TO_NEW_USER" },
- { 1120, "CMD_INFO_REQ" },
- { 1130, "CMD_EXT_INFO_REQ" },
- { 1180, "CMD_CHANGE_PW" },
- { 1190, "CMD_NEW_USER_INFO" },
- { 1200, "CMD_UPDATE_EXT_INFO" },
- { CMD_QUERY_SERVERS, "CMD_QUERY_SERVERS" },
- { CMD_QUERY_ADDONS, "CMD_QUERY_ADDONS" },
- { CMD_STATUS_CHANGE, "CMD_STATUS_CHANGE" },
- { 1260, "CMD_NEW_USER_1" },
- { 1290, "CMD_UPDATE_INFO" },
- { 1300, "CMD_AUTH_UPDATE" },
- { 1310, "CMD_KEEP_ALIVE2" },
- { 1320, "CMD_LOGIN_2" },
- { CMD_ADD_TO_LIST, "CMD_ADD_TO_LIST" },
- { 1380, "CMD_RAND_SET" },
- { CMD_RAND_SEARCH, "CMD_RAND_SEARCH" },
- { CMD_META_USER, "CMD_META_USER" },
- { 1700, "CMD_INVIS_LIST" },
- { 1710, "CMD_VIS_LIST" },
- { 1720, "CMD_UPDATE_LIST" },
- { 0, NULL }
+ { CMD_ACK, "CMD_ACK" },
+ { CMD_SEND_MSG, "CMD_SEND_MESSAGE" },
+ { CMD_LOGIN, "CMD_LOGIN" },
+ { CMD_REG_NEW_USER, "CMD_REG_NEW_USER" },
+ { 1030, "CMD_CONTACT_LIST" },
+ { 1050, "CMD_SEARCH_UIN" },
+ { 1060, "CMD_SEARCH_USER" },
+ { 1070, "CMD_KEEP_ALIVE" },
+ { CMD_SEND_TEXT_CODE, "CMD_SEND_TEXT_CODE" },
+ { CMD_ACK_MESSAGES, "CMD_ACK_MESSAGES" },
+ { 1100, "CMD_LOGIN_1" },
+ { CMD_MSG_TO_NEW_USER, "CMD_MSG_TO_NEW_USER" },
+ { 1120, "CMD_INFO_REQ" },
+ { 1130, "CMD_EXT_INFO_REQ" },
+ { 1180, "CMD_CHANGE_PW" },
+ { 1190, "CMD_NEW_USER_INFO" },
+ { 1200, "CMD_UPDATE_EXT_INFO" },
+ { CMD_QUERY_SERVERS, "CMD_QUERY_SERVERS" },
+ { CMD_QUERY_ADDONS, "CMD_QUERY_ADDONS" },
+ { CMD_STATUS_CHANGE, "CMD_STATUS_CHANGE" },
+ { 1260, "CMD_NEW_USER_1" },
+ { 1290, "CMD_UPDATE_INFO" },
+ { 1300, "CMD_AUTH_UPDATE" },
+ { 1310, "CMD_KEEP_ALIVE2" },
+ { 1320, "CMD_LOGIN_2" },
+ { CMD_ADD_TO_LIST, "CMD_ADD_TO_LIST" },
+ { 1380, "CMD_RAND_SET" },
+ { CMD_RAND_SEARCH, "CMD_RAND_SEARCH" },
+ { CMD_META_USER, "CMD_META_USER" },
+ { 1700, "CMD_INVIS_LIST" },
+ { 1710, "CMD_VIS_LIST" },
+ { 1720, "CMD_UPDATE_LIST" },
+ { 0, NULL }
};
#if 0
static const value_string group_vals[] = {
- { 1, "Name" },
- { 2, "General" },
- { 3, "Romance" },
- { 4, "Games" },
- { 5, "Students" },
- { 6, "20 Something" },
- { 7, "30 Something" },
- { 8, "40 Something" },
- { 9, "50 or worse" },
- { 10, "Man want women" },
- { 11, "Women want men" },
- { 0, NULL }
+ { 1, "Name" },
+ { 2, "General" },
+ { 3, "Romance" },
+ { 4, "Games" },
+ { 5, "Students" },
+ { 6, "20 Something" },
+ { 7, "30 Something" },
+ { 8, "40 Something" },
+ { 9, "50 or worse" },
+ { 10, "Man want women" },
+ { 11, "Women want men" },
+ { 0, NULL }
};
#endif
@@ -365,65 +365,65 @@ static const value_string group_vals[] = {
*/
static const guchar
table_v5 [] = {
- 0x59, 0x60, 0x37, 0x6B, 0x65, 0x62, 0x46, 0x48, 0x53, 0x61, 0x4C, 0x59, 0x60, 0x57, 0x5B, 0x3D,
- 0x5E, 0x34, 0x6D, 0x36, 0x50, 0x3F, 0x6F, 0x67, 0x53, 0x61, 0x4C, 0x59, 0x40, 0x47, 0x63, 0x39,
- 0x50, 0x5F, 0x5F, 0x3F, 0x6F, 0x47, 0x43, 0x69, 0x48, 0x33, 0x31, 0x64, 0x35, 0x5A, 0x4A, 0x42,
- 0x56, 0x40, 0x67, 0x53, 0x41, 0x07, 0x6C, 0x49, 0x58, 0x3B, 0x4D, 0x46, 0x68, 0x43, 0x69, 0x48,
- 0x33, 0x31, 0x44, 0x65, 0x62, 0x46, 0x48, 0x53, 0x41, 0x07, 0x6C, 0x69, 0x48, 0x33, 0x51, 0x54,
- 0x5D, 0x4E, 0x6C, 0x49, 0x38, 0x4B, 0x55, 0x4A, 0x62, 0x46, 0x48, 0x33, 0x51, 0x34, 0x6D, 0x36,
- 0x50, 0x5F, 0x5F, 0x5F, 0x3F, 0x6F, 0x47, 0x63, 0x59, 0x40, 0x67, 0x33, 0x31, 0x64, 0x35, 0x5A,
- 0x6A, 0x52, 0x6E, 0x3C, 0x51, 0x34, 0x6D, 0x36, 0x50, 0x5F, 0x5F, 0x3F, 0x4F, 0x37, 0x4B, 0x35,
- 0x5A, 0x4A, 0x62, 0x66, 0x58, 0x3B, 0x4D, 0x66, 0x58, 0x5B, 0x5D, 0x4E, 0x6C, 0x49, 0x58, 0x3B,
- 0x4D, 0x66, 0x58, 0x3B, 0x4D, 0x46, 0x48, 0x53, 0x61, 0x4C, 0x59, 0x40, 0x67, 0x33, 0x31, 0x64,
- 0x55, 0x6A, 0x32, 0x3E, 0x44, 0x45, 0x52, 0x6E, 0x3C, 0x31, 0x64, 0x55, 0x6A, 0x52, 0x4E, 0x6C,
- 0x69, 0x48, 0x53, 0x61, 0x4C, 0x39, 0x30, 0x6F, 0x47, 0x63, 0x59, 0x60, 0x57, 0x5B, 0x3D, 0x3E,
- 0x64, 0x35, 0x3A, 0x3A, 0x5A, 0x6A, 0x52, 0x4E, 0x6C, 0x69, 0x48, 0x53, 0x61, 0x6C, 0x49, 0x58,
- 0x3B, 0x4D, 0x46, 0x68, 0x63, 0x39, 0x50, 0x5F, 0x5F, 0x3F, 0x6F, 0x67, 0x53, 0x41, 0x25, 0x41,
- 0x3C, 0x51, 0x54, 0x3D, 0x5E, 0x54, 0x5D, 0x4E, 0x4C, 0x39, 0x50, 0x5F, 0x5F, 0x5F, 0x3F, 0x6F,
- 0x47, 0x43, 0x69, 0x48, 0x33, 0x51, 0x54, 0x5D, 0x6E, 0x3C, 0x31, 0x64, 0x35, 0x5A, 0x00, 0x00 };
+ 0x59, 0x60, 0x37, 0x6B, 0x65, 0x62, 0x46, 0x48, 0x53, 0x61, 0x4C, 0x59, 0x60, 0x57, 0x5B, 0x3D,
+ 0x5E, 0x34, 0x6D, 0x36, 0x50, 0x3F, 0x6F, 0x67, 0x53, 0x61, 0x4C, 0x59, 0x40, 0x47, 0x63, 0x39,
+ 0x50, 0x5F, 0x5F, 0x3F, 0x6F, 0x47, 0x43, 0x69, 0x48, 0x33, 0x31, 0x64, 0x35, 0x5A, 0x4A, 0x42,
+ 0x56, 0x40, 0x67, 0x53, 0x41, 0x07, 0x6C, 0x49, 0x58, 0x3B, 0x4D, 0x46, 0x68, 0x43, 0x69, 0x48,
+ 0x33, 0x31, 0x44, 0x65, 0x62, 0x46, 0x48, 0x53, 0x41, 0x07, 0x6C, 0x69, 0x48, 0x33, 0x51, 0x54,
+ 0x5D, 0x4E, 0x6C, 0x49, 0x38, 0x4B, 0x55, 0x4A, 0x62, 0x46, 0x48, 0x33, 0x51, 0x34, 0x6D, 0x36,
+ 0x50, 0x5F, 0x5F, 0x5F, 0x3F, 0x6F, 0x47, 0x63, 0x59, 0x40, 0x67, 0x33, 0x31, 0x64, 0x35, 0x5A,
+ 0x6A, 0x52, 0x6E, 0x3C, 0x51, 0x34, 0x6D, 0x36, 0x50, 0x5F, 0x5F, 0x3F, 0x4F, 0x37, 0x4B, 0x35,
+ 0x5A, 0x4A, 0x62, 0x66, 0x58, 0x3B, 0x4D, 0x66, 0x58, 0x5B, 0x5D, 0x4E, 0x6C, 0x49, 0x58, 0x3B,
+ 0x4D, 0x66, 0x58, 0x3B, 0x4D, 0x46, 0x48, 0x53, 0x61, 0x4C, 0x59, 0x40, 0x67, 0x33, 0x31, 0x64,
+ 0x55, 0x6A, 0x32, 0x3E, 0x44, 0x45, 0x52, 0x6E, 0x3C, 0x31, 0x64, 0x55, 0x6A, 0x52, 0x4E, 0x6C,
+ 0x69, 0x48, 0x53, 0x61, 0x4C, 0x39, 0x30, 0x6F, 0x47, 0x63, 0x59, 0x60, 0x57, 0x5B, 0x3D, 0x3E,
+ 0x64, 0x35, 0x3A, 0x3A, 0x5A, 0x6A, 0x52, 0x4E, 0x6C, 0x69, 0x48, 0x53, 0x61, 0x6C, 0x49, 0x58,
+ 0x3B, 0x4D, 0x46, 0x68, 0x63, 0x39, 0x50, 0x5F, 0x5F, 0x3F, 0x6F, 0x67, 0x53, 0x41, 0x25, 0x41,
+ 0x3C, 0x51, 0x54, 0x3D, 0x5E, 0x54, 0x5D, 0x4E, 0x4C, 0x39, 0x50, 0x5F, 0x5F, 0x5F, 0x3F, 0x6F,
+ 0x47, 0x43, 0x69, 0x48, 0x33, 0x51, 0x54, 0x5D, 0x6E, 0x3C, 0x31, 0x64, 0x35, 0x5A, 0x00, 0x00 };
static guint32
get_v5key(guint32 code, int len)
{
- guint32 a1, a2, a3, a4, a5;
- guint32 check, key;
-
- a1 = code & 0x0001f000;
- a2 = code & 0x07c007c0;
- a3 = code & 0x003e0001;
- a4 = code & 0xf8000000;
- a5 = code & 0x0000083e;
-
- a1 = a1 >> 0x0c;
- a2 = a2 >> 0x01;
- a3 = a3 << 0x0a;
- a4 = a4 >> 0x10;
- a5 = a5 << 0x0f;
-
- check = a5 + a1 + a2 + a3 + a4;
- key = len * 0x68656C6C;
- key += check;
- return key;
+ guint32 a1, a2, a3, a4, a5;
+ guint32 check, key;
+
+ a1 = code & 0x0001f000;
+ a2 = code & 0x07c007c0;
+ a3 = code & 0x003e0001;
+ a4 = code & 0xf8000000;
+ a5 = code & 0x0000083e;
+
+ a1 = a1 >> 0x0c;
+ a2 = a2 >> 0x01;
+ a3 = a3 << 0x0a;
+ a4 = a4 >> 0x10;
+ a5 = a5 << 0x0f;
+
+ check = a5 + a1 + a2 + a3 + a4;
+ key = len * 0x68656C6C;
+ key += check;
+ return key;
}
static void
decrypt_v5(guchar *bfr, guint32 size,guint32 key)
{
- guint32 i;
- guint32 k;
-
- for (i=ICQ5_CL_SESSIONID; i < size; i+=4 ) {
- k = key+table_v5[i&0xff];
- if ( i != 0x16 ) {
- bfr[i] ^= (guchar)(k & 0xff);
- bfr[i+1] ^= (guchar)((k & 0xff00)>>8);
- }
- if ( i != 0x12 ) {
- bfr[i+2] ^= (guchar)((k & 0xff0000)>>16);
- bfr[i+3] ^= (guchar)((k & 0xff000000)>>24);
- }
- }
+ guint32 i;
+ guint32 k;
+
+ for (i=ICQ5_CL_SESSIONID; i < size; i+=4 ) {
+ k = key+table_v5[i&0xff];
+ if ( i != 0x16 ) {
+ bfr[i] ^= (guchar)(k & 0xff);
+ bfr[i+1] ^= (guchar)((k & 0xff00)>>8);
+ }
+ if ( i != 0x12 ) {
+ bfr[i+2] ^= (guchar)((k & 0xff0000)>>16);
+ bfr[i+3] ^= (guchar)((k & 0xff000000)>>24);
+ }
+ }
}
/*
@@ -434,238 +434,238 @@ decrypt_v5(guchar *bfr, guint32 size,guint32 key)
* length. Else, return the number of chars processed.
*/
static guint16
-proto_add_icq_attr(proto_tree* tree, /* The tree to add to */
- tvbuff_t *tvb, /* Tvbuff with packet */
- const int offset, /* Offset from the start of packet of field */
- const char* descr) /* The description to use in the tree */
+proto_add_icq_attr(proto_tree *tree, /* The tree to add to */
+ tvbuff_t *tvb, /* Tvbuff with packet */
+ const int offset, /* Offset from the start of packet of field */
+ const char *descr) /* The description to use in the tree */
{
- guint16 len;
-
- len = tvb_get_letohs(tvb, offset);
- if (len > tvb_reported_length_remaining(tvb, offset))
- return -1; /* length goes past end of packet */
- proto_tree_add_text(tree, tvb, offset, len+2,
- "%s[%u]: %.*s", descr, len, len,
- tvb_get_string_enc(wmem_packet_scope(), tvb, offset + 2, len, ENC_ASCII));
- return len + 2;
+ guint16 len;
+
+ len = tvb_get_letohs(tvb, offset);
+ if (len > tvb_reported_length_remaining(tvb, offset))
+ return -1; /* length goes past end of packet */
+ proto_tree_add_text(tree, tvb, offset, len+2,
+ "%s[%u]: %.*s", descr, len, len,
+ tvb_get_string_enc(wmem_packet_scope(), tvb, offset + 2, len, ENC_ASCII));
+ return len + 2;
}
static void
-icqv5_decode_msgType(proto_tree* tree, tvbuff_t *tvb, int offset, int size,
- packet_info *pinfo)
+icqv5_decode_msgType(proto_tree *tree, tvbuff_t *tvb, int offset, int size,
+ packet_info *pinfo)
{
- proto_item *msg_item;
- proto_tree *subtree;
- int left = size;
- guint16 msgType;
- gint sep_offset;
- int sz; /* Size of the current element */
- unsigned int n;
- static const char* url_field_descr[] = {
- "Description",
- "URL",
- };
-#define N_URL_FIELDS (sizeof url_field_descr / sizeof url_field_descr[0])
- static const char* email_field_descr[] = {
- "Nickname",
- "First name",
- "Last name",
- "Email address",
- "Unknown",
- "Text"
- };
-#define N_EMAIL_FIELDS (sizeof email_field_descr / sizeof email_field_descr[0])
- static const char* auth_req_field_descr[] = {
- "Nickname",
- "First name",
- "Last name",
- "Email address",
- "Unknown",
- "Reason"
- };
-#define N_AUTH_REQ_FIELDS (sizeof auth_req_field_descr / sizeof auth_req_field_descr[0])
- static const char* user_added_field_descr[] = {
- "Nickname",
- "First name",
- "Last name",
- "Email address",
- };
-#define N_USER_ADDED_FIELDS (sizeof user_added_field_descr / sizeof user_added_field_descr[0])
-
- msgType = tvb_get_letohs(tvb, offset);
- subtree = proto_tree_add_subtree_format(tree, tvb, offset, size, ett_icq_body_parts, NULL,
- "%s Message", val_to_str_const(msgType, msgTypeCode, "Unknown"));
-
- msg_item = proto_tree_add_item(subtree, hf_icq_msg_type, tvb, offset, 2, ENC_LITTLE_ENDIAN);
- offset += 2;
- left -= 2;
- if (msgType != MSG_AUTH) {
- /*
- * XXX - does a MSG_AUTH message really have 3 bytes of information
- * rather than a length field?
- */
- proto_tree_add_text(subtree, tvb, offset, 2, "Length: %u",
- tvb_get_letohs(tvb, offset));
- offset += 2;
- left -= 2;
- }
-
- switch(msgType) {
- case 0xffff: /* Field unknown */
- break;
- default:
- expert_add_info_format(pinfo, msg_item, &ei_icq_unknown_command,
- "Unknown msgType: %u (0x%x)", msgType, msgType);
- break;
- case MSG_TEXT:
- proto_tree_add_text(subtree, tvb, offset, left, "Msg: %.*s", left-1,
- tvb_get_string_enc(wmem_packet_scope(), tvb, offset, left, ENC_ASCII));
- break;
- case MSG_URL:
- for (n = 0; n < N_URL_FIELDS; n++) {
- if (n != N_URL_FIELDS - 1) {
- sep_offset = tvb_find_guint8(tvb, offset, left, 0xfe);
- sz = sep_offset - offset + 1;
- } else {
- sz = left;
- }
- if (sz != 0) {
- proto_tree_add_text(subtree, tvb, offset, sz, "%s: %.*s",
- url_field_descr[n],
- sz - 1,
- tvb_get_string_enc(wmem_packet_scope(), tvb, offset, sz, ENC_ASCII));
- } else {
- proto_tree_add_text(subtree, tvb, offset, 0,
- "%s: %s", url_field_descr[n], "(empty)");
- }
- offset += sz;
- left -= sz;
- }
- break;
- case MSG_EMAIL:
- for (n = 0; n < N_EMAIL_FIELDS; n++) {
- if (n != N_EMAIL_FIELDS - 1) {
- sep_offset = tvb_find_guint8(tvb, offset, left, 0xfe);
- sz = sep_offset - offset + 1;
- } else {
- sz = left;
- }
- if (sz != 0) {
- proto_tree_add_text(subtree, tvb, offset, sz, "%s: %.*s",
- email_field_descr[n],
- sz - 1,
- tvb_get_string_enc(wmem_packet_scope(), tvb, offset, sz, ENC_ASCII));
- } else {
- proto_tree_add_text(subtree, tvb, offset, 0, "%s: %s",
- email_field_descr[n], "(empty)");
- }
- offset += sz;
- left -= sz;
- }
- break;
-
- case MSG_AUTH:
- {
- /* Three bytes, first is a char signifying success */
- unsigned char auth_suc;
-
- auth_suc = tvb_get_guint8(tvb, offset);
- proto_tree_add_text(subtree, tvb, offset, 1,
- "Authorization: (%u) %s",auth_suc,
- (auth_suc==0)?"Denied":"Allowed");
- offset++;
- proto_tree_add_text(subtree, tvb, offset, 2, "x1: 0x%04x",
- tvb_get_letohs(tvb, offset));
- break;
- }
- case MSG_AUTH_REQ:
- for (n = 0; n < N_AUTH_REQ_FIELDS; n++) {
- if (n != N_AUTH_REQ_FIELDS - 1) {
- sep_offset = tvb_find_guint8(tvb, offset, left, 0xfe);
- sz = sep_offset - offset + 1;
- } else {
- sz = left;
- }
- if (sz != 0) {
- proto_tree_add_text(subtree, tvb, offset, sz, "%s: %.*s",
- auth_req_field_descr[n], sz - 1,
- tvb_get_string_enc(wmem_packet_scope(), tvb, offset, sz, ENC_ASCII));
- } else {
- proto_tree_add_text(subtree, tvb, offset, 0, "%s: %s",
- auth_req_field_descr[n], "(empty)");
- }
- offset += sz;
- left -= sz;
- }
- break;
- case MSG_USER_ADDED:
- for (n = 0; n < N_USER_ADDED_FIELDS; n++) {
- if (n != N_USER_ADDED_FIELDS - 1) {
- sep_offset = tvb_find_guint8(tvb, offset, left, 0xfe);
- sz = sep_offset - offset + 1;
- } else {
- sz = left;
- }
- if (sz != 0) {
- proto_tree_add_text(subtree, tvb, offset, sz, "%s: %.*s",
- user_added_field_descr[n], sz - 1,
- tvb_get_string_enc(wmem_packet_scope(), tvb, offset, sz, ENC_ASCII));
- } else {
- proto_tree_add_text(subtree, tvb, offset, 0, "%s: %s",
- user_added_field_descr[n], "(empty)");
- }
- offset += sz;
- left -= sz;
- }
- break;
- case MSG_CONTACTS:
- {
- gint sep_offset_prev;
- int sz_local = 0; /* Size of the current element */
- int n_local = 0; /* The nth element */
- gboolean last = FALSE;
-
- while (!last) {
- sep_offset = tvb_find_guint8(tvb, offset, left, 0xfe);
- if (sep_offset != -1) {
- sz_local = sep_offset - offset + 1;
- }
- else {
- sz_local = left;
- last = TRUE;
- }
-
- if (n_local == 0) {
- /* The first element is the number of Nick/UIN pairs follow */
- proto_tree_add_text(subtree, tvb, offset, sz_local,
- "Number of pairs: %.*s", sz_local - 1,
- tvb_get_string_enc(wmem_packet_scope(), tvb, offset, sz_local, ENC_ASCII));
- n_local++;
- } else if (!last) {
- int svsz = sz_local;
-
- left -= sz_local;
- sep_offset_prev = sep_offset;
- sep_offset = tvb_find_guint8(tvb, sep_offset_prev, left, 0xfe);
- if (sep_offset != -1)
- sz_local = sep_offset - offset + 1;
- else {
- sz_local = left;
- last = TRUE;
- }
- proto_tree_add_text(subtree, tvb, offset, sz_local + svsz,
- "%.*s: %.*s", svsz - 1,
- tvb_get_string_enc(wmem_packet_scope(), tvb, offset, svsz, ENC_ASCII), sz_local - 1,
- tvb_get_string_enc(wmem_packet_scope(), tvb, sep_offset_prev + 1, sz_local, ENC_ASCII));
- n_local += 2;
- }
-
- left -= (sz_local+1);
- offset = sep_offset + 1;
- }
- break;
- }
- }
+ proto_item *msg_item;
+ proto_tree *subtree;
+ int left = size;
+ guint16 msgType;
+ gint sep_offset;
+ int sz; /* Size of the current element */
+ unsigned int n;
+ static const char *url_field_descr[] = {
+ "Description",
+ "URL",
+ };
+#define N_URL_FIELDS (sizeof url_field_descr / sizeof url_field_descr[0])
+ static const char *email_field_descr[] = {
+ "Nickname",
+ "First name",
+ "Last name",
+ "Email address",
+ "Unknown",
+ "Text"
+ };
+#define N_EMAIL_FIELDS (sizeof email_field_descr / sizeof email_field_descr[0])
+ static const char *auth_req_field_descr[] = {
+ "Nickname",
+ "First name",
+ "Last name",
+ "Email address",
+ "Unknown",
+ "Reason"
+ };
+#define N_AUTH_REQ_FIELDS (sizeof auth_req_field_descr / sizeof auth_req_field_descr[0])
+ static const char *user_added_field_descr[] = {
+ "Nickname",
+ "First name",
+ "Last name",
+ "Email address",
+ };
+#define N_USER_ADDED_FIELDS (sizeof user_added_field_descr / sizeof user_added_field_descr[0])
+
+ msgType = tvb_get_letohs(tvb, offset);
+ subtree = proto_tree_add_subtree_format(tree, tvb, offset, size, ett_icq_body_parts, NULL,
+ "%s Message", val_to_str_const(msgType, msgTypeCode, "Unknown"));
+
+ msg_item = proto_tree_add_item(subtree, hf_icq_msg_type, tvb, offset, 2, ENC_LITTLE_ENDIAN);
+ offset += 2;
+ left -= 2;
+ if (msgType != MSG_AUTH) {
+ /*
+ * XXX - does a MSG_AUTH message really have 3 bytes of information
+ * rather than a length field?
+ */
+ proto_tree_add_text(subtree, tvb, offset, 2, "Length: %u",
+ tvb_get_letohs(tvb, offset));
+ offset += 2;
+ left -= 2;
+ }
+
+ switch(msgType) {
+ case 0xffff: /* Field unknown */
+ break;
+ default:
+ expert_add_info_format(pinfo, msg_item, &ei_icq_unknown_command,
+ "Unknown msgType: %u (0x%x)", msgType, msgType);
+ break;
+ case MSG_TEXT:
+ proto_tree_add_text(subtree, tvb, offset, left, "Msg: %.*s", left-1,
+ tvb_get_string_enc(wmem_packet_scope(), tvb, offset, left, ENC_ASCII));
+ break;
+ case MSG_URL:
+ for (n = 0; n < N_URL_FIELDS; n++) {
+ if (n != N_URL_FIELDS - 1) {
+ sep_offset = tvb_find_guint8(tvb, offset, left, 0xfe);
+ sz = sep_offset - offset + 1;
+ } else {
+ sz = left;
+ }
+ if (sz != 0) {
+ proto_tree_add_text(subtree, tvb, offset, sz, "%s: %.*s",
+ url_field_descr[n],
+ sz - 1,
+ tvb_get_string_enc(wmem_packet_scope(), tvb, offset, sz, ENC_ASCII));
+ } else {
+ proto_tree_add_text(subtree, tvb, offset, 0,
+ "%s: %s", url_field_descr[n], "(empty)");
+ }
+ offset += sz;
+ left -= sz;
+ }
+ break;
+ case MSG_EMAIL:
+ for (n = 0; n < N_EMAIL_FIELDS; n++) {
+ if (n != N_EMAIL_FIELDS - 1) {
+ sep_offset = tvb_find_guint8(tvb, offset, left, 0xfe);
+ sz = sep_offset - offset + 1;
+ } else {
+ sz = left;
+ }
+ if (sz != 0) {
+ proto_tree_add_text(subtree, tvb, offset, sz, "%s: %.*s",
+ email_field_descr[n],
+ sz - 1,
+ tvb_get_string_enc(wmem_packet_scope(), tvb, offset, sz, ENC_ASCII));
+ } else {
+ proto_tree_add_text(subtree, tvb, offset, 0, "%s: %s",
+ email_field_descr[n], "(empty)");
+ }
+ offset += sz;
+ left -= sz;
+ }
+ break;
+
+ case MSG_AUTH:
+ {
+ /* Three bytes, first is a char signifying success */
+ unsigned char auth_suc;
+
+ auth_suc = tvb_get_guint8(tvb, offset);
+ proto_tree_add_text(subtree, tvb, offset, 1,
+ "Authorization: (%u) %s",auth_suc,
+ (auth_suc==0)?"Denied":"Allowed");
+ offset++;
+ proto_tree_add_text(subtree, tvb, offset, 2, "x1: 0x%04x",
+ tvb_get_letohs(tvb, offset));
+ break;
+ }
+ case MSG_AUTH_REQ:
+ for (n = 0; n < N_AUTH_REQ_FIELDS; n++) {
+ if (n != N_AUTH_REQ_FIELDS - 1) {
+ sep_offset = tvb_find_guint8(tvb, offset, left, 0xfe);
+ sz = sep_offset - offset + 1;
+ } else {
+ sz = left;
+ }
+ if (sz != 0) {
+ proto_tree_add_text(subtree, tvb, offset, sz, "%s: %.*s",
+ auth_req_field_descr[n], sz - 1,
+ tvb_get_string_enc(wmem_packet_scope(), tvb, offset, sz, ENC_ASCII));
+ } else {
+ proto_tree_add_text(subtree, tvb, offset, 0, "%s: %s",
+ auth_req_field_descr[n], "(empty)");
+ }
+ offset += sz;
+ left -= sz;
+ }
+ break;
+ case MSG_USER_ADDED:
+ for (n = 0; n < N_USER_ADDED_FIELDS; n++) {
+ if (n != N_USER_ADDED_FIELDS - 1) {
+ sep_offset = tvb_find_guint8(tvb, offset, left, 0xfe);
+ sz = sep_offset - offset + 1;
+ } else {
+ sz = left;
+ }
+ if (sz != 0) {
+ proto_tree_add_text(subtree, tvb, offset, sz, "%s: %.*s",
+ user_added_field_descr[n], sz - 1,
+ tvb_get_string_enc(wmem_packet_scope(), tvb, offset, sz, ENC_ASCII));
+ } else {
+ proto_tree_add_text(subtree, tvb, offset, 0, "%s: %s",
+ user_added_field_descr[n], "(empty)");
+ }
+ offset += sz;
+ left -= sz;
+ }
+ break;
+ case MSG_CONTACTS:
+ {
+ gint sep_offset_prev;
+ int sz_local = 0; /* Size of the current element */
+ int n_local = 0; /* The nth element */
+ gboolean last = FALSE;
+
+ while (!last) {
+ sep_offset = tvb_find_guint8(tvb, offset, left, 0xfe);
+ if (sep_offset != -1) {
+ sz_local = sep_offset - offset + 1;
+ }
+ else {
+ sz_local = left;
+ last = TRUE;
+ }
+
+ if (n_local == 0) {
+ /* The first element is the number of Nick/UIN pairs follow */
+ proto_tree_add_text(subtree, tvb, offset, sz_local,
+ "Number of pairs: %.*s", sz_local - 1,
+ tvb_get_string_enc(wmem_packet_scope(), tvb, offset, sz_local, ENC_ASCII));
+ n_local++;
+ } else if (!last) {
+ int svsz = sz_local;
+
+ left -= sz_local;
+ sep_offset_prev = sep_offset;
+ sep_offset = tvb_find_guint8(tvb, sep_offset_prev, left, 0xfe);
+ if (sep_offset != -1)
+ sz_local = sep_offset - offset + 1;
+ else {
+ sz_local = left;
+ last = TRUE;
+ }
+ proto_tree_add_text(subtree, tvb, offset, sz_local + svsz,
+ "%.*s: %.*s", svsz - 1,
+ tvb_get_string_enc(wmem_packet_scope(), tvb, offset, svsz, ENC_ASCII), sz_local - 1,
+ tvb_get_string_enc(wmem_packet_scope(), tvb, sep_offset_prev + 1, sz_local, ENC_ASCII));
+ n_local += 2;
+ }
+
+ left -= (sz_local+1);
+ offset = sep_offset + 1;
+ }
+ break;
+ }
+ }
}
/*********************************
@@ -674,95 +674,95 @@ icqv5_decode_msgType(proto_tree* tree, tvbuff_t *tvb, int offset, int size,
*
*********************************/
static void
-icqv5_cmd_send_text_code(proto_tree* tree, /* Tree to put the data in */
- tvbuff_t *tvb, /* Decrypted packet content */
- int offset) /* Offset from the start of the packet to the content */
+icqv5_cmd_send_text_code(proto_tree *tree, /* Tree to put the data in */
+ tvbuff_t *tvb, /* Decrypted packet content */
+ int offset) /* Offset from the start of the packet to the content */
{
- proto_tree* subtree = tree;
- guint16 len;
- guint16 x1;
-
- len = tvb_get_letohs(tvb, offset+CMD_SEND_TEXT_CODE_LEN);
- proto_tree_add_text(subtree, tvb, offset + CMD_SEND_TEXT_CODE_LEN,
- 2, "Length: %d", len);
-
- if (len>0) {
- proto_tree_add_text(subtree, tvb, offset + CMD_SEND_TEXT_CODE_TEXT,
- len, "Text: %.*s", len,
- tvb_get_string_enc(wmem_packet_scope(), tvb, offset + CMD_SEND_TEXT_CODE_TEXT,
- len, ENC_ASCII));
- }
-
- x1 = tvb_get_letohs(tvb, offset + CMD_SEND_TEXT_CODE_TEXT + len);
- proto_tree_add_text(subtree, tvb,
- offset + CMD_SEND_TEXT_CODE_TEXT + len,
- 2, "X1: 0x%04x", x1);
+ proto_tree *subtree = tree;
+ guint16 len;
+ guint16 x1;
+
+ len = tvb_get_letohs(tvb, offset+CMD_SEND_TEXT_CODE_LEN);
+ proto_tree_add_text(subtree, tvb, offset + CMD_SEND_TEXT_CODE_LEN,
+ 2, "Length: %d", len);
+
+ if (len>0) {
+ proto_tree_add_text(subtree, tvb, offset + CMD_SEND_TEXT_CODE_TEXT,
+ len, "Text: %.*s", len,
+ tvb_get_string_enc(wmem_packet_scope(), tvb, offset + CMD_SEND_TEXT_CODE_TEXT,
+ len, ENC_ASCII));
+ }
+
+ x1 = tvb_get_letohs(tvb, offset + CMD_SEND_TEXT_CODE_TEXT + len);
+ proto_tree_add_text(subtree, tvb,
+ offset + CMD_SEND_TEXT_CODE_TEXT + len,
+ 2, "X1: 0x%04x", x1);
}
static void
-icqv5_cmd_send_msg(proto_tree* tree, tvbuff_t *tvb, int offset, int size,
- packet_info *pinfo)
+icqv5_cmd_send_msg(proto_tree *tree, tvbuff_t *tvb, int offset, int size,
+ packet_info *pinfo)
{
- proto_tree_add_text(tree, tvb, offset + CMD_SEND_MSG_RECV_UIN, 4,
- "Receiver UIN: %u",
- tvb_get_letohl(tvb, offset + CMD_SEND_MSG_RECV_UIN));
- size -= 4;
+ proto_tree_add_text(tree, tvb, offset + CMD_SEND_MSG_RECV_UIN, 4,
+ "Receiver UIN: %u",
+ tvb_get_letohl(tvb, offset + CMD_SEND_MSG_RECV_UIN));
+ size -= 4;
- icqv5_decode_msgType(tree, tvb, offset + CMD_SEND_MSG_MSG_TYPE,
- size, pinfo);
+ icqv5_decode_msgType(tree, tvb, offset + CMD_SEND_MSG_MSG_TYPE,
+ size, pinfo);
}
static void
-icqv5_cmd_login(proto_tree* tree, tvbuff_t *tvb, int offset)
+icqv5_cmd_login(proto_tree *tree, tvbuff_t *tvb, int offset)
{
- proto_tree* subtree = tree;
- time_t theTime;
- char *aTime;
- guint32 port;
- guint32 passwdLen;
-
- if (tree) {
- theTime = tvb_get_letohl(tvb, offset + CMD_LOGIN_TIME);
- aTime = abs_time_secs_to_str(wmem_packet_scope(), theTime, ABSOLUTE_TIME_LOCAL, TRUE);
- proto_tree_add_text(subtree, tvb, offset + CMD_LOGIN_TIME, 4,
- "Time: %ld = %s", (long)theTime, aTime);
- port = tvb_get_letohl(tvb, offset + CMD_LOGIN_PORT);
- proto_tree_add_text(subtree, tvb, offset + CMD_LOGIN_PORT, 4,
- "Port: %u", port);
- passwdLen = tvb_get_letohs(tvb, offset + CMD_LOGIN_PASSLEN);
- proto_tree_add_text(subtree, tvb, offset + CMD_LOGIN_PASSLEN,
- 2 + passwdLen, "Passwd: %.*s", (int)passwdLen,
- tvb_get_string_enc(wmem_packet_scope(), tvb, offset + CMD_LOGIN_PASSWD,
- passwdLen, ENC_ASCII));
- proto_tree_add_text(subtree, tvb,
- offset + CMD_LOGIN_PASSWD + passwdLen + CMD_LOGIN_IP,
- 4, "IP: %s", tvb_ip_to_str(tvb, offset + CMD_LOGIN_PASSWD + passwdLen + CMD_LOGIN_IP));
- proto_tree_add_item(subtree, hf_icq_status, tvb, offset + CMD_LOGIN_PASSWD + passwdLen + CMD_LOGIN_STATUS, 4, ENC_LITTLE_ENDIAN);
- }
+ proto_tree *subtree = tree;
+ time_t theTime;
+ char *aTime;
+ guint32 port;
+ guint32 passwdLen;
+
+ if (tree) {
+ theTime = tvb_get_letohl(tvb, offset + CMD_LOGIN_TIME);
+ aTime = abs_time_secs_to_str(wmem_packet_scope(), theTime, ABSOLUTE_TIME_LOCAL, TRUE);
+ proto_tree_add_text(subtree, tvb, offset + CMD_LOGIN_TIME, 4,
+ "Time: %ld = %s", (long)theTime, aTime);
+ port = tvb_get_letohl(tvb, offset + CMD_LOGIN_PORT);
+ proto_tree_add_text(subtree, tvb, offset + CMD_LOGIN_PORT, 4,
+ "Port: %u", port);
+ passwdLen = tvb_get_letohs(tvb, offset + CMD_LOGIN_PASSLEN);
+ proto_tree_add_text(subtree, tvb, offset + CMD_LOGIN_PASSLEN,
+ 2 + passwdLen, "Passwd: %.*s", (int)passwdLen,
+ tvb_get_string_enc(wmem_packet_scope(), tvb, offset + CMD_LOGIN_PASSWD,
+ passwdLen, ENC_ASCII));
+ proto_tree_add_text(subtree, tvb,
+ offset + CMD_LOGIN_PASSWD + passwdLen + CMD_LOGIN_IP,
+ 4, "IP: %s", tvb_ip_to_str(tvb, offset + CMD_LOGIN_PASSWD + passwdLen + CMD_LOGIN_IP));
+ proto_tree_add_item(subtree, hf_icq_status, tvb, offset + CMD_LOGIN_PASSWD + passwdLen + CMD_LOGIN_STATUS, 4, ENC_LITTLE_ENDIAN);
+ }
}
static void
-icqv5_cmd_contact_list(proto_tree* tree, tvbuff_t *tvb, int offset)
+icqv5_cmd_contact_list(proto_tree *tree, tvbuff_t *tvb, int offset)
{
- unsigned char num;
- int i;
- guint32 uin;
-
- if (tree) {
- num = tvb_get_guint8(tvb, offset + CMD_CONTACT_LIST_NUM);
- proto_tree_add_text(tree, tvb, offset + CMD_CONTACT_LIST,
- 1, "Number of uins: %u", num);
- /*
- * A sequence of num times UIN follows
- */
- offset += (CMD_CONTACT_LIST_NUM + 1);
- for (i = 0; i < num; i++) {
- uin = tvb_get_letohl(tvb, offset);
- proto_tree_add_text(tree, tvb, offset, 4,
- "UIN[%d]: %u", i ,uin);
- offset += 4;
- }
- }
+ unsigned char num;
+ int i;
+ guint32 uin;
+
+ if (tree) {
+ num = tvb_get_guint8(tvb, offset + CMD_CONTACT_LIST_NUM);
+ proto_tree_add_text(tree, tvb, offset + CMD_CONTACT_LIST,
+ 1, "Number of uins: %u", num);
+ /*
+ * A sequence of num times UIN follows
+ */
+ offset += (CMD_CONTACT_LIST_NUM + 1);
+ for (i = 0; i < num; i++) {
+ uin = tvb_get_letohl(tvb, offset);
+ proto_tree_add_text(tree, tvb, offset, 4,
+ "UIN[%d]: %u", i ,uin);
+ offset += 4;
+ }
+ }
}
/**********************
@@ -772,306 +772,306 @@ icqv5_cmd_contact_list(proto_tree* tree, tvbuff_t *tvb, int offset)
**********************
*/
static void
-icqv5_srv_user_online(proto_tree* tree,/* Tree to put the data in */
- tvbuff_t *tvb, /* Tvbuff with packet */
- int offset) /* Offset from the start of the packet to the content */
+icqv5_srv_user_online(proto_tree *tree,/* Tree to put the data in */
+ tvbuff_t *tvb, /* Tvbuff with packet */
+ int offset) /* Offset from the start of the packet to the content */
{
- proto_tree* subtree = tree;
-
- if (tree) {
- proto_tree_add_text(subtree, tvb, offset + SRV_USER_ONL_UIN, 4,
- "UIN: %u",
- tvb_get_letohl(tvb, offset + SRV_USER_ONL_UIN));
- proto_tree_add_text(subtree, tvb, offset + SRV_USER_ONL_IP, 4,
- "IP: %s", tvb_ip_to_str(tvb, offset + SRV_USER_ONL_IP));
- proto_tree_add_text(subtree, tvb, offset + SRV_USER_ONL_PORT, 4,
- "Port: %u",
- tvb_get_letohl(tvb, offset + SRV_USER_ONL_PORT));
- proto_tree_add_text(subtree, tvb, offset + SRV_USER_ONL_REALIP, 4,
- "RealIP: %s", tvb_ip_to_str(tvb, offset + SRV_USER_ONL_REALIP));
- proto_tree_add_item(subtree, hf_icq_status, tvb, offset + SRV_USER_ONL_STATUS, 2, ENC_LITTLE_ENDIAN);
- /*
- * Kojak: Hypothesis is that this field might be an encoding for the
- * version used by the UIN that changed. To test this, I included
- * this line to the code.
- */
- proto_tree_add_text(subtree, tvb, offset + SRV_USER_ONL_X2, 4,
- "Version: %08x",
- tvb_get_letohl(tvb, offset + SRV_USER_ONL_X2));
- }
+ proto_tree *subtree = tree;
+
+ if (tree) {
+ proto_tree_add_text(subtree, tvb, offset + SRV_USER_ONL_UIN, 4,
+ "UIN: %u",
+ tvb_get_letohl(tvb, offset + SRV_USER_ONL_UIN));
+ proto_tree_add_text(subtree, tvb, offset + SRV_USER_ONL_IP, 4,
+ "IP: %s", tvb_ip_to_str(tvb, offset + SRV_USER_ONL_IP));
+ proto_tree_add_text(subtree, tvb, offset + SRV_USER_ONL_PORT, 4,
+ "Port: %u",
+ tvb_get_letohl(tvb, offset + SRV_USER_ONL_PORT));
+ proto_tree_add_text(subtree, tvb, offset + SRV_USER_ONL_REALIP, 4,
+ "RealIP: %s", tvb_ip_to_str(tvb, offset + SRV_USER_ONL_REALIP));
+ proto_tree_add_item(subtree, hf_icq_status, tvb, offset + SRV_USER_ONL_STATUS, 2, ENC_LITTLE_ENDIAN);
+ /*
+ * Kojak: Hypothesis is that this field might be an encoding for the
+ * version used by the UIN that changed. To test this, I included
+ * this line to the code.
+ */
+ proto_tree_add_text(subtree, tvb, offset + SRV_USER_ONL_X2, 4,
+ "Version: %08x",
+ tvb_get_letohl(tvb, offset + SRV_USER_ONL_X2));
+ }
}
static void
-icqv5_srv_multi(proto_tree* tree, /* Tree to put the data in */
- tvbuff_t *tvb, /* Packet content */
- int offset, /* Offset from the start of the packet to the content */
- packet_info* pinfo)
+icqv5_srv_multi(proto_tree *tree, /* Tree to put the data in */
+ tvbuff_t *tvb, /* Packet content */
+ int offset, /* Offset from the start of the packet to the content */
+ packet_info *pinfo)
{
- guint8 num;
- guint16 pktSz;
- int i;
-
- num = tvb_get_guint8(tvb, offset + SRV_MULTI_NUM);
- proto_tree_add_text(tree, tvb, offset + SRV_MULTI_NUM, 1,
- "Number of pkts: %u", num);
- /*
- * A sequence of num times ( pktsize, packetData) follows
- */
- offset += (SRV_MULTI_NUM + 1);
- for (i = 0; i < num; i++) {
- pktSz = tvb_get_letohs(tvb, offset);
- offset += 2;
- dissect_icqv5Server(tvb, offset, pinfo, tree, pktSz);
- offset += pktSz;
- }
+ guint8 num;
+ guint16 pktSz;
+ int i;
+
+ num = tvb_get_guint8(tvb, offset + SRV_MULTI_NUM);
+ proto_tree_add_text(tree, tvb, offset + SRV_MULTI_NUM, 1,
+ "Number of pkts: %u", num);
+ /*
+ * A sequence of num times ( pktsize, packetData) follows
+ */
+ offset += (SRV_MULTI_NUM + 1);
+ for (i = 0; i < num; i++) {
+ pktSz = tvb_get_letohs(tvb, offset);
+ offset += 2;
+ dissect_icqv5Server(tvb, offset, pinfo, tree, pktSz);
+ offset += pktSz;
+ }
}
static void
-icqv5_srv_meta_user(proto_tree* tree, /* Tree to put the data in */
- tvbuff_t *tvb, /* Tvbuff with packet */
- int offset, /* Offset from the start of the packet to the content */
- int size _U_, /* Number of chars left to do */
- packet_info *pinfo)
+icqv5_srv_meta_user(proto_tree *tree, /* Tree to put the data in */
+ tvbuff_t *tvb, /* Tvbuff with packet */
+ int offset, /* Offset from the start of the packet to the content */
+ int size _U_, /* Number of chars left to do */
+ packet_info *pinfo)
{
- proto_tree* sstree;
- proto_item* ti;
- guint16 subcmd;
- unsigned char result;
-
- subcmd = tvb_get_letohs(tvb, offset + SRV_META_USER_SUBCMD);
- ti = proto_tree_add_item(tree, hf_icq_meta_user_subcmd, tvb, offset + SRV_META_USER_SUBCMD, 2, ENC_LITTLE_ENDIAN);
- sstree = proto_item_add_subtree(ti, ett_icq_body_parts);
- result = tvb_get_guint8(tvb, offset + SRV_META_USER_RESULT);
- proto_tree_add_text(sstree, tvb, offset + SRV_META_USER_RESULT,
- 1, "%s", (result==0x0a)?"Success":"Failure");
-
- /* Skip the META_USER header */
- offset += 3;
-
- switch(subcmd) {
- case META_EX_USER_FOUND:
- {
- /* This is almost the same as META_USER_FOUND,
- * however, there's an extra length field
- */
- guint16 pktLen;
-
- /* Read the length field */
- pktLen = tvb_get_letohs(tvb, offset);
- proto_tree_add_text(sstree, tvb, offset, 2,
- "Length: %u", pktLen);
-
- offset += 2;
- }
- /* FALLTHRU */
- case META_USER_FOUND:
- {
- /* The goto mentioned in this block should be local to this
- * block if C'd allow it.
- *
- * They are used to "implement" a poorman's exception handling
- */
- int len = 0;
- static const char *descr[] = {
- "Nick",
- "First name",
- "Last name",
- "Email",
- NULL
- };
- const char** d = descr;
- unsigned char auth;
- /*
- * Read UIN
- */
- proto_tree_add_text(sstree, tvb, offset, 4,
- "UIN: %u", tvb_get_letohl(tvb, offset));
- offset+=4;
-
- for ( ; *d!=NULL; d++) {
- len = proto_add_icq_attr(sstree, tvb, offset, *d);
- if (len == -1)
- return;
- offset += len;
- }
- /* Get the authorize setting */
- auth = tvb_get_guint8(tvb, offset);
- proto_tree_add_text(sstree, tvb, offset, 1,
- "authorization: %s", (auth==0x01)?"Necessary":"Who needs it");
- offset++;
- /* Get x2 */
- proto_tree_add_text(sstree, tvb, offset, 2,
- "x2: 0x%04x", tvb_get_letohs(tvb, offset));
- offset+=2;
- /* Get x3 */
- proto_tree_add_text(sstree, tvb, offset, 4,
- "x3: 0x%08x", tvb_get_letohl(tvb, offset));
- break;
- }
- case META_ABOUT:
- {
- int len;
-
- /* Get the about information */
- len = tvb_get_letohs(tvb, offset);
- offset+=2;
- proto_tree_add_text(sstree, tvb, offset - 2,
- len+2, "About(%d): %.*s", len,
- len, tvb_get_string_enc(wmem_packet_scope(), tvb, offset, len, ENC_ASCII));
- break;
- }
- case META_USER_INFO:
- {
- /* The goto mentioned in this block should be local to this
- * block if C'd allow it.
- *
- * They are used to "implement" a poorman's exception handling
- */
- static const char* descr[] = {
- "Nick",
- "First name",
- "Last name",
- "Primary email",
- "Secondary email",
- "Old email",
- "City",
- "State",
- "Phone",
- "Fax",
- "Street",
- "Cellphone",
- "Zip",
- NULL
- };
- const char** d = descr;
- guint16 country;
- guint8 user_timezone;
- guint8 auth;
- int len = 0;
+ proto_tree *sstree;
+ proto_item *ti;
+ guint16 subcmd;
+ unsigned char result;
+
+ subcmd = tvb_get_letohs(tvb, offset + SRV_META_USER_SUBCMD);
+ ti = proto_tree_add_item(tree, hf_icq_meta_user_subcmd, tvb, offset + SRV_META_USER_SUBCMD, 2, ENC_LITTLE_ENDIAN);
+ sstree = proto_item_add_subtree(ti, ett_icq_body_parts);
+ result = tvb_get_guint8(tvb, offset + SRV_META_USER_RESULT);
+ proto_tree_add_text(sstree, tvb, offset + SRV_META_USER_RESULT,
+ 1, "%s", (result==0x0a)?"Success":"Failure");
+
+ /* Skip the META_USER header */
+ offset += 3;
+
+ switch(subcmd) {
+ case META_EX_USER_FOUND:
+ {
+ /* This is almost the same as META_USER_FOUND,
+ * however, there's an extra length field
+ */
+ guint16 pktLen;
+
+ /* Read the length field */
+ pktLen = tvb_get_letohs(tvb, offset);
+ proto_tree_add_text(sstree, tvb, offset, 2,
+ "Length: %u", pktLen);
+
+ offset += 2;
+ }
+ /* FALLTHRU */
+ case META_USER_FOUND:
+ {
+ /* The goto mentioned in this block should be local to this
+ * block if C'd allow it.
+ *
+ * They are used to "implement" a poorman's exception handling
+ */
+ int len = 0;
+ static const char *descr[] = {
+ "Nick",
+ "First name",
+ "Last name",
+ "Email",
+ NULL
+ };
+ const char **d = descr;
+ unsigned char auth;
+ /*
+ * Read UIN
+ */
+ proto_tree_add_text(sstree, tvb, offset, 4,
+ "UIN: %u", tvb_get_letohl(tvb, offset));
+ offset+=4;
+
+ for ( ; *d!=NULL; d++) {
+ len = proto_add_icq_attr(sstree, tvb, offset, *d);
+ if (len == -1)
+ return;
+ offset += len;
+ }
+ /* Get the authorize setting */
+ auth = tvb_get_guint8(tvb, offset);
+ proto_tree_add_text(sstree, tvb, offset, 1,
+ "authorization: %s", (auth==0x01)?"Necessary":"Who needs it");
+ offset++;
+ /* Get x2 */
+ proto_tree_add_text(sstree, tvb, offset, 2,
+ "x2: 0x%04x", tvb_get_letohs(tvb, offset));
+ offset+=2;
+ /* Get x3 */
+ proto_tree_add_text(sstree, tvb, offset, 4,
+ "x3: 0x%08x", tvb_get_letohl(tvb, offset));
+ break;
+ }
+ case META_ABOUT:
+ {
+ int len;
+
+ /* Get the about information */
+ len = tvb_get_letohs(tvb, offset);
+ offset+=2;
+ proto_tree_add_text(sstree, tvb, offset - 2,
+ len+2, "About(%d): %.*s", len,
+ len, tvb_get_string_enc(wmem_packet_scope(), tvb, offset, len, ENC_ASCII));
+ break;
+ }
+ case META_USER_INFO:
+ {
+ /* The goto mentioned in this block should be local to this
+ * block if C'd allow it.
+ *
+ * They are used to "implement" a poorman's exception handling
+ */
+ static const char *descr[] = {
+ "Nick",
+ "First name",
+ "Last name",
+ "Primary email",
+ "Secondary email",
+ "Old email",
+ "City",
+ "State",
+ "Phone",
+ "Fax",
+ "Street",
+ "Cellphone",
+ "Zip",
+ NULL
+ };
+ const char **d = descr;
+ guint16 country;
+ guint8 user_timezone;
+ guint8 auth;
+ int len = 0;
#if 0
- /* Get the uin */
- uin = tvb_get_letohl(tvb, offset);
- proto_tree_add_text(sstree, tvb, offset, 4, "UIN: %u", uin);
- offset+=4;
+ /* Get the uin */
+ uin = tvb_get_letohl(tvb, offset);
+ proto_tree_add_text(sstree, tvb, offset, 4, "UIN: %u", uin);
+ offset+=4;
#endif
- /*
- * Get every field from the description
- */
- for ( ; *d!=NULL; d++) {
- len = proto_add_icq_attr(sstree, tvb, offset, *d);
- if (len < 0) {
- offset+=2;
- continue;
- }
- offset+=len;
- }
- /* Get country code */
- country = tvb_get_letohs(tvb, offset);
- proto_tree_add_text(sstree, tvb, offset, 2,
- "Countrycode: %u", country);
- offset+=2;
- /* Get the timezone setting */
- user_timezone = tvb_get_guint8(tvb, offset);
- proto_tree_add_text(sstree, tvb, offset, 1,
- "Timezone: %u", user_timezone);
- offset++;
- /* Get the authorize setting */
- auth = tvb_get_guint8(tvb, offset);
- proto_tree_add_text(sstree, tvb, offset, 1,
- "Authorization: (%u) %s", auth,
- (auth==0)?"No":"Yes");
- offset++;
- /* Get the webaware setting */
- auth = tvb_get_guint8(tvb, offset);
- proto_tree_add_text(sstree, tvb, offset, 1,
- "Webaware: (%u) %s", auth,
- (auth==0)?"No":"Yes");
- offset++;
- /* Get the authorize setting */
- auth = tvb_get_guint8(tvb, offset);
- proto_tree_add_text(sstree, tvb, offset, 1,
- "HideIP: (%u) %s", auth, (auth==0)?"No":"Yes");
- break;
- }
- default:
- /* This information is already printed in the tree */
- expert_add_info_format(pinfo, ti, &ei_icq_unknown_meta_subcmd,
- "Unknown Meta subcmd: 0x%x", subcmd);
- break;
- }
+ /*
+ * Get every field from the description
+ */
+ for ( ; *d!=NULL; d++) {
+ len = proto_add_icq_attr(sstree, tvb, offset, *d);
+ if (len < 0) {
+ offset+=2;
+ continue;
+ }
+ offset+=len;
+ }
+ /* Get country code */
+ country = tvb_get_letohs(tvb, offset);
+ proto_tree_add_text(sstree, tvb, offset, 2,
+ "Countrycode: %u", country);
+ offset+=2;
+ /* Get the timezone setting */
+ user_timezone = tvb_get_guint8(tvb, offset);
+ proto_tree_add_text(sstree, tvb, offset, 1,
+ "Timezone: %u", user_timezone);
+ offset++;
+ /* Get the authorize setting */
+ auth = tvb_get_guint8(tvb, offset);
+ proto_tree_add_text(sstree, tvb, offset, 1,
+ "Authorization: (%u) %s", auth,
+ (auth==0)?"No":"Yes");
+ offset++;
+ /* Get the webaware setting */
+ auth = tvb_get_guint8(tvb, offset);
+ proto_tree_add_text(sstree, tvb, offset, 1,
+ "Webaware: (%u) %s", auth,
+ (auth==0)?"No":"Yes");
+ offset++;
+ /* Get the authorize setting */
+ auth = tvb_get_guint8(tvb, offset);
+ proto_tree_add_text(sstree, tvb, offset, 1,
+ "HideIP: (%u) %s", auth, (auth==0)?"No":"Yes");
+ break;
+ }
+ default:
+ /* This information is already printed in the tree */
+ expert_add_info_format(pinfo, ti, &ei_icq_unknown_meta_subcmd,
+ "Unknown Meta subcmd: 0x%x", subcmd);
+ break;
+ }
}
static void
-icqv5_srv_recv_message(proto_tree* tree, /* Tree to put the data in */
- tvbuff_t* tvb, /* Packet content */
- int offset, /* Offset from the start of the packet to the content */
- int size, /* Number of chars left to do */
- packet_info *pinfo)
+icqv5_srv_recv_message(proto_tree *tree, /* Tree to put the data in */
+ tvbuff_t *tvb, /* Packet content */
+ int offset, /* Offset from the start of the packet to the content */
+ int size, /* Number of chars left to do */
+ packet_info *pinfo)
{
- guint16 year;
- guint8 month;
- guint8 day;
- guint8 hour;
- guint8 minute;
-
- proto_tree_add_item(tree, hf_icq_uin, tvb, offset + SRV_RECV_MSG_UIN,
- 4, ENC_LITTLE_ENDIAN);
- year = tvb_get_letohs(tvb, offset + SRV_RECV_MSG_YEAR);
- month = tvb_get_guint8(tvb, offset + SRV_RECV_MSG_MONTH);
- day = tvb_get_guint8(tvb, offset + SRV_RECV_MSG_DAY);
- hour = tvb_get_guint8(tvb, offset + SRV_RECV_MSG_HOUR);
- minute = tvb_get_guint8(tvb, offset + SRV_RECV_MSG_MINUTE);
-
- proto_tree_add_text(tree, tvb, offset + SRV_RECV_MSG_YEAR,
- 2 + 4,
- "Time: %u-%u-%u %02u:%02u",
- day, month, year, hour, minute);
- icqv5_decode_msgType(tree, tvb, offset + SRV_RECV_MSG_MSG_TYPE,
- size-10, pinfo);
+ guint16 year;
+ guint8 month;
+ guint8 day;
+ guint8 hour;
+ guint8 minute;
+
+ proto_tree_add_item(tree, hf_icq_uin, tvb, offset + SRV_RECV_MSG_UIN,
+ 4, ENC_LITTLE_ENDIAN);
+ year = tvb_get_letohs(tvb, offset + SRV_RECV_MSG_YEAR);
+ month = tvb_get_guint8(tvb, offset + SRV_RECV_MSG_MONTH);
+ day = tvb_get_guint8(tvb, offset + SRV_RECV_MSG_DAY);
+ hour = tvb_get_guint8(tvb, offset + SRV_RECV_MSG_HOUR);
+ minute = tvb_get_guint8(tvb, offset + SRV_RECV_MSG_MINUTE);
+
+ proto_tree_add_text(tree, tvb, offset + SRV_RECV_MSG_YEAR,
+ 2 + 4,
+ "Time: %u-%u-%u %02u:%02u",
+ day, month, year, hour, minute);
+ icqv5_decode_msgType(tree, tvb, offset + SRV_RECV_MSG_MSG_TYPE,
+ size-10, pinfo);
}
static void
-icqv5_srv_rand_user(proto_tree* tree, /* Tree to put the data in */
- tvbuff_t *tvb, /* Tvbuff with packet */
- int offset) /* Offset from the start of the packet to the content */
+icqv5_srv_rand_user(proto_tree *tree, /* Tree to put the data in */
+ tvbuff_t *tvb, /* Tvbuff with packet */
+ int offset) /* Offset from the start of the packet to the content */
{
- proto_tree* subtree = tree;
- guint32 uin;
- guint32 port;
- guint8 commClass;
- guint16 tcpVer;
-
- if (tree) {
- /* guint32 UIN */
- uin = tvb_get_letohl(tvb, offset + SRV_RAND_USER_UIN);
- proto_tree_add_text(subtree, tvb, offset + SRV_RAND_USER_UIN,
- 4, "UIN: %u", uin);
- /* guint32 IP */
- proto_tree_add_text(subtree, tvb, offset + SRV_RAND_USER_IP,
- 4, "IP: %s", tvb_ip_to_str(tvb, offset + SRV_RAND_USER_IP));
- /* guint16 portNum */
- /* XXX - 16 bits, or 32 bits? */
- port = tvb_get_letohs(tvb, offset + SRV_RAND_USER_PORT);
- proto_tree_add_text(subtree, tvb, offset + SRV_RAND_USER_UIN,
- 4, "Port: %u", port);
- /* guint32 realIP */
- proto_tree_add_text(subtree, tvb, offset + SRV_RAND_USER_REAL_IP,
- 4, "RealIP: %s", tvb_ip_to_str(tvb, offset + SRV_RAND_USER_REAL_IP));
- /* guint8 Communication Class */
- commClass = tvb_get_guint8(tvb, offset + SRV_RAND_USER_CLASS);
- proto_tree_add_text(subtree, tvb, offset + SRV_RAND_USER_CLASS,
- 1, "Class: %s",
- (commClass!=4)?"User to User":"Through Server");
- /* guint32 status */
- /* XXX - 16 bits, or 32 bits? */
- proto_tree_add_item(subtree, hf_icq_status, tvb, offset + SRV_RAND_USER_STATUS, 4, ENC_LITTLE_ENDIAN);
-
- /* guint16 tcpVersion */
- tcpVer = tvb_get_letohs(tvb, offset + SRV_RAND_USER_TCP_VER);
- proto_tree_add_text(subtree, tvb, offset + SRV_RAND_USER_TCP_VER,
- 2, "TCPVersion: %u", tcpVer);
- }
+ proto_tree *subtree = tree;
+ guint32 uin;
+ guint32 port;
+ guint8 commClass;
+ guint16 tcpVer;
+
+ if (tree) {
+ /* guint32 UIN */
+ uin = tvb_get_letohl(tvb, offset + SRV_RAND_USER_UIN);
+ proto_tree_add_text(subtree, tvb, offset + SRV_RAND_USER_UIN,
+ 4, "UIN: %u", uin);
+ /* guint32 IP */
+ proto_tree_add_text(subtree, tvb, offset + SRV_RAND_USER_IP,
+ 4, "IP: %s", tvb_ip_to_str(tvb, offset + SRV_RAND_USER_IP));
+ /* guint16 portNum */
+ /* XXX - 16 bits, or 32 bits? */
+ port = tvb_get_letohs(tvb, offset + SRV_RAND_USER_PORT);
+ proto_tree_add_text(subtree, tvb, offset + SRV_RAND_USER_UIN,
+ 4, "Port: %u", port);
+ /* guint32 realIP */
+ proto_tree_add_text(subtree, tvb, offset + SRV_RAND_USER_REAL_IP,
+ 4, "RealIP: %s", tvb_ip_to_str(tvb, offset + SRV_RAND_USER_REAL_IP));
+ /* guint8 Communication Class */
+ commClass = tvb_get_guint8(tvb, offset + SRV_RAND_USER_CLASS);
+ proto_tree_add_text(subtree, tvb, offset + SRV_RAND_USER_CLASS,
+ 1, "Class: %s",
+ (commClass!=4)?"User to User":"Through Server");
+ /* guint32 status */
+ /* XXX - 16 bits, or 32 bits? */
+ proto_tree_add_item(subtree, hf_icq_status, tvb, offset + SRV_RAND_USER_STATUS, 4, ENC_LITTLE_ENDIAN);
+
+ /* guint16 tcpVersion */
+ tcpVer = tvb_get_letohs(tvb, offset + SRV_RAND_USER_TCP_VER);
+ proto_tree_add_text(subtree, tvb, offset + SRV_RAND_USER_TCP_VER,
+ 2, "TCPVersion: %u", tcpVer);
+ }
}
/*
@@ -1080,227 +1080,227 @@ icqv5_srv_rand_user(proto_tree* tree, /* Tree to put the data in */
static void
dissect_icqv5Client(tvbuff_t *tvb, packet_info *pinfo, proto_tree *tree)
{
- proto_tree *icq_header_tree, *icq_body_tree;
- proto_item *ti, *cmd_item;
-
- int pktsize; /* The actual size of the ICQ content */
- int capturedsize; /* The captured size of the ICQ content */
- guint32 rounded_size;
- guint32 code, key;
- guint16 cmd;
- guint8 *decr_pd; /* Decrypted content */
- tvbuff_t *decr_tvb;
-
- pktsize = tvb_reported_length(tvb);
- capturedsize = tvb_length(tvb);
-
- /* Get the encryption key */
- code = tvb_get_letohl(tvb, ICQ5_CL_CHECKCODE);
- key = get_v5key(code, pktsize);
-
- /*
- * Make a copy of the packet data, and decrypt it.
- * The decryption processes 4 bytes at a time, and starts at
- * an offset of ICQ5_CL_SESSIONID (which isn't a multiple of 4),
- * so we make sure that there are
- *
- * (ICQ5_CL_SESSIONID + a multiple of 4)
- *
- * bytes in the buffer.
- */
- rounded_size = ((((capturedsize - ICQ5_CL_SESSIONID) + 3)/4)*4) + ICQ5_CL_SESSIONID;
- /* rounded_size might exceed the tvb bounds so we can't just use tvb_memdup here. */
- decr_pd = (guint8 *)g_malloc(rounded_size);
- tvb_memcpy(tvb, decr_pd, 0, capturedsize);
- decrypt_v5(decr_pd, rounded_size, key);
-
- /* Allocate a new tvbuff, referring to the decrypted data. */
- decr_tvb = tvb_new_child_real_data(tvb, decr_pd, capturedsize, pktsize);
-
- /* Arrange that the allocated packet data copy be freed when the
- tvbuff is freed. */
- tvb_set_free_cb(decr_tvb, g_free);
-
- /* Add the decrypted data to the data source list. */
- add_new_data_source(pinfo, decr_tvb, "Decrypted");
-
- cmd = tvb_get_letohs(decr_tvb, ICQ5_CL_CMD);
-
- col_add_fstr(pinfo->cinfo, COL_INFO, "ICQv5 %s", val_to_str_const(cmd, clientCmdCode, "Unknown"));
-
- icq_header_tree = proto_tree_add_subtree(tree, tvb, 0, ICQ5_CL_HDRSIZE, ett_icq_header, NULL, "Header");
-
- ti = proto_tree_add_boolean(icq_header_tree, hf_icq_type, tvb, 0, 0, ICQ5_CLIENT);
- PROTO_ITEM_SET_GENERATED(ti);
-
- proto_tree_add_item(icq_header_tree, hf_icq_version, tvb, ICQ_VERSION, 2, ENC_LITTLE_ENDIAN);
- proto_tree_add_item(icq_header_tree, hf_icq_uin, tvb, ICQ5_CL_UIN, 4, ENC_LITTLE_ENDIAN);
- proto_tree_add_item(icq_header_tree, hf_icq_sessionid, decr_tvb, ICQ5_CL_SESSIONID, 4, ENC_LITTLE_ENDIAN);
- cmd_item = proto_tree_add_item(icq_header_tree, hf_icq_client_cmd, decr_tvb, ICQ5_CL_CMD, 2, ENC_LITTLE_ENDIAN);
- proto_tree_add_item(icq_header_tree, hf_icq_seqnum1, decr_tvb, ICQ5_CL_SEQNUM1, 2, ENC_LITTLE_ENDIAN);
- proto_tree_add_item(icq_header_tree, hf_icq_seqnum2, decr_tvb, ICQ5_CL_SEQNUM2, 2, ENC_LITTLE_ENDIAN);
- proto_tree_add_item(icq_header_tree, hf_icq_checkcode, tvb, ICQ5_CL_CHECKCODE, 4, ENC_LITTLE_ENDIAN);
- ti = proto_tree_add_uint(icq_header_tree, hf_icq_checkcode_key, tvb, ICQ5_CL_CHECKCODE, 4, key);
- PROTO_ITEM_SET_GENERATED(ti);
-
- icq_body_tree = proto_tree_add_subtree(tree, decr_tvb, ICQ5_CL_HDRSIZE, pktsize - ICQ5_CL_HDRSIZE, ett_icq_body, NULL, "Body");
-
- switch(cmd) {
- case CMD_ACK:
- proto_tree_add_item(icq_body_tree, hf_icq_ack_random, decr_tvb, ICQ5_CL_HDRSIZE + CMD_ACK_RANDOM, 4, ENC_LITTLE_ENDIAN);
- break;
- case CMD_SEND_MSG:
- case CMD_MSG_TO_NEW_USER:
- icqv5_cmd_send_msg(icq_body_tree, decr_tvb, ICQ5_CL_HDRSIZE,
- pktsize - ICQ5_CL_HDRSIZE, pinfo);
- break;
- case CMD_RAND_SEARCH:
- proto_tree_add_item(icq_body_tree, hf_icq_group, decr_tvb, ICQ5_CL_HDRSIZE + CMD_RAND_SEARCH_GROUP, 4, ENC_LITTLE_ENDIAN);
- break;
- case CMD_LOGIN:
- icqv5_cmd_login(icq_body_tree, decr_tvb, ICQ5_CL_HDRSIZE);
- break;
- case CMD_SEND_TEXT_CODE:
- icqv5_cmd_send_text_code(icq_body_tree, decr_tvb, ICQ5_CL_HDRSIZE);
- break;
- case CMD_STATUS_CHANGE:
- proto_tree_add_item(icq_body_tree, hf_icq_status, decr_tvb, ICQ5_CL_HDRSIZE + CMD_STATUS_CHANGE_STATUS, 4, ENC_LITTLE_ENDIAN);
- break;
- case CMD_ACK_MESSAGES:
- proto_tree_add_item(icq_body_tree, hf_icq_ack_random, decr_tvb, ICQ5_CL_HDRSIZE + CMD_ACK_MESSAGES_RANDOM, 4, ENC_LITTLE_ENDIAN);
- break;
- case CMD_KEEP_ALIVE:
- proto_tree_add_item(icq_body_tree, hf_icq_keep_alive_random, decr_tvb, ICQ5_CL_HDRSIZE + CMD_KEEP_ALIVE_RANDOM, 4, ENC_LITTLE_ENDIAN);
- break;
- case CMD_ADD_TO_LIST:
- proto_tree_add_item(icq_body_tree, hf_icq_uin, decr_tvb, ICQ5_CL_HDRSIZE + CMD_ADD_TO_LIST_UIN, 4, ENC_LITTLE_ENDIAN);
- break;
- case CMD_CONTACT_LIST:
- icqv5_cmd_contact_list(icq_body_tree, decr_tvb, ICQ5_CL_HDRSIZE);
- break;
- case CMD_META_USER:
- case CMD_REG_NEW_USER:
- case CMD_QUERY_SERVERS:
- case CMD_QUERY_ADDONS:
- proto_tree_add_text(icq_body_tree, tvb, ICQ5_CL_HDRSIZE, 0, "No parameters");
- break;
- default:
- expert_add_info(pinfo, cmd_item, &ei_icq_unknown_command);
- break;
- }
+ proto_tree *icq_header_tree, *icq_body_tree;
+ proto_item *ti, *cmd_item;
+
+ int pktsize; /* The actual size of the ICQ content */
+ int capturedsize; /* The captured size of the ICQ content */
+ guint32 rounded_size;
+ guint32 code, key;
+ guint16 cmd;
+ guint8 *decr_pd; /* Decrypted content */
+ tvbuff_t *decr_tvb;
+
+ pktsize = tvb_reported_length(tvb);
+ capturedsize = tvb_length(tvb);
+
+ /* Get the encryption key */
+ code = tvb_get_letohl(tvb, ICQ5_CL_CHECKCODE);
+ key = get_v5key(code, pktsize);
+
+ /*
+ * Make a copy of the packet data, and decrypt it.
+ * The decryption processes 4 bytes at a time, and starts at
+ * an offset of ICQ5_CL_SESSIONID (which isn't a multiple of 4),
+ * so we make sure that there are
+ *
+ * (ICQ5_CL_SESSIONID + a multiple of 4)
+ *
+ * bytes in the buffer.
+ */
+ rounded_size = ((((capturedsize - ICQ5_CL_SESSIONID) + 3)/4)*4) + ICQ5_CL_SESSIONID;
+ /* rounded_size might exceed the tvb bounds so we can't just use tvb_memdup here. */
+ decr_pd = (guint8 *)g_malloc(rounded_size);
+ tvb_memcpy(tvb, decr_pd, 0, capturedsize);
+ decrypt_v5(decr_pd, rounded_size, key);
+
+ /* Allocate a new tvbuff, referring to the decrypted data. */
+ decr_tvb = tvb_new_child_real_data(tvb, decr_pd, capturedsize, pktsize);
+
+ /* Arrange that the allocated packet data copy be freed when the
+ tvbuff is freed. */
+ tvb_set_free_cb(decr_tvb, g_free);
+
+ /* Add the decrypted data to the data source list. */
+ add_new_data_source(pinfo, decr_tvb, "Decrypted");
+
+ cmd = tvb_get_letohs(decr_tvb, ICQ5_CL_CMD);
+
+ col_add_fstr(pinfo->cinfo, COL_INFO, "ICQv5 %s", val_to_str_const(cmd, clientCmdCode, "Unknown"));
+
+ icq_header_tree = proto_tree_add_subtree(tree, tvb, 0, ICQ5_CL_HDRSIZE, ett_icq_header, NULL, "Header");
+
+ ti = proto_tree_add_boolean(icq_header_tree, hf_icq_type, tvb, 0, 0, ICQ5_CLIENT);
+ PROTO_ITEM_SET_GENERATED(ti);
+
+ proto_tree_add_item(icq_header_tree, hf_icq_version, tvb, ICQ_VERSION, 2, ENC_LITTLE_ENDIAN);
+ proto_tree_add_item(icq_header_tree, hf_icq_uin, tvb, ICQ5_CL_UIN, 4, ENC_LITTLE_ENDIAN);
+ proto_tree_add_item(icq_header_tree, hf_icq_sessionid, decr_tvb, ICQ5_CL_SESSIONID, 4, ENC_LITTLE_ENDIAN);
+ cmd_item = proto_tree_add_item(icq_header_tree, hf_icq_client_cmd, decr_tvb, ICQ5_CL_CMD, 2, ENC_LITTLE_ENDIAN);
+ proto_tree_add_item(icq_header_tree, hf_icq_seqnum1, decr_tvb, ICQ5_CL_SEQNUM1, 2, ENC_LITTLE_ENDIAN);
+ proto_tree_add_item(icq_header_tree, hf_icq_seqnum2, decr_tvb, ICQ5_CL_SEQNUM2, 2, ENC_LITTLE_ENDIAN);
+ proto_tree_add_item(icq_header_tree, hf_icq_checkcode, tvb, ICQ5_CL_CHECKCODE, 4, ENC_LITTLE_ENDIAN);
+ ti = proto_tree_add_uint(icq_header_tree, hf_icq_checkcode_key, tvb, ICQ5_CL_CHECKCODE, 4, key);
+ PROTO_ITEM_SET_GENERATED(ti);
+
+ icq_body_tree = proto_tree_add_subtree(tree, decr_tvb, ICQ5_CL_HDRSIZE, pktsize - ICQ5_CL_HDRSIZE, ett_icq_body, NULL, "Body");
+
+ switch(cmd) {
+ case CMD_ACK:
+ proto_tree_add_item(icq_body_tree, hf_icq_ack_random, decr_tvb, ICQ5_CL_HDRSIZE + CMD_ACK_RANDOM, 4, ENC_LITTLE_ENDIAN);
+ break;
+ case CMD_SEND_MSG:
+ case CMD_MSG_TO_NEW_USER:
+ icqv5_cmd_send_msg(icq_body_tree, decr_tvb, ICQ5_CL_HDRSIZE,
+ pktsize - ICQ5_CL_HDRSIZE, pinfo);
+ break;
+ case CMD_RAND_SEARCH:
+ proto_tree_add_item(icq_body_tree, hf_icq_group, decr_tvb, ICQ5_CL_HDRSIZE + CMD_RAND_SEARCH_GROUP, 4, ENC_LITTLE_ENDIAN);
+ break;
+ case CMD_LOGIN:
+ icqv5_cmd_login(icq_body_tree, decr_tvb, ICQ5_CL_HDRSIZE);
+ break;
+ case CMD_SEND_TEXT_CODE:
+ icqv5_cmd_send_text_code(icq_body_tree, decr_tvb, ICQ5_CL_HDRSIZE);
+ break;
+ case CMD_STATUS_CHANGE:
+ proto_tree_add_item(icq_body_tree, hf_icq_status, decr_tvb, ICQ5_CL_HDRSIZE + CMD_STATUS_CHANGE_STATUS, 4, ENC_LITTLE_ENDIAN);
+ break;
+ case CMD_ACK_MESSAGES:
+ proto_tree_add_item(icq_body_tree, hf_icq_ack_random, decr_tvb, ICQ5_CL_HDRSIZE + CMD_ACK_MESSAGES_RANDOM, 4, ENC_LITTLE_ENDIAN);
+ break;
+ case CMD_KEEP_ALIVE:
+ proto_tree_add_item(icq_body_tree, hf_icq_keep_alive_random, decr_tvb, ICQ5_CL_HDRSIZE + CMD_KEEP_ALIVE_RANDOM, 4, ENC_LITTLE_ENDIAN);
+ break;
+ case CMD_ADD_TO_LIST:
+ proto_tree_add_item(icq_body_tree, hf_icq_uin, decr_tvb, ICQ5_CL_HDRSIZE + CMD_ADD_TO_LIST_UIN, 4, ENC_LITTLE_ENDIAN);
+ break;
+ case CMD_CONTACT_LIST:
+ icqv5_cmd_contact_list(icq_body_tree, decr_tvb, ICQ5_CL_HDRSIZE);
+ break;
+ case CMD_META_USER:
+ case CMD_REG_NEW_USER:
+ case CMD_QUERY_SERVERS:
+ case CMD_QUERY_ADDONS:
+ proto_tree_add_text(icq_body_tree, tvb, ICQ5_CL_HDRSIZE, 0, "No parameters");
+ break;
+ default:
+ expert_add_info(pinfo, cmd_item, &ei_icq_unknown_command);
+ break;
+ }
}
static void
dissect_icqv5Server(tvbuff_t *tvb, int offset, packet_info *pinfo,
- proto_tree *tree, int pktsize)
+ proto_tree *tree, int pktsize)
{
- /* Server traffic is easy, not encrypted */
- proto_tree *icq_header_tree, *icq_body_tree;
- proto_item *ti, *cmd_item;
-
- guint16 cmd = tvb_get_letohs(tvb, offset + ICQ5_SRV_CMD);
-
- if (pktsize == -1) {
- col_add_fstr(pinfo->cinfo, COL_INFO, "ICQv5 %s", val_to_str_const(cmd, serverCmdCode, "Unknown"));
- pktsize = tvb_reported_length(tvb);
- }
-
- icq_header_tree = proto_tree_add_subtree(tree, tvb, offset, ICQ5_SRV_HDRSIZE, ett_icq_header, NULL, "Header");
-
- ti = proto_tree_add_boolean(icq_header_tree, hf_icq_type, tvb, 0, 0, ICQ5_SERVER);
- PROTO_ITEM_SET_GENERATED(ti);
-
- proto_tree_add_item(icq_header_tree, hf_icq_version, tvb, offset + ICQ_VERSION, 2, ENC_LITTLE_ENDIAN);
- proto_tree_add_item(icq_header_tree, hf_icq_sessionid, tvb, offset + ICQ5_SRV_SESSIONID, 4, ENC_LITTLE_ENDIAN);
- cmd_item = proto_tree_add_item(icq_header_tree, hf_icq_server_cmd, tvb, offset + ICQ5_SRV_CMD, 2, ENC_LITTLE_ENDIAN);
- proto_tree_add_item(icq_header_tree, hf_icq_seqnum1, tvb, offset + ICQ5_SRV_SEQNUM1, 2, ENC_LITTLE_ENDIAN);
- proto_tree_add_item(icq_header_tree, hf_icq_seqnum2, tvb, offset + ICQ5_SRV_SEQNUM2, 2, ENC_LITTLE_ENDIAN);
- proto_tree_add_item(icq_header_tree, hf_icq_uin, tvb, offset + ICQ5_SRV_UIN, 4, ENC_LITTLE_ENDIAN);
- proto_tree_add_item(icq_header_tree, hf_icq_checkcode, tvb, offset + ICQ5_SRV_CHECKCODE, 4, ENC_LITTLE_ENDIAN);
-
- icq_body_tree = proto_tree_add_subtree(tree, tvb, ICQ5_CL_HDRSIZE, pktsize - ICQ5_SRV_HDRSIZE, ett_icq_body, NULL, "Body");
-
- switch (cmd) {
- case SRV_RAND_USER:
- icqv5_srv_rand_user(icq_body_tree, tvb, offset + ICQ5_SRV_HDRSIZE);
- break;
- case SRV_SYS_DELIVERED_MESS:
- /* The message structures are all the same. Why not run
- * the same routine? */
- icqv5_cmd_send_msg(icq_body_tree, tvb, offset + ICQ5_SRV_HDRSIZE,
- pktsize - ICQ5_SRV_HDRSIZE, pinfo);
- break;
- case SRV_USER_ONLINE:
- icqv5_srv_user_online(icq_body_tree, tvb, offset + ICQ5_SRV_HDRSIZE);
- break;
- case SRV_USER_OFFLINE:
- proto_tree_add_item(icq_body_tree, hf_icq_uin, tvb, offset + ICQ5_SRV_HDRSIZE + SRV_USER_OFFLINE_UIN, 4, ENC_LITTLE_ENDIAN);
- break;
- case SRV_LOGIN_REPLY:
- proto_tree_add_text(tree, tvb, offset + ICQ5_SRV_HDRSIZE + SRV_LOGIN_REPLY_IP, 4,
- "IP: %s", tvb_ip_to_str(tvb, offset + ICQ5_SRV_HDRSIZE + SRV_LOGIN_REPLY_IP));
- break;
- case SRV_META_USER:
- icqv5_srv_meta_user(icq_body_tree, tvb, offset + ICQ5_SRV_HDRSIZE,
- pktsize - ICQ5_SRV_HDRSIZE, pinfo);
- break;
- case SRV_RECV_MESSAGE:
- icqv5_srv_recv_message(icq_body_tree, tvb, offset + ICQ5_SRV_HDRSIZE,
- pktsize - ICQ5_SRV_HDRSIZE, pinfo);
- break;
- case SRV_MULTI:
- icqv5_srv_multi(icq_body_tree, tvb, offset + ICQ5_SRV_HDRSIZE, pinfo);
- break;
- case SRV_ACK:
- case SRV_SILENT_TOO_LONG:
- case SRV_GO_AWAY:
- case SRV_NEW_UIN:
- case SRV_BAD_PASS:
- case SRV_UPDATE_SUCCESS:
- proto_tree_add_text(icq_body_tree, tvb, offset + ICQ5_SRV_HDRSIZE, 0, "No Parameters");
- break;
- default:
- expert_add_info(pinfo, cmd_item, &ei_icq_unknown_command);
- break;
- }
+ /* Server traffic is easy, not encrypted */
+ proto_tree *icq_header_tree, *icq_body_tree;
+ proto_item *ti, *cmd_item;
+
+ guint16 cmd = tvb_get_letohs(tvb, offset + ICQ5_SRV_CMD);
+
+ if (pktsize == -1) {
+ col_add_fstr(pinfo->cinfo, COL_INFO, "ICQv5 %s", val_to_str_const(cmd, serverCmdCode, "Unknown"));
+ pktsize = tvb_reported_length(tvb);
+ }
+
+ icq_header_tree = proto_tree_add_subtree(tree, tvb, offset, ICQ5_SRV_HDRSIZE, ett_icq_header, NULL, "Header");
+
+ ti = proto_tree_add_boolean(icq_header_tree, hf_icq_type, tvb, 0, 0, ICQ5_SERVER);
+ PROTO_ITEM_SET_GENERATED(ti);
+
+ proto_tree_add_item(icq_header_tree, hf_icq_version, tvb, offset + ICQ_VERSION, 2, ENC_LITTLE_ENDIAN);
+ proto_tree_add_item(icq_header_tree, hf_icq_sessionid, tvb, offset + ICQ5_SRV_SESSIONID, 4, ENC_LITTLE_ENDIAN);
+ cmd_item = proto_tree_add_item(icq_header_tree, hf_icq_server_cmd, tvb, offset + ICQ5_SRV_CMD, 2, ENC_LITTLE_ENDIAN);
+ proto_tree_add_item(icq_header_tree, hf_icq_seqnum1, tvb, offset + ICQ5_SRV_SEQNUM1, 2, ENC_LITTLE_ENDIAN);
+ proto_tree_add_item(icq_header_tree, hf_icq_seqnum2, tvb, offset + ICQ5_SRV_SEQNUM2, 2, ENC_LITTLE_ENDIAN);
+ proto_tree_add_item(icq_header_tree, hf_icq_uin, tvb, offset + ICQ5_SRV_UIN, 4, ENC_LITTLE_ENDIAN);
+ proto_tree_add_item(icq_header_tree, hf_icq_checkcode, tvb, offset + ICQ5_SRV_CHECKCODE, 4, ENC_LITTLE_ENDIAN);
+
+ icq_body_tree = proto_tree_add_subtree(tree, tvb, ICQ5_CL_HDRSIZE, pktsize - ICQ5_SRV_HDRSIZE, ett_icq_body, NULL, "Body");
+
+ switch (cmd) {
+ case SRV_RAND_USER:
+ icqv5_srv_rand_user(icq_body_tree, tvb, offset + ICQ5_SRV_HDRSIZE);
+ break;
+ case SRV_SYS_DELIVERED_MESS:
+ /* The message structures are all the same. Why not run
+ * the same routine? */
+ icqv5_cmd_send_msg(icq_body_tree, tvb, offset + ICQ5_SRV_HDRSIZE,
+ pktsize - ICQ5_SRV_HDRSIZE, pinfo);
+ break;
+ case SRV_USER_ONLINE:
+ icqv5_srv_user_online(icq_body_tree, tvb, offset + ICQ5_SRV_HDRSIZE);
+ break;
+ case SRV_USER_OFFLINE:
+ proto_tree_add_item(icq_body_tree, hf_icq_uin, tvb, offset + ICQ5_SRV_HDRSIZE + SRV_USER_OFFLINE_UIN, 4, ENC_LITTLE_ENDIAN);
+ break;
+ case SRV_LOGIN_REPLY:
+ proto_tree_add_text(tree, tvb, offset + ICQ5_SRV_HDRSIZE + SRV_LOGIN_REPLY_IP, 4,
+ "IP: %s", tvb_ip_to_str(tvb, offset + ICQ5_SRV_HDRSIZE + SRV_LOGIN_REPLY_IP));
+ break;
+ case SRV_META_USER:
+ icqv5_srv_meta_user(icq_body_tree, tvb, offset + ICQ5_SRV_HDRSIZE,
+ pktsize - ICQ5_SRV_HDRSIZE, pinfo);
+ break;
+ case SRV_RECV_MESSAGE:
+ icqv5_srv_recv_message(icq_body_tree, tvb, offset + ICQ5_SRV_HDRSIZE,
+ pktsize - ICQ5_SRV_HDRSIZE, pinfo);
+ break;
+ case SRV_MULTI:
+ icqv5_srv_multi(icq_body_tree, tvb, offset + ICQ5_SRV_HDRSIZE, pinfo);
+ break;
+ case SRV_ACK:
+ case SRV_SILENT_TOO_LONG:
+ case SRV_GO_AWAY:
+ case SRV_NEW_UIN:
+ case SRV_BAD_PASS:
+ case SRV_UPDATE_SUCCESS:
+ proto_tree_add_text(icq_body_tree, tvb, offset + ICQ5_SRV_HDRSIZE, 0, "No Parameters");
+ break;
+ default:
+ expert_add_info(pinfo, cmd_item, &ei_icq_unknown_command);
+ break;
+ }
}
static void dissect_icqv5(tvbuff_t *tvb, packet_info *pinfo, proto_tree *tree)
{
- if (tvb_get_letohl(tvb, ICQ5_UNKNOWN) == 0) {
- dissect_icqv5Client(tvb, pinfo, tree);
- } else {
- dissect_icqv5Server(tvb, 0, pinfo, tree, -1);
- }
+ if (tvb_get_letohl(tvb, ICQ5_UNKNOWN) == 0) {
+ dissect_icqv5Client(tvb, pinfo, tree);
+ } else {
+ dissect_icqv5Server(tvb, 0, pinfo, tree, -1);
+ }
}
static int
dissect_icq(tvbuff_t *tvb, packet_info *pinfo, proto_tree *tree, void *data _U_)
{
- int version;
- proto_item *ti;
- proto_tree *icq_tree;
-
- version = tvb_get_letohs(tvb, ICQ_VERSION);
- if (version < 2 || version > 5)
- return 0; /* This is not a (recognized) ICQ packet */
-
- col_add_fstr(pinfo->cinfo, COL_PROTOCOL, "ICQv%d", version);
- col_add_fstr(pinfo->cinfo, COL_INFO, "ICQ Version %d protocol", version);
-
- ti = proto_tree_add_protocol_format(tree, proto_icq, tvb, 0, -1, "ICQv%d", version);
- icq_tree = proto_item_add_subtree(ti, ett_icq);
-
- if (version == 5)
- {
- dissect_icqv5(tvb, pinfo, icq_tree);
- }
- else
- {
- proto_tree_add_item(icq_tree, hf_icq_version, tvb, ICQ_VERSION, 2, ENC_LITTLE_ENDIAN);
- }
-
- return (tvb_length(tvb));
+ int version;
+ proto_item *ti;
+ proto_tree *icq_tree;
+
+ version = tvb_get_letohs(tvb, ICQ_VERSION);
+ if (version < 2 || version > 5)
+ return 0; /* This is not a (recognized) ICQ packet */
+
+ col_add_fstr(pinfo->cinfo, COL_PROTOCOL, "ICQv%d", version);
+ col_add_fstr(pinfo->cinfo, COL_INFO, "ICQ Version %d protocol", version);
+
+ ti = proto_tree_add_protocol_format(tree, proto_icq, tvb, 0, -1, "ICQv%d", version);
+ icq_tree = proto_item_add_subtree(ti, ett_icq);
+
+ if (version == 5)
+ {
+ dissect_icqv5(tvb, pinfo, icq_tree);
+ }
+ else
+ {
+ proto_tree_add_item(icq_tree, hf_icq_version, tvb, ICQ_VERSION, 2, ENC_LITTLE_ENDIAN);
+ }
+
+ return (tvb_length(tvb));
}
/* registration with the filtering engine */
@@ -1308,79 +1308,79 @@ void
proto_register_icq(void)
{
static hf_register_info hf[] = {
- { &hf_icq_version,
- {"Version", "icq.version", FT_UINT16, BASE_DEC, NULL, 0x0, NULL, HFILL }},
- { &hf_icq_type,
- {"Client/Server", "icq.client", FT_BOOLEAN, BASE_NONE, TFS(&tfs_client_server), 0x0, NULL, HFILL }},
- { &hf_icq_msg_type,
- {"Type", "icq.msg_type", FT_UINT16, BASE_DEC, VALS(msgTypeCode), 0x0, NULL, HFILL }},
- { &hf_icq_uin,
- {"UIN", "icq.uin", FT_UINT32, BASE_DEC, NULL, 0x0, NULL, HFILL }},
- { &hf_icq_sessionid,
- {"Session ID", "icq.sessionid", FT_UINT32, BASE_HEX, NULL, 0x0, NULL, HFILL }},
- { &hf_icq_client_cmd,
- {"Client command", "icq.client_cmd", FT_UINT16, BASE_DEC, VALS(clientCmdCode), 0x0, NULL, HFILL }},
- { &hf_icq_server_cmd,
- {"Server command", "icq.server_cmd", FT_UINT16, BASE_DEC, VALS(serverCmdCode), 0x0, NULL, HFILL }},
- { &hf_icq_checkcode,
- {"Checkcode", "icq.checkcode", FT_UINT32, BASE_HEX, NULL, 0x0, NULL, HFILL }},
- { &hf_icq_checkcode_key,
- {"Key", "icq.checkcode_key", FT_UINT32, BASE_HEX, NULL, 0x0, NULL, HFILL }},
- { &hf_icq_seqnum1,
- {"Seq Number 1", "icq.seqnum1", FT_UINT16, BASE_HEX, NULL, 0x0, NULL, HFILL }},
- { &hf_icq_seqnum2,
- {"Seq Number 2", "icq.seqnum2", FT_UINT16, BASE_HEX, NULL, 0x0, NULL, HFILL }},
- { &hf_icq_group,
- {"Group", "icq.group", FT_UINT32, BASE_DEC, NULL, 0x0, NULL, HFILL }},
- { &hf_icq_ack_random,
- {"Random", "icq.ack.random", FT_UINT32, BASE_HEX, NULL, 0x0, NULL, HFILL }},
- { &hf_icq_keep_alive_random,
- {"Random", "icq.keep_alive.random", FT_UINT32, BASE_HEX, NULL, 0x0, NULL, HFILL }},
- { &hf_icq_status,
- {"Client command", "icq.status", FT_UINT32, BASE_DEC, VALS(statusCode), 0x0, NULL, HFILL }},
- { &hf_icq_meta_user_subcmd,
- {"Subcommand", "icq.meta_user.subcmd", FT_UINT16, BASE_DEC, VALS(serverMetaSubCmdCode), 0x0, NULL, HFILL }},
+ { &hf_icq_version,
+ {"Version", "icq.version", FT_UINT16, BASE_DEC, NULL, 0x0, NULL, HFILL }},
+ { &hf_icq_type,
+ {"Client/Server", "icq.client", FT_BOOLEAN, BASE_NONE, TFS(&tfs_client_server), 0x0, NULL, HFILL }},
+ { &hf_icq_msg_type,
+ {"Type", "icq.msg_type", FT_UINT16, BASE_DEC, VALS(msgTypeCode), 0x0, NULL, HFILL }},
+ { &hf_icq_uin,
+ {"UIN", "icq.uin", FT_UINT32, BASE_DEC, NULL, 0x0, NULL, HFILL }},
+ { &hf_icq_sessionid,
+ {"Session ID", "icq.sessionid", FT_UINT32, BASE_HEX, NULL, 0x0, NULL, HFILL }},
+ { &hf_icq_client_cmd,
+ {"Client command", "icq.client_cmd", FT_UINT16, BASE_DEC, VALS(clientCmdCode), 0x0, NULL, HFILL }},
+ { &hf_icq_server_cmd,
+ {"Server command", "icq.server_cmd", FT_UINT16, BASE_DEC, VALS(serverCmdCode), 0x0, NULL, HFILL }},
+ { &hf_icq_checkcode,
+ {"Checkcode", "icq.checkcode", FT_UINT32, BASE_HEX, NULL, 0x0, NULL, HFILL }},
+ { &hf_icq_checkcode_key,
+ {"Key", "icq.checkcode_key", FT_UINT32, BASE_HEX, NULL, 0x0, NULL, HFILL }},
+ { &hf_icq_seqnum1,
+ {"Seq Number 1", "icq.seqnum1", FT_UINT16, BASE_HEX, NULL, 0x0, NULL, HFILL }},
+ { &hf_icq_seqnum2,
+ {"Seq Number 2", "icq.seqnum2", FT_UINT16, BASE_HEX, NULL, 0x0, NULL, HFILL }},
+ { &hf_icq_group,
+ {"Group", "icq.group", FT_UINT32, BASE_DEC, NULL, 0x0, NULL, HFILL }},
+ { &hf_icq_ack_random,
+ {"Random", "icq.ack.random", FT_UINT32, BASE_HEX, NULL, 0x0, NULL, HFILL }},
+ { &hf_icq_keep_alive_random,
+ {"Random", "icq.keep_alive.random", FT_UINT32, BASE_HEX, NULL, 0x0, NULL, HFILL }},
+ { &hf_icq_status,
+ {"Client command", "icq.status", FT_UINT32, BASE_DEC, VALS(statusCode), 0x0, NULL, HFILL }},
+ { &hf_icq_meta_user_subcmd,
+ {"Subcommand", "icq.meta_user.subcmd", FT_UINT16, BASE_DEC, VALS(serverMetaSubCmdCode), 0x0, NULL, HFILL }},
+ };
+
+
+ static gint *ett[] = {
+ &ett_icq,
+ &ett_icq_header,
+ &ett_icq_body,
+ &ett_icq_body_parts,
+ };
+ static ei_register_info ei[] = {
+ { &ei_icq_unknown_meta_subcmd, { "icq.unknown_meta_subcmd", PI_UNDECODED, PI_WARN, "Unknown meta subcmd", EXPFILL }},
+ { &ei_icq_unknown_command, { "icq.unknown_command", PI_UNDECODED, PI_WARN, "Unknown command", EXPFILL }},
};
+ expert_module_t *expert_icq;
- static gint *ett[] = {
- &ett_icq,
- &ett_icq_header,
- &ett_icq_body,
- &ett_icq_body_parts,
- };
- static ei_register_info ei[] = {
- { &ei_icq_unknown_meta_subcmd, { "icq.unknown_meta_subcmd", PI_UNDECODED, PI_WARN, "Unknown meta subcmd", EXPFILL }},
- { &ei_icq_unknown_command, { "icq.unknown_command", PI_UNDECODED, PI_WARN, "Unknown command", EXPFILL }},
- };
-
- expert_module_t* expert_icq;
-
- proto_icq = proto_register_protocol("ICQ Protocol", "ICQ", "icq");
- proto_register_field_array(proto_icq, hf, array_length(hf));
- proto_register_subtree_array(ett, array_length(ett));
- expert_icq = expert_register_protocol(proto_icq);
- expert_register_field_array(expert_icq, ei, array_length(ei));
+ proto_icq = proto_register_protocol("ICQ Protocol", "ICQ", "icq");
+ proto_register_field_array(proto_icq, hf, array_length(hf));
+ proto_register_subtree_array(ett, array_length(ett));
+ expert_icq = expert_register_protocol(proto_icq);
+ expert_register_field_array(expert_icq, ei, array_length(ei));
}
void
proto_reg_handoff_icq(void)
{
- dissector_handle_t icq_handle;
+ dissector_handle_t icq_handle;
- icq_handle = new_create_dissector_handle(dissect_icq, proto_icq);
- dissector_add_uint("udp.port", UDP_PORT_ICQ, icq_handle);
+ icq_handle = new_create_dissector_handle(dissect_icq, proto_icq);
+ dissector_add_uint("udp.port", UDP_PORT_ICQ, icq_handle);
}
/*
- * Editor modelines
+ * Editor modelines - http://www.wireshark.org/tools/modelines.html
*
- * Local Variables:
- * c-basic-offset: 8
+ * Local variables:
+ * c-basic-offset: 4
* tab-width: 8
- * indent-tabs-mode: t
+ * indent-tabs-mode: nil
* End:
*
- * ex: set shiftwidth=8 tabstop=8 noexpandtab:
- * :indentSize=8:tabSize=8:noTabs=false:
+ * vi: set shiftwidth=4 tabstop=8 expandtab:
+ * :indentSize=4:tabSize=8:noTabs=true:
*/
diff --git a/epan/dissectors/packet-rtpproxy.c b/epan/dissectors/packet-rtpproxy.c
index c0b60ebfb4..f58163ae00 100644
--- a/epan/dissectors/packet-rtpproxy.c
+++ b/epan/dissectors/packet-rtpproxy.c
@@ -97,10 +97,10 @@ static int hf_rtpproxy_response_in = -1;
static int hf_rtpproxy_response_time = -1;
typedef struct _rtpproxy_info {
- guint32 req_frame;
- guint32 resp_frame;
- nstime_t req_time;
- gchar* callid;
+ guint32 req_frame;
+ guint32 resp_frame;
+ nstime_t req_time;
+ gchar* callid;
} rtpproxy_info_t;
static dissector_handle_t rtcp_handle;
@@ -109,122 +109,122 @@ static dissector_handle_t rtp_handle;
static dissector_handle_t bencode_handle;
typedef struct _rtpproxy_conv_info {
- wmem_tree_t *trans;
+ wmem_tree_t *trans;
} rtpproxy_conv_info_t;
static const string_string versiontypenames[] = {
- { "20040107", "Basic RTP proxy functionality" },
- { "20050322", "Support for multiple RTP streams and MOH" },
- { "20060704", "Support for extra parameter in the V command" },
- { "20071116", "Support for RTP re-packetization" },
- { "20071218", "Support for forking (copying) RTP stream" },
- { "20080403", "Support for RTP statistics querying" },
- { "20081102", "Support for setting codecs in the update/lookup command" },
- { "20081224", "Support for session timeout notifications" },
- { "20090810", "Support for automatic bridging" },
- { 0, NULL }
+ { "20040107", "Basic RTP proxy functionality" },
+ { "20050322", "Support for multiple RTP streams and MOH" },
+ { "20060704", "Support for extra parameter in the V command" },
+ { "20071116", "Support for RTP re-packetization" },
+ { "20071218", "Support for forking (copying) RTP stream" },
+ { "20080403", "Support for RTP statistics querying" },
+ { "20081102", "Support for setting codecs in the update/lookup command" },
+ { "20081224", "Support for session timeout notifications" },
+ { "20090810", "Support for automatic bridging" },
+ { 0, NULL }
};
static const value_string commandtypenames[] = {
- { 'V', "Handshake/Ping" },
- { 'v', "Handshake/Ping" },
- { 'U', "Offer/Update" },
- { 'u', "Offer/Update" },
- { 'L', "Answer/Lookup" },
- { 'l', "Answer/Lookup" },
- { 'I', "Information"},
- { 'i', "Information"},
- { 'X', "Close all active sessions"},
- { 'x', "Close all active sessions"},
- { 'D', "Delete an active session (Bye/Cancel/Error)"},
- { 'd', "Delete an active session (Bye/Cancel/Error)"},
- { 'P', "Start playback (music-on-hold)"},
- { 'p', "Start playback (music-on-hold)"},
- { 'S', "Stop playback (music-on-hold)"},
- { 's', "Stop playback (music-on-hold)"},
- { 'R', "Start recording"},
- { 'r', "Start recording"},
- { 'C', "Copy stream"},
- { 'c', "Copy stream"},
- { 'Q', "Query info about a session"},
- { 'q', "Query info about a session"},
- { 0, NULL }
+ { 'V', "Handshake/Ping" },
+ { 'v', "Handshake/Ping" },
+ { 'U', "Offer/Update" },
+ { 'u', "Offer/Update" },
+ { 'L', "Answer/Lookup" },
+ { 'l', "Answer/Lookup" },
+ { 'I', "Information"},
+ { 'i', "Information"},
+ { 'X', "Close all active sessions"},
+ { 'x', "Close all active sessions"},
+ { 'D', "Delete an active session (Bye/Cancel/Error)"},
+ { 'd', "Delete an active session (Bye/Cancel/Error)"},
+ { 'P', "Start playback (music-on-hold)"},
+ { 'p', "Start playback (music-on-hold)"},
+ { 'S', "Stop playback (music-on-hold)"},
+ { 's', "Stop playback (music-on-hold)"},
+ { 'R', "Start recording"},
+ { 'r', "Start recording"},
+ { 'C', "Copy stream"},
+ { 'c', "Copy stream"},
+ { 'Q', "Query info about a session"},
+ { 'q', "Query info about a session"},
+ { 0, NULL }
};
static const value_string paramtypenames[] = {
- /* Official command parameters */
- {'4', "Remote address is IPv4"},
- {'6', "Remote address is IPv6"},
- {'a', "Asymmetric RTP"},
- {'A', "Asymmetric RTP"},
- {'b', "Brief stats"},
- {'B', "Brief stats"},
- {'c', "Codecs"},
- {'C', "Codecs"},
- {'e', "External network (non RFC 1918)"},
- {'E', "External network (non RFC 1918)"},
- {'i', "Internal network (RFC 1918)"},
- {'I', "Internal network (RFC 1918)"},
- {'l', "Local address"},
- {'L', "Local address"},
- {'r', "Remote address"},
- {'R', "Remote address"},
- {'s', "Symmetric RTP (default)"},
- {'S', "Symmetric RTP (default)"},
- {'w', "Weak connection (allows roaming)"},
- {'W', "Weak connection (allows roaming)"},
- {'z', "repacketiZe"},
- {'Z', "repacketiZe"},
- /* Unofficial command parameters / expensions */
- {'d', "DTMF payload ID (unofficial extension)"},
- {'D', "DTMF payload ID (unofficial extension)"},
- {'m', "codec Mapping (unofficial extension)"},
- {'M', "codec Mapping (unofficial extension)"},
- {'p', "Protocol type (unofficial extension)"},
- {'P', "Protocol type (unofficial extension)"},
- {'t', "Transcode to (unofficial extension)"},
- {'T', "Transcode to (unofficial extension)"},
- {'v', "Accounting (unofficial extension)"},
- {'V', "Accounting (unofficial extension)"},
- {0, NULL}
+ /* Official command parameters */
+ {'4', "Remote address is IPv4"},
+ {'6', "Remote address is IPv6"},
+ {'a', "Asymmetric RTP"},
+ {'A', "Asymmetric RTP"},
+ {'b', "Brief stats"},
+ {'B', "Brief stats"},
+ {'c', "Codecs"},
+ {'C', "Codecs"},
+ {'e', "External network (non RFC 1918)"},
+ {'E', "External network (non RFC 1918)"},
+ {'i', "Internal network (RFC 1918)"},
+ {'I', "Internal network (RFC 1918)"},
+ {'l', "Local address"},
+ {'L', "Local address"},
+ {'r', "Remote address"},
+ {'R', "Remote address"},
+ {'s', "Symmetric RTP (default)"},
+ {'S', "Symmetric RTP (default)"},
+ {'w', "Weak connection (allows roaming)"},
+ {'W', "Weak connection (allows roaming)"},
+ {'z', "repacketiZe"},
+ {'Z', "repacketiZe"},
+ /* Unofficial command parameters / expensions */
+ {'d', "DTMF payload ID (unofficial extension)"},
+ {'D', "DTMF payload ID (unofficial extension)"},
+ {'m', "codec Mapping (unofficial extension)"},
+ {'M', "codec Mapping (unofficial extension)"},
+ {'p', "Protocol type (unofficial extension)"},
+ {'P', "Protocol type (unofficial extension)"},
+ {'t', "Transcode to (unofficial extension)"},
+ {'T', "Transcode to (unofficial extension)"},
+ {'v', "Accounting (unofficial extension)"},
+ {'V', "Accounting (unofficial extension)"},
+ {0, NULL}
};
static const value_string prototypenames[] = {
- { '0', "UDP (default)"},
- { '1', "TCP"},
- { '2', "SCTP"},
- { 0, NULL }
+ { '0', "UDP (default)"},
+ { '1', "TCP"},
+ { '2', "SCTP"},
+ { 0, NULL }
};
static const value_string acctypenames[] = {
- { '0', "Start"},
- { '1', "Interim update"},
- { '2', "Stop"},
- { 0, NULL }
+ { '0', "Start"},
+ { '1', "Interim update"},
+ { '2', "Stop"},
+ { 0, NULL }
};
static const value_string oktypenames[] = {
- { '0', "Ok"},
- { '1', "Version Supported"},
- { 0, NULL }
+ { '0', "Ok"},
+ { '1', "Version Supported"},
+ { 0, NULL }
};
static const string_string errortypenames[] = {
- { "E0", "Syntax error" },
- { "E1", "Syntax error" },
- { "E2", "Syntax error" },
- { "E3", "Unknown command" },
- { "E4", "Syntax error" },
- { "E5", "Out of memory" },
- { "E6", "<no description>" },
- { "E7", "Software error (can't create listener)" },
- { "E8", "Not Found" },
- { "E10", "Software error (can't create listener)" },
- { "E11", "Out of memory" },
- { "E12", "Out of memory" },
- { "E13", "Out of memory" },
- { "E14", "Out of memory" },
- { 0, NULL }
+ { "E0", "Syntax error" },
+ { "E1", "Syntax error" },
+ { "E2", "Syntax error" },
+ { "E3", "Unknown command" },
+ { "E4", "Syntax error" },
+ { "E5", "Out of memory" },
+ { "E6", "<no description>" },
+ { "E7", "Software error (can't create listener)" },
+ { "E8", "Not Found" },
+ { "E10", "Software error (can't create listener)" },
+ { "E11", "Out of memory" },
+ { "E12", "Out of memory" },
+ { "E13", "Out of memory" },
+ { "E14", "Out of memory" },
+ { 0, NULL }
};
static gint ett_rtpproxy = -1;
@@ -262,1221 +262,1229 @@ void proto_reg_handoff_rtpproxy(void);
static gint
rtpproxy_add_tag(proto_tree *rtpproxy_tree, tvbuff_t *tvb, guint begin, guint realsize)
{
- proto_item *ti = NULL;
- proto_tree *another_tree = NULL;
- gint new_offset;
- guint end;
-
- new_offset = tvb_find_guint8(tvb, begin, -1, ' ');
- if(new_offset < 0)
- end = realsize; /* No more parameters */
- else
- end = new_offset;
-
- /* SER/OpenSER/OpenSIPS/Kamailio adds Media-ID right after the Tag
- * separated by a semicolon
- */
- new_offset = tvb_find_guint8(tvb, begin, end, ';');
- if(new_offset == -1){
- ti = proto_tree_add_item(rtpproxy_tree, hf_rtpproxy_tag, tvb, begin, end - begin, ENC_ASCII | ENC_NA);
- another_tree = proto_item_add_subtree(ti, ett_rtpproxy_tag);
- ti = proto_tree_add_item(another_tree, hf_rtpproxy_mediaid, tvb, new_offset+1, 0, ENC_ASCII | ENC_NA);
- proto_item_append_text(ti, "<skipped>");
- PROTO_ITEM_SET_GENERATED(ti);
- }
- else{
- ti = proto_tree_add_item(rtpproxy_tree, hf_rtpproxy_tag, tvb, begin, new_offset - begin, ENC_ASCII | ENC_NA);
- if ((guint)new_offset == begin){
- proto_item_append_text(ti, "<skipped>"); /* A very first Offer/Update command */
- PROTO_ITEM_SET_GENERATED(ti);
- }
- another_tree = proto_item_add_subtree(ti, ett_rtpproxy_tag);
- proto_tree_add_item(another_tree, hf_rtpproxy_mediaid, tvb, new_offset+1, end - (new_offset+1), ENC_ASCII | ENC_NA);
- }
- return (end == realsize ? -1 : (gint)end);
+ proto_item *ti = NULL;
+ proto_tree *another_tree = NULL;
+ gint new_offset;
+ guint end;
+
+ new_offset = tvb_find_guint8(tvb, begin, -1, ' ');
+ if(new_offset < 0)
+ end = realsize; /* No more parameters */
+ else
+ end = new_offset;
+
+ /* SER/OpenSER/OpenSIPS/Kamailio adds Media-ID right after the Tag
+ * separated by a semicolon
+ */
+ new_offset = tvb_find_guint8(tvb, begin, end, ';');
+ if(new_offset == -1){
+ ti = proto_tree_add_item(rtpproxy_tree, hf_rtpproxy_tag, tvb, begin, end - begin, ENC_ASCII | ENC_NA);
+ another_tree = proto_item_add_subtree(ti, ett_rtpproxy_tag);
+ ti = proto_tree_add_item(another_tree, hf_rtpproxy_mediaid, tvb, new_offset+1, 0, ENC_ASCII | ENC_NA);
+ proto_item_append_text(ti, "<skipped>");
+ PROTO_ITEM_SET_GENERATED(ti);
+ }
+ else{
+ ti = proto_tree_add_item(rtpproxy_tree, hf_rtpproxy_tag, tvb, begin, new_offset - begin, ENC_ASCII | ENC_NA);
+ if ((guint)new_offset == begin){
+ proto_item_append_text(ti, "<skipped>"); /* A very first Offer/Update command */
+ PROTO_ITEM_SET_GENERATED(ti);
+ }
+ another_tree = proto_item_add_subtree(ti, ett_rtpproxy_tag);
+ proto_tree_add_item(another_tree, hf_rtpproxy_mediaid, tvb, new_offset+1, end - (new_offset+1), ENC_ASCII | ENC_NA);
+ }
+ return (end == realsize ? -1 : (gint)end);
}
static void
rtpproxy_add_parameter(tvbuff_t *tvb, packet_info *pinfo, proto_tree *rtpproxy_tree, guint begin, guint realsize)
{
- proto_item *ti;
- proto_tree *another_tree = NULL;
- guint offset = 0;
- guint new_offset = 0;
- gint i;
- guint pt = 0;
- gchar** codecs = NULL;
- guint codec_len;
- guint8* rawstr = NULL;
- guint32 ipaddr[4]; /* Enough room for IPv4 or IPv6 */
-
- /* Extract the entire parameters line. */
- /* Something like "t4p1iic8,0,2,4,18,96,97,98,100,101" */
- rawstr = tvb_get_string_enc(wmem_packet_scope(), tvb, begin, realsize, ENC_ASCII);
-
- while(offset < realsize){
- ti = proto_tree_add_item(rtpproxy_tree, hf_rtpproxy_command_parameter, tvb, begin + offset, 1, ENC_NA);
- offset++; /* Skip 1-byte parameter's type */
- switch (g_ascii_tolower(tvb_get_guint8(tvb, begin+offset-1)))
- {
- /* Official long parameters */
- case 'c':
- new_offset = (gint)strspn(rawstr+offset, "0123456789,");
- another_tree = proto_item_add_subtree(ti, ett_rtpproxy_command_parameters_codecs);
- codecs = g_strsplit(tvb_get_string_enc(wmem_packet_scope(), tvb, begin+offset, new_offset, ENC_ASCII), ",", 0);
- i = 0;
- while(codecs[i]){
- /* We assume strings < 2^32-1 bytes long. :-) */
- codec_len = (guint)strlen(codecs[i]);
- ti = proto_tree_add_uint(another_tree, hf_rtpproxy_command_parameter_codec, tvb, begin+offset, codec_len,
- (guint16) g_ascii_strtoull((gchar*)tvb_get_string_enc(wmem_packet_scope(), tvb, begin+offset, codec_len, ENC_ASCII), NULL, 10));
- proto_item_append_text(ti, " (%s)", val_to_str_ext((guint)strtoul(tvb_format_text(tvb,begin+offset,codec_len),NULL,10), &rtp_payload_type_vals_ext, "Unknown"));
- offset += codec_len;
- if(codecs[i+1])
- offset++; /* skip comma */
- i++;
- };
- g_strfreev(codecs);
- break;
- case 'l':
- new_offset = (gint)strspn(rawstr+offset, "0123456789.");
- another_tree = proto_item_add_subtree(ti, ett_rtpproxy_command_parameters_local);
- if(str_to_ip((char*)tvb_get_string_enc(wmem_packet_scope(), tvb, begin+offset, new_offset, ENC_ASCII), ipaddr))
- proto_tree_add_ipv4(another_tree, hf_rtpproxy_command_parameter_local_ipv4, tvb, begin+offset, new_offset, ipaddr[0]);
- else
- proto_tree_add_expert(another_tree, pinfo, &ei_rtpproxy_bad_ipv4, tvb, begin+offset, new_offset);
- offset += new_offset;
- break;
- case 'r':
- new_offset = (gint)strspn(rawstr+offset, "0123456789.");
- another_tree = proto_item_add_subtree(ti, ett_rtpproxy_command_parameters_remote);
- if(str_to_ip((char*)tvb_get_string_enc(wmem_packet_scope(), tvb, begin+offset, new_offset, ENC_ASCII), ipaddr))
- proto_tree_add_ipv4(another_tree, hf_rtpproxy_command_parameter_remote_ipv4, tvb, begin+offset, new_offset, ipaddr[0]);
- else
- proto_tree_add_expert(another_tree, pinfo, &ei_rtpproxy_bad_ipv4, tvb, begin+offset, new_offset);
- offset += new_offset;
- break;
- case 'z':
- new_offset = (gint)strspn(rawstr+offset, "0123456789");
- another_tree = proto_item_add_subtree(ti, ett_rtpproxy_command_parameters_repacketize);
- proto_tree_add_uint(another_tree, hf_rtpproxy_command_parameter_repacketize, tvb, begin+offset, new_offset,
- (guint16) g_ascii_strtoull((gchar*)tvb_get_string_enc(wmem_packet_scope(), tvb, begin+offset, new_offset, ENC_ASCII), NULL, 10));
- offset += new_offset;
- break;
- /* Unofficial long parameters */
- case 'd':
- new_offset = (gint)strspn(rawstr+offset, "0123456789");
- another_tree = proto_item_add_subtree(ti, ett_rtpproxy_command_parameters_dtmf);
- proto_tree_add_uint(another_tree, hf_rtpproxy_command_parameter_dtmf, tvb, begin+offset, new_offset,
- (guint16) g_ascii_strtoull((gchar*)tvb_get_string_enc(wmem_packet_scope(), tvb, begin+offset, new_offset, ENC_ASCII), NULL, 10));
- if(rtpproxy_establish_conversation){
- pt = (guint)strtoul(tvb_format_text(tvb,begin+offset,new_offset),NULL,10);
- dissector_add_uint("rtp.pt", pt, rtp_events_handle);
- }
- offset += new_offset;
- break;
- case 'm':
- new_offset = (gint)strspn(rawstr+offset, "0123456789=,");
- /* TODO */
- offset += new_offset;
- break;
- case 'p':
- another_tree = proto_item_add_subtree(ti, ett_rtpproxy_command_parameters_proto);
- proto_tree_add_item(another_tree, hf_rtpproxy_command_parameter_proto, tvb, begin+offset, 1, ENC_NA);
- offset++;
- break;
- case 't':
- new_offset = (gint)strspn(rawstr+offset, "0123456789");
- another_tree = proto_item_add_subtree(ti, ett_rtpproxy_command_parameters_transcode);
- ti = proto_tree_add_uint(another_tree, hf_rtpproxy_command_parameter_transcode, tvb, begin+offset, new_offset,
- (guint16) g_ascii_strtoull((gchar*)tvb_get_string_enc(wmem_packet_scope(), tvb, begin+offset, new_offset, ENC_ASCII), NULL, 10));
- proto_item_append_text(ti, " (%s)", val_to_str_ext((guint)strtoul(tvb_format_text(tvb,begin+offset, new_offset),NULL,10), &rtp_payload_type_vals_ext, "Unknown"));
- offset += new_offset;
- break;
- case 'v':
- another_tree = proto_item_add_subtree(ti, ett_rtpproxy_command_parameters_acc);
- proto_tree_add_item(another_tree, hf_rtpproxy_command_parameter_acc, tvb, begin+offset, 1, ENC_NA);
- offset++;
- break;
- default:
- break;
- }
- }
+ proto_item *ti;
+ proto_tree *another_tree = NULL;
+ guint offset = 0;
+ guint new_offset = 0;
+ gint i;
+ guint pt = 0;
+ gchar** codecs = NULL;
+ guint codec_len;
+ guint8* rawstr = NULL;
+ guint32 ipaddr[4]; /* Enough room for IPv4 or IPv6 */
+
+ /* Extract the entire parameters line. */
+ /* Something like "t4p1iic8,0,2,4,18,96,97,98,100,101" */
+ rawstr = tvb_get_string_enc(wmem_packet_scope(), tvb, begin, realsize, ENC_ASCII);
+
+ while(offset < realsize){
+ ti = proto_tree_add_item(rtpproxy_tree, hf_rtpproxy_command_parameter, tvb, begin + offset, 1, ENC_NA);
+ offset++; /* Skip 1-byte parameter's type */
+ switch (g_ascii_tolower(tvb_get_guint8(tvb, begin+offset-1)))
+ {
+ /* Official long parameters */
+ case 'c':
+ new_offset = (gint)strspn(rawstr+offset, "0123456789,");
+ another_tree = proto_item_add_subtree(ti, ett_rtpproxy_command_parameters_codecs);
+ codecs = g_strsplit(tvb_get_string_enc(wmem_packet_scope(), tvb, begin+offset, new_offset, ENC_ASCII), ",", 0);
+ i = 0;
+ while(codecs[i]){
+ /* We assume strings < 2^32-1 bytes long. :-) */
+ codec_len = (guint)strlen(codecs[i]);
+ ti = proto_tree_add_uint(another_tree, hf_rtpproxy_command_parameter_codec, tvb, begin+offset, codec_len,
+ (guint16) g_ascii_strtoull((gchar*)tvb_get_string_enc(wmem_packet_scope(), tvb, begin+offset, codec_len, ENC_ASCII), NULL, 10));
+ proto_item_append_text(ti, " (%s)", val_to_str_ext((guint)strtoul(tvb_format_text(tvb,begin+offset,codec_len),NULL,10), &rtp_payload_type_vals_ext, "Unknown"));
+ offset += codec_len;
+ if(codecs[i+1])
+ offset++; /* skip comma */
+ i++;
+ };
+ g_strfreev(codecs);
+ break;
+ case 'l':
+ new_offset = (gint)strspn(rawstr+offset, "0123456789.");
+ another_tree = proto_item_add_subtree(ti, ett_rtpproxy_command_parameters_local);
+ if(str_to_ip((char*)tvb_get_string_enc(wmem_packet_scope(), tvb, begin+offset, new_offset, ENC_ASCII), ipaddr))
+ proto_tree_add_ipv4(another_tree, hf_rtpproxy_command_parameter_local_ipv4, tvb, begin+offset, new_offset, ipaddr[0]);
+ else
+ proto_tree_add_expert(another_tree, pinfo, &ei_rtpproxy_bad_ipv4, tvb, begin+offset, new_offset);
+ offset += new_offset;
+ break;
+ case 'r':
+ new_offset = (gint)strspn(rawstr+offset, "0123456789.");
+ another_tree = proto_item_add_subtree(ti, ett_rtpproxy_command_parameters_remote);
+ if(str_to_ip((char*)tvb_get_string_enc(wmem_packet_scope(), tvb, begin+offset, new_offset, ENC_ASCII), ipaddr))
+ proto_tree_add_ipv4(another_tree, hf_rtpproxy_command_parameter_remote_ipv4, tvb, begin+offset, new_offset, ipaddr[0]);
+ else
+ proto_tree_add_expert(another_tree, pinfo, &ei_rtpproxy_bad_ipv4, tvb, begin+offset, new_offset);
+ offset += new_offset;
+ break;
+ case 'z':
+ new_offset = (gint)strspn(rawstr+offset, "0123456789");
+ another_tree = proto_item_add_subtree(ti, ett_rtpproxy_command_parameters_repacketize);
+ proto_tree_add_uint(another_tree, hf_rtpproxy_command_parameter_repacketize, tvb, begin+offset, new_offset,
+ (guint16) g_ascii_strtoull((gchar*)tvb_get_string_enc(wmem_packet_scope(), tvb, begin+offset, new_offset, ENC_ASCII), NULL, 10));
+ offset += new_offset;
+ break;
+ /* Unofficial long parameters */
+ case 'd':
+ new_offset = (gint)strspn(rawstr+offset, "0123456789");
+ another_tree = proto_item_add_subtree(ti, ett_rtpproxy_command_parameters_dtmf);
+ proto_tree_add_uint(another_tree, hf_rtpproxy_command_parameter_dtmf, tvb, begin+offset, new_offset,
+ (guint16) g_ascii_strtoull((gchar*)tvb_get_string_enc(wmem_packet_scope(), tvb, begin+offset, new_offset, ENC_ASCII), NULL, 10));
+ if(rtpproxy_establish_conversation){
+ pt = (guint)strtoul(tvb_format_text(tvb,begin+offset,new_offset),NULL,10);
+ dissector_add_uint("rtp.pt", pt, rtp_events_handle);
+ }
+ offset += new_offset;
+ break;
+ case 'm':
+ new_offset = (gint)strspn(rawstr+offset, "0123456789=,");
+ /* TODO */
+ offset += new_offset;
+ break;
+ case 'p':
+ another_tree = proto_item_add_subtree(ti, ett_rtpproxy_command_parameters_proto);
+ proto_tree_add_item(another_tree, hf_rtpproxy_command_parameter_proto, tvb, begin+offset, 1, ENC_NA);
+ offset++;
+ break;
+ case 't':
+ new_offset = (gint)strspn(rawstr+offset, "0123456789");
+ another_tree = proto_item_add_subtree(ti, ett_rtpproxy_command_parameters_transcode);
+ ti = proto_tree_add_uint(another_tree, hf_rtpproxy_command_parameter_transcode, tvb, begin+offset, new_offset,
+ (guint16) g_ascii_strtoull((gchar*)tvb_get_string_enc(wmem_packet_scope(), tvb, begin+offset, new_offset, ENC_ASCII), NULL, 10));
+ proto_item_append_text(ti, " (%s)", val_to_str_ext((guint)strtoul(tvb_format_text(tvb,begin+offset, new_offset),NULL,10), &rtp_payload_type_vals_ext, "Unknown"));
+ offset += new_offset;
+ break;
+ case 'v':
+ another_tree = proto_item_add_subtree(ti, ett_rtpproxy_command_parameters_acc);
+ proto_tree_add_item(another_tree, hf_rtpproxy_command_parameter_acc, tvb, begin+offset, 1, ENC_NA);
+ offset++;
+ break;
+ default:
+ break;
+ }
+ }
}
static rtpproxy_info_t *
rtpproxy_add_tid(gboolean is_request, tvbuff_t *tvb, packet_info *pinfo, proto_tree *rtpproxy_tree, rtpproxy_conv_info_t *rtpproxy_conv, gchar* cookie)
{
- rtpproxy_info_t *rtpproxy_info;
- proto_item *pi;
-
- if (!PINFO_FD_VISITED(pinfo)) {
- if (is_request){
- rtpproxy_info = wmem_new(wmem_file_scope(), rtpproxy_info_t);
- rtpproxy_info->req_frame = PINFO_FD_NUM(pinfo);
- rtpproxy_info->resp_frame = 0;
- rtpproxy_info->req_time = pinfo->fd->abs_ts;
- rtpproxy_info->callid = NULL;
- wmem_tree_insert_string(rtpproxy_conv->trans, cookie, rtpproxy_info, 0);
- } else {
- rtpproxy_info = (rtpproxy_info_t *)wmem_tree_lookup_string(rtpproxy_conv->trans, cookie, 0);
- if (rtpproxy_info) {
- rtpproxy_info->resp_frame = PINFO_FD_NUM(pinfo);
- }
- }
- } else {
- rtpproxy_info = (rtpproxy_info_t *)wmem_tree_lookup_string(rtpproxy_conv->trans, cookie, 0);
- if (rtpproxy_info && (is_request ? rtpproxy_info->resp_frame : rtpproxy_info->req_frame)) {
- nstime_t ns;
-
- pi = proto_tree_add_uint(rtpproxy_tree, is_request ? hf_rtpproxy_response_in : hf_rtpproxy_request_in, tvb, 0, 0, is_request ? rtpproxy_info->resp_frame : rtpproxy_info->req_frame);
- PROTO_ITEM_SET_GENERATED(pi);
-
- /* If reply then calculate response time */
- if (!is_request){
- nstime_delta(&ns, &pinfo->fd->abs_ts, &rtpproxy_info->req_time);
- pi = proto_tree_add_time(rtpproxy_tree, hf_rtpproxy_response_time, tvb, 0, 0, &ns);
- PROTO_ITEM_SET_GENERATED(pi);
- if (nstime_cmp(&rtpproxy_timeout_ns, &ns) < 0)
- expert_add_info_format(pinfo, rtpproxy_tree, &ei_rtpproxy_timeout, "Response timeout %.3f seconds", nstime_to_sec(&ns));
- }
- }
- }
- /* Could be NULL so we should check it before dereferencing */
- return rtpproxy_info;
+ rtpproxy_info_t *rtpproxy_info;
+ proto_item *pi;
+
+ if (!PINFO_FD_VISITED(pinfo)) {
+ if (is_request){
+ rtpproxy_info = wmem_new(wmem_file_scope(), rtpproxy_info_t);
+ rtpproxy_info->req_frame = PINFO_FD_NUM(pinfo);
+ rtpproxy_info->resp_frame = 0;
+ rtpproxy_info->req_time = pinfo->fd->abs_ts;
+ rtpproxy_info->callid = NULL;
+ wmem_tree_insert_string(rtpproxy_conv->trans, cookie, rtpproxy_info, 0);
+ } else {
+ rtpproxy_info = (rtpproxy_info_t *)wmem_tree_lookup_string(rtpproxy_conv->trans, cookie, 0);
+ if (rtpproxy_info) {
+ rtpproxy_info->resp_frame = PINFO_FD_NUM(pinfo);
+ }
+ }
+ } else {
+ rtpproxy_info = (rtpproxy_info_t *)wmem_tree_lookup_string(rtpproxy_conv->trans, cookie, 0);
+ if (rtpproxy_info && (is_request ? rtpproxy_info->resp_frame : rtpproxy_info->req_frame)) {
+ nstime_t ns;
+
+ pi = proto_tree_add_uint(rtpproxy_tree, is_request ? hf_rtpproxy_response_in : hf_rtpproxy_request_in, tvb, 0, 0, is_request ? rtpproxy_info->resp_frame : rtpproxy_info->req_frame);
+ PROTO_ITEM_SET_GENERATED(pi);
+
+ /* If reply then calculate response time */
+ if (!is_request){
+ nstime_delta(&ns, &pinfo->fd->abs_ts, &rtpproxy_info->req_time);
+ pi = proto_tree_add_time(rtpproxy_tree, hf_rtpproxy_response_time, tvb, 0, 0, &ns);
+ PROTO_ITEM_SET_GENERATED(pi);
+ if (nstime_cmp(&rtpproxy_timeout_ns, &ns) < 0)
+ expert_add_info_format(pinfo, rtpproxy_tree, &ei_rtpproxy_timeout, "Response timeout %.3f seconds", nstime_to_sec(&ns));
+ }
+ }
+ }
+ /* Could be NULL so we should check it before dereferencing */
+ return rtpproxy_info;
}
static void
rtpproxy_add_notify_addr(tvbuff_t *tvb, packet_info *pinfo, proto_tree *rtpproxy_tree, guint begin, guint end)
{
- gint offset = 0;
- gint tmp = 0;
- gboolean ipv6 = FALSE;
- guint32 ipaddr[4]; /* Enough room for IPv4 or IPv6 */
- proto_item *ti;
-
- /* Check for at least one colon */
- offset = tvb_find_guint8(tvb, begin, end, ':');
- if(offset != -1){
- /* Find if it's the latest colon (not in case of a IPv6) */
- while((tmp = tvb_find_guint8(tvb, offset+1, end, ':')) != -1){
- ipv6 = TRUE;
- offset = tmp;
- }
- /* We have ip:port */
- if(ipv6){
- if(str_to_ip6((char*)tvb_get_string_enc(wmem_packet_scope(), tvb, begin, offset - begin, ENC_ASCII), ipaddr))
- proto_tree_add_ipv6(rtpproxy_tree, hf_rtpproxy_notify_ipv6, tvb, begin, offset - begin, (const guint8 *)ipaddr);
- else
- proto_tree_add_expert(rtpproxy_tree, pinfo, &ei_rtpproxy_bad_ipv6, tvb, begin, offset - begin);
- }
- else{
- if(str_to_ip((char*)tvb_get_string_enc(wmem_packet_scope(), tvb, begin, offset - begin, ENC_ASCII), ipaddr))
- proto_tree_add_ipv4(rtpproxy_tree, hf_rtpproxy_notify_ipv4, tvb, begin, offset - begin, ipaddr[0]);
- else
- proto_tree_add_expert(rtpproxy_tree, pinfo, &ei_rtpproxy_bad_ipv4, tvb, begin, offset - begin);
- }
- proto_tree_add_uint(rtpproxy_tree, hf_rtpproxy_notify_port, tvb, offset+1, end - (offset+1),
- (guint16) g_ascii_strtoull((gchar*)tvb_get_string_enc(wmem_packet_scope(), tvb, offset+1, end - (offset+1), ENC_ASCII), NULL, 10));
- }
- else{
- /* Only port is supplied - take IPv4/IPv6 from ip.src/ipv6.src respectively */
- expert_add_info(pinfo, rtpproxy_tree, &ei_rtpproxy_notify_no_ip);
- if (pinfo->src.type == AT_IPv4)
- ti = proto_tree_add_ipv4(rtpproxy_tree, hf_rtpproxy_notify_ipv4, tvb, begin, 0, ((guint32*)(pinfo->src.data))[0]);
- else
- ti = proto_tree_add_ipv6(rtpproxy_tree, hf_rtpproxy_notify_ipv6, tvb, begin, 0, (const guint8 *)(pinfo->src.data));
- PROTO_ITEM_SET_GENERATED(ti);
- proto_tree_add_uint(rtpproxy_tree, hf_rtpproxy_notify_port, tvb, begin, end - begin,
- (guint16) g_ascii_strtoull((gchar*)tvb_get_string_enc(wmem_packet_scope(), tvb, begin, end - begin, ENC_ASCII), NULL, 10));
- }
+ gint offset = 0;
+ gint tmp = 0;
+ gboolean ipv6 = FALSE;
+ guint32 ipaddr[4]; /* Enough room for IPv4 or IPv6 */
+ proto_item *ti;
+
+ /* Check for at least one colon */
+ offset = tvb_find_guint8(tvb, begin, end, ':');
+ if(offset != -1){
+ /* Find if it's the latest colon (not in case of a IPv6) */
+ while((tmp = tvb_find_guint8(tvb, offset+1, end, ':')) != -1){
+ ipv6 = TRUE;
+ offset = tmp;
+ }
+ /* We have ip:port */
+ if(ipv6){
+ if(str_to_ip6((char*)tvb_get_string_enc(wmem_packet_scope(), tvb, begin, offset - begin, ENC_ASCII), ipaddr))
+ proto_tree_add_ipv6(rtpproxy_tree, hf_rtpproxy_notify_ipv6, tvb, begin, offset - begin, (const guint8 *)ipaddr);
+ else
+ proto_tree_add_expert(rtpproxy_tree, pinfo, &ei_rtpproxy_bad_ipv6, tvb, begin, offset - begin);
+ }
+ else{
+ if(str_to_ip((char*)tvb_get_string_enc(wmem_packet_scope(), tvb, begin, offset - begin, ENC_ASCII), ipaddr))
+ proto_tree_add_ipv4(rtpproxy_tree, hf_rtpproxy_notify_ipv4, tvb, begin, offset - begin, ipaddr[0]);
+ else
+ proto_tree_add_expert(rtpproxy_tree, pinfo, &ei_rtpproxy_bad_ipv4, tvb, begin, offset - begin);
+ }
+ proto_tree_add_uint(rtpproxy_tree, hf_rtpproxy_notify_port, tvb, offset+1, end - (offset+1),
+ (guint16) g_ascii_strtoull((gchar*)tvb_get_string_enc(wmem_packet_scope(), tvb, offset+1, end - (offset+1), ENC_ASCII), NULL, 10));
+ }
+ else{
+ /* Only port is supplied - take IPv4/IPv6 from ip.src/ipv6.src respectively */
+ expert_add_info(pinfo, rtpproxy_tree, &ei_rtpproxy_notify_no_ip);
+ if (pinfo->src.type == AT_IPv4)
+ ti = proto_tree_add_ipv4(rtpproxy_tree, hf_rtpproxy_notify_ipv4, tvb, begin, 0, ((guint32*)(pinfo->src.data))[0]);
+ else
+ ti = proto_tree_add_ipv6(rtpproxy_tree, hf_rtpproxy_notify_ipv6, tvb, begin, 0, (const guint8 *)(pinfo->src.data));
+ PROTO_ITEM_SET_GENERATED(ti);
+ proto_tree_add_uint(rtpproxy_tree, hf_rtpproxy_notify_port, tvb, begin, end - begin,
+ (guint16) g_ascii_strtoull((gchar*)tvb_get_string_enc(wmem_packet_scope(), tvb, begin, end - begin, ENC_ASCII), NULL, 10));
+ }
}
static int
dissect_rtpproxy(tvbuff_t *tvb, packet_info *pinfo, proto_tree *tree, void *data _U_)
{
- gboolean has_lf = FALSE;
- gint offset = 0;
- gint new_offset = 0;
- guint tmp;
- guint tmp2;
- gint realsize = 0;
- guint8* rawstr;
- guint8* tmpstr;
- proto_item *ti;
- proto_item *ti2;
- proto_tree *rtpproxy_tree;
- conversation_t *conversation;
- rtpproxy_conv_info_t *rtpproxy_conv;
- gchar* cookie = NULL;
- /* For RT(C)P setup */
- address addr;
- guint16 port;
- guint32 ipaddr[4]; /* Enough room for IPv4 or IPv6 */
- rtpproxy_info_t *rtpproxy_info = NULL;
- tvbuff_t *subtvb;
-
- /* If it does not start with a printable character it's not RTPProxy */
- if(!isprint(tvb_get_guint8(tvb, 0)))
- return 0;
-
- /* Extract Cookie */
- offset = tvb_find_guint8(tvb, offset, -1, ' ');
- if(offset == -1)
- return 0;
-
- /* Clear out stuff in the info column - we''l set it later */
- col_clear(pinfo->cinfo, COL_INFO);
-
- ti = proto_tree_add_item(tree, proto_rtpproxy, tvb, 0, -1, ENC_NA);
- rtpproxy_tree = proto_item_add_subtree(ti, ett_rtpproxy);
-
- proto_tree_add_item(rtpproxy_tree, hf_rtpproxy_cookie, tvb, 0, offset, ENC_ASCII | ENC_NA);
- cookie = tvb_get_string_enc(wmem_packet_scope(), tvb, 0, offset, ENC_ASCII);
-
- /* Skip whitespace */
- offset = tvb_skip_wsp(tvb, offset+1, -1);
-
- /* Calculate size to prevent recalculation in the future */
- realsize = tvb_reported_length(tvb);
-
-
- /* Check for LF (required for TCP connection, optional for UDP) */
- if (tvb_get_guint8(tvb, realsize - 1) == '\n'){
- col_set_str(pinfo->cinfo, COL_PROTOCOL, "RTPproxy");
- /* Don't count trailing LF */
- realsize -= 1;
- has_lf = TRUE;
- }
- else
- col_set_str(pinfo->cinfo, COL_PROTOCOL, "RTPproxy (no LF)"); /* FIXME replace with expert info field */
-
-
- /* Try to create conversation */
- conversation = find_or_create_conversation(pinfo);
- rtpproxy_conv = (rtpproxy_conv_info_t *)conversation_get_proto_data(conversation, proto_rtpproxy);
- if (!rtpproxy_conv) {
- rtpproxy_conv = wmem_new(wmem_file_scope(), rtpproxy_conv_info_t);
- rtpproxy_conv->trans = wmem_tree_new(wmem_file_scope());
- conversation_add_proto_data(conversation, proto_rtpproxy, rtpproxy_conv);
- }
-
- /* Get payload string */
- rawstr = tvb_get_string_enc(wmem_packet_scope(), tvb, offset, realsize - offset, ENC_ASCII);
-
- /* Extract command */
- tmp = g_ascii_tolower(tvb_get_guint8(tvb, offset));
- switch (tmp)
- {
- case 's':
- /* A specific case - long statistics answer */
- /* %COOKIE% sessions created %NUM0% active sessions: %NUM1% */
- rtpproxy_add_tid(FALSE, tvb, pinfo, rtpproxy_tree, rtpproxy_conv, cookie);
- if ('e' == tvb_get_guint8(tvb, offset+1)){
- col_add_fstr(pinfo->cinfo, COL_INFO, "Reply: %s", rawstr);
- ti = proto_tree_add_item(rtpproxy_tree, hf_rtpproxy_reply, tvb, offset, -1, ENC_NA);
-
- rtpproxy_tree = proto_item_add_subtree(ti, ett_rtpproxy_reply);
- proto_tree_add_item(rtpproxy_tree, hf_rtpproxy_status, tvb, offset, realsize - offset, ENC_ASCII | ENC_NA);
- break;
- }
- case 'i':
- case 'x':
- case 'u':
- case 'l':
- case 'd':
- tmp2 = tvb_get_guint8(tvb, offset+1);
- if(('1' <= tmp2) && (tmp2 <= '9') && (tvb_get_guint8(tvb, offset+2) == ':')){
- col_add_fstr(pinfo->cinfo, COL_INFO, "RTPproxy-ng: %s", rawstr);
- ti = proto_tree_add_item(rtpproxy_tree, hf_rtpproxy_ng_bencode, tvb, offset, -1, ENC_ASCII | ENC_NA);
- rtpproxy_tree = proto_item_add_subtree(ti, ett_rtpproxy_ng_bencode);
- subtvb = tvb_new_subset_remaining(tvb, offset);
- call_dissector(bencode_handle, subtvb, pinfo, rtpproxy_tree);
- break;
- }
- case 'p':
- case 'v':
- case 'r':
- case 'c':
- case 'q':
- rtpproxy_info = rtpproxy_add_tid(TRUE, tvb, pinfo, rtpproxy_tree, rtpproxy_conv, cookie);
- col_add_fstr(pinfo->cinfo, COL_INFO, "Request: %s", rawstr);
- ti = proto_tree_add_item(rtpproxy_tree, hf_rtpproxy_request, tvb, offset, -1, ENC_NA);
- rtpproxy_tree = proto_item_add_subtree(ti, ett_rtpproxy_request);
-
- /* A specific case - version request */
- if ((tmp == 'v') && (offset + (gint)strlen("VF YYYMMDD") + 1 == realsize)){
- /* Skip whitespace */
- new_offset = tvb_skip_wsp(tvb, offset + ((guint)strlen("VF") + 1), -1);
- ti = proto_tree_add_item(rtpproxy_tree, hf_rtpproxy_version_request, tvb, new_offset, (gint)strlen("YYYYMMDD"), ENC_ASCII | ENC_NA);
- tmpstr = tvb_get_string_enc(wmem_packet_scope(), tvb, new_offset, (gint)strlen("YYYYMMDD"), ENC_ASCII);
- proto_item_append_text(ti, " (%s)", str_to_str(tmpstr, versiontypenames, "Unknown"));
- break;
- }
-
- /* All other commands */
- ti = proto_tree_add_item(rtpproxy_tree, hf_rtpproxy_command, tvb, offset, 1, ENC_NA);
-
- /* A specific case - handshake/ping */
- if (tmp == 'v')
- break; /* No more parameters */
-
- /* A specific case - close all calls */
- if (tmp == 'x')
- break; /* No more parameters */
-
- /* Extract parameters */
- /* Parameters should be right after the command and before EOL (in case of Info command) or before whitespace */
- new_offset = (tmp == 'i' ? (realsize - 1 > offset ? offset + (gint)strlen("Ib") : offset + (gint)strlen("I")) : tvb_find_guint8(tvb, offset, -1, ' '));
-
- if (new_offset != offset + 1){
- rtpproxy_tree = proto_item_add_subtree(ti, ett_rtpproxy_command);
- ti2 = proto_tree_add_item(rtpproxy_tree, hf_rtpproxy_command_parameters, tvb, offset+1, new_offset - (offset+1), ENC_ASCII | ENC_NA);
- rtpproxy_add_parameter(tvb, pinfo, proto_item_add_subtree(ti2, ett_rtpproxy_command_parameters), offset+1, new_offset - (offset+1));
- rtpproxy_tree = proto_item_get_parent(ti);
- }
-
- /* A specific case - query information */
- if (tmp == 'i')
- break; /* No more parameters */
-
- /* Skip whitespace */
- offset = tvb_skip_wsp(tvb, new_offset+1, -1);
-
- /* Extract Call-ID */
- new_offset = tvb_find_guint8(tvb, offset, -1, ' ');
- proto_tree_add_item(rtpproxy_tree, hf_rtpproxy_callid, tvb, offset, new_offset - offset, ENC_ASCII | ENC_NA);
- if(rtpproxy_info && !rtpproxy_info->callid)
- rtpproxy_info->callid = tvb_get_string_enc(wmem_file_scope(), tvb, offset, new_offset - offset, ENC_ASCII);
- /* Skip whitespace */
- offset = tvb_skip_wsp(tvb, new_offset+1, -1);
-
- /* Extract IP and Port in case of Offer/Answer */
- if ((tmp == 'u') || (tmp == 'l')){
- /* Extract IP */
- new_offset = tvb_find_guint8(tvb, offset, -1, ' ');
- if (tvb_find_guint8(tvb, offset, new_offset - offset, ':') == -1){
- if(str_to_ip((char*)tvb_get_string_enc(wmem_packet_scope(), tvb, offset, new_offset - offset, ENC_ASCII), ipaddr))
- proto_tree_add_ipv4(rtpproxy_tree, hf_rtpproxy_ipv4, tvb, offset, new_offset - offset, ipaddr[0]);
- else
- proto_tree_add_expert(rtpproxy_tree, pinfo, &ei_rtpproxy_bad_ipv4, tvb, offset, new_offset - offset);
- }
- else{
- if(str_to_ip6((char*)tvb_get_string_enc(wmem_packet_scope(), tvb, offset, new_offset - offset, ENC_ASCII), ipaddr))
- proto_tree_add_ipv6(rtpproxy_tree, hf_rtpproxy_ipv6, tvb, offset, new_offset - offset, (const guint8 *)ipaddr);
- else
- proto_tree_add_expert(rtpproxy_tree, pinfo, &ei_rtpproxy_bad_ipv6, tvb, offset, new_offset - offset);
- }
- /* Skip whitespace */
- offset = tvb_skip_wsp(tvb, new_offset+1, -1);
-
- /* Extract Port */
- new_offset = tvb_find_guint8(tvb, offset, -1, ' ');
- proto_tree_add_uint(rtpproxy_tree, hf_rtpproxy_port, tvb, offset, new_offset - offset,
- (guint16) g_ascii_strtoull((gchar*)tvb_get_string_enc(wmem_packet_scope(), tvb, offset, new_offset - offset, ENC_ASCII), NULL, 10));
- /* Skip whitespace */
- offset = tvb_skip_wsp(tvb, new_offset+1, -1);
- }
-
- /* Extract Copy target */
- if (tmp == 'c'){
- new_offset = tvb_find_guint8(tvb, offset, -1, ' ');
- proto_tree_add_item(rtpproxy_tree, hf_rtpproxy_copy_target, tvb, offset, new_offset - offset, ENC_ASCII | ENC_NA);
- /* Skip whitespace */
- offset = tvb_skip_wsp(tvb, new_offset+1, -1);
- }
-
- /* Extract Playback file and codecs */
- if (tmp == 'p'){
- /* Extract filename */
- new_offset = tvb_find_guint8(tvb, offset, -1, ' ');
- proto_tree_add_item(rtpproxy_tree, hf_rtpproxy_playback_filename, tvb, offset, new_offset - offset, ENC_ASCII | ENC_NA);
- /* Skip whitespace */
- offset = tvb_skip_wsp(tvb, new_offset+1, -1);
-
- /* Extract codec */
- new_offset = tvb_find_guint8(tvb, offset, -1, ' ');
- proto_tree_add_uint(rtpproxy_tree, hf_rtpproxy_playback_codec, tvb, offset, new_offset - offset,
- (guint16) g_ascii_strtoull((gchar*)tvb_get_string_enc(wmem_packet_scope(), tvb, offset, new_offset - offset, ENC_ASCII), NULL, 10));
- /* Skip whitespace */
- offset = tvb_skip_wsp(tvb, new_offset+1, -1);
- }
-
- /* Extract first tag */
- new_offset = rtpproxy_add_tag(rtpproxy_tree, tvb, offset, realsize);
- if(new_offset == -1)
- break; /* No more parameters */
- /* Skip whitespace */
- offset = tvb_skip_wsp(tvb, new_offset+1, -1);
-
- /* Extract second tag */
- new_offset = rtpproxy_add_tag(rtpproxy_tree, tvb, offset, realsize);
- if(new_offset == -1)
- break; /* No more parameters */
- /* Skip whitespace */
- offset = tvb_skip_wsp(tvb, new_offset+1, -1);
-
- /* Extract Notification address */
- if (tmp == 'u'){
- ti = proto_tree_add_item(rtpproxy_tree, hf_rtpproxy_notify, tvb, offset, realsize - offset, ENC_ASCII | ENC_NA);
- proto_item_set_text(ti, "Notify");
- rtpproxy_tree = proto_item_add_subtree(ti, ett_rtpproxy_notify);
-
- /* Check for NotifyTag parameter (separated by space) */
- new_offset = tvb_find_guint8(tvb, offset, -1, ' ');
- if(new_offset == -1){
- /* NotifyTag wasn't found (we should re-use Call-ID instead) */
- rtpproxy_add_notify_addr(tvb, pinfo, rtpproxy_tree, offset, realsize);
- break; /* No more parameters */
- }
-
- /* NotifyTag was found */
- rtpproxy_add_notify_addr(tvb, pinfo, rtpproxy_tree, offset, new_offset);
- /* Skip whitespace */
- offset = tvb_skip_wsp(tvb, new_offset+1, -1);
-
- proto_tree_add_item(rtpproxy_tree, hf_rtpproxy_notify_tag, tvb, offset, realsize - offset, ENC_ASCII | ENC_NA);
- }
- break;
- case 'a':
- case 'e':
- case '0':
- case '1':
- case '2':
- case '3':
- case '4':
- case '5':
- case '6':
- case '7':
- case '8':
- case '9':
- rtpproxy_info = rtpproxy_add_tid(FALSE, tvb, pinfo, rtpproxy_tree, rtpproxy_conv, cookie);
- if (tmp == 'e')
- col_add_fstr(pinfo->cinfo, COL_INFO, "Error reply: %s", rawstr);
- else
- col_add_fstr(pinfo->cinfo, COL_INFO, "Reply: %s", rawstr);
-
- ti = proto_tree_add_item(rtpproxy_tree, hf_rtpproxy_reply, tvb, offset, -1, ENC_NA);
- rtpproxy_tree = proto_item_add_subtree(ti, ett_rtpproxy_reply);
-
- if(rtpproxy_info && rtpproxy_info->callid){
- ti = proto_tree_add_string(rtpproxy_tree, hf_rtpproxy_callid, tvb, offset, 0, rtpproxy_info->callid);
- PROTO_ITEM_SET_GENERATED(ti);
- }
-
- if (tmp == 'e'){
- tmp = tvb_find_line_end(tvb, offset, -1, &new_offset, FALSE);
- tmpstr = tvb_get_string_enc(wmem_packet_scope(), tvb, offset, tmp, ENC_ASCII);
- ti = proto_tree_add_item(rtpproxy_tree, hf_rtpproxy_error, tvb, offset, (gint)strlen(tmpstr), ENC_ASCII | ENC_NA);
- proto_item_append_text(ti, " (%s)", str_to_str(tmpstr, errortypenames, "Unknown"));
- break;
- }
-
- if (tmp == 'a'){
- /* A specific case - short statistics answer */
- /* %COOKIE% active sessions: %NUM1% */
- proto_tree_add_item(rtpproxy_tree, hf_rtpproxy_status, tvb, offset, realsize - offset, ENC_ASCII | ENC_NA);
- break;
- }
- if ((tmp == '0')&& ((tvb_reported_length(tvb) == (guint)(offset+1))||(tvb_reported_length(tvb) == (guint)(offset+2)))){
- proto_tree_add_item(rtpproxy_tree, hf_rtpproxy_ok, tvb, offset, 1, ENC_ASCII | ENC_NA);
- break;
- }
- if ((tmp == '1') && ((tvb_reported_length(tvb) == (guint)(offset+1))||(tvb_reported_length(tvb) == (guint)(offset+2)))){
- proto_tree_add_item(rtpproxy_tree, hf_rtpproxy_ok, tvb, offset, 1, ENC_ASCII | ENC_NA);
- break;
- }
- if (tvb_reported_length(tvb) == (guint)(offset+9)){
- proto_tree_add_item(rtpproxy_tree, hf_rtpproxy_version_supported, tvb, offset, 8, ENC_ASCII | ENC_NA);
- break;
- }
-
- /* Extract Port */
- new_offset = tvb_find_guint8(tvb, offset, -1, ' ');
- /* Convert port to unsigned 16-bit number */
- port = (guint16) g_ascii_strtoull((gchar*)tvb_get_string_enc(wmem_packet_scope(), tvb, offset, new_offset - offset, ENC_ASCII), NULL, 10);
- proto_tree_add_uint(rtpproxy_tree, hf_rtpproxy_port, tvb, offset, new_offset - offset, port);
- /* Skip whitespace */
- offset = tvb_skip_wsp(tvb, new_offset+1, -1);
-
- /* Extract IP */
- memset(&addr, 0, sizeof(address));
-
- /* Try rtpengine bogus extension first. It appends 4 or
- * 6 depending on type of the IP. See
- * https://github.com/sipwise/rtpengine/blob/master/daemon/call_interfaces.c#L66
- * for further details */
- tmp = tvb_find_guint8(tvb, offset, -1, ' ');
- if(tmp == (guint)(-1)){
- /* No extension - operate normally */
- tmp = tvb_find_line_end(tvb, offset, -1, &new_offset, FALSE);
- }
- else {
- tmp -= offset;
- }
-
- if (tvb_find_guint8(tvb, offset, -1, ':') == -1){
- if (str_to_ip((char*)tvb_get_string_enc(wmem_packet_scope(), tvb, offset, tmp, ENC_ASCII), ipaddr)){
- addr.type = AT_IPv4;
- addr.len = 4;
- addr.data = wmem_memdup(wmem_packet_scope(), ipaddr, 4);
- proto_tree_add_ipv4(rtpproxy_tree, hf_rtpproxy_ipv4, tvb, offset, tmp, ipaddr[0]);
- }
- else
- proto_tree_add_expert(rtpproxy_tree, pinfo, &ei_rtpproxy_bad_ipv4, tvb, offset, tmp);
- }
- else{
- if (str_to_ip6((char*)tvb_get_string_enc(wmem_packet_scope(), tvb, offset, tmp, ENC_ASCII), ipaddr)){
- addr.type = AT_IPv6;
- addr.len = 16;
- addr.data = wmem_memdup(wmem_packet_scope(), ipaddr, 16);
- proto_tree_add_ipv6(rtpproxy_tree, hf_rtpproxy_ipv6, tvb, offset, tmp, (const guint8 *)ipaddr);
- }
- else
- proto_tree_add_expert(rtpproxy_tree, pinfo, &ei_rtpproxy_bad_ipv6, tvb, offset, tmp);
- }
-
- if(rtpproxy_establish_conversation){
- if (rtp_handle) {
- /* FIXME tell if isn't a video stream, and setup codec mapping */
- if (addr.len)
- rtp_add_address(pinfo, &addr, port, 0, "RTPproxy", pinfo->fd->num, 0, NULL);
- }
- if (rtcp_handle) {
- if (addr.len)
- rtcp_add_address(pinfo, &addr, port+1, 0, "RTPproxy", pinfo->fd->num);
- }
- }
- break;
- default:
- break;
- }
- if (has_lf)
- proto_tree_add_item(rtpproxy_tree, hf_rtpproxy_lf, tvb, realsize, 1, ENC_NA);
-
- return tvb_length(tvb);
+ gboolean has_lf = FALSE;
+ gint offset = 0;
+ gint new_offset = 0;
+ guint tmp;
+ guint tmp2;
+ gint realsize = 0;
+ guint8* rawstr;
+ guint8* tmpstr;
+ proto_item *ti;
+ proto_item *ti2;
+ proto_tree *rtpproxy_tree;
+ conversation_t *conversation;
+ rtpproxy_conv_info_t *rtpproxy_conv;
+ gchar* cookie = NULL;
+ /* For RT(C)P setup */
+ address addr;
+ guint16 port;
+ guint32 ipaddr[4]; /* Enough room for IPv4 or IPv6 */
+ rtpproxy_info_t *rtpproxy_info = NULL;
+ tvbuff_t *subtvb;
+
+ /* If it does not start with a printable character it's not RTPProxy */
+ if(!isprint(tvb_get_guint8(tvb, 0)))
+ return 0;
+
+ /* Extract Cookie */
+ offset = tvb_find_guint8(tvb, offset, -1, ' ');
+ if(offset == -1)
+ return 0;
+
+ /* Clear out stuff in the info column - we''l set it later */
+ col_clear(pinfo->cinfo, COL_INFO);
+
+ ti = proto_tree_add_item(tree, proto_rtpproxy, tvb, 0, -1, ENC_NA);
+ rtpproxy_tree = proto_item_add_subtree(ti, ett_rtpproxy);
+
+ proto_tree_add_item(rtpproxy_tree, hf_rtpproxy_cookie, tvb, 0, offset, ENC_ASCII | ENC_NA);
+ cookie = tvb_get_string_enc(wmem_packet_scope(), tvb, 0, offset, ENC_ASCII);
+
+ /* Skip whitespace */
+ offset = tvb_skip_wsp(tvb, offset+1, -1);
+
+ /* Calculate size to prevent recalculation in the future */
+ realsize = tvb_reported_length(tvb);
+
+
+ /* Check for LF (required for TCP connection, optional for UDP) */
+ if (tvb_get_guint8(tvb, realsize - 1) == '\n'){
+ col_set_str(pinfo->cinfo, COL_PROTOCOL, "RTPproxy");
+ /* Don't count trailing LF */
+ realsize -= 1;
+ has_lf = TRUE;
+ }
+ else
+ col_set_str(pinfo->cinfo, COL_PROTOCOL, "RTPproxy (no LF)"); /* FIXME replace with expert info field */
+
+
+ /* Try to create conversation */
+ conversation = find_or_create_conversation(pinfo);
+ rtpproxy_conv = (rtpproxy_conv_info_t *)conversation_get_proto_data(conversation, proto_rtpproxy);
+ if (!rtpproxy_conv) {
+ rtpproxy_conv = wmem_new(wmem_file_scope(), rtpproxy_conv_info_t);
+ rtpproxy_conv->trans = wmem_tree_new(wmem_file_scope());
+ conversation_add_proto_data(conversation, proto_rtpproxy, rtpproxy_conv);
+ }
+
+ /* Get payload string */
+ rawstr = tvb_get_string_enc(wmem_packet_scope(), tvb, offset, realsize - offset, ENC_ASCII);
+
+ /* Extract command */
+ tmp = g_ascii_tolower(tvb_get_guint8(tvb, offset));
+ switch (tmp)
+ {
+ case 's':
+ /* A specific case - long statistics answer */
+ /* %COOKIE% sessions created %NUM0% active sessions: %NUM1% */
+ rtpproxy_add_tid(FALSE, tvb, pinfo, rtpproxy_tree, rtpproxy_conv, cookie);
+ if ('e' == tvb_get_guint8(tvb, offset+1)){
+ col_add_fstr(pinfo->cinfo, COL_INFO, "Reply: %s", rawstr);
+ ti = proto_tree_add_item(rtpproxy_tree, hf_rtpproxy_reply, tvb, offset, -1, ENC_NA);
+
+ rtpproxy_tree = proto_item_add_subtree(ti, ett_rtpproxy_reply);
+ proto_tree_add_item(rtpproxy_tree, hf_rtpproxy_status, tvb, offset, realsize - offset, ENC_ASCII | ENC_NA);
+ break;
+ }
+ case 'i':
+ case 'x':
+ case 'u':
+ case 'l':
+ case 'd':
+ tmp2 = tvb_get_guint8(tvb, offset+1);
+ if(('1' <= tmp2) && (tmp2 <= '9') && (tvb_get_guint8(tvb, offset+2) == ':')){
+ col_add_fstr(pinfo->cinfo, COL_INFO, "RTPproxy-ng: %s", rawstr);
+ ti = proto_tree_add_item(rtpproxy_tree, hf_rtpproxy_ng_bencode, tvb, offset, -1, ENC_ASCII | ENC_NA);
+ rtpproxy_tree = proto_item_add_subtree(ti, ett_rtpproxy_ng_bencode);
+ subtvb = tvb_new_subset_remaining(tvb, offset);
+ call_dissector(bencode_handle, subtvb, pinfo, rtpproxy_tree);
+ break;
+ }
+ case 'p':
+ case 'v':
+ case 'r':
+ case 'c':
+ case 'q':
+ rtpproxy_info = rtpproxy_add_tid(TRUE, tvb, pinfo, rtpproxy_tree, rtpproxy_conv, cookie);
+ col_add_fstr(pinfo->cinfo, COL_INFO, "Request: %s", rawstr);
+ ti = proto_tree_add_item(rtpproxy_tree, hf_rtpproxy_request, tvb, offset, -1, ENC_NA);
+ rtpproxy_tree = proto_item_add_subtree(ti, ett_rtpproxy_request);
+
+ /* A specific case - version request */
+ if ((tmp == 'v') && (offset + (gint)strlen("VF YYYMMDD") + 1 == realsize)){
+ /* Skip whitespace */
+ new_offset = tvb_skip_wsp(tvb, offset + ((guint)strlen("VF") + 1), -1);
+ ti = proto_tree_add_item(rtpproxy_tree, hf_rtpproxy_version_request, tvb, new_offset, (gint)strlen("YYYYMMDD"), ENC_ASCII | ENC_NA);
+ tmpstr = tvb_get_string_enc(wmem_packet_scope(), tvb, new_offset, (gint)strlen("YYYYMMDD"), ENC_ASCII);
+ proto_item_append_text(ti, " (%s)", str_to_str(tmpstr, versiontypenames, "Unknown"));
+ break;
+ }
+
+ /* All other commands */
+ ti = proto_tree_add_item(rtpproxy_tree, hf_rtpproxy_command, tvb, offset, 1, ENC_NA);
+
+ /* A specific case - handshake/ping */
+ if (tmp == 'v')
+ break; /* No more parameters */
+
+ /* A specific case - close all calls */
+ if (tmp == 'x')
+ break; /* No more parameters */
+
+ /* Extract parameters */
+ /* Parameters should be right after the command and before EOL (in case of Info command) or before whitespace */
+ new_offset = (tmp == 'i' ? (realsize - 1 > offset ? offset + (gint)strlen("Ib") : offset + (gint)strlen("I")) : tvb_find_guint8(tvb, offset, -1, ' '));
+
+ if (new_offset != offset + 1){
+ rtpproxy_tree = proto_item_add_subtree(ti, ett_rtpproxy_command);
+ ti2 = proto_tree_add_item(rtpproxy_tree, hf_rtpproxy_command_parameters, tvb, offset+1, new_offset - (offset+1), ENC_ASCII | ENC_NA);
+ rtpproxy_add_parameter(tvb, pinfo, proto_item_add_subtree(ti2, ett_rtpproxy_command_parameters), offset+1, new_offset - (offset+1));
+ rtpproxy_tree = proto_item_get_parent(ti);
+ }
+
+ /* A specific case - query information */
+ if (tmp == 'i')
+ break; /* No more parameters */
+
+ /* Skip whitespace */
+ offset = tvb_skip_wsp(tvb, new_offset+1, -1);
+
+ /* Extract Call-ID */
+ new_offset = tvb_find_guint8(tvb, offset, -1, ' ');
+ proto_tree_add_item(rtpproxy_tree, hf_rtpproxy_callid, tvb, offset, new_offset - offset, ENC_ASCII | ENC_NA);
+ if(rtpproxy_info && !rtpproxy_info->callid)
+ rtpproxy_info->callid = tvb_get_string_enc(wmem_file_scope(), tvb, offset, new_offset - offset, ENC_ASCII);
+ /* Skip whitespace */
+ offset = tvb_skip_wsp(tvb, new_offset+1, -1);
+
+ /* Extract IP and Port in case of Offer/Answer */
+ if ((tmp == 'u') || (tmp == 'l')){
+ /* Extract IP */
+ new_offset = tvb_find_guint8(tvb, offset, -1, ' ');
+ if (tvb_find_guint8(tvb, offset, new_offset - offset, ':') == -1){
+ if(str_to_ip((char*)tvb_get_string_enc(wmem_packet_scope(), tvb, offset, new_offset - offset, ENC_ASCII), ipaddr))
+ proto_tree_add_ipv4(rtpproxy_tree, hf_rtpproxy_ipv4, tvb, offset, new_offset - offset, ipaddr[0]);
+ else
+ proto_tree_add_expert(rtpproxy_tree, pinfo, &ei_rtpproxy_bad_ipv4, tvb, offset, new_offset - offset);
+ }
+ else{
+ if(str_to_ip6((char*)tvb_get_string_enc(wmem_packet_scope(), tvb, offset, new_offset - offset, ENC_ASCII), ipaddr))
+ proto_tree_add_ipv6(rtpproxy_tree, hf_rtpproxy_ipv6, tvb, offset, new_offset - offset, (const guint8 *)ipaddr);
+ else
+ proto_tree_add_expert(rtpproxy_tree, pinfo, &ei_rtpproxy_bad_ipv6, tvb, offset, new_offset - offset);
+ }
+ /* Skip whitespace */
+ offset = tvb_skip_wsp(tvb, new_offset+1, -1);
+
+ /* Extract Port */
+ new_offset = tvb_find_guint8(tvb, offset, -1, ' ');
+ proto_tree_add_uint(rtpproxy_tree, hf_rtpproxy_port, tvb, offset, new_offset - offset,
+ (guint16) g_ascii_strtoull((gchar*)tvb_get_string_enc(wmem_packet_scope(), tvb, offset, new_offset - offset, ENC_ASCII), NULL, 10));
+ /* Skip whitespace */
+ offset = tvb_skip_wsp(tvb, new_offset+1, -1);
+ }
+
+ /* Extract Copy target */
+ if (tmp == 'c'){
+ new_offset = tvb_find_guint8(tvb, offset, -1, ' ');
+ proto_tree_add_item(rtpproxy_tree, hf_rtpproxy_copy_target, tvb, offset, new_offset - offset, ENC_ASCII | ENC_NA);
+ /* Skip whitespace */
+ offset = tvb_skip_wsp(tvb, new_offset+1, -1);
+ }
+
+ /* Extract Playback file and codecs */
+ if (tmp == 'p'){
+ /* Extract filename */
+ new_offset = tvb_find_guint8(tvb, offset, -1, ' ');
+ proto_tree_add_item(rtpproxy_tree, hf_rtpproxy_playback_filename, tvb, offset, new_offset - offset, ENC_ASCII | ENC_NA);
+ /* Skip whitespace */
+ offset = tvb_skip_wsp(tvb, new_offset+1, -1);
+
+ /* Extract codec */
+ new_offset = tvb_find_guint8(tvb, offset, -1, ' ');
+ proto_tree_add_uint(rtpproxy_tree, hf_rtpproxy_playback_codec, tvb, offset, new_offset - offset,
+ (guint16) g_ascii_strtoull((gchar*)tvb_get_string_enc(wmem_packet_scope(), tvb, offset, new_offset - offset, ENC_ASCII), NULL, 10));
+ /* Skip whitespace */
+ offset = tvb_skip_wsp(tvb, new_offset+1, -1);
+ }
+
+ /* Extract first tag */
+ new_offset = rtpproxy_add_tag(rtpproxy_tree, tvb, offset, realsize);
+ if(new_offset == -1)
+ break; /* No more parameters */
+ /* Skip whitespace */
+ offset = tvb_skip_wsp(tvb, new_offset+1, -1);
+
+ /* Extract second tag */
+ new_offset = rtpproxy_add_tag(rtpproxy_tree, tvb, offset, realsize);
+ if(new_offset == -1)
+ break; /* No more parameters */
+ /* Skip whitespace */
+ offset = tvb_skip_wsp(tvb, new_offset+1, -1);
+
+ /* Extract Notification address */
+ if (tmp == 'u'){
+ ti = proto_tree_add_item(rtpproxy_tree, hf_rtpproxy_notify, tvb, offset, realsize - offset, ENC_ASCII | ENC_NA);
+ proto_item_set_text(ti, "Notify");
+ rtpproxy_tree = proto_item_add_subtree(ti, ett_rtpproxy_notify);
+
+ /* Check for NotifyTag parameter (separated by space) */
+ new_offset = tvb_find_guint8(tvb, offset, -1, ' ');
+ if(new_offset == -1){
+ /* NotifyTag wasn't found (we should re-use Call-ID instead) */
+ rtpproxy_add_notify_addr(tvb, pinfo, rtpproxy_tree, offset, realsize);
+ break; /* No more parameters */
+ }
+
+ /* NotifyTag was found */
+ rtpproxy_add_notify_addr(tvb, pinfo, rtpproxy_tree, offset, new_offset);
+ /* Skip whitespace */
+ offset = tvb_skip_wsp(tvb, new_offset+1, -1);
+
+ proto_tree_add_item(rtpproxy_tree, hf_rtpproxy_notify_tag, tvb, offset, realsize - offset, ENC_ASCII | ENC_NA);
+ }
+ break;
+ case 'a':
+ case 'e':
+ case '0':
+ case '1':
+ case '2':
+ case '3':
+ case '4':
+ case '5':
+ case '6':
+ case '7':
+ case '8':
+ case '9':
+ rtpproxy_info = rtpproxy_add_tid(FALSE, tvb, pinfo, rtpproxy_tree, rtpproxy_conv, cookie);
+ if (tmp == 'e')
+ col_add_fstr(pinfo->cinfo, COL_INFO, "Error reply: %s", rawstr);
+ else
+ col_add_fstr(pinfo->cinfo, COL_INFO, "Reply: %s", rawstr);
+
+ ti = proto_tree_add_item(rtpproxy_tree, hf_rtpproxy_reply, tvb, offset, -1, ENC_NA);
+ rtpproxy_tree = proto_item_add_subtree(ti, ett_rtpproxy_reply);
+
+ if(rtpproxy_info && rtpproxy_info->callid){
+ ti = proto_tree_add_string(rtpproxy_tree, hf_rtpproxy_callid, tvb, offset, 0, rtpproxy_info->callid);
+ PROTO_ITEM_SET_GENERATED(ti);
+ }
+
+ if (tmp == 'e'){
+ tmp = tvb_find_line_end(tvb, offset, -1, &new_offset, FALSE);
+ tmpstr = tvb_get_string_enc(wmem_packet_scope(), tvb, offset, tmp, ENC_ASCII);
+ ti = proto_tree_add_item(rtpproxy_tree, hf_rtpproxy_error, tvb, offset, (gint)strlen(tmpstr), ENC_ASCII | ENC_NA);
+ proto_item_append_text(ti, " (%s)", str_to_str(tmpstr, errortypenames, "Unknown"));
+ break;
+ }
+
+ if (tmp == 'a'){
+ /* A specific case - short statistics answer */
+ /* %COOKIE% active sessions: %NUM1% */
+ proto_tree_add_item(rtpproxy_tree, hf_rtpproxy_status, tvb, offset, realsize - offset, ENC_ASCII | ENC_NA);
+ break;
+ }
+ if ((tmp == '0')&& ((tvb_reported_length(tvb) == (guint)(offset+1))||(tvb_reported_length(tvb) == (guint)(offset+2)))){
+ proto_tree_add_item(rtpproxy_tree, hf_rtpproxy_ok, tvb, offset, 1, ENC_ASCII | ENC_NA);
+ break;
+ }
+ if ((tmp == '1') && ((tvb_reported_length(tvb) == (guint)(offset+1))||(tvb_reported_length(tvb) == (guint)(offset+2)))){
+ proto_tree_add_item(rtpproxy_tree, hf_rtpproxy_ok, tvb, offset, 1, ENC_ASCII | ENC_NA);
+ break;
+ }
+ if (tvb_reported_length(tvb) == (guint)(offset+9)){
+ proto_tree_add_item(rtpproxy_tree, hf_rtpproxy_version_supported, tvb, offset, 8, ENC_ASCII | ENC_NA);
+ break;
+ }
+
+ /* Extract Port */
+ new_offset = tvb_find_guint8(tvb, offset, -1, ' ');
+ /* Convert port to unsigned 16-bit number */
+ port = (guint16) g_ascii_strtoull((gchar*)tvb_get_string_enc(wmem_packet_scope(), tvb, offset, new_offset - offset, ENC_ASCII), NULL, 10);
+ proto_tree_add_uint(rtpproxy_tree, hf_rtpproxy_port, tvb, offset, new_offset - offset, port);
+ /* Skip whitespace */
+ offset = tvb_skip_wsp(tvb, new_offset+1, -1);
+
+ /* Extract IP */
+ memset(&addr, 0, sizeof(address));
+
+ /* Try rtpengine bogus extension first. It appends 4 or
+ * 6 depending on type of the IP. See
+ * https://github.com/sipwise/rtpengine/blob/master/daemon/call_interfaces.c#L66
+ * for further details */
+ tmp = tvb_find_guint8(tvb, offset, -1, ' ');
+ if(tmp == (guint)(-1)){
+ /* No extension - operate normally */
+ tmp = tvb_find_line_end(tvb, offset, -1, &new_offset, FALSE);
+ }
+ else {
+ tmp -= offset;
+ }
+
+ if (tvb_find_guint8(tvb, offset, -1, ':') == -1){
+ if (str_to_ip((char*)tvb_get_string_enc(wmem_packet_scope(), tvb, offset, tmp, ENC_ASCII), ipaddr)){
+ addr.type = AT_IPv4;
+ addr.len = 4;
+ addr.data = wmem_memdup(wmem_packet_scope(), ipaddr, 4);
+ proto_tree_add_ipv4(rtpproxy_tree, hf_rtpproxy_ipv4, tvb, offset, tmp, ipaddr[0]);
+ }
+ else
+ proto_tree_add_expert(rtpproxy_tree, pinfo, &ei_rtpproxy_bad_ipv4, tvb, offset, tmp);
+ }
+ else{
+ if (str_to_ip6((char*)tvb_get_string_enc(wmem_packet_scope(), tvb, offset, tmp, ENC_ASCII), ipaddr)){
+ addr.type = AT_IPv6;
+ addr.len = 16;
+ addr.data = wmem_memdup(wmem_packet_scope(), ipaddr, 16);
+ proto_tree_add_ipv6(rtpproxy_tree, hf_rtpproxy_ipv6, tvb, offset, tmp, (const guint8 *)ipaddr);
+ }
+ else
+ proto_tree_add_expert(rtpproxy_tree, pinfo, &ei_rtpproxy_bad_ipv6, tvb, offset, tmp);
+ }
+
+ if(rtpproxy_establish_conversation){
+ if (rtp_handle) {
+ /* FIXME tell if isn't a video stream, and setup codec mapping */
+ if (addr.len)
+ rtp_add_address(pinfo, &addr, port, 0, "RTPproxy", pinfo->fd->num, 0, NULL);
+ }
+ if (rtcp_handle) {
+ if (addr.len)
+ rtcp_add_address(pinfo, &addr, port+1, 0, "RTPproxy", pinfo->fd->num);
+ }
+ }
+ break;
+ default:
+ break;
+ }
+ if (has_lf)
+ proto_tree_add_item(rtpproxy_tree, hf_rtpproxy_lf, tvb, realsize, 1, ENC_NA);
+
+ return tvb_length(tvb);
}
void
proto_register_rtpproxy(void)
{
- module_t *rtpproxy_module;
- expert_module_t* expert_rtpproxy_module;
-
- static hf_register_info hf[] = {
- {
- &hf_rtpproxy_cookie,
- {
- "Cookie",
- "rtpproxy.cookie",
- FT_STRING,
- BASE_NONE,
- NULL,
- 0x0,
- NULL,
- HFILL
- }
- },
- {
- &hf_rtpproxy_version_request,
- {
- "Version Request",
- "rtpproxy.version",
- FT_STRING,
- BASE_NONE,
- NULL,
- 0x0,
- NULL,
- HFILL
- }
- },
- {
- &hf_rtpproxy_version_supported,
- {
- "Version Supported",
- "rtpproxy.version_supported",
- FT_STRING,
- BASE_NONE,
- NULL,
- 0x0,
- NULL,
- HFILL
- }
- },
- {
- &hf_rtpproxy_error,
- {
- "Error",
- "rtpproxy.error",
- FT_STRING,
- BASE_NONE,
- NULL,
- 0x0,
- NULL,
- HFILL
- }
- },
- {
- &hf_rtpproxy_ok,
- {
- "Ok",
- "rtpproxy.ok",
- FT_UINT8,
- BASE_DEC,
- VALS(oktypenames),
- 0x0,
- NULL,
- HFILL
- }
- },
- {
- &hf_rtpproxy_status,
- {
- "Status",
- "rtpproxy.status",
- FT_STRING,
- BASE_NONE,
- NULL,
- 0x0,
- NULL,
- HFILL
- }
- },
- {
- &hf_rtpproxy_ipv4,
- {
- "IPv4",
- "rtpproxy.ipv4",
- FT_IPv4,
- BASE_NONE,
- NULL,
- 0x0,
- NULL,
- HFILL
- }
- },
- {
- &hf_rtpproxy_ipv6,
- {
- "IPv6",
- "rtpproxy.ipv6",
- FT_IPv6,
- BASE_NONE,
- NULL,
- 0x0,
- NULL,
- HFILL
- }
- },
- {
- &hf_rtpproxy_port,
- {
- "Port",
- "rtpproxy.port",
- FT_UINT16, /* 0 - 65535 */
- BASE_DEC,
- NULL,
- 0x0,
- NULL,
- HFILL
- }
- },
- {
- &hf_rtpproxy_request,
- {
- "Request",
- "rtpproxy.request",
- FT_NONE,
- BASE_NONE,
- NULL,
- 0x0,
- NULL,
- HFILL
- }
- },
- {
- &hf_rtpproxy_command,
- {
- "Command",
- "rtpproxy.command",
- FT_UINT8,
- BASE_DEC,
- VALS(commandtypenames),
- 0x0,
- NULL,
- HFILL
- }
- },
- {
- &hf_rtpproxy_command_parameters,
- {
- "Command parameters",
- "rtpproxy.command_parameters",
- FT_STRING,
- BASE_NONE,
- NULL,
- 0x0,
- NULL,
- HFILL
- }
- },
- {
- &hf_rtpproxy_command_parameter,
- {
- "Parameter",
- "rtpproxy.command_parameter",
- FT_UINT8,
- BASE_DEC,
- VALS(paramtypenames),
- 0x0,
- NULL,
- HFILL
- }
- },
- {
- &hf_rtpproxy_command_parameter_codec,
- {
- "Allowed codec",
- "rtpproxy.command_parameter_codec",
- FT_UINT8, /* 0 - 127 */
- BASE_DEC,
- NULL,
- 0x0,
- NULL,
- HFILL
- }
- },
- {
- &hf_rtpproxy_command_parameter_local_ipv4,
- {
- "Local IPv4 address",
- "rtpproxy.command_parameter_local_ipv4",
- FT_IPv4, /* FIXME - is it ever possible to see IPv6 here? */
- BASE_NONE,
- NULL,
- 0x0,
- NULL,
- HFILL
- }
- },
- {
- &hf_rtpproxy_command_parameter_remote_ipv4,
- {
- "Remote IPv4 address",
- "rtpproxy.command_parameter_remote_ipv4",
- FT_IPv4, /* FIXME - is it ever possible to see IPv6 here? */
- BASE_NONE,
- NULL,
- 0x0,
- NULL,
- HFILL
- }
- },
- {
- &hf_rtpproxy_command_parameter_repacketize,
- {
- "Repacketize (ms)",
- "rtpproxy.command_parameter_repacketize",
- FT_UINT16, /* 0 - 1000 milliseconds */
- BASE_DEC,
- NULL,
- 0x0,
- NULL,
- HFILL
- }
- },
- {
- &hf_rtpproxy_command_parameter_dtmf,
- {
- "DTMF payload ID",
- "rtpproxy.command_parameter_dtmf",
- FT_UINT8, /* 0 - 127 */
- BASE_DEC,
- NULL,
- 0x0,
- NULL,
- HFILL
- }
- },
- {
- &hf_rtpproxy_command_parameter_proto,
- {
- "RTP tramsission protocol",
- "rtpproxy.command_parameter_proto",
- FT_UINT8,
- BASE_DEC,
- VALS(prototypenames),
- 0x0,
- NULL,
- HFILL
- }
- },
- {
- &hf_rtpproxy_command_parameter_transcode,
- {
- "Transcode to",
- "rtpproxy.command_parameter_transcode",
- FT_UINT8, /* 0 - 127 */
- BASE_DEC,
- NULL,
- 0x0,
- NULL,
- HFILL
- }
- },
- {
- &hf_rtpproxy_command_parameter_acc,
- {
- "Accounting",
- "rtpproxy.command_parameter_acc",
- FT_UINT8,
- BASE_DEC,
- VALS(acctypenames),
- 0x0,
- NULL,
- HFILL
- }
- },
- {
- &hf_rtpproxy_copy_target,
- {
- "Copy target",
- "rtpproxy.copy_target",
- FT_STRING, /* Filename or UDP address, e.g. /var/tmp/fileXXXX.yyy or IP:Port */
- BASE_NONE,
- NULL,
- 0x0,
- NULL,
- HFILL
- }
- },
- {
- &hf_rtpproxy_playback_filename,
- {
- "Playback filename",
- "rtpproxy.playback_filename",
- FT_STRING,
- BASE_NONE,
- NULL,
- 0x0,
- NULL,
- HFILL
- }
- },
- {
- &hf_rtpproxy_playback_codec,
- {
- "Playback codec",
- "rtpproxy.playback_codec",
- FT_UINT8, /* 0 - 127 */
- BASE_DEC,
- NULL,
- 0x0,
- NULL,
- HFILL
- }
- },
- {
- &hf_rtpproxy_callid,
- {
- "Call-ID",
- "rtpproxy.callid",
- FT_STRING,
- BASE_NONE,
- NULL,
- 0x0,
- NULL,
- HFILL
- }
- },
- {
- &hf_rtpproxy_notify,
- {
- "Notify",
- "rtpproxy.notify",
- FT_STRING,
- BASE_NONE,
- NULL,
- 0x0,
- NULL,
- HFILL
- }
- },
- {
- &hf_rtpproxy_tag,
- {
- "Tag",
- "rtpproxy.tag",
- FT_STRING,
- BASE_NONE,
- NULL,
- 0x0,
- NULL,
- HFILL
- }
- },
- {
- &hf_rtpproxy_mediaid,
- {
- "Media-ID",
- "rtpproxy.mediaid",
- FT_STRING,
- BASE_NONE,
- NULL,
- 0x0,
- NULL,
- HFILL
- }
- },
- {
- &hf_rtpproxy_notify_ipv4,
- {
- "Notification IPv4",
- "rtpproxy.notify_ipv4",
- FT_IPv4,
- BASE_NONE,
- NULL,
- 0x0,
- NULL,
- HFILL
- }
- },
- {
- &hf_rtpproxy_notify_ipv6,
- {
- "Notification IPv6",
- "rtpproxy.notify_ipv6",
- FT_IPv6,
- BASE_NONE,
- NULL,
- 0x0,
- NULL,
- HFILL
- }
- },
- {
- &hf_rtpproxy_notify_port,
- {
- "Notification Port",
- "rtpproxy.notify_port",
- FT_UINT16,
- BASE_DEC,
- NULL,
- 0x0,
- NULL,
- HFILL
- }
- },
- {
- &hf_rtpproxy_notify_tag,
- {
- "Notification Tag",
- "rtpproxy.notify_tag",
- FT_STRING,
- BASE_NONE,
- NULL,
- 0x0,
- NULL,
- HFILL
- }
- },
- {
- &hf_rtpproxy_reply,
- {
- "Reply",
- "rtpproxy.reply",
- FT_NONE,
- BASE_NONE,
- NULL,
- 0x0,
- NULL,
- HFILL
- }
- },
- {
- &hf_rtpproxy_lf,
- {
- "LF",
- "rtpproxy.lf",
- FT_NONE,
- BASE_NONE,
- NULL,
- 0x0,
- NULL,
- HFILL
- }
- },
- {
- &hf_rtpproxy_request_in,
- {
- "Request In",
- "rtpproxy.request_in",
- FT_FRAMENUM,
- BASE_NONE,
- NULL,
- 0x0,
- NULL,
- HFILL
- }
-
- },
- {
- &hf_rtpproxy_response_in,
- {
- "Response In",
- "rtpproxy.response_in",
- FT_FRAMENUM,
- BASE_NONE,
- NULL,
- 0x0,
- NULL,
- HFILL
- }
- },
- {
- &hf_rtpproxy_response_time,
- {
- "Response Time",
- "rtpproxy.response_time",
- FT_RELATIVE_TIME,
- BASE_NONE,
- NULL,
- 0x0,
- "The time between the Request and the Reply",
- HFILL
- }
- },
- {
- &hf_rtpproxy_ng_bencode,
- {
- "RTPproxy-ng bencode packet",
- "rtpproxy.ng.bencode",
- FT_STRING,
- BASE_NONE,
- NULL,
- 0x0,
- "Serialized structure of integers, dictionaries, strings and lists.",
- HFILL
- }
- }
- };
-
- static ei_register_info ei[] = {
- { &ei_rtpproxy_timeout, { "rtpproxy.response_timeout", PI_RESPONSE_CODE, PI_WARN, "TIMEOUT", EXPFILL }},
- { &ei_rtpproxy_notify_no_ip, { "rtpproxy.notify_no_ip", PI_RESPONSE_CODE, PI_COMMENT, "No notification IP address provided. Using ip.src or ipv6.src as a value.", EXPFILL }},
- { &ei_rtpproxy_bad_ipv4, { "rtpproxy.bad_ipv4", PI_MALFORMED, PI_ERROR, "Bad IPv4", EXPFILL }},
- { &ei_rtpproxy_bad_ipv6, { "rtpproxy.bad_ipv6", PI_MALFORMED, PI_ERROR, "Bad IPv6", EXPFILL }},
- };
-
- /* Setup protocol subtree array */
- static gint *ett[] = {
- &ett_rtpproxy,
- &ett_rtpproxy_request,
- &ett_rtpproxy_command,
- &ett_rtpproxy_command_parameters,
- &ett_rtpproxy_command_parameters_codecs,
- &ett_rtpproxy_command_parameters_local,
- &ett_rtpproxy_command_parameters_remote,
- &ett_rtpproxy_command_parameters_repacketize,
- &ett_rtpproxy_command_parameters_dtmf,
- &ett_rtpproxy_command_parameters_cmap,
- &ett_rtpproxy_command_parameters_proto,
- &ett_rtpproxy_command_parameters_transcode,
- &ett_rtpproxy_command_parameters_acc,
- &ett_rtpproxy_tag,
- &ett_rtpproxy_notify,
- &ett_rtpproxy_reply,
- &ett_rtpproxy_ng_bencode
- };
-
- proto_rtpproxy = proto_register_protocol (
- "Sippy RTPproxy Protocol", /* name */
- "RTPproxy", /* short name */
- "rtpproxy" /* abbrev */
- );
-
- proto_register_field_array(proto_rtpproxy, hf, array_length(hf));
- proto_register_subtree_array(ett, array_length(ett));
-
- expert_rtpproxy_module = expert_register_protocol(proto_rtpproxy);
- expert_register_field_array(expert_rtpproxy_module, ei, array_length(ei));
-
- rtpproxy_module = prefs_register_protocol(proto_rtpproxy, proto_reg_handoff_rtpproxy);
-
- prefs_register_uint_preference(rtpproxy_module, "tcp.port",
- "RTPproxy TCP Port", /* Title */
- "RTPproxy TCP Port", /* Descr */
- 10,
- &rtpproxy_tcp_port);
-
- prefs_register_uint_preference(rtpproxy_module, "udp.port",
- "RTPproxy UDP Port", /* Title */
- "RTPproxy UDP Port", /* Descr */
- 10,
- &rtpproxy_udp_port);
-
- prefs_register_bool_preference(rtpproxy_module, "establish_conversation",
+ module_t *rtpproxy_module;
+ expert_module_t* expert_rtpproxy_module;
+
+ static hf_register_info hf[] = {
+ {
+ &hf_rtpproxy_cookie,
+ {
+ "Cookie",
+ "rtpproxy.cookie",
+ FT_STRING,
+ BASE_NONE,
+ NULL,
+ 0x0,
+ NULL,
+ HFILL
+ }
+ },
+ {
+ &hf_rtpproxy_version_request,
+ {
+ "Version Request",
+ "rtpproxy.version",
+ FT_STRING,
+ BASE_NONE,
+ NULL,
+ 0x0,
+ NULL,
+ HFILL
+ }
+ },
+ {
+ &hf_rtpproxy_version_supported,
+ {
+ "Version Supported",
+ "rtpproxy.version_supported",
+ FT_STRING,
+ BASE_NONE,
+ NULL,
+ 0x0,
+ NULL,
+ HFILL
+ }
+ },
+ {
+ &hf_rtpproxy_error,
+ {
+ "Error",
+ "rtpproxy.error",
+ FT_STRING,
+ BASE_NONE,
+ NULL,
+ 0x0,
+ NULL,
+ HFILL
+ }
+ },
+ {
+ &hf_rtpproxy_ok,
+ {
+ "Ok",
+ "rtpproxy.ok",
+ FT_UINT8,
+ BASE_DEC,
+ VALS(oktypenames),
+ 0x0,
+ NULL,
+ HFILL
+ }
+ },
+ {
+ &hf_rtpproxy_status,
+ {
+ "Status",
+ "rtpproxy.status",
+ FT_STRING,
+ BASE_NONE,
+ NULL,
+ 0x0,
+ NULL,
+ HFILL
+ }
+ },
+ {
+ &hf_rtpproxy_ipv4,
+ {
+ "IPv4",
+ "rtpproxy.ipv4",
+ FT_IPv4,
+ BASE_NONE,
+ NULL,
+ 0x0,
+ NULL,
+ HFILL
+ }
+ },
+ {
+ &hf_rtpproxy_ipv6,
+ {
+ "IPv6",
+ "rtpproxy.ipv6",
+ FT_IPv6,
+ BASE_NONE,
+ NULL,
+ 0x0,
+ NULL,
+ HFILL
+ }
+ },
+ {
+ &hf_rtpproxy_port,
+ {
+ "Port",
+ "rtpproxy.port",
+ FT_UINT16, /* 0 - 65535 */
+ BASE_DEC,
+ NULL,
+ 0x0,
+ NULL,
+ HFILL
+ }
+ },
+ {
+ &hf_rtpproxy_request,
+ {
+ "Request",
+ "rtpproxy.request",
+ FT_NONE,
+ BASE_NONE,
+ NULL,
+ 0x0,
+ NULL,
+ HFILL
+ }
+ },
+ {
+ &hf_rtpproxy_command,
+ {
+ "Command",
+ "rtpproxy.command",
+ FT_UINT8,
+ BASE_DEC,
+ VALS(commandtypenames),
+ 0x0,
+ NULL,
+ HFILL
+ }
+ },
+ {
+ &hf_rtpproxy_command_parameters,
+ {
+ "Command parameters",
+ "rtpproxy.command_parameters",
+ FT_STRING,
+ BASE_NONE,
+ NULL,
+ 0x0,
+ NULL,
+ HFILL
+ }
+ },
+ {
+ &hf_rtpproxy_command_parameter,
+ {
+ "Parameter",
+ "rtpproxy.command_parameter",
+ FT_UINT8,
+ BASE_DEC,
+ VALS(paramtypenames),
+ 0x0,
+ NULL,
+ HFILL
+ }
+ },
+ {
+ &hf_rtpproxy_command_parameter_codec,
+ {
+ "Allowed codec",
+ "rtpproxy.command_parameter_codec",
+ FT_UINT8, /* 0 - 127 */
+ BASE_DEC,
+ NULL,
+ 0x0,
+ NULL,
+ HFILL
+ }
+ },
+ {
+ &hf_rtpproxy_command_parameter_local_ipv4,
+ {
+ "Local IPv4 address",
+ "rtpproxy.command_parameter_local_ipv4",
+ FT_IPv4, /* FIXME - is it ever possible to see IPv6 here? */
+ BASE_NONE,
+ NULL,
+ 0x0,
+ NULL,
+ HFILL
+ }
+ },
+ {
+ &hf_rtpproxy_command_parameter_remote_ipv4,
+ {
+ "Remote IPv4 address",
+ "rtpproxy.command_parameter_remote_ipv4",
+ FT_IPv4, /* FIXME - is it ever possible to see IPv6 here? */
+ BASE_NONE,
+ NULL,
+ 0x0,
+ NULL,
+ HFILL
+ }
+ },
+ {
+ &hf_rtpproxy_command_parameter_repacketize,
+ {
+ "Repacketize (ms)",
+ "rtpproxy.command_parameter_repacketize",
+ FT_UINT16, /* 0 - 1000 milliseconds */
+ BASE_DEC,
+ NULL,
+ 0x0,
+ NULL,
+ HFILL
+ }
+ },
+ {
+ &hf_rtpproxy_command_parameter_dtmf,
+ {
+ "DTMF payload ID",
+ "rtpproxy.command_parameter_dtmf",
+ FT_UINT8, /* 0 - 127 */
+ BASE_DEC,
+ NULL,
+ 0x0,
+ NULL,
+ HFILL
+ }
+ },
+ {
+ &hf_rtpproxy_command_parameter_proto,
+ {
+ "RTP tramsission protocol",
+ "rtpproxy.command_parameter_proto",
+ FT_UINT8,
+ BASE_DEC,
+ VALS(prototypenames),
+ 0x0,
+ NULL,
+ HFILL
+ }
+ },
+ {
+ &hf_rtpproxy_command_parameter_transcode,
+ {
+ "Transcode to",
+ "rtpproxy.command_parameter_transcode",
+ FT_UINT8, /* 0 - 127 */
+ BASE_DEC,
+ NULL,
+ 0x0,
+ NULL,
+ HFILL
+ }
+ },
+ {
+ &hf_rtpproxy_command_parameter_acc,
+ {
+ "Accounting",
+ "rtpproxy.command_parameter_acc",
+ FT_UINT8,
+ BASE_DEC,
+ VALS(acctypenames),
+ 0x0,
+ NULL,
+ HFILL
+ }
+ },
+ {
+ &hf_rtpproxy_copy_target,
+ {
+ "Copy target",
+ "rtpproxy.copy_target",
+ FT_STRING, /* Filename or UDP address, e.g. /var/tmp/fileXXXX.yyy or IP:Port */
+ BASE_NONE,
+ NULL,
+ 0x0,
+ NULL,
+ HFILL
+ }
+ },
+ {
+ &hf_rtpproxy_playback_filename,
+ {
+ "Playback filename",
+ "rtpproxy.playback_filename",
+ FT_STRING,
+ BASE_NONE,
+ NULL,
+ 0x0,
+ NULL,
+ HFILL
+ }
+ },
+ {
+ &hf_rtpproxy_playback_codec,
+ {
+ "Playback codec",
+ "rtpproxy.playback_codec",
+ FT_UINT8, /* 0 - 127 */
+ BASE_DEC,
+ NULL,
+ 0x0,
+ NULL,
+ HFILL
+ }
+ },
+ {
+ &hf_rtpproxy_callid,
+ {
+ "Call-ID",
+ "rtpproxy.callid",
+ FT_STRING,
+ BASE_NONE,
+ NULL,
+ 0x0,
+ NULL,
+ HFILL
+ }
+ },
+ {
+ &hf_rtpproxy_notify,
+ {
+ "Notify",
+ "rtpproxy.notify",
+ FT_STRING,
+ BASE_NONE,
+ NULL,
+ 0x0,
+ NULL,
+ HFILL
+ }
+ },
+ {
+ &hf_rtpproxy_tag,
+ {
+ "Tag",
+ "rtpproxy.tag",
+ FT_STRING,
+ BASE_NONE,
+ NULL,
+ 0x0,
+ NULL,
+ HFILL
+ }
+ },
+ {
+ &hf_rtpproxy_mediaid,
+ {
+ "Media-ID",
+ "rtpproxy.mediaid",
+ FT_STRING,
+ BASE_NONE,
+ NULL,
+ 0x0,
+ NULL,
+ HFILL
+ }
+ },
+ {
+ &hf_rtpproxy_notify_ipv4,
+ {
+ "Notification IPv4",
+ "rtpproxy.notify_ipv4",
+ FT_IPv4,
+ BASE_NONE,
+ NULL,
+ 0x0,
+ NULL,
+ HFILL
+ }
+ },
+ {
+ &hf_rtpproxy_notify_ipv6,
+ {
+ "Notification IPv6",
+ "rtpproxy.notify_ipv6",
+ FT_IPv6,
+ BASE_NONE,
+ NULL,
+ 0x0,
+ NULL,
+ HFILL
+ }
+ },
+ {
+ &hf_rtpproxy_notify_port,
+ {
+ "Notification Port",
+ "rtpproxy.notify_port",
+ FT_UINT16,
+ BASE_DEC,
+ NULL,
+ 0x0,
+ NULL,
+ HFILL
+ }
+ },
+ {
+ &hf_rtpproxy_notify_tag,
+ {
+ "Notification Tag",
+ "rtpproxy.notify_tag",
+ FT_STRING,
+ BASE_NONE,
+ NULL,
+ 0x0,
+ NULL,
+ HFILL
+ }
+ },
+ {
+ &hf_rtpproxy_reply,
+ {
+ "Reply",
+ "rtpproxy.reply",
+ FT_NONE,
+ BASE_NONE,
+ NULL,
+ 0x0,
+ NULL,
+ HFILL
+ }
+ },
+ {
+ &hf_rtpproxy_lf,
+ {
+ "LF",
+ "rtpproxy.lf",
+ FT_NONE,
+ BASE_NONE,
+ NULL,
+ 0x0,
+ NULL,
+ HFILL
+ }
+ },
+ {
+ &hf_rtpproxy_request_in,
+ {
+ "Request In",
+ "rtpproxy.request_in",
+ FT_FRAMENUM,
+ BASE_NONE,
+ NULL,
+ 0x0,
+ NULL,
+ HFILL
+ }
+
+ },
+ {
+ &hf_rtpproxy_response_in,
+ {
+ "Response In",
+ "rtpproxy.response_in",
+ FT_FRAMENUM,
+ BASE_NONE,
+ NULL,
+ 0x0,
+ NULL,
+ HFILL
+ }
+ },
+ {
+ &hf_rtpproxy_response_time,
+ {
+ "Response Time",
+ "rtpproxy.response_time",
+ FT_RELATIVE_TIME,
+ BASE_NONE,
+ NULL,
+ 0x0,
+ "The time between the Request and the Reply",
+ HFILL
+ }
+ },
+ {
+ &hf_rtpproxy_ng_bencode,
+ {
+ "RTPproxy-ng bencode packet",
+ "rtpproxy.ng.bencode",
+ FT_STRING,
+ BASE_NONE,
+ NULL,
+ 0x0,
+ "Serialized structure of integers, dictionaries, strings and lists.",
+ HFILL
+ }
+ }
+ };
+
+ static ei_register_info ei[] = {
+ { &ei_rtpproxy_timeout,
+ { "rtpproxy.response_timeout", PI_RESPONSE_CODE, PI_WARN,
+ "TIMEOUT", EXPFILL }},
+ { &ei_rtpproxy_notify_no_ip,
+ { "rtpproxy.notify_no_ip", PI_RESPONSE_CODE, PI_COMMENT,
+ "No notification IP address provided. Using ip.src or ipv6.src as a value.", EXPFILL }},
+ { &ei_rtpproxy_bad_ipv4,
+ { "rtpproxy.bad_ipv4", PI_MALFORMED, PI_ERROR,
+ "Bad IPv4", EXPFILL }},
+ { &ei_rtpproxy_bad_ipv6,
+ { "rtpproxy.bad_ipv6", PI_MALFORMED, PI_ERROR,
+ "Bad IPv6", EXPFILL }},
+ };
+
+ /* Setup protocol subtree array */
+ static gint *ett[] = {
+ &ett_rtpproxy,
+ &ett_rtpproxy_request,
+ &ett_rtpproxy_command,
+ &ett_rtpproxy_command_parameters,
+ &ett_rtpproxy_command_parameters_codecs,
+ &ett_rtpproxy_command_parameters_local,
+ &ett_rtpproxy_command_parameters_remote,
+ &ett_rtpproxy_command_parameters_repacketize,
+ &ett_rtpproxy_command_parameters_dtmf,
+ &ett_rtpproxy_command_parameters_cmap,
+ &ett_rtpproxy_command_parameters_proto,
+ &ett_rtpproxy_command_parameters_transcode,
+ &ett_rtpproxy_command_parameters_acc,
+ &ett_rtpproxy_tag,
+ &ett_rtpproxy_notify,
+ &ett_rtpproxy_reply,
+ &ett_rtpproxy_ng_bencode
+ };
+
+ proto_rtpproxy = proto_register_protocol (
+ "Sippy RTPproxy Protocol", /* name */
+ "RTPproxy", /* short name */
+ "rtpproxy" /* abbrev */
+ );
+
+ proto_register_field_array(proto_rtpproxy, hf, array_length(hf));
+ proto_register_subtree_array(ett, array_length(ett));
+
+ expert_rtpproxy_module = expert_register_protocol(proto_rtpproxy);
+ expert_register_field_array(expert_rtpproxy_module, ei, array_length(ei));
+
+ rtpproxy_module = prefs_register_protocol(proto_rtpproxy, proto_reg_handoff_rtpproxy);
+
+ prefs_register_uint_preference(rtpproxy_module, "tcp.port",
+ "RTPproxy TCP Port", /* Title */
+ "RTPproxy TCP Port", /* Descr */
+ 10,
+ &rtpproxy_tcp_port);
+
+ prefs_register_uint_preference(rtpproxy_module, "udp.port",
+ "RTPproxy UDP Port", /* Title */
+ "RTPproxy UDP Port", /* Descr */
+ 10,
+ &rtpproxy_udp_port);
+
+ prefs_register_bool_preference(rtpproxy_module, "establish_conversation",
"Establish Media Conversation",
"Specifies that RTP/RTCP/T.38/MSRP/etc streams are decoded based "
"upon port numbers found in RTPproxy answers",
&rtpproxy_establish_conversation);
- prefs_register_uint_preference(rtpproxy_module, "reply.timeout",
- "RTPproxy reply timeout", /* Title */
- "Maximum timeout value in waiting for reply from RTPProxy (in milliseconds).", /* Descr */
- 10,
- &rtpproxy_timeout);
+ prefs_register_uint_preference(rtpproxy_module, "reply.timeout",
+ "RTPproxy reply timeout", /* Title */
+ "Maximum timeout value in waiting for reply from RTPProxy (in milliseconds).", /* Descr */
+ 10,
+ &rtpproxy_timeout);
}
void
proto_reg_handoff_rtpproxy(void)
{
- static guint old_rtpproxy_tcp_port = 0;
- static guint old_rtpproxy_udp_port = 0;
-
- static gboolean rtpproxy_initialized = FALSE;
-
- static dissector_handle_t rtpproxy_tcp_handle, rtpproxy_udp_handle;
-
- if(!rtpproxy_initialized){
- rtpproxy_tcp_handle = new_create_dissector_handle(dissect_rtpproxy, proto_rtpproxy);
- rtpproxy_udp_handle = new_create_dissector_handle(dissect_rtpproxy, proto_rtpproxy);
- rtpproxy_initialized = TRUE;
- }
-
- /* Register TCP port for dissection */
- if(old_rtpproxy_tcp_port != 0 && old_rtpproxy_tcp_port != rtpproxy_tcp_port)
- dissector_delete_uint("tcp.port", old_rtpproxy_tcp_port, rtpproxy_tcp_handle);
- if(rtpproxy_tcp_port != 0 && old_rtpproxy_tcp_port != rtpproxy_tcp_port)
- dissector_add_uint("tcp.port", rtpproxy_tcp_port, rtpproxy_tcp_handle);
- old_rtpproxy_tcp_port = rtpproxy_tcp_port;
-
- /* Register UDP port for dissection */
- if(old_rtpproxy_udp_port != 0 && old_rtpproxy_udp_port != rtpproxy_udp_port)
- dissector_delete_uint("udp.port", old_rtpproxy_udp_port, rtpproxy_udp_handle);
- if(rtpproxy_udp_port != 0 && old_rtpproxy_udp_port != rtpproxy_udp_port)
- dissector_add_uint("udp.port", rtpproxy_udp_port, rtpproxy_udp_handle);
- old_rtpproxy_udp_port = rtpproxy_udp_port;
-
- rtcp_handle = find_dissector("rtcp");
- rtp_events_handle = find_dissector("rtpevent");
- rtp_handle = find_dissector("rtp");
- bencode_handle = find_dissector("bencode");
-
- /* Calculate nstime_t struct for the timeout from the rtpproxy_timeout value in milliseconds */
- rtpproxy_timeout_ns.secs = (rtpproxy_timeout - rtpproxy_timeout % 1000) / 1000;
- rtpproxy_timeout_ns.nsecs = (rtpproxy_timeout % 1000) * 1000;
+ static guint old_rtpproxy_tcp_port = 0;
+ static guint old_rtpproxy_udp_port = 0;
+
+ static gboolean rtpproxy_initialized = FALSE;
+
+ static dissector_handle_t rtpproxy_tcp_handle, rtpproxy_udp_handle;
+
+ if(!rtpproxy_initialized){
+ rtpproxy_tcp_handle = new_create_dissector_handle(dissect_rtpproxy, proto_rtpproxy);
+ rtpproxy_udp_handle = new_create_dissector_handle(dissect_rtpproxy, proto_rtpproxy);
+ rtpproxy_initialized = TRUE;
+ }
+
+ /* Register TCP port for dissection */
+ if(old_rtpproxy_tcp_port != 0 && old_rtpproxy_tcp_port != rtpproxy_tcp_port)
+ dissector_delete_uint("tcp.port", old_rtpproxy_tcp_port, rtpproxy_tcp_handle);
+ if(rtpproxy_tcp_port != 0 && old_rtpproxy_tcp_port != rtpproxy_tcp_port)
+ dissector_add_uint("tcp.port", rtpproxy_tcp_port, rtpproxy_tcp_handle);
+ old_rtpproxy_tcp_port = rtpproxy_tcp_port;
+
+ /* Register UDP port for dissection */
+ if(old_rtpproxy_udp_port != 0 && old_rtpproxy_udp_port != rtpproxy_udp_port)
+ dissector_delete_uint("udp.port", old_rtpproxy_udp_port, rtpproxy_udp_handle);
+ if(rtpproxy_udp_port != 0 && old_rtpproxy_udp_port != rtpproxy_udp_port)
+ dissector_add_uint("udp.port", rtpproxy_udp_port, rtpproxy_udp_handle);
+ old_rtpproxy_udp_port = rtpproxy_udp_port;
+
+ rtcp_handle = find_dissector("rtcp");
+ rtp_events_handle = find_dissector("rtpevent");
+ rtp_handle = find_dissector("rtp");
+ bencode_handle = find_dissector("bencode");
+
+ /* Calculate nstime_t struct for the timeout from the rtpproxy_timeout value in milliseconds */
+ rtpproxy_timeout_ns.secs = (rtpproxy_timeout - rtpproxy_timeout % 1000) / 1000;
+ rtpproxy_timeout_ns.nsecs = (rtpproxy_timeout % 1000) * 1000;
}
/*
* Editor modelines - http://www.wireshark.org/tools/modelines.html
*
* Local variables:
- * c-basic-offset: 8
+ * c-basic-offset: 4
* tab-width: 8
- * indent-tabs-mode: t
+ * indent-tabs-mode: nil
* End:
*
- * vi: set shiftwidth=8 tabstop=8 noexpandtab:
- * :indentSize=8:tabSize=8:noTabs=false:
+ * vi: set shiftwidth=4 tabstop=8 expandtab:
+ * :indentSize=4:tabSize=8:noTabs=true:
*/
diff --git a/epan/dissectors/packet-ssh.c b/epan/dissectors/packet-ssh.c
index 411a825f23..b52f0c6bb3 100644
--- a/epan/dissectors/packet-ssh.c
+++ b/epan/dissectors/packet-ssh.c
@@ -65,58 +65,58 @@ void proto_register_ssh(void);
void proto_reg_handoff_ssh(void);
/* SSH Version 1 definition , from openssh ssh1.h */
-#define SSH1_MSG_NONE 0 /* no message */
-#define SSH1_MSG_DISCONNECT 1 /* cause (string) */
-#define SSH1_SMSG_PUBLIC_KEY 2 /* ck,msk,srvk,hostk */
-#define SSH1_CMSG_SESSION_KEY 3 /* key (BIGNUM) */
-#define SSH1_CMSG_USER 4 /* user (string) */
+#define SSH1_MSG_NONE 0 /* no message */
+#define SSH1_MSG_DISCONNECT 1 /* cause (string) */
+#define SSH1_SMSG_PUBLIC_KEY 2 /* ck,msk,srvk,hostk */
+#define SSH1_CMSG_SESSION_KEY 3 /* key (BIGNUM) */
+#define SSH1_CMSG_USER 4 /* user (string) */
-#define SSH_VERSION_UNKNOWN 0
-#define SSH_VERSION_1 1
-#define SSH_VERSION_2 2
+#define SSH_VERSION_UNKNOWN 0
+#define SSH_VERSION_1 1
+#define SSH_VERSION_2 2
/* proto data */
struct ssh_peer_data {
- guint counter;
+ guint counter;
- guint32 frame_version_start;
- guint32 frame_version_end;
+ guint32 frame_version_start;
+ guint32 frame_version_end;
- guint32 frame_key_start;
- guint32 frame_key_end;
+ guint32 frame_key_start;
+ guint32 frame_key_end;
- gchar* kex_proposal;
+ gchar* kex_proposal;
- /* For all subsequent proposals,
- [0] is client-to-server and [1] is server-to-client. */
+ /* For all subsequent proposals,
+ [0] is client-to-server and [1] is server-to-client. */
#define CLIENT_TO_SERVER_PROPOSAL 0
#define SERVER_TO_CLIENT_PROPOSAL 1
- gchar* mac_proposals[2];
- gchar* mac;
- gint mac_length;
+ gchar* mac_proposals[2];
+ gchar* mac;
+ gint mac_length;
- gchar* enc_proposals[2];
- gchar* enc;
+ gchar* enc_proposals[2];
+ gchar* enc;
- gchar* comp_proposals[2];
- gchar* comp;
+ gchar* comp_proposals[2];
+ gchar* comp;
- gint length_is_plaintext;
+ gint length_is_plaintext;
};
struct ssh_flow_data {
- guint version;
+ guint version;
- gchar* kex;
- int (*kex_specific_dissector)(guint8 msg_code, tvbuff_t *tvb, packet_info *pinfo, int offset, proto_tree *tree);
+ gchar* kex;
+ int (*kex_specific_dissector)(guint8 msg_code, tvbuff_t *tvb, packet_info *pinfo, int offset, proto_tree *tree);
- /* [0] is client's, [1] is server's */
+ /* [0] is client's, [1] is server's */
#define CLIENT_PEER_DATA 0
#define SERVER_PEER_DATA 1
- struct ssh_peer_data peer_data[2];
+ struct ssh_peer_data peer_data[2];
};
static int proto_ssh = -1;
@@ -186,138 +186,138 @@ static dissector_handle_t ssh_handle;
/* Message Numbers (from RFC 4250) (1-255) */
/* Transport layer protocol: generic (1-19) */
-#define SSH_MSG_DISCONNECT 1
-#define SSH_MSG_IGNORE 2
-#define SSH_MSG_UNIMPLEMENTED 3
-#define SSH_MSG_DEBUG 4
-#define SSH_MSG_SERVICE_REQUEST 5
-#define SSH_MSG_SERVICE_ACCEPT 6
+#define SSH_MSG_DISCONNECT 1
+#define SSH_MSG_IGNORE 2
+#define SSH_MSG_UNIMPLEMENTED 3
+#define SSH_MSG_DEBUG 4
+#define SSH_MSG_SERVICE_REQUEST 5
+#define SSH_MSG_SERVICE_ACCEPT 6
/* Transport layer protocol: Algorithm negotiation (20-29) */
-#define SSH_MSG_KEXINIT 20
-#define SSH_MSG_NEWKEYS 21
+#define SSH_MSG_KEXINIT 20
+#define SSH_MSG_NEWKEYS 21
/* Transport layer: Key exchange method specific (reusable) (30-49) */
-#define SSH_MSG_KEXDH_INIT 30
-#define SSH_MSG_KEXDH_REPLY 31
+#define SSH_MSG_KEXDH_INIT 30
+#define SSH_MSG_KEXDH_REPLY 31
-#define SSH_MSG_KEX_DH_GEX_REQUEST_OLD 30
-#define SSH_MSG_KEX_DH_GEX_GROUP 31
-#define SSH_MSG_KEX_DH_GEX_INIT 32
-#define SSH_MSG_KEX_DH_GEX_REPLY 33
-#define SSH_MSG_KEX_DH_GEX_REQUEST 34
+#define SSH_MSG_KEX_DH_GEX_REQUEST_OLD 30
+#define SSH_MSG_KEX_DH_GEX_GROUP 31
+#define SSH_MSG_KEX_DH_GEX_INIT 32
+#define SSH_MSG_KEX_DH_GEX_REPLY 33
+#define SSH_MSG_KEX_DH_GEX_REQUEST 34
/* User authentication protocol: generic (50-59) */
-#define SSH_MSG_USERAUTH_REQUEST 50
-#define SSH_MSG_USERAUTH_FAILURE 51
-#define SSH_MSG_USERAUTH_SUCCESS 52
-#define SSH_MSG_USERAUTH_BANNER 53
+#define SSH_MSG_USERAUTH_REQUEST 50
+#define SSH_MSG_USERAUTH_FAILURE 51
+#define SSH_MSG_USERAUTH_SUCCESS 52
+#define SSH_MSG_USERAUTH_BANNER 53
/* User authentication protocol: method specific (reusable) (50-79) */
/* Connection protocol: generic (80-89) */
-#define SSH_MSG_GLOBAL_REQUEST 80
-#define SSH_MSG_REQUEST_SUCCESS 81
-#define SSH_MSG_REQUEST_FAILURE 82
+#define SSH_MSG_GLOBAL_REQUEST 80
+#define SSH_MSG_REQUEST_SUCCESS 81
+#define SSH_MSG_REQUEST_FAILURE 82
/* Connection protocol: channel related messages (90-127) */
-#define SSH_MSG_CHANNEL_OPEN 90
-#define SSH_MSG_CHANNEL_OPEN_CONFIRMATION 91
-#define SSH_MSG_CHANNEL_OPEN_FAILURE 92
-#define SSH_MSG_CHANNEL_WINDOW_ADJUST 93
-#define SSH_MSG_CHANNEL_DATA 94
-#define SSH_MSG_CHANNEL_EXTENDED_DATA 95
-#define SSH_MSG_CHANNEL_EOF 96
-#define SSH_MSG_CHANNEL_CLOSE 97
-#define SSH_MSG_CHANNEL_REQUEST 98
-#define SSH_MSG_CHANNEL_SUCCESS 99
-#define SSH_MSG_CHANNEL_FAILURE 100
+#define SSH_MSG_CHANNEL_OPEN 90
+#define SSH_MSG_CHANNEL_OPEN_CONFIRMATION 91
+#define SSH_MSG_CHANNEL_OPEN_FAILURE 92
+#define SSH_MSG_CHANNEL_WINDOW_ADJUST 93
+#define SSH_MSG_CHANNEL_DATA 94
+#define SSH_MSG_CHANNEL_EXTENDED_DATA 95
+#define SSH_MSG_CHANNEL_EOF 96
+#define SSH_MSG_CHANNEL_CLOSE 97
+#define SSH_MSG_CHANNEL_REQUEST 98
+#define SSH_MSG_CHANNEL_SUCCESS 99
+#define SSH_MSG_CHANNEL_FAILURE 100
/* 128-191 reserved for client protocols */
/* 192-255 local extensions */
static const value_string ssh2_msg_vals[] = {
- { SSH_MSG_DISCONNECT, "Disconnect" },
- { SSH_MSG_IGNORE, "Ignore" },
- { SSH_MSG_UNIMPLEMENTED, "Unimplemented" },
- { SSH_MSG_DEBUG, "Debug" },
- { SSH_MSG_SERVICE_REQUEST, "Service Request" },
- { SSH_MSG_SERVICE_ACCEPT, "Service Accept" },
- { SSH_MSG_KEXINIT, "Key Exchange Init" },
- { SSH_MSG_NEWKEYS, "New Keys" },
- { SSH_MSG_USERAUTH_REQUEST, "User Authentication Request" },
- { SSH_MSG_USERAUTH_FAILURE, "User Authentication Failure" },
- { SSH_MSG_USERAUTH_SUCCESS, "User Authentication Success" },
- { SSH_MSG_USERAUTH_BANNER, "User Authentication Banner" },
- { SSH_MSG_GLOBAL_REQUEST, "Global Request" },
- { SSH_MSG_REQUEST_SUCCESS, "Request Success" },
- { SSH_MSG_REQUEST_FAILURE, "Request Failure" },
- { SSH_MSG_CHANNEL_OPEN, "Channel Open" },
- { SSH_MSG_CHANNEL_OPEN_CONFIRMATION, "Channel Open Confirmation" },
- { SSH_MSG_CHANNEL_OPEN_FAILURE, "Channel Open Failure" },
- { SSH_MSG_CHANNEL_WINDOW_ADJUST, "Window Adjust" },
- { SSH_MSG_CHANNEL_DATA, "Channel Data" },
- { SSH_MSG_CHANNEL_EXTENDED_DATA, "Channel Extended Data" },
- { SSH_MSG_CHANNEL_EOF, "Channel EOF" },
- { SSH_MSG_CHANNEL_CLOSE, "Channel Close" },
- { SSH_MSG_CHANNEL_REQUEST, "Channel Request" },
- { SSH_MSG_CHANNEL_SUCCESS, "Channel Success" },
- { SSH_MSG_CHANNEL_FAILURE, "Channel Failure" },
- { 0, NULL }
+ { SSH_MSG_DISCONNECT, "Disconnect" },
+ { SSH_MSG_IGNORE, "Ignore" },
+ { SSH_MSG_UNIMPLEMENTED, "Unimplemented" },
+ { SSH_MSG_DEBUG, "Debug" },
+ { SSH_MSG_SERVICE_REQUEST, "Service Request" },
+ { SSH_MSG_SERVICE_ACCEPT, "Service Accept" },
+ { SSH_MSG_KEXINIT, "Key Exchange Init" },
+ { SSH_MSG_NEWKEYS, "New Keys" },
+ { SSH_MSG_USERAUTH_REQUEST, "User Authentication Request" },
+ { SSH_MSG_USERAUTH_FAILURE, "User Authentication Failure" },
+ { SSH_MSG_USERAUTH_SUCCESS, "User Authentication Success" },
+ { SSH_MSG_USERAUTH_BANNER, "User Authentication Banner" },
+ { SSH_MSG_GLOBAL_REQUEST, "Global Request" },
+ { SSH_MSG_REQUEST_SUCCESS, "Request Success" },
+ { SSH_MSG_REQUEST_FAILURE, "Request Failure" },
+ { SSH_MSG_CHANNEL_OPEN, "Channel Open" },
+ { SSH_MSG_CHANNEL_OPEN_CONFIRMATION, "Channel Open Confirmation" },
+ { SSH_MSG_CHANNEL_OPEN_FAILURE, "Channel Open Failure" },
+ { SSH_MSG_CHANNEL_WINDOW_ADJUST, "Window Adjust" },
+ { SSH_MSG_CHANNEL_DATA, "Channel Data" },
+ { SSH_MSG_CHANNEL_EXTENDED_DATA, "Channel Extended Data" },
+ { SSH_MSG_CHANNEL_EOF, "Channel EOF" },
+ { SSH_MSG_CHANNEL_CLOSE, "Channel Close" },
+ { SSH_MSG_CHANNEL_REQUEST, "Channel Request" },
+ { SSH_MSG_CHANNEL_SUCCESS, "Channel Success" },
+ { SSH_MSG_CHANNEL_FAILURE, "Channel Failure" },
+ { 0, NULL }
};
static const value_string ssh2_kex_dh_msg_vals[] = {
- { SSH_MSG_KEXDH_INIT, "Diffie-Hellman Key Exchange Init" },
- { SSH_MSG_KEXDH_REPLY, "Diffie-Hellman Key Exchange Reply" },
- { 0, NULL }
+ { SSH_MSG_KEXDH_INIT, "Diffie-Hellman Key Exchange Init" },
+ { SSH_MSG_KEXDH_REPLY, "Diffie-Hellman Key Exchange Reply" },
+ { 0, NULL }
};
static const value_string ssh2_kex_dh_gex_msg_vals[] = {
- { SSH_MSG_KEX_DH_GEX_REQUEST_OLD, "Diffie-Hellman Group Exchange Request (Old)" },
- { SSH_MSG_KEX_DH_GEX_GROUP, "Diffie-Hellman Group Exchange Group" },
- { SSH_MSG_KEX_DH_GEX_INIT, "Diffie-Hellman Group Exchange Init" },
- { SSH_MSG_KEX_DH_GEX_REPLY, "Diffie-Hellman Group Exchange Reply" },
- { SSH_MSG_KEX_DH_GEX_REQUEST, "Diffie-Hellman Group Exchange Request" },
- { 0, NULL }
+ { SSH_MSG_KEX_DH_GEX_REQUEST_OLD, "Diffie-Hellman Group Exchange Request (Old)" },
+ { SSH_MSG_KEX_DH_GEX_GROUP, "Diffie-Hellman Group Exchange Group" },
+ { SSH_MSG_KEX_DH_GEX_INIT, "Diffie-Hellman Group Exchange Init" },
+ { SSH_MSG_KEX_DH_GEX_REPLY, "Diffie-Hellman Group Exchange Reply" },
+ { SSH_MSG_KEX_DH_GEX_REQUEST, "Diffie-Hellman Group Exchange Request" },
+ { 0, NULL }
};
static const value_string ssh1_msg_vals[] = {
- {SSH1_MSG_NONE, "No Message"},
- {SSH1_MSG_DISCONNECT, "Disconnect"},
- {SSH1_SMSG_PUBLIC_KEY, "Public Key"},
- {SSH1_CMSG_SESSION_KEY, "Session Key"},
- {SSH1_CMSG_USER, "User"},
- {0, NULL}
+ {SSH1_MSG_NONE, "No Message"},
+ {SSH1_MSG_DISCONNECT, "Disconnect"},
+ {SSH1_SMSG_PUBLIC_KEY, "Public Key"},
+ {SSH1_CMSG_SESSION_KEY, "Session Key"},
+ {SSH1_CMSG_USER, "User"},
+ {0, NULL}
};
static int ssh_dissect_key_init(tvbuff_t *tvb, int offset, proto_tree *tree,
- int is_response,
- struct ssh_flow_data *global_data);
+ int is_response,
+ struct ssh_flow_data *global_data);
static int ssh_dissect_proposal(tvbuff_t *tvb, int offset, proto_tree *tree,
- int hf_index_length, int hf_index_value, gchar **store);
+ int hf_index_length, int hf_index_value, gchar **store);
static int ssh_dissect_ssh1(tvbuff_t *tvb, packet_info *pinfo,
- struct ssh_flow_data *global_data,
- int offset, proto_tree *tree, int is_response,
- gboolean *need_desegmentation);
+ struct ssh_flow_data *global_data,
+ int offset, proto_tree *tree, int is_response,
+ gboolean *need_desegmentation);
static int ssh_dissect_ssh2(tvbuff_t *tvb, packet_info *pinfo,
- struct ssh_flow_data *global_data,
- int offset, proto_tree *tree, int is_response,
- gboolean *need_desegmentation);
+ struct ssh_flow_data *global_data,
+ int offset, proto_tree *tree, int is_response,
+ gboolean *need_desegmentation);
static int ssh_dissect_key_exchange(tvbuff_t *tvb, packet_info *pinfo,
- struct ssh_flow_data *global_data,
- int offset, proto_tree *tree, int is_response,
- gboolean *need_desegmentation);
+ struct ssh_flow_data *global_data,
+ int offset, proto_tree *tree, int is_response,
+ gboolean *need_desegmentation);
static int ssh_dissect_kex_dh(guint8 msg_code, tvbuff_t *tvb,
- packet_info *pinfo, int offset, proto_tree *tree);
+ packet_info *pinfo, int offset, proto_tree *tree);
static int ssh_dissect_kex_dh_gex(guint8 msg_code, tvbuff_t *tvb,
- packet_info *pinfo, int offset, proto_tree *tree);
+ packet_info *pinfo, int offset, proto_tree *tree);
static int ssh_dissect_protocol(tvbuff_t *tvb, packet_info *pinfo,
- struct ssh_flow_data *global_data,
- int offset, proto_tree *tree, int is_response, guint *version,
- gboolean *need_desegmentation);
+ struct ssh_flow_data *global_data,
+ int offset, proto_tree *tree, int is_response, guint *version,
+ gboolean *need_desegmentation);
static int ssh_dissect_encrypted_packet(tvbuff_t *tvb, packet_info *pinfo,
- struct ssh_peer_data *peer_data,
- int offset, proto_tree *tree);
+ struct ssh_peer_data *peer_data,
+ int offset, proto_tree *tree);
static void ssh_choose_algo(gchar *client, gchar *server, gchar **result);
static void ssh_set_mac_length(struct ssh_peer_data *peer_data);
static void ssh_set_kex_specific_dissector(struct ssh_flow_data *global_data);
@@ -327,1103 +327,1103 @@ static void
dissect_ssh(tvbuff_t *tvb, packet_info *pinfo, proto_tree *tree)
{
- proto_tree *ssh_tree = NULL;
- proto_item *ti;
- conversation_t *conversation;
- int last_offset, offset = 0;
-
- gboolean is_response = (pinfo->destport != pinfo->match_uint),
- need_desegmentation;
- guint version;
-
- struct ssh_flow_data *global_data=NULL;
- struct ssh_peer_data *peer_data;
-
- conversation = find_or_create_conversation(pinfo);
-
- global_data = (struct ssh_flow_data *)conversation_get_proto_data(conversation, proto_ssh);
- if (!global_data) {
- global_data = (struct ssh_flow_data *)wmem_alloc0(wmem_file_scope(), sizeof(struct ssh_flow_data));
- global_data->version=SSH_VERSION_UNKNOWN;
- global_data->kex_specific_dissector=ssh_dissect_kex_dh;
- global_data->peer_data[CLIENT_PEER_DATA].mac_length=-1;
- global_data->peer_data[SERVER_PEER_DATA].mac_length=-1;
-
- conversation_add_proto_data(conversation, proto_ssh, global_data);
- }
-
- peer_data = &global_data->peer_data[is_response];
-
- if (tree) {
- ti = proto_tree_add_item(tree, proto_ssh, tvb, offset, -1, ENC_NA);
- ssh_tree = proto_item_add_subtree(ti, ett_ssh);
- }
-
- version = global_data->version;
-
- switch(version) {
- case SSH_VERSION_UNKNOWN:
- col_set_str(pinfo->cinfo, COL_PROTOCOL, "SSH");
- break;
- case SSH_VERSION_1:
- col_set_str(pinfo->cinfo, COL_PROTOCOL, "SSHv1");
- break;
- case SSH_VERSION_2:
- col_set_str(pinfo->cinfo, COL_PROTOCOL, "SSHv2");
- break;
-
- }
-
- col_clear(pinfo->cinfo, COL_INFO);
-
- while(tvb_reported_length_remaining(tvb, offset)> 0) {
- gboolean after_version_start = (peer_data->frame_version_start == 0 ||
- pinfo->fd->num >= peer_data->frame_version_start);
- gboolean before_version_end = (peer_data->frame_version_end == 0 ||
- pinfo->fd->num <= peer_data->frame_version_end);
-
- need_desegmentation = FALSE;
- last_offset = offset;
-
- peer_data->counter++;
-
- if (after_version_start && before_version_end &&
- (tvb_strncaseeql(tvb, offset, "SSH-", 4) == 0)) {
- if (peer_data->frame_version_start == 0)
- peer_data->frame_version_start = pinfo->fd->num;
-
- offset = ssh_dissect_protocol(tvb, pinfo,
- global_data,
- offset, ssh_tree, is_response,
- &version, &need_desegmentation);
-
- if (!need_desegmentation) {
- peer_data->frame_version_end = pinfo->fd->num;
- global_data->version = version;
- }
- } else {
- switch(version) {
-
- case SSH_VERSION_UNKNOWN:
- offset = ssh_dissect_encrypted_packet(tvb, pinfo,
- &global_data->peer_data[is_response], offset, ssh_tree);
- break;
-
- case SSH_VERSION_1:
- offset = ssh_dissect_ssh1(tvb, pinfo, global_data,
- offset, ssh_tree, is_response,
- &need_desegmentation);
- break;
-
- case SSH_VERSION_2:
- offset = ssh_dissect_ssh2(tvb, pinfo, global_data,
- offset, ssh_tree, is_response,
- &need_desegmentation);
- break;
- }
- }
-
- if (need_desegmentation)
- return;
- if (offset <= last_offset)
- THROW(ReportedBoundsError);
- }
-
- col_prepend_fstr(pinfo->cinfo, COL_INFO, "%s: ", is_response ? "Server" : "Client");
+ proto_tree *ssh_tree = NULL;
+ proto_item *ti;
+ conversation_t *conversation;
+ int last_offset, offset = 0;
+
+ gboolean is_response = (pinfo->destport != pinfo->match_uint),
+ need_desegmentation;
+ guint version;
+
+ struct ssh_flow_data *global_data=NULL;
+ struct ssh_peer_data *peer_data;
+
+ conversation = find_or_create_conversation(pinfo);
+
+ global_data = (struct ssh_flow_data *)conversation_get_proto_data(conversation, proto_ssh);
+ if (!global_data) {
+ global_data = (struct ssh_flow_data *)wmem_alloc0(wmem_file_scope(), sizeof(struct ssh_flow_data));
+ global_data->version=SSH_VERSION_UNKNOWN;
+ global_data->kex_specific_dissector=ssh_dissect_kex_dh;
+ global_data->peer_data[CLIENT_PEER_DATA].mac_length=-1;
+ global_data->peer_data[SERVER_PEER_DATA].mac_length=-1;
+
+ conversation_add_proto_data(conversation, proto_ssh, global_data);
+ }
+
+ peer_data = &global_data->peer_data[is_response];
+
+ if (tree) {
+ ti = proto_tree_add_item(tree, proto_ssh, tvb, offset, -1, ENC_NA);
+ ssh_tree = proto_item_add_subtree(ti, ett_ssh);
+ }
+
+ version = global_data->version;
+
+ switch(version) {
+ case SSH_VERSION_UNKNOWN:
+ col_set_str(pinfo->cinfo, COL_PROTOCOL, "SSH");
+ break;
+ case SSH_VERSION_1:
+ col_set_str(pinfo->cinfo, COL_PROTOCOL, "SSHv1");
+ break;
+ case SSH_VERSION_2:
+ col_set_str(pinfo->cinfo, COL_PROTOCOL, "SSHv2");
+ break;
+
+ }
+
+ col_clear(pinfo->cinfo, COL_INFO);
+
+ while(tvb_reported_length_remaining(tvb, offset)> 0) {
+ gboolean after_version_start = (peer_data->frame_version_start == 0 ||
+ pinfo->fd->num >= peer_data->frame_version_start);
+ gboolean before_version_end = (peer_data->frame_version_end == 0 ||
+ pinfo->fd->num <= peer_data->frame_version_end);
+
+ need_desegmentation = FALSE;
+ last_offset = offset;
+
+ peer_data->counter++;
+
+ if (after_version_start && before_version_end &&
+ (tvb_strncaseeql(tvb, offset, "SSH-", 4) == 0)) {
+ if (peer_data->frame_version_start == 0)
+ peer_data->frame_version_start = pinfo->fd->num;
+
+ offset = ssh_dissect_protocol(tvb, pinfo,
+ global_data,
+ offset, ssh_tree, is_response,
+ &version, &need_desegmentation);
+
+ if (!need_desegmentation) {
+ peer_data->frame_version_end = pinfo->fd->num;
+ global_data->version = version;
+ }
+ } else {
+ switch(version) {
+
+ case SSH_VERSION_UNKNOWN:
+ offset = ssh_dissect_encrypted_packet(tvb, pinfo,
+ &global_data->peer_data[is_response], offset, ssh_tree);
+ break;
+
+ case SSH_VERSION_1:
+ offset = ssh_dissect_ssh1(tvb, pinfo, global_data,
+ offset, ssh_tree, is_response,
+ &need_desegmentation);
+ break;
+
+ case SSH_VERSION_2:
+ offset = ssh_dissect_ssh2(tvb, pinfo, global_data,
+ offset, ssh_tree, is_response,
+ &need_desegmentation);
+ break;
+ }
+ }
+
+ if (need_desegmentation)
+ return;
+ if (offset <= last_offset)
+ THROW(ReportedBoundsError);
+ }
+
+ col_prepend_fstr(pinfo->cinfo, COL_INFO, "%s: ", is_response ? "Server" : "Client");
}
static int
ssh_dissect_ssh2(tvbuff_t *tvb, packet_info *pinfo,
- struct ssh_flow_data *global_data,
- int offset, proto_tree *tree, int is_response,
- gboolean *need_desegmentation)
+ struct ssh_flow_data *global_data,
+ int offset, proto_tree *tree, int is_response,
+ gboolean *need_desegmentation)
{
- proto_item *ssh2_tree=NULL;
-
- struct ssh_peer_data *peer_data = &global_data->peer_data[is_response];
-
- if (tree) {
- wmem_strbuf_t *title=wmem_strbuf_new(wmem_packet_scope(), "SSH Version 2");
-
- if (peer_data->enc || peer_data->mac || peer_data->comp) {
- wmem_strbuf_append_printf(title, " (");
- if (peer_data->enc)
- wmem_strbuf_append_printf(title, "encryption:%s%s",
- peer_data->enc,
- peer_data->mac || peer_data->comp
- ? " " : "");
- if (peer_data->mac)
- wmem_strbuf_append_printf(title, "mac:%s%s",
- peer_data->mac,
- peer_data->comp ? " " : "");
- if (peer_data->comp)
- wmem_strbuf_append_printf(title, "compression:%s",
- peer_data->comp);
- wmem_strbuf_append_printf(title, ")");
- }
-
- ssh2_tree=proto_tree_add_subtree(tree, tvb, offset, -1, ett_ssh2, NULL, wmem_strbuf_get_str(title));
- }
-
- if ((peer_data->frame_key_start == 0) ||
- ((peer_data->frame_key_start <= pinfo->fd->num) &&
- ((peer_data->frame_key_end == 0) || (pinfo->fd->num <= peer_data->frame_key_end)))) {
- offset = ssh_dissect_key_exchange(tvb, pinfo, global_data,
- offset, ssh2_tree, is_response,
- need_desegmentation);
- } else {
- offset = ssh_dissect_encrypted_packet(tvb, pinfo,
- &global_data->peer_data[is_response], offset, ssh2_tree);
- }
-
- return offset;
+ proto_item *ssh2_tree=NULL;
+
+ struct ssh_peer_data *peer_data = &global_data->peer_data[is_response];
+
+ if (tree) {
+ wmem_strbuf_t *title=wmem_strbuf_new(wmem_packet_scope(), "SSH Version 2");
+
+ if (peer_data->enc || peer_data->mac || peer_data->comp) {
+ wmem_strbuf_append_printf(title, " (");
+ if (peer_data->enc)
+ wmem_strbuf_append_printf(title, "encryption:%s%s",
+ peer_data->enc,
+ peer_data->mac || peer_data->comp
+ ? " " : "");
+ if (peer_data->mac)
+ wmem_strbuf_append_printf(title, "mac:%s%s",
+ peer_data->mac,
+ peer_data->comp ? " " : "");
+ if (peer_data->comp)
+ wmem_strbuf_append_printf(title, "compression:%s",
+ peer_data->comp);
+ wmem_strbuf_append_printf(title, ")");
+ }
+
+ ssh2_tree=proto_tree_add_subtree(tree, tvb, offset, -1, ett_ssh2, NULL, wmem_strbuf_get_str(title));
+ }
+
+ if ((peer_data->frame_key_start == 0) ||
+ ((peer_data->frame_key_start <= pinfo->fd->num) &&
+ ((peer_data->frame_key_end == 0) || (pinfo->fd->num <= peer_data->frame_key_end)))) {
+ offset = ssh_dissect_key_exchange(tvb, pinfo, global_data,
+ offset, ssh2_tree, is_response,
+ need_desegmentation);
+ } else {
+ offset = ssh_dissect_encrypted_packet(tvb, pinfo,
+ &global_data->peer_data[is_response], offset, ssh2_tree);
+ }
+
+ return offset;
}
static int
ssh_dissect_ssh1(tvbuff_t *tvb, packet_info *pinfo,
- struct ssh_flow_data *global_data,
- int offset, proto_tree *tree, int is_response,
- gboolean *need_desegmentation)
+ struct ssh_flow_data *global_data,
+ int offset, proto_tree *tree, int is_response,
+ gboolean *need_desegmentation)
{
- guint plen, padding_length, len;
- guint8 msg_code;
- guint remain_length;
-
- proto_item *ssh1_tree;
-
- struct ssh_peer_data *peer_data = &global_data->peer_data[is_response];
-
- ssh1_tree=proto_tree_add_subtree(tree, tvb, offset, -1, ett_ssh1, NULL, "SSH Version 1");
-
- /*
- * We use "tvb_ensure_length_remaining()" to make sure there
- * actually *is* data remaining.
- *
- * This means we're guaranteed that "remain_length" is positive.
- */
- remain_length = tvb_ensure_length_remaining(tvb, offset);
- /*
- * Can we do reassembly?
- */
- if (ssh_desegment && pinfo->can_desegment) {
- /*
- * Yes - would an SSH header starting at this offset be split
- * across segment boundaries?
- */
- if (remain_length < 4) {
- /*
- * Yes. Tell the TCP dissector where the data for
- * this message starts in the data it handed us and
- * that we need "some more data." Don't tell it
- * exactly how many bytes we need because if/when we
- * ask for even more (after the header) that will
- * break reassembly.
- */
- pinfo->desegment_offset = offset;
- pinfo->desegment_len = DESEGMENT_ONE_MORE_SEGMENT;
- *need_desegmentation = TRUE;
- return offset;
- }
- }
- plen = tvb_get_ntohl(tvb, offset) ;
- padding_length = 8 - plen%8;
-
-
- if (ssh_desegment && pinfo->can_desegment) {
- if (plen+4+padding_length > remain_length) {
- pinfo->desegment_offset = offset;
- pinfo->desegment_len = plen+padding_length - remain_length;
- *need_desegmentation = TRUE;
- return offset;
- }
- }
-
- if (plen >= 0xffff) {
- if (ssh1_tree && plen > 0) {
- proto_tree_add_uint_format(ssh1_tree, hf_ssh_packet_length, tvb,
- offset, 4, plen, "Overly large length %x", plen);
- }
- plen = remain_length-4-padding_length;
- } else {
- if (ssh1_tree && plen > 0) {
- proto_tree_add_uint(ssh1_tree, hf_ssh_packet_length, tvb,
- offset, 4, plen);
- }
- }
- offset+=4;
+ guint plen, padding_length, len;
+ guint8 msg_code;
+ guint remain_length;
+
+ proto_item *ssh1_tree;
+
+ struct ssh_peer_data *peer_data = &global_data->peer_data[is_response];
+
+ ssh1_tree=proto_tree_add_subtree(tree, tvb, offset, -1, ett_ssh1, NULL, "SSH Version 1");
+
+ /*
+ * We use "tvb_ensure_length_remaining()" to make sure there
+ * actually *is* data remaining.
+ *
+ * This means we're guaranteed that "remain_length" is positive.
+ */
+ remain_length = tvb_ensure_length_remaining(tvb, offset);
+ /*
+ * Can we do reassembly?
+ */
+ if (ssh_desegment && pinfo->can_desegment) {
+ /*
+ * Yes - would an SSH header starting at this offset be split
+ * across segment boundaries?
+ */
+ if (remain_length < 4) {
+ /*
+ * Yes. Tell the TCP dissector where the data for
+ * this message starts in the data it handed us and
+ * that we need "some more data." Don't tell it
+ * exactly how many bytes we need because if/when we
+ * ask for even more (after the header) that will
+ * break reassembly.
+ */
+ pinfo->desegment_offset = offset;
+ pinfo->desegment_len = DESEGMENT_ONE_MORE_SEGMENT;
+ *need_desegmentation = TRUE;
+ return offset;
+ }
+ }
+ plen = tvb_get_ntohl(tvb, offset) ;
+ padding_length = 8 - plen%8;
+
+
+ if (ssh_desegment && pinfo->can_desegment) {
+ if (plen+4+padding_length > remain_length) {
+ pinfo->desegment_offset = offset;
+ pinfo->desegment_len = plen+padding_length - remain_length;
+ *need_desegmentation = TRUE;
+ return offset;
+ }
+ }
+
+ if (plen >= 0xffff) {
+ if (ssh1_tree && plen > 0) {
+ proto_tree_add_uint_format(ssh1_tree, hf_ssh_packet_length, tvb,
+ offset, 4, plen, "Overly large length %x", plen);
+ }
+ plen = remain_length-4-padding_length;
+ } else {
+ if (ssh1_tree && plen > 0) {
+ proto_tree_add_uint(ssh1_tree, hf_ssh_packet_length, tvb,
+ offset, 4, plen);
+ }
+ }
+ offset+=4;
/* padding length */
- if (tree) {
- proto_tree_add_uint(ssh1_tree, hf_ssh_padding_length, tvb,
- offset, padding_length, padding_length);
- }
- offset += padding_length;
-
- /* msg_code */
- if ((peer_data->frame_key_start == 0) ||
- ((peer_data->frame_key_start >= pinfo->fd->num) && (pinfo->fd->num <= peer_data->frame_key_end))) {
- msg_code = tvb_get_guint8(tvb, offset);
-
- proto_tree_add_item(ssh1_tree, hf_ssh_msg_code, tvb, offset, 1, ENC_NA);
- col_append_sep_str(pinfo->cinfo, COL_INFO, NULL,
- val_to_str(msg_code, ssh1_msg_vals, "Unknown (%u)"));
- offset += 1;
- len = plen -1;
- if (!pinfo->fd->flags.visited) {
- if (peer_data->frame_key_start == 0)
- peer_data->frame_key_start = pinfo->fd->num;
- peer_data->frame_key_end = pinfo->fd->num;
- }
- } else {
- len = plen;
- col_append_sep_fstr(pinfo->cinfo, COL_INFO, NULL, "Encrypted packet (len=%d)", len);
- }
- /* payload */
- if (ssh1_tree) {
- proto_tree_add_item(ssh1_tree, hf_ssh_payload,
- tvb, offset, len, ENC_NA);
- }
- offset+=len;
-
- return offset;
+ if (tree) {
+ proto_tree_add_uint(ssh1_tree, hf_ssh_padding_length, tvb,
+ offset, padding_length, padding_length);
+ }
+ offset += padding_length;
+
+ /* msg_code */
+ if ((peer_data->frame_key_start == 0) ||
+ ((peer_data->frame_key_start >= pinfo->fd->num) && (pinfo->fd->num <= peer_data->frame_key_end))) {
+ msg_code = tvb_get_guint8(tvb, offset);
+
+ proto_tree_add_item(ssh1_tree, hf_ssh_msg_code, tvb, offset, 1, ENC_NA);
+ col_append_sep_str(pinfo->cinfo, COL_INFO, NULL,
+ val_to_str(msg_code, ssh1_msg_vals, "Unknown (%u)"));
+ offset += 1;
+ len = plen -1;
+ if (!pinfo->fd->flags.visited) {
+ if (peer_data->frame_key_start == 0)
+ peer_data->frame_key_start = pinfo->fd->num;
+ peer_data->frame_key_end = pinfo->fd->num;
+ }
+ } else {
+ len = plen;
+ col_append_sep_fstr(pinfo->cinfo, COL_INFO, NULL, "Encrypted packet (len=%d)", len);
+ }
+ /* payload */
+ if (ssh1_tree) {
+ proto_tree_add_item(ssh1_tree, hf_ssh_payload,
+ tvb, offset, len, ENC_NA);
+ }
+ offset+=len;
+
+ return offset;
}
static int
ssh_tree_add_mpint(tvbuff_t *tvb, int offset, proto_tree *tree,
- int hf_ssh_mpint_selection)
+ int hf_ssh_mpint_selection)
{
- guint len = tvb_get_ntohl(tvb, offset);
- if (tree) {
- proto_tree_add_uint(tree, hf_ssh_mpint_length, tvb,
- offset, 4, len);
- }
- offset+=4;
- if (tree) {
- proto_tree_add_item(tree, hf_ssh_mpint_selection,
- tvb, offset, len, ENC_NA);
- }
- return 4+len;
+ guint len = tvb_get_ntohl(tvb, offset);
+ if (tree) {
+ proto_tree_add_uint(tree, hf_ssh_mpint_length, tvb,
+ offset, 4, len);
+ }
+ offset+=4;
+ if (tree) {
+ proto_tree_add_item(tree, hf_ssh_mpint_selection,
+ tvb, offset, len, ENC_NA);
+ }
+ return 4+len;
}
static int
ssh_tree_add_string(tvbuff_t *tvb, int offset, proto_tree *tree,
- int hf_ssh_string, int hf_ssh_string_length)
+ int hf_ssh_string, int hf_ssh_string_length)
{
- guint len = tvb_get_ntohl(tvb, offset);
- if (tree) {
- proto_tree_add_uint(tree, hf_ssh_string_length, tvb,
- offset, 4, len);
- }
- offset+=4;
- if (tree) {
- proto_tree_add_item(tree, hf_ssh_string,
- tvb, offset, len, ENC_NA);
- }
- return 4+len;
+ guint len = tvb_get_ntohl(tvb, offset);
+ if (tree) {
+ proto_tree_add_uint(tree, hf_ssh_string_length, tvb,
+ offset, 4, len);
+ }
+ offset+=4;
+ if (tree) {
+ proto_tree_add_item(tree, hf_ssh_string,
+ tvb, offset, len, ENC_NA);
+ }
+ return 4+len;
}
static int
ssh_dissect_key_exchange(tvbuff_t *tvb, packet_info *pinfo,
- struct ssh_flow_data *global_data,
- int offset, proto_tree *tree, int is_response,
- gboolean *need_desegmentation)
+ struct ssh_flow_data *global_data,
+ int offset, proto_tree *tree, int is_response,
+ gboolean *need_desegmentation)
{
- guint plen, len;
- guint8 padding_length;
- guint remain_length;
- int last_offset=offset;
- guint msg_code;
-
- proto_item *ti;
- proto_item *key_ex_tree =NULL;
-
- struct ssh_peer_data *peer_data = &global_data->peer_data[is_response];
-
- /*
- * We use "tvb_ensure_length_remaining()" to make sure there
- * actually *is* data remaining.
- *
- * This means we're guaranteed that "remain_length" is positive.
- */
- remain_length = tvb_ensure_length_remaining(tvb, offset);
- /*
- * Can we do reassembly?
- */
- if (ssh_desegment && pinfo->can_desegment) {
- /*
- * Yes - would an SSH header starting at this offset
- * be split across segment boundaries?
- */
- if (remain_length < 4) {
- /*
- * Yes. Tell the TCP dissector where the data for
- * this message starts in the data it handed us and
- * that we need "some more data." Don't tell it
- * exactly how many bytes we need because if/when we
- * ask for even more (after the header) that will
- * break reassembly.
- */
- pinfo->desegment_offset = offset;
- pinfo->desegment_len = DESEGMENT_ONE_MORE_SEGMENT;
- *need_desegmentation = TRUE;
- return offset;
- }
- }
- plen = tvb_get_ntohl(tvb, offset) ;
-
- if (ssh_desegment && pinfo->can_desegment) {
- if (plen +4 > remain_length) {
- pinfo->desegment_offset = offset;
- pinfo->desegment_len = plen+4 - remain_length;
- *need_desegmentation = TRUE;
- return offset;
- }
- }
- /*
- * Need to check plen > 0x80000000 here
- */
-
- ti = proto_tree_add_uint(tree, hf_ssh_packet_length, tvb,
- offset, 4, plen);
- if (plen >= 0xffff) {
- expert_add_info_format(pinfo, ti, &ei_ssh_packet_length, "Overly large number %d", plen);
- plen = remain_length-4;
- }
- offset+=4;
-
- /* padding length */
- padding_length = tvb_get_guint8(tvb, offset);
- proto_tree_add_uint(tree, hf_ssh_padding_length, tvb, offset, 1, padding_length);
- offset += 1;
-
- key_ex_tree=proto_tree_add_subtree(tree, tvb, offset, -1, ett_key_exchange, NULL, "Key Exchange");
-
- /* msg_code */
- msg_code = tvb_get_guint8(tvb, offset);
-
- if (msg_code >= 30 && msg_code < 40) {
- offset = global_data->kex_specific_dissector(msg_code, tvb, pinfo, offset, key_ex_tree);
- } else {
- proto_tree_add_item(key_ex_tree, hf_ssh2_msg_code, tvb, offset, 1, ENC_NA);
- offset += 1;
-
- col_append_sep_str(pinfo->cinfo, COL_INFO, NULL,
- val_to_str(msg_code, ssh2_msg_vals, "Unknown (%u)"));
-
- /* 16 bytes cookie */
- switch(msg_code)
- {
- case SSH_MSG_KEXINIT:
- if ((peer_data->frame_key_start == 0) || (peer_data->frame_key_start == pinfo->fd->num)) {
- offset = ssh_dissect_key_init(tvb, offset, key_ex_tree, is_response, global_data);
- peer_data->frame_key_start = pinfo->fd->num;
- }
- break;
- case SSH_MSG_NEWKEYS:
- if (peer_data->frame_key_end == 0) {
- peer_data->frame_key_end = pinfo->fd->num;
- ssh_choose_algo(global_data->peer_data[CLIENT_PEER_DATA].enc_proposals[is_response],
- global_data->peer_data[SERVER_PEER_DATA].enc_proposals[is_response],
- &peer_data->enc);
-
- /* some ciphers have their own MAC so the "negotiated" one is meaningless */
- if(peer_data->enc && (0 == strcmp(peer_data->enc, "aes128-gcm@openssh.com") ||
- 0 == strcmp(peer_data->enc, "aes256-gcm@openssh.com"))) {
- peer_data->mac = wmem_strdup(wmem_file_scope(), (const gchar *)"<implicit>");
- peer_data->mac_length = 16;
- peer_data->length_is_plaintext = 1;
- }
- else if(peer_data->enc && 0 == strcmp(peer_data->enc, "chacha20-poly1305@openssh.com")) {
- peer_data->mac = wmem_strdup(wmem_file_scope(), (const gchar *)"<implicit>");
- peer_data->mac_length = 16;
- }
- else {
- ssh_choose_algo(global_data->peer_data[CLIENT_PEER_DATA].mac_proposals[is_response],
- global_data->peer_data[SERVER_PEER_DATA].mac_proposals[is_response],
- &peer_data->mac);
- ssh_set_mac_length(peer_data);
- }
-
- ssh_choose_algo(global_data->peer_data[CLIENT_PEER_DATA].comp_proposals[is_response],
- global_data->peer_data[SERVER_PEER_DATA].comp_proposals[is_response],
- &peer_data->comp);
- }
- break;
- }
- }
-
- len = plen+4-padding_length-(offset-last_offset);
- if (len > 0) {
- proto_tree_add_item(key_ex_tree, hf_ssh_payload, tvb, offset, len, ENC_NA);
- }
- offset +=len;
-
- /* padding */
- proto_tree_add_item(key_ex_tree, hf_ssh_padding_string, tvb, offset, padding_length, ENC_NA);
- offset+= padding_length;
-
- return offset;
+ guint plen, len;
+ guint8 padding_length;
+ guint remain_length;
+ int last_offset=offset;
+ guint msg_code;
+
+ proto_item *ti;
+ proto_item *key_ex_tree =NULL;
+
+ struct ssh_peer_data *peer_data = &global_data->peer_data[is_response];
+
+ /*
+ * We use "tvb_ensure_length_remaining()" to make sure there
+ * actually *is* data remaining.
+ *
+ * This means we're guaranteed that "remain_length" is positive.
+ */
+ remain_length = tvb_ensure_length_remaining(tvb, offset);
+ /*
+ * Can we do reassembly?
+ */
+ if (ssh_desegment && pinfo->can_desegment) {
+ /*
+ * Yes - would an SSH header starting at this offset
+ * be split across segment boundaries?
+ */
+ if (remain_length < 4) {
+ /*
+ * Yes. Tell the TCP dissector where the data for
+ * this message starts in the data it handed us and
+ * that we need "some more data." Don't tell it
+ * exactly how many bytes we need because if/when we
+ * ask for even more (after the header) that will
+ * break reassembly.
+ */
+ pinfo->desegment_offset = offset;
+ pinfo->desegment_len = DESEGMENT_ONE_MORE_SEGMENT;
+ *need_desegmentation = TRUE;
+ return offset;
+ }
+ }
+ plen = tvb_get_ntohl(tvb, offset) ;
+
+ if (ssh_desegment && pinfo->can_desegment) {
+ if (plen +4 > remain_length) {
+ pinfo->desegment_offset = offset;
+ pinfo->desegment_len = plen+4 - remain_length;
+ *need_desegmentation = TRUE;
+ return offset;
+ }
+ }
+ /*
+ * Need to check plen > 0x80000000 here
+ */
+
+ ti = proto_tree_add_uint(tree, hf_ssh_packet_length, tvb,
+ offset, 4, plen);
+ if (plen >= 0xffff) {
+ expert_add_info_format(pinfo, ti, &ei_ssh_packet_length, "Overly large number %d", plen);
+ plen = remain_length-4;
+ }
+ offset+=4;
+
+ /* padding length */
+ padding_length = tvb_get_guint8(tvb, offset);
+ proto_tree_add_uint(tree, hf_ssh_padding_length, tvb, offset, 1, padding_length);
+ offset += 1;
+
+ key_ex_tree=proto_tree_add_subtree(tree, tvb, offset, -1, ett_key_exchange, NULL, "Key Exchange");
+
+ /* msg_code */
+ msg_code = tvb_get_guint8(tvb, offset);
+
+ if (msg_code >= 30 && msg_code < 40) {
+ offset = global_data->kex_specific_dissector(msg_code, tvb, pinfo, offset, key_ex_tree);
+ } else {
+ proto_tree_add_item(key_ex_tree, hf_ssh2_msg_code, tvb, offset, 1, ENC_NA);
+ offset += 1;
+
+ col_append_sep_str(pinfo->cinfo, COL_INFO, NULL,
+ val_to_str(msg_code, ssh2_msg_vals, "Unknown (%u)"));
+
+ /* 16 bytes cookie */
+ switch(msg_code)
+ {
+ case SSH_MSG_KEXINIT:
+ if ((peer_data->frame_key_start == 0) || (peer_data->frame_key_start == pinfo->fd->num)) {
+ offset = ssh_dissect_key_init(tvb, offset, key_ex_tree, is_response, global_data);
+ peer_data->frame_key_start = pinfo->fd->num;
+ }
+ break;
+ case SSH_MSG_NEWKEYS:
+ if (peer_data->frame_key_end == 0) {
+ peer_data->frame_key_end = pinfo->fd->num;
+ ssh_choose_algo(global_data->peer_data[CLIENT_PEER_DATA].enc_proposals[is_response],
+ global_data->peer_data[SERVER_PEER_DATA].enc_proposals[is_response],
+ &peer_data->enc);
+
+ /* some ciphers have their own MAC so the "negotiated" one is meaningless */
+ if(peer_data->enc && (0 == strcmp(peer_data->enc, "aes128-gcm@openssh.com") ||
+ 0 == strcmp(peer_data->enc, "aes256-gcm@openssh.com"))) {
+ peer_data->mac = wmem_strdup(wmem_file_scope(), (const gchar *)"<implicit>");
+ peer_data->mac_length = 16;
+ peer_data->length_is_plaintext = 1;
+ }
+ else if(peer_data->enc && 0 == strcmp(peer_data->enc, "chacha20-poly1305@openssh.com")) {
+ peer_data->mac = wmem_strdup(wmem_file_scope(), (const gchar *)"<implicit>");
+ peer_data->mac_length = 16;
+ }
+ else {
+ ssh_choose_algo(global_data->peer_data[CLIENT_PEER_DATA].mac_proposals[is_response],
+ global_data->peer_data[SERVER_PEER_DATA].mac_proposals[is_response],
+ &peer_data->mac);
+ ssh_set_mac_length(peer_data);
+ }
+
+ ssh_choose_algo(global_data->peer_data[CLIENT_PEER_DATA].comp_proposals[is_response],
+ global_data->peer_data[SERVER_PEER_DATA].comp_proposals[is_response],
+ &peer_data->comp);
+ }
+ break;
+ }
+ }
+
+ len = plen+4-padding_length-(offset-last_offset);
+ if (len > 0) {
+ proto_tree_add_item(key_ex_tree, hf_ssh_payload, tvb, offset, len, ENC_NA);
+ }
+ offset +=len;
+
+ /* padding */
+ proto_tree_add_item(key_ex_tree, hf_ssh_padding_string, tvb, offset, padding_length, ENC_NA);
+ offset+= padding_length;
+
+ return offset;
}
static int ssh_dissect_kex_dh(guint8 msg_code, tvbuff_t *tvb,
- packet_info *pinfo, int offset, proto_tree *tree)
+ packet_info *pinfo, int offset, proto_tree *tree)
{
- proto_tree_add_item(tree, hf_ssh2_kex_dh_msg_code, tvb, offset, 1, ENC_NA);
- offset += 1;
+ proto_tree_add_item(tree, hf_ssh2_kex_dh_msg_code, tvb, offset, 1, ENC_NA);
+ offset += 1;
- col_append_sep_str(pinfo->cinfo, COL_INFO, NULL,
- val_to_str(msg_code, ssh2_kex_dh_msg_vals, "Unknown (%u)"));
+ col_append_sep_str(pinfo->cinfo, COL_INFO, NULL,
+ val_to_str(msg_code, ssh2_kex_dh_msg_vals, "Unknown (%u)"));
- switch (msg_code) {
- case SSH_MSG_KEXDH_INIT:
- offset += ssh_tree_add_mpint(tvb, offset, tree, hf_ssh_mpint_e);
- break;
+ switch (msg_code) {
+ case SSH_MSG_KEXDH_INIT:
+ offset += ssh_tree_add_mpint(tvb, offset, tree, hf_ssh_mpint_e);
+ break;
- case SSH_MSG_KEXDH_REPLY:
- offset += ssh_tree_add_string(tvb, offset, tree, hf_ssh_kexdh_host_key, hf_ssh_kexdh_host_key_length);
- offset += ssh_tree_add_mpint(tvb, offset, tree, hf_ssh_mpint_f);
- offset += ssh_tree_add_string(tvb, offset, tree, hf_ssh_kexdh_h_sig, hf_ssh_kexdh_h_sig_length);
- break;
- }
+ case SSH_MSG_KEXDH_REPLY:
+ offset += ssh_tree_add_string(tvb, offset, tree, hf_ssh_kexdh_host_key, hf_ssh_kexdh_host_key_length);
+ offset += ssh_tree_add_mpint(tvb, offset, tree, hf_ssh_mpint_f);
+ offset += ssh_tree_add_string(tvb, offset, tree, hf_ssh_kexdh_h_sig, hf_ssh_kexdh_h_sig_length);
+ break;
+ }
- return offset;
+ return offset;
}
static int ssh_dissect_kex_dh_gex(guint8 msg_code, tvbuff_t *tvb,
- packet_info *pinfo, int offset, proto_tree *tree)
+ packet_info *pinfo, int offset, proto_tree *tree)
{
- proto_tree_add_item(tree, hf_ssh2_kex_dh_gex_msg_code, tvb, offset, 1, ENC_NA);
- offset += 1;
-
- col_append_sep_str(pinfo->cinfo, COL_INFO, NULL,
- val_to_str(msg_code, ssh2_kex_dh_gex_msg_vals, "Unknown (%u)"));
-
- switch (msg_code) {
- case SSH_MSG_KEX_DH_GEX_REQUEST_OLD:
- proto_tree_add_item(tree, hf_ssh_dh_gex_nbits, tvb, offset, 4, ENC_BIG_ENDIAN);
- offset += 4;
- break;
-
- case SSH_MSG_KEX_DH_GEX_GROUP:
- offset += ssh_tree_add_mpint(tvb, offset, tree, hf_ssh_mpint_p);
- offset += ssh_tree_add_mpint(tvb, offset, tree, hf_ssh_mpint_g);
- break;
-
- case SSH_MSG_KEX_DH_GEX_INIT:
- offset += ssh_tree_add_mpint(tvb, offset, tree, hf_ssh_mpint_e);
- break;
-
- case SSH_MSG_KEX_DH_GEX_REPLY:
- offset += ssh_tree_add_string(tvb, offset, tree, hf_ssh_kexdh_host_key, hf_ssh_kexdh_host_key_length);
- offset += ssh_tree_add_mpint(tvb, offset, tree, hf_ssh_mpint_f);
- offset += ssh_tree_add_string(tvb, offset, tree, hf_ssh_kexdh_h_sig, hf_ssh_kexdh_h_sig_length);
- break;
-
- case SSH_MSG_KEX_DH_GEX_REQUEST:
- proto_tree_add_item(tree, hf_ssh_dh_gex_min, tvb, offset, 4, ENC_BIG_ENDIAN);
- offset += 4;
- proto_tree_add_item(tree, hf_ssh_dh_gex_nbits, tvb, offset, 4, ENC_BIG_ENDIAN);
- offset += 4;
- proto_tree_add_item(tree, hf_ssh_dh_gex_max, tvb, offset, 4, ENC_BIG_ENDIAN);
- offset += 4;
- break;
- }
-
- return offset;
+ proto_tree_add_item(tree, hf_ssh2_kex_dh_gex_msg_code, tvb, offset, 1, ENC_NA);
+ offset += 1;
+
+ col_append_sep_str(pinfo->cinfo, COL_INFO, NULL,
+ val_to_str(msg_code, ssh2_kex_dh_gex_msg_vals, "Unknown (%u)"));
+
+ switch (msg_code) {
+ case SSH_MSG_KEX_DH_GEX_REQUEST_OLD:
+ proto_tree_add_item(tree, hf_ssh_dh_gex_nbits, tvb, offset, 4, ENC_BIG_ENDIAN);
+ offset += 4;
+ break;
+
+ case SSH_MSG_KEX_DH_GEX_GROUP:
+ offset += ssh_tree_add_mpint(tvb, offset, tree, hf_ssh_mpint_p);
+ offset += ssh_tree_add_mpint(tvb, offset, tree, hf_ssh_mpint_g);
+ break;
+
+ case SSH_MSG_KEX_DH_GEX_INIT:
+ offset += ssh_tree_add_mpint(tvb, offset, tree, hf_ssh_mpint_e);
+ break;
+
+ case SSH_MSG_KEX_DH_GEX_REPLY:
+ offset += ssh_tree_add_string(tvb, offset, tree, hf_ssh_kexdh_host_key, hf_ssh_kexdh_host_key_length);
+ offset += ssh_tree_add_mpint(tvb, offset, tree, hf_ssh_mpint_f);
+ offset += ssh_tree_add_string(tvb, offset, tree, hf_ssh_kexdh_h_sig, hf_ssh_kexdh_h_sig_length);
+ break;
+
+ case SSH_MSG_KEX_DH_GEX_REQUEST:
+ proto_tree_add_item(tree, hf_ssh_dh_gex_min, tvb, offset, 4, ENC_BIG_ENDIAN);
+ offset += 4;
+ proto_tree_add_item(tree, hf_ssh_dh_gex_nbits, tvb, offset, 4, ENC_BIG_ENDIAN);
+ offset += 4;
+ proto_tree_add_item(tree, hf_ssh_dh_gex_max, tvb, offset, 4, ENC_BIG_ENDIAN);
+ offset += 4;
+ break;
+ }
+
+ return offset;
}
static int
ssh_dissect_encrypted_packet(tvbuff_t *tvb, packet_info *pinfo,
- struct ssh_peer_data *peer_data,
- int offset, proto_tree *tree)
+ struct ssh_peer_data *peer_data,
+ int offset, proto_tree *tree)
{
- gint len;
- guint plen;
-
- len = tvb_reported_length_remaining(tvb, offset);
- col_append_sep_fstr(pinfo->cinfo, COL_INFO, NULL, "Encrypted packet (len=%d)", len);
-
- if (tree) {
- gint encrypted_len = len;
-
- if (len > 4 && peer_data->length_is_plaintext) {
- plen = tvb_get_ntohl(tvb, offset) ;
- proto_tree_add_uint(tree, hf_ssh_packet_length, tvb, offset, 4, plen);
- encrypted_len -= 4;
- }
- else if (len > 4) {
- proto_tree_add_item(tree, hf_ssh_packet_length_encrypted, tvb, offset, 4, ENC_NA);
- encrypted_len -= 4;
- }
-
- if (peer_data->mac_length>0)
- encrypted_len -= peer_data->mac_length;
-
- proto_tree_add_item(tree, hf_ssh_encrypted_packet,
- tvb, offset+4, encrypted_len, ENC_NA);
-
- if (peer_data->mac_length>0)
- proto_tree_add_item(tree, hf_ssh_mac_string,
- tvb, offset+4+encrypted_len,
- peer_data->mac_length, ENC_NA);
- }
- offset+=len;
- return offset;
+ gint len;
+ guint plen;
+
+ len = tvb_reported_length_remaining(tvb, offset);
+ col_append_sep_fstr(pinfo->cinfo, COL_INFO, NULL, "Encrypted packet (len=%d)", len);
+
+ if (tree) {
+ gint encrypted_len = len;
+
+ if (len > 4 && peer_data->length_is_plaintext) {
+ plen = tvb_get_ntohl(tvb, offset) ;
+ proto_tree_add_uint(tree, hf_ssh_packet_length, tvb, offset, 4, plen);
+ encrypted_len -= 4;
+ }
+ else if (len > 4) {
+ proto_tree_add_item(tree, hf_ssh_packet_length_encrypted, tvb, offset, 4, ENC_NA);
+ encrypted_len -= 4;
+ }
+
+ if (peer_data->mac_length>0)
+ encrypted_len -= peer_data->mac_length;
+
+ proto_tree_add_item(tree, hf_ssh_encrypted_packet,
+ tvb, offset+4, encrypted_len, ENC_NA);
+
+ if (peer_data->mac_length>0)
+ proto_tree_add_item(tree, hf_ssh_mac_string,
+ tvb, offset+4+encrypted_len,
+ peer_data->mac_length, ENC_NA);
+ }
+ offset+=len;
+ return offset;
}
static int
ssh_dissect_protocol(tvbuff_t *tvb, packet_info *pinfo,
- struct ssh_flow_data *global_data,
- int offset, proto_tree *tree, int is_response, guint * version,
- gboolean *need_desegmentation)
+ struct ssh_flow_data *global_data,
+ int offset, proto_tree *tree, int is_response, guint * version,
+ gboolean *need_desegmentation)
{
- guint remain_length;
- gint linelen, protolen;
-
- /*
- * If the first packet do not contain the banner,
- * it is dump in the middle of a flow or not a ssh at all
- */
- if (tvb_strncaseeql(tvb, offset, "SSH-", 4) != 0) {
- offset = ssh_dissect_encrypted_packet(tvb, pinfo,
- &global_data->peer_data[is_response], offset, tree);
- return offset;
- }
-
- if (!is_response) {
- if (tvb_strncaseeql(tvb, offset, "SSH-2.", 6) == 0) {
- *(version) = SSH_VERSION_2;
- } else if (tvb_strncaseeql(tvb, offset, "SSH-1.99-", 9) == 0) {
- *(version) = SSH_VERSION_2;
- } else if (tvb_strncaseeql(tvb, offset, "SSH-1.", 6) == 0) {
- *(version) = SSH_VERSION_1;
- }
- }
-
- /*
- * We use "tvb_ensure_length_remaining()" to make sure there
- * actually *is* data remaining.
- *
- * This means we're guaranteed that "remain_length" is positive.
- */
- remain_length = tvb_ensure_length_remaining(tvb, offset);
- /*linelen = tvb_find_line_end(tvb, offset, -1, &next_offset, FALSE);
- */
- linelen = tvb_find_guint8(tvb, offset, -1, '\n');
-
- if (ssh_desegment && pinfo->can_desegment) {
- if (linelen == -1 || remain_length < (guint)linelen-offset) {
- pinfo->desegment_offset = offset;
- pinfo->desegment_len = linelen-remain_length;
- *need_desegmentation = TRUE;
- return offset;
- }
- }
- if (linelen == -1) {
- /* XXX - reassemble across segment boundaries? */
- linelen = remain_length;
- protolen = linelen;
- } else {
- linelen = linelen - offset + 1;
-
- if (linelen > 1 && tvb_get_guint8(tvb, offset + linelen - 2) == '\r')
- protolen = linelen - 2;
- else
- protolen = linelen - 1;
- }
-
- col_append_sep_fstr(pinfo->cinfo, COL_INFO, NULL, "Protocol (%s)",
- tvb_format_text(tvb, offset, protolen));
-
- proto_tree_add_item(tree, hf_ssh_protocol,
- tvb, offset, linelen, ENC_ASCII|ENC_NA);
- offset+=linelen;
- return offset;
+ guint remain_length;
+ gint linelen, protolen;
+
+ /*
+ * If the first packet do not contain the banner,
+ * it is dump in the middle of a flow or not a ssh at all
+ */
+ if (tvb_strncaseeql(tvb, offset, "SSH-", 4) != 0) {
+ offset = ssh_dissect_encrypted_packet(tvb, pinfo,
+ &global_data->peer_data[is_response], offset, tree);
+ return offset;
+ }
+
+ if (!is_response) {
+ if (tvb_strncaseeql(tvb, offset, "SSH-2.", 6) == 0) {
+ *(version) = SSH_VERSION_2;
+ } else if (tvb_strncaseeql(tvb, offset, "SSH-1.99-", 9) == 0) {
+ *(version) = SSH_VERSION_2;
+ } else if (tvb_strncaseeql(tvb, offset, "SSH-1.", 6) == 0) {
+ *(version) = SSH_VERSION_1;
+ }
+ }
+
+ /*
+ * We use "tvb_ensure_length_remaining()" to make sure there
+ * actually *is* data remaining.
+ *
+ * This means we're guaranteed that "remain_length" is positive.
+ */
+ remain_length = tvb_ensure_length_remaining(tvb, offset);
+ /*linelen = tvb_find_line_end(tvb, offset, -1, &next_offset, FALSE);
+ */
+ linelen = tvb_find_guint8(tvb, offset, -1, '\n');
+
+ if (ssh_desegment && pinfo->can_desegment) {
+ if (linelen == -1 || remain_length < (guint)linelen-offset) {
+ pinfo->desegment_offset = offset;
+ pinfo->desegment_len = linelen-remain_length;
+ *need_desegmentation = TRUE;
+ return offset;
+ }
+ }
+ if (linelen == -1) {
+ /* XXX - reassemble across segment boundaries? */
+ linelen = remain_length;
+ protolen = linelen;
+ } else {
+ linelen = linelen - offset + 1;
+
+ if (linelen > 1 && tvb_get_guint8(tvb, offset + linelen - 2) == '\r')
+ protolen = linelen - 2;
+ else
+ protolen = linelen - 1;
+ }
+
+ col_append_sep_fstr(pinfo->cinfo, COL_INFO, NULL, "Protocol (%s)",
+ tvb_format_text(tvb, offset, protolen));
+
+ proto_tree_add_item(tree, hf_ssh_protocol,
+ tvb, offset, linelen, ENC_ASCII|ENC_NA);
+ offset+=linelen;
+ return offset;
}
static void
ssh_set_mac_length(struct ssh_peer_data *peer_data)
{
- char *size_str;
- guint size=0;
- char *mac_name = peer_data->mac;
- char *strip;
-
- if (!mac_name) return;
- mac_name = wmem_strdup(NULL, (const gchar *)mac_name);
- if (!mac_name) return;
-
- /* strip trailing "-etm@openssh.com" or "@openssh.com" */
- strip = strstr(mac_name, "-etm@openssh.com");
- if (strip) {
- peer_data->length_is_plaintext = 1;
- *strip = '\0';
- }
- else {
- strip = strstr(mac_name, "@openssh.com");
- if (strip) *strip = '\0';
- }
-
- if ((size_str=g_strrstr(mac_name, "-")) && ((size=atoi(size_str+1)))) {
- peer_data->mac_length = (size > 0) ? size / 8 : 0;
- }
- else if (strcmp(mac_name, "hmac-sha1") == 0) {
- peer_data->mac_length = 20;
- }
- else if (strcmp(mac_name, "hmac-md5") == 0) {
- peer_data->mac_length = 16;
- }
- else if (strcmp(mac_name, "hmac-ripemd160") == 0) {
- peer_data->mac_length = 20;
- }
- else if (strcmp(mac_name, "none") == 0) {
- peer_data->mac_length = 0;
- }
-
- wmem_free(NULL, mac_name);
+ char *size_str;
+ guint size=0;
+ char *mac_name = peer_data->mac;
+ char *strip;
+
+ if (!mac_name) return;
+ mac_name = wmem_strdup(NULL, (const gchar *)mac_name);
+ if (!mac_name) return;
+
+ /* strip trailing "-etm@openssh.com" or "@openssh.com" */
+ strip = strstr(mac_name, "-etm@openssh.com");
+ if (strip) {
+ peer_data->length_is_plaintext = 1;
+ *strip = '\0';
+ }
+ else {
+ strip = strstr(mac_name, "@openssh.com");
+ if (strip) *strip = '\0';
+ }
+
+ if ((size_str=g_strrstr(mac_name, "-")) && ((size=atoi(size_str+1)))) {
+ peer_data->mac_length = (size > 0) ? size / 8 : 0;
+ }
+ else if (strcmp(mac_name, "hmac-sha1") == 0) {
+ peer_data->mac_length = 20;
+ }
+ else if (strcmp(mac_name, "hmac-md5") == 0) {
+ peer_data->mac_length = 16;
+ }
+ else if (strcmp(mac_name, "hmac-ripemd160") == 0) {
+ peer_data->mac_length = 20;
+ }
+ else if (strcmp(mac_name, "none") == 0) {
+ peer_data->mac_length = 0;
+ }
+
+ wmem_free(NULL, mac_name);
}
static void ssh_set_kex_specific_dissector(struct ssh_flow_data *global_data)
{
- const char *kex_name = global_data->kex;
+ const char *kex_name = global_data->kex;
- if (!kex_name) return;
+ if (!kex_name) return;
- if (strcmp(kex_name, "diffie-hellman-group-exchange-sha1") == 0 ||
- strcmp(kex_name, "diffie-hellman-group-exchange-sha256") == 0)
- {
- global_data->kex_specific_dissector = ssh_dissect_kex_dh_gex;
- }
+ if (strcmp(kex_name, "diffie-hellman-group-exchange-sha1") == 0 ||
+ strcmp(kex_name, "diffie-hellman-group-exchange-sha256") == 0)
+ {
+ global_data->kex_specific_dissector = ssh_dissect_kex_dh_gex;
+ }
}
static gint
ssh_gslist_compare_strings(gconstpointer a, gconstpointer b)
{
- if (a == NULL && b == NULL)
- return 0;
- if (a == NULL)
- return -1;
- if (b == NULL)
- return 1;
- return strcmp((const char*)a, (const char*)b);
+ if (a == NULL && b == NULL)
+ return 0;
+ if (a == NULL)
+ return -1;
+ if (b == NULL)
+ return 1;
+ return strcmp((const char*)a, (const char*)b);
}
/* expects that *result is NULL */
static void
ssh_choose_algo(gchar *client, gchar *server, gchar **result)
{
- gchar **server_strings=NULL;
- gchar **client_strings=NULL;
- gchar **step;
- GSList *server_list = NULL;
-
- if (!client || !server || !result || *result)
- return;
-
- server_strings = g_strsplit(server, ",", 0);
- for (step = server_strings; *step; step++) {
- server_list = g_slist_append(server_list, *step);
- }
-
- client_strings = g_strsplit(client, ",", 0);
- for (step = client_strings; *step; step++) {
- GSList *agreed;
- if ((agreed=g_slist_find_custom(server_list, *step, ssh_gslist_compare_strings))) {
- *result = wmem_strdup(wmem_file_scope(), (const gchar *)agreed->data);
- break;
- }
- }
-
- g_strfreev(client_strings);
- g_slist_free(server_list);
- g_strfreev(server_strings);
+ gchar **server_strings=NULL;
+ gchar **client_strings=NULL;
+ gchar **step;
+ GSList *server_list = NULL;
+
+ if (!client || !server || !result || *result)
+ return;
+
+ server_strings = g_strsplit(server, ",", 0);
+ for (step = server_strings; *step; step++) {
+ server_list = g_slist_append(server_list, *step);
+ }
+
+ client_strings = g_strsplit(client, ",", 0);
+ for (step = client_strings; *step; step++) {
+ GSList *agreed;
+ if ((agreed=g_slist_find_custom(server_list, *step, ssh_gslist_compare_strings))) {
+ *result = wmem_strdup(wmem_file_scope(), (const gchar *)agreed->data);
+ break;
+ }
+ }
+
+ g_strfreev(client_strings);
+ g_slist_free(server_list);
+ g_strfreev(server_strings);
}
static int
ssh_dissect_key_init(tvbuff_t *tvb, int offset, proto_tree *tree,
- int is_response, struct ssh_flow_data *global_data)
+ int is_response, struct ssh_flow_data *global_data)
{
- int start_offset = offset;
+ int start_offset = offset;
- proto_item *tf;
+ proto_item *tf;
proto_tree *key_init_tree;
- struct ssh_peer_data *peer_data = &global_data->peer_data[is_response];
-
- key_init_tree=proto_tree_add_subtree(tree, tvb, offset, -1, ett_key_init, &tf, "Algorithms");
- proto_tree_add_item(key_init_tree, hf_ssh_cookie,
- tvb, offset, 16, ENC_NA);
- offset += 16;
-
- offset = ssh_dissect_proposal(tvb, offset, key_init_tree,
- hf_ssh_kex_algorithms_length, hf_ssh_kex_algorithms,
- &peer_data->kex_proposal);
- offset = ssh_dissect_proposal(tvb, offset, key_init_tree,
- hf_ssh_server_host_key_algorithms_length,
- hf_ssh_server_host_key_algorithms, NULL);
- offset = ssh_dissect_proposal(tvb, offset, key_init_tree,
- hf_ssh_encryption_algorithms_client_to_server_length,
- hf_ssh_encryption_algorithms_client_to_server,
- &peer_data->enc_proposals[CLIENT_TO_SERVER_PROPOSAL]);
- offset = ssh_dissect_proposal(tvb, offset, key_init_tree,
- hf_ssh_encryption_algorithms_server_to_client_length,
- hf_ssh_encryption_algorithms_server_to_client,
- &peer_data->enc_proposals[SERVER_TO_CLIENT_PROPOSAL]);
- offset = ssh_dissect_proposal(tvb, offset, key_init_tree,
- hf_ssh_mac_algorithms_client_to_server_length,
- hf_ssh_mac_algorithms_client_to_server,
- &peer_data->mac_proposals[CLIENT_TO_SERVER_PROPOSAL]);
- offset = ssh_dissect_proposal(tvb, offset, key_init_tree,
- hf_ssh_mac_algorithms_server_to_client_length,
- hf_ssh_mac_algorithms_server_to_client,
- &peer_data->mac_proposals[SERVER_TO_CLIENT_PROPOSAL]);
- offset = ssh_dissect_proposal(tvb, offset, key_init_tree,
- hf_ssh_compression_algorithms_client_to_server_length,
- hf_ssh_compression_algorithms_client_to_server,
- &peer_data->comp_proposals[CLIENT_TO_SERVER_PROPOSAL]);
- offset = ssh_dissect_proposal(tvb, offset, key_init_tree,
- hf_ssh_compression_algorithms_server_to_client_length,
- hf_ssh_compression_algorithms_server_to_client,
- &peer_data->comp_proposals[SERVER_TO_CLIENT_PROPOSAL]);
- offset = ssh_dissect_proposal(tvb, offset, key_init_tree,
- hf_ssh_languages_client_to_server_length,
- hf_ssh_languages_client_to_server, NULL);
- offset = ssh_dissect_proposal(tvb, offset, key_init_tree,
- hf_ssh_languages_server_to_client_length,
- hf_ssh_languages_server_to_client, NULL);
-
- proto_tree_add_item(key_init_tree, hf_ssh_kex_first_packet_follows,
- tvb, offset, 1, ENC_BIG_ENDIAN);
- offset+=1;
-
- proto_tree_add_item(key_init_tree, hf_ssh_kex_reserved,
- tvb, offset, 4, ENC_NA);
- offset+=4;
-
- if (global_data->peer_data[CLIENT_PEER_DATA].kex_proposal &&
- global_data->peer_data[SERVER_PEER_DATA].kex_proposal &&
- !global_data->kex)
- {
- /* Note: we're ignoring first_kex_packet_follows. */
- ssh_choose_algo(
- global_data->peer_data[CLIENT_PEER_DATA].kex_proposal,
- global_data->peer_data[SERVER_PEER_DATA].kex_proposal,
- &global_data->kex);
- ssh_set_kex_specific_dissector(global_data);
- }
-
- if (tf != NULL) {
- proto_item_set_len(tf, offset-start_offset);
- }
-
- return offset;
+ struct ssh_peer_data *peer_data = &global_data->peer_data[is_response];
+
+ key_init_tree=proto_tree_add_subtree(tree, tvb, offset, -1, ett_key_init, &tf, "Algorithms");
+ proto_tree_add_item(key_init_tree, hf_ssh_cookie,
+ tvb, offset, 16, ENC_NA);
+ offset += 16;
+
+ offset = ssh_dissect_proposal(tvb, offset, key_init_tree,
+ hf_ssh_kex_algorithms_length, hf_ssh_kex_algorithms,
+ &peer_data->kex_proposal);
+ offset = ssh_dissect_proposal(tvb, offset, key_init_tree,
+ hf_ssh_server_host_key_algorithms_length,
+ hf_ssh_server_host_key_algorithms, NULL);
+ offset = ssh_dissect_proposal(tvb, offset, key_init_tree,
+ hf_ssh_encryption_algorithms_client_to_server_length,
+ hf_ssh_encryption_algorithms_client_to_server,
+ &peer_data->enc_proposals[CLIENT_TO_SERVER_PROPOSAL]);
+ offset = ssh_dissect_proposal(tvb, offset, key_init_tree,
+ hf_ssh_encryption_algorithms_server_to_client_length,
+ hf_ssh_encryption_algorithms_server_to_client,
+ &peer_data->enc_proposals[SERVER_TO_CLIENT_PROPOSAL]);
+ offset = ssh_dissect_proposal(tvb, offset, key_init_tree,
+ hf_ssh_mac_algorithms_client_to_server_length,
+ hf_ssh_mac_algorithms_client_to_server,
+ &peer_data->mac_proposals[CLIENT_TO_SERVER_PROPOSAL]);
+ offset = ssh_dissect_proposal(tvb, offset, key_init_tree,
+ hf_ssh_mac_algorithms_server_to_client_length,
+ hf_ssh_mac_algorithms_server_to_client,
+ &peer_data->mac_proposals[SERVER_TO_CLIENT_PROPOSAL]);
+ offset = ssh_dissect_proposal(tvb, offset, key_init_tree,
+ hf_ssh_compression_algorithms_client_to_server_length,
+ hf_ssh_compression_algorithms_client_to_server,
+ &peer_data->comp_proposals[CLIENT_TO_SERVER_PROPOSAL]);
+ offset = ssh_dissect_proposal(tvb, offset, key_init_tree,
+ hf_ssh_compression_algorithms_server_to_client_length,
+ hf_ssh_compression_algorithms_server_to_client,
+ &peer_data->comp_proposals[SERVER_TO_CLIENT_PROPOSAL]);
+ offset = ssh_dissect_proposal(tvb, offset, key_init_tree,
+ hf_ssh_languages_client_to_server_length,
+ hf_ssh_languages_client_to_server, NULL);
+ offset = ssh_dissect_proposal(tvb, offset, key_init_tree,
+ hf_ssh_languages_server_to_client_length,
+ hf_ssh_languages_server_to_client, NULL);
+
+ proto_tree_add_item(key_init_tree, hf_ssh_kex_first_packet_follows,
+ tvb, offset, 1, ENC_BIG_ENDIAN);
+ offset+=1;
+
+ proto_tree_add_item(key_init_tree, hf_ssh_kex_reserved,
+ tvb, offset, 4, ENC_NA);
+ offset+=4;
+
+ if (global_data->peer_data[CLIENT_PEER_DATA].kex_proposal &&
+ global_data->peer_data[SERVER_PEER_DATA].kex_proposal &&
+ !global_data->kex)
+ {
+ /* Note: we're ignoring first_kex_packet_follows. */
+ ssh_choose_algo(
+ global_data->peer_data[CLIENT_PEER_DATA].kex_proposal,
+ global_data->peer_data[SERVER_PEER_DATA].kex_proposal,
+ &global_data->kex);
+ ssh_set_kex_specific_dissector(global_data);
+ }
+
+ if (tf != NULL) {
+ proto_item_set_len(tf, offset-start_offset);
+ }
+
+ return offset;
}
static int
ssh_dissect_proposal(tvbuff_t *tvb, int offset, proto_tree *tree,
- int hf_index_length, int hf_index_value, gchar **store)
+ int hf_index_length, int hf_index_value, gchar **store)
{
- guint32 len = tvb_get_ntohl(tvb, offset);
- proto_tree_add_uint(tree, hf_index_length, tvb, offset, 4, len);
- offset += 4;
+ guint32 len = tvb_get_ntohl(tvb, offset);
+ proto_tree_add_uint(tree, hf_index_length, tvb, offset, 4, len);
+ offset += 4;
- proto_tree_add_item(tree, hf_index_value, tvb, offset, len,
- ENC_ASCII);
- if (store)
- *store = tvb_get_string_enc(wmem_file_scope(), tvb, offset, len, ENC_ASCII);
- offset += len;
+ proto_tree_add_item(tree, hf_index_value, tvb, offset, len,
+ ENC_ASCII);
+ if (store)
+ *store = tvb_get_string_enc(wmem_file_scope(), tvb, offset, len, ENC_ASCII);
+ offset += len;
- return offset;
+ return offset;
}
void
proto_register_ssh(void)
{
- static hf_register_info hf[] = {
- { &hf_ssh_packet_length,
- { "Packet Length", "ssh.packet_length",
- FT_UINT32, BASE_DEC, NULL, 0x0,
- "SSH packet length", HFILL }},
-
- { &hf_ssh_packet_length_encrypted,
- { "Packet Length (encrypted)", "ssh.packet_length_encrypted",
- FT_BYTES, BASE_NONE, NULL, 0x0,
- "SSH packet length (encrypted)", HFILL }},
-
- { &hf_ssh_padding_length,
- { "Padding Length", "ssh.padding_length",
- FT_UINT8, BASE_DEC, NULL, 0x0,
- "SSH Packet Number", HFILL }},
-
- { &hf_ssh_msg_code,
- { "Message Code", "ssh.message_code",
- FT_UINT8, BASE_DEC, VALS(ssh1_msg_vals), 0x0,
- "SSH Message Code", HFILL }},
-
- { &hf_ssh2_msg_code,
- { "Message Code", "ssh.message_code",
- FT_UINT8, BASE_DEC, VALS(ssh2_msg_vals), 0x0,
- "SSH Message Code", HFILL }},
-
- { &hf_ssh2_kex_dh_msg_code,
- { "Message Code", "ssh.message_code",
- FT_UINT8, BASE_DEC, VALS(ssh2_kex_dh_msg_vals), 0x0,
- "SSH Message Code", HFILL }},
-
- { &hf_ssh2_kex_dh_gex_msg_code,
- { "Message Code", "ssh.message_code",
- FT_UINT8, BASE_DEC, VALS(ssh2_kex_dh_gex_msg_vals), 0x0,
- "SSH Message Code", HFILL }},
-
- { &hf_ssh_mpint_g,
- { "DH base (G)", "ssh.dh.g",
- FT_BYTES, BASE_NONE, NULL, 0x0,
- "SSH DH base (G)", HFILL }},
-
- { &hf_ssh_mpint_p,
- { "DH modulus (P)", "ssh.dh.p",
- FT_BYTES, BASE_NONE, NULL, 0x0,
- "SSH DH modulus (P)", HFILL }},
-
- { &hf_ssh_mpint_e,
- { "DH client e", "ssh.dh.e",
- FT_BYTES, BASE_NONE, NULL, 0x0,
- "SSH DH client e", HFILL }},
-
- { &hf_ssh_mpint_f,
- { "DH server f", "ssh.dh.f",
- FT_BYTES, BASE_NONE, NULL, 0x0,
- "SSH DH server f", HFILL }},
-
- { &hf_ssh_mpint_length,
- { "Multi Precision Integer Length", "ssh.mpint_length",
- FT_UINT32, BASE_DEC, NULL, 0x0,
- "SSH mpint length", HFILL }},
-
- { &hf_ssh_kexdh_host_key,
- { "KEX DH host key", "ssh.kexdh.host_key",
- FT_BYTES, BASE_NONE, NULL, 0x0,
- "SSH KEX DH host key", HFILL }},
-
- { &hf_ssh_kexdh_h_sig,
- { "KEX DH H signature", "ssh.kexdh.h_sig",
- FT_BYTES, BASE_NONE, NULL, 0x0,
- "SSH KEX DH H signature", HFILL }},
-
- { &hf_ssh_kexdh_host_key_length,
- { "KEX DH host key length", "ssh.kexdh.host_key_length",
- FT_UINT32, BASE_DEC, NULL, 0x0,
- "SSH KEX DH host key length", HFILL }},
-
- { &hf_ssh_kexdh_h_sig_length,
- { "KEX DH H signature length", "ssh.kexdh.h_sig_length",
- FT_UINT32, BASE_DEC, NULL, 0x0,
- "SSH KEX DH H signature length", HFILL }},
-
- { &hf_ssh_encrypted_packet,
- { "Encrypted Packet", "ssh.encrypted_packet",
- FT_BYTES, BASE_NONE, NULL, 0x0,
- "SSH Protocol Packet", HFILL }},
-
- { &hf_ssh_protocol,
- { "Protocol", "ssh.protocol",
- FT_STRING, BASE_NONE, NULL, 0x0,
- "SSH Protocol", HFILL }},
-
- { &hf_ssh_cookie,
- { "Cookie", "ssh.cookie",
- FT_BYTES, BASE_NONE, NULL, 0x0,
- "SSH Cookie", HFILL }},
-
- { &hf_ssh_kex_first_packet_follows,
- { "KEX First Packet Follows", "ssh.kex.first_packet_follows",
- FT_UINT8, BASE_DEC, NULL, 0x0,
- "SSH KEX Fist Packet Follows", HFILL }},
-
- { &hf_ssh_kex_reserved,
- { "Reserved", "ssh.kex.reserved",
- FT_BYTES, BASE_NONE, NULL, 0x0,
- "SSH Protocol KEX Reserved", HFILL }},
-
- { &hf_ssh_dh_gex_min,
- { "DH GEX Min", "ssh.dh_gex.min",
- FT_UINT32, BASE_DEC, NULL, 0x0,
- "SSH DH GEX Minimum", HFILL }},
-
- { &hf_ssh_dh_gex_nbits,
- { "DH GEX Number of Bits", "ssh.dh_gex.nbits",
- FT_UINT32, BASE_DEC, NULL, 0x0,
- "SSH DH GEX Number of Bits", HFILL }},
-
- { &hf_ssh_dh_gex_max,
- { "DH GEX Max", "ssh.dh_gex.max",
- FT_UINT32, BASE_DEC, NULL, 0x0,
- "SSH DH GEX Maximum", HFILL }},
-
- { &hf_ssh_payload,
- { "Payload", "ssh.payload",
- FT_BYTES, BASE_NONE, NULL, 0x0,
- "SSH Payload", HFILL }},
-
- { &hf_ssh_padding_string,
- { "Padding String", "ssh.padding_string",
- FT_BYTES, BASE_NONE, NULL, 0x0,
- "SSH Padding String", HFILL }},
-
- { &hf_ssh_mac_string,
- { "MAC", "ssh.mac",
- FT_BYTES, BASE_NONE, NULL, 0x0,
- "SSH Protocol Packet MAC", HFILL }},
-
- { &hf_ssh_kex_algorithms,
- { "kex_algorithms string", "ssh.kex_algorithms",
- FT_STRINGZ, BASE_NONE, NULL, 0x0,
- "SSH kex_algorithms string", HFILL }},
-
- { &hf_ssh_server_host_key_algorithms,
- { "server_host_key_algorithms string", "ssh.server_host_key_algorithms",
- FT_STRINGZ, BASE_NONE, NULL, 0x0,
- "SSH server_host_key_algorithms string", HFILL }},
-
- { &hf_ssh_encryption_algorithms_client_to_server,
- { "encryption_algorithms_client_to_server string", "ssh.encryption_algorithms_client_to_server",
- FT_STRINGZ, BASE_NONE, NULL, 0x0,
- "SSH encryption_algorithms_client_to_server string", HFILL }},
-
- { &hf_ssh_encryption_algorithms_server_to_client,
- { "encryption_algorithms_server_to_client string", "ssh.encryption_algorithms_server_to_client",
- FT_STRINGZ, BASE_NONE, NULL, 0x0,
- "SSH encryption_algorithms_server_to_client string", HFILL }},
-
- { &hf_ssh_mac_algorithms_client_to_server,
- { "mac_algorithms_client_to_server string", "ssh.mac_algorithms_client_to_server",
- FT_STRINGZ, BASE_NONE, NULL, 0x0,
- "SSH mac_algorithms_client_to_server string", HFILL }},
-
- { &hf_ssh_mac_algorithms_server_to_client,
- { "mac_algorithms_server_to_client string", "ssh.mac_algorithms_server_to_client",
- FT_STRINGZ, BASE_NONE, NULL, 0x0,
- "SSH mac_algorithms_server_to_client string", HFILL }},
-
- { &hf_ssh_compression_algorithms_client_to_server,
- { "compression_algorithms_client_to_server string", "ssh.compression_algorithms_client_to_server",
- FT_STRINGZ, BASE_NONE, NULL, 0x0,
- "SSH compression_algorithms_client_to_server string", HFILL }},
-
- { &hf_ssh_compression_algorithms_server_to_client,
- { "compression_algorithms_server_to_client string", "ssh.compression_algorithms_server_to_client",
- FT_STRINGZ, BASE_NONE, NULL, 0x0,
- "SSH compression_algorithms_server_to_client string", HFILL }},
-
- { &hf_ssh_languages_client_to_server,
- { "languages_client_to_server string", "ssh.languages_client_to_server",
- FT_STRINGZ, BASE_NONE, NULL, 0x0,
- "SSH languages_client_to_server string", HFILL }},
-
- { &hf_ssh_languages_server_to_client,
- { "languages_server_to_client string", "ssh.languages_server_to_client",
- FT_STRINGZ, BASE_NONE, NULL, 0x0,
- "SSH languages_server_to_client string", HFILL }},
-
- { &hf_ssh_kex_algorithms_length,
- { "kex_algorithms length", "ssh.kex_algorithms_length",
- FT_UINT32, BASE_DEC, NULL, 0x0,
- "SSH kex_algorithms length", HFILL }},
-
- { &hf_ssh_server_host_key_algorithms_length,
- { "server_host_key_algorithms length", "ssh.server_host_key_algorithms_length",
- FT_UINT32, BASE_DEC, NULL, 0x0,
- "SSH server_host_key_algorithms length", HFILL }},
-
- { &hf_ssh_encryption_algorithms_client_to_server_length,
- { "encryption_algorithms_client_to_server length", "ssh.encryption_algorithms_client_to_server_length",
- FT_UINT32, BASE_DEC, NULL, 0x0,
- "SSH encryption_algorithms_client_to_server length", HFILL }},
-
- { &hf_ssh_encryption_algorithms_server_to_client_length,
- { "encryption_algorithms_server_to_client length", "ssh.encryption_algorithms_server_to_client_length",
- FT_UINT32, BASE_DEC, NULL, 0x0,
- "SSH encryption_algorithms_server_to_client length", HFILL }},
-
- { &hf_ssh_mac_algorithms_client_to_server_length,
- { "mac_algorithms_client_to_server length", "ssh.mac_algorithms_client_to_server_length",
- FT_UINT32, BASE_DEC, NULL, 0x0,
- "SSH mac_algorithms_client_to_server length", HFILL }},
-
- { &hf_ssh_mac_algorithms_server_to_client_length,
- { "mac_algorithms_server_to_client length", "ssh.mac_algorithms_server_to_client_length",
- FT_UINT32, BASE_DEC, NULL, 0x0,
- "SSH mac_algorithms_server_to_client length", HFILL }},
-
- { &hf_ssh_compression_algorithms_client_to_server_length,
- { "compression_algorithms_client_to_server length", "ssh.compression_algorithms_client_to_server_length",
- FT_UINT32, BASE_DEC, NULL, 0x0,
- "SSH compression_algorithms_client_to_server length", HFILL }},
-
- { &hf_ssh_compression_algorithms_server_to_client_length,
- { "compression_algorithms_server_to_client length", "ssh.compression_algorithms_server_to_client_length",
- FT_UINT32, BASE_DEC, NULL, 0x0,
- "SSH compression_algorithms_server_to_client length", HFILL }},
-
- { &hf_ssh_languages_client_to_server_length,
- { "languages_client_to_server length", "ssh.languages_client_to_server_length",
- FT_UINT32, BASE_DEC, NULL, 0x0,
- "SSH languages_client_to_server length", HFILL }},
-
- { &hf_ssh_languages_server_to_client_length,
- { "languages_server_to_client length", "ssh.languages_server_to_client_length",
- FT_UINT32, BASE_DEC, NULL, 0x0,
- "SSH languages_server_to_client length", HFILL }},
- };
-
- static gint *ett[] = {
- &ett_ssh,
- &ett_key_exchange,
- &ett_ssh1,
- &ett_ssh2,
- &ett_key_init
- };
-
- static ei_register_info ei[] = {
- { &ei_ssh_packet_length, { "ssh.packet_length.error", PI_PROTOCOL, PI_WARN, "Overly large number", EXPFILL }},
- };
-
- module_t *ssh_module;
- expert_module_t *expert_ssh;
-
- proto_ssh = proto_register_protocol("SSH Protocol", "SSH", "ssh");
- proto_register_field_array(proto_ssh, hf, array_length(hf));
- proto_register_subtree_array(ett, array_length(ett));
- expert_ssh = expert_register_protocol(proto_ssh);
- expert_register_field_array(expert_ssh, ei, array_length(ei));
-
- ssh_module = prefs_register_protocol(proto_ssh, NULL);
- prefs_register_bool_preference(ssh_module, "desegment_buffers",
- "Reassemble SSH buffers spanning multiple TCP segments",
- "Whether the SSH dissector should reassemble SSH buffers spanning multiple TCP segments. "
- "To use this option, you must also enable \"Allow subdissectors to reassemble TCP streams\" in the TCP protocol settings.",
- &ssh_desegment);
-
- ssh_handle = register_dissector("ssh", dissect_ssh, proto_ssh);
+ static hf_register_info hf[] = {
+ { &hf_ssh_packet_length,
+ { "Packet Length", "ssh.packet_length",
+ FT_UINT32, BASE_DEC, NULL, 0x0,
+ "SSH packet length", HFILL }},
+
+ { &hf_ssh_packet_length_encrypted,
+ { "Packet Length (encrypted)", "ssh.packet_length_encrypted",
+ FT_BYTES, BASE_NONE, NULL, 0x0,
+ "SSH packet length (encrypted)", HFILL }},
+
+ { &hf_ssh_padding_length,
+ { "Padding Length", "ssh.padding_length",
+ FT_UINT8, BASE_DEC, NULL, 0x0,
+ "SSH Packet Number", HFILL }},
+
+ { &hf_ssh_msg_code,
+ { "Message Code", "ssh.message_code",
+ FT_UINT8, BASE_DEC, VALS(ssh1_msg_vals), 0x0,
+ "SSH Message Code", HFILL }},
+
+ { &hf_ssh2_msg_code,
+ { "Message Code", "ssh.message_code",
+ FT_UINT8, BASE_DEC, VALS(ssh2_msg_vals), 0x0,
+ "SSH Message Code", HFILL }},
+
+ { &hf_ssh2_kex_dh_msg_code,
+ { "Message Code", "ssh.message_code",
+ FT_UINT8, BASE_DEC, VALS(ssh2_kex_dh_msg_vals), 0x0,
+ "SSH Message Code", HFILL }},
+
+ { &hf_ssh2_kex_dh_gex_msg_code,
+ { "Message Code", "ssh.message_code",
+ FT_UINT8, BASE_DEC, VALS(ssh2_kex_dh_gex_msg_vals), 0x0,
+ "SSH Message Code", HFILL }},
+
+ { &hf_ssh_mpint_g,
+ { "DH base (G)", "ssh.dh.g",
+ FT_BYTES, BASE_NONE, NULL, 0x0,
+ "SSH DH base (G)", HFILL }},
+
+ { &hf_ssh_mpint_p,
+ { "DH modulus (P)", "ssh.dh.p",
+ FT_BYTES, BASE_NONE, NULL, 0x0,
+ "SSH DH modulus (P)", HFILL }},
+
+ { &hf_ssh_mpint_e,
+ { "DH client e", "ssh.dh.e",
+ FT_BYTES, BASE_NONE, NULL, 0x0,
+ "SSH DH client e", HFILL }},
+
+ { &hf_ssh_mpint_f,
+ { "DH server f", "ssh.dh.f",
+ FT_BYTES, BASE_NONE, NULL, 0x0,
+ "SSH DH server f", HFILL }},
+
+ { &hf_ssh_mpint_length,
+ { "Multi Precision Integer Length", "ssh.mpint_length",
+ FT_UINT32, BASE_DEC, NULL, 0x0,
+ "SSH mpint length", HFILL }},
+
+ { &hf_ssh_kexdh_host_key,
+ { "KEX DH host key", "ssh.kexdh.host_key",
+ FT_BYTES, BASE_NONE, NULL, 0x0,
+ "SSH KEX DH host key", HFILL }},
+
+ { &hf_ssh_kexdh_h_sig,
+ { "KEX DH H signature", "ssh.kexdh.h_sig",
+ FT_BYTES, BASE_NONE, NULL, 0x0,
+ "SSH KEX DH H signature", HFILL }},
+
+ { &hf_ssh_kexdh_host_key_length,
+ { "KEX DH host key length", "ssh.kexdh.host_key_length",
+ FT_UINT32, BASE_DEC, NULL, 0x0,
+ "SSH KEX DH host key length", HFILL }},
+
+ { &hf_ssh_kexdh_h_sig_length,
+ { "KEX DH H signature length", "ssh.kexdh.h_sig_length",
+ FT_UINT32, BASE_DEC, NULL, 0x0,
+ "SSH KEX DH H signature length", HFILL }},
+
+ { &hf_ssh_encrypted_packet,
+ { "Encrypted Packet", "ssh.encrypted_packet",
+ FT_BYTES, BASE_NONE, NULL, 0x0,
+ "SSH Protocol Packet", HFILL }},
+
+ { &hf_ssh_protocol,
+ { "Protocol", "ssh.protocol",
+ FT_STRING, BASE_NONE, NULL, 0x0,
+ "SSH Protocol", HFILL }},
+
+ { &hf_ssh_cookie,
+ { "Cookie", "ssh.cookie",
+ FT_BYTES, BASE_NONE, NULL, 0x0,
+ "SSH Cookie", HFILL }},
+
+ { &hf_ssh_kex_first_packet_follows,
+ { "KEX First Packet Follows", "ssh.kex.first_packet_follows",
+ FT_UINT8, BASE_DEC, NULL, 0x0,
+ "SSH KEX Fist Packet Follows", HFILL }},
+
+ { &hf_ssh_kex_reserved,
+ { "Reserved", "ssh.kex.reserved",
+ FT_BYTES, BASE_NONE, NULL, 0x0,
+ "SSH Protocol KEX Reserved", HFILL }},
+
+ { &hf_ssh_dh_gex_min,
+ { "DH GEX Min", "ssh.dh_gex.min",
+ FT_UINT32, BASE_DEC, NULL, 0x0,
+ "SSH DH GEX Minimum", HFILL }},
+
+ { &hf_ssh_dh_gex_nbits,
+ { "DH GEX Number of Bits", "ssh.dh_gex.nbits",
+ FT_UINT32, BASE_DEC, NULL, 0x0,
+ "SSH DH GEX Number of Bits", HFILL }},
+
+ { &hf_ssh_dh_gex_max,
+ { "DH GEX Max", "ssh.dh_gex.max",
+ FT_UINT32, BASE_DEC, NULL, 0x0,
+ "SSH DH GEX Maximum", HFILL }},
+
+ { &hf_ssh_payload,
+ { "Payload", "ssh.payload",
+ FT_BYTES, BASE_NONE, NULL, 0x0,
+ "SSH Payload", HFILL }},
+
+ { &hf_ssh_padding_string,
+ { "Padding String", "ssh.padding_string",
+ FT_BYTES, BASE_NONE, NULL, 0x0,
+ "SSH Padding String", HFILL }},
+
+ { &hf_ssh_mac_string,
+ { "MAC", "ssh.mac",
+ FT_BYTES, BASE_NONE, NULL, 0x0,
+ "SSH Protocol Packet MAC", HFILL }},
+
+ { &hf_ssh_kex_algorithms,
+ { "kex_algorithms string", "ssh.kex_algorithms",
+ FT_STRINGZ, BASE_NONE, NULL, 0x0,
+ "SSH kex_algorithms string", HFILL }},
+
+ { &hf_ssh_server_host_key_algorithms,
+ { "server_host_key_algorithms string", "ssh.server_host_key_algorithms",
+ FT_STRINGZ, BASE_NONE, NULL, 0x0,
+ "SSH server_host_key_algorithms string", HFILL }},
+
+ { &hf_ssh_encryption_algorithms_client_to_server,
+ { "encryption_algorithms_client_to_server string", "ssh.encryption_algorithms_client_to_server",
+ FT_STRINGZ, BASE_NONE, NULL, 0x0,
+ "SSH encryption_algorithms_client_to_server string", HFILL }},
+
+ { &hf_ssh_encryption_algorithms_server_to_client,
+ { "encryption_algorithms_server_to_client string", "ssh.encryption_algorithms_server_to_client",
+ FT_STRINGZ, BASE_NONE, NULL, 0x0,
+ "SSH encryption_algorithms_server_to_client string", HFILL }},
+
+ { &hf_ssh_mac_algorithms_client_to_server,
+ { "mac_algorithms_client_to_server string", "ssh.mac_algorithms_client_to_server",
+ FT_STRINGZ, BASE_NONE, NULL, 0x0,
+ "SSH mac_algorithms_client_to_server string", HFILL }},
+
+ { &hf_ssh_mac_algorithms_server_to_client,
+ { "mac_algorithms_server_to_client string", "ssh.mac_algorithms_server_to_client",
+ FT_STRINGZ, BASE_NONE, NULL, 0x0,
+ "SSH mac_algorithms_server_to_client string", HFILL }},
+
+ { &hf_ssh_compression_algorithms_client_to_server,
+ { "compression_algorithms_client_to_server string", "ssh.compression_algorithms_client_to_server",
+ FT_STRINGZ, BASE_NONE, NULL, 0x0,
+ "SSH compression_algorithms_client_to_server string", HFILL }},
+
+ { &hf_ssh_compression_algorithms_server_to_client,
+ { "compression_algorithms_server_to_client string", "ssh.compression_algorithms_server_to_client",
+ FT_STRINGZ, BASE_NONE, NULL, 0x0,
+ "SSH compression_algorithms_server_to_client string", HFILL }},
+
+ { &hf_ssh_languages_client_to_server,
+ { "languages_client_to_server string", "ssh.languages_client_to_server",
+ FT_STRINGZ, BASE_NONE, NULL, 0x0,
+ "SSH languages_client_to_server string", HFILL }},
+
+ { &hf_ssh_languages_server_to_client,
+ { "languages_server_to_client string", "ssh.languages_server_to_client",
+ FT_STRINGZ, BASE_NONE, NULL, 0x0,
+ "SSH languages_server_to_client string", HFILL }},
+
+ { &hf_ssh_kex_algorithms_length,
+ { "kex_algorithms length", "ssh.kex_algorithms_length",
+ FT_UINT32, BASE_DEC, NULL, 0x0,
+ "SSH kex_algorithms length", HFILL }},
+
+ { &hf_ssh_server_host_key_algorithms_length,
+ { "server_host_key_algorithms length", "ssh.server_host_key_algorithms_length",
+ FT_UINT32, BASE_DEC, NULL, 0x0,
+ "SSH server_host_key_algorithms length", HFILL }},
+
+ { &hf_ssh_encryption_algorithms_client_to_server_length,
+ { "encryption_algorithms_client_to_server length", "ssh.encryption_algorithms_client_to_server_length",
+ FT_UINT32, BASE_DEC, NULL, 0x0,
+ "SSH encryption_algorithms_client_to_server length", HFILL }},
+
+ { &hf_ssh_encryption_algorithms_server_to_client_length,
+ { "encryption_algorithms_server_to_client length", "ssh.encryption_algorithms_server_to_client_length",
+ FT_UINT32, BASE_DEC, NULL, 0x0,
+ "SSH encryption_algorithms_server_to_client length", HFILL }},
+
+ { &hf_ssh_mac_algorithms_client_to_server_length,
+ { "mac_algorithms_client_to_server length", "ssh.mac_algorithms_client_to_server_length",
+ FT_UINT32, BASE_DEC, NULL, 0x0,
+ "SSH mac_algorithms_client_to_server length", HFILL }},
+
+ { &hf_ssh_mac_algorithms_server_to_client_length,
+ { "mac_algorithms_server_to_client length", "ssh.mac_algorithms_server_to_client_length",
+ FT_UINT32, BASE_DEC, NULL, 0x0,
+ "SSH mac_algorithms_server_to_client length", HFILL }},
+
+ { &hf_ssh_compression_algorithms_client_to_server_length,
+ { "compression_algorithms_client_to_server length", "ssh.compression_algorithms_client_to_server_length",
+ FT_UINT32, BASE_DEC, NULL, 0x0,
+ "SSH compression_algorithms_client_to_server length", HFILL }},
+
+ { &hf_ssh_compression_algorithms_server_to_client_length,
+ { "compression_algorithms_server_to_client length", "ssh.compression_algorithms_server_to_client_length",
+ FT_UINT32, BASE_DEC, NULL, 0x0,
+ "SSH compression_algorithms_server_to_client length", HFILL }},
+
+ { &hf_ssh_languages_client_to_server_length,
+ { "languages_client_to_server length", "ssh.languages_client_to_server_length",
+ FT_UINT32, BASE_DEC, NULL, 0x0,
+ "SSH languages_client_to_server length", HFILL }},
+
+ { &hf_ssh_languages_server_to_client_length,
+ { "languages_server_to_client length", "ssh.languages_server_to_client_length",
+ FT_UINT32, BASE_DEC, NULL, 0x0,
+ "SSH languages_server_to_client length", HFILL }},
+ };
+
+ static gint *ett[] = {
+ &ett_ssh,
+ &ett_key_exchange,
+ &ett_ssh1,
+ &ett_ssh2,
+ &ett_key_init
+ };
+
+ static ei_register_info ei[] = {
+ { &ei_ssh_packet_length, { "ssh.packet_length.error", PI_PROTOCOL, PI_WARN, "Overly large number", EXPFILL }},
+ };
+
+ module_t *ssh_module;
+ expert_module_t *expert_ssh;
+
+ proto_ssh = proto_register_protocol("SSH Protocol", "SSH", "ssh");
+ proto_register_field_array(proto_ssh, hf, array_length(hf));
+ proto_register_subtree_array(ett, array_length(ett));
+ expert_ssh = expert_register_protocol(proto_ssh);
+ expert_register_field_array(expert_ssh, ei, array_length(ei));
+
+ ssh_module = prefs_register_protocol(proto_ssh, NULL);
+ prefs_register_bool_preference(ssh_module, "desegment_buffers",
+ "Reassemble SSH buffers spanning multiple TCP segments",
+ "Whether the SSH dissector should reassemble SSH buffers spanning multiple TCP segments. "
+ "To use this option, you must also enable \"Allow subdissectors to reassemble TCP streams\" in the TCP protocol settings.",
+ &ssh_desegment);
+
+ ssh_handle = register_dissector("ssh", dissect_ssh, proto_ssh);
}
void
proto_reg_handoff_ssh(void)
{
- dissector_add_uint("tcp.port", TCP_PORT_SSH, ssh_handle);
- dissector_add_uint("sctp.port", SCTP_PORT_SSH, ssh_handle);
- dissector_add_uint("sctp.ppi", SSH_PAYLOAD_PROTOCOL_ID, ssh_handle);
+ dissector_add_uint("tcp.port", TCP_PORT_SSH, ssh_handle);
+ dissector_add_uint("sctp.port", SCTP_PORT_SSH, ssh_handle);
+ dissector_add_uint("sctp.ppi", SSH_PAYLOAD_PROTOCOL_ID, ssh_handle);
}
/*
* Editor modelines - http://www.wireshark.org/tools/modelines.html
*
* Local variables:
- * c-basic-offset: 8
+ * c-basic-offset: 4
* tab-width: 8
- * indent-tabs-mode: t
+ * indent-tabs-mode: nil
* End:
*
- * vi: set shiftwidth=8 tabstop=8 noexpandtab:
- * :indentSize=8:tabSize=8:noTabs=false:
+ * vi: set shiftwidth=4 tabstop=8 expandtab:
+ * :indentSize=4:tabSize=8:noTabs=true:
*/