Coverage Report

Created: 2026-09-28 06:52

next uncovered line (L), next uncovered region (R), next uncovered branch (B)
/src/wireshark/epan/packet.c
Line
Count
Source
1
/* packet.c
2
 * Routines for packet disassembly
3
 *
4
 * Wireshark - Network traffic analyzer
5
 * By Gerald Combs <gerald@wireshark.org>
6
 * Copyright 1998 Gerald Combs
7
 *
8
 * SPDX-License-Identifier: GPL-2.0-or-later
9
 */
10
11
#include "config.h"
12
9.50k
#define WS_LOG_DOMAIN LOG_DOMAIN_EPAN
13
14
#include <glib.h>
15
16
#include <stdio.h>
17
#include <stdlib.h>
18
19
#include <stdarg.h>
20
#include <string.h>
21
#include <time.h>
22
23
#include <epan/packet.h>
24
#include "timestamp.h"
25
26
#include "osi-utils.h"
27
#include "to_str.h"
28
29
#include "addr_resolv.h"
30
#include "tvbuff.h"
31
#include "epan_dissect.h"
32
33
#include <epan/wmem_scopes.h>
34
35
#include <epan/column-info.h>
36
#include <epan/exceptions.h>
37
#include <epan/reassemble.h>
38
#include <epan/stream.h>
39
#include <epan/expert.h>
40
#include <epan/prefs.h>
41
#include <epan/range.h>
42
43
#include <wsutil/str_util.h>
44
#include <wsutil/wslog.h>
45
#include <wsutil/ws_assert.h>
46
47
static int proto_malformed;
48
static dissector_handle_t frame_handle;
49
static dissector_handle_t file_handle;
50
static dissector_handle_t data_handle;
51
52
/**
53
 * A data source.
54
 * Has a tvbuff and a name.
55
 */
56
struct data_source {
57
  tvbuff_t *tvb;
58
  char *name;
59
  data_source_media_type_e media_type;
60
};
61
62
/*
63
 * A dissector table.
64
 *
65
 * "hash_table" is a hash table, indexed by port number, supplying
66
 * a "struct dtbl_entry"; it records what dissector is assigned to
67
 * that uint or string value in that table.
68
 *
69
 * "dissector_handles" is a list of all dissectors that *could* be
70
 * used in that table; not all of them are necessarily in the table,
71
 * as they may be for protocols that don't have a fixed uint value,
72
 * e.g. for TCP or UDP port number tables and protocols with no fixed
73
 * port number. It's only non-NULL for tables that allow "Decode As".
74
 * After initial handoff registration, it's sorted by the filter name
75
 * of the protocol associated with the handle (using an empty string
76
 * if there is no protocol.) That's mostly for tshark -d error messages;
77
 * the GUI re-sorts by the dissector handle description. (XXX - They
78
 * could be sorted on first use, especially if that's the only user.)
79
 *
80
 * "da_descriptions" is a hash table, keyed by dissector handle description,
81
 * of all the dissector handles that could be used for Decode As. The
82
 * descriptions are what are presented in the GUI and what are written
83
 * to the decode_as_entries UAT.
84
 *
85
 * "ui_name" is the name the dissector table has in the user interface.
86
 *
87
 * "type" is a field type giving the width of the uint value for that
88
 * dissector table, if it's a uint dissector table.
89
 *
90
 * "param" is the base in which to display the uint value for that
91
 * dissector table, if it's a uint dissector table, or if it's a string
92
 * table, true/false to indicate case-insensitive or not.
93
 *
94
 * "protocol" is the protocol associated with the dissector table. Used
95
 * for determining dependencies.
96
 */
97
struct dissector_table {
98
  GHashTable  *hash_table;
99
  GSList    *dissector_handles;
100
  GHashTable  *da_descriptions;
101
  const char  *ui_name;
102
  ftenum_t  type;
103
  int   param;
104
  protocol_t  *protocol;
105
};
106
107
/*
108
 * Dissector tables. const char * -> dissector_table *
109
 */
110
static GHashTable *dissector_tables;
111
static bool all_tables_handles_sorted = false;
112
113
/*
114
 * Dissector table aliases. const char * -> const char *
115
 */
116
static GHashTable *dissector_table_aliases;
117
118
/*
119
 * List of registered dissectors.
120
 */
121
static GHashTable *registered_dissectors;
122
123
/*
124
 * A dissector dependency list.
125
 * XXX - These are protocol short names, not dissectors (which is likely
126
 * what we want, as protocols are enabled and disabled, not dissectors
127
 * other than heuristic dissectors.)
128
 */
129
struct depend_dissector_list {
130
  GHashTable  *dissectors;
131
};
132
133
/* Maps char * protocol short name to depend_dissector_list_t
134
 * XXX - This doesn't get freed when proto_deregister_dissector
135
 * is called. Might it make sense to store this information in
136
 * the proto_t?
137
 * XXX - Which direction should these be stored? Issue #1402 discusses,
138
 * e.g., if HTTP is enabled then making sure that lower level protocols
139
 * like TLS, TCP, IP, etc. are enabled. But here as registered the key
140
 * is the protocol of the dissector that calls the other handle (whether
141
 * via table or registered with _add_dependency.) That is, "TCP" and
142
 * "TLS" are keys that have "HTTP" in their depend_dissector_list, rather
143
 * than the other way around. Either use could be interesting (a bit moot
144
 * since this isn't actually used yet.)
145
 */
146
static GHashTable *depend_dissector_lists;
147
148
/* Allow protocols to register a "cleanup" routine to be
149
 * run after the initial sequential run through the packets.
150
 * Note that the file can still be open after this; this is not
151
 * the final cleanup. */
152
static GSList *postseq_cleanup_routines;
153
154
/*
155
 * Post-dissector information - handle for the dissector and a list
156
 * of hfids for the fields the post-dissector wants.
157
 */
158
typedef struct {
159
  dissector_handle_t handle;
160
  GArray *wanted_hfids;
161
} postdissector;
162
163
/*
164
 * Array of all postdissectors.
165
 */
166
static GArray *postdissectors;
167
168
/*
169
 * i-th element of that array.
170
 */
171
2.29M
#define POSTDISSECTORS(i) g_array_index(postdissectors, postdissector, i)
172
173
static void
174
destroy_depend_dissector_list(void *data)
175
0
{
176
0
       depend_dissector_list_t dissector_list = (depend_dissector_list_t)data;
177
0
       GHashTable *table = dissector_list->dissectors;
178
179
0
       g_hash_table_destroy(table);
180
0
       g_slice_free(struct depend_dissector_list, dissector_list);
181
0
}
182
183
/*
184
 * A heuristics dissector list.
185
 */
186
struct heur_dissector_list {
187
  const char  *ui_name;
188
  protocol_t  *protocol;
189
  GSList    *dissectors;
190
};
191
192
static GHashTable *heur_dissector_lists;
193
194
/* Name hashtables for fast detection of duplicate names */
195
static GHashTable* heuristic_short_names;
196
197
static void
198
destroy_heuristic_dissector_entry(void *data)
199
0
{
200
0
  heur_dtbl_entry_t *hdtbl_entry = (heur_dtbl_entry_t *)data;
201
0
  g_free(hdtbl_entry->list_name);
202
0
  g_free(hdtbl_entry->short_name);
203
0
  g_slice_free(heur_dtbl_entry_t, data);
204
0
}
205
206
static void
207
destroy_heuristic_dissector_list(void *data)
208
0
{
209
0
  heur_dissector_list_t dissector_list = (heur_dissector_list_t)data;
210
0
  GSList **list = &(dissector_list->dissectors);
211
212
0
  g_slist_free_full(*list, destroy_heuristic_dissector_entry);
213
0
  g_slice_free(struct heur_dissector_list, dissector_list);
214
0
}
215
216
static void
217
destroy_dissector_table(void *data)
218
0
{
219
0
  struct dissector_table *table = (struct dissector_table *)data;
220
221
0
  g_hash_table_destroy(table->hash_table);
222
0
  g_slist_free(table->dissector_handles);
223
0
  if (table->da_descriptions)
224
0
    g_hash_table_destroy(table->da_descriptions);
225
0
  g_slice_free(struct dissector_table, data);
226
0
}
227
228
void
229
packet_init(void)
230
16
{
231
16
  dissector_tables = g_hash_table_new_full(g_str_hash, g_str_equal,
232
16
      NULL, destroy_dissector_table);
233
16
  all_tables_handles_sorted = false;
234
235
16
  dissector_table_aliases = g_hash_table_new_full(g_str_hash, g_str_equal,
236
16
      NULL, NULL);
237
238
16
  registered_dissectors = g_hash_table_new_full(g_str_hash, g_str_equal,
239
16
      NULL, NULL);
240
241
16
  postdissectors = g_array_sized_new(false, false, (unsigned)sizeof(postdissector), 1);
242
243
16
  depend_dissector_lists = g_hash_table_new_full(g_str_hash, g_str_equal,
244
16
      g_free, destroy_depend_dissector_list);
245
246
16
  heur_dissector_lists = g_hash_table_new_full(g_str_hash, g_str_equal,
247
16
      NULL, destroy_heuristic_dissector_list);
248
249
16
  heuristic_short_names  = g_hash_table_new(g_str_hash, g_str_equal);
250
16
}
251
252
void
253
packet_cache_proto_handles(void)
254
16
{
255
16
  frame_handle = find_dissector("frame");
256
16
  ws_assert(frame_handle != NULL);
257
258
16
  file_handle = find_dissector("file");
259
16
  ws_assert(file_handle != NULL);
260
261
16
  data_handle = find_dissector("data");
262
16
  ws_assert(data_handle != NULL);
263
264
16
  proto_malformed = proto_get_id_by_filter_name("_ws.malformed");
265
16
  ws_assert(proto_malformed != -1);
266
16
}
267
268
/* List of routines that are called before we make a pass through a capture file
269
 * and dissect all its packets. See register_init_routine, register_cleanup_routine
270
 * and register_shutdown_routine in packet.h */
271
/**
272
 * List of "init" routines, which are called before we make a pass through
273
 * a capture file and dissect all its packets (e.g., when we read in a
274
 * new capture file, or run a "filter packets" or "colorize packets"
275
 * pass over the current capture file or when the preferences are changed).
276
 *
277
 * See register_init_routine().
278
 */
279
static GSList *init_routines;
280
281
/**
282
 * List of "cleanup" routines, which are called after closing a capture
283
 * file (or when preferences are changed; in that case these routines
284
 * are called before the init routines are executed). They can be used
285
 * to release resources that are allocated in an "init" routine.
286
 *
287
 * See register_cleanup_routine().
288
 */
289
static GSList *cleanup_routines;
290
291
/*
292
 * List of "shutdown" routines, which are called once, just before
293
 * program exit.
294
 *
295
 * See register_shutdown_routine().
296
 */
297
static GSList *shutdown_routines;
298
299
typedef void (*void_func_t)(void);
300
301
/* Initialize all data structures used for dissection. */
302
static void
303
call_routine(void *routine, void *dummy _U_)
304
1.55k
{
305
1.55k
  void_func_t func = (void_func_t)routine;
306
1.55k
  (*func)();
307
1.55k
}
308
309
void
310
packet_cleanup(void)
311
0
{
312
0
  g_slist_free(init_routines);
313
0
  g_slist_free(cleanup_routines);
314
0
  g_slist_free(postseq_cleanup_routines);
315
0
  g_hash_table_destroy(dissector_tables);
316
0
  g_hash_table_destroy(dissector_table_aliases);
317
0
  g_hash_table_destroy(registered_dissectors);
318
0
  g_hash_table_destroy(depend_dissector_lists);
319
0
  g_hash_table_destroy(heur_dissector_lists);
320
0
  g_hash_table_destroy(heuristic_short_names);
321
0
  g_slist_foreach(shutdown_routines, &call_routine, NULL);
322
0
  g_slist_free(shutdown_routines);
323
0
  if (postdissectors) {
324
0
    for (unsigned i = 0; i < postdissectors->len; i++) {
325
0
      if (POSTDISSECTORS(i).wanted_hfids) {
326
0
        g_array_free(POSTDISSECTORS(i).wanted_hfids, true);
327
0
      }
328
0
    }
329
0
    g_array_free(postdissectors, true);
330
0
  }
331
0
}
332
333
/*
334
 * Given a tvbuff, and a length from a packet header, adjust the length
335
 * of the tvbuff to reflect the specified length.
336
 */
337
void
338
set_actual_length(tvbuff_t *tvb, const unsigned specified_len)
339
33.7k
{
340
33.7k
  if (specified_len < tvb_reported_length(tvb)) {
341
    /* Adjust the length of this tvbuff to include only the specified
342
       payload length.
343
344
       The dissector above the one calling us (the dissector above is
345
       probably us) may use that to determine how much of its packet
346
       was padding. */
347
984
    tvb_set_reported_length(tvb, specified_len);
348
984
  }
349
33.7k
}
350
351
void
352
register_init_routine(void (*func)(void))
353
1.55k
{
354
1.55k
  init_routines = g_slist_prepend(init_routines, (void *)func);
355
1.55k
}
356
357
void
358
register_cleanup_routine(void (*func)(void))
359
848
{
360
848
  cleanup_routines = g_slist_prepend(cleanup_routines, (void *)func);
361
848
}
362
363
/* register a new shutdown routine */
364
void
365
register_shutdown_routine(void (*func)(void))
366
418
{
367
418
  shutdown_routines = g_slist_prepend(shutdown_routines, (void *)func);
368
418
}
369
370
/* Initialize all data structures used for dissection. */
371
void
372
init_dissection(const char* app_env_var_prefix)
373
16
{
374
  /*
375
   * Reinitialize resolution information. Don't leak host entries from
376
   * one file to another (e.g. embarrassing-host-name.example.com from
377
   * file1.pcapng into a name resolution block in file2.pcapng).
378
   */
379
16
  host_name_lookup_reset(app_env_var_prefix);
380
381
16
  wmem_enter_file_scope();
382
383
  /* Initialize the table of conversations. */
384
16
  epan_conversation_init();
385
386
  /* Initialize protocol-specific variables. */
387
16
  g_slist_foreach(init_routines, &call_routine, NULL);
388
389
  /* Initialize the stream-handling tables */
390
16
  stream_init();
391
392
  /* Initialize the expert infos */
393
16
  expert_packet_init();
394
16
}
395
396
void
397
cleanup_dissection(void)
398
0
{
399
  /* Cleanup protocol-specific variables. */
400
0
  g_slist_foreach(cleanup_routines, &call_routine, NULL);
401
402
  /* Cleanup the stream-handling tables */
403
0
  stream_cleanup();
404
405
  /* Cleanup the expert infos */
406
0
  expert_packet_cleanup();
407
408
0
  wmem_leave_file_scope();
409
410
  /*
411
   * Keep the name resolution info around until we start the next
412
   * dissection. Lua scripts may potentially do name resolution at
413
   * any time, even if we're not dissecting and have no capture
414
   * file open.
415
   */
416
0
}
417
418
void
419
register_postseq_cleanup_routine(void_func_t func)
420
16
{
421
16
  postseq_cleanup_routines = g_slist_prepend(postseq_cleanup_routines,
422
16
      (void *)func);
423
16
}
424
425
/* Call all the registered "postseq_cleanup" routines. */
426
void
427
postseq_cleanup_all_protocols(void)
428
0
{
429
0
  g_slist_foreach(postseq_cleanup_routines,
430
0
      &call_routine, NULL);
431
0
}
432
433
/*
434
 * Add a new data source to the list of data sources for a frame, given
435
 * the tvbuff for the data source and its name.
436
 */
437
struct data_source *add_new_data_source(packet_info *pinfo, tvbuff_t *tvb, const char *name)
438
650k
{
439
650k
  struct data_source *src;
440
441
650k
  src = wmem_new(pinfo->pool, struct data_source);
442
650k
  src->tvb = tvb;
443
650k
  src->name = wmem_strdup(pinfo->pool, name);
444
650k
  src->media_type = DS_MEDIA_TYPE_APPLICATION_OCTET_STREAM;
445
  /* This could end up slow, but we should never have that many data
446
   * sources so it probably doesn't matter */
447
650k
  pinfo->data_src = g_slist_append(pinfo->data_src, src);
448
650k
  return src;
449
650k
}
450
451
void
452
set_data_source_name(packet_info *pinfo, struct data_source *src, const char *name)
453
0
{
454
0
  if (src) {
455
0
    src->name = wmem_strdup(pinfo->pool, name);
456
0
  }
457
0
}
458
459
void set_data_source_media_type(struct data_source *src, data_source_media_type_e media_type)
460
0
{
461
0
  if (src) {
462
0
    src->media_type = media_type;
463
0
  }
464
0
}
465
466
void
467
remove_last_data_source(packet_info *pinfo)
468
0
{
469
0
  GSList *last;
470
471
0
  last = g_slist_last(pinfo->data_src);
472
0
  pinfo->data_src = g_slist_delete_link(pinfo->data_src, last);
473
0
}
474
475
char*
476
get_data_source_description(const struct data_source *src)
477
0
{
478
0
  unsigned length = tvb_captured_length(src->tvb);
479
480
0
  return wmem_strdup_printf(NULL, "%s (%u byte%s)", src->name, length,
481
0
        plurality(length, "", "s"));
482
0
}
483
484
const char *
485
get_data_source_name(const struct data_source *src)
486
0
{
487
0
  if (src) {
488
0
    return src->name;
489
0
  }
490
0
  return NULL;
491
0
}
492
493
tvbuff_t *
494
get_data_source_tvb(const struct data_source *src)
495
0
{
496
0
  if (src) {
497
0
    return src->tvb;
498
0
  }
499
0
  return NULL;
500
0
}
501
502
/*
503
 * Find and return data source with the given name.
504
 */
505
struct data_source *
506
get_data_source_by_name(const packet_info *pinfo, const char *name)
507
0
{
508
0
  if (!pinfo) {
509
0
    return NULL;
510
0
  }
511
0
  for (GSList *source = pinfo->data_src; source; source = source->next) {
512
0
    struct data_source *this_source = (struct data_source *)source->data;
513
0
    if (this_source->name && strcmp(this_source->name, name) == 0) {
514
0
      return this_source;
515
0
    }
516
0
  }
517
0
  return NULL;
518
0
}
519
520
/*
521
 * Find and return the data source associated with a given tvb.
522
 */
523
struct data_source *
524
get_data_source_by_tvb(const packet_info *pinfo, const tvbuff_t *tvb)
525
0
{
526
0
  if (!pinfo) {
527
0
    return NULL;
528
0
  }
529
0
  for (GSList *source = pinfo->data_src; source; source = source->next) {
530
0
    struct data_source *this_source = (struct data_source *)source->data;
531
0
    if (this_source->tvb == tvb) {
532
0
      return this_source;
533
0
    }
534
0
  }
535
0
  return NULL;
536
0
}
537
538
int32_t get_data_source_index_by_tvb(const packet_info *pinfo, const tvbuff_t *tvb)
539
6.26k
{
540
6.26k
  if (!pinfo) {
541
0
    return -1;
542
0
  }
543
6.26k
  int32_t idx = 0;
544
6.86k
  for (GSList *source = pinfo->data_src; source; source = source->next) {
545
6.86k
    struct data_source *this_source = (struct data_source *)source->data;
546
6.86k
    if (this_source->tvb == tvb) {
547
6.26k
      return idx;
548
6.26k
    }
549
594
    ++idx;
550
594
  }
551
0
  return -1;
552
6.26k
}
553
554
data_source_media_type_e get_data_source_media_type(const struct data_source *src)
555
0
{
556
0
  if (src) {
557
0
    return src->media_type;
558
0
  }
559
0
  return DS_MEDIA_TYPE_APPLICATION_OCTET_STREAM;
560
0
}
561
562
563
/*
564
 * Free up a frame's list of data sources.
565
 */
566
void
567
free_data_sources(packet_info *pinfo)
568
191k
{
569
191k
  if (pinfo->data_src) {
570
191k
    g_slist_free(pinfo->data_src);
571
191k
    pinfo->data_src = NULL;
572
191k
  }
573
191k
}
574
575
void
576
mark_frame_as_depended_upon(frame_data *fd, uint32_t frame_num)
577
20.2k
{
578
  /* Don't mark a frame as dependent on itself */
579
20.2k
  if (frame_num != fd->num) {
580
    /* ws_assert(frame_num < fd->num) - we assume in several other
581
     * places in the code that frames don't depend on future
582
     * frames. */
583
2.96k
    if (fd->dependent_frames == NULL) {
584
672
      fd->dependent_frames = g_hash_table_new(g_direct_hash, g_direct_equal);
585
672
    }
586
2.96k
    g_hash_table_add(fd->dependent_frames, GUINT_TO_POINTER(frame_num));
587
2.96k
  }
588
20.2k
}
589
590
/* Allow dissectors to register a "final_registration" routine
591
 * that is run like the proto_register_XXX() routine, but at the
592
 * end of the epan_init() function; that is, *after* all other
593
 * subsystems, like dfilters, have finished initializing. This is
594
 * useful for dissector registration routines which need to compile
595
 * display filters. dfilters can't initialize itself until all protocols
596
 * have registered themselves. */
597
static GSList *final_registration_routines;
598
599
void
600
register_final_registration_routine(void (*func)(void))
601
0
{
602
0
  final_registration_routines = g_slist_prepend(final_registration_routines,
603
0
      (void *)func);
604
0
}
605
606
/* Call all the registered "final_registration" routines. */
607
void
608
final_registration_all_protocols(void)
609
16
{
610
16
  g_slist_foreach(final_registration_routines,
611
16
      &call_routine, NULL);
612
16
}
613
614
615
/* Creates the top-most tvbuff and calls the "frame" dissector */
616
void
617
dissect_record(epan_dissect_t *edt, int file_type_subtype, wtap_rec *rec,
618
    frame_data *fd, column_info *cinfo)
619
191k
{
620
191k
  frame_data_t frame_dissector_data;
621
622
191k
  if (!fd->visited) {
623
    /* This is the first pass, so prime the epan_dissect_t with the
624
      hfids postdissectors want on the first pass. */
625
    /* XXX - This can fail with an unhandled exception, e.g., if a
626
     * field was deregistered.  */
627
191k
    prime_epan_dissect_with_postdissector_wanted_hfids(edt);
628
191k
  }
629
630
191k
  if (cinfo != NULL)
631
0
    col_init(cinfo, edt->session);
632
191k
  edt->pi.epan = edt->session;
633
  /* edt->pi.pool created in epan_dissect_init() */
634
191k
  edt->pi.current_proto = "<Missing Protocol Name>";
635
191k
  edt->pi.cinfo = cinfo;
636
191k
  edt->pi.presence_flags = 0;
637
191k
  edt->pi.num = fd->num;
638
  /*
639
   * XXX - this doesn't check the wtap_rec because, for
640
   * some capture files, time stamps are supplied only
641
   * when reading sequentially, so we keep the time stamp
642
   * in the frame_data structure.
643
   */
644
191k
  if (fd->has_ts) {
645
191k
    edt->pi.presence_flags |= PINFO_HAS_TS;
646
191k
    edt->pi.abs_ts = fd->abs_ts;
647
191k
  }
648
191k
  switch (rec->rec_type) {
649
650
191k
  case REC_TYPE_PACKET:
651
191k
    edt->pi.pseudo_header = &rec->rec_header.packet_header.pseudo_header;
652
191k
    break;
653
654
0
  case REC_TYPE_FT_SPECIFIC_EVENT:
655
0
  case REC_TYPE_FT_SPECIFIC_REPORT:
656
0
    edt->pi.pseudo_header = &rec->rec_header.ft_specific_header.pseudo_header;
657
0
    break;
658
659
0
  case REC_TYPE_SYSCALL:
660
0
    edt->pi.pseudo_header = NULL;
661
0
    break;
662
663
0
  case REC_TYPE_SYSTEMD_JOURNAL_EXPORT:
664
0
    edt->pi.pseudo_header = NULL;
665
0
    break;
666
667
0
  case REC_TYPE_CUSTOM_BLOCK:
668
0
    edt->pi.pseudo_header = NULL;
669
0
    break;
670
671
191k
  }
672
673
191k
  edt->pi.fd            = fd;
674
191k
  edt->pi.rec           = rec;
675
191k
  clear_address(&edt->pi.dl_src);
676
191k
  clear_address(&edt->pi.dl_dst);
677
191k
  clear_address(&edt->pi.net_src);
678
191k
  clear_address(&edt->pi.net_dst);
679
191k
  clear_address(&edt->pi.src);
680
191k
  clear_address(&edt->pi.dst);
681
191k
  edt->pi.noreassembly_reason = "";
682
191k
  edt->pi.ptype = PT_NONE;
683
191k
  edt->pi.use_conv_addr_port_endpoints = false;
684
191k
  edt->pi.conv_addr_port_endpoints = NULL;
685
191k
  edt->pi.conv_elements = NULL;
686
191k
  edt->pi.p2p_dir = P2P_DIR_UNKNOWN;
687
191k
  edt->pi.link_dir = LINK_DIR_UNKNOWN;
688
191k
  edt->pi.src_win_scale = -1; /* unknown Rcv.Wind.Shift */
689
191k
  edt->pi.dst_win_scale = -1; /* unknown Rcv.Wind.Shift */
690
191k
  edt->pi.layers = wmem_list_new(edt->pi.pool);
691
191k
  edt->pi.proto_data = NULL;
692
191k
  edt->tvb = NULL;
693
694
  /*
695
   * This is time relative to the first frame in the capture,
696
   * regardless of what time reference frames precede it.
697
   *
698
   * XXX - should there be a field indicating whether the
699
   * frame *has* a relative time stamp?
700
   *
701
   * XXX - what is pinfo->rel_ts used for?  All times are
702
   * relative to some zero point on the t axis, so why
703
   * is pinfo->rel_ts used instead of pinfo->abs_ts?
704
   *
705
   * XXX - Some records aren't packets, and some, packets or not, don't
706
   * have time stamps. Should pinfo->rel_ts be relative to the first
707
   * frame (or packet record, or record of the time type as the current
708
   * record?) that *has* a time stamp?
709
   */
710
191k
  frame_rel_first_frame_time(edt->session, fd, &edt->pi.rel_ts);
711
712
  /* pinfo->rel_cap_ts is used by the new Plot dialog, though
713
   * it could probably just use frame_rel_start_time instead.
714
   */
715
191k
  nstime_t rel_time;
716
191k
  if (frame_rel_start_time(edt->session, fd, &rel_time)) {
717
0
    nstime_copy(&edt->pi.rel_cap_ts, &rel_time);
718
0
    edt->pi.rel_cap_ts_present = true;
719
0
  }
720
721
  /*
722
   * If the block has been modified, use the modified block,
723
   * otherwise use the block from the file.
724
   */
725
191k
  if (fd->has_modified_block) {
726
0
    frame_dissector_data.pkt_block = epan_get_modified_block(edt->session, fd);
727
0
  }
728
191k
  else {
729
191k
    frame_dissector_data.pkt_block = rec->block;
730
191k
  }
731
191k
  frame_dissector_data.file_type_subtype = file_type_subtype;
732
191k
  frame_dissector_data.color_edt = edt; /* Used strictly for "coloring rules" */
733
734
191k
  TRY {
735
    /*
736
     * XXX - currently, the length arguments in
737
     * tvbuff structure are signed, but the captured
738
     * and reported length values are unsigned; this means
739
     * that length values > 2^31 - 1 will appear as
740
     * negative lengths
741
     *
742
     * Captured length values that large will already
743
     * have been filtered out by the Wiretap modules
744
     * (the file will be reported as corrupted), to
745
     * avoid trying to allocate large chunks of data.
746
     *
747
     * Reported length values will not have been
748
     * filtered out, and should not be filtered out,
749
     * as those lengths are not necessarily invalid.
750
     */
751
191k
    edt->tvb = tvb_new_real_data(ws_buffer_start_ptr(&rec->data),
752
191k
                    fd->cap_len, fd->pkt_len);
753
    /* Add this tvbuffer into the data_src list */
754
191k
    add_new_data_source(&edt->pi, edt->tvb, rec->rec_type_name);
755
756
    /* Even though dissect_frame() catches all the exceptions a
757
     * sub-dissector can throw, dissect_frame() itself may throw
758
     * a ReportedBoundsError in bizarre cases. Thus, we catch the exception
759
     * in this function. */
760
191k
    call_dissector_with_data(frame_handle, edt->tvb, &edt->pi, edt->tree, &frame_dissector_data);
761
191k
  }
762
191k
  CATCH(BoundsError) {
763
0
    ws_assert_not_reached();
764
0
  }
765
191k
  CATCH2(FragmentBoundsError, ReportedBoundsError) {
766
0
    proto_tree_add_protocol_format(edt->tree, proto_malformed, edt->tvb, 0, 0,
767
0
                 "[Malformed %s: Packet Length]",
768
0
                 rec->rec_type_name);
769
0
  }
770
191k
  ENDTRY;
771
191k
  wtap_block_unref(rec->block);
772
191k
  rec->block = NULL;
773
774
191k
  fd->visited = 1;
775
191k
}
776
777
/* Creates the top-most tvbuff and calls the "file" dissector */
778
void
779
dissect_file(epan_dissect_t *edt, wtap_rec *rec,
780
    frame_data *fd, column_info *cinfo)
781
0
{
782
0
  file_data_t file_dissector_data;
783
784
0
  if (!fd->visited) {
785
         /* This is the first pass, so prime the epan_dissect_t with the
786
      hfids postdissectors want on the first pass. */
787
0
         prime_epan_dissect_with_postdissector_wanted_hfids(edt);
788
0
  }
789
790
0
  if (cinfo != NULL)
791
0
    col_init(cinfo, edt->session);
792
0
  edt->pi.epan = edt->session;
793
  /* edt->pi.pool created in epan_dissect_init() */
794
0
  edt->pi.current_proto = "<Missing Filetype Name>";
795
0
  edt->pi.cinfo = cinfo;
796
0
  edt->pi.fd    = fd;
797
0
  edt->pi.rec   = rec;
798
0
  edt->pi.pseudo_header = NULL;
799
0
  clear_address(&edt->pi.dl_src);
800
0
  clear_address(&edt->pi.dl_dst);
801
0
  clear_address(&edt->pi.net_src);
802
0
  clear_address(&edt->pi.net_dst);
803
0
  clear_address(&edt->pi.src);
804
0
  clear_address(&edt->pi.dst);
805
0
  edt->pi.noreassembly_reason = "";
806
0
  edt->pi.ptype = PT_NONE;
807
0
  edt->pi.use_conv_addr_port_endpoints = false;
808
0
  edt->pi.conv_addr_port_endpoints = NULL;
809
0
  edt->pi.conv_elements = NULL;
810
0
  edt->pi.p2p_dir = P2P_DIR_UNKNOWN;
811
0
  edt->pi.link_dir = LINK_DIR_UNKNOWN;
812
0
  edt->pi.layers = wmem_list_new(edt->pi.pool);
813
0
  edt->pi.proto_data = NULL;
814
0
  edt->tvb = NULL;
815
816
0
  frame_rel_first_frame_time(edt->session, fd, &edt->pi.rel_ts);
817
818
0
  TRY {
819
    /*
820
     * If the block has been modified, use the modified block,
821
     * otherwise use the block from the file.
822
     */
823
0
    if (fd->has_modified_block) {
824
0
      file_dissector_data.pkt_block = epan_get_modified_block(edt->session, fd);
825
0
    }
826
0
    else {
827
0
      file_dissector_data.pkt_block = rec->block;
828
0
    }
829
0
    file_dissector_data.color_edt = edt; /* Used strictly for "coloring rules" */
830
831
0
    edt->tvb = tvb_new_real_data(ws_buffer_start_ptr(&rec->data),
832
0
                    fd->cap_len, fd->pkt_len > INT_MAX ? INT_MAX : fd->pkt_len);
833
    /* Add this tvbuffer into the data_src list */
834
0
    add_new_data_source(&edt->pi, edt->tvb, "File");
835
836
    /* Even though dissect_file() catches all the exceptions a
837
     * sub-dissector can throw, dissect_frame() itself may throw
838
     * a ReportedBoundsError in bizarre cases. Thus, we catch the exception
839
     * in this function. */
840
0
    call_dissector_with_data(file_handle, edt->tvb, &edt->pi, edt->tree, &file_dissector_data);
841
842
0
  }
843
0
  CATCH(BoundsError) {
844
0
    ws_assert_not_reached();
845
0
  }
846
0
  CATCH3(FragmentBoundsError, ContainedBoundsError, ReportedBoundsError) {
847
0
    proto_tree_add_protocol_format(edt->tree, proto_malformed, edt->tvb, 0, 0,
848
0
                 "[Malformed Record: Packet Length]");
849
0
  }
850
0
  ENDTRY;
851
0
  wtap_block_unref(rec->block);
852
0
  rec->block = NULL;
853
854
0
  fd->visited = 1;
855
0
}
856
857
/*********************** code added for sub-dissector lookup *********************/
858
859
enum dissector_e {
860
  DISSECTOR_TYPE_SIMPLE,
861
  DISSECTOR_TYPE_CALLBACK
862
};
863
864
/*
865
 * A dissector handle.
866
 */
867
struct dissector_handle {
868
  const char  *name;    /* dissector name */
869
  const char  *description; /* dissector description */
870
  char            *pref_suffix;
871
  enum dissector_e dissector_type;
872
  union {
873
    dissector_t dissector_type_simple;
874
    dissector_cb_t  dissector_type_callback;
875
  } dissector_func;
876
  void    *dissector_data;
877
  protocol_t  *protocol;
878
};
879
880
static void
881
add_layer(packet_info *pinfo, int proto_id)
882
1.79M
{
883
1.79M
  int *proto_layer_num_ptr;
884
885
1.79M
  pinfo->curr_layer_num++;
886
1.79M
  wmem_list_append(pinfo->layers, GINT_TO_POINTER(proto_id));
887
888
  /* Increment layer number for this proto id. */
889
1.79M
  if (pinfo->proto_layers == NULL) {
890
191k
    pinfo->proto_layers = wmem_map_new(pinfo->pool, g_direct_hash, g_direct_equal);
891
191k
  }
892
893
1.79M
  proto_layer_num_ptr = wmem_map_lookup(pinfo->proto_layers, GINT_TO_POINTER(proto_id));
894
1.79M
  if (proto_layer_num_ptr == NULL) {
895
    /* Insert new layer */
896
1.34M
    proto_layer_num_ptr = wmem_new(pinfo->pool, int);
897
1.34M
    *proto_layer_num_ptr = 1;
898
1.34M
    wmem_map_insert(pinfo->proto_layers, GINT_TO_POINTER(proto_id), proto_layer_num_ptr);
899
1.34M
  }
900
446k
  else {
901
    /* Increment layer number */
902
446k
    (*proto_layer_num_ptr)++;
903
446k
  }
904
1.79M
  pinfo->curr_proto_layer_num = *proto_layer_num_ptr;
905
1.79M
}
906
907
static void
908
remove_last_layer(packet_info *pinfo, bool reduce_count)
909
453k
{
910
453k
  int *proto_layer_num_ptr;
911
453k
  wmem_list_frame_t *frame;
912
453k
  int proto_id;
913
914
453k
  if (reduce_count) {
915
451k
    pinfo->curr_layer_num--;
916
451k
  }
917
918
453k
  frame = wmem_list_tail(pinfo->layers);
919
453k
  proto_id = GPOINTER_TO_INT(wmem_list_frame_data(frame));
920
453k
  wmem_list_remove_frame(pinfo->layers, frame);
921
922
453k
  if (reduce_count) {
923
    /* Reduce count for removed protocol layer. */
924
451k
    proto_layer_num_ptr = wmem_map_lookup(pinfo->proto_layers, GINT_TO_POINTER(proto_id));
925
451k
    if (proto_layer_num_ptr && *proto_layer_num_ptr > 0) {
926
451k
      (*proto_layer_num_ptr)--;
927
451k
    }
928
451k
  }
929
453k
}
930
931
932
/* This function will return
933
 *   >0  this protocol was successfully dissected and this was this protocol.
934
 *   0   this packet did not match this protocol.
935
 *
936
 * XXX - if the dissector only dissects metadata passed through the data
937
 * pointer, and dissects none of the packet data, that's indistinguishable
938
 * from "packet did not match this protocol".  See issues #12366 and
939
 * #12368.
940
 */
941
static int
942
call_dissector_through_handle(dissector_handle_t handle, tvbuff_t *tvb,
943
            packet_info *pinfo, proto_tree *tree, void *data)
944
1.62M
{
945
1.62M
  const char *saved_proto;
946
1.62M
  int     saved_proto_layer_num;
947
1.62M
  int         len;
948
949
1.62M
  saved_proto = pinfo->current_proto;
950
1.62M
  saved_proto_layer_num = pinfo->curr_proto_layer_num;
951
952
1.62M
  if ((handle->protocol != NULL) && (!proto_is_bytes_pino(handle->protocol))) {
953
1.54M
    pinfo->current_proto =
954
1.54M
      proto_get_protocol_short_name(handle->protocol);
955
1.54M
  }
956
957
1.62M
  switch (handle->dissector_type) {
958
959
1.62M
  case DISSECTOR_TYPE_SIMPLE:
960
1.62M
    len = (handle->dissector_func.dissector_type_simple)(tvb, pinfo, tree, data);
961
1.62M
    break;
962
963
21
  case DISSECTOR_TYPE_CALLBACK:
964
21
    len = (handle->dissector_func.dissector_type_callback)(tvb, pinfo, tree, data, handle->dissector_data);
965
21
    break;
966
967
0
  default:
968
0
    ws_assert_not_reached();
969
1.62M
  }
970
1.16M
  pinfo->current_proto = saved_proto;
971
1.16M
  pinfo->curr_proto_layer_num = saved_proto_layer_num;
972
973
1.16M
  return len;
974
1.62M
}
975
976
/*
977
 * Call a dissector through a handle.
978
 * If the protocol for that handle isn't enabled, return 0 without
979
 * calling the dissector.
980
 * Otherwise, if the handle refers to a new-style dissector, call the
981
 * dissector and return its return value, otherwise call it and return
982
 * the length of the tvbuff pointed to by the argument.
983
 */
984
985
static int
986
call_dissector_work_error(dissector_handle_t handle, tvbuff_t *tvb,
987
        packet_info *pinfo_arg, proto_tree *tree, void *);
988
989
static int
990
call_dissector_work(dissector_handle_t handle, tvbuff_t *tvb, packet_info *pinfo,
991
        proto_tree *tree, bool add_proto_name, void *data)
992
2.19M
{
993
2.19M
  const char  *saved_proto;
994
2.19M
  int          saved_proto_layer_num;
995
2.19M
  uint16_t     saved_can_desegment;
996
2.19M
  int          len;
997
2.19M
  unsigned     saved_layers_len = 0;
998
2.19M
  unsigned     saved_tree_count = tree ? tree->tree_data->count : 0;
999
2.19M
  unsigned     saved_desegment_len = pinfo->desegment_len;
1000
2.19M
  bool         consumed_none;
1001
1002
2.19M
  if (handle->protocol != NULL &&
1003
2.13M
      !proto_is_protocol_enabled(handle->protocol)) {
1004
    /*
1005
     * The protocol isn't enabled.
1006
     */
1007
573k
    return 0;
1008
573k
  }
1009
1010
1.62M
  saved_proto = pinfo->current_proto;
1011
1.62M
  saved_proto_layer_num = pinfo->curr_proto_layer_num;
1012
1.62M
  saved_can_desegment = pinfo->can_desegment;
1013
1.62M
  saved_layers_len = wmem_list_count(pinfo->layers);
1014
1.62M
  DISSECTOR_ASSERT(saved_layers_len < prefs.gui_max_tree_depth);
1015
1016
  /*
1017
   * can_desegment is set to 2 by anyone which offers the
1018
   * desegmentation api/service.
1019
   * Then every time a subdissector is called it is decremented
1020
   * by one.
1021
   * Thus only the subdissector immediately on top of whoever
1022
   * offers this service can use it.
1023
   * We save the current value of "can_desegment" for the
1024
   * benefit of TCP proxying dissectors such as SOCKS, so they
1025
   * can restore it and allow the dissectors they call to use
1026
   * the desegmentation service.
1027
   */
1028
1.62M
  pinfo->saved_can_desegment = saved_can_desegment;
1029
1.62M
  pinfo->can_desegment = saved_can_desegment-(saved_can_desegment>0);
1030
1.62M
  if ((handle->protocol != NULL) && (!proto_is_bytes_pino(handle->protocol))) {
1031
1.54M
    pinfo->current_proto =
1032
1.54M
      proto_get_protocol_short_name(handle->protocol);
1033
1034
    /*
1035
     * Add the protocol name to the layers only if told to
1036
     * do so. Asn2wrs generated dissectors may be added
1037
     * multiple times otherwise.
1038
     */
1039
    /* XXX Should we check for a duplicate layer here? */
1040
1.54M
    if (add_proto_name) {
1041
1.35M
      add_layer(pinfo, proto_get_id(handle->protocol));
1042
1.35M
    }
1043
1.54M
  }
1044
1045
1.62M
  if (pinfo->flags.in_error_pkt) {
1046
156k
    len = call_dissector_work_error(handle, tvb, pinfo, tree, data);
1047
1.46M
  } else {
1048
    /*
1049
     * Just call the subdissector.
1050
     */
1051
1.46M
    len = call_dissector_through_handle(handle, tvb, pinfo, tree, data);
1052
1.46M
  }
1053
1.62M
  consumed_none = len == 0 || (pinfo->desegment_len != saved_desegment_len && pinfo->desegment_offset == 0);
1054
  /* If len == 0, then the dissector didn't accept the packet.
1055
   * In the latter case, the dissector accepted the packet, but didn't
1056
   * consume any bytes because they all belong in a later segment.
1057
   * In the latter case, we probably won't call a dissector here again
1058
   * on the next pass, so removing the layer keeps any *further* layers
1059
   * past this one the same on subsequent passes.
1060
   *
1061
   * XXX: DISSECTOR_ASSERT that the tree count didn't change? If the
1062
   * dissector didn't consume any bytes but added items to the tree,
1063
   * that's improper behavior and needs a rethink. We could also move the
1064
   * test that the packet didn't change desegment_offset and desegment_len
1065
   * while rejecting the packet from packet-tcp.c decode_tcp_ports to here.
1066
   */
1067
1.62M
  if (handle->protocol != NULL && !proto_is_bytes_pino(handle->protocol) && add_proto_name &&
1068
996k
    (consumed_none || (tree && saved_tree_count == tree->tree_data->count))) {
1069
    /*
1070
     * We've added a layer and either the dissector didn't
1071
     * consume any data or we didn't add any items to the
1072
     * tree. Remove it.
1073
     */
1074
74.5k
    while (wmem_list_count(pinfo->layers) > saved_layers_len) {
1075
      /*
1076
       * Only reduce the layer number if the dissector didn't
1077
       * consume any data. Since tree can be NULL on
1078
       * the first pass, we cannot check it or it will
1079
       * break dissectors that rely on a stable value.
1080
       */
1081
38.0k
      remove_last_layer(pinfo, consumed_none);
1082
38.0k
    }
1083
36.5k
  }
1084
1.62M
  pinfo->current_proto = saved_proto;
1085
1.62M
  pinfo->curr_proto_layer_num = saved_proto_layer_num;
1086
1.62M
  pinfo->can_desegment = saved_can_desegment;
1087
1.62M
  return len;
1088
2.19M
}
1089
1090
1091
static int
1092
call_dissector_work_error(dissector_handle_t handle, tvbuff_t *tvb,
1093
        packet_info *pinfo_arg, proto_tree *tree, void *data)
1094
156k
{
1095
156k
  packet_info  *pinfo = pinfo_arg;
1096
156k
  const char   *saved_proto;
1097
156k
  uint16_t      saved_can_desegment;
1098
156k
  volatile int  len = 0;
1099
156k
  bool          save_writable;
1100
156k
  address       save_dl_src;
1101
156k
  address       save_dl_dst;
1102
156k
  address       save_net_src;
1103
156k
  address       save_net_dst;
1104
156k
  address       save_src;
1105
156k
  address       save_dst;
1106
156k
  uint32_t        save_ptype;
1107
156k
  uint32_t        save_srcport;
1108
156k
  uint32_t        save_destport;
1109
1110
  /*
1111
  * This isn't a packet being transported inside
1112
  * the protocol whose dissector is calling us,
1113
  * it's a copy of a packet that caused an error
1114
  * in some protocol included in a packet that
1115
  * reports the error (e.g., an ICMP Unreachable
1116
  * packet).
1117
  */
1118
1119
  /*
1120
  * Save the current state of the writability of
1121
  * the columns, and restore them after the
1122
  * dissector returns, so that the columns
1123
  * don't reflect the packet that got the error,
1124
  * they reflect the packet that reported the
1125
  * error.
1126
  */
1127
156k
  saved_proto = pinfo->current_proto;
1128
156k
  saved_can_desegment = pinfo->can_desegment;
1129
1130
156k
  save_writable = col_get_writable(pinfo->cinfo, -1);
1131
156k
  col_set_writable(pinfo->cinfo, -1, false);
1132
156k
  copy_address_shallow(&save_dl_src, &pinfo->dl_src);
1133
156k
  copy_address_shallow(&save_dl_dst, &pinfo->dl_dst);
1134
156k
  copy_address_shallow(&save_net_src, &pinfo->net_src);
1135
156k
  copy_address_shallow(&save_net_dst, &pinfo->net_dst);
1136
156k
  copy_address_shallow(&save_src, &pinfo->src);
1137
156k
  copy_address_shallow(&save_dst, &pinfo->dst);
1138
156k
  save_ptype = pinfo->ptype;
1139
156k
  save_srcport = pinfo->srcport;
1140
156k
  save_destport = pinfo->destport;
1141
1142
  /* Dissect the contained packet. */
1143
156k
  TRY {
1144
156k
    len = call_dissector_through_handle(handle, tvb,pinfo, tree, data);
1145
156k
  }
1146
156k
  CATCH(BoundsError) {
1147
    /*
1148
    * Restore the column writability and addresses and ports.
1149
    */
1150
25
    col_set_writable(pinfo->cinfo, -1, save_writable);
1151
25
    copy_address_shallow(&pinfo->dl_src, &save_dl_src);
1152
25
    copy_address_shallow(&pinfo->dl_dst, &save_dl_dst);
1153
25
    copy_address_shallow(&pinfo->net_src, &save_net_src);
1154
25
    copy_address_shallow(&pinfo->net_dst, &save_net_dst);
1155
25
    copy_address_shallow(&pinfo->src, &save_src);
1156
25
    copy_address_shallow(&pinfo->dst, &save_dst);
1157
25
    pinfo->ptype = save_ptype;
1158
25
    pinfo->srcport = save_srcport;
1159
25
    pinfo->destport = save_destport;
1160
1161
    /*
1162
    * Restore the current protocol, so any
1163
    * "Short Frame" indication reflects that
1164
    * protocol, not the protocol for the
1165
    * packet that got the error.
1166
    */
1167
25
    pinfo->current_proto = saved_proto;
1168
1169
    /*
1170
    * Restore the desegmentability state.
1171
    */
1172
25
    pinfo->can_desegment = saved_can_desegment;
1173
1174
    /*
1175
    * Rethrow the exception, so this will be
1176
    * reported as a short frame.
1177
    */
1178
25
    RETHROW;
1179
0
  }
1180
156k
  CATCH3(FragmentBoundsError, ContainedBoundsError, ReportedBoundsError) {
1181
    /*
1182
    * "ret" wasn't set because an exception was thrown
1183
    * before "call_dissector_through_handle()" returned.
1184
    * As it called something, at least one dissector
1185
    * accepted the packet, and, as an exception was
1186
    * thrown, not only was all the tvbuff dissected,
1187
    * a dissector tried dissecting past the end of
1188
    * the data in some tvbuff, so we'll assume that
1189
    * the entire tvbuff was dissected.
1190
    */
1191
48.2k
    len = tvb_captured_length(tvb);
1192
48.2k
  }
1193
156k
  ENDTRY;
1194
1195
156k
  col_set_writable(pinfo->cinfo, -1, save_writable);
1196
156k
  copy_address_shallow(&pinfo->dl_src, &save_dl_src);
1197
156k
  copy_address_shallow(&pinfo->dl_dst, &save_dl_dst);
1198
156k
  copy_address_shallow(&pinfo->net_src, &save_net_src);
1199
156k
  copy_address_shallow(&pinfo->net_dst, &save_net_dst);
1200
156k
  copy_address_shallow(&pinfo->src, &save_src);
1201
156k
  copy_address_shallow(&pinfo->dst, &save_dst);
1202
156k
  pinfo->ptype = save_ptype;
1203
156k
  pinfo->srcport = save_srcport;
1204
156k
  pinfo->destport = save_destport;
1205
156k
  pinfo->want_pdu_tracking = 0;
1206
156k
  return len;
1207
156k
}
1208
1209
/*
1210
 * An entry in the hash table portion of a dissector table.
1211
 */
1212
struct dtbl_entry {
1213
  dissector_handle_t initial;
1214
  dissector_handle_t current;
1215
};
1216
1217
/* Finds a dissector table by table name. */
1218
dissector_table_t
1219
find_dissector_table(const char *name)
1220
331k
{
1221
331k
  dissector_table_t dissector_table = (dissector_table_t) g_hash_table_lookup(dissector_tables, name);
1222
331k
  if (! dissector_table) {
1223
0
    const char *new_name = (const char *) g_hash_table_lookup(dissector_table_aliases, name);
1224
0
    if (new_name) {
1225
0
      dissector_table = (dissector_table_t) g_hash_table_lookup(dissector_tables, new_name);
1226
0
    }
1227
0
    if (dissector_table) {
1228
0
      ws_warning("%s is now %s", name, new_name);
1229
0
    }
1230
0
  }
1231
331k
  return dissector_table;
1232
331k
}
1233
1234
/* Find an entry in a uint dissector table. */
1235
static dtbl_entry_t *
1236
find_uint_dtbl_entry(dissector_table_t sub_dissectors, const uint32_t pattern)
1237
1.35M
{
1238
1.35M
  switch (sub_dissectors->type) {
1239
1240
441k
  case FT_UINT8:
1241
1.00M
  case FT_UINT16:
1242
1.00M
  case FT_UINT24:
1243
1.35M
  case FT_UINT32:
1244
    /*
1245
     * You can do a uint lookup in these tables.
1246
     */
1247
1.35M
    break;
1248
377
  case FT_NONE:
1249
    /* For now treat as uint */
1250
377
    break;
1251
1252
0
  default:
1253
    /*
1254
     * But you can't do a uint lookup in any other types
1255
     * of tables.
1256
     */
1257
0
    ws_assert_not_reached();
1258
1.35M
  }
1259
1260
  /*
1261
   * Find the entry.
1262
   */
1263
1.35M
  return (dtbl_entry_t *)g_hash_table_lookup(sub_dissectors->hash_table,
1264
1.35M
           GUINT_TO_POINTER(pattern));
1265
1.35M
}
1266
1267
#if 0
1268
static void
1269
dissector_add_uint_sanity_check(const char *name, uint32_t pattern, dissector_handle_t handle, dissector_table_t sub_dissectors)
1270
{
1271
  dtbl_entry_t *dtbl_entry;
1272
1273
  if (pattern == 0) {
1274
    ws_warning("%s: %s registering using a pattern of 0",
1275
        name, proto_get_protocol_filter_name(proto_get_id(handle->protocol)));
1276
  }
1277
1278
  dtbl_entry = g_hash_table_lookup(sub_dissectors->hash_table, GUINT_TO_POINTER(pattern));
1279
  if (dtbl_entry != NULL) {
1280
    ws_warning("%s: %s registering using pattern %d already registered by %s",
1281
        name, proto_get_protocol_filter_name(proto_get_id(handle->protocol)),
1282
        pattern, proto_get_protocol_filter_name(proto_get_id(dtbl_entry->initial->protocol)));
1283
  }
1284
}
1285
#endif
1286
1287
/* Get and check subdissector table and handle
1288
 * @return true if subdissector and handle exist */
1289
static bool
1290
dissector_get_table_checked(const char *name, dissector_handle_t handle, dissector_table_t *sub_dissectors)
1291
298k
{
1292
298k
  *sub_dissectors = find_dissector_table(name);
1293
1294
  /*
1295
   * Make sure the handle and the dissector table exist.
1296
   */
1297
298k
  if (handle == NULL) {
1298
0
    ws_dissector_oops("handle to register \"%s\" to doesn't exist\n",
1299
0
        name);
1300
0
    return false;
1301
0
  }
1302
298k
  if (*sub_dissectors == NULL) {
1303
0
    ws_dissector_oops("dissector table \"%s\" doesn't exist\n"
1304
0
        "Protocol being registered is \"%s\"\n",
1305
0
        name, proto_get_protocol_long_name(handle->protocol));
1306
0
    return false;
1307
0
  }
1308
1309
298k
  return true;
1310
298k
}
1311
1312
static void
1313
dissector_add_uint_real(const char *name _U_, const uint32_t pattern, dissector_handle_t handle, dissector_table_t sub_dissectors)
1314
187k
{
1315
187k
  dtbl_entry_t      *dtbl_entry;
1316
1317
187k
  switch (sub_dissectors->type) {
1318
1319
19.5k
  case FT_UINT8:
1320
54.1k
  case FT_UINT16:
1321
54.9k
  case FT_UINT24:
1322
187k
  case FT_UINT32:
1323
    /*
1324
     * You can do a uint lookup in these tables.
1325
     */
1326
187k
    break;
1327
1328
0
  default:
1329
    /*
1330
     * But you can't do a uint lookup in any other types
1331
     * of tables.
1332
     */
1333
0
    ws_assert_not_reached();
1334
187k
  }
1335
1336
#if 0
1337
  dissector_add_uint_sanity_check(name, pattern, handle, sub_dissectors);
1338
#endif
1339
1340
187k
  dtbl_entry = g_new(dtbl_entry_t, 1);
1341
187k
  dtbl_entry->current = handle;
1342
187k
  dtbl_entry->initial = dtbl_entry->current;
1343
1344
  /* do the table insertion */
1345
187k
  g_hash_table_insert(sub_dissectors->hash_table,
1346
187k
           GUINT_TO_POINTER(pattern), (void *)dtbl_entry);
1347
187k
}
1348
1349
/* Add an entry to a uint dissector table. */
1350
void
1351
dissector_add_uint(const char *name, const uint32_t pattern, dissector_handle_t handle)
1352
177k
{
1353
177k
  dissector_table_t sub_dissectors;
1354
1355
177k
  if (!dissector_get_table_checked(name, handle, &sub_dissectors))
1356
0
    return;
1357
1358
177k
  dissector_add_uint_real(name, pattern, handle, sub_dissectors);
1359
1360
  /*
1361
   * Now, if this table supports "Decode As", add this handle
1362
   * to the list of handles that could be used for "Decode As"
1363
   * with this table, because it *is* being used with this table.
1364
   */
1365
177k
  if (dissector_table_supports_decode_as(sub_dissectors))
1366
17.8k
    dissector_add_for_decode_as(name, handle);
1367
177k
}
1368
1369
void dissector_add_uint_range(const char *name, range_t *range,
1370
            dissector_handle_t handle)
1371
2.70k
{
1372
2.70k
  if (!range) {
1373
0
    return;
1374
0
  }
1375
1376
2.70k
  dissector_table_t  sub_dissectors;
1377
2.70k
  uint32_t i, j;
1378
1379
2.70k
  if (!dissector_get_table_checked(name, handle, &sub_dissectors))
1380
0
    return;
1381
1382
6.12k
  for (i = 0; i < range->nranges; i++) {
1383
9.87k
    for (j = range->ranges[i].low; j < range->ranges[i].high; j++)
1384
6.44k
      dissector_add_uint_real(name, j, handle, sub_dissectors);
1385
3.42k
    dissector_add_uint_real(name, range->ranges[i].high, handle, sub_dissectors);
1386
3.42k
  }
1387
  /*
1388
   * Even an empty range would want a chance for
1389
   * Decode As, if the dissector table supports
1390
   * it.
1391
   */
1392
2.70k
  if (dissector_table_supports_decode_as(sub_dissectors))
1393
2.56k
    dissector_add_for_decode_as(name, handle);
1394
2.70k
}
1395
1396
static range_t*
1397
dissector_add_range_preference(const char *name, dissector_handle_t handle, const char* range_str)
1398
11.6k
{
1399
11.6k
  range_t** range;
1400
11.6k
  module_t *module;
1401
11.6k
  char *description, *title;
1402
11.6k
  dissector_table_t  pref_dissector_table = find_dissector_table(name);
1403
11.6k
  int proto_id = proto_get_id(handle->protocol);
1404
11.6k
  uint32_t max_value = 0;
1405
1406
11.6k
  if (!pref_dissector_table) {
1407
0
    ws_warning("Unable to find dissector table for %s", name);
1408
0
    return NULL;
1409
0
  }
1410
1411
  /* If a dissector is added for Decode As only, it's dissector
1412
    table value would default to 0.
1413
    Set up a preference value with that information
1414
   */
1415
11.6k
  range = wmem_new0(wmem_epan_scope(), range_t*);
1416
1417
  /* If the dissector's protocol already has a preference module, use it */
1418
11.6k
  const char* module_name = proto_get_protocol_filter_name(proto_id);
1419
11.6k
  module = prefs_find_module(module_name);
1420
11.6k
  if (module == NULL) {
1421
    /* Otherwise create a new one */
1422
5.00k
    module = prefs_register_protocol(proto_id, NULL);
1423
5.00k
  }
1424
1425
11.6k
  const char *pref_suffix = dissector_handle_get_pref_suffix(handle);
1426
11.6k
  const char *fullname = wmem_strdup_printf(wmem_epan_scope(), "%s%s", name, pref_suffix);
1427
1428
  /* Some preference callback functions use the proto_reg_handoff_
1429
    routine to apply preferences, which could duplicate the
1430
    registration of a preference.  Check for that here */
1431
11.6k
  if (prefs_find_preference(module, fullname) == NULL) {
1432
11.5k
    const char *handle_desc = dissector_handle_get_description(handle);
1433
11.5k
    if (g_strcmp0(range_str, "") > 0) {
1434
7.71k
      description = wmem_strdup_printf(wmem_epan_scope(), "%s %s(s) (default: %s)",
1435
7.71k
                      handle_desc, pref_dissector_table->ui_name, range_str);
1436
7.71k
    } else {
1437
3.82k
      description = wmem_strdup_printf(wmem_epan_scope(), "%s %s(s)",
1438
3.82k
                      handle_desc, pref_dissector_table->ui_name);
1439
3.82k
    }
1440
11.5k
    title = wmem_strdup_printf(wmem_epan_scope(), "%s %s(s)", handle_desc, pref_dissector_table->ui_name);
1441
1442
    /* Max value is based on datatype of dissector table */
1443
11.5k
    switch (pref_dissector_table->type) {
1444
1445
416
    case FT_UINT8:
1446
416
      max_value = 0xFF;
1447
416
      break;
1448
11.0k
    case FT_UINT16:
1449
11.0k
      max_value = 0xFFFF;
1450
11.0k
      break;
1451
0
    case FT_UINT24:
1452
0
      max_value = 0xFFFFFF;
1453
0
      break;
1454
48
    case FT_UINT32:
1455
48
      max_value = 0xFFFFFFFF;
1456
48
      break;
1457
1458
0
    default:
1459
0
      ws_error("The dissector table %s (%s) is not an integer type - are you using a buggy plugin?", name, pref_dissector_table->ui_name);
1460
0
      ws_assert_not_reached();
1461
11.5k
    }
1462
1463
11.5k
    range_convert_str(wmem_epan_scope(), range, range_str, max_value);
1464
11.5k
    prefs_register_decode_as_range_preference(module, fullname, title, description, range, max_value, name, handle_desc);
1465
11.5k
  } else {
1466
    /* We have a duplicate. This might just be the handoff routine
1467
     * getting called twice, which isn't ideal but we can ignore
1468
     * for now. Log it at a level that isn't printed by default.
1469
     */
1470
80
    ws_info("Registering automatic preference %s in %s twice", fullname, module_name);
1471
    /* Check this is just registering the same handle to the same
1472
     * preference, and not registering a different handle of the
1473
     * same protocol and the same pref_suffix to the same table.
1474
     */
1475
80
    dissector_handle_t dup_handle;
1476
27.0k
    for (GSList *entry = pref_dissector_table->dissector_handles; entry != NULL; entry = g_slist_next(entry))
1477
27.0k
    {
1478
27.0k
      dup_handle = (dissector_handle_t)entry->data;
1479
27.0k
      if (handle->protocol != dup_handle->protocol) {
1480
26.9k
        continue;
1481
26.9k
      }
1482
48
      if ((g_strcmp0(pref_suffix, dissector_handle_get_pref_suffix(dup_handle)) == 0) &&
1483
48
          (handle != dup_handle))
1484
0
      {
1485
0
        const char *dissector_name = dissector_handle_get_dissector_name(handle);
1486
0
        if (dissector_name == NULL)
1487
0
          dissector_name = "(anonymous)";
1488
0
        const char *dup_dissector_name;
1489
0
        dup_dissector_name = dissector_handle_get_dissector_name(dup_handle);
1490
0
        if (dup_dissector_name == NULL) {
1491
0
          dup_dissector_name = "(anonymous)";
1492
0
        }
1493
0
        ws_dissector_bug("Dissectors %s and %s in dissector table %s would have the same Decode As preference\n",
1494
0
            dissector_name,
1495
0
            dup_dissector_name,
1496
0
            name);
1497
0
      }
1498
48
    }
1499
80
  }
1500
1501
11.6k
  return *range;
1502
11.6k
}
1503
1504
void dissector_add_uint_with_preference(const char *name, const uint32_t pattern,
1505
    dissector_handle_t handle)
1506
6.17k
{
1507
6.17k
  char* range_str;
1508
1509
6.17k
  range_str = wmem_strdup_printf(NULL, "%d", pattern);
1510
6.17k
  dissector_add_range_preference(name, handle, range_str);
1511
6.17k
  wmem_free(NULL, range_str);
1512
6.17k
  dissector_add_uint(name, pattern, handle);
1513
6.17k
}
1514
1515
void dissector_add_uint_range_with_preference(const char *name, const char* range_str,
1516
    dissector_handle_t handle)
1517
2.46k
{
1518
2.46k
  range_t* range;
1519
1520
2.46k
  range = dissector_add_range_preference(name, handle, range_str);
1521
2.46k
  dissector_add_uint_range(name, range, handle);
1522
2.46k
}
1523
1524
/* Delete the entry for a dissector in a uint dissector table
1525
   with a particular pattern. */
1526
1527
/* NOTE: this doesn't use the dissector call variable. It is included to */
1528
/*  be consistent with the dissector_add_uint and more importantly to be used */
1529
/*  if the technique of adding a temporary dissector is implemented.  */
1530
/*  If temporary dissectors are deleted, then the original dissector must */
1531
/*  be available. */
1532
void
1533
dissector_delete_uint(const char *name, const uint32_t pattern,
1534
  dissector_handle_t handle _U_)
1535
16
{
1536
16
  dissector_table_t sub_dissectors = find_dissector_table(name);
1537
16
  dtbl_entry_t *dtbl_entry;
1538
1539
  /* sanity check */
1540
16
  ws_assert(sub_dissectors);
1541
1542
  /*
1543
   * Find the entry.
1544
   */
1545
16
  dtbl_entry = find_uint_dtbl_entry(sub_dissectors, pattern);
1546
1547
16
  if (dtbl_entry != NULL) {
1548
    /*
1549
     * Found - remove it.
1550
     */
1551
0
    g_hash_table_remove(sub_dissectors->hash_table,
1552
0
            GUINT_TO_POINTER(pattern));
1553
0
  }
1554
16
}
1555
1556
void dissector_delete_uint_range(const char *name, range_t *range,
1557
         dissector_handle_t handle)
1558
16
{
1559
16
  uint32_t i, j;
1560
1561
16
  if (range) {
1562
0
    for (i = 0; i < range->nranges; i++) {
1563
0
      for (j = range->ranges[i].low; j < range->ranges[i].high; j++)
1564
0
        dissector_delete_uint(name, j, handle);
1565
0
      dissector_delete_uint(name, range->ranges[i].high, handle);
1566
0
    }
1567
0
  }
1568
16
}
1569
1570
/* Remove an entry from a guid dissector table. */
1571
void dissector_delete_guid(const char *name, guid_key* guid_val, dissector_handle_t handle)
1572
0
{
1573
0
  dissector_table_t  sub_dissectors;
1574
0
  dtbl_entry_t      *dtbl_entry;
1575
1576
0
  sub_dissectors = find_dissector_table(name);
1577
1578
  /* sanity check */
1579
0
  ws_assert(sub_dissectors);
1580
1581
  /* Find the table entry */
1582
0
  dtbl_entry = (dtbl_entry_t *)g_hash_table_lookup(sub_dissectors->hash_table, guid_val);
1583
1584
0
  if (dtbl_entry == NULL) {
1585
0
    fprintf(stderr, "OOPS: guid not found in dissector table \"%s\"\n", name);
1586
0
    return;
1587
0
  }
1588
1589
  /* Make sure the handles match */
1590
0
  if (dtbl_entry->current != handle) {
1591
0
    fprintf(stderr, "OOPS: handle does not match for guid in dissector table \"%s\"\n", name);
1592
0
    return;
1593
0
  }
1594
1595
  /* Remove the table entry */
1596
0
  g_hash_table_remove(sub_dissectors->hash_table, guid_val);
1597
0
}
1598
1599
1600
static gboolean
1601
dissector_delete_all_check (void *key _U_, void *value, void *user_data)
1602
80
{
1603
80
  dtbl_entry_t *dtbl_entry = (dtbl_entry_t *) value;
1604
80
  dissector_handle_t handle = (dissector_handle_t) user_data;
1605
1606
80
  if (!dtbl_entry->current->protocol) {
1607
    /*
1608
     * Not all dissectors are registered with a protocol, so we need this
1609
     * check when running from dissector_delete_from_all_tables.
1610
     */
1611
0
    return FALSE;
1612
0
  }
1613
1614
80
  return (proto_get_id (dtbl_entry->current->protocol) == proto_get_id (handle->protocol));
1615
80
}
1616
1617
/* Delete all entries from a dissector table. */
1618
void dissector_delete_all(const char *name, dissector_handle_t handle)
1619
288
{
1620
288
  dissector_table_t sub_dissectors = find_dissector_table(name);
1621
288
  ws_assert (sub_dissectors);
1622
1623
288
  g_hash_table_foreach_remove (sub_dissectors->hash_table, dissector_delete_all_check, handle);
1624
288
}
1625
1626
static void
1627
dissector_delete_from_table(void *key _U_, void *value, void *user_data)
1628
0
{
1629
0
  dissector_table_t sub_dissectors = (dissector_table_t) value;
1630
0
  ws_assert (sub_dissectors);
1631
1632
0
  dissector_handle_t handle = (dissector_handle_t) user_data;
1633
1634
0
  g_hash_table_foreach_remove(sub_dissectors->hash_table, dissector_delete_all_check, user_data);
1635
0
  sub_dissectors->dissector_handles = g_slist_remove(sub_dissectors->dissector_handles, user_data);
1636
0
  if (sub_dissectors->da_descriptions)
1637
0
    g_hash_table_remove(sub_dissectors->da_descriptions, handle->description);
1638
0
}
1639
1640
/* Delete handle from all tables and dissector_handles lists */
1641
static void
1642
dissector_delete_from_all_tables(dissector_handle_t handle)
1643
0
{
1644
0
  g_hash_table_foreach(dissector_tables, dissector_delete_from_table, handle);
1645
0
}
1646
1647
/* Change the entry for a dissector in a uint dissector table
1648
   with a particular pattern to use a new dissector handle. */
1649
void
1650
dissector_change_uint(const char *name, const uint32_t pattern, dissector_handle_t handle)
1651
0
{
1652
0
  dissector_table_t sub_dissectors = find_dissector_table(name);
1653
0
  dtbl_entry_t *dtbl_entry;
1654
1655
  /* sanity check */
1656
0
  ws_assert(sub_dissectors);
1657
1658
  /*
1659
   * See if the entry already exists. If so, reuse it.
1660
   */
1661
0
  dtbl_entry = find_uint_dtbl_entry(sub_dissectors, pattern);
1662
0
  if (dtbl_entry != NULL) {
1663
    /*
1664
     * If there's no initial value, and the user said not
1665
     * to decode it, just remove the entry to save memory.
1666
     */
1667
0
    if (handle == NULL && dtbl_entry->initial == NULL) {
1668
0
      g_hash_table_remove(sub_dissectors->hash_table,
1669
0
              GUINT_TO_POINTER(pattern));
1670
0
      return;
1671
0
    }
1672
0
    dtbl_entry->current = handle;
1673
0
    return;
1674
0
  }
1675
1676
  /*
1677
   * Don't create an entry if there is no dissector handle - I.E. the
1678
   * user said not to decode something that wasn't being decoded
1679
   * in the first place.
1680
   */
1681
0
  if (handle == NULL)
1682
0
    return;
1683
1684
0
  dtbl_entry = g_new(dtbl_entry_t, 1);
1685
0
  dtbl_entry->initial = NULL;
1686
0
  dtbl_entry->current = handle;
1687
1688
  /* do the table insertion */
1689
0
  g_hash_table_insert(sub_dissectors->hash_table,
1690
0
           GUINT_TO_POINTER(pattern), (void *)dtbl_entry);
1691
0
}
1692
1693
/* Reset an entry in a uint dissector table to its initial value. */
1694
void
1695
dissector_reset_uint(const char *name, const uint32_t pattern)
1696
0
{
1697
0
  dissector_table_t  sub_dissectors = find_dissector_table(name);
1698
0
  dtbl_entry_t      *dtbl_entry;
1699
1700
  /* sanity check */
1701
0
  ws_assert(sub_dissectors);
1702
1703
  /*
1704
   * Find the entry.
1705
   */
1706
0
  dtbl_entry = find_uint_dtbl_entry(sub_dissectors, pattern);
1707
1708
0
  if (dtbl_entry == NULL)
1709
0
    return;
1710
1711
  /*
1712
   * Found - is there an initial value?
1713
   */
1714
0
  if (dtbl_entry->initial != NULL) {
1715
0
    dtbl_entry->current = dtbl_entry->initial;
1716
0
  } else {
1717
0
    g_hash_table_remove(sub_dissectors->hash_table,
1718
0
            GUINT_TO_POINTER(pattern));
1719
0
  }
1720
0
}
1721
1722
/* Return true if an entry in a uint dissector table is found and has been
1723
 * changed (i.e. dissector_change_uint() has been called, such as from
1724
 * Decode As, prefs registered via dissector_add_uint_[range_]with_preference),
1725
 * etc.), otherwise return false.
1726
 */
1727
bool
1728
dissector_is_uint_changed(dissector_table_t const sub_dissectors, const uint32_t uint_val)
1729
260k
{
1730
260k
  if (sub_dissectors != NULL) {
1731
260k
    dtbl_entry_t *dtbl_entry = find_uint_dtbl_entry(sub_dissectors, uint_val);
1732
260k
    if (dtbl_entry != NULL)
1733
134k
      return (dtbl_entry->current != dtbl_entry->initial);
1734
260k
  }
1735
125k
  return false;
1736
260k
}
1737
1738
/* Look for a given value in a given uint dissector table and, if found,
1739
   call the dissector with the arguments supplied, and return the number
1740
   of bytes consumed by the dissector, otherwise return 0. */
1741
1742
int
1743
dissector_try_uint_with_data(dissector_table_t sub_dissectors, const uint32_t uint_val,
1744
           tvbuff_t *tvb, packet_info *pinfo, proto_tree *tree,
1745
           const bool add_proto_name, void *data)
1746
727k
{
1747
727k
  dtbl_entry_t            *dtbl_entry;
1748
727k
  struct dissector_handle *handle;
1749
727k
  uint32_t                 saved_match_uint;
1750
727k
  int len;
1751
1752
727k
  dtbl_entry = find_uint_dtbl_entry(sub_dissectors, uint_val);
1753
727k
  if (dtbl_entry == NULL) {
1754
    /*
1755
     * There's no entry in the table for our value.
1756
     */
1757
153k
    return 0;
1758
153k
  }
1759
1760
  /*
1761
   * Is there currently a dissector handle for this entry?
1762
   */
1763
573k
  handle = dtbl_entry->current;
1764
573k
  if (handle == NULL) {
1765
    /*
1766
     * No - pretend this dissector didn't exist,
1767
     * so that other dissectors might have a chance
1768
     * to dissect this packet.
1769
     */
1770
0
    return 0;
1771
0
  }
1772
1773
  /*
1774
   * Save the current value of "pinfo->match_uint",
1775
   * set it to the uint_val that matched, call the
1776
   * dissector, and restore "pinfo->match_uint".
1777
   */
1778
573k
  saved_match_uint  = pinfo->match_uint;
1779
573k
  pinfo->match_uint = uint_val;
1780
573k
  len = call_dissector_work(handle, tvb, pinfo, tree, add_proto_name, data);
1781
573k
  pinfo->match_uint = saved_match_uint;
1782
1783
  /*
1784
   * If a new-style dissector returned 0, it means that
1785
   * it didn't think this tvbuff represented a packet for
1786
   * its protocol, and didn't dissect anything.
1787
   *
1788
   * Old-style dissectors can't reject the packet.
1789
   *
1790
   * 0 is also returned if the protocol wasn't enabled.
1791
   *
1792
   * If the packet was rejected, we return 0, so that
1793
   * other dissectors might have a chance to dissect this
1794
   * packet, otherwise we return the dissected length.
1795
   */
1796
573k
  return len;
1797
573k
}
1798
1799
int
1800
dissector_try_uint(dissector_table_t sub_dissectors, const uint32_t uint_val,
1801
       tvbuff_t *tvb, packet_info *pinfo, proto_tree *tree)
1802
245k
{
1803
1804
245k
  return dissector_try_uint_with_data(sub_dissectors, uint_val, tvb, pinfo, tree, true, NULL);
1805
245k
}
1806
1807
/* Look for a given value in a given uint dissector table and, if found,
1808
   return the dissector handle for that value. */
1809
dissector_handle_t
1810
dissector_get_uint_handle(dissector_table_t const sub_dissectors, const uint32_t uint_val)
1811
366k
{
1812
366k
  dtbl_entry_t *dtbl_entry;
1813
1814
366k
  dtbl_entry = find_uint_dtbl_entry(sub_dissectors, uint_val);
1815
366k
  if (dtbl_entry != NULL)
1816
34.3k
    return dtbl_entry->current;
1817
332k
  else
1818
332k
    return NULL;
1819
366k
}
1820
1821
dissector_handle_t
1822
dissector_get_default_uint_handle(const char *name, const uint32_t uint_val)
1823
56
{
1824
56
  dissector_table_t sub_dissectors = find_dissector_table(name);
1825
1826
56
  if (sub_dissectors != NULL) {
1827
56
    dtbl_entry_t *dtbl_entry = find_uint_dtbl_entry(sub_dissectors, uint_val);
1828
56
    if (dtbl_entry != NULL)
1829
56
      return dtbl_entry->initial;
1830
56
  }
1831
0
  return NULL;
1832
56
}
1833
1834
/* Find an entry in a string dissector table. */
1835
static dtbl_entry_t *
1836
find_string_dtbl_entry(dissector_table_t const sub_dissectors, const char *pattern)
1837
25.7k
{
1838
25.7k
  dtbl_entry_t *ret;
1839
25.7k
  char *key;
1840
1841
25.7k
  switch (sub_dissectors->type) {
1842
1843
25.7k
  case FT_STRING:
1844
25.7k
  case FT_STRINGZ:
1845
25.7k
  case FT_STRINGZPAD:
1846
25.7k
  case FT_STRINGZTRUNC:
1847
    /*
1848
     * You can do a string lookup in these tables.
1849
     */
1850
25.7k
    break;
1851
1852
0
  default:
1853
    /*
1854
     * But you can't do a string lookup in any other types
1855
     * of tables.
1856
     */
1857
0
    ws_assert_not_reached();
1858
25.7k
  }
1859
1860
25.7k
  if (sub_dissectors->param == STRING_CASE_INSENSITIVE) {
1861
3.67k
    key = g_ascii_strdown(pattern, -1);
1862
22.1k
  } else {
1863
22.1k
    key = g_strdup(pattern);
1864
22.1k
  }
1865
1866
  /*
1867
   * Find the entry.
1868
   */
1869
25.7k
  ret = (dtbl_entry_t *)g_hash_table_lookup(sub_dissectors->hash_table, key);
1870
1871
25.7k
  g_free(key);
1872
1873
25.7k
  return ret;
1874
25.7k
}
1875
1876
/* Add an entry to a string dissector table. */
1877
void
1878
dissector_add_string(const char *name, const char *pattern,
1879
         dissector_handle_t handle)
1880
43.1k
{
1881
43.1k
  dissector_table_t  sub_dissectors;
1882
43.1k
  dtbl_entry_t      *dtbl_entry;
1883
43.1k
  char *key;
1884
1885
43.1k
  if (!dissector_get_table_checked(name, handle, &sub_dissectors))
1886
0
    return;
1887
1888
43.1k
  switch (sub_dissectors->type) {
1889
1890
43.0k
  case FT_STRING:
1891
43.1k
  case FT_STRINGZ:
1892
43.1k
  case FT_STRINGZPAD:
1893
43.1k
  case FT_STRINGZTRUNC:
1894
    /*
1895
     * You can do a string lookup in these tables.
1896
     */
1897
43.1k
    break;
1898
1899
0
  default:
1900
    /*
1901
     * But you can't do a string lookup in any other types
1902
     * of tables.
1903
     */
1904
0
    ws_assert_not_reached();
1905
43.1k
  }
1906
1907
43.1k
  dtbl_entry = g_new(dtbl_entry_t, 1);
1908
43.1k
  dtbl_entry->current = handle;
1909
43.1k
  dtbl_entry->initial = dtbl_entry->current;
1910
1911
43.1k
  if (sub_dissectors->param == STRING_CASE_INSENSITIVE) {
1912
7.31k
    key = g_ascii_strdown(pattern, -1);
1913
35.8k
  } else {
1914
35.8k
    key = g_strdup(pattern);
1915
35.8k
  }
1916
1917
  /* do the table insertion */
1918
43.1k
  g_hash_table_insert(sub_dissectors->hash_table, (void *)key,
1919
43.1k
           (void *)dtbl_entry);
1920
1921
  /*
1922
   * Now, if this table supports "Decode As", add this handle
1923
   * to the list of handles that could be used for "Decode As"
1924
   * with this table, because it *is* being used with this table.
1925
   */
1926
43.1k
  if (dissector_table_supports_decode_as(sub_dissectors))
1927
8.30k
    dissector_add_for_decode_as(name, handle);
1928
43.1k
}
1929
1930
/* Delete the entry for a dissector in a string dissector table
1931
   with a particular pattern. */
1932
1933
/* NOTE: this doesn't use the dissector call variable. It is included to */
1934
/*  be consistent with the dissector_add_string and more importantly to */
1935
/*      be used if the technique of adding a temporary dissector is */
1936
/*      implemented.  */
1937
/*  If temporary dissectors are deleted, then the original dissector must */
1938
/*  be available. */
1939
void
1940
dissector_delete_string(const char *name, const char *pattern,
1941
  dissector_handle_t handle _U_)
1942
0
{
1943
0
  dissector_table_t  sub_dissectors = find_dissector_table(name);
1944
0
  dtbl_entry_t      *dtbl_entry;
1945
1946
  /* sanity check */
1947
0
  ws_assert(sub_dissectors);
1948
1949
  /*
1950
   * Find the entry.
1951
   */
1952
0
  dtbl_entry = find_string_dtbl_entry(sub_dissectors, pattern);
1953
1954
0
  if (dtbl_entry != NULL) {
1955
    /*
1956
     * Found - remove it.
1957
     */
1958
0
    g_hash_table_remove(sub_dissectors->hash_table, pattern);
1959
0
  }
1960
0
}
1961
1962
/* Change the entry for a dissector in a string dissector table
1963
   with a particular pattern to use a new dissector handle. */
1964
void
1965
dissector_change_string(const char *name, const char *pattern,
1966
      dissector_handle_t handle)
1967
0
{
1968
0
  dissector_table_t  sub_dissectors = find_dissector_table(name);
1969
0
  dtbl_entry_t      *dtbl_entry;
1970
1971
  /* sanity check */
1972
0
  ws_assert(sub_dissectors);
1973
1974
  /*
1975
   * See if the entry already exists. If so, reuse it.
1976
   */
1977
0
  dtbl_entry = find_string_dtbl_entry(sub_dissectors, pattern);
1978
0
  if (dtbl_entry != NULL) {
1979
    /*
1980
     * If there's no initial value, and the user said not
1981
     * to decode it, just remove the entry to save memory.
1982
     */
1983
0
    if (handle == NULL && dtbl_entry->initial == NULL) {
1984
0
      g_hash_table_remove(sub_dissectors->hash_table,
1985
0
              pattern);
1986
0
      return;
1987
0
    }
1988
0
    dtbl_entry->current = handle;
1989
0
    return;
1990
0
  }
1991
1992
  /*
1993
   * Don't create an entry if there is no dissector handle - I.E. the
1994
   * user said not to decode something that wasn't being decoded
1995
   * in the first place.
1996
   */
1997
0
  if (handle == NULL)
1998
0
    return;
1999
2000
0
  dtbl_entry = g_new(dtbl_entry_t, 1);
2001
0
  dtbl_entry->initial = NULL;
2002
0
  dtbl_entry->current = handle;
2003
2004
  /* do the table insertion */
2005
0
  g_hash_table_insert(sub_dissectors->hash_table, (void *)g_strdup(pattern),
2006
0
           (void *)dtbl_entry);
2007
0
}
2008
2009
/* Reset an entry in a string sub-dissector table to its initial value. */
2010
void
2011
dissector_reset_string(const char *name, const char *pattern)
2012
0
{
2013
0
  dissector_table_t  sub_dissectors = find_dissector_table(name);
2014
0
  dtbl_entry_t      *dtbl_entry;
2015
2016
  /* sanity check */
2017
0
  ws_assert(sub_dissectors);
2018
2019
  /*
2020
   * Find the entry.
2021
   */
2022
0
  dtbl_entry = find_string_dtbl_entry(sub_dissectors, pattern);
2023
2024
0
  if (dtbl_entry == NULL)
2025
0
    return;
2026
2027
  /*
2028
   * Found - is there an initial value?
2029
   */
2030
0
  if (dtbl_entry->initial != NULL) {
2031
0
    dtbl_entry->current = dtbl_entry->initial;
2032
0
  } else {
2033
0
    g_hash_table_remove(sub_dissectors->hash_table, pattern);
2034
0
  }
2035
0
}
2036
2037
/* Return true if an entry in a uint dissector table is found and has been
2038
 * changed (i.e. dissector_change_uint() has been called, such as from
2039
 * Decode As, prefs registered via dissector_add_uint_[range_]with_preference),
2040
 * etc.), otherwise return false.
2041
 */
2042
bool
2043
dissector_is_string_changed(dissector_table_t const sub_dissectors, const char *string)
2044
0
{
2045
0
  if (sub_dissectors != NULL) {
2046
0
    dtbl_entry_t *dtbl_entry = find_string_dtbl_entry(sub_dissectors, string);
2047
0
    if (dtbl_entry != NULL)
2048
0
      return (dtbl_entry->current != dtbl_entry->initial);
2049
0
  }
2050
0
  return false;
2051
0
}
2052
2053
/* Look for a given string in a given dissector table and, if found, call
2054
   the dissector with the arguments supplied, and return length of dissected data,
2055
   otherwise return 0. */
2056
int
2057
dissector_try_string_with_data(dissector_table_t sub_dissectors, const char *string,
2058
         tvbuff_t *tvb, packet_info *pinfo, proto_tree *tree, const bool add_proto_name, void *data)
2059
24.8k
{
2060
24.8k
  dtbl_entry_t            *dtbl_entry;
2061
24.8k
  struct dissector_handle *handle;
2062
24.8k
  int                      len;
2063
24.8k
  const char              *saved_match_string;
2064
2065
  /* XXX ASSERT instead ? */
2066
24.8k
  if (!string) return 0;
2067
24.8k
  dtbl_entry = find_string_dtbl_entry(sub_dissectors, string);
2068
24.8k
  if (dtbl_entry != NULL) {
2069
    /*
2070
     * Is there currently a dissector handle for this entry?
2071
     */
2072
19.1k
    handle = dtbl_entry->current;
2073
19.1k
    if (handle == NULL) {
2074
      /*
2075
       * No - pretend this dissector didn't exist,
2076
       * so that other dissectors might have a chance
2077
       * to dissect this packet.
2078
       */
2079
0
      return 0;
2080
0
    }
2081
2082
    /*
2083
     * Save the current value of "pinfo->match_string",
2084
     * set it to the string that matched, call the
2085
     * dissector, and restore "pinfo->match_string".
2086
     */
2087
19.1k
    saved_match_string = pinfo->match_string;
2088
19.1k
    pinfo->match_string = string;
2089
19.1k
    len = call_dissector_work(handle, tvb, pinfo, tree, add_proto_name, data);
2090
19.1k
    pinfo->match_string = saved_match_string;
2091
2092
    /*
2093
     * If a new-style dissector returned 0, it means that
2094
     * it didn't think this tvbuff represented a packet for
2095
     * its protocol, and didn't dissect anything.
2096
     *
2097
     * Old-style dissectors can't reject the packet.
2098
     *
2099
     * 0 is also returned if the protocol wasn't enabled.
2100
     *
2101
     * If the packet was rejected, we return 0, so that
2102
     * other dissectors might have a chance to dissect this
2103
     * packet, otherwise we return the dissected length.
2104
     */
2105
19.1k
    return len;
2106
19.1k
  }
2107
5.72k
  return 0;
2108
24.8k
}
2109
2110
/* Look for a given value in a given string dissector table and, if found,
2111
   return the dissector handle for that value. */
2112
dissector_handle_t
2113
dissector_get_string_handle(dissector_table_t sub_dissectors,
2114
          const char *string)
2115
897
{
2116
897
  dtbl_entry_t *dtbl_entry;
2117
2118
  /* XXX ASSERT instead ? */
2119
897
  if (!string) return NULL;
2120
897
  dtbl_entry = find_string_dtbl_entry(sub_dissectors, string);
2121
897
  if (dtbl_entry != NULL)
2122
6
    return dtbl_entry->current;
2123
891
  else
2124
891
    return NULL;
2125
897
}
2126
2127
dissector_handle_t
2128
dissector_get_default_string_handle(const char *name, const char *string)
2129
0
{
2130
0
  dissector_table_t sub_dissectors;
2131
2132
  /* XXX ASSERT instead ? */
2133
0
  if (!string) return NULL;
2134
0
  sub_dissectors = find_dissector_table(name);
2135
0
  if (sub_dissectors != NULL) {
2136
0
    dtbl_entry_t *dtbl_entry = find_string_dtbl_entry(sub_dissectors, string);
2137
0
    if (dtbl_entry != NULL)
2138
0
      return dtbl_entry->initial;
2139
0
  }
2140
0
  return NULL;
2141
0
}
2142
2143
/* Add an entry to a "custom" dissector table. */
2144
void dissector_add_custom_table_handle(const char *name, void *pattern, dissector_handle_t handle)
2145
24.3k
{
2146
24.3k
  dissector_table_t  sub_dissectors;
2147
24.3k
  dtbl_entry_t      *dtbl_entry;
2148
2149
24.3k
  if (!dissector_get_table_checked(name, handle, &sub_dissectors))
2150
0
    return;
2151
2152
24.3k
  ws_assert(sub_dissectors->type == FT_BYTES);
2153
2154
24.3k
  dtbl_entry = g_new(dtbl_entry_t, 1);
2155
24.3k
  dtbl_entry->current = handle;
2156
24.3k
  dtbl_entry->initial = dtbl_entry->current;
2157
2158
  /* do the table insertion */
2159
24.3k
  g_hash_table_insert(sub_dissectors->hash_table, (void *)pattern,
2160
24.3k
           (void *)dtbl_entry);
2161
2162
  /*
2163
   * Now, if this table supports "Decode As", add this handle
2164
   * to the list of handles that could be used for "Decode As"
2165
   * with this table, because it *is* being used with this table.
2166
   */
2167
24.3k
  if (dissector_table_supports_decode_as(sub_dissectors))
2168
0
    dissector_add_for_decode_as(name, handle);
2169
24.3k
}
2170
2171
dissector_handle_t dissector_get_custom_table_handle(dissector_table_t sub_dissectors, void *key)
2172
32.0k
{
2173
32.0k
  dtbl_entry_t *dtbl_entry = (dtbl_entry_t *)g_hash_table_lookup(sub_dissectors->hash_table, key);
2174
2175
32.0k
  if (dtbl_entry != NULL)
2176
8.86k
    return dtbl_entry->current;
2177
2178
23.1k
  return NULL;
2179
32.0k
}
2180
/* Add an entry to a guid dissector table. */
2181
void dissector_add_guid(const char *name, guid_key* guid_val, dissector_handle_t handle)
2182
1.61k
{
2183
1.61k
  dissector_table_t  sub_dissectors;
2184
1.61k
  dtbl_entry_t      *dtbl_entry;
2185
2186
1.61k
  if (!dissector_get_table_checked(name, handle, &sub_dissectors))
2187
0
    return;
2188
2189
1.61k
  if (sub_dissectors->type != FT_GUID) {
2190
0
    ws_assert_not_reached();
2191
0
  }
2192
2193
1.61k
  dtbl_entry = g_new(dtbl_entry_t, 1);
2194
1.61k
  dtbl_entry->current = handle;
2195
1.61k
  dtbl_entry->initial = dtbl_entry->current;
2196
2197
  /* do the table insertion */
2198
1.61k
  g_hash_table_insert(sub_dissectors->hash_table,
2199
1.61k
           guid_val, (void *)dtbl_entry);
2200
2201
  /*
2202
   * Now, if this table supports "Decode As", add this handle
2203
   * to the list of handles that could be used for "Decode As"
2204
   * with this table, because it *is* being used with this table.
2205
   */
2206
1.61k
  if (dissector_table_supports_decode_as(sub_dissectors))
2207
1.52k
    dissector_add_for_decode_as(name, handle);
2208
1.61k
}
2209
2210
/* Look for a given value in a given guid dissector table and, if found,
2211
   call the dissector with the arguments supplied, and return true,
2212
   otherwise return false. */
2213
int dissector_try_guid_with_data(dissector_table_t sub_dissectors,
2214
    guid_key* guid_val, tvbuff_t *tvb, packet_info *pinfo, proto_tree *tree, const bool add_proto_name, void *data)
2215
0
{
2216
0
  dtbl_entry_t            *dtbl_entry;
2217
0
  struct dissector_handle *handle;
2218
0
  int len;
2219
2220
0
  dtbl_entry = (dtbl_entry_t *)g_hash_table_lookup(sub_dissectors->hash_table, guid_val);
2221
0
  if (dtbl_entry != NULL) {
2222
    /*
2223
     * Is there currently a dissector handle for this entry?
2224
     */
2225
0
    handle = dtbl_entry->current;
2226
0
    if (handle == NULL) {
2227
      /*
2228
       * No - pretend this dissector didn't exist,
2229
       * so that other dissectors might have a chance
2230
       * to dissect this packet.
2231
       */
2232
0
      return 0;
2233
0
    }
2234
2235
    /*
2236
     * Save the current value of "pinfo->match_uint",
2237
     * set it to the uint_val that matched, call the
2238
     * dissector, and restore "pinfo->match_uint".
2239
     */
2240
0
    len = call_dissector_work(handle, tvb, pinfo, tree, add_proto_name, data);
2241
2242
    /*
2243
     * If a new-style dissector returned 0, it means that
2244
     * it didn't think this tvbuff represented a packet for
2245
     * its protocol, and didn't dissect anything.
2246
     *
2247
     * Old-style dissectors can't reject the packet.
2248
     *
2249
     * 0 is also returned if the protocol wasn't enabled.
2250
     *
2251
     * If the packet was rejected, we return 0, so that
2252
     * other dissectors might have a chance to dissect this
2253
     * packet, otherwise we return the dissected length.
2254
     */
2255
0
    return len;
2256
0
  }
2257
0
  return 0;
2258
0
}
2259
2260
/** Look for a given value in a given guid dissector table and, if found,
2261
 * return the current dissector handle for that value.
2262
 *
2263
 * @param[in] sub_dissectors Dissector table to search.
2264
 * @param[in] guid_val Value to match.
2265
 * @return The matching dissector handle on success, NULL if no match is found.
2266
 */
2267
dissector_handle_t dissector_get_guid_handle(
2268
    dissector_table_t const sub_dissectors, guid_key* guid_val)
2269
0
{
2270
0
  dtbl_entry_t *dtbl_entry;
2271
2272
0
  dtbl_entry = (dtbl_entry_t *)g_hash_table_lookup(sub_dissectors->hash_table, guid_val);
2273
0
  if (dtbl_entry != NULL)
2274
0
    return dtbl_entry->current;
2275
0
  else
2276
0
    return NULL;
2277
0
}
2278
2279
/* Use the currently assigned payload dissector for the dissector table and,
2280
   if any, call the dissector with the arguments supplied, and return the
2281
   number of bytes consumed, otherwise return 0. */
2282
int dissector_try_payload_with_data(dissector_table_t sub_dissectors,
2283
    tvbuff_t *tvb, packet_info *pinfo, proto_tree *tree, const bool add_proto_name, void *data)
2284
377
{
2285
377
  return dissector_try_uint_with_data(sub_dissectors, 0, tvb, pinfo, tree, add_proto_name, data);
2286
377
}
2287
2288
/* Change the entry for a dissector in a payload (FT_NONE) dissector table
2289
   with a particular pattern to use a new dissector handle. */
2290
void dissector_change_payload(const char *name, dissector_handle_t handle)
2291
0
{
2292
0
  dissector_change_uint(name, 0, handle);
2293
0
}
2294
2295
/* Reset payload (FT_NONE) dissector table to its initial value. */
2296
void dissector_reset_payload(const char *name)
2297
0
{
2298
0
  dissector_reset_uint(name, 0);
2299
0
}
2300
2301
/* Given a payload dissector table (type FT_NONE), return the handle of
2302
   the dissector that is currently active, i.e. that was selected via
2303
   Decode As. */
2304
dissector_handle_t
2305
dissector_get_payload_handle(dissector_table_t const dissector_table)
2306
0
{
2307
0
  return dissector_get_uint_handle(dissector_table, 0);
2308
0
}
2309
2310
dissector_handle_t
2311
dtbl_entry_get_handle (dtbl_entry_t *dtbl_entry)
2312
0
{
2313
0
  return dtbl_entry->current;
2314
0
}
2315
2316
static int
2317
dissector_compare_filter_name(const void *dissector_a, const void *dissector_b)
2318
178k
{
2319
178k
  const struct dissector_handle *a = (const struct dissector_handle *)dissector_a;
2320
178k
  const struct dissector_handle *b = (const struct dissector_handle *)dissector_b;
2321
178k
  const char *a_name, *b_name;
2322
178k
  int ret;
2323
2324
178k
  if (a->protocol == NULL)
2325
48
    a_name = "";
2326
178k
  else
2327
178k
    a_name = proto_get_protocol_filter_name(proto_get_id(a->protocol));
2328
2329
178k
  if (b->protocol == NULL)
2330
96
    b_name = "";
2331
178k
  else
2332
178k
    b_name = proto_get_protocol_filter_name(proto_get_id(b->protocol));
2333
2334
178k
  ret = strcmp(a_name, b_name);
2335
178k
  return ret;
2336
178k
}
2337
2338
void
2339
packet_all_tables_sort_handles(void)
2340
16
{
2341
16
  GHashTableIter iter;
2342
16
  g_hash_table_iter_init(&iter, dissector_tables);
2343
16
  void *key, *value;
2344
16
  dissector_table_t table;
2345
9.71k
  while (g_hash_table_iter_next(&iter, &key, &value)) {
2346
9.69k
    table = (dissector_table_t)value;
2347
9.69k
    table->dissector_handles = g_slist_sort(table->dissector_handles, (GCompareFunc)dissector_compare_filter_name);
2348
9.69k
  }
2349
  /* Any handles added to a table after this (e.g., by a Lua dissector,
2350
   * by reloading Lua dissectors, by a UAT or other preference) will
2351
   * be added using g_slist_insert_sorted. */
2352
16
  all_tables_handles_sorted = true;
2353
16
}
2354
2355
/* Add a handle to the list of handles that *could* be used with this
2356
   table.  That list is used by the "Decode As"/"-d" code in the UI. */
2357
void
2358
dissector_add_for_decode_as(const char *name, dissector_handle_t handle)
2359
48.8k
{
2360
48.8k
  dissector_table_t  sub_dissectors;
2361
48.8k
  dissector_handle_t dup_handle;
2362
2363
48.8k
  if (!dissector_get_table_checked(name, handle, &sub_dissectors))
2364
0
    return;
2365
2366
48.8k
  const char *dissector_name;
2367
48.8k
  dissector_name = dissector_handle_get_dissector_name(handle);
2368
48.8k
  if (dissector_name == NULL)
2369
5.07k
    dissector_name = "(anonymous)";
2370
2371
  /*
2372
   * Make sure it supports Decode As.
2373
   */
2374
48.8k
  if (!dissector_table_supports_decode_as(sub_dissectors)) {
2375
0
    ws_dissector_bug("Registering dissector %s for protocol %s in dissector table %s, which doesn't support Decode As\n",
2376
0
            dissector_name,
2377
0
            proto_get_protocol_short_name(handle->protocol),
2378
0
            name);
2379
0
    return;
2380
0
  }
2381
2382
  /* For Decode As selection to work, there has to be a description.
2383
   * One is generated if there's a protocol (PINOs are used in some
2384
   * cases to guarantee unique descriptions), but some dissectors are
2385
   * registered without a protocol. That is allowed for fixed tables
2386
   * that don't support Decode As.
2387
   */
2388
48.8k
  if (handle->description == NULL) {
2389
0
    ws_dissector_bug("Cannot register dissector %s in dissector table %s for Decode As without a protocol or description\n",
2390
0
        dissector_name, name);
2391
0
    return;
2392
0
  }
2393
2394
  /* Ensure that the description is unique in the table, so that Decode As
2395
   * selection and UAT preference writing works.
2396
   *
2397
   * XXX - We could do the insert first and then check the return value,
2398
   * saving on a hash comparison. (The failure mode would be slightly
2399
   * different, as it would become last insertion wins.)
2400
   */
2401
48.8k
  dup_handle = g_hash_table_lookup(sub_dissectors->da_descriptions, handle->description);
2402
48.8k
  if (dup_handle != NULL) {
2403
    /* Is this a different handle with the same description, or
2404
     * just trying to insert the same handle a second time? */
2405
9.79k
    if (dup_handle != handle) {
2406
0
      const char *dup_dissector_name;
2407
2408
0
      dup_dissector_name = dissector_handle_get_dissector_name(dup_handle);
2409
0
      if (dup_dissector_name == NULL)
2410
0
        dup_dissector_name = "(anonymous)";
2411
0
      ws_dissector_bug("Dissectors %s and %s in dissector table %s have the same description %s\n",
2412
0
          dissector_name,
2413
0
          dup_dissector_name,
2414
0
          name, handle->description);
2415
0
    }
2416
9.79k
    return;
2417
9.79k
  }
2418
2419
  /* Add the dissector as a dependency
2420
    (some dissector tables don't have protocol association, so there is
2421
    the need for the NULL check */
2422
39.0k
  if (sub_dissectors->protocol != NULL)
2423
37.6k
    register_depend_dissector(proto_get_protocol_short_name(sub_dissectors->protocol), proto_get_protocol_short_name(handle->protocol));
2424
2425
  /* Add it to the list. */
2426
39.0k
  g_hash_table_insert(sub_dissectors->da_descriptions, (void *)handle->description, handle);
2427
39.0k
  if (all_tables_handles_sorted) {
2428
0
    sub_dissectors->dissector_handles =
2429
0
      g_slist_insert_sorted(sub_dissectors->dissector_handles, (void *)handle, (GCompareFunc)dissector_compare_filter_name);
2430
39.0k
  } else {
2431
39.0k
    sub_dissectors->dissector_handles =
2432
39.0k
      g_slist_prepend(sub_dissectors->dissector_handles, (void *)handle);
2433
39.0k
  }
2434
39.0k
}
2435
2436
void dissector_add_for_decode_as_with_preference(const char *name,
2437
    dissector_handle_t handle)
2438
2.97k
{
2439
  /* If a dissector is added for Decode As only, it's dissector
2440
     table value would default to 0.
2441
     Set up a preference value with that information
2442
   */
2443
2.97k
  dissector_add_range_preference(name, handle, "");
2444
2445
2.97k
  dissector_add_for_decode_as(name, handle);
2446
2.97k
}
2447
2448
dissector_handle_t
2449
dtbl_entry_get_initial_handle (dtbl_entry_t *dtbl_entry)
2450
0
{
2451
0
  return dtbl_entry->initial;
2452
0
}
2453
2454
GSList *
2455
12
dissector_table_get_dissector_handles(dissector_table_t dissector_table) {
2456
12
  if (!dissector_table)
2457
0
    return NULL;
2458
2459
12
  return dissector_table->dissector_handles;
2460
12
}
2461
2462
/*
2463
 * Data structure used as user data when iterating dissector handles
2464
 */
2465
typedef struct lookup_entry {
2466
  const char* dissector_description;
2467
  dissector_handle_t handle;
2468
} lookup_entry_t;
2469
2470
/*
2471
 * A callback function to changed a dissector_handle if matched
2472
 * This is used when iterating a dissector table
2473
 */
2474
static void
2475
find_dissector_in_table(void *item, void *user_data)
2476
0
{
2477
0
  dissector_handle_t handle = (dissector_handle_t)item;
2478
0
  lookup_entry_t * lookup = (lookup_entry_t *)user_data;
2479
0
  const char *description = dissector_handle_get_description(handle);
2480
0
  if (description && strcmp(lookup->dissector_description, description) == 0) {
2481
0
    lookup->handle = handle;
2482
0
  }
2483
0
}
2484
2485
dissector_handle_t dissector_table_get_dissector_handle(dissector_table_t dissector_table, const char* description)
2486
0
{
2487
  /* Can this even be called for tables that don't support Decode As? */
2488
0
  if (dissector_table->da_descriptions) {
2489
0
    return g_hash_table_lookup(dissector_table->da_descriptions, description);
2490
0
  }
2491
2492
0
  lookup_entry_t lookup;
2493
2494
0
  lookup.dissector_description = description;
2495
0
  lookup.handle = NULL;
2496
2497
0
  g_slist_foreach(dissector_table->dissector_handles, find_dissector_in_table, &lookup);
2498
0
  return lookup.handle;
2499
0
}
2500
2501
ftenum_t
2502
0
dissector_table_get_type(dissector_table_t dissector_table) {
2503
0
  if (!dissector_table) return FT_NONE;
2504
0
  return dissector_table->type;
2505
0
}
2506
2507
inline void
2508
dissector_table_allow_decode_as_internal(dissector_table_t dissector_table)
2509
1.21k
{
2510
1.21k
  if (dissector_table->da_descriptions == NULL) {
2511
1.08k
    dissector_table->da_descriptions = g_hash_table_new(wmem_str_hash, g_str_equal);
2512
1.08k
  }
2513
1.21k
}
2514
2515
void
2516
dissector_table_allow_decode_as(dissector_table_t dissector_table)
2517
0
{
2518
0
  dissector_table_allow_decode_as_internal(dissector_table);
2519
0
}
2520
2521
inline bool
2522
dissector_table_supports_decode_as(dissector_table_t dissector_table)
2523
307k
{
2524
307k
  return dissector_table->da_descriptions != NULL;
2525
307k
}
2526
2527
static int
2528
uuid_equal(const void *k1, const void *k2)
2529
768
{
2530
768
  const guid_key *key1 = (const guid_key *)k1;
2531
768
  const guid_key *key2 = (const guid_key *)k2;
2532
768
  return ((memcmp(&key1->guid, &key2->guid, sizeof (e_guid_t)) == 0)
2533
16
    && (key1->ver == key2->ver));
2534
768
}
2535
2536
static unsigned
2537
uuid_hash(const void *k)
2538
1.61k
{
2539
1.61k
  const guid_key *key = (const guid_key *)k;
2540
  /* This isn't perfect, but the Data1 part of these is almost always unique. */
2541
1.61k
  return key->guid.data1;
2542
1.61k
}
2543
2544
/**************************************************/
2545
/*                                                */
2546
/*       Routines to walk dissector tables        */
2547
/*                                                */
2548
/**************************************************/
2549
2550
typedef struct dissector_foreach_info {
2551
  void *        caller_data;
2552
  DATFunc       caller_func;
2553
  GHFunc        next_func;
2554
  const char   *table_name;
2555
  ftenum_t      selector_type;
2556
} dissector_foreach_info_t;
2557
2558
/*
2559
 * Called for each entry in a dissector table.
2560
 */
2561
static void
2562
dissector_table_foreach_func (void *key, void *value, void *user_data)
2563
960
{
2564
960
  dissector_foreach_info_t *info;
2565
960
  dtbl_entry_t             *dtbl_entry;
2566
2567
960
  ws_assert(value);
2568
960
  ws_assert(user_data);
2569
2570
960
  dtbl_entry = (dtbl_entry_t *)value;
2571
960
  if (dtbl_entry->current == NULL ||
2572
960
      dtbl_entry->current->protocol == NULL) {
2573
    /*
2574
     * Either there is no dissector for this entry, or
2575
     * the dissector doesn't have a protocol associated
2576
     * with it.
2577
     *
2578
     * XXX - should the latter check be done?
2579
     */
2580
0
    return;
2581
0
  }
2582
2583
960
  info = (dissector_foreach_info_t *)user_data;
2584
960
  info->caller_func(info->table_name, info->selector_type, key, value,
2585
960
        info->caller_data);
2586
960
}
2587
2588
/*
2589
 * Called for each entry in the table of all dissector tables.
2590
 */
2591
static void
2592
dissector_all_tables_foreach_func (void *key, void *value, void *user_data)
2593
9.69k
{
2594
9.69k
  dissector_table_t         sub_dissectors;
2595
9.69k
  dissector_foreach_info_t *info;
2596
2597
9.69k
  ws_assert(value);
2598
9.69k
  ws_assert(user_data);
2599
2600
9.69k
  sub_dissectors = (dissector_table_t)value;
2601
9.69k
  info = (dissector_foreach_info_t *)user_data;
2602
9.69k
  info->table_name = (char*) key;
2603
9.69k
  info->selector_type = get_dissector_table_selector_type(info->table_name);
2604
9.69k
  g_hash_table_foreach(sub_dissectors->hash_table, info->next_func, info);
2605
9.69k
}
2606
2607
#if 0
2608
/*
2609
 * Walk all dissector tables calling a user supplied function on each
2610
 * entry.
2611
 */
2612
static void
2613
dissector_all_tables_foreach (DATFunc func,
2614
            void *user_data)
2615
{
2616
  dissector_foreach_info_t info;
2617
2618
  info.caller_data = user_data;
2619
  info.caller_func = func;
2620
  info.next_func   = dissector_table_foreach_func;
2621
  g_hash_table_foreach(dissector_tables, dissector_all_tables_foreach_func, &info);
2622
}
2623
#endif
2624
2625
/*
2626
 * Walk one dissector table's hash table calling a user supplied function
2627
 * on each entry.
2628
 */
2629
void
2630
dissector_table_foreach (const char *table_name,
2631
       DATFunc     func,
2632
       void *      user_data)
2633
16
{
2634
16
  dissector_foreach_info_t info;
2635
16
  dissector_table_t        sub_dissectors = find_dissector_table(table_name);
2636
2637
16
  info.table_name    = table_name;
2638
16
  info.selector_type = sub_dissectors->type;
2639
16
  info.caller_func   = func;
2640
16
  info.caller_data   = user_data;
2641
16
  g_hash_table_foreach(sub_dissectors->hash_table, dissector_table_foreach_func, &info);
2642
16
}
2643
2644
/*
2645
 * Walk one dissector table's list of handles calling a user supplied
2646
 * function on each entry.
2647
 */
2648
void
2649
dissector_table_foreach_handle(const char     *table_name,
2650
             DATFunc_handle  func,
2651
             void *          user_data)
2652
0
{
2653
0
  dissector_table_t sub_dissectors = find_dissector_table(table_name);
2654
0
  GSList *tmp;
2655
2656
0
  for (tmp = sub_dissectors->dissector_handles; tmp != NULL;
2657
0
       tmp = g_slist_next(tmp))
2658
0
    func(table_name, tmp->data, user_data);
2659
0
}
2660
2661
/*
2662
 * Called for each entry in a dissector table.
2663
 */
2664
static void
2665
dissector_table_foreach_changed_func (void *key, void *value, void *user_data)
2666
254k
{
2667
254k
  dtbl_entry_t             *dtbl_entry;
2668
254k
  dissector_foreach_info_t *info;
2669
2670
254k
  ws_assert(value);
2671
254k
  ws_assert(user_data);
2672
2673
254k
  dtbl_entry = (dtbl_entry_t *)value;
2674
254k
  if (dtbl_entry->initial == dtbl_entry->current) {
2675
    /*
2676
     * Entry hasn't changed - don't call the function.
2677
     */
2678
254k
    return;
2679
254k
  }
2680
2681
0
  info = (dissector_foreach_info_t *)user_data;
2682
0
  info->caller_func(info->table_name, info->selector_type, key, value,
2683
0
        info->caller_data);
2684
0
}
2685
2686
/*
2687
 * Walk all dissector tables calling a user supplied function only on
2688
 * any entry that has been changed from its original state.
2689
 */
2690
void
2691
dissector_all_tables_foreach_changed (DATFunc  func,
2692
              void *user_data)
2693
16
{
2694
16
  dissector_foreach_info_t info;
2695
2696
16
  info.caller_data = user_data;
2697
16
  info.caller_func = func;
2698
16
  info.next_func   = dissector_table_foreach_changed_func;
2699
16
  g_hash_table_foreach(dissector_tables, dissector_all_tables_foreach_func, &info);
2700
16
}
2701
2702
/*
2703
 * Walk one dissector table calling a user supplied function only on
2704
 * any entry that has been changed from its original state.
2705
 */
2706
void
2707
dissector_table_foreach_changed (const char *table_name,
2708
         DATFunc     func,
2709
         void *      user_data)
2710
0
{
2711
0
  dissector_foreach_info_t info;
2712
0
  dissector_table_t sub_dissectors = find_dissector_table(table_name);
2713
2714
0
  info.table_name    = table_name;
2715
0
  info.selector_type = sub_dissectors->type;
2716
0
  info.caller_func   = func;
2717
0
  info.caller_data   = user_data;
2718
0
  g_hash_table_foreach(sub_dissectors->hash_table,
2719
0
           dissector_table_foreach_changed_func, &info);
2720
0
}
2721
2722
typedef struct dissector_foreach_table_info {
2723
  void *        caller_data;
2724
  DATFunc_table caller_func;
2725
} dissector_foreach_table_info_t;
2726
2727
/*
2728
 * Called for each entry in the table of all dissector tables.
2729
 * This is used if we directly process the hash table.
2730
 */
2731
static void
2732
dissector_all_tables_foreach_table_func (void *key, void *value, void *user_data)
2733
9.69k
{
2734
9.69k
  dissector_table_t               table;
2735
9.69k
  dissector_foreach_table_info_t *info;
2736
2737
9.69k
  table = (dissector_table_t)value;
2738
9.69k
  info  = (dissector_foreach_table_info_t *)user_data;
2739
9.69k
  (*info->caller_func)((char *)key, table->ui_name, info->caller_data);
2740
9.69k
}
2741
2742
/*
2743
 * Called for each key in the table of all dissector tables.
2744
 * This is used if we get a list of table names, sort it, and process the list.
2745
 */
2746
static void
2747
dissector_all_tables_foreach_list_func (void *key, void *user_data)
2748
0
{
2749
0
  dissector_table_t               table;
2750
0
  dissector_foreach_table_info_t *info;
2751
2752
0
  table = (dissector_table_t)g_hash_table_lookup(dissector_tables, key);
2753
0
  info  = (dissector_foreach_table_info_t *)user_data;
2754
0
  (*info->caller_func)((char*)key, table->ui_name, info->caller_data);
2755
0
}
2756
2757
/*
2758
 * Walk all dissector tables calling a user supplied function on each
2759
 * table.
2760
 */
2761
void
2762
dissector_all_tables_foreach_table (DATFunc_table func,
2763
            void *        user_data,
2764
            GCompareFunc  compare_key_func)
2765
16
{
2766
16
  dissector_foreach_table_info_t info;
2767
16
  GList *list;
2768
2769
16
  info.caller_data = user_data;
2770
16
  info.caller_func = func;
2771
16
  if (compare_key_func != NULL)
2772
0
  {
2773
0
    list = g_hash_table_get_keys(dissector_tables);
2774
0
    list = g_list_sort(list, compare_key_func);
2775
0
    g_list_foreach(list, dissector_all_tables_foreach_list_func, &info);
2776
0
    g_list_free(list);
2777
0
  }
2778
16
  else
2779
16
  {
2780
16
    g_hash_table_foreach(dissector_tables, dissector_all_tables_foreach_table_func, &info);
2781
16
  }
2782
16
}
2783
2784
dissector_table_t
2785
register_dissector_table(const char *name, const char *ui_name, const int proto, const ftenum_t type,
2786
       const int param)
2787
9.52k
{
2788
9.52k
  dissector_table_t sub_dissectors;
2789
2790
  /* Create and register the dissector table for this name; returns */
2791
  /* a pointer to the dissector table. */
2792
9.52k
  sub_dissectors = g_slice_new(struct dissector_table);
2793
9.52k
  switch (type) {
2794
2795
2.51k
  case FT_UINT8:
2796
4.20k
  case FT_UINT16:
2797
4.40k
  case FT_UINT24:
2798
7.92k
  case FT_UINT32:
2799
    /*
2800
     * XXX - there's no "g_uint_hash()" or "g_uint_equal()",
2801
     * so we use "g_direct_hash()" and "g_direct_equal()".
2802
     */
2803
7.92k
    sub_dissectors->hash_table = g_hash_table_new_full(g_direct_hash,
2804
7.92k
                     g_direct_equal,
2805
7.92k
                     NULL,
2806
7.92k
                     &g_free);
2807
7.92k
    break;
2808
2809
1.13k
  case FT_STRING:
2810
1.15k
  case FT_STRINGZ:
2811
1.15k
  case FT_STRINGZPAD:
2812
1.15k
  case FT_STRINGZTRUNC:
2813
1.15k
    sub_dissectors->hash_table = g_hash_table_new_full(g_str_hash,
2814
1.15k
                     g_str_equal,
2815
1.15k
                     &g_free,
2816
1.15k
                     &g_free);
2817
1.15k
    break;
2818
32
  case FT_GUID:
2819
32
    sub_dissectors->hash_table = g_hash_table_new_full(uuid_hash,
2820
32
                     uuid_equal,
2821
32
                     NULL,
2822
32
                     &g_free);
2823
32
    break;
2824
2825
416
  case FT_NONE:
2826
    /* Dissector tables with FT_NONE don't have values associated with
2827
       dissectors so this will always be a hash table size of 1 just
2828
       to store the single dtbl_entry_t */
2829
416
    sub_dissectors->hash_table = g_hash_table_new_full(g_direct_hash,
2830
416
                     g_direct_equal,
2831
416
                     NULL,
2832
416
                     &g_free);
2833
416
    break;
2834
2835
0
  default:
2836
0
    ws_error("The dissector table %s (%s) is registering an unsupported type - are you using a buggy plugin?", name, ui_name);
2837
0
    ws_assert_not_reached();
2838
9.52k
  }
2839
9.52k
  sub_dissectors->dissector_handles = NULL;
2840
9.52k
  sub_dissectors->da_descriptions = NULL;
2841
9.52k
  sub_dissectors->ui_name = ui_name;
2842
9.52k
  sub_dissectors->type    = type;
2843
9.52k
  sub_dissectors->param   = param;
2844
9.52k
  sub_dissectors->protocol  = (proto == -1) ? NULL : find_protocol_by_id(proto);
2845
  /* Make sure the registration is unique */
2846
9.52k
  if (!g_hash_table_insert(dissector_tables, (void *)name, (void *) sub_dissectors)) {
2847
0
    ws_error("The dissector table %s (%s) is already registered - are you using a buggy plugin?", name, ui_name);
2848
0
  }
2849
9.52k
  return sub_dissectors;
2850
9.52k
}
2851
2852
dissector_table_t register_custom_dissector_table(const char *name,
2853
  const char *ui_name, const int proto, GHashFunc hash_func, GEqualFunc key_equal_func,
2854
  GDestroyNotify key_destroy_func)
2855
176
{
2856
176
  dissector_table_t sub_dissectors;
2857
2858
  /* Create and register the dissector table for this name; returns */
2859
  /* a pointer to the dissector table. */
2860
176
  sub_dissectors = g_slice_new(struct dissector_table);
2861
176
  sub_dissectors->hash_table = g_hash_table_new_full(hash_func,
2862
176
                     key_equal_func,
2863
176
                     key_destroy_func,
2864
176
                     &g_free);
2865
2866
176
  sub_dissectors->dissector_handles = NULL;
2867
176
  sub_dissectors->da_descriptions = NULL;
2868
176
  sub_dissectors->ui_name = ui_name;
2869
176
  sub_dissectors->type    = FT_BYTES; /* Consider key a "blob" of data, no need to really create new type */
2870
176
  sub_dissectors->param   = BASE_NONE;
2871
176
  sub_dissectors->protocol  = (proto == -1) ? NULL : find_protocol_by_id(proto);
2872
  /* Make sure the registration is unique */
2873
176
  if (!g_hash_table_insert(dissector_tables, (void *)name, (void *) sub_dissectors)) {
2874
0
    ws_error("The dissector table %s (%s) is already registered - are you using a buggy plugin?", name, ui_name);
2875
0
  }
2876
176
  return sub_dissectors;
2877
176
}
2878
2879
void
2880
48
register_dissector_table_alias(dissector_table_t dissector_table, const char *alias_name) {
2881
48
  if (!dissector_table || !alias_name) return;
2882
2883
32
  const char *name = NULL;
2884
32
  GList *list = g_hash_table_get_keys(dissector_tables);
2885
6.46k
  for (GList *cur = list; cur; cur = cur->next) {
2886
6.46k
    if (g_hash_table_lookup(dissector_tables, cur->data) == dissector_table) {
2887
32
      name = (const char *) cur->data;
2888
32
      break;
2889
32
    }
2890
6.46k
  }
2891
32
  g_list_free(list);
2892
32
  if (!name) return;
2893
2894
32
  g_hash_table_insert(dissector_table_aliases, (void *) alias_name, (void *) name);
2895
32
}
2896
2897
void
2898
deregister_dissector_table(const char *name)
2899
0
{
2900
0
  dissector_table_t sub_dissectors = (dissector_table_t) g_hash_table_lookup(dissector_tables, name);
2901
0
  if (!sub_dissectors) return;
2902
2903
0
  g_hash_table_remove(dissector_tables, name);
2904
2905
0
  GList *list = g_hash_table_get_keys(dissector_table_aliases);
2906
0
  for (GList *cur = list; cur; cur = cur->next) {
2907
0
    void *alias_name = cur->data;
2908
0
    if (g_hash_table_lookup(dissector_table_aliases, alias_name) == name) {
2909
0
      g_hash_table_remove(dissector_table_aliases, alias_name);
2910
0
    }
2911
0
  }
2912
0
  g_list_free(list);
2913
0
}
2914
2915
const char *
2916
get_dissector_table_ui_name(const char *name)
2917
0
{
2918
0
  dissector_table_t sub_dissectors = find_dissector_table(name);
2919
0
  if (!sub_dissectors) return NULL;
2920
2921
0
  return sub_dissectors->ui_name;
2922
0
}
2923
2924
ftenum_t
2925
get_dissector_table_selector_type(const char *name)
2926
9.69k
{
2927
9.69k
  dissector_table_t sub_dissectors = find_dissector_table(name);
2928
9.69k
  if (!sub_dissectors) return FT_NONE;
2929
2930
9.69k
  return sub_dissectors->type;
2931
9.69k
}
2932
2933
int
2934
get_dissector_table_param(const char *name)
2935
0
{
2936
0
  dissector_table_t sub_dissectors = find_dissector_table(name);
2937
0
  if (!sub_dissectors) return 0;
2938
2939
0
  return sub_dissectors->param;
2940
0
}
2941
2942
static void
2943
check_valid_heur_name_or_fail(const char *heur_name)
2944
7.15k
{
2945
7.15k
  if (proto_check_field_name_lower(heur_name)) {
2946
0
    ws_error("Heuristic Protocol internal name \"%s\" has one or more invalid characters."
2947
0
      " Allowed are lowercase, digits, '-', '_' and non-repeating '.'."
2948
0
      " This might be caused by an inappropriate plugin or a development error.", heur_name);
2949
0
  }
2950
7.15k
}
2951
2952
/* Finds a heuristic dissector table by table name. */
2953
heur_dissector_list_t
2954
find_heur_dissector_list(const char *name)
2955
7.20k
{
2956
7.20k
  return (heur_dissector_list_t)g_hash_table_lookup(heur_dissector_lists, name);
2957
7.20k
}
2958
2959
bool
2960
0
has_heur_dissector_list(const char *name) {
2961
0
  return (find_heur_dissector_list(name) != NULL);
2962
0
}
2963
2964
heur_dtbl_entry_t* find_heur_dissector_by_unique_short_name(const char *short_name)
2965
7.18k
{
2966
7.18k
  return (heur_dtbl_entry_t*)g_hash_table_lookup(heuristic_short_names, short_name);
2967
7.18k
}
2968
2969
void
2970
heur_dissector_add(const char *name, heur_dissector_t dissector, const char *display_name, const char *internal_name, const int proto, heuristic_enable_e enable)
2971
7.15k
{
2972
7.15k
  heur_dissector_list_t  sub_dissectors = find_heur_dissector_list(name);
2973
7.15k
  const char            *proto_name;
2974
7.15k
  heur_dtbl_entry_t     *hdtbl_entry;
2975
7.15k
  GSList                *list_entry;
2976
2977
  /*
2978
   * Make sure the dissector table exists.
2979
   */
2980
7.15k
  if (sub_dissectors == NULL) {
2981
0
    fprintf(stderr, "OOPS: dissector table \"%s\" doesn't exist\n",
2982
0
        name);
2983
0
    proto_name = proto_get_protocol_name(proto);
2984
0
    if (proto_name != NULL) {
2985
0
      fprintf(stderr, "Protocol being registered is \"%s\"\n",
2986
0
          proto_name);
2987
0
    }
2988
0
    if (wireshark_abort_on_dissector_bug)
2989
0
      abort();
2990
0
    return;
2991
0
  }
2992
2993
  /* Verify that sub-dissector is not already in the list */
2994
7.15k
  for (list_entry = sub_dissectors->dissectors;
2995
195k
    list_entry != NULL; list_entry = list_entry->next)
2996
188k
  {
2997
188k
    hdtbl_entry = (heur_dtbl_entry_t *)list_entry->data;
2998
188k
    if ((hdtbl_entry->dissector == dissector) &&
2999
0
      (hdtbl_entry->protocol == find_protocol_by_id(proto)))
3000
0
    {
3001
0
      proto_name = proto_get_protocol_name(proto);
3002
0
      if (proto_name != NULL) {
3003
0
        fprintf(stderr, "Protocol %s is already registered in \"%s\" table\n",
3004
0
            proto_name, name);
3005
0
      }
3006
0
      if (wireshark_abort_on_dissector_bug)
3007
0
        abort();
3008
0
      return;
3009
0
    }
3010
188k
  }
3011
3012
  /* Make sure short_name is "parsing friendly" since it should only be used internally */
3013
7.15k
  check_valid_heur_name_or_fail(internal_name);
3014
3015
7.15k
  hdtbl_entry = g_slice_new(heur_dtbl_entry_t);
3016
7.15k
  hdtbl_entry->dissector = dissector;
3017
7.15k
  hdtbl_entry->protocol  = find_protocol_by_id(proto);
3018
7.15k
  hdtbl_entry->display_name = display_name;
3019
7.15k
  hdtbl_entry->short_name = g_strdup(internal_name);
3020
7.15k
  hdtbl_entry->list_name = g_strdup(name);
3021
7.15k
  hdtbl_entry->enabled   = (enable == HEURISTIC_ENABLE);
3022
7.15k
  hdtbl_entry->enabled_by_default = (enable == HEURISTIC_ENABLE);
3023
3024
  /* do the table insertion */
3025
  /* Ensure short_name is unique */
3026
7.15k
  if (!g_hash_table_insert(heuristic_short_names, (void *)hdtbl_entry->short_name, hdtbl_entry)) {
3027
0
    ws_error("Duplicate heuristic short_name \"%s\"."
3028
0
      " This might be caused by an inappropriate plugin or a development error.", internal_name);
3029
0
  }
3030
3031
7.15k
  sub_dissectors->dissectors = g_slist_prepend(sub_dissectors->dissectors,
3032
7.15k
      (void *)hdtbl_entry);
3033
3034
  /* XXX - could be optimized to pass hdtbl_entry directly */
3035
7.15k
  proto_add_heuristic_dissector(hdtbl_entry->protocol, hdtbl_entry->short_name);
3036
3037
  /* Add the dissector as a dependency
3038
    (some heuristic tables don't have protocol association, so there is
3039
    the need for the NULL check */
3040
7.15k
  if (sub_dissectors->protocol != NULL)
3041
7.15k
    register_depend_dissector(proto_get_protocol_short_name(sub_dissectors->protocol), proto_get_protocol_short_name(hdtbl_entry->protocol));
3042
7.15k
}
3043
3044
3045
3046
static int
3047
16
find_matching_heur_dissector(const void *a, const void *b) {
3048
16
  const heur_dtbl_entry_t *hdtbl_entry_a = (const heur_dtbl_entry_t *) a;
3049
16
  const heur_dtbl_entry_t *hdtbl_entry_b = (const heur_dtbl_entry_t *) b;
3050
3051
16
  return (hdtbl_entry_a->dissector == hdtbl_entry_b->dissector) &&
3052
16
    (hdtbl_entry_a->protocol == hdtbl_entry_b->protocol) ? 0 : 1;
3053
16
}
3054
3055
void
3056
16
heur_dissector_delete(const char *name, heur_dissector_t dissector, const int proto) {
3057
16
  heur_dissector_list_t  sub_dissectors = find_heur_dissector_list(name);
3058
16
  heur_dtbl_entry_t      hdtbl_entry;
3059
16
  GSList                *found_entry;
3060
3061
  /* sanity check */
3062
16
  ws_assert(sub_dissectors != NULL);
3063
3064
16
  hdtbl_entry.dissector = dissector;
3065
16
  hdtbl_entry.protocol  = find_protocol_by_id(proto);
3066
3067
16
  found_entry = g_slist_find_custom(sub_dissectors->dissectors,
3068
16
      (void *) &hdtbl_entry, find_matching_heur_dissector);
3069
3070
16
  if (found_entry) {
3071
0
    heur_dtbl_entry_t *found_hdtbl_entry = (heur_dtbl_entry_t *)(found_entry->data);
3072
0
    proto_add_deregistered_data(found_hdtbl_entry->list_name);
3073
0
    g_hash_table_remove(heuristic_short_names, found_hdtbl_entry->short_name);
3074
0
    proto_add_deregistered_data(found_hdtbl_entry->short_name);
3075
0
    proto_add_deregistered_slice(sizeof(heur_dtbl_entry_t), found_hdtbl_entry);
3076
0
    sub_dissectors->dissectors = g_slist_delete_link(sub_dissectors->dissectors,
3077
0
        found_entry);
3078
0
  }
3079
16
}
3080
3081
bool
3082
dissector_try_heuristic(heur_dissector_list_t sub_dissectors, tvbuff_t *tvb,
3083
      packet_info *pinfo, proto_tree *tree, heur_dtbl_entry_t **heur_dtbl_entry, void *data)
3084
59.5k
{
3085
59.5k
  bool               status;
3086
59.5k
  const char        *saved_curr_proto;
3087
59.5k
  int                saved_proto_layer_num;
3088
59.5k
  const char        *saved_heur_list_name;
3089
59.5k
  GSList            *entry;
3090
59.5k
  GSList            *prev_entry = NULL;
3091
59.5k
  uint16_t           saved_can_desegment;
3092
59.5k
  unsigned           saved_layers_len = 0;
3093
59.5k
  heur_dtbl_entry_t *hdtbl_entry;
3094
59.5k
  int                proto_id;
3095
59.5k
  int                len;
3096
59.5k
  bool               consumed_none;
3097
59.5k
  unsigned           saved_desegment_len;
3098
59.5k
  unsigned           saved_tree_count = tree ? tree->tree_data->count : 0;
3099
3100
  /* can_desegment is set to 2 by anyone which offers this api/service.
3101
     then every time a subdissector is called it is decremented by one.
3102
     thus only the subdissector immediately on top of whoever offers this
3103
     service can use it.
3104
     We save the current value of "can_desegment" for the
3105
     benefit of TCP proxying dissectors such as SOCKS, so they
3106
     can restore it and allow the dissectors they call to use
3107
     the desegmentation service.
3108
  */
3109
59.5k
  saved_can_desegment        = pinfo->can_desegment;
3110
59.5k
  pinfo->saved_can_desegment = saved_can_desegment;
3111
59.5k
  pinfo->can_desegment       = saved_can_desegment-(saved_can_desegment>0);
3112
3113
59.5k
  status      = false;
3114
59.5k
  saved_curr_proto = pinfo->current_proto;
3115
59.5k
  saved_proto_layer_num = pinfo->curr_proto_layer_num;
3116
59.5k
  saved_heur_list_name = pinfo->heur_list_name;
3117
3118
59.5k
  saved_layers_len = wmem_list_count(pinfo->layers);
3119
59.5k
  *heur_dtbl_entry = NULL;
3120
3121
59.5k
  DISSECTOR_ASSERT(saved_layers_len < prefs.gui_max_tree_depth);
3122
3123
602k
  for (entry = sub_dissectors->dissectors; entry != NULL;
3124
552k
      entry = g_slist_next(entry)) {
3125
    /* XXX - why set this now and above? */
3126
552k
    pinfo->can_desegment = saved_can_desegment-(saved_can_desegment>0);
3127
552k
    hdtbl_entry = (heur_dtbl_entry_t *)entry->data;
3128
3129
552k
    if (hdtbl_entry->protocol != NULL &&
3130
552k
      (!proto_is_protocol_enabled(hdtbl_entry->protocol)||(hdtbl_entry->enabled==false))) {
3131
      /*
3132
       * No - don't try this dissector.
3133
       */
3134
116k
      continue;
3135
116k
    }
3136
3137
435k
    if (hdtbl_entry->protocol != NULL) {
3138
435k
      proto_id = proto_get_id(hdtbl_entry->protocol);
3139
      /* do NOT change this behavior - wslua uses the protocol short name set here in order
3140
         to determine which Lua-based heuristic dissector to call */
3141
435k
      pinfo->current_proto =
3142
435k
        proto_get_protocol_short_name(hdtbl_entry->protocol);
3143
3144
      /*
3145
       * Add the protocol name to the layers; we'll remove it
3146
       * if the dissector fails.
3147
       */
3148
435k
      add_layer(pinfo, proto_id);
3149
435k
    }
3150
3151
435k
    pinfo->heur_list_name = hdtbl_entry->list_name;
3152
3153
435k
    saved_desegment_len = pinfo->desegment_len;
3154
435k
    len = (hdtbl_entry->dissector)(tvb, pinfo, tree, data);
3155
435k
    consumed_none = len == 0 || (pinfo->desegment_len != saved_desegment_len && pinfo->desegment_offset == 0);
3156
435k
    if (hdtbl_entry->protocol != NULL &&
3157
425k
      (consumed_none || (tree && saved_tree_count == tree->tree_data->count))) {
3158
      /*
3159
       * We added a protocol layer above. The dissector
3160
       * didn't consume any data or it didn't add any
3161
       * items to the tree so remove it from the list.
3162
       */
3163
831k
      while (wmem_list_count(pinfo->layers) > saved_layers_len) {
3164
        /*
3165
         * Only reduce the layer number if the dissector
3166
         * didn't consume data. Since tree can be NULL on
3167
         * the first pass, we cannot check it or it will
3168
         * break dissectors that rely on a stable value.
3169
         */
3170
415k
        remove_last_layer(pinfo, consumed_none);
3171
415k
      }
3172
415k
    }
3173
435k
    if (len) {
3174
9.42k
      if (ws_log_msg_is_active(WS_LOG_DOMAIN, LOG_LEVEL_DEBUG)) {
3175
0
        ws_debug("Frame: %d | Layers: %s | Dissector: %s\n", pinfo->num, proto_list_layers(pinfo), hdtbl_entry->short_name);
3176
0
      }
3177
3178
9.42k
      *heur_dtbl_entry = hdtbl_entry;
3179
3180
      /* Bubble the matched entry to the top for faster search next time. */
3181
9.42k
      if (prev_entry != NULL) {
3182
4.62k
        sub_dissectors->dissectors = g_slist_remove_link(sub_dissectors->dissectors, entry);
3183
4.62k
        sub_dissectors->dissectors = g_slist_concat(entry, sub_dissectors->dissectors);
3184
4.62k
      }
3185
9.42k
      status = true;
3186
9.42k
      break;
3187
9.42k
    }
3188
425k
    prev_entry = entry;
3189
425k
  }
3190
3191
59.5k
  pinfo->current_proto = saved_curr_proto;
3192
59.5k
  pinfo->curr_proto_layer_num = saved_proto_layer_num;
3193
59.5k
  pinfo->heur_list_name = saved_heur_list_name;
3194
59.5k
  pinfo->can_desegment = saved_can_desegment;
3195
59.5k
  return status;
3196
59.5k
}
3197
3198
typedef struct heur_dissector_foreach_info {
3199
  void *        caller_data;
3200
  DATFunc_heur  caller_func;
3201
  GHFunc        next_func;
3202
  const char   *table_name;
3203
} heur_dissector_foreach_info_t;
3204
3205
/*
3206
 * Called for each entry in a heuristic dissector table.
3207
 */
3208
static void
3209
heur_dissector_table_foreach_func (void *data, void *user_data)
3210
0
{
3211
0
  heur_dissector_foreach_info_t *info;
3212
3213
0
  ws_assert(data);
3214
0
  ws_assert(user_data);
3215
3216
0
  info = (heur_dissector_foreach_info_t *)user_data;
3217
0
  info->caller_func(info->table_name, (heur_dtbl_entry_t *)data,
3218
0
        info->caller_data);
3219
0
}
3220
3221
/*
3222
 * Walk one heuristic dissector table's list calling a user supplied function
3223
 * on each entry.
3224
 */
3225
void
3226
heur_dissector_table_foreach (const char  *table_name,
3227
            DATFunc_heur func,
3228
            void *       user_data)
