2 * Routines for decoding isis complete & partial SNP and their payload
4 * $Id: packet-isis-snp.c,v 1.1 1999/12/15 04:34:19 guy Exp $
5 * Stuart Stanley <stuarts@mxmail.net>
7 * Ethereal - Network traffic analyzer
8 * By Gerald Combs <gerald@zing.org>
9 * Copyright 1998 Gerald Combs
12 * This program is free software; you can redistribute it and/or
13 * modify it under the terms of the GNU General Public License
14 * as published by the Free Software Foundation; either version 2
15 * of the License, or (at your option) any later version.
17 * This program is distributed in the hope that it will be useful,
18 * but WITHOUT ANY WARRANTY; without even the implied warranty of
19 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
20 * GNU General Public License for more details.
22 * You should have received a copy of the GNU General Public License
23 * along with this program; if not, write to the Free Software
24 * Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
33 #ifdef HAVE_SYS_TYPES_H
34 # include <sys/types.h>
41 #include "packet-isis.h"
42 #include "packet-isis-clv.h"
43 #include "packet-isis-lsp.h"
44 #include "packet-isis-snp.h"
47 static int proto_isis_csnp = -1;
48 static int hf_isis_csnp_pdu_length = -1;
49 static gint ett_isis_csnp = -1;
50 static gint ett_isis_csnp_lsp_entries = -1;
51 static gint ett_isis_csnp_authentication = -1;
52 static gint ett_isis_csnp_clv_unknown = -1;
55 static int proto_isis_psnp = -1;
56 static int hf_isis_psnp_pdu_length = -1;
57 static gint ett_isis_psnp = -1;
58 static gint ett_isis_psnp_lsp_entries = -1;
59 static gint ett_isis_psnp_authentication = -1;
60 static gint ett_isis_psnp_clv_unknown = -1;
62 static void dissect_snp_lsp_entries(const u_char *pd, int offset,
63 guint length, frame_data *fd, proto_tree *tree );
64 static void dissect_l1_snp_authentication_clv(const u_char *pd, int offset,
65 guint length, frame_data *fd, proto_tree *tree );
66 static void dissect_l2_snp_authentication_clv(const u_char *pd, int offset,
67 guint length, frame_data *fd, proto_tree *tree );
69 static const isis_clv_handle_t clv_l1_csnp_opts[] = {
71 ISIS_CLV_L1_CSNP_LSP_ENTRIES,
73 &ett_isis_csnp_lsp_entries,
74 dissect_snp_lsp_entries
77 ISIS_CLV_L1_CSNP_AUTHENTICATION_NS,
78 "Authentication(non spec)",
79 &ett_isis_csnp_authentication,
80 dissect_l1_snp_authentication_clv
83 ISIS_CLV_L1_CSNP_AUTHENTICATION,
85 &ett_isis_csnp_authentication,
86 dissect_l1_snp_authentication_clv
93 static const isis_clv_handle_t clv_l2_csnp_opts[] = {
95 ISIS_CLV_L2_CSNP_LSP_ENTRIES,
97 &ett_isis_csnp_lsp_entries,
98 dissect_snp_lsp_entries
101 ISIS_CLV_L2_CSNP_AUTHENTICATION_NS,
102 "Authentication(non spec)",
103 &ett_isis_csnp_authentication,
104 dissect_l2_snp_authentication_clv
107 ISIS_CLV_L2_CSNP_AUTHENTICATION,
109 &ett_isis_csnp_authentication,
110 dissect_l2_snp_authentication_clv
117 static const isis_clv_handle_t clv_l1_psnp_opts[] = {
119 ISIS_CLV_L1_PSNP_LSP_ENTRIES,
121 &ett_isis_psnp_lsp_entries,
122 dissect_snp_lsp_entries
125 ISIS_CLV_L1_PSNP_AUTHENTICATION_NS,
126 "Authentication(non spec)",
127 &ett_isis_psnp_authentication,
128 dissect_l1_snp_authentication_clv
131 ISIS_CLV_L1_PSNP_AUTHENTICATION,
133 &ett_isis_psnp_authentication,
134 dissect_l1_snp_authentication_clv
141 static const isis_clv_handle_t clv_l2_psnp_opts[] = {
143 ISIS_CLV_L2_PSNP_LSP_ENTRIES,
145 &ett_isis_psnp_lsp_entries,
146 dissect_snp_lsp_entries
149 ISIS_CLV_L2_PSNP_AUTHENTICATION,
151 &ett_isis_psnp_authentication,
152 dissect_l2_snp_authentication_clv
155 ISIS_CLV_L2_PSNP_AUTHENTICATION_NS,
156 "Authentication(non spec)",
157 &ett_isis_psnp_authentication,
158 dissect_l2_snp_authentication_clv
165 * Name: dissect_snp_payload()
168 * All the snp packets use a common payload format. We have up
169 * to n entries (based on length), which are made of:
170 * 2 : remaining life time
172 * 4 : sequence number
176 * u_char * : packet data
177 * int : offset into packet data where we are.
178 * int : length of payload to decode.
179 * frame_data * : frame data (complete frame)
180 * proto_tree * : protocol display tree to fill out. May be NULL
183 * void, but we will add to proto tree if !NULL.
186 dissect_snp_lsp_entries(const u_char *pd, int offset, guint length,
187 frame_data *fd, proto_tree *tree ) {
190 ps = (isis_snp_t *) &pd[offset];
191 while ( length > 0 ) {
192 if ( length < sizeof(isis_psnp_t) ) {
193 isis_dissect_unknown(offset, length, tree, fd,
194 "Short SNP header entry (%d vs %d)", length,
195 sizeof(isis_psnp_t) );
199 proto_tree_add_text(tree, offset, 2, "Remaining life: %d",
200 pntohs(&ps->isis_snp_remaining_lifetime));
201 isis_lsp_decode_lsp_id( "LSP ID", tree, offset + 2,
202 &ps->isis_snp_lsp_id );
203 proto_tree_add_text(tree, offset+10, 4,
204 "LSP Sequence Number: 0x%04x",
205 pntohl(&ps->isis_snp_sequence_number));
206 proto_tree_add_text(tree, offset+14, 2,
207 "LSP checksum: 0x%02x",
208 pntohl(&ps->isis_snp_checksum));
209 length -= sizeof ( isis_snp_t );
210 offset += sizeof ( isis_snp_t );
217 * Name: isis_dissect_isis_csnp()
220 * Tear apart a L1 or L2 CSNP header and then call into payload dissect
221 * to pull apart the lsp id payload.
224 * int : type (l1 csnp, l2 csnp)
225 * u_char * : packet data
226 * int : offset into packet data where we are.
227 * guint : length of clv we are decoding
228 * frame_data * : frame data (complete frame)
229 * proto_tree * : protocol display tree to fill out. May be NULL
232 * void, but we will add to proto tree if !NULL.
235 isis_dissect_isis_csnp(int type, int header_length, const u_char *pd,
236 int offset, frame_data *fd, proto_tree *tree){
239 proto_tree *csnp_tree = NULL;
245 if (fd->cap_len < (offset + hlen)) {
246 isis_dissect_unknown(offset, hlen, tree, fd,
247 "not enough capture data for header (%d vs %d)",
248 hlen, offset - fd->cap_len);
252 ilp = (isis_csnp_t *) &pd[offset];
255 ti = proto_tree_add_item(tree, proto_isis_csnp,
256 offset, fd->cap_len - offset, NULL);
257 csnp_tree = proto_item_add_subtree(ti, ett_isis_csnp);
258 proto_tree_add_item(csnp_tree, hf_isis_csnp_pdu_length,
259 offset, 2, pntohs(&ilp->isis_csnp_pdu_length));
260 proto_tree_add_text(csnp_tree, offset + 2, 7,
261 "Source id: %02x%02x.%02x%02x.%02x%02x.%02x",
262 ilp->isis_csnp_source_id[0],
263 ilp->isis_csnp_source_id[1],
264 ilp->isis_csnp_source_id[2],
265 ilp->isis_csnp_source_id[3],
266 ilp->isis_csnp_source_id[4],
267 ilp->isis_csnp_source_id[5],
268 ilp->isis_csnp_source_id[6] );
269 isis_lsp_decode_lsp_id( "Start LSP id", csnp_tree, offset + 9,
270 &ilp->isis_csnp_start_lsp_id );
271 isis_lsp_decode_lsp_id( "End LSP id", csnp_tree, offset + 17,
272 &ilp->isis_csnp_start_lsp_id );
276 len = pntohs(&ilp->isis_csnp_pdu_length);
277 len -= header_length;
281 /* Call into payload dissector */
282 if (type == ISIS_TYPE_L1_CSNP ) {
283 isis_dissect_clvs ( clv_l1_csnp_opts, len, pd, offset, fd,
284 csnp_tree, ett_isis_csnp_clv_unknown );
286 isis_dissect_clvs ( clv_l2_csnp_opts, len, pd, offset, fd,
287 csnp_tree, ett_isis_csnp_clv_unknown );
292 * Name: isis_dissect_isis_psnp()
295 * Tear apart a L1 or L2 PSNP header and then call into payload dissect
296 * to pull apart the lsp id payload.
299 * u_char * : packet data
300 * int : offset into packet data where we are.
301 * guint : length of clv we are decoding
302 * frame_data * : frame data (complete frame)
303 * proto_tree * : protocol display tree to fill out. May be NULL
306 * void, but we will add to proto tree if !NULL.
309 isis_dissect_isis_psnp(int type, int header_length, const u_char *pd,
310 int offset, frame_data *fd, proto_tree *tree){
313 proto_tree *psnp_tree = NULL;
319 if (fd->cap_len < (offset + hlen)) {
320 isis_dissect_unknown(offset, hlen, tree, fd,
321 "not enough capture data for header (%d vs %d)",
322 hlen, offset - fd->cap_len);
326 ilp = (isis_psnp_t *) &pd[offset];
329 ti = proto_tree_add_item(tree, proto_isis_psnp,
330 offset, fd->cap_len - offset, NULL);
331 psnp_tree = proto_item_add_subtree(ti, ett_isis_psnp);
332 proto_tree_add_item(psnp_tree, hf_isis_psnp_pdu_length,
333 offset, 2, pntohs(&ilp->isis_psnp_pdu_length));
334 proto_tree_add_text(psnp_tree, offset + 2, 7,
335 "Source id: %02x%02x.%02x%02x.%02x%02x.%02x",
336 ilp->isis_psnp_source_id[0],
337 ilp->isis_psnp_source_id[1],
338 ilp->isis_psnp_source_id[2],
339 ilp->isis_psnp_source_id[3],
340 ilp->isis_psnp_source_id[4],
341 ilp->isis_psnp_source_id[5],
342 ilp->isis_psnp_source_id[6] );
346 len = pntohs(&ilp->isis_psnp_pdu_length);
347 len -= header_length;
349 isis_dissect_unknown(offset, header_length, tree, fd,
350 "packet header length %d went beyond packet",
354 /* Call into payload dissector */
355 if (type == ISIS_TYPE_L1_CSNP ) {
356 isis_dissect_clvs ( clv_l1_csnp_opts, len, pd, offset, fd,
357 psnp_tree, ett_isis_psnp_clv_unknown );
359 isis_dissect_clvs ( clv_l2_csnp_opts, len, pd, offset, fd,
360 psnp_tree, ett_isis_psnp_clv_unknown );
365 * Name: dissect_L1_snp_authentication_clv()
368 * Decode for a lsp packets authenticaion clv. Calls into the
369 * clv common one. An auth inside a L1 SNP is a per area password
372 * u_char * : packet data
373 * int : current offset into packet data
374 * guint : length of this clv
375 * frame_data * : frame data
376 * proto_tree * : proto tree to build on (may be null)
379 * void, will modify proto_tree if not null.
382 dissect_l1_snp_authentication_clv(const u_char *pd, int offset,
383 guint length, frame_data *fd, proto_tree *tree) {
384 isis_dissect_authentication_clv(pd, offset, length, fd, tree,
385 "Per area authentication" );
389 * Name: dissect_l2_authentication_clv()
392 * Decode for a lsp packets authenticaion clv. Calls into the
393 * clv common one. An auth inside a L2 LSP is a per domain password
396 * u_char * : packet data
397 * int : current offset into packet data
398 * guint : length of this clv
399 * frame_data * : frame data
400 * proto_tree * : proto tree to build on (may be null)
403 * void, will modify proto_tree if not null.
406 dissect_l2_snp_authentication_clv(const u_char *pd, int offset,
407 guint length, frame_data *fd, proto_tree *tree) {
408 isis_dissect_authentication_clv(pd, offset, length, fd, tree,
409 "Per domain authentication" );
413 * Name: proto_register_isis_csnp()
416 * Register our protocol sub-sets with protocol manager.
417 * NOTE: this procedure is autolinked by the makefile process that
421 * u_char * : packet data
422 * int : offset into packet data where we are.
423 * guint : length of clv we are decoding
424 * frame_data * : frame data (complete frame)
425 * proto_tree * : protocol display tree to fill out. May be NULL
428 * void, but we will add to proto tree if !NULL.
431 proto_register_isis_csnp(void) {
432 static hf_register_info hf[] = {
433 { &hf_isis_csnp_pdu_length,
434 { "PDU length", "isis_csnp.pdu_length", FT_UINT16,
435 BASE_DEC, NULL, 0x0, "" }},
437 static gint *ett[] = {
439 &ett_isis_csnp_lsp_entries,
440 &ett_isis_csnp_authentication,
441 &ett_isis_csnp_clv_unknown,
444 proto_isis_csnp = proto_register_protocol("ISIS csnp", "ISIS-csnp");
445 proto_register_field_array(proto_isis_csnp, hf, array_length(hf));
446 proto_register_subtree_array(ett, array_length(ett));
451 * Name: proto_register_isis_psnp()
454 * Register our protocol sub-sets with protocol manager.
455 * NOTE: this procedure is autolinked by the makefile process that
459 * u_char * : packet data
460 * int : offset into packet data where we are.
461 * guint : length of clv we are decoding
462 * frame_data * : frame data (complete frame)
463 * proto_tree * : protocol display tree to fill out. May be NULL
466 * void, but we will add to proto tree if !NULL.
469 proto_register_isis_psnp(void) {
470 static hf_register_info hf[] = {
471 { &hf_isis_psnp_pdu_length,
472 { "PDU length", "isis_psnp.pdu_length", FT_UINT16,
473 BASE_DEC, NULL, 0x0, "" }},
475 static gint *ett[] = {
477 &ett_isis_psnp_lsp_entries,
478 &ett_isis_psnp_authentication,
479 &ett_isis_psnp_clv_unknown,
482 proto_isis_psnp = proto_register_protocol("ISIS psnp", "ISIS-psnp");
483 proto_register_field_array(proto_isis_psnp, hf, array_length(hf));
484 proto_register_subtree_array(ett, array_length(ett));