Revert "TODO epan/dissectors/asn1/kerberos/packet-kerberos-template.c new GSS flags"
[wireshark-sm.git] / epan / dissectors / packet-lisp.c
blob0ec4e6fda8747b605ec247558ec5fe80fd0f0fab
1 /* packet-lisp.c
2 * Routines for Locator/ID Separation Protocol (LISP) Control Message dissection
3 * Copyright 2011, 2014 Lorand Jakab <ljakab@ac.upc.edu>
5 * Geo Coordinates LCAF dissection based on previous work by Radu Terciu
7 * Wireshark - Network traffic analyzer
8 * By Gerald Combs <gerald@wireshark.org>
9 * Copyright 1998 Gerald Combs
11 * SPDX-License-Identifier: GPL-2.0-or-later
14 #include "config.h"
15 #include "packet-lisp.h"
17 #include <epan/to_str.h>
18 #include <epan/afn.h>
19 #include <epan/oui.h>
20 #include <epan/expert.h>
21 #include <epan/tfs.h>
22 #include <wsutil/array.h>
23 #include <wsutil/utf8_entities.h>
25 void proto_register_lisp(void);
26 void proto_reg_handoff_lisp(void);
29 * See RFC 6830 "Locator/ID Separation Protocol (LISP)",
30 * draft-ietf-lisp-lcaf-05 "LISP Canonical Address Format (LCAF)",
31 * draft-ietf-lisp-vendor-lcaf-07 "Vendor Specific LISP Canonical Address Format (LCAF)"
32 * draft-ietf-lisp-sec-04 "LISP-Security (LISP-SEC)",
33 * draft-ermagan-lisp-nat-traversal-03 "NAT traversal for LISP",
34 * draft-farinacci-lisp-name-encoding-09 "LISP Distinguished Name Encoding"
35 * for packet format and protocol information.
38 /* LISP Control Message types */
39 #define LISP_MAP_REQUEST 1
40 #define LISP_MAP_REPLY 2
41 #define LISP_MAP_REGISTER 3
42 #define LISP_MAP_NOTIFY 4
43 #define LISP_MAP_REFERRAL 6
44 #define LISP_INFO 7
45 #define LISP_ECM 8
47 #define LISP_ACT_NONE 0
48 #define LISP_ACT_FWD_NATIVE 1
49 #define LISP_ACT_MREQ 2
50 #define LISP_ACT_DROP 3
51 #define LISP_ACT_DROP_PD 4
52 #define LISP_ACT_DROP_AF 5
53 #define LISP_ACT_FWD_UA 6
55 #define DDT_NODE_REF 0
56 #define DDT_MS_REF 1
57 #define DDT_MS_ACK 2
58 #define DDT_MS_NREG 3
59 #define DDT_DLGT_HOLE 4
60 #define DDT_NAUTH 5
62 #define LCAF_NULL 0
63 #define LCAF_AFI_LIST 1
64 #define LCAF_IID 2
65 #define LCAF_ASN 3
66 #define LCAF_APP_DATA 4
67 #define LCAF_GEO 5
68 #define LCAF_OKEY 6
69 #define LCAF_NATT 7
70 #define LCAF_NONCE_LOC 8
71 #define LCAF_MCAST_INFO 9
72 #define LCAF_ELP 10
73 #define LCAF_SEC_KEY 11
74 #define LCAF_SRC_DST_KEY 12
75 #define LCAF_RLE 13
76 #define LCAF_JSON 14
77 #define LCAF_KV_ADDR_PAIR 15
78 #define LCAF_VENDOR 255
80 #define LCAF_HEADER_LEN 6
81 #define LISP_ECM_HEADER_LEN 4
83 #define LISP_MAP_ACT 0xE000
84 #define LISP_MAP_AUTH 0x1000
85 #define REFERRAL_INCOMPLETE 0x0800
86 #define LOCAL_BIT_MASK 0x0004
87 #define PROBE_BIT_MASK 0x0002
88 #define REACH_BIT_MASK 0x0001
90 #define MAP_REQ_FLAG_A 0x080000
91 #define MAP_REQ_FLAG_M 0x040000
92 #define MAP_REQ_FLAG_P 0x020000
93 #define MAP_REQ_FLAG_S 0x010000
94 #define MAP_REQ_FLAG_p 0x008000
95 #define MAP_REQ_FLAG_s 0x004000
96 #define MAP_REQ_RESERVED 0x003FE0
98 #define MAP_REP_FLAG_P 0x080000
99 #define MAP_REP_FLAG_E 0x040000
100 #define MAP_REP_FLAG_S 0x020000
101 #define MAP_REP_RESERVED 0x01FFFF
103 #define MAP_REG_FLAG_P 0x080000
104 #define MAP_REG_FLAG_S 0x040000
105 #define MAP_REG_FLAG_I 0x020000
106 #define MAP_REG_FLAG_R 0x010000
107 #define MAP_REG_RESERVED 0x00FFFE
108 #define MAP_REG_FLAG_M 0x000001
110 #define MAP_NOT_FLAG_I 0x080000
111 #define MAP_NOT_FLAG_R 0x040000
112 #define MAP_NOT_RESERVED 0x03FFFF
114 #define MAP_REF_RESERVED 0x0FFFFF
116 #define INFO_FLAG_R 0x080000
117 #define INFO_RESERVED 0x07FFFFFF
119 #define ECM_FLAG_S 0x08000000
120 #define ECM_FLAG_D 0x04000000
122 #define MCINFO_FLAG_R 0x04
123 #define MCINFO_FLAG_L 0x02
124 #define MCINFO_FLAG_J 0x01
126 #define ELP_FLAG_L 0x0004
127 #define ELP_FLAG_P 0x0002
128 #define ELP_FLAG_S 0x0001
130 /* Initialize the protocol and registered fields */
131 static int proto_lisp;
132 static int hf_lisp_type;
133 static int hf_lisp_irc;
134 static int hf_lisp_records;
135 static int hf_lisp_nonce;
136 static int hf_lisp_keyid;
137 static int hf_lisp_authlen;
138 static int hf_lisp_auth;
139 static int hf_lisp_msrtr_keyid;
140 static int hf_lisp_msrtr_authlen;
141 static int hf_lisp_msrtr_auth;
142 static int hf_lisp_xtrid;
143 static int hf_lisp_siteid;
145 /* Map-Request fields */
146 static int hf_lisp_mreq_flags;
147 static int hf_lisp_mreq_flags_auth;
148 static int hf_lisp_mreq_flags_mrp;
149 static int hf_lisp_mreq_flags_probe;
150 static int hf_lisp_mreq_flags_smr;
151 static int hf_lisp_mreq_flags_pitr;
152 static int hf_lisp_mreq_flags_smri;
153 static int hf_lisp_mreq_res;
154 static int hf_lisp_mreq_srceid_afi;
155 static int hf_lisp_mreq_srceid_string;
156 static int hf_lisp_mreq_srceid_ipv4;
157 static int hf_lisp_mreq_srceid_ipv6;
158 static int hf_lisp_mreq_srceid_mac;
159 static int hf_lisp_mreq_itr_rloc;
160 static int hf_lisp_mreq_itr_rloc_afi;
161 static int hf_lisp_mreq_itr_rloc_ipv4;
162 static int hf_lisp_mreq_itr_rloc_ipv6;
163 static int hf_lisp_mreq_record;
164 static int hf_lisp_mreq_record_res;
165 static int hf_lisp_mreq_record_prefix_length;
166 static int hf_lisp_mreq_record_prefix_afi;
167 static int hf_lisp_mreq_record_prefix_ipv4;
168 static int hf_lisp_mreq_record_prefix_ipv6;
169 static int hf_lisp_mreq_record_prefix_mac;
170 static int hf_lisp_mreq_record_prefix_dn;
172 /* Map-Reply fields */
173 static int hf_lisp_mrep_record;
174 static int hf_lisp_mrep_flags_probe;
175 static int hf_lisp_mrep_flags_enlr;
176 static int hf_lisp_mrep_flags_sec;
177 static int hf_lisp_mrep_res;
179 /* Map-Register fields */
180 static int hf_lisp_mreg_flags_pmr;
181 static int hf_lisp_mreg_flags_sec;
182 static int hf_lisp_mreg_flags_xtrid;
183 static int hf_lisp_mreg_flags_rtr;
184 static int hf_lisp_mreg_flags_wmn;
185 static int hf_lisp_mreg_res;
187 /* Map-Notify fields */
188 static int hf_lisp_mnot_flags_xtrid;
189 static int hf_lisp_mnot_flags_rtr;
190 static int hf_lisp_mnot_res;
192 /* Map-Referral fields */
193 static int hf_lisp_mref_res;
194 static int hf_lisp_referral_sigcnt;
195 static int hf_lisp_referral_incomplete;
197 /* Info fields */
198 static int hf_lisp_info_r;
199 static int hf_lisp_info_res1;
200 static int hf_lisp_info_ttl;
201 static int hf_lisp_info_res2;
202 static int hf_lisp_info_prefix_masklen;
203 static int hf_lisp_info_prefix_afi;
204 static int hf_lisp_info_prefix_ipv4;
205 static int hf_lisp_info_prefix_ipv6;
206 static int hf_lisp_info_afi;
208 /* Mapping record fields */
209 static int hf_lisp_mapping;
210 static int hf_lisp_mapping_ttl;
211 static int hf_lisp_mapping_loccnt;
212 static int hf_lisp_mapping_eid_masklen;
213 static int hf_lisp_mapping_act;
214 static int hf_lisp_mapping_auth;
215 static int hf_lisp_mapping_res1;
216 static int hf_lisp_mapping_res2;
217 static int hf_lisp_mapping_ver;
218 static int hf_lisp_mapping_eid_afi;
219 static int hf_lisp_mapping_eid_ipv4;
220 static int hf_lisp_mapping_eid_ipv6;
221 static int hf_lisp_mapping_eid_mac;
222 static int hf_lisp_mapping_eid_dn;
224 /* Locator fields */
225 static int hf_lisp_loc;
226 static int hf_lisp_loc_priority;
227 static int hf_lisp_loc_weight;
228 static int hf_lisp_loc_mpriority;
229 static int hf_lisp_loc_mweight;
230 static int hf_lisp_loc_flags;
231 static int hf_lisp_loc_flags_local;
232 static int hf_lisp_loc_flags_probe;
233 static int hf_lisp_loc_flags_reach;
234 static int hf_lisp_loc_flags_res;
235 static int hf_lisp_loc_afi;
236 static int hf_lisp_loc_locator;
238 /* LCAF fields */
239 static int hf_lisp_lcaf;
240 static int hf_lisp_lcaf_header;
241 static int hf_lisp_lcaf_res1;
242 static int hf_lisp_lcaf_flags;
243 static int hf_lisp_lcaf_type;
244 static int hf_lisp_lcaf_res2;
245 static int hf_lisp_lcaf_length;
247 /* LCAF AFI List fields */
248 static int hf_lisp_lcaf_afi_list_item;
249 static int hf_lisp_lcaf_afi_list_afi;
250 static int hf_lisp_lcaf_afi_list_ipv4;
251 static int hf_lisp_lcaf_afi_list_ipv6;
252 static int hf_lisp_lcaf_afi_list_mac;
253 static int hf_lisp_lcaf_afi_list_dn;
255 /* LCAF IID fields */
256 static int hf_lisp_lcaf_iid;
257 static int hf_lisp_lcaf_iid_afi;
258 static int hf_lisp_lcaf_iid_ipv4;
259 static int hf_lisp_lcaf_iid_ipv6;
260 static int hf_lisp_lcaf_iid_mac;
261 static int hf_lisp_lcaf_iid_dn;
263 /* LCAF ASN fields */
264 static int hf_lisp_lcaf_asn;
265 static int hf_lisp_lcaf_asn_afi;
266 static int hf_lisp_lcaf_asn_ipv4;
267 static int hf_lisp_lcaf_asn_ipv6;
268 static int hf_lisp_lcaf_asn_mac;
269 static int hf_lisp_lcaf_asn_dn;
271 /* LCAF Geo Coordinates fields */
272 static int hf_lisp_lcaf_geo_lat;
273 static int hf_lisp_lcaf_geo_lat_hemisphere;
274 static int hf_lisp_lcaf_geo_lat_deg;
275 static int hf_lisp_lcaf_geo_lat_min;
276 static int hf_lisp_lcaf_geo_lat_sec;
277 static int hf_lisp_lcaf_geo_lon;
278 static int hf_lisp_lcaf_geo_lon_hemisphere;
279 static int hf_lisp_lcaf_geo_lon_deg;
280 static int hf_lisp_lcaf_geo_lon_min;
281 static int hf_lisp_lcaf_geo_lon_sec;
282 static int hf_lisp_lcaf_geo_alt;
283 static int hf_lisp_lcaf_geo_afi;
284 static int hf_lisp_lcaf_geo_ipv4;
285 static int hf_lisp_lcaf_geo_ipv6;
286 static int hf_lisp_lcaf_geo_mac;
287 static int hf_lisp_lcaf_geo_dn;
289 /* LCAF NATT fields */
290 static int hf_lisp_lcaf_natt_msport;
291 static int hf_lisp_lcaf_natt_etrport;
292 static int hf_lisp_lcaf_natt_rloc;
293 static int hf_lisp_lcaf_natt_rloc_afi;
294 static int hf_lisp_lcaf_natt_rloc_ipv4;
295 static int hf_lisp_lcaf_natt_rloc_ipv6;
297 /* LCAF Nonce Locator fields */
298 static int hf_lisp_lcaf_nonce_loc_res;
299 static int hf_lisp_lcaf_nonce_loc;
300 static int hf_lisp_lcaf_nonce_loc_afi;
301 static int hf_lisp_lcaf_nonce_loc_ipv4;
302 static int hf_lisp_lcaf_nonce_loc_ipv6;
303 static int hf_lisp_lcaf_nonce_loc_mac;
304 static int hf_lisp_lcaf_nonce_loc_dn;
306 /* LCAF Multicast Group Membership Information fields */
307 static int hf_lisp_lcaf_mcinfo_flags;
308 static int hf_lisp_lcaf_mcinfo_flags_res;
309 static int hf_lisp_lcaf_mcinfo_flags_rp;
310 static int hf_lisp_lcaf_mcinfo_flags_leave;
311 static int hf_lisp_lcaf_mcinfo_flags_join;
312 static int hf_lisp_lcaf_mcinfo_iid;
313 static int hf_lisp_lcaf_mcinfo_res;
314 static int hf_lisp_lcaf_mcinfo_src_masklen;
315 static int hf_lisp_lcaf_mcinfo_grp_masklen;
316 static int hf_lisp_lcaf_mcinfo_src;
317 static int hf_lisp_lcaf_mcinfo_src_afi;
318 static int hf_lisp_lcaf_mcinfo_src_ipv4;
319 static int hf_lisp_lcaf_mcinfo_src_ipv6;
320 static int hf_lisp_lcaf_mcinfo_grp;
321 static int hf_lisp_lcaf_mcinfo_grp_afi;
322 static int hf_lisp_lcaf_mcinfo_grp_ipv4;
323 static int hf_lisp_lcaf_mcinfo_grp_ipv6;
325 /* LCAF ELP fields */
326 static int hf_lisp_lcaf_elp_hop;
327 static int hf_lisp_lcaf_elp_hop_flags;
328 static int hf_lisp_lcaf_elp_hop_flags_res;
329 static int hf_lisp_lcaf_elp_hop_flags_lookup;
330 static int hf_lisp_lcaf_elp_hop_flags_probe;
331 static int hf_lisp_lcaf_elp_hop_flags_strict;
332 static int hf_lisp_lcaf_elp_hop_afi;
333 static int hf_lisp_lcaf_elp_hop_ipv4;
334 static int hf_lisp_lcaf_elp_hop_ipv6;
336 /* LCAF Source/Destination 2-Tuple Lookups fields */
337 static int hf_lisp_lcaf_srcdst_res;
338 static int hf_lisp_lcaf_srcdst_src_masklen;
339 static int hf_lisp_lcaf_srcdst_dst_masklen;
340 static int hf_lisp_lcaf_srcdst_src;
341 static int hf_lisp_lcaf_srcdst_src_afi;
342 static int hf_lisp_lcaf_srcdst_src_ipv4;
343 static int hf_lisp_lcaf_srcdst_src_ipv6;
344 static int hf_lisp_lcaf_srcdst_src_mac;
345 static int hf_lisp_lcaf_srcdst_dst;
346 static int hf_lisp_lcaf_srcdst_dst_afi;
347 static int hf_lisp_lcaf_srcdst_dst_ipv4;
348 static int hf_lisp_lcaf_srcdst_dst_ipv6;
349 static int hf_lisp_lcaf_srcdst_dst_mac;
351 /* LCAF RLE fields */
352 static int hf_lisp_lcaf_rle_entry;
353 static int hf_lisp_lcaf_rle_entry_res;
354 static int hf_lisp_lcaf_rle_entry_level;
355 static int hf_lisp_lcaf_rle_entry_afi;
356 static int hf_lisp_lcaf_rle_entry_ipv4;
357 static int hf_lisp_lcaf_rle_entry_ipv6;
359 /* LCAF Key/Value Pair fields */
360 static int hf_lisp_lcaf_kv_key;
361 static int hf_lisp_lcaf_kv_key_afi;
362 static int hf_lisp_lcaf_kv_key_ipv4;
363 static int hf_lisp_lcaf_kv_key_ipv6;
364 static int hf_lisp_lcaf_kv_key_mac;
365 static int hf_lisp_lcaf_kv_key_dn;
366 static int hf_lisp_lcaf_kv_value;
367 static int hf_lisp_lcaf_kv_value_afi;
368 static int hf_lisp_lcaf_kv_value_ipv4;
369 static int hf_lisp_lcaf_kv_value_ipv6;
370 static int hf_lisp_lcaf_kv_value_mac;
371 static int hf_lisp_lcaf_kv_value_dn;
373 /* Vendor Specific LCAF fields */
374 static int hf_lisp_lcaf_vendor_res;
375 static int hf_lisp_lcaf_vendor_oui;
376 static int hf_lisp_lcaf_vendor_data;
378 /* Encapsulated Control Message fields */
379 static int hf_lisp_ecm_flags_sec;
380 static int hf_lisp_ecm_flags_ddt;
381 static int hf_lisp_ecm_res;
383 /* Initialize the subtree pointers */
384 static int ett_lisp;
385 static int ett_lisp_mr;
386 static int ett_lisp_mreq_flags;
387 static int ett_lisp_mapping;
388 static int ett_lisp_itr;
389 static int ett_lisp_record;
390 static int ett_lisp_lcaf;
391 static int ett_lisp_lcaf_header;
392 static int ett_lisp_lcaf_geo_lat;
393 static int ett_lisp_lcaf_geo_lon;
394 static int ett_lisp_lcaf_natt_rloc;
395 static int ett_lisp_lcaf_mcinfo_flags;
396 static int ett_lisp_lcaf_mcinfo_src;
397 static int ett_lisp_lcaf_mcinfo_grp;
398 static int ett_lisp_lcaf_elp_hop;
399 static int ett_lisp_lcaf_elp_hop_flags;
400 static int ett_lisp_lcaf_srcdst_src;
401 static int ett_lisp_lcaf_srcdst_dst;
402 static int ett_lisp_lcaf_rle_entry;
403 static int ett_lisp_lcaf_kv_key;
404 static int ett_lisp_lcaf_kv_value;
405 static int ett_lisp_lcaf_vendor;
406 static int ett_lisp_loc;
407 static int ett_lisp_loc_flags;
408 static int ett_lisp_info_prefix;
409 static int ett_lisp_afi_list;
411 static expert_field ei_lisp_undecoded;
412 static expert_field ei_lisp_expected_field;
413 static expert_field ei_lisp_invalid_field;
414 static expert_field ei_lisp_unexpected_field;
416 static dissector_handle_t lisp_handle;
418 static dissector_handle_t ipv4_handle;
419 static dissector_handle_t ipv6_handle;
421 static bool encapsulated;
422 static bool ddt_originated;
424 static const value_string lisp_typevals[] = {
425 { LISP_MAP_REQUEST, "Map-Request" },
426 { LISP_MAP_REPLY, "Map-Reply" },
427 { LISP_MAP_REGISTER, "Map-Register" },
428 { LISP_MAP_NOTIFY, "Map-Notify" },
429 { LISP_MAP_REFERRAL, "Map-Referral" },
430 { LISP_INFO, "Info" },
431 { LISP_ECM, "Encapsulated Control Message" },
432 { 0, NULL}
435 static const value_string mapping_actions[] = {
436 { LISP_ACT_NONE, "No-Action" },
437 { LISP_ACT_FWD_NATIVE, "Natively-Forward" },
438 { LISP_ACT_MREQ, "Send-Map-Request" },
439 { LISP_ACT_DROP, "Drop/No-Reason" },
440 { LISP_ACT_DROP_PD, "Drop/Policy-Denied" },
441 { LISP_ACT_DROP_AF, "Drop/Authentication-Failure" },
442 { LISP_ACT_FWD_UA, "Forward-For-Unknown-Address" },
443 { 0, NULL}
446 static const value_string referral_actions[] = {
447 { DDT_NODE_REF, "Node Referral" },
448 { DDT_MS_REF, "Map-Server Referral" },
449 { DDT_MS_ACK, "Map-Server ACK" },
450 { DDT_MS_NREG, "Map-Server Not Registered" },
451 { DDT_DLGT_HOLE, "Delegation Hole" },
452 { DDT_NAUTH, "Not Authoritative" },
453 { 0, NULL}
456 static const value_string lcaf_typevals[] = {
457 { LCAF_NULL, "Null Body" },
458 { LCAF_AFI_LIST, "AFI List" },
459 { LCAF_IID, "Instance ID" },
460 { LCAF_ASN, "AS Number" },
461 { LCAF_APP_DATA, "Application Data" },
462 { LCAF_GEO, "Geo Coordinates" },
463 { LCAF_OKEY, "Opaque Key" },
464 { LCAF_NATT, "NAT Traversal" },
465 { LCAF_NONCE_LOC, "Nonce Locator" },
466 { LCAF_MCAST_INFO, "Multicast Info" },
467 { LCAF_ELP, "Explicit Locator Path" },
468 { LCAF_SEC_KEY, "Security Key" },
469 { LCAF_SRC_DST_KEY, "Source/Dest Key" },
470 { LCAF_RLE, "Replication List Entry" },
471 { LCAF_JSON, "JSON Data Model" },
472 { LCAF_KV_ADDR_PAIR, "Key/Value Address Pair" },
473 { LCAF_VENDOR, "Vendor Specific LCAF" },
474 { 0, NULL}
477 static const value_string lat_typevals[] = {
478 { 0, "S" },
479 { 1, "N" },
480 { 0, NULL}
483 static const value_string lon_typevals[] = {
484 { 0, "W" },
485 { 1, "E" },
486 { 0, NULL}
489 /* Add your company OUI here if you're developing a vendor LCAF dissector */
490 static const value_string oui_vals[] = {
491 { OUI_CISCO, "Cisco" },
492 { 0, NULL}
495 static int
496 get_lcaf_data(tvbuff_t *tvb, int offset, uint8_t *lcaf_type, uint16_t *len)
498 /* Jump over Rsvd1 and Flags (16 bits) */
499 offset += 2;
501 /* Type (8 bits) */
502 if (lcaf_type)
503 *lcaf_type = tvb_get_uint8(tvb, offset);
504 offset += 1;
506 /* Jump over Rsvd2 bits (8 bits) */
507 offset += 1;
509 /* Length (16 bits) */
510 if (len)
511 /* Adding the size of the LCAF header as well */
512 *len = tvb_get_ntohs(tvb, offset) + LCAF_HEADER_LEN;
513 offset += 2;
515 return offset;
518 const char *
519 // NOLINTNEXTLINE(misc-no-recursion)
520 get_addr_str(tvbuff_t *tvb, packet_info *pinfo, int offset, uint16_t afi, uint16_t *addr_len)
522 const char *notset_str = "not set";
523 const char *addr_str;
524 uint8_t lcaf_type;
525 uint32_t iid, asn;
526 uint16_t cur_len;
528 switch (afi) {
529 case AFNUM_RESERVED:
530 *addr_len = 0;
531 return notset_str;
532 case AFNUM_INET:
533 *addr_len = INET_ADDRLEN;
534 addr_str = tvb_ip_to_str(pinfo->pool, tvb, offset);
535 return addr_str;
536 case AFNUM_INET6:
537 *addr_len = INET6_ADDRLEN;
538 addr_str = tvb_ip6_to_str(pinfo->pool, tvb, offset);
539 return addr_str;
540 case AFNUM_LCAF:
541 get_lcaf_data(tvb, offset, &lcaf_type, addr_len);
542 addr_str = val_to_str(lcaf_type, lcaf_typevals, "Unknown LCAF Type (%d)");
543 if (lcaf_type == LCAF_IID) {
544 iid = tvb_get_ntohl(tvb, offset + LCAF_HEADER_LEN);
545 afi = tvb_get_ntohs(tvb, offset + LCAF_HEADER_LEN + 4);
546 increment_dissection_depth(pinfo);
547 addr_str = get_addr_str(tvb, pinfo, offset + LCAF_HEADER_LEN + 6, afi, &cur_len);
548 decrement_dissection_depth(pinfo);
549 return wmem_strdup_printf(pinfo->pool, "[%d] %s", iid, addr_str);
551 if (lcaf_type == LCAF_ASN) {
552 asn = tvb_get_ntohl(tvb, offset + LCAF_HEADER_LEN);
553 afi = tvb_get_ntohs(tvb, offset + LCAF_HEADER_LEN + 4);
554 increment_dissection_depth(pinfo);
555 addr_str = get_addr_str(tvb, pinfo, offset + LCAF_HEADER_LEN + 6, afi, &cur_len);
556 decrement_dissection_depth(pinfo);
557 return wmem_strdup_printf(pinfo->pool, "%s (ASN %d)", addr_str, asn);
559 return addr_str;
560 case AFNUM_802:
561 case AFNUM_EUI48:
562 *addr_len = EUI48_ADDRLEN;
563 addr_str = tvb_ether_to_str(pinfo->pool, tvb, offset);
564 return addr_str;
565 case AFNUM_DISTNAME:
566 *addr_len = tvb_strsize(tvb, offset);
567 addr_str = tvb_get_stringz_enc(pinfo->pool, tvb, offset, NULL, ENC_ASCII);
568 return addr_str;
569 default:
570 return NULL;
574 static int
575 // NOLINTNEXTLINE(misc-no-recursion)
576 dissect_lcaf_natt_rloc(tvbuff_t *tvb, packet_info *pinfo, proto_tree *tree,
577 int offset, const char *str, int idx)
579 uint16_t addr_len = 0;
580 uint16_t rloc_afi;
581 const char *rloc_str;
582 proto_item *ti;
583 proto_tree *rloc_tree;
585 ti = proto_tree_add_item(tree, hf_lisp_lcaf_natt_rloc, tvb, offset, 2, ENC_NA);
586 rloc_tree = proto_item_add_subtree(ti, ett_lisp_lcaf_natt_rloc);
588 /* AFI (2 bytes) */
589 proto_tree_add_item(rloc_tree, hf_lisp_lcaf_natt_rloc_afi, tvb, offset, 2, ENC_BIG_ENDIAN);
590 rloc_afi = tvb_get_ntohs(tvb, offset);
591 offset += 2;
593 /* Reencap hop */
594 rloc_str = get_addr_str(tvb, pinfo, offset, rloc_afi, &addr_len);
596 switch (rloc_afi) {
597 case AFNUM_RESERVED:
598 break;
599 case AFNUM_INET:
600 proto_tree_add_item(rloc_tree, hf_lisp_lcaf_natt_rloc_ipv4,
601 tvb, offset, INET_ADDRLEN, ENC_BIG_ENDIAN);
602 break;
603 case AFNUM_INET6:
604 proto_tree_add_item(rloc_tree, hf_lisp_lcaf_natt_rloc_ipv6,
605 tvb, offset, INET6_ADDRLEN, ENC_NA);
606 break;
607 case AFNUM_LCAF:
608 dissect_lcaf(tvb, pinfo, rloc_tree, offset, NULL);
609 break;
610 default:
611 expert_add_info_format(pinfo, rloc_tree, &ei_lisp_unexpected_field,
612 "Unexpected NAT-T RLOC AFI (%d), cannot decode", rloc_afi);
615 if (idx) {
616 proto_item_append_text(ti, str, idx, rloc_str);
617 } else {
618 proto_item_append_text(ti, str, rloc_str);
620 proto_item_set_len(ti, 2 + addr_len);
622 return addr_len + 2;
625 static int
626 // NOLINTNEXTLINE(misc-no-recursion)
627 dissect_lcaf_elp_hop(tvbuff_t *tvb, packet_info *pinfo, proto_tree *tree,
628 int offset, int idx, proto_item *tip)
630 uint16_t addr_len = 0;
631 uint16_t hop_afi;
632 uint16_t hop_flags;
633 const char *hop_str;
634 proto_item *ti, *ti_flags;
635 proto_tree *hop_tree, *flags_tree;
637 ti = proto_tree_add_item(tree, hf_lisp_lcaf_elp_hop, tvb, offset, 2, ENC_NA);
638 hop_tree = proto_item_add_subtree(ti, ett_lisp_lcaf_elp_hop);
640 /* Flags (2 bytes) */
641 ti_flags = proto_tree_add_item(hop_tree, hf_lisp_lcaf_elp_hop_flags, tvb, offset, 2, ENC_BIG_ENDIAN);
642 flags_tree = proto_item_add_subtree(ti_flags, ett_lisp_lcaf_elp_hop_flags);
643 proto_tree_add_item(flags_tree, hf_lisp_lcaf_elp_hop_flags_res, tvb, offset, 2, ENC_BIG_ENDIAN);
644 proto_tree_add_item(flags_tree, hf_lisp_lcaf_elp_hop_flags_lookup, tvb, offset, 2, ENC_BIG_ENDIAN);
645 proto_tree_add_item(flags_tree, hf_lisp_lcaf_elp_hop_flags_probe, tvb, offset, 2, ENC_BIG_ENDIAN);
646 proto_tree_add_item(flags_tree, hf_lisp_lcaf_elp_hop_flags_strict, tvb, offset, 2, ENC_BIG_ENDIAN);
648 hop_flags = tvb_get_ntohs(tvb, offset);
649 offset += 2;
651 /* AFI (2 bytes) */
652 proto_tree_add_item(hop_tree, hf_lisp_lcaf_elp_hop_afi, tvb, offset, 2, ENC_BIG_ENDIAN);
653 hop_afi = tvb_get_ntohs(tvb, offset);
654 offset += 2;
656 /* Reencap hop */
657 hop_str = get_addr_str(tvb, pinfo, offset, hop_afi, &addr_len);
659 switch (hop_afi) {
660 case AFNUM_INET:
661 proto_tree_add_item(hop_tree, hf_lisp_lcaf_elp_hop_ipv4,
662 tvb, offset, INET_ADDRLEN, ENC_BIG_ENDIAN);
663 break;
664 case AFNUM_INET6:
665 proto_tree_add_item(hop_tree, hf_lisp_lcaf_elp_hop_ipv6,
666 tvb, offset, INET6_ADDRLEN, ENC_NA);
667 break;
668 case AFNUM_LCAF:
669 dissect_lcaf(tvb, pinfo, hop_tree, offset, NULL);
670 break;
671 default:
672 expert_add_info_format(pinfo, hop_tree, &ei_lisp_unexpected_field,
673 "Unexpected Reencap Hop AFI (%d), cannot decode", hop_afi);
676 if (idx) {
677 proto_item_append_text(ti, " %d.", idx);
678 } else {
679 proto_item_append_text(ti, ":");
682 proto_item_append_text(ti, " %s", hop_str);
683 proto_item_set_len(ti, 4 + addr_len);
685 if (hop_flags & 0x04)
686 proto_item_append_text(ti, ", Lookup");
687 if (hop_flags & 0x02)
688 proto_item_append_text(ti, ", RLOC-Probe");
689 if (hop_flags & 0x01)
690 proto_item_append_text(ti, ", Strict");
692 proto_item_append_text(tip, ", %s", hop_str);
694 return addr_len + 4;
698 static int
699 // NOLINTNEXTLINE(misc-no-recursion)
700 dissect_lcaf_rle_entry(tvbuff_t *tvb, packet_info *pinfo, proto_tree *tree,
701 int offset, int idx, proto_item *tip)
703 uint8_t level;
704 uint16_t addr_len = 0;
705 uint16_t entry_afi;
706 const char *entry_str;
707 proto_item *ti;
708 proto_tree *entry_tree;
710 ti = proto_tree_add_item(tree, hf_lisp_lcaf_rle_entry, tvb, offset, 2, ENC_NA);
711 entry_tree = proto_item_add_subtree(ti, ett_lisp_lcaf_rle_entry);
713 /* Reserved (3 bytes) */
714 proto_tree_add_item(entry_tree, hf_lisp_lcaf_rle_entry_res, tvb, offset, 3, ENC_BIG_ENDIAN);
715 offset += 3;
717 /* Level Value (1 byte) */
718 proto_tree_add_item(entry_tree, hf_lisp_lcaf_rle_entry_level, tvb, offset, 1, ENC_BIG_ENDIAN);
719 level = tvb_get_uint8(tvb, offset);
720 offset += 1;
722 /* AFI (2 bytes) */
723 proto_tree_add_item(entry_tree, hf_lisp_lcaf_rle_entry_afi, tvb, offset, 2, ENC_BIG_ENDIAN);
724 entry_afi = tvb_get_ntohs(tvb, offset);
725 offset += 2;
727 /* RTR/ETR entry */
728 entry_str = get_addr_str(tvb, pinfo, offset, entry_afi, &addr_len);
730 switch (entry_afi) {
731 case AFNUM_INET:
732 proto_tree_add_item(entry_tree, hf_lisp_lcaf_rle_entry_ipv4,
733 tvb, offset, INET_ADDRLEN, ENC_BIG_ENDIAN);
734 break;
735 case AFNUM_INET6:
736 proto_tree_add_item(entry_tree, hf_lisp_lcaf_rle_entry_ipv6,
737 tvb, offset, INET6_ADDRLEN, ENC_NA);
738 break;
739 case AFNUM_LCAF:
740 dissect_lcaf(tvb, pinfo, entry_tree, offset, NULL);
741 break;
742 default:
743 expert_add_info_format(pinfo, entry_tree, &ei_lisp_unexpected_field,
744 "Unexpected RTR/ETR AFI (%d), cannot decode", entry_afi);
747 if (idx) {
748 proto_item_append_text(ti, " %d.", idx);
749 } else {
750 proto_item_append_text(ti, ":");
753 proto_item_append_text(ti, " %s, level %d", entry_str, level);
754 proto_item_set_len(ti, 6 + addr_len);
756 proto_item_append_text(tip, ", %s (%d)", entry_str, level);
758 return addr_len + 6;
763 * Dissector code for AFI List
767 static int
768 // NOLINTNEXTLINE(misc-no-recursion)
769 dissect_lcaf_afi_list(tvbuff_t *tvb, packet_info *pinfo, proto_tree *tree,
770 int offset, uint16_t length)
772 int old_offset;
773 int remaining = length;
774 int i = 1;
775 int str_len;
777 uint16_t addr_len = 0;
778 uint16_t afi;
779 const char *lcaf_str;
780 char *disp_str;
781 proto_item *tir;
782 proto_tree *lisp_afi_list_tree;
784 while (remaining > 0) {
785 afi = tvb_get_ntohs(tvb, offset);
786 tir = proto_tree_add_item(tree, hf_lisp_lcaf_afi_list_item, tvb, offset, LCAF_HEADER_LEN, ENC_NA);
787 lisp_afi_list_tree = proto_item_add_subtree(tir, ett_lisp_afi_list);
788 proto_tree_add_item(lisp_afi_list_tree, hf_lisp_lcaf_afi_list_afi, tvb, offset, 2, ENC_BIG_ENDIAN);
789 offset += 2;
790 remaining -= 2;
792 switch (afi) {
793 case AFNUM_INET:
794 proto_tree_add_item(lisp_afi_list_tree, hf_lisp_lcaf_afi_list_ipv4, tvb, offset, INET_ADDRLEN, ENC_BIG_ENDIAN);
795 proto_item_append_text(tir, " %d. IPv4 Address: %s", i, tvb_ip_to_str(pinfo->pool, tvb, offset));
796 proto_item_set_len(tir, 2 + INET_ADDRLEN);
797 offset += INET_ADDRLEN;
798 remaining -= INET_ADDRLEN;
799 break;
800 case AFNUM_INET6:
801 proto_tree_add_item(lisp_afi_list_tree, hf_lisp_lcaf_afi_list_ipv6, tvb, offset, INET6_ADDRLEN, ENC_NA);
802 proto_item_append_text(tir, " %d. IPv6 Address: %s", i, tvb_ip6_to_str(pinfo->pool, tvb, offset));
803 proto_item_set_len(tir, 2 + INET6_ADDRLEN);
804 offset += INET6_ADDRLEN;
805 remaining -= INET6_ADDRLEN;
806 break;
807 case AFNUM_LCAF:
808 old_offset = offset;
809 lcaf_str = get_addr_str(tvb, pinfo, offset, afi, &addr_len);
810 proto_item_append_text(tir, " %d. %s", i, lcaf_str);
811 proto_item_set_len(tir, 2 + addr_len);
812 offset = dissect_lcaf(tvb, pinfo, lisp_afi_list_tree, offset, tir);
813 remaining -= (offset - old_offset);
814 break;
815 case AFNUM_802:
816 case AFNUM_EUI48:
817 proto_tree_add_item(lisp_afi_list_tree, hf_lisp_lcaf_afi_list_mac, tvb, offset, EUI48_ADDRLEN, ENC_NA);
818 proto_item_append_text(tir, " %d. MAC Address: %s", i, tvb_ether_to_str(pinfo->pool, tvb, offset));
819 proto_item_set_len(tir, 2 + EUI48_ADDRLEN);
820 offset += EUI48_ADDRLEN;
821 remaining -= EUI48_ADDRLEN;
822 break;
823 case AFNUM_DISTNAME:
824 str_len = tvb_strsize(tvb, offset);
825 proto_tree_add_item_ret_display_string(lisp_afi_list_tree, hf_lisp_lcaf_afi_list_dn, tvb, offset, str_len, ENC_ASCII,
826 pinfo->pool, &disp_str);
827 proto_item_append_text(tir, " %d. Distinguished Name: %s", i, disp_str);
828 offset += str_len;
829 remaining -= str_len;
830 break;
831 default:
832 expert_add_info_format(pinfo, tree, &ei_lisp_unexpected_field,
833 "Unexpected AFI (%d), cannot decode", afi);
834 return -1;
836 i++;
839 return offset;
844 * Dissector code for Instance ID
846 * 0 1 2 3
847 * 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1
848 * +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
849 * | AFI = 16387 | Rsvd1 | Flags |
850 * +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
851 * | Type = 2 | Rsvd2 | 4 + n |
852 * +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
853 * | Instance ID |
854 * +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
855 * | AFI = x | Address ... |
856 * +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
860 static int
861 // NOLINTNEXTLINE(misc-no-recursion)
862 dissect_lcaf_iid(tvbuff_t *tvb, packet_info *pinfo, proto_tree *tree, int offset, proto_item *tip)
864 const char *ip_address;
865 uint16_t afi, addr_len = 0;
866 int str_len;
868 /* Instance ID (4 bytes) */
869 proto_tree_add_item(tree, hf_lisp_lcaf_iid, tvb, offset, 4, ENC_BIG_ENDIAN);
870 proto_item_append_text(tip, ": %d", tvb_get_ntohl(tvb, offset));
871 offset += 4;
873 /* AFI (2 bytes) */
874 afi = tvb_get_ntohs(tvb, offset);
875 proto_tree_add_item(tree, hf_lisp_lcaf_iid_afi, tvb, offset, 2, ENC_BIG_ENDIAN);
876 offset += 2;
878 /* Address */
879 ip_address = get_addr_str(tvb, pinfo, offset, afi, &addr_len);
880 if (ip_address && afi)
881 proto_item_append_text(tip, ", Address: %s", ip_address);
883 switch (afi) {
884 case AFNUM_RESERVED:
885 break;
886 case AFNUM_INET:
887 proto_tree_add_item(tree, hf_lisp_lcaf_iid_ipv4,
888 tvb, offset, INET_ADDRLEN, ENC_BIG_ENDIAN);
889 offset += INET_ADDRLEN;
890 break;
891 case AFNUM_INET6:
892 proto_tree_add_item(tree, hf_lisp_lcaf_iid_ipv6,
893 tvb, offset, INET6_ADDRLEN, ENC_NA);
894 offset += INET6_ADDRLEN;
895 break;
896 case AFNUM_LCAF:
897 offset = dissect_lcaf(tvb, pinfo, tree, offset, NULL);
898 break;
899 case AFNUM_802:
900 case AFNUM_EUI48:
901 proto_tree_add_item(tree, hf_lisp_lcaf_iid_mac,
902 tvb, offset, EUI48_ADDRLEN, ENC_NA);
903 offset += EUI48_ADDRLEN;
904 break;
905 case AFNUM_DISTNAME:
906 str_len = tvb_strsize(tvb, offset);
907 proto_tree_add_item(tree, hf_lisp_lcaf_iid_dn, tvb, offset, str_len, ENC_ASCII);
908 offset += str_len;
909 break;
910 default:
911 expert_add_info_format(pinfo, tree, &ei_lisp_unexpected_field,
912 "Unexpected Instance ID AFI (%d), cannot decode", afi);
914 return offset;
919 * Dissector code for AS Number
921 * 0 1 2 3
922 * 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1
923 * +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
924 * | AFI = 16387 | Rsvd1 | Flags |
925 * +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
926 * | Type = 3 | Rsvd2 | 4 + n |
927 * +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
928 * | AS Number |
929 * +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
930 * | AFI = x | Address ... |
931 * +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
935 static int
936 // NOLINTNEXTLINE(misc-no-recursion)
937 dissect_lcaf_asn(tvbuff_t *tvb, packet_info *pinfo, proto_tree *tree, int offset, proto_item *tip)
939 const char *addr;
940 uint16_t afi, addr_len = 0;
941 int str_len;
943 /* AS Number (4 bytes) */
944 proto_tree_add_item(tree, hf_lisp_lcaf_asn, tvb, offset, 4, ENC_BIG_ENDIAN);
945 proto_item_append_text(tip, ": %d", tvb_get_ntohl(tvb, offset));
946 offset += 4;
948 /* AFI (2 bytes) */
949 afi = tvb_get_ntohs(tvb, offset);
950 proto_tree_add_item(tree, hf_lisp_lcaf_asn_afi, tvb, offset, 2, ENC_BIG_ENDIAN);
951 offset += 2;
953 /* Address */
954 addr = get_addr_str(tvb, pinfo, offset, afi, &addr_len);
955 if (addr && afi)
956 proto_item_append_text(tip, ", Address: %s", addr);
958 switch (afi) {
959 case AFNUM_RESERVED:
960 break;
961 case AFNUM_INET:
962 proto_tree_add_item(tree, hf_lisp_lcaf_asn_ipv4,
963 tvb, offset, INET_ADDRLEN, ENC_BIG_ENDIAN);
964 offset += INET_ADDRLEN;
965 break;
966 case AFNUM_INET6:
967 proto_tree_add_item(tree, hf_lisp_lcaf_asn_ipv6,
968 tvb, offset, INET6_ADDRLEN, ENC_NA);
969 offset += INET6_ADDRLEN;
970 break;
971 case AFNUM_LCAF:
972 offset = dissect_lcaf(tvb, pinfo, tree, offset, NULL);
973 break;
974 case AFNUM_802:
975 case AFNUM_EUI48:
976 proto_tree_add_item(tree, hf_lisp_lcaf_asn_mac,
977 tvb, offset, EUI48_ADDRLEN, ENC_NA);
978 offset += EUI48_ADDRLEN;
979 break;
980 case AFNUM_DISTNAME:
981 str_len = tvb_strsize(tvb, offset);
982 proto_tree_add_item(tree, hf_lisp_lcaf_asn_dn, tvb, offset, str_len, ENC_ASCII);
983 offset += str_len;
984 break;
985 default:
986 expert_add_info_format(pinfo, tree, &ei_lisp_unexpected_field,
987 "Unexpected Instance ID AFI (%d), cannot decode", afi);
989 return offset;
994 * Dissector code for Geo Coordinates LCAF
996 * 0 1 2 3
997 * 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1
998 * +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
999 * | AFI = 16387 | Rsvd1 | Flags |
1000 * +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
1001 * | Type = 5 | Rsvd2 | 12 + n |
1002 * +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
1003 * |N| Latitude Degrees | Minutes | Seconds |
1004 * +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
1005 * |E| Longitude Degrees | Minutes | Seconds |
1006 * +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
1007 * | Altitude |
1008 * +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
1009 * | AFI = x | Address ... |
1010 * +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
1014 static int
1015 // NOLINTNEXTLINE(misc-no-recursion)
1016 dissect_lcaf_geo(tvbuff_t *tvb, packet_info *pinfo, proto_tree *tree, int offset, proto_item *tir)
1018 uint16_t addr_len = 0;
1019 bool north, east;
1020 uint16_t deg;
1021 uint8_t min, sec;
1022 uint32_t alt;
1023 uint16_t afi;
1024 int str_len;
1025 const char *ip_address;
1026 const uint16_t mask = 0x7FFF; /* prepare mask for N or E bit */
1027 proto_item *ti_lat, *ti_lon, *ti_alt;
1028 proto_tree *lat_tree, *lon_tree;
1030 /* PROCESS LATITUDE */
1032 ti_lat = proto_tree_add_item(tree, hf_lisp_lcaf_geo_lat, tvb, offset, 4, ENC_NA);
1033 lat_tree = proto_item_add_subtree(ti_lat, ett_lisp_lcaf_geo_lat);
1035 /* Hemisphere and degrees (2 bytes) */
1036 proto_tree_add_item(lat_tree, hf_lisp_lcaf_geo_lat_hemisphere, tvb, offset, 2, ENC_BIG_ENDIAN);
1037 proto_tree_add_item(lat_tree, hf_lisp_lcaf_geo_lat_deg, tvb, offset, 2, ENC_BIG_ENDIAN);
1038 deg = tvb_get_ntohs(tvb, offset);
1039 north = deg >> 15;
1040 deg &= mask;
1041 if (deg > 90)
1042 expert_add_info_format(pinfo, tree, &ei_lisp_invalid_field,
1043 "Invalid latitude degrees value (%d)", deg);
1044 offset += 2;
1046 /* Minutes (1 byte) */
1047 proto_tree_add_item(lat_tree, hf_lisp_lcaf_geo_lat_min, tvb, offset, 1, ENC_BIG_ENDIAN);
1048 min = tvb_get_uint8(tvb, offset);
1049 if (min > 60)
1050 expert_add_info_format(pinfo, tree, &ei_lisp_invalid_field,
1051 "Invalid latitude minutes value (%d)", min);
1052 offset += 1;
1054 /* Seconds (1 byte) */
1055 proto_tree_add_item(lat_tree, hf_lisp_lcaf_geo_lat_sec, tvb, offset, 1, ENC_BIG_ENDIAN);
1056 sec = tvb_get_uint8(tvb, offset);
1057 if (sec > 60)
1058 expert_add_info_format(pinfo, tree, &ei_lisp_invalid_field,
1059 "Invalid latitude seconds value (%d)", min);
1060 offset += 1;
1062 proto_item_append_text(ti_lat, ": %s %d" UTF8_DEGREE_SIGN "%d' %d\"",
1063 val_to_str_const(north, lat_typevals, ""), deg, min, sec);
1064 proto_item_append_text(tir, ": (%s%d" UTF8_DEGREE_SIGN "%d'%d\"",
1065 val_to_str_const(north, lat_typevals, ""), deg, min, sec);
1067 /* PROCESS LONGITUDE */
1069 ti_lon = proto_tree_add_item(tree, hf_lisp_lcaf_geo_lon, tvb, offset, 4, ENC_NA);
1070 lon_tree = proto_item_add_subtree(ti_lon, ett_lisp_lcaf_geo_lon);
1072 /* Hemisphere and degrees (2 bytes) */
1073 proto_tree_add_item(lon_tree, hf_lisp_lcaf_geo_lon_hemisphere, tvb, offset, 2, ENC_BIG_ENDIAN);
1074 proto_tree_add_item(lon_tree, hf_lisp_lcaf_geo_lon_deg, tvb, offset, 2, ENC_BIG_ENDIAN);
1075 deg = tvb_get_ntohs(tvb, offset);
1076 east = deg >> 15;
1077 deg &= mask;
1078 if (deg > 180)
1079 expert_add_info_format(pinfo, tree, &ei_lisp_invalid_field,
1080 "Invalid longitude degrees value (%d)", deg);
1081 offset += 2;
1083 /* Minutes (1 byte) */
1084 proto_tree_add_item(lon_tree, hf_lisp_lcaf_geo_lon_min, tvb, offset, 1, ENC_BIG_ENDIAN);
1085 min = tvb_get_uint8(tvb, offset);
1086 if (min > 60)
1087 expert_add_info_format(pinfo, tree, &ei_lisp_invalid_field,
1088 "Invalid longitude minutes value (%d)", min);
1089 offset += 1;
1091 /* Seconds (1 byte) */
1092 proto_tree_add_item(lon_tree, hf_lisp_lcaf_geo_lon_sec, tvb, offset, 1, ENC_BIG_ENDIAN);
1093 sec = tvb_get_uint8(tvb, offset);
1094 if (sec > 60)
1095 expert_add_info_format(pinfo, tree, &ei_lisp_invalid_field,
1096 "Invalid longitude seconds value (%d)", min);
1097 offset += 1;
1099 proto_item_append_text(ti_lon, ": %s %d" UTF8_DEGREE_SIGN " %d' %d\"",
1100 val_to_str_const(east, lon_typevals, ""), deg, min, sec);
1101 proto_item_append_text(tir, ", %s%d" UTF8_DEGREE_SIGN "%d'%d\")",
1102 val_to_str_const(east, lon_typevals, ""), deg, min, sec);
1104 /* PROCESS ALTITUDE */
1106 ti_alt = proto_tree_add_item(tree, hf_lisp_lcaf_geo_alt, tvb, offset, 4, ENC_NA);
1107 alt = tvb_get_ntohl(tvb, offset);
1108 /* if altitude equals 0x7fffffff then no altitude information encoded */
1109 if (alt == 0x7fffffff) {
1110 proto_item_append_text(ti_alt, ": no value encoded");
1111 } else {
1112 proto_item_append_text(ti_alt, ": %d m", alt);
1113 proto_item_append_text(tir, ", Altitude: %d m", alt);
1115 offset += 4;
1117 /* PROCESS ADDRESS */
1119 /* AFI (2 bytes) */
1120 afi = tvb_get_ntohs(tvb, offset);
1121 proto_tree_add_item(tree, hf_lisp_lcaf_geo_afi, tvb, offset, 2, ENC_BIG_ENDIAN);
1122 offset += 2;
1124 ip_address = get_addr_str(tvb, pinfo, offset, afi, &addr_len);
1125 if (ip_address && afi)
1126 proto_item_append_text(tir, ", Address: %s", ip_address);
1128 switch (afi) {
1129 case AFNUM_RESERVED:
1130 break;
1131 case AFNUM_INET:
1132 proto_tree_add_item(tree, hf_lisp_lcaf_geo_ipv4,
1133 tvb, offset, INET_ADDRLEN, ENC_BIG_ENDIAN);
1134 offset += INET_ADDRLEN;
1135 break;
1136 case AFNUM_INET6:
1137 proto_tree_add_item(tree, hf_lisp_lcaf_geo_ipv6,
1138 tvb, offset, INET6_ADDRLEN, ENC_NA);
1139 offset += INET6_ADDRLEN;
1140 break;
1141 case AFNUM_LCAF:
1142 offset = dissect_lcaf(tvb, pinfo, tree, offset, NULL);
1143 break;
1144 case AFNUM_802:
1145 case AFNUM_EUI48:
1146 proto_tree_add_item(tree, hf_lisp_lcaf_geo_mac,
1147 tvb, offset, EUI48_ADDRLEN, ENC_NA);
1148 offset += EUI48_ADDRLEN;
1149 break;
1150 case AFNUM_DISTNAME:
1151 str_len = tvb_strsize(tvb, offset);
1152 proto_tree_add_item(tree, hf_lisp_lcaf_geo_dn, tvb, offset, str_len, ENC_ASCII);
1153 offset += str_len;
1154 break;
1155 default:
1156 expert_add_info_format(pinfo, tree, &ei_lisp_unexpected_field,
1157 "Unexpected Geo Coordinates AFI (%d), cannot decode", afi);
1159 return offset;
1164 * Dissector code for NAT-Traversal
1166 * 0 1 2 3
1167 * 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1
1168 * +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
1169 * | AFI = 16387 | Rsvd1 | Flags |
1170 * +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
1171 * | Type = 7 | Rsvd2 | 4 + n |
1172 * +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
1173 * | MS UDP Port Number | ETR UDP Port Number |
1174 * +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
1175 * | AFI = x | Global ETR RLOC Address ... |
1176 * +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
1177 * | AFI = x | MS RLOC Address ... |
1178 * +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
1179 * | AFI = x | Private ETR RLOC Address ... |
1180 * +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
1181 * | AFI = x | RTR RLOC Address 1 ... |
1182 * +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
1183 * | AFI = x | RTR RLOC Address n ... |
1184 * +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
1188 static int
1189 // NOLINTNEXTLINE(misc-no-recursion)
1190 dissect_lcaf_natt(tvbuff_t *tvb, packet_info *pinfo, proto_tree *tree,
1191 int offset, uint16_t length)
1193 int i;
1194 int len;
1195 int remaining = length;
1196 const char *global_etr = " of Global ETR: %s";
1197 const char *ms = " of MS: %s";
1198 const char *private_etr = " of Private ETR: %s";
1199 const char *rtr = " of RTR %d: %s";
1201 remaining -= 4;
1203 proto_tree_add_item(tree, hf_lisp_lcaf_natt_msport, tvb, offset, 2, ENC_BIG_ENDIAN);
1204 offset += 2;
1205 remaining -= 2;
1206 proto_tree_add_item(tree, hf_lisp_lcaf_natt_etrport, tvb, offset, 2, ENC_BIG_ENDIAN);
1207 offset += 2;
1208 remaining -= 2;
1210 len = dissect_lcaf_natt_rloc(tvb, pinfo, tree, offset, global_etr, 0);
1211 offset += len;
1212 remaining -= len;
1214 len = dissect_lcaf_natt_rloc(tvb, pinfo, tree, offset, ms, 0);
1215 offset += len;
1216 remaining -= len;
1218 len = dissect_lcaf_natt_rloc(tvb, pinfo, tree, offset, private_etr, 0);
1219 offset += len;
1220 remaining -= len;
1222 i = 1;
1223 while (remaining > 0) {
1224 len = dissect_lcaf_natt_rloc(tvb, pinfo, tree, offset, rtr, i);
1225 offset += len;
1226 remaining -= len;
1227 i++;
1230 return offset;
1235 * Dissector code for Nonce Locator
1237 * 0 1 2 3
1238 * 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1
1239 * +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
1240 * | AFI = 16387 | Rsvd1 | Flags |
1241 * +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
1242 * | Type = 8 | Rsvd2 | 4 + n |
1243 * +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
1244 * | Reserved | Nonce |
1245 * +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
1246 * | AFI = x | Address ... |
1247 * +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
1251 static int
1252 // NOLINTNEXTLINE(misc-no-recursion)
1253 dissect_lcaf_nonce_loc(tvbuff_t *tvb, packet_info *pinfo, proto_tree *tree, int offset, proto_item *tip)
1255 const char *addr;
1256 uint16_t afi, addr_len = 0;
1257 int str_len;
1259 /* Reserved (1 byte) */
1260 proto_tree_add_item(tree, hf_lisp_lcaf_nonce_loc_res, tvb, offset, 1, ENC_BIG_ENDIAN);
1261 proto_item_append_text(tip, ": %d", tvb_get_ntohl(tvb, offset));
1262 offset += 1;
1264 /* Nonce (3 bytes) */
1265 proto_tree_add_item(tree, hf_lisp_lcaf_nonce_loc, tvb, offset, 3, ENC_BIG_ENDIAN);
1266 proto_item_append_text(tip, ": %d", tvb_get_ntohl(tvb, offset));
1267 offset += 3;
1269 /* AFI (2 bytes) */
1270 afi = tvb_get_ntohs(tvb, offset);
1271 proto_tree_add_item(tree, hf_lisp_lcaf_nonce_loc_afi, tvb, offset, 2, ENC_BIG_ENDIAN);
1272 offset += 2;
1274 /* Address */
1275 addr = get_addr_str(tvb, pinfo, offset, afi, &addr_len);
1276 if (addr && afi)
1277 proto_item_append_text(tip, ", Address: %s", addr);
1279 switch (afi) {
1280 case AFNUM_RESERVED:
1281 break;
1282 case AFNUM_INET:
1283 proto_tree_add_item(tree, hf_lisp_lcaf_nonce_loc_ipv4,
1284 tvb, offset, INET_ADDRLEN, ENC_BIG_ENDIAN);
1285 offset += INET_ADDRLEN;
1286 break;
1287 case AFNUM_INET6:
1288 proto_tree_add_item(tree, hf_lisp_lcaf_nonce_loc_ipv6,
1289 tvb, offset, INET6_ADDRLEN, ENC_NA);
1290 offset += INET6_ADDRLEN;
1291 break;
1292 case AFNUM_LCAF:
1293 offset = dissect_lcaf(tvb, pinfo, tree, offset, NULL);
1294 break;
1295 case AFNUM_802:
1296 case AFNUM_EUI48:
1297 proto_tree_add_item(tree, hf_lisp_lcaf_nonce_loc_mac,
1298 tvb, offset, EUI48_ADDRLEN, ENC_NA);
1299 offset += EUI48_ADDRLEN;
1300 break;
1301 case AFNUM_DISTNAME:
1302 str_len = tvb_strsize(tvb, offset);
1303 proto_tree_add_item(tree, hf_lisp_lcaf_nonce_loc_dn, tvb, offset, str_len, ENC_ASCII);
1304 offset += str_len;
1305 break;
1306 default:
1307 expert_add_info_format(pinfo, tree, &ei_lisp_unexpected_field,
1308 "Unexpected Instance ID AFI (%d), cannot decode", afi);
1310 return offset;
1315 * Dissector code for Multicast Group Membership Information
1317 * 0 1 2 3
1318 * 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1
1319 * +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
1320 * | AFI = 16387 | Rsvd1 | Flags |
1321 * +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
1322 * | Type = 9 | Rsvd2 |R|L|J| 8 + n |
1323 * +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
1324 * | Instance-ID |
1325 * +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
1326 * | Reserved | Source MaskLen| Group MaskLen |
1327 * +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
1328 * | AFI = x | Source/Subnet Address ... |
1329 * +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
1330 * | AFI = x | Group Address ... |
1331 * +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
1335 static int
1336 // NOLINTNEXTLINE(misc-no-recursion)
1337 dissect_lcaf_mcast_info(tvbuff_t *tvb, packet_info *pinfo, proto_tree *tree,
1338 int offset, proto_item *tir)
1340 uint8_t src_masklen, grp_masklen;
1341 uint16_t afi, addr_len = 0;
1342 uint32_t iid;
1343 const char *src_str, *grp_str;
1344 proto_item *ti_src, *ti_grp;
1345 proto_tree *src_tree, *grp_tree;
1347 /* Instance ID (4 bytes) */
1348 proto_tree_add_item(tree, hf_lisp_lcaf_mcinfo_iid, tvb, offset, 4, ENC_BIG_ENDIAN);
1349 iid = tvb_get_ntohl(tvb, offset);
1350 offset += 4;
1352 /* Reserved (2 bytes) */
1353 proto_tree_add_item(tree, hf_lisp_lcaf_mcinfo_res, tvb, offset, 2, ENC_BIG_ENDIAN);
1354 offset += 2;
1356 /* Source Mask Length (1 byte) */
1357 proto_tree_add_item(tree, hf_lisp_lcaf_mcinfo_src_masklen, tvb, offset, 1, ENC_BIG_ENDIAN);
1358 src_masklen = tvb_get_uint8(tvb, offset);
1359 offset += 1;
1361 /* Group Mask Length (1 byte) */
1362 proto_tree_add_item(tree, hf_lisp_lcaf_mcinfo_grp_masklen, tvb, offset, 1, ENC_BIG_ENDIAN);
1363 grp_masklen = tvb_get_uint8(tvb, offset);
1364 offset += 1;
1366 ti_src = proto_tree_add_item(tree, hf_lisp_lcaf_mcinfo_src, tvb, offset, 2, ENC_NA);
1367 src_tree = proto_item_add_subtree(ti_src, ett_lisp_lcaf_mcinfo_src);
1369 /* Source/Subnet AFI (2 bytes) */
1370 proto_tree_add_item(src_tree, hf_lisp_lcaf_mcinfo_src_afi, tvb, offset, 2, ENC_BIG_ENDIAN);
1371 afi = tvb_get_ntohs(tvb, offset);
1372 offset += 2;
1374 /* Source/Subnet Address */
1375 src_str = get_addr_str(tvb, pinfo, offset, afi, &addr_len);
1377 switch (afi) {
1378 case AFNUM_INET:
1379 proto_tree_add_item(src_tree, hf_lisp_lcaf_mcinfo_src_ipv4,
1380 tvb, offset, INET_ADDRLEN, ENC_BIG_ENDIAN);
1381 offset += INET_ADDRLEN;
1382 break;
1383 case AFNUM_INET6:
1384 proto_tree_add_item(src_tree, hf_lisp_lcaf_mcinfo_src_ipv6,
1385 tvb, offset, INET6_ADDRLEN, ENC_NA);
1386 offset += INET6_ADDRLEN;
1387 break;
1388 case AFNUM_LCAF:
1389 offset = dissect_lcaf(tvb, pinfo, src_tree, offset, NULL);
1390 break;
1391 default:
1392 expert_add_info_format(pinfo, src_tree, &ei_lisp_unexpected_field,
1393 "Unexpected Source Prefix AFI (%d), cannot decode", afi);
1396 proto_item_append_text(ti_src, ": %s", src_str);
1397 proto_item_set_len(ti_src, 2 + addr_len);
1399 ti_grp = proto_tree_add_item(tree, hf_lisp_lcaf_mcinfo_grp, tvb, offset, 2, ENC_NA);
1400 grp_tree = proto_item_add_subtree(ti_grp, ett_lisp_lcaf_mcinfo_grp);
1402 /* Group AFI (2 bytes) */
1403 proto_tree_add_item(grp_tree, hf_lisp_lcaf_mcinfo_grp_afi, tvb, offset, 2, ENC_BIG_ENDIAN);
1404 afi = tvb_get_ntohs(tvb, offset);
1405 offset += 2;
1407 /* Group Address */
1408 grp_str = get_addr_str(tvb, pinfo, offset, afi, &addr_len);
1410 switch (afi) {
1411 case AFNUM_INET:
1412 proto_tree_add_item(grp_tree, hf_lisp_lcaf_mcinfo_grp_ipv4,
1413 tvb, offset, INET_ADDRLEN, ENC_BIG_ENDIAN);
1414 offset += INET_ADDRLEN;
1415 break;
1416 case AFNUM_INET6:
1417 proto_tree_add_item(grp_tree, hf_lisp_lcaf_mcinfo_grp_ipv6,
1418 tvb, offset, INET6_ADDRLEN, ENC_NA);
1419 offset += INET6_ADDRLEN;
1420 break;
1421 case AFNUM_LCAF:
1422 offset = dissect_lcaf(tvb, pinfo, grp_tree, offset, NULL);
1423 break;
1424 default:
1425 expert_add_info_format(pinfo, grp_tree, &ei_lisp_unexpected_field,
1426 "Unexpected Destination Prefix AFI (%d), cannot decode", afi);
1429 proto_item_append_text(ti_grp, ": %s", grp_str);
1430 proto_item_set_len(ti_grp, 2 + addr_len);
1432 proto_item_append_text(tir, " ([%d], %s/%d, %s/%d)", iid, src_str, src_masklen, grp_str, grp_masklen);
1433 return offset;
1438 * Dissector code for Explicit Locator Path
1440 * 0 1 2 3
1441 * 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1
1442 * +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
1443 * | AFI = 16387 | Rsvd1 | Flags |
1444 * +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
1445 * | Type = 10 | Rsvd2 | n |
1446 * +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
1447 * | Rsvd3 |L|P|S| AFI = x |
1448 * +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
1449 * | Reencap Hop 1 ... |
1450 * +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
1451 * | Rsvd3 |L|P|S| AFI = x |
1452 * +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
1453 * | Reencap Hop k ... |
1454 * +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
1459 static int
1460 // NOLINTNEXTLINE(misc-no-recursion)
1461 dissect_lcaf_elp(tvbuff_t *tvb, packet_info *pinfo, proto_tree *tree,
1462 int offset, uint16_t length, proto_item *tir)
1464 int len;
1465 int remaining = length;
1466 int i = 1;
1468 while (remaining > 0) {
1469 len = dissect_lcaf_elp_hop(tvb, pinfo, tree, offset, i, tir);
1470 offset += len;
1471 remaining -= len;
1472 i++;
1475 return offset;
1480 * Dissector code for Source/Destination 2-Tuple Lookups
1482 * 0 1 2 3
1483 * 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1
1484 * +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
1485 * | AFI = 16387 | Rsvd1 | Flags |
1486 * +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
1487 * | Type = 12 | Rsvd2 | 4 + n |
1488 * +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
1489 * | Reserved | Source-ML | Dest-ML |
1490 * +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
1491 * | AFI = x | Source-Prefix ... |
1492 * +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
1493 * | AFI = x | Destination-Prefix ... |
1494 * +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
1498 static int
1499 // NOLINTNEXTLINE(misc-no-recursion)
1500 dissect_lcaf_src_dst_key(tvbuff_t *tvb, packet_info *pinfo, proto_tree *tree,
1501 int offset, proto_item *tir)
1503 uint8_t src_masklen, dst_masklen;
1504 uint16_t afi, addr_len = 0;
1505 const char *src_str, *dst_str;
1506 proto_item *ti_src, *ti_dst;
1507 proto_tree *src_tree, *dst_tree;
1509 /* Reserved (2 bytes) */
1510 proto_tree_add_item(tree, hf_lisp_lcaf_srcdst_res, tvb, offset, 2, ENC_BIG_ENDIAN);
1511 offset += 2;
1513 /* Source Prefix Mask Length (1 byte) */
1514 proto_tree_add_item(tree, hf_lisp_lcaf_srcdst_src_masklen, tvb, offset, 1, ENC_BIG_ENDIAN);
1515 src_masklen = tvb_get_uint8(tvb, offset);
1516 offset += 1;
1518 /* Destination Prefix Mask Length (1 byte) */
1519 proto_tree_add_item(tree, hf_lisp_lcaf_srcdst_dst_masklen, tvb, offset, 1, ENC_BIG_ENDIAN);
1520 dst_masklen = tvb_get_uint8(tvb, offset);
1521 offset += 1;
1523 ti_src = proto_tree_add_item(tree, hf_lisp_lcaf_srcdst_src, tvb, offset, 2, ENC_NA);
1524 src_tree = proto_item_add_subtree(ti_src, ett_lisp_lcaf_srcdst_src);
1526 /* Source Prefix AFI (2 bytes) */
1527 proto_tree_add_item(src_tree, hf_lisp_lcaf_srcdst_src_afi, tvb, offset, 2, ENC_BIG_ENDIAN);
1528 afi = tvb_get_ntohs(tvb, offset);
1529 offset += 2;
1531 /* Source Prefix */
1532 src_str = get_addr_str(tvb, pinfo, offset, afi, &addr_len);
1534 switch (afi) {
1535 case AFNUM_INET:
1536 proto_tree_add_item(src_tree, hf_lisp_lcaf_srcdst_src_ipv4,
1537 tvb, offset, INET_ADDRLEN, ENC_BIG_ENDIAN);
1538 offset += INET_ADDRLEN;
1539 break;
1540 case AFNUM_INET6:
1541 proto_tree_add_item(src_tree, hf_lisp_lcaf_srcdst_src_ipv6,
1542 tvb, offset, INET6_ADDRLEN, ENC_NA);
1543 offset += INET6_ADDRLEN;
1544 break;
1545 case AFNUM_LCAF:
1546 offset = dissect_lcaf(tvb, pinfo, src_tree, offset, NULL);
1547 break;
1548 case AFNUM_802:
1549 case AFNUM_EUI48:
1550 proto_tree_add_item(src_tree, hf_lisp_lcaf_srcdst_src_mac,
1551 tvb, offset, EUI48_ADDRLEN, ENC_NA);
1552 offset += EUI48_ADDRLEN;
1553 break;
1554 default:
1555 expert_add_info_format(pinfo, src_tree, &ei_lisp_unexpected_field,
1556 "Unexpected Source Prefix AFI (%d), cannot decode", afi);
1559 proto_item_append_text(ti_src, ": %s", src_str);
1560 proto_item_set_len(ti_src, 2 + addr_len);
1562 ti_dst = proto_tree_add_item(tree, hf_lisp_lcaf_srcdst_dst, tvb, offset, 2, ENC_NA);
1563 dst_tree = proto_item_add_subtree(ti_dst, ett_lisp_lcaf_srcdst_dst);
1565 /* Destination Prefix AFI (2 bytes) */
1566 proto_tree_add_item(dst_tree, hf_lisp_lcaf_srcdst_dst_afi, tvb, offset, 2, ENC_BIG_ENDIAN);
1567 afi = tvb_get_ntohs(tvb, offset);
1568 offset += 2;
1570 /* Destination Prefix */
1571 dst_str = get_addr_str(tvb, pinfo, offset, afi, &addr_len);
1573 switch (afi) {
1574 case AFNUM_INET:
1575 proto_tree_add_item(dst_tree, hf_lisp_lcaf_srcdst_dst_ipv4,
1576 tvb, offset, INET_ADDRLEN, ENC_BIG_ENDIAN);
1577 offset += INET_ADDRLEN;
1578 break;
1579 case AFNUM_INET6:
1580 proto_tree_add_item(dst_tree, hf_lisp_lcaf_srcdst_dst_ipv6,
1581 tvb, offset, INET6_ADDRLEN, ENC_NA);
1582 offset += INET6_ADDRLEN;
1583 break;
1584 case AFNUM_LCAF:
1585 offset = dissect_lcaf(tvb, pinfo, dst_tree, offset, NULL);
1586 break;
1587 case AFNUM_802:
1588 case AFNUM_EUI48:
1589 proto_tree_add_item(dst_tree, hf_lisp_lcaf_srcdst_dst_mac,
1590 tvb, offset, EUI48_ADDRLEN, ENC_NA);
1591 offset += EUI48_ADDRLEN;
1592 break;
1593 default:
1594 expert_add_info_format(pinfo, dst_tree, &ei_lisp_unexpected_field,
1595 "Unexpected Destination Prefix AFI (%d), cannot decode", afi);
1598 proto_item_append_text(ti_dst, ": %s", dst_str);
1599 proto_item_set_len(ti_dst, 2 + addr_len);
1601 proto_item_append_text(tir, " (%s/%d, %s/%d)", src_str, src_masklen, dst_str, dst_masklen);
1602 return offset;
1607 * Dissector code for Replication List Entries for Multicast Forwarding
1609 * 0 1 2 3
1610 * 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1
1611 * +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
1612 * | AFI = 16387 | Rsvd1 | Flags |
1613 * +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
1614 * | Type = 13 | Rsvd2 | 4 + n |
1615 * +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
1616 * | Rsvd3 | Rsvd4 | Level Value |
1617 * +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
1618 * | AFI = x | RTR/ETR #1 ... |
1619 * +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
1620 * | Rsvd3 | Rsvd4 | Level Value |
1621 * +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
1622 * | AFI = x | RTR/ETR #n ... |
1623 * +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
1627 static int
1628 // NOLINTNEXTLINE(misc-no-recursion)
1629 dissect_lcaf_rle(tvbuff_t *tvb, packet_info *pinfo, proto_tree *tree,
1630 int offset, uint16_t length, proto_item *tir)
1632 int len;
1633 int remaining = length;
1634 int i = 1;
1636 while (remaining > 0) {
1637 len = dissect_lcaf_rle_entry(tvb, pinfo, tree, offset, i, tir);
1638 offset += len;
1639 remaining -= len;
1640 i++;
1643 return offset;
1648 * Dissector code for Key/Value Address Pairs
1650 * 0 1 2 3
1651 * 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1
1652 * +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
1653 * | AFI = 16387 | Rsvd1 | Flags |
1654 * +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
1655 * | Type = 15 | Rsvd2 | n |
1656 * +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
1657 * | AFI = x | Address as Key ... |
1658 * +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
1659 * | AFI = x | Address as Value ... |
1660 * +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
1664 static int
1665 // NOLINTNEXTLINE(misc-no-recursion)
1666 dissect_lcaf_kv_addr_pair(tvbuff_t *tvb, packet_info *pinfo, proto_tree *tree,
1667 int offset)
1669 uint16_t afi, addr_len = 0;
1670 const char *key_str, *value_str;
1671 proto_item *ti_key, *ti_value;
1672 proto_tree *key_tree, *value_tree;
1673 int str_len;
1675 ti_key = proto_tree_add_item(tree, hf_lisp_lcaf_kv_key, tvb, offset, 2, ENC_NA);
1676 key_tree = proto_item_add_subtree(ti_key, ett_lisp_lcaf_kv_key);
1678 /* Key AFI (2 bytes) */
1679 proto_tree_add_item(key_tree, hf_lisp_lcaf_kv_key_afi, tvb, offset, 2, ENC_BIG_ENDIAN);
1680 afi = tvb_get_ntohs(tvb, offset);
1681 offset += 2;
1683 /* Key */
1684 key_str = get_addr_str(tvb, pinfo, offset, afi, &addr_len);
1686 switch (afi) {
1687 case AFNUM_INET:
1688 proto_tree_add_item(key_tree, hf_lisp_lcaf_kv_key_ipv4,
1689 tvb, offset, INET_ADDRLEN, ENC_BIG_ENDIAN);
1690 offset += INET_ADDRLEN;
1691 break;
1692 case AFNUM_INET6:
1693 proto_tree_add_item(key_tree, hf_lisp_lcaf_kv_key_ipv6,
1694 tvb, offset, INET6_ADDRLEN, ENC_NA);
1695 offset += INET6_ADDRLEN;
1696 break;
1697 case AFNUM_LCAF:
1698 offset = dissect_lcaf(tvb, pinfo, key_tree, offset, NULL);
1699 break;
1700 case AFNUM_802:
1701 case AFNUM_EUI48:
1702 proto_tree_add_item(key_tree, hf_lisp_lcaf_kv_key_mac,
1703 tvb, offset, EUI48_ADDRLEN, ENC_NA);
1704 offset += EUI48_ADDRLEN;
1705 break;
1706 case AFNUM_DISTNAME:
1707 str_len = tvb_strsize(tvb, offset);
1708 proto_tree_add_item(key_tree, hf_lisp_lcaf_kv_key_dn, tvb, offset, str_len, ENC_ASCII);
1709 offset += str_len;
1710 break;
1711 default:
1712 expert_add_info_format(pinfo, key_tree, &ei_lisp_unexpected_field,
1713 "Unexpected Key AFI (%d), cannot decode", afi);
1716 proto_item_append_text(ti_key, ": %s", key_str);
1717 proto_item_set_len(ti_key, 2 + addr_len);
1719 ti_value = proto_tree_add_item(tree, hf_lisp_lcaf_kv_value, tvb, offset, 2, ENC_NA);
1720 value_tree = proto_item_add_subtree(ti_value, ett_lisp_lcaf_kv_value);
1722 /* Value AFI (2 bytes) */
1723 proto_tree_add_item(value_tree, hf_lisp_lcaf_kv_value_afi, tvb, offset, 2, ENC_BIG_ENDIAN);
1724 afi = tvb_get_ntohs(tvb, offset);
1725 offset += 2;
1727 /* Value */
1728 value_str = get_addr_str(tvb, pinfo, offset, afi, &addr_len);
1730 switch (afi) {
1731 case AFNUM_INET:
1732 proto_tree_add_item(value_tree, hf_lisp_lcaf_kv_value_ipv4,
1733 tvb, offset, INET_ADDRLEN, ENC_BIG_ENDIAN);
1734 offset += INET_ADDRLEN;
1735 break;
1736 case AFNUM_INET6:
1737 proto_tree_add_item(value_tree, hf_lisp_lcaf_kv_value_ipv6,
1738 tvb, offset, INET6_ADDRLEN, ENC_NA);
1739 offset += INET6_ADDRLEN;
1740 break;
1741 case AFNUM_LCAF:
1742 offset = dissect_lcaf(tvb, pinfo, value_tree, offset, NULL);
1743 break;
1744 case AFNUM_802:
1745 case AFNUM_EUI48:
1746 proto_tree_add_item(value_tree, hf_lisp_lcaf_kv_value_mac,
1747 tvb, offset, EUI48_ADDRLEN, ENC_NA);
1748 offset += EUI48_ADDRLEN;
1749 break;
1750 case AFNUM_DISTNAME:
1751 str_len = tvb_strsize(tvb, offset);
1752 proto_tree_add_item(value_tree, hf_lisp_lcaf_kv_value_dn, tvb, offset, str_len, ENC_ASCII);
1753 offset += str_len;
1754 break;
1755 default:
1756 expert_add_info_format(pinfo, value_tree, &ei_lisp_unexpected_field,
1757 "Unexpected Value AFI (%d), cannot decode", afi);
1760 proto_item_append_text(ti_value, ": %s", value_str);
1761 proto_item_set_len(ti_value, 2 + addr_len);
1763 return offset;
1768 * Dissector code for Vendor Specific LCAF
1770 * 0 1 2 3
1771 * 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1
1772 * +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
1773 * | AFI = 16387 | Rsvd1 | Flags |
1774 * +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
1775 * | Type = 255 | Rsvd2 | Length |
1776 * +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
1777 * | Rsvd3 | Organizationally Unique Identifier (OUI) |
1778 * +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
1779 * | Internal format... |
1780 * +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
1784 static int
1785 dissect_lcaf_vendor(tvbuff_t *tvb, packet_info *pinfo, proto_tree *tree,
1786 int offset, uint16_t length)
1788 int len;
1789 proto_item *ti_vendor;
1790 proto_tree *vendor_tree;
1792 /* Reserved (1 byte) */
1793 proto_tree_add_item(tree, hf_lisp_lcaf_vendor_res, tvb, offset, 1, ENC_BIG_ENDIAN);
1794 offset += 1;
1796 /* Organizationally Unique Identifier (3 bytes) */
1797 proto_tree_add_item(tree, hf_lisp_lcaf_vendor_oui, tvb, offset, 3, ENC_BIG_ENDIAN);
1798 offset += 3;
1800 /* Vendor Data */
1801 len = length - 4;
1802 ti_vendor = proto_tree_add_item(tree, hf_lisp_lcaf_vendor_data, tvb, offset, len, ENC_NA);
1803 vendor_tree = proto_item_add_subtree(ti_vendor, ett_lisp_lcaf_vendor);
1804 expert_add_info_format(pinfo, vendor_tree, &ei_lisp_undecoded,
1805 "Look up the vendor's OUI (IEEE 802-2001) and contact them for support on decoding this field");
1806 offset += len;
1808 return offset;
1813 * Dissector code for LISP Canonical Address Format (LCAF)
1815 * 0 1 2 3
1816 * 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1
1817 * +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
1818 * | AFI = 16387 | Rsvd1 | Flags |
1819 * +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
1820 * | Type | Rsvd2 | Length |
1821 * +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
1823 * Type 0: Null Body Type
1824 * Type 1: AFI List Type
1825 * Type 2: Instance ID Type
1826 * Type 3: AS Number Type
1827 * Type 4: Application Data Type
1828 * Type 5: Geo Coordinates Type
1829 * Type 6: Opaque Key Type
1830 * Type 7: NAT-Traversal Type
1831 * Type 8: Nonce Locator Type
1832 * Type 9: Multicast Info Type
1833 * Type 10: Explicit Locator Path Type
1834 * Type 11: Security Key Type
1835 * Type 12: Source/Dest Key Type
1836 * Type 13: Replication List Entry Type
1837 * Type 14: JSON Data Model Type
1838 * Type 15: Key/Value Address Pair Type
1839 * Type 255: Vendor Specific LCAF
1844 // NOLINTNEXTLINE(misc-no-recursion)
1845 dissect_lcaf(tvbuff_t *tvb, packet_info *pinfo, proto_tree *tree, int offset, proto_item *tip)
1847 uint8_t lcaf_type;
1848 uint16_t len;
1849 proto_item *tir, *ti_header, *ti_flags, *ti;
1850 proto_tree *lcaf_tree, *lcaf_header_tree, *flags_tree;
1851 tvbuff_t *payload_tvb;
1853 len = tvb_get_ntohs(tvb, offset + 4);
1855 tir = proto_tree_add_item(tree, hf_lisp_lcaf, tvb, offset, LCAF_HEADER_LEN + len, ENC_NA);
1856 lcaf_tree = proto_item_add_subtree(tir, ett_lisp_lcaf);
1858 ti_header = proto_tree_add_item(lcaf_tree, hf_lisp_lcaf_header, tvb, offset, LCAF_HEADER_LEN, ENC_NA);
1859 lcaf_header_tree = proto_item_add_subtree(ti_header, ett_lisp_lcaf_header);
1861 /* Reserved bits (8 bits) */
1862 proto_tree_add_item(lcaf_header_tree, hf_lisp_lcaf_res1, tvb, offset, 1, ENC_BIG_ENDIAN);
1863 offset += 1;
1865 /* Flags (8 bits) */
1866 proto_tree_add_item(lcaf_header_tree, hf_lisp_lcaf_flags, tvb, offset, 1, ENC_BIG_ENDIAN);
1867 offset += 1;
1869 /* Type (8 bits) */
1870 proto_tree_add_item(lcaf_header_tree, hf_lisp_lcaf_type, tvb, offset, 1, ENC_BIG_ENDIAN);
1871 lcaf_type = tvb_get_uint8(tvb, offset);
1872 proto_item_append_text(tir, ": %s", val_to_str(lcaf_type, lcaf_typevals, "Unknown (%d)"));
1873 offset += 1;
1875 if (lcaf_type == LCAF_MCAST_INFO) {
1876 ti_flags = proto_tree_add_item(lcaf_header_tree, hf_lisp_lcaf_mcinfo_flags, tvb, offset, 1, ENC_BIG_ENDIAN);
1877 flags_tree = proto_item_add_subtree(ti_flags, ett_lisp_lcaf_mcinfo_flags);
1879 /* Reserved (5 bits) */
1880 proto_tree_add_item(flags_tree, hf_lisp_lcaf_mcinfo_flags_res, tvb, offset, 1, ENC_BIG_ENDIAN);
1882 /* Flags (3 bits) */
1883 proto_tree_add_item(flags_tree, hf_lisp_lcaf_mcinfo_flags_rp, tvb, offset, 1, ENC_NA);
1884 proto_tree_add_item(flags_tree, hf_lisp_lcaf_mcinfo_flags_leave, tvb, offset, 1, ENC_NA);
1885 proto_tree_add_item(flags_tree, hf_lisp_lcaf_mcinfo_flags_join, tvb, offset, 1, ENC_NA);
1886 } else {
1887 /* Reserved (8 bits) */
1888 proto_tree_add_item(lcaf_header_tree, hf_lisp_lcaf_res2, tvb, offset, 1, ENC_BIG_ENDIAN);
1890 offset += 1;
1892 /* Length (16 bits) */
1893 proto_tree_add_item(lcaf_header_tree, hf_lisp_lcaf_length, tvb, offset, 2, ENC_BIG_ENDIAN);
1894 offset += 2;
1896 payload_tvb = tvb_new_subset_length(tvb, 0, offset + len);
1897 ti = (tip) ? tip : tir;
1899 increment_dissection_depth(pinfo);
1900 switch (lcaf_type) {
1901 case LCAF_NULL:
1902 break;
1903 case LCAF_AFI_LIST:
1904 offset = dissect_lcaf_afi_list(payload_tvb, pinfo, lcaf_tree, offset, len);
1905 break;
1906 case LCAF_IID:
1907 offset = dissect_lcaf_iid(payload_tvb, pinfo, lcaf_tree, offset, ti);
1908 break;
1909 case LCAF_ASN:
1910 offset = dissect_lcaf_asn(payload_tvb, pinfo, lcaf_tree, offset, ti);
1911 break;
1912 case LCAF_GEO:
1913 offset = dissect_lcaf_geo(payload_tvb, pinfo, lcaf_tree, offset, ti);
1914 break;
1915 case LCAF_NATT:
1916 offset = dissect_lcaf_natt(payload_tvb, pinfo, lcaf_tree, offset, len);
1917 break;
1918 case LCAF_NONCE_LOC:
1919 offset = dissect_lcaf_nonce_loc(payload_tvb, pinfo, lcaf_tree, offset, ti);
1920 break;
1921 case LCAF_MCAST_INFO:
1922 offset = dissect_lcaf_mcast_info(payload_tvb, pinfo, lcaf_tree, offset, ti);
1923 break;
1924 case LCAF_ELP:
1925 offset = dissect_lcaf_elp(payload_tvb, pinfo, lcaf_tree, offset, len, ti);
1926 break;
1927 case LCAF_SRC_DST_KEY:
1928 offset = dissect_lcaf_src_dst_key(payload_tvb, pinfo, lcaf_tree, offset, ti);
1929 break;
1930 case LCAF_RLE:
1931 offset = dissect_lcaf_rle(payload_tvb, pinfo, lcaf_tree, offset, len, ti);
1932 break;
1933 case LCAF_KV_ADDR_PAIR:
1934 offset = dissect_lcaf_kv_addr_pair(payload_tvb, pinfo, lcaf_tree, offset);
1935 break;
1936 case LCAF_VENDOR:
1937 offset = dissect_lcaf_vendor(payload_tvb, pinfo, lcaf_tree, offset, len);
1938 break;
1939 default:
1940 proto_tree_add_expert(tree, pinfo, &ei_lisp_undecoded, tvb, offset, len);
1941 return offset + len;
1943 decrement_dissection_depth(pinfo);
1944 return offset;
1949 * Dissector code for locator records within control packets
1951 * 0 1 2 3
1952 * 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1
1953 * +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
1954 * | Priority | Weight | M Priority | M Weight |
1955 * +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
1956 * | Unused Flags |L|p|R| Loc-AFI |
1957 * +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
1958 * | Locator |
1959 * +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
1963 static int
1964 dissect_lisp_locator(tvbuff_t *tvb, packet_info *pinfo, proto_tree *lisp_mapping_tree, int rec)
1966 int offset = 0;
1967 uint16_t addr_len = 0;
1968 uint8_t prio;
1969 uint8_t weight;
1970 uint8_t m_prio;
1971 uint8_t m_weight;
1972 uint16_t flags;
1973 uint16_t loc_afi;
1974 const char *locator;
1975 proto_item *tir, *ti_flags;
1976 proto_tree *lisp_lcaf_tree, *lisp_loc_tree, *lisp_flags_tree;
1978 tir = proto_tree_add_item(lisp_mapping_tree, hf_lisp_loc, tvb, offset, 8, ENC_NA);
1980 lisp_loc_tree = proto_item_add_subtree(tir, ett_lisp_loc);
1982 proto_tree_add_item(lisp_loc_tree, hf_lisp_loc_priority, tvb, offset, 1, ENC_BIG_ENDIAN);
1983 prio = tvb_get_uint8(tvb, offset);
1984 offset += 1;
1986 proto_tree_add_item(lisp_loc_tree, hf_lisp_loc_weight, tvb, offset, 1, ENC_BIG_ENDIAN);
1987 weight = tvb_get_uint8(tvb, offset);
1988 offset += 1;
1990 proto_tree_add_item(lisp_loc_tree, hf_lisp_loc_mpriority, tvb, offset, 1, ENC_BIG_ENDIAN);
1991 m_prio = tvb_get_uint8(tvb, offset);
1992 offset += 1;
1994 proto_tree_add_item(lisp_loc_tree, hf_lisp_loc_mweight, tvb, offset, 1, ENC_BIG_ENDIAN);
1995 m_weight = tvb_get_uint8(tvb, offset);
1996 offset += 1;
1998 ti_flags = proto_tree_add_item(lisp_loc_tree, hf_lisp_loc_flags, tvb, offset, 2, ENC_BIG_ENDIAN);
1999 lisp_flags_tree = proto_item_add_subtree(ti_flags, ett_lisp_loc_flags);
2000 proto_tree_add_item(lisp_flags_tree, hf_lisp_loc_flags_res, tvb, offset, 2, ENC_BIG_ENDIAN);
2001 proto_tree_add_item(lisp_flags_tree, hf_lisp_loc_flags_local, tvb, offset, 2, ENC_BIG_ENDIAN);
2002 proto_tree_add_item(lisp_flags_tree, hf_lisp_loc_flags_probe, tvb, offset, 2, ENC_BIG_ENDIAN);
2003 proto_tree_add_item(lisp_flags_tree, hf_lisp_loc_flags_reach, tvb, offset, 2, ENC_BIG_ENDIAN);
2004 flags = tvb_get_ntohs(tvb, offset);
2005 offset += 2;
2007 proto_tree_add_item(lisp_loc_tree, hf_lisp_loc_afi, tvb, offset, 2, ENC_BIG_ENDIAN);
2008 loc_afi = tvb_get_ntohs(tvb, offset);
2009 offset += 2;
2011 locator = get_addr_str(tvb, pinfo, offset, loc_afi, &addr_len);
2013 if (locator == NULL) {
2014 expert_add_info_format(pinfo, lisp_mapping_tree, &ei_lisp_unexpected_field,
2015 "Unexpected locator AFI (%d), cannot decode", loc_afi);
2016 return offset;
2019 if (loc_afi == AFNUM_LCAF) {
2020 /* Create a sub-tree for the mapping */
2021 lisp_lcaf_tree = proto_item_add_subtree(tir, ett_lisp_lcaf);
2022 offset = dissect_lcaf(tvb, pinfo, lisp_lcaf_tree, offset, NULL);
2023 } else {
2024 proto_tree_add_string(lisp_loc_tree, hf_lisp_loc_locator, tvb, offset, addr_len, locator);
2025 offset += addr_len;
2028 proto_item_append_text(tir, " %d, %sRLOC: %s%s, %s, Priority/Weight: %d/%d, Multicast Priority/Weight: %d/%d",
2029 rec,
2030 (flags&LOCAL_BIT_MASK) ? "Local " : "",
2031 locator,
2032 (flags&PROBE_BIT_MASK) ? " (probed)" : "",
2033 (flags&REACH_BIT_MASK) ? "Reachable" : "Unreachable",
2034 prio, weight, m_prio, m_weight);
2035 proto_item_set_len(tir, 8 + addr_len);
2037 return offset;
2042 * Dissector code for mapping records within control packets
2044 * 0 1 2 3
2045 * 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1
2046 * +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
2047 * | Record TTL |
2048 * +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
2049 * | Locator Count | EID mask-len | ACT |A| Reserved |
2050 * +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
2051 * | Rsvd | Map-Version Number | EID-AFI |
2052 * +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
2053 * | EID-prefix |
2054 * +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
2059 dissect_lisp_mapping(tvbuff_t *tvb, packet_info *pinfo, proto_tree *lisp_tree,
2060 uint8_t rec_cnt, int rec, bool referral, int offset, proto_item *tim)
2062 int i;
2063 int str_len;
2064 uint16_t addr_len = 0;
2065 uint8_t prefix_mask, loc_cnt;
2066 uint16_t flags;
2067 uint16_t act;
2068 uint16_t prefix_afi, eid_afi;
2069 const char *prefix;
2070 proto_item *tir;
2071 proto_tree *lisp_mapping_tree, *lcaf_prefix_tree;
2073 prefix_mask = tvb_get_uint8(tvb, offset + 5);
2074 flags = tvb_get_ntohs(tvb, offset + 6);
2075 prefix_afi = tvb_get_ntohs(tvb, offset + 10);
2077 act = flags & LISP_MAP_ACT;
2078 act >>= 13;
2080 prefix = get_addr_str(tvb, pinfo, offset + 12, prefix_afi, &addr_len);
2082 if (prefix == NULL) {
2083 expert_add_info_format(pinfo, lisp_tree, &ei_lisp_unexpected_field,
2084 "Unexpected EID prefix AFI (%d), cannot decode", prefix_afi);
2085 return offset;
2087 tir = proto_tree_add_item(lisp_tree, hf_lisp_mapping, tvb, offset, 12 + addr_len, ENC_NA);
2088 if (tim) {
2089 proto_item_append_text(tim, " for %s/%d", prefix, prefix_mask);
2092 /* Update the INFO column if there is only one record */
2093 if (rec_cnt == 1)
2094 col_append_fstr(pinfo->cinfo, COL_INFO, " for %s/%d",
2095 prefix, prefix_mask);
2097 /* Create a sub-tree for the mapping */
2098 lisp_mapping_tree = proto_item_add_subtree(tir, ett_lisp_mapping);
2099 proto_item_append_text(tir, " %d, EID Prefix: %s/%d", rec, prefix, prefix_mask);
2101 /* TTL (32 bits) */
2102 proto_tree_add_item(lisp_mapping_tree, hf_lisp_mapping_ttl, tvb, offset, 4, ENC_BIG_ENDIAN);
2103 if (tvb_get_ntohl(tvb, offset) == 0xFFFFFFFF) {
2104 proto_item_append_text(tir, ", TTL: Unlimited");
2105 } else {
2106 proto_item_append_text(tir, ", TTL: %d", tvb_get_ntohl(tvb, offset));
2108 offset += 4;
2110 /* Locator count (8 bits) */
2111 proto_tree_add_item(lisp_mapping_tree, hf_lisp_mapping_loccnt, tvb, offset, 1, ENC_BIG_ENDIAN);
2112 loc_cnt = tvb_get_uint8(tvb, offset);
2113 offset += 1;
2115 /* EID mask length (8 bits) */
2116 proto_tree_add_item(lisp_mapping_tree, hf_lisp_mapping_eid_masklen, tvb, offset, 1, ENC_BIG_ENDIAN);
2117 offset += 1;
2119 /* Action (3 bits) */
2120 proto_tree_add_item(lisp_mapping_tree, hf_lisp_mapping_act, tvb, offset, 2, ENC_BIG_ENDIAN);
2121 proto_item_append_text(tir, ", %s%s%s",
2122 (referral) ? "" : "Action: ",
2123 val_to_str(act, (referral) ? referral_actions : mapping_actions, "Invalid action code (%d)"),
2124 (referral&&(flags&REFERRAL_INCOMPLETE)) ? " (Incomplete)" : "");
2126 /* Authoritative bit */
2127 proto_tree_add_item(lisp_mapping_tree, hf_lisp_mapping_auth, tvb, offset, 2, ENC_BIG_ENDIAN);
2128 if (flags&LISP_MAP_AUTH) {
2129 proto_item_append_text(tir, ", Authoritative");
2130 } else {
2131 proto_item_append_text(tir, ", Not Authoritative");
2134 /* Incomplete bit in Map-Referrals */
2135 if (referral)
2136 proto_tree_add_item(lisp_mapping_tree, hf_lisp_referral_incomplete, tvb, offset, 2, ENC_BIG_ENDIAN);
2138 /* Reserved (11 bits) */
2139 proto_tree_add_item(lisp_mapping_tree, hf_lisp_mapping_res1, tvb, offset, 2, ENC_BIG_ENDIAN);
2140 offset += 2;
2142 if (referral) {
2143 /* SigCnt (4 bits) */
2144 proto_tree_add_item(lisp_mapping_tree, hf_lisp_referral_sigcnt, tvb, offset, 2, ENC_BIG_ENDIAN);
2145 } else {
2146 /* Reserved (4 bits) */
2147 proto_tree_add_item(lisp_mapping_tree, hf_lisp_mapping_res2, tvb, offset, 2, ENC_BIG_ENDIAN);
2150 /* Map-Version Number (12 bits) */
2151 proto_tree_add_item(lisp_mapping_tree, hf_lisp_mapping_ver, tvb, offset, 2, ENC_BIG_ENDIAN);
2152 offset += 2;
2154 /* EID prefix AFI (16 bits) */
2155 eid_afi = tvb_get_ntohs(tvb, offset);
2156 proto_tree_add_item(lisp_mapping_tree, hf_lisp_mapping_eid_afi, tvb, offset, 2, ENC_BIG_ENDIAN);
2157 offset += 2;
2159 /* EID */
2160 switch (eid_afi) {
2161 case AFNUM_INET:
2162 proto_tree_add_item(lisp_mapping_tree, hf_lisp_mapping_eid_ipv4, tvb, offset, INET_ADDRLEN, ENC_BIG_ENDIAN);
2163 offset += INET_ADDRLEN;
2164 break;
2165 case AFNUM_INET6:
2166 proto_tree_add_item(lisp_mapping_tree, hf_lisp_mapping_eid_ipv6, tvb, offset, INET6_ADDRLEN, ENC_NA);
2167 offset += INET6_ADDRLEN;
2168 break;
2169 case AFNUM_LCAF:
2170 lcaf_prefix_tree = proto_tree_add_subtree_format(lisp_mapping_tree, tvb, offset, addr_len, ett_lisp_lcaf, NULL, "EID Prefix: %s", prefix);
2171 dissect_lcaf(tvb, pinfo, lcaf_prefix_tree, offset, NULL);
2172 offset += addr_len;
2173 break;
2174 case AFNUM_802:
2175 case AFNUM_EUI48:
2176 proto_tree_add_item(lisp_mapping_tree, hf_lisp_mapping_eid_mac, tvb, offset, EUI48_ADDRLEN, ENC_NA);
2177 offset += EUI48_ADDRLEN;
2178 break;
2179 case AFNUM_DISTNAME:
2180 str_len = tvb_strsize(tvb, offset);
2181 proto_tree_add_item(lisp_mapping_tree, hf_lisp_mapping_eid_dn, tvb, offset, str_len, ENC_ASCII);
2182 offset += str_len;
2183 break;
2186 /* Locators */
2187 for(i=0; i < loc_cnt; i++) {
2188 tvbuff_t *loc_tvb;
2189 int len = 0;
2191 loc_tvb = tvb_new_subset_remaining(tvb, offset);
2192 len = dissect_lisp_locator(loc_tvb, pinfo, lisp_mapping_tree, i+1);
2193 offset += len;
2196 return offset;
2201 * Dissector code for Map-Request type control packets
2203 * 0 1 2 3
2204 * 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1
2205 * +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
2206 * |Type=1 |A|M|P|S|p|s| Reserved | IRC | Record Count |
2207 * +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
2208 * | Nonce . . . |
2209 * +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
2210 * | . . . Nonce |
2211 * +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
2212 * | Source-EID-AFI | Source EID Address ... |
2213 * +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
2214 * | ITR-RLOC-AFI 1 | ITR-RLOC Address 1 ... |
2215 * +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
2216 * | ... |
2217 * +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
2218 * | ITR-RLOC-AFI n | ITR-RLOC Address n ... |
2219 * +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
2220 * / | Reserved | EID mask-len | EID-prefix-AFI |
2221 * Rec +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
2222 * \ | EID-prefix ... |
2223 * +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
2224 * | Map-Reply Record ... |
2225 * +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
2229 static void
2230 dissect_lisp_map_request(tvbuff_t *tvb, packet_info *pinfo, proto_tree *lisp_tree)
2232 int i;
2233 uint16_t addr_len = 0;
2234 int offset = 0;
2235 uint16_t flags;
2236 bool mrep;
2237 bool smr;
2238 bool probe;
2239 bool pitr;
2240 bool smr_invoked;
2241 uint8_t itr_rec_cnt = 0;
2242 uint8_t rec_cnt = 0;
2243 uint16_t src_eid_afi;
2244 const char *src_eid;
2245 proto_item *ti_flags;
2246 proto_tree *flags_tree, *lcaf_src_eid_tree, *lcaf_prefix_tree;
2247 tvbuff_t *next_tvb;
2249 /* Flags (6 bits)*/
2250 flags = tvb_get_ntohs(tvb, offset);
2251 mrep = flags & (MAP_REQ_FLAG_M >> 8);
2252 smr = flags & (MAP_REQ_FLAG_S >> 8);
2253 probe = flags & (MAP_REQ_FLAG_P >> 8);
2254 pitr = flags & (MAP_REQ_FLAG_p >> 8);
2255 smr_invoked = flags & (MAP_REQ_FLAG_s >> 8);
2257 ti_flags = proto_tree_add_item(lisp_tree, hf_lisp_mreq_flags, tvb, offset, 3, ENC_BIG_ENDIAN);
2258 flags_tree = proto_item_add_subtree(ti_flags, ett_lisp_mreq_flags);
2259 proto_tree_add_item(flags_tree, hf_lisp_mreq_flags_auth, tvb, offset, 3, ENC_BIG_ENDIAN);
2260 proto_tree_add_item(flags_tree, hf_lisp_mreq_flags_mrp, tvb, offset, 3, ENC_BIG_ENDIAN);
2261 proto_tree_add_item(flags_tree, hf_lisp_mreq_flags_probe, tvb, offset, 3, ENC_BIG_ENDIAN);
2262 proto_tree_add_item(flags_tree, hf_lisp_mreq_flags_smr, tvb, offset, 3, ENC_BIG_ENDIAN);
2263 proto_tree_add_item(flags_tree, hf_lisp_mreq_flags_pitr, tvb, offset, 3, ENC_BIG_ENDIAN);
2264 proto_tree_add_item(flags_tree, hf_lisp_mreq_flags_smri, tvb, offset, 3, ENC_BIG_ENDIAN);
2266 if (pitr)
2267 col_append_str(pinfo->cinfo, COL_INFO, " by P-ITR");
2269 if (smr)
2270 col_append_str(pinfo->cinfo, COL_INFO, " (SMR)");
2272 if (probe)
2273 col_append_str(pinfo->cinfo, COL_INFO, " (RLOC-probe)");
2275 if (smr_invoked)
2276 col_append_str(pinfo->cinfo, COL_INFO, " (SMR-invoked)");
2278 /* Reserved bits (9 bits) */
2279 proto_tree_add_item(lisp_tree, hf_lisp_mreq_res, tvb, offset, 3, ENC_BIG_ENDIAN);
2281 /* ITR record count (5 bits) */
2282 itr_rec_cnt = tvb_get_uint8(tvb, offset + 2) & 0x1F;
2283 proto_tree_add_item(lisp_tree, hf_lisp_irc, tvb, offset, 3, ENC_BIG_ENDIAN);
2284 offset += 3;
2286 /* Record count (8 bits) */
2287 rec_cnt = tvb_get_uint8(tvb, offset);
2288 proto_tree_add_item(lisp_tree, hf_lisp_records, tvb, offset, 1, ENC_BIG_ENDIAN);
2289 offset += 1;
2291 /* Nonce (64 bits) */
2292 proto_tree_add_item(lisp_tree, hf_lisp_nonce, tvb, offset, 8, ENC_BIG_ENDIAN);
2293 offset += 8;
2295 /* Source EID AFI (16 bits) */
2296 src_eid_afi = tvb_get_ntohs(tvb, offset);
2297 proto_tree_add_item(lisp_tree, hf_lisp_mreq_srceid_afi, tvb, offset, 2, ENC_BIG_ENDIAN);
2298 offset += 2;
2300 /* Source EID */
2301 switch (src_eid_afi) {
2302 case AFNUM_RESERVED:
2303 proto_tree_add_string(lisp_tree, hf_lisp_mreq_srceid_string, tvb, offset, 0, "not set");
2304 break;
2305 case AFNUM_INET:
2306 proto_tree_add_item(lisp_tree,
2307 hf_lisp_mreq_srceid_ipv4, tvb, offset, INET_ADDRLEN, ENC_BIG_ENDIAN);
2308 offset += INET_ADDRLEN;
2309 break;
2310 case AFNUM_INET6:
2311 proto_tree_add_item(lisp_tree,
2312 hf_lisp_mreq_srceid_ipv6, tvb, offset, INET6_ADDRLEN, ENC_NA);
2313 offset += INET6_ADDRLEN;
2314 break;
2315 case AFNUM_LCAF:
2316 src_eid = get_addr_str(tvb, pinfo, offset, src_eid_afi, &addr_len);
2317 lcaf_src_eid_tree = proto_tree_add_subtree_format(lisp_tree, tvb, offset, addr_len, ett_lisp_lcaf, NULL, "Source EID: %s", src_eid);
2318 dissect_lcaf(tvb, pinfo, lcaf_src_eid_tree, offset, NULL);
2319 offset += addr_len;
2320 break;
2321 case AFNUM_802:
2322 case AFNUM_EUI48:
2323 proto_tree_add_item(lisp_tree,
2324 hf_lisp_mreq_srceid_mac, tvb, offset, EUI48_ADDRLEN, ENC_NA);
2325 offset += EUI48_ADDRLEN;
2326 break;
2327 default:
2328 expert_add_info_format(pinfo, lisp_tree, &ei_lisp_unexpected_field,
2329 "Unexpected Source EID AFI (%d), cannot decode", src_eid_afi);
2330 next_tvb = tvb_new_subset_remaining(tvb, offset);
2331 call_data_dissector(next_tvb, pinfo, lisp_tree);
2332 return;
2335 /* ITR records */
2336 for(i=0; i < itr_rec_cnt+1; i++) {
2337 uint16_t itr_afi;
2338 proto_item *tir;
2339 proto_tree *lisp_itr_tree;
2341 itr_afi = tvb_get_ntohs(tvb, offset);
2342 tir = proto_tree_add_item(lisp_tree, hf_lisp_mreq_itr_rloc, tvb, offset, 2, ENC_NA);
2343 lisp_itr_tree = proto_item_add_subtree(tir, ett_lisp_itr);
2344 proto_tree_add_item(lisp_itr_tree, hf_lisp_mreq_itr_rloc_afi, tvb, offset, 2, ENC_BIG_ENDIAN);
2345 offset += 2;
2347 switch (itr_afi) {
2348 case AFNUM_INET:
2349 proto_tree_add_item(lisp_itr_tree, hf_lisp_mreq_itr_rloc_ipv4, tvb, offset, 4, ENC_BIG_ENDIAN);
2350 proto_item_append_text(tir, " %d: %s", i + 1, tvb_ip_to_str(pinfo->pool, tvb, offset));
2351 proto_item_set_len(tir, 2 + INET_ADDRLEN);
2352 offset += INET_ADDRLEN;
2353 break;
2354 case AFNUM_INET6:
2355 proto_tree_add_item(lisp_itr_tree, hf_lisp_mreq_itr_rloc_ipv6, tvb, offset, 16, ENC_NA);
2356 proto_item_append_text(tir, " %d: %s", i + 1, tvb_ip6_to_str(pinfo->pool, tvb, offset));
2357 proto_item_set_len(tir, 2 + INET6_ADDRLEN);
2358 offset += INET6_ADDRLEN;
2359 break;
2360 default:
2361 expert_add_info_format(pinfo, lisp_tree, &ei_lisp_unexpected_field,
2362 "Unexpected ITR-RLOC-AFI (%d), cannot decode", itr_afi);
2363 next_tvb = tvb_new_subset_remaining(tvb, offset);
2364 call_data_dissector(next_tvb, pinfo, lisp_tree);
2365 return;
2369 /* Query records */
2370 for(i=0; i < rec_cnt; i++) {
2371 int str_len;
2372 uint16_t prefix_mask;
2373 uint16_t prefix_afi;
2374 const char *prefix;
2375 proto_item *tir;
2376 proto_tree *lisp_record_tree;
2378 addr_len = 0;
2379 prefix_mask = tvb_get_uint8(tvb, offset + 1);
2380 prefix_afi = tvb_get_ntohs(tvb, offset + 2);
2381 prefix = get_addr_str(tvb, pinfo, offset + 4, prefix_afi, &addr_len);
2383 if (prefix == NULL) {
2384 expert_add_info_format(pinfo, lisp_tree, &ei_lisp_unexpected_field,
2385 "Unexpected EID prefix AFI (%d), cannot decode", prefix_afi);
2386 next_tvb = tvb_new_subset_remaining(tvb, offset);
2387 call_data_dissector(next_tvb, pinfo, lisp_tree);
2388 return;
2391 tir = proto_tree_add_item(lisp_tree, hf_lisp_mreq_record, tvb, offset, 4+addr_len, ENC_NA);
2393 /* Update the INFO column if there is only one record */
2394 if (rec_cnt == 1)
2395 col_append_fstr(pinfo->cinfo, COL_INFO, " for %s/%d", prefix, prefix_mask);
2397 lisp_record_tree = proto_item_add_subtree(tir, ett_lisp_record);
2398 proto_tree_add_item(lisp_record_tree, hf_lisp_mreq_record_res, tvb, offset, 1, ENC_BIG_ENDIAN);
2399 offset += 1;
2401 proto_tree_add_item(lisp_record_tree, hf_lisp_mreq_record_prefix_length, tvb, offset, 1, ENC_BIG_ENDIAN);
2402 offset += 1;
2404 proto_tree_add_item(lisp_record_tree, hf_lisp_mreq_record_prefix_afi, tvb, offset, 2, ENC_BIG_ENDIAN);
2405 offset += 2;
2407 switch (prefix_afi) {
2408 case AFNUM_INET:
2409 proto_tree_add_item(lisp_record_tree, hf_lisp_mreq_record_prefix_ipv4, tvb, offset, INET_ADDRLEN, ENC_NA);
2410 offset += INET_ADDRLEN;
2411 break;
2412 case AFNUM_INET6:
2413 proto_tree_add_item(lisp_record_tree, hf_lisp_mreq_record_prefix_ipv6, tvb, offset, INET6_ADDRLEN, ENC_NA);
2414 offset += INET6_ADDRLEN;
2415 break;
2416 case AFNUM_LCAF:
2417 lcaf_prefix_tree = proto_tree_add_subtree_format(lisp_record_tree, tvb, offset, addr_len, ett_lisp_lcaf, NULL, "Prefix: %s", prefix);
2418 dissect_lcaf(tvb, pinfo, lcaf_prefix_tree, offset, NULL);
2419 offset += addr_len;
2420 break;
2421 case AFNUM_802:
2422 case AFNUM_EUI48:
2423 proto_tree_add_item(lisp_record_tree, hf_lisp_mreq_record_prefix_mac, tvb, offset, EUI48_ADDRLEN, ENC_NA);
2424 offset += EUI48_ADDRLEN;
2425 break;
2426 case AFNUM_DISTNAME:
2427 str_len = tvb_strsize(tvb, offset);
2428 proto_tree_add_item(lisp_record_tree, hf_lisp_mreq_record_prefix_dn, tvb, offset, str_len, ENC_ASCII);
2429 offset += str_len;
2430 break;
2432 proto_item_append_text(tir, " %d: %s/%d", i+1, prefix, prefix_mask);
2435 /* If M bit is set, we also have a Map-Reply */
2436 if (mrep) {
2437 proto_item *tim;
2438 proto_tree *lisp_mr_tree;
2440 tim = proto_tree_add_item(lisp_tree, hf_lisp_mrep_record, tvb, offset, -1, ENC_NA);
2441 lisp_mr_tree = proto_item_add_subtree(tim, ett_lisp_mr);
2443 offset = dissect_lisp_mapping(tvb, pinfo, lisp_mr_tree, 0, 1, false, offset, NULL);
2446 next_tvb = tvb_new_subset_remaining(tvb, offset);
2447 call_data_dissector(next_tvb, pinfo, lisp_tree);
2452 * Dissector code for Map-Reply type control packets
2454 * 0 1 2 3
2455 * 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1
2456 * +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
2457 * |Type=2 |P|E|S| Reserved | Record Count |
2458 * +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
2459 * | Nonce . . . |
2460 * +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
2461 * | . . . Nonce |
2462 * +-> +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
2463 * | | Record TTL |
2464 * | +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
2465 * R | Locator Count | EID mask-len | ACT |A| Reserved |
2466 * e +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
2467 * c | Rsvd | Map-Version Number | EID-AFI |
2468 * o +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
2469 * r | EID-prefix |
2470 * d +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
2471 * | /| Priority | Weight | M Priority | M Weight |
2472 * | L +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
2473 * | o | Unused Flags |L|p|R| Loc-AFI |
2474 * | c +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
2475 * | \| Locator |
2476 * +-> +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
2480 static void
2481 dissect_lisp_map_reply(tvbuff_t *tvb, packet_info *pinfo, proto_tree *lisp_tree)
2483 int i;
2484 int offset = 0;
2485 bool probe;
2486 uint8_t flags;
2487 uint8_t rec_cnt = 0;
2488 tvbuff_t *next_tvb;
2490 /* Flags (2 bits) */
2491 flags = tvb_get_uint8(tvb, offset);
2492 probe = flags & (MAP_REP_FLAG_P >> 16);
2493 proto_tree_add_item(lisp_tree, hf_lisp_mrep_flags_probe, tvb, offset, 3, ENC_BIG_ENDIAN);
2494 proto_tree_add_item(lisp_tree, hf_lisp_mrep_flags_enlr, tvb, offset, 3, ENC_BIG_ENDIAN);
2496 /* Flags defined in LISP-SEC draft (1 bit) */
2497 proto_tree_add_item(lisp_tree, hf_lisp_mrep_flags_sec, tvb, offset, 3, ENC_BIG_ENDIAN);
2499 if (probe)
2500 col_append_str(pinfo->cinfo, COL_INFO, " (RLOC-probe reply)");
2502 /* Reserved bits (18 bits) */
2503 proto_tree_add_item(lisp_tree, hf_lisp_mrep_res, tvb, offset, 3, ENC_BIG_ENDIAN);
2504 offset += 3;
2506 /* Record count (8 bits) */
2507 rec_cnt = tvb_get_uint8(tvb, offset);
2508 proto_tree_add_item(lisp_tree, hf_lisp_records, tvb, offset, 1, ENC_BIG_ENDIAN);
2509 offset += 1;
2511 /* Nonce (64 bits) */
2512 proto_tree_add_item(lisp_tree, hf_lisp_nonce, tvb, offset, 8, ENC_BIG_ENDIAN);
2513 offset += 8;
2515 /* Reply records */
2516 for(i=0; i < rec_cnt; i++) {
2517 offset = dissect_lisp_mapping(tvb, pinfo, lisp_tree, rec_cnt, i+1, false, offset, NULL);
2520 next_tvb = tvb_new_subset_remaining(tvb, offset);
2521 call_data_dissector(next_tvb, pinfo, lisp_tree);
2526 * Dissector code for Map-Register type control packets
2528 * 0 1 2 3
2529 * 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1
2530 * +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
2531 * |Type=3 |P|S|I|R| Reserved |M| Record Count |
2532 * +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
2533 * | Nonce . . . |
2534 * +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
2535 * | . . . Nonce |
2536 * +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
2537 * | Key ID | Authentication Data Length |
2538 * +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
2539 * ~ Authentication Data ~
2540 * +-> +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
2541 * | | Record TTL |
2542 * | +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
2543 * R | Locator Count | EID mask-len | ACT |A| Reserved |
2544 * e +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
2545 * c | Rsvd | Map-Version Number | EID-AFI |
2546 * o +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
2547 * r | EID-prefix |
2548 * d +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
2549 * | /| Priority | Weight | M Priority | M Weight |
2550 * | L +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
2551 * | o | Unused Flags |L|p|R| Loc-AFI |
2552 * | c +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
2553 * | \| Locator |
2554 * +-> +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
2559 dissect_lisp_map_register(tvbuff_t *tvb, packet_info *pinfo, proto_tree *lisp_tree,
2560 int offset, proto_item *tim, bool keep_going)
2562 int i;
2563 uint8_t rec_cnt = 0;
2564 tvbuff_t *next_tvb;
2565 uint16_t authlen = 0;
2566 uint16_t flags;
2567 bool xtrid;
2568 bool rtr;
2570 /* Flags (1 bit) */
2571 proto_tree_add_item(lisp_tree, hf_lisp_mreg_flags_pmr, tvb, offset, 3, ENC_BIG_ENDIAN);
2573 /* Flags defined in LISP-SEC draft (1 bit) */
2574 proto_tree_add_item(lisp_tree, hf_lisp_mreg_flags_sec, tvb, offset, 3, ENC_BIG_ENDIAN);
2576 /* Flags defined in NAT Traversal draft (2 bits) */
2577 flags = tvb_get_ntohs(tvb, offset);
2578 xtrid = flags & (MAP_REG_FLAG_I >> 8);
2579 rtr = flags & (MAP_REG_FLAG_R >> 8);
2581 proto_tree_add_item(lisp_tree, hf_lisp_mreg_flags_xtrid, tvb, offset, 3, ENC_BIG_ENDIAN);
2582 proto_tree_add_item(lisp_tree, hf_lisp_mreg_flags_rtr, tvb, offset, 3, ENC_BIG_ENDIAN);
2584 if (rtr)
2585 col_append_str(pinfo->cinfo, COL_INFO, " (RTR)");
2587 /* Reserved bits (15 bits) */
2588 proto_tree_add_item(lisp_tree, hf_lisp_mreg_res, tvb, offset, 3, ENC_BIG_ENDIAN);
2590 /* Flags (1 bit) */
2591 proto_tree_add_item(lisp_tree, hf_lisp_mreg_flags_wmn, tvb, offset, 3, ENC_BIG_ENDIAN);
2592 offset += 3;
2594 /* Record count (8 bits) */
2595 rec_cnt = tvb_get_uint8(tvb, offset);
2596 proto_tree_add_item(lisp_tree, hf_lisp_records, tvb, offset, 1, ENC_BIG_ENDIAN);
2597 offset += 1;
2599 /* Nonce (64 bits) */
2600 proto_tree_add_item(lisp_tree, hf_lisp_nonce, tvb, offset, 8, ENC_BIG_ENDIAN);
2601 offset += 8;
2603 /* Key ID (16 bits) */
2604 proto_tree_add_item(lisp_tree, hf_lisp_keyid, tvb, offset, 2, ENC_BIG_ENDIAN);
2605 offset += 2;
2607 /* Authentication Data Length (16 bits) */
2608 authlen = tvb_get_ntohs(tvb, offset);
2609 proto_tree_add_item(lisp_tree, hf_lisp_authlen, tvb, offset, 2, ENC_BIG_ENDIAN);
2610 offset += 2;
2612 /* Authentication Data */
2613 /* XXX: need to check is there is still enough data in buffer */
2614 proto_tree_add_item(lisp_tree, hf_lisp_auth, tvb, offset, authlen, ENC_NA);
2615 offset += authlen;
2617 for(i=0; i < rec_cnt; i++) {
2618 offset = dissect_lisp_mapping(tvb, pinfo, lisp_tree, rec_cnt, i+1, false, offset, tim);
2621 /* If I bit is set, we have an xTR-ID and a site-ID field */
2622 if (xtrid) {
2623 proto_tree_add_item(lisp_tree, hf_lisp_xtrid, tvb, offset, LISP_XTRID_LEN, ENC_NA);
2624 proto_tree_add_item(lisp_tree, hf_lisp_siteid, tvb, offset + LISP_XTRID_LEN, LISP_SITEID_LEN, ENC_NA);
2625 offset += LISP_XTRID_LEN + LISP_SITEID_LEN;
2628 if (keep_going) {
2629 next_tvb = tvb_new_subset_remaining(tvb, offset);
2630 call_data_dissector(next_tvb, pinfo, lisp_tree);
2631 } else {
2632 return offset;
2635 return 0;
2640 * Dissector code for Map-Notify type control packets
2642 * 0 1 2 3
2643 * 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1
2644 * +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
2645 * |Type=4 |I|R| Reserved | Record Count |
2646 * +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
2647 * | Nonce . . . |
2648 * +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
2649 * | . . . Nonce |
2650 * +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
2651 * | Key ID | Authentication Data Length |
2652 * +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
2653 * ~ Authentication Data ~
2654 * +-> +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
2655 * | | Record TTL |
2656 * | +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
2657 * R | Locator Count | EID mask-len | ACT |A| Reserved |
2658 * e +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
2659 * c | Rsvd | Map-Version Number | EID-AFI |
2660 * o +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
2661 * r | EID-prefix |
2662 * d +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
2663 * | /| Priority | Weight | M Priority | M Weight |
2664 * | L +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
2665 * | o | Unused Flags |L|p|R| Loc-AFI |
2666 * | c +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
2667 * | \| Locator |
2668 * +-> +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
2672 static void
2673 dissect_lisp_map_notify(tvbuff_t *tvb, packet_info *pinfo, proto_tree *lisp_tree)
2675 int i;
2676 int offset = 0;
2677 uint8_t rec_cnt = 0;
2678 tvbuff_t *next_tvb;
2679 uint16_t authlen = 0;
2680 uint16_t flags;
2681 bool xtrid;
2682 bool rtr;
2684 /* Flags defined in NAT Traversal draft (2 bits) */
2685 flags = tvb_get_ntohs(tvb, offset);
2686 xtrid = flags & (MAP_NOT_FLAG_I >> 8);
2687 rtr = flags & (MAP_NOT_FLAG_R >> 8);
2689 proto_tree_add_item(lisp_tree, hf_lisp_mnot_flags_xtrid, tvb, offset, 3, ENC_BIG_ENDIAN);
2690 proto_tree_add_item(lisp_tree, hf_lisp_mnot_flags_rtr, tvb, offset, 3, ENC_BIG_ENDIAN);
2692 if (rtr)
2693 col_append_str(pinfo->cinfo, COL_INFO, " (RTR)");
2695 /* Reserved bits (18 bits) */
2696 proto_tree_add_item(lisp_tree, hf_lisp_mnot_res, tvb, offset, 3, ENC_BIG_ENDIAN);
2697 offset += 3;
2699 /* Record count (8 bits) */
2700 rec_cnt = tvb_get_uint8(tvb, offset);
2701 proto_tree_add_item(lisp_tree, hf_lisp_records, tvb, offset, 1, ENC_BIG_ENDIAN);
2702 offset += 1;
2704 /* Nonce (64 bits) */
2705 proto_tree_add_item(lisp_tree, hf_lisp_nonce, tvb, offset, 8, ENC_BIG_ENDIAN);
2706 offset += 8;
2708 /* Key ID (16 bits) */
2709 proto_tree_add_item(lisp_tree, hf_lisp_keyid, tvb, offset, 2, ENC_BIG_ENDIAN);
2710 offset += 2;
2712 /* Authentication Data Length (16 bits) */
2713 authlen = tvb_get_ntohs(tvb, offset);
2714 proto_tree_add_item(lisp_tree, hf_lisp_authlen, tvb, offset, 2, ENC_BIG_ENDIAN);
2715 offset += 2;
2717 /* Authentication Data */
2718 /* XXX: need to check is there is still enough data in buffer */
2719 proto_tree_add_item(lisp_tree, hf_lisp_auth, tvb, offset, authlen, ENC_NA);
2720 offset += authlen;
2722 for(i=0; i < rec_cnt; i++) {
2723 offset = dissect_lisp_mapping(tvb, pinfo, lisp_tree, rec_cnt, i+1, false, offset, NULL);
2726 /* If I bit is set, we have an xTR-ID and a site-ID field */
2727 if (xtrid) {
2728 proto_tree_add_item(lisp_tree, hf_lisp_xtrid, tvb, offset, LISP_XTRID_LEN, ENC_NA);
2729 proto_tree_add_item(lisp_tree, hf_lisp_siteid, tvb, offset + LISP_XTRID_LEN, LISP_SITEID_LEN, ENC_NA);
2730 offset += LISP_XTRID_LEN + LISP_SITEID_LEN;
2733 /* If R bit is set, we have MS-RTR authentication data */
2734 if (rtr) {
2735 /* MS-RTR Key ID (16 bits) */
2736 proto_tree_add_item(lisp_tree, hf_lisp_msrtr_keyid, tvb, offset, 2, ENC_BIG_ENDIAN);
2737 offset += 2;
2739 /* MS-RTR Authentication Data Length (16 bits) */
2740 authlen = tvb_get_ntohs(tvb, offset);
2741 proto_tree_add_item(lisp_tree, hf_lisp_msrtr_authlen, tvb, offset, 2, ENC_BIG_ENDIAN);
2742 offset += 2;
2744 /* MS-RTR Authentication Data */
2745 /* XXX: need to check is there is still enough data in buffer */
2746 proto_tree_add_item(lisp_tree, hf_lisp_msrtr_auth, tvb, offset, authlen, ENC_NA);
2747 offset += authlen;
2750 next_tvb = tvb_new_subset_remaining(tvb, offset);
2751 call_data_dissector(next_tvb, pinfo, lisp_tree);
2755 * Dissector code for Map-Referral type control packets
2757 * 0 1 2 3
2758 * 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1
2759 * +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
2760 * |Type=6 | Reserved | Record Count |
2761 * +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
2762 * | Nonce . . . |
2763 * +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
2764 * | . . . Nonce |
2765 * +-> +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
2766 * | | Record TTL |
2767 * | +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
2768 * R | Referral Count| EID mask-len | ACT |A|I| Reserved |
2769 * e +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
2770 * c |SigCnt | Map Version Number | EID-AFI |
2771 * o +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
2772 * r | EID-prefix ... |
2773 * d +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
2774 * | /| Priority | Weight | M Priority | M Weight |
2775 * | L +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
2776 * | o | Unused Flags |R| Loc/LCAF-AFI |
2777 * | c +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
2778 * | \| Locator ... |
2779 * +-> +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
2783 static void
2784 dissect_lisp_map_referral(tvbuff_t *tvb, packet_info *pinfo, proto_tree *lisp_tree)
2786 int i;
2787 int offset = 0;
2788 uint8_t rec_cnt = 0;
2789 tvbuff_t *next_tvb;
2791 /* Reserved bits (20 bits) */
2792 proto_tree_add_item(lisp_tree, hf_lisp_mref_res, tvb, offset, 3, ENC_BIG_ENDIAN);
2793 offset += 3;
2795 /* Record count (8 bits) */
2796 rec_cnt = tvb_get_uint8(tvb, offset);
2797 proto_tree_add_item(lisp_tree, hf_lisp_records, tvb, offset, 1, ENC_BIG_ENDIAN);
2798 offset += 1;
2800 /* Nonce (64 bits) */
2801 proto_tree_add_item(lisp_tree, hf_lisp_nonce, tvb, offset, 8, ENC_BIG_ENDIAN);
2802 offset += 8;
2804 /* Referral records */
2805 for(i=0; i < rec_cnt; i++) {
2806 offset = dissect_lisp_mapping(tvb, pinfo, lisp_tree, rec_cnt, i+1, true, offset, NULL);
2809 next_tvb = tvb_new_subset_remaining(tvb, offset);
2810 call_data_dissector(next_tvb, pinfo, lisp_tree);
2815 * Dissector code for Info type control packets
2817 * 0 1 2 3
2818 * 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1
2819 * +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
2820 * |Type=7 |R| Reserved |
2821 * +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
2822 * | Nonce . . . |
2823 * +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
2824 * | . . . Nonce |
2825 * +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
2826 * | Key ID | Authentication Data Length |
2827 * +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
2828 * ~ Authentication Data ~
2829 * +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
2830 * | TTL |
2831 * +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
2832 * | Reserved | EID mask-len | EID-prefix-AFI |
2833 * +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
2834 * | EID-prefix |
2835 * +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
2836 * | AFI | ...
2837 * +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
2841 static void
2842 dissect_lisp_info(tvbuff_t *tvb, packet_info *pinfo, proto_tree *lisp_tree)
2844 int offset = 0;
2845 tvbuff_t *next_tvb;
2846 uint8_t flags;
2847 bool reply;
2848 uint16_t authlen = 0;
2849 uint8_t prefix_mask;
2850 uint16_t prefix_afi, afi;
2851 const char *prefix;
2852 uint16_t addr_len = 0;
2853 proto_item *tir, *ti_prefix;
2854 proto_tree *prefix_tree;
2856 /* Flags (1 bit) */
2857 flags = tvb_get_uint8(tvb, offset);
2858 reply = flags & (INFO_FLAG_R >> 16);
2860 if (reply)
2861 col_append_str(pinfo->cinfo, COL_INFO, "-Reply");
2862 else
2863 col_append_str(pinfo->cinfo, COL_INFO, "-Request");
2865 proto_tree_add_item(lisp_tree, hf_lisp_info_r, tvb, offset, 3, ENC_BIG_ENDIAN);
2867 /* Reserved bits (27 bits) */
2868 proto_tree_add_item(lisp_tree, hf_lisp_info_res1, tvb, offset, 4, ENC_BIG_ENDIAN);
2869 offset += 4;
2871 /* Nonce (64 bits) */
2872 proto_tree_add_item(lisp_tree, hf_lisp_nonce, tvb, offset, 8, ENC_BIG_ENDIAN);
2873 offset += 8;
2875 /* Key ID (16 bits) */
2876 proto_tree_add_item(lisp_tree, hf_lisp_keyid, tvb, offset, 2, ENC_BIG_ENDIAN);
2877 offset += 2;
2879 /* Authentication Data Length (16 bits) */
2880 authlen = tvb_get_ntohs(tvb, offset);
2881 proto_tree_add_item(lisp_tree, hf_lisp_authlen, tvb, offset, 2, ENC_BIG_ENDIAN);
2882 offset += 2;
2884 /* Authentication Data */
2885 /* XXX: need to check is there is still enough data in buffer */
2886 proto_tree_add_item(lisp_tree, hf_lisp_auth, tvb, offset, authlen, ENC_NA);
2887 offset += authlen;
2889 /* TTL */
2890 proto_tree_add_item(lisp_tree, hf_lisp_info_ttl, tvb, offset, 4, ENC_BIG_ENDIAN);
2891 offset += 4;
2893 /* Reserved bits (8 bits) */
2894 proto_tree_add_item(lisp_tree, hf_lisp_info_res2, tvb, offset, 1, ENC_BIG_ENDIAN);
2895 offset += 1;
2897 prefix_tree = proto_tree_add_subtree(lisp_tree, tvb, offset, 3, ett_lisp_info_prefix, &ti_prefix, "EID Prefix: ");
2899 proto_tree_add_item(prefix_tree, hf_lisp_info_prefix_masklen, tvb, offset, 1, ENC_BIG_ENDIAN);
2900 prefix_mask = tvb_get_uint8(tvb, offset); offset += 1;
2902 proto_tree_add_item(prefix_tree, hf_lisp_info_prefix_afi, tvb, offset, 2, ENC_BIG_ENDIAN);
2903 prefix_afi = tvb_get_ntohs(tvb, offset); offset += 2;
2905 prefix = get_addr_str(tvb, pinfo, offset, prefix_afi, &addr_len);
2907 if (prefix == NULL) {
2908 expert_add_info_format(pinfo, lisp_tree, &ei_lisp_unexpected_field,
2909 "Unexpected EID prefix AFI (%d), cannot decode", prefix_afi);
2910 next_tvb = tvb_new_subset_remaining(tvb, offset);
2911 call_data_dissector(next_tvb, pinfo, lisp_tree);
2912 return;
2915 switch (prefix_afi) {
2916 case AFNUM_INET:
2917 proto_tree_add_item(prefix_tree, hf_lisp_info_prefix_ipv4, tvb, offset, INET_ADDRLEN, ENC_BIG_ENDIAN);
2918 break;
2919 case AFNUM_INET6:
2920 proto_tree_add_item(prefix_tree, hf_lisp_info_prefix_ipv6, tvb, offset, INET6_ADDRLEN, ENC_NA);
2921 break;
2924 proto_item_append_text(ti_prefix, "%s/%d", prefix, prefix_mask);
2925 proto_item_set_len(ti_prefix, 3 + addr_len);
2926 offset += addr_len;
2928 /* Update the INFO column */
2929 col_append_fstr(pinfo->cinfo, COL_INFO, " for %s/%d", prefix, prefix_mask);
2931 tir = proto_tree_add_item(lisp_tree, hf_lisp_info_afi, tvb, offset, 2, ENC_BIG_ENDIAN);
2932 afi = tvb_get_ntohs(tvb, offset); offset += 2;
2934 if (!reply) {
2935 if (afi != 0) {
2936 expert_add_info_format(pinfo, tir, &ei_lisp_expected_field,
2937 "Expecting NULL AFI (0), found %d, incorrect packet!", afi);
2939 } else {
2940 if (afi != AFNUM_LCAF) {
2941 expert_add_info_format(pinfo, tir, &ei_lisp_expected_field,
2942 "Expecting LCAF AFI (%d), found %d, incorrect packet!",
2943 AFNUM_LCAF, afi);
2944 } else {
2945 offset = dissect_lcaf(tvb, pinfo, lisp_tree, offset, NULL);
2949 next_tvb = tvb_new_subset_remaining(tvb, offset);
2950 call_data_dissector(next_tvb, pinfo, lisp_tree);
2955 * Dissector code for Encapsulated Control Message type packets
2957 * +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
2958 * |Type=8 |S|D| Reserved |
2959 * +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
2960 * | IPv4 or IPv6 Header |
2961 * | (uses RLOC or EID addresses) |
2962 * ~ ~
2966 static void
2967 dissect_lisp_ecm(tvbuff_t *tvb, packet_info *pinfo, proto_tree *tree, proto_tree *lisp_tree)
2969 tvbuff_t *next_tvb;
2970 uint8_t flags;
2971 uint8_t ip_ver;
2973 /* Flags (2 bits) */
2974 flags = tvb_get_uint8(tvb, 0);
2975 ddt_originated = flags & (ECM_FLAG_D >> 24);
2977 proto_tree_add_item(lisp_tree, hf_lisp_ecm_flags_sec, tvb, 0, 4, ENC_BIG_ENDIAN);
2978 proto_tree_add_item(lisp_tree, hf_lisp_ecm_flags_ddt, tvb, 0, 4, ENC_BIG_ENDIAN);
2979 proto_tree_add_item(lisp_tree, hf_lisp_ecm_res, tvb, 0, 4, ENC_BIG_ENDIAN);
2981 /* Determine if encapsulated packet is IPv4 or IPv6, and call dissector */
2982 next_tvb = tvb_new_subset_remaining(tvb, LISP_ECM_HEADER_LEN);
2983 ip_ver = tvb_get_bits8(next_tvb, 0, 4);
2985 switch (ip_ver) {
2986 case 4:
2987 call_dissector(ipv4_handle, next_tvb, pinfo, tree);
2988 break;
2989 case 6:
2990 call_dissector(ipv6_handle, next_tvb, pinfo, tree);
2991 break;
2992 default:
2993 call_data_dissector(next_tvb, pinfo, tree);
2994 break;
2996 encapsulated = false;
3001 * Main dissector code
3004 static int
3005 dissect_lisp(tvbuff_t *tvb, packet_info *pinfo, proto_tree *tree, void *data _U_)
3007 uint8_t type;
3009 proto_tree *lisp_tree = NULL;
3011 /* Clear Info column before fetching data in case an exception is thrown */
3012 col_clear(pinfo->cinfo, COL_INFO);
3014 type = tvb_get_bits8(tvb, 0, 4);
3016 /* Make entries in Protocol column and Info column on summary display */
3017 col_set_str(pinfo->cinfo, COL_PROTOCOL, "LISP");
3019 if (encapsulated) {
3020 col_add_fstr(pinfo->cinfo, COL_INFO, "Encapsulated %s", val_to_str(type, lisp_typevals,
3021 "Unknown LISP Control Packet (%d)"));
3022 } else {
3023 col_add_str(pinfo->cinfo, COL_INFO, val_to_str(type, lisp_typevals,
3024 "Unknown LISP Control Packet (%d)"));
3027 if (ddt_originated) {
3028 col_append_str(pinfo->cinfo, COL_INFO, " (DDT-originated)");
3029 ddt_originated = false;
3032 if (tree) {
3033 proto_item *ti;
3035 /* create display subtree for the protocol */
3036 ti = proto_tree_add_item(tree, proto_lisp, tvb, 0,
3037 (type == LISP_ECM) ? LISP_ECM_HEADER_LEN : -1, ENC_NA);
3039 lisp_tree = proto_item_add_subtree(ti, ett_lisp);
3041 proto_tree_add_item(lisp_tree,
3042 hf_lisp_type, tvb, 0, 3, ENC_BIG_ENDIAN);
3045 /* Sub-dissectors are indirectly called by the following and thus
3046 this code should be executed whether or not tree==NULL.
3048 switch (type) {
3049 case LISP_MAP_REQUEST:
3050 dissect_lisp_map_request(tvb, pinfo, lisp_tree);
3051 break;
3052 case LISP_MAP_REPLY:
3053 dissect_lisp_map_reply(tvb, pinfo, lisp_tree);
3054 break;
3055 case LISP_MAP_REGISTER:
3056 dissect_lisp_map_register(tvb, pinfo, lisp_tree, 0, NULL, true);
3057 break;
3058 case LISP_MAP_NOTIFY:
3059 dissect_lisp_map_notify(tvb, pinfo, lisp_tree);
3060 break;
3061 case LISP_MAP_REFERRAL:
3062 dissect_lisp_map_referral(tvb, pinfo, lisp_tree);
3063 break;
3064 case LISP_INFO:
3065 dissect_lisp_info(tvb, pinfo, lisp_tree);
3066 break;
3067 case LISP_ECM:
3068 encapsulated = true;
3069 dissect_lisp_ecm(tvb, pinfo, tree, lisp_tree);
3070 break;
3071 default:
3072 call_data_dissector(tvb, pinfo, tree);
3073 break;
3076 /* Return the amount of data this dissector was able to dissect */
3077 return tvb_reported_length(tvb);
3082 * Register the LISP protocol with Wireshark
3085 void
3086 proto_register_lisp(void)
3088 /* Setup list of header fields */
3089 static hf_register_info hf[] = {
3090 { &hf_lisp_type,
3091 { "Type", "lisp.type",
3092 FT_UINT24, BASE_DEC, VALS(lisp_typevals), 0xF00000, "LISP Control Message Type", HFILL }},
3093 { &hf_lisp_irc,
3094 { "ITR-RLOC Count", "lisp.irc",
3095 FT_UINT24, BASE_DEC, NULL, 0x00001F, NULL, HFILL }},
3096 { &hf_lisp_records,
3097 { "Record Count", "lisp.records",
3098 FT_UINT8, BASE_DEC, NULL, 0x0, NULL, HFILL }},
3099 { &hf_lisp_nonce,
3100 { "Nonce", "lisp.nonce",
3101 FT_UINT64, BASE_HEX, NULL, 0x0, NULL, HFILL }},
3102 { &hf_lisp_mreq_flags,
3103 { "Flags", "lisp.mreq.flags",
3104 FT_UINT24, BASE_HEX, NULL, 0x0FC000, NULL, HFILL }},
3105 { &hf_lisp_mreq_flags_auth,
3106 { "A bit (Authoritative)", "lisp.mreq.flags.auth",
3107 FT_BOOLEAN, 24, TFS(&tfs_set_notset), MAP_REQ_FLAG_A, NULL, HFILL }},
3108 { &hf_lisp_mreq_flags_mrp,
3109 { "M bit (Map-Reply present)", "lisp.mreq.flags.mrp",
3110 FT_BOOLEAN, 24, TFS(&tfs_set_notset), MAP_REQ_FLAG_M, NULL, HFILL }},
3111 { &hf_lisp_mreq_flags_probe,
3112 { "P bit (Probe)", "lisp.mreq.flags.probe",
3113 FT_BOOLEAN, 24, TFS(&tfs_set_notset), MAP_REQ_FLAG_P, NULL, HFILL }},
3114 { &hf_lisp_mreq_flags_smr,
3115 { "S bit (Solicit-Map-Request)", "lisp.mreq.flags.smr",
3116 FT_BOOLEAN, 24, TFS(&tfs_set_notset), MAP_REQ_FLAG_S, NULL, HFILL }},
3117 { &hf_lisp_mreq_flags_pitr,
3118 { "p bit (Proxy ITR)", "lisp.mreq.flags.pitr",
3119 FT_BOOLEAN, 24, TFS(&tfs_set_notset), MAP_REQ_FLAG_p, NULL, HFILL }},
3120 { &hf_lisp_mreq_flags_smri,
3121 { "s bit (SMR-invoked)", "lisp.mreq.flags.smri",
3122 FT_BOOLEAN, 24, TFS(&tfs_set_notset), MAP_REQ_FLAG_s, NULL, HFILL }},
3123 { &hf_lisp_mreq_res,
3124 { "Reserved bits", "lisp.mreq.res",
3125 FT_UINT24, BASE_HEX, NULL, MAP_REQ_RESERVED, "Must be zero", HFILL }},
3126 { &hf_lisp_mreq_srceid_afi,
3127 { "Source EID AFI", "lisp.mreq.srceid.afi",
3128 FT_UINT16, BASE_DEC, VALS(afn_vals), 0x0, "Source EID Address Family Indicator", HFILL }},
3129 { &hf_lisp_mreq_srceid_string,
3130 { "Source EID", "lisp.mreq.srceid.string",
3131 FT_STRING, BASE_NONE, NULL, 0x0, "Source EID Address", HFILL }},
3132 { &hf_lisp_mreq_srceid_ipv4,
3133 { "Source EID", "lisp.mreq.srceid.ipv4",
3134 FT_IPv4, BASE_NONE, NULL, 0x0, "Source EID Address", HFILL }},
3135 { &hf_lisp_mreq_srceid_ipv6,
3136 { "Source EID", "lisp.mreq.srceid_ipv6",
3137 FT_IPv6, BASE_NONE, NULL, 0x0, "Source EID Address", HFILL }},
3138 { &hf_lisp_mreq_srceid_mac,
3139 { "Source EID", "lisp.mreq.srceid.mac",
3140 FT_ETHER, BASE_NONE, NULL, 0x0, NULL, HFILL }},
3141 { &hf_lisp_mreq_itr_rloc,
3142 { "ITR-RLOC", "lisp.mreq.itr_rloc",
3143 FT_NONE, BASE_NONE, NULL, 0x0, "Originating ITR RLOC Address", HFILL }},
3144 { &hf_lisp_mreq_itr_rloc_afi,
3145 { "ITR-RLOC AFI", "lisp.mreq.itr_rloc.afi",
3146 FT_UINT16, BASE_DEC, VALS(afn_vals), 0x0, "Originating ITR RLOC Address Family Indicator", HFILL }},
3147 { &hf_lisp_mreq_itr_rloc_ipv4,
3148 { "ITR-RLOC Address", "lisp.mreq.itr_rloc_ipv4",
3149 FT_IPv4, BASE_NONE, NULL, 0x0, "Originating ITR RLOC Address", HFILL }},
3150 { &hf_lisp_mreq_itr_rloc_ipv6,
3151 { "ITR-RLOC Address", "lisp.mreq.itr_rloc_ipv6",
3152 FT_IPv6, BASE_NONE, NULL, 0x0, "Originating ITR RLOC Address", HFILL }},
3153 { &hf_lisp_mreq_record_res,
3154 { "Reserved", "lisp.mreq.record.res",
3155 FT_UINT8, BASE_HEX, NULL, 0x0, NULL, HFILL }},
3156 { &hf_lisp_mreq_record_prefix_length,
3157 { "Prefix Length", "lisp.mreq.record.prefix.length",
3158 FT_UINT8, BASE_DEC, NULL, 0x0, NULL, HFILL }},
3159 { &hf_lisp_mreq_record_prefix_afi,
3160 { "Prefix AFI", "lisp.mreq.record.prefix.afi",
3161 FT_UINT16, BASE_DEC, VALS(afn_vals), 0x0, NULL, HFILL }},
3162 { &hf_lisp_mreq_record_prefix_ipv4,
3163 { "Prefix", "lisp.mreq.record.prefix.ipv4",
3164 FT_IPv4, BASE_NONE, NULL, 0x0, NULL, HFILL }},
3165 { &hf_lisp_mreq_record_prefix_ipv6,
3166 { "Prefix", "lisp.mreq.record.prefix.ipv6",
3167 FT_IPv6, BASE_NONE, NULL, 0x0, NULL, HFILL }},
3168 { &hf_lisp_mreq_record_prefix_mac,
3169 { "Prefix", "lisp.mreq.record.prefix.mac",
3170 FT_ETHER, BASE_NONE, NULL, 0x0, NULL, HFILL }},
3171 { &hf_lisp_mreq_record_prefix_dn,
3172 { "Prefix", "lisp.mreq.record.prefix.dn",
3173 FT_STRINGZ, BASE_NONE, NULL, 0x0, NULL, HFILL }},
3174 { &hf_lisp_mreq_record,
3175 { "Map-Request Record", "lisp.mreq.record",
3176 FT_NONE, BASE_NONE, NULL, 0x0, NULL, HFILL }},
3177 { &hf_lisp_mrep_record,
3178 { "Map-Reply Record", "lisp.mrep.record",
3179 FT_NONE, BASE_NONE, NULL, 0x0, NULL, HFILL }},
3180 { &hf_lisp_mrep_flags_probe,
3181 { "P bit (Probe)", "lisp.mrep.flags.probe",
3182 FT_BOOLEAN, 24, TFS(&tfs_set_notset), MAP_REP_FLAG_P, NULL, HFILL }},
3183 { &hf_lisp_mrep_flags_enlr,
3184 { "E bit (Echo-Nonce locator reachability algorithm enabled)", "lisp.mrep.flags.enlr",
3185 FT_BOOLEAN, 24, TFS(&tfs_set_notset), MAP_REP_FLAG_E, NULL, HFILL }},
3186 { &hf_lisp_mrep_flags_sec,
3187 { "S bit (LISP-SEC capable)", "lisp.mrep.flags.sec",
3188 FT_BOOLEAN, 24, TFS(&tfs_set_notset), MAP_REP_FLAG_S, NULL, HFILL }},
3189 { &hf_lisp_mrep_res,
3190 { "Reserved bits", "lisp.mrep.res",
3191 FT_UINT24, BASE_HEX, NULL, MAP_REP_RESERVED, "Must be zero", HFILL }},
3192 { &hf_lisp_mreg_flags_pmr,
3193 { "P bit (Proxy-Map-Reply)", "lisp.mreg.flags.pmr",
3194 FT_BOOLEAN, 24, TFS(&tfs_set_notset), MAP_REG_FLAG_P, NULL, HFILL }},
3195 { &hf_lisp_mreg_flags_sec,
3196 { "S bit (LISP-SEC capable)", "lisp.mreg.flags.sec",
3197 FT_BOOLEAN, 24, TFS(&tfs_set_notset), MAP_REG_FLAG_S, NULL, HFILL }},
3198 { &hf_lisp_mreg_flags_xtrid,
3199 { "I bit (xTR-ID present)", "lisp.mreg.flags.xtrid",
3200 FT_BOOLEAN, 24, TFS(&tfs_set_notset), MAP_REG_FLAG_I, NULL, HFILL }},
3201 { &hf_lisp_mreg_flags_rtr,
3202 { "R bit (Built for an RTR)", "lisp.mreg.flags.rtr",
3203 FT_BOOLEAN, 24, TFS(&tfs_set_notset), MAP_REG_FLAG_R, NULL, HFILL }},
3204 { &hf_lisp_mreg_flags_wmn,
3205 { "M bit (Want-Map-Notify)", "lisp.mreg.flags.wmn",
3206 FT_BOOLEAN, 24, TFS(&tfs_set_notset), MAP_REG_FLAG_M, NULL, HFILL }},
3207 { &hf_lisp_mreg_res,
3208 { "Reserved bits", "lisp.mreg.res",
3209 FT_UINT24, BASE_HEX, NULL, MAP_REG_RESERVED, "Must be zero", HFILL }},
3210 { &hf_lisp_mref_res,
3211 { "Reserved bits", "lisp.mref.res",
3212 FT_UINT24, BASE_HEX, NULL, MAP_REF_RESERVED, "Must be zero", HFILL }},
3213 { &hf_lisp_keyid,
3214 { "Key ID", "lisp.keyid",
3215 FT_UINT16, BASE_HEX, NULL, 0x0, NULL, HFILL }},
3216 { &hf_lisp_authlen,
3217 { "Authentication Data Length", "lisp.authlen",
3218 FT_UINT16, BASE_DEC, NULL, 0x0, NULL, HFILL }},
3219 { &hf_lisp_auth,
3220 { "Authentication Data", "lisp.auth",
3221 FT_BYTES, BASE_NONE, NULL, 0x0, NULL, HFILL }},
3222 { &hf_lisp_msrtr_keyid,
3223 { "MS-RTR Key ID", "lisp.msrtr.keyid",
3224 FT_UINT16, BASE_HEX, NULL, 0x0, NULL, HFILL }},
3225 { &hf_lisp_msrtr_authlen,
3226 { "MS-RTR Authentication Data Length", "lisp.msrtr.authlen",
3227 FT_UINT16, BASE_DEC, NULL, 0x0, NULL, HFILL }},
3228 { &hf_lisp_msrtr_auth,
3229 { "MS-RTR Authentication Data", "lisp.msrtr.auth",
3230 FT_BYTES, BASE_NONE, NULL, 0x0, NULL, HFILL }},
3231 { &hf_lisp_xtrid,
3232 { "xTR-ID", "lisp.xtrid",
3233 FT_BYTES, BASE_NONE, NULL, 0x0, NULL, HFILL }},
3234 { &hf_lisp_siteid,
3235 { "Site-ID", "lisp.siteid",
3236 FT_BYTES, BASE_NONE, NULL, 0x0, NULL, HFILL }},
3237 { &hf_lisp_mnot_flags_xtrid,
3238 { "I bit (xTR-ID present)", "lisp.mnot.flags.xtrid",
3239 FT_BOOLEAN, 24, TFS(&tfs_set_notset), MAP_NOT_FLAG_I, NULL, HFILL }},
3240 { &hf_lisp_mnot_flags_rtr,
3241 { "R bit (Built for an RTR)", "lisp.mnot.flags.rtr",
3242 FT_BOOLEAN, 24, TFS(&tfs_set_notset), MAP_NOT_FLAG_R, NULL, HFILL }},
3243 { &hf_lisp_mnot_res,
3244 { "Reserved bits", "lisp.mnot.res",
3245 FT_UINT24, BASE_HEX, NULL, MAP_NOT_RESERVED, "Must be zero", HFILL }},
3246 { &hf_lisp_info_r,
3247 { "R bit (Info-Reply)", "lisp.info.r",
3248 FT_BOOLEAN, 24, TFS(&tfs_set_notset), INFO_FLAG_R, NULL, HFILL }},
3249 { &hf_lisp_info_res1,
3250 { "Reserved bits", "lisp.info.res1",
3251 FT_UINT32, BASE_HEX, NULL, INFO_RESERVED, "Must be zero", HFILL }},
3252 { &hf_lisp_info_ttl,
3253 { "TTL", "lisp.info.ttl",
3254 FT_UINT32, BASE_DEC, NULL, 0x0, "RTR information time-to-live", HFILL }},
3255 { &hf_lisp_info_res2,
3256 { "Reserved bits", "lisp.info.res2",
3257 FT_UINT8, BASE_HEX, NULL, 0xFF, "Must be zero", HFILL }},
3258 { &hf_lisp_info_prefix_masklen,
3259 { "EID Prefix Mask Length", "lisp.info.prefix.masklen",
3260 FT_UINT8, BASE_DEC, NULL, 0x0, NULL, HFILL }},
3261 { &hf_lisp_info_prefix_afi,
3262 { "Prefix AFI", "lisp.info.prefix.afi",
3263 FT_UINT16, BASE_DEC, VALS(afn_vals), 0x0, NULL, HFILL }},
3264 { &hf_lisp_info_prefix_ipv4,
3265 { "Prefix", "lisp.info.prefix.ipv4",
3266 FT_IPv4, BASE_NONE, NULL, 0x0, NULL, HFILL }},
3267 { &hf_lisp_info_prefix_ipv6,
3268 { "Prefix", "lisp.info.prefix.ipv6",
3269 FT_IPv6, BASE_NONE, NULL, 0x0, NULL, HFILL }},
3270 { &hf_lisp_info_afi,
3271 { "AFI", "lisp.info.afi",
3272 FT_UINT16, BASE_DEC, VALS(afn_vals), 0x0, "Address Family Indicator", HFILL }},
3273 { &hf_lisp_loc,
3274 { "Locator Record", "lisp.loc",
3275 FT_NONE, BASE_NONE, NULL, 0x0, NULL, HFILL }},
3276 { &hf_lisp_loc_priority,
3277 { "Priority", "lisp.loc.priority",
3278 FT_UINT8, BASE_DEC, NULL, 0x0, NULL, HFILL }},
3279 { &hf_lisp_loc_weight,
3280 { "Weight", "lisp.loc.weight",
3281 FT_UINT8, BASE_DEC, NULL, 0x0, NULL, HFILL }},
3282 { &hf_lisp_loc_mpriority,
3283 { "Multicast Priority", "lisp.loc.multicast_priority",
3284 FT_UINT8, BASE_DEC, NULL, 0x0, NULL, HFILL }},
3285 { &hf_lisp_loc_mweight,
3286 { "Multicast Weight", "lisp.loc.multicast_weight",
3287 FT_UINT8, BASE_DEC, NULL, 0x0, NULL, HFILL }},
3288 { &hf_lisp_loc_flags,
3289 { "Flags", "lisp.loc.flags",
3290 FT_UINT16, BASE_HEX, NULL, 0x0, NULL, HFILL }},
3291 { &hf_lisp_loc_flags_local,
3292 { "Local", "lisp.loc.flags.local",
3293 FT_BOOLEAN, 16, TFS(&tfs_set_notset), LOCAL_BIT_MASK, NULL, HFILL }},
3294 { &hf_lisp_loc_flags_probe,
3295 { "Probe", "lisp.loc.flags.probe",
3296 FT_BOOLEAN, 16, TFS(&tfs_set_notset), PROBE_BIT_MASK, NULL, HFILL }},
3297 { &hf_lisp_loc_flags_reach,
3298 { "Reachable", "lisp.loc.flags.reach",
3299 FT_BOOLEAN, 16, TFS(&tfs_set_notset), REACH_BIT_MASK, NULL, HFILL }},
3300 { &hf_lisp_loc_flags_res,
3301 { "Reserved", "lisp.loc.flags.res",
3302 FT_UINT16, BASE_HEX, NULL, 0xFFF8, "Must be zero", HFILL }},
3303 { &hf_lisp_loc_afi,
3304 { "AFI", "lisp.loc.afi",
3305 FT_UINT16, BASE_DEC, VALS(afn_vals), 0x0, NULL, HFILL }},
3306 { &hf_lisp_loc_locator,
3307 { "Locator", "lisp.loc.locator",
3308 FT_STRING, BASE_NONE, NULL, 0x0, NULL, HFILL }},
3309 { &hf_lisp_mapping,
3310 { "Mapping Record", "lisp.mapping",
3311 FT_NONE, BASE_NONE, NULL, 0x0, NULL, HFILL }},
3312 { &hf_lisp_mapping_ttl,
3313 { "Record TTL", "lisp.mapping.ttl",
3314 FT_UINT32, BASE_DEC, NULL, 0x0, NULL, HFILL }},
3315 { &hf_lisp_mapping_loccnt,
3316 { "Locator Count", "lisp.mapping.loccnt",
3317 FT_UINT8, BASE_DEC, NULL, 0x0, NULL, HFILL }},
3318 { &hf_lisp_mapping_eid_masklen,
3319 { "EID Mask Length", "lisp.mapping.eid.masklen",
3320 FT_UINT8, BASE_DEC, NULL, 0x0, NULL, HFILL }},
3321 { &hf_lisp_mapping_act,
3322 { "Action", "lisp.mapping.act",
3323 FT_UINT16, BASE_DEC, VALS(mapping_actions), 0xE000, NULL, HFILL }},
3324 { &hf_lisp_mapping_auth,
3325 { "Authoritative bit", "lisp.mapping.auth",
3326 FT_BOOLEAN, 16, TFS(&tfs_set_notset), LISP_MAP_AUTH, NULL, HFILL }},
3327 { &hf_lisp_referral_incomplete,
3328 { "Incomplete", "lisp.referral.incomplete",
3329 FT_BOOLEAN, 16, TFS(&tfs_set_notset), REFERRAL_INCOMPLETE, NULL, HFILL }},
3330 { &hf_lisp_mapping_res1,
3331 { "Reserved", "lisp.mapping.res1",
3332 FT_UINT16, BASE_HEX, NULL, 0x07FF, NULL, HFILL }},
3333 { &hf_lisp_mapping_res2,
3334 { "Reserved", "lisp.mapping.res2",
3335 FT_UINT16, BASE_HEX, NULL, 0xF000, NULL, HFILL }},
3336 { &hf_lisp_mapping_ver,
3337 { "Mapping Version", "lisp.mapping.ver",
3338 FT_UINT16, BASE_DEC, NULL, 0x0FFF, NULL, HFILL }},
3339 { &hf_lisp_referral_sigcnt,
3340 { "Signature Count", "lisp.referral.sigcnt",
3341 FT_UINT16, BASE_DEC, NULL, 0xF000, NULL, HFILL }},
3342 { &hf_lisp_mapping_eid_afi,
3343 { "EID Prefix AFI", "lisp.mapping.eid.afi",
3344 FT_UINT16, BASE_DEC, VALS(afn_vals), 0x0, NULL, HFILL }},
3345 { &hf_lisp_mapping_eid_ipv4,
3346 { "EID Prefix", "lisp.mapping.eid.ipv4",
3347 FT_IPv4, BASE_NONE, NULL, 0x0, NULL, HFILL }},
3348 { &hf_lisp_mapping_eid_ipv6,
3349 { "EID Prefix", "lisp.mapping.eid.ipv6",
3350 FT_IPv6, BASE_NONE, NULL, 0x0, NULL, HFILL }},
3351 { &hf_lisp_mapping_eid_mac,
3352 { "EID Prefix", "lisp.mapping.eid.mac",
3353 FT_ETHER, BASE_NONE, NULL, 0x0, NULL, HFILL }},
3354 { &hf_lisp_mapping_eid_dn,
3355 { "EID Prefix", "lisp.mapping.eid.dn",
3356 FT_STRINGZ, BASE_NONE, NULL, 0x0, NULL, HFILL }},
3357 { &hf_lisp_ecm_flags_sec,
3358 { "S bit (LISP-SEC capable)", "lisp.ecm.flags.sec",
3359 FT_BOOLEAN, 32, TFS(&tfs_set_notset), ECM_FLAG_S, NULL, HFILL }},
3360 { &hf_lisp_ecm_flags_ddt,
3361 { "D bit (DDT-originated)", "lisp.ecm.flags.ddt",
3362 FT_BOOLEAN, 32, TFS(&tfs_set_notset), ECM_FLAG_D, NULL, HFILL }},
3363 { &hf_lisp_ecm_res,
3364 { "Reserved bits", "lisp.ecm.res",
3365 FT_UINT32, BASE_HEX, NULL, 0x03FFFFFF, NULL, HFILL }},
3366 { &hf_lisp_lcaf,
3367 { "LCAF", "lisp.lcaf",
3368 FT_NONE, BASE_NONE, NULL, 0x0, NULL, HFILL }},
3369 { &hf_lisp_lcaf_header,
3370 { "LCAF Header", "lisp.lcaf.header",
3371 FT_BYTES, BASE_NONE, NULL, 0x0, NULL, HFILL }},
3372 { &hf_lisp_lcaf_res1,
3373 { "Reserved bits", "lisp.lcaf.res1",
3374 FT_UINT8, BASE_HEX, NULL, 0x0, NULL, HFILL }},
3375 { &hf_lisp_lcaf_flags,
3376 { "Flags", "lisp.lcaf.flags",
3377 FT_UINT8, BASE_HEX, NULL, 0x0, NULL, HFILL }},
3378 { &hf_lisp_lcaf_type,
3379 { "Type", "lisp.lcaf.type",
3380 FT_UINT8, BASE_DEC, VALS(lcaf_typevals), 0x0, "LISP LCAF Type", HFILL }},
3381 { &hf_lisp_lcaf_res2,
3382 { "Reserved bits", "lisp.lcaf.res2",
3383 FT_UINT8, BASE_HEX, NULL, 0x0, NULL, HFILL }},
3384 { &hf_lisp_lcaf_length,
3385 { "Length", "lisp.lcaf.length",
3386 FT_UINT16, BASE_DEC, NULL, 0x0, NULL, HFILL }},
3387 { &hf_lisp_lcaf_afi_list_item,
3388 { "List Item", "lisp.lcaf.afi_list.item",
3389 FT_NONE, BASE_NONE, NULL, 0x0, "AFI List Item", HFILL }},
3390 { &hf_lisp_lcaf_afi_list_afi,
3391 { "List Item AFI", "lisp.lcaf.afi_list.afi",
3392 FT_UINT16, BASE_DEC, VALS(afn_vals), 0x0, NULL, HFILL }},
3393 { &hf_lisp_lcaf_afi_list_ipv4,
3394 { "List Item Address", "lisp.lcaf.afi_list.ipv4",
3395 FT_IPv4, BASE_NONE, NULL, 0x0, NULL, HFILL }},
3396 { &hf_lisp_lcaf_afi_list_ipv6,
3397 { "List Item Address", "lisp.lcaf.afi_list.ipv6",
3398 FT_IPv6, BASE_NONE, NULL, 0x0, NULL, HFILL }},
3399 { &hf_lisp_lcaf_afi_list_mac,
3400 { "List Item Address", "lisp.lcaf.afi_list.mac",
3401 FT_ETHER, BASE_NONE, NULL, 0x0, NULL, HFILL }},
3402 { &hf_lisp_lcaf_afi_list_dn,
3403 { "List Item Address", "lisp.lcaf.afi_list.dn",
3404 FT_STRINGZ, BASE_NONE, NULL, 0x0, NULL, HFILL }},
3405 { &hf_lisp_lcaf_iid,
3406 { "Instance ID", "lisp.lcaf.iid",
3407 FT_UINT32, BASE_DEC, NULL, 0x0, NULL, HFILL }},
3408 { &hf_lisp_lcaf_iid_afi,
3409 { "Address AFI", "lisp.lcaf.iid.afi",
3410 FT_UINT16, BASE_DEC, VALS(afn_vals), 0x0, NULL, HFILL }},
3411 { &hf_lisp_lcaf_iid_ipv4,
3412 { "Address", "lisp.lcaf.iid.ipv4",
3413 FT_IPv4, BASE_NONE, NULL, 0x0, NULL, HFILL }},
3414 { &hf_lisp_lcaf_iid_ipv6,
3415 { "Address", "lisp.lcaf.iid.ipv6",
3416 FT_IPv6, BASE_NONE, NULL, 0x0, NULL, HFILL }},
3417 { &hf_lisp_lcaf_iid_mac,
3418 { "Address", "lisp.lcaf.iid.mac",
3419 FT_ETHER, BASE_NONE, NULL, 0x0, NULL, HFILL }},
3420 { &hf_lisp_lcaf_iid_dn,
3421 { "Address", "lisp.lcaf.iid.dn",
3422 FT_STRINGZ, BASE_NONE, NULL, 0x0, NULL, HFILL }},
3423 { &hf_lisp_lcaf_asn,
3424 { "AS Number", "lisp.lcaf.asn",
3425 FT_UINT32, BASE_DEC, NULL, 0x0, NULL, HFILL }},
3426 { &hf_lisp_lcaf_asn_afi,
3427 { "Address AFI", "lisp.lcaf.asn.afi",
3428 FT_UINT16, BASE_DEC, VALS(afn_vals), 0x0, NULL, HFILL }},
3429 { &hf_lisp_lcaf_asn_ipv4,
3430 { "Address", "lisp.lcaf.asn.ipv4",
3431 FT_IPv4, BASE_NONE, NULL, 0x0, NULL, HFILL }},
3432 { &hf_lisp_lcaf_asn_ipv6,
3433 { "Address", "lisp.lcaf.asn.ipv6",
3434 FT_IPv6, BASE_NONE, NULL, 0x0, NULL, HFILL }},
3435 { &hf_lisp_lcaf_asn_mac,
3436 { "Address", "lisp.lcaf.asn.mac",
3437 FT_ETHER, BASE_NONE, NULL, 0x0, NULL, HFILL }},
3438 { &hf_lisp_lcaf_asn_dn,
3439 { "Address", "lisp.lcaf.asn.dn",
3440 FT_STRINGZ, BASE_NONE, NULL, 0x0, NULL, HFILL }},
3441 { &hf_lisp_lcaf_geo_lat,
3442 { "Latitude", "lisp.lcaf.geo.lat",
3443 FT_NONE, BASE_NONE, NULL, 0x0, NULL, HFILL }},
3444 { &hf_lisp_lcaf_geo_lat_hemisphere,
3445 { "Hemisphere", "lisp.lcaf.geo.lat.hemisphere",
3446 FT_UINT16, BASE_DEC, VALS(lat_typevals), 0x8000, NULL, HFILL }},
3447 { &hf_lisp_lcaf_geo_lat_deg,
3448 { "Degrees", "lisp.lcaf.geo.lat.deg",
3449 FT_UINT16, BASE_DEC, NULL, 0x7FFF, NULL, HFILL }},
3450 { &hf_lisp_lcaf_geo_lat_min,
3451 { "Minutes", "lisp.lcaf.geo.lat.min",
3452 FT_UINT8, BASE_DEC, NULL, 0x0, NULL, HFILL }},
3453 { &hf_lisp_lcaf_geo_lat_sec,
3454 { "Seconds", "lisp.lcaf.geo.lat.sec",
3455 FT_UINT8, BASE_DEC, NULL, 0x0, NULL, HFILL }},
3456 { &hf_lisp_lcaf_geo_lon,
3457 { "Longitude", "lisp.lcaf.geo.lon",
3458 FT_NONE, BASE_NONE, NULL, 0x0, NULL, HFILL }},
3459 { &hf_lisp_lcaf_geo_lon_hemisphere,
3460 { "Hemisphere", "lisp.lcaf.geo.lon.hemisphere",
3461 FT_UINT16, BASE_DEC, VALS(lon_typevals), 0x8000, NULL, HFILL }},
3462 { &hf_lisp_lcaf_geo_lon_deg,
3463 { "Degrees", "lisp.lcaf.geo.lon.deg",
3464 FT_UINT16, BASE_DEC, NULL, 0x7FFF, NULL, HFILL }},
3465 { &hf_lisp_lcaf_geo_lon_min,
3466 { "Minutes", "lisp.lcaf.geo.lon.min",
3467 FT_UINT8, BASE_DEC, NULL, 0x0, NULL, HFILL }},
3468 { &hf_lisp_lcaf_geo_lon_sec,
3469 { "Seconds", "lisp.lcaf.geo.lon.sec",
3470 FT_UINT8, BASE_DEC, NULL, 0x0, NULL, HFILL }},
3471 { &hf_lisp_lcaf_geo_alt,
3472 { "Altitude", "lisp.lcaf.geo.alt",
3473 FT_NONE, BASE_NONE, NULL, 0x0, NULL, HFILL }},
3474 { &hf_lisp_lcaf_geo_afi,
3475 { "Address AFI", "lisp.lcaf.geo.afi",
3476 FT_UINT16, BASE_DEC, VALS(afn_vals), 0x0, NULL, HFILL }},
3477 { &hf_lisp_lcaf_geo_ipv4,
3478 { "Address", "lisp.lcaf.geo.ipv4",
3479 FT_IPv4, BASE_NONE, NULL, 0x0, NULL, HFILL }},
3480 { &hf_lisp_lcaf_geo_ipv6,
3481 { "Address", "lisp.lcaf.geo.ipv6",
3482 FT_IPv6, BASE_NONE, NULL, 0x0, NULL, HFILL }},
3483 { &hf_lisp_lcaf_geo_mac,
3484 { "Address", "lisp.lcaf.geo.mac",
3485 FT_ETHER, BASE_NONE, NULL, 0x0, NULL, HFILL }},
3486 { &hf_lisp_lcaf_geo_dn,
3487 { "Address", "lisp.lcaf.geo.dn",
3488 FT_STRINGZ, BASE_NONE, NULL, 0x0, NULL, HFILL }},
3489 { &hf_lisp_lcaf_nonce_loc_res,
3490 { "Reserved bits", "lisp.lcaf.nonce_loc.res",
3491 FT_UINT8, BASE_HEX, NULL, 0x0, NULL, HFILL }},
3492 { &hf_lisp_lcaf_nonce_loc,
3493 { "Nonce", "lisp.lcaf.nonce_loc",
3494 FT_UINT24, BASE_HEX, NULL, 0x0, NULL, HFILL }},
3495 { &hf_lisp_lcaf_nonce_loc_afi,
3496 { "Address AFI", "lisp.lcaf.nonce_loc.afi",
3497 FT_UINT16, BASE_DEC, VALS(afn_vals), 0x0, NULL, HFILL }},
3498 { &hf_lisp_lcaf_nonce_loc_ipv4,
3499 { "Address", "lisp.lcaf.nonce_loc.ipv4",
3500 FT_IPv4, BASE_NONE, NULL, 0x0, NULL, HFILL }},
3501 { &hf_lisp_lcaf_nonce_loc_ipv6,
3502 { "Address", "lisp.lcaf.nonce_loc.ipv6",
3503 FT_IPv6, BASE_NONE, NULL, 0x0, NULL, HFILL }},
3504 { &hf_lisp_lcaf_nonce_loc_mac,
3505 { "Address", "lisp.lcaf.nonce_loc.mac",
3506 FT_ETHER, BASE_NONE, NULL, 0x0, NULL, HFILL }},
3507 { &hf_lisp_lcaf_nonce_loc_dn,
3508 { "Address", "lisp.lcaf.nonce_loc.dn",
3509 FT_STRINGZ, BASE_NONE, NULL, 0x0, NULL, HFILL }},
3510 { &hf_lisp_lcaf_mcinfo_flags,
3511 { "Multicast Info Flags", "lisp.lcaf.mcinfo.flags",
3512 FT_UINT8, BASE_HEX, NULL, 0x0, NULL, HFILL }},
3513 { &hf_lisp_lcaf_mcinfo_flags_res,
3514 { "Reserved", "lisp.lcaf.mcinfo.flags.res",
3515 FT_UINT8, BASE_HEX, NULL, 0xF8, "Must be zero", HFILL }},
3516 { &hf_lisp_lcaf_mcinfo_flags_rp,
3517 { "RP-bit", "lisp.lcaf.mcinfo.flags.rp",
3518 FT_BOOLEAN, 8, TFS(&tfs_set_notset), MCINFO_FLAG_R, NULL, HFILL }},
3519 { &hf_lisp_lcaf_mcinfo_flags_leave,
3520 { "Leave (L-bit)", "lisp.lcaf.mcinfo.flags.leave",
3521 FT_BOOLEAN, 8, TFS(&tfs_set_notset), MCINFO_FLAG_L, NULL, HFILL }},
3522 { &hf_lisp_lcaf_mcinfo_flags_join,
3523 { "Join (J-bit)", "lisp.lcaf_mcinfo.flags.join",
3524 FT_BOOLEAN, 8, TFS(&tfs_set_notset), MCINFO_FLAG_J, NULL, HFILL }},
3525 { &hf_lisp_lcaf_mcinfo_iid,
3526 { "Instance ID", "lisp.lcaf.mcinfo_iid",
3527 FT_UINT32, BASE_DEC, NULL, 0x0, NULL, HFILL }},
3528 { &hf_lisp_lcaf_mcinfo_res,
3529 { "Reserved bits", "lisp.lcaf.mcinfo.res",
3530 FT_UINT16, BASE_HEX, NULL, 0x0, NULL, HFILL }},
3531 { &hf_lisp_lcaf_mcinfo_src_masklen,
3532 { "Source Mask Length", "lisp.lcaf.mcinfo.src.masklen",
3533 FT_UINT8, BASE_DEC, NULL, 0x0, NULL, HFILL }},
3534 { &hf_lisp_lcaf_mcinfo_grp_masklen,
3535 { "Group Mask Length", "lisp.lcaf.mcinfo.grp.masklen",
3536 FT_UINT8, BASE_DEC, NULL, 0x0, NULL, HFILL }},
3537 { &hf_lisp_lcaf_mcinfo_src,
3538 { "Source/Subnet Address", "lisp.lcaf.mcinfo.src",
3539 FT_NONE, BASE_NONE, NULL, 0x0, NULL, HFILL }},
3540 { &hf_lisp_lcaf_mcinfo_src_afi,
3541 { "Source/Subnet AFI", "lisp.lcaf.mcinfo.src.afi",
3542 FT_UINT16, BASE_DEC, VALS(afn_vals), 0x0, NULL, HFILL }},
3543 { &hf_lisp_lcaf_mcinfo_src_ipv4,
3544 { "Source/Subnet Address", "lisp.lcaf.mcinfo.src.ipv4",
3545 FT_IPv4, BASE_NONE, NULL, 0x0, NULL, HFILL }},
3546 { &hf_lisp_lcaf_mcinfo_src_ipv6,
3547 { "Source/Subnet Address", "lisp.lcaf.mcinfo.src.ipv6",
3548 FT_IPv6, BASE_NONE, NULL, 0x0, NULL, HFILL }},
3549 { &hf_lisp_lcaf_mcinfo_grp,
3550 { "Group Address", "lisp.lcaf.mcinfo.grp",
3551 FT_NONE, BASE_NONE, NULL, 0x0, NULL, HFILL }},
3552 { &hf_lisp_lcaf_mcinfo_grp_afi,
3553 { "Group AFI", "lisp.lcaf.mcinfo.grp.afi",
3554 FT_UINT16, BASE_DEC, VALS(afn_vals), 0x0, NULL, HFILL }},
3555 { &hf_lisp_lcaf_mcinfo_grp_ipv4,
3556 { "Group Address", "lisp.lcaf.mcinfo.grp.ipv4",
3557 FT_IPv4, BASE_NONE, NULL, 0x0, NULL, HFILL }},
3558 { &hf_lisp_lcaf_mcinfo_grp_ipv6,
3559 { "Group Address", "lisp.lcaf.mcinfo.grp.ipv6",
3560 FT_IPv6, BASE_NONE, NULL, 0x0, NULL, HFILL }},
3561 { &hf_lisp_lcaf_elp_hop,
3562 { "Reencap Hop", "lisp.lcaf.elp_hop",
3563 FT_NONE, BASE_NONE, NULL, 0x0, NULL, HFILL }},
3564 { &hf_lisp_lcaf_elp_hop_flags,
3565 { "Flags", "lisp.lcaf.elp_hop.flags",
3566 FT_UINT16, BASE_HEX, NULL, 0x0, NULL, HFILL }},
3567 { &hf_lisp_lcaf_elp_hop_flags_res,
3568 { "Reserved", "lisp.lcaf.elp_hop.flags.res",
3569 FT_UINT16, BASE_HEX, NULL, 0xFFF8, "Must be zero", HFILL }},
3570 { &hf_lisp_lcaf_elp_hop_flags_lookup,
3571 { "Lookup", "lisp.lcaf.elp_hop.flags.local",
3572 FT_BOOLEAN, 16, TFS(&tfs_set_notset), ELP_FLAG_L, NULL, HFILL }},
3573 { &hf_lisp_lcaf_elp_hop_flags_probe,
3574 { "Probe", "lisp.lcaf.elp_hop.flags.probe",
3575 FT_BOOLEAN, 16, TFS(&tfs_set_notset), ELP_FLAG_P, NULL, HFILL }},
3576 { &hf_lisp_lcaf_elp_hop_flags_strict,
3577 { "Strict", "lisp.lcaf_elp_hop.flags.strict",
3578 FT_BOOLEAN, 16, TFS(&tfs_set_notset), ELP_FLAG_S, NULL, HFILL }},
3579 { &hf_lisp_lcaf_elp_hop_afi,
3580 { "Reencap Hop AFI", "lisp.lcaf.elp_hop.afi",
3581 FT_UINT16, BASE_DEC, VALS(afn_vals), 0x0, NULL, HFILL }},
3582 { &hf_lisp_lcaf_elp_hop_ipv4,
3583 { "Reencap Hop", "lisp.lcaf.elp_hop.ipv4",
3584 FT_IPv4, BASE_NONE, NULL, 0x0, NULL, HFILL }},
3585 { &hf_lisp_lcaf_elp_hop_ipv6,
3586 { "Reencap Hop", "lisp.lcaf.elp_hop.ipv6",
3587 FT_IPv6, BASE_NONE, NULL, 0x0, NULL, HFILL }},
3588 { &hf_lisp_lcaf_srcdst_res,
3589 { "Reserved bits", "lisp.lcaf.srcdst.res",
3590 FT_UINT16, BASE_HEX, NULL, 0x0, NULL, HFILL }},
3591 { &hf_lisp_lcaf_srcdst_src_masklen,
3592 { "Source Prefix Mask Length", "lisp.lcaf.srcdst.src.masklen",
3593 FT_UINT8, BASE_DEC, NULL, 0x0, NULL, HFILL }},
3594 { &hf_lisp_lcaf_srcdst_dst_masklen,
3595 { "Destination Prefix Mask Length", "lisp.lcaf.srcdst.dst.masklen",
3596 FT_UINT8, BASE_DEC, NULL, 0x0, NULL, HFILL }},
3597 { &hf_lisp_lcaf_srcdst_src,
3598 { "Source Prefix", "lisp.lcaf.srcdst.src",
3599 FT_NONE, BASE_NONE, NULL, 0x0, NULL, HFILL }},
3600 { &hf_lisp_lcaf_srcdst_src_afi,
3601 { "Source Prefix AFI", "lisp.lcaf.srcdst.src.afi",
3602 FT_UINT16, BASE_DEC, VALS(afn_vals), 0x0, NULL, HFILL }},
3603 { &hf_lisp_lcaf_srcdst_src_ipv4,
3604 { "Source Prefix", "lisp.lcaf.srcdst.src.ipv4",
3605 FT_IPv4, BASE_NONE, NULL, 0x0, NULL, HFILL }},
3606 { &hf_lisp_lcaf_srcdst_src_ipv6,
3607 { "Source Prefix", "lisp.lcaf.srcdst.src.ipv6",
3608 FT_IPv6, BASE_NONE, NULL, 0x0, NULL, HFILL }},
3609 { &hf_lisp_lcaf_srcdst_src_mac,
3610 { "Destination Prefix", "lisp.lcaf.srcdst.src.mac",
3611 FT_ETHER, BASE_NONE, NULL, 0x0, NULL, HFILL }},
3612 { &hf_lisp_lcaf_srcdst_dst,
3613 { "Destination Prefix", "lisp.lcaf.srcdst.dst",
3614 FT_NONE, BASE_NONE, NULL, 0x0, NULL, HFILL }},
3615 { &hf_lisp_lcaf_srcdst_dst_afi,
3616 { "Destination Prefix AFI", "lisp.lcaf.srcdst.dst.afi",
3617 FT_UINT16, BASE_DEC, VALS(afn_vals), 0x0, NULL, HFILL }},
3618 { &hf_lisp_lcaf_srcdst_dst_ipv4,
3619 { "Destination Prefix", "lisp.lcaf.srcdst.dst.ipv4",
3620 FT_IPv4, BASE_NONE, NULL, 0x0, NULL, HFILL }},
3621 { &hf_lisp_lcaf_srcdst_dst_ipv6,
3622 { "Destination Prefix", "lisp.lcaf.srcdst.dst.ipv6",
3623 FT_IPv6, BASE_NONE, NULL, 0x0, NULL, HFILL }},
3624 { &hf_lisp_lcaf_srcdst_dst_mac,
3625 { "Destination Prefix", "lisp.lcaf.srcdst.dst.mac",
3626 FT_ETHER, BASE_NONE, NULL, 0x0, NULL, HFILL }},
3627 { &hf_lisp_lcaf_rle_entry,
3628 { "RTR/ETR", "lisp.lcaf.rle_entry",
3629 FT_NONE, BASE_NONE, NULL, 0x0, NULL, HFILL }},
3630 { &hf_lisp_lcaf_rle_entry_res,
3631 { "Reserved bits", "lisp.lcaf.rle_entry.res",
3632 FT_UINT24, BASE_HEX, NULL, 0x0, "Must be zero", HFILL }},
3633 { &hf_lisp_lcaf_rle_entry_level,
3634 { "Level Value", "lisp.lcaf.rle_entry.level",
3635 FT_UINT8, BASE_DEC, NULL, 0x0, NULL, HFILL }},
3636 { &hf_lisp_lcaf_rle_entry_afi,
3637 { "RTR/ETR AFI", "lisp.lcaf.rle_entry.afi",
3638 FT_UINT16, BASE_DEC, VALS(afn_vals), 0x0, NULL, HFILL }},
3639 { &hf_lisp_lcaf_rle_entry_ipv4,
3640 { "RTR/ETR", "lisp.lcaf.rle_entry.ipv4",
3641 FT_IPv4, BASE_NONE, NULL, 0x0, NULL, HFILL }},
3642 { &hf_lisp_lcaf_rle_entry_ipv6,
3643 { "RTR/ETR", "lisp.lcaf.rle_entry.ipv6",
3644 FT_IPv6, BASE_NONE, NULL, 0x0, NULL, HFILL }},
3645 { &hf_lisp_lcaf_kv_key,
3646 { "Key", "lisp.lcaf.kv_key",
3647 FT_NONE, BASE_NONE, NULL, 0x0, NULL, HFILL }},
3648 { &hf_lisp_lcaf_kv_key_afi,
3649 { "Key AFI", "lisp.lcaf.kv_key.afi",
3650 FT_UINT16, BASE_DEC, VALS(afn_vals), 0x0, NULL, HFILL }},
3651 { &hf_lisp_lcaf_kv_key_ipv4,
3652 { "Key", "lisp.lcaf.kv_key.ipv4",
3653 FT_IPv4, BASE_NONE, NULL, 0x0, NULL, HFILL }},
3654 { &hf_lisp_lcaf_kv_key_ipv6,
3655 { "Key", "lisp.lcaf.kv_key.ipv6",
3656 FT_IPv6, BASE_NONE, NULL, 0x0, NULL, HFILL }},
3657 { &hf_lisp_lcaf_kv_key_mac,
3658 { "Key", "lisp.lcaf.kv_key.mac",
3659 FT_ETHER, BASE_NONE, NULL, 0x0, NULL, HFILL }},
3660 { &hf_lisp_lcaf_kv_key_dn,
3661 { "Key", "lisp.lcaf.kv_key.dn",
3662 FT_STRINGZ, BASE_NONE, NULL, 0x0, NULL, HFILL }},
3663 { &hf_lisp_lcaf_kv_value,
3664 { "Value", "lisp.lcaf.kv_value",
3665 FT_NONE, BASE_NONE, NULL, 0x0, NULL, HFILL }},
3666 { &hf_lisp_lcaf_kv_value_afi,
3667 { "Value AFI", "lisp.lcaf.kv_value.afi",
3668 FT_UINT16, BASE_DEC, VALS(afn_vals), 0x0, NULL, HFILL }},
3669 { &hf_lisp_lcaf_kv_value_ipv4,
3670 { "Value", "lisp.lcaf.kv_value.ipv4",
3671 FT_IPv4, BASE_NONE, NULL, 0x0, NULL, HFILL }},
3672 { &hf_lisp_lcaf_kv_value_ipv6,
3673 { "Value", "lisp.lcaf.kv_value.ipv6",
3674 FT_IPv6, BASE_NONE, NULL, 0x0, NULL, HFILL }},
3675 { &hf_lisp_lcaf_kv_value_mac,
3676 { "Value", "lisp.lcaf.kv_value.mac",
3677 FT_ETHER, BASE_NONE, NULL, 0x0, NULL, HFILL }},
3678 { &hf_lisp_lcaf_kv_value_dn,
3679 { "Value", "lisp.lcaf.kv_value.dn",
3680 FT_STRINGZ, BASE_NONE, NULL, 0x0, NULL, HFILL }},
3681 { &hf_lisp_lcaf_natt_rloc,
3682 { "RLOC", "lisp.lcaf.natt.rloc",
3683 FT_NONE, BASE_NONE, NULL, 0x0, NULL, HFILL }},
3684 { &hf_lisp_lcaf_natt_rloc_afi,
3685 { "RLOC AFI", "lisp.lcaf.natt.rloc.afi",
3686 FT_UINT16, BASE_DEC, VALS(afn_vals), 0x0, NULL, HFILL }},
3687 { &hf_lisp_lcaf_natt_rloc_ipv4,
3688 { "RLOC", "lisp.lcaf.natt.rloc.ipv4",
3689 FT_IPv4, BASE_NONE, NULL, 0x0, NULL, HFILL }},
3690 { &hf_lisp_lcaf_natt_rloc_ipv6,
3691 { "RLOC", "lisp.lcaf.natt.rloc.ipv6",
3692 FT_IPv6, BASE_NONE, NULL, 0x0, NULL, HFILL }},
3693 { &hf_lisp_lcaf_natt_msport,
3694 { "MS UDP Port Number", "lisp.lcaf.natt.msport",
3695 FT_UINT16, BASE_DEC, NULL, 0x0, NULL, HFILL }},
3696 { &hf_lisp_lcaf_natt_etrport,
3697 { "ETR UDP Port Number", "lisp.lcaf.natt.etrport",
3698 FT_UINT16, BASE_DEC, NULL, 0x0, NULL, HFILL }},
3699 { &hf_lisp_lcaf_vendor_res,
3700 { "Reserved", "lisp.lcaf.vendor.res",
3701 FT_UINT8, BASE_HEX, NULL, 0x0, "Must be zero", HFILL }},
3702 { &hf_lisp_lcaf_vendor_oui,
3703 { "OUI", "lisp.lcaf.vendor.oui",
3704 FT_UINT24, BASE_HEX, VALS(oui_vals), 0x0, "Organizationally Unique Identifier", HFILL }},
3705 { &hf_lisp_lcaf_vendor_data,
3706 { "Vendor Specific Data", "lisp.lcaf.vendor.data",
3707 FT_BYTES, BASE_NONE, NULL, 0x0, NULL, HFILL }},
3710 /* Setup protocol subtree array */
3711 static int *ett[] = {
3712 &ett_lisp,
3713 &ett_lisp_mr,
3714 &ett_lisp_mreq_flags,
3715 &ett_lisp_mapping,
3716 &ett_lisp_itr,
3717 &ett_lisp_record,
3718 &ett_lisp_lcaf,
3719 &ett_lisp_lcaf_header,
3720 &ett_lisp_lcaf_geo_lat,
3721 &ett_lisp_lcaf_geo_lon,
3722 &ett_lisp_lcaf_natt_rloc,
3723 &ett_lisp_lcaf_mcinfo_flags,
3724 &ett_lisp_lcaf_mcinfo_src,
3725 &ett_lisp_lcaf_mcinfo_grp,
3726 &ett_lisp_lcaf_elp_hop,
3727 &ett_lisp_lcaf_elp_hop_flags,
3728 &ett_lisp_lcaf_srcdst_src,
3729 &ett_lisp_lcaf_srcdst_dst,
3730 &ett_lisp_lcaf_rle_entry,
3731 &ett_lisp_lcaf_kv_key,
3732 &ett_lisp_lcaf_kv_value,
3733 &ett_lisp_lcaf_vendor,
3734 &ett_lisp_loc,
3735 &ett_lisp_loc_flags,
3736 &ett_lisp_info_prefix,
3737 &ett_lisp_afi_list
3740 static ei_register_info ei[] = {
3741 { &ei_lisp_undecoded, { "lisp.undecoded", PI_UNDECODED, PI_WARN, "Not dissected yet (report to wireshark.org)", EXPFILL }},
3742 { &ei_lisp_unexpected_field, { "lisp.unexpected_field", PI_PROTOCOL, PI_ERROR, "Unexpected field", EXPFILL }},
3743 { &ei_lisp_invalid_field, { "lisp.invalid_field", PI_PROTOCOL, PI_WARN, "Invalid field", EXPFILL }},
3744 { &ei_lisp_expected_field, { "lisp.expected_field", PI_PROTOCOL, PI_ERROR, "Expecting field", EXPFILL }},
3747 expert_module_t* expert_lisp;
3749 /* Register the protocol name and description */
3750 proto_lisp = proto_register_protocol("Locator/ID Separation Protocol",
3751 "LISP Control", "lisp");
3753 /* Required function calls to register the header fields and subtrees used */
3754 proto_register_field_array(proto_lisp, hf, array_length(hf));
3755 proto_register_subtree_array(ett, array_length(ett));
3756 expert_lisp = expert_register_protocol(proto_lisp);
3757 expert_register_field_array(expert_lisp, ei, array_length(ei));
3759 /* Register dissector so that other dissectors can call it */
3760 lisp_handle = register_dissector("lisp", dissect_lisp, proto_lisp);
3765 * Simple form of proto_reg_handoff_lisp which can be used if there are
3766 * no prefs-dependent registration function calls.
3769 void
3770 proto_reg_handoff_lisp(void)
3772 dissector_add_uint_with_preference("udp.port", LISP_CONTROL_PORT, lisp_handle);
3773 ipv4_handle = find_dissector_add_dependency("ip", proto_lisp);
3774 ipv6_handle = find_dissector_add_dependency("ipv6", proto_lisp);
3778 * Editor modelines - https://www.wireshark.org/tools/modelines.html
3780 * Local variables:
3781 * c-basic-offset: 4
3782 * tab-width: 8
3783 * indent-tabs-mode: nil
3784 * End:
3786 * vi: set shiftwidth=4 tabstop=8 expandtab:
3787 * :indentSize=4:tabSize=8:noTabs=true: