* Routines for dcerpc endpoint mapper dissection
* Copyright 2001, Todd Sabin <tas@webspan.net>
*
- * $Id: packet-dcerpc-epm.c,v 1.16 2002/10/23 00:48:33 guy Exp $
+ * $Id: packet-dcerpc-epm.c,v 1.24 2003/11/21 08:40:00 guy Exp $
*
* Ethereal - Network traffic analyzer
* By Gerald Combs <gerald@ethereal.com>
static e_uuid_t uuid_epm = { 0xe1af8308, 0x5d1f, 0x11c9, { 0x91, 0xa4, 0x08, 0x00, 0x2b, 0x14, 0xa0, 0xfa } };
static guint16 ver_epm = 3;
+static const value_string ep_service[] = {
+ { 0, "rpc_c_ep_all_elts" },
+ { 1, "rpc_c_ep_match_by_if" },
+ { 2, "rpc_c_ep_match_by_obj" },
+ { 3, "rpc_c_ep_match_by_both" },
+ { 0, NULL },
+};
/* typedef struct {
unsigned int tower_len,
offset = dissect_ndr_pointer(tvb, offset, pinfo, tree, drep,
epm_dissect_pointer_UUID, NDR_POINTER_PTR,
- "Object:", hf_epm_object, 0);
+ "Object:", hf_epm_object);
offset = dissect_ndr_pointer(tvb, offset, pinfo, tree, drep,
epm_dissect_pointer_IF_ID, NDR_POINTER_PTR,
- "Interface:", hf_epm_if_id, 0);
+ "Interface:", hf_epm_if_id);
offset = dissect_ndr_uint32 (tvb, offset, pinfo, tree, drep,
hf_epm_ver_opt, NULL);
- if (tree) {
- proto_tree_add_bytes (tree, hf_epm_hnd, tvb, offset, 20,
- tvb_get_ptr (tvb, offset, 20));
- }
- offset += 20;
+
+ offset = dissect_ndr_ctx_hnd (tvb, offset, pinfo, tree, drep,
+ hf_epm_hnd, NULL);
offset = dissect_ndr_uint32 (tvb, offset, pinfo, tree, drep,
hf_epm_max_ents, NULL);
guint32 len;
gint strlen;
dcerpc_info *di;
- char *str;
+ const char *str;
di=pinfo->private_data;
if(di->conformant_run){
offset = dissect_ndr_pointer(tvb, offset, pinfo, tree, drep,
epm_dissect_tower, NDR_POINTER_PTR,
- "Tower pointer:", -1, 1);
+ "Tower pointer:", -1);
offset = dissect_ndr_uint32 (tvb, offset, pinfo, tree, drep,
hf_epm_ann_offset, NULL);
offset = dissect_ndr_uint32 (tvb, offset, pinfo, tree, drep,
hf_epm_ann_len, &len);
- str=(char *)tvb_get_ptr(tvb, offset, -1);
+ str=(const char *)tvb_get_ptr(tvb, offset, -1);
strlen=len;
strlen=MIN(strlen,tvb_length_remaining(tvb, offset));
proto_tree_add_item(tree, hf_epm_annotation, tvb, offset, len, TRUE);
offset = dissect_ndr_pointer(tvb, offset, pinfo, tree, drep,
epm_dissect_ept_entry_t_array, NDR_POINTER_REF,
- "Entries:", -1, 1);
+ "Entries:", -1);
offset = dissect_ndr_uint32 (tvb, offset, pinfo, tree, drep,
hf_epm_rc, NULL);
return offset;
}
-#if 0
static int
epm_dissect_uuid (tvbuff_t *tvb, int offset,
packet_info *pinfo, proto_tree *tree,
hf_epm_uuid, NULL);
return offset;
}
-#endif
-
+#define PROTO_ID_OSI_OID 0x00
+#define PROTO_ID_DNA_SESSCTL 0x02
+#define PROTO_ID_DNA_SESSCTL_V3 0x03
+#define PROTO_ID_DNA_NSP 0x04
+#define PROTO_ID_OSI_TP4 0x05
+#define PROTO_ID_OSI_CLNS 0x06
+#define PROTO_ID_TCP 0x07
+#define PROTO_ID_UDP 0x08
+#define PROTO_ID_IP 0x09
+#define PROTO_ID_RPC_CL 0x0a
+#define PROTO_ID_RPC_CO 0x0b
+#define PROTO_ID_UUID 0x0d
+#define PROTO_ID_NAMED_PIPES 0x0f
+#define PROTO_ID_NAMED_PIPES_2 0x10
+#define PROTO_ID_NETBIOS 0x11
+#define PROTO_ID_NETBEUI 0x12
+#define PROTO_ID_NETWARE_SPX 0x13
+#define PROTO_ID_NETWARE_IPX 0x14
+#define PROTO_ID_ATALK_STREAM 0x16
+#define PROTO_ID_ATALK_DATAGRAM 0x17
+#define PROTO_ID_ATALK 0x18
+#define PROTO_ID_NETBIOS_2 0x19
+#define PROTO_ID_VINES_SPP 0x1a
+#define PROTO_ID_VINES_IPC 0x1b
+#define PROTO_ID_STREETTALK 0x1c
+#define PROTO_ID_UNIX_DOMAIN 0x20
+#define PROTO_ID_NULL 0x21
+#define PROTO_ID_NETBIOS_3 0x22
static const value_string proto_id_vals[] = {
- { 0x00, "OSI OID"},
- { 0x0d, "UUID"},
- { 0x05, "OSI TP4"},
- { 0x06, "OSI CLNS or DNA Routing"},
- { 0x07, "DOD TCP"},
- { 0x08, "DOD UDP"},
- { 0x09, "DOD IP"},
- { 0x0a, "RPC connectionless protocol"},
- { 0x0b, "RPC connection-oriented protocol"},
- { 0x02, "DNA Session Control"},
- { 0x03, "DNA Session Control V3"},
- { 0x04, "DNA NSP Transport"},
- { 0x0f, "Named Pipes"},
- { 0x10, "Named Pipes"},
- { 0x11, "NetBIOS"},
- { 0x12, "NetBEUI"},
- { 0x13, "Netware SPX"},
- { 0x14, "Netware IPX"},
- { 0x16, "Appletalk Stream"},
- { 0x17, "Appletalk Datagram"},
- { 0x18, "Appletalk"},
- { 0x19, "NetBIOS"},
- { 0x1a, "Vines SPP"},
- { 0x1b, "Vines IPC"},
- { 0x1c, "StreetTalk"},
- { 0x20, "Unix Domain Socket"},
- { 0x21, "null"},
- { 0x22, "NetBIOS"},
+ { PROTO_ID_OSI_OID, "OSI OID"},
+ { PROTO_ID_DNA_SESSCTL, "DNA Session Control"},
+ { PROTO_ID_DNA_SESSCTL_V3, "DNA Session Control V3"},
+ { PROTO_ID_DNA_NSP, "DNA NSP Transport"},
+ { PROTO_ID_OSI_TP4, "OSI TP4"},
+ { PROTO_ID_OSI_CLNS, "OSI CLNS or DNA Routing"},
+ { PROTO_ID_TCP, "DOD TCP"},
+ { PROTO_ID_UDP, "DOD UDP"},
+ { PROTO_ID_IP, "DOD IP"},
+ { PROTO_ID_RPC_CL, "RPC connectionless protocol"},
+ { PROTO_ID_RPC_CO, "RPC connection-oriented protocol"},
+ { PROTO_ID_UUID, "UUID"},
+ { PROTO_ID_NAMED_PIPES, "Named Pipes"},
+ { PROTO_ID_NAMED_PIPES_2, "Named Pipes"},
+ { PROTO_ID_NETBIOS, "NetBIOS"},
+ { PROTO_ID_NETBEUI, "NetBEUI"},
+ { PROTO_ID_NETWARE_SPX, "Netware SPX"},
+ { PROTO_ID_NETWARE_IPX, "Netware IPX"},
+ { PROTO_ID_ATALK_STREAM, "Appletalk Stream"},
+ { PROTO_ID_ATALK_DATAGRAM, "Appletalk Datagram"},
+ { PROTO_ID_ATALK, "Appletalk"},
+ { PROTO_ID_NETBIOS_2, "NetBIOS"},
+ { PROTO_ID_VINES_SPP, "Vines SPP"},
+ { PROTO_ID_VINES_IPC, "Vines IPC"},
+ { PROTO_ID_STREETTALK, "StreetTalk"},
+ { PROTO_ID_UNIX_DOMAIN, "Unix Domain Socket"},
+ { PROTO_ID_NULL, "null"},
+ { PROTO_ID_NETBIOS_3, "NetBIOS"},
{ 0, NULL},
};
proto_tree_add_uint(tr, hf_epm_tower_proto_id, tvb, offset, 1, proto_id);
switch(proto_id){
- case 0x0d: /* UUID */
+ case PROTO_ID_UUID:
dcerpc_tvb_get_uuid (tvb, offset+1, drep, &uuid);
+
proto_tree_add_string_format (tr, hf_epm_uuid, tvb, offset+1, 16, "",
"UUID: %08x-%04x-%04x-%02x%02x-%02x%02x%02x%02x%02x%02x",
uuid.Data1, uuid.Data2, uuid.Data3,
uuid.Data4[2], uuid.Data4[3],
uuid.Data4[4], uuid.Data4[5],
uuid.Data4[6], uuid.Data4[7]);
- proto_tree_add_text(tr, tvb, offset+17, 2, "Version %d.%d", tvb_get_guint8(tvb, offset+18), tvb_get_guint8(tvb, offset+17));
- break;
- }
+ proto_tree_add_text(tr, tvb, offset+17, 2, "Version %d.%d", tvb_get_guint8(tvb, offset+17), tvb_get_guint8(tvb, offset+18));
+
+ {
+ guint16 version = tvb_get_ntohs(tvb, offset+17);
+ char *service = dcerpc_get_proto_name(&uuid, version);
+ if (service)
+ proto_item_append_text(tr, "UUID: %s", service);
+ else
+ proto_item_append_text(tr, "UUID: %08x-%04x-%04x-%02x%02x-%02x%02x%02x%02x%02x%02x Version %d.%d", uuid.Data1, uuid.Data2, uuid.Data3,
+ uuid.Data4[0], uuid.Data4[1],
+ uuid.Data4[2], uuid.Data4[3],
+ uuid.Data4[4], uuid.Data4[5],
+ uuid.Data4[6], uuid.Data4[7],
+ tvb_get_guint8(tvb, offset+17),
+ tvb_get_guint8(tvb, offset+18));
+ }
+ break;
+ }
offset += len;
len = tvb_get_letohs(tvb, offset);
offset += 2;
switch(proto_id){
- case 0x07: /* TCP this one is always big endian */
+
+ case PROTO_ID_TCP: /* this one is always big endian */
proto_tree_add_item(tr, hf_epm_proto_tcp_port, tvb, offset, 2, FALSE);
proto_item_append_text(tr, "TCP Port:%d", tvb_get_ntohs(tvb, offset));
break;
- case 0x08: /* UDP this one is always big endian */
+ case PROTO_ID_UDP: /* this one is always big endian */
proto_tree_add_item(tr, hf_epm_proto_udp_port, tvb, offset, 2, FALSE);
proto_item_append_text(tr, "UDP Port:%d", tvb_get_ntohs(tvb, offset));
break;
- case 0x09: /* IP this one is always big endian */
+ case PROTO_ID_IP: /* this one is always big endian */
proto_tree_add_item(tr, hf_epm_proto_ip, tvb, offset, 4, TRUE);
proto_item_append_text(tr, "IP:%s", ip_to_str(tvb_get_ptr(tvb, offset, 4)));
break;
- case 0x0f: /* \\PIPE\xxx named pipe */
+ case PROTO_ID_RPC_CO:
+ proto_item_append_text(tr, "RPC connection-oriented protocol");
+ break;
+
+ case PROTO_ID_NAMED_PIPES: /* \\PIPE\xxx named pipe */
proto_tree_add_item(tr, hf_epm_proto_named_pipes, tvb, offset, len, TRUE);
proto_item_append_text(tr, "NamedPipe:%*s",MIN(len,tvb_length_remaining(tvb, offset)), tvb_get_ptr(tvb, offset, -1));
break;
- case 0x10: /* PIPENAME named pipe */
+ case PROTO_ID_NAMED_PIPES_2: /* PIPENAME named pipe */
proto_tree_add_item(tr, hf_epm_proto_named_pipes, tvb, offset, len, TRUE);
proto_item_append_text(tr, "PIPE:%*s",MIN(len,tvb_length_remaining(tvb, offset)), tvb_get_ptr(tvb, offset, -1));
break;
- case 0x11: /* \\NETBIOS netbios name */
+ case PROTO_ID_NETBIOS: /* \\NETBIOS netbios name */
proto_tree_add_item(tr, hf_epm_proto_netbios_name, tvb, offset, len, TRUE);
proto_item_append_text(tr, "NetBIOS:%*s",MIN(len,tvb_length_remaining(tvb, offset)), tvb_get_ptr(tvb, offset, -1));
break;
+
default:
if(len){
proto_tree_add_text(tr, tvb, offset, len, "not decoded yet");
{
offset = dissect_ndr_pointer(tvb, offset, pinfo, tree, drep,
epm_dissect_tower, NDR_POINTER_PTR,
- "Tower pointer:", -1, 1);
+ "Tower pointer:", -1);
return offset;
}
static int
packet_info *pinfo, proto_tree *tree,
char *drep)
{
- /* [in] handle_t h */
- offset = dissect_ndr_ctx_hnd (tvb, offset, pinfo, tree, drep,
- hf_epm_hnd, NULL);
-
-#if 0
- /* according to opengroup we should have an uuid pointer here.
- in my w2k captures i can not see any such thing */
/* [in, ptr] uuid_p_t object */
offset = dissect_ndr_pointer(tvb, offset, pinfo, tree, drep,
epm_dissect_uuid, NDR_POINTER_PTR,
- "UUID pointer:", -1, 1);
-#endif
+ "UUID pointer:", -1);
/* [in, ptr] twr_p_t map_tower */
offset = dissect_ndr_pointer(tvb, offset, pinfo, tree, drep,
epm_dissect_tower, NDR_POINTER_PTR,
- "Tower pointer:", -1, 1);
+ "Tower pointer:", -1);
/* [in, out] ept_lookup_handle_t *entry_handle */
offset = dissect_ndr_ctx_hnd (tvb, offset, pinfo, tree, drep,
/* [out, length_is(*num_towers), size_is(max_towers), ptr] twr_p_t towers[] */
offset = dissect_ndr_pointer(tvb, offset, pinfo, tree, drep,
epm_dissect_tower_array, NDR_POINTER_REF,
- "Tower array:", -1, 1);
+ "Tower array:", -1);
/* [out] error_status_t *status */
offset = dissect_ndr_uint32 (tvb, offset, pinfo, tree, drep,
packet_info *pinfo, proto_tree *tree,
char *drep)
{
- /* [in, out] ept_lookup_handle_t *entry_handle */
- offset = dissect_ndr_ctx_hnd (tvb, offset, pinfo, tree, drep,
- hf_epm_hnd, NULL);
-
offset = dissect_ndr_uint32 (tvb, offset, pinfo, tree, drep,
hf_epm_num_ents, NULL);
offset = dissect_ndr_pointer(tvb, offset, pinfo, tree, drep,
epm_dissect_ept_entry_t_ucarray, NDR_POINTER_REF,
- "Entries:", -1, 1);
+ "Entries:", -1);
offset = dissect_ndr_uint32 (tvb, offset, pinfo, tree, drep,
hf_epm_replace, NULL);
packet_info *pinfo, proto_tree *tree,
char *drep)
{
- offset = dissect_ndr_ctx_hnd (tvb, offset, pinfo, tree, drep,
- hf_epm_hnd, NULL);
-
offset = dissect_ndr_uint32 (tvb, offset, pinfo, tree, drep,
hf_epm_num_ents, NULL);
offset = dissect_ndr_pointer(tvb, offset, pinfo, tree, drep,
epm_dissect_ept_entry_t_ucarray, NDR_POINTER_REF,
- "Entries:", -1, 1);
+ "Entries:", -1);
return offset;
}
}
+
+static int
+epm_dissect_ept_lookup_handle_free_rqst (tvbuff_t *tvb, int offset,
+ packet_info *pinfo, proto_tree *tree,
+ char *drep)
+{
+ /* [in, out] ept_lookup_handle_t *entry_handle */
+ offset = dissect_ndr_ctx_hnd (tvb, offset, pinfo, tree, drep,
+ hf_epm_hnd, NULL);
+
+ return offset;
+}
+
+static int
+epm_dissect_ept_lookup_handle_free_resp (tvbuff_t *tvb, int offset,
+ packet_info *pinfo, proto_tree *tree,
+ char *drep)
+{
+ /* [in, out] ept_lookup_handle_t *entry_handle */
+ offset = dissect_ndr_ctx_hnd (tvb, offset, pinfo, tree, drep,
+ hf_epm_hnd, NULL);
+
+ offset = dissect_ndr_uint32 (tvb, offset, pinfo, tree, drep,
+ hf_epm_rc, NULL);
+
+ return offset;
+}
+
+
static dcerpc_sub_dissector epm_dissectors[] = {
{ 0, "Insert",
epm_dissect_ept_insert_rqst,
{ 3, "Map",
epm_dissect_ept_map_rqst,
epm_dissect_ept_map_resp },
- { 4, "ept_lookup_handle_free", NULL, NULL },
- { 5, "ept_inq_object", NULL, NULL },
- { 6, "ept_mgmt_delete", NULL, NULL },
+ { 4, "LookupHandleFree",
+ epm_dissect_ept_lookup_handle_free_rqst,
+ epm_dissect_ept_lookup_handle_free_resp },
+ { 5, "InqObject", NULL, NULL },
+ { 6, "MgmtDelete", NULL, NULL },
{ 0, NULL, NULL, NULL }
};
-static const value_string epm_opnum_vals[] = {
- { 0, "Insert" },
- { 1, "Delete" },
- { 2, "Lookup" },
- { 3, "Map" },
- { 4, "lookup_handle_free" },
- { 5, "inq_object" },
- { 6, "mgmt_delete" },
- { 0, NULL }
-};
-
void
proto_register_epm (void)
{
static hf_register_info hf[] = {
{ &hf_epm_opnum,
{ "Operation", "epm.opnum", FT_UINT16, BASE_DEC,
- VALS(epm_opnum_vals), 0x0, "Operation", HFILL }},
+ NULL, 0x0, "Operation", HFILL }},
{ &hf_epm_inquiry_type,
- { "Inquiry type", "epm.inq_type", FT_UINT32, BASE_DEC, NULL, 0x0, "", HFILL }},
+ { "Inquiry type", "epm.inq_type", FT_UINT32, BASE_DEC, VALS(ep_service), 0x0, "", HFILL }},
{ &hf_epm_object,
{ "Object", "epm.object", FT_STRING, BASE_NONE, NULL, 0x0, "", HFILL }},
{ &hf_epm_if_id,