2 * Routines for ANSI IS-683-A (OTA (Mobile)) dissection
4 * Copyright 2003, Michael Lum <mlum [AT] telostech.com>
5 * In association with Telos Technology Inc.
7 * $Id: packet-ansi_683.c,v 1.4 2003/12/08 23:40:12 guy Exp $
9 * Ethereal - Network traffic analyzer
10 * By Gerald Combs <gerald@ethereal.com>
11 * Copyright 1998 Gerald Combs
13 * This program is free software; you can redistribute it and/or
14 * modify it under the terms of the GNU General Public License
15 * as published by the Free Software Foundation; either version 2
16 * of the License, or (at your option) any later version.
18 * This program is distributed in the hope that it will be useful,
19 * but WITHOUT ANY WARRANTY; without even the implied warranty of
20 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
21 * GNU General Public License for more details.
23 * You should have received a copy of the GNU General Public License
24 * along with this program; if not, write to the Free Software
25 * Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
36 #ifdef HAVE_SYS_TYPES_H
37 # include <sys/types.h>
40 #ifdef HAVE_NETINET_IN_H
41 # include <netinet/in.h>
46 #include "epan/packet.h"
49 static char *ansi_proto_name = "ANSI IS-683-A (OTA (Mobile))";
50 static char *ansi_proto_name_short = "IS-683-A";
52 #define ANSI_683_FORWARD 0
53 #define ANSI_683_REVERSE 1
56 /* Initialize the subtree pointers */
57 static gint ett_ansi_683 = -1;
58 static gint ett_for_nam_block = -1;
59 static gint ett_for_sspr_block = -1;
60 static gint ett_rev_sspr_block = -1;
61 static gint ett_rev_nam_block = -1;
62 static gint ett_key_p = -1;
63 static gint ett_key_g = -1;
64 static gint ett_rev_feat = -1;
65 static gint ett_for_val_block = -1;
66 static gint ett_band_cap = -1;
68 /* Initialize the protocol and registered fields */
69 static int proto_ansi_683 = -1;
70 static int hf_ansi_683_none = -1;
71 static int hf_ansi_683_for_msg_type = -1;
72 static int hf_ansi_683_rev_msg_type = -1;
73 static int hf_ansi_683_length = -1;
75 static char bigbuf[1024];
76 static dissector_handle_t data_handle;
77 static packet_info *g_pinfo;
78 static proto_tree *g_tree;
84 my_match_strval(guint32 val, const value_string *vs, gint *idx)
90 if (vs[i].value == val)
104 /* PARAM FUNCTIONS */
106 #define EXTRANEOUS_DATA_CHECK(edc_len, edc_max_len) \
107 if ((edc_len) > (edc_max_len)) \
109 proto_tree_add_none_format(tree, hf_ansi_683_none, tvb, \
110 offset, (edc_len) - (edc_max_len), "Extraneous Data"); \
113 #define SHORT_DATA_CHECK(sdc_len, sdc_min_len) \
114 if ((sdc_len) < (sdc_min_len)) \
116 proto_tree_add_none_format(tree, hf_ansi_683_none, tvb, \
117 offset, (sdc_len), "Short Data (?)"); \
121 #define EXACT_DATA_CHECK(edc_len, edc_eq_len) \
122 if ((edc_len) != (edc_eq_len)) \
124 proto_tree_add_none_format(tree, hf_ansi_683_none, tvb, \
125 offset, (edc_len), "Unexpected Data Length"); \
130 rev_feat_id_type(guint8 feat_id)
136 case 0: str = "NAM Download (DATA_P_REV)"; break;
137 case 1: str = "Key Exchange (A_KEY_P_REV)"; break;
138 case 2: str = "System Selection for Preferred Roaming (SSPR_P_REV)"; break;
139 case 3: str = "Service Programming Lock (SPL_P_REV)"; break;
140 case 4: str = "Over-The-Air Parameter Administration (OTAPA_P_REV)"; break;
142 if ((feat_id >= 5) && (feat_id <= 191)) { str = "Reserved for future standardization"; break; }
143 else if ((feat_id >= 192) && (feat_id <= 254)) { str = "Available for manufacturer-specific features"; break; }
144 else { str = "Reserved"; break; }
151 rev_res_code_type(guint8 res_code)
157 case 0: str = "Accepted - Operation successful"; break;
158 case 1: str = "Rejected - Unknown reason"; break;
159 case 2: str = "Rejected - Data size mismatch"; break;
160 case 3: str = "Rejected - Protocol version mismatch"; break;
161 case 4: str = "Rejected - Invalid parameter"; break;
162 case 5: str = "Rejected - SID/NID length mismatch"; break;
163 case 6: str = "Rejected - Message not expected in this mode"; break;
164 case 7: str = "Rejected - BLOCK_ID value not supported"; break;
165 case 8: str = "Rejected - Preferred roaming list length mismatch"; break;
166 case 9: str = "Rejected - CRC error"; break;
167 case 10: str = "Rejected - Mobile station locked"; break;
168 case 11: str = "Rejected - Invalid SPC"; break;
169 case 12: str = "Rejected - SPC change denied by the user"; break;
170 case 13: str = "Rejected - Invalid SPASM"; break;
171 case 14: str = "Rejected - BLOCK_ID not expected in this mode"; break;
173 if ((res_code >= 15) && (res_code <= 127)) { str = "Reserved for future standardization"; break; }
174 else if ((res_code >= 128) && (res_code <= 254)) { str = "Available for manufacturer-specific Result Code definitions"; break; }
175 else { str = "Reserved"; break; }
181 #define VERIFY_SPC_VAL_BLOCK 0
182 #define CHANGE_SPC_VAL_BLOCK 1
183 #define VALDATE_SPASM_VAL_BLOCK 2
186 for_val_param_block_type(guint8 block_type)
192 case 0: str = "Verify SPC"; break;
193 case 1: str = "Change SPC"; break;
194 case 2: str = "Validate SPASM"; break;
196 if ((block_type >= 3) && (block_type <= 127)) { str = "Reserved for future standardization"; break; }
197 else if ((block_type >= 128) && (block_type <= 254)) { str = "Available for manufacturer-specific parameter block definitions"; break; }
198 else { str = "Reserved"; break; }
205 rev_sspr_param_block_type(guint8 block_type)
211 case 0: str = "Preferred Roaming List Dimensions"; break;
212 case 1: str = "Preferred Roaming List"; break;
214 if ((block_type >= 2) && (block_type <= 127)) { str = "Reserved for future standardization"; break; }
215 else if ((block_type >= 128) && (block_type <= 254)) { str = "Available for manufacturer-specific parameter block definitions"; break; }
216 else { str = "Reserved"; break; }
223 for_sspr_param_block_type(guint8 block_type)
229 case 0: str = "Preferred Roaming List"; break;
231 if ((block_type >= 1) && (block_type <= 127)) { str = "Reserved for future standardization"; break; }
232 else if ((block_type >= 128) && (block_type <= 254)) { str = "Available for manufacturer-specific parameter block definitions"; break; }
233 else { str = "Reserved"; break; }
239 #define CDMA_ANALOG_NAM_BLOCK 0
240 #define MDN_NAM_BLOCK 1
241 #define CDMA_NAM_BLOCK 2
242 #define IMSI_T_NAM_BLOCK 3
245 rev_nam_param_block_type(guint8 block_type)
251 case 0: str = "CDMA/Analog NAM"; break;
252 case 1: str = "Mobile Directory Number"; break;
253 case 2: str = "CDMA NAM"; break;
254 case 3: str = "IMSI_T"; break;
256 if ((block_type >= 4) && (block_type <= 127)) { str = "Reserved for future standardization"; break; }
257 else if ((block_type >= 128) && (block_type <= 254)) { str = "Available for manufacturer-specific parameter block definitions"; break; }
258 else { str = "Reserved"; break; }
265 for_nam_param_block_type(guint8 block_type)
271 case 0: str = "CDMA/Analog NAM Download"; break;
272 case 1: str = "Mobile Directory Number"; break;
273 case 2: str = "CDMA NAM Download"; break;
274 case 3: str = "IMSI_T"; break;
276 if ((block_type >= 4) && (block_type <= 127)) { str = "Reserved for future standardization"; break; }
277 else if ((block_type >= 128) && (block_type <= 254)) { str = "Available for manufacturer-specific parameter block definitions"; break; }
278 else { str = "Reserved"; break; }
285 param_verify_spc_val_block(tvbuff_t *tvb, proto_tree *tree, guint len, guint32 offset)
287 guint32 saved_offset;
291 EXACT_DATA_CHECK(len, 3);
293 saved_offset = offset;
295 value = tvb_get_ntoh24(tvb, offset);
297 proto_tree_add_none_format(tree, hf_ansi_683_none,
299 "Service programming code (%d)",
304 param_cdma_analog_nam_block(tvbuff_t *tvb, proto_tree *tree, guint len, guint32 offset)
306 guint32 saved_offset;
310 saved_offset = offset;
312 value = tvb_get_ntohs(tvb, offset);
314 other_decode_bitfield_value(bigbuf, value, 0xffe0, 16);
315 proto_tree_add_none_format(tree, hf_ansi_683_none,
317 "%s : First paging channel (FIRSTCHP) used in the home system (%d)",
319 (value & 0xffe0) >> 5);
323 value = tvb_get_ntoh24(tvb, offset);
325 other_decode_bitfield_value(bigbuf, value, 0x1fffc0, 24);
326 proto_tree_add_none_format(tree, hf_ansi_683_none,
328 "%s : Home system identification (HOME_SID) (%d)",
330 (value & 0x1fffc0) >> 6);
332 other_decode_bitfield_value(bigbuf, value, 0x20, 8);
333 proto_tree_add_none_format(tree, hf_ansi_683_none,
335 "%s : Extended address indicator (EX)",
340 value = tvb_get_ntohs(tvb, offset);
342 other_decode_bitfield_value(bigbuf, value, 0x1fe0, 16);
343 proto_tree_add_none_format(tree, hf_ansi_683_none,
345 "%s : Station class mark (SCM) (%d)",
347 (value & 0x1fe0) >> 5);
351 value = tvb_get_ntohs(tvb, offset);
353 other_decode_bitfield_value(bigbuf, value, 0x1fe0, 16);
354 proto_tree_add_none_format(tree, hf_ansi_683_none,
356 "%s : Mobile station protocol revision number (MOB_P_REV) (%d)",
358 (value & 0x1fe0) >> 5);
360 other_decode_bitfield_value(bigbuf, value, 0x10, 8);
361 proto_tree_add_none_format(tree, hf_ansi_683_none,
363 "%s : IMSI_M Class assignment of the mobile station (IMSI_M_CLASS), Class %d",
365 (value & 0x10) >> 4);
367 other_decode_bitfield_value(bigbuf, value, 0x0e, 8);
368 proto_tree_add_none_format(tree, hf_ansi_683_none,
370 "%s : Number of IMSI_M address digits (IMSI_M_ADDR_NUM) (%d), %d digits in NMSI",
373 (value & 0x10) ? ((value & 0x0e) >> 1) + 4 : 0);
377 value = tvb_get_ntoh24(tvb, offset);
379 other_decode_bitfield_value(bigbuf, value, 0x01ff80, 24);
380 proto_tree_add_none_format(tree, hf_ansi_683_none,
382 "%s : Mobile country code (MCC_M)",
385 other_decode_bitfield_value(bigbuf, value, 0x7f, 8);
386 proto_tree_add_none_format(tree, hf_ansi_683_none,
388 "%s : 11th and 12th digits of the IMSI_M (IMSI__M_11_12)",
393 proto_tree_add_none_format(tree, hf_ansi_683_none,
395 "The least significant 10 digits of the IMSI_M (IMSI_M_S) (34 bits)");
399 value = tvb_get_guint8(tvb, offset);
401 other_decode_bitfield_value(bigbuf, value, 0x3c, 8);
402 proto_tree_add_none_format(tree, hf_ansi_683_none,
404 "%s : Access overload class (ACCOLC) (%d)",
406 (value & 0x3c) >> 2);
408 other_decode_bitfield_value(bigbuf, value, 0x02, 8);
409 proto_tree_add_none_format(tree, hf_ansi_683_none,
411 "%s : Local control status (LOCAL_CONTROL)",
414 other_decode_bitfield_value(bigbuf, value, 0x01, 8);
415 proto_tree_add_none_format(tree, hf_ansi_683_none,
417 "%s : Termination indicator for the home system (MOB_TERM_HOME)",
422 value = tvb_get_guint8(tvb, offset);
424 other_decode_bitfield_value(bigbuf, value, 0x80, 8);
425 proto_tree_add_none_format(tree, hf_ansi_683_none,
427 "%s : Termination indicator for SID roaming (MOB_TERM_FOR_SID)",
430 other_decode_bitfield_value(bigbuf, value, 0x40, 8);
431 proto_tree_add_none_format(tree, hf_ansi_683_none,
433 "%s : Termination indicator for NID roaming (MOB_TERM_FOR_NID)",
436 value = tvb_get_ntohs(tvb, offset);
438 other_decode_bitfield_value(bigbuf, value, 0x3fc0, 16);
439 proto_tree_add_none_format(tree, hf_ansi_683_none,
441 "%s : Maximum stored SID/NID pairs (MAX_SID_NID) (%d)",
443 (value & 0x3fc0) >> 6);
447 value = tvb_get_ntohs(tvb, offset);
449 count = (value & 0x3fc0) >> 6;
451 other_decode_bitfield_value(bigbuf, value, 0x3fc0, 16);
452 proto_tree_add_none_format(tree, hf_ansi_683_none,
454 "%s : Number of stored SID/NID pairs (STORED_SID_NID) (%d)",
458 other_decode_bitfield_value(bigbuf, value, 0x003f, 16);
459 proto_tree_add_none_format(tree, hf_ansi_683_none,
461 "%s : SID/NID pairs (MSB)",
466 proto_tree_add_none_format(tree, hf_ansi_683_none,
467 tvb, offset, len - (offset - saved_offset),
468 "SID/NID pairs, Reserved");
472 param_mdn_nam_block(tvbuff_t *tvb, proto_tree *tree, guint len, guint32 offset)
474 guint32 saved_offset;
475 guint32 value, count, i;
477 memset((void *) bigbuf, 0, sizeof(bigbuf));
479 saved_offset = offset;
481 value = tvb_get_guint8(tvb, offset);
483 count = (value & 0xf0) >> 4;
485 other_decode_bitfield_value(bigbuf, value, 0xf0, 8);
486 proto_tree_add_none_format(tree, hf_ansi_683_none,
488 "%s : Number of digits (N_DIGITS) (%d)",
492 for (i=0; i < count; i++)
494 bigbuf[i] = 0x30 + (value & 0x0f);
499 value = tvb_get_guint8(tvb, offset);
500 bigbuf[i+1] = 0x30 + (value & 0xf0);
505 proto_tree_add_none_format(tree, hf_ansi_683_none,
506 tvb, saved_offset, len,
507 "Mobile directory number, %s",
512 other_decode_bitfield_value(bigbuf, value, 0x0f, 8);
513 proto_tree_add_none_format(tree, hf_ansi_683_none,
521 param_cdma_nam_block(tvbuff_t *tvb, proto_tree *tree, guint len, guint32 offset)
523 guint32 saved_offset;
527 saved_offset = offset;
529 value = tvb_get_guint8(tvb, offset);
531 other_decode_bitfield_value(bigbuf, value, 0xc0, 8);
532 proto_tree_add_none_format(tree, hf_ansi_683_none,
537 other_decode_bitfield_value(bigbuf, value, 0x20, 8);
538 proto_tree_add_none_format(tree, hf_ansi_683_none,
543 other_decode_bitfield_value(bigbuf, value, 0x1f, 8);
544 proto_tree_add_none_format(tree, hf_ansi_683_none,
551 value = tvb_get_guint8(tvb, offset);
553 other_decode_bitfield_value(bigbuf, value, 0xff, 8);
554 proto_tree_add_none_format(tree, hf_ansi_683_none,
556 "%s : Mobile station protocol revision number (MOB_P_REV) (%d)",
562 value = tvb_get_ntohs(tvb, offset);
564 other_decode_bitfield_value(bigbuf, value, 0x8000, 16);
565 proto_tree_add_none_format(tree, hf_ansi_683_none,
567 "%s : IMSI_M Class assignment of the mobile station (IMSI_M_CLASS), Class %d",
569 (value & 0x8000) >> 15);
571 other_decode_bitfield_value(bigbuf, value, 0x7000, 16);
572 proto_tree_add_none_format(tree, hf_ansi_683_none,
574 "%s : Number of IMSI_M address digits (IMSI_M_ADDR_NUM) (%d), %d digits in NMSI",
576 (value & 0x7000) >> 12,
577 (value & 0x8000) ? ((value & 0x7000) >> 12) + 4 : 0);
579 other_decode_bitfield_value(bigbuf, value, 0x0ffc, 16);
580 proto_tree_add_none_format(tree, hf_ansi_683_none,
582 "%s : Mobile country code (MCC_M)",
587 value = tvb_get_ntohs(tvb, offset);
589 other_decode_bitfield_value(bigbuf, value, 0x3f80, 16);
590 proto_tree_add_none_format(tree, hf_ansi_683_none,
592 "%s : 11th and 12th digits of the IMSI_M (IMSI__M_11_12)",
597 proto_tree_add_none_format(tree, hf_ansi_683_none,
599 "The least significant 10 digits of the IMSI_M (IMSI_M_S) (34 bits)");
603 value = tvb_get_ntohs(tvb, offset);
605 other_decode_bitfield_value(bigbuf, value, 0x01e0, 16);
606 proto_tree_add_none_format(tree, hf_ansi_683_none,
608 "%s : Access overload class (ACCOLC) (%d)",
610 (value & 0x01e0) >> 5);
612 other_decode_bitfield_value(bigbuf, value, 0x10, 8);
613 proto_tree_add_none_format(tree, hf_ansi_683_none,
615 "%s : Local control status (LOCAL_CONTROL)",
618 other_decode_bitfield_value(bigbuf, value, 0x08, 8);
619 proto_tree_add_none_format(tree, hf_ansi_683_none,
621 "%s : Termination indicator for the home system (MOB_TERM_HOME)",
624 other_decode_bitfield_value(bigbuf, value, 0x04, 8);
625 proto_tree_add_none_format(tree, hf_ansi_683_none,
627 "%s : Termination indicator for SID roaming (MOB_TERM_FOR_SID)",
630 other_decode_bitfield_value(bigbuf, value, 0x02, 8);
631 proto_tree_add_none_format(tree, hf_ansi_683_none,
633 "%s : Termination indicator for NID roaming (MOB_TERM_FOR_NID)",
638 value = tvb_get_ntohs(tvb, offset);
640 other_decode_bitfield_value(bigbuf, value, 0x01fe, 16);
641 proto_tree_add_none_format(tree, hf_ansi_683_none,
643 "%s : Maximum stored SID/NID pairs (MAX_SID_NID) (%d)",
645 (value & 0x01fe) >> 1);
649 value = tvb_get_ntohs(tvb, offset);
651 count = (value & 0x01fe) >> 1;
653 other_decode_bitfield_value(bigbuf, value, 0x01fe, 16);
654 proto_tree_add_none_format(tree, hf_ansi_683_none,
656 "%s : Number of stored SID/NID pairs (STORED_SID_NID) (%d)",
660 other_decode_bitfield_value(bigbuf, value, 0x01, 8);
661 proto_tree_add_none_format(tree, hf_ansi_683_none,
663 "%s : SID/NID pairs (MSB)",
668 proto_tree_add_none_format(tree, hf_ansi_683_none,
669 tvb, offset, len - (offset - saved_offset),
670 "SID/NID pairs, Reserved");
674 param_imsi_t_nam_block(tvbuff_t *tvb, proto_tree *tree, guint len, guint32 offset)
676 guint32 saved_offset;
680 * XXX avoid warning for now, may use this variable
681 * for validation later
685 saved_offset = offset;
687 value = tvb_get_guint8(tvb, offset);
689 other_decode_bitfield_value(bigbuf, value, 0x80, 8);
690 proto_tree_add_none_format(tree, hf_ansi_683_none,
692 "%s : IMSI_T Class assignment of the mobile station (IMSI_T_CLASS), Class %d",
694 (value & 0x80) >> 7);
696 other_decode_bitfield_value(bigbuf, value, 0x70, 8);
697 proto_tree_add_none_format(tree, hf_ansi_683_none,
699 "%s : Number of IMSI_T address digits (IMSI_T_ADDR_NUM ) (%d), %d digits in NMSI",
702 (value & 0x80) ? ((value & 0x70) >> 4) + 4 : 0);
704 value = tvb_get_ntohs(tvb, offset);
706 other_decode_bitfield_value(bigbuf, value, 0x0ffc, 16);
707 proto_tree_add_none_format(tree, hf_ansi_683_none,
709 "%s : Mobile country code (MCC_T)",
714 value = tvb_get_ntohs(tvb, offset);
716 other_decode_bitfield_value(bigbuf, value, 0x03f8, 16);
717 proto_tree_add_none_format(tree, hf_ansi_683_none,
719 "%s : 11th and 12th digits of the IMSI_T (IMSI__T_11_12)",
724 proto_tree_add_none_format(tree, hf_ansi_683_none,
726 "The least significant 10 digits of the IMSI_T (IMSI_T_S) (34 bits)");
730 value = tvb_get_guint8(tvb, offset);
732 other_decode_bitfield_value(bigbuf, value, 0x01, 8);
733 proto_tree_add_none_format(tree, hf_ansi_683_none,
740 msg_config_req(tvbuff_t *tvb, proto_tree *tree, guint len, guint32 offset)
742 guint8 oct, num_blocks;
744 guint32 i, saved_offset;
746 SHORT_DATA_CHECK(len, 1);
748 saved_offset = offset;
750 num_blocks = tvb_get_guint8(tvb, offset);
752 proto_tree_add_none_format(tree, hf_ansi_683_none,
754 "Number of parameter blocks (%d)",
759 if (num_blocks > (len - (offset - saved_offset)))
761 proto_tree_add_none_format(tree, hf_ansi_683_none, tvb,
762 offset, len - (offset - saved_offset), "Short Data (?)");
766 for (i=0; i < num_blocks; i++)
768 oct = tvb_get_guint8(tvb, offset);
770 str = rev_nam_param_block_type(oct);
772 proto_tree_add_none_format(tree, hf_ansi_683_none,
781 EXTRANEOUS_DATA_CHECK(len, offset - saved_offset);
785 msg_download_req(tvbuff_t *tvb, proto_tree *tree, guint len, guint32 offset)
787 guint8 oct, block_id, block_len;
791 guint32 i, saved_offset;
793 SHORT_DATA_CHECK(len, 1);
795 saved_offset = offset;
797 oct = tvb_get_guint8(tvb, offset);
799 proto_tree_add_none_format(tree, hf_ansi_683_none,
801 "Number of parameter blocks (%d)",
806 for (i=0; i < oct; i++)
808 block_id = tvb_get_guint8(tvb, offset);
810 str = for_nam_param_block_type(block_id);
813 proto_tree_add_none_format(tree, hf_ansi_683_none,
819 subtree = proto_item_add_subtree(item, ett_for_nam_block);
822 block_len = tvb_get_guint8(tvb, offset);
824 proto_tree_add_uint(subtree, hf_ansi_683_length,
825 tvb, offset, 1, block_len);
828 if (block_len > (len - (offset - saved_offset)))
830 proto_tree_add_none_format(subtree, hf_ansi_683_none, tvb,
831 offset, len - (offset - saved_offset), "Short Data (?)");
839 case CDMA_ANALOG_NAM_BLOCK:
840 param_cdma_analog_nam_block(tvb, subtree, block_len, offset);
844 param_mdn_nam_block(tvb, subtree, block_len, offset);
848 param_cdma_nam_block(tvb, subtree, block_len, offset);
851 case IMSI_T_NAM_BLOCK:
852 param_imsi_t_nam_block(tvb, subtree, block_len, offset);
856 proto_tree_add_none_format(subtree, hf_ansi_683_none,
857 tvb, offset, block_len, "Block Data");
865 EXTRANEOUS_DATA_CHECK(len, offset - saved_offset);
869 msg_ms_key_req(tvbuff_t *tvb, proto_tree *tree, guint len, guint32 offset)
871 guint8 oct, param_len;
874 guint32 saved_offset;
876 SHORT_DATA_CHECK(len, 3);
878 saved_offset = offset;
880 oct = tvb_get_guint8(tvb, offset);
882 proto_tree_add_none_format(tree, hf_ansi_683_none,
884 "A-Key Protocol Revision (%d)",
888 param_len = tvb_get_guint8(tvb, offset);
891 proto_tree_add_none_format(tree, hf_ansi_683_none,
892 tvb, offset, param_len + 1,
893 "Key exchange parameter P");
894 subtree = proto_item_add_subtree(item, ett_key_p);
896 proto_tree_add_uint(subtree, hf_ansi_683_length,
897 tvb, offset, 1, param_len);
902 proto_tree_add_none_format(subtree, hf_ansi_683_none,
903 tvb, offset, param_len,
908 param_len = tvb_get_guint8(tvb, offset);
911 proto_tree_add_none_format(tree, hf_ansi_683_none,
912 tvb, offset, param_len + 1,
913 "Key exchange parameter G");
914 subtree = proto_item_add_subtree(item, ett_key_g);
916 proto_tree_add_uint(subtree, hf_ansi_683_length,
917 tvb, offset, 1, param_len);
922 proto_tree_add_none_format(subtree, hf_ansi_683_none,
923 tvb, offset, param_len,
928 EXTRANEOUS_DATA_CHECK(len, offset - saved_offset);
932 msg_key_gen_req(tvbuff_t *tvb, proto_tree *tree, guint len, guint32 offset)
935 guint32 saved_offset;
937 SHORT_DATA_CHECK(len, 2);
939 saved_offset = offset;
941 param_len = tvb_get_guint8(tvb, offset);
943 proto_tree_add_uint(tree, hf_ansi_683_length,
944 tvb, offset, 1, param_len);
947 if (param_len > (len - (offset - saved_offset)))
949 proto_tree_add_none_format(tree, hf_ansi_683_none, tvb,
950 offset, len - (offset - saved_offset), "Short Data (?)");
956 proto_tree_add_none_format(tree, hf_ansi_683_none,
957 tvb, offset, param_len,
958 "Calculation Result");
962 EXTRANEOUS_DATA_CHECK(len, offset - saved_offset);
966 msg_reauth_req(tvbuff_t *tvb, proto_tree *tree, guint len, guint32 offset)
969 EXACT_DATA_CHECK(len, 4);
971 proto_tree_add_none_format(tree, hf_ansi_683_none,
973 "Random Challenge value");
977 msg_sspr_config_req(tvbuff_t *tvb, proto_tree *tree, guint len, guint32 offset)
981 guint32 saved_offset;
986 SHORT_DATA_CHECK(len, 1);
988 saved_offset = offset;
990 oct = tvb_get_guint8(tvb, offset);
992 str = rev_sspr_param_block_type(oct);
995 proto_tree_add_none_format(tree, hf_ansi_683_none,
1005 subtree = proto_item_add_subtree(item, ett_rev_sspr_block);
1007 if ((len - (offset - saved_offset)) < 3)
1009 proto_tree_add_none_format(subtree, hf_ansi_683_none, tvb,
1010 offset, len - (offset - saved_offset), "Short Data (?)");
1014 value = tvb_get_ntohs(tvb, offset);
1016 proto_tree_add_none_format(subtree, hf_ansi_683_none,
1018 "Segment offset (%d)",
1022 oct = tvb_get_guint8(tvb, offset);
1024 proto_tree_add_none_format(subtree, hf_ansi_683_none,
1026 "Maximum segment size (%d)",
1031 EXTRANEOUS_DATA_CHECK(len, offset - saved_offset);
1035 msg_sspr_download_req(tvbuff_t *tvb, proto_tree *tree, guint len, guint32 offset)
1037 guint8 oct, block_len;
1039 guint32 saved_offset;
1040 proto_tree *subtree;
1043 SHORT_DATA_CHECK(len, 2);
1045 saved_offset = offset;
1047 oct = tvb_get_guint8(tvb, offset);
1049 str = for_sspr_param_block_type(oct);
1052 proto_tree_add_none_format(tree, hf_ansi_683_none,
1058 subtree = proto_item_add_subtree(item, ett_for_sspr_block);
1061 block_len = tvb_get_guint8(tvb, offset);
1063 proto_tree_add_uint(subtree, hf_ansi_683_length,
1064 tvb, offset, 1, block_len);
1067 if (block_len > (len - (offset - saved_offset)))
1069 proto_tree_add_none_format(subtree, hf_ansi_683_none, tvb,
1070 offset, len - (offset - saved_offset), "Short Data (?)");
1076 proto_tree_add_none_format(subtree, hf_ansi_683_none,
1077 tvb, offset, block_len, "Block Data");
1078 offset += block_len;
1081 EXTRANEOUS_DATA_CHECK(len, offset - saved_offset);
1085 msg_validate_req(tvbuff_t *tvb, proto_tree *tree, guint len, guint32 offset)
1087 guint8 oct, block_id, block_len;
1089 proto_tree *subtree;
1091 guint32 i, saved_offset, block_offset;
1093 SHORT_DATA_CHECK(len, 1);
1095 saved_offset = offset;
1097 oct = tvb_get_guint8(tvb, offset);
1099 proto_tree_add_none_format(tree, hf_ansi_683_none,
1101 "Number of parameter blocks (%d)",
1106 if ((guint32)(oct * 2) > (len - (offset - saved_offset)))
1108 proto_tree_add_none_format(tree, hf_ansi_683_none, tvb,
1109 offset, len - (offset - saved_offset), "Short Data (?)");
1113 for (i=0; i < oct; i++)
1115 block_offset = offset;
1116 block_id = tvb_get_guint8(tvb, offset);
1118 str = for_val_param_block_type(block_id);
1121 proto_tree_add_none_format(tree, hf_ansi_683_none,
1125 subtree = proto_item_add_subtree(item, ett_for_val_block);
1127 proto_tree_add_none_format(subtree, hf_ansi_683_none,
1134 block_len = tvb_get_guint8(tvb, offset);
1136 proto_tree_add_uint(subtree, hf_ansi_683_length,
1137 tvb, offset, 1, block_len);
1141 proto_item_set_len(item, (offset - block_offset) + block_len);
1143 if (block_len > (len - (offset - saved_offset)))
1145 proto_tree_add_none_format(subtree, hf_ansi_683_none, tvb,
1146 offset, len - (offset - saved_offset), "Short Data (?)");
1154 case VERIFY_SPC_VAL_BLOCK:
1155 param_verify_spc_val_block(tvb, subtree, block_len, offset);
1158 case CHANGE_SPC_VAL_BLOCK:
1159 case VALDATE_SPASM_VAL_BLOCK:
1161 proto_tree_add_none_format(subtree, hf_ansi_683_none,
1162 tvb, offset, block_len, "Block Data");
1166 offset += block_len;
1170 EXTRANEOUS_DATA_CHECK(len, offset - saved_offset);
1174 msg_otapa_req(tvbuff_t *tvb, proto_tree *tree, guint len, guint32 offset)
1177 guint32 saved_offset;
1179 EXACT_DATA_CHECK(len, 1);
1181 saved_offset = offset;
1183 oct = tvb_get_guint8(tvb, offset);
1185 other_decode_bitfield_value(bigbuf, oct, 0x80, 8);
1186 proto_tree_add_none_format(tree, hf_ansi_683_none,
1188 "%s : %s OTAPA session",
1190 (oct & 0x80) ? "Start" : "Stop");
1192 other_decode_bitfield_value(bigbuf, oct, 0x7f, 8);
1193 proto_tree_add_none_format(tree, hf_ansi_683_none,
1202 msg_config_rsp(tvbuff_t *tvb, proto_tree *tree, guint len, guint32 offset)
1204 guint8 oct, num_blocks, block_len;
1206 guint32 i, saved_offset;
1207 proto_tree *subtree;
1210 SHORT_DATA_CHECK(len, 1);
1212 saved_offset = offset;
1214 num_blocks = tvb_get_guint8(tvb, offset);
1216 proto_tree_add_none_format(tree, hf_ansi_683_none,
1218 "Number of parameter blocks (%d)",
1223 if ((guint32)(num_blocks * 2) > (len - (offset - saved_offset)))
1225 proto_tree_add_none_format(tree, hf_ansi_683_none, tvb,
1226 offset, len - (offset - saved_offset), "Short Data (?)");
1230 for (i=0; i < num_blocks; i++)
1232 oct = tvb_get_guint8(tvb, offset);
1234 str = rev_nam_param_block_type(oct);
1237 proto_tree_add_none_format(tree, hf_ansi_683_none,
1243 subtree = proto_item_add_subtree(item, ett_rev_nam_block);
1246 block_len = tvb_get_guint8(tvb, offset);
1248 proto_tree_add_uint(subtree, hf_ansi_683_length,
1249 tvb, offset, 1, block_len);
1252 if (block_len > (len - (offset - saved_offset)))
1254 proto_tree_add_none_format(subtree, hf_ansi_683_none, tvb,
1255 offset, len - (offset - saved_offset), "Short Data (?)");
1261 proto_tree_add_none_format(subtree, hf_ansi_683_none,
1262 tvb, offset, block_len, "Block Data");
1263 offset += block_len;
1267 if (num_blocks > (len - (offset - saved_offset)))
1269 proto_tree_add_none_format(tree, hf_ansi_683_none, tvb,
1270 offset, len - (offset - saved_offset), "Short Data (?)");
1274 for (i=0; i < num_blocks; i++)
1276 oct = tvb_get_guint8(tvb, offset);
1278 str = rev_res_code_type(oct);
1280 proto_tree_add_none_format(tree, hf_ansi_683_none,
1289 EXTRANEOUS_DATA_CHECK(len, offset - saved_offset);
1293 msg_download_rsp(tvbuff_t *tvb, proto_tree *tree, guint len, guint32 offset)
1295 guint8 oct, num_blocks;
1297 guint32 i, saved_offset;
1298 proto_tree *subtree;
1301 SHORT_DATA_CHECK(len, 1);
1303 saved_offset = offset;
1305 num_blocks = tvb_get_guint8(tvb, offset);
1307 proto_tree_add_none_format(tree, hf_ansi_683_none,
1309 "Number of parameter blocks (%d)",
1314 if ((guint32)(num_blocks * 2) > (len - (offset - saved_offset)))
1316 proto_tree_add_none_format(tree, hf_ansi_683_none, tvb,
1317 offset, len - (offset - saved_offset), "Short Data (?)");
1321 for (i=0; i < num_blocks; i++)
1323 oct = tvb_get_guint8(tvb, offset);
1325 str = for_nam_param_block_type(oct);
1328 proto_tree_add_none_format(tree, hf_ansi_683_none,
1334 subtree = proto_item_add_subtree(item, ett_for_nam_block);
1337 oct = tvb_get_guint8(tvb, offset);
1339 str = rev_res_code_type(oct);
1341 proto_tree_add_none_format(subtree, hf_ansi_683_none,
1350 EXTRANEOUS_DATA_CHECK(len, offset - saved_offset);
1354 msg_ms_key_rsp(tvbuff_t *tvb, proto_tree *tree, guint len, guint32 offset)
1358 guint32 saved_offset;
1360 EXACT_DATA_CHECK(len, 1);
1362 saved_offset = offset;
1364 oct = tvb_get_guint8(tvb, offset);
1366 str = rev_res_code_type(oct);
1368 proto_tree_add_none_format(tree, hf_ansi_683_none,
1370 "Key exchange result code, %s (%d)",
1378 msg_key_gen_rsp(tvbuff_t *tvb, proto_tree *tree, guint len, guint32 offset)
1380 guint8 oct, result_len;
1382 guint32 saved_offset;
1384 SHORT_DATA_CHECK(len, 2);
1386 saved_offset = offset;
1388 oct = tvb_get_guint8(tvb, offset);
1390 str = rev_res_code_type(oct);
1392 proto_tree_add_none_format(tree, hf_ansi_683_none,
1394 "Key exchange result code, %s (%d)",
1400 result_len = tvb_get_guint8(tvb, offset);
1402 proto_tree_add_uint(tree, hf_ansi_683_length,
1403 tvb, offset, 1, result_len);
1406 if (result_len > (len - (offset - saved_offset)))
1408 proto_tree_add_none_format(tree, hf_ansi_683_none, tvb,
1409 offset, len - (offset - saved_offset), "Short Data (?)");
1415 proto_tree_add_none_format(tree, hf_ansi_683_none,
1416 tvb, offset, result_len, "Calculation Result");
1417 offset += result_len;
1420 EXTRANEOUS_DATA_CHECK(len, offset - saved_offset);
1424 msg_reauth_rsp(tvbuff_t *tvb, proto_tree *tree, guint len, guint32 offset)
1426 guint32 saved_offset;
1429 EXACT_DATA_CHECK(len, 7);
1431 saved_offset = offset;
1433 value = tvb_get_ntoh24(tvb, offset);
1435 other_decode_bitfield_value(bigbuf, value, 0xffffc0, 24);
1436 proto_tree_add_none_format(tree, hf_ansi_683_none,
1438 "%s : Authentication signature data (AUTHR) (%d)",
1440 (value & 0xffffc0) >> 6);
1444 value = tvb_get_ntohs(tvb, offset);
1446 other_decode_bitfield_value(bigbuf, value, 0x3fc0, 16);
1447 proto_tree_add_none_format(tree, hf_ansi_683_none,
1449 "%s : Random challenge value (RANDC) (%d)",
1451 (value & 0x3fc0) >> 6);
1453 other_decode_bitfield_value(bigbuf, value, 0x3f, 8);
1454 proto_tree_add_none_format(tree, hf_ansi_683_none,
1456 "%s : Call history parameter (COUNT) (%d)",
1462 value = tvb_get_ntoh24(tvb, offset);
1464 other_decode_bitfield_value(bigbuf, value, 0xffffff, 24);
1465 proto_tree_add_none_format(tree, hf_ansi_683_none,
1467 "%s : Authentication Data input parameter (AUTH_DATA) (%d)",
1473 msg_commit_rsp(tvbuff_t *tvb, proto_tree *tree, guint len, guint32 offset)
1477 guint32 saved_offset;
1479 EXACT_DATA_CHECK(len, 1);
1481 saved_offset = offset;
1483 oct = tvb_get_guint8(tvb, offset);
1485 str = rev_res_code_type(oct);
1487 proto_tree_add_none_format(tree, hf_ansi_683_none,
1489 "Data commit result code, %s (%d)",
1497 msg_protocap_rsp(tvbuff_t *tvb, proto_tree *tree, guint len, guint32 offset)
1499 guint8 oct, num_feat, add_len;
1501 guint32 i, saved_offset;
1503 proto_tree *subtree;
1506 SHORT_DATA_CHECK(len, 5);
1508 saved_offset = offset;
1510 value = tvb_get_ntohs(tvb, offset);
1512 proto_tree_add_none_format(tree, hf_ansi_683_none,
1514 "Mobile station firmware revision number (%d)",
1519 oct = tvb_get_guint8(tvb, offset);
1521 proto_tree_add_none_format(tree, hf_ansi_683_none,
1523 "Mobile station manufacturer
\92s model number (%d)",
1528 num_feat = tvb_get_guint8(tvb, offset);
1530 proto_tree_add_none_format(tree, hf_ansi_683_none,
1532 "Number of features (%d)",
1537 if ((guint32)(num_feat * 2) > (len - (offset - saved_offset)))
1539 proto_tree_add_none_format(tree, hf_ansi_683_none, tvb,
1540 offset, len - (offset - saved_offset), "Short Data (?)");
1544 for (i=0; i < num_feat; i++)
1546 oct = tvb_get_guint8(tvb, offset);
1548 str = rev_feat_id_type(oct);
1551 proto_tree_add_none_format(tree, hf_ansi_683_none,
1553 "Feature ID, %s (%d)",
1557 subtree = proto_item_add_subtree(item, ett_rev_feat);
1560 oct = tvb_get_guint8(tvb, offset);
1562 proto_tree_add_none_format(subtree, hf_ansi_683_none,
1564 "Feature protocol version (%d)",
1570 add_len = tvb_get_guint8(tvb, offset);
1572 proto_tree_add_uint(tree, hf_ansi_683_length,
1573 tvb, offset, 1, add_len);
1576 if (add_len > (len - (offset - saved_offset)))
1578 proto_tree_add_none_format(tree, hf_ansi_683_none, tvb,
1579 offset, len - (offset - saved_offset), "Short Data (?)");
1585 oct = tvb_get_guint8(tvb, offset);
1588 proto_tree_add_none_format(tree, hf_ansi_683_none,
1590 "Band/Mode Capability Information");
1592 subtree = proto_item_add_subtree(item, ett_band_cap);
1594 other_decode_bitfield_value(bigbuf, oct, 0x80, 8);
1595 proto_tree_add_none_format(subtree, hf_ansi_683_none,
1597 "%s : Band Class 0 Analog",
1600 other_decode_bitfield_value(bigbuf, oct, 0x40, 8);
1601 proto_tree_add_none_format(subtree, hf_ansi_683_none,
1603 "%s : Band Class 0 CDMA",
1606 other_decode_bitfield_value(bigbuf, oct, 0x20, 8);
1607 proto_tree_add_none_format(subtree, hf_ansi_683_none,
1609 "%s : Band Class 1 CDMA",
1612 other_decode_bitfield_value(bigbuf, oct, 0x1f, 8);
1613 proto_tree_add_none_format(subtree, hf_ansi_683_none,
1622 proto_tree_add_none_format(tree, hf_ansi_683_none,
1623 tvb, offset, add_len - 1,
1624 "More Additional Fields");
1625 offset += (add_len - 1);
1629 EXTRANEOUS_DATA_CHECK(len, offset - saved_offset);
1633 msg_sspr_config_rsp(tvbuff_t *tvb, proto_tree *tree, guint len, guint32 offset)
1635 guint8 oct, block_len;
1637 guint32 saved_offset;
1639 SHORT_DATA_CHECK(len, 3);
1641 saved_offset = offset;
1643 oct = tvb_get_guint8(tvb, offset);
1645 str = rev_sspr_param_block_type(oct);
1647 proto_tree_add_none_format(tree, hf_ansi_683_none,
1655 oct = tvb_get_guint8(tvb, offset);
1657 str = rev_res_code_type(oct);
1659 proto_tree_add_none_format(tree, hf_ansi_683_none,
1661 "SSPR Configuration result code, %s (%d)",
1667 block_len = tvb_get_guint8(tvb, offset);
1669 proto_tree_add_uint(tree, hf_ansi_683_length,
1670 tvb, offset, 1, block_len);
1673 if (block_len > (len - (offset - saved_offset)))
1675 proto_tree_add_none_format(tree, hf_ansi_683_none, tvb,
1676 offset, len - (offset - saved_offset), "Short Data (?)");
1682 proto_tree_add_none_format(tree, hf_ansi_683_none,
1683 tvb, offset, block_len, "Block Data");
1684 offset += block_len;
1687 EXTRANEOUS_DATA_CHECK(len, offset - saved_offset);
1691 msg_sspr_download_rsp(tvbuff_t *tvb, proto_tree *tree, guint len, guint32 offset)
1695 guint32 saved_offset;
1698 EXACT_DATA_CHECK(len, 5);
1700 saved_offset = offset;
1702 oct = tvb_get_guint8(tvb, offset);
1704 str = for_sspr_param_block_type(oct);
1706 proto_tree_add_none_format(tree, hf_ansi_683_none,
1714 oct = tvb_get_guint8(tvb, offset);
1716 str = rev_res_code_type(oct);
1718 proto_tree_add_none_format(tree, hf_ansi_683_none,
1720 "SSPR Download result code, %s (%d)",
1726 value = tvb_get_ntohs(tvb, offset);
1728 proto_tree_add_none_format(tree, hf_ansi_683_none,
1730 "Segment offset (%d)",
1734 oct = tvb_get_guint8(tvb, offset);
1736 proto_tree_add_none_format(tree, hf_ansi_683_none,
1738 "Maximum segment size (%d)",
1744 msg_validate_rsp(tvbuff_t *tvb, proto_tree *tree, guint len, guint32 offset)
1746 guint8 oct, block_id, num_blocks;
1748 guint32 i, saved_offset;
1749 proto_tree *subtree;
1752 SHORT_DATA_CHECK(len, 1);
1754 saved_offset = offset;
1756 num_blocks = tvb_get_guint8(tvb, offset);
1758 proto_tree_add_none_format(tree, hf_ansi_683_none,
1760 "Number of parameter blocks (%d)",
1765 if ((guint32)(num_blocks * 2) > (len - (offset - saved_offset)))
1767 proto_tree_add_none_format(tree, hf_ansi_683_none, tvb,
1768 offset, len - (offset - saved_offset), "Short Data (?)");
1772 for (i=0; i < num_blocks; i++)
1774 block_id = tvb_get_guint8(tvb, offset);
1776 str = for_val_param_block_type(block_id);
1779 proto_tree_add_none_format(tree, hf_ansi_683_none,
1785 subtree = proto_item_add_subtree(item, ett_for_val_block);
1788 oct = tvb_get_guint8(tvb, offset);
1790 str = rev_res_code_type(oct);
1792 proto_tree_add_none_format(subtree, hf_ansi_683_none,
1801 EXTRANEOUS_DATA_CHECK(len, offset - saved_offset);
1805 msg_otapa_rsp(tvbuff_t *tvb, proto_tree *tree, guint len, guint32 offset)
1809 guint32 saved_offset;
1811 SHORT_DATA_CHECK(len, 2);
1813 saved_offset = offset;
1815 oct = tvb_get_guint8(tvb, offset);
1817 str = rev_res_code_type(oct);
1819 proto_tree_add_none_format(tree, hf_ansi_683_none,
1827 oct = tvb_get_guint8(tvb, offset);
1829 other_decode_bitfield_value(bigbuf, oct, 0xfe, 8);
1830 proto_tree_add_none_format(tree, hf_ansi_683_none,
1835 other_decode_bitfield_value(bigbuf, oct, 0x01, 8);
1836 proto_tree_add_none_format(tree, hf_ansi_683_none,
1838 "%s : NAM_LOCK indicator",
1845 if (4 > (len - (offset - saved_offset)))
1847 proto_tree_add_none_format(tree, hf_ansi_683_none, tvb,
1848 offset, len - (offset - saved_offset), "Short Data (?)");
1852 proto_tree_add_none_format(tree, hf_ansi_683_none,
1854 "SPASM random challenge");
1858 EXTRANEOUS_DATA_CHECK(len, offset - saved_offset);
1861 static const value_string for_msg_type_strings[] = {
1862 { 0, "Configuration Request" },
1863 { 1, "Download Request" },
1864 { 2, "MS Key Request" },
1865 { 3, "Key Generation Request" },
1866 { 4, "Re-Authenticate Request" },
1867 { 5, "Commit Request" },
1868 { 6, "Protocol Capability Request" },
1869 { 7, "SSPR Configuration Request" },
1870 { 8, "SSPR Download Request" },
1871 { 9, "Validation Request" },
1872 { 10, "OTAPA Request" },
1875 #define NUM_FOR_MSGS (sizeof(for_msg_type_strings)/sizeof(value_string))
1876 static void (*ansi_683_for_msg_fcn[])(tvbuff_t *tvb, proto_tree *tree, guint len, guint32 offset) = {
1877 msg_config_req, /* Configuration Request */
1878 msg_download_req, /* Download Request */
1879 msg_ms_key_req, /* MS Key Request */
1880 msg_key_gen_req, /* Key Generation Request */
1881 msg_reauth_req, /* Re-Authenticate Request */
1882 NULL /* No data */, /* Commit Request */
1883 NULL /* No data */, /* Protocol Capability Request */
1884 msg_sspr_config_req, /* SSPR Configuration Request */
1885 msg_sspr_download_req, /* SSPR Download Request */
1886 msg_validate_req, /* Validation Request */
1887 msg_otapa_req, /* OTAPA Request */
1891 static const value_string rev_msg_type_strings[] = {
1892 { 0, "Configuration Response" },
1893 { 1, "Download Response" },
1894 { 2, "MS Key Response" },
1895 { 3, "Key Generation Response" },
1896 { 4, "Re-Authenticate Response" },
1897 { 5, "Commit Response" },
1898 { 6, "Protocol Capability Response" },
1899 { 7, "SSPR Configuration Response" },
1900 { 8, "SSPR Download Response" },
1901 { 9, "Validation Response" },
1902 { 10, "OTAPA Response" },
1905 #define NUM_REV_MSGS (sizeof(rev_msg_type_strings)/sizeof(value_string))
1906 static void (*ansi_683_rev_msg_fcn[])(tvbuff_t *tvb, proto_tree *tree, guint len, guint32 offset) = {
1907 msg_config_rsp, /* Configuration Response */
1908 msg_download_rsp, /* Download Response */
1909 msg_ms_key_rsp, /* MS Key Response */
1910 msg_key_gen_rsp, /* Key Generation Response */
1911 msg_reauth_rsp, /* Re-Authenticate Response */
1912 msg_commit_rsp, /* Commit Response */
1913 msg_protocap_rsp, /* Protocol Capability Response */
1914 msg_sspr_config_rsp, /* SSPR Configuration Response */
1915 msg_sspr_download_rsp, /* SSPR Download Response */
1916 msg_validate_rsp, /* Validation Response */
1917 msg_otapa_rsp, /* OTAPA Response */
1923 dissect_ansi_683_for_message(tvbuff_t *tvb, proto_tree *ansi_683_tree)
1930 msg_type = tvb_get_guint8(tvb, 0);
1932 str = my_match_strval(msg_type, for_msg_type_strings, &idx);
1940 * No Information column data
1943 proto_tree_add_uint(ansi_683_tree, hf_ansi_683_for_msg_type,
1944 tvb, 0, 1, msg_type);
1946 if (ansi_683_for_msg_fcn[idx] != NULL)
1948 (*ansi_683_for_msg_fcn[idx])(tvb, ansi_683_tree, tvb_length(tvb) - 1, 1);
1953 dissect_ansi_683_rev_message(tvbuff_t *tvb, proto_tree *ansi_683_tree)
1960 msg_type = tvb_get_guint8(tvb, 0);
1962 str = my_match_strval(msg_type, rev_msg_type_strings, &idx);
1970 * No Information column data
1973 proto_tree_add_uint(ansi_683_tree, hf_ansi_683_rev_msg_type,
1974 tvb, 0, 1, msg_type);
1976 (*ansi_683_rev_msg_fcn[idx])(tvb, ansi_683_tree, tvb_length(tvb) - 1, 1);
1980 dissect_ansi_683(tvbuff_t *tvb, packet_info *pinfo, proto_tree *tree)
1982 proto_item *ansi_683_item;
1983 proto_tree *ansi_683_tree = NULL;
1987 if (check_col(pinfo->cinfo, COL_PROTOCOL))
1989 col_set_str(pinfo->cinfo, COL_PROTOCOL, ansi_proto_name_short);
1992 /* In the interest of speed, if "tree" is NULL, don't do any work not
1993 * necessary to generate protocol tree items.
2000 * create the ansi_683 protocol tree
2003 proto_tree_add_protocol_format(tree, proto_ansi_683, tvb, 0, -1,
2006 (pinfo->match_port == ANSI_683_FORWARD) ? "Forward" : "Reverse");
2009 proto_item_add_subtree(ansi_683_item, ett_ansi_683);
2011 if (pinfo->match_port == ANSI_683_FORWARD)
2013 dissect_ansi_683_for_message(tvb, ansi_683_tree);
2017 dissect_ansi_683_rev_message(tvb, ansi_683_tree);
2023 /* Register the protocol with Ethereal */
2025 proto_register_ansi_683(void)
2028 /* Setup list of header fields */
2029 static hf_register_info hf[] =
2031 { &hf_ansi_683_for_msg_type,
2032 { "Forward Link Message Type",
2033 "ansi_683.for_msg_type",
2034 FT_UINT8, BASE_DEC, VALS(for_msg_type_strings), 0,
2036 { &hf_ansi_683_rev_msg_type,
2037 { "Reverse Link Message Type",
2038 "ansi_683.rev_msg_type",
2039 FT_UINT8, BASE_DEC, VALS(rev_msg_type_strings), 0,
2041 { &hf_ansi_683_length,
2042 { "Length", "ansi_683.len",
2043 FT_UINT8, BASE_DEC, NULL, 0,
2046 { &hf_ansi_683_none,
2047 { "Sub tree", "ansi_683.none",
2053 /* Setup protocol subtree array */
2054 #define NUM_INDIVIDUAL_PARAMS 10
2055 static gint *ett[NUM_INDIVIDUAL_PARAMS];
2057 memset((void *) ett, 0, sizeof(ett));
2059 ett[0] = &ett_ansi_683;
2060 ett[1] = &ett_for_nam_block;
2061 ett[2] = &ett_rev_nam_block;
2062 ett[3] = &ett_key_p;
2063 ett[4] = &ett_key_g;
2064 ett[5] = &ett_rev_feat;
2065 ett[6] = &ett_for_val_block;
2066 ett[7] = &ett_for_sspr_block;
2067 ett[8] = &ett_band_cap;
2068 ett[9] = &ett_rev_sspr_block;
2070 /* Register the protocol name and description */
2072 proto_register_protocol(ansi_proto_name, "ANSI IS-683-A (OTA (Mobile))", "ansi_683");
2074 /* Required function calls to register the header fields and subtrees used */
2075 proto_register_field_array(proto_ansi_683, hf, array_length(hf));
2076 proto_register_subtree_array(ett, array_length(ett));
2081 proto_reg_handoff_ansi_683(void)
2083 dissector_handle_t ansi_683_handle;
2085 ansi_683_handle = create_dissector_handle(dissect_ansi_683, proto_ansi_683);
2087 dissector_add("ansi_map.ota", ANSI_683_FORWARD, ansi_683_handle);
2088 dissector_add("ansi_map.ota", ANSI_683_REVERSE, ansi_683_handle);
2089 dissector_add("ansi_a.ota", ANSI_683_FORWARD, ansi_683_handle);
2090 dissector_add("ansi_a.ota", ANSI_683_REVERSE, ansi_683_handle);
2092 data_handle = find_dissector("data");