2 * Routines for GSM Supplementary Services dissection
5 * Routines are shared by GSM MAP/GSM A dissectors.
6 * This file provides SHARED routines and is NOT a
7 * standalone dissector.
9 * Copyright 2004, Michael Lum <mlum [AT] telostech.com>
10 * In association with Telos Technology Inc.
15 * Mobile radio Layer 3 supplementary service specification;
17 * (3GPP TS 24.080 version 4.3.0 Release 4)
19 * Michael Lum <mlum [AT] telostech.com>,
22 * $Id: packet-gsm_ss.c,v 1.3 2004/04/21 05:53:56 guy Exp $
24 * Ethereal - Network traffic analyzer
25 * By Gerald Combs <gerald@ethereal.com>
26 * Copyright 1998 Gerald Combs
28 * Copied from packet-gsm_map.c (where "WHATEVER_FILE_YOU_USED"
29 * is a dissector file; if you just copied this from README.developer,
30 * don't bother with the "Copied from" - you don't even need to put
31 * in a "Copied from" if you copied an existing dissector, especially
32 * if the bulk of the code in the new dissector is your code)
34 * This program is free software; you can redistribute it and/or
35 * modify it under the terms of the GNU General Public License
36 * as published by the Free Software Foundation; either version 2
37 * of the License, or (at your option) any later version.
39 * This program is distributed in the hope that it will be useful,
40 * but WITHOUT ANY WARRANTY; without even the implied warranty of
41 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
42 * GNU General Public License for more details.
44 * You should have received a copy of the GNU General Public License
45 * along with this program; if not, write to the Free Software
46 * Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
57 #include "epan/packet.h"
61 #include "packet-tcap.h"
62 #include "packet-gsm_sms.h"
63 #include "packet-gsm_ss.h"
66 const value_string gsm_ss_err_code_strings[] = {
67 { 1, "Unknown Subscriber" },
69 { 5, "Unidentified Subscriber" },
70 { 6, "Absent Subscriber SM" },
71 { 7, "Unknown Equipment" },
72 { 8, "Roaming Not Allowed" },
73 { 9, "Illegal Subscriber" },
74 { 10, "Bearer Service Not Provisioned" },
75 { 11, "Teleservice Not Provisioned" },
76 { 12, "Illegal Equipment" },
77 { 13, "Call Barred" },
78 { 14, "Forwarding Violation" },
80 { 16, "Illegal SS Operation" },
81 { 17, "SS Error Status" },
82 { 18, "SS Not Available" },
83 { 19, "SS Subscription Violation" },
84 { 20, "SS Incompatibility" },
85 { 21, "Facility Not Supported" },
86 { 25, "No Handover Number Available" },
87 { 26, "Subsequent Handover Failure" },
88 { 27, "Absent Subscriber" },
89 { 28, "Incompatible Terminal" },
90 { 29, "Short Term Denial" },
91 { 30, "Long Term Denial" },
92 { 31, "Subscriber Busy For MT SMS" },
93 { 32, "SM Delivery Failure" },
94 { 33, "Message Waiting List Full" },
95 { 34, "System Failure" },
96 { 35, "Data Missing" },
97 { 36, "Unexpected Data Value" },
98 { 37, "PW Registration Failure" },
99 { 38, "Negative PW Check" },
100 { 39, "No Roaming Number Available" },
101 { 40, "Tracing Buffer Full" },
102 { 42, "Target Cell Outside Group Call Area" },
103 { 43, "Number Of PW Attempts Violation" },
104 { 44, "Number Changed" },
105 { 45, "Busy Subscriber" },
106 { 46, "No Subscriber Reply" },
107 { 47, "Forwarding Failed" },
108 { 48, "OR Not Allowed" },
109 { 49, "ATI Not Allowed" },
110 { 50, "No Group Call Number Available" },
111 { 51, "Resource Limitation" },
112 { 52, "Unauthorized Requesting Network" },
113 { 53, "Unauthorized LCS Client" },
114 { 54, "Position Method Failure" },
115 { 58, "Unknown Or Unreachable LCS Client" },
116 { 59, "MM Event Not Supported" },
117 { 60, "ATSI Not Allowed" },
118 { 61, "ATM Not Allowed" },
119 { 62, "Information Not Available" },
120 { 71, "Unknown Alphabet" },
122 { 120, "Nbr Sb Exceeded" },
123 { 121, "Rejected By User" },
124 { 122, "Rejected By Network" },
125 { 123, "Deflection To Served Subscriber" },
126 { 124, "Special Service Code" },
127 { 125, "Invalid Deflected To Number" },
128 { 126, "Max Number Of MPTY Participants Exceeded" },
129 { 127, "Resources Not Available" },
133 const value_string gsm_ss_opr_code_strings[] = {
134 { 10, "Register SS" },
136 { 12, "Activate SS" },
137 { 13, "Deactivate SS" },
138 { 14, "Interrogate SS" },
140 { 17, "Register Password" },
141 { 18, "Get Password" },
142 { 19, "Process Unstructured SS Data" },
143 { 38, "Forward Check SS Indication" },
144 { 59, "Process Unstructured SS Request" },
145 { 60, "Unstructured SS Request" },
146 { 61, "Unstructured SS Notify" },
147 { 77, "Erase CC Entry" },
148 { 117, "Call Deflection" },
149 { 118, "User User Service" },
150 { 119, "Access Register CC Entry" },
151 { 120, "Forward CUG Info" },
152 { 121, "Split MPTY" },
153 { 122, "Retrieve MPTY" },
154 { 123, "Hold MPTY" },
155 { 124, "Build MPTY" },
156 { 125, "Forward Charge Advice" },
157 { 126, "Explicit CT" },
158 { 116, "LCS Location Notification" },
165 /* never initialize in field array */
166 static int hf_null = -1;
167 #define HF_NULL &hf_null
169 gint gsm_ss_ett[NUM_GSM_SS_ETT]; /* initialization is left to users */
171 static gboolean gsm_ss_seven_bit = FALSE;
172 static gboolean gsm_ss_eight_bit = FALSE;
173 static gboolean gsm_ss_ucs2 = FALSE;
174 static gboolean gsm_ss_compressed = FALSE;
177 typedef struct dgt_set_t
179 unsigned char out[15];
184 static dgt_set_t Dgt_tbcd = {
186 /* 0 1 2 3 4 5 6 7 8 9 a b c d e */
187 '0','1','2','3','4','5','6','7','8','9','?','B','C','*','#'
192 static dgt_set_t Dgt_msid = {
194 /* 0 1 2 3 4 5 6 7 8 9 a b c d e */
195 '0','1','2','3','4','5','6','7','8','9','?','?','?','?','?'
200 /* FORWARD DECLARATIONS */
202 static void op_generic_ss(ASN1_SCK *asn1, proto_tree *tree, guint exp_len);
205 /* GENERIC HELPER FUNCTIONS */
208 * Unpack BCD input pattern into output ASCII pattern
210 * Input Pattern is supplied using the same format as the digits
212 * Returns: length of unpacked pattern
216 char *out, /* ASCII pattern out */
217 guchar *in, /* packed pattern in */
218 int num_octs, /* Number of octets to unpack */
219 dgt_set_t *dgt /* Digit definitions */
228 * unpack first value in byte
231 *out++ = dgt->out[i & 0x0f];
235 * unpack second value in byte
239 if (i == 0x0f) /* odd number bytes - hit filler */
242 *out++ = dgt->out[i];
253 my_match_strval(guint32 val, const value_string *vs, gint *idx)
257 while (vs[i].strptr) {
258 if (vs[i].value == val)
261 return(vs[i].strptr);
271 /* PARAMETER dissection */
274 param_AddressString(ASN1_SCK *asn1, proto_tree *tree, guint len, int hf_field)
282 saved_offset = asn1->offset;
283 asn1_int32_value_decode(asn1, 1, &value);
285 other_decode_bitfield_value(bigbuf, value, 0x80, 8);
286 proto_tree_add_text(tree, asn1->tvb,
289 bigbuf, (value & 0x80) ? "No E" : "E");
291 switch ((value & 0x70) >> 4)
293 case 0x00: str = "unknown"; break;
294 case 0x01: str = "International Number"; break;
295 case 0x02: str = "National Significant Number"; break;
296 case 0x03: str = "Network Specific Number"; break;
297 case 0x04: str = "Subscriber Number"; break;
298 case 0x05: str = "Reserved"; break;
299 case 0x06: str = "Abbreviated Number"; break;
300 case 0x07: str = "Reserved for extension"; break;
303 other_decode_bitfield_value(bigbuf, value, 0x70, 8);
304 proto_tree_add_text(tree, asn1->tvb,
305 saved_offset, asn1->offset - saved_offset,
309 switch (value & 0x0f)
311 case 0x00: str = "unknown"; break;
312 case 0x01: str = "ISDN/Telephony Numbering (Rec ITU-T E.164)"; break;
313 case 0x02: str = "spare"; break;
314 case 0x03: str = "Data Numbering (ITU-T Rec. X.121)"; break;
315 case 0x04: str = "Telex Numbering (ITU-T Rec. F.69)"; break;
316 case 0x05: str = "spare"; break;
317 case 0x06: str = "Land Mobile Numbering (ITU-T Rec. E.212)"; break;
318 case 0x07: str = "spare"; break;
319 case 0x08: str = "National Numbering"; break;
320 case 0x09: str = "Private Numbering"; break;
321 case 0x0f: str = "Reserved for extension"; break;
327 other_decode_bitfield_value(bigbuf, value, 0x0f, 8);
328 proto_tree_add_text(tree, asn1->tvb,
329 saved_offset, asn1->offset - saved_offset,
333 saved_offset = asn1->offset;
334 asn1_string_value_decode(asn1, len - 1, &poctets);
336 my_dgt_tbcd_unpack(bigbuf, poctets, len - 1, &Dgt_msid);
341 proto_tree_add_text(tree, asn1->tvb,
342 saved_offset, len - 1, "BCD Digits %s", bigbuf);
346 proto_tree_add_string_format(tree, hf_field, asn1->tvb,
347 saved_offset, len - 1, bigbuf, "BCD Digits %s", bigbuf);
352 param_ssCode(ASN1_SCK *asn1, proto_tree *tree, guint len, int hf_field)
360 saved_offset = asn1->offset;
361 asn1_int32_value_decode(asn1, len, &value);
366 str = "allSS - all SS";
370 str = "allLineIdentificationSS - all line identification SS";
374 str = "clip - calling line identification presentation";
378 str = "clir - calling line identification restriction";
382 str = "colp - connected line identification presentation";
386 str = "colr - connected line identification restriction";
390 str = "mci - malicious call identification";
394 str = "allNameIdentificationSS - all name indentification SS";
398 str = "cnap - calling name presentation";
402 str = "allForwardingSS - all forwarding SS";
406 str = "cfu - call forwarding unconditional";
410 str = "allCondForwardingSS - all conditional forwarding SS";
414 str = "cfb - call forwarding busy";
418 str = "cfnry - call forwarding on no reply";
422 str = "cfnrc - call forwarding on mobile subscriber not reachable";
426 str = "cd - call deflection";
430 str = "allCallOfferingSS - all call offering SS includes also all forwarding SS";
434 str = "ect - explicit call transfer";
438 str = "mah - mobile access hunting";
442 str = "allCallCompletionSS - all Call completion SS";
446 str = "cw - call waiting";
450 str = "hold - call hold";
454 str = "ccbs-A - completion of call to busy subscribers, originating side";
458 str = "ccbs-B - completion of call to busy subscribers, destination side";
462 str = "mc - multicall";
466 str = "allMultiPartySS - all multiparty SS";
470 str = "multiPTY - multiparty";
474 str = "allCommunityOfInterestSS - all community of interest SS";
478 str = "cug - closed user group";
482 str = "allChargingSS - all charging SS";
486 str = "aoci - advice of charge information";
490 str = "aocc - advice of charge charging";
494 str = "allAdditionalInfoTransferSS - all additional information transfer SS";
498 str = "uus1 - UUS1 user-to-user signalling";
502 str = "uus2 - UUS2 user-to-user signalling";
506 str = "uus3 - UUS3 user-to-user signalling";
510 str = "allBarringSS - all barring SS";
514 str = "barringOfOutgoingCalls";
518 str = "baoc - barring of all outgoing calls";
522 str = "boic - barring of outgoing international calls";
526 str = "boicExHC - barring of outgoing international calls except those directed to the home PLMN";
530 str = "barringOfIncomingCalls";
534 str = "baic - barring of all incoming calls";
538 str = "bicRoam - barring of incoming calls when roaming outside home PLMN Country";
542 str = "allPLMN-specificSS";
546 str = "allCallPrioritySS - all call priority SS";
550 str = "emlpp - enhanced Multilevel Precedence Pre-emption (EMLPP) service";
554 str = "allLCSPrivacyException - all LCS Privacy Exception Classes";
558 str = "universal - allow location by any LCS client";
562 str = "callrelated - allow location by any value added LCS client to which a call is established from the target MS";
566 str = "callunrelated - allow location by designated external value added LCS clients";
570 str = "plmnoperator - allow location by designated PLMN operator LCS clients";
574 str = "allMOLR-SS - all Mobile Originating Location Request Classes";
578 str = "basicSelfLocation - allow an MS to request its own location";
582 str = "autonomousSelfLocation - allow an MS to perform self location without interaction with the PLMN for a predetermined period of time";
586 str = "transferToThirdParty - allow an MS to request transfer of its location to another LCS client";
593 str = "reserved for future use";
597 proto_tree_add_text(tree, asn1->tvb, saved_offset, len, str);
604 param_ssStatus(ASN1_SCK *asn1, proto_tree *tree, guint len, int hf_field)
612 saved_offset = asn1->offset;
613 asn1_int32_value_decode(asn1, len, &value);
615 other_decode_bitfield_value(bigbuf, value, 0xf0, 8);
616 proto_tree_add_text(tree, asn1->tvb,
622 * Q bit is valid only if A bit is "Active"
624 other_decode_bitfield_value(bigbuf, value, 0x08, 8);
625 proto_tree_add_text(tree, asn1->tvb,
630 ((value & 0x08) ? "Quiescent" : "Operative") : "N/A");
632 other_decode_bitfield_value(bigbuf, value, 0x04, 8);
633 proto_tree_add_text(tree, asn1->tvb,
635 "%s : P bit: %sProvisioned",
637 (value & 0x04) ? "" : "Not ");
639 other_decode_bitfield_value(bigbuf, value, 0x02, 8);
640 proto_tree_add_text(tree, asn1->tvb,
642 "%s : R bit: %sRegistered",
644 (value & 0x02) ? "" : "Not ");
646 other_decode_bitfield_value(bigbuf, value, 0x01, 8);
647 proto_tree_add_text(tree, asn1->tvb,
649 "%s : A bit: %sActive",
651 (value & 0x01) ? "" : "Not ");
655 param_bearerservice(ASN1_SCK *asn1, proto_tree *tree, guint len, int hf_field)
663 saved_offset = asn1->offset;
664 asn1_int32_value_decode(asn1, len, &value);
668 case 0x00: str = "allBearerServices"; break;
669 case 0x10: str = "allDataCDA-Services"; break;
670 case 0x11: str = "dataCDA-300bps"; break;
671 case 0x12: str = "dataCDA-1200bps"; break;
672 case 0x13: str = "dataCDA-1200-75bps"; break;
673 case 0x14: str = "dataCDA-2400bps"; break;
674 case 0x15: str = "dataCDA-4800bps"; break;
675 case 0x16: str = "dataCDA-9600bps"; break;
676 case 0x17: str = "general-dataCDA"; break;
677 case 0x18: str = "allDataCDS-Services"; break;
678 case 0x1a: str = "dataCDS-1200bps"; break;
679 case 0x1c: str = "dataCDS-2400bps"; break;
680 case 0x1d: str = "dataCDS-4800bps"; break;
681 case 0x1e: str = "dataCDS-9600bps"; break;
682 case 0x1f: str = "general-dataCDS"; break;
684 case 0x20: str = "allPadAccessCA-Services"; break;
685 case 0x21: str = "padAccessCA-300bps"; break;
686 case 0x22: str = "padAccessCA-1200bps"; break;
687 case 0x23: str = "padAccessCA-1200-75bps"; break;
688 case 0x24: str = "padAccessCA-2400bps"; break;
689 case 0x25: str = "padAccessCA-4800bps"; break;
690 case 0x26: str = "padAccessCA-9600bps"; break;
691 case 0x27: str = "general-padAccessCA"; break;
692 case 0x28: str = "allDataPDS-Services"; break;
693 case 0x2c: str = "dataPDS-2400bps"; break;
694 case 0x2d: str = "dataPDS-4800bps"; break;
695 case 0x2e: str = "dataPDS-9600bps"; break;
696 case 0x2f: str = "general-dataPDS"; break;
698 case 0x30: str = "allAlternateSpeech-DataCDA"; break;
699 case 0x38: str = "allAlternateSpeech-DataCDS"; break;
700 case 0x40: str = "allSpeechFollowedByDataCDA"; break;
701 case 0x48: str = "allSpeechFollowedByDataCDS"; break;
703 case 0x50: str = "allDataCircuitAsynchronous"; break;
704 case 0x60: str = "allAsynchronousServices"; break;
705 case 0x58: str = "allDataCircuitSynchronous"; break;
706 case 0x68: str = "allSynchronousServices"; break;
708 case 0xd0: str = "allPLMN-specificBS"; break;
709 case 0xd1: str = "plmn-specificBS-1"; break;
710 case 0xd2: str = "plmn-specificBS-2"; break;
711 case 0xd3: str = "plmn-specificBS-3"; break;
712 case 0xd4: str = "plmn-specificBS-4"; break;
713 case 0xd5: str = "plmn-specificBS-5"; break;
714 case 0xd6: str = "plmn-specificBS-6"; break;
715 case 0xd7: str = "plmn-specificBS-7"; break;
716 case 0xd8: str = "plmn-specificBS-8"; break;
717 case 0xd9: str = "plmn-specificBS-9"; break;
718 case 0xda: str = "plmn-specificBS-A"; break;
719 case 0xdb: str = "plmn-specificBS-B"; break;
720 case 0xdc: str = "plmn-specificBS-C"; break;
721 case 0xdd: str = "plmn-specificBS-D"; break;
722 case 0xde: str = "plmn-specificBS-E"; break;
723 case 0xdf: str = "plmn-specificBS-F"; break;
730 proto_tree_add_text(tree, asn1->tvb, saved_offset, len, str);
734 param_teleservice(ASN1_SCK *asn1, proto_tree *tree, guint len, int hf_field)
742 saved_offset = asn1->offset;
743 asn1_int32_value_decode(asn1, len, &value);
747 case 0x00: str = "allTeleservices"; break;
748 case 0x10: str = "allSpeechTransmissionServices"; break;
749 case 0x11: str = "telephony"; break;
750 case 0x12: str = "emergencyCalls"; break;
751 case 0x20: str = "allShortMessageServices"; break;
752 case 0x21: str = "shortMessageMT-PP"; break;
753 case 0x22: str = "shortMessageMO-PP"; break;
754 case 0x60: str = "allFacsimileTransmissionServices"; break;
755 case 0x61: str = "facsimileGroup3AndAlterSpeech"; break;
756 case 0x62: str = "automaticFacsimileGroup3"; break;
757 case 0x63: str = "facsimileGroup4"; break;
759 case 0x70: str = "allDataTeleservices"; break;
760 case 0x80: str = "allTeleservices-ExeptSMS"; break;
762 case 0x90: str = "allVoiceGroupCallServices"; break;
763 case 0x91: str = "voiceGroupCall"; break;
764 case 0x92: str = "voiceBroadcastCall"; break;
766 case 0xd0: str = "allPLMN-specificTS"; break;
767 case 0xd1: str = "plmn-specificTS-1"; break;
768 case 0xd2: str = "plmn-specificTS-2"; break;
769 case 0xd3: str = "plmn-specificTS-3"; break;
770 case 0xd4: str = "plmn-specificTS-4"; break;
771 case 0xd5: str = "plmn-specificTS-5"; break;
772 case 0xd6: str = "plmn-specificTS-6"; break;
773 case 0xd7: str = "plmn-specificTS-7"; break;
774 case 0xd8: str = "plmn-specificTS-8"; break;
775 case 0xd9: str = "plmn-specificTS-9"; break;
776 case 0xda: str = "plmn-specificTS-A"; break;
777 case 0xdb: str = "plmn-specificTS-B"; break;
778 case 0xdc: str = "plmn-specificTS-C"; break;
779 case 0xdd: str = "plmn-specificTS-D"; break;
780 case 0xde: str = "plmn-specificTS-E"; break;
781 case 0xdf: str = "plmn-specificTS-F"; break;
788 proto_tree_add_text(tree, asn1->tvb, saved_offset, len, str);
793 * Same as Cell Broadcast
796 param_ussdDCS(ASN1_SCK *asn1, proto_tree *tree, guint len, int hf_field)
807 gsm_ss_seven_bit = FALSE;
808 gsm_ss_eight_bit = FALSE;
810 gsm_ss_compressed = FALSE;
812 saved_offset = asn1->offset;
813 asn1_int32_value_decode(asn1, len, &value);
816 proto_tree_add_text(tree, asn1->tvb,
818 "Data Coding Scheme (%d)",
821 subtree = proto_item_add_subtree(item, gsm_ss_ett[GSM_SS_ETT_PARAM]);
823 if ((value & 0xf0) == 0x00)
825 /* 0000.... Language using the default alphabet */
827 switch (value & 0x0f)
829 case 0x00: str = "German"; break;
830 case 0x01: str = "English"; break;
831 case 0x02: str = "Italian"; break;
832 case 0x03: str = "French"; break;
833 case 0x04: str = "Spanish"; break;
834 case 0x05: str = "Dutch"; break;
835 case 0x06: str = "Swedish"; break;
836 case 0x07: str = "Danish"; break;
837 case 0x08: str = "Portuguese"; break;
838 case 0x09: str = "Finnish"; break;
839 case 0x0a: str = "Norwegian"; break;
840 case 0x0b: str = "Greek"; break;
841 case 0x0c: str = "Turkish"; break;
842 case 0x0d: str = "Hungarian"; break;
843 case 0x0e: str = "Polish"; break;
844 case 0x0f: str = "Language unspecified"; break;
847 other_decode_bitfield_value(bigbuf, value, 0x0f, 8);
848 proto_tree_add_text(subtree, asn1->tvb,
850 "%s : %s language using default alphabet",
854 gsm_ss_seven_bit = TRUE;
856 else if ((value & 0xf0) == 0x10)
858 switch (value & 0x0f)
860 case 0x00: str = "Default alphabet; message preceded by language indication"; break;
861 case 0x01: str = "UCS2; message preceded by language indication"; break;
863 str = "Reserved for European languages";
867 other_decode_bitfield_value(bigbuf, value, 0xff, 8);
868 proto_tree_add_text(subtree, asn1->tvb,
874 else if ((value & 0xf0) == 0x20)
876 switch (value & 0x0f)
878 case 0x00: str = "Czech"; break;
880 str = "Reserved for European languages using the default alphabet";
884 other_decode_bitfield_value(bigbuf, value, 0xff, 8);
885 proto_tree_add_text(subtree, asn1->tvb,
891 else if ((value & 0xf0) == 0x30)
893 other_decode_bitfield_value(bigbuf, value, 0xff, 8);
894 proto_tree_add_text(subtree, asn1->tvb,
896 "%s : Reserved for European Languages using the default alphabet",
899 else if ((value & 0xc0) == 0x40)
901 other_decode_bitfield_value(bigbuf, value, 0xc0, 8);
902 proto_tree_add_text(subtree, asn1->tvb,
904 "%s : General Data Coding indication",
907 gsm_ss_compressed = (value & 0x20) >> 5;
909 other_decode_bitfield_value(bigbuf, value, 0x20, 8);
910 proto_tree_add_text(subtree, asn1->tvb,
912 "%s : Text is %scompressed",
914 gsm_ss_compressed ? "" : "not ");
916 other_decode_bitfield_value(bigbuf, value, 0x10, 8);
917 proto_tree_add_text(subtree, asn1->tvb,
921 (value & 0x10) ? "Message class is defined below" :
922 "Reserved, no message class");
924 switch ((value & 0x0c) >> 2)
926 case 0x00: str = "GSM 7 bit default alphabet";
927 gsm_ss_seven_bit = TRUE;
929 case 0x01: str = "8 bit data"; break;
930 case 0x02: str = "UCS2 (16 bit)";
933 case 0x03: str = "Reserved"; break;
936 other_decode_bitfield_value(bigbuf, value, 0x0c, 8);
937 proto_tree_add_text(subtree, asn1->tvb,
939 "%s : Character set: %s",
943 switch (value & 0x03)
945 case 0x00: str = "Class 0"; break;
946 case 0x01: str = "Class 1 Default meaning: ME-specific"; break;
947 case 0x02: str = "Class 2 (U)SIM specific message"; break;
948 case 0x03: str = "Class 3 Default meaning: TE-specific"; break;
951 other_decode_bitfield_value(bigbuf, value, 0x03, 8);
952 proto_tree_add_text(subtree, asn1->tvb,
954 "%s : Message Class: %s%s",
957 (value & 0x10) ? "" : " (reserved)");
959 else if ((value & 0xf0) == 0xf0)
961 other_decode_bitfield_value(bigbuf, value, 0xf0, 8);
962 proto_tree_add_text(subtree, asn1->tvb,
964 "%s : Data Coding / Message Handling",
967 other_decode_bitfield_value(bigbuf, value, 0x08, 8);
968 proto_tree_add_text(subtree, asn1->tvb,
973 gsm_ss_seven_bit = !(gsm_ss_eight_bit = (value & 0x04) ? TRUE : FALSE);
975 other_decode_bitfield_value(bigbuf, value, 0x04, 8);
976 proto_tree_add_text(subtree, asn1->tvb,
978 "%s : Message coding: %s",
980 gsm_ss_eight_bit ? "8 bit data" : "Default alphabet");
982 switch (value & 0x03)
984 case 0x00: str = "No message class"; break;
985 case 0x01: str = "Class 1 user defined"; break;
986 case 0x02: str = "Class 2 user defined"; break;
987 case 0x03: str = "Class 3 Default meaning: TE-specific"; break;
990 other_decode_bitfield_value(bigbuf, value, 0x03, 8);
991 proto_tree_add_text(subtree, asn1->tvb,
993 "%s : Message Class: %s",
999 other_decode_bitfield_value(bigbuf, value, 0xff, 8);
1000 proto_tree_add_text(subtree, asn1->tvb,
1002 "%s : Reserved coding groups",
1008 param_ussdString(ASN1_SCK *asn1, proto_tree *tree, guint len, int hf_field)
1016 hf_field = hf_field;
1018 saved_offset = asn1->offset;
1020 if (gsm_ss_compressed)
1022 proto_tree_add_text(tree, asn1->tvb,
1028 if (gsm_ss_seven_bit)
1033 gsm_sms_char_7bit_unpack(fill_bits, len, sizeof(bigbuf),
1034 tvb_get_ptr(asn1->tvb, saved_offset, len), bigbuf);
1035 bigbuf[out_len] = '\0';
1036 gsm_sms_char_ascii_decode(bigbuf, bigbuf, out_len);
1038 proto_tree_add_text(tree, asn1->tvb, saved_offset, len, "%s", bigbuf);
1040 else if (gsm_ss_eight_bit)
1042 proto_tree_add_text(tree, asn1->tvb, saved_offset, len, "%s",
1043 tvb_format_text(asn1->tvb, saved_offset, len));
1045 else if (gsm_ss_ucs2)
1047 ustr = tvb_fake_unicode(asn1->tvb, saved_offset, len, FALSE);
1048 proto_tree_add_text(tree, asn1->tvb, saved_offset, len, "%s", ustr);
1053 /* don't know what form it is */
1055 proto_tree_add_text(tree, asn1->tvb,
1061 asn1->offset += len;
1065 param_ia5String(ASN1_SCK *asn1, proto_tree *tree, guint len, int hf_field)
1069 hf_field = hf_field;
1071 saved_offset = asn1->offset;
1073 proto_tree_add_text(tree, asn1->tvb, saved_offset, len, "%s",
1074 tvb_format_text(asn1->tvb, saved_offset, len));
1076 asn1->offset += len;
1080 param_password(ASN1_SCK *asn1, proto_tree *tree, guint len, int hf_field)
1084 hf_field = hf_field;
1086 saved_offset = asn1->offset;
1088 proto_tree_add_text(tree, asn1->tvb, saved_offset, len, "%s",
1089 tvb_format_text(asn1->tvb, saved_offset, len));
1091 asn1->offset += len;
1095 param_guidanceInfo(ASN1_SCK *asn1, proto_tree *tree, guint len, int hf_field)
1101 hf_field = hf_field;
1103 saved_offset = asn1->offset;
1104 asn1_int32_value_decode(asn1, 1, &value);
1108 case 0: str = "enterPW"; break;
1109 case 1: str = "enterNewPW"; break;
1110 case 2: str = "enterNewPW-Again"; break;
1116 proto_tree_add_text(tree, asn1->tvb, saved_offset, len, str);
1120 param_forwardingOpt(ASN1_SCK *asn1, proto_tree *tree, guint len, int hf_field)
1127 hf_field = hf_field;
1129 saved_offset = asn1->offset;
1130 asn1_int32_value_decode(asn1, 1, &value);
1132 other_decode_bitfield_value(bigbuf, value, 0x80, 8);
1133 proto_tree_add_text(tree, asn1->tvb,
1135 "%s : %snotification to forwarding party",
1137 (value & 0x80) ? "" : "no ");
1139 other_decode_bitfield_value(bigbuf, value, 0x40, 8);
1140 proto_tree_add_text(tree, asn1->tvb,
1142 "%s : %sredirecting presentation",
1144 (value & 0x40) ? "" : "no ");
1146 other_decode_bitfield_value(bigbuf, value, 0x20, 8);
1147 proto_tree_add_text(tree, asn1->tvb,
1149 "%s : %snotification to calling party",
1151 (value & 0x20) ? "" : "no ");
1153 other_decode_bitfield_value(bigbuf, value, 0x10, 8);
1154 proto_tree_add_text(tree, asn1->tvb,
1159 switch ((value & 0x0c) >> 2)
1161 case 0x00: str = "MS not reachable"; break;
1162 case 0x01: str = "MS busy"; break;
1163 case 0x02: str = "No reply"; break;
1164 case 0x03: str = "Unconditional (in SRI result) or Deflection"; break;
1167 other_decode_bitfield_value(bigbuf, value, 0x0c, 8);
1168 proto_tree_add_text(tree, asn1->tvb,
1170 "%s : forwarding reason, %s (%u)",
1173 (value & 0x0c) >> 2);
1175 other_decode_bitfield_value(bigbuf, value, 0x03, 8);
1176 proto_tree_add_text(tree, asn1->tvb,
1181 asn1->offset += len;
1187 GSM_SS_P_SS_CODE, /* SS-Code */
1188 GSM_SS_P_SS_STATUS, /* SS-Status */
1189 GSM_SS_P_BEARERSERVICE, /* Bearer Service */
1190 GSM_SS_P_TELESERVICE, /* Tele Service */
1191 GSM_SS_P_FORWARD_TO_NUM, /* Forward to Number */
1192 GSM_SS_P_LONG_FORWARD_TO_NUM, /* Long Forward to Number */
1193 GSM_SS_P_USSD_DCS, /* USSD Data Coding Scheme */
1194 GSM_SS_P_USSD_STRING, /* USSD String */
1195 GSM_SS_P_IA5_STRING, /* IA5 String */
1196 GSM_SS_P_PASSWORD, /* Password */
1197 GSM_SS_P_GUIDANCE_INFO, /* Guidance Info */
1198 GSM_SS_P_FORWARDING_OPT, /* Forwarding Options */
1199 GSM_SS_P_NONE /* NONE */
1203 #define NUM_PARAM_1 (GSM_SS_P_NONE+1)
1204 static gint ett_param_1[NUM_PARAM_1];
1205 static void (*param_1_fcn[])(ASN1_SCK *asn1, proto_tree *tree, guint len, int hf_field) = {
1206 param_ssCode, /* SS-Code */
1207 param_ssStatus, /* SS-Status */
1208 param_bearerservice, /* Bearer Service */
1209 param_teleservice, /* Tele Service */
1210 param_AddressString, /* Forward to Number */
1211 param_AddressString, /* Long Forward to Number */
1212 param_ussdDCS, /* USSD Data Coding Scheme */
1213 param_ussdString, /* USSD String */
1214 param_ia5String, /* IA5 String */
1215 param_password, /* Password */
1216 param_guidanceInfo, /* Guidance Info */
1217 param_forwardingOpt, /* Forwarding Options */
1221 static int *param_1_hf[] = {
1222 HF_NULL, /* SS-Code */
1223 HF_NULL, /* SS-Status */
1224 HF_NULL, /* Bearer Service */
1225 HF_NULL, /* Tele Service */
1226 HF_NULL, /* Forward to Number */
1227 HF_NULL, /* Long Forward to Number */
1228 HF_NULL, /* USSD Data Coding Scheme */
1229 HF_NULL, /* USSD String */
1230 HF_NULL, /* IA5 String */
1231 HF_NULL, /* Password */
1232 HF_NULL, /* Guidance Info */
1233 HF_NULL, /* Forwarding Options */
1237 #define GSM_SS_START_SUBTREE(_Gtree, _Gsaved_offset, _Gtag, _Gstr1, _Gett, _Gdef_len_p, _Glen_p, _Gsubtree_p) \
1239 guint _len_offset; \
1240 proto_item *_item; \
1242 _len_offset = asn1->offset; \
1243 asn1_length_decode(asn1, _Gdef_len_p, _Glen_p); \
1246 proto_tree_add_text(_Gtree, asn1->tvb, _Gsaved_offset, -1, _Gstr1); \
1248 _Gsubtree_p = proto_item_add_subtree(_item, _Gett); \
1250 proto_tree_add_text(_Gsubtree_p, asn1->tvb, \
1251 _Gsaved_offset, _len_offset - _Gsaved_offset, "Tag: 0x%02x", _Gtag); \
1255 proto_tree_add_text(_Gsubtree_p, asn1->tvb, \
1256 _len_offset, asn1->offset - _len_offset, "Length: %d", *_Glen_p); \
1260 proto_tree_add_text(_Gsubtree_p, asn1->tvb, \
1261 _len_offset, asn1->offset - _len_offset, "Length: Indefinite"); \
1263 *_Glen_p = tcap_find_eoc(asn1); \
1266 proto_item_set_len(_item, (asn1->offset - _Gsaved_offset) + *_Glen_p + \
1267 (*_Gdef_len_p ? 0 : TCAP_EOC_LEN)); \
1270 #define GSM_SS_PARAM_DISPLAY(Gtree, Goffset, Gtag, Ga1, Ga2) \
1272 gint _ett_param_idx; \
1274 void (*_param_fcn)(ASN1_SCK *asn1, proto_tree *tree, guint len, int hf_field) = NULL; \
1275 int *_param_hf = NULL; \
1276 proto_tree *_subtree; \
1277 gboolean _def_len; \
1279 if (Ga1 == GSM_SS_P_NONE) \
1281 _ett_param_idx = gsm_ss_ett[GSM_SS_ETT_PARAM]; \
1282 _param_fcn = NULL; \
1283 _param_hf = HF_NULL; \
1287 _ett_param_idx = ett_param_1[Ga1]; \
1288 _param_fcn = param_1_fcn[Ga1]; \
1289 _param_hf = param_1_hf[Ga1]; \
1292 GSM_SS_START_SUBTREE(Gtree, Goffset, Gtag, Ga2, _ett_param_idx, &_def_len, &_len, _subtree); \
1296 if (Ga1 == GSM_SS_P_NONE || _param_fcn == NULL) \
1298 proto_tree_add_text(_subtree, asn1->tvb, \
1299 asn1->offset, _len, "Parameter Data"); \
1301 asn1->offset += _len; \
1305 (*_param_fcn)(asn1, _subtree, _len, *_param_hf); \
1311 guint _saved_offset; \
1313 _saved_offset = asn1->offset; \
1314 asn1_eoc_decode(asn1, -1); \
1316 proto_tree_add_text(Gtree, asn1->tvb, \
1317 _saved_offset, asn1->offset - _saved_offset, "End of Contents"); \
1323 param_forwardingFeature(ASN1_SCK *asn1, proto_tree *tree, guint exp_len)
1328 proto_tree *subtree;
1332 saved_offset = asn1->offset;
1333 asn1_id_decode1(asn1, &tag);
1335 GSM_SS_START_SUBTREE(tree, saved_offset, tag, "Forwarding Feature",
1336 gsm_ss_ett[GSM_SS_ETT_SEQUENCE],
1337 &def_len, &len, subtree);
1339 if (tcap_check_tag(asn1, 0x82))
1341 saved_offset = asn1->offset;
1342 asn1_id_decode1(asn1, &tag);
1344 GSM_SS_PARAM_DISPLAY(subtree, saved_offset, tag, GSM_SS_P_BEARERSERVICE, "Bearerservice");
1347 if (tcap_check_tag(asn1, 0x83))
1349 saved_offset = asn1->offset;
1350 asn1_id_decode1(asn1, &tag);
1352 GSM_SS_PARAM_DISPLAY(subtree, saved_offset, tag, GSM_SS_P_TELESERVICE, "Teleservice");
1355 if (tcap_check_tag(asn1, 0x84))
1357 saved_offset = asn1->offset;
1358 asn1_id_decode1(asn1, &tag);
1360 GSM_SS_PARAM_DISPLAY(subtree, saved_offset, tag, GSM_SS_P_SS_STATUS, "SS-Status");
1363 if (tcap_check_tag(asn1, 0x85))
1365 saved_offset = asn1->offset;
1366 asn1_id_decode1(asn1, &tag);
1368 GSM_SS_PARAM_DISPLAY(subtree, saved_offset, tag, GSM_SS_P_FORWARD_TO_NUM, "Forwarded to Number");
1371 if (tcap_check_tag(asn1, 0x88))
1373 saved_offset = asn1->offset;
1374 asn1_id_decode1(asn1, &tag);
1376 GSM_SS_PARAM_DISPLAY(subtree, saved_offset, tag, GSM_SS_P_NONE, "Forwarded to Subaddress");
1379 if (tcap_check_tag(asn1, 0x86))
1381 saved_offset = asn1->offset;
1382 asn1_id_decode1(asn1, &tag);
1384 GSM_SS_PARAM_DISPLAY(subtree, saved_offset, tag, GSM_SS_P_FORWARDING_OPT, "Forwarding Options");
1387 if (tcap_check_tag(asn1, 0x87))
1389 saved_offset = asn1->offset;
1390 asn1_id_decode1(asn1, &tag);
1392 GSM_SS_PARAM_DISPLAY(subtree, saved_offset, tag, GSM_SS_P_NONE, "No Reply Condition Time");
1395 if (tcap_check_tag(asn1, 0x89))
1397 saved_offset = asn1->offset;
1398 asn1_id_decode1(asn1, &tag);
1400 GSM_SS_PARAM_DISPLAY(subtree, saved_offset, tag, GSM_SS_P_LONG_FORWARD_TO_NUM, "Long Forward to Number");
1405 saved_offset = asn1->offset;
1406 asn1_eoc_decode(asn1, -1);
1408 proto_tree_add_text(subtree, asn1->tvb,
1409 saved_offset, asn1->offset - saved_offset, "End of Contents");
1414 param_forwardingFeatureList(ASN1_SCK *asn1, proto_tree *tree, guint exp_len)
1416 guint saved_offset, start_offset;
1419 proto_tree *subtree;
1421 saved_offset = asn1->offset;
1422 asn1_id_decode1(asn1, &tag);
1424 GSM_SS_START_SUBTREE(tree, saved_offset, tag, "Forwarding Feature List",
1425 gsm_ss_ett[GSM_SS_ETT_SEQUENCE],
1426 &def_len, &len, subtree);
1428 start_offset = asn1->offset;
1430 while ((tvb_length_remaining(asn1->tvb, asn1->offset) > 0) &&
1431 (!tcap_check_tag(asn1, 0)))
1433 if ((exp_len != 0) &&
1434 ((asn1->offset - saved_offset) >= exp_len))
1439 param_forwardingFeature(asn1, subtree, len - (asn1->offset - start_offset));
1444 saved_offset = asn1->offset;
1445 asn1_eoc_decode(asn1, -1);
1447 proto_tree_add_text(subtree, asn1->tvb,
1448 saved_offset, asn1->offset - saved_offset, "End of Contents");
1453 param_callBarringFeature(ASN1_SCK *asn1, proto_tree *tree, guint exp_len)
1458 proto_tree *subtree;
1462 saved_offset = asn1->offset;
1463 asn1_id_decode1(asn1, &tag);
1465 GSM_SS_START_SUBTREE(tree, saved_offset, tag, "Call Barring Feature",
1466 gsm_ss_ett[GSM_SS_ETT_SEQUENCE],
1467 &def_len, &len, subtree);
1469 if (tcap_check_tag(asn1, 0x82))
1471 saved_offset = asn1->offset;
1472 asn1_id_decode1(asn1, &tag);
1474 GSM_SS_PARAM_DISPLAY(subtree, saved_offset, tag, GSM_SS_P_BEARERSERVICE, "Bearerservice");
1477 if (tcap_check_tag(asn1, 0x83))
1479 saved_offset = asn1->offset;
1480 asn1_id_decode1(asn1, &tag);
1482 GSM_SS_PARAM_DISPLAY(subtree, saved_offset, tag, GSM_SS_P_TELESERVICE, "Teleservice");
1485 if (tcap_check_tag(asn1, 0x84))
1487 saved_offset = asn1->offset;
1488 asn1_id_decode1(asn1, &tag);
1490 GSM_SS_PARAM_DISPLAY(subtree, saved_offset, tag, GSM_SS_P_SS_STATUS, "SS-Status");
1495 saved_offset = asn1->offset;
1496 asn1_eoc_decode(asn1, -1);
1498 proto_tree_add_text(subtree, asn1->tvb,
1499 saved_offset, asn1->offset - saved_offset, "End of Contents");
1504 param_callBarringFeatureList(ASN1_SCK *asn1, proto_tree *tree, guint exp_len)
1506 guint saved_offset, start_offset;
1509 proto_tree *subtree;
1511 saved_offset = asn1->offset;
1512 asn1_id_decode1(asn1, &tag);
1514 GSM_SS_START_SUBTREE(tree, saved_offset, tag, "Call Barring Feature List",
1515 gsm_ss_ett[GSM_SS_ETT_SEQUENCE],
1516 &def_len, &len, subtree);
1518 start_offset = asn1->offset;
1520 while ((tvb_length_remaining(asn1->tvb, asn1->offset) > 0) &&
1521 (!tcap_check_tag(asn1, 0)))
1523 if ((exp_len != 0) &&
1524 ((asn1->offset - saved_offset) >= exp_len))
1529 param_callBarringFeature(asn1, subtree, len - (asn1->offset - start_offset));
1534 saved_offset = asn1->offset;
1535 asn1_eoc_decode(asn1, -1);
1537 proto_tree_add_text(subtree, asn1->tvb,
1538 saved_offset, asn1->offset - saved_offset, "End of Contents");
1543 param_ssData(ASN1_SCK *asn1, proto_tree *tree, guint exp_len)
1547 saved_offset = asn1->offset;
1550 op_generic_ss(asn1, tree, exp_len);
1554 param_ssInfo(ASN1_SCK *asn1, proto_tree *tree)
1556 guint saved_offset, start_offset;
1558 gboolean def_len = FALSE;
1559 proto_tree *subtree;
1561 saved_offset = asn1->offset;
1562 asn1_id_decode1(asn1, &tag);
1566 case 0xa0: /* forwardingInfo */
1567 GSM_SS_START_SUBTREE(tree, saved_offset, tag, "Forwarding Info",
1568 gsm_ss_ett[GSM_SS_ETT_SEQUENCE],
1569 &def_len, &len, subtree);
1571 start_offset = asn1->offset;
1573 if (tcap_check_tag(asn1, 0x04))
1575 saved_offset = asn1->offset;
1576 asn1_id_decode1(asn1, &tag);
1578 GSM_SS_PARAM_DISPLAY(subtree, saved_offset, tag, GSM_SS_P_SS_CODE, "SS-Code");
1581 param_forwardingFeatureList(asn1, subtree, len - (asn1->offset - start_offset));
1585 saved_offset = asn1->offset;
1586 asn1_eoc_decode(asn1, -1);
1588 proto_tree_add_text(subtree, asn1->tvb,
1589 saved_offset, asn1->offset - saved_offset, "End of Contents");
1593 case 0xa1: /* callBarringInfo */
1594 GSM_SS_START_SUBTREE(tree, saved_offset, tag, "Call Barring Info",
1595 gsm_ss_ett[GSM_SS_ETT_SEQUENCE],
1596 &def_len, &len, subtree);
1598 start_offset = asn1->offset;
1600 if (tcap_check_tag(asn1, 0x04))
1602 saved_offset = asn1->offset;
1603 asn1_id_decode1(asn1, &tag);
1605 GSM_SS_PARAM_DISPLAY(subtree, saved_offset, tag, GSM_SS_P_SS_CODE, "SS-Code");
1608 param_callBarringFeatureList(asn1, subtree, len - (asn1->offset - start_offset));
1612 saved_offset = asn1->offset;
1613 asn1_eoc_decode(asn1, -1);
1615 proto_tree_add_text(subtree, asn1->tvb,
1616 saved_offset, asn1->offset - saved_offset, "End of Contents");
1620 case 0xa3: /* ss-Data */
1621 GSM_SS_START_SUBTREE(tree, saved_offset, tag, "ss-Data",
1622 gsm_ss_ett[GSM_SS_ETT_SEQUENCE],
1623 &def_len, &len, subtree);
1625 start_offset = asn1->offset;
1627 param_ssData(asn1, subtree, len - (asn1->offset - start_offset));
1631 saved_offset = asn1->offset;
1632 asn1_eoc_decode(asn1, -1);
1634 proto_tree_add_text(subtree, asn1->tvb,
1635 saved_offset, asn1->offset - saved_offset, "End of Contents");
1640 GSM_SS_START_SUBTREE(tree, saved_offset, tag, "Unexpected TAG",
1641 gsm_ss_ett[GSM_SS_ETT_SEQUENCE],
1642 &def_len, &len, subtree);
1644 op_generic_ss(asn1, subtree, len);
1648 saved_offset = asn1->offset;
1649 asn1_eoc_decode(asn1, -1);
1651 proto_tree_add_text(subtree, asn1->tvb,
1652 saved_offset, asn1->offset - saved_offset, "End of Contents");
1659 param_ssForBS(ASN1_SCK *asn1, proto_tree *tree)
1661 guint saved_offset, start_offset;
1662 guint tag, len, rem_len;
1663 gboolean def_len = FALSE;
1664 proto_tree *subtree;
1666 saved_offset = asn1->offset;
1667 asn1_id_decode1(asn1, &tag);
1669 GSM_SS_START_SUBTREE(tree, saved_offset, tag, "Sequence",
1670 gsm_ss_ett[GSM_SS_ETT_SEQUENCE],
1671 &def_len, &len, subtree);
1673 start_offset = asn1->offset;
1675 saved_offset = asn1->offset;
1676 asn1_id_decode1(asn1, &tag);
1678 GSM_SS_PARAM_DISPLAY(subtree, saved_offset, tag, GSM_SS_P_SS_CODE, "SS-Code");
1680 if (tcap_check_tag(asn1, 0x82))
1682 saved_offset = asn1->offset;
1683 asn1_id_decode1(asn1, &tag);
1685 GSM_SS_PARAM_DISPLAY(subtree, saved_offset, tag, GSM_SS_P_BEARERSERVICE, "Bearerservice");
1688 if (tcap_check_tag(asn1, 0x83))
1690 saved_offset = asn1->offset;
1691 asn1_id_decode1(asn1, &tag);
1693 GSM_SS_PARAM_DISPLAY(subtree, saved_offset, tag, GSM_SS_P_TELESERVICE, "Teleservice");
1696 if (tcap_check_tag(asn1, 0x84))
1698 saved_offset = asn1->offset;
1699 asn1_id_decode1(asn1, &tag);
1701 GSM_SS_PARAM_DISPLAY(subtree, saved_offset, tag, GSM_SS_P_NONE, "Long FTN supported");
1704 rem_len = len - (asn1->offset - start_offset);
1708 op_generic_ss(asn1, subtree, rem_len);
1713 saved_offset = asn1->offset;
1714 asn1_eoc_decode(asn1, -1);
1716 proto_tree_add_text(subtree, asn1->tvb,
1717 saved_offset, asn1->offset - saved_offset, "End of Contents");
1722 param_ussdArg(ASN1_SCK *asn1, proto_tree *tree)
1724 guint saved_offset, start_offset;
1725 guint tag, len, rem_len;
1726 gboolean def_len = FALSE;
1727 proto_tree *subtree;
1729 saved_offset = asn1->offset;
1730 asn1_id_decode1(asn1, &tag);
1732 GSM_SS_START_SUBTREE(tree, saved_offset, tag, "Sequence",
1733 gsm_ss_ett[GSM_SS_ETT_SEQUENCE],
1734 &def_len, &len, subtree);
1736 start_offset = asn1->offset;
1738 saved_offset = asn1->offset;
1739 asn1_id_decode1(asn1, &tag);
1741 GSM_SS_PARAM_DISPLAY(subtree, saved_offset, tag, GSM_SS_P_USSD_DCS, "USSD Data Coding Scheme");
1743 saved_offset = asn1->offset;
1744 asn1_id_decode1(asn1, &tag);
1746 GSM_SS_PARAM_DISPLAY(subtree, saved_offset, tag, GSM_SS_P_USSD_STRING, "USSD String");
1748 rem_len = len - (asn1->offset - start_offset);
1752 op_generic_ss(asn1, subtree, rem_len);
1757 saved_offset = asn1->offset;
1758 asn1_eoc_decode(asn1, -1);
1760 proto_tree_add_text(subtree, asn1->tvb,
1761 saved_offset, asn1->offset - saved_offset, "End of Contents");
1766 param_ussdRes(ASN1_SCK *asn1, proto_tree *tree)
1768 guint saved_offset, start_offset;
1769 guint tag, len, rem_len;
1770 gboolean def_len = FALSE;
1771 proto_tree *subtree;
1773 saved_offset = asn1->offset;
1774 asn1_id_decode1(asn1, &tag);
1776 GSM_SS_START_SUBTREE(tree, saved_offset, tag, "Sequence",
1777 gsm_ss_ett[GSM_SS_ETT_SEQUENCE],
1778 &def_len, &len, subtree);
1780 start_offset = asn1->offset;
1782 saved_offset = asn1->offset;
1783 asn1_id_decode1(asn1, &tag);
1785 GSM_SS_PARAM_DISPLAY(subtree, saved_offset, tag, GSM_SS_P_USSD_DCS, "USSD Data Coding Scheme");
1787 saved_offset = asn1->offset;
1788 asn1_id_decode1(asn1, &tag);
1790 GSM_SS_PARAM_DISPLAY(subtree, saved_offset, tag, GSM_SS_P_USSD_STRING, "USSD String");
1792 rem_len = len - (asn1->offset - start_offset);
1796 op_generic_ss(asn1, subtree, rem_len);
1801 saved_offset = asn1->offset;
1802 asn1_eoc_decode(asn1, -1);
1804 proto_tree_add_text(subtree, asn1->tvb,
1805 saved_offset, asn1->offset - saved_offset, "End of Contents");
1813 op_generic_ss(ASN1_SCK *asn1, proto_tree *tree, guint exp_len)
1815 guint orig_offset, saved_offset, len_offset;
1817 gboolean def_len = FALSE;
1819 proto_tree *subtree;
1821 orig_offset = asn1->offset;
1823 while ((tvb_length_remaining(asn1->tvb, asn1->offset) > 0) &&
1824 (!tcap_check_tag(asn1, 0)))
1826 if ((exp_len != 0) &&
1827 ((asn1->offset - orig_offset) >= exp_len))
1832 saved_offset = asn1->offset;
1833 asn1_id_decode1(asn1, &tag);
1835 if (TCAP_CONSTRUCTOR(tag))
1837 GSM_SS_START_SUBTREE(tree, saved_offset, tag, "Sequence",
1838 gsm_ss_ett[GSM_SS_ETT_SEQUENCE],
1839 &def_len, &len, subtree);
1841 op_generic_ss(asn1, subtree, len);
1845 saved_offset = asn1->offset;
1846 asn1_eoc_decode(asn1, -1);
1848 proto_tree_add_text(subtree, asn1->tvb,
1849 saved_offset, asn1->offset - saved_offset, "End of Contents");
1854 len_offset = asn1->offset;
1855 asn1_length_decode(asn1, &def_len, &len);
1859 proto_tree_add_text(tree, asn1->tvb,
1860 saved_offset, len_offset - saved_offset,
1861 "Tag: 0x%02x", tag);
1863 proto_tree_add_text(tree, asn1->tvb,
1864 len_offset, asn1->offset - len_offset, "Length: Indefinite");
1866 len = tcap_find_eoc(asn1);
1868 op_generic_ss(asn1, tree, len);
1870 saved_offset = asn1->offset;
1871 asn1_eoc_decode(asn1, -1);
1873 proto_tree_add_text(tree, asn1->tvb,
1874 saved_offset, asn1->offset - saved_offset, "End of Contents");
1879 proto_tree_add_text(tree, asn1->tvb,
1880 saved_offset, (asn1->offset - saved_offset) + len, "Parameter");
1882 subtree = proto_item_add_subtree(item, gsm_ss_ett[GSM_SS_ETT_PARAM]);
1884 proto_tree_add_text(subtree, asn1->tvb,
1885 saved_offset, len_offset - saved_offset,
1886 "Tag: 0x%02x", tag);
1888 proto_tree_add_text(subtree, asn1->tvb,
1889 len_offset, asn1->offset - len_offset, "Length: %d", len);
1893 proto_tree_add_text(subtree, asn1->tvb,
1894 asn1->offset, len, "Parameter Data");
1896 asn1->offset += len;
1902 op_register_ss(ASN1_SCK *asn1, proto_tree *tree, guint exp_len)
1904 guint saved_offset, start_offset;
1905 guint tag, len, rem_len;
1906 gboolean def_len = FALSE;
1907 proto_tree *subtree;
1911 if (tvb_length_remaining(asn1->tvb, asn1->offset) <= 0) return;
1913 saved_offset = asn1->offset;
1914 asn1_id_decode1(asn1, &tag);
1916 GSM_SS_START_SUBTREE(tree, saved_offset, tag, "Sequence",
1917 gsm_ss_ett[GSM_SS_ETT_SEQUENCE],
1918 &def_len, &len, subtree);
1920 start_offset = asn1->offset;
1922 saved_offset = asn1->offset;
1923 asn1_id_decode1(asn1, &tag);
1925 GSM_SS_PARAM_DISPLAY(subtree, saved_offset, tag, GSM_SS_P_SS_CODE, "SS-Code");
1927 if (tcap_check_tag(asn1, 0x82))
1929 saved_offset = asn1->offset;
1930 asn1_id_decode1(asn1, &tag);
1932 GSM_SS_PARAM_DISPLAY(subtree, saved_offset, tag, GSM_SS_P_BEARERSERVICE, "Bearerservice");
1935 if (tcap_check_tag(asn1, 0x83))
1937 saved_offset = asn1->offset;
1938 asn1_id_decode1(asn1, &tag);
1940 GSM_SS_PARAM_DISPLAY(subtree, saved_offset, tag, GSM_SS_P_TELESERVICE, "Teleservice");
1943 if (tcap_check_tag(asn1, 0x84))
1945 saved_offset = asn1->offset;
1946 asn1_id_decode1(asn1, &tag);
1948 GSM_SS_PARAM_DISPLAY(subtree, saved_offset, tag, GSM_SS_P_FORWARD_TO_NUM, "Forwarded to Number");
1951 if (tcap_check_tag(asn1, 0x86))
1953 saved_offset = asn1->offset;
1954 asn1_id_decode1(asn1, &tag);
1956 GSM_SS_PARAM_DISPLAY(subtree, saved_offset, tag, GSM_SS_P_NONE, "Forwarded to Subaddress");
1959 if (tcap_check_tag(asn1, 0x85))
1961 saved_offset = asn1->offset;
1962 asn1_id_decode1(asn1, &tag);
1964 GSM_SS_PARAM_DISPLAY(subtree, saved_offset, tag, GSM_SS_P_NONE, "No Reply Condition Time");
1967 if (tcap_check_tag(asn1, 0x87))
1969 saved_offset = asn1->offset;
1970 asn1_id_decode1(asn1, &tag);
1972 GSM_SS_PARAM_DISPLAY(subtree, saved_offset, tag, GSM_SS_P_NONE, "Default Priority");
1975 if (tcap_check_tag(asn1, 0x88))
1977 saved_offset = asn1->offset;
1978 asn1_id_decode1(asn1, &tag);
1980 GSM_SS_PARAM_DISPLAY(subtree, saved_offset, tag, GSM_SS_P_NONE, "Number Users");
1983 if (tcap_check_tag(asn1, 0x89))
1985 saved_offset = asn1->offset;
1986 asn1_id_decode1(asn1, &tag);
1988 GSM_SS_PARAM_DISPLAY(subtree, saved_offset, tag, GSM_SS_P_NONE, "Long FTN supported");
1991 rem_len = len - (asn1->offset - start_offset);
1995 op_generic_ss(asn1, subtree, rem_len);
2000 saved_offset = asn1->offset;
2001 asn1_eoc_decode(asn1, -1);
2003 proto_tree_add_text(subtree, asn1->tvb,
2004 saved_offset, asn1->offset - saved_offset, "End of Contents");
2009 op_register_ss_rr(ASN1_SCK *asn1, proto_tree *tree, guint exp_len)
2015 if (tvb_length_remaining(asn1->tvb, asn1->offset) <= 0) return;
2017 saved_offset = asn1->offset;
2019 param_ssInfo(asn1, tree);
2023 op_erase_ss(ASN1_SCK *asn1, proto_tree *tree, guint exp_len)
2029 if (tvb_length_remaining(asn1->tvb, asn1->offset) <= 0) return;
2031 saved_offset = asn1->offset;
2033 param_ssForBS(asn1, tree);
2037 op_erase_ss_rr(ASN1_SCK *asn1, proto_tree *tree, guint exp_len)
2043 if (tvb_length_remaining(asn1->tvb, asn1->offset) <= 0) return;
2045 saved_offset = asn1->offset;
2047 param_ssInfo(asn1, tree);
2051 op_activate_ss(ASN1_SCK *asn1, proto_tree *tree, guint exp_len)
2057 if (tvb_length_remaining(asn1->tvb, asn1->offset) <= 0) return;
2059 saved_offset = asn1->offset;
2061 param_ssForBS(asn1, tree);
2065 op_activate_ss_rr(ASN1_SCK *asn1, proto_tree *tree, guint exp_len)
2071 if (tvb_length_remaining(asn1->tvb, asn1->offset) <= 0) return;
2073 saved_offset = asn1->offset;
2075 param_ssInfo(asn1, tree);
2079 op_deactivate_ss(ASN1_SCK *asn1, proto_tree *tree, guint exp_len)
2085 if (tvb_length_remaining(asn1->tvb, asn1->offset) <= 0) return;
2087 saved_offset = asn1->offset;
2089 param_ssForBS(asn1, tree);
2093 op_deactivate_ss_rr(ASN1_SCK *asn1, proto_tree *tree, guint exp_len)
2099 if (tvb_length_remaining(asn1->tvb, asn1->offset) <= 0) return;
2101 saved_offset = asn1->offset;
2103 param_ssInfo(asn1, tree);
2107 op_interrogate_ss(ASN1_SCK *asn1, proto_tree *tree, guint exp_len)
2113 if (tvb_length_remaining(asn1->tvb, asn1->offset) <= 0) return;
2115 saved_offset = asn1->offset;
2117 param_ssForBS(asn1, tree);
2121 op_interrogate_ss_rr(ASN1_SCK *asn1, proto_tree *tree, guint exp_len)
2128 if (tvb_length_remaining(asn1->tvb, asn1->offset) <= 0) return;
2130 saved_offset = asn1->offset;
2131 asn1_id_decode1(asn1, &tag);
2135 case 0x80: /* SS-Status */
2136 GSM_SS_PARAM_DISPLAY(tree, saved_offset, tag, GSM_SS_P_SS_STATUS, "SS-Status");
2139 case 0x82: /* BasicServiceGroupList */
2141 asn1->offset = saved_offset;
2142 op_generic_ss(asn1, tree, exp_len);
2145 case 0x83: /* ForwardingFeatureList */
2146 asn1->offset = saved_offset;
2147 param_forwardingFeatureList(asn1, tree, exp_len);
2150 case 0x84: /* GenericServiceInfo */
2152 asn1->offset = saved_offset;
2153 op_generic_ss(asn1, tree, exp_len);
2157 asn1->offset = saved_offset;
2158 op_generic_ss(asn1, tree, exp_len);
2164 op_reg_password(ASN1_SCK *asn1, proto_tree *tree, guint exp_len)
2171 if (tvb_length_remaining(asn1->tvb, asn1->offset) <= 0) return;
2173 saved_offset = asn1->offset;
2174 asn1_id_decode1(asn1, &tag);
2176 GSM_SS_PARAM_DISPLAY(tree, saved_offset, tag, GSM_SS_P_SS_CODE, "SS-Code");
2178 rem_len = exp_len - (asn1->offset - saved_offset);
2182 op_generic_ss(asn1, tree, rem_len);
2187 op_reg_password_rr(ASN1_SCK *asn1, proto_tree *tree, guint exp_len)
2194 if (tvb_length_remaining(asn1->tvb, asn1->offset) <= 0) return;
2196 saved_offset = asn1->offset;
2197 asn1_id_decode1(asn1, &tag);
2199 GSM_SS_PARAM_DISPLAY(tree, saved_offset, tag, GSM_SS_P_PASSWORD, "New Password");
2201 rem_len = exp_len - (asn1->offset - saved_offset);
2205 op_generic_ss(asn1, tree, rem_len);
2210 op_get_password(ASN1_SCK *asn1, proto_tree *tree, guint exp_len)
2217 if (tvb_length_remaining(asn1->tvb, asn1->offset) <= 0) return;
2219 saved_offset = asn1->offset;
2220 asn1_id_decode1(asn1, &tag);
2222 GSM_SS_PARAM_DISPLAY(tree, saved_offset, tag, GSM_SS_P_GUIDANCE_INFO, "Guidance Info");
2224 rem_len = exp_len - (asn1->offset - saved_offset);
2228 op_generic_ss(asn1, tree, rem_len);
2233 op_get_password_rr(ASN1_SCK *asn1, proto_tree *tree, guint exp_len)
2240 if (tvb_length_remaining(asn1->tvb, asn1->offset) <= 0) return;
2242 saved_offset = asn1->offset;
2243 asn1_id_decode1(asn1, &tag);
2245 GSM_SS_PARAM_DISPLAY(tree, saved_offset, tag, GSM_SS_P_PASSWORD, "Current Password");
2247 rem_len = exp_len - (asn1->offset - saved_offset);
2251 op_generic_ss(asn1, tree, rem_len);
2256 op_proc_uss_data(ASN1_SCK *asn1, proto_tree *tree, guint exp_len)
2263 if (tvb_length_remaining(asn1->tvb, asn1->offset) <= 0) return;
2265 saved_offset = asn1->offset;
2267 if (tcap_check_tag(asn1, 0x16))
2269 saved_offset = asn1->offset;
2270 asn1_id_decode1(asn1, &tag);
2272 GSM_SS_PARAM_DISPLAY(tree, saved_offset, tag, GSM_SS_P_IA5_STRING, "SS-UserData");
2275 rem_len = exp_len - (asn1->offset - saved_offset);
2279 op_generic_ss(asn1, tree, rem_len);
2284 op_proc_uss_data_rr(ASN1_SCK *asn1, proto_tree *tree, guint exp_len)
2291 if (tvb_length_remaining(asn1->tvb, asn1->offset) <= 0) return;
2293 saved_offset = asn1->offset;
2295 if (tcap_check_tag(asn1, 0x16))
2297 saved_offset = asn1->offset;
2298 asn1_id_decode1(asn1, &tag);
2300 GSM_SS_PARAM_DISPLAY(tree, saved_offset, tag, GSM_SS_P_IA5_STRING, "SS-UserData");
2303 rem_len = exp_len - (asn1->offset - saved_offset);
2307 op_generic_ss(asn1, tree, rem_len);
2312 op_proc_uss_req(ASN1_SCK *asn1, proto_tree *tree, guint exp_len)
2318 if (tvb_length_remaining(asn1->tvb, asn1->offset) <= 0) return;
2320 saved_offset = asn1->offset;
2322 param_ussdArg(asn1, tree);
2326 op_proc_uss_req_rr(ASN1_SCK *asn1, proto_tree *tree, guint exp_len)
2332 if (tvb_length_remaining(asn1->tvb, asn1->offset) <= 0) return;
2334 saved_offset = asn1->offset;
2336 param_ussdRes(asn1, tree);
2340 op_uss_req(ASN1_SCK *asn1, proto_tree *tree, guint exp_len)
2346 if (tvb_length_remaining(asn1->tvb, asn1->offset) <= 0) return;
2348 saved_offset = asn1->offset;
2350 param_ussdArg(asn1, tree);
2354 op_uss_req_rr(ASN1_SCK *asn1, proto_tree *tree, guint exp_len)
2360 if (tvb_length_remaining(asn1->tvb, asn1->offset) <= 0) return;
2362 saved_offset = asn1->offset;
2364 param_ussdRes(asn1, tree);
2368 op_uss_notify(ASN1_SCK *asn1, proto_tree *tree, guint exp_len)
2374 if (tvb_length_remaining(asn1->tvb, asn1->offset) <= 0) return;
2376 saved_offset = asn1->offset;
2378 param_ussdArg(asn1, tree);
2381 #define GSM_SS_NUM_OP (sizeof(gsm_ss_opr_code_strings)/sizeof(value_string))
2382 static void (*op_fcn[])(ASN1_SCK *asn1, proto_tree *tree, guint exp_len) = {
2383 op_register_ss, /* RegisterSS */
2384 op_erase_ss, /* EraseSS */
2385 op_activate_ss, /* ActivateSS */
2386 op_deactivate_ss, /* DeactivateSS */
2387 op_interrogate_ss, /* InterrogateSS */
2388 NULL, /* NotifySS */
2389 op_reg_password, /* RegisterPassword */
2390 op_get_password, /* GetPassword */
2391 op_proc_uss_data, /* ProcessUnstructuredSS-Data */
2392 NULL, /* ForwardCheckSS-Indication */
2393 op_proc_uss_req, /* ProcessUnstructuredSS-Request */
2394 op_uss_req, /* UnstructuredSS-Request */
2395 op_uss_notify, /* UnstructuredSS-Notify */
2396 NULL, /* EraseCC-Entry */
2397 NULL, /* LCS-LocationNotification */
2398 NULL, /* LCS-MOLR */
2399 NULL, /* AccessRegisterCCEntry */
2400 NULL, /* ForwardCUG-Info */
2401 NULL /* NO ARGS */, /* SplitMPTY */
2402 NULL /* NO ARGS */, /* RetrieveMPTY */
2403 NULL /* NO ARGS */, /* HoldMPTY */
2404 NULL /* NO ARGS */, /* BuildMPTY */
2405 NULL, /* ForwardChargeAdvice */
2406 NULL, /* ExplicitCT */
2407 NULL, /* LCS-LocationNotification */
2408 NULL, /* LCS-MOLR */
2413 static void (*op_fcn_rr[])(ASN1_SCK *asn1, proto_tree *tree, guint exp_len) = {
2414 op_register_ss_rr, /* RegisterSS */
2415 op_erase_ss_rr, /* EraseSS */
2416 op_activate_ss_rr, /* ActivateSS */
2417 op_deactivate_ss_rr, /* DeactivateSS */
2418 op_interrogate_ss_rr, /* InterrogateSS */
2419 NULL, /* NotifySS */
2420 op_reg_password_rr, /* RegisterPassword */
2421 op_get_password_rr, /* GetPassword */
2422 op_proc_uss_data_rr, /* ProcessUnstructuredSS-Data */
2423 NULL, /* ForwardCheckSS-Indication */
2424 op_proc_uss_req_rr, /* ProcessUnstructuredSS-Request */
2425 op_uss_req_rr, /* UnstructuredSS-Request */
2426 NULL /* NO ARGS */, /* UnstructuredSS-Notify */
2427 NULL, /* EraseCC-Entry */
2428 NULL, /* LCS Location Notification */
2429 NULL, /* LCS MOLR */
2430 NULL, /* AccessRegisterCCEntry */
2431 NULL, /* ForwardCUG-Info */
2432 NULL, /* SplitMPTY */
2433 NULL, /* RetrieveMPTY */
2434 NULL, /* HoldMPTY */
2435 NULL, /* BuildMPTY */
2436 NULL /* NO ARGS */, /* ForwardChargeAdvice */
2437 NULL, /* ExplicitCT */
2438 NULL, /* LCS-LocationNotification */
2439 NULL, /* LCS-MOLR */
2445 gsm_ss_dissect(ASN1_SCK *asn1, proto_tree *tree, guint exp_len,
2446 guint opr_code, guint comp_type_tag)
2448 void (*dissect_fcn)(ASN1_SCK *asn1, proto_tree *tree, guint exp_len);
2455 str = my_match_strval(opr_code, gsm_ss_opr_code_strings, &op_idx);
2459 switch (comp_type_tag)
2461 case TCAP_COMP_INVOKE:
2462 dissect_fcn = op_fcn[op_idx];
2466 dissect_fcn = op_fcn_rr[op_idx];
2475 * no parameters should be present in the component types
2482 if (dissect_fcn == NULL)
2484 op_generic_ss(asn1, tree, exp_len);
2488 (*dissect_fcn)(asn1, tree, exp_len);