2008-08-24 17:42:30 +00:00
/* packet-gsm_a_gm.c
* Routines for GSM A Interface GPRS Mobilty Management and GPRS Session Management
*
* Copyright 2003 , Michael Lum < mlum [ AT ] telostech . com >
* In association with Telos Technology Inc .
*
* Added the GPRS Mobility Managment Protocol and
* the GPRS Session Managment Protocol
* Copyright 2004 , Rene Pilz < rene . pilz [ AT ] ftw . com >
* In association with Telecommunications Research Center
* Vienna ( ftw . ) Betriebs - GmbH within the Project Metawin .
*
* Title 3 GPP Other
*
* Reference [ 7 ]
* Mobile radio interface Layer 3 specification ;
* Core network protocols ;
* Stage 3
* ( 3 GPP TS 24.008 version 5.9 .0 Release 5 )
*
* Reference [ 8 ]
* Mobile radio interface Layer 3 specification ;
* Core network protocols ;
* Stage 3
* ( 3 GPP TS 24.008 version 6.7 .0 Release 6 )
* ( 3 GPP TS 24.008 version 6.8 .0 Release 6 )
*
* $ Id $
*
* Wireshark - Network traffic analyzer
* By Gerald Combs < gerald @ wireshark . org >
* Copyright 1998 Gerald Combs
*
* This program is free software ; you can redistribute it and / or
* modify it under the terms of the GNU General Public License
* as published by the Free Software Foundation ; either version 2
* of the License , or ( at your option ) any later version .
*
* This program is distributed in the hope that it will be useful ,
* but WITHOUT ANY WARRANTY ; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE . See the
* GNU General Public License for more details .
*
* You should have received a copy of the GNU General Public License
* along with this program ; if not , write to the Free Software
* Foundation , Inc . , 59 Temple Place - Suite 330 , Boston , MA 02111 - 1307 , USA .
*/
# ifdef HAVE_CONFIG_H
# include "config.h"
# endif
# include <stdio.h>
# include <stdlib.h>
# include <string.h>
# include <epan/packet.h>
# include <epan/prefs.h>
# include <epan/tap.h>
# include <epan/asn1.h>
# include "packet-bssap.h"
# include "packet-sccp.h"
# include "packet-ber.h"
# include "packet-q931.h"
# include "packet-gsm_a_common.h"
# include "packet-ipv6.h"
# include "packet-e212.h"
# include "packet-ppp.h"
/* PROTOTYPES/FORWARDS */
const value_string gsm_a_dtap_msg_gmm_strings [ ] = {
{ 0x01 , " Attach Request " } ,
{ 0x02 , " Attach Accept " } ,
{ 0x03 , " Attach Complete " } ,
{ 0x04 , " Attach Reject " } ,
{ 0x05 , " Detach Request " } ,
{ 0x06 , " Detach Accept " } ,
{ 0x08 , " Routing Area Update Request " } ,
{ 0x09 , " Routing Area Update Accept " } ,
{ 0x0a , " Routing Area Update Complete " } ,
{ 0x0b , " Routing Area Update Reject " } ,
{ 0x0c , " Service Request " } ,
{ 0x0d , " Service Accept " } ,
{ 0x0e , " Service Reject " } ,
{ 0x10 , " P-TMSI Reallocation Command " } ,
{ 0x11 , " P-TMSI Reallocation Complete " } ,
{ 0x12 , " Authentication and Ciphering Req " } ,
{ 0x13 , " Authentication and Ciphering Resp " } ,
{ 0x14 , " Authentication and Ciphering Rej " } ,
{ 0x1c , " Authentication and Ciphering Failure " } ,
{ 0x15 , " Identity Request " } ,
{ 0x16 , " Identity Response " } ,
{ 0x20 , " GMM Status " } ,
{ 0x21 , " GMM Information " } ,
{ 0 , NULL }
} ;
const value_string gsm_a_dtap_msg_sm_strings [ ] = {
{ 0x41 , " Activate PDP Context Request " } ,
{ 0x42 , " Activate PDP Context Accept " } ,
{ 0x43 , " Activate PDP Context Reject " } ,
{ 0x44 , " Request PDP Context Activation " } ,
{ 0x45 , " Request PDP Context Activation rej. " } ,
{ 0x46 , " Deactivate PDP Context Request " } ,
{ 0x47 , " Deactivate PDP Context Accept " } ,
{ 0x48 , " Modify PDP Context Request(Network to MS direction) " } ,
{ 0x49 , " Modify PDP Context Accept (MS to network direction) " } ,
{ 0x4a , " Modify PDP Context Request(MS to network direction) " } ,
{ 0x4b , " Modify PDP Context Accept (Network to MS direction) " } ,
{ 0x4c , " Modify PDP Context Reject " } ,
{ 0x4d , " Activate Secondary PDP Context Request " } ,
{ 0x4e , " Activate Secondary PDP Context Accept " } ,
{ 0x4f , " Activate Secondary PDP Context Reject " } ,
{ 0x50 , " Reserved: was allocated in earlier phases of the protocol " } ,
{ 0x51 , " Reserved: was allocated in earlier phases of the protocol " } ,
{ 0x52 , " Reserved: was allocated in earlier phases of the protocol " } ,
{ 0x53 , " Reserved: was allocated in earlier phases of the protocol " } ,
{ 0x54 , " Reserved: was allocated in earlier phases of the protocol " } ,
{ 0x55 , " SM Status " } ,
{ 0x56 , " Activate MBMS Context Request " } ,
{ 0x57 , " Activate MBMS Context Accept " } ,
{ 0x58 , " Activate MBMS Context Reject " } ,
{ 0x59 , " Request MBMS Context Activation " } ,
{ 0x5a , " Request MBMS Context Activation Reject " } ,
{ 0 , NULL }
} ;
const value_string gsm_gm_elem_strings [ ] = {
/* GPRS Mobility Management Information Elements 10.5.5 */
{ 0x00 , " Attach Result " } ,
{ 0x00 , " Attach Type " } ,
{ 0x00 , " Cipher Algorithm " } ,
{ 0x00 , " TMSI Status " } ,
{ 0x00 , " Detach Type " } ,
{ 0x00 , " DRX Parameter " } ,
{ 0x00 , " Force to Standby " } ,
{ 0x00 , " Force to Standby " } ,
{ 0x00 , " P-TMSI Signature " } ,
{ 0x00 , " P-TMSI Signature 2 " } ,
{ 0x00 , " Identity Type 2 " } ,
{ 0x00 , " IMEISV Request " } ,
{ 0x00 , " Receive N-PDU Numbers List " } ,
{ 0x00 , " MS Network Capability " } ,
{ 0x00 , " MS Radio Access Capability " } ,
{ 0x00 , " GMM Cause " } ,
{ 0x00 , " Routing Area Identification " } ,
{ 0x00 , " Update Result " } ,
{ 0x00 , " Update Type " } ,
{ 0x00 , " A&C Reference Number " } ,
{ 0x00 , " A&C Reference Number " } ,
{ 0x00 , " Service Type " } ,
{ 0x00 , " Cell Notification " } ,
{ 0x00 , " PS LCS Capability " } ,
{ 0x00 , " Network Feature Support " } ,
{ 0x00 , " Inter RAT information container " } ,
/* Session Management Information Elements 10.5.6 */
{ 0x00 , " Access Point Name " } ,
{ 0x00 , " Network Service Access Point Identifier " } ,
{ 0x00 , " Protocol Configuration Options " } ,
{ 0x00 , " Packet Data Protocol Address " } ,
{ 0x00 , " Quality Of Service " } ,
{ 0x00 , " SM Cause " } ,
{ 0x00 , " Linked TI " } ,
{ 0x00 , " LLC Service Access Point Identifier " } ,
{ 0x00 , " Tear Down Indicator " } ,
{ 0x00 , " Packet Flow Identifier " } ,
{ 0x00 , " Traffic Flow Template " } ,
/* GPRS Common Information Elements 10.5.7 */
{ 0x00 , " PDP Context Status " } ,
{ 0x00 , " Radio Priority " } ,
{ 0x00 , " GPRS Timer " } ,
{ 0x00 , " GPRS Timer 2 " } ,
{ 0x00 , " Radio Priority 2 " } ,
{ 0x00 , " MBMS context status " } ,
{ 0x00 , " Spare Nibble " } ,
{ 0 , NULL }
} ;
# define DTAP_GMM_IEI_MASK 0xff
# define DTAP_SM_IEI_MASK 0xff
/* Initialize the protocol and registered fields */
static int proto_a_gm = - 1 ;
static int hf_gsm_a_dtap_msg_gmm_type = - 1 ;
static int hf_gsm_a_dtap_msg_sm_type = - 1 ;
int hf_gsm_a_gm_elem_id = - 1 ;
static int hf_gsm_a_qos_delay_cls = - 1 ;
static int hf_gsm_a_qos_qos_reliability_cls = - 1 ;
static int hf_gsm_a_qos_traffic_cls = - 1 ;
static int hf_gsm_a_qos_del_order = - 1 ;
static int hf_gsm_a_qos_del_of_err_sdu = - 1 ;
static int hf_gsm_a_qos_ber = - 1 ;
static int hf_gsm_a_qos_sdu_err_rat = - 1 ;
static int hf_gsm_a_qos_traff_hdl_pri = - 1 ;
static int hf_gsm_a_gmm_split_on_ccch = - 1 ;
static int hf_gsm_a_gmm_non_drx_timer = - 1 ;
static int hf_gsm_a_gmm_cn_spec_drs_cycle_len_coef = - 1 ;
static int hf_gsm_a_ptmsi_sig = - 1 ;
static int hf_gsm_a_ptmsi_sig2 = - 1 ;
static int hf_gsm_a_tft_op_code = - 1 ;
static int hf_gsm_a_tft_e_bit = - 1 ;
static int hf_gsm_a_tft_pkt_flt = - 1 ;
static int hf_gsm_a_tft_ip4_address = - 1 ;
static int hf_gsm_a_tft_ip4_mask = - 1 ;
static int hf_gsm_a_tft_ip6_address = - 1 ;
static int hf_gsm_a_tft_ip6_mask = - 1 ;
static int hf_gsm_a_tft_protocol_header = - 1 ;
static int hf_gsm_a_tft_port = - 1 ;
static int hf_gsm_a_tft_port_low = - 1 ;
static int hf_gsm_a_tft_port_high = - 1 ;
static int hf_gsm_a_tft_security = - 1 ;
static int hf_gsm_a_tft_traffic_mask = - 1 ;
2009-05-14 18:26:18 +00:00
static int hf_gsm_a_gm_acc_tech_type = - 1 ;
static int hf_gsm_a_gm_acc_cap_struct_len = - 1 ;
static int hf_gsm_a_gm_sms_value = - 1 ;
static int hf_gsm_a_gm_sm_value = - 1 ;
2008-08-24 17:42:30 +00:00
/* Initialize the subtree pointers */
static gint ett_tc_component = - 1 ;
static gint ett_tc_invoke_id = - 1 ;
static gint ett_tc_linked_id = - 1 ;
static gint ett_tc_opr_code = - 1 ;
static gint ett_tc_err_code = - 1 ;
static gint ett_tc_prob_code = - 1 ;
static gint ett_tc_sequence = - 1 ;
static gint ett_gmm_drx = - 1 ;
static gint ett_gmm_detach_type = - 1 ;
static gint ett_gmm_attach_type = - 1 ;
static gint ett_gmm_context_stat = - 1 ;
static gint ett_gmm_update_type = - 1 ;
static gint ett_gmm_radio_cap = - 1 ;
static gint ett_gmm_rai = - 1 ;
static gint ett_sm_tft = - 1 ;
static dissector_handle_t data_handle ;
2008-11-17 19:41:44 +00:00
static dissector_handle_t rrc_irat_ho_info_handle ;
2008-08-24 17:42:30 +00:00
static dissector_table_t gprs_sm_pco_subdissector_table ; /* GPRS SM PCO PPP Protocols */
# define NUM_GSM_GM_ELEM (sizeof(gsm_gm_elem_strings) / sizeof(value_string))
gint ett_gsm_gm_elem [ NUM_GSM_GM_ELEM ] ;
2008-11-17 19:41:44 +00:00
const gchar pdp_str [ 2 ] [ 20 ] = { " PDP-INACTIVE " , " PDP-ACTIVE " } ;
2008-08-24 17:42:30 +00:00
/*
* [ 7 ] 10.5 .5 .1
*/
2008-12-23 20:49:15 +00:00
static guint16
2008-09-05 05:49:39 +00:00
de_gmm_attach_res ( tvbuff_t * tvb , proto_tree * tree , guint32 offset , guint len _U_ , gchar * add_string _U_ , int string_len _U_ )
2008-08-24 17:42:30 +00:00
{
2009-05-07 21:22:36 +00:00
guint8 oct ;
guint32 curr_offset ;
const gchar * str ;
2008-08-24 17:42:30 +00:00
curr_offset = offset ;
oct = tvb_get_guint8 ( tvb , curr_offset ) ;
switch ( oct & 7 )
{
2009-05-07 21:22:36 +00:00
case 1 : str = " GPRS only attached " ; break ;
case 3 : str = " Combined GPRS/IMSI attached " ; break ;
2008-08-24 17:42:30 +00:00
default : str = " reserved " ;
}
proto_tree_add_text ( tree ,
2008-09-05 05:49:39 +00:00
tvb , curr_offset , 1 ,
" Attach Result: (%u) %s " ,
oct & 7 ,
str ) ;
2008-08-24 17:42:30 +00:00
curr_offset + + ;
/* no length check possible */
return ( curr_offset - offset ) ;
}
/*
* [ 7 ] 10.5 .5 .2
*/
2008-12-23 20:49:15 +00:00
static guint16
2008-09-05 05:49:39 +00:00
de_gmm_attach_type ( tvbuff_t * tvb , proto_tree * tree , guint32 offset , guint len _U_ , gchar * add_string _U_ , int string_len _U_ )
2008-08-24 17:42:30 +00:00
{
2009-05-07 21:22:36 +00:00
guint8 oct ;
guint8 oct_ciph ;
guint32 curr_offset ;
const gchar * str_follow ;
const gchar * str_attach ;
proto_item * tf = NULL ;
proto_tree * tf_tree = NULL ;
2008-08-24 17:42:30 +00:00
curr_offset = offset ;
oct = tvb_get_guint8 ( tvb , curr_offset ) ;
oct_ciph = oct > > 4 ;
oct & = 0x0f ;
switch ( oct & 7 )
{
2009-05-07 21:22:36 +00:00
case 1 : str_attach = " GPRS attach " ; break ;
case 2 : str_attach = " GPRS attach while IMSI attached " ; break ;
case 3 : str_attach = " Combined GPRS/IMSI attach " ; break ;
2008-08-24 17:42:30 +00:00
default : str_attach = " reserved " ;
}
switch ( oct & 8 )
{
2009-05-07 21:22:36 +00:00
case 8 : str_follow = " Follow-on request pending " ; break ;
2008-08-24 17:42:30 +00:00
default : str_follow = " No follow-on request pending " ;
}
tf = proto_tree_add_text ( tree ,
tvb , curr_offset , 1 ,
" Attach Type " ) ;
tf_tree = proto_item_add_subtree ( tf , ett_gmm_attach_type ) ;
proto_tree_add_text ( tf_tree ,
2008-09-05 05:49:39 +00:00
tvb , curr_offset , 1 ,
" Type: (%u) %s " ,
oct & 7 ,
str_attach ) ;
2008-08-24 17:42:30 +00:00
proto_tree_add_text ( tf_tree ,
2008-09-05 05:49:39 +00:00
tvb , curr_offset , 1 ,
" Follow: (%u) %s " ,
( oct > > 3 ) & 1 ,
str_follow ) ;
2008-08-24 17:42:30 +00:00
/* The ciphering key sequence number is added here */
proto_tree_add_text ( tree ,
2008-09-05 05:49:39 +00:00
tvb , curr_offset , 1 ,
" Ciphering key sequence number: 0x%02x (%u) " ,
oct_ciph ,
oct_ciph ) ;
2008-08-24 17:42:30 +00:00
curr_offset + + ;
/* no length check possible */
return ( curr_offset - offset ) ;
}
/*
* [ 7 ] 10.5 .5 .3
*/
2008-12-23 20:49:15 +00:00
static guint16
2008-09-05 05:49:39 +00:00
de_gmm_ciph_alg ( tvbuff_t * tvb , proto_tree * tree , guint32 offset , guint len _U_ , gchar * add_string _U_ , int string_len _U_ )
2008-08-24 17:42:30 +00:00
{
2009-05-07 21:22:36 +00:00
guint8 oct ;
guint32 curr_offset ;
const gchar * str ;
2008-08-24 17:42:30 +00:00
curr_offset = offset ;
oct = tvb_get_guint8 ( tvb , curr_offset ) ;
switch ( oct & 7 )
{
2009-05-07 21:22:36 +00:00
case 0 : str = " ciphering not used " ; break ;
case 1 : str = " GPRS Encryption Algorithm GEA/1 " ; break ;
case 2 : str = " GPRS Encryption Algorithm GEA/2 " ; break ;
case 3 : str = " GPRS Encryption Algorithm GEA/3 " ; break ;
case 4 : str = " GPRS Encryption Algorithm GEA/4 " ; break ;
case 5 : str = " GPRS Encryption Algorithm GEA/5 " ; break ;
case 6 : str = " GPRS Encryption Algorithm GEA/6 " ; break ;
case 7 : str = " GPRS Encryption Algorithm GEA/7 " ; break ;
2008-08-24 17:42:30 +00:00
default : str = " This should never happen " ;
}
proto_tree_add_text ( tree ,
2008-09-05 05:49:39 +00:00
tvb , curr_offset , 1 ,
" Ciphering Algorithm: (%u) %s " ,
oct & 7 ,
str ) ;
2008-08-24 17:42:30 +00:00
curr_offset + + ;
/* no length check possible */
return ( curr_offset - offset ) ;
}
/*
* [ 7 ] 10.5 .5 .4
*/
2008-12-23 20:49:15 +00:00
static guint16
2008-09-05 05:49:39 +00:00
de_gmm_tmsi_stat ( tvbuff_t * tvb , proto_tree * tree , guint32 offset , guint len _U_ , gchar * add_string _U_ , int string_len _U_ )
2008-08-24 17:42:30 +00:00
{
2009-05-07 21:22:36 +00:00
guint8 oct ;
guint32 curr_offset ;
const gchar * str ;
2008-08-24 17:42:30 +00:00
curr_offset = offset ;
oct = tvb_get_guint8 ( tvb , curr_offset ) ;
switch ( oct & 1 )
{
2009-05-07 21:22:36 +00:00
case 0 : str = " no valid TMSI available " ; break ;
case 1 : str = " valid TMSI available " ; break ;
2008-08-24 17:42:30 +00:00
default : str = " This should never happen " ;
}
proto_tree_add_text ( tree ,
2008-09-05 05:49:39 +00:00
tvb , curr_offset , 1 ,
" TMSI Status: (%u) %s " ,
oct & 1 ,
str ) ;
2008-08-24 17:42:30 +00:00
2008-10-08 16:09:28 +00:00
curr_offset + + ;
2008-08-24 17:42:30 +00:00
/* no length check possible */
return ( curr_offset - offset ) ;
}
/*
* [ 7 ] 10.5 .5 .5
*/
2008-12-23 20:49:15 +00:00
static guint16
2008-09-05 05:49:39 +00:00
de_gmm_detach_type ( tvbuff_t * tvb , proto_tree * tree , guint32 offset , guint len _U_ , gchar * add_string _U_ , int string_len _U_ )
2008-08-24 17:42:30 +00:00
{
2009-05-07 21:22:36 +00:00
guint8 oct ;
guint32 curr_offset ;
const gchar * str ;
const gchar * str_power ;
proto_item * tf = NULL ;
proto_tree * tf_tree = NULL ;
2008-08-24 17:42:30 +00:00
curr_offset = offset ;
oct = tvb_get_guint8 ( tvb , curr_offset ) ;
switch ( oct & 7 )
{
2009-05-07 21:22:36 +00:00
case 1 : str = " GPRS detach/re-attach required " ; break ;
case 2 : str = " IMSI detach/re-attach not required " ; break ;
case 3 : str = " Combined GPRS/IMSI detach/IMSI detach (after VLR failure) " ; break ;
2008-08-24 17:42:30 +00:00
default : str = " Combined GPRS/IMSI detach/re-attach not required " ;
}
switch ( oct & 8 )
{
2009-05-07 21:22:36 +00:00
case 8 : str_power = " power switched off " ; break ;
default : str_power = " normal detach " ; break ;
2008-08-24 17:42:30 +00:00
}
tf = proto_tree_add_text ( tree ,
tvb , curr_offset , 1 ,
" Detach Type " ) ;
tf_tree = proto_item_add_subtree ( tf , ett_gmm_detach_type ) ;
proto_tree_add_text ( tf_tree ,
2008-09-05 05:49:39 +00:00
tvb , curr_offset , 1 ,
" Type: (%u) %s " ,
oct & 7 ,
str ) ;
2008-08-24 17:42:30 +00:00
proto_tree_add_text ( tf_tree ,
2008-09-05 05:49:39 +00:00
tvb , curr_offset , 1 ,
" Power: (%u) %s " ,
( oct > > 3 ) & 1 ,
str_power ) ;
2008-08-24 17:42:30 +00:00
curr_offset + + ;
/* no length check possible */
return ( curr_offset - offset ) ;
}
/*
* [ 7 ] 10.5 .5 .6
*
* SPLIT on CCCH , octet 3 ( bit 4 )
* 0 Split pg cycle on CCCH is not supported by the mobile station
* 1 Split pg cycle on CCCH is supported by the mobile station
*/
static const true_false_string gsm_a_gmm_split_on_ccch_value = {
2008-09-05 05:49:39 +00:00
" Split pg cycle on CCCH is supported by the mobile station " ,
" Split pg cycle on CCCH is not supported by the mobile station "
2008-08-24 17:42:30 +00:00
} ;
/* non-DRX timer, octet 3
* bit
* 3 2 1
*/
static const value_string gsm_a_gmm_non_drx_timer_strings [ ] = {
{ 0x00 , " no non-DRX mode after transfer state " } ,
{ 0x01 , " max. 1 sec non-DRX mode after transfer state " } ,
{ 0x02 , " max. 2 sec non-DRX mode after transfer state " } ,
{ 0x03 , " max. 4 sec non-DRX mode after transfer state " } ,
{ 0x04 , " max. 8 sec non-DRX mode after transfer state " } ,
{ 0x05 , " max. 16 sec non-DRX mode after transfer state " } ,
{ 0x06 , " max. 32 sec non-DRX mode after transfer state " } ,
{ 0x07 , " max. 64 sec non-DRX mode after transfer state " } ,
{ 0 , NULL } ,
} ;
/*
* CN Specific DRX cycle length coefficient , octet 3
* bit
* 8 7 6 5 Iu mode specific
* 0 0 0 0 CN Specific DRX cycle length coefficient not specified by the MS , ie . the
* system information value ' CN domain specific DRX cycle length ' is used .
* ( Ref 3 GPP TS 25.331 )
* 0 1 1 0 CN Specific DRX cycle length coefficient 6
* 0 1 1 1 CN Specific DRX cycle length coefficient 7
* 1 0 0 0 CN Specific DRX cycle length coefficient 8
* 1 0 0 1 CN Specific DRX cycle length coefficient 9
* All other values shall be interpreted as " CN Specific DRX cycle length coefficient not
* specified by the MS " by this version of the protocol.
* NOTE : In Iu mode this field ( octet 3 bits 8 to 5 ) is used , but was spare in earlier
* versions of this protocol .
*/
static const value_string gsm_a_gmm_cn_spec_drs_cycle_len_coef_strings [ ] = {
{ 0x00 , " CN Specific DRX cycle length coefficient not specified by the MS " } ,
{ 0x01 , " CN Specific DRX cycle length coefficient not specified by the MS " } ,
{ 0x02 , " CN Specific DRX cycle length coefficient not specified by the MS " } ,
{ 0x03 , " CN Specific DRX cycle length coefficient not specified by the MS " } ,
{ 0x04 , " CN Specific DRX cycle length coefficient not specified by the MS " } ,
{ 0x05 , " CN Specific DRX cycle length coefficient not specified by the MS " } ,
{ 0x06 , " CN Specific DRX cycle length coefficient 6 " } ,
{ 0x07 , " CN Specific DRX cycle length coefficient 7 " } ,
{ 0x08 , " CN Specific DRX cycle length coefficient 8 " } ,
{ 0x09 , " CN Specific DRX cycle length coefficient 9 " } ,
{ 0x0a , " CN Specific DRX cycle length coefficient not specified by the MS " } ,
{ 0x0b , " CN Specific DRX cycle length coefficient not specified by the MS " } ,
{ 0x0c , " CN Specific DRX cycle length coefficient not specified by the MS " } ,
{ 0x0d , " CN Specific DRX cycle length coefficient not specified by the MS " } ,
{ 0x0e , " CN Specific DRX cycle length coefficient not specified by the MS " } ,
{ 0x0f , " CN Specific DRX cycle length coefficient not specified by the MS " } ,
{ 0 , NULL } ,
} ;
2008-12-23 20:49:15 +00:00
guint16
2008-09-05 05:49:39 +00:00
de_gmm_drx_param ( tvbuff_t * tvb , proto_tree * tree , guint32 offset , guint len _U_ , gchar * add_string _U_ , int string_len _U_ )
2008-08-24 17:42:30 +00:00
{
2009-05-07 21:22:36 +00:00
guint8 oct ;
guint32 curr_offset ;
const gchar * str ;
gchar str_val [ 3 ] ;
proto_item * tf = NULL ;
proto_tree * tf_tree = NULL ;
2008-08-24 17:42:30 +00:00
curr_offset = offset ;
tf = proto_tree_add_text ( tree ,
tvb , curr_offset , 2 ,
" DRX Parameter " ) ;
tf_tree = proto_item_add_subtree ( tf , ett_gmm_drx ) ;
oct = tvb_get_guint8 ( tvb , curr_offset ) ;
switch ( oct )
{
2009-05-07 21:22:36 +00:00
case 0 : str = " 704 " ; break ;
case 65 : str = " 71 " ; break ;
case 66 : str = " 72 " ; break ;
case 67 : str = " 74 " ; break ;
case 68 : str = " 75 " ; break ;
case 69 : str = " 77 " ; break ;
case 70 : str = " 79 " ; break ;
case 71 : str = " 80 " ; break ;
case 72 : str = " 83 " ; break ;
case 73 : str = " 86 " ; break ;
case 74 : str = " 88 " ; break ;
case 75 : str = " 90 " ; break ;
case 76 : str = " 92 " ; break ;
case 77 : str = " 96 " ; break ;
2008-08-24 17:42:30 +00:00
case 78 : str = " 101 " ; break ;
case 79 : str = " 103 " ; break ;
case 80 : str = " 107 " ; break ;
case 81 : str = " 112 " ; break ;
case 82 : str = " 116 " ; break ;
case 83 : str = " 118 " ; break ;
case 84 : str = " 128 " ; break ;
case 85 : str = " 141 " ; break ;
case 86 : str = " 144 " ; break ;
case 87 : str = " 150 " ; break ;
case 88 : str = " 160 " ; break ;
case 89 : str = " 171 " ; break ;
case 90 : str = " 176 " ; break ;
case 91 : str = " 192 " ; break ;
case 92 : str = " 214 " ; break ;
case 93 : str = " 224 " ; break ;
case 94 : str = " 235 " ; break ;
case 95 : str = " 256 " ; break ;
case 96 : str = " 288 " ; break ;
case 97 : str = " 320 " ; break ;
case 98 : str = " 352 " ; break ;
2009-05-07 21:22:36 +00:00
default :
str_val [ 0 ] = oct / 10 + ' 0 ' ;
str_val [ 1 ] = oct % 10 + ' 0 ' ;
str_val [ 2 ] = 0 ;
str = str_val ;
2008-08-24 17:42:30 +00:00
}
proto_tree_add_text ( tf_tree ,
2008-09-05 05:49:39 +00:00
tvb , curr_offset , 1 ,
" Split PG Cycle Code: (%u) %s " ,
oct ,
str ) ;
2008-08-24 17:42:30 +00:00
curr_offset + + ;
proto_tree_add_item ( tf_tree , hf_gsm_a_gmm_cn_spec_drs_cycle_len_coef , tvb , curr_offset , 1 , FALSE ) ;
proto_tree_add_item ( tf_tree , hf_gsm_a_gmm_split_on_ccch , tvb , curr_offset , 1 , FALSE ) ;
proto_tree_add_item ( tf_tree , hf_gsm_a_gmm_non_drx_timer , tvb , curr_offset , 1 , FALSE ) ;
curr_offset + + ;
/* no length check possible */
return ( curr_offset - offset ) ;
}
/*
* [ 7 ] 10.5 .5 .7
*/
2008-12-23 20:49:15 +00:00
static guint16
2008-09-05 05:49:39 +00:00
de_gmm_ftostby ( tvbuff_t * tvb , proto_tree * tree , guint32 offset , guint len _U_ , gchar * add_string _U_ , int string_len _U_ )
2008-08-24 17:42:30 +00:00
{
2009-05-07 21:22:36 +00:00
guint8 oct ;
guint32 curr_offset ;
const gchar * str ;
2008-08-24 17:42:30 +00:00
curr_offset = offset ;
oct = tvb_get_guint8 ( tvb , curr_offset ) ;
switch ( oct & 7 )
{
2009-05-07 21:22:36 +00:00
case 1 : str = " Force to standby indicated " ; break ;
2008-08-24 17:42:30 +00:00
default : str = " force to standby not indicated " ;
}
proto_tree_add_text ( tree ,
2008-09-05 05:49:39 +00:00
tvb , curr_offset , 1 ,
" Force to Standby: (%u) %s " ,
oct & 7 ,
str ) ;
2008-08-24 17:42:30 +00:00
curr_offset + + ;
/* no length check possible */
return ( curr_offset - offset ) ;
}
/*
* [ 7 ] 10.5 .5 .7
*/
2008-12-23 20:49:15 +00:00
static guint16
2008-09-05 05:49:39 +00:00
de_gmm_ftostby_h ( tvbuff_t * tvb , proto_tree * tree , guint32 offset , guint len _U_ , gchar * add_string _U_ , int string_len _U_ )
2008-08-24 17:42:30 +00:00
{
2009-05-07 21:22:36 +00:00
guint8 oct ;
guint32 curr_offset ;
const gchar * str ;
2008-08-24 17:42:30 +00:00
curr_offset = offset ;
oct = tvb_get_guint8 ( tvb , curr_offset ) ;
/* IMPORTANT - IT'S ASSUMED THAT THE INFORMATION IS IN THE HIGHER NIBBLE */
oct > > = 4 ;
switch ( oct & 7 )
{
2009-05-07 21:22:36 +00:00
case 1 : str = " Force to standby indicated " ; break ;
2008-08-24 17:42:30 +00:00
default : str = " force to standby not indicated " ;
}
proto_tree_add_text ( tree ,
2008-09-05 05:49:39 +00:00
tvb , curr_offset , 1 ,
" Force to Standby: (%u) %s " ,
oct & 7 ,
str ) ;
2008-08-24 17:42:30 +00:00
curr_offset + + ;
/* no length check possible */
return ( curr_offset - offset ) ;
}
/*
* [ 7 ] 10.5 .5 .8
*/
2008-12-23 20:49:15 +00:00
static guint16
2008-08-24 17:42:30 +00:00
de_gmm_ptmsi_sig ( tvbuff_t * tvb , proto_tree * tree , guint32 offset , guint len _U_ , gchar * add_string _U_ , int string_len _U_ )
{
2009-05-07 21:22:36 +00:00
guint32 curr_offset ;
proto_item * curr_item ;
2008-09-05 05:49:39 +00:00
2008-08-24 17:42:30 +00:00
curr_offset = offset ;
2008-09-05 05:49:39 +00:00
2008-08-24 17:42:30 +00:00
curr_item = proto_tree_add_item ( tree , hf_gsm_a_ptmsi_sig , tvb , curr_offset , 3 , FALSE ) ;
proto_item_append_text ( curr_item , " %s " , add_string ? add_string : " " ) ;
curr_offset + = 3 ;
/* no length check possible */
return ( curr_offset - offset ) ;
}
/*
* [ 7 ] 10.5 .5 .8 a
*/
2008-12-23 20:49:15 +00:00
static guint16
2008-08-24 17:42:30 +00:00
de_gmm_ptmsi_sig2 ( tvbuff_t * tvb , proto_tree * tree , guint32 offset , guint len , gchar * add_string , int string_len _U_ )
{
2009-05-07 21:22:36 +00:00
guint32 curr_offset ;
proto_item * curr_item ;
2008-09-05 05:49:39 +00:00
2008-08-24 17:42:30 +00:00
curr_offset = offset ;
curr_item = proto_tree_add_item ( tree , hf_gsm_a_ptmsi_sig2 , tvb , curr_offset , 3 , FALSE ) ;
proto_item_append_text ( curr_item , " %s " , add_string ? add_string : " " ) ;
curr_offset + = 3 ;
EXTRANEOUS_DATA_CHECK ( len , curr_offset - offset ) ;
return ( curr_offset - offset ) ;
}
/*
* [ 7 ] 10.5 .5 .9
*/
2008-12-23 20:49:15 +00:00
static guint16
2008-09-05 05:49:39 +00:00
de_gmm_ident_type2 ( tvbuff_t * tvb , proto_tree * tree , guint32 offset , guint len _U_ , gchar * add_string _U_ , int string_len _U_ )
2008-08-24 17:42:30 +00:00
{
2009-05-07 21:22:36 +00:00
guint8 oct ;
guint32 curr_offset ;
const gchar * str ;
2008-08-24 17:42:30 +00:00
curr_offset = offset ;
oct = tvb_get_guint8 ( tvb , curr_offset ) ;
switch ( oct & 7 )
{
2009-05-07 21:22:36 +00:00
case 2 : str = " IMEI " ; break ;
case 3 : str = " IMEISV " ; break ;
case 4 : str = " TMSI " ; break ;
2008-09-05 05:49:39 +00:00
default : str = " IMSI " ;
2008-08-24 17:42:30 +00:00
}
proto_tree_add_text ( tree ,
2008-09-05 05:49:39 +00:00
tvb , curr_offset , 1 ,
" Identity Type 2: (%u) %s " ,
oct & 7 ,
str ) ;
2008-08-24 17:42:30 +00:00
curr_offset + + ;
/* no length check possible */
return ( curr_offset - offset ) ;
}
/*
* [ 7 ] 10.5 .5 .10
*/
2008-12-23 20:49:15 +00:00
static guint16
2008-09-05 05:49:39 +00:00
de_gmm_imeisv_req ( tvbuff_t * tvb , proto_tree * tree , guint32 offset , guint len _U_ , gchar * add_string _U_ , int string_len _U_ )
2008-08-24 17:42:30 +00:00
{
2009-05-07 21:22:36 +00:00
guint8 oct ;
guint32 curr_offset ;
const gchar * str ;
2008-08-24 17:42:30 +00:00
curr_offset = offset ;
oct = tvb_get_guint8 ( tvb , curr_offset ) ;
/* IMPORTANT - IT'S ASSUMED THAT THE INFORMATION IS IN THE HIGHER NIBBLE */
oct > > = 4 ;
switch ( oct & 7 )
{
2009-05-07 21:22:36 +00:00
case 1 : str = " IMEISV requested " ; break ;
2008-09-05 05:49:39 +00:00
default : str = " IMEISV not requested " ;
2008-08-24 17:42:30 +00:00
}
proto_tree_add_text ( tree ,
2008-09-05 05:49:39 +00:00
tvb , curr_offset , 1 ,
" IMEISV Request: (%u) %s " ,
oct & 7 ,
str ) ;
2008-08-24 17:42:30 +00:00
curr_offset + + ;
/* no length check possible */
return ( curr_offset - offset ) ;
}
/*
* [ 7 ] 10.5 .5 .11
*/
2008-12-23 20:49:15 +00:00
static guint16
2008-08-24 17:42:30 +00:00
de_gmm_rec_npdu_lst ( tvbuff_t * tvb , proto_tree * tree , guint32 offset , guint len , gchar * add_string _U_ , int string_len _U_ )
{
guint32 curr_offset ;
guint curr_len ;
curr_len = len ;
curr_offset = offset ;
if ( len = = 0 ) return 0 ;
do
{
2008-09-05 05:49:39 +00:00
guint32 oct ;
oct = tvb_get_guint8 ( tvb , curr_offset ) ;
oct < < = 8 ;
oct | = tvb_get_guint8 ( tvb , curr_offset + 1 ) ;
curr_len - = 2 ;
oct < < = 8 ;
proto_tree_add_text ( tree ,
tvb , curr_offset , 2 ,
2008-08-24 17:42:30 +00:00
" NSAPI %d: 0x%02x (%u) " ,
oct > > 20 ,
( oct > > 12 ) & 0xff ,
( oct > > 12 ) & 0xff ) ;
2008-09-05 05:49:39 +00:00
curr_offset + = 2 ;
if ( curr_len > 2 )
{
oct | = tvb_get_guint8 ( tvb , curr_offset + 2 ) ;
curr_len - - ;
oct < < = 12 ;
2008-08-24 17:42:30 +00:00
2008-09-05 05:49:39 +00:00
proto_tree_add_text ( tree ,
tvb , curr_offset - 1 , 2 ,
" NSAPI %d: 0x%02x (%u) " ,
oct > > 20 ,
( oct > > 12 ) & 0xff ,
( oct > > 12 ) & 0xff ) ;
curr_offset + + ;
}
2008-08-24 17:42:30 +00:00
} while ( curr_len > 1 ) ;
EXTRANEOUS_DATA_CHECK ( len , curr_offset - offset ) ;
return ( curr_offset - offset ) ;
}
/*
* [ 7 ] 10.5 .5 .12
*/
2008-12-23 20:49:15 +00:00
guint16
2008-08-24 17:42:30 +00:00
de_gmm_ms_net_cap ( tvbuff_t * tvb , proto_tree * tree , guint32 offset , guint len , gchar * add_string _U_ , int string_len _U_ )
{
guint8 oct ;
guint32 curr_offset ;
guint curr_len ;
guint gea_val ;
gchar answer_gea [ 2 ] [ 40 ] = { " encryption algorithm not available " ,
" encryption algorithm available " } ;
gchar answer_smdch [ 2 ] [ 120 ] = { " Mobile station does not support mobile terminated point to point SMS via dedicated signalling channels " ,
" Mobile station supports mobile terminated point to point SMS via dedicated signalling channels " } ;
gchar answer_smgprs [ 2 ] [ 100 ] = { " Mobile station does not support mobile terminated point to point SMS via GPRS packet data channels " ,
" Mobile station supports mobile terminated point to point SMS via GPRS packet data channels " } ;
gchar answer_ucs2 [ 2 ] [ 100 ] = { " the ME has a preference for the default alphabet (defined in 3GPP TS 23.038 [8b]) over UCS2 " ,
" the ME has no preference between the use of the default alphabet and the use of UCS2 " } ;
gchar answer_ssid [ 4 ] [ 80 ] = { " default value of phase 1 " ,
" capability of handling of ellipsis notation and phase 2 error handling " ,
" capability of handling of ellipsis notation and phase 2 error handling " ,
" capability of handling of ellipsis notation and phase 2 error handling " } ;
gchar answer_solsa [ 2 ] [ 40 ] = { " The ME does not support SoLSA " ,
" The ME supports SoLSA " } ;
gchar answer_rev [ 2 ] [ 80 ] = { " used by a mobile station not supporting R99 or later versions of the protocol " ,
" used by a mobile station supporting R99 or later versions of the protocol " } ;
gchar answer_pfc [ 2 ] [ 80 ] = { " Mobile station does not support BSS packet flow procedures " ,
" Mobile station does support BSS packet flow procedures " } ;
gchar answer_lcs [ 2 ] [ 80 ] = { " LCS value added location request notification capability not supported " ,
" LCS value added location request notification capability supported " } ;
curr_len = len ;
curr_offset = offset ;
if ( curr_len = = 0 ) { EXTRANEOUS_DATA_CHECK ( len , curr_offset - offset ) ; return ( curr_offset - offset ) ; }
oct = tvb_get_guint8 ( tvb , curr_offset ) ;
curr_len - - ;
/* bit 8 */
proto_tree_add_text ( tree ,
2008-09-05 05:49:39 +00:00
tvb , curr_offset , 1 ,
" GEA1: (%u) %s " ,
oct > > 7 ,
answer_gea [ oct > > 7 ] ) ;
2008-08-24 17:42:30 +00:00
oct < < = 1 ;
/* bit 7 */
proto_tree_add_text ( tree ,
2008-09-05 05:49:39 +00:00
tvb , curr_offset , 1 ,
" SM capabilities via dedicated channels: (%u) %s " ,
oct > > 7 ,
answer_smdch [ oct > > 7 ] ) ;
2008-08-24 17:42:30 +00:00
oct < < = 1 ;
/* bit 6 */
proto_tree_add_text ( tree ,
2008-09-05 05:49:39 +00:00
tvb , curr_offset , 1 ,
" SM capabilities via GPRS channels: (%u) %s " ,
oct > > 7 ,
answer_smgprs [ oct > > 7 ] ) ;
2008-08-24 17:42:30 +00:00
oct < < = 1 ;
/* bit 5 */
proto_tree_add_text ( tree ,
2008-09-05 05:49:39 +00:00
tvb , curr_offset , 1 ,
" UCS2 support: (%u) %s " ,
oct > > 7 ,
answer_ucs2 [ oct > > 7 ] ) ;
2008-08-24 17:42:30 +00:00
oct < < = 1 ;
/* bit 4 3 */
proto_tree_add_text ( tree ,
2008-09-05 05:49:39 +00:00
tvb , curr_offset , 1 ,
" SS Screening Indicator: (%u) %s " ,
oct > > 6 ,
answer_ssid [ oct > > 6 ] ) ;
2008-08-24 17:42:30 +00:00
oct < < = 2 ;
/* bit 2 */
proto_tree_add_text ( tree ,
2008-09-05 05:49:39 +00:00
tvb , curr_offset , 1 ,
" SoLSA Capability: (%u) %s " ,
oct > > 7 ,
answer_solsa [ oct > > 7 ] ) ;
2008-08-24 17:42:30 +00:00
oct < < = 1 ;
/* bit 1 */
proto_tree_add_text ( tree ,
2008-09-05 05:49:39 +00:00
tvb , curr_offset , 1 ,
" Revision level indicator: (%u) %s " ,
oct > > 7 ,
answer_rev [ oct > > 7 ] ) ;
2008-08-24 17:42:30 +00:00
curr_offset + + ;
if ( curr_len = = 0 ) { EXTRANEOUS_DATA_CHECK ( len , curr_offset - offset ) ; return ( curr_offset - offset ) ; }
oct = tvb_get_guint8 ( tvb , curr_offset ) ;
curr_len - - ;
proto_tree_add_text ( tree ,
2008-09-05 05:49:39 +00:00
tvb , curr_offset , 1 ,
" PFC feature mode: (%u) %s " ,
oct > > 7 ,
answer_pfc [ oct > > 7 ] ) ;
2008-08-24 17:42:30 +00:00
oct < < = 1 ;
for ( gea_val = 2 ; gea_val < 8 ; gea_val + + )
{
2008-09-05 05:49:39 +00:00
proto_tree_add_text ( tree ,
tvb , curr_offset , 1 ,
" GEA%d: (%u) %s " , gea_val ,
oct > > 7 ,
answer_gea [ oct > > 7 ] ) ;
oct < < = 1 ;
2008-08-24 17:42:30 +00:00
}
proto_tree_add_text ( tree ,
2008-09-05 05:49:39 +00:00
tvb , curr_offset , 1 ,
" LCS VA capability:: (%u) %s " ,
oct > > 7 ,
answer_lcs [ oct > > 7 ] ) ;
2008-08-24 17:42:30 +00:00
curr_offset + + ;
EXTRANEOUS_DATA_CHECK ( len , curr_offset - offset ) ;
return ( curr_offset - offset ) ;
}
/*
* [ 7 ] 10.5 .5 .12 a
*/
# define GET_DATA /* check if we have enough bits left */ \
2008-09-05 05:49:39 +00:00
if ( curr_bits_length < bits_needed ) \
continue ; \
/* check if oct has enougth bits */ \
if ( bits_in_oct < bits_needed ) \
{ \
guint32 tmp_oct ; \
if ( curr_len = = 0 ) \
2008-08-24 17:42:30 +00:00
{ \
2008-09-05 05:49:39 +00:00
proto_tree_add_text ( tf_tree , \
2008-08-24 17:42:30 +00:00
tvb , curr_offset , 1 , \
" Not enough data available " ) ; \
} \
2008-09-05 05:49:39 +00:00
tmp_oct = tvb_get_guint8 ( tvb , curr_offset ) ; \
oct | = tmp_oct < < ( 32 - 8 - bits_in_oct ) ; \
curr_len - - ; \
curr_offset + + ; \
if ( bits_in_oct ! = 0 ) \
add_ocetets = 1 ; \
2008-08-24 17:42:30 +00:00
else \
2008-09-05 05:49:39 +00:00
add_ocetets = 0 ; \
bits_in_oct + = 8 ; \
} \
else \
add_ocetets = 0 ;
2008-08-24 17:42:30 +00:00
2009-05-14 18:26:18 +00:00
/* Access Technology Type */
static const value_string gsm_a_gm_acc_tech_type_vals [ ] = {
{ 0x00 , " GSM P " } ,
{ 0x01 , " GSM E --note that GSM E covers GSM P " } ,
{ 0x02 , " GSM R --note that GSM R covers GSM E and GSM P " } ,
{ 0x03 , " GSM 1800 " } ,
{ 0x04 , " GSM 1900 " } ,
{ 0x05 , " GSM 450 " } ,
{ 0x06 , " GSM 480 " } ,
{ 0x07 , " GSM 850 " } ,
{ 0x08 , " GSM 750 " } ,
{ 0x09 , " GSM T 380 " } ,
{ 0x0a , " GSM T 410 " } ,
{ 0x0b , " GSM T 900 " } ,
{ 0x0c , " GSM 710 " } ,
{ 0x0d , " GSM T 810 " } ,
{ 0x0f , " Indicates the presence of a list of Additional access technologies " } ,
{ 0 , NULL }
} ;
/* SMS_VALUE (Switch-Measure-Switch) (4 bit field) */
static const value_string gsm_a_gm_sm_vals [ ] = {
{ 0x00 , " 1/4 timeslot (~144 microseconds) " } ,
{ 0x01 , " 2/4 timeslot (~288 microseconds) " } ,
{ 0x02 , " 3/4 timeslot (~433 microseconds) " } ,
{ 0x03 , " 4/4 timeslot (~577 microseconds) " } ,
{ 0x04 , " 5/4 timeslot (~721 microseconds) " } ,
{ 0x05 , " 6/4 timeslot (~865 microseconds) " } ,
{ 0x06 , " 7/4 timeslot (~1009 microseconds) " } ,
{ 0x07 , " 8/4 timeslot (~1154 microseconds) " } ,
{ 0x08 , " 9/4 timeslot (~1297 microseconds) " } ,
{ 0x09 , " 10/4 timeslot (~1441 microseconds) " } ,
{ 0x0a , " 11/4 timeslot (~1586 microseconds) " } ,
{ 0x0b , " 12/4 timeslot (~1730 microseconds) " } ,
{ 0x0c , " 13/4 timeslot (~1874 microseconds) " } ,
{ 0x0d , " 14/4 timeslot (~2018 microseconds) " } ,
{ 0x0e , " 15/4 timeslot (~2163 microseconds) " } ,
{ 0x0f , " 16/4 timeslot (~2307 microseconds) " } ,
{ 0 , NULL }
} ;
2008-12-23 20:49:15 +00:00
guint16
2008-08-24 17:42:30 +00:00
de_gmm_ms_radio_acc_cap ( tvbuff_t * tvb , proto_tree * tree , guint32 offset , guint len , gchar * add_string _U_ , int string_len _U_ )
{
2009-05-07 21:22:36 +00:00
guint32 curr_offset ;
guint curr_len ;
2009-05-14 18:26:18 +00:00
int bit_offset ;
2008-08-24 17:42:30 +00:00
proto_item * tf = NULL ;
2008-09-05 05:49:39 +00:00
proto_tree * tf_tree = NULL ;
2009-05-07 21:22:36 +00:00
guint32 oct ;
guchar bits_in_oct ;
guchar bits_needed ;
guint bits_length ;
guint add_ocetets ; /* octets which are covered by one element -1 */
guint curr_bits_length ;
guchar acc_type ;
2009-05-15 18:38:13 +00:00
guint value ;
2008-09-05 05:49:39 +00:00
const gchar * str ;
2009-05-07 21:22:36 +00:00
gchar multi_slot_str [ 64 ] [ 230 ] = {
2008-08-24 17:42:30 +00:00
" Not specified " , /* 00 */
" Max Rx-Slot/TDMA:1 Max Tx-Slot/TDMA:1 Max-Sum-Slot/TDMA:2 Tta:3 Ttb:2 Tra:4 Trb:2 Type:1 " , /* 01 */
" Max Rx-Slot/TDMA:2 Max Tx-Slot/TDMA:1 Max-Sum-Slot/TDMA:3 Tta:3 Ttb:2 Tra:3 Trb:1 Type:1 " , /* 02 */
" Max Rx-Slot/TDMA:2 Max Tx-Slot/TDMA:2 Max-Sum-Slot/TDMA:3 Tta:3 Ttb:2 Tra:3 Trb:1 Type:1 " , /* 03 */
" Max Rx-Slot/TDMA:3 Max Tx-Slot/TDMA:1 Max-Sum-Slot/TDMA:4 Tta:3 Ttb:1 Tra:3 Trb:1 Type:1 " , /* 04 */
" Max Rx-Slot/TDMA:2 Max Tx-Slot/TDMA:2 Max-Sum-Slot/TDMA:4 Tta:3 Ttb:1 Tra:3 Trb:1 Type:1 " , /* 05 */
" Max Rx-Slot/TDMA:3 Max Tx-Slot/TDMA:2 Max-Sum-Slot/TDMA:4 Tta:3 Ttb:1 Tra:3 Trb:1 Type:1 " , /* 06 */
" Max Rx-Slot/TDMA:3 Max Tx-Slot/TDMA:3 Max-Sum-Slot/TDMA:4 Tta:3 Ttb:1 Tra:3 Trb:1 Type:1 " , /* 07 */
" Max Rx-Slot/TDMA:4 Max Tx-Slot/TDMA:1 Max-Sum-Slot/TDMA:5 Tta:3 Ttb:1 Tra:2 Trb:1 Type:1 " , /* 08 */
" Max Rx-Slot/TDMA:3 Max Tx-Slot/TDMA:2 Max-Sum-Slot/TDMA:5 Tta:3 Ttb:1 Tra:2 Trb:1 Type:1 " , /* 09 */
" Max Rx-Slot/TDMA:4 Max Tx-Slot/TDMA:2 Max-Sum-Slot/TDMA:5 Tta:3 Ttb:1 Tra:2 Trb:1 Type:1 " , /* 10 */
" Max Rx-Slot/TDMA:4 Max Tx-Slot/TDMA:3 Max-Sum-Slot/TDMA:5 Tta:3 Ttb:1 Tra:2 Trb:1 Type:1 " , /* 11 */
" Max Rx-Slot/TDMA:4 Max Tx-Slot/TDMA:4 Max-Sum-Slot/TDMA:5 Tta:2 Ttb:1 Tra:2 Trb:1 Type:1 " , /* 12 */
" Max Rx-Slot/TDMA:3 Max Tx-Slot/TDMA:3 Max-Sum-Slot/TDMA:NA Tta:NA Ttb:a) Tra:3 Trb:a) Type:2 (a: 1 with frequency hopping, 0 otherwise) " , /* 13 */
" Max Rx-Slot/TDMA:4 Max Tx-Slot/TDMA:4 Max-Sum-Slot/TDMA:NA Tta:NA Ttb:a) Tra:3 Trb:a) Type:2 (a: 1 with frequency hopping, 0 otherwise) " , /* 14 */
" Max Rx-Slot/TDMA:5 Max Tx-Slot/TDMA:5 Max-Sum-Slot/TDMA:NA Tta:NA Ttb:a) Tra:3 Trb:a) Type:2 (a: 1 with frequency hopping, 0 otherwise) " , /* 15 */
" Max Rx-Slot/TDMA:6 Max Tx-Slot/TDMA:6 Max-Sum-Slot/TDMA:NA Tta:NA Ttb:a) Tra:2 Trb:a) Type:2 (a: 1 with frequency hopping, 0 otherwise) " , /* 16 */
" Max Rx-Slot/TDMA:7 Max Tx-Slot/TDMA:7 Max-Sum-Slot/TDMA:NA Tta:NA Ttb:a) Tra:1 Trb:0 Type:2 (a: 1 with frequency hopping, 0 otherwise) " , /* 17 */
" Max Rx-Slot/TDMA:8 Max Tx-Slot/TDMA:8 Max-Sum-Slot/TDMA:NA Tta:NA Ttb:0 Tra:0 Trb:0 Type:2 " , /* 18 */
" Max Rx-Slot/TDMA:6 Max Tx-Slot/TDMA:2 Max-Sum-Slot/TDMA:NA Tta:3 Ttb:b) Tra:2 Trb:c) Type:1 (b: 1 with frequency hopping or change from Rx to Tx, 0 otherwise; c: 1 with frequency hopping or change from Tx to Rx, 0 otherwise " , /* 19 */
" Max Rx-Slot/TDMA:6 Max Tx-Slot/TDMA:3 Max-Sum-Slot/TDMA:NA Tta:3 Ttb:b) Tra:2 Trb:c) Type:1 (b: 1 with frequency hopping or change from Rx to Tx, 0 otherwise; c: 1 with frequency hopping or change from Tx to Rx, 0 otherwise " , /* 20 */
" Max Rx-Slot/TDMA:6 Max Tx-Slot/TDMA:4 Max-Sum-Slot/TDMA:NA Tta:3 Ttb:b) Tra:2 Trb:c) Type:1 (b: 1 with frequency hopping or change from Rx to Tx, 0 otherwise; c: 1 with frequency hopping or change from Tx to Rx, 0 otherwise " , /* 21 */
" Max Rx-Slot/TDMA:6 Max Tx-Slot/TDMA:4 Max-Sum-Slot/TDMA:NA Tta:3 Ttb:b) Tra:2 Trb:c) Type:1 (b: 1 with frequency hopping or change from Rx to Tx, 0 otherwise; c: 1 with frequency hopping or change from Tx to Rx, 0 otherwise " , /* 22 */
" Max Rx-Slot/TDMA:6 Max Tx-Slot/TDMA:6 Max-Sum-Slot/TDMA:NA Tta:3 Ttb:b) Tra:2 Trb:c) Type:1 (b: 1 with frequency hopping or change from Rx to Tx, 0 otherwise; c: 1 with frequency hopping or change from Tx to Rx, 0 otherwise " , /* 23 */
" Max Rx-Slot/TDMA:8 Max Tx-Slot/TDMA:2 Max-Sum-Slot/TDMA:NA Tta:3 Ttb:b) Tra:2 Trb:c) Type:1 (b: 1 with frequency hopping or change from Rx to Tx, 0 otherwise; c: 1 with frequency hopping or change from Tx to Rx, 0 otherwise " , /* 24 */
" Max Rx-Slot/TDMA:8 Max Tx-Slot/TDMA:3 Max-Sum-Slot/TDMA:NA Tta:3 Ttb:b) Tra:2 Trb:c) Type:1 (b: 1 with frequency hopping or change from Rx to Tx, 0 otherwise; c: 1 with frequency hopping or change from Tx to Rx, 0 otherwise " , /* 25 */
" Max Rx-Slot/TDMA:8 Max Tx-Slot/TDMA:4 Max-Sum-Slot/TDMA:NA Tta:3 Ttb:b) Tra:2 Trb:c) Type:1 (b: 1 with frequency hopping or change from Rx to Tx, 0 otherwise; c: 1 with frequency hopping or change from Tx to Rx, 0 otherwise " , /* 26 */
" Max Rx-Slot/TDMA:8 Max Tx-Slot/TDMA:4 Max-Sum-Slot/TDMA:NA Tta:3 Ttb:b) Tra:2 Trb:c) Type:1 (b: 1 with frequency hopping or change from Rx to Tx, 0 otherwise; c: 1 with frequency hopping or change from Tx to Rx, 0 otherwise " , /* 27 */
" Max Rx-Slot/TDMA:8 Max Tx-Slot/TDMA:6 Max-Sum-Slot/TDMA:NA Tta:3 Ttb:b) Tra:2 Trb:c) Type:1 (b: 1 with frequency hopping or change from Rx to Tx, 0 otherwise; c: 1 with frequency hopping or change from Tx to Rx, 0 otherwise " , /* 28 */
" Max Rx-Slot/TDMA:8 Max Tx-Slot/TDMA:8 Max-Sum-Slot/TDMA:NA Tta:3 Ttb:b) Tra:2 Trb:c) Type:1 (b: 1 with frequency hopping or change from Rx to Tx, 0 otherwise; c: 1 with frequency hopping or change from Tx to Rx, 0 otherwise " , /* 29 */
" Max Rx-Slot/TDMA:5 Max Tx-Slot/TDMA:1 Max-Sum-Slot/TDMA:6 Tta:2 Ttb:1 Tra:1 Trb:1 Type:1 " , /* 30 */
" Max Rx-Slot/TDMA:5 Max Tx-Slot/TDMA:2 Max-Sum-Slot/TDMA:6 Tta:2 Ttb:1 Tra:1 Trb:1 Type:1 " , /* 31 */
" Max Rx-Slot/TDMA:5 Max Tx-Slot/TDMA:3 Max-Sum-Slot/TDMA:6 Tta:2 Ttb:1 Tra:1 Trb:1 Type:1 " , /* 32 */
" Max Rx-Slot/TDMA:5 Max Tx-Slot/TDMA:4 Max-Sum-Slot/TDMA:6 Tta:2 Ttb:1 Tra:1 Trb:1 Type:1 " , /* 33 */
" Max Rx-Slot/TDMA:5 Max Tx-Slot/TDMA:5 Max-Sum-Slot/TDMA:6 Tta:2 Ttb:1 Tra:1 Trb:1 Type:1 " , /* 34 */
" Max Rx-Slot/TDMA:5 Max Tx-Slot/TDMA:1 Max-Sum-Slot/TDMA:6 Tta:2 Ttb:1 Tra:1+to Trb:1 Type:1 (to: to = 31 symbol periods (this can be provided by a TA offset, i.e. a minimum TA value)) " , /* 35 */
" Max Rx-Slot/TDMA:5 Max Tx-Slot/TDMA:2 Max-Sum-Slot/TDMA:6 Tta:2 Ttb:1 Tra:1+to Trb:1 Type:1 (to: to = 31 symbol periods (this can be provided by a TA offset, i.e. a minimum TA value)) " , /* 36 */
" Max Rx-Slot/TDMA:5 Max Tx-Slot/TDMA:3 Max-Sum-Slot/TDMA:6 Tta:2 Ttb:1 Tra:1+to Trb:1 Type:1 (to: to = 31 symbol periods (this can be provided by a TA offset, i.e. a minimum TA value)) " , /* 37 */
" Max Rx-Slot/TDMA:5 Max Tx-Slot/TDMA:4 Max-Sum-Slot/TDMA:6 Tta:2 Ttb:1 Tra:1+to Trb:1 Type:1 (to: to = 31 symbol periods (this can be provided by a TA offset, i.e. a minimum TA value)) " , /* 38 */
" Max Rx-Slot/TDMA:5 Max Tx-Slot/TDMA:5 Max-Sum-Slot/TDMA:6 Tta:2 Ttb:1 Tra:1+to Trb:1 Type:1 (to: to = 31 symbol periods (this can be provided by a TA offset, i.e. a minimum TA value)) " , /* 39 */
" Max Rx-Slot/TDMA:6 Max Tx-Slot/TDMA:1 Max-Sum-Slot/TDMA:7 Tta:1 Ttb:1 Tra:1 Trb:to Type:1 (to: to = 31 symbol periods (this can be provided by a TA offset, i.e. a minimum TA value)) " , /* 40 */
" Max Rx-Slot/TDMA:6 Max Tx-Slot/TDMA:2 Max-Sum-Slot/TDMA:7 Tta:1 Ttb:1 Tra:1 Trb:to Type:1 (to: to = 31 symbol periods (this can be provided by a TA offset, i.e. a minimum TA value)) " , /* 41 */
" Max Rx-Slot/TDMA:6 Max Tx-Slot/TDMA:3 Max-Sum-Slot/TDMA:7 Tta:1 Ttb:1 Tra:1 Trb:to Type:1 (to: to = 31 symbol periods (this can be provided by a TA offset, i.e. a minimum TA value)) " , /* 42 */
" Max Rx-Slot/TDMA:6 Max Tx-Slot/TDMA:4 Max-Sum-Slot/TDMA:7 Tta:1 Ttb:1 Tra:1 Trb:to Type:1 (to: to = 31 symbol periods (this can be provided by a TA offset, i.e. a minimum TA value)) " , /* 43 */
" Max Rx-Slot/TDMA:6 Max Tx-Slot/TDMA:5 Max-Sum-Slot/TDMA:7 Tta:1 Ttb:1 Tra:1 Trb:to Type:1 (to: to = 31 symbol periods (this can be provided by a TA offset, i.e. a minimum TA value)) " , /* 44 */
" Max Rx-Slot/TDMA:6 Max Tx-Slot/TDMA:6 Max-Sum-Slot/TDMA:7 Tta:1 Ttb:1 Tra:1 Trb:to Type:1 (to: to = 31 symbol periods (this can be provided by a TA offset, i.e. a minimum TA value)) " , /* 45 */
" Not specified " , /* 46 */
" Not specified " , /* 47 */
" Not specified " , /* 48 */
" Not specified " , /* 49 */
" Not specified " , /* 50 */
" Not specified " , /* 51 */
" Not specified " , /* 52 */
" Not specified " , /* 53 */
" Not specified " , /* 54 */
" Not specified " , /* 55 */
" Not specified " , /* 56 */
" Not specified " , /* 57 */
" Not specified " , /* 58 */
" Not specified " , /* 59 */
" Not specified " , /* 60 */
" Not specified " , /* 61 */
" Not specified " , /* 62 */
" Not specified " , /* 63 */
} ;
2008-09-05 05:49:39 +00:00
guint indx = 0 ;
2008-08-24 17:42:30 +00:00
guchar dtm_gprs_mslot = 0 ;
guchar dtm_egprs_mslot = 4 ;
gboolean finished = TRUE ;
curr_len = len ;
curr_offset = offset ;
2009-05-14 18:26:18 +00:00
bit_offset = offset < < 3 ;
2008-08-24 17:42:30 +00:00
bits_in_oct = 0 ;
oct = 0 ;
2009-05-15 18:38:13 +00:00
2008-08-24 17:42:30 +00:00
do
{
2008-09-05 05:49:39 +00:00
/* check for a new round */
if ( ( curr_len * 8 + bits_in_oct ) < 11 )
break ;
2008-08-24 17:42:30 +00:00
2008-09-05 05:49:39 +00:00
/* now read the first 11 bits */
2008-08-24 17:42:30 +00:00
curr_bits_length = 11 ;
2008-09-05 05:49:39 +00:00
/*
*
*/
if ( curr_len ! = len )
2008-08-24 17:42:30 +00:00
{
2008-09-05 05:49:39 +00:00
bits_needed = 1 ;
GET_DATA ;
if ( ( oct > > ( 32 - bits_needed ) ) = = 1 )
{
curr_bits_length - = bits_needed ;
2008-08-24 17:42:30 +00:00
oct < < = bits_needed ;
2008-09-05 05:49:39 +00:00
bits_in_oct - = bits_needed ;
if ( ( curr_len * 8 + bits_in_oct ) < 11 )
break ;
curr_bits_length = 11 ;
}
else
{
curr_bits_length - = bits_needed ;
2008-08-24 17:42:30 +00:00
oct < < = bits_needed ;
2008-09-05 05:49:39 +00:00
bits_in_oct - = bits_needed ;
break ;
}
2008-08-24 17:42:30 +00:00
}
2008-09-05 05:49:39 +00:00
indx + + ;
tf = proto_tree_add_text ( tree ,
tvb , curr_offset , 1 ,
" MS RA capability %d " , indx ) ;
2008-08-24 17:42:30 +00:00
2008-09-05 05:49:39 +00:00
tf_tree = proto_item_add_subtree ( tf , ett_gmm_radio_cap ) ;
2008-08-24 17:42:30 +00:00
2008-09-05 05:49:39 +00:00
/*
* Access Technology
*/
bits_needed = 4 ;
GET_DATA ;
2008-08-24 17:42:30 +00:00
2008-09-05 05:49:39 +00:00
acc_type = oct > > ( 32 - bits_needed ) ;
2008-08-24 17:42:30 +00:00
2009-05-14 18:26:18 +00:00
proto_tree_add_bits_item ( tf_tree , hf_gsm_a_gm_acc_tech_type , tvb , bit_offset , 4 , FALSE ) ;
bit_offset + = 4 ;
2008-08-24 17:42:30 +00:00
curr_bits_length - = bits_needed ;
oct < < = bits_needed ;
bits_in_oct - = bits_needed ;
2009-05-14 18:26:18 +00:00
/* < Access capabilities struct > ::= */
2008-09-05 05:49:39 +00:00
/*
* get bits_length
*/
bits_needed = 7 ;
GET_DATA ;
2008-08-24 17:42:30 +00:00
2008-09-05 05:49:39 +00:00
bits_length = curr_bits_length = oct > > ( 32 - bits_needed ) ;
2009-05-14 18:26:18 +00:00
proto_tree_add_bits_item ( tf_tree , hf_gsm_a_gm_acc_cap_struct_len , tvb , bit_offset , 7 , FALSE ) ;
proto_item_set_len ( tf , ( bits_length > > 3 ) + 1 ) ;
2008-08-24 17:42:30 +00:00
/* This is already done - length doesn't contain this field
curr_bits_length - = bits_needed ;
*/
2009-05-14 18:26:18 +00:00
bit_offset + = 7 ;
2008-08-24 17:42:30 +00:00
oct < < = bits_needed ;
bits_in_oct - = bits_needed ;
2008-09-05 05:49:39 +00:00
if ( acc_type = = 0x0f )
2008-08-24 17:42:30 +00:00
{
2008-09-05 05:49:39 +00:00
do
2008-08-24 17:42:30 +00:00
{
2008-09-05 05:49:39 +00:00
/*
* Additional access technologies :
*/
finished = TRUE ; /* Break out of the loop unless proven unfinished */
2008-08-24 17:42:30 +00:00
/*
2008-09-05 05:49:39 +00:00
* Presence bit
2008-08-24 17:42:30 +00:00
*/
2008-09-05 05:49:39 +00:00
bits_needed = 1 ;
GET_DATA ;
/* analyse bits */
switch ( oct > > ( 32 - bits_needed ) )
2008-08-24 17:42:30 +00:00
{
2008-09-05 05:49:39 +00:00
case 0x00 : str = " Not Present " ; finished = TRUE ; break ;
2009-05-07 21:22:36 +00:00
case 0x01 : str = " Present " ; finished = FALSE ; break ;
default : str = " This should not happen " ;
2008-08-24 17:42:30 +00:00
}
2008-09-05 05:49:39 +00:00
proto_tree_add_text ( tf_tree ,
tvb , curr_offset - 1 - add_ocetets , 1 + add_ocetets ,
" Presence: (%u) %s " , oct > > ( 32 - bits_needed ) , str ) ;
2009-05-14 18:26:18 +00:00
bit_offset + + ;
2008-09-05 05:49:39 +00:00
curr_bits_length - = bits_needed ;
oct < < = bits_needed ;
bits_in_oct - = bits_needed ;
2008-08-24 17:42:30 +00:00
2008-09-05 05:49:39 +00:00
if ( finished )
{
/*
* No more valid data , get spare bits if any
*/
while ( curr_bits_length > 0 )
{
if ( curr_bits_length > 8 )
bits_needed = 8 ;
else
bits_needed = curr_bits_length ;
GET_DATA ;
curr_bits_length - = bits_needed ;
oct < < = bits_needed ;
bits_in_oct - = bits_needed ;
2009-05-14 18:26:18 +00:00
bit_offset + = bits_needed ;
2008-09-05 05:49:39 +00:00
}
continue ;
}
2008-08-24 17:42:30 +00:00
2008-09-05 05:49:39 +00:00
/*
* Access Technology
*/
bits_needed = 4 ;
GET_DATA ;
2008-08-24 17:42:30 +00:00
2008-09-05 05:49:39 +00:00
acc_type = oct > > ( 32 - bits_needed ) ;
2008-08-24 17:42:30 +00:00
2009-05-15 18:38:13 +00:00
proto_tree_add_bits_item ( tf_tree , hf_gsm_a_gm_acc_cap_struct_len , tvb , bit_offset , 7 , FALSE ) ;
2009-05-14 18:26:18 +00:00
bit_offset + = 4 ;
2008-09-05 05:49:39 +00:00
curr_bits_length - = bits_needed ;
oct < < = bits_needed ;
bits_in_oct - = bits_needed ;
/*
* RF Power
*/
bits_needed = 3 ;
GET_DATA ;
2009-05-15 18:38:13 +00:00
value = tvb_get_bits8 ( tvb , bit_offset , 3 ) ;
2008-09-05 05:49:39 +00:00
/* analyse bits */
if ( acc_type = = 0x04 ) /* GSM 1900 */
{
2009-05-15 18:38:13 +00:00
switch ( value )
2008-09-05 05:49:39 +00:00
{
2009-05-07 21:22:36 +00:00
case 0x01 : str = " 1 W (30 dBm) " ; break ;
2008-09-05 05:49:39 +00:00
case 0x02 : str = " 0,25 W (24 dBm) " ; break ;
2009-05-07 21:22:36 +00:00
case 0x03 : str = " 2 W (33 dBm) " ; break ;
default : str = " Not specified " ;
2008-09-05 05:49:39 +00:00
}
2008-08-24 17:42:30 +00:00
}
2008-09-05 05:49:39 +00:00
else if ( acc_type = = 0x03 )
2008-08-24 17:42:30 +00:00
{
2009-05-15 18:38:13 +00:00
/*
* 3 GSM 1800
*/
switch ( value )
2008-09-05 05:49:39 +00:00
{
2009-05-07 21:22:36 +00:00
case 0x01 : str = " 1 W (30 dBm) " ; break ;
2008-09-05 05:49:39 +00:00
case 0x02 : str = " 0,25 W (24 dBm) " ; break ;
2009-05-07 21:22:36 +00:00
case 0x03 : str = " 4 W (36 dBm) " ; break ;
default : str = " Not specified " ;
2008-09-05 05:49:39 +00:00
}
}
else if ( acc_type < = 0x08 )
{
2009-05-15 18:38:13 +00:00
/* 0 GSM P
* 1 GSM E
* 2 GSM R
* 5 GSM 450
* 6 GSM 480
* 7 GSM 850
*/
switch ( value )
2008-09-05 05:49:39 +00:00
{
2009-05-07 21:22:36 +00:00
case 0x02 : str = " 8 W (39 dBm) " ; break ;
case 0x03 : str = " 5 W (37 dBm) " ; break ;
case 0x04 : str = " 2 W (33 dBm) " ; break ;
2008-09-05 05:49:39 +00:00
case 0x05 : str = " 0,8 W (29 dBm) " ; break ;
2009-05-07 21:22:36 +00:00
default : str = " Not specified " ;
2008-09-05 05:49:39 +00:00
}
}
else
str = " Not specified?? " ;
2008-08-24 17:42:30 +00:00
2009-05-15 18:38:13 +00:00
/* decode_bits_in_field(gint bit_offset, gint no_of_bits, guint64 value)*/
2008-09-05 05:49:39 +00:00
proto_tree_add_text ( tf_tree ,
tvb , curr_offset - 1 - add_ocetets , 1 + add_ocetets ,
2009-05-15 18:38:13 +00:00
" %s RF Power Capability, GMSK Power Class: (%u) %s " , decode_bits_in_field ( bit_offset , 3 , value ) , value , str ) ;
2009-05-14 18:26:18 +00:00
bit_offset + = 3 ;
2008-09-05 05:49:39 +00:00
curr_bits_length - = bits_needed ;
oct < < = bits_needed ;
bits_in_oct - = bits_needed ;
2008-08-24 17:42:30 +00:00
2008-09-05 05:49:39 +00:00
/*
* 8 PSK Power Class
*/
bits_needed = 2 ;
GET_DATA ;
2008-08-24 17:42:30 +00:00
2009-05-15 18:38:13 +00:00
value = tvb_get_bits8 ( tvb , bit_offset , 2 ) ;
2008-09-05 05:49:39 +00:00
/* analyse bits */
2009-05-15 18:38:13 +00:00
switch ( value )
2008-09-05 05:49:39 +00:00
{
case 0x00 : str = " 8PSK modulation not supported for uplink " ; break ;
case 0x01 : str = " Power class E1 " ; break ;
case 0x02 : str = " Power class E2 " ; break ;
case 0x03 : str = " Power class E3 " ; break ;
2009-05-07 21:22:36 +00:00
default : str = " This should not happen " ;
2008-09-05 05:49:39 +00:00
}
2008-08-24 17:42:30 +00:00
2008-09-05 05:49:39 +00:00
proto_tree_add_text ( tf_tree ,
tvb , curr_offset - 1 - add_ocetets , 1 + add_ocetets ,
2009-05-15 18:38:13 +00:00
" 8PSK Power Class: (%u) %s " , value , str ) ;
2009-05-14 18:26:18 +00:00
bit_offset + = 2 ;
2008-09-05 05:49:39 +00:00
curr_bits_length - = bits_needed ;
oct < < = bits_needed ;
bits_in_oct - = bits_needed ;
2008-08-24 17:42:30 +00:00
2008-09-05 05:49:39 +00:00
} while ( ! finished ) ;
/* goto next one */
continue ;
}
2008-08-24 17:42:30 +00:00
/*
* RF Power
*/
bits_needed = 3 ;
2008-09-05 05:49:39 +00:00
GET_DATA ;
2008-08-24 17:42:30 +00:00
2009-05-15 18:38:13 +00:00
value = tvb_get_bits8 ( tvb , bit_offset , 3 ) ;
2008-09-05 05:49:39 +00:00
/* analyse bits */
if ( acc_type = = 0x04 ) /* GSM 1900 */
{
2009-05-15 18:38:13 +00:00
switch ( value )
2008-09-05 05:49:39 +00:00
{
2009-05-07 21:22:36 +00:00
case 0x01 : str = " 1 W (30 dBm) " ; break ;
2008-08-24 17:42:30 +00:00
case 0x02 : str = " 0,25 W (24 dBm) " ; break ;
2009-05-07 21:22:36 +00:00
case 0x03 : str = " 2 W (33 dBm) " ; break ;
default : str = " Not specified " ;
2008-08-24 17:42:30 +00:00
}
}
else if ( acc_type = = 0x03 )
{
2009-05-15 18:38:13 +00:00
switch ( value )
2008-09-05 05:49:39 +00:00
{
2009-05-07 21:22:36 +00:00
case 0x01 : str = " 1 W (30 dBm) " ; break ;
2008-08-24 17:42:30 +00:00
case 0x02 : str = " 0,25 W (24 dBm) " ; break ;
2009-05-07 21:22:36 +00:00
case 0x03 : str = " 4 W (36 dBm) " ; break ;
default : str = " Not specified " ;
2008-08-24 17:42:30 +00:00
}
}
2008-09-05 05:49:39 +00:00
else if ( acc_type < = 0x08 )
2008-08-24 17:42:30 +00:00
{
2009-05-15 18:38:13 +00:00
switch ( value )
2008-08-24 17:42:30 +00:00
{
2009-05-07 21:22:36 +00:00
case 0x02 : str = " 8 W (39 dBm) " ; break ;
case 0x03 : str = " 5 W (37 dBm) " ; break ;
case 0x04 : str = " 2 W (33 dBm) " ; break ;
2008-08-24 17:42:30 +00:00
case 0x05 : str = " 0,8 W (29 dBm) " ; break ;
2009-05-07 21:22:36 +00:00
default : str = " Not specified " ;
2008-08-24 17:42:30 +00:00
}
}
else
str = " Not specified?? " ;
proto_tree_add_text ( tf_tree ,
2008-09-05 05:49:39 +00:00
tvb , curr_offset - 1 - add_ocetets , 1 + add_ocetets ,
2009-05-15 18:38:13 +00:00
" %s RF Power Capability, GMSK Power Class: (%u) %s " , decode_bits_in_field ( bit_offset , 3 , value ) , value , str ) ;
2009-05-14 18:26:18 +00:00
bit_offset + = 3 ;
2008-08-24 17:42:30 +00:00
curr_bits_length - = bits_needed ;
oct < < = bits_needed ;
bits_in_oct - = bits_needed ;
/*
* A5 Bits ?
*/
bits_needed = 1 ;
2008-09-05 05:49:39 +00:00
GET_DATA ;
2008-08-24 17:42:30 +00:00
2008-09-05 05:49:39 +00:00
/* analyse bits */
2008-08-24 17:42:30 +00:00
if ( ( oct > > ( 32 - bits_needed ) ) = = 0 )
{
2008-09-05 05:49:39 +00:00
proto_tree_add_text ( tf_tree ,
tvb , curr_offset - 1 - add_ocetets , 1 + add_ocetets ,
" A5 Bits: (%u) same values apply for parameters as in the immediately preceding Access capabilities field within this IE " , oct > > ( 32 - bits_needed ) ) ;
2009-05-14 18:26:18 +00:00
bit_offset + + ;
2008-09-05 05:49:39 +00:00
curr_bits_length - = bits_needed ;
2008-08-24 17:42:30 +00:00
oct < < = bits_needed ;
2008-09-05 05:49:39 +00:00
bits_in_oct - = bits_needed ;
2008-08-24 17:42:30 +00:00
}
else
{
int i ;
2008-09-05 05:49:39 +00:00
proto_tree_add_text ( tf_tree ,
tvb , curr_offset - 1 - add_ocetets , 1 + add_ocetets ,
" A5 Bits: (%u) A5 bits follows " , oct > > ( 32 - bits_needed ) ) ;
2008-08-24 17:42:30 +00:00
2009-05-14 18:26:18 +00:00
bit_offset + + ;
2008-09-05 05:49:39 +00:00
curr_bits_length - = bits_needed ;
2008-08-24 17:42:30 +00:00
oct < < = bits_needed ;
bits_in_oct - = bits_needed ;
for ( i = 1 ; i < = 7 ; i + + )
{
2008-09-05 05:49:39 +00:00
/*
* A5 Bits decoding
*/
bits_needed = 1 ;
GET_DATA ;
2008-08-24 17:42:30 +00:00
2008-09-05 05:49:39 +00:00
/* analyse bits */
switch ( oct > > ( 32 - bits_needed ) )
{
case 0x00 : str = " encryption algorithm not available " ; break ;
2009-05-07 21:22:36 +00:00
case 0x01 : str = " encryption algorithm available " ; break ;
default : str = " This should not happen " ;
2008-09-05 05:49:39 +00:00
}
proto_tree_add_text ( tf_tree ,
tvb , curr_offset - 1 - add_ocetets , 1 + add_ocetets ,
" A5/%d: (%u) %s " , i , oct > > ( 32 - bits_needed ) , str ) ;
2009-05-14 18:26:18 +00:00
bit_offset + + ;
2008-09-05 05:49:39 +00:00
curr_bits_length - = bits_needed ;
oct < < = bits_needed ;
bits_in_oct - = bits_needed ;
}
}
2008-08-24 17:42:30 +00:00
/*
* ES IND
*/
bits_needed = 1 ;
2008-09-05 05:49:39 +00:00
GET_DATA ;
2008-08-24 17:42:30 +00:00
2008-09-05 05:49:39 +00:00
/* analyse bits */
switch ( oct > > ( 32 - bits_needed ) )
2008-08-24 17:42:30 +00:00
{
2008-09-05 05:49:39 +00:00
case 0x00 : str = " controlled early Classmark Sending option is not implemented " ; break ;
2009-05-07 21:22:36 +00:00
case 0x01 : str = " controlled early Classmark Sending option is implemented " ; break ;
default : str = " This should not happen " ;
2008-08-24 17:42:30 +00:00
}
proto_tree_add_text ( tf_tree ,
2008-09-05 05:49:39 +00:00
tvb , curr_offset - 1 - add_ocetets , 1 + add_ocetets ,
" Controlled early Classmark Sending: (%u) %s " , oct > > ( 32 - bits_needed ) , str ) ;
2009-05-14 18:26:18 +00:00
bit_offset + + ;
2008-08-24 17:42:30 +00:00
curr_bits_length - = bits_needed ;
oct < < = bits_needed ;
bits_in_oct - = bits_needed ;
/*
* PS
*/
bits_needed = 1 ;
2008-09-05 05:49:39 +00:00
GET_DATA ;
2008-08-24 17:42:30 +00:00
2008-09-05 05:49:39 +00:00
/* analyse bits */
switch ( oct > > ( 32 - bits_needed ) )
2008-08-24 17:42:30 +00:00
{
2008-09-05 05:49:39 +00:00
case 0x00 : str = " PS capability not present " ; break ;
2009-05-07 21:22:36 +00:00
case 0x01 : str = " PS capability present " ; break ;
default : str = " This should not happen " ;
2008-08-24 17:42:30 +00:00
}
proto_tree_add_text ( tf_tree ,
2008-09-05 05:49:39 +00:00
tvb , curr_offset - 1 - add_ocetets , 1 + add_ocetets ,
" Pseudo Synchronisation: (%u) %s " , oct > > ( 32 - bits_needed ) , str ) ;
2009-05-14 18:26:18 +00:00
bit_offset + + ;
2008-08-24 17:42:30 +00:00
curr_bits_length - = bits_needed ;
oct < < = bits_needed ;
bits_in_oct - = bits_needed ;
/*
* VGCS
*/
bits_needed = 1 ;
2008-09-05 05:49:39 +00:00
GET_DATA ;
2008-08-24 17:42:30 +00:00
2008-09-05 05:49:39 +00:00
/* analyse bits */
switch ( oct > > ( 32 - bits_needed ) )
2008-08-24 17:42:30 +00:00
{
2008-09-05 05:49:39 +00:00
case 0x00 : str = " no VGCS capability or no notifications wanted " ; break ;
2009-05-07 21:22:36 +00:00
case 0x01 : str = " VGCS capability and notifications wanted " ; break ;
default : str = " This should not happen " ;
2008-08-24 17:42:30 +00:00
}
proto_tree_add_text ( tf_tree ,
2008-09-05 05:49:39 +00:00
tvb , curr_offset - 1 - add_ocetets , 1 + add_ocetets ,
" Voice Group Call Service: (%u) %s " , oct > > ( 32 - bits_needed ) , str ) ;
2009-05-14 18:26:18 +00:00
bit_offset + + ;
2008-08-24 17:42:30 +00:00
curr_bits_length - = bits_needed ;
oct < < = bits_needed ;
bits_in_oct - = bits_needed ;
/*
* VBS
*/
bits_needed = 1 ;
2008-09-05 05:49:39 +00:00
GET_DATA ;
2008-08-24 17:42:30 +00:00
2008-09-05 05:49:39 +00:00
/* analyse bits */
switch ( oct > > ( 32 - bits_needed ) )
2008-08-24 17:42:30 +00:00
{
2008-09-05 05:49:39 +00:00
case 0x00 : str = " no VBS capability or no notifications wanted " ; break ;
2009-05-07 21:22:36 +00:00
case 0x01 : str = " VBS capability and notifications wanted " ; break ;
default : str = " This should not happen " ;
2008-08-24 17:42:30 +00:00
}
proto_tree_add_text ( tf_tree ,
2008-09-05 05:49:39 +00:00
tvb , curr_offset - 1 - add_ocetets , 1 + add_ocetets ,
" Voice Broadcast Service: (%u) %s " , oct > > ( 32 - bits_needed ) , str ) ;
2009-05-14 18:26:18 +00:00
bit_offset + + ;
2008-08-24 17:42:30 +00:00
curr_bits_length - = bits_needed ;
oct < < = bits_needed ;
bits_in_oct - = bits_needed ;
/*
* Multislot capability ?
*/
bits_needed = 1 ;
2008-09-05 05:49:39 +00:00
GET_DATA ;
2008-08-24 17:42:30 +00:00
2008-09-05 05:49:39 +00:00
/* analyse bits */
2008-08-24 17:42:30 +00:00
if ( ( oct > > ( 32 - bits_needed ) ) = = 0 )
{
2008-09-05 05:49:39 +00:00
proto_tree_add_text ( tf_tree ,
tvb , curr_offset - 1 - add_ocetets , 1 + add_ocetets ,
" Multislot capability: (%u) same values apply for parameters as in the immediately preceding Access capabilities field within this IE " , oct > > ( 32 - bits_needed ) ) ;
2009-05-14 18:26:18 +00:00
bit_offset + + ;
2008-09-05 05:49:39 +00:00
curr_bits_length - = bits_needed ;
2008-08-24 17:42:30 +00:00
oct < < = bits_needed ;
2008-09-05 05:49:39 +00:00
bits_in_oct - = bits_needed ;
2008-08-24 17:42:30 +00:00
}
else
{
2008-09-05 05:49:39 +00:00
proto_tree_add_text ( tf_tree ,
2008-08-24 17:42:30 +00:00
tvb , curr_offset - 1 - add_ocetets , 1 + add_ocetets ,
" Multislot capability: (%u) Multislot capability struct available " , oct > > ( 32 - bits_needed ) ) ;
2009-05-14 18:26:18 +00:00
bit_offset + + ;
2008-08-24 17:42:30 +00:00
2008-09-05 05:49:39 +00:00
curr_bits_length - = bits_needed ;
2008-08-24 17:42:30 +00:00
oct < < = bits_needed ;
2008-09-05 05:49:39 +00:00
bits_in_oct - = bits_needed ;
2008-08-24 17:42:30 +00:00
2008-09-05 05:49:39 +00:00
/*
2008-08-24 17:42:30 +00:00
* HSCSD multislot class ?
2008-09-05 05:49:39 +00:00
*/
bits_needed = 1 ;
GET_DATA ;
2008-08-24 17:42:30 +00:00
2008-09-05 05:49:39 +00:00
/* analyse bits */
2008-08-24 17:42:30 +00:00
if ( ( oct > > ( 32 - bits_needed ) ) = = 0 )
2008-09-05 05:49:39 +00:00
{
proto_tree_add_text ( tf_tree ,
tvb , curr_offset - 1 - add_ocetets , 1 + add_ocetets ,
" HSCSD multislot class: (%u) Bits are not available " , oct > > ( 32 - bits_needed ) ) ;
2009-05-14 18:26:18 +00:00
bit_offset + + ;
2008-09-05 05:49:39 +00:00
curr_bits_length - = bits_needed ;
2008-08-24 17:42:30 +00:00
oct < < = bits_needed ;
2008-09-05 05:49:39 +00:00
bits_in_oct - = bits_needed ;
}
2008-08-24 17:42:30 +00:00
else
2008-09-05 05:49:39 +00:00
{
curr_bits_length - = bits_needed ;
2008-08-24 17:42:30 +00:00
oct < < = bits_needed ;
2008-09-05 05:49:39 +00:00
bits_in_oct - = bits_needed ;
2009-05-14 18:26:18 +00:00
bit_offset + + ;
2008-08-24 17:42:30 +00:00
2008-09-05 05:49:39 +00:00
/*
* HSCSD multislot class
2008-08-24 17:42:30 +00:00
*/
2008-09-05 05:49:39 +00:00
bits_needed = 5 ;
GET_DATA ;
2008-08-24 17:42:30 +00:00
2008-09-05 05:49:39 +00:00
/* analyse bits */
proto_tree_add_text ( tf_tree ,
tvb , curr_offset - 1 - add_ocetets , 1 + add_ocetets ,
" HSCSD multislot class: (%u) %s " , oct > > ( 32 - bits_needed ) , multi_slot_str [ oct > > ( 32 - bits_needed ) ] ) ;
2009-05-14 18:26:18 +00:00
bit_offset + = 5 ;
2008-09-05 05:49:39 +00:00
curr_bits_length - = bits_needed ;
2008-08-24 17:42:30 +00:00
oct < < = bits_needed ;
2008-09-05 05:49:39 +00:00
bits_in_oct - = bits_needed ;
}
2008-08-24 17:42:30 +00:00
2008-09-05 05:49:39 +00:00
/*
2008-08-24 17:42:30 +00:00
* GPRS multislot class ?
2008-09-05 05:49:39 +00:00
*/
bits_needed = 1 ;
GET_DATA ;
2008-08-24 17:42:30 +00:00
2008-09-05 05:49:39 +00:00
/* analyse bits */
2008-08-24 17:42:30 +00:00
if ( ( oct > > ( 32 - bits_needed ) ) = = 0 )
2008-09-05 05:49:39 +00:00
{
proto_tree_add_text ( tf_tree ,
tvb , curr_offset - 1 - add_ocetets , 1 + add_ocetets ,
" GPRS multislot class: (%u) Bits are not available " , oct > > ( 32 - bits_needed ) ) ;
2009-05-14 18:26:18 +00:00
bit_offset + + ;
2008-09-05 05:49:39 +00:00
curr_bits_length - = bits_needed ;
2008-08-24 17:42:30 +00:00
oct < < = bits_needed ;
2008-09-05 05:49:39 +00:00
bits_in_oct - = bits_needed ;
}
2008-08-24 17:42:30 +00:00
else
2008-09-05 05:49:39 +00:00
{
curr_bits_length - = bits_needed ;
2008-08-24 17:42:30 +00:00
oct < < = bits_needed ;
2008-09-05 05:49:39 +00:00
bits_in_oct - = bits_needed ;
2009-05-14 18:26:18 +00:00
bit_offset + + ;
2008-08-24 17:42:30 +00:00
2008-09-05 05:49:39 +00:00
/*
* GPRS multislot class
2008-08-24 17:42:30 +00:00
*/
2008-09-05 05:49:39 +00:00
bits_needed = 5 ;
GET_DATA ;
2008-08-24 17:42:30 +00:00
2008-09-05 05:49:39 +00:00
/* analyse bits */
proto_tree_add_text ( tf_tree ,
tvb , curr_offset - 1 - add_ocetets , 1 + add_ocetets ,
" GPRS multislot class: (%u) %s " , oct > > ( 32 - bits_needed ) , multi_slot_str [ oct > > ( 32 - bits_needed ) ] ) ;
2009-05-14 18:26:18 +00:00
bit_offset + = 5 ;
2008-09-05 05:49:39 +00:00
curr_bits_length - = bits_needed ;
2008-08-24 17:42:30 +00:00
oct < < = bits_needed ;
2008-09-05 05:49:39 +00:00
bits_in_oct - = bits_needed ;
2008-08-24 17:42:30 +00:00
2008-09-05 05:49:39 +00:00
/*
* GPRS Extended Dynamic Allocation Capability
2008-08-24 17:42:30 +00:00
*/
2008-09-05 05:49:39 +00:00
bits_needed = 1 ;
GET_DATA ;
2008-08-24 17:42:30 +00:00
2008-09-05 05:49:39 +00:00
/* analyse bits */
switch ( oct > > ( 32 - bits_needed ) )
{
case 0x00 : str = " Extended Dynamic Allocation Capability for GPRS is not implemented " ; break ;
2009-05-07 21:22:36 +00:00
case 0x01 : str = " Extended Dynamic Allocation Capability for GPRS is implemented " ; break ;
default : str = " This should not happen " ;
2008-09-05 05:49:39 +00:00
}
proto_tree_add_text ( tf_tree ,
tvb , curr_offset - 1 - add_ocetets , 1 + add_ocetets ,
" GPRS Extended Dynamic Allocation Capability: (%u) %s " , oct > > ( 32 - bits_needed ) , str ) ;
2009-05-14 18:26:18 +00:00
bit_offset + + ;
2008-09-05 05:49:39 +00:00
curr_bits_length - = bits_needed ;
2008-08-24 17:42:30 +00:00
oct < < = bits_needed ;
2008-09-05 05:49:39 +00:00
bits_in_oct - = bits_needed ;
}
2008-08-24 17:42:30 +00:00
2008-09-05 05:49:39 +00:00
/*
* SMS / SM values
*/
bits_needed = 1 ;
GET_DATA ;
2008-08-24 17:42:30 +00:00
2008-09-05 05:49:39 +00:00
/* analyse bits */
2008-08-24 17:42:30 +00:00
if ( ( oct > > ( 32 - bits_needed ) ) = = 0 )
2008-09-05 05:49:39 +00:00
{
proto_tree_add_text ( tf_tree ,
tvb , curr_offset - 1 - add_ocetets , 1 + add_ocetets ,
" SMS/SM values: (%u) Bits are not available " , oct > > ( 32 - bits_needed ) ) ;
2009-05-14 18:26:18 +00:00
bit_offset + + ;
2008-09-05 05:49:39 +00:00
curr_bits_length - = bits_needed ;
2008-08-24 17:42:30 +00:00
oct < < = bits_needed ;
2008-09-05 05:49:39 +00:00
bits_in_oct - = bits_needed ;
}
2008-08-24 17:42:30 +00:00
else
2008-09-05 05:49:39 +00:00
{
curr_bits_length - = bits_needed ;
2008-08-24 17:42:30 +00:00
oct < < = bits_needed ;
2008-09-05 05:49:39 +00:00
bits_in_oct - = bits_needed ;
2009-05-14 18:26:18 +00:00
bit_offset + + ;
2008-08-24 17:42:30 +00:00
2008-09-05 05:49:39 +00:00
/*
* Switch - Measure - Switch value
2008-08-24 17:42:30 +00:00
*/
2008-09-05 05:49:39 +00:00
bits_needed = 4 ;
GET_DATA ;
2008-08-24 17:42:30 +00:00
2008-09-05 05:49:39 +00:00
/* analyse bits */
2009-05-14 18:26:18 +00:00
proto_tree_add_bits_item ( tf_tree , hf_gsm_a_gm_sms_value , tvb , bit_offset , 4 , FALSE ) ;
bit_offset + = 4 ;
2008-09-05 05:49:39 +00:00
curr_bits_length - = bits_needed ;
2008-08-24 17:42:30 +00:00
oct < < = bits_needed ;
2008-09-05 05:49:39 +00:00
bits_in_oct - = bits_needed ;
2008-08-24 17:42:30 +00:00
2008-09-05 05:49:39 +00:00
/*
* Switch - Measure value
2008-08-24 17:42:30 +00:00
*/
2008-09-05 05:49:39 +00:00
bits_needed = 4 ;
GET_DATA ;
2008-08-24 17:42:30 +00:00
2008-09-05 05:49:39 +00:00
/* analyse bits */
2009-05-14 18:26:18 +00:00
proto_tree_add_bits_item ( tf_tree , hf_gsm_a_gm_sm_value , tvb , bit_offset , 4 , FALSE ) ;
bit_offset + = 4 ;
2008-09-05 05:49:39 +00:00
curr_bits_length - = bits_needed ;
2008-08-24 17:42:30 +00:00
oct < < = bits_needed ;
2008-09-05 05:49:39 +00:00
bits_in_oct - = bits_needed ;
}
2008-08-24 17:42:30 +00:00
2008-09-05 05:49:39 +00:00
/*
2008-08-24 17:42:30 +00:00
* ECSD multislot class ?
2008-09-05 05:49:39 +00:00
*/
bits_needed = 1 ;
2008-08-24 17:42:30 +00:00
GET_DATA ;
/* analyse bits */
if ( ( oct > > ( 32 - bits_needed ) ) = = 0 )
2008-09-05 05:49:39 +00:00
{
proto_tree_add_text ( tf_tree ,
tvb , curr_offset - 1 - add_ocetets , 1 + add_ocetets ,
" ECSD multislot class: (%u) Bits are not available " , oct > > ( 32 - bits_needed ) ) ;
2009-05-14 18:26:18 +00:00
bit_offset + + ;
2008-09-05 05:49:39 +00:00
curr_bits_length - = bits_needed ;
2008-08-24 17:42:30 +00:00
oct < < = bits_needed ;
2008-09-05 05:49:39 +00:00
bits_in_oct - = bits_needed ;
}
2008-08-24 17:42:30 +00:00
else
2008-09-05 05:49:39 +00:00
{
curr_bits_length - = bits_needed ;
2008-08-24 17:42:30 +00:00
oct < < = bits_needed ;
2008-09-05 05:49:39 +00:00
bits_in_oct - = bits_needed ;
2009-05-14 18:26:18 +00:00
bit_offset + + ;
2008-08-24 17:42:30 +00:00
2008-09-05 05:49:39 +00:00
/*
* ECSD multislot class
2008-08-24 17:42:30 +00:00
*/
2008-09-05 05:49:39 +00:00
bits_needed = 5 ;
GET_DATA ;
2008-08-24 17:42:30 +00:00
2008-09-05 05:49:39 +00:00
/* analyse bits */
proto_tree_add_text ( tf_tree ,
tvb , curr_offset - 1 - add_ocetets , 1 + add_ocetets ,
" ECSD multislot class: (%u) %s " , oct > > ( 32 - bits_needed ) , multi_slot_str [ oct > > ( 32 - bits_needed ) ] ) ;
2009-05-14 18:26:18 +00:00
bit_offset + = 5 ;
2008-09-05 05:49:39 +00:00
curr_bits_length - = bits_needed ;
2008-08-24 17:42:30 +00:00
oct < < = bits_needed ;
2008-09-05 05:49:39 +00:00
bits_in_oct - = bits_needed ;
}
2008-08-24 17:42:30 +00:00
2008-09-05 05:49:39 +00:00
/*
* EGPRS multislot class ?
*/
bits_needed = 1 ;
2008-08-24 17:42:30 +00:00
GET_DATA ;
/* analyse bits */
if ( ( oct > > ( 32 - bits_needed ) ) = = 0 )
2008-09-05 05:49:39 +00:00
{
proto_tree_add_text ( tf_tree ,
tvb , curr_offset - 1 - add_ocetets , 1 + add_ocetets ,
" EGPRS multislot class: (%u) Bits are not available " , oct > > ( 32 - bits_needed ) ) ;
curr_bits_length - = bits_needed ;
2008-08-24 17:42:30 +00:00
oct < < = bits_needed ;
2008-09-05 05:49:39 +00:00
bits_in_oct - = bits_needed ;
2009-05-14 18:26:18 +00:00
bit_offset + + ;
2008-09-05 05:49:39 +00:00
}
2008-08-24 17:42:30 +00:00
else
2008-09-05 05:49:39 +00:00
{
curr_bits_length - = bits_needed ;
2008-08-24 17:42:30 +00:00
oct < < = bits_needed ;
2008-09-05 05:49:39 +00:00
bits_in_oct - = bits_needed ;
2009-05-14 18:26:18 +00:00
bit_offset + + ;
2008-08-24 17:42:30 +00:00
2008-09-05 05:49:39 +00:00
/*
* EGPRS multislot class
2008-08-24 17:42:30 +00:00
*/
2008-09-05 05:49:39 +00:00
bits_needed = 5 ;
GET_DATA ;
2008-08-24 17:42:30 +00:00
2008-09-05 05:49:39 +00:00
/* analyse bits */
proto_tree_add_text ( tf_tree ,
2008-08-24 17:42:30 +00:00
tvb , curr_offset - 1 - add_ocetets , 1 + add_ocetets ,
2008-09-05 05:49:39 +00:00
" EGPRS multislot class: (%u) %s " , oct > > ( 32 - bits_needed ) , multi_slot_str [ oct > > ( 32 - bits_needed ) ] ) ;
2009-05-14 18:26:18 +00:00
bit_offset + = 5 ;
2008-09-05 05:49:39 +00:00
curr_bits_length - = bits_needed ;
2008-08-24 17:42:30 +00:00
oct < < = bits_needed ;
2008-09-05 05:49:39 +00:00
bits_in_oct - = bits_needed ;
2008-08-24 17:42:30 +00:00
2008-09-05 05:49:39 +00:00
/*
* EGPRS Extended Dynamic Allocation Capability
2008-08-24 17:42:30 +00:00
*/
2008-09-05 05:49:39 +00:00
bits_needed = 1 ;
GET_DATA ;
2008-08-24 17:42:30 +00:00
2008-09-05 05:49:39 +00:00
/* analyse bits */
switch ( oct > > ( 32 - bits_needed ) )
{
case 0x00 : str = " Extended Dynamic Allocation Capability for EGPRS is not implemented " ; break ;
2009-05-07 21:22:36 +00:00
case 0x01 : str = " Extended Dynamic Allocation Capability for EGPRS is implemented " ; break ;
default : str = " This should not happen " ;
2008-09-05 05:49:39 +00:00
}
proto_tree_add_text ( tf_tree ,
tvb , curr_offset - 1 - add_ocetets , 1 + add_ocetets ,
" EGPRS Extended Dynamic Allocation Capability: (%u) %s " , oct > > ( 32 - bits_needed ) , str ) ;
2009-05-14 18:26:18 +00:00
bit_offset + + ;
2008-09-05 05:49:39 +00:00
curr_bits_length - = bits_needed ;
2008-08-24 17:42:30 +00:00
oct < < = bits_needed ;
2008-09-05 05:49:39 +00:00
bits_in_oct - = bits_needed ;
}
2008-08-24 17:42:30 +00:00
/*
2008-09-05 05:49:39 +00:00
* DTM GPRS Multi Slot Class ?
2008-08-24 17:42:30 +00:00
*/
2008-09-05 05:49:39 +00:00
bits_needed = 1 ;
2008-08-24 17:42:30 +00:00
GET_DATA ;
/* analyse bits */
2008-09-05 05:49:39 +00:00
if ( ( oct > > ( 32 - bits_needed ) ) = = 0 )
{
proto_tree_add_text ( tf_tree ,
2008-08-24 17:42:30 +00:00
tvb , curr_offset - 1 - add_ocetets , 1 + add_ocetets ,
2008-09-05 05:49:39 +00:00
" DTM GPRS Multi Slot Class: (%u) Bits are not available " , oct > > ( 32 - bits_needed ) ) ;
2009-05-14 18:26:18 +00:00
bit_offset + + ;
2008-09-05 05:49:39 +00:00
curr_bits_length - = bits_needed ;
oct < < = bits_needed ;
bits_in_oct - = bits_needed ;
}
else
{
curr_bits_length - = bits_needed ;
oct < < = bits_needed ;
2008-08-24 17:42:30 +00:00
bits_in_oct - = bits_needed ;
2009-05-14 18:26:18 +00:00
bit_offset + + ;
2008-08-24 17:42:30 +00:00
2008-09-05 05:49:39 +00:00
/*
* DTM GPRS Multi Slot Class
*/
bits_needed = 2 ;
2008-08-24 17:42:30 +00:00
GET_DATA ;
/* analyse bits */
2008-09-05 05:49:39 +00:00
dtm_gprs_mslot = oct > > ( 32 - bits_needed ) ;
2008-08-24 17:42:30 +00:00
switch ( oct > > ( 32 - bits_needed ) )
{
2009-05-07 21:22:36 +00:00
case 0 : str = " Unused. If received, the network shall interpret this as Multislot class 5 " ; break ;
case 1 : str = " Multislot class 5 supported " ; break ;
case 2 : str = " Multislot class 9 supported " ; break ;
case 3 : str = " Multislot class 11 supported " ; break ;
2008-08-24 17:42:30 +00:00
default : str = " This should not happen " ;
}
2008-09-05 05:49:39 +00:00
proto_tree_add_text ( tf_tree ,
tvb , curr_offset - 1 - add_ocetets , 1 + add_ocetets ,
" DTM GPRS Multi Slot Class: (%u) %s " , oct > > ( 32 - bits_needed ) , str ) ;
2009-05-14 18:26:18 +00:00
bit_offset + = 2 ;
2008-09-05 05:49:39 +00:00
curr_bits_length - = bits_needed ;
oct < < = bits_needed ;
bits_in_oct - = bits_needed ;
/*
* Single Slot DTM
*/
bits_needed = 1 ;
GET_DATA ;
/* analyse bits */
switch ( oct > > ( 32 - bits_needed ) )
{
case 0x00 : str = " Single Slot DTM not supported " ; break ;
2009-05-07 21:22:36 +00:00
case 0x01 : str = " Single Slot DTM supported " ; break ;
default : str = " This should not happen " ;
2008-09-05 05:49:39 +00:00
}
proto_tree_add_text ( tf_tree ,
2008-08-24 17:42:30 +00:00
tvb , curr_offset - 1 - add_ocetets , 1 + add_ocetets ,
2008-09-05 05:49:39 +00:00
" Single Slot DTM: (%u) %s " , oct > > ( 32 - bits_needed ) , str ) ;
2009-05-14 18:26:18 +00:00
bit_offset + + ;
2008-09-05 05:49:39 +00:00
curr_bits_length - = bits_needed ;
oct < < = bits_needed ;
bits_in_oct - = bits_needed ;
/*
* DTM EGPRS Multi Slot Class ?
*/
bits_needed = 1 ;
GET_DATA ;
/* analyse bits */
dtm_egprs_mslot = oct > > ( 32 - bits_needed ) ;
if ( ( oct > > ( 32 - bits_needed ) ) = = 0 )
{
proto_tree_add_text ( tf_tree ,
tvb , curr_offset - 1 - add_ocetets , 1 + add_ocetets ,
" DTM EGPRS Multi Slot Class: (%u) Bits are not available " , oct > > ( 32 - bits_needed ) ) ;
2009-05-14 18:26:18 +00:00
bit_offset + + ;
2008-09-05 05:49:39 +00:00
curr_bits_length - = bits_needed ;
oct < < = bits_needed ;
bits_in_oct - = bits_needed ;
}
else
{
curr_bits_length - = bits_needed ;
oct < < = bits_needed ;
bits_in_oct - = bits_needed ;
2009-05-14 18:26:18 +00:00
bit_offset + + ;
2008-09-05 05:49:39 +00:00
/*
* DTM EGPRS Multi Slot Class
*/
bits_needed = 2 ;
GET_DATA ;
/* analyse bits */
switch ( oct > > ( 32 - bits_needed ) )
{
case 0 : str = " Unused. If received, the network shall interpret this as Multislot class 5 " ; break ;
2009-05-07 21:22:36 +00:00
case 1 : str = " Multislot class 5 supported " ; break ;
case 2 : str = " Multislot class 9 supported " ; break ;
case 3 : str = " Multislot class 11 supported " ; break ;
2008-09-05 05:49:39 +00:00
default : str = " This should not happen " ;
}
proto_tree_add_text ( tf_tree ,
tvb , curr_offset - 1 - add_ocetets , 1 + add_ocetets ,
" DTM EGPRS Multi Slot Class: (%u) %s " , oct > > ( 32 - bits_needed ) , str ) ;
2009-05-14 18:26:18 +00:00
bit_offset + = 2 ;
2008-09-05 05:49:39 +00:00
curr_bits_length - = bits_needed ;
2008-08-24 17:42:30 +00:00
oct < < = bits_needed ;
2008-09-05 05:49:39 +00:00
bits_in_oct - = bits_needed ;
}
2008-08-24 17:42:30 +00:00
}
}
/*
* 8 PSK Power Capability ?
*/
bits_needed = 1 ;
2008-09-05 05:49:39 +00:00
GET_DATA ;
2008-08-24 17:42:30 +00:00
2008-09-05 05:49:39 +00:00
/* analyse bits */
2008-08-24 17:42:30 +00:00
if ( ( oct > > ( 32 - bits_needed ) ) = = 0 )
{
2008-09-05 05:49:39 +00:00
proto_tree_add_text ( tf_tree ,
tvb , curr_offset - 1 - add_ocetets , 1 + add_ocetets ,
" 8PSK Power Capability: (%u) Bits are not available " , oct > > ( 32 - bits_needed ) ) ;
2009-05-14 18:26:18 +00:00
bit_offset + + ;
2008-09-05 05:49:39 +00:00
curr_bits_length - = bits_needed ;
2008-08-24 17:42:30 +00:00
oct < < = bits_needed ;
2008-09-05 05:49:39 +00:00
bits_in_oct - = bits_needed ;
2008-08-24 17:42:30 +00:00
}
else
{
2008-09-05 05:49:39 +00:00
curr_bits_length - = bits_needed ;
2008-08-24 17:42:30 +00:00
oct < < = bits_needed ;
2008-09-05 05:49:39 +00:00
bits_in_oct - = bits_needed ;
2009-05-14 18:26:18 +00:00
bit_offset + + ;
2008-08-24 17:42:30 +00:00
2008-09-05 05:49:39 +00:00
/*
2008-08-24 17:42:30 +00:00
* 8 PSK Power Capability
2008-09-05 05:49:39 +00:00
*/
2008-08-24 17:42:30 +00:00
bits_needed = 2 ;
2008-09-05 05:49:39 +00:00
GET_DATA ;
2008-08-24 17:42:30 +00:00
2008-09-05 05:49:39 +00:00
/* analyse bits */
switch ( oct > > ( 32 - bits_needed ) )
2008-08-24 17:42:30 +00:00
{
2009-05-07 21:22:36 +00:00
case 0x00 : str = " Reserved " ; break ;
2008-09-05 05:49:39 +00:00
case 0x01 : str = " Power class E1 " ; break ;
case 0x02 : str = " Power class E2 " ; break ;
case 0x03 : str = " Power class E3 " ; break ;
2009-05-07 21:22:36 +00:00
default : str = " This should not happen " ;
2008-09-05 05:49:39 +00:00
}
2008-08-24 17:42:30 +00:00
proto_tree_add_text ( tf_tree ,
2008-09-05 05:49:39 +00:00
tvb , curr_offset - 1 - add_ocetets , 1 + add_ocetets ,
" 8PSK Power Capability: (%u) %s " , oct > > ( 32 - bits_needed ) , str ) ;
2009-05-14 18:26:18 +00:00
bit_offset + = 2 ;
2008-09-05 05:49:39 +00:00
curr_bits_length - = bits_needed ;
2008-08-24 17:42:30 +00:00
oct < < = bits_needed ;
bits_in_oct - = bits_needed ;
2008-09-05 05:49:39 +00:00
}
2008-08-24 17:42:30 +00:00
/*
* COMPACT Interference Measurement Capability
*/
bits_needed = 1 ;
2008-09-05 05:49:39 +00:00
GET_DATA ;
2008-08-24 17:42:30 +00:00
2008-09-05 05:49:39 +00:00
/* analyse bits */
switch ( oct > > ( 32 - bits_needed ) )
2008-08-24 17:42:30 +00:00
{
2008-09-05 05:49:39 +00:00
case 0x00 : str = " COMPACT Interference Measurement Capability is not implemented " ; break ;
2009-05-07 21:22:36 +00:00
case 0x01 : str = " COMPACT Interference Measurement Capability is implemented " ; break ;
default : str = " This should not happen " ;
2008-08-24 17:42:30 +00:00
}
proto_tree_add_text ( tf_tree ,
2008-09-05 05:49:39 +00:00
tvb , curr_offset - 1 - add_ocetets , 1 + add_ocetets ,
" COMPACT Interference Measurement Capability: (%u) %s " , oct > > ( 32 - bits_needed ) , str ) ;
2009-05-14 18:26:18 +00:00
bit_offset + + ;
2008-08-24 17:42:30 +00:00
curr_bits_length - = bits_needed ;
oct < < = bits_needed ;
bits_in_oct - = bits_needed ;
/*
* Revision Level Indicator
*/
bits_needed = 1 ;
2008-09-05 05:49:39 +00:00
GET_DATA ;
2008-08-24 17:42:30 +00:00
2008-09-05 05:49:39 +00:00
/* analyse bits */
switch ( oct > > ( 32 - bits_needed ) )
2008-08-24 17:42:30 +00:00
{
2008-09-05 05:49:39 +00:00
case 0x00 : str = " The ME is Release 98 or older " ; break ;
2009-05-07 21:22:36 +00:00
case 0x01 : str = " The ME is Release 99 onwards " ; break ;
default : str = " This should not happen " ;
2008-08-24 17:42:30 +00:00
}
proto_tree_add_text ( tf_tree ,
2008-09-05 05:49:39 +00:00
tvb , curr_offset - 1 - add_ocetets , 1 + add_ocetets ,
" Revision Level Indicator: (%u) %s " , oct > > ( 32 - bits_needed ) , str ) ;
2009-05-14 18:26:18 +00:00
bit_offset + + ;
2008-08-24 17:42:30 +00:00
curr_bits_length - = bits_needed ;
oct < < = bits_needed ;
bits_in_oct - = bits_needed ;
/*
* UMTS FDD Radio Access Technology Capability
*/
bits_needed = 1 ;
2008-09-05 05:49:39 +00:00
GET_DATA ;
2008-08-24 17:42:30 +00:00
2008-09-05 05:49:39 +00:00
/* analyse bits */
switch ( oct > > ( 32 - bits_needed ) )
2008-08-24 17:42:30 +00:00
{
2008-09-05 05:49:39 +00:00
case 0x00 : str = " UMTS FDD not supported " ; break ;
2009-05-07 21:22:36 +00:00
case 0x01 : str = " UMTS FDD supported " ; break ;
default : str = " This should not happen " ;
2008-08-24 17:42:30 +00:00
}
proto_tree_add_text ( tf_tree ,
2008-09-05 05:49:39 +00:00
tvb , curr_offset - 1 - add_ocetets , 1 + add_ocetets ,
" UMTS FDD Radio Access Technology Capability: (%u) %s " , oct > > ( 32 - bits_needed ) , str ) ;
2009-05-14 18:26:18 +00:00
bit_offset + + ;
2008-08-24 17:42:30 +00:00
curr_bits_length - = bits_needed ;
oct < < = bits_needed ;
bits_in_oct - = bits_needed ;
/*
* UMTS 3.84 Mcps TDD Radio Access Technology Capability
*/
bits_needed = 1 ;
2008-09-05 05:49:39 +00:00
GET_DATA ;
2008-08-24 17:42:30 +00:00
/* analyse bits */
2008-09-05 05:49:39 +00:00
switch ( oct > > ( 32 - bits_needed ) )
2008-08-24 17:42:30 +00:00
{
2008-09-05 05:49:39 +00:00
case 0x00 : str = " UMTS 3.84 Mcps TDD not supported " ; break ;
2009-05-07 21:22:36 +00:00
case 0x01 : str = " UMTS 3.84 Mcps TDD supported " ; break ;
default : str = " This should not happen " ;
2008-08-24 17:42:30 +00:00
}
proto_tree_add_text ( tf_tree ,
2008-09-05 05:49:39 +00:00
tvb , curr_offset - 1 - add_ocetets , 1 + add_ocetets ,
" UMTS 3.84 Mcps TDD Radio Access Technology Capability: (%u) %s " , oct > > ( 32 - bits_needed ) , str ) ;
2009-05-14 18:26:18 +00:00
bit_offset + + ;
2008-08-24 17:42:30 +00:00
curr_bits_length - = bits_needed ;
oct < < = bits_needed ;
bits_in_oct - = bits_needed ;
/*
* CDMA 2000 Radio Access Technology Capability
*/
bits_needed = 1 ;
2008-09-05 05:49:39 +00:00
GET_DATA ;
2008-08-24 17:42:30 +00:00
2008-09-05 05:49:39 +00:00
/* analyse bits */
switch ( oct > > ( 32 - bits_needed ) )
2008-08-24 17:42:30 +00:00
{
2008-09-05 05:49:39 +00:00
case 0x00 : str = " CDMA 2000 not supported " ; break ;
2009-05-07 21:22:36 +00:00
case 0x01 : str = " CDMA 2000 supported " ; break ;
default : str = " This should not happen " ;
2008-08-24 17:42:30 +00:00
}
proto_tree_add_text ( tf_tree ,
2008-09-05 05:49:39 +00:00
tvb , curr_offset - 1 - add_ocetets , 1 + add_ocetets ,
" CDMA 2000 Radio Access Technology Capability: (%u) %s " , oct > > ( 32 - bits_needed ) , str ) ;
2009-05-14 18:26:18 +00:00
bit_offset + + ;
2008-08-24 17:42:30 +00:00
curr_bits_length - = bits_needed ;
oct < < = bits_needed ;
bits_in_oct - = bits_needed ;
/*
* UMTS 1.28 Mcps TDD Radio Access Technology Capability
*/
bits_needed = 1 ;
2008-09-05 05:49:39 +00:00
GET_DATA ;
2008-08-24 17:42:30 +00:00
2008-09-05 05:49:39 +00:00
/* analyse bits */
switch ( oct > > ( 32 - bits_needed ) )
2008-08-24 17:42:30 +00:00
{
2008-09-05 05:49:39 +00:00
case 0x00 : str = " UMTS 1.28 Mcps TDD not supported " ; break ;
2009-05-07 21:22:36 +00:00
case 0x01 : str = " UMTS 1.28 Mcps TDD supported " ; break ;
default : str = " This should not happen " ;
2008-08-24 17:42:30 +00:00
}
proto_tree_add_text ( tf_tree ,
2008-09-05 05:49:39 +00:00
tvb , curr_offset - 1 - add_ocetets , 1 + add_ocetets ,
" UMTS 1.28 Mcps TDD Radio Access Technology Capability: (%u) %s " , oct > > ( 32 - bits_needed ) , str ) ;
2009-05-14 18:26:18 +00:00
bit_offset + + ;
2008-08-24 17:42:30 +00:00
curr_bits_length - = bits_needed ;
oct < < = bits_needed ;
bits_in_oct - = bits_needed ;
/*
* GERAN Feature Package 1
*/
bits_needed = 1 ;
2008-09-05 05:49:39 +00:00
GET_DATA ;
2008-08-24 17:42:30 +00:00
2008-09-05 05:49:39 +00:00
/* analyse bits */
switch ( oct > > ( 32 - bits_needed ) )
2008-08-24 17:42:30 +00:00
{
2008-09-05 05:49:39 +00:00
case 0x00 : str = " GERAN feature package 1 not supported " ; break ;
2009-05-07 21:22:36 +00:00
case 0x01 : str = " GERAN feature package 1 supported " ; break ;
default : str = " This should not happen " ;
2008-08-24 17:42:30 +00:00
}
proto_tree_add_text ( tf_tree ,
tvb , curr_offset - 1 - add_ocetets , 1 + add_ocetets ,
" GERAN Feature Package 1: (%u) %s " , oct > > ( 32 - bits_needed ) , str ) ;
2009-05-14 18:26:18 +00:00
bit_offset + + ;
2008-08-24 17:42:30 +00:00
curr_bits_length - = bits_needed ;
oct < < = bits_needed ;
bits_in_oct - = bits_needed ;
/*
* Extended DTM ( E ) GPRS Multi Slot Class
*/
bits_needed = 1 ;
2008-09-05 05:49:39 +00:00
GET_DATA ;
2008-08-24 17:42:30 +00:00
2008-09-05 05:49:39 +00:00
/* analyse bits */
2008-08-24 17:42:30 +00:00
if ( ( oct > > ( 32 - bits_needed ) ) = = 0 )
{
2008-09-05 05:49:39 +00:00
proto_tree_add_text ( tf_tree ,
tvb , curr_offset - 1 - add_ocetets , 1 + add_ocetets ,
" Extended DTM (E)GPRS Multi Slot Class: (%u) Bits are not available " , oct > > ( 32 - bits_needed ) ) ;
curr_bits_length - = bits_needed ;
2008-08-24 17:42:30 +00:00
oct < < = bits_needed ;
2008-09-05 05:49:39 +00:00
bits_in_oct - = bits_needed ;
2009-05-14 18:26:18 +00:00
bit_offset + + ;
2008-08-24 17:42:30 +00:00
}
else
{
2008-09-05 05:49:39 +00:00
curr_bits_length - = bits_needed ;
2008-08-24 17:42:30 +00:00
oct < < = bits_needed ;
2008-09-05 05:49:39 +00:00
bits_in_oct - = bits_needed ;
2008-08-24 17:42:30 +00:00
2008-09-05 05:49:39 +00:00
/*
2008-08-24 17:42:30 +00:00
* Extended DTM GPRS Multi Slot Class
2008-09-05 05:49:39 +00:00
*/
2008-08-24 17:42:30 +00:00
bits_needed = 2 ;
2008-09-05 05:49:39 +00:00
GET_DATA ;
2008-08-24 17:42:30 +00:00
2008-09-05 05:49:39 +00:00
/* analyse bits */
switch ( ( oct > > ( 32 - bits_needed ) ) | ( dtm_gprs_mslot < < 4 ) )
2008-08-24 17:42:30 +00:00
{
2009-05-07 21:22:36 +00:00
case 0x00 : str = " Unused. If received, it shall be interpreted as Multislot class 5 supported " ; break ;
case 0x01 : str = " Unused. If received, it shall be interpreted as Multislot class 5 supported " ; break ;
case 0x02 : str = " Unused. If received, it shall be interpreted as Multislot class 5 supported " ; break ;
case 0x03 : str = " Unused. If received, it shall be interpreted as Multislot class 5 supported " ; break ;
case 0x10 : str = " Multislot class 5 supported " ; break ;
case 0x11 : str = " Multislot class 6 supported " ; break ;
case 0x12 : str = " Unused. If received, it shall be interpreted as Multislot class 5 supported " ; break ;
case 0x13 : str = " Unused. If received, it shall be interpreted as Multislot class 5 supported " ; break ;
case 0x20 : str = " Multislot class 9 supported " ; break ;
2008-08-24 17:42:30 +00:00
case 0x21 : str = " Multislot class 10 supported " ; break ;
2009-05-07 21:22:36 +00:00
case 0x22 : str = " Unused. If received, it shall be interpreted as Multislot class 9 supported " ; break ;
case 0x23 : str = " Unused. If received, it shall be interpreted as Multislot class 9 supported " ; break ;
2008-08-24 17:42:30 +00:00
case 0x30 : str = " Multislot class 11 supported " ; break ;
case 0x31 : str = " Unused. If received, it shall be interpreted as Multislot class 11 supported " ; break ;
case 0x32 : str = " Unused. If received, it shall be interpreted as Multislot class 11 supported " ; break ;
case 0x33 : str = " Unused. If received, it shall be interpreted as Multislot class 11 supported " ; break ;
2009-05-07 21:22:36 +00:00
default : str = " This should not happen " ;
2008-09-05 05:49:39 +00:00
}
2008-08-24 17:42:30 +00:00
proto_tree_add_text ( tf_tree ,
2008-09-05 05:49:39 +00:00
tvb , curr_offset - 1 - add_ocetets , 1 + add_ocetets ,
" Extended DTM GPRS Multi Slot Class: (%u) %s " , oct > > ( 32 - bits_needed ) , str ) ;
2009-05-14 18:26:18 +00:00
bit_offset + = 2 ;
2008-09-05 05:49:39 +00:00
curr_bits_length - = bits_needed ;
2008-08-24 17:42:30 +00:00
oct < < = bits_needed ;
bits_in_oct - = bits_needed ;
2008-09-05 05:49:39 +00:00
if ( dtm_egprs_mslot < = 3 )
{
/*
2008-08-24 17:42:30 +00:00
* Extended DTM EGPRS Multi Slot Class
2008-09-05 05:49:39 +00:00
*/
bits_needed = 2 ;
GET_DATA ;
2008-08-24 17:42:30 +00:00
2008-09-05 05:49:39 +00:00
/* analyse bits */
switch ( ( oct > > ( 32 - bits_needed ) ) | ( dtm_egprs_mslot < < 4 ) )
2008-08-24 17:42:30 +00:00
{
2009-05-07 21:22:36 +00:00
case 0x00 : str = " Unused. If received, it shall be interpreted as Multislot class 5 supported " ; break ;
case 0x01 : str = " Unused. If received, it shall be interpreted as Multislot class 5 supported " ; break ;
case 0x02 : str = " Unused. If received, it shall be interpreted as Multislot class 5 supported " ; break ;
case 0x03 : str = " Unused. If received, it shall be interpreted as Multislot class 5 supported " ; break ;
case 0x10 : str = " Multislot class 5 supported " ; break ;
case 0x11 : str = " Multislot class 6 supported " ; break ;
case 0x12 : str = " Unused. If received, it shall be interpreted as Multislot class 5 supported " ; break ;
case 0x13 : str = " Unused. If received, it shall be interpreted as Multislot class 5 supported " ; break ;
case 0x20 : str = " Multislot class 9 supported " ; break ;
2008-08-24 17:42:30 +00:00
case 0x21 : str = " Multislot class 10 supported " ; break ;
2009-05-07 21:22:36 +00:00
case 0x22 : str = " Unused. If received, it shall be interpreted as Multislot class 9 supported " ; break ;
case 0x23 : str = " Unused. If received, it shall be interpreted as Multislot class 9 supported " ; break ;
2008-08-24 17:42:30 +00:00
case 0x30 : str = " Multislot class 11 supported " ; break ;
case 0x31 : str = " Unused. If received, it shall be interpreted as Multislot class 11 supported " ; break ;
2008-09-05 05:49:39 +00:00
case 0x32 : str = " Unused. If received, it shall be interpreted as Multislot class 11 supported " ; break ;
2008-08-24 17:42:30 +00:00
case 0x33 : str = " Unused. If received, it shall be interpreted as Multislot class 11 supported " ; break ;
2009-05-07 21:22:36 +00:00
default : str = " This should not happen " ;
2008-09-05 05:49:39 +00:00
}
2008-08-24 17:42:30 +00:00
2008-09-05 05:49:39 +00:00
proto_tree_add_text ( tf_tree ,
tvb , curr_offset - 1 - add_ocetets , 1 + add_ocetets ,
" Extended DTM EGPRS Multi Slot Class: (%u) %s " , oct > > ( 32 - bits_needed ) , str ) ;
2009-05-14 18:26:18 +00:00
bit_offset + = 2 ;
2008-09-05 05:49:39 +00:00
curr_bits_length - = bits_needed ;
2008-08-24 17:42:30 +00:00
oct < < = bits_needed ;
bits_in_oct - = bits_needed ;
2008-09-05 05:49:39 +00:00
}
2008-08-24 17:42:30 +00:00
}
/*
* Modulation based multislot class support
*/
bits_needed = 1 ;
2008-09-05 05:49:39 +00:00
GET_DATA ;
2008-08-24 17:42:30 +00:00
2008-09-05 05:49:39 +00:00
/* analyse bits */
switch ( oct > > ( 32 - bits_needed ) )
2008-08-24 17:42:30 +00:00
{
2008-09-05 05:49:39 +00:00
case 0x00 : str = " Modulation based multislot class not supported " ; break ;
2009-05-07 21:22:36 +00:00
case 0x01 : str = " Modulation based multislot class supported " ; break ;
default : str = " This should not happen " ;
2008-08-24 17:42:30 +00:00
}
proto_tree_add_text ( tf_tree ,
2008-09-05 05:49:39 +00:00
tvb , curr_offset - 1 - add_ocetets , 1 + add_ocetets ,
" Modulation based multislot class support: (%u) %s " , oct > > ( 32 - bits_needed ) , str ) ;
2009-05-14 18:26:18 +00:00
bit_offset + + ;
2008-08-24 17:42:30 +00:00
curr_bits_length - = bits_needed ;
oct < < = bits_needed ;
bits_in_oct - = bits_needed ;
/*
* High Multislot Capability
*/
bits_needed = 1 ;
2008-09-05 05:49:39 +00:00
GET_DATA ;
2008-08-24 17:42:30 +00:00
2008-09-05 05:49:39 +00:00
/* analyse bits */
2008-08-24 17:42:30 +00:00
if ( ( oct > > ( 32 - bits_needed ) ) = = 0 )
{
2008-09-05 05:49:39 +00:00
proto_tree_add_text ( tf_tree ,
tvb , curr_offset - 1 - add_ocetets , 1 + add_ocetets ,
" High Multislot Capability: (%u) Bits are not available " , oct > > ( 32 - bits_needed ) ) ;
2009-05-14 18:26:18 +00:00
bit_offset + + ;
2008-09-05 05:49:39 +00:00
curr_bits_length - = bits_needed ;
2008-08-24 17:42:30 +00:00
oct < < = bits_needed ;
2008-09-05 05:49:39 +00:00
bits_in_oct - = bits_needed ;
2008-08-24 17:42:30 +00:00
}
else
{
2008-09-05 05:49:39 +00:00
curr_bits_length - = bits_needed ;
2008-08-24 17:42:30 +00:00
oct < < = bits_needed ;
2008-09-05 05:49:39 +00:00
bits_in_oct - = bits_needed ;
2009-05-14 18:26:18 +00:00
bit_offset + + ;
2008-08-24 17:42:30 +00:00
2008-09-05 05:49:39 +00:00
/*
2008-08-24 17:42:30 +00:00
* High Multislot Capability
2008-09-05 05:49:39 +00:00
*/
2008-08-24 17:42:30 +00:00
bits_needed = 2 ;
2008-09-05 05:49:39 +00:00
GET_DATA ;
2008-08-24 17:42:30 +00:00
2008-09-05 05:49:39 +00:00
/* analyse bits */
2008-08-24 17:42:30 +00:00
proto_tree_add_text ( tf_tree ,
tvb , curr_offset - 1 - add_ocetets , 1 + add_ocetets ,
2009-05-07 21:22:36 +00:00
" High Multislot Capability: 0x%02x (%u) "
" - This field effect all other multislot fields. "
" To understand the value please read TS 24.008 5.6.0 "
" Release 5 Chap 10.5.5.12 Page 406 " ,
oct > > ( 32 - bits_needed ) ,
oct > > ( 32 - bits_needed ) ) ;
2009-05-14 18:26:18 +00:00
bit_offset + = 2 ;
2008-09-05 05:49:39 +00:00
curr_bits_length - = bits_needed ;
2008-08-24 17:42:30 +00:00
oct < < = bits_needed ;
bits_in_oct - = bits_needed ;
2008-09-05 05:49:39 +00:00
}
2008-08-24 17:42:30 +00:00
/*
* GERAN Iu Mode Capability
*/
bits_needed = 1 ;
2008-09-05 05:49:39 +00:00
GET_DATA ;
2008-08-24 17:42:30 +00:00
2008-09-05 05:49:39 +00:00
/* analyse bits */
switch ( oct > > ( 32 - bits_needed ) )
2008-08-24 17:42:30 +00:00
{
2008-09-05 05:49:39 +00:00
case 0x00 : str = " GERAN Iu mode not supported " ; break ;
2009-05-07 21:22:36 +00:00
case 0x01 : str = " GERAN Iu mode supported " ; break ;
default : str = " This should not happen " ;
2008-08-24 17:42:30 +00:00
}
proto_tree_add_text ( tf_tree ,
2008-09-05 05:49:39 +00:00
tvb , curr_offset - 1 - add_ocetets , 1 + add_ocetets ,
" GERAN Iu Mode Capability: (%u) %s " , oct > > ( 32 - bits_needed ) , str ) ;
2009-05-14 18:26:18 +00:00
bit_offset + + ;
2008-08-24 17:42:30 +00:00
curr_bits_length - = bits_needed ;
oct < < = bits_needed ;
bits_in_oct - = bits_needed ;
/*
* GMSK / 8 - PSK Multislot Power Profile
*/
bits_needed = 1 ;
2008-09-05 05:49:39 +00:00
GET_DATA ;
2008-08-24 17:42:30 +00:00
2008-09-05 05:49:39 +00:00
/* analyse bits */
2008-08-24 17:42:30 +00:00
if ( ( oct > > ( 32 - bits_needed ) ) = = 0 )
{
2008-09-05 05:49:39 +00:00
proto_tree_add_text ( tf_tree ,
tvb , curr_offset - 1 - add_ocetets , 1 + add_ocetets ,
" GMSK/8-PSK Multislot Power Profile: (%u) Bits are not available " , oct > > ( 32 - bits_needed ) ) ;
2009-05-14 18:26:18 +00:00
bit_offset + + ;
2008-09-05 05:49:39 +00:00
curr_bits_length - = bits_needed ;
2008-08-24 17:42:30 +00:00
oct < < = bits_needed ;
2008-09-05 05:49:39 +00:00
bits_in_oct - = bits_needed ;
2008-08-24 17:42:30 +00:00
}
else
{
2008-09-05 05:49:39 +00:00
curr_bits_length - = bits_needed ;
2008-08-24 17:42:30 +00:00
oct < < = bits_needed ;
2008-09-05 05:49:39 +00:00
bits_in_oct - = bits_needed ;
2009-05-14 18:26:18 +00:00
bit_offset + + ;
2008-08-24 17:42:30 +00:00
2008-09-05 05:49:39 +00:00
/*
2008-08-24 17:42:30 +00:00
* GMSK Multislot Power Profile
2008-09-05 05:49:39 +00:00
*/
2008-08-24 17:42:30 +00:00
bits_needed = 2 ;
2008-09-05 05:49:39 +00:00
GET_DATA ;
2008-08-24 17:42:30 +00:00
2008-09-05 05:49:39 +00:00
/* analyse bits */
switch ( oct > > ( 32 - bits_needed ) )
{
case 0x00 : str = " GMSK_MULTISLOT_POWER_PROFILE 0 " ; break ;
case 0x01 : str = " GMSK_MULTISLOT_POWER_PROFILE 1 " ; break ;
case 0x02 : str = " GMSK_MULTISLOT_POWER_PROFILE 2 " ; break ;
case 0x03 : str = " GMSK_MULTISLOT_POWER_PROFILE 3 " ; break ;
2009-05-07 21:22:36 +00:00
default : str = " This should not happen " ;
2008-09-05 05:49:39 +00:00
}
2008-08-24 17:42:30 +00:00
proto_tree_add_text ( tf_tree ,
2008-09-05 05:49:39 +00:00
tvb , curr_offset - 1 - add_ocetets , 1 + add_ocetets ,
" GMSK Multislot Power Profile: (%u) %s " , oct > > ( 32 - bits_needed ) , str ) ;
2009-05-14 18:26:18 +00:00
bit_offset + = 2 ;
2008-09-05 05:49:39 +00:00
curr_bits_length - = bits_needed ;
2008-08-24 17:42:30 +00:00
oct < < = bits_needed ;
bits_in_oct - = bits_needed ;
2008-09-05 05:49:39 +00:00
/*
2008-08-24 17:42:30 +00:00
* 8 - PSK Multislot Power Profile
2008-09-05 05:49:39 +00:00
*/
2008-08-24 17:42:30 +00:00
bits_needed = 2 ;
2008-09-05 05:49:39 +00:00
GET_DATA ;
2008-08-24 17:42:30 +00:00
2008-09-05 05:49:39 +00:00
/* analyse bits */
switch ( oct > > ( 32 - bits_needed ) )
{
case 0x00 : str = " 8-PSK_MULTISLOT_POWER_PROFILE 0 " ; break ;
case 0x01 : str = " 8-PSK_MULTISLOT_POWER_PROFILE 1 " ; break ;
case 0x02 : str = " 8-PSK_MULTISLOT_POWER_PROFILE 2 " ; break ;
case 0x03 : str = " 8-PSK_MULTISLOT_POWER_PROFILE 3 " ; break ;
2009-05-07 21:22:36 +00:00
default : str = " This should not happen " ;
2008-09-05 05:49:39 +00:00
}
2008-08-24 17:42:30 +00:00
proto_tree_add_text ( tf_tree ,
tvb , curr_offset - 1 - add_ocetets , 1 + add_ocetets ,
" 8-PSK Multislot Power Profile: (%u) %s " , oct > > ( 32 - bits_needed ) , str ) ;
2009-05-14 18:26:18 +00:00
bit_offset + = 2 ;
2008-09-05 05:49:39 +00:00
curr_bits_length - = bits_needed ;
2008-08-24 17:42:30 +00:00
oct < < = bits_needed ;
bits_in_oct - = bits_needed ;
2008-09-05 05:49:39 +00:00
}
2008-08-24 17:42:30 +00:00
2008-09-05 05:49:39 +00:00
/*
* we are too long . . . so jump over it
*/
while ( curr_bits_length > 0 )
{
if ( curr_bits_length > 8 )
bits_needed = 8 ;
else
bits_needed = curr_bits_length ;
GET_DATA ;
curr_bits_length - = bits_needed ;
2008-08-24 17:42:30 +00:00
oct < < = bits_needed ;
2008-09-05 05:49:39 +00:00
bits_in_oct - = bits_needed ;
}
2008-08-24 17:42:30 +00:00
} while ( 1 ) ;
curr_offset + = curr_len ;
EXTRANEOUS_DATA_CHECK ( len , curr_offset - offset ) ;
return ( curr_offset - offset ) ;
}
/*
* [ 7 ] 10.5 .5 .14
*/
2008-12-23 20:49:15 +00:00
static guint16
2008-09-05 05:49:39 +00:00
de_gmm_cause ( tvbuff_t * tvb , proto_tree * tree , guint32 offset , guint len _U_ , gchar * add_string _U_ , int string_len _U_ )
2008-08-24 17:42:30 +00:00
{
2009-05-07 21:22:36 +00:00
guint8 oct ;
guint32 curr_offset ;
const gchar * str ;
2008-08-24 17:42:30 +00:00
curr_offset = offset ;
oct = tvb_get_guint8 ( tvb , curr_offset ) ;
switch ( oct )
{
/* additional causes can be found in annex g */
2009-05-07 21:22:36 +00:00
case 0x02 : str = " IMSI unknown in HLR " ; break ;
case 0x03 : str = " Illegal MS " ; break ;
case 0x04 : str = " IMSI unknown in VLR " ; break ;
case 0x05 : str = " IMEI not accepted " ; break ;
case 0x06 : str = " Illegal ME " ; break ;
case 0x07 : str = " GPRS services not allowed " ; break ;
case 0x08 : str = " GPRS services and non-GPRS services not allowed " ; break ;
case 0x09 : str = " MS identity cannot be derived by the network " ; break ;
case 0x0a : str = " Implicitly detached " ; break ;
case 0x0b : str = " PLMN not allowed " ; break ;
case 0x0c : str = " Location Area not allowed " ; break ;
case 0x0d : str = " Roaming not allowed in this location area " ; break ;
case 0x0e : str = " GPRS services not allowed in this PLMN " ; break ;
case 0x0f : str = " No Suitable Cells In Location Area " ; break ;
case 0x10 : str = " MSC temporarily not reachable " ; break ;
case 0x11 : str = " Network failure " ; break ;
case 0x14 : str = " MAC failure " ; break ;
case 0x15 : str = " Synch failure " ; break ;
case 0x16 : str = " Congestion " ; break ;
case 0x17 : str = " GSM authentication unacceptable " ; break ;
case 0x20 : str = " Service option not supported " ; break ;
case 0x21 : str = " Requested service option not subscribed " ; break ;
case 0x22 : str = " Service option temporarily out of order " ; break ;
case 0x26 : str = " Call cannot be identified " ; break ;
case 0x28 : str = " No PDP context activated " ; break ;
case 0x30 : str = " retry upon entry into a new cell " ; break ;
case 0x31 : str = " retry upon entry into a new cell " ; break ;
case 0x32 : str = " retry upon entry into a new cell " ; break ;
case 0x33 : str = " retry upon entry into a new cell " ; break ;
case 0x34 : str = " retry upon entry into a new cell " ; break ;
case 0x35 : str = " retry upon entry into a new cell " ; break ;
case 0x36 : str = " retry upon entry into a new cell " ; break ;
case 0x37 : str = " retry upon entry into a new cell " ; break ;
case 0x38 : str = " retry upon entry into a new cell " ; break ;
case 0x39 : str = " retry upon entry into a new cell " ; break ;
case 0x3a : str = " retry upon entry into a new cell " ; break ;
case 0x3b : str = " retry upon entry into a new cell " ; break ;
case 0x3c : str = " retry upon entry into a new cell " ; break ;
case 0x3d : str = " retry upon entry into a new cell " ; break ;
case 0x3e : str = " retry upon entry into a new cell " ; break ;
case 0x3f : str = " retry upon entry into a new cell " ; break ;
case 0x5f : str = " Semantically incorrect message " ; break ;
case 0x60 : str = " Invalid mandatory information " ; break ;
case 0x61 : str = " Message type non-existent or not implemented " ; break ;
2008-08-24 17:42:30 +00:00
case 0x62 : str = " Message type not compatible with the protocol state " ; break ;
case 0x63 : str = " Information element non-existent or not implemented " ; break ;
2009-05-07 21:22:36 +00:00
case 0x64 : str = " Conditional IE error " ; break ;
case 0x65 : str = " Message not compatible with the protocol state " ; break ;
case 0x6f : str = " Protocol error, unspecified " ; break ;
default : str = " Protocol error, unspecified " ;
2008-08-24 17:42:30 +00:00
}
proto_tree_add_text ( tree ,
2008-09-05 05:49:39 +00:00
tvb , curr_offset , 1 ,
" gmm Cause: (%u) %s " ,
oct ,
str ) ;
2008-08-24 17:42:30 +00:00
curr_offset + + ;
/* no length check possible */
return ( curr_offset - offset ) ;
}
/*
* [ 7 ] 10.5 .5 .15 Routing area identification
*/
2008-12-23 20:49:15 +00:00
guint16
2008-09-05 05:49:39 +00:00
de_gmm_rai ( tvbuff_t * tvb , proto_tree * tree , guint32 offset , guint len _U_ , gchar * add_string _U_ , int string_len _U_ )
2008-08-24 17:42:30 +00:00
{
2009-05-07 21:22:36 +00:00
proto_tree * subtree ;
proto_item * item ;
guint32 mcc ;
guint32 mnc ;
guint32 lac ;
guint32 rac ;
guint32 curr_offset ;
2008-08-24 17:42:30 +00:00
curr_offset = offset ;
mcc = ( tvb_get_guint8 ( tvb , curr_offset ) & 0x0f ) < < 8 ;
mcc | = ( tvb_get_guint8 ( tvb , curr_offset ) & 0xf0 ) ;
mcc | = ( tvb_get_guint8 ( tvb , curr_offset + 1 ) & 0x0f ) ;
mnc = ( tvb_get_guint8 ( tvb , curr_offset + 2 ) & 0x0f ) < < 8 ;
mnc | = ( tvb_get_guint8 ( tvb , curr_offset + 2 ) & 0xf0 ) ;
mnc | = ( tvb_get_guint8 ( tvb , curr_offset + 1 ) & 0xf0 ) > > 4 ;
if ( ( mnc & 0x000f ) = = 0x000f )
mnc = mnc > > 4 ;
lac = tvb_get_guint8 ( tvb , curr_offset + 3 ) ;
lac < < = 8 ;
lac | = tvb_get_guint8 ( tvb , curr_offset + 4 ) ;
rac = tvb_get_guint8 ( tvb , curr_offset + 5 ) ;
item = proto_tree_add_text ( tree ,
tvb , curr_offset , 6 ,
" Routing area identification: %x-%x-%x-%x " ,
mcc , mnc , lac , rac ) ;
subtree = proto_item_add_subtree ( item , ett_gmm_rai ) ;
dissect_e212_mcc_mnc ( tvb , subtree , offset ) ;
curr_offset + = 6 ;
/* no length check possible */
return ( curr_offset - offset ) ;
}
/*
* [ 7 ] 10.5 .5 .17
*/
2008-12-23 20:49:15 +00:00
static guint16
2008-09-05 05:49:39 +00:00
de_gmm_update_res ( tvbuff_t * tvb , proto_tree * tree , guint32 offset , guint len _U_ , gchar * add_string _U_ , int string_len _U_ )
2008-08-24 17:42:30 +00:00
{
2009-05-07 21:22:36 +00:00
guint8 oct ;
guint32 curr_offset ;
const gchar * str ;
2008-08-24 17:42:30 +00:00
curr_offset = offset ;
oct = tvb_get_guint8 ( tvb , curr_offset ) ;
/* IMPORTANT - IT'S ASSUMED THAT THE INFORMATION IS IN THE HIGHER NIBBLE */
oct > > = 4 ;
switch ( oct & 7 )
{
2009-05-07 21:22:36 +00:00
case 0 : str = " RA updated " ; break ;
case 1 : str = " combined RA/LA updated " ; break ;
2008-08-24 17:42:30 +00:00
default : str = " reserved " ;
}
proto_tree_add_text ( tree ,
2008-09-05 05:49:39 +00:00
tvb , curr_offset , 1 ,
" Update Result: (%u) %s " ,
oct & 7 ,
str ) ;
2008-08-24 17:42:30 +00:00
curr_offset + + ;
/* no length check possible */
return ( curr_offset - offset ) ;
}
/*
* [ 7 ] 10.5 .5 .18
*/
2008-12-23 20:49:15 +00:00
static guint16
2008-09-05 05:49:39 +00:00
de_gmm_update_type ( tvbuff_t * tvb , proto_tree * tree , guint32 offset , guint len _U_ , gchar * add_string _U_ , int string_len _U_ )
2008-08-24 17:42:30 +00:00
{
2009-05-07 21:22:36 +00:00
guint8 oct ;
guint8 oct_ciph ;
guint32 curr_offset ;
const gchar * str_follow ;
const gchar * str_update ;
proto_item * tf = NULL ;
proto_tree * tf_tree = NULL ;
2008-08-24 17:42:30 +00:00
curr_offset = offset ;
oct = tvb_get_guint8 ( tvb , curr_offset ) ;
oct_ciph = oct > > 4 ;
oct & = 0x0f ;
switch ( oct & 7 )
{
2009-05-07 21:22:36 +00:00
case 0 : str_update = " RA updating " ; break ;
case 1 : str_update = " combined RA/LA updating " ; break ;
case 2 : str_update = " combined RA/LA updating with IMSI attach " ; break ;
case 3 : str_update = " Periodic updating " ; break ;
2008-08-24 17:42:30 +00:00
default : str_update = " reserved " ;
}
switch ( oct & 8 )
{
2009-05-07 21:22:36 +00:00
case 8 : str_follow = " Follow-on request pending " ; break ;
2008-08-24 17:42:30 +00:00
default : str_follow = " No follow-on request pending " ;
}
tf = proto_tree_add_text ( tree ,
tvb , curr_offset , 1 ,
" Update Type " ) ;
tf_tree = proto_item_add_subtree ( tf , ett_gmm_update_type ) ;
proto_tree_add_text ( tf_tree ,
2008-09-05 05:49:39 +00:00
tvb , curr_offset , 1 ,
" Type: (%u) %s " ,
oct & 7 ,
str_update ) ;
2008-08-24 17:42:30 +00:00
proto_tree_add_text ( tf_tree ,
2008-09-05 05:49:39 +00:00
tvb , curr_offset , 1 ,
" Follow: (%u) %s " ,
( oct > > 3 ) & 1 ,
str_follow ) ;
2008-08-24 17:42:30 +00:00
/* The ciphering key sequence number is added here */
proto_tree_add_text ( tree ,
2008-09-05 05:49:39 +00:00
tvb , curr_offset , 1 ,
" Ciphering key sequence number: 0x%02x (%u) " ,
oct_ciph ,
oct_ciph ) ;
2008-08-24 17:42:30 +00:00
curr_offset + + ;
/* no length check possible */
return ( curr_offset - offset ) ;
}
/*
* [ 7 ] 10.5 .5 .19
*/
2008-12-23 20:49:15 +00:00
static guint16
2008-09-05 05:49:39 +00:00
de_gmm_ac_ref_nr ( tvbuff_t * tvb , proto_tree * tree , guint32 offset , guint len _U_ , gchar * add_string _U_ , int string_len _U_ )
2008-08-24 17:42:30 +00:00
{
guint8 oct ;
guint32 curr_offset ;
curr_offset = offset ;
oct = tvb_get_guint8 ( tvb , curr_offset ) ;
proto_tree_add_text ( tree ,
2008-09-05 05:49:39 +00:00
tvb , curr_offset , 1 ,
" A&C reference number: 0x%02x (%u) " ,
oct & 0xf ,
oct & 0xf ) ;
2008-08-24 17:42:30 +00:00
curr_offset + + ;
/* no length check possible */
return ( curr_offset - offset ) ;
}
/*
* [ 7 ] 10.5 .5 .19
*/
2008-12-23 20:49:15 +00:00
static guint16
2008-09-05 05:49:39 +00:00
de_gmm_ac_ref_nr_h ( tvbuff_t * tvb , proto_tree * tree , guint32 offset , guint len _U_ , gchar * add_string _U_ , int string_len _U_ )
2008-08-24 17:42:30 +00:00
{
guint8 oct ;
guint32 curr_offset ;
curr_offset = offset ;
oct = tvb_get_guint8 ( tvb , curr_offset ) ;
/* IMPORTANT - IT'S ASSUMED THAT THE INFORMATION IS IN THE HIGHER NIBBLE */
oct > > = 4 ;
proto_tree_add_text ( tree ,
2008-09-05 05:49:39 +00:00
tvb , curr_offset , 1 ,
" A&C reference number: 0x%02x (%u) " ,
oct ,
oct ) ;
2008-08-24 17:42:30 +00:00
curr_offset + + ;
/* no length check possible */
return ( curr_offset - offset ) ;
}
/*
* [ 8 ] 10.5 .5 .20
*/
2008-12-23 20:49:15 +00:00
static guint16
2008-09-05 05:49:39 +00:00
de_gmm_service_type ( tvbuff_t * tvb , proto_tree * tree , guint32 offset , guint len _U_ , gchar * add_string _U_ , int string_len _U_ )
2008-08-24 17:42:30 +00:00
{
2009-05-07 21:22:36 +00:00
guint8 oct ;
guint8 oct_ciph ;
guint32 curr_offset ;
const gchar * str ;
2008-08-24 17:42:30 +00:00
curr_offset = offset ;
oct = tvb_get_guint8 ( tvb , curr_offset ) ;
oct_ciph = oct ;
oct_ciph & = 7 ;
oct = oct > > 4 ;
switch ( oct & 7 )
{
case 0 : str = " Signalling " ; break ;
case 1 : str = " Data " ; break ;
case 2 : str = " Paging Response " ; break ;
case 3 : str = " MBMS Notification Response " ; break ; /* reponse->response*/
default : str = " reserved " ;
}
/* The ciphering key sequence number is added here */
proto_tree_add_text ( tree ,
2008-09-05 05:49:39 +00:00
tvb , curr_offset , 1 ,
" Ciphering key sequence number: 0x%02x (%u) " ,
oct_ciph ,
oct_ciph ) ;
2008-08-24 17:42:30 +00:00
proto_tree_add_text ( tree ,
2008-09-05 05:49:39 +00:00
tvb , curr_offset , 1 ,
" Service Type: (%u) %s " ,
oct & 7 ,
str ) ;
2008-08-24 17:42:30 +00:00
curr_offset + + ;
/* no length check possible */
return ( curr_offset - offset ) ;
}
/*
* [ 7 ] 10.5 .5 .21
*/
2008-12-23 20:49:15 +00:00
static guint16
2008-09-05 05:49:39 +00:00
de_gmm_cell_notfi ( tvbuff_t * tvb , proto_tree * tree , guint32 offset , guint len _U_ , gchar * add_string _U_ , int string_len _U_ )
2008-08-24 17:42:30 +00:00
{
guint32 curr_offset ;
curr_offset = offset ;
proto_tree_add_text ( tree ,
tvb , curr_offset , 0 ,
" Cell Notification " ) ;
/* no length check possible */
return ( curr_offset - offset ) ;
}
/*
* [ 7 ] 10.5 .5 .22
*/
2008-12-23 20:49:15 +00:00
static guint16
2008-09-05 05:49:39 +00:00
de_gmm_ps_lcs_cap ( tvbuff_t * tvb , proto_tree * tree , guint32 offset , guint len _U_ , gchar * add_string _U_ , int string_len _U_ )
2008-08-24 17:42:30 +00:00
{
guint8 oct ;
guint32 curr_offset ;
gchar str_otd [ 2 ] [ 40 ] = { " MS assisted E-OTD not supported " ,
" MS assisted E-OTD supported " } ;
gchar str_gps [ 2 ] [ 40 ] = { " MS assisted GPS not supported " ,
" MS assisted GPS supported " } ;
curr_offset = offset ;
oct = tvb_get_guint8 ( tvb , curr_offset ) ;
oct < < = 3 ; /* move away the spare bits */
proto_tree_add_text ( tree ,
2008-09-05 05:49:39 +00:00
tvb , curr_offset , 1 ,
" OTD-A: (%u) %s " ,
oct > > 7 ,
str_otd [ oct > > 7 ] ) ;
oct < < = 1 ;
2008-08-24 17:42:30 +00:00
proto_tree_add_text ( tree ,
2008-09-05 05:49:39 +00:00
tvb , curr_offset , 1 ,
" OTD-B: (%u) %s " ,
oct > > 7 ,
str_otd [ oct > > 7 ] ) ;
oct < < = 1 ;
2008-08-24 17:42:30 +00:00
proto_tree_add_text ( tree ,
2008-09-05 05:49:39 +00:00
tvb , curr_offset , 1 ,
" GPS-A: (%u) %s " ,
oct > > 7 ,
str_gps [ oct > > 7 ] ) ;
oct < < = 1 ;
2008-08-24 17:42:30 +00:00
proto_tree_add_text ( tree ,
2008-09-05 05:49:39 +00:00
tvb , curr_offset , 1 ,
" GPS-B: (%u) %s " ,
oct > > 7 ,
str_gps [ oct > > 7 ] ) ;
oct < < = 1 ;
2008-08-24 17:42:30 +00:00
proto_tree_add_text ( tree ,
2008-09-05 05:49:39 +00:00
tvb , curr_offset , 1 ,
" GPS-C: (%u) %s " ,
oct > > 7 ,
str_gps [ oct > > 7 ] ) ;
2008-08-24 17:42:30 +00:00
curr_offset + + ;
EXTRANEOUS_DATA_CHECK ( len , curr_offset - offset ) ;
return ( curr_offset - offset ) ;
}
/*
* [ 7 ] 10.5 .5 .23
*/
2008-12-23 20:49:15 +00:00
static guint16
2008-09-05 05:49:39 +00:00
de_gmm_net_feat_supp ( tvbuff_t * tvb , proto_tree * tree , guint32 offset , guint len _U_ , gchar * add_string _U_ , int string_len _U_ )
2008-08-24 17:42:30 +00:00
{
guint8 oct ;
guint32 curr_offset ;
const gchar * str ;
curr_offset = offset ;
oct = tvb_get_guint8 ( tvb , curr_offset ) ;
switch ( oct & 8 )
{
case 8 : str = " LCS-MOLR via PS domain not supported " ; break ;
default : str = " LCS-MOLR via PS domain supported " ;
}
proto_tree_add_text ( tree ,
2008-09-05 05:49:39 +00:00
tvb , curr_offset , 1 ,
" Network Feature Support: (%u) %s " ,
( oct > > 3 ) & 1 ,
str ) ;
2008-08-24 17:42:30 +00:00
curr_offset + + ;
/* no length check possible */
return ( curr_offset - offset ) ;
}
2008-11-17 19:41:44 +00:00
/* [7] 10.5.5.24 Inter RAT information container */
2008-12-23 20:49:15 +00:00
static guint16
2008-11-17 19:41:44 +00:00
de_gmm_rat_info_container ( tvbuff_t * tvb , proto_tree * tree , guint32 offset , guint len , gchar * add_string _U_ , int string_len _U_ )
2008-08-24 17:42:30 +00:00
{
guint32 curr_offset ;
2008-11-17 19:41:44 +00:00
tvbuff_t * rrc_irat_ho_info_tvb ;
static packet_info p_info ;
2008-08-24 17:42:30 +00:00
curr_offset = offset ;
/* The value part of the Inter RAT information container information element is the INTER RAT HANDOVER INFO as
defined in 3 GPP TS 25.331 [ 23 c ] . If this field includes padding bits , they are defined in 3 GPP TS 25.331 [ 23 c ] . */
2008-11-17 19:41:44 +00:00
rrc_irat_ho_info_tvb = tvb_new_subset ( tvb , curr_offset , len , len ) ;
if ( rrc_irat_ho_info_handle )
call_dissector ( rrc_irat_ho_info_handle , rrc_irat_ho_info_tvb , & p_info , tree ) ;
else
proto_tree_add_text ( tree , tvb , curr_offset , len , " INTER RAT HANDOVER INFO - Not decoded " ) ;
2008-08-24 17:42:30 +00:00
return len ;
}
/*
* [ 7 ] 10.5 .7 .1
*/
2008-12-23 20:49:15 +00:00
static guint16
2008-09-05 05:49:39 +00:00
de_gc_context_stat ( tvbuff_t * tvb , proto_tree * tree , guint32 offset , guint len _U_ , gchar * add_string _U_ , int string_len _U_ )
2008-08-24 17:42:30 +00:00
{
guint8 oct ;
guint16 pdp_nr ;
guint32 curr_offset ;
proto_item * tf = NULL ;
2008-09-05 05:49:39 +00:00
proto_tree * tf_tree = NULL ;
2008-08-24 17:42:30 +00:00
curr_offset = offset ;
oct = tvb_get_guint8 ( tvb , curr_offset ) ;
tf = proto_tree_add_text ( tree ,
tvb , curr_offset , 1 ,
" PDP Context Status " ) ;
tf_tree = proto_item_add_subtree ( tf , ett_gmm_context_stat ) ;
oct = tvb_get_guint8 ( tvb , curr_offset ) ;
for ( pdp_nr = 0 ; pdp_nr < 16 ; pdp_nr + + )
{
2008-09-05 05:49:39 +00:00
if ( pdp_nr = = 8 )
{
curr_offset + + ;
oct = tvb_get_guint8 ( tvb , curr_offset ) ;
}
proto_tree_add_text ( tf_tree ,
tvb , curr_offset , 1 ,
" NSAPI %d: (%u) %s " , pdp_nr ,
oct & 1 ,
2008-11-17 19:41:44 +00:00
pdp_str [ oct & 1 ] ) ;
2008-09-05 05:49:39 +00:00
oct > > = 1 ;
2008-08-24 17:42:30 +00:00
}
curr_offset + + ;
EXTRANEOUS_DATA_CHECK ( len , curr_offset - offset ) ;
return ( curr_offset - offset ) ;
}
/*
* [ 7 ] 10.5 .7 .2
*/
2008-12-23 20:49:15 +00:00
static guint16
2008-09-05 05:49:39 +00:00
de_gc_radio_prio ( tvbuff_t * tvb , proto_tree * tree , guint32 offset , guint len _U_ , gchar * add_string _U_ , int string_len _U_ )
2008-08-24 17:42:30 +00:00
{
guint8 oct ;
guint32 curr_offset ;
const gchar * str ;
curr_offset = offset ;
oct = tvb_get_guint8 ( tvb , curr_offset ) ;
switch ( oct & 7 )
{
case 1 : str = " priority level 1 (highest) " ; break ;
case 2 : str = " priority level 2 " ; break ;
case 3 : str = " priority level 3 " ; break ;
case 4 : str = " priority level 4 (lowest) " ; break ;
default : str = " priority level 4 (lowest) " ;
}
proto_tree_add_text ( tree ,
2008-09-05 05:49:39 +00:00
tvb , curr_offset , 1 ,
" Radio Priority (PDP or SMS): (%u) %s " ,
oct & 7 ,
str ) ;
2008-08-24 17:42:30 +00:00
curr_offset + + ;
return ( curr_offset - offset ) ;
}
/*
* [ 7 ] 10.5 .7 .3
*/
2008-12-23 20:49:15 +00:00
static guint16
2008-09-05 05:49:39 +00:00
de_gc_timer ( tvbuff_t * tvb , proto_tree * tree , guint32 offset , guint len _U_ , gchar * add_string _U_ , int string_len _U_ )
2008-08-24 17:42:30 +00:00
{
guint8 oct ;
guint16 val ;
guint32 curr_offset ;
const gchar * str ;
curr_offset = offset ;
oct = tvb_get_guint8 ( tvb , curr_offset ) ;
val = oct & 0x1f ;
switch ( oct > > 5 )
{
case 0 : str = " sec " ; val * = 2 ; break ;
case 1 : str = " min " ; break ;
case 2 : str = " min " ; val * = 6 ; break ;
case 7 :
2008-09-05 05:49:39 +00:00
proto_tree_add_text ( tree ,
tvb , curr_offset , 1 ,
" GPRS Timer: timer is deactivated " ) ;
2008-08-24 17:42:30 +00:00
default : str = " min " ;
}
proto_tree_add_text ( tree ,
2008-09-05 05:49:39 +00:00
tvb , curr_offset , 1 ,
" GPRS Timer: (%u) %u %s " ,
oct , val ,
str ) ;
2008-08-24 17:42:30 +00:00
curr_offset + + ;
/* no length check possible */
return ( curr_offset - offset ) ;
}
/*
* [ 7 ] 10.5 .7 .4
*/
2008-12-23 20:49:15 +00:00
static guint16
2008-09-05 05:49:39 +00:00
de_gc_timer2 ( tvbuff_t * tvb , proto_tree * tree , guint32 offset , guint len _U_ , gchar * add_string , int string_len _U_ )
2008-08-24 17:42:30 +00:00
{
guint8 oct ;
guint16 val ;
guint32 curr_offset ;
const gchar * str ;
curr_offset = offset ;
oct = tvb_get_guint8 ( tvb , curr_offset ) ;
val = oct & 0x1f ;
switch ( oct > > 5 )
{
case 0 : str = " sec " ; val * = 2 ; break ;
case 1 : str = " min " ; break ;
case 2 : str = " min " ; val * = 6 ; break ;
case 7 :
2008-09-05 05:49:39 +00:00
proto_tree_add_text ( tree ,
tvb , curr_offset , 1 ,
" GPRS Timer: timer is deactivated " ) ;
2008-08-24 17:42:30 +00:00
default : str = " min " ;
}
proto_tree_add_text ( tree ,
2008-09-05 05:49:39 +00:00
tvb , curr_offset , 1 ,
" GPRS Timer: (%u) %u %s %s " ,
oct , val ,
str , add_string ? add_string : " " ) ;
2008-08-24 17:42:30 +00:00
curr_offset + + ;
return ( curr_offset - offset ) ;
}
/*
* [ 7 ] 10.5 .7 .5
*/
2008-12-23 20:49:15 +00:00
static guint16
2008-09-05 05:49:39 +00:00
de_gc_radio_prio2 ( tvbuff_t * tvb , proto_tree * tree , guint32 offset , guint len _U_ , gchar * add_string _U_ , int string_len _U_ )
2008-08-24 17:42:30 +00:00
{
guint8 oct ;
guint32 curr_offset ;
const gchar * str ;
curr_offset = offset ;
oct = tvb_get_guint8 ( tvb , curr_offset ) ;
/* IMPORTANT - IT'S ASSUMED THAT THE INFORMATION IS IN THE HIGHER NIBBLE */
oct > > = 4 ;
switch ( oct & 7 )
{
case 1 : str = " priority level 1 (highest) " ; break ;
case 2 : str = " priority level 2 " ; break ;
case 3 : str = " priority level 3 " ; break ;
case 4 : str = " priority level 4 (lowest) " ; break ;
default : str = " priority level 4 (lowest) " ;
}
proto_tree_add_text ( tree ,
2008-09-05 05:49:39 +00:00
tvb , curr_offset , 1 ,
" Radio Priority (TOM8): (%u) %s " ,
oct & 7 ,
str ) ;
2008-08-24 17:42:30 +00:00
curr_offset + + ;
return ( curr_offset - offset ) ;
}
/*
* [ 8 ] 10.5 .7 .6 MBMS context status
*/
2008-12-23 20:49:15 +00:00
static guint16
2008-11-17 19:41:44 +00:00
de_gc_mbms_context_stat ( tvbuff_t * tvb , proto_tree * tree , guint32 offset , guint len , gchar * add_string _U_ , int string_len _U_ )
2008-08-24 17:42:30 +00:00
{
guint32 curr_offset ;
2008-11-17 19:41:44 +00:00
guint8 oct , i , j ;
proto_item * tf = NULL ;
proto_tree * tf_tree = NULL ;
2008-08-24 17:42:30 +00:00
curr_offset = offset ;
2008-11-17 19:41:44 +00:00
oct = tvb_get_guint8 ( tvb , curr_offset ) ;
tf = proto_tree_add_text ( tree ,
tvb , curr_offset , 1 ,
" MBMS Context Status " ) ;
tf_tree = proto_item_add_subtree ( tf , ett_gmm_context_stat ) ;
for ( i = 0 ; i < len ; i + + )
{
oct = tvb_get_guint8 ( tvb , curr_offset ) ;
for ( j = 0 ; j < 8 ; j + + )
{
proto_tree_add_text ( tf_tree ,
tvb , curr_offset , 1 ,
" NSAPI %d: (%u) %s " , 128 + i * 8 + j ,
oct & 1 ,
pdp_str [ oct & 1 ] ) ;
oct > > = 1 ;
}
curr_offset + + ;
}
2008-08-24 17:42:30 +00:00
return ( len ) ;
}
/*
* [ 7 ] 10.5 .6 .1
*/
# define MAX_APN_LENGTH 50
2008-12-23 20:49:15 +00:00
guint16
2008-08-24 17:42:30 +00:00
de_sm_apn ( tvbuff_t * tvb , proto_tree * tree , guint32 offset , guint len , gchar * add_string , int string_len _U_ )
{
guint32 curr_offset ;
2008-09-05 05:49:39 +00:00
guint curr_len ;
2008-08-24 17:42:30 +00:00
const guint8 * cptr ;
2008-09-05 05:49:39 +00:00
guint8 str [ MAX_APN_LENGTH + 1 ] ;
2008-08-24 17:42:30 +00:00
cptr = tvb_get_ptr ( tvb , offset , len ) ;
curr_offset = offset ;
/* init buffer and copy it */
memset ( str , 0 , MAX_APN_LENGTH ) ;
memcpy ( str , cptr , len < MAX_APN_LENGTH ? len : MAX_APN_LENGTH ) ;
curr_len = 0 ;
while ( ( curr_len < len ) & & ( curr_len < MAX_APN_LENGTH ) )
{
guint step = str [ curr_len ] ;
str [ curr_len ] = ' . ' ;
curr_len + = step + 1 ;
}
proto_tree_add_text ( tree ,
tvb , curr_offset , len ,
" APN: %s %s " , str + 1 , add_string ? add_string : " " ) ;
curr_offset + = len ;
EXTRANEOUS_DATA_CHECK ( len , curr_offset - offset ) ;
return ( curr_offset - offset ) ;
}
/*
* [ 7 ] 10.5 .6 .2
*/
2008-12-23 20:49:15 +00:00
static guint16
2008-09-05 05:49:39 +00:00
de_sm_nsapi ( tvbuff_t * tvb , proto_tree * tree , guint32 offset , guint len _U_ , gchar * add_string , int string_len _U_ )
2008-08-24 17:42:30 +00:00
{
guint8 oct ;
guint32 curr_offset ;
curr_offset = offset ;
oct = tvb_get_guint8 ( tvb , curr_offset ) ;
proto_tree_add_text ( tree ,
2008-09-05 05:49:39 +00:00
tvb , curr_offset , 1 ,
" NSAPI: 0x%02x (%u) %s " ,
oct & 0x0f , oct & 0x0f , add_string ? add_string : " " ) ;
2008-08-24 17:42:30 +00:00
curr_offset + + ;
return ( curr_offset - offset ) ;
}
/*
2009-03-04 19:51:55 +00:00
* [ 7 ] 10.5 .6 .3 Protocol configuration options
2008-08-24 17:42:30 +00:00
*/
2009-02-16 21:21:11 +00:00
guint16
2008-08-24 17:42:30 +00:00
de_sm_pco ( tvbuff_t * tvb , proto_tree * tree , guint32 offset , guint len , gchar * add_string _U_ , int string_len _U_ )
{
guint32 curr_offset ;
guint curr_len ;
guchar oct ;
struct e_in6_addr ipv6_addr ;
curr_len = len ;
curr_offset = offset ;
oct = tvb_get_guint8 ( tvb , curr_offset ) ;
curr_len - - ;
curr_offset + + ;
proto_tree_add_text ( tree , tvb , curr_offset , 1 , " Ext: 0x%02x (%u) " , oct > > 7 , oct > > 7 ) ;
proto_tree_add_text ( tree , tvb , curr_offset , 1 , " Configuration Protocol: PPP (%u) " , oct & 0x0f ) ;
while ( curr_len > 0 )
{
guchar e_len ;
guint16 prot ;
2008-09-05 05:49:39 +00:00
tvbuff_t * l3_tvb ;
dissector_handle_t handle = NULL ;
static packet_info p_info ;
prot = tvb_get_guint8 ( tvb , curr_offset ) ;
prot < < = 8 ;
prot | = tvb_get_guint8 ( tvb , curr_offset + 1 ) ;
e_len = tvb_get_guint8 ( tvb , curr_offset + 2 ) ;
2008-08-24 17:42:30 +00:00
curr_len - = 3 ;
curr_offset + = 3 ;
switch ( prot )
{
case 0x0001 :
2008-09-05 05:49:39 +00:00
{
2009-04-18 06:34:58 +00:00
if ( e_len = = 0 ) {
proto_tree_add_text ( tree , tvb , curr_offset - 3 , 2 , " Parameter: (%u) P-CSCF Address Request " , prot ) ;
} else {
proto_tree_add_text ( tree , tvb , curr_offset - 3 , 2 , " Parameter: (%u) P-CSCF Address " , prot ) ;
}
2008-09-05 05:49:39 +00:00
proto_tree_add_text ( tree , tvb , curr_offset - 1 , 1 , " Length: 0x%02x (%u) " , e_len , e_len ) ;
2009-04-18 06:34:58 +00:00
if ( e_len > 0 ) {
tvb_get_ipv6 ( tvb , curr_offset , & ipv6_addr ) ;
proto_tree_add_text ( tree ,
tvb , curr_offset , 16 ,
" IPv6: %s " , ip6_to_str ( & ipv6_addr ) ) ;
}
2008-09-05 05:49:39 +00:00
break ;
}
2008-08-24 17:42:30 +00:00
case 0x0002 :
2008-09-05 05:49:39 +00:00
proto_tree_add_text ( tree , tvb , curr_offset - 3 , 2 , " Parameter: (%u) IM CN Subsystem Signaling Flag " , prot ) ;
proto_tree_add_text ( tree , tvb , curr_offset - 1 , 1 , " Length: 0x%02x (%u) " , e_len , e_len ) ;
break ;
2008-08-24 17:42:30 +00:00
case 0x0003 :
{
2009-04-18 06:34:58 +00:00
if ( e_len = = 0 ) {
proto_tree_add_text ( tree , tvb , curr_offset - 3 , 2 , " Parameter: (%u) DNS Server Address Request " , prot ) ;
} else {
proto_tree_add_text ( tree , tvb , curr_offset - 3 , 2 , " Parameter: (%u) DNS Server Address " , prot ) ;
}
2008-08-24 17:42:30 +00:00
proto_tree_add_text ( tree , tvb , curr_offset - 1 , 1 , " Length: 0x%02x (%u) " , e_len , e_len ) ;
2008-09-05 05:49:39 +00:00
2009-04-18 06:34:58 +00:00
if ( e_len > 0 ) {
tvb_get_ipv6 ( tvb , curr_offset , & ipv6_addr ) ;
proto_tree_add_text ( tree ,
tvb , curr_offset , 16 ,
" IPv6: %s " , ip6_to_str ( & ipv6_addr ) ) ;
}
2008-09-05 05:49:39 +00:00
break ;
2008-08-24 17:42:30 +00:00
}
2008-09-05 05:49:39 +00:00
case 0x0004 :
proto_tree_add_text ( tree , tvb , curr_offset - 3 , 2 , " Parameter: (%u) Policy Control rejection code " , prot ) ;
2008-08-24 17:42:30 +00:00
proto_tree_add_text ( tree , tvb , curr_offset - 1 , 1 , " Length: 0x%02x (%u) " , e_len , e_len ) ;
2008-09-05 05:49:39 +00:00
oct = tvb_get_guint8 ( tvb , curr_offset ) ;
proto_tree_add_text ( tree , tvb , curr_offset , 1 , " Reject Code: 0x%02x (%u) " , e_len , e_len ) ;
break ;
default :
{
handle = dissector_get_port_handle ( gprs_sm_pco_subdissector_table , prot ) ;
if ( handle ! = NULL )
{
proto_tree_add_text ( tree , tvb , curr_offset - 3 , 2 , " Protocol: (%u) %s " ,
prot , val_to_str ( prot , ppp_vals , " Unknown " ) ) ;
proto_tree_add_text ( tree , tvb , curr_offset - 1 , 1 , " Length: 0x%02x (%u) " , e_len , e_len ) ;
/*
* dissect the embedded message
*/
l3_tvb = tvb_new_subset ( tvb , curr_offset , e_len , e_len ) ;
call_dissector ( handle , l3_tvb , & p_info , tree ) ;
}
else
{
2008-12-18 19:08:49 +00:00
proto_tree_add_text ( tree , tvb , curr_offset - 3 , 2 , " Protocol/Parameter: (%u) unknown " , prot ) ;
2008-09-05 05:49:39 +00:00
proto_tree_add_text ( tree , tvb , curr_offset - 1 , 1 , " Length: 0x%02x (%u) " , e_len , e_len ) ;
/*
* dissect the embedded DATA message
*/
l3_tvb = tvb_new_subset ( tvb , curr_offset , e_len , e_len ) ;
call_dissector ( data_handle , l3_tvb , & p_info , tree ) ;
}
2008-08-24 17:42:30 +00:00
}
}
2008-09-05 05:49:39 +00:00
curr_len - = e_len ;
curr_offset + = e_len ;
2008-08-24 17:42:30 +00:00
}
curr_offset + = curr_len ;
2008-09-05 05:49:39 +00:00
2008-08-24 17:42:30 +00:00
EXTRANEOUS_DATA_CHECK ( len , curr_offset - offset ) ;
return ( curr_offset - offset ) ;
}
/*
* [ 7 ] 10.5 .6 .4
*/
2008-12-23 20:49:15 +00:00
static guint16
2008-08-24 17:42:30 +00:00
de_sm_pdp_addr ( tvbuff_t * tvb , proto_tree * tree , guint32 offset , guint len , gchar * add_string _U_ , int string_len _U_ )
{
guint32 curr_offset ;
guint curr_len ;
const gchar * str ;
2008-09-05 05:49:39 +00:00
guchar oct ;
guchar oct2 ;
2008-08-24 17:42:30 +00:00
struct e_in6_addr ipv6_addr ;
curr_len = len ;
curr_offset = offset ;
oct = tvb_get_guint8 ( tvb , curr_offset ) ;
switch ( oct & 0x0f )
{
case 0x00 : str = " ETSI allocated address " ; break ;
case 0x01 : str = " IETF allocated address " ; break ;
case 0x0f : str = " Empty PDP type " ; break ;
default : str = " reserved " ;
}
proto_tree_add_text ( tree ,
tvb , curr_offset , 1 ,
" PDP type organisation: (%u) %s " , oct & 0x0f , str ) ;
oct2 = tvb_get_guint8 ( tvb , curr_offset + 1 ) ;
if ( ( oct & 0x0f ) = = 0 )
{
2008-09-05 05:49:39 +00:00
switch ( oct2 )
{
2008-08-24 17:42:30 +00:00
case 0x00 : str = " Reserved, used in earlier version of this protocol " ; break ;
case 0x01 : str = " PDP-type PPP " ; break ;
default : str = " reserved " ;
2008-09-05 05:49:39 +00:00
}
2008-08-24 17:42:30 +00:00
}
else if ( ( oct & 0x0f ) = = 1 )
{
2008-09-05 05:49:39 +00:00
switch ( oct2 )
{
case 0x21 : str = " IPv4 address " ; break ;
2008-08-24 17:42:30 +00:00
case 0x57 : str = " IPv6 address " ; break ;
default : str = " IPv4 address " ;
2008-09-05 05:49:39 +00:00
}
2008-08-24 17:42:30 +00:00
}
else if ( ( oct2 = = 0 ) & & ( ( oct & 0x0f ) = = 0x0f ) )
2008-09-05 05:49:39 +00:00
str = " Empty " ;
2008-08-24 17:42:30 +00:00
else
2008-09-05 05:49:39 +00:00
str = " Not specified " ;
2008-08-24 17:42:30 +00:00
proto_tree_add_text ( tree ,
tvb , curr_offset + 1 , 1 ,
" PDP type number: (%u) %s " , oct2 , str ) ;
if ( ( len = = 2 ) & & ( ( oct2 = = 0x21 ) | | ( oct2 = = 0x57 ) ) )
{
2008-09-05 05:49:39 +00:00
proto_tree_add_text ( tree ,
2008-08-24 17:42:30 +00:00
tvb , curr_offset + 1 , 1 ,
" Dynamic addressing " ) ;
2008-09-05 05:49:39 +00:00
curr_offset + = curr_len ;
2008-08-24 17:42:30 +00:00
2008-09-05 05:49:39 +00:00
EXTRANEOUS_DATA_CHECK ( len , curr_offset - offset ) ;
return ( curr_offset - offset ) ;
2008-08-24 17:42:30 +00:00
}
else if ( len = = 2 )
{
2008-09-05 05:49:39 +00:00
proto_tree_add_text ( tree ,
2008-08-24 17:42:30 +00:00
tvb , curr_offset + 1 , 1 ,
" No PDP address is included " ) ;
2008-09-05 05:49:39 +00:00
curr_offset + = curr_len ;
2008-08-24 17:42:30 +00:00
2008-09-05 05:49:39 +00:00
EXTRANEOUS_DATA_CHECK ( len , curr_offset - offset ) ;
return ( curr_offset - offset ) ;
2008-08-24 17:42:30 +00:00
}
else if ( len < 2 )
{
2008-09-05 05:49:39 +00:00
proto_tree_add_text ( tree ,
2008-08-24 17:42:30 +00:00
tvb , curr_offset + 1 , 1 ,
" Length is bogus - should be >= 2 " ) ;
2008-09-05 05:49:39 +00:00
curr_offset + = curr_len ;
2008-08-24 17:42:30 +00:00
2008-09-05 05:49:39 +00:00
EXTRANEOUS_DATA_CHECK ( len , curr_offset - offset ) ;
return ( curr_offset - offset ) ;
2008-08-24 17:42:30 +00:00
}
if ( ( ( oct2 = = 0x21 ) & & ( len ! = 6 ) ) | |
( ( oct2 = = 0x57 ) & & ( len ! = 18 ) ) )
{
2008-09-05 05:49:39 +00:00
proto_tree_add_text ( tree ,
2008-08-24 17:42:30 +00:00
tvb , curr_offset + 2 , len - 2 ,
" Can't display address " ) ;
}
switch ( oct2 )
{
case 0x21 :
if ( len - 2 ! = 4 ) {
proto_tree_add_text ( tree ,
2008-09-05 05:49:39 +00:00
tvb , curr_offset + 2 , 0 ,
" IPv4: length is wrong " ) ;
} else {
2008-08-24 17:42:30 +00:00
proto_tree_add_text ( tree ,
2008-09-05 05:49:39 +00:00
tvb , curr_offset + 2 , len - 2 ,
" IPv4: %s " , ip_to_str ( tvb_get_ptr ( tvb , offset + 2 , 4 ) ) ) ;
}
break ;
2008-08-24 17:42:30 +00:00
case 0x57 :
if ( len - 2 ! = 16 ) {
proto_tree_add_text ( tree ,
2008-09-05 05:49:39 +00:00
tvb , curr_offset + 2 , 0 ,
" IPv6: length is wrong " ) ;
} else {
tvb_get_ipv6 ( tvb , curr_offset + 2 , & ipv6_addr ) ;
2008-08-24 17:42:30 +00:00
proto_tree_add_text ( tree ,
tvb , curr_offset + 2 , len - 2 ,
2008-09-05 05:49:39 +00:00
" IPv6: %s " , ip6_to_str ( & ipv6_addr ) ) ;
}
break ;
2008-08-24 17:42:30 +00:00
}
curr_offset + = curr_len ;
2008-09-05 05:49:39 +00:00
2008-08-24 17:42:30 +00:00
EXTRANEOUS_DATA_CHECK ( len , curr_offset - offset ) ;
return ( curr_offset - offset ) ;
}
/*
* [ 7 ] 10.5 .6 .5 3 GPP TS 24.008 version 7.8 .0 Release 7
*/
static const value_string gsm_a_qos_delay_cls_vals [ ] = {
{ 0x00 , " Subscribed delay class (in MS to network direction) " } ,
{ 0x01 , " Delay class 1 " } ,
{ 0x02 , " Delay class 2 " } ,
{ 0x03 , " Delay class 3 " } ,
{ 0x04 , " Delay class 4 (best effort) " } ,
{ 0x07 , " Reserved " } ,
{ 0 , NULL }
} ;
static const value_string gsm_a_qos_reliability_vals [ ] = {
{ 0x00 , " Subscribed reliability class (in MS to network direction) " } ,
{ 0x01 , " Acknowledged GTP, LLC, and RLC; Protected data " } ,
{ 0x02 , " Unacknowledged GTP, Ack LLC/RLC, Protected data " } ,
{ 0x03 , " Unacknowledged GTP/LLC, Ack RLC, Protected data " } ,
{ 0x04 , " Unacknowledged GTP/LLC/RLC, Protected data " } ,
{ 0x05 , " Unacknowledged GTP/LLC/RLC, Unprotected data " } ,
{ 0x07 , " Reserved " } ,
{ 0 , NULL }
} ;
/* Delivery of erroneous SDUs, octet 6 (see 3GPP TS 23.107) Bits 3 2 1 */
const value_string gsm_a_qos_del_of_err_sdu_vals [ ] = {
{ 0 , " Subscribed delivery of erroneous SDUs/Reserved " } ,
{ 1 , " No detect('-') " } ,
{ 2 , " Erroneous SDUs are delivered('yes') " } ,
{ 3 , " Erroneous SDUs are not delivered('No') " } ,
{ 7 , " Reserved " } ,
{ 0 , NULL }
} ;
/* Delivery order, octet 6 (see 3GPP TS 23.107) Bits 5 4 3 */
const value_string gsm_a_qos_del_order_vals [ ] = {
{ 0 , " Subscribed delivery order/Reserved " } ,
{ 1 , " With delivery order ('yes') " } ,
{ 2 , " Without delivery order ('no') " } ,
{ 3 , " Reserved " } ,
{ 0 , NULL }
} ;
/* Traffic class, octet 6 (see 3GPP TS 23.107) Bits 8 7 6 */
const value_string gsm_a_qos_traffic_cls_vals [ ] = {
{ 0 , " Subscribed traffic class/Reserved " } ,
{ 1 , " Conversational class " } ,
{ 2 , " Streaming class " } ,
{ 3 , " Interactive class " } ,
{ 4 , " Background class " } ,
{ 7 , " Reserved " } ,
{ 0 , NULL }
} ;
/* Residual Bit Error Rate (BER), octet 10 (see 3GPP TS 23.107) Bits 8 7 6 5 */
const value_string gsm_a_qos_ber_vals [ ] = {
{ 0 , " Subscribed residual BER/Reserved " } ,
{ 1 , " 5*10-2 " } ,
{ 2 , " 1*10-2 " } ,
{ 3 , " 5*10-3 " } ,
{ 4 , " 4*10-3 " } ,
{ 5 , " 1*10-3 " } ,
{ 6 , " 1*10-4 " } ,
{ 7 , " 1*10-5 " } ,
{ 8 , " 1*10-6 " } ,
{ 9 , " 6*10-8 " } ,
{ 10 , " Reserved " } ,
{ 0 , NULL }
} ;
/* SDU error ratio, octet 10 (see 3GPP TS 23.107) Bits 4 3 2 1 */
const value_string gsm_a_qos_sdu_err_rat_vals [ ] = {
{ 0 , " Subscribed SDU error ratio/Reserved " } ,
{ 1 , " 1*10-2 " } ,
{ 2 , " 7*10-3 " } ,
{ 3 , " 1*10-3 " } ,
{ 4 , " 1*10-4 " } ,
{ 5 , " 1*10-5 " } ,
{ 6 , " 1*10-6 " } ,
{ 7 , " 1*10-1 " } ,
{ 15 , " Reserved " } ,
{ 0 , NULL }
} ;
/* Traffic handling priority, octet 11 (see 3GPP TS 23.107) Bits 2 1 */
const value_string gsm_a_qos_traff_hdl_pri_vals [ ] = {
{ 0 , " Subscribed traffic handling priority/Reserved " } ,
{ 1 , " Priority level 1 " } ,
{ 2 , " Priority level 2 " } ,
{ 3 , " Priority level 3 " } ,
{ 0 , NULL }
} ;
2008-12-23 20:49:15 +00:00
guint16
2008-08-24 17:42:30 +00:00
de_sm_qos ( tvbuff_t * tvb , proto_tree * tree , guint32 offset , guint len , gchar * add_string _U_ , int string_len _U_ )
{
guint32 curr_offset ;
guint curr_len ;
2008-09-05 05:49:39 +00:00
guchar oct , tmp_oct ;
2008-08-24 17:42:30 +00:00
const gchar * str ;
curr_len = len ;
curr_offset = offset ;
oct = tvb_get_guint8 ( tvb , curr_offset ) ;
2008-09-05 05:49:39 +00:00
proto_tree_add_item ( tree , hf_gsm_a_qos_delay_cls , tvb , curr_offset , 1 , FALSE ) ;
proto_tree_add_item ( tree , hf_gsm_a_qos_qos_reliability_cls , tvb , curr_offset , 1 , FALSE ) ;
2008-08-24 17:42:30 +00:00
curr_offset + = 1 ;
curr_len - = 1 ;
if ( curr_len = = 0 )
{
2008-09-05 05:49:39 +00:00
EXTRANEOUS_DATA_CHECK ( len , curr_offset - offset ) ;
2008-08-24 17:42:30 +00:00
2008-09-05 05:49:39 +00:00
return ( curr_offset - offset ) ;
2008-08-24 17:42:30 +00:00
}
oct = tvb_get_guint8 ( tvb , curr_offset ) ;
switch ( oct > > 4 )
{
case 0x00 : str = " Subscribed peak throughput/reserved " ; break ;
case 0x01 : str = " Up to 1 000 octet/s " ; break ;
case 0x02 : str = " Up to 2 000 octet/s " ; break ;
case 0x03 : str = " Up to 4 000 octet/s " ; break ;
case 0x04 : str = " Up to 8 000 octet/s " ; break ;
case 0x05 : str = " Up to 16 000 octet/s " ; break ;
case 0x06 : str = " Up to 32 000 octet/s " ; break ;
case 0x07 : str = " Up to 64 000 octet/s " ; break ;
case 0x08 : str = " Up to 128 000 octet/s " ; break ;
case 0x09 : str = " Up to 256 000 octet/s " ; break ;
case 0x0f : str = " Reserved " ; break ;
default : str = " Up to 1 000 octet/s " ;
}
proto_tree_add_text ( tree ,
tvb , curr_offset , 1 ,
" Peak throughput: (%u) %s " , oct > > 4 , str ) ;
switch ( oct & 0x7 )
{
case 0x00 : str = " Subscribed precedence/reserved " ; break ;
case 0x01 : str = " High priority " ; break ;
case 0x02 : str = " Normal priority " ; break ;
case 0x03 : str = " Low priority " ; break ;
case 0x07 : str = " Reserved " ; break ;
default : str = " Normal priority " ;
}
proto_tree_add_text ( tree ,
tvb , curr_offset , 1 ,
" Precedence class: (%u) %s " , oct & 7 , str ) ;
curr_offset + = 1 ;
curr_len - = 1 ;
if ( curr_len = = 0 )
{
2008-09-05 05:49:39 +00:00
EXTRANEOUS_DATA_CHECK ( len , curr_offset - offset ) ;
2008-08-24 17:42:30 +00:00
2008-09-05 05:49:39 +00:00
return ( curr_offset - offset ) ;
2008-08-24 17:42:30 +00:00
}
oct = tvb_get_guint8 ( tvb , curr_offset ) ;
switch ( oct & 0x1f )
{
case 0x00 : str = " Subscribed peak throughput/reserved " ; break ;
case 0x01 : str = " 100 octet/h " ; break ;
case 0x02 : str = " 200 octet/h " ; break ;
case 0x03 : str = " 500 octet/h " ; break ;
case 0x04 : str = " 1 000 octet/h " ; break ;
case 0x05 : str = " 2 000 octet/h " ; break ;
case 0x06 : str = " 5 000 octet/h " ; break ;
case 0x07 : str = " 10 000 octet/h " ; break ;
case 0x08 : str = " 20 000 octet/h " ; break ;
case 0x09 : str = " 50 000 octet/h " ; break ;
case 0x0a : str = " 100 000 octet/h " ; break ;
case 0x0b : str = " 200 000 octet/h " ; break ;
case 0x0c : str = " 500 000 octet/h " ; break ;
case 0x0d : str = " 1 000 000 octet/h " ; break ;
case 0x0e : str = " 2 000 000 octet/h " ; break ;
case 0x0f : str = " 5 000 000 octet/h " ; break ;
case 0x10 : str = " 10 000 000 octet/h " ; break ;
case 0x11 : str = " 20 000 000 octet/h " ; break ;
case 0x12 : str = " 50 000 000 octet/h " ; break ;
case 0x1e : str = " Reserved " ; break ;
case 0x1f : str = " Best effort " ; break ;
default : str = " Best effort " ;
}
proto_tree_add_text ( tree ,
tvb , curr_offset , 1 ,
" Mean throughput: (%u) %s " , oct & 0x1f , str ) ;
curr_offset + = 1 ;
curr_len - = 1 ;
if ( curr_len = = 0 )
{
2008-09-05 05:49:39 +00:00
EXTRANEOUS_DATA_CHECK ( len , curr_offset - offset ) ;
2008-08-24 17:42:30 +00:00
2008-09-05 05:49:39 +00:00
return ( curr_offset - offset ) ;
2008-08-24 17:42:30 +00:00
}
proto_tree_add_item ( tree , hf_gsm_a_qos_traffic_cls , tvb , curr_offset , 1 , FALSE ) ;
proto_tree_add_item ( tree , hf_gsm_a_qos_del_order , tvb , curr_offset , 1 , FALSE ) ;
proto_tree_add_item ( tree , hf_gsm_a_qos_del_of_err_sdu , tvb , curr_offset , 1 , FALSE ) ;
curr_offset + = 1 ;
curr_len - = 1 ;
if ( curr_len = = 0 )
{
2008-09-05 05:49:39 +00:00
EXTRANEOUS_DATA_CHECK ( len , curr_offset - offset ) ;
2008-08-24 17:42:30 +00:00
2008-09-05 05:49:39 +00:00
return ( curr_offset - offset ) ;
2008-08-24 17:42:30 +00:00
}
oct = tvb_get_guint8 ( tvb , curr_offset ) ;
switch ( oct )
{
case 0x00 : str = " Subscribed maximum SDU size/reserved " ; break ;
case 0x97 : str = " 1502 octets " ; break ;
case 0x98 : str = " 1510 octets " ; break ;
case 0x99 : str = " 1520 octets " ; break ;
case 0xff : str = " Reserved " ; break ;
default : str = " Unspecified " ;
}
if ( ( oct > = 1 ) & & ( oct < = 0x96 ) )
2008-09-05 05:49:39 +00:00
proto_tree_add_text ( tree ,
2008-08-24 17:42:30 +00:00
tvb , curr_offset , 1 ,
2008-09-05 05:49:39 +00:00
" Maximum SDU size: (%u) %u octets " , oct , oct * 10 ) ;
2008-08-24 17:42:30 +00:00
else
2008-09-05 05:49:39 +00:00
proto_tree_add_text ( tree ,
2008-08-24 17:42:30 +00:00
tvb , curr_offset , 1 ,
2008-09-05 05:49:39 +00:00
" Maximum SDU size: (%u) %s " , oct , str ) ;
2008-08-24 17:42:30 +00:00
curr_offset + = 1 ;
curr_len - = 1 ;
if ( curr_len = = 0 )
{
2008-09-05 05:49:39 +00:00
EXTRANEOUS_DATA_CHECK ( len , curr_offset - offset ) ;
2008-08-24 17:42:30 +00:00
2008-09-05 05:49:39 +00:00
return ( curr_offset - offset ) ;
2008-08-24 17:42:30 +00:00
}
oct = tvb_get_guint8 ( tvb , curr_offset ) ;
switch ( oct )
{
case 0x00 : str = " Subscribed maximum bit rate for uplink/reserved " ; break ;
case 0xff : str = " 0kbps " ; break ;
default : str = " This should not happen - BUG " ;
}
if ( ( oct > = 1 ) & & ( oct < = 0x3f ) )
2008-09-05 05:49:39 +00:00
proto_tree_add_text ( tree ,
2008-08-24 17:42:30 +00:00
tvb , curr_offset , 1 ,
2008-09-05 05:49:39 +00:00
" Maximum bit rate for uplink: (%u) %ukbps " , oct , oct ) ;
2008-08-24 17:42:30 +00:00
else if ( ( oct > = 0x40 ) & & ( oct < = 0x7f ) )
2008-09-05 05:49:39 +00:00
proto_tree_add_text ( tree ,
2008-08-24 17:42:30 +00:00
tvb , curr_offset , 1 ,
2008-09-05 05:49:39 +00:00
" Maximum bit rate for uplink: (%u) %ukbps " , oct , ( oct - 0x40 ) * 8 + 64 ) ; /* - was (oct-0x40)*8 */
2008-08-24 17:42:30 +00:00
else if ( ( oct > = 0x80 ) & & ( oct < = 0xfe ) )
2008-09-05 05:49:39 +00:00
proto_tree_add_text ( tree ,
2008-08-24 17:42:30 +00:00
tvb , curr_offset , 1 ,
2008-09-05 05:49:39 +00:00
" Maximum bit rate for uplink: (%u) %ukbps " , oct , ( oct - 0x80 ) * 64 + 576 ) ; /* - was (oct-0x80)*64 */
2008-08-24 17:42:30 +00:00
else
2008-09-05 05:49:39 +00:00
proto_tree_add_text ( tree ,
2008-08-24 17:42:30 +00:00
tvb , curr_offset , 1 ,
2008-09-05 05:49:39 +00:00
" Maximum bit rate for uplink: (%u) %s " , oct , str ) ;
2008-08-24 17:42:30 +00:00
curr_offset + = 1 ;
curr_len - = 1 ;
if ( curr_len = = 0 )
{
2008-09-05 05:49:39 +00:00
EXTRANEOUS_DATA_CHECK ( len , curr_offset - offset ) ;
2008-08-24 17:42:30 +00:00
2008-09-05 05:49:39 +00:00
return ( curr_offset - offset ) ;
2008-08-24 17:42:30 +00:00
}
oct = tvb_get_guint8 ( tvb , curr_offset ) ;
switch ( oct )
{
case 0x00 : str = " Subscribed maximum bit rate for uplink/reserved " ; break ;
case 0xff : str = " 0kbps " ; break ;
default : str = " This should not happen - BUG " ;
}
if ( ( oct > = 1 ) & & ( oct < = 0x3f ) )
2008-09-05 05:49:39 +00:00
proto_tree_add_text ( tree ,
2008-08-24 17:42:30 +00:00
tvb , curr_offset , 1 ,
2008-09-05 05:49:39 +00:00
" Maximum bit rate for downlink: (%u) %ukbps " , oct , oct ) ;
2008-08-24 17:42:30 +00:00
else if ( ( oct > = 0x40 ) & & ( oct < = 0x7f ) )
2008-09-05 05:49:39 +00:00
proto_tree_add_text ( tree ,
2008-08-24 17:42:30 +00:00
tvb , curr_offset , 1 ,
2008-09-05 05:49:39 +00:00
" Maximum bit rate for downlink: (%u) %ukbps " , oct , ( oct - 0x40 ) * 8 + 64 ) ; /*same as above*/
2008-08-24 17:42:30 +00:00
else if ( ( oct > = 0x80 ) & & ( oct < = 0xfe ) )
2008-09-05 05:49:39 +00:00
proto_tree_add_text ( tree ,
2008-08-24 17:42:30 +00:00
tvb , curr_offset , 1 ,
2008-09-05 05:49:39 +00:00
" Maximum bit rate for downlink: (%u) %ukbps " , oct , ( oct - 0x80 ) * 64 + 576 ) ; /*same as above*/
2008-08-24 17:42:30 +00:00
else
2008-09-05 05:49:39 +00:00
proto_tree_add_text ( tree ,
2008-08-24 17:42:30 +00:00
tvb , curr_offset , 1 ,
2008-09-05 05:49:39 +00:00
" Maximum bit rate for downlink: (%u) %s " , oct , str ) ;
2008-08-24 17:42:30 +00:00
curr_offset + = 1 ;
curr_len - = 1 ;
if ( curr_len = = 0 )
{
2008-09-05 05:49:39 +00:00
EXTRANEOUS_DATA_CHECK ( len , curr_offset - offset ) ;
2008-08-24 17:42:30 +00:00
2008-09-05 05:49:39 +00:00
return ( curr_offset - offset ) ;
2008-08-24 17:42:30 +00:00
}
2008-10-23 19:22:54 +00:00
/* Octet 10 */
2008-08-24 17:42:30 +00:00
proto_tree_add_item ( tree , hf_gsm_a_qos_ber , tvb , curr_offset , 1 , FALSE ) ;
proto_tree_add_item ( tree , hf_gsm_a_qos_sdu_err_rat , tvb , curr_offset , 1 , FALSE ) ;
curr_offset + = 1 ;
curr_len - = 1 ;
if ( curr_len = = 0 )
{
2008-09-05 05:49:39 +00:00
EXTRANEOUS_DATA_CHECK ( len , curr_offset - offset ) ;
2008-08-24 17:42:30 +00:00
2008-09-05 05:49:39 +00:00
return ( curr_offset - offset ) ;
2008-08-24 17:42:30 +00:00
}
2008-10-23 19:22:54 +00:00
/* Octet 11 */
2008-08-24 17:42:30 +00:00
oct = tvb_get_guint8 ( tvb , curr_offset ) ;
switch ( oct > > 2 )
{
case 0x00 : str = " Subscribed transfer delay/reserved " ; break ;
case 0x3f : str = " Reserved " ; break ;
default : str = " This should not happen - BUG " ;
}
tmp_oct = oct > > 2 ;
if ( ( tmp_oct > = 1 ) & & ( tmp_oct < = 0x0f ) )
2008-09-05 05:49:39 +00:00
proto_tree_add_text ( tree ,
2008-08-24 17:42:30 +00:00
tvb , curr_offset , 1 ,
" Transfer Delay: (%u) %ums " , oct > > 2 , ( oct > > 2 ) * 10 ) ;
else if ( ( tmp_oct > = 0x10 ) & & ( tmp_oct < = 0x1f ) )
2008-09-05 05:49:39 +00:00
proto_tree_add_text ( tree ,
2008-08-24 17:42:30 +00:00
tvb , curr_offset , 1 ,
" Transfer Delay: (%u) %ums " , oct > > 2 , ( ( oct > > 2 ) - 0x10 ) * 50 + 200 ) ;
else if ( ( tmp_oct > = 0x20 ) & & ( tmp_oct < = 0x3e ) )
2008-09-05 05:49:39 +00:00
proto_tree_add_text ( tree ,
2008-08-24 17:42:30 +00:00
tvb , curr_offset , 1 ,
" Transfer Delay: (%u) %ums " , oct > > 2 , ( ( oct > > 2 ) - 0x20 ) * 100 + 1000 ) ;
else
2008-09-05 05:49:39 +00:00
proto_tree_add_text ( tree ,
2008-08-24 17:42:30 +00:00
tvb , curr_offset , 1 ,
" Transfer Delay: (%u) %s " , oct > > 2 , str ) ;
switch ( oct & 0x03 )
{
case 0x00 : str = " Subscribed traffic handling priority/reserved " ; break ;
case 0x01 : str = " Priority level 1 " ; break ;
case 0x02 : str = " Priority level 2 " ; break ;
case 0x03 : str = " Priority level 3 " ; break ;
default : str = " This should not happen - BUG " ;
}
proto_tree_add_text ( tree ,
tvb , curr_offset , 1 ,
" Traffic Handling priority: (%u) %s " , oct & 0x03 , str ) ;
curr_offset + = 1 ;
curr_len - = 1 ;
if ( curr_len = = 0 )
{
2008-09-05 05:49:39 +00:00
EXTRANEOUS_DATA_CHECK ( len , curr_offset - offset ) ;
2008-08-24 17:42:30 +00:00
2008-09-05 05:49:39 +00:00
return ( curr_offset - offset ) ;
2008-08-24 17:42:30 +00:00
}
2008-10-23 19:22:54 +00:00
/* Octet 12 */
2008-08-24 17:42:30 +00:00
oct = tvb_get_guint8 ( tvb , curr_offset ) ;
switch ( oct )
{
case 0x00 : str = " Subscribed guaranteed bit rate for uplink/reserved " ; break ;
case 0xff : str = " 0kbps " ; break ;
default : str = " This should not happen - BUG " ;
}
if ( ( oct > = 1 ) & & ( oct < = 0x3f ) )
2008-09-05 05:49:39 +00:00
proto_tree_add_text ( tree ,
2008-08-24 17:42:30 +00:00
tvb , curr_offset , 1 ,
2008-09-05 05:49:39 +00:00
" Guaranteed bit rate for uplink: (%u) %ukbps " , oct , oct ) ;
2008-08-24 17:42:30 +00:00
else if ( ( oct > = 0x40 ) & & ( oct < = 0x7f ) )
2008-09-05 05:49:39 +00:00
proto_tree_add_text ( tree ,
2008-08-24 17:42:30 +00:00
tvb , curr_offset , 1 ,
2008-09-05 05:49:39 +00:00
" Guaranteed bit rate for uplink: (%u) %ukbps " , oct , ( oct - 0x40 ) * 8 + 64 ) ; /*same as for max bit rate*/
2008-08-24 17:42:30 +00:00
else if ( ( oct > = 0x80 ) & & ( oct < = 0xfe ) )
2008-09-05 05:49:39 +00:00
proto_tree_add_text ( tree ,
2008-08-24 17:42:30 +00:00
tvb , curr_offset , 1 ,
2008-09-05 05:49:39 +00:00
" Guaranteed bit rate for uplink: (%u) %ukbps " , oct , ( oct - 0x80 ) * 64 + 576 ) ; /*same as for max bit rate*/
2008-08-24 17:42:30 +00:00
else
2008-09-05 05:49:39 +00:00
proto_tree_add_text ( tree ,
2008-08-24 17:42:30 +00:00
tvb , curr_offset , 1 ,
2008-09-05 05:49:39 +00:00
" Guaranteed bit rate for uplink: (%u) %s " , oct , str ) ;
2008-08-24 17:42:30 +00:00
curr_offset + = 1 ;
curr_len - = 1 ;
if ( curr_len = = 0 )
{
2008-09-05 05:49:39 +00:00
EXTRANEOUS_DATA_CHECK ( len , curr_offset - offset ) ;
2008-08-24 17:42:30 +00:00
2008-09-05 05:49:39 +00:00
return ( curr_offset - offset ) ;
2008-08-24 17:42:30 +00:00
}
oct = tvb_get_guint8 ( tvb , curr_offset ) ;
switch ( oct )
{
case 0x00 : str = " Subscribed guaranteed bit rate for uplink/reserved " ; break ;
case 0xff : str = " 0kbps " ; break ;
default : str = " This should not happen - BUG " ;
}
if ( ( oct > = 1 ) & & ( oct < = 0x3f ) )
2008-09-05 05:49:39 +00:00
proto_tree_add_text ( tree ,
2008-08-24 17:42:30 +00:00
tvb , curr_offset , 1 ,
2008-09-05 05:49:39 +00:00
" Guaranteed bit rate for downlink: (%u) %ukbps " , oct , oct ) ;
2008-08-24 17:42:30 +00:00
else if ( ( oct > = 0x40 ) & & ( oct < = 0x7f ) )
2008-09-05 05:49:39 +00:00
proto_tree_add_text ( tree ,
2008-08-24 17:42:30 +00:00
tvb , curr_offset , 1 ,
2008-09-05 05:49:39 +00:00
" Guaranteed bit rate for downlink: (%u) %ukbps " , oct , ( oct - 0x40 ) * 8 + 64 ) ; /*same as above*/
2008-08-24 17:42:30 +00:00
else if ( ( oct > = 0x80 ) & & ( oct < = 0xfe ) )
2008-09-05 05:49:39 +00:00
proto_tree_add_text ( tree ,
2008-08-24 17:42:30 +00:00
tvb , curr_offset , 1 ,
2008-09-05 05:49:39 +00:00
" Guaranteed bit rate for downlink: (%u) %ukbps " , oct , ( oct - 0x80 ) * 64 + 576 ) ; /*same as above*/
2008-08-24 17:42:30 +00:00
else
2008-09-05 05:49:39 +00:00
proto_tree_add_text ( tree ,
2008-08-24 17:42:30 +00:00
tvb , curr_offset , 1 ,
2008-09-05 05:49:39 +00:00
" Guaranteed bit rate for downlink: (%u) %s " , oct , str ) ;
2008-08-24 17:42:30 +00:00
curr_offset + = 1 ;
curr_len - = 1 ;
if ( curr_len = = 0 )
{
2008-09-05 05:49:39 +00:00
EXTRANEOUS_DATA_CHECK ( len , curr_offset - offset ) ;
2008-08-24 17:42:30 +00:00
2008-09-05 05:49:39 +00:00
return ( curr_offset - offset ) ;
2008-08-24 17:42:30 +00:00
}
2008-10-23 19:22:54 +00:00
/* Ocet 14 */
2008-08-24 17:42:30 +00:00
oct = tvb_get_guint8 ( tvb , curr_offset ) ;
switch ( ( oct > > 4 ) & 1 )
{
case 0x00 : str = " Not optimised for signalling traffic " ; break ;
case 0x01 : str = " Optimised for signalling traffic " ; break ;
default : str = " This should not happen - BUG " ;
}
proto_tree_add_text ( tree ,
tvb , curr_offset , 1 ,
" Signalling Indication: (%u) %s " , ( oct > > 4 ) & 1 , str ) ;
switch ( oct & 7 )
{
case 0x00 : str = " unknown " ; break ;
case 0x01 : str = " speech " ; break ;
default : str = " unknown " ;
}
proto_tree_add_text ( tree ,
tvb , curr_offset , 1 ,
" Source Statistics Descriptor: (%u) %s " , oct & 7 , str ) ;
curr_offset + = 1 ;
curr_len - = 1 ;
if ( curr_len = = 0 )
{
2008-09-05 05:49:39 +00:00
EXTRANEOUS_DATA_CHECK ( len , curr_offset - offset ) ;
2008-08-24 17:42:30 +00:00
2008-09-05 05:49:39 +00:00
return ( curr_offset - offset ) ;
2008-08-24 17:42:30 +00:00
}
2008-10-23 19:22:54 +00:00
/* Octet 15 */
2008-08-24 17:42:30 +00:00
oct = tvb_get_guint8 ( tvb , curr_offset ) ;
switch ( oct )
{
case 0x00 : str = " Use the value indicated by the Maximum bit rate for downlink " ; break ;
default : str = " Unspecified " ;
}
2008-10-23 19:22:54 +00:00
if ( ( oct > = 1 ) & & ( oct < = 0x4a ) )
2008-09-05 05:49:39 +00:00
proto_tree_add_text ( tree ,
2008-08-24 17:42:30 +00:00
tvb , curr_offset , 1 ,
2008-09-05 05:49:39 +00:00
" Maximum bit rate for downlink (extended): (%u) %ukbps " , oct , oct * 100 ) ;
2008-10-23 19:22:54 +00:00
if ( ( oct > = 0x4b ) & & ( oct < = 0xba ) )
proto_tree_add_text ( tree ,
tvb , curr_offset , 1 ,
" Maximum bit rate for downlink (extended): (%u) %uMbps " , oct , 16 + oct - 0x4a ) ;
if ( ( oct > = 0xbb ) & & ( oct < = 0xfa ) )
proto_tree_add_text ( tree ,
tvb , curr_offset , 1 ,
" Maximum bit rate for downlink (extended): (%u) %uMbps " , oct , 128 + oct - 0xba * 2 ) ;
2008-08-24 17:42:30 +00:00
else
2008-09-05 05:49:39 +00:00
proto_tree_add_text ( tree ,
2008-08-24 17:42:30 +00:00
tvb , curr_offset , 1 ,
2008-09-05 05:49:39 +00:00
" Maximum bit rate for downlink (extended): (%u) %s " , oct , str ) ;
2008-08-24 17:42:30 +00:00
curr_offset + = 1 ;
curr_len - = 1 ;
if ( curr_len = = 0 )
{
2008-09-05 05:49:39 +00:00
EXTRANEOUS_DATA_CHECK ( len , curr_offset - offset ) ;
2008-08-24 17:42:30 +00:00
2008-09-05 05:49:39 +00:00
return ( curr_offset - offset ) ;
2008-08-24 17:42:30 +00:00
}
2008-10-23 19:22:54 +00:00
/* Octet 16 */
2008-08-24 17:42:30 +00:00
oct = tvb_get_guint8 ( tvb , curr_offset ) ;
switch ( oct )
{
case 0x00 : str = " Use the value indicated by the Guaranteed bit rate for downlink " ; break ;
default : str = " Unspecified " ;
}
if ( ( oct > = 1 ) & & ( oct < = 0x4a ) )
2008-09-05 05:49:39 +00:00
proto_tree_add_text ( tree ,
2008-08-24 17:42:30 +00:00
tvb , curr_offset , 1 ,
2008-09-05 05:49:39 +00:00
" Guaranteed bit rate for downlink (extended): (%u) %ukbps " , oct , oct * 100 ) ;
2008-10-23 19:22:54 +00:00
if ( ( oct > = 0x4b ) & & ( oct < = 0xba ) )
proto_tree_add_text ( tree ,
tvb , curr_offset , 1 ,
" Guaranteed bit rate for downlink (extended): (%u) %uMbps " , oct , 16 + oct - 0x4a ) ;
if ( ( oct > = 0xbb ) & & ( oct < = 0xfa ) )
proto_tree_add_text ( tree ,
tvb , curr_offset , 1 ,
" Guaranteed bit rate for downlink (extended): (%u) %uMbps " , oct , 128 + oct - 0xba * 2 ) ;
2008-08-24 17:42:30 +00:00
else
2008-09-05 05:49:39 +00:00
proto_tree_add_text ( tree ,
2008-08-24 17:42:30 +00:00
tvb , curr_offset , 1 ,
2008-09-05 05:49:39 +00:00
" Guaranteed bit rate for downlink (extended): (%u) %s " , oct , str ) ;
2008-08-24 17:42:30 +00:00
curr_offset + = 1 ;
curr_len - = 1 ;
2008-10-23 19:22:54 +00:00
if ( curr_len = = 0 )
{
EXTRANEOUS_DATA_CHECK ( len , curr_offset - offset ) ;
return ( curr_offset - offset ) ;
}
/* Maximum bit rate for uplink (extended) Octet 17 */
oct = tvb_get_guint8 ( tvb , curr_offset ) ;
switch ( oct )
{
case 0x00 : str = " Use the value indicated by the Maximum bit rate for uplink " ; break ;
default : str = " Unspecified " ;
}
if ( ( oct > = 1 ) & & ( oct < = 0x4a ) )
proto_tree_add_text ( tree ,
tvb , curr_offset , 1 ,
" Maximum bit rate for uplink (extended): (%u) %ukbps " , oct , oct * 100 ) ;
if ( ( oct > = 0x4b ) & & ( oct < = 0xba ) )
proto_tree_add_text ( tree ,
tvb , curr_offset , 1 ,
" Maximum bit rate for uplink (extended): (%u) %uMbps " , oct , 16 + oct - 0x4a ) ;
if ( ( oct > = 0xbb ) & & ( oct < = 0xfa ) )
proto_tree_add_text ( tree ,
tvb , curr_offset , 1 ,
" Maximum bit rate for uplink (extended): (%u) %uMbps " , oct , 128 + oct - 0xba * 2 ) ;
else
proto_tree_add_text ( tree ,
tvb , curr_offset , 1 ,
" Maximum bit rate for uplink (extended): (%u) %s " , oct , str ) ;
curr_offset + = 1 ;
curr_len - = 1 ;
if ( curr_len = = 0 )
{
EXTRANEOUS_DATA_CHECK ( len , curr_offset - offset ) ;
return ( curr_offset - offset ) ;
}
/* Guaranteed bit rate for uplink (extended) Octet 18 */
oct = tvb_get_guint8 ( tvb , curr_offset ) ;
switch ( oct )
{
case 0x00 : str = " Use the value indicated by the Guaranteed bit rate for uplink " ; break ;
default : str = " Unspecified " ;
}
if ( ( oct > = 1 ) & & ( oct < = 0x4a ) )
proto_tree_add_text ( tree ,
tvb , curr_offset , 1 ,
" Guaranteed bit rate for uplink (extended): (%u) %ukbps " , oct , oct * 100 ) ;
if ( ( oct > = 0x4b ) & & ( oct < = 0xba ) )
proto_tree_add_text ( tree ,
tvb , curr_offset , 1 ,
" Guaranteed bit rate for uplink (extended): (%u) %uMbps " , oct , 16 + oct - 0x4a ) ;
if ( ( oct > = 0xbb ) & & ( oct < = 0xfa ) )
proto_tree_add_text ( tree ,
tvb , curr_offset , 1 ,
" Guaranteed bit rate for uplink (extended): (%u) %uMbps " , oct , 128 + oct - 0xba * 2 ) ;
else
proto_tree_add_text ( tree ,
tvb , curr_offset , 1 ,
" Guaranteed bit rate for uplink (extended): (%u) %s " , oct , str ) ;
curr_offset + = 1 ;
curr_len - = 1 ;
2008-08-24 17:42:30 +00:00
EXTRANEOUS_DATA_CHECK ( len , curr_offset - offset ) ;
return ( curr_offset - offset ) ;
}
/*
* [ 8 ] 10.5 .6 .6 SM cause
*/
2008-12-23 20:49:15 +00:00
static guint16
2008-09-05 05:49:39 +00:00
de_sm_cause ( tvbuff_t * tvb , proto_tree * tree , guint32 offset , guint len _U_ , gchar * add_string , int string_len _U_ )
2008-08-24 17:42:30 +00:00
{
guint8 oct ;
guint32 curr_offset ;
const gchar * str ;
curr_offset = offset ;
oct = tvb_get_guint8 ( tvb , curr_offset ) ;
switch ( oct )
{
case 0x08 : str = " Operator Determined Barring " ; break ;
case 0x18 : str = " MBMS bearer capabilities insufficient for the service " ; break ;
case 0x19 : str = " LLC or SNDCP failure(GSM only) " ; break ;
case 0x1a : str = " Insufficient resources " ; break ;
case 0x1b : str = " Missing or unknown APN " ; break ;
case 0x1c : str = " Unknown PDP address or PDP type " ; break ;
2008-12-17 00:08:38 +00:00
case 0x1d : str = " User Authentication failed " ; break ;
2008-08-24 17:42:30 +00:00
case 0x1e : str = " Activation rejected by GGSN " ; break ;
case 0x1f : str = " Activation rejected, unspecified " ; break ;
case 0x20 : str = " Service option not supported " ; break ;
case 0x21 : str = " Requested service option not subscribed " ; break ;
case 0x22 : str = " Service option temporarily out of order " ; break ;
case 0x23 : str = " NSAPI already used (not sent) " ; break ;
case 0x24 : str = " Regular deactivation " ; break ;
case 0x25 : str = " QoS not accepted " ; break ;
case 0x26 : str = " Network failure " ; break ;
case 0x27 : str = " Reactivation required " ; break ;
case 0x28 : str = " Feature not supported " ; break ;
case 0x29 : str = " Semantic error in the TFT operation " ; break ;
case 0x2a : str = " Syntactical error in the TFT operation " ; break ;
case 0x2b : str = " Unknown PDP context " ; break ;
case 0x2e : str = " PDP context without TFT already activated " ; break ;
case 0x2f : str = " Multicast group membership time-out " ; break ;
case 0x2c : str = " Semantic errors in packet filter(s) " ; break ;
case 0x2d : str = " Syntactical errors in packet filter(s) " ; break ;
case 0x51 : str = " Invalid transaction identifier value " ; break ;
case 0x5f : str = " Semantically incorrect message " ; break ;
case 0x60 : str = " Invalid mandatory information " ; break ;
case 0x61 : str = " Message type non-existent or not implemented " ; break ;
case 0x62 : str = " Message type not compatible with the protocol state " ; break ;
case 0x63 : str = " Information element non-existent or not implemented " ; break ;
case 0x64 : str = " Conditional IE error " ; break ;
case 0x65 : str = " Message not compatible with the protocol state " ; break ;
case 0x6f : str = " Protocol error, unspecified " ; break ;
case 0x70 : str = " APN restriction value incompatible with active PDP context " ; break ;
default : str = " Protocol error, unspecified " ; break ;
}
proto_tree_add_text ( tree ,
2008-09-05 05:49:39 +00:00
tvb , curr_offset , 1 ,
" Cause: (%u) %s %s " ,
oct , str , add_string ? add_string : " " ) ;
2008-08-24 17:42:30 +00:00
curr_offset + + ;
return ( curr_offset - offset ) ;
}
/*
* [ 7 ] 10.5 .6 .7
*/
2008-12-23 20:49:15 +00:00
static guint16
2008-08-24 17:42:30 +00:00
de_sm_linked_ti ( tvbuff_t * tvb , proto_tree * tree , guint32 offset , guint len , gchar * add_string _U_ , int string_len _U_ )
{
guint32 curr_offset ;
guint curr_len ;
2009-05-07 21:22:36 +00:00
gchar oct ;
2008-08-24 17:42:30 +00:00
2009-05-07 21:22:36 +00:00
gchar ti_flag [ 2 ] [ 80 ] = { " The message is sent from the side that originates the TI " ,
2008-08-24 17:42:30 +00:00
" The message is sent to the side that originates the TI " } ;
curr_len = len ;
curr_offset = offset ;
oct = tvb_get_guint8 ( tvb , curr_offset ) ;
proto_tree_add_text ( tree ,
tvb , curr_offset , 1 ,
" TI flag: (%u) %s " , oct > > 7 , ti_flag [ oct > > 7 ] ) ;
if ( curr_len > 1 )
{
oct = tvb_get_guint8 ( tvb , curr_offset ) ;
2008-09-05 05:49:39 +00:00
2008-08-24 17:42:30 +00:00
proto_tree_add_text ( tree ,
2008-09-05 05:49:39 +00:00
tvb , curr_offset , 1 ,
" TI value: 0x%02x (%u) " , oct & 0x7f , oct & 0x7f ) ;
2008-08-24 17:42:30 +00:00
proto_tree_add_text ( tree ,
2008-09-05 05:49:39 +00:00
tvb , curr_offset , 1 ,
" ext: 0x%02x (%u) " , oct > > 7 , oct > > 7 ) ;
2008-08-24 17:42:30 +00:00
}
else
{
proto_tree_add_text ( tree ,
2008-09-05 05:49:39 +00:00
tvb , curr_offset , 1 ,
" TI value: 0x%02x (%u) " , ( oct > > 4 ) & 7 , ( oct > > 4 ) & 7 ) ;
2008-08-24 17:42:30 +00:00
}
curr_offset + = curr_len ;
EXTRANEOUS_DATA_CHECK ( len , curr_offset - offset ) ;
return ( curr_offset - offset ) ;
}
/*
* [ 7 ] 10.5 .6 .9
*/
2008-12-23 20:49:15 +00:00
static guint16
2008-09-05 05:49:39 +00:00
de_sm_sapi ( tvbuff_t * tvb , proto_tree * tree , guint32 offset , guint len _U_ , gchar * add_string , int string_len _U_ )
2008-08-24 17:42:30 +00:00
{
guint8 oct ;
guint32 curr_offset ;
curr_offset = offset ;
oct = tvb_get_guint8 ( tvb , curr_offset ) ;
proto_tree_add_text ( tree ,
2008-09-05 05:49:39 +00:00
tvb , curr_offset , 1 ,
" LLC SAPI: 0x%02x (%u) %s " ,
oct & 0x0f , oct & 0x0f , add_string ? add_string : " " ) ;
2008-08-24 17:42:30 +00:00
curr_offset + + ;
return ( curr_offset - offset ) ;
}
/*
* [ 7 ] 10.5 .6 .10
*/
2008-12-23 20:49:15 +00:00
static guint16
2008-09-05 05:49:39 +00:00
de_sm_tear_down ( tvbuff_t * tvb , proto_tree * tree , guint32 offset , guint len _U_ , gchar * add_string , int string_len _U_ )
2008-08-24 17:42:30 +00:00
{
guint8 oct ;
guint32 curr_offset ;
gchar str [ 2 ] [ 30 ] = { " tear down not requested " , " tear down requested " } ;
curr_offset = offset ;
oct = tvb_get_guint8 ( tvb , curr_offset ) ;
proto_tree_add_text ( tree ,
2008-09-05 05:49:39 +00:00
tvb , curr_offset , 1 ,
" Tear Down Indicator: (%u) %s %s " ,
oct & 1 , str [ oct & 1 ] , add_string ? add_string : " " ) ;
2008-08-24 17:42:30 +00:00
curr_offset + + ;
return ( curr_offset - offset ) ;
}
/*
* [ 7 ] 10.5 .6 .11
*/
/* Packet Flow Identifier value (octet 3) */
static const value_string gsm_a_packet_flow_id_vals [ ] = {
{ 0 , " Best Effort " } ,
{ 1 , " Signaling " } ,
{ 2 , " SMS " } ,
{ 3 , " TOM8 " } ,
{ 4 , " reserved " } ,
{ 5 , " reserved " } ,
{ 6 , " reserved " } ,
{ 7 , " reserved " } ,
{ 0 , NULL }
} ;
2008-12-23 20:49:15 +00:00
guint16
2008-08-24 17:42:30 +00:00
de_sm_pflow_id ( tvbuff_t * tvb , proto_tree * tree , guint32 offset , guint len , gchar * add_string _U_ , int string_len _U_ )
{
guint32 curr_offset ;
guint curr_len ;
guchar oct ;
curr_len = len ;
curr_offset = offset ;
oct = tvb_get_guint8 ( tvb , curr_offset ) ;
proto_tree_add_text ( tree ,
tvb , curr_offset , 1 ,
" Packet Flow Identifier: (%u) %s " , oct & 0x7f ,
val_to_str ( oct & 0x7f , gsm_a_packet_flow_id_vals , " dynamically assigned (%u) " ) ) ;
curr_offset + = curr_len ;
EXTRANEOUS_DATA_CHECK ( len , curr_offset - offset ) ;
return ( curr_offset - offset ) ;
}
/*
* [ 7 ] 10.5 .6 .12 TFT - Traffic Flow Template
*/
/* TFT operation code (octet 3) */
static const value_string gsm_a_tft_op_code_vals [ ] = {
{ 0 , " Spare " } ,
{ 1 , " Create new TFT " } ,
{ 2 , " Delete existing TFT " } ,
{ 3 , " Add packet filters to existing TFT " } ,
{ 4 , " Replace packet filters in existing TFT " } ,
{ 5 , " Delete packet filters from existing TFT " } ,
{ 6 , " No TFT operation " } ,
{ 7 , " Reserved " } ,
{ 0 , NULL }
} ;
static const true_false_string gsm_a_tft_e_bit = {
" parameters list is included " ,
" parameters list is not included "
} ;
2008-12-23 20:49:15 +00:00
static guint16
2008-08-24 17:42:30 +00:00
de_sm_tflow_temp ( tvbuff_t * tvb , proto_tree * tree , guint32 offset , guint len , gchar * add_string _U_ , int string_len _U_ )
{
2009-05-07 21:22:36 +00:00
guint32 curr_offset ;
guint curr_len ;
proto_item * tf = NULL ;
proto_tree * tf_tree = NULL ;
proto_tree * comp_tree = NULL ;
guchar op_code ;
guchar pkt_fil_count ;
guchar e_bit ;
const gchar * str ;
guchar count ;
guchar oct ;
gint pf_length ;
gint pf_identifier ;
gint pack_component_type ;
2008-08-24 17:42:30 +00:00
curr_len = len ;
curr_offset = offset ;
/*
* parse first octet . It contain TFT operation code , E bit and Number of packet filters
*/
oct = tvb_get_guint8 ( tvb , curr_offset ) ;
op_code = oct > > 5 ;
pkt_fil_count = oct & 0x0f ;
e_bit = ( oct > > 4 ) & 1 ;
proto_tree_add_item ( tree , hf_gsm_a_tft_op_code , tvb , curr_offset , 1 , FALSE ) ;
proto_tree_add_item ( tree , hf_gsm_a_tft_e_bit , tvb , curr_offset , 1 , FALSE ) ;
proto_tree_add_item ( tree , hf_gsm_a_tft_pkt_flt , tvb , curr_offset , 1 , FALSE ) ;
curr_offset + + ;
curr_len - - ;
/* Packet filter list dissect */
count = 0 ;
if ( op_code = = 2 ) /* delete TFT contains no packet filters. so we will jump over it */
2008-09-05 05:49:39 +00:00
count = pkt_fil_count ;
2008-08-24 17:42:30 +00:00
while ( count < pkt_fil_count )
{
2008-09-05 05:49:39 +00:00
tf = proto_tree_add_text ( tree ,
2008-08-24 17:42:30 +00:00
tvb , curr_offset , 1 ,
" Packet filter %d " , count ) ; /* 0-> 7 */
tf_tree = proto_item_add_subtree ( tf , ett_sm_tft ) ;
2008-09-05 05:49:39 +00:00
if ( op_code = = 5 ) /* Delete packet filters from existing TFT - just a list of identifiers */
{
if ( ( curr_offset - offset ) < 1 ) {
proto_tree_add_text ( tf_tree , tvb , curr_offset , 1 , " Not enough data " ) ;
return ( curr_offset - offset ) ;
}
oct = tvb_get_guint8 ( tvb , curr_offset ) ;
curr_offset + + ;
curr_len - - ;
2008-08-24 17:42:30 +00:00
2008-09-05 05:49:39 +00:00
proto_tree_add_text ( tf_tree ,
tvb , curr_offset - 1 , 1 ,
" Packet filter identifier: 0x%02x (%u) " , oct , oct ) ;
2008-08-24 17:42:30 +00:00
}
2008-09-05 05:49:39 +00:00
else /* create new, Add packet filters or Replace packet filters */
{
2008-08-24 17:42:30 +00:00
2008-09-05 05:49:39 +00:00
if ( ( curr_offset - offset ) < 1 ) {
proto_tree_add_text ( tf_tree , tvb , curr_offset , 1 , " Not enough data " ) ;
return ( curr_offset - offset ) ;
}
pf_identifier = tvb_get_guint8 ( tvb , curr_offset ) ;
curr_offset + + ;
curr_len - - ;
2008-08-24 17:42:30 +00:00
2008-09-05 05:49:39 +00:00
proto_tree_add_text ( tf_tree ,
tvb , curr_offset - 1 , 1 ,
" Packet filter identifier: %u (%u) " , pf_identifier , pf_identifier ) ;
2008-08-24 17:42:30 +00:00
if ( ( curr_offset - offset ) < 1 ) {
proto_tree_add_text ( tf_tree , tvb , curr_offset , 1 , " Not enough data " ) ;
return ( curr_offset - offset ) ;
}
2008-09-05 05:49:39 +00:00
oct = tvb_get_guint8 ( tvb , curr_offset ) ;
2008-08-24 17:42:30 +00:00
curr_offset + + ;
curr_len - - ;
2008-09-05 05:49:39 +00:00
proto_tree_add_text ( tf_tree ,
tvb , curr_offset - 1 , 1 ,
" Packet evaluation precedence: 0x%02x (%u) " , oct , oct ) ;
if ( ( curr_offset - offset ) < 1 ) { proto_tree_add_text ( tf_tree , tvb , curr_offset , 1 , " Not enough data " ) ; return ( curr_offset - offset ) ; }
pf_length = tvb_get_guint8 ( tvb , curr_offset ) ;
curr_offset + + ;
curr_len - - ;
proto_tree_add_text ( tf_tree ,
tvb , curr_offset - 1 , 1 ,
" Packet filter length: 0x%02x (%u) " , pf_length , pf_length ) ;
/* New tree for component */
/* Dissect Packet filter Component */
/* while ( filter_len > 1 ) */
/* packet filter component type identifier: */
if ( pf_length > 0 ) {
if ( ( curr_offset - offset ) < 1 ) {
proto_tree_add_text ( tf_tree , tvb , curr_offset , 1 , " Not enough data " ) ;
return ( curr_offset - offset ) ;
}
pack_component_type = tvb_get_guint8 ( tvb , curr_offset ) ;
curr_offset + + ;
curr_len - - ;
tf = proto_tree_add_text ( tf_tree , tvb , curr_offset - 1 , 1 , " Packet filter component type identifier: " ) ;
comp_tree = proto_item_add_subtree ( tf , ett_sm_tft ) ;
switch ( pack_component_type ) {
2008-08-24 17:42:30 +00:00
case 0x10 :
str = " IPv4 source address type " ;
proto_tree_add_item ( comp_tree , hf_gsm_a_tft_ip4_address , tvb , curr_offset , 4 , FALSE ) ;
2008-09-05 05:49:39 +00:00
curr_offset + = 4 ;
curr_len - = 4 ;
2008-08-24 17:42:30 +00:00
proto_tree_add_item ( comp_tree , hf_gsm_a_tft_ip4_mask , tvb , curr_offset , 4 , FALSE ) ;
2008-09-05 05:49:39 +00:00
curr_offset + = 4 ;
curr_len - = 4 ;
2008-08-24 17:42:30 +00:00
break ;
case 0x20 :
str = " IPv6 source address type " ;
proto_tree_add_item ( comp_tree , hf_gsm_a_tft_ip6_address , tvb , curr_offset , 16 , FALSE ) ;
curr_offset + = 16 ;
curr_len - = 16 ;
proto_tree_add_item ( comp_tree , hf_gsm_a_tft_ip6_mask , tvb , curr_offset , 16 , FALSE ) ;
curr_offset + = 16 ;
curr_len - = 16 ;
break ;
case 0x30 :
str = " Protocol identifier/Next header type " ;
proto_tree_add_item ( comp_tree , hf_gsm_a_tft_protocol_header , tvb , curr_offset , 1 , FALSE ) ;
curr_offset + = 1 ;
curr_len - = 1 ;
break ;
case 0x40 :
str = " Single destination port type " ;
proto_tree_add_item ( comp_tree , hf_gsm_a_tft_port , tvb , curr_offset , 2 , FALSE ) ;
curr_offset + = 2 ;
curr_len - = 2 ;
case 0x41 :
str = " Destination port range type " ;
proto_tree_add_item ( comp_tree , hf_gsm_a_tft_port_low , tvb , curr_offset , 2 , FALSE ) ;
proto_tree_add_item ( comp_tree , hf_gsm_a_tft_port_high , tvb , curr_offset , 2 , FALSE ) ;
curr_offset + = 4 ;
curr_len - = 4 ;
break ;
case 0x50 :
str = " Single source port type " ;
proto_tree_add_item ( comp_tree , hf_gsm_a_tft_port , tvb , curr_offset , 2 , FALSE ) ;
curr_offset + = 2 ;
curr_len - = 2 ;
break ;
case 0x51 :
str = " Source port range type " ;
proto_tree_add_item ( comp_tree , hf_gsm_a_tft_port_low , tvb , curr_offset , 2 , FALSE ) ;
proto_tree_add_item ( comp_tree , hf_gsm_a_tft_port_high , tvb , curr_offset , 2 , FALSE ) ;
curr_offset + = 4 ;
curr_len - = 4 ;
break ;
case 0x60 :
str = " Security parameter index type " ;
proto_tree_add_item ( comp_tree , hf_gsm_a_tft_security , tvb , curr_offset , 4 , FALSE ) ;
curr_offset + = 4 ;
curr_len - = 4 ;
break ;
case 0x70 :
str = " Type of service/Traffic class type " ;
proto_tree_add_item ( comp_tree , hf_gsm_a_qos_traffic_cls , tvb , curr_offset , 1 , FALSE ) ;
proto_tree_add_item ( comp_tree , hf_gsm_a_tft_traffic_mask , tvb , curr_offset , 1 , FALSE ) ;
curr_offset + = 2 ;
curr_len - = 2 ;
break ;
case 0x80 :
str = " Flow label type " ;
proto_tree_add_item ( comp_tree , hf_gsm_a_tft_traffic_mask , tvb , curr_offset , 1 , FALSE ) ;
curr_offset + = 3 ;
curr_len - = 3 ;
break ;
default :
str = " not specified " ;
2008-09-05 05:49:39 +00:00
}
proto_item_append_text ( tf , " (%u) %s " , pack_component_type , str ) ;
count + + ;
2008-08-24 17:42:30 +00:00
}
}
}
/* The parameters list contains a variable number of parameters that might need to be
* transferred in addition to the packet filters . If the parameters list is included , the E
* bit is set to 1 ; otherwise , the E bit is set to 0.
*/
2008-09-05 05:49:39 +00:00
if ( e_bit = = 1 ) {
2008-12-17 00:08:38 +00:00
proto_tree_add_text ( tf_tree , tvb , curr_offset , 1 , " Note: Possible Authorization Token/Flow Identifier not decoded yet " ) ;
2008-09-05 05:49:39 +00:00
}
return ( curr_offset - offset ) ;
2008-08-24 17:42:30 +00:00
}
2008-12-23 20:49:15 +00:00
guint16 ( * gm_elem_fcn [ ] ) ( tvbuff_t * tvb , proto_tree * tree , guint32 offset , guint len , gchar * add_string , int string_len ) = {
2008-08-24 17:42:30 +00:00
/* GPRS Mobility Management Information Elements 10.5.5 */
de_gmm_attach_res , /* Attach Result */
de_gmm_attach_type , /* Attach Type */
de_gmm_ciph_alg , /* Cipher Algorithm */
de_gmm_tmsi_stat , /* TMSI Status */
de_gmm_detach_type , /* Detach Type */
de_gmm_drx_param , /* DRX Parameter */
2009-05-07 21:22:36 +00:00
de_gmm_ftostby , /* Force to Standby */
2008-08-24 17:42:30 +00:00
de_gmm_ftostby_h , /* Force to Standby - Info is in the high nibble */
de_gmm_ptmsi_sig , /* P-TMSI Signature */
de_gmm_ptmsi_sig2 , /* P-TMSI Signature 2 */
de_gmm_ident_type2 , /* Identity Type 2 */
de_gmm_imeisv_req , /* IMEISV Request */
de_gmm_rec_npdu_lst , /* Receive N-PDU Numbers List */
de_gmm_ms_net_cap , /* MS Network Capability */
2009-05-07 21:22:36 +00:00
de_gmm_ms_radio_acc_cap , /* MS Radio Access Capability */
de_gmm_cause , /* GMM Cause */
de_gmm_rai , /* Routing Area Identification */
2008-08-24 17:42:30 +00:00
de_gmm_update_res , /* Update Result */
de_gmm_update_type , /* Update Type */
de_gmm_ac_ref_nr , /* A&C Reference Number */
2009-05-07 21:22:36 +00:00
de_gmm_ac_ref_nr_h , /* A&C Reference Numer - Info is in the high nibble */
2008-08-24 17:42:30 +00:00
de_gmm_service_type , /* Service Type */
de_gmm_cell_notfi , /* Cell Notification */
de_gmm_ps_lcs_cap , /* PS LCS Capability */
de_gmm_net_feat_supp , /* Network Feature Support */
de_gmm_rat_info_container , /* Inter RAT information container */
/* Session Management Information Elements 10.5.6 */
2009-05-07 21:22:36 +00:00
de_sm_apn , /* Access Point Name */
de_sm_nsapi , /* Network Service Access Point Identifier */
de_sm_pco , /* Protocol Configuration Options */
de_sm_pdp_addr , /* Packet Data Protocol Address */
de_sm_qos , /* Quality Of Service */
de_sm_cause , /* SM Cause */
2008-08-24 17:42:30 +00:00
de_sm_linked_ti , /* Linked TI */
2009-05-07 21:22:36 +00:00
de_sm_sapi , /* LLC Service Access Point Identifier */
2008-08-24 17:42:30 +00:00
de_sm_tear_down , /* Tear Down Indicator */
2009-05-07 21:22:36 +00:00
de_sm_pflow_id , /* Packet Flow Identifier */
2008-08-24 17:42:30 +00:00
de_sm_tflow_temp , /* Traffic Flow Template */
/* GPRS Common Information Elements 10.5.7 */
de_gc_context_stat , /* PDP Context Status */
de_gc_radio_prio , /* Radio Priority */
2009-05-07 21:22:36 +00:00
de_gc_timer , /* GPRS Timer */
de_gc_timer2 , /* GPRS Timer 2 */
2008-08-24 17:42:30 +00:00
de_gc_radio_prio2 , /* Radio Priority 2 */
2009-05-07 21:22:36 +00:00
de_gc_mbms_context_stat , /* 10.5.7.6 MBMS context status */
2008-08-24 17:42:30 +00:00
NULL , /* NONE */
} ;
/* MESSAGE FUNCTIONS */
/*
* [ 7 ] 9.4 .1
*/
static void
dtap_gmm_attach_req ( tvbuff_t * tvb , proto_tree * tree , guint32 offset , guint len )
{
guint32 curr_offset ;
guint32 consumed ;
guint curr_len ;
curr_offset = offset ;
curr_len = len ;
gsm_a_dtap_pinfo - > p2p_dir = P2P_DIR_RECV ;
ELEM_MAND_LV ( GSM_A_PDU_TYPE_GM , DE_MS_NET_CAP , " " ) ;
/* Included in attach type
ELEM_MAND_V ( GSM_A_PDU_TYPE_COMMON , DE_CIPH_KEY_SEQ_NUM ) ;
curr_offset - - ;
curr_len + + ;
*/
ELEM_MAND_V ( GSM_A_PDU_TYPE_GM , DE_ATTACH_TYPE ) ;
ELEM_MAND_V ( GSM_A_PDU_TYPE_GM , DE_DRX_PARAM ) ;
ELEM_MAND_LV ( GSM_A_PDU_TYPE_COMMON , DE_MID , " " ) ;
ELEM_MAND_V ( GSM_A_PDU_TYPE_GM , DE_RAI ) ;
ELEM_MAND_LV ( GSM_A_PDU_TYPE_GM , DE_MS_RAD_ACC_CAP , " " ) ;
ELEM_OPT_TV ( 0x19 , GSM_A_PDU_TYPE_GM , DE_P_TMSI_SIG , " - Old P-TMSI Signature " ) ;
ELEM_OPT_TV ( 0x17 , GSM_A_PDU_TYPE_GM , DE_GPRS_TIMER , " - Ready Timer " ) ;
ELEM_OPT_TV_SHORT ( 0x90 , GSM_A_PDU_TYPE_GM , DE_TMSI_STAT , " " ) ;
ELEM_OPT_TLV ( 0x33 , GSM_A_PDU_TYPE_GM , DE_PS_LCS_CAP , " " ) ;
EXTRANEOUS_DATA_CHECK ( curr_len , 0 ) ;
}
/*
* [ 7 ] 9.4 .2
*/
static void
dtap_gmm_attach_acc ( tvbuff_t * tvb , proto_tree * tree , guint32 offset , guint len )
{
guint32 curr_offset ;
guint32 consumed ;
guint curr_len ;
curr_offset = offset ;
curr_len = len ;
gsm_a_dtap_pinfo - > p2p_dir = P2P_DIR_SENT ;
ELEM_MAND_V ( GSM_A_PDU_TYPE_GM , DE_FORCE_TO_STAND_H ) ;
curr_len + + ;
curr_offset - - ;
ELEM_MAND_V ( GSM_A_PDU_TYPE_GM , DE_ATTACH_RES ) ;
ELEM_MAND_V ( GSM_A_PDU_TYPE_GM , DE_GPRS_TIMER ) ;
ELEM_MAND_V ( GSM_A_PDU_TYPE_GM , DE_RAD_PRIO_2 ) ;
curr_len + + ;
curr_offset - - ;
ELEM_MAND_V ( GSM_A_PDU_TYPE_GM , DE_RAD_PRIO ) ;
ELEM_MAND_V ( GSM_A_PDU_TYPE_GM , DE_RAI ) ;
ELEM_OPT_TV ( 0x19 , GSM_A_PDU_TYPE_GM , DE_P_TMSI_SIG , " " ) ;
ELEM_OPT_TV ( 0x17 , GSM_A_PDU_TYPE_GM , DE_GPRS_TIMER , " - Negotiated Ready Timer " ) ;
ELEM_OPT_TLV ( 0x18 , GSM_A_PDU_TYPE_COMMON , DE_MID , " - Allocated P-TMSI " ) ;
ELEM_OPT_TLV ( 0x23 , GSM_A_PDU_TYPE_COMMON , DE_MID , " " ) ;
ELEM_OPT_TV ( 0x25 , GSM_A_PDU_TYPE_GM , DE_GMM_CAUSE , " " ) ;
ELEM_OPT_TLV ( 0x2A , GSM_A_PDU_TYPE_GM , DE_GPRS_TIMER_2 , " - T3302 " ) ;
ELEM_OPT_T ( 0x8C , GSM_A_PDU_TYPE_GM , DE_CELL_NOT , " " ) ;
ELEM_OPT_TLV ( 0x4A , GSM_A_PDU_TYPE_COMMON , DE_PLMN_LIST , " " ) ;
ELEM_OPT_TV_SHORT ( 0xB0 , GSM_A_PDU_TYPE_GM , DE_NET_FEAT_SUP , " " ) ;
ELEM_OPT_TLV ( 0x34 , GSM_A_PDU_TYPE_DTAP , DE_EMERGENCY_NUM_LIST , " " ) ;
EXTRANEOUS_DATA_CHECK ( curr_len , 0 ) ;
}
/*
* [ 7 ] 9.4 .3
*/
static void
dtap_gmm_attach_com ( tvbuff_t * tvb , proto_tree * tree , guint32 offset , guint len )
{
guint32 curr_offset ;
/* guint32 consumed; */
guint curr_len ;
curr_offset = offset ;
curr_len = len ;
gsm_a_dtap_pinfo - > p2p_dir = P2P_DIR_RECV ;
EXTRANEOUS_DATA_CHECK ( curr_len , 0 ) ;
}
/*
* [ 7 ] 9.4 .4
*/
static void
dtap_gmm_attach_rej ( tvbuff_t * tvb , proto_tree * tree , guint32 offset , guint len )
{
guint32 curr_offset ;
guint32 consumed ;
guint curr_len ;
curr_offset = offset ;
curr_len = len ;
gsm_a_dtap_pinfo - > p2p_dir = P2P_DIR_SENT ;
ELEM_MAND_V ( GSM_A_PDU_TYPE_GM , DE_GMM_CAUSE ) ;
ELEM_OPT_TLV ( 0x2A , GSM_A_PDU_TYPE_GM , DE_GPRS_TIMER_2 , " - T3302 " ) ;
EXTRANEOUS_DATA_CHECK ( curr_len , 0 ) ;
}
/*
* [ 7 ] 9.4 .5
*/
static void
dtap_gmm_detach_req ( tvbuff_t * tvb , proto_tree * tree , guint32 offset , guint len )
{
guint32 curr_offset ;
guint32 consumed ;
guint curr_len ;
curr_offset = offset ;
curr_len = len ;
gsm_a_dtap_pinfo - > p2p_dir = P2P_DIR_SENT ;
ELEM_MAND_V ( GSM_A_PDU_TYPE_GM , DE_FORCE_TO_STAND_H ) ;
/* Force to standy might be wrong - To decode it correct, we need the direction */
curr_len + + ;
curr_offset - - ;
ELEM_MAND_V ( GSM_A_PDU_TYPE_GM , DE_DETACH_TYPE ) ;
ELEM_OPT_TV ( 0x25 , GSM_A_PDU_TYPE_GM , DE_GMM_CAUSE , " " ) ;
ELEM_OPT_TLV ( 0x18 , GSM_A_PDU_TYPE_COMMON , DE_MID , " - P-TMSI " ) ;
ELEM_OPT_TLV ( 0x19 , GSM_A_PDU_TYPE_GM , DE_P_TMSI_SIG , " " ) ;
EXTRANEOUS_DATA_CHECK ( curr_len , 0 ) ;
}
/*
* [ 7 ] 9.4 .6
*/
static void
dtap_gmm_detach_acc ( tvbuff_t * tvb , proto_tree * tree , guint32 offset , guint len )
{
guint32 curr_offset ;
guint32 consumed ;
guint curr_len ;
curr_offset = offset ;
curr_len = len ;
gsm_a_dtap_pinfo - > p2p_dir = P2P_DIR_RECV ;
if ( curr_len ! = 0 )
{
ELEM_MAND_V ( GSM_A_PDU_TYPE_COMMON , DE_SPARE_NIBBLE ) ;
curr_len + + ;
curr_offset - - ;
ELEM_MAND_V ( GSM_A_PDU_TYPE_GM , DE_FORCE_TO_STAND ) ;
}
EXTRANEOUS_DATA_CHECK ( curr_len , 0 ) ;
}
/*
* [ 7 ] 9.4 .7
*/
static void
dtap_gmm_ptmsi_realloc_cmd ( tvbuff_t * tvb , proto_tree * tree , guint32 offset , guint len )
{
guint32 curr_offset ;
guint32 consumed ;
guint curr_len ;
curr_offset = offset ;
curr_len = len ;
gsm_a_dtap_pinfo - > p2p_dir = P2P_DIR_SENT ;
ELEM_MAND_LV ( GSM_A_PDU_TYPE_COMMON , DE_MID , " - Allocated P-TMSI " ) ;
ELEM_MAND_V ( GSM_A_PDU_TYPE_GM , DE_RAI ) ;
ELEM_MAND_V ( GSM_A_PDU_TYPE_COMMON , DE_SPARE_NIBBLE ) ;
curr_len + + ;
curr_offset - - ;
ELEM_MAND_V ( GSM_A_PDU_TYPE_GM , DE_FORCE_TO_STAND ) ;
ELEM_OPT_TV ( 0x19 , GSM_A_PDU_TYPE_COMMON , DE_MID , " - P-TMSI Signature " ) ;
EXTRANEOUS_DATA_CHECK ( curr_len , 0 ) ;
}
/*
* [ 7 ] 9.4 .8
*/
static void
dtap_gmm_ptmsi_realloc_com ( tvbuff_t * tvb , proto_tree * tree , guint32 offset , guint len )
{
guint32 curr_offset ;
/* guint32 consumed; */
guint curr_len ;
curr_offset = offset ;
curr_len = len ;
gsm_a_dtap_pinfo - > p2p_dir = P2P_DIR_RECV ;
EXTRANEOUS_DATA_CHECK ( curr_len , 0 ) ;
}
/*
* [ 7 ] 9.4 .9
*/
static void
dtap_gmm_auth_ciph_req ( tvbuff_t * tvb , proto_tree * tree , guint32 offset , guint len )
{
guint32 curr_offset ;
guint32 consumed ;
2009-05-07 21:22:36 +00:00
guint curr_len ;
guint8 oct ;
2008-08-24 17:42:30 +00:00
curr_offset = offset ;
curr_len = len ;
gsm_a_dtap_pinfo - > p2p_dir = P2P_DIR_SENT ;
ELEM_MAND_V ( GSM_A_PDU_TYPE_GM , DE_IMEISV_REQ ) ;
curr_offset - - ;
curr_len + + ;
ELEM_MAND_V ( GSM_A_PDU_TYPE_GM , DE_CIPH_ALG ) ;
ELEM_MAND_V ( GSM_A_PDU_TYPE_GM , DE_AC_REF_NUM_H ) ;
curr_offset - - ;
curr_len + + ;
ELEM_MAND_V ( GSM_A_PDU_TYPE_GM , DE_FORCE_TO_STAND ) ;
ELEM_OPT_TV ( 0x21 , GSM_A_PDU_TYPE_DTAP , DE_AUTH_PARAM_RAND , " " ) ;
#if 0
ELEM_OPT_TV_SHORT ( 0x08 , GSM_A_PDU_TYPE_COMMON , DE_CIPH_KEY_SEQ_NUM , " " ) ;
# else
if ( curr_len > 0 )
{
2008-09-05 05:49:39 +00:00
oct = tvb_get_guint8 ( tvb , curr_offset ) ;
if ( ( oct & 0xf0 ) = = 0x80 )
{
2008-08-24 17:42:30 +00:00
/* The ciphering key sequence number is added here */
2008-09-05 05:49:39 +00:00
proto_tree_add_text ( tree ,
2008-08-24 17:42:30 +00:00
tvb , curr_offset , 1 ,
" Ciphering key sequence number: 0x%02x (%u) " ,
2008-09-05 05:49:39 +00:00
oct & 7 ,
2008-08-24 17:42:30 +00:00
oct & 7 ) ;
2008-09-05 05:49:39 +00:00
curr_offset + + ;
2008-08-24 17:42:30 +00:00
curr_len - - ;
2008-09-05 05:49:39 +00:00
}
2008-08-24 17:42:30 +00:00
}
# endif
if ( curr_len = = 0 )
{
EXTRANEOUS_DATA_CHECK ( curr_len , 0 ) ;
return ;
}
ELEM_OPT_TLV ( 0x28 , GSM_A_PDU_TYPE_DTAP , DE_AUTH_PARAM_AUTN , " " ) ;
EXTRANEOUS_DATA_CHECK ( curr_len , 0 ) ;
}
/*
* [ 7 ] 9.4 .10
*/
static void
dtap_gmm_auth_ciph_resp ( tvbuff_t * tvb , proto_tree * tree , guint32 offset , guint len )
{
guint32 curr_offset ;
guint32 consumed ;
guint curr_len ;
curr_offset = offset ;
curr_len = len ;
gsm_a_dtap_pinfo - > p2p_dir = P2P_DIR_RECV ;
ELEM_MAND_V ( GSM_A_PDU_TYPE_COMMON , DE_SPARE_NIBBLE ) ;
curr_offset - - ;
curr_len + + ;
ELEM_MAND_V ( GSM_A_PDU_TYPE_GM , DE_AC_REF_NUM ) ;
ELEM_OPT_TV ( 0x22 , GSM_A_PDU_TYPE_DTAP , DE_AUTH_RESP_PARAM , " " ) ;
ELEM_OPT_TLV ( 0x23 , GSM_A_PDU_TYPE_COMMON , DE_MID , " - IMEISV " ) ;
ELEM_OPT_TLV ( 0x29 , GSM_A_PDU_TYPE_DTAP , DE_AUTH_RESP_PARAM_EXT , " " ) ;
EXTRANEOUS_DATA_CHECK ( curr_len , 0 ) ;
}
/*
* [ 7 ] 9.4 .11
*/
static void
dtap_gmm_auth_ciph_rej ( tvbuff_t * tvb , proto_tree * tree , guint32 offset , guint len )
{
guint32 curr_offset ;
guint curr_len ;
curr_offset = offset ;
curr_len = len ;
gsm_a_dtap_pinfo - > p2p_dir = P2P_DIR_SENT ;
EXTRANEOUS_DATA_CHECK ( curr_len , 0 ) ;
}
/*
* [ 7 ] 9.4 .10 a
*/
static void
dtap_gmm_auth_ciph_fail ( tvbuff_t * tvb , proto_tree * tree , guint32 offset , guint len )
{
guint32 curr_offset ;
guint32 consumed ;
guint curr_len ;
curr_offset = offset ;
curr_len = len ;
gsm_a_dtap_pinfo - > p2p_dir = P2P_DIR_RECV ;
ELEM_MAND_V ( GSM_A_PDU_TYPE_GM , DE_GMM_CAUSE ) ;
ELEM_OPT_TLV ( 0x30 , GSM_A_PDU_TYPE_DTAP , DE_AUTH_FAIL_PARAM , " " ) ;
EXTRANEOUS_DATA_CHECK ( curr_len , 0 ) ;
}
/*
* [ 7 ] 9.4 .12
*/
static void
dtap_gmm_ident_req ( tvbuff_t * tvb , proto_tree * tree , guint32 offset , guint len )
{
guint32 curr_offset ;
guint curr_len ;
curr_offset = offset ;
curr_len = len ;
gsm_a_dtap_pinfo - > p2p_dir = P2P_DIR_SENT ;
/* If the half octect that are about to get decoded is the LAST in the octetstream, the macro will call return BEFORE we get a chance to fix the index. The end result will be that the first half-octet will be decoded but not the last. */
2009-05-07 21:22:36 +00:00
#if 0
ELEM_MAND_V ( GSM_A_PDU_TYPE_GM , DE_ID_TYPE_2 ) ;
2008-08-24 17:42:30 +00:00
curr_offset - - ;
curr_len + + ;
2009-05-07 21:22:36 +00:00
ELEM_MAND_V ( GSM_A_PDU_TYPE_GM , DE_FORCE_TO_STAND_H ) ;
# endif
2008-08-24 17:42:30 +00:00
elem_v ( tvb , tree , GSM_A_PDU_TYPE_GM , DE_FORCE_TO_STAND_H , curr_offset ) ;
elem_v ( tvb , tree , GSM_A_PDU_TYPE_GM , DE_ID_TYPE_2 , curr_offset ) ;
curr_offset + = 1 ;
curr_len - = 1 ;
EXTRANEOUS_DATA_CHECK ( curr_len , 0 ) ;
}
/*
* [ 7 ] 9.4 .13
*/
static void
dtap_gmm_ident_res ( tvbuff_t * tvb , proto_tree * tree , guint32 offset , guint len )
{
guint32 curr_offset ;
guint32 consumed ;
guint curr_len ;
curr_offset = offset ;
curr_len = len ;
gsm_a_dtap_pinfo - > p2p_dir = P2P_DIR_RECV ;
ELEM_MAND_LV ( GSM_A_PDU_TYPE_COMMON , DE_MID , " " ) ;
EXTRANEOUS_DATA_CHECK ( curr_len , 0 ) ;
}
/*
* [ 7 ] 9.4 .14
*/
static void
dtap_gmm_rau_req ( tvbuff_t * tvb , proto_tree * tree , guint32 offset , guint len )
{
guint32 curr_offset ;
guint32 consumed ;
guint curr_len ;
curr_offset = offset ;
curr_len = len ;
gsm_a_dtap_pinfo - > p2p_dir = P2P_DIR_RECV ;
/* is included in update type
ELEM_MAND_V ( GSM_A_PDU_TYPE_COMMON , DE_CIPH_KEY_SEQ_NUM ) ;
curr_offset - - ;
curr_len + + ;
*/
ELEM_MAND_V ( GSM_A_PDU_TYPE_GM , DE_UPD_TYPE ) ;
ELEM_MAND_V ( GSM_A_PDU_TYPE_GM , DE_RAI ) ;
ELEM_MAND_LV ( GSM_A_PDU_TYPE_GM , DE_MS_RAD_ACC_CAP , " " ) ;
ELEM_OPT_TV ( 0x19 , GSM_A_PDU_TYPE_GM , DE_P_TMSI_SIG , " - Old P-TMSI Signature " ) ;
ELEM_OPT_TV ( 0x17 , GSM_A_PDU_TYPE_GM , DE_GPRS_TIMER , " - Requested Ready Timer " ) ;
ELEM_OPT_TV ( 0x27 , GSM_A_PDU_TYPE_GM , DE_DRX_PARAM , " " ) ;
ELEM_OPT_TV_SHORT ( 0x90 , GSM_A_PDU_TYPE_GM , DE_TMSI_STAT , " " ) ;
ELEM_OPT_TLV ( 0x18 , GSM_A_PDU_TYPE_COMMON , DE_MID , " - P-TMSI " ) ;
ELEM_OPT_TLV ( 0x31 , GSM_A_PDU_TYPE_GM , DE_MS_NET_CAP , " " ) ;
ELEM_OPT_TLV ( 0x32 , GSM_A_PDU_TYPE_GM , DE_PDP_CONTEXT_STAT , " " ) ;
ELEM_OPT_TLV ( 0x33 , GSM_A_PDU_TYPE_GM , DE_PS_LCS_CAP , " " ) ;
EXTRANEOUS_DATA_CHECK ( curr_len , 0 ) ;
}
/*
* [ 7 ] 9.4 .15
*/
static void
dtap_gmm_rau_acc ( tvbuff_t * tvb , proto_tree * tree , guint32 offset , guint len )
{
guint32 curr_offset ;
guint32 consumed ;
guint curr_len ;
curr_offset = offset ;
curr_len = len ;
gsm_a_dtap_pinfo - > p2p_dir = P2P_DIR_SENT ;
ELEM_MAND_V ( GSM_A_PDU_TYPE_GM , DE_UPD_RES ) ;
curr_offset - - ;
curr_len + + ;
ELEM_MAND_V ( GSM_A_PDU_TYPE_GM , DE_FORCE_TO_STAND ) ;
ELEM_MAND_V ( GSM_A_PDU_TYPE_GM , DE_GPRS_TIMER ) ;
ELEM_MAND_V ( GSM_A_PDU_TYPE_GM , DE_RAI ) ;
ELEM_OPT_TV ( 0x19 , GSM_A_PDU_TYPE_GM , DE_P_TMSI_SIG , " " ) ;
ELEM_OPT_TLV ( 0x18 , GSM_A_PDU_TYPE_COMMON , DE_MID , " - Allocated P-TMSI " ) ;
ELEM_OPT_TLV ( 0x23 , GSM_A_PDU_TYPE_COMMON , DE_MID , " " ) ;
ELEM_OPT_TLV ( 0x26 , GSM_A_PDU_TYPE_GM , DE_REC_N_PDU_NUM_LIST , " " ) ;
ELEM_OPT_TV ( 0x17 , GSM_A_PDU_TYPE_GM , DE_GPRS_TIMER , " - Negotiated Ready Timer " ) ;
ELEM_OPT_TV ( 0x25 , GSM_A_PDU_TYPE_GM , DE_GMM_CAUSE , " " ) ;
ELEM_OPT_TLV ( 0x2A , GSM_A_PDU_TYPE_GM , DE_GPRS_TIMER_2 , " - T3302 " ) ;
ELEM_OPT_T ( 0x8C , GSM_A_PDU_TYPE_GM , DE_CELL_NOT , " " ) ;
ELEM_OPT_TLV ( 0x4A , GSM_A_PDU_TYPE_COMMON , DE_PLMN_LIST , " " ) ;
ELEM_OPT_TLV ( 0x32 , GSM_A_PDU_TYPE_GM , DE_PDP_CONTEXT_STAT , " " ) ;
ELEM_OPT_TV_SHORT ( 0xB0 , GSM_A_PDU_TYPE_GM , DE_NET_FEAT_SUP , " " ) ;
ELEM_OPT_TLV ( 0x34 , GSM_A_PDU_TYPE_DTAP , DE_EMERGENCY_NUM_LIST , " " ) ;
EXTRANEOUS_DATA_CHECK ( curr_len , 0 ) ;
}
/*
* [ 7 ] 9.4 .16
*/
static void
dtap_gmm_rau_com ( tvbuff_t * tvb , proto_tree * tree , guint32 offset , guint len )
{
guint32 curr_offset ;
guint32 consumed ;
guint curr_len ;
curr_offset = offset ;
curr_len = len ;
gsm_a_dtap_pinfo - > p2p_dir = P2P_DIR_RECV ;
/* [7] 10.5.5.11 */
ELEM_OPT_TLV ( 0x26 , GSM_A_PDU_TYPE_GM , DE_REC_N_PDU_NUM_LIST , " " ) ;
/* Inter RAT information container 10.5.5.24 TS 24.008 version 6.8.0 Release 6 */
/*TO DO: Implement */
ELEM_OPT_TLV ( 0x27 , GSM_A_PDU_TYPE_GM , DE_RAT_INFO_CONTAINER , " " ) ;
2008-09-05 05:49:39 +00:00
2008-08-24 17:42:30 +00:00
EXTRANEOUS_DATA_CHECK ( curr_len , 0 ) ;
}
/*
* [ 7 ] 9.4 .17
*/
static void
dtap_gmm_rau_rej ( tvbuff_t * tvb , proto_tree * tree , guint32 offset , guint len )
{
guint32 curr_offset ;
guint32 consumed ;
guint curr_len ;
curr_offset = offset ;
curr_len = len ;
gsm_a_dtap_pinfo - > p2p_dir = P2P_DIR_SENT ;
ELEM_MAND_V ( GSM_A_PDU_TYPE_GM , DE_GMM_CAUSE ) ;
ELEM_MAND_V ( GSM_A_PDU_TYPE_COMMON , DE_SPARE_NIBBLE ) ;
curr_offset - - ;
curr_len + + ;
ELEM_MAND_V ( GSM_A_PDU_TYPE_GM , DE_FORCE_TO_STAND ) ;
ELEM_OPT_TLV ( 0x26 , GSM_A_PDU_TYPE_GM , DE_GPRS_TIMER_2 , " - T3302 " ) ;
EXTRANEOUS_DATA_CHECK ( curr_len , 0 ) ;
}
/*
* [ 7 ] 9.4 .18
*/
static void
dtap_gmm_status ( tvbuff_t * tvb , proto_tree * tree , guint32 offset , guint len )
{
guint32 curr_offset ;
guint32 consumed ;
guint curr_len ;
curr_offset = offset ;
curr_len = len ;
gsm_a_dtap_pinfo - > p2p_dir = P2P_DIR_UNKNOWN ;
ELEM_MAND_V ( GSM_A_PDU_TYPE_GM , DE_GMM_CAUSE ) ;
EXTRANEOUS_DATA_CHECK ( curr_len , 0 ) ;
}
/*
* [ 8 ] 9.4 .19 GMM Information
*/
static void
dtap_gmm_information ( tvbuff_t * tvb , proto_tree * tree , guint32 offset , guint len )
{
guint32 curr_offset ;
guint32 consumed ;
guint curr_len ;
curr_offset = offset ;
curr_len = len ;
gsm_a_dtap_pinfo - > p2p_dir = P2P_DIR_SENT ;
ELEM_OPT_TLV ( 0x43 , GSM_A_PDU_TYPE_DTAP , DE_NETWORK_NAME , " - Full Name " ) ;
ELEM_OPT_TLV ( 0x45 , GSM_A_PDU_TYPE_DTAP , DE_NETWORK_NAME , " - Short Name " ) ;
ELEM_OPT_TV ( 0x46 , GSM_A_PDU_TYPE_DTAP , DE_TIME_ZONE , " " ) ;
ELEM_OPT_TV ( 0x47 , GSM_A_PDU_TYPE_DTAP , DE_TIME_ZONE_TIME , " " ) ;
ELEM_OPT_TLV ( 0x48 , GSM_A_PDU_TYPE_DTAP , DE_LSA_ID , " " ) ;
ELEM_OPT_TLV ( 0x49 , GSM_A_PDU_TYPE_DTAP , DE_DAY_SAVING_TIME , " " ) ;
EXTRANEOUS_DATA_CHECK ( curr_len , 0 ) ;
}
/*
* [ 7 ] 9.4 .20
*/
static void
dtap_gmm_service_req ( tvbuff_t * tvb , proto_tree * tree , guint32 offset , guint len )
{
guint32 curr_offset ;
guint32 consumed ;
guint curr_len ;
curr_offset = offset ;
curr_len = len ;
gsm_a_dtap_pinfo - > p2p_dir = P2P_DIR_RECV ;
/* Is included in SRVC TYPE
ELEM_MAND_V ( GSM_A_PDU_TYPE_COMMON , DE_CIPH_KEY_SEQ_NUM ) ;
curr_offset - - ;
curr_len + + ;
*/
ELEM_MAND_V ( GSM_A_PDU_TYPE_GM , DE_SRVC_TYPE ) ;
/* P-TMSI Mobile station identity 10.5.1.4 M LV 6 */
ELEM_MAND_LV ( GSM_A_PDU_TYPE_COMMON , DE_MID , " " ) ;
ELEM_OPT_TLV ( 0x32 , GSM_A_PDU_TYPE_GM , DE_PDP_CONTEXT_STAT , " " ) ;
/* MBMS context status 10.5.7.6 TLV 2 - 18 */
ELEM_OPT_TLV ( 0x35 , GSM_A_PDU_TYPE_GM , DE_MBMS_CTX_STATUS , " " ) ;
EXTRANEOUS_DATA_CHECK ( curr_len , 0 ) ;
}
/*
* [ 7 ] 9.4 .21
*/
static void
dtap_gmm_service_acc ( tvbuff_t * tvb , proto_tree * tree , guint32 offset , guint len )
{
guint32 curr_offset ;
guint32 consumed ;
guint curr_len ;
curr_offset = offset ;
curr_len = len ;
gsm_a_dtap_pinfo - > p2p_dir = P2P_DIR_SENT ;
ELEM_OPT_TLV ( 0x32 , GSM_A_PDU_TYPE_GM , DE_PDP_CONTEXT_STAT , " " ) ;
/* MBMS context status 10.5.7.6 TLV 2 - 18 */
ELEM_OPT_TLV ( 0x35 , GSM_A_PDU_TYPE_GM , DE_MBMS_CTX_STATUS , " " ) ;
EXTRANEOUS_DATA_CHECK ( curr_len , 0 ) ;
}
/*
* [ 7 ] 9.4 .22
*/
static void
dtap_gmm_service_rej ( tvbuff_t * tvb , proto_tree * tree , guint32 offset , guint len )
{
guint32 curr_offset ;
guint32 consumed ;
guint curr_len ;
curr_offset = offset ;
curr_len = len ;
gsm_a_dtap_pinfo - > p2p_dir = P2P_DIR_SENT ;
ELEM_MAND_V ( GSM_A_PDU_TYPE_GM , DE_GMM_CAUSE ) ;
EXTRANEOUS_DATA_CHECK ( curr_len , 0 ) ;
}
/*
* [ 8 ] 9.5 .1 Activate PDP context request
*/
static void
dtap_sm_act_pdp_req ( tvbuff_t * tvb , proto_tree * tree , guint32 offset , guint len )
{
guint32 curr_offset ;
guint32 consumed ;
guint curr_len ;
curr_offset = offset ;
curr_len = len ;
gsm_a_dtap_pinfo - > p2p_dir = P2P_DIR_UNKNOWN ;
ELEM_MAND_V ( GSM_A_PDU_TYPE_GM , DE_NET_SAPI ) ;
ELEM_MAND_V ( GSM_A_PDU_TYPE_GM , DE_LLC_SAPI ) ;
ELEM_MAND_LV ( GSM_A_PDU_TYPE_GM , DE_QOS , " - Requested QoS " ) ;
ELEM_MAND_LV ( GSM_A_PDU_TYPE_GM , DE_PD_PRO_ADDR , " - Requested PDP address " ) ;
ELEM_OPT_TLV ( 0x28 , GSM_A_PDU_TYPE_GM , DE_ACC_POINT_NAME , " " ) ;
ELEM_OPT_TLV ( 0x27 , GSM_A_PDU_TYPE_GM , DE_PRO_CONF_OPT , " " ) ;
EXTRANEOUS_DATA_CHECK ( curr_len , 0 ) ;
}
/*
* [ 8 ] 9.5 .2 Activate PDP context accept
*/
static void
dtap_sm_act_pdp_acc ( tvbuff_t * tvb , proto_tree * tree , guint32 offset , guint len )
{
guint32 curr_offset ;
guint32 consumed ;
guint curr_len ;
curr_offset = offset ;
curr_len = len ;
gsm_a_dtap_pinfo - > p2p_dir = P2P_DIR_UNKNOWN ;
ELEM_MAND_V ( GSM_A_PDU_TYPE_GM , DE_LLC_SAPI ) ;
ELEM_MAND_LV ( GSM_A_PDU_TYPE_GM , DE_QOS , " - Negotiated QoS " ) ;
#if 0
/* This is done automatically */
ELEM_MAND_V ( GSM_A_PDU_TYPE_GM , DE_SPARE ) ;
curr_offset - - ;
curr_len + + ;
# endif
ELEM_MAND_V ( GSM_A_PDU_TYPE_GM , DE_RAD_PRIO ) ;
ELEM_OPT_TLV ( 0x2B , GSM_A_PDU_TYPE_GM , DE_PD_PRO_ADDR , " " ) ;
ELEM_OPT_TLV ( 0x27 , GSM_A_PDU_TYPE_GM , DE_PRO_CONF_OPT , " " ) ;
ELEM_OPT_TLV ( 0x34 , GSM_A_PDU_TYPE_GM , DE_PACKET_FLOW_ID , " " ) ;
EXTRANEOUS_DATA_CHECK ( curr_len , 0 ) ;
}
/*
* [ 8 ] 9.5 .3 Activate PDP context reject
*/
static void
dtap_sm_act_pdp_rej ( tvbuff_t * tvb , proto_tree * tree , guint32 offset , guint len )
{
guint32 curr_offset ;
guint32 consumed ;
guint curr_len ;
curr_offset = offset ;
curr_len = len ;
gsm_a_dtap_pinfo - > p2p_dir = P2P_DIR_UNKNOWN ;
ELEM_MAND_V ( GSM_A_PDU_TYPE_GM , DE_SM_CAUSE ) ;
ELEM_OPT_TLV ( 0x27 , GSM_A_PDU_TYPE_GM , DE_PRO_CONF_OPT , " " ) ;
EXTRANEOUS_DATA_CHECK ( curr_len , 0 ) ;
}
/*
* [ 8 ] 9.5 .4 Activate Secondary PDP Context Request
*/
static void
dtap_sm_act_sec_pdp_req ( tvbuff_t * tvb , proto_tree * tree , guint32 offset , guint len )
{
guint32 curr_offset ;
guint32 consumed ;
guint curr_len ;
curr_offset = offset ;
curr_len = len ;
gsm_a_dtap_pinfo - > p2p_dir = P2P_DIR_UNKNOWN ;
ELEM_MAND_V ( GSM_A_PDU_TYPE_GM , DE_NET_SAPI ) ;
ELEM_MAND_V ( GSM_A_PDU_TYPE_GM , DE_LLC_SAPI ) ;
ELEM_MAND_LV ( GSM_A_PDU_TYPE_GM , DE_QOS , " - Requested QoS " ) ;
ELEM_MAND_LV ( GSM_A_PDU_TYPE_GM , DE_LINKED_TI , " " ) ;
/* 3GPP TS 24.008 version 6.8.0 Release 6, 36 TFT Traffic Flow Template 10.5.6.12 O TLV 3-257 */
ELEM_OPT_TLV ( 0x36 , GSM_A_PDU_TYPE_GM , DE_TRAFFIC_FLOW_TEMPLATE , " " ) ;
ELEM_OPT_TLV ( 0x27 , GSM_A_PDU_TYPE_GM , DE_PRO_CONF_OPT , " " ) ;
EXTRANEOUS_DATA_CHECK ( curr_len , 0 ) ;
}
/*
* [ 7 ] 9.5 .5
*/
static void
dtap_sm_act_sec_pdp_acc ( tvbuff_t * tvb , proto_tree * tree , guint32 offset , guint len )
{
guint32 curr_offset ;
guint32 consumed ;
guint curr_len ;
curr_offset = offset ;
curr_len = len ;
gsm_a_dtap_pinfo - > p2p_dir = P2P_DIR_UNKNOWN ;
ELEM_MAND_V ( GSM_A_PDU_TYPE_GM , DE_LLC_SAPI ) ;
ELEM_MAND_LV ( GSM_A_PDU_TYPE_GM , DE_QOS , " - Negotiated QoS " ) ;
ELEM_MAND_V ( GSM_A_PDU_TYPE_GM , DE_RAD_PRIO ) ;
#if 0
/* This is done automatically */
ELEM_MAND_V ( GSM_A_PDU_TYPE_GM , DE_SPARE ) ;
curr_offset - - ;
curr_len + + ;
# endif
ELEM_OPT_TLV ( 0x34 , GSM_A_PDU_TYPE_GM , DE_PACKET_FLOW_ID , " " ) ;
ELEM_OPT_TLV ( 0x27 , GSM_A_PDU_TYPE_GM , DE_PRO_CONF_OPT , " " ) ;
EXTRANEOUS_DATA_CHECK ( curr_len , 0 ) ;
}
/*
* [ 8 ] 9.5 .6 Activate Secondary PDP Context Reject
*/
static void
dtap_sm_act_sec_pdp_rej ( tvbuff_t * tvb , proto_tree * tree , guint32 offset , guint len )
{
guint32 curr_offset ;
guint32 consumed ;
guint curr_len ;
curr_offset = offset ;
curr_len = len ;
gsm_a_dtap_pinfo - > p2p_dir = P2P_DIR_UNKNOWN ;
ELEM_MAND_V ( GSM_A_PDU_TYPE_GM , DE_SM_CAUSE ) ;
ELEM_OPT_TLV ( 0x27 , GSM_A_PDU_TYPE_GM , DE_PRO_CONF_OPT , " " ) ;
EXTRANEOUS_DATA_CHECK ( curr_len , 0 ) ;
}
/*
* [ 8 ] 9.5 .7 Request PDP context activation
*/
static void
dtap_sm_req_pdp_act ( tvbuff_t * tvb , proto_tree * tree , guint32 offset , guint len )
{
guint32 curr_offset ;
guint32 consumed ;
guint curr_len ;
curr_offset = offset ;
curr_len = len ;
gsm_a_dtap_pinfo - > p2p_dir = P2P_DIR_UNKNOWN ;
ELEM_MAND_LV ( GSM_A_PDU_TYPE_GM , DE_PD_PRO_ADDR , " - Offered PDP address " ) ;
ELEM_OPT_TLV ( 0x28 , GSM_A_PDU_TYPE_GM , DE_ACC_POINT_NAME , " " ) ;
ELEM_OPT_TLV ( 0x27 , GSM_A_PDU_TYPE_GM , DE_PRO_CONF_OPT , " " ) ;
EXTRANEOUS_DATA_CHECK ( curr_len , 0 ) ;
}
/*
* [ 8 ] 9.5 .8 Request PDP context activation reject
*/
static void
dtap_sm_req_pdp_act_rej ( tvbuff_t * tvb , proto_tree * tree , guint32 offset , guint len )
{
guint32 curr_offset ;
guint32 consumed ;
guint curr_len ;
curr_offset = offset ;
curr_len = len ;
gsm_a_dtap_pinfo - > p2p_dir = P2P_DIR_UNKNOWN ;
ELEM_MAND_V ( GSM_A_PDU_TYPE_GM , DE_SM_CAUSE ) ;
ELEM_OPT_TLV ( 0x27 , GSM_A_PDU_TYPE_GM , DE_PRO_CONF_OPT , " " ) ;
EXTRANEOUS_DATA_CHECK ( curr_len , 0 ) ;
}
/*
* [ 8 ] 9.5 .9 Modify PDP context request ( Network to MS direction )
*/
static void
dtap_sm_mod_pdp_req_net ( tvbuff_t * tvb , proto_tree * tree , guint32 offset , guint len )
{
guint32 curr_offset ;
guint32 consumed ;
guint curr_len ;
curr_offset = offset ;
curr_len = len ;
gsm_a_dtap_pinfo - > p2p_dir = P2P_DIR_UNKNOWN ;
ELEM_MAND_V ( GSM_A_PDU_TYPE_GM , DE_RAD_PRIO ) ;
#if 0
/* This is done automatically */
ELEM_MAND_V ( GSM_A_PDU_TYPE_GM , DE_SPARE ) ;
curr_offset - - ;
curr_len + + ;
# endif
ELEM_MAND_V ( GSM_A_PDU_TYPE_GM , DE_LLC_SAPI ) ;
ELEM_MAND_LV ( GSM_A_PDU_TYPE_GM , DE_QOS , " - New QoS " ) ;
ELEM_OPT_TLV ( 0x2B , GSM_A_PDU_TYPE_GM , DE_PD_PRO_ADDR , " " ) ;
ELEM_OPT_TLV ( 0x34 , GSM_A_PDU_TYPE_GM , DE_PACKET_FLOW_ID , " " ) ;
ELEM_OPT_TLV ( 0x27 , GSM_A_PDU_TYPE_GM , DE_PRO_CONF_OPT , " " ) ;
EXTRANEOUS_DATA_CHECK ( curr_len , 0 ) ;
}
/*
* [ 8 ] 9.5 .10 Modify PDP context request ( MS to network direction )
*/
static void
dtap_sm_mod_pdp_req_ms ( tvbuff_t * tvb , proto_tree * tree , guint32 offset , guint len )
{
guint32 curr_offset ;
guint32 consumed ;
guint curr_len ;
curr_offset = offset ;
curr_len = len ;
gsm_a_dtap_pinfo - > p2p_dir = P2P_DIR_UNKNOWN ;
ELEM_OPT_TV ( 0x32 , GSM_A_PDU_TYPE_GM , DE_LLC_SAPI , " - Requested LLC SAPI " ) ;
ELEM_OPT_TLV ( 0x30 , GSM_A_PDU_TYPE_GM , DE_QOS , " - Requested new QoS " ) ;
ELEM_OPT_TLV ( 0x31 , GSM_A_PDU_TYPE_GM , DE_TRAFFIC_FLOW_TEMPLATE , " - New TFT " ) ;
ELEM_OPT_TLV ( 0x27 , GSM_A_PDU_TYPE_GM , DE_PRO_CONF_OPT , " " ) ;
EXTRANEOUS_DATA_CHECK ( curr_len , 0 ) ;
}
/*
* [ 8 ] 9.5 .11 Modify PDP context accept ( MS to network direction )
*/
static void
dtap_sm_mod_pdp_acc_ms ( tvbuff_t * tvb , proto_tree * tree , guint32 offset , guint len )
{
guint32 curr_offset ;
guint32 consumed ;
guint curr_len ;
curr_offset = offset ;
curr_len = len ;
gsm_a_dtap_pinfo - > p2p_dir = P2P_DIR_UNKNOWN ;
ELEM_OPT_TLV ( 0x27 , GSM_A_PDU_TYPE_GM , DE_PRO_CONF_OPT , " " ) ;
EXTRANEOUS_DATA_CHECK ( curr_len , 0 ) ;
}
/*
* [ 8 ] 9.5 .12 Modify PDP context accept ( Network to MS direction )
*/
static void
dtap_sm_mod_pdp_acc_net ( tvbuff_t * tvb , proto_tree * tree , guint32 offset , guint len )
{
guint32 curr_offset ;
guint32 consumed ;
guint curr_len ;
curr_offset = offset ;
curr_len = len ;
gsm_a_dtap_pinfo - > p2p_dir = P2P_DIR_UNKNOWN ;
ELEM_OPT_TLV ( 0x30 , GSM_A_PDU_TYPE_GM , DE_QOS , " - Negotiated QoS " ) ;
ELEM_OPT_TV ( 0x32 , GSM_A_PDU_TYPE_GM , DE_LLC_SAPI , " - Negotiated LLC SAPI " ) ;
ELEM_OPT_TV_SHORT ( 0x80 , GSM_A_PDU_TYPE_GM , DE_RAD_PRIO , " - New radio priority " ) ;
ELEM_OPT_TLV ( 0x34 , GSM_A_PDU_TYPE_GM , DE_PACKET_FLOW_ID , " " ) ;
ELEM_OPT_TLV ( 0x27 , GSM_A_PDU_TYPE_GM , DE_PRO_CONF_OPT , " " ) ;
EXTRANEOUS_DATA_CHECK ( curr_len , 0 ) ;
}
/*
* [ 8 ] 9.5 .13 Modify PDP Context Reject
*/
static void
dtap_sm_mod_pdp_rej ( tvbuff_t * tvb , proto_tree * tree , guint32 offset , guint len )
{
guint32 curr_offset ;
guint32 consumed ;
guint curr_len ;
curr_offset = offset ;
curr_len = len ;
gsm_a_dtap_pinfo - > p2p_dir = P2P_DIR_UNKNOWN ;
ELEM_MAND_V ( GSM_A_PDU_TYPE_GM , DE_SM_CAUSE ) ;
ELEM_OPT_TLV ( 0x27 , GSM_A_PDU_TYPE_GM , DE_PRO_CONF_OPT , " " ) ;
EXTRANEOUS_DATA_CHECK ( curr_len , 0 ) ;
}
/*
* [ 8 ] 9.5 .14 Deactivate PDP context request
*/
static void
dtap_sm_deact_pdp_req ( tvbuff_t * tvb , proto_tree * tree , guint32 offset , guint len )
{
guint32 curr_offset ;
guint32 consumed ;
guint curr_len ;
curr_offset = offset ;
curr_len = len ;
gsm_a_dtap_pinfo - > p2p_dir = P2P_DIR_UNKNOWN ;
ELEM_MAND_V ( GSM_A_PDU_TYPE_GM , DE_SM_CAUSE ) ;
ELEM_OPT_TV_SHORT ( 0x90 , GSM_A_PDU_TYPE_GM , DE_TEAR_DOWN_IND , " " ) ;
ELEM_OPT_TLV ( 0x27 , GSM_A_PDU_TYPE_GM , DE_PRO_CONF_OPT , " " ) ;
/* MBMS context status 10.5.7.6 TLV 2 - 18 */
ELEM_OPT_TLV ( 0x35 , GSM_A_PDU_TYPE_GM , DE_MBMS_CTX_STATUS , " " ) ;
EXTRANEOUS_DATA_CHECK ( curr_len , 0 ) ;
}
/*
* [ 8 ] 9.5 .15 Deactivate PDP context accept
*/
static void
dtap_sm_deact_pdp_acc ( tvbuff_t * tvb , proto_tree * tree , guint32 offset , guint len )
{
guint32 curr_offset ;
guint32 consumed ;
guint curr_len ;
curr_offset = offset ;
curr_len = len ;
gsm_a_dtap_pinfo - > p2p_dir = P2P_DIR_UNKNOWN ;
ELEM_OPT_TLV ( 0x27 , GSM_A_PDU_TYPE_GM , DE_PRO_CONF_OPT , " " ) ;
/* MBMS context status 10.5.7.6 TLV 2 - 18 */
ELEM_OPT_TLV ( 0x35 , GSM_A_PDU_TYPE_GM , DE_MBMS_CTX_STATUS , " " ) ;
EXTRANEOUS_DATA_CHECK ( curr_len , 0 ) ;
}
/*
* [ 8 ] 9.5 .21 SM Status
*/
static void
dtap_sm_status ( tvbuff_t * tvb , proto_tree * tree , guint32 offset , guint len )
{
guint32 curr_offset ;
guint32 consumed ;
guint curr_len ;
curr_offset = offset ;
curr_len = len ;
gsm_a_dtap_pinfo - > p2p_dir = P2P_DIR_UNKNOWN ;
ELEM_MAND_V ( GSM_A_PDU_TYPE_GM , DE_SM_CAUSE ) ;
EXTRANEOUS_DATA_CHECK ( curr_len , 0 ) ;
}
/*
* [ 8 ] 9.5 .22 Activate MBMS Context Request
*/
/* Requested MBMS NSAPI Enhanced Network service access point identifier 10.5.6.15 M V */
/* Requested LLC SAPI LLC service access point identifier 10.5.6.9 M V 1 */
/* Supported MBMS bearer capabilities MBMS bearer capabilities 10.5.6.14 M LV 2 - 3 */
/* Requested multicast address Packet data protocol address 10.5.6.4 M LV 3 - 19 */
/* Access point name Access point name 10.5.6.1 M LV 2 - 101 */
/* 35 MBMS protocol configuration options MBMS protocol configuration options 10.5.6.15 O TLV 3 - 253 */
/*
* [ 8 ] 9.5 .23 Activate MBMS Context Accept
*/
/*
* [ 8 ] 9.5 .24 Activate MBMS Context Reject
*/
/*
* [ 8 ] 9.5 .25 Request MBMS Context Activation
*/
/*
* [ 8 ] 9.5 .26 Request MBMS Context Activation Reject
*/
# define NUM_GSM_DTAP_MSG_GMM (sizeof(gsm_a_dtap_msg_gmm_strings) / sizeof(value_string))
static gint ett_gsm_dtap_msg_gmm [ NUM_GSM_DTAP_MSG_GMM ] ;
static void ( * dtap_msg_gmm_fcn [ ] ) ( tvbuff_t * tvb , proto_tree * tree , guint32 offset , guint len ) = {
dtap_gmm_attach_req , /* Attach Request */
dtap_gmm_attach_acc , /* Attach Accept */
dtap_gmm_attach_com , /* Attach Complete */
dtap_gmm_attach_rej , /* Attach Reject */
dtap_gmm_detach_req , /* Detach Request */
dtap_gmm_detach_acc , /* Detach Accept */
dtap_gmm_rau_req , /* Routing Area Update Request */
dtap_gmm_rau_acc , /* Routing Area Update Accept */
dtap_gmm_rau_com , /* Routing Area Update Complete */
dtap_gmm_rau_rej , /* Routing Area Update Reject */
dtap_gmm_service_req , /* Service Request */
dtap_gmm_service_acc , /* Service Accept */
dtap_gmm_service_rej , /* Service Reject */
dtap_gmm_ptmsi_realloc_cmd , /* P-TMSI Reallocation Command */
dtap_gmm_ptmsi_realloc_com , /* P-TMSI Reallocation Complete */
dtap_gmm_auth_ciph_req , /* Authentication and Ciphering Req */
dtap_gmm_auth_ciph_resp , /* Authentication and Ciphering Resp */
dtap_gmm_auth_ciph_rej , /* Authentication and Ciphering Rej */
dtap_gmm_auth_ciph_fail , /* Authentication and Ciphering Failure */
dtap_gmm_ident_req , /* Identity Request */
dtap_gmm_ident_res , /* Identity Response */
dtap_gmm_status , /* GMM Status */
dtap_gmm_information , /* GMM Information */
NULL , /* NONE */
} ;
# define NUM_GSM_DTAP_MSG_SM (sizeof(gsm_a_dtap_msg_sm_strings) / sizeof(value_string))
static gint ett_gsm_dtap_msg_sm [ NUM_GSM_DTAP_MSG_SM ] ;
static void ( * dtap_msg_sm_fcn [ ] ) ( tvbuff_t * tvb , proto_tree * tree , guint32 offset , guint len ) = {
dtap_sm_act_pdp_req , /* Activate PDP Context Request */
dtap_sm_act_pdp_acc , /* Activate PDP Context Accept */
dtap_sm_act_pdp_rej , /* Activate PDP Context Reject */
dtap_sm_req_pdp_act , /* Request PDP Context Activation */
dtap_sm_req_pdp_act_rej , /* Request PDP Context Activation rej. */
dtap_sm_deact_pdp_req , /* Deactivate PDP Context Request */
dtap_sm_deact_pdp_acc , /* Deactivate PDP Context Accept */
dtap_sm_mod_pdp_req_net , /* Modify PDP Context Request(Network to MS direction) */
dtap_sm_mod_pdp_acc_ms , /* Modify PDP Context Accept (MS to network direction) */
dtap_sm_mod_pdp_req_ms , /* Modify PDP Context Request(MS to network direction) */
dtap_sm_mod_pdp_acc_net , /* Modify PDP Context Accept (Network to MS direction) */
dtap_sm_mod_pdp_rej , /* Modify PDP Context Reject */
dtap_sm_act_sec_pdp_req , /* Activate Secondary PDP Context Request */
dtap_sm_act_sec_pdp_acc , /* Activate Secondary PDP Context Accept */
dtap_sm_act_sec_pdp_rej , /* Activate Secondary PDP Context Reject */
NULL , /* Reserved: was allocated in earlier phases of the protocol */
NULL , /* Reserved: was allocated in earlier phases of the protocol */
NULL , /* Reserved: was allocated in earlier phases of the protocol */
NULL , /* Reserved: was allocated in earlier phases of the protocol */
NULL , /* Reserved: was allocated in earlier phases of the protocol */
dtap_sm_status , /* SM Status */
/* Activate MBMS Context Request */
/* Activate MBMS Context Accept */
/* Activate MBMS Context Reject */
/* Request MBMS Context Activation */
/* Request MBMS Context Activation Reject */
NULL , /* NONE */
} ;
void get_gmm_msg_params ( guint8 oct , const gchar * * msg_str , int * ett_tree , int * hf_idx , msg_fcn * msg_fcn )
{
gint idx ;
* msg_str = match_strval_idx ( ( guint32 ) ( oct & DTAP_GMM_IEI_MASK ) , gsm_a_dtap_msg_gmm_strings , & idx ) ;
* ett_tree = ett_gsm_dtap_msg_gmm [ idx ] ;
* hf_idx = hf_gsm_a_dtap_msg_gmm_type ;
* msg_fcn = dtap_msg_gmm_fcn [ idx ] ;
return ;
}
void get_sm_msg_params ( guint8 oct , const gchar * * msg_str , int * ett_tree , int * hf_idx , msg_fcn * msg_fcn )
{
gint idx ;
* msg_str = match_strval_idx ( ( guint32 ) ( oct & DTAP_SM_IEI_MASK ) , gsm_a_dtap_msg_sm_strings , & idx ) ;
* ett_tree = ett_gsm_dtap_msg_sm [ idx ] ;
* hf_idx = hf_gsm_a_dtap_msg_sm_type ;
* msg_fcn = dtap_msg_sm_fcn [ idx ] ;
return ;
}
/* Register the protocol with Wireshark */
void
proto_register_gsm_a_gm ( void )
{
guint i ;
guint last_offset ;
/* Setup list of header fields */
static hf_register_info hf [ ] =
{
{ & hf_gsm_a_dtap_msg_gmm_type ,
2008-09-05 05:49:39 +00:00
{ " DTAP GPRS Mobility Management Message Type " , " gsm_a.dtap_msg_gmm_type " ,
2009-05-07 21:22:36 +00:00
FT_UINT8 , BASE_HEX , VALS ( gsm_a_dtap_msg_gmm_strings ) , 0x0 ,
NULL , HFILL }
2008-08-24 17:42:30 +00:00
} ,
{ & hf_gsm_a_dtap_msg_sm_type ,
2009-05-07 21:22:36 +00:00
{ " DTAP GPRS Session Management Message Type " , " gsm_a.dtap_msg_sm_type " ,
FT_UINT8 , BASE_HEX , VALS ( gsm_a_dtap_msg_sm_strings ) , 0x0 ,
NULL , HFILL }
2008-08-24 17:42:30 +00:00
} ,
{ & hf_gsm_a_gm_elem_id ,
2008-09-05 05:49:39 +00:00
{ " Element ID " , " gsm_a_gm.elem_id " ,
FT_UINT8 , BASE_DEC , NULL , 0 ,
2009-05-07 21:22:36 +00:00
NULL , HFILL }
2008-08-24 17:42:30 +00:00
} ,
{ & hf_gsm_a_qos_delay_cls ,
2009-05-07 21:22:36 +00:00
{ " Quality of Service Delay class " , " gsm_a.qos.delay_cls " ,
FT_UINT8 , BASE_DEC , VALS ( gsm_a_qos_delay_cls_vals ) , 0x38 ,
NULL , HFILL }
2008-09-05 05:49:39 +00:00
} ,
2008-08-24 17:42:30 +00:00
{ & hf_gsm_a_qos_qos_reliability_cls ,
{ " Reliability class " , " gsm_a.qos.delay_cls " ,
2009-05-07 21:22:36 +00:00
FT_UINT8 , BASE_DEC , VALS ( gsm_a_qos_delay_cls_vals ) , 0x07 ,
NULL , HFILL }
2008-09-05 05:49:39 +00:00
} ,
2008-08-24 17:42:30 +00:00
{ & hf_gsm_a_qos_traffic_cls ,
2009-05-07 21:22:36 +00:00
{ " Traffic class " , " gsm_a.qos.traffic_cls " ,
FT_UINT8 , BASE_DEC , VALS ( gsm_a_qos_traffic_cls_vals ) , 0xe0 ,
NULL , HFILL }
2008-09-05 05:49:39 +00:00
} ,
2008-08-24 17:42:30 +00:00
{ & hf_gsm_a_qos_del_order ,
2009-05-07 21:22:36 +00:00
{ " Delivery order " , " gsm_a.qos.del_order " ,
FT_UINT8 , BASE_DEC , VALS ( gsm_a_qos_traffic_cls_vals ) , 0x18 ,
NULL , HFILL }
2008-09-05 05:49:39 +00:00
} ,
2008-08-24 17:42:30 +00:00
{ & hf_gsm_a_qos_del_of_err_sdu ,
2009-05-07 21:22:36 +00:00
{ " Delivery of erroneous SDUs " , " gsm_a.qos.del_of_err_sdu " ,
FT_UINT8 , BASE_DEC , VALS ( gsm_a_qos_del_of_err_sdu_vals ) , 0x03 ,
NULL , HFILL }
2008-09-05 05:49:39 +00:00
} ,
2008-08-24 17:42:30 +00:00
{ & hf_gsm_a_qos_ber ,
2009-05-07 21:22:36 +00:00
{ " Residual Bit Error Rate (BER) " , " gsm_a.qos.ber " ,
FT_UINT8 , BASE_DEC , VALS ( gsm_a_qos_ber_vals ) , 0xf0 ,
NULL , HFILL }
2008-09-05 05:49:39 +00:00
} ,
2008-08-24 17:42:30 +00:00
{ & hf_gsm_a_qos_sdu_err_rat ,
2009-05-07 21:22:36 +00:00
{ " SDU error ratio " , " gsm_a.qos.sdu_err_rat " ,
FT_UINT8 , BASE_DEC , VALS ( gsm_a_qos_sdu_err_rat_vals ) , 0x0f ,
NULL , HFILL }
2008-09-05 05:49:39 +00:00
} ,
2008-08-24 17:42:30 +00:00
{ & hf_gsm_a_qos_traff_hdl_pri ,
2009-05-07 21:22:36 +00:00
{ " Traffic handling priority " , " gsm_a.qos.traff_hdl_pri " ,
FT_UINT8 , BASE_DEC , VALS ( gsm_a_qos_traff_hdl_pri_vals ) , 0x03 ,
NULL , HFILL }
2008-09-05 05:49:39 +00:00
} ,
2008-08-24 17:42:30 +00:00
{ & hf_gsm_a_gmm_split_on_ccch ,
{ " SPLIT on CCCH " , " gsm_a.gmm.split_on_ccch " ,
2009-05-07 21:22:36 +00:00
FT_BOOLEAN , 8 , TFS ( & gsm_a_gmm_split_on_ccch_value ) , 0x08 ,
NULL , HFILL }
2008-08-24 17:42:30 +00:00
} ,
{ & hf_gsm_a_gmm_non_drx_timer ,
{ " Non-DRX timer " , " gsm_a.gmm.non_drx_timer " ,
2009-05-07 21:22:36 +00:00
FT_UINT8 , BASE_DEC , VALS ( gsm_a_gmm_non_drx_timer_strings ) , 0x07 ,
NULL , HFILL }
2008-08-24 17:42:30 +00:00
} ,
{ & hf_gsm_a_gmm_cn_spec_drs_cycle_len_coef ,
{ " CN Specific DRX cycle length coefficient " , " gsm_a.gmm.cn_spec_drs_cycle_len_coef " ,
2009-05-07 21:22:36 +00:00
FT_UINT8 , BASE_DEC , VALS ( gsm_a_gmm_cn_spec_drs_cycle_len_coef_strings ) , 0xf0 ,
NULL , HFILL }
2008-08-24 17:42:30 +00:00
} ,
{ & hf_gsm_a_tft_op_code ,
{ " TFT operation code " , " gsm_a.tft.op_code " ,
2009-05-07 21:22:36 +00:00
FT_UINT8 , BASE_DEC , VALS ( gsm_a_tft_op_code_vals ) , 0xe0 ,
NULL , HFILL }
2008-08-24 17:42:30 +00:00
} ,
{ & hf_gsm_a_tft_e_bit ,
{ " E bit " , " gsm_a.tft.e_bit " ,
2009-05-07 21:22:36 +00:00
FT_BOOLEAN , 8 , TFS ( & gsm_a_tft_e_bit ) , 0x10 ,
NULL , HFILL }
2008-08-24 17:42:30 +00:00
} ,
{ & hf_gsm_a_tft_pkt_flt ,
{ " Number of packet filters " , " gsm_a.tft.pkt_flt " ,
2009-05-07 21:22:36 +00:00
FT_UINT8 , BASE_DEC , NULL , 0x0f ,
NULL , HFILL }
2008-08-24 17:42:30 +00:00
} ,
2008-09-05 05:49:39 +00:00
{ & hf_gsm_a_tft_ip4_address ,
2009-05-07 21:22:36 +00:00
{ " IPv4 adress " , " gsm_a.tft.ip4_address " ,
FT_IPv4 , BASE_NONE , NULL , 0x0 ,
NULL , HFILL }
2008-09-05 05:49:39 +00:00
} ,
2008-08-24 17:42:30 +00:00
{ & hf_gsm_a_tft_ip4_mask ,
2009-05-07 21:22:36 +00:00
{ " IPv4 address mask " , " gsm_a.tft.ip4_mask " ,
FT_IPv4 , BASE_NONE , NULL , 0x0 ,
NULL , HFILL }
} ,
2008-08-24 17:42:30 +00:00
{ & hf_gsm_a_tft_ip6_address ,
2009-05-07 21:22:36 +00:00
{ " IPv6 adress " , " gsm_a.tft.ip6_address " ,
FT_IPv6 , BASE_NONE , NULL , 0x0 ,
NULL , HFILL }
2008-09-05 05:49:39 +00:00
} ,
2008-08-24 17:42:30 +00:00
{ & hf_gsm_a_tft_ip6_mask ,
2009-05-07 21:22:36 +00:00
{ " IPv6 adress mask " , " gsm_a.tft.ip6_mask " ,
FT_IPv6 , BASE_NONE , NULL , 0x0 ,
NULL , HFILL }
2008-09-05 05:49:39 +00:00
} ,
2008-08-24 17:42:30 +00:00
{ & hf_gsm_a_tft_protocol_header ,
2009-05-07 21:22:36 +00:00
{ " Protocol/header " , " gsm_a.tft.protocol_header " ,
FT_UINT8 , BASE_HEX , NULL , 0x0 ,
NULL , HFILL }
2008-09-05 05:49:39 +00:00
} ,
2008-08-24 17:42:30 +00:00
{ & hf_gsm_a_tft_port ,
2009-05-07 21:22:36 +00:00
{ " Port " , " gsm_a.tft.port " ,
FT_UINT16 , BASE_DEC , NULL , 0x0 ,
NULL , HFILL }
2008-09-05 05:49:39 +00:00
} ,
2008-08-24 17:42:30 +00:00
{ & hf_gsm_a_tft_port_low ,
2009-05-07 21:22:36 +00:00
{ " Low limit port " , " gsm_a.tft.port_low " ,
FT_UINT16 , BASE_DEC , NULL , 0x0 ,
NULL , HFILL }
2008-09-05 05:49:39 +00:00
} ,
2008-08-24 17:42:30 +00:00
{ & hf_gsm_a_tft_port_high ,
2009-05-07 21:22:36 +00:00
{ " High limit port " , " gsm_a.tft.port_high " ,
FT_UINT16 , BASE_DEC , NULL , 0x0 ,
NULL , HFILL }
2008-09-05 05:49:39 +00:00
} ,
2008-08-24 17:42:30 +00:00
{ & hf_gsm_a_tft_security ,
2009-05-07 21:22:36 +00:00
{ " IPSec security parameter index " , " gsm_a.tft.security " ,
FT_UINT32 , BASE_HEX , NULL , 0x0 ,
NULL , HFILL }
2008-09-05 05:49:39 +00:00
} ,
2008-08-24 17:42:30 +00:00
{ & hf_gsm_a_tft_traffic_mask ,
2009-05-07 21:22:36 +00:00
{ " Mask field " , " gsm_a.tft.traffic_mask " ,
FT_UINT8 , BASE_HEX , NULL , 0x0 ,
NULL , HFILL }
2008-09-05 05:49:39 +00:00
} ,
2008-08-24 17:42:30 +00:00
{ & hf_gsm_a_ptmsi_sig ,
2009-05-07 21:22:36 +00:00
{ " P-TMSI Signature " , " gsm_a.ptmsi_sig " ,
FT_UINT24 , BASE_HEX , NULL , 0x0 ,
NULL , HFILL }
2008-09-05 05:49:39 +00:00
} ,
2008-08-24 17:42:30 +00:00
{ & hf_gsm_a_ptmsi_sig2 ,
2009-05-07 21:22:36 +00:00
{ " P-TMSI Signature 2 " , " gsm_a.ptmsi_sig2 " ,
FT_UINT24 , BASE_HEX , NULL , 0x0 ,
NULL , HFILL }
2008-09-05 05:49:39 +00:00
} ,
2009-05-14 18:26:18 +00:00
{ & hf_gsm_a_gm_acc_tech_type ,
{ " Access Technology Type " , " gsm_a.gm.acc_tech_type " ,
FT_UINT8 , BASE_DEC , VALS ( gsm_a_gm_acc_tech_type_vals ) , 0x0 ,
NULL , HFILL }
} ,
{ & hf_gsm_a_gm_acc_cap_struct_len ,
{ " Length in bits " , " gsm_a.gm.acc_cap_struct_len " ,
FT_UINT8 , BASE_HEX_DEC , NULL , 0x0 ,
NULL , HFILL }
} ,
{ & hf_gsm_a_gm_sms_value ,
{ " SMS_VALUE (Switch-Measure-Switch) " , " gsm_a.gm.sms " ,
FT_UINT8 , BASE_DEC , VALS ( gsm_a_gm_sm_vals ) , 0x0 ,
NULL , HFILL }
} ,
{ & hf_gsm_a_gm_sm_value ,
{ " (SM_VALUE) Switch-Measure " , " gsm_a.gm.sm " ,
FT_UINT8 , BASE_DEC , VALS ( gsm_a_gm_sm_vals ) , 0x0 ,
NULL , HFILL }
} ,
2008-08-24 17:42:30 +00:00
} ;
/* Setup protocol subtree array */
# define NUM_INDIVIDUAL_ELEMS 15
static gint * ett [ NUM_INDIVIDUAL_ELEMS +
NUM_GSM_DTAP_MSG_GMM + NUM_GSM_DTAP_MSG_SM +
NUM_GSM_GM_ELEM ] ;
2009-05-07 21:22:36 +00:00
ett [ 0 ] = & ett_tc_component ;
ett [ 1 ] = & ett_tc_invoke_id ;
ett [ 2 ] = & ett_tc_linked_id ;
ett [ 3 ] = & ett_tc_opr_code ;
ett [ 4 ] = & ett_tc_err_code ;
ett [ 5 ] = & ett_tc_prob_code ;
ett [ 6 ] = & ett_tc_sequence ;
ett [ 7 ] = & ett_gmm_drx ;
ett [ 8 ] = & ett_gmm_detach_type ;
ett [ 9 ] = & ett_gmm_attach_type ;
2008-08-24 17:42:30 +00:00
ett [ 10 ] = & ett_gmm_context_stat ;
ett [ 11 ] = & ett_gmm_update_type ;
ett [ 12 ] = & ett_gmm_radio_cap ;
ett [ 13 ] = & ett_gmm_rai ;
ett [ 14 ] = & ett_sm_tft ;
last_offset = NUM_INDIVIDUAL_ELEMS ;
for ( i = 0 ; i < NUM_GSM_DTAP_MSG_GMM ; i + + , last_offset + + )
{
2008-09-05 05:49:39 +00:00
ett_gsm_dtap_msg_gmm [ i ] = - 1 ;
ett [ last_offset ] = & ett_gsm_dtap_msg_gmm [ i ] ;
2008-08-24 17:42:30 +00:00
}
for ( i = 0 ; i < NUM_GSM_DTAP_MSG_SM ; i + + , last_offset + + )
{
2008-09-05 05:49:39 +00:00
ett_gsm_dtap_msg_sm [ i ] = - 1 ;
ett [ last_offset ] = & ett_gsm_dtap_msg_sm [ i ] ;
2008-08-24 17:42:30 +00:00
}
for ( i = 0 ; i < NUM_GSM_GM_ELEM ; i + + , last_offset + + )
{
2008-09-05 05:49:39 +00:00
ett_gsm_gm_elem [ i ] = - 1 ;
ett [ last_offset ] = & ett_gsm_gm_elem [ i ] ;
2008-08-24 17:42:30 +00:00
}
proto_a_gm =
2008-09-05 05:49:39 +00:00
proto_register_protocol ( " GSM A-I/F GPRS Mobility and Session Management " , " GSM Management " , " gsm_a_gm " ) ;
2008-08-24 17:42:30 +00:00
proto_register_field_array ( proto_a_gm , hf , array_length ( hf ) ) ;
proto_register_subtree_array ( ett , array_length ( ett ) ) ;
/* subdissector code */
gprs_sm_pco_subdissector_table = register_dissector_table ( " sm_pco.protocol " ,
" GPRS SM PCO PPP protocol " , FT_UINT16 , BASE_HEX ) ;
}
void
proto_reg_handoff_gsm_a_gm ( void )
{
data_handle = find_dissector ( " data " ) ;
2008-11-17 19:41:44 +00:00
rrc_irat_ho_info_handle = find_dissector ( " rrc.irat.irat_ho_info " ) ;
2008-08-24 17:42:30 +00:00
}