3229
0
{
3230
0
  heur_dissector_foreach_info_t info;
3231
0
  heur_dissector_list_t         sub_dissectors = find_heur_dissector_list(table_name);
3232
0
  DISSECTOR_ASSERT(sub_dissectors != NULL);
3233
3234
0
  info.table_name    = table_name;
3235
0
  info.caller_func   = func;
3236
0
  info.caller_data   = user_data;
3237
0
  g_slist_foreach(sub_dissectors->dissectors,
3238
0
      heur_dissector_table_foreach_func, &info);
3239
0
}
3240
3241
/*
3242
 * Called for each entry in the table of all heuristic dissector tables.
3243
 */
3244
typedef struct heur_dissector_foreach_table_info {
3245
  void *             caller_data;
3246
  DATFunc_heur_table caller_func;
3247
} heur_dissector_foreach_table_info_t;
3248
3249
/*
3250
 * Called for each entry in the table of all heuristic dissector tables.
3251
 * This is used if we directly process the hash table.
3252
 */
3253
static void
3254
dissector_all_heur_tables_foreach_table_func (void *key, void *value, void *user_data)
3255
0
{
3256
0
  heur_dissector_foreach_table_info_t *info;
3257
3258
0
  info = (heur_dissector_foreach_table_info_t *)user_data;
3259
0
  (*info->caller_func)((char *)key, (struct heur_dissector_list *)value, info->caller_data);
3260
0
}
3261
3262
/*
3263
 * Called for each key in the table of all dissector tables.
3264
 * This is used if we get a list of table names, sort it, and process the list.
3265
 */
3266
static void
3267
dissector_all_heur_tables_foreach_list_func (void *key, void *user_data)
3268
0
{
3269
0
  struct heur_dissector_list          *list;
3270
0
  heur_dissector_foreach_table_info_t *info;
3271
3272
0
  list = (struct heur_dissector_list *)g_hash_table_lookup(heur_dissector_lists, key);
3273
0
  info = (heur_dissector_foreach_table_info_t *)user_data;
3274
0
  (*info->caller_func)((char*)key, list, info->caller_data);
3275
0
}
3276
3277
/*
3278
 * Walk all heuristic dissector tables calling a user supplied function on each
3279
 * table.
3280
 */
3281
void
3282
dissector_all_heur_tables_foreach_table (DATFunc_heur_table func,
3283
           void *             user_data,
3284
           GCompareFunc       compare_key_func)
3285
0
{
3286
0
  heur_dissector_foreach_table_info_t info;
3287
0
  GList *list;
3288
3289
0
  info.caller_data = user_data;
3290
0
  info.caller_func = func;
3291
0
  if (compare_key_func != NULL)
3292
0
  {
3293
0
    list = g_hash_table_get_keys(dissector_tables);
3294
0
    list = g_list_sort(list, compare_key_func);
3295
0
    g_list_foreach(list, dissector_all_heur_tables_foreach_list_func, &info);
3296
0
    g_list_free(list);
3297
0
  }
3298
0
  else
3299
0
  {
3300
0
    g_hash_table_foreach(heur_dissector_lists, dissector_all_heur_tables_foreach_table_func, &info);
3301
0
  }
3302
0
}
3303
3304
static void
3305
display_heur_dissector_table_entries(const char *table_name,
3306
    heur_dtbl_entry_t *hdtbl_entry, void *user_data _U_)
3307
0
{
3308
0
  if (hdtbl_entry->protocol != NULL) {
3309
0
    printf("%s\t%s\t%c\t%c\t%s\t%s\n",
3310
0
           table_name,
3311
0
           proto_get_protocol_filter_name(proto_get_id(hdtbl_entry->protocol)),
3312
0
           (proto_is_protocol_enabled(hdtbl_entry->protocol) && hdtbl_entry->enabled) ? 'T' : 'F',
3313
0
           (proto_is_protocol_enabled_by_default(hdtbl_entry->protocol) && hdtbl_entry->enabled_by_default) ? 'T' : 'F',
3314
0
           hdtbl_entry->short_name,
3315
0
           hdtbl_entry->display_name);
3316
0
  }
3317
0
}
3318
3319
static void
3320
dissector_dump_heur_decodes_display(const char *table_name, struct heur_dissector_list *listptr _U_, void *user_data _U_)
3321
0
{
3322
0
  heur_dissector_table_foreach(table_name, display_heur_dissector_table_entries, NULL);
3323
0
}
3324
3325
/*
3326
 * For each heuristic dissector table, dump list of dissectors (filter_names) for that table
3327
 */
3328
void
3329
dissector_dump_heur_decodes(void)
3330
0
{
3331
0
  dissector_all_heur_tables_foreach_table(dissector_dump_heur_decodes_display, NULL, NULL);
3332
0
}
3333
3334
3335
heur_dissector_list_t
3336
register_heur_dissector_list_with_description(const char *name, const char *ui_name, const int proto)
3337
1.52k
{
3338
1.52k
  heur_dissector_list_t sub_dissectors;
3339
3340
  /* Create and register the dissector table for this name; returns */
3341
  /* a pointer to the dissector table. */
3342
1.52k
  sub_dissectors = g_slice_new(struct heur_dissector_list);
3343
1.52k
  sub_dissectors->protocol  = (proto == -1) ? NULL : find_protocol_by_id(proto);
3344
1.52k
  sub_dissectors->ui_name = ui_name;
3345
1.52k
  sub_dissectors->dissectors = NULL; /* initially empty */
3346
  /* Make sure the registration is unique */
3347
1.52k
  if (!g_hash_table_insert(heur_dissector_lists, (void *)name,
3348
1.52k
          (void *) sub_dissectors)) {
3349
0
    ws_error("The heuristic dissector list %s is already registered - are you using a buggy plugin?", name);
3350
0
  }
3351
1.52k
  return sub_dissectors;
3352
1.52k
}
3353
3354
heur_dissector_list_t
3355
register_heur_dissector_list(const char *name, const int proto)
3356
32
{
3357
32
  return register_heur_dissector_list_with_description(name, NULL, proto);
3358
32
}
3359
3360
void
3361
deregister_heur_dissector_list(const char *name)
3362
0
{
3363
0
  heur_dissector_list_t sub_dissectors = find_heur_dissector_list(name);
3364
0
  if (sub_dissectors == NULL) {
3365
0
    return;
3366
0
  }
3367
3368
0
  g_hash_table_remove(heur_dissector_lists, name);
3369
0
}
3370
3371
const char *
3372
heur_dissector_list_get_description(heur_dissector_list_t list)
3373
0
{
3374
0
  return list ? list->ui_name : NULL;
3375
0
}
3376
3377
/*
3378
 * Register dissectors by name; used if one dissector always calls a
3379
 * particular dissector, or if it bases the decision of which dissector
3380
 * to call on something other than a numerical value or on "try a bunch
3381
 * of dissectors until one likes the packet".
3382
 */
3383
3384
/* Get the long name of the protocol for a dissector handle, if it has
3385
   a protocol. */
3386
const char *
3387
dissector_handle_get_protocol_long_name(const dissector_handle_t handle)
3388
77
{
3389
77
  if (handle == NULL || handle->protocol == NULL) {
3390
0
    return NULL;
3391
0
  }
3392
77
  return proto_get_protocol_long_name(handle->protocol);
3393
77
}
3394
3395
/* Get the short name of the protocol for a dissector handle, if it has
3396
   a protocol. */
3397
const char *
3398
dissector_handle_get_protocol_short_name(const dissector_handle_t handle)
3399
34.4k
{
3400
34.4k
  if (handle == NULL || handle->protocol == NULL) {
3401
16
    return NULL;
3402
16
  }
3403
34.4k
  return proto_get_protocol_short_name(handle->protocol);
3404
34.4k
}
3405
3406
/* Get the description for what the dissector in the dissector handle
3407
   dissects, if it has one. */
3408
const char *
3409
dissector_handle_get_description(const dissector_handle_t handle)
3410
32.7k
{
3411
32.7k
  if (handle == NULL) {
3412
12.0k
    return NULL;
3413
12.0k
  }
3414
20.6k
  return handle->description;
3415
32.7k
}
3416
3417
/* Get the index of the protocol for a dissector handle, if it has
3418
   a protocol. */
3419
int
3420
dissector_handle_get_protocol_index(const dissector_handle_t handle)
3421
11.0k
{
3422
11.0k
  if (handle == NULL || handle->protocol == NULL) {
3423
    /*
3424
     * No protocol (see, for example, the handle for
3425
     * dissecting the set of protocols where the first
3426
     * octet of the payload is an OSI network layer protocol
3427
     * ID).
3428
     */
3429
4
    return -1;
3430
4
  }
3431
11.0k
  return proto_get_id(handle->protocol);
3432
11.0k
}
3433
3434
/* Get a GList of all registered dissector names. The content of the list
3435
   is owned by the hash table and should not be modified or freed.
3436
   Use g_list_free() when done using the list. */
3437
GList*
3438
get_dissector_names(void)
3439
0
{
3440
0
  if (!registered_dissectors) {
3441
0
    return NULL;
3442
0
  }
3443
3444
0
  return g_hash_table_get_keys(registered_dissectors);
3445
0
}
3446
3447
/* Find a registered dissector by name. */
3448
dissector_handle_t
3449
find_dissector(const char *name)
3450
10.1k
{
3451
10.1k
  return (dissector_handle_t)g_hash_table_lookup(registered_dissectors, name);
3452
10.1k
}
3453
3454
/** Find a dissector by name and add parent protocol as a dependency*/
3455
dissector_handle_t find_dissector_add_dependency(const char *name, const int parent_proto)
3456
16.4k
{
3457
16.4k
  dissector_handle_t handle = (dissector_handle_t)g_hash_table_lookup(registered_dissectors, name);
3458
16.4k
  if ((handle != NULL) && (parent_proto > 0))
3459
16.1k
  {
3460
16.1k
    register_depend_dissector(proto_get_protocol_short_name(find_protocol_by_id(parent_proto)), dissector_handle_get_protocol_short_name(handle));
3461
16.1k
  }
3462
3463
16.4k
  return handle;
3464
16.4k
}
3465
3466
/* Get a dissector name from handle. */
3467
const char *
3468
dissector_handle_get_dissector_name(const dissector_handle_t handle)
3469
49.7k
{
3470
49.7k
  if (handle == NULL) {
3471
9
    return NULL;
3472
9
  }
3473
49.7k
  return handle->name;
3474
49.7k
}
3475
3476
const char *
3477
dissector_handle_get_pref_suffix(const dissector_handle_t handle)
3478
11.6k
{
3479
11.6k
  if (handle == NULL) {
3480
0
    return "";
3481
0
  }
3482
11.6k
  return handle->pref_suffix ? handle->pref_suffix : "";
3483
11.6k
}
3484
3485
static void
3486
check_valid_dissector_name_or_fail(const char *name)
3487
47.4k
{
3488
47.4k
  if (proto_check_field_name(name)) {
3489
0
    ws_error("Dissector name \"%s\" has one or more invalid characters."
3490
0
      " Allowed are letters, digits, '-', '_' and non-repeating '.'."
3491
0
      " This might be caused by an inappropriate plugin or a development error.", name);
3492
0
  }
3493
47.4k
}
3494
3495
static dissector_handle_t
3496
new_dissector_handle(const int proto, const char *name, const char *description)
3497
232k
{
3498
232k
  struct dissector_handle *handle;
3499
3500
  /* Make sure name is "parsing friendly" - descriptions should be
3501
   * used for complicated phrases. NULL for anonymous unregistered
3502
   * dissectors is allowed; we check for that in various places.
3503
   *
3504
   * (It might be safer to have a default name used for anonymous
3505
   * dissectors rather than NULL checks scattered in the code.)
3506
   */
3507
232k
  if (name) {
3508
47.4k
    check_valid_dissector_name_or_fail(name);
3509
47.4k
  }
3510
3511
232k
  handle      = wmem_new(wmem_epan_scope(), struct dissector_handle);
3512
232k
  handle->name    = name;
3513
232k
  handle->description = description;
3514
232k
  handle->protocol  = find_protocol_by_id(proto);
3515
232k
  handle->pref_suffix     = NULL;
3516
3517
232k
  if (handle->description == NULL) {
3518
    /*
3519
     * No description for what this dissector dissects
3520
     * was supplied; use the short name for the protocol,
3521
     * if we have the protocol.
3522
     *
3523
     * (We may have no protocol; see, for example, the handle
3524
     * for dissecting the set of protocols where the first
3525
     * octet of the payload is an OSI network layer protocol
3526
     * ID.)
3527
     */
3528
205k
    if (handle->protocol != NULL)
3529
199k
      handle->description = proto_get_protocol_short_name(handle->protocol);
3530
205k
  } else {
3531
27.0k
    if (name && g_strcmp0(name, proto_get_protocol_filter_name(proto)) != 0) {
3532
688
      handle->pref_suffix = ascii_strdown_inplace(wmem_strdup_printf(wmem_epan_scope(), ".%s", name));
3533
688
      char *pos = handle->pref_suffix;
3534
704
      while ((pos = strchr(pos, '-')) != NULL) {
3535
16
        *pos++ = '_';
3536
16
      }
3537
688
    }
3538
27.0k
  }
3539
232k
  return handle;
3540
232k
}
3541
3542
dissector_handle_t
3543
create_dissector_handle_with_name_and_description(dissector_t dissector,
3544
            const int proto,
3545
            const char* name,
3546
            const char* description)
3547
219k
{
3548
219k
  dissector_handle_t handle;
3549
3550
219k
  handle = new_dissector_handle(proto, name, description);
3551
219k
  handle->dissector_type = DISSECTOR_TYPE_SIMPLE;
3552
219k
  handle->dissector_func.dissector_type_simple = dissector;
3553
219k
  handle->dissector_data = NULL;
3554
219k
  return handle;
3555
219k
}
3556
3557
dissector_handle_t
3558
create_dissector_handle_with_name(dissector_t dissector,
3559
        const int proto, const char* name)
3560
36.0k
{
3561
36.0k
  return create_dissector_handle_with_name_and_description(dissector, proto, name, NULL);
3562
36.0k
}
3563
3564
/* Create an anonymous handle for a new dissector. */
3565
dissector_handle_t
3566
create_dissector_handle(dissector_t dissector, const int proto)
3567
156k
{
3568
156k
  return create_dissector_handle_with_name_and_description(dissector, proto, NULL, NULL);
3569
156k
}
3570
3571
static dissector_handle_t
3572
create_dissector_handle_with_name_and_data(dissector_cb_t dissector, const int proto, const char *name, void* cb_data)
3573
12.8k
{
3574
12.8k
  dissector_handle_t handle;
3575
3576
12.8k
  handle = new_dissector_handle(proto, name, NULL);
3577
12.8k
  handle->dissector_type = DISSECTOR_TYPE_CALLBACK;
3578
12.8k
  handle->dissector_func.dissector_type_callback = dissector;
3579
12.8k
  handle->dissector_data = cb_data;
3580
12.8k
  return handle;
3581
12.8k
}
3582
3583
dissector_handle_t
3584
create_dissector_handle_with_data(dissector_cb_t dissector, const int proto, void* cb_data)
3585
2.49k
{
3586
2.49k
  return create_dissector_handle_with_name_and_data(dissector, proto, NULL, cb_data);
3587
2.49k
}
3588
3589
/* Destroy an anonymous handle for a dissector. */
3590
static void
3591
destroy_dissector_handle(dissector_handle_t handle)
3592
0
{
3593
0
  if (handle == NULL) return;
3594
3595
0
  dissector_delete_from_all_tables(handle);
3596
0
  deregister_postdissector(handle);
3597
0
  if (handle->pref_suffix) {
3598
0
    wmem_free(wmem_epan_scope(), handle->pref_suffix);
3599
0
  }
3600
0
  wmem_free(wmem_epan_scope(), handle);
3601
0
}
3602
3603
static dissector_handle_t
3604
register_dissector_handle(const char *name, dissector_handle_t handle)
3605
47.3k
{
3606
47.3k
  bool new_entry;
3607
3608
  /* A registered dissector should have a name. */
3609
47.3k
  if (name == NULL || name[0] == '\0') {
3610
0
    ws_error("A registered dissector name cannot be NULL or the empty string."
3611
0
      " Anonymous dissector handles can be created with create_dissector_handle()."
3612
0
      " This might be caused by an inappropriate plugin or a development error.");
3613
0
  }
3614
3615
47.3k
  new_entry = g_hash_table_insert(registered_dissectors, (void *)name, handle);
3616
47.3k
  if (!new_entry) {
3617
    /* Make sure the registration is unique */
3618
0
    ws_error("dissector handle name \"%s\" is already registered", name);
3619
0
  }
3620
3621
47.3k
  return handle;
3622
47.3k
}
3623
3624
/* Register a new dissector by name. */
3625
dissector_handle_t
3626
register_dissector(const char *name, dissector_t dissector, const int proto)
3627
36.0k
{
3628
36.0k
  dissector_handle_t handle;
3629
3630
36.0k
  handle = create_dissector_handle_with_name(dissector, proto, name);
3631
3632
36.0k
  return register_dissector_handle(name, handle);
3633
36.0k
}
3634
3635
dissector_handle_t
3636
register_dissector_with_description(const char *name, const char *description, dissector_t dissector, const int proto)
3637
896
{
3638
896
  dissector_handle_t handle;
3639
3640
896
  handle = create_dissector_handle_with_name_and_description(dissector, proto, name, description);
3641
3642
896
  return register_dissector_handle(name, handle);
3643
896
}
3644
3645
dissector_handle_t
3646
register_dissector_with_data(const char *name, dissector_cb_t dissector, const int proto, void *cb_data)
3647
10.3k
{
3648
10.3k
  dissector_handle_t handle;
3649
3650
10.3k
  handle = create_dissector_handle_with_name_and_data(dissector, proto, name, cb_data);
3651
3652
10.3k
  return register_dissector_handle(name, handle);
3653
10.3k
}
3654
3655
static bool
3656
remove_depend_dissector_from_list(depend_dissector_list_t sub_dissectors, const char *dependent)
3657
0
{
3658
0
  return g_hash_table_remove(sub_dissectors->dissectors, dependent);
3659
0
}
3660
3661
static void
3662
remove_depend_dissector_ghfunc(void *key _U_, void *value, void *user_data)
3663
0
{
3664
0
  depend_dissector_list_t sub_dissectors = (depend_dissector_list_t) value;
3665
0
  const char *dependent = (const char *)user_data;
3666
3667
0
  remove_depend_dissector_from_list(sub_dissectors, dependent);
3668
0
}
3669
3670
/* Deregister a dissector by name. */
3671
void
3672
deregister_dissector(const char *name)
3673
0
{
3674
0
  dissector_handle_t handle = find_dissector(name);
3675
0
  if (handle == NULL) return;
3676
3677
0
  g_hash_table_remove(registered_dissectors, name);
3678
0
  g_hash_table_remove(depend_dissector_lists, name);
3679
0
  g_hash_table_foreach(depend_dissector_lists, remove_depend_dissector_ghfunc, (void *)name);
3680
3681
0
  destroy_dissector_handle(handle);
3682
0
}
3683
3684
/* Call a dissector through a handle but if the dissector rejected it
3685
 * return 0.
3686
 */
3687
int
3688
call_dissector_only(dissector_handle_t handle, tvbuff_t *tvb,
3689
        packet_info *pinfo, proto_tree *tree, void *data)
3690
1.34M
{
3691
1.34M
  int ret;
3692
3693
1.34M
  DISSECTOR_ASSERT(handle != NULL);
3694
1.34M
  ret = call_dissector_work(handle, tvb, pinfo, tree, true, data);
3695
1.34M
  return ret;
3696
1.34M
}
3697
3698
/* Call a dissector through a handle and if this fails call the "data"
3699
 * dissector.
3700
 */
3701
int
3702
call_dissector_with_data(dissector_handle_t handle, tvbuff_t *tvb,
3703
                   packet_info *pinfo, proto_tree *tree, void *data)
3704
567k
{
3705
567k
  int ret;
3706
3707
567k
  ret = call_dissector_only(handle, tvb, pinfo, tree, data);
3708
567k
  if (ret == 0) {
3709
    /*
3710
     * The protocol was disabled, or the dissector rejected
3711
     * it.  Just dissect this packet as data.
3712
     */
3713
9.80k
    return call_data_dissector(tvb, pinfo, tree);
3714
9.80k
  }
3715
558k
  return ret;
3716
567k
}
3717
3718
int
3719
call_dissector(dissector_handle_t handle, tvbuff_t *tvb,
3720
         packet_info *pinfo, proto_tree *tree)
3721
313k
{
3722
313k
  return call_dissector_with_data(handle, tvb, pinfo, tree, NULL);
3723
313k
}
3724
3725
int
3726
call_data_dissector(tvbuff_t *tvb, packet_info *pinfo, proto_tree *tree)
3727
261k
{
3728
261k
  DISSECTOR_ASSERT(data_handle->protocol != NULL);
3729
261k
  return call_dissector_work(data_handle, tvb, pinfo, tree, true, NULL);
3730
261k
}
3731
3732
/*
3733
 * Call a heuristic dissector through a heur_dtbl_entry
3734
 */
3735
void call_heur_dissector_direct(heur_dtbl_entry_t *heur_dtbl_entry, tvbuff_t *tvb,
3736
  packet_info *pinfo, proto_tree *tree, void *data)
3737
0
{
3738
0
  const char        *saved_curr_proto;
3739
0
  unsigned           saved_proto_layer_num;
3740
0
  const char        *saved_heur_list_name;
3741
0
  uint16_t           saved_can_desegment;
3742
0
  unsigned           saved_layers_len = 0;
3743
3744
0
  DISSECTOR_ASSERT(heur_dtbl_entry);
3745
3746
  /* can_desegment is set to 2 by anyone which offers this api/service.
3747
     then every time a subdissector is called it is decremented by one.
3748
     thus only the subdissector immediately on top of whoever offers this
3749
     service can use it.
3750
     We save the current value of "can_desegment" for the
3751
     benefit of TCP proxying dissectors such as SOCKS, so they
3752
     can restore it and allow the dissectors they call to use
3753
     the desegmentation service.
3754
  */
3755
0
  saved_can_desegment        = pinfo->can_desegment;
3756
0
  pinfo->saved_can_desegment = saved_can_desegment;
3757
0
  pinfo->can_desegment       = saved_can_desegment-(saved_can_desegment>0);
3758
3759
0
  saved_curr_proto = pinfo->current_proto;
3760
0
  saved_proto_layer_num = pinfo->curr_proto_layer_num;
3761
0
  saved_heur_list_name = pinfo->heur_list_name;
3762
3763
0
  saved_layers_len = wmem_list_count(pinfo->layers);
3764
3765
0
  if (!heur_dtbl_entry->enabled ||
3766
0
    (heur_dtbl_entry->protocol != NULL && !proto_is_protocol_enabled(heur_dtbl_entry->protocol))) {
3767
0
    DISSECTOR_ASSERT(data_handle->protocol != NULL);
3768
0
    call_dissector_work(data_handle, tvb, pinfo, tree, true, NULL);
3769
0
    return;
3770
0
  }
3771
3772
0
  if (heur_dtbl_entry->protocol != NULL) {
3773
    /* do NOT change this behavior - wslua uses the protocol short name set here in order
3774
      to determine which Lua-based heuristic dissector to call */
3775
0
    pinfo->current_proto = proto_get_protocol_short_name(heur_dtbl_entry->protocol);
3776
0
    add_layer(pinfo, proto_get_id(heur_dtbl_entry->protocol));
3777
0
  }
3778
3779
0
  pinfo->heur_list_name = heur_dtbl_entry->list_name;
3780
3781
  /* call the dissector, in case of failure call data handle (might happen with exported PDUs) */
3782
0
  if (!(*heur_dtbl_entry->dissector)(tvb, pinfo, tree, data)) {
3783
    /*
3784
     * We added a protocol layer above. The dissector
3785
     * didn't accept the packet or it didn't add any
3786
     * items to the tree so remove it from the list.
3787
     */
3788
0
    while (wmem_list_count(pinfo->layers) > saved_layers_len) {
3789
0
      remove_last_layer(pinfo, true);
3790
0
    }
3791
3792
0
    call_dissector_work(data_handle, tvb, pinfo, tree, true, NULL);
3793
0
  }
3794
3795
  /* XXX: Remove layers if it was accepted but didn't actually consume
3796
   * data due to desegmentation? (Currently the only callers of this
3797
   * are UDP and exported PDUs, so not yet necessary.)
3798
   */
3799
3800
  /* Restore info from caller */
3801
0
  pinfo->can_desegment = saved_can_desegment;
3802
0
  pinfo->current_proto = saved_curr_proto;
3803
0
  pinfo->curr_proto_layer_num = saved_proto_layer_num;
3804
0
  pinfo->heur_list_name = saved_heur_list_name;
3805
3806
0
}
3807
3808
bool register_depend_dissector(const char* parent, const char* dependent)
3809
61.0k
{
3810
61.0k
  depend_dissector_list_t sub_dissectors;
3811
3812
61.0k
  if ((parent == NULL) || (dependent == NULL))
3813
16
  {
3814
    /* XXX - assert on parent? */
3815
16
    return false;
3816
16
  }
3817
3818
61.0k
  sub_dissectors = find_depend_dissector_list(parent);
3819
61.0k
  if (sub_dissectors == NULL) {
3820
    /* parent protocol doesn't exist, create it */
3821
8.25k
    sub_dissectors = g_slice_new(struct depend_dissector_list);
3822
8.25k
    sub_dissectors->dissectors = g_hash_table_new(g_str_hash, g_str_equal); /* initially empty */
3823
8.25k
    g_hash_table_insert(depend_dissector_lists, (void *)g_strdup(parent), (void *) sub_dissectors);
3824
8.25k
  }
3825
3826
  /* Verify that sub-dissector is not already in the list */
3827
61.0k
  g_hash_table_add(sub_dissectors->dissectors, (void *)dependent);
3828
61.0k
  return true;
3829
61.0k
}
3830
3831
bool deregister_depend_dissector(const char* parent, const char* dependent)
3832
0
{
3833
0
  depend_dissector_list_t  sub_dissectors = find_depend_dissector_list(parent);
3834
3835
  /* sanity check */
3836
0
  ws_assert(sub_dissectors != NULL);
3837
3838
0
  return remove_depend_dissector_from_list(sub_dissectors, dependent);
3839
0
}
3840
3841
depend_dissector_list_t find_depend_dissector_list(const char* name)
3842
61.0k
{
3843
61.0k
  return (depend_dissector_list_t)g_hash_table_lookup(depend_dissector_lists, name);
3844
61.0k
}
3845
3846
/*
3847
 * Dumps the "layer type"/"decode as" associations to stdout, similar
3848
 * to the proto_registrar_dump_*() routines.
3849
 *
3850
 * There is one record per line. The fields are tab-delimited.
3851
 *
3852
 * Field 1 = layer type, e.g. "tcp.port"
3853
 * Field 2 = selector - decimal for integer tables, strings for string tables,
3854
 *           blank for payload tables. Custom and GUID tables aren't shown.
3855
 * Field 3 = "decode as" name, e.g. "http"
3856
 *
3857
 * XXX - View -> Internals -> Dissector Tables in the GUI includes the UI name,
3858
 * and separates tables by category. We could add fields for the the UI name
3859
 * and category.
3860
 *
3861
 * The GUI doesn't display FT_NONE (it should) nor FT_GUID tables, but does
3862
 * FT_BYTES (Custom) tables with the handle description name as key.
3863
 * That may or may not be helpful.
3864
 */
3865
3866
3867
static void
3868
dissector_dump_decodes_display(const char *table_name,
3869
             ftenum_t selector_type _U_, void *key, void *value)
3870
0
{
3871
0
  dissector_table_t   sub_dissectors = find_dissector_table(table_name);
3872
0
  dtbl_entry_t       *dtbl_entry;
3873
0
  dissector_handle_t  handle;
3874
0
  int                 proto_id;
3875
0
  const char         *decode_as;
3876
0
  char                fstring[32];
3877
0
  int                 field_width = 0;
3878
3879
0
  ws_assert(sub_dissectors);
3880
3881
0
  dtbl_entry = (dtbl_entry_t *)value;
3882
0
  ws_assert(dtbl_entry);
3883
3884
0
  handle   = dtbl_entry->current;
3885
  /* current might be NULL, if there was an initial value but then
3886
   * set to no handle via Decode As. */
3887
0
  if (!handle)
3888
0
    return;
3889
3890
0
  proto_id = dissector_handle_get_protocol_index(handle);
3891
3892
0
  if (proto_id != -1) {
3893
0
    decode_as = proto_get_protocol_filter_name(proto_id);
3894
0
    ws_assert(decode_as != NULL);
3895
0
    switch (sub_dissectors->type) {
3896
0
      case FT_UINT32:
3897
0
        field_width += 2;
3898
        // fallthrough
3899
0
      case FT_UINT24:
3900
0
        field_width += 2;
3901
        // fallthrough
3902
0
      case FT_UINT16:
3903
0
        field_width += 2;
3904
        // fallthrough
3905
0
      case FT_UINT8:
3906
0
        field_width += 2;
3907
0
        switch (sub_dissectors->param)
3908
0
        {
3909
0
          case BASE_OCT:
3910
0
            snprintf(fstring, 32, "%%s\t0%%o\t%%s\n");
3911
0
            break;
3912
3913
0
          case BASE_HEX:
3914
0
            snprintf(fstring, 32, "%%s\t0x%%0%ux\t%%s\n", field_width);
3915
0
            break;
3916
3917
0
          case BASE_DEC:
3918
0
          default:
3919
0
            snprintf(fstring, 32, "%%s\t%%u\t%%s\n");
3920
0
            break;
3921
0
        };
3922
3923
0
        printf(fstring, table_name, GPOINTER_TO_UINT(key), decode_as);
3924
0
        break;
3925
3926
0
      case FT_STRING:
3927
0
        printf("%s\t%s\t%s\n", table_name, (char*)key, decode_as);
3928
0
        break;
3929
3930
0
      case FT_NONE:
3931
0
        printf("%s\t\t%s\n", table_name, decode_as);
3932
0
        break;
3933
3934
0
      case FT_GUID:
3935
        // We could output something here with the guid_key
3936
0
        break;
3937
3938
0
      case FT_BYTES:
3939
        // View->Internals->Dissector Tables uses the description,
3940
        // but that doesn't tell anything about how the table is
3941
        // configured. (This isn't a list of all possible handles.)
3942
        // Is it useful to output?
3943
0
        break;
3944
3945
0
      default:
3946
0
        break;
3947
0
    }
3948
0
  }
3949
0
}
3950
3951
static int compare_ints(const void *a, const void *b)
3952
0
{
3953
0
  uint32_t inta, intb;
3954
3955
0
  inta = GPOINTER_TO_UINT(a);
3956
0
  intb = GPOINTER_TO_UINT(b);
3957
3958
0
  if (inta < intb)
3959
0
    return -1;
3960
0
  if (inta > intb)
3961
0
    return 1;
3962
0
  return 0;
3963
0
}
3964
3965
static void
3966
dissector_dump_table_decodes(const char *table_name, const char *ui_name _U_, void *user_data _U_)
3967
0
{
3968
0
  dissector_table_t   sub_dissectors = find_dissector_table(table_name);
3969
0
  GList *keys;
3970
3971
0
  ws_assert(sub_dissectors);
3972
0
  keys = g_hash_table_get_keys(sub_dissectors->hash_table);
3973
3974
0
  switch (sub_dissectors->type) {
3975
0
    case FT_UINT8:
3976
0
    case FT_UINT16:
3977
0
    case FT_UINT24:
3978
0
    case FT_UINT32:
3979
0
      keys = g_list_sort(keys, compare_ints);
3980
0
      break;
3981
3982
0
    case FT_STRING:
3983
0
    case FT_STRINGZ:
3984
0
    case FT_UINT_STRING:
3985
0
    case FT_STRINGZPAD:
3986
0
    case FT_STRINGZTRUNC:
3987
0
      keys = g_list_sort(keys, (GCompareFunc)strcmp);
3988
0
      break;
3989
3990
    /* FT_NONE we don't need to sort. We could do something for
3991
     * FT_GUID and FT_BYTES (Custom) if we were to output them,
3992
     * possibly with g_list_sort_with_data.
3993
     */
3994
0
    default:
3995
0
      break;
3996
0
  }
3997
3998
0
  for (GList *entry = g_list_first(keys); entry; entry = entry->next) {
3999
0
    void *key = entry->data;
4000
0
    void *value = g_hash_table_lookup(sub_dissectors->hash_table, key);
4001
0
    dissector_dump_decodes_display(table_name, sub_dissectors->type, key, value);
4002
0
  }
4003
4004
0
  g_list_free(keys);
4005
0
}
4006
4007
void
4008
dissector_dump_decodes(void)
4009
0
{
4010
0
  dissector_all_tables_foreach_table(dissector_dump_table_decodes, NULL, (GCompareFunc)strcmp);
4011
0
}
4012
4013
/*
4014
 * Dumps information about dissector tables to stdout.
4015
 *
4016
 * There is one record per line. The fields are tab-delimited.
4017
 *
4018
 * Field 1 = dissector table name, e.g. "tcp.port"
4019
 * Field 2 = name used for the dissector table in the GUI
4020
 * Field 3 = type (textual representation of the ftenum type)
4021
 * Field 4 = base for display (for integer types)
4022
 * Field 5 = protocol name
4023
 * Field 6 = "decode as" support
4024
 *
4025
 * This does not dump the *individual entries* in the dissector tables,
4026
 * i.e. it doesn't show what dissector handles what particular value
4027
 * of the key in the dissector table.
4028
 */
4029
4030
static void
4031
dissector_dump_dissector_tables_display (void *key, void *user_data _U_)
4032
0
{
4033
0
  const char    *table_name = (const char *)key;
4034
0
  dissector_table_t table;
4035
4036
0
  table = (dissector_table_t)g_hash_table_lookup(dissector_tables, key);
4037
0
  printf("%s\t%s\t%s", table_name, table->ui_name, ftype_name(table->type));
4038
0
  switch (table->type) {
4039
4040
0
  case FT_UINT8:
4041
0
  case FT_UINT16:
4042
0
  case FT_UINT24:
4043
0
  case FT_UINT32:
4044
0
    switch(table->param) {
4045
4046
0
    case BASE_NONE:
4047
0
      printf("\tBASE_NONE");
4048
0
      break;
4049
4050
0
    case BASE_DEC:
4051
0
      printf("\tBASE_DEC");
4052
0
      break;
4053
4054
0
    case BASE_HEX:
4055
0
      printf("\tBASE_HEX");
4056
0
      break;
4057
4058
0
    case BASE_OCT:
4059
0
      printf("\tBASE_OCT");
4060
0
      break;
4061
4062
0
    default:
4063
0
      printf("\t%d", table->param);
4064
0
      break;
4065
0
    }
4066
0
    break;
4067
4068
0
  default:
4069
0
    break;
4070
0
  }
4071
0
  if (table->protocol != NULL) {
4072
0
    printf("\t%s",
4073
0
        proto_get_protocol_short_name(table->protocol));
4074
0
  } else
4075
0
    printf("\t(no protocol)");
4076
0
  printf("\tDecode As %ssupported",
4077
0
      dissector_table_supports_decode_as(table) ? "" : "not ");
4078
0
  printf("\n");
4079
0
}
4080
4081
/** The output format of this function is meant to parallel
4082
 * that of dissector_dump_dissector_tables_display().
4083
 * Field 3 is shown as "heuristic".
4084
 * Field 4 is omitted, as it is for FT_STRING dissector tables above.
4085
 * Field 6 is omitted since "Decode As" doesn't apply.
4086
 */
4087
4088
static void
4089
dissector_dump_heur_dissector_tables_display (void *key, void *user_data _U_)
4090
0
{
4091
0
  const char    *list_name = (const char *)key;
4092
0
  heur_dissector_list_t list;
4093
4094
0
  list = (heur_dissector_list_t)g_hash_table_lookup(heur_dissector_lists, key);
4095
0
  printf("%s\t%s\theuristic", list_name, list->ui_name ? list->ui_name : list_name);
4096
4097
0
  if (list->protocol != NULL) {
4098
0
    printf("\t%s",
4099
0
        proto_get_protocol_short_name(list->protocol));
4100
0
  } else
4101
0
    printf("\t(no protocol)");
4102
0
  printf("\n");
4103
0
}
4104
4105
static int
4106
compare_dissector_key_name(const void *dissector_a, const void *dissector_b)
4107
0
{
4108
0
  return strcmp((const char*)dissector_a, (const char*)dissector_b);
4109
0
}
4110
4111
void
4112
dissector_dump_dissector_tables(void)
4113
0
{
4114
0
  GList *list;
4115
4116
0
  list = g_hash_table_get_keys(dissector_tables);
4117
0
  list = g_list_sort(list, compare_dissector_key_name);
4118
0
  g_list_foreach(list, dissector_dump_dissector_tables_display, NULL);
4119
0
  g_list_free(list);
4120
4121
0
  list = g_hash_table_get_keys(heur_dissector_lists);
4122
0
  list = g_list_sort(list, compare_dissector_key_name);
4123
0
  g_list_foreach(list, dissector_dump_heur_dissector_tables_display, NULL);
4124
0
  g_list_free(list);
4125
0
}
4126
4127
/*
4128
 * Dumps the entries in the table of registered dissectors.
4129
 *
4130
 * There is one record per line. The fields are tab-delimited.
4131
 *
4132
 * Field 1 = dissector name
4133
 * Field 2 = dissector description
4134
 */
4135
4136
struct dissector_info {
4137
  const char *name;
4138
  const char *description;
4139
};
4140
4141
static int
4142
compare_dissector_info_names(const void *arg1, const void *arg2)
4143
0
{
4144
0
  const struct dissector_info *info1 = (const struct dissector_info *) arg1;
4145
0
  const struct dissector_info *info2 = (const struct dissector_info *) arg2;
4146
4147
0
  return strcmp(info1->name, info2->name);
4148
0
}
4149
4150
void
4151
dissector_dump_dissectors(void)
4152
0
{
4153
0
  GHashTableIter iter;
4154
0
  struct dissector_info *dissectors_info;
4155
0
  unsigned num_protocols;
4156
0
  void *key, *value;
4157
0
  unsigned proto_index;
4158
4159
0
  g_hash_table_iter_init(&iter, registered_dissectors);
4160
0
  num_protocols = g_hash_table_size(registered_dissectors);
4161
0
  dissectors_info = g_new(struct dissector_info, num_protocols);
4162
0
  proto_index = 0;
4163
0
  while (g_hash_table_iter_next(&iter, &key, &value)) {
4164
0
    dissectors_info[proto_index].name = (const char *)key;
4165
0
    dissectors_info[proto_index].description =
4166
0
        ((dissector_handle_t) value)->description;
4167
0
    proto_index++;
4168
0
  }
4169
0
  qsort(dissectors_info, num_protocols, sizeof(struct dissector_info),
4170
0
      compare_dissector_info_names);
4171
0
  for (proto_index = 0; proto_index < num_protocols; proto_index++) {
4172
0
    printf("%s\t%s\n", dissectors_info[proto_index].name,
4173
0
        dissectors_info[proto_index].description);
4174
0
  }
4175
0
  g_free(dissectors_info);
4176
0
}
4177
4178
void
4179
register_postdissector(dissector_handle_t handle)
4180
64
{
4181
64
  postdissector p;
4182
4183
64
  p.handle = handle;
4184
64
  p.wanted_hfids = NULL;
4185
64
  postdissectors = g_array_append_val(postdissectors, p);
4186
64
}
4187
4188
void
4189
set_postdissector_wanted_hfids(dissector_handle_t handle, GArray *wanted_hfids)
4190
0
{
4191
0
  unsigned i;
4192
4193
0
  if (!postdissectors) return;
4194
4195
0
  for (i = 0; i < postdissectors->len; i++) {
4196
0
    if (POSTDISSECTORS(i).handle == handle) {
4197
0
      if (POSTDISSECTORS(i).wanted_hfids) {
4198
0
        g_array_free(POSTDISSECTORS(i).wanted_hfids, true);
4199
0
      }
4200
0
      POSTDISSECTORS(i).wanted_hfids = wanted_hfids;
4201
0
      break;
4202
0
    }
4203
0
  }
4204
0
}
4205
4206
void
4207
deregister_postdissector(dissector_handle_t handle)
4208
0
{
4209
0
  unsigned i;
4210
4211
0
  if (!postdissectors) return;
4212
4213
0
  for (i = 0; i < postdissectors->len; i++) {
4214
0
    if (POSTDISSECTORS(i).handle == handle) {
4215
0
      if (POSTDISSECTORS(i).wanted_hfids) {
4216
0
        g_array_free(POSTDISSECTORS(i).wanted_hfids, true);
4217
0
      }
4218
0
      postdissectors = g_array_remove_index_fast(postdissectors, i);
4219
0
      break;
4220
0
    }
4221
0
  }
4222
0
}
4223
4224
bool
4225
have_postdissector(void)
4226
191k
{
4227
191k
  unsigned i;
4228
191k
  dissector_handle_t handle;
4229
4230
764k
  for (i = 0; i < postdissectors->len; i++) {
4231
764k
    handle = POSTDISSECTORS(i).handle;
4232
4233
764k
    if (handle->protocol != NULL
4234
764k
        && proto_is_protocol_enabled(handle->protocol)) {
4235
      /* We have at least one enabled postdissector */
4236
191k
      return true;
4237
191k
    }
4238
764k
  }
4239
0
  return false;
4240
191k
}
4241
4242
void
4243
call_all_postdissectors(tvbuff_t *tvb, packet_info *pinfo, proto_tree *tree)
4244
191k
{
4245
191k
  unsigned i;
4246
4247
956k
  for (i = 0; i < postdissectors->len; i++) {
4248
764k
    call_dissector_only(POSTDISSECTORS(i).handle,
4249
764k
            tvb, pinfo, tree, NULL);
4250
764k
  }
4251
191k
}
4252
4253
bool
4254
postdissectors_want_hfids(void)
4255
0
{
4256
0
  unsigned i;
4257
4258
0
  for (i = 0; i < postdissectors->len; i++) {
4259
0
    if (POSTDISSECTORS(i).wanted_hfids != NULL &&
4260
0
        POSTDISSECTORS(i).wanted_hfids->len != 0 &&
4261
0
        (POSTDISSECTORS(i).handle->protocol == NULL ||
4262
0
         proto_is_protocol_enabled(POSTDISSECTORS(i).handle->protocol)))
4263
0
      return true;
4264
0
  }
4265
0
  return false;
4266
0
}
4267
4268
void
4269
prime_epan_dissect_with_postdissector_wanted_hfids(epan_dissect_t *edt)
4270
191k
{
4271
191k
  unsigned i;
4272
4273
191k
  if (postdissectors == NULL) {
4274
    /*
4275
     * No postdissector expressed an interest in any hfids.
4276
     */
4277
0
    return;
4278
0
  }
4279
956k
  for (i = 0; i < postdissectors->len; i++) {
4280
764k
    if (POSTDISSECTORS(i).wanted_hfids != NULL &&
4281
0
        POSTDISSECTORS(i).wanted_hfids->len != 0 &&
4282
0
        (POSTDISSECTORS(i).handle->protocol == NULL ||
4283
0
         proto_is_protocol_enabled(POSTDISSECTORS(i).handle->protocol)))
4284
0
      epan_dissect_prime_with_hfid_array(edt,
4285
0
          POSTDISSECTORS(i).wanted_hfids);
4286
764k
  }
4287
191k
}
4288
4289
void
4290
3.45M
increment_dissection_depth_by_n(packet_info *pinfo, unsigned n) {
4291
3.45M
  DISSECTOR_ASSERT_HINT(!ckd_add(&pinfo->dissection_depth, pinfo->dissection_depth, n),
4292
3.45M
    "pinfo->dissection_depth overflowed.");
4293
3.45M
  DISSECTOR_ASSERT(pinfo->dissection_depth < prefs.gui_max_tree_depth);
4294
3.45M
}
4295
4296
void
4297
3.03M
increment_dissection_depth(packet_info *pinfo) {
4298
3.03M
  increment_dissection_depth_by_n(pinfo, 1);
4299
3.03M
}
4300
4301
void
4302
3.26M
decrement_dissection_depth_by_n(packet_info *pinfo, unsigned n) {
4303
3.26M
  DISSECTOR_ASSERT_HINT(!ckd_sub(&pinfo->dissection_depth, pinfo->dissection_depth, n),
4304
3.26M
    "pinfo->dissection_depth underflowed.");
4305
3.26M
}
4306
4307
void
4308
2.87M
decrement_dissection_depth(packet_info *pinfo) {
4309
2.87M
  decrement_dissection_depth_by_n(pinfo, 1);
4310
2.87M
}
4311
4312
/*
4313
 * Editor modelines  -  https://www.wireshark.org/tools/modelines.html
4314
 *
4315
 * Local variables:
4316
 * c-basic-offset: 8
4317
 * tab-width: 8
4318
 * indent-tabs-mode: t
4319
 * End:
4320
 *
4321
 * vi: set shiftwidth=8 tabstop=8 noexpandtab:
4322
 * :indentSize=8:tabSize=8:noTabs=false:
4323
 */