3 * Wireshark - Network traffic analyzer
4 * By Gerald Combs <gerald@wireshark.org>
5 * Copyright 1998 Gerald Combs
7 * This program is free software; you can redistribute it and/or
8 * modify it under the terms of the GNU General Public License
9 * as published by the Free Software Foundation; either version 2
10 * of the License, or (at your option) any later version.
12 * This program is distributed in the hope that it will be useful,
13 * but WITHOUT ANY WARRANTY; without even the implied warranty of
14 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
15 * GNU General Public License for more details.
17 * You should have received a copy of the GNU General Public License
18 * along with this program; if not, write to the Free Software
19 * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
24 #ifdef HAVE_NETINET_IN_H
25 # include <netinet/in.h> /* needed for <arpa/inet.h> on some platforms */
28 #ifdef HAVE_ARPA_INET_H
29 #include <arpa/inet.h>
32 #ifdef HAVE_SYS_SOCKET_H
33 #include <sys/socket.h> /* needed to define AF_ values on UNIX */
36 #include <string.h> /* for memcmp */
38 #include "address_types.h"
40 #include "to_str-int.h"
41 #include "addr_resolv.h"
42 #include "wsutil/pint.h"
43 #include "wsutil/str_util.h"
44 #include "wsutil/inet_v6defs.h"
46 #include <epan/dissectors/packet-mtp3.h>
48 struct _address_type_t {
49 int addr_type; /* From address_type enumeration or registered value */
51 const char *pretty_name;
52 AddrValueToString addr_to_str;
53 AddrValueToStringLen addr_str_len;
54 AddrColFilterString addr_col_filter;
55 AddrFixedLen addr_fixed_len;
57 /* XXX - Some sort of compare functions (like ftype)? ***/
58 /* XXX - Include functions for name resolution? ***/
61 #define MAX_DISSECTOR_ADDR_TYPE 20
62 #define MAX_ADDR_TYPE_VALUE (AT_END_OF_LIST+MAX_DISSECTOR_ADDR_TYPE)
64 static int num_dissector_addr_type;
65 static address_type_t dissector_type_addresses[MAX_DISSECTOR_ADDR_TYPE];
67 /* Keep track of address_type_t's via their id number */
68 static address_type_t* type_list[MAX_ADDR_TYPE_VALUE];
71 * If a user _does_ pass in a too-small buffer, this is probably
72 * going to be too long to fit. However, even a partial string
73 * starting with "[Buf" should provide enough of a clue to be
76 #define BUF_TOO_SMALL_ERR "[Buffer too small]"
78 static void address_type_register(int addr_type, address_type_t *at)
81 g_assert(addr_type < MAX_ADDR_TYPE_VALUE);
82 g_assert(addr_type == at->addr_type);
84 /* Don't re-register. */
85 g_assert(type_list[addr_type] == NULL);
87 type_list[addr_type] = at;
90 int address_type_dissector_register(const char* name, const char* pretty_name,
91 AddrValueToString to_str_func, AddrValueToStringLen str_len_func,
92 AddrColFilterString col_filter_str_func, AddrFixedLen fixed_len_func)
96 /* Ensure valid data/functions for required fields */
97 DISSECTOR_ASSERT(name);
98 DISSECTOR_ASSERT(pretty_name);
99 DISSECTOR_ASSERT(to_str_func);
100 DISSECTOR_ASSERT(str_len_func);
102 /* This shouldn't happen, so flag it for fixing */
103 DISSECTOR_ASSERT(num_dissector_addr_type < MAX_DISSECTOR_ADDR_TYPE);
105 addr_type = AT_END_OF_LIST+num_dissector_addr_type;
106 dissector_type_addresses[num_dissector_addr_type].addr_type = addr_type;
107 dissector_type_addresses[num_dissector_addr_type].name = name;
108 dissector_type_addresses[num_dissector_addr_type].pretty_name = pretty_name;
109 dissector_type_addresses[num_dissector_addr_type].addr_to_str = to_str_func;
110 dissector_type_addresses[num_dissector_addr_type].addr_str_len = str_len_func;
111 dissector_type_addresses[num_dissector_addr_type].addr_col_filter = col_filter_str_func;
112 dissector_type_addresses[num_dissector_addr_type].addr_fixed_len = fixed_len_func;
114 type_list[addr_type] = &dissector_type_addresses[num_dissector_addr_type];
116 num_dissector_addr_type++;
121 /******************************************************************************
123 ******************************************************************************/
124 gboolean none_addr_to_str(const address* addr _U_, gchar *buf, int buf_len _U_)
130 int none_addr_str_len(const address* addr _U_)
132 return 1; /* NULL character for empty string */
135 int none_addr_len(void)
140 /******************************************************************************
142 ******************************************************************************/
143 gboolean ether_to_str(const address* addr, gchar *buf, int buf_len _U_)
145 bytes_to_hexstr_punct(buf, (const guint8*)addr->data, 6, ':');
150 int ether_str_len(const address* addr _U_)
155 static const char* ether_col_filter_str(const address* addr _U_, gboolean is_src)
168 /******************************************************************************
170 ******************************************************************************/
171 static gboolean ipv4_to_str(const address* addr, gchar *buf, int buf_len)
173 ip_to_str_buf((const guint8*)addr->data, buf, buf_len);
177 static int ipv4_str_len(const address* addr _U_)
179 return MAX_IP_STR_LEN;
182 static const char* ipv4_col_filter_str(const address* addr _U_, gboolean is_src)
190 static int ipv4_len(void)
195 /******************************************************************************
197 ******************************************************************************/
199 * inet_ntop6(src, dst, size)
200 * convert IPv6 binary address into presentation (printable) format
205 ip6_to_str_buf_len(const guchar* src, char *buf, size_t buf_len)
207 struct { int base, len; } best, cur;
211 if (buf_len < MAX_IP6_STR_LEN) { /* buf_len < 40 */
212 g_strlcpy(buf, BUF_TOO_SMALL_ERR, buf_len); /* Let the unexpected value alert user */
218 * Copy the input (bytewise) array into a wordwise array.
219 * Find the longest run of 0x00's in src[] for :: shorthanding.
221 for (i = 0; i < 16; i += 2) {
222 words[i / 2] = (src[i+1] << 0);
223 words[i / 2] |= (src[i] << 8);
225 best.base = -1; best.len = 0;
226 cur.base = -1; cur.len = 0;
227 for (i = 0; i < 8; i++) {
229 if (cur.base == -1) {
235 if (cur.base != -1) {
236 if (best.base == -1 || cur.len > best.len)
242 if (cur.base != -1) {
243 if (best.base == -1 || cur.len > best.len)
246 if (best.base != -1 && best.len < 2)
249 /* Is this address an encapsulated IPv4? */
251 * Orginal code dated 1996 uses ::/96 as a valid IPv4-compatible addresses
252 * but since Feb 2006 ::/96 is deprecated one.
253 * Quoting wikipedia [0]:
254 * > The 96-bit zero-value prefix ::/96, originally known as IPv4-compatible
255 * > addresses, was mentioned in 1995[35] but first described in 1998.[41]
256 * > This class of addresses was used to represent IPv4 addresses within
257 * > an IPv6 transition technology. Such an IPv6 address has its first
258 * > (most significant) 96 bits set to zero, while its last 32 bits are the
259 * > IPv4 address that is represented.
260 * > In February 2006 the Internet Engineering Task Force (IETF) has deprecated
261 * > the use of IPv4-compatible addresses.[1] The only remaining use of this address
262 * > format is to represent an IPv4 address in a table or database with fixed size
263 * > members that must also be able to store an IPv6 address.
265 * If needed it can be fixed by changing next line:
266 * if (best.base == 0 && (best.len == 6 || (best.len == 5 && words[5] == 0xffff)))
268 * if (best.base == 0 && best.len == 5 && words[5] == 0xffff)
270 * [0] http://en.wikipedia.org/wiki/IPv6_address#Historical_notes
273 if (best.base == 0 && (best.len == 6 || (best.len == 5 && words[5] == 0xffff)))
275 /* best.len == 6 -> ::IPv4; 5 -> ::ffff:IPv4 */
276 buf = g_stpcpy(buf, "::");
278 buf = g_stpcpy(buf, "ffff:");
279 ip_to_str_buf(src + 12, buf, MAX_IP_STR_LEN);
280 /* max: 2 + 5 + 16 == 23 bytes */
287 for (i = 0; i < 8; i++) {
288 /* Are we inside the best run of 0x00's? */
289 if (i == best.base) {
293 /* Was it a trailing run of 0x00's? */
299 /* Are we following an initial run of 0x00s or any real hex? */
303 buf = word_to_hex_npad(buf, words[i]); /* max: 4B */
304 /* max: 8 * 4 + 7 == 39 bytes */
306 *buf = '\0'; /* 40 byte */
310 ip6_to_str_buf(const struct e_in6_addr *ad, gchar *buf)
312 ip6_to_str_buf_len((const guchar*)ad, buf, MAX_IP6_STR_LEN);
315 static gboolean ipv6_to_str(const address* addr, gchar *buf, int buf_len)
317 ip6_to_str_buf_len((const guchar*)addr->data, buf, buf_len);
321 static int ipv6_str_len(const address* addr _U_)
323 return MAX_IP6_STR_LEN;
326 static const char* ipv6_col_filter_str(const address* addr _U_, gboolean is_src)
334 static int ipv6_len(void)
339 /******************************************************************************
341 ******************************************************************************/
342 static gboolean ipx_to_str(const address* addr, gchar *buf, int buf_len _U_)
344 const guint8 *addrdata = (const guint8 *)addr->data;
346 buf = bytes_to_hexstr(buf, &addrdata[0], 4); /* 8 bytes */
347 *buf++ = '.'; /*1 byte */
348 buf = bytes_to_hexstr(buf, &addrdata[4], 6); /* 12 bytes */
349 *buf++ = '\0'; /* NULL terminate */
353 static int ipx_str_len(const address* addr _U_)
358 static int ipx_len(void)
363 /******************************************************************************
365 * XXX - This functionality should really be in packet-vines.c as a dissector
366 * address type, but need to resolve "address type" as "field type"
367 ******************************************************************************/
368 static gboolean vines_to_str(const address* addr, gchar *buf, int buf_len _U_)
370 const guint8 *addr_data = (const guint8 *)addr->data;
372 buf = dword_to_hex(buf, pntoh32(&addr_data[0])); /* 8 bytes */
373 *buf++ = '.'; /* 1 byte */
374 buf = word_to_hex(buf, pntoh16(&addr_data[4])); /* 4 bytes */
375 *buf = '\0'; /* NULL terminate */
380 static int vines_str_len(const address* addr _U_)
385 static int vines_len(void)
387 return VINES_ADDR_LEN;
390 /******************************************************************************
392 ******************************************************************************/
393 static gboolean fc_to_str(const address* addr, gchar *buf, int buf_len _U_)
395 buf = bytes_to_hexstr_punct(buf, (const guint8 *)addr->data, 3, '.');
396 *buf = '\0'; /* NULL terminate */
401 static int fc_str_len(const address* addr _U_)
406 static int fc_len(void)
411 /******************************************************************************
413 * XXX - Doubles as a "field type", should it be defined here?
414 * XXX - currently this has some address resolution worked into the "base" string
415 ******************************************************************************/
416 /* FC Network Header Network Address Authority Identifiers */
417 #define FC_NH_NAA_IEEE 1 /* IEEE 802.1a */
418 #define FC_NH_NAA_IEEE_E 2 /* IEEE Exteneded */
419 #define FC_NH_NAA_LOCAL 3
420 #define FC_NH_NAA_IP 4 /* 32-bit IP address */
421 #define FC_NH_NAA_IEEE_R 5 /* IEEE Registered */
422 #define FC_NH_NAA_IEEE_R_E 6 /* IEEE Registered Exteneded */
423 /* according to FC-PH 3 draft these are now reclaimed and reserved */
424 #define FC_NH_NAA_CCITT_INDV 12 /* CCITT 60 bit individual address */
425 #define FC_NH_NAA_CCITT_GRP 14 /* CCITT 60 bit group address */
427 static gboolean fcwwn_to_str(const address* addr, gchar *buf, int buf_len)
429 const guint8 *addrp = (const guint8*)addr->data;
434 if (buf_len < 200) { /* This is mostly for manufacturer name */
435 g_strlcpy(buf, BUF_TOO_SMALL_ERR, buf_len); /* Let the unexpected value alert user */
439 ethptr = bytes_to_hexstr_punct(buf, addrp, 8, ':'); /* 23 bytes */
440 fmt = (addrp[0] & 0xF0) >> 4;
444 case FC_NH_NAA_IEEE_E:
445 memcpy (oui, &addrp[2], 6);
447 g_snprintf (ethptr, buf_len-23, " (%s)", get_manuf_name(oui));
450 case FC_NH_NAA_IEEE_R:
451 oui[0] = ((addrp[0] & 0x0F) << 4) | ((addrp[1] & 0xF0) >> 4);
452 oui[1] = ((addrp[1] & 0x0F) << 4) | ((addrp[2] & 0xF0) >> 4);
453 oui[2] = ((addrp[2] & 0x0F) << 4) | ((addrp[3] & 0xF0) >> 4);
454 oui[3] = ((addrp[3] & 0x0F) << 4) | ((addrp[4] & 0xF0) >> 4);
455 oui[4] = ((addrp[4] & 0x0F) << 4) | ((addrp[5] & 0xF0) >> 4);
456 oui[5] = ((addrp[5] & 0x0F) << 4) | ((addrp[6] & 0xF0) >> 4);
458 g_snprintf (ethptr, buf_len-23, " (%s)", get_manuf_name(oui));
469 static int fcwwn_str_len(const address* addr _U_)
474 static int fcwwn_len(void)
476 return FCWWN_ADDR_LEN;
479 /******************************************************************************
481 * XXX - This should really be a dissector address type as its address string
482 * is partially determined by a dissector preference.
483 ******************************************************************************/
484 static gboolean ss7pc_to_str(const address* addr, gchar *buf, int buf_len)
486 mtp3_addr_to_str_buf((const mtp3_addr_pc_t *)addr->data, buf, buf_len);
490 static int ss7pc_str_len(const address* addr _U_)
495 /******************************************************************************
497 ******************************************************************************/
498 static gboolean stringz_addr_to_str(const address* addr, gchar *buf, int buf_len)
500 g_strlcpy(buf, (const gchar *)addr->data, buf_len);
504 static int stringz_addr_str_len(const address* addr)
509 /******************************************************************************
511 ******************************************************************************/
512 static gboolean eui64_addr_to_str(const address* addr, gchar *buf, int buf_len _U_)
514 buf = bytes_to_hexstr_punct(buf, (const guint8 *)addr->data, 8, ':');
515 *buf = '\0'; /* NULL terminate */
519 static int eui64_str_len(const address* addr _U_)
521 return EUI64_STR_LEN;
524 static int eui64_len(void)
529 /******************************************************************************
531 ******************************************************************************/
533 ib_addr_to_str( const address *addr, gchar *buf, int buf_len){
534 if (addr->len >= 16) { /* GID is 128bits */
535 #define PREAMBLE_STR_LEN ((int)(sizeof("GID: ") - 1))
536 g_strlcpy(buf, "GID: ", buf_len);
537 if (buf_len < PREAMBLE_STR_LEN ||
538 inet_ntop(AF_INET6, addr->data, buf + PREAMBLE_STR_LEN,
539 buf_len - PREAMBLE_STR_LEN) == NULL ) /* Returns NULL if no space and does not touch buf */
540 g_strlcpy(buf, BUF_TOO_SMALL_ERR, buf_len); /* Let the unexpected value alert user */
541 } else { /* this is a LID (16 bits) */
544 memcpy((void *)&lid_number, addr->data, sizeof lid_number);
545 g_snprintf(buf,buf_len,"LID: %u",lid_number);
551 static int ib_str_len(const address* addr _U_)
553 return MAX_ADDR_STR_LEN; /* XXX - This is overkill */
556 /******************************************************************************
558 * XXX - This functionality should really be in packet-usb.c as a dissector
559 * address type, but currently need support of AT_USB in conversation_table.c
560 ******************************************************************************/
561 static gboolean usb_addr_to_str(const address* addr, gchar *buf, int buf_len _U_)
563 const guint8 *addrp = (const guint8 *)addr->data;
565 if(pletoh32(&addrp[0])==0xffffffff){
566 g_strlcpy(buf, "host", buf_len);
568 g_snprintf(buf, buf_len, "%d.%d.%d", pletoh16(&addrp[8]),
569 pletoh32(&addrp[0]), pletoh32(&addrp[4]));
575 static int usb_addr_str_len(const address* addr _U_)
580 /******************************************************************************
582 ******************************************************************************/
583 static gboolean ax25_addr_to_str(const address* addr, gchar *buf, int buf_len _U_)
585 const guint8 *addrdata = (const guint8 *)addr->data;
587 *buf++ = printable_char_or_period(addrdata[0] >> 1);
588 *buf++ = printable_char_or_period(addrdata[1] >> 1);
589 *buf++ = printable_char_or_period(addrdata[2] >> 1);
590 *buf++ = printable_char_or_period(addrdata[3] >> 1);
591 *buf++ = printable_char_or_period(addrdata[4] >> 1);
592 *buf++ = printable_char_or_period(addrdata[5] >> 1);
594 buf = uint_to_str_back(buf, (addrdata[6] >> 1) & 0x0f);
595 *buf = '\0'; /* NULL terminate */
600 static int ax25_addr_str_len(const address* addr _U_)
602 return 21; /* Leaves extra space (10 bytes) just for uint_to_str_back() */
605 static const char* ax25_col_filter_str(const address* addr _U_, gboolean is_src)
613 static int ax25_len(void)
615 return AX25_ADDR_LEN;
618 /******************************************************************************
619 * END OF PROVIDED ADDRESS TYPES
620 ******************************************************************************/
625 void address_types_initialize(void)
627 static address_type_t none_address = {
628 AT_NONE, /* addr_type */
629 "AT_NONE", /* name */
630 "No address", /* pretty_name */
631 none_addr_to_str, /* addr_to_str */
632 none_addr_str_len, /* addr_str_len */
633 NULL, /* addr_col_filter */
634 none_addr_len /* addr_fixed_len */
637 static address_type_t ether_address = {
638 AT_ETHER, /* addr_type */
639 "AT_ETHER", /* name */
640 "Ethernet address", /* pretty_name */
641 ether_to_str, /* addr_to_str */
642 ether_str_len, /* addr_str_len */
643 ether_col_filter_str, /* addr_col_filter */
644 ether_len /* addr_fixed_len */
647 static address_type_t ipv4_address = {
648 AT_IPv4, /* addr_type */
649 "AT_IPv4", /* name */
650 "IPv4 address", /* pretty_name */
651 ipv4_to_str, /* addr_to_str */
652 ipv4_str_len, /* addr_str_len */
653 ipv4_col_filter_str, /* addr_col_filter */
654 ipv4_len /* addr_fixed_len */
657 static address_type_t ipv6_address = {
658 AT_IPv6, /* addr_type */
659 "AT_IPv6", /* name */
660 "IPv6 address", /* pretty_name */
661 ipv6_to_str, /* addr_to_str */
662 ipv6_str_len, /* addr_str_len */
663 ipv6_col_filter_str, /* addr_col_filter */
664 ipv6_len /* addr_fixed_len */
667 static address_type_t ipx_address = {
668 AT_IPX, /* addr_type */
670 "IPX address", /* pretty_name */
671 ipx_to_str, /* addr_to_str */
672 ipx_str_len, /* addr_str_len */
673 NULL, /* addr_col_filter */
674 ipx_len /* addr_fixed_len */
677 static address_type_t vines_address = {
678 AT_VINES, /* addr_type */
679 "AT_VINES", /* name */
680 "Banyan Vines address", /* pretty_name */
681 vines_to_str, /* addr_to_str */
682 vines_str_len, /* addr_str_len */
683 NULL, /* addr_col_filter */
684 vines_len /*addr_fixed_len */
687 static address_type_t fc_address = {
688 AT_FC, /* addr_type */
690 "FC address", /* pretty_name */
691 fc_to_str, /* addr_to_str */
692 fc_str_len, /* addr_str_len */
693 NULL, /* addr_col_filter */
694 fc_len /*addr_fixed_len */
697 static address_type_t fcwwn_address = {
698 AT_FCWWN, /* addr_type */
699 "AT_FCWWN", /* name */
700 "Fibre Channel WWN", /* pretty_name */
701 fcwwn_to_str, /* addr_to_str */
702 fcwwn_str_len, /* addr_str_len */
703 NULL, /* addr_col_filter */
704 fcwwn_len /* addr_fixed_len */
707 static address_type_t ss7pc_address = {
708 AT_SS7PC, /* addr_type */
709 "AT_SS7PC", /* name */
710 "SS7 Point Code", /* pretty_name */
711 ss7pc_to_str, /* addr_to_str */
712 ss7pc_str_len, /* addr_str_len */
713 NULL, /* addr_col_filter */
714 NULL /* addr_fixed_len */
717 static address_type_t stringz_address = {
718 AT_STRINGZ, /* addr_type */
719 "AT_STRINGZ", /* name */
720 "String address", /* pretty_name */
721 stringz_addr_to_str, /* addr_to_str */
722 stringz_addr_str_len, /* addr_str_len */
723 NULL, /* addr_col_filter */
724 NULL /* addr_fixed_len */
727 static address_type_t eui64_address = {
728 AT_EUI64, /* addr_type */
729 "AT_EUI64", /* name */
730 "IEEE EUI-64", /* pretty_name */
731 eui64_addr_to_str, /* addr_to_str */
732 eui64_str_len, /* addr_str_len */
733 NULL, /* addr_col_filter */
734 eui64_len /* addr_fixed_len */
737 static address_type_t ib_address = {
738 AT_IB, /* addr_type */
740 "Infiniband GID/LID", /* pretty_name */
741 ib_addr_to_str, /* addr_to_str */
742 ib_str_len, /* addr_str_len */
743 NULL, /* addr_col_filter */
744 NULL /* addr_fixed_len */
747 static address_type_t usb_address = {
748 AT_USB, /* addr_type */
750 "USB Address", /* pretty_name */
751 usb_addr_to_str, /* addr_to_str */
752 usb_addr_str_len, /* addr_str_len */
753 NULL, /* addr_col_filter */
754 NULL /* addr_fixed_len */
757 static address_type_t ax25_address = {
758 AT_AX25, /* addr_type */
759 "AT_AX25", /* name */
760 "AX.25 Address", /* pretty_name */
761 ax25_addr_to_str, /* addr_to_str */
762 ax25_addr_str_len,/* addr_str_len */
763 ax25_col_filter_str, /* addr_col_filter */
764 ax25_len /* addr_fixed_len */
767 num_dissector_addr_type = 0;
769 /* Initialize the type array. This is mostly for handling
770 "dissector registered" address type range (for NULL checking) */
771 memset(type_list, 0, MAX_ADDR_TYPE_VALUE*sizeof(address_type_t*));
773 address_type_register(AT_NONE, &none_address );
774 address_type_register(AT_ETHER, ðer_address );
775 address_type_register(AT_IPv4, &ipv4_address );
776 address_type_register(AT_IPv6, &ipv6_address );
777 address_type_register(AT_IPX, &ipx_address );
778 address_type_register(AT_VINES, &vines_address );
779 address_type_register(AT_FC, &fc_address );
780 address_type_register(AT_FCWWN, &fcwwn_address );
781 address_type_register(AT_SS7PC, &ss7pc_address );
782 address_type_register(AT_STRINGZ, &stringz_address );
783 address_type_register(AT_EUI64, &eui64_address );
784 address_type_register(AT_IB, &ib_address );
785 address_type_register(AT_USB, &usb_address );
786 address_type_register(AT_AX25, &ax25_address );
789 /* Given an address type id, return an address_type_t* */
790 #define ADDR_TYPE_LOOKUP(addr_type, result) \
792 g_assert(addr_type < MAX_ADDR_TYPE_VALUE); \
793 result = type_list[addr_type];
795 static int address_type_get_length(const address* addr)
799 ADDR_TYPE_LOOKUP(addr->type, at);
801 if ((at == NULL) || (at->addr_str_len == NULL))
804 return at->addr_str_len(addr);
807 /*XXX FIXME the code below may be called very very frequently in the future.
808 optimize it for speed and get rid of the slow sprintfs */
809 /* XXX - perhaps we should have individual address types register
810 a table of routines to do operations such as address-to-name translation,
811 address-to-string translation, and the like, and have this call them,
812 and also have an address-to-string-with-a-name routine */
813 /* convert an address struct into a printable string */
816 address_to_str(wmem_allocator_t *scope, const address *addr)
819 int len = address_type_get_length(addr);
822 len = MAX_ADDR_STR_LEN;
824 str=(gchar *)wmem_alloc(scope, len);
825 address_to_str_buf(addr, str, len);
829 void address_to_str_buf(const address* addr, gchar *buf, int buf_len)
833 if (!buf || !buf_len)
836 ADDR_TYPE_LOOKUP(addr->type, at);
838 if ((at == NULL) || (at->addr_to_str == NULL))
844 at->addr_to_str(addr, buf, buf_len);
847 const char* address_type_column_filter_string(const address* addr, gboolean src)
851 ADDR_TYPE_LOOKUP(addr->type, at);
853 if ((at == NULL) || (at->addr_col_filter == NULL))
858 return at->addr_col_filter(addr, src);
862 tvb_address_to_str(wmem_allocator_t *scope, tvbuff_t *tvb, int type, const gint offset)
867 ADDR_TYPE_LOOKUP(type, at);
874 /* The address type must have a fixed length to use this function */
875 /* For variable length fields, use tvb_address_var_to_str() */
876 if (at->addr_fixed_len == NULL)
878 g_assert_not_reached();
882 TVB_SET_ADDRESS(&addr, type, tvb, offset, at->addr_fixed_len());
884 return address_to_str(scope, &addr);
887 gchar* tvb_address_var_to_str(wmem_allocator_t *scope, tvbuff_t *tvb, address_type type, const gint offset, int length)
891 TVB_SET_ADDRESS(&addr, type, tvb, offset, length);
893 return address_to_str(scope, &addr);
898 * Editor modelines - http://www.wireshark.org/tools/modelines.html
903 * indent-tabs-mode: nil
906 * vi: set shiftwidth=4 tabstop=8 expandtab:
907 * :indentSize=4:tabSize=8:noTabs=true: