2 XXX all this offset>>3 and calculations of bytes in the tvb everytime
3 we put something in the tree is just silly. should be replaced with some
7 * Routines for dissection of ASN.1 Aligned PER
10 * $Id: packet-per.c,v 1.23 2003/10/27 22:28:48 guy Exp $
12 * Ethereal - Network traffic analyzer
13 * By Gerald Combs <gerald@ethereal.com>
14 * Copyright 1998 Gerald Combs
16 * This program is free software; you can redistribute it and/or
17 * modify it under the terms of the GNU General Public License
18 * as published by the Free Software Foundation; either version 2
19 * of the License, or (at your option) any later version.
21 * This program is distributed in the hope that it will be useful,
22 * but WITHOUT ANY WARRANTY; without even the implied warranty of
23 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
24 * GNU General Public License for more details.
26 * You should have received a copy of the GNU General Public License
27 * along with this program; if not, write to the Free Software
28 * Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
36 #include <epan/packet.h>
42 #include "packet-per.h"
45 static int proto_per = -1;
46 static int hf_per_GeneralString_length = -1;
47 static int hf_per_extension_bit = -1;
48 static int hf_per_extension_present_bit = -1;
49 static int hf_per_choice_extension = -1;
50 static int hf_per_num_sequence_extensions = -1;
51 static int hf_per_small_number_bit = -1;
52 static int hf_per_optional_field_bit = -1;
53 static int hf_per_sequence_of_length = -1;
54 static int hf_per_object_identifier_length = -1;
55 static int hf_per_open_type_length = -1;
56 static int hf_per_octet_string_length = -1;
59 static gint ett_per_sequence_of_item = -1;
63 #define DEBUG_ENTRY(x) \
64 printf("#%d %s tvb:0x%08x\n",pinfo->fd->num,x,(int)tvb);
66 #define DEBUG_ENTRY(x) \
71 /* whether the PER helpers should put the internal PER fields into the tree
74 static guint display_internal_per_fields = FALSE;
78 static const true_false_string tfs_extension_present_bit = {
82 static const true_false_string tfs_extension_bit = {
83 "Extension bit is set",
84 "Extension bit is clear"
86 static const true_false_string tfs_small_number_bit = {
87 "The number is small, 0-63",
88 "The number is large, >63"
90 static const true_false_string tfs_optional_field_bit = {
99 /* this decodes and returns a length determinant according to 10.9 */
101 dissect_per_length_determinant(tvbuff_t *tvb, guint32 offset, packet_info *pinfo _U_, proto_tree *tree, int hf_index, guint32 *length)
112 offset=(offset&0xfffffff8)+8;
114 byte=tvb_get_guint8(tvb, offset>>3);
120 proto_tree_add_uint(tree, hf_index, tvb, (offset>>3)-1, 1, *length);
124 if((byte&0xc0)==0x80){
126 *length=((*length)<<8)+tvb_get_guint8(tvb, offset>>3);
129 proto_tree_add_uint(tree, hf_index, tvb, (offset>>3)-2, 2, *length);
133 NOT_DECODED_YET("10.9.3.8.1");
137 /* 10.6 normally small non-negative whole number */
139 dissect_per_normally_small_nonnegative_whole_number(tvbuff_t *tvb, guint32 offset, packet_info *pinfo, proto_tree *tree, int hf_index, guint32 *length)
141 gboolean small_number;
144 DEBUG_ENTRY("dissect_per_normally_small_nonnegative_whole_number");
149 offset=dissect_per_boolean(tvb, offset, pinfo, tree, hf_per_small_number_bit, &small_number, NULL);
155 offset=dissect_per_boolean(tvb, offset, pinfo, tree, -1, &small_number, NULL);
163 proto_tree_add_uint(tree, hf_index, tvb, (offset>>3)-1, 1, *length);
165 proto_tree_add_uint(tree, hf_index, tvb, (offset>>3), 1, *length);
172 offset=dissect_per_length_determinant(tvb, offset, pinfo, tree, hf_index, length);
179 /* this function reads a GeneralString */
180 /* currently based on pure guesswork since RFC2833 didnt tell me much
181 i guess that the PER encoding for this is a normally-small-whole-number
182 followed by a ascii string.
184 based on pure guesswork. it looks ok in the only capture i have where
185 there is a 1 byte general string encoded
188 dissect_per_GeneralString(tvbuff_t *tvb, guint32 offset, packet_info *pinfo, proto_tree *tree, int hf_index)
190 proto_tree *etr=NULL;
193 if(display_internal_per_fields){
197 offset=dissect_per_length_determinant(tvb, offset, pinfo, etr, hf_per_GeneralString_length, &length);
200 proto_tree_add_item(tree, hf_index, tvb, offset>>3, length, FALSE);
207 /* 19 this function dissects a sequence of */
209 dissect_per_sequence_of_helper(tvbuff_t *tvb, guint32 offset, packet_info *pinfo, proto_tree *tree, int (*func)(tvbuff_t *, int , packet_info *, proto_tree *), guint32 length)
213 DEBUG_ENTRY("dissect_per_sequence_of_helper");
214 for(i=0;i<length;i++){
215 guint32 lold_offset=offset;
219 litem=proto_tree_add_text(tree, tvb, offset>>3, 0, "Item %d", i);
220 ltree=proto_item_add_subtree(litem, ett_per_sequence_of_item);
222 offset=(*func)(tvb, offset, pinfo, ltree);
223 proto_item_set_len(litem, (offset>>3)!=(lold_offset>>3)?(offset>>3)-(lold_offset>>3):1);
229 dissect_per_sequence_of(tvbuff_t *tvb, guint32 offset, packet_info *pinfo, proto_tree *parent_tree, int hf_index, gint ett_index, int (*func)(tvbuff_t *, int , packet_info *, proto_tree *))
233 guint32 old_offset=offset;
235 proto_tree *etr = NULL;
237 DEBUG_ENTRY("dissect_per_sequence_of");
239 item=proto_tree_add_item(parent_tree, hf_index, tvb, offset>>3, 0, FALSE);
240 tree=proto_item_add_subtree(item, ett_index);
242 /* semi-constrained whole number for number of elements */
243 /* each element encoded as 10.9 */
245 if(display_internal_per_fields){
248 offset=dissect_per_length_determinant(tvb, offset, pinfo, etr, hf_per_sequence_of_length, &length);
250 offset=dissect_per_sequence_of_helper(tvb, offset, pinfo, tree, func, length);
253 proto_item_set_len(item, (offset>>3)!=(old_offset>>3)?(offset>>3)-(old_offset>>3):1);
258 /* dissect a constrained IA5String that consists of the full ASCII set,
259 i.e. no FROM stuff limiting the alphabet
262 dissect_per_IA5String(tvbuff_t *tvb, guint32 offset, packet_info *pinfo, proto_tree *tree, int hf_index, int min_len, int max_len)
264 offset=dissect_per_octet_string(tvb, offset, pinfo, tree, hf_index, min_len, max_len, NULL, NULL);
269 /* XXX we dont do >64k length strings yet */
271 dissect_per_restricted_character_string(tvbuff_t *tvb, guint32 offset, packet_info *pinfo, proto_tree *tree, int hf_index, int min_len, int max_len, char *alphabet, int alphabet_length)
274 gboolean byte_aligned;
275 static char str[1024];
280 DEBUG_ENTRY("dissect_per_restricted_character_string");
281 /* xx.x if the length is 0 bytes there will be no encoding */
294 if(min_len!=max_len){
295 proto_tree *etr = NULL;
297 if(display_internal_per_fields){
300 offset=dissect_per_constrained_integer(tvb, offset, pinfo,
301 etr, hf_per_octet_string_length, min_len, max_len,
302 &length, NULL, FALSE);
307 /* xx.x if length is fixed or constrained to be less than or equal to
308 two bytes, then it will not be byte aligned. */
310 if((min_len==max_len)&&(max_len<=2)){
319 offset=(offset&0xfffffff8)+8;
325 NOT_DECODED_YET("restricted char string too long");
329 /* 27.5.2 depending of the alphabet length, find how many bits
330 are used to encode each character */
332 if(alphabet_length<=2){
334 } else if(alphabet_length<=4){
336 } else if(alphabet_length<=8){
338 } else if(alphabet_length<=16){
340 } else if(alphabet_length<=32){
342 } else if(alphabet_length<=64){
344 } else if(alphabet_length<=128){
350 if(alphabet_length<=2){
352 } else if(alphabet_length<=4){
354 } else if(alphabet_length<=16){
361 for(char_pos=0;char_pos<length;char_pos++){
367 for(i=0;i<bits_per_char;i++){
368 offset=dissect_per_boolean(tvb, offset, pinfo, tree, -1, &bit, NULL);
371 if (val >= alphabet_length)
372 str[char_pos] = '?'; /* XXX - how to mark this? */
374 str[char_pos]=alphabet[val];
377 proto_tree_add_string(tree, hf_index, tvb, (old_offset>>3), (offset>>3)-(old_offset>>3), str);
382 dissect_per_NumericString(tvbuff_t *tvb, guint32 offset, packet_info *pinfo, proto_tree *tree, int hf_index, int min_len, int max_len)
384 offset=dissect_per_restricted_character_string(tvb, offset, pinfo, tree, hf_index, min_len, max_len, " 0123456789", 11);
389 dissect_per_PrintableString(tvbuff_t *tvb, guint32 offset, packet_info *pinfo, proto_tree *tree, int hf_index, int min_len, int max_len)
391 offset=dissect_per_restricted_character_string(tvb, offset, pinfo, tree, hf_index, min_len, max_len, " '()+,-.*0123456789:=?ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz", 74);
395 dissect_per_BMPString(tvbuff_t *tvb, guint32 offset, packet_info *pinfo, proto_tree *tree, int hf_index, int min_len, int max_len)
400 /* xx.x if the length is 0 bytes there will be no encoding */
413 if(min_len!=max_len){
414 proto_tree *etr = NULL;
416 if(display_internal_per_fields){
419 offset=dissect_per_constrained_integer(tvb, offset, pinfo,
420 etr, hf_per_octet_string_length, min_len, max_len,
421 &length, NULL, FALSE);
425 /* align to byte boundary */
427 offset=(offset&0xfffffff8)+8;
431 NOT_DECODED_YET("BMPString too long");
435 str = tvb_fake_unicode(tvb, offset>>3, length, FALSE);
437 proto_tree_add_string(tree, hf_index, tvb, offset>>3, length*2, str);
439 offset+=(length<<3)*2;
445 /* this function dissects a constrained sequence of */
447 dissect_per_constrained_sequence_of(tvbuff_t *tvb, guint32 offset, packet_info *pinfo, proto_tree *parent_tree, int hf_index, gint ett_index, int (*func)(tvbuff_t *, int , packet_info *, proto_tree *), int min_len, int max_len)
451 guint32 old_offset=offset;
455 DEBUG_ENTRY("dissect_per_constrained_sequence_of");
456 item=proto_tree_add_item(parent_tree, hf_index, tvb, offset>>3, 0, FALSE);
457 tree=proto_item_add_subtree(item, ett_index);
459 /* 19.5 if min==max and min,max<64k ==> no length determinant */
460 if((min_len==max_len) && (min_len<65536)){
465 /* 19.6 ub>=64k or unset */
467 guint32 old_offset=offset;
468 /* semi-constrained whole number for number of elements */
469 /* each element encoded as 10.9 */
470 offset=dissect_per_length_determinant(tvb, offset, pinfo, tree, -1, &length);
472 proto_tree_add_uint(tree, hf_per_sequence_of_length, tvb, old_offset>>3, (offset>>3)!=(old_offset>>3)?(offset>>3)-(old_offset>>3):1, length);
476 /* constrained whole number for number of elements */
477 offset=dissect_per_constrained_integer(tvb, offset, pinfo,
478 tree, hf_per_sequence_of_length, min_len, max_len,
479 &length, NULL, FALSE);
484 offset=dissect_per_sequence_of_helper(tvb, offset, pinfo, tree, func, length);
487 proto_item_set_len(item, (offset>>3)!=(old_offset>>3)?(offset>>3)-(old_offset>>3):1);
491 /* this function dissects a constrained set of */
493 dissect_per_constrained_set_of(tvbuff_t *tvb, guint32 offset, packet_info *pinfo, proto_tree *parent_tree, int hf_index, gint ett_index, int (*func)(tvbuff_t *, int , packet_info *, proto_tree *), int min_len, int max_len)
495 /* for basic-per a set-of is encoded in the same way as a sequence-of */
496 DEBUG_ENTRY("dissect_per_constrained_set_of");
497 offset=dissect_per_constrained_sequence_of(tvb, offset, pinfo, parent_tree, hf_index, ett_index, func, min_len, max_len);
506 /* this function dissects a set of */
508 dissect_per_set_of(tvbuff_t *tvb, guint32 offset, packet_info *pinfo, proto_tree *parent_tree, int hf_index, gint ett_index, int (*func)(tvbuff_t *, int , packet_info *, proto_tree *))
510 /* for basic-per a set-of is encoded in the same way as a sequence-of */
511 DEBUG_ENTRY("dissect_per_set_of");
512 offset=dissect_per_sequence_of(tvb, offset, pinfo, parent_tree, hf_index, ett_index, func);
519 /* this function reads a OBJECT IDENTIFIER */
521 dissect_per_object_identifier(tvbuff_t *tvb, guint32 offset, packet_info *pinfo _U_, proto_tree *tree, int hf_index, char *value_string)
527 proto_tree *etr=NULL;
529 DEBUG_ENTRY("dissect_per_object_identifier");
531 if(display_internal_per_fields){
535 /* first byte is the count and it is byte aligned */
537 offset=(offset&0xfffffff8)+8;
539 count=tvb_get_guint8(tvb, offset>>3);
542 proto_tree_add_uint(etr, hf_per_object_identifier_length, tvb, offset>>3, 1, count);
546 for(i=0,strp=str;i<count;i++){
547 byte=tvb_get_guint8(tvb,offset>>3);
551 NOT_DECODED_YET("too long octet_string");
557 /* the first byte contains the first two object identifier components */
559 strp+=sprintf(strp,"0.%d",byte);
561 strp+=sprintf(strp,"1.%d",byte-40);
563 strp+=sprintf(strp,"2.%d",byte-80);
568 value=(value<<7)|(byte&0x7f);
573 strp+=sprintf(strp,".%d",value);
578 proto_tree_add_string(tree, hf_index, tvb, (offset>>3)-count, count, str);
581 strcpy(value_string, str);
590 /* this function reads a single bit */
592 dissect_per_boolean(tvbuff_t *tvb, guint32 offset, packet_info *pinfo _U_, proto_tree *tree, int hf_index, gboolean *bool, proto_item **item)
596 header_field_info *hfi;
599 DEBUG_ENTRY("dissect_per_boolean");
601 ch=tvb_get_guint8(tvb, offset>>3);
602 mask=1<<(7-(offset&0x07));
610 hfi = proto_registrar_get_nth(hf_index);
611 sprintf(str,"%s: %c%c%c%c %c%c%c%c %s",
613 mask&0x80?'0'+value:'.',
614 mask&0x40?'0'+value:'.',
615 mask&0x20?'0'+value:'.',
616 mask&0x10?'0'+value:'.',
617 mask&0x08?'0'+value:'.',
618 mask&0x04?'0'+value:'.',
619 mask&0x02?'0'+value:'.',
620 mask&0x01?'0'+value:'.',
623 it=proto_tree_add_boolean_format(tree, hf_index, tvb, offset>>3, 1, value, str);
638 /* we currently only handle integers up to 32 bits in length. */
640 dissect_per_integer(tvbuff_t *tvb, guint32 offset, packet_info *pinfo, proto_tree *tree, int hf_index, gint32 *value, proto_item **item)
647 offset=dissect_per_length_determinant(tvb, offset, pinfo, tree, -1, &length);
650 NOT_DECODED_YET("too long integer");
655 for(i=0;i<length;i++){
657 if(tvb_get_guint8(tvb, offset>>3)&0x80){
658 /* negative number */
661 /* positive number */
665 val=(val<<8)|tvb_get_guint8(tvb,offset>>3);
668 it=proto_tree_add_int(tree, hf_index, tvb, (offset>>3)-(length+1), length+1, val);
681 /* this function reads a constrained integer with or without a
682 PER visible extension marker present
684 has_extension==TRUE would map to asn constructs such as:
685 rfc-number INTEGER (1..32768, ...)
686 while has_extension==FALSE would map to:
687 t35CountryCode INTEGER (0..255)
689 it only handles integers that fit inside a 32 bit integer
695 10.5.6 unaligned version
696 10.5.7 aligned version
697 10.5.7.1 decoding of 0-255 1-8 bits
698 10.5.7.2 decoding og 0-256 8 bits
699 10.5.7.3 decoding of 0-65535 16 bits
703 dissect_per_constrained_integer(tvbuff_t *tvb, guint32 offset, packet_info *pinfo, proto_tree *tree, int hf_index, guint32 min, guint32 max, guint32 *value, proto_item **item, gboolean has_extension)
707 header_field_info *hfi;
712 DEBUG_ENTRY("dissect_per_constrained_integer");
714 gboolean extension_present;
715 offset=dissect_per_boolean(tvb, offset, pinfo, tree, -1, &extension_present, NULL);
716 if(extension_present){
717 offset=dissect_per_integer(tvb, offset, pinfo, tree,
724 hfi = proto_registrar_get_nth(hf_index);
728 /* just set range really big so it will fall through
729 to the bottom of the encoding */
740 it=proto_tree_add_uint_format(tree, hf_index, tvb, offset>>3, 0, min, "%s: %d", hfi->name, min);
763 } else if(range<=16){
765 } else if(range<=32){
767 } else if(range<=64){
769 } else if(range<=128){
771 } else if(range<=256){
774 /* prepare the string */
775 sprintf(str, "%s: ", hfi->name);
776 for(bit=0;bit<((int)(offset&0x07));bit++){
782 /* read the bits for the int */
783 for(i=0;i<num_bits;i++){
792 offset=dissect_per_boolean(tvb, offset, pinfo, tree, -1, &tmp, NULL);
809 it=proto_tree_add_uint_format(tree, hf_index, tvb, (offset-num_bits)>>3, length, val, "%s : %s (%d)", str, val_to_str(val, hfi->strings, "Unknown(%d)"),val);
811 it=proto_tree_add_uint(tree, hf_index, tvb, (offset-num_bits)>>3, length, val);
820 } else if(range==256){
825 /* in the aligned case, align to byte boundary */
827 offset=(offset&0xfffffff8)+8;
829 val=tvb_get_guint8(tvb, offset>>3);
833 it=proto_tree_add_uint(tree, hf_index, tvb, (offset>>3)-1, 1, val);
841 } else if(range<=65536){
846 /* in the aligned case, align to byte boundary */
848 offset=(offset&0xfffffff8)+8;
850 val=tvb_get_guint8(tvb, offset>>3);
853 val|=tvb_get_guint8(tvb, offset>>3);
857 it=proto_tree_add_uint(tree, hf_index, tvb, (offset>>3)-2, 2, val);
871 offset=dissect_per_boolean(tvb, offset, pinfo, tree, -1, &bit, NULL);
873 offset=dissect_per_boolean(tvb, offset, pinfo, tree, -1, &bit, NULL);
874 num_bytes=(num_bytes<<1)|bit;
876 num_bytes++; /* lower bound for length determinant is 1 */
880 offset=(offset&0xfffffff8)+8;
883 for(i=0;i<num_bytes;i++){
884 val=(val<<8)|tvb_get_guint8(tvb,offset>>3);
888 it=proto_tree_add_uint(tree, hf_index, tvb, (offset>>3)-(num_bytes+1), num_bytes+1, val);
898 NOT_DECODED_YET("10.5");
902 /* this functions decodes a CHOICE
903 it can only handle CHOICE INDEX values that fits inside a 32 bit integer.
910 22.7 extension marker == 0
911 22.8 extension marker == 1
914 dissect_per_choice(tvbuff_t *tvb, guint32 offset, packet_info *pinfo, proto_tree *tree, int hf_index, gint ett_index, per_choice_t *choice, char *name, guint32 *value)
916 gboolean extension_present, extension_flag;
917 int extension_root_entries;
918 guint32 choice_index;
922 guint32 old_offset=offset;
923 int min_choice=INT_MAX;
926 DEBUG_ENTRY("dissect_per_choice");
928 it=proto_tree_add_text(tree, tvb, offset>>3, 0, name);
929 tr=proto_item_add_subtree(it, ett_index);
932 /* first check if there should be an extension bit for this CHOICE.
933 we do this by just checking the first choice arm
935 if(choice[0].extension==ASN1_NO_EXTENSIONS){
938 proto_tree *etr=NULL;
940 if(display_internal_per_fields){
944 /* will be placed called again below to place it in the tree */
945 offset=dissect_per_boolean(tvb, offset, pinfo, etr, hf_per_extension_bit, &extension_flag, NULL);
948 /* count the number of entries in the extension_root */
949 extension_root_entries=0;
950 for(i=0;choice[i].name;i++){
951 switch(choice[i].extension){
952 case ASN1_NO_EXTENSIONS:
953 case ASN1_EXTENSION_ROOT:
954 if(choice[i].value<min_choice){
955 min_choice=choice[i].value;
957 if(choice[i].value>max_choice){
958 max_choice=choice[i].value;
960 extension_root_entries++;
965 if( (!extension_present)
966 || (extension_present && (extension_flag==0)) ){
967 guint32 choice_offset=offset;
968 proto_tree *choicetree;
969 proto_item *choiceitem;
970 proto_tree *etr=NULL;
974 /*qqq make it similar to the section below instead */
975 offset=dissect_per_constrained_integer(tvb, offset, pinfo,
976 tr, hf_index, min_choice, max_choice,
977 &choice_index, &choiceitem, FALSE);
982 choicetree=proto_item_add_subtree(choiceitem, ett_index);
984 if(display_internal_per_fields){
988 /* find and call the appropriate callback */
989 for(i=0;choice[i].name;i++){
990 if(choice[i].value==(int)choice_index){
992 offset=choice[i].func(tvb, offset, pinfo, choicetree);
995 NOT_DECODED_YET(choice[i].name);
1000 proto_item_set_len(choiceitem, (offset>>3)!=(choice_offset>>3)?(offset>>3)-(choice_offset>>3):1);
1004 guint32 choice_offset;
1005 proto_tree *choicetree;
1006 proto_item *choiceitem;
1007 proto_tree *etr=NULL;
1009 if(display_internal_per_fields){
1014 offset=dissect_per_normally_small_nonnegative_whole_number(tvb, offset, pinfo, etr, hf_per_choice_extension, &choice_index);
1015 offset=dissect_per_length_determinant(tvb, offset, pinfo, etr, hf_per_open_type_length, &length);
1018 choice_offset=offset;
1019 choiceitem=proto_tree_add_text(tr, tvb, offset>>3, 0, "Choice");
1020 choicetree=proto_item_add_subtree(choiceitem, ett_index);
1023 for(i=0;choice[i].name;i++){
1024 if(choice[i].extension==ASN1_NOT_EXTENSION_ROOT){
1040 /* if we dont know how to decode this one, just step offset to the next structure */
1042 NOT_DECODED_YET("unknown choice extension");
1046 proto_item_set_text(choiceitem, choice[index].name);
1047 new_offset=choice[index].func(tvb, offset, pinfo, choicetree);
1049 if((new_offset>(offset+(length*8)))||((new_offset+8)<(offset+length*8))){
1050 printf("new_offset:%d offset:%d length*8:%d\n",new_offset,offset,length*8);
1051 /* g_assert_not_reached();*/
1056 proto_item_set_len(choiceitem, (offset>>3)!=(choice_offset>>3)?(offset>>3)-(choice_offset>>3):1);
1059 proto_item_set_len(it, (offset>>3)!=(old_offset>>3)?(offset>>3)-(old_offset>>3):1);
1065 index_get_optional_name(per_sequence_t *sequence, int index)
1069 for(i=0;sequence[i].name;i++){
1070 if((sequence[i].extension!=ASN1_NOT_EXTENSION_ROOT)&&(sequence[i].optional==ASN1_OPTIONAL)){
1072 return sequence[i].name;
1077 return "<unknown type>";
1081 index_get_extension_name(per_sequence_t *sequence, int index)
1085 for(i=0;sequence[i].name;i++){
1086 if(sequence[i].extension==ASN1_NOT_EXTENSION_ROOT){
1088 return sequence[i].name;
1093 return "<unknown type>";
1096 /* this functions decodes a SEQUENCE
1097 it can only handle SEQUENCES with at most 32 DEFAULT or OPTIONAL fields
1099 18.2 optinal/default items in root
1100 18.3 we ignore the case where n>64K
1101 18.4 the root sequence
1109 dissect_per_sequence(tvbuff_t *tvb, guint32 offset, packet_info *pinfo, proto_tree *parent_tree, int hf_index, gint ett_index, per_sequence_t *sequence)
1111 gboolean extension_present, extension_flag, optional_field_flag;
1114 guint32 old_offset=offset;
1115 guint32 i, num_opts;
1116 guint32 optional_mask;
1119 DEBUG_ENTRY("dissect_per_sequence");
1121 item=proto_tree_add_item(parent_tree, hf_index, tvb, offset>>3, 0, FALSE);
1122 tree=proto_item_add_subtree(item, ett_index);
1125 /* first check if there should be an extension bit for this CHOICE.
1126 we do this by just checking the first choice arm
1130 if(sequence[0].extension==ASN1_NO_EXTENSIONS){
1131 extension_present=0;
1133 proto_tree *etr=NULL;
1135 if(display_internal_per_fields){
1138 extension_present=1;
1139 offset=dissect_per_boolean(tvb, offset, pinfo, etr, hf_per_extension_bit, &extension_flag, NULL);
1143 for(i=0;sequence[i].name;i++){
1144 if((sequence[i].extension!=ASN1_NOT_EXTENSION_ROOT)&&(sequence[i].optional==ASN1_OPTIONAL)){
1150 for(i=0;i<num_opts;i++){
1151 proto_item *it=NULL;
1152 proto_tree *etr=NULL;
1153 if(display_internal_per_fields){
1156 offset=dissect_per_boolean(tvb, offset, pinfo, etr, hf_per_optional_field_bit, &optional_field_flag, &it);
1158 if(optional_field_flag){
1159 optional_mask|=0x01;
1162 proto_item_append_text(it, " (%s %s present)",
1163 index_get_optional_name(sequence, i),
1164 optional_field_flag?"is":"is NOT"
1171 for(i=0;sequence[i].name;i++){
1172 if( (sequence[i].extension==ASN1_NO_EXTENSIONS)
1173 || (sequence[i].extension==ASN1_EXTENSION_ROOT) ){
1174 if(sequence[i].optional==ASN1_OPTIONAL){
1175 gboolean is_present;
1176 is_present=(1<<(num_opts-1))&optional_mask;
1182 if(sequence[i].func){
1183 offset=sequence[i].func(tvb, offset, pinfo, tree);
1185 NOT_DECODED_YET(sequence[i].name);
1192 gboolean extension_bit;
1193 guint32 num_known_extensions;
1194 guint32 num_extensions;
1195 guint32 extension_mask;
1196 proto_tree *etr=NULL;
1197 proto_item *it=NULL;
1199 if(display_internal_per_fields){
1203 offset=dissect_per_normally_small_nonnegative_whole_number(tvb, offset, pinfo, etr, hf_per_num_sequence_extensions, &num_extensions);
1204 /* the X.691 standard is VERY unclear here.
1205 there is no mention that the lower bound lb for this
1206 (apparently) semiconstrained value is 1,
1207 apart from the NOTE: comment in 18.8 that this value can
1209 In my book, there is a semantic difference between having
1210 a comment that says that the value can not be zero
1211 and stating that the lb is 1.
1212 I dont know if this is right or not but it makes
1213 some of the very few captures I have decode properly.
1215 It could also be that the captures I have are generated by
1216 a broken implementation.
1217 If this is wrong and you dont report it as a bug
1218 then it wont get fixed!
1223 for(i=0;i<num_extensions;i++){
1224 offset=dissect_per_boolean(tvb, offset, pinfo, etr, hf_per_extension_present_bit, &extension_bit, &it);
1225 extension_mask=(extension_mask<<1)|extension_bit;
1227 proto_item_append_text(it, " (%s %s present)",
1228 index_get_extension_name(sequence, i),
1229 extension_bit?"is":"is NOT"
1235 /* find how many extensions we know about */
1236 num_known_extensions=0;
1237 for(i=0;sequence[i].name;i++){
1238 if(sequence[i].extension==ASN1_NOT_EXTENSION_ROOT){
1239 num_known_extensions++;
1243 /* decode the extensions one by one */
1244 for(i=0;i<num_extensions;i++){
1247 guint32 extension_index;
1250 if(!((1L<<(num_extensions-1-i))&extension_mask)){
1251 /* this extension is not encoded in this PDU */
1255 offset=dissect_per_length_determinant(tvb, offset, pinfo, etr, hf_per_open_type_length, &length);
1257 if(i>=num_known_extensions){
1258 /* we dont know how to decode this extension */
1260 NOT_DECODED_YET("unknown sequence extension");
1265 for(j=0,k=0;sequence[j].name;j++){
1266 if(sequence[j].extension==ASN1_NOT_EXTENSION_ROOT){
1275 if(sequence[extension_index].func){
1276 new_offset=sequence[extension_index].func(tvb, offset, pinfo, tree);
1278 NOT_DECODED_YET(sequence[extension_index].name);
1286 proto_item_set_len(item, (offset>>3)!=(old_offset>>3)?(offset>>3)-(old_offset>>3):1);
1294 /* this fucntion dissects an OCTET STRING
1304 max_len or min_len == -1 means there is no lower/upper constraint
1306 hf_index can either be a FT_BYTES or an FT_STRING
1309 dissect_per_octet_string(tvbuff_t *tvb, guint32 offset, packet_info *pinfo, proto_tree *tree, int hf_index, int min_len, int max_len, guint32 *value_offset, guint32 *value_len)
1312 header_field_info *hfi;
1314 hfi = (hf_index==-1) ? NULL : proto_registrar_get_nth(hf_index);
1316 DEBUG_ENTRY("dissect_per_octet_string");
1317 /* 16.5 if the length is 0 bytes there will be no encoding */
1327 /* 16.6 if length is fixed and less than or equal to two bytes*/
1328 if((min_len==max_len)&&(max_len<=2)){
1329 static char bytes[4];
1330 guint32 i, old_offset=offset;
1334 offset=dissect_per_boolean(tvb, offset, pinfo, tree, -1, &bit, NULL);
1335 bytes[0]=(bytes[0]<<1)|bit;
1339 offset=dissect_per_boolean(tvb, offset, pinfo, tree, -1, &bit, NULL);
1340 bytes[1]=(bytes[1]<<1)|bit;
1345 if(hfi->type==FT_STRING){
1346 proto_tree_add_string(tree, hf_index, tvb, old_offset>>3, min_len+(offset&0x07)?1:0, bytes);
1348 proto_tree_add_bytes(tree, hf_index, tvb, old_offset>>3, min_len+(offset&0x07)?1:0, bytes);
1352 *value_offset = old_offset>>3;
1355 *value_len = min_len+(offset&0x07)?1:0;
1361 /* 16.7 if length is fixed and less than to 64k*/
1362 if((min_len==max_len)&&(min_len<65536)){
1365 offset=(offset&0xfffffff8)+8;
1368 proto_tree_add_item(tree, hf_index, tvb, offset>>3, min_len, FALSE);
1371 *value_offset = offset>>3;
1374 *value_len = min_len;
1382 proto_tree *etr = NULL;
1384 if(display_internal_per_fields){
1387 offset=dissect_per_constrained_integer(tvb, offset, pinfo,
1388 etr, hf_per_octet_string_length, min_len, max_len,
1389 &length, NULL, FALSE);
1391 offset=dissect_per_length_determinant(tvb, offset, pinfo, tree, hf_per_octet_string_length, &length);
1396 offset=(offset&0xfffffff8)+8;
1399 proto_tree_add_item(tree, hf_index, tvb, offset>>3, length, FALSE);
1403 *value_offset = offset>>3;
1406 *value_len = length;
1416 proto_register_per(void)
1418 static hf_register_info hf[] =
1420 { &hf_per_num_sequence_extensions,
1421 { "Number of Sequence Extensions", "per.num_sequence_extensions", FT_UINT32, BASE_DEC,
1422 NULL, 0, "Number of extensions encoded in this sequence", HFILL }},
1423 { &hf_per_choice_extension,
1424 { "Choice Extension", "per.choice_extension", FT_UINT32, BASE_DEC,
1425 NULL, 0, "Which extension of the Choice is encoded", HFILL }},
1426 { &hf_per_GeneralString_length,
1427 { "GeneralString Length", "per.generalstring_length", FT_UINT32, BASE_DEC,
1428 NULL, 0, "Length of the GeneralString", HFILL }},
1429 { &hf_per_extension_bit,
1430 { "Extension Bit", "per.extension_bit", FT_BOOLEAN, 8,
1431 TFS(&tfs_extension_bit), 0x01, "The extension bit of an aggregate", HFILL }},
1432 { &hf_per_extension_present_bit,
1433 { "Extension Present Bit", "per.extension_present_bit", FT_BOOLEAN, 8,
1434 TFS(&tfs_extension_present_bit), 0x01, "Whether this optional extension is present or not", HFILL }},
1435 { &hf_per_small_number_bit,
1436 { "Small Number Bit", "per.small_number_bit", FT_BOOLEAN, 8,
1437 TFS(&tfs_small_number_bit), 0x01, "The small number bit for a section 10.6 integer", HFILL }},
1438 { &hf_per_optional_field_bit,
1439 { "Optional Field Bit", "per.optional_field_bit", FT_BOOLEAN, 8,
1440 TFS(&tfs_optional_field_bit), 0x01, "This bit specifies the presence/absence of an optional field", HFILL }},
1441 { &hf_per_sequence_of_length,
1442 { "Sequence-Of Length", "per.sequence_of_length", FT_UINT32, BASE_DEC,
1443 NULL, 0, "Number of items in the Sequence Of", HFILL }},
1444 { &hf_per_object_identifier_length,
1445 { "Object Length", "per.object_length", FT_UINT32, BASE_DEC,
1446 NULL, 0, "Length of the object identifier", HFILL }},
1447 { &hf_per_open_type_length,
1448 { "Open Type Length", "per.open_type_length", FT_UINT32, BASE_DEC,
1449 NULL, 0, "Length of an open type encoding", HFILL }},
1450 { &hf_per_octet_string_length,
1451 { "Octet String Length", "per.octet_string_length", FT_UINT32, BASE_DEC,
1452 NULL, 0, "Number of bytes in the Octet String", HFILL }},
1455 static gint *ett[] =
1457 &ett_per_sequence_of_item
1459 module_t *per_module;
1461 proto_per = proto_register_protocol("Packed Encoding Rules (ASN.1 X.691)", "PER", "per");
1462 proto_register_field_array(proto_per, hf, array_length(hf));
1463 proto_register_subtree_array(ett, array_length(ett));
1465 per_module = prefs_register_protocol(proto_per, NULL);
1466 prefs_register_bool_preference(per_module, "display_internal_per_fields",
1467 "Display the internal PER fields in the tree",
1468 "Whether the dissector should put the internal PER data in the tree or if it should hide it",
1469 &display_internal_per_fields);
1474 proto_reg_handoff_per(void)