diff options
Diffstat (limited to 'epan/dissectors/asn1/c1222/packet-c1222-template.c')
-rw-r--r-- | epan/dissectors/asn1/c1222/packet-c1222-template.c | 185 |
1 files changed, 106 insertions, 79 deletions
diff --git a/epan/dissectors/asn1/c1222/packet-c1222-template.c b/epan/dissectors/asn1/c1222/packet-c1222-template.c index f9d25c9cb6..60252356a6 100644 --- a/epan/dissectors/asn1/c1222/packet-c1222-template.c +++ b/epan/dissectors/asn1/c1222/packet-c1222-template.c @@ -37,8 +37,8 @@ #define C1222_EPSEM_FLAG_RESPONSE_CONTROL 0x03 #define C1222_PROCEDURE_RESPONSE 0xf000 -#define C1222_PROCEDURE_MFG 0x800 -#define C1222_PROCEDURE_NUMBER 0x7ff +#define C1222_PROCEDURE_MFG 0x0800 +#define C1222_PROCEDURE_NUMBER 0x07ff /* if the packet is encrypted, it can be * good, bad, or simply not checked @@ -70,18 +70,18 @@ static dissector_handle_t c1222_handle=NULL; static dissector_handle_t c1222_udp_handle=NULL; /* Initialize the protocol and registered fields */ -static int proto_c1222 = -1; +static int proto_c1222; #include "packet-c1222-hf.c" /* These are the EPSEM pieces */ /* first, the flag components */ -static int hf_c1222_epsem_flags = -1; -static int hf_c1222_epsem_flags_reserved = -1; -static int hf_c1222_epsem_flags_recovery = -1; -static int hf_c1222_epsem_flags_proxy = -1; -static int hf_c1222_epsem_flags_ed_class = -1; -static int hf_c1222_epsem_flags_security_modes = -1; -static int hf_c1222_epsem_flags_response_control = -1; +static int hf_c1222_epsem_flags; +static int hf_c1222_epsem_flags_reserved; +static int hf_c1222_epsem_flags_recovery; +static int hf_c1222_epsem_flags_proxy; +static int hf_c1222_epsem_flags_ed_class; +static int hf_c1222_epsem_flags_security_modes; +static int hf_c1222_epsem_flags_response_control; /* and the structure of the flag components */ static int * const c1222_flags[] = { &hf_c1222_epsem_flags_reserved, @@ -93,53 +93,53 @@ static int * const c1222_flags[] = { NULL }; /* next the optional ed_class */ -static int hf_c1222_epsem_ed_class = -1; +static int hf_c1222_epsem_ed_class; /* now the aggregate epsem */ -static int hf_c1222_epsem_total = -1; +static int hf_c1222_epsem_total; /* generic command */ -static int hf_c1222_cmd = -1; -static int hf_c1222_err = -1; -static int hf_c1222_data = -1; +static int hf_c1222_cmd; +static int hf_c1222_err; +static int hf_c1222_data; /* individual epsem fields */ -static int hf_c1222_logon_id = -1; -static int hf_c1222_logon_user = -1; -static int hf_c1222_security_password = -1; -static int hf_c1222_auth_len = -1; -static int hf_c1222_auth_data = -1; -static int hf_c1222_read_table = -1; -static int hf_c1222_read_offset = -1; -static int hf_c1222_read_count = -1; -static int hf_c1222_write_table = -1; -static int hf_c1222_write_offset = -1; -static int hf_c1222_write_size = -1; -static int hf_c1222_write_data = -1; -static int hf_c1222_procedure_response = -1; -static int hf_c1222_procedure_mfg = -1; -static int hf_c1222_procedure_num = -1; -static int hf_c1222_procedure_sequence = -1; -static int hf_c1222_write_chksum = -1; -static int hf_c1222_write_chksum_status = -1; -static int hf_c1222_wait_secs = -1; -static int hf_c1222_neg_pkt_size = -1; -static int hf_c1222_neg_nbr_pkts = -1; -static int hf_c1222_timing_setup_traffic = -1; -static int hf_c1222_timing_setup_inter_char = -1; -static int hf_c1222_timing_setup_resp_to = -1; -static int hf_c1222_timing_setup_nbr_retries = -1; +static int hf_c1222_logon_id; +static int hf_c1222_logon_user; +static int hf_c1222_security_password; +static int hf_c1222_auth_len; +static int hf_c1222_auth_data; +static int hf_c1222_read_table; +static int hf_c1222_read_offset; +static int hf_c1222_read_count; +static int hf_c1222_write_table; +static int hf_c1222_write_offset; +static int hf_c1222_write_size; +static int hf_c1222_write_data; +static int hf_c1222_procedure_response; +static int hf_c1222_procedure_mfg; +static int hf_c1222_procedure_num; +static int hf_c1222_procedure_sequence; +static int hf_c1222_write_chksum; +static int hf_c1222_write_chksum_status; +static int hf_c1222_wait_secs; +static int hf_c1222_neg_pkt_size; +static int hf_c1222_neg_nbr_pkts; +static int hf_c1222_timing_setup_traffic; +static int hf_c1222_timing_setup_inter_char; +static int hf_c1222_timing_setup_resp_to; +static int hf_c1222_timing_setup_nbr_retries; /* the MAC */ -static int hf_c1222_epsem_mac = -1; +static int hf_c1222_epsem_mac; /* crypto result flags */ -static int hf_c1222_epsem_crypto_good = -1; -static int hf_c1222_epsem_crypto_bad = -1; +static int hf_c1222_epsem_crypto_good; +static int hf_c1222_epsem_crypto_bad; /* Initialize the subtree pointers */ -static int ett_c1222 = -1; -static int ett_c1222_epsem = -1; -static int ett_c1222_flags = -1; -static int ett_c1222_crypto = -1; -static int ett_c1222_cmd = -1; +static int ett_c1222; +static int ett_c1222_epsem; +static int ett_c1222_flags; +static int ett_c1222_crypto; +static int ett_c1222_cmd; /* these pointers are for the header elements that may be needed to verify the crypto */ static guint8 *aSO_context = NULL; @@ -167,17 +167,30 @@ static guint32 calling_AP_title_len = 0; static guint32 key_id_element_len = 0; static guint32 iv_element_len = 0; +/* these are the related allocation sizes (which might be different from the lengths) */ +static guint32 aSO_context_allocated = 0; +static guint32 called_AP_title_allocated = 0; +static guint32 called_AP_invocation_id_allocated = 0; +static guint32 calling_AE_qualifier_allocated = 0; +static guint32 calling_AP_invocation_id_allocated = 0; +static guint32 mechanism_name_allocated = 0; +static guint32 calling_authentication_value_allocated = 0; +static guint32 user_information_allocated = 0; +static guint32 calling_AP_title_allocated = 0; +static guint32 key_id_element_allocated = 0; +static guint32 iv_element_allocated = 0; + #include "packet-c1222-ett.c" -static expert_field ei_c1222_command_truncated = EI_INIT; -static expert_field ei_c1222_bad_checksum = EI_INIT; -static expert_field ei_c1222_epsem_missing = EI_INIT; -static expert_field ei_c1222_epsem_failed_authentication = EI_INIT; -static expert_field ei_c1222_epsem_not_decryped = EI_INIT; -static expert_field ei_c1222_ed_class_missing = EI_INIT; -static expert_field ei_c1222_epsem_ber_length_error = EI_INIT; -static expert_field ei_c1222_epsem_field_length_error = EI_INIT; -static expert_field ei_c1222_mac_missing = EI_INIT; +static expert_field ei_c1222_command_truncated; +static expert_field ei_c1222_bad_checksum; +static expert_field ei_c1222_epsem_missing; +static expert_field ei_c1222_epsem_failed_authentication; +static expert_field ei_c1222_epsem_not_decrypted; +static expert_field ei_c1222_ed_class_missing; +static expert_field ei_c1222_epsem_ber_length_error; +static expert_field ei_c1222_epsem_field_length_error; +static expert_field ei_c1222_mac_missing; /* Preferences */ static gboolean c1222_desegment = TRUE; @@ -300,11 +313,13 @@ static uat_t *c1222_uat; #define FILL_TABLE(fieldname) \ length = offset - start_offset; \ fieldname = (guint8 *)tvb_memdup(actx->pinfo->pool, tvb, start_offset, length); \ - fieldname##_len = length; + fieldname##_len = length; \ + fieldname##_allocated = length; #define FILL_TABLE_TRUNCATE(fieldname, len) \ length = 1 + 2*(offset - start_offset); \ fieldname = (guint8 *)tvb_memdup(actx->pinfo->pool, tvb, start_offset, length); \ - fieldname##_len = len; + fieldname##_len = len; \ + fieldname##_allocated = length; #define FILL_TABLE_APTITLE(fieldname) \ length = offset - start_offset; \ switch (tvb_get_guint8(tvb, start_offset)) { \ @@ -312,6 +327,7 @@ static uat_t *c1222_uat; tvb_ensure_bytes_exist(tvb, start_offset, length); \ fieldname##_len = length + c1222_baseoid_len; \ fieldname = (guint8 *)wmem_alloc(actx->pinfo->pool, fieldname##_len); \ + fieldname##_allocated = fieldname##_len; \ fieldname[0] = 0x06; /* create absolute OID tag */ \ fieldname[1] = (fieldname##_len - 2) & 0xff; \ memcpy(&(fieldname[2]), c1222_baseoid, c1222_baseoid_len); \ @@ -321,6 +337,7 @@ static uat_t *c1222_uat; default: \ fieldname = (guint8 *)tvb_memdup(actx->pinfo->pool, tvb, start_offset, length); \ fieldname##_len = length; \ + fieldname##_allocated = length; \ break; \ } @@ -641,21 +658,23 @@ typedef struct tagTOP_ELEMENT_CONTROL guint8 **element; /* pointer to element length */ guint32 *length; + /* pointer to element allocated size */ + guint32 *allocated; } TOP_ELEMENT_CONTROL; static const TOP_ELEMENT_CONTROL canonifyTable[] = { - { FALSE, FALSE, 0xA1, TRUE, &aSO_context, &aSO_context_len }, - { TRUE , FALSE, 0xA2, TRUE, &called_AP_title, &called_AP_title_len }, - { FALSE, FALSE, 0xA4, TRUE, &called_AP_invocation_id, &called_AP_invocation_id_len }, - { FALSE, FALSE, 0xA7, TRUE, &calling_AE_qualifier, &calling_AE_qualifier_len }, - { TRUE, FALSE, 0xA8, TRUE, &calling_AP_invocation_id, &calling_AP_invocation_id_len }, - { FALSE, FALSE, 0x8B, TRUE, &mechanism_name, &mechanism_name_len }, - { FALSE, FALSE, 0xAC, TRUE, &calling_authentication_value, &calling_authentication_value_len }, - { TRUE , TRUE , 0xBE, TRUE, &user_information, &user_information_len }, - { FALSE, FALSE, 0xA6, TRUE, &calling_AP_title, &calling_AP_title_len }, - { FALSE, FALSE, 0xAC, FALSE, &key_id_element, &key_id_element_len }, - { FALSE, FALSE, 0xAC, FALSE, &iv_element, &iv_element_len }, - { FALSE, FALSE, 0x0, TRUE, NULL, NULL } + { FALSE, FALSE, 0xA1, TRUE, &aSO_context, &aSO_context_len, &aSO_context_allocated }, + { TRUE , FALSE, 0xA2, TRUE, &called_AP_title, &called_AP_title_len, &called_AP_title_allocated }, + { FALSE, FALSE, 0xA4, TRUE, &called_AP_invocation_id, &called_AP_invocation_id_len, &called_AP_invocation_id_allocated }, + { FALSE, FALSE, 0xA7, TRUE, &calling_AE_qualifier, &calling_AE_qualifier_len, &calling_AE_qualifier_allocated }, + { TRUE, FALSE, 0xA8, TRUE, &calling_AP_invocation_id, &calling_AP_invocation_id_len, &calling_AP_invocation_id_allocated }, + { FALSE, FALSE, 0x8B, TRUE, &mechanism_name, &mechanism_name_len, &mechanism_name_allocated }, + { FALSE, FALSE, 0xAC, TRUE, &calling_authentication_value, &calling_authentication_value_len, &calling_authentication_value_allocated }, + { TRUE , TRUE , 0xBE, TRUE, &user_information, &user_information_len, &user_information_allocated }, + { FALSE, FALSE, 0xA6, TRUE, &calling_AP_title, &calling_AP_title_len, &calling_AP_title_allocated }, + { FALSE, FALSE, 0xAC, FALSE, &key_id_element, &key_id_element_len, &key_id_element_allocated }, + { FALSE, FALSE, 0xAC, FALSE, &iv_element, &iv_element_len, &iv_element_allocated }, + { FALSE, FALSE, 0x0, TRUE, NULL, NULL, NULL } }; static void @@ -729,7 +748,7 @@ c1222_uat_data_copy_cb(void *dest, const void *source, size_t len _U_) * \param err is updated to point to an error string if needed * \return FALSE if error; TRUE otherwise */ -static gboolean +static bool c1222_uat_data_update_cb(void* n, char** err) { c1222_uat_data_t* new_rec = (c1222_uat_data_t *)n; @@ -765,11 +784,12 @@ static gboolean canonify_unencrypted_header(guchar *buff, guint32 *offset, guint32 buffsize) { const TOP_ELEMENT_CONTROL *t = canonifyTable; - guint32 len; + guint32 len, allocated; for (t = canonifyTable; t->element != NULL; t++) { len = *(t->length); + allocated = *(t->allocated); if (t->required && *(t->element) == NULL) return FALSE; if (*(t->element) != NULL) { @@ -786,6 +806,11 @@ canonify_unencrypted_header(guchar *buff, guint32 *offset, guint32 buffsize) if (buffsize < *offset + len) { return FALSE; } + /* bail out if our we're trying to read past the end of our element */ + /* the network is always hostile */ + if (allocated < len) { + return FALSE; + } memcpy(&buff[*offset], *(t->element), len); (*offset) += len; if (t->addtag) { @@ -929,7 +954,7 @@ dissect_epsem(tvbuff_t *tvb, int offset, guint32 len, packet_info *pinfo, proto_ int local_offset; gint len2; int cmd_err; - gboolean ind; + bool ind; guchar *buffer; tvbuff_t *epsem_buffer = NULL; gboolean crypto_good = FALSE; @@ -990,7 +1015,7 @@ dissect_epsem(tvbuff_t *tvb, int offset, guint32 len, packet_info *pinfo, proto_ /* it's only encrypted if we have an undecrypted payload */ if (encrypted) { proto_tree_add_item(tree, hf_c1222_epsem_total, tvb, offset, -1, ENC_NA); - expert_add_info(pinfo, tree, &ei_c1222_epsem_not_decryped); + expert_add_info(pinfo, tree, &ei_c1222_epsem_not_decrypted); local_offset = offset+len2-4; epsem_buffer = tvb; } else { /* it's not (now) encrypted */ @@ -1082,7 +1107,7 @@ get_c1222_message_len(packet_info *pinfo, tvbuff_t *tvb, int offset, void *data { int orig_offset; guint length; - gboolean ind; + bool ind; orig_offset = offset; /* note that this assumes a Tag length of 1 which is always valid for C12.22 */ @@ -1368,7 +1393,7 @@ void proto_register_c1222(void) { { &ei_c1222_bad_checksum, { "c1222.bad_checksum", PI_CHECKSUM, PI_ERROR, "Bad checksum", EXPFILL }}, { &ei_c1222_epsem_missing, { "c1222.epsem.missing", PI_MALFORMED, PI_ERROR, "C12.22 EPSEM missing", EXPFILL }}, { &ei_c1222_epsem_failed_authentication, { "c1222.epsem.failed_authentication", PI_SECURITY, PI_ERROR, "C12.22 EPSEM failed authentication", EXPFILL }}, - { &ei_c1222_epsem_not_decryped, { "c1222.epsem.not_decryped", PI_UNDECODED, PI_WARN, "C12.22 EPSEM could not be decrypted", EXPFILL }}, + { &ei_c1222_epsem_not_decrypted, { "c1222.epsem.not_decrypted", PI_UNDECODED, PI_WARN, "C12.22 EPSEM could not be decrypted", EXPFILL }}, { &ei_c1222_ed_class_missing, { "c1222.ed_class_missing", PI_SECURITY, PI_ERROR, "C12.22 ED Class missing", EXPFILL }}, { &ei_c1222_epsem_ber_length_error, { "c1222.epsem.ber_length_error", PI_MALFORMED, PI_ERROR, "C12.22 EPSEM BER length error", EXPFILL }}, { &ei_c1222_epsem_field_length_error, { "c1222.epsem.field_length_error", PI_MALFORMED, PI_ERROR, "C12.22 EPSEM field length error", EXPFILL }}, @@ -1391,6 +1416,10 @@ void proto_register_c1222(void) { proto_register_subtree_array(ett, array_length(ett)); expert_c1222 = expert_register_protocol(proto_c1222); expert_register_field_array(expert_c1222, ei, array_length(ei)); + /* Register dissectors */ + c1222_handle = register_dissector("c1222.tcp", dissect_c1222, proto_c1222); + c1222_udp_handle = register_dissector("c1222.udp", dissect_c1222_common, proto_c1222); + /* Register dissection preferences */ c1222_module = prefs_register_protocol(proto_c1222, proto_reg_handoff_c1222); prefs_register_bool_preference(c1222_module, "desegment", "Reassemble all C12.22 messages spanning multiple TCP segments", @@ -1438,8 +1467,6 @@ proto_reg_handoff_c1222(void) guint8 *temp = NULL; if( !initialized ) { - c1222_handle = create_dissector_handle(dissect_c1222, proto_c1222); - c1222_udp_handle = create_dissector_handle(dissect_c1222_common, proto_c1222); dissector_add_uint_with_preference("tcp.port", C1222_PORT, c1222_handle); dissector_add_uint_with_preference("udp.port", C1222_PORT, c1222_udp_handle); initialized = TRUE; |