Revert "TODO epan/dissectors/asn1/kerberos/packet-kerberos-template.c new GSS flags"
[wireshark-sm.git] / epan / dissectors / packet-gnutella.c
blobb70b15ed6a19b081209066ea1afbb2ccbf161742
1 /* packet-gnutella.c
2 * Routines for gnutella dissection
3 * Copyright 2001, B. Johannessen <bob@havoq.com>
5 * Wireshark - Network traffic analyzer
6 * By Gerald Combs <gerald@wireshark.org>
7 * Copyright 1998 Gerald Combs
9 * SPDX-License-Identifier: GPL-2.0-or-later
12 #include "config.h"
14 #include <epan/packet.h>
15 #include "packet-tcp.h"
17 void proto_register_gnutella(void);
18 void proto_reg_handoff_gnutella(void);
20 static dissector_handle_t gnutella_handle;
23 * See
25 * http://rfc-gnutella.sourceforge.net/developer/index.html
28 static int proto_gnutella;
30 static int hf_gnutella_stream;
32 static int hf_gnutella_header;
33 static int hf_gnutella_header_id;
34 static int hf_gnutella_header_payload;
35 static int hf_gnutella_header_ttl;
36 static int hf_gnutella_header_hops;
37 static int hf_gnutella_header_size;
39 static int hf_gnutella_pong_payload;
40 static int hf_gnutella_pong_port;
41 static int hf_gnutella_pong_ip;
42 static int hf_gnutella_pong_files;
43 static int hf_gnutella_pong_kbytes;
45 static int hf_gnutella_query_payload;
46 static int hf_gnutella_query_min_speed;
47 static int hf_gnutella_query_search;
49 static int hf_gnutella_queryhit_payload;
50 static int hf_gnutella_queryhit_count;
51 static int hf_gnutella_queryhit_port;
52 static int hf_gnutella_queryhit_ip;
53 static int hf_gnutella_queryhit_speed;
54 static int hf_gnutella_queryhit_extra;
55 static int hf_gnutella_queryhit_servent_id;
57 static int hf_gnutella_queryhit_hit;
58 static int hf_gnutella_queryhit_hit_index;
59 static int hf_gnutella_queryhit_hit_size;
60 static int hf_gnutella_queryhit_hit_name;
61 static int hf_gnutella_queryhit_hit_extra;
63 static int hf_gnutella_push_payload;
64 static int hf_gnutella_push_servent_id;
65 static int hf_gnutella_push_index;
66 static int hf_gnutella_push_ip;
67 static int hf_gnutella_push_port;
69 static int ett_gnutella;
71 #define GNUTELLA_TCP_PORT 6346
74 * Used to determine whether a chunk of data looks like a Gnutella packet
75 * or not - it might be a transfer stream, or it might be part of a
76 * Gnutella packet that starts in an earlier missing TCP segment.
78 * One Gnutella spec says packets SHOULD be no bigger than 4K, although
79 * that's SHOULD, not MUST.
81 #define GNUTELLA_MAX_SNAP_SIZE 4096
83 #define GNUTELLA_UNKNOWN_NAME "Unknown"
84 #define GNUTELLA_PING 0x00
85 #define GNUTELLA_PING_NAME "Ping"
86 #define GNUTELLA_PONG 0x01
87 #define GNUTELLA_PONG_NAME "Pong"
88 #define GNUTELLA_PUSH 0x40
89 #define GNUTELLA_PUSH_NAME "Push"
90 #define GNUTELLA_QUERY 0x80
91 #define GNUTELLA_QUERY_NAME "Query"
92 #define GNUTELLA_QUERYHIT 0x81
93 #define GNUTELLA_QUERYHIT_NAME "QueryHit"
95 #define GNUTELLA_HEADER_LENGTH 23
96 #define GNUTELLA_SERVENT_ID_LENGTH 16
97 #define GNUTELLA_PORT_LENGTH 2
98 #define GNUTELLA_IP_LENGTH 4
99 #define GNUTELLA_LONG_LENGTH 4
100 #define GNUTELLA_SHORT_LENGTH 2
101 #define GNUTELLA_BYTE_LENGTH 1
103 #define GNUTELLA_PONG_LENGTH 14
104 #define GNUTELLA_PONG_PORT_OFFSET 0
105 #define GNUTELLA_PONG_IP_OFFSET 2
106 #define GNUTELLA_PONG_FILES_OFFSET 6
107 #define GNUTELLA_PONG_KBYTES_OFFSET 10
109 #define GNUTELLA_QUERY_SPEED_OFFSET 0
110 #define GNUTELLA_QUERY_SEARCH_OFFSET 2
112 #define GNUTELLA_QUERYHIT_HEADER_LENGTH 11
113 #define GNUTELLA_QUERYHIT_COUNT_OFFSET 0
114 #define GNUTELLA_QUERYHIT_PORT_OFFSET 1
115 #define GNUTELLA_QUERYHIT_IP_OFFSET 3
116 #define GNUTELLA_QUERYHIT_SPEED_OFFSET 7
117 #define GNUTELLA_QUERYHIT_FIRST_HIT_OFFSET 11
118 #define GNUTELLA_QUERYHIT_HIT_INDEX_OFFSET 0
119 #define GNUTELLA_QUERYHIT_HIT_SIZE_OFFSET 4
120 #define GNUTELLA_QUERYHIT_END_OF_STRING_LENGTH 2
122 #define GNUTELLA_PUSH_SERVENT_ID_OFFSET 0
123 #define GNUTELLA_PUSH_INDEX_OFFSET 16
124 #define GNUTELLA_PUSH_IP_OFFSET 20
125 #define GNUTELLA_PUSH_PORT_OFFSET 24
127 #define GNUTELLA_HEADER_ID_OFFSET 0
128 #define GNUTELLA_HEADER_PAYLOAD_OFFSET 16
129 #define GNUTELLA_HEADER_TTL_OFFSET 17
130 #define GNUTELLA_HEADER_HOPS_OFFSET 18
131 #define GNUTELLA_HEADER_SIZE_OFFSET 19
133 static void dissect_gnutella_pong(tvbuff_t *tvb, unsigned offset, proto_tree *tree) {
135 proto_tree_add_item(tree,
136 hf_gnutella_pong_port,
137 tvb,
138 offset + GNUTELLA_PONG_PORT_OFFSET,
139 GNUTELLA_PORT_LENGTH,
140 ENC_LITTLE_ENDIAN);
142 proto_tree_add_item(tree,
143 hf_gnutella_pong_ip,
144 tvb,
145 offset + GNUTELLA_PONG_IP_OFFSET,
146 GNUTELLA_IP_LENGTH,
147 ENC_BIG_ENDIAN);
149 proto_tree_add_item(tree,
150 hf_gnutella_pong_files,
151 tvb,
152 offset + GNUTELLA_PONG_FILES_OFFSET,
153 GNUTELLA_LONG_LENGTH,
154 ENC_LITTLE_ENDIAN);
156 proto_tree_add_item(tree,
157 hf_gnutella_pong_kbytes,
158 tvb,
159 offset + GNUTELLA_PONG_KBYTES_OFFSET,
160 GNUTELLA_LONG_LENGTH,
161 ENC_LITTLE_ENDIAN);
165 static void dissect_gnutella_query(tvbuff_t *tvb, unsigned offset, proto_tree *tree, unsigned size) {
167 proto_tree_add_item(tree,
168 hf_gnutella_query_min_speed,
169 tvb,
170 offset + GNUTELLA_QUERY_SPEED_OFFSET,
171 GNUTELLA_SHORT_LENGTH,
172 ENC_LITTLE_ENDIAN);
174 if (size > GNUTELLA_SHORT_LENGTH) {
176 * XXX - the 0.4 spec says, of this field:
178 * It SHOULD use an ASCII-compatible encoding and
179 * charset. In this version of the protocol, no
180 * encoding was specified, but most servents use
181 * the ISO-8859-1 character set, but other encodings
182 * such as UTF-8 MAY also be used (possibly in
183 * conjonction with Query Data), as well as other
184 * international character sets (ISO-8859-*, KOI-8,
185 * S-JIS, Big5, ...).
187 * No obvious mechanism is provided to indicate what
188 * encoding is being used; perhaps this should be
189 * made a preference, defaulting to ISO 8859-1.
191 proto_tree_add_item(tree,
192 hf_gnutella_query_search,
193 tvb,
194 offset + GNUTELLA_QUERY_SEARCH_OFFSET,
195 size - GNUTELLA_SHORT_LENGTH,
196 ENC_ASCII);
198 else {
199 proto_tree_add_string_format(tree,
200 hf_gnutella_query_search, tvb,
201 offset + GNUTELLA_QUERY_SEARCH_OFFSET,
202 0, "", "Missing data for Query Search.");
206 static void dissect_gnutella_queryhit(tvbuff_t *tvb, unsigned offset, proto_tree *tree, unsigned size) {
208 proto_tree *qhi, *hit_tree;
209 int hit_count, i;
210 int hit_offset;
211 int name_length, extra_length;
212 int idx_at_offset, size_at_offset;
213 int servent_id_at_offset;
214 int name_at_offset, extra_at_offset;
215 int cur_char, remaining, used;
217 hit_count = tvb_get_uint8(tvb, offset + GNUTELLA_QUERYHIT_COUNT_OFFSET);
219 proto_tree_add_uint(tree,
220 hf_gnutella_queryhit_count,
221 tvb,
222 offset + GNUTELLA_QUERYHIT_COUNT_OFFSET,
223 GNUTELLA_BYTE_LENGTH,
224 hit_count);
226 proto_tree_add_item(tree,
227 hf_gnutella_queryhit_port,
228 tvb,
229 offset + GNUTELLA_QUERYHIT_PORT_OFFSET,
230 GNUTELLA_PORT_LENGTH,
231 ENC_LITTLE_ENDIAN);
233 proto_tree_add_item(tree,
234 hf_gnutella_queryhit_ip,
235 tvb,
236 offset + GNUTELLA_QUERYHIT_IP_OFFSET,
237 GNUTELLA_IP_LENGTH,
238 ENC_BIG_ENDIAN);
240 proto_tree_add_item(tree,
241 hf_gnutella_queryhit_speed,
242 tvb,
243 offset + GNUTELLA_QUERYHIT_SPEED_OFFSET,
244 GNUTELLA_LONG_LENGTH,
245 ENC_LITTLE_ENDIAN);
247 hit_offset = offset + GNUTELLA_QUERYHIT_FIRST_HIT_OFFSET;
249 for(i = 0; i < hit_count; i++) {
250 idx_at_offset = hit_offset;
251 size_at_offset = hit_offset + GNUTELLA_QUERYHIT_HIT_SIZE_OFFSET;
253 hit_offset += (GNUTELLA_LONG_LENGTH * 2);
255 name_length = 0;
256 extra_length = 0;
258 name_at_offset = hit_offset;
260 while(hit_offset - offset < size) {
261 cur_char = tvb_get_uint8(tvb, hit_offset);
262 if(cur_char == '\0')
263 break;
265 hit_offset++;
266 name_length++;
269 hit_offset++;
271 extra_at_offset = hit_offset;
273 while(hit_offset - offset < size) {
274 cur_char = tvb_get_uint8(tvb, hit_offset);
275 if(cur_char == '\0')
276 break;
278 hit_offset++;
279 extra_length++;
282 hit_offset++;
284 qhi = proto_tree_add_item(tree,
285 hf_gnutella_queryhit_hit,
286 tvb,
287 idx_at_offset,
288 (GNUTELLA_LONG_LENGTH * 2) +
289 name_length + extra_length +
290 GNUTELLA_QUERYHIT_END_OF_STRING_LENGTH,
291 ENC_NA);
293 hit_tree = proto_item_add_subtree(qhi, ett_gnutella);
295 proto_tree_add_item(hit_tree,
296 hf_gnutella_queryhit_hit_index,
297 tvb,
298 idx_at_offset,
299 GNUTELLA_LONG_LENGTH,
300 ENC_LITTLE_ENDIAN);
302 proto_tree_add_item(hit_tree,
303 hf_gnutella_queryhit_hit_size,
304 tvb,
305 size_at_offset,
306 GNUTELLA_LONG_LENGTH,
307 ENC_LITTLE_ENDIAN);
309 proto_tree_add_item(hit_tree,
310 hf_gnutella_queryhit_hit_name,
311 tvb,
312 name_at_offset,
313 name_length,
314 ENC_ASCII);
316 if(extra_length) {
317 proto_tree_add_item(hit_tree,
318 hf_gnutella_queryhit_hit_extra,
319 tvb,
320 extra_at_offset,
321 extra_length,
322 ENC_NA);
326 used = hit_offset - offset;
327 remaining = size - used;
329 if(remaining > GNUTELLA_SERVENT_ID_LENGTH) {
330 servent_id_at_offset = hit_offset + remaining - GNUTELLA_SERVENT_ID_LENGTH;
332 proto_tree_add_item(tree,
333 hf_gnutella_queryhit_extra,
334 tvb,
335 hit_offset,
336 servent_id_at_offset - hit_offset,
337 ENC_NA);
339 else {
340 servent_id_at_offset = hit_offset;
343 proto_tree_add_item(tree,
344 hf_gnutella_queryhit_servent_id,
345 tvb,
346 servent_id_at_offset,
347 GNUTELLA_SERVENT_ID_LENGTH,
348 ENC_NA);
352 static void dissect_gnutella_push(tvbuff_t *tvb, unsigned offset, proto_tree *tree) {
354 proto_tree_add_item(tree,
355 hf_gnutella_push_servent_id,
356 tvb,
357 offset + GNUTELLA_PUSH_SERVENT_ID_OFFSET,
358 GNUTELLA_SERVENT_ID_LENGTH,
359 ENC_NA);
361 proto_tree_add_item(tree,
362 hf_gnutella_push_index,
363 tvb,
364 offset + GNUTELLA_PUSH_INDEX_OFFSET,
365 GNUTELLA_LONG_LENGTH,
366 ENC_LITTLE_ENDIAN);
368 proto_tree_add_item(tree,
369 hf_gnutella_push_ip,
370 tvb,
371 offset + GNUTELLA_PUSH_IP_OFFSET,
372 GNUTELLA_IP_LENGTH,
373 ENC_BIG_ENDIAN);
375 proto_tree_add_item(tree,
376 hf_gnutella_push_port,
377 tvb,
378 offset + GNUTELLA_PUSH_PORT_OFFSET,
379 GNUTELLA_PORT_LENGTH,
380 ENC_LITTLE_ENDIAN);
384 static unsigned
385 get_gnutella_pdu_len(packet_info *pinfo _U_, tvbuff_t *tvb,
386 int offset, void *data _U_)
388 uint32_t size;
390 size = tvb_get_letohl(
391 tvb,
392 offset + GNUTELLA_HEADER_SIZE_OFFSET);
393 if (size > GNUTELLA_MAX_SNAP_SIZE) {
395 * XXX - arbitrary limit, preventing overflows and
396 * attempts to reassemble 4GB of data.
398 size = GNUTELLA_MAX_SNAP_SIZE;
401 /* The size doesn't include the header */
402 return GNUTELLA_HEADER_LENGTH + size;
405 static int dissect_gnutella_pdu(tvbuff_t *tvb, packet_info *pinfo, proto_tree *tree, void* data _U_) {
407 proto_item *ti, *hi, *pi;
408 proto_tree *gnutella_tree = NULL;
409 proto_tree *gnutella_header_tree, *gnutella_pong_tree;
410 proto_tree *gnutella_queryhit_tree, *gnutella_push_tree;
411 proto_tree *gnutella_query_tree;
412 uint8_t payload_descriptor;
413 uint32_t size = 0;
414 const char *payload_descriptor_text;
416 if (tree) {
417 ti = proto_tree_add_item(tree,
418 proto_gnutella,
419 tvb,
422 ENC_NA);
423 gnutella_tree = proto_item_add_subtree(ti, ett_gnutella);
425 size = tvb_get_letohl(
426 tvb,
427 GNUTELLA_HEADER_SIZE_OFFSET);
430 payload_descriptor = tvb_get_uint8(
431 tvb,
432 GNUTELLA_HEADER_PAYLOAD_OFFSET);
434 switch(payload_descriptor) {
435 case GNUTELLA_PING:
436 payload_descriptor_text = GNUTELLA_PING_NAME;
437 break;
438 case GNUTELLA_PONG:
439 payload_descriptor_text = GNUTELLA_PONG_NAME;
440 break;
441 case GNUTELLA_PUSH:
442 payload_descriptor_text = GNUTELLA_PUSH_NAME;
443 break;
444 case GNUTELLA_QUERY:
445 payload_descriptor_text = GNUTELLA_QUERY_NAME;
446 break;
447 case GNUTELLA_QUERYHIT:
448 payload_descriptor_text = GNUTELLA_QUERYHIT_NAME;
449 break;
450 default:
451 payload_descriptor_text = GNUTELLA_UNKNOWN_NAME;
452 break;
455 col_append_sep_str(pinfo->cinfo, COL_INFO, NULL,
456 payload_descriptor_text);
458 if (tree) {
459 hi = proto_tree_add_item(gnutella_tree,
460 hf_gnutella_header,
461 tvb,
463 GNUTELLA_HEADER_LENGTH,
464 ENC_NA);
465 gnutella_header_tree = proto_item_add_subtree(hi, ett_gnutella);
467 proto_tree_add_item(gnutella_header_tree,
468 hf_gnutella_header_id,
469 tvb,
470 GNUTELLA_HEADER_ID_OFFSET,
471 GNUTELLA_SERVENT_ID_LENGTH,
472 ENC_NA);
474 proto_tree_add_uint_format_value(gnutella_header_tree,
475 hf_gnutella_header_payload,
476 tvb,
477 GNUTELLA_HEADER_PAYLOAD_OFFSET,
478 GNUTELLA_BYTE_LENGTH,
479 payload_descriptor,
480 "%i (%s)",
481 payload_descriptor,
482 payload_descriptor_text);
484 proto_tree_add_item(gnutella_header_tree,
485 hf_gnutella_header_ttl,
486 tvb,
487 GNUTELLA_HEADER_TTL_OFFSET,
488 GNUTELLA_BYTE_LENGTH,
489 ENC_BIG_ENDIAN);
491 proto_tree_add_item(gnutella_header_tree,
492 hf_gnutella_header_hops,
493 tvb,
494 GNUTELLA_HEADER_HOPS_OFFSET,
495 GNUTELLA_BYTE_LENGTH,
496 ENC_BIG_ENDIAN);
498 proto_tree_add_uint(gnutella_header_tree,
499 hf_gnutella_header_size,
500 tvb,
501 GNUTELLA_HEADER_SIZE_OFFSET,
502 GNUTELLA_LONG_LENGTH,
503 size);
505 if (size > 0) {
506 switch(payload_descriptor) {
507 case GNUTELLA_PONG:
508 pi = proto_tree_add_item(
509 gnutella_header_tree,
510 hf_gnutella_pong_payload,
511 tvb,
512 GNUTELLA_HEADER_LENGTH,
513 size,
514 ENC_NA);
515 gnutella_pong_tree = proto_item_add_subtree(
517 ett_gnutella);
518 dissect_gnutella_pong(
519 tvb,
520 GNUTELLA_HEADER_LENGTH,
521 gnutella_pong_tree);
522 break;
523 case GNUTELLA_PUSH:
524 pi = proto_tree_add_item(
525 gnutella_header_tree,
526 hf_gnutella_push_payload,
527 tvb,
528 GNUTELLA_HEADER_LENGTH,
529 size,
530 ENC_NA);
531 gnutella_push_tree = proto_item_add_subtree(
533 ett_gnutella);
534 dissect_gnutella_push(
535 tvb,
536 GNUTELLA_HEADER_LENGTH,
537 gnutella_push_tree);
538 break;
539 case GNUTELLA_QUERY:
540 pi = proto_tree_add_item(
541 gnutella_header_tree,
542 hf_gnutella_query_payload,
543 tvb,
544 GNUTELLA_HEADER_LENGTH,
545 size,
546 ENC_NA);
547 gnutella_query_tree = proto_item_add_subtree(
549 ett_gnutella);
550 dissect_gnutella_query(
551 tvb,
552 GNUTELLA_HEADER_LENGTH,
553 gnutella_query_tree,
554 size);
555 break;
556 case GNUTELLA_QUERYHIT:
557 pi = proto_tree_add_item(
558 gnutella_header_tree,
559 hf_gnutella_queryhit_payload,
560 tvb,
561 GNUTELLA_HEADER_LENGTH,
562 size,
563 ENC_NA);
564 gnutella_queryhit_tree = proto_item_add_subtree(
566 ett_gnutella);
567 dissect_gnutella_queryhit(
568 tvb,
569 GNUTELLA_HEADER_LENGTH,
570 gnutella_queryhit_tree,
571 size);
572 break;
577 return tvb_captured_length(tvb);
581 static int dissect_gnutella(tvbuff_t *tvb, packet_info *pinfo, proto_tree *tree, void* data) {
583 proto_item *ti;
584 proto_tree *gnutella_tree = NULL;
585 uint32_t size;
587 col_set_str(pinfo->cinfo, COL_PROTOCOL, "Gnutella");
589 col_clear(pinfo->cinfo, COL_INFO);
592 * OK, do we have enough data to determine whether this
593 * is Gnutella messages or just a transfer stream?
595 if (tvb_bytes_exist(tvb, GNUTELLA_HEADER_SIZE_OFFSET, 4)) {
597 * Yes - fetch the length and see if it's bigger
598 * than GNUTELLA_MAX_SNAP_SIZE; if it is, we assume
599 * it's a transfer stream.
601 * Should we also check the payload descriptor?
603 size = tvb_get_letohl(
604 tvb,
605 GNUTELLA_HEADER_SIZE_OFFSET);
606 if (size > GNUTELLA_MAX_SNAP_SIZE) {
607 if (tree) {
608 ti = proto_tree_add_item(tree,
609 proto_gnutella,
610 tvb,
613 ENC_NA);
614 gnutella_tree = proto_item_add_subtree(ti,
615 ett_gnutella);
617 proto_tree_add_item(gnutella_tree,
618 hf_gnutella_stream,
619 tvb,
622 ENC_NA);
624 return tvb_captured_length(tvb);
628 tcp_dissect_pdus(tvb, pinfo, tree, true, GNUTELLA_HEADER_SIZE_OFFSET+4,
629 get_gnutella_pdu_len, dissect_gnutella_pdu, data);
630 return tvb_captured_length(tvb);
633 void proto_register_gnutella(void) {
635 static hf_register_info hf[] = {
636 { &hf_gnutella_header,
637 { "Descriptor Header", "gnutella.header",
638 FT_NONE, BASE_NONE, NULL, 0,
639 "Gnutella Descriptor Header", HFILL }
641 { &hf_gnutella_pong_payload,
642 { "Pong", "gnutella.pong.payload",
643 FT_NONE, BASE_NONE, NULL, 0,
644 "Gnutella Pong Payload", HFILL }
646 { &hf_gnutella_push_payload,
647 { "Push", "gnutella.push.payload",
648 FT_NONE, BASE_NONE, NULL, 0,
649 "Gnutella Push Payload", HFILL }
651 { &hf_gnutella_query_payload,
652 { "Query", "gnutella.query.payload",
653 FT_NONE, BASE_NONE, NULL, 0,
654 "Gnutella Query Payload", HFILL }
656 { &hf_gnutella_queryhit_payload,
657 { "QueryHit", "gnutella.queryhit.payload",
658 FT_NONE, BASE_NONE, NULL, 0,
659 "Gnutella QueryHit Payload", HFILL }
661 { &hf_gnutella_stream,
662 { "Gnutella Upload / Download Stream", "gnutella.stream",
663 FT_NONE, BASE_NONE, NULL, 0,
664 NULL, HFILL }
666 { &hf_gnutella_header_id,
667 { "ID", "gnutella.header.id",
668 FT_BYTES, BASE_NONE, NULL, 0,
669 "Gnutella Descriptor ID", HFILL }
671 { &hf_gnutella_header_payload,
672 { "Payload", "gnutella.header.payload",
673 FT_UINT8, BASE_DEC, NULL, 0,
674 "Gnutella Descriptor Payload", HFILL }
676 { &hf_gnutella_header_ttl,
677 { "TTL", "gnutella.header.ttl",
678 FT_UINT8, BASE_DEC, NULL, 0,
679 "Gnutella Descriptor Time To Live", HFILL }
681 { &hf_gnutella_header_hops,
682 { "Hops", "gnutella.header.hops",
683 FT_UINT8, BASE_DEC, NULL, 0,
684 "Gnutella Descriptor Hop Count", HFILL }
686 { &hf_gnutella_header_size,
687 { "Length", "gnutella.header.size",
688 FT_UINT8, BASE_DEC, NULL, 0,
689 "Gnutella Descriptor Payload Length", HFILL }
691 { &hf_gnutella_pong_port,
692 { "Port", "gnutella.pong.port",
693 FT_UINT16, BASE_DEC, NULL, 0,
694 "Gnutella Pong TCP Port", HFILL }
696 { &hf_gnutella_pong_ip,
697 { "IP", "gnutella.pong.ip",
698 FT_IPv4, BASE_NONE, NULL, 0,
699 "Gnutella Pong IP Address", HFILL }
701 { &hf_gnutella_pong_files,
702 { "Files Shared", "gnutella.pong.files",
703 FT_UINT32, BASE_DEC, NULL, 0,
704 "Gnutella Pong Files Shared", HFILL }
706 { &hf_gnutella_pong_kbytes,
707 { "KBytes Shared", "gnutella.pong.kbytes",
708 FT_UINT32, BASE_DEC, NULL, 0,
709 "Gnutella Pong KBytes Shared", HFILL }
711 { &hf_gnutella_query_min_speed,
712 { "Min Speed", "gnutella.query.min_speed",
713 FT_UINT32, BASE_DEC, NULL, 0,
714 "Gnutella Query Minimum Speed", HFILL }
716 { &hf_gnutella_query_search,
717 { "Search", "gnutella.query.search",
718 FT_STRINGZ, BASE_NONE, NULL, 0,
719 "Gnutella Query Search", HFILL }
721 { &hf_gnutella_queryhit_hit,
722 { "Hit", "gnutella.queryhit.hit",
723 FT_NONE, BASE_NONE, NULL, 0,
724 "Gnutella QueryHit", HFILL }
726 { &hf_gnutella_queryhit_hit_index,
727 { "Index", "gnutella.queryhit.hit.index",
728 FT_UINT32, BASE_DEC, NULL, 0,
729 "Gnutella QueryHit Index", HFILL }
731 { &hf_gnutella_queryhit_hit_size,
732 { "Size", "gnutella.queryhit.hit.size",
733 FT_UINT32, BASE_DEC, NULL, 0,
734 "Gnutella QueryHit Size", HFILL }
736 { &hf_gnutella_queryhit_hit_name,
737 { "Name", "gnutella.queryhit.hit.name",
738 FT_STRING, BASE_NONE, NULL, 0,
739 "Gnutella Query Name", HFILL }
741 { &hf_gnutella_queryhit_hit_extra,
742 { "Extra", "gnutella.queryhit.hit.extra",
743 FT_BYTES, BASE_NONE, NULL, 0,
744 "Gnutella Query Extra", HFILL }
746 { &hf_gnutella_queryhit_count,
747 { "Count", "gnutella.queryhit.count",
748 FT_UINT8, BASE_DEC, NULL, 0,
749 "Gnutella QueryHit Count", HFILL }
751 { &hf_gnutella_queryhit_port,
752 { "Port", "gnutella.queryhit.port",
753 FT_UINT16, BASE_DEC, NULL, 0,
754 "Gnutella QueryHit Port", HFILL }
756 { &hf_gnutella_queryhit_ip,
757 { "IP", "gnutella.queryhit.ip",
758 FT_IPv4, BASE_NONE, NULL, 0,
759 "Gnutella QueryHit IP Address", HFILL }
761 { &hf_gnutella_queryhit_speed,
762 { "Speed", "gnutella.queryhit.speed",
763 FT_UINT32, BASE_DEC, NULL, 0,
764 "Gnutella QueryHit Speed", HFILL }
766 { &hf_gnutella_queryhit_extra,
767 { "Extra", "gnutella.queryhit.extra",
768 FT_BYTES, BASE_NONE, NULL, 0,
769 "Gnutella QueryHit Extra", HFILL }
771 { &hf_gnutella_queryhit_servent_id,
772 { "Servent ID", "gnutella.queryhit.servent_id",
773 FT_BYTES, BASE_NONE, NULL, 0,
774 "Gnutella QueryHit Servent ID", HFILL }
776 { &hf_gnutella_push_servent_id,
777 { "Servent ID", "gnutella.push.servent_id",
778 FT_BYTES, BASE_NONE, NULL, 0,
779 "Gnutella Push Servent ID", HFILL }
781 { &hf_gnutella_push_ip,
782 { "IP", "gnutella.push.ip",
783 FT_IPv4, BASE_NONE, NULL, 0,
784 "Gnutella Push IP Address", HFILL }
786 { &hf_gnutella_push_index,
787 { "Index", "gnutella.push.index",
788 FT_UINT32, BASE_DEC, NULL, 0,
789 "Gnutella Push Index", HFILL }
791 { &hf_gnutella_push_port,
792 { "Port", "gnutella.push.port",
793 FT_UINT16, BASE_DEC, NULL, 0,
794 "Gnutella Push Port", HFILL }
798 static int *ett[] = {
799 &ett_gnutella,
802 proto_gnutella = proto_register_protocol("Gnutella Protocol", "GNUTELLA", "gnutella");
804 proto_register_field_array(proto_gnutella, hf, array_length(hf));
806 proto_register_subtree_array(ett, array_length(ett));
808 gnutella_handle = register_dissector("gnutella", dissect_gnutella, proto_gnutella);
811 void proto_reg_handoff_gnutella(void) {
812 dissector_add_uint_with_preference("tcp.port", GNUTELLA_TCP_PORT, gnutella_handle);
816 * Editor modelines - https://www.wireshark.org/tools/modelines.html
818 * Local variables:
819 * c-basic-offset: 8
820 * tab-width: 8
821 * indent-tabs-mode: t
822 * End:
824 * vi: set shiftwidth=8 tabstop=8 noexpandtab:
825 * :indentSize=8:tabSize=8:noTabs=false: