2 * Copyright (C) 2000,2001 Fabio Fiorina
4 * This file is part of GNUTLS.
6 * GNUTLS is free software; you can redistribute it and/or modify
7 * it under the terms of the GNU General Public License as published by
8 * the Free Software Foundation; either version 2 of the License, or
9 * (at your option) any later version.
11 * GNUTLS is distributed in the hope that it will be useful,
12 * but WITHOUT ANY WARRANTY; without even the implied warranty of
13 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
14 * GNU General Public License for more details.
16 * You should have received a copy of the GNU General Public License
17 * along with this program; if not, write to the Free Software
18 * Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA
22 /*****************************************************/
23 /* File: x509_der.c */
24 /* Description: Functions to manage DER encoding */
25 /*****************************************************/
32 #define TAG_BOOLEAN 0x01
33 #define TAG_INTEGER 0x02
34 #define TAG_SEQUENCE 0x10
36 #define TAG_OCTET_STRING 0x04
37 #define TAG_BIT_STRING 0x03
38 #define TAG_UTCTime 0x17
39 #define TAG_GENERALIZEDTime 0x18
40 #define TAG_OBJECT_ID 0x06
41 #define TAG_ENUMERATED 0x0A
46 _asn1_ltostr(long v,char *str)
63 temp[start+count]='0'+(char)r;
68 for(k=0;k<count;k++) str[k+start]=temp[start+count-k-1];
75 _asn1_length_der(unsigned long len,unsigned char *ans,int *ans_len)
78 unsigned char temp[128];
82 if(ans!=NULL) ans[0]=(unsigned char)len;
94 ans[0]=((unsigned char)k&0x7F)+128;
95 while(k--) ans[*ans_len-1-k]=temp[k];
102 _asn1_get_length_der(unsigned char *der,int *len)
117 while(punt<=k) ans=ans*256+der[punt++];
126 _asn1_tag_der(unsigned char class,unsigned int tag_value,unsigned char *ans,int *ans_len)
129 unsigned char temp[128];
133 ans[0]=(class&0xE0) + ((unsigned char)(tag_value&0x1F));
138 ans[0]=(class&0xE0) + 31;
141 temp[k++]=tag_value&0x7F;
142 tag_value=tag_value>>7;
145 while(k--) ans[*ans_len-1-k]=temp[k]+128;
146 ans[*ans_len-1]-=128;
152 _asn1_get_tag_der(unsigned char *der,unsigned char *class,int *len)
157 if((der[0]&0x1F)!=0x1F){
166 while(der[punt]&128) ris=ris*128+(der[punt++]&0x7F);
167 ris=ris*128+(der[punt++]&0x7F);
175 _asn1_octet_der(unsigned char *str,int str_len,unsigned char *der,int *der_len)
179 if(der==NULL) return;
180 _asn1_length_der(str_len,der,&len_len);
181 memcpy(der+len_len,str,str_len);
182 *der_len=str_len+len_len;
187 _asn1_get_octet_der(unsigned char *der,int *der_len,unsigned char *str,int str_size, int *str_len)
191 if(str==NULL) return ASN_OK;
192 *str_len=_asn1_get_length_der(der,&len_len);
193 if ( str_size >= *str_len)
194 memcpy(str,der+len_len,*str_len);
196 return ASN_MEM_ERROR;
198 *der_len=*str_len+len_len;
205 _asn1_time_der(unsigned char *str,unsigned char *der,int *der_len)
209 if(der==NULL) return;
210 _asn1_length_der(strlen(str),der,&len_len);
211 memcpy(der+len_len,str,strlen(str));
212 *der_len=len_len+strlen(str);
218 _asn1_get_utctime_der(unsigned char *der,int *der_len,unsigned char *str)
223 if(str==NULL) return;
224 str_len=_asn1_get_length_der(der,&len_len);
225 memcpy(temp,der+len_len,str_len);
226 *der_len=str_len+len_len;
230 strcat(temp,"00+0000");
234 strcat(temp,"+0000");
238 memmove(temp+12,temp+10,6);
239 temp[10]=temp[11]='0';
253 _asn1_get_time_der(unsigned char *der,int *der_len,unsigned char *str)
257 if(str==NULL) return;
258 str_len=_asn1_get_length_der(der,&len_len);
259 memcpy(str,der+len_len,str_len);
261 *der_len=str_len+len_len;
265 _asn1_objectid_der(unsigned char *str,unsigned char *der,int *der_len)
267 int len_len,counter,k,first;
268 char temp[128],*n_end,*n_start;
270 unsigned long val,val1=0;
272 if(der==NULL) return;
274 _asn1_str_cpy(temp, sizeof(temp), str);
275 _asn1_str_cat(temp, sizeof(temp), " ");
279 while((n_end=strchr(n_start,' '))){
281 val=strtoul(n_start,NULL,10);
284 if(counter==1) val1=val;
292 bit7=(val>>(k*7))&0x7F;
293 if(bit7 || first || !k){
305 _asn1_length_der(*der_len,NULL,&len_len);
306 memmove(der+len_len,der,*der_len);
307 _asn1_length_der(*der_len,der,&len_len);
313 _asn1_get_objectid_der(unsigned char *der,int *der_len,unsigned char *str, int str_size)
317 unsigned long val,val1;
319 if(str==NULL) return;
320 len=_asn1_get_length_der(der,&len_len);
322 val1=der[len_len]/40;
323 val=der[len_len]-val1*40;
325 _asn1_str_cpy(str, str_size, _asn1_ltostr(val1,temp));
326 _asn1_str_cat(str, str_size, " ");
327 _asn1_str_cat(str, str_size, _asn1_ltostr(val,temp));
332 val|=der[len_len+k]&0x7F;
333 if(!(der[len_len+k]&0x80)){
334 _asn1_str_cat(str, str_size," ");
335 _asn1_str_cat(str, str_size,_asn1_ltostr(val,temp));
339 *der_len=len+len_len;
344 char bit_mask[]={0xFF,0xFE,0xFC,0xF8,0xF0,0xE0,0xC0,0x80};
347 _asn1_bit_der(unsigned char *str,int bit_len,unsigned char *der,int *der_len)
349 int len_len,len_byte,len_pad;
351 if(der==NULL) return;
353 len_pad=8-(bit_len&7);
354 if(len_pad==8) len_pad=0;
356 _asn1_length_der(len_byte+1,der,&len_len);
357 der[len_len]=len_pad;
358 memcpy(der+len_len+1,str,len_byte);
359 der[len_len+len_byte]&=bit_mask[len_pad];
360 *der_len=len_byte+len_len+1;
365 _asn1_get_bit_der(unsigned char *der,int *der_len,unsigned char *str, int str_size, int *bit_len)
367 int len_len,len_byte;
369 if(str==NULL) return ASN_OK;
370 len_byte=_asn1_get_length_der(der,&len_len)-1;
372 if (str_size >= len_byte)
373 memcpy(str,der+len_len+1,len_byte);
375 return ASN_MEM_ERROR;
377 *bit_len=len_byte*8-der[len_len];
378 *der_len=len_byte+len_len+1;
392 _asn1_complete_explicit_tag(node_asn *node,unsigned char *der,int *counter)
395 int is_tag_implicit,len2,len3;
396 unsigned char temp[10];
400 if(node->type&CONST_TAG){
403 if(type_field(p->type)==TYPE_TAG){
404 if(p->type&CONST_EXPLICIT){
405 len2=strtol(p->name,NULL,10);
406 _asn1_set_name(p,NULL);
407 _asn1_length_der(*counter-len2,temp,&len3);
408 memmove(der+len2+len3,der+len2,*counter-len2);
409 memcpy(der+len2,temp,len3);
413 else{ /* CONST_IMPLICIT */
414 if(!is_tag_implicit){
426 _asn1_insert_tag_der(node_asn *node,unsigned char *der,int *counter)
429 int tag_len,is_tag_implicit;
430 unsigned char class,class_implicit=0,temp[10];
431 unsigned long tag_implicit=0;
435 if(node->type&CONST_TAG){
438 if(type_field(p->type)==TYPE_TAG){
439 if(p->type&CONST_APPLICATION) class=APPLICATION;
440 else if(p->type&CONST_UNIVERSAL) class=UNIVERSAL;
441 else if(p->type&CONST_PRIVATE) class=PRIVATE;
442 else class=CONTEXT_SPECIFIC;
444 if(p->type&CONST_EXPLICIT){
446 _asn1_tag_der(class_implicit,tag_implicit,der+*counter,&tag_len);
448 _asn1_tag_der(class|STRUCTURED,strtoul(p->value,NULL,10),der+*counter,&tag_len);
450 _asn1_ltostr(*counter,temp);
451 _asn1_set_name(p,temp);
455 else{ /* CONST_IMPLICIT */
456 if(!is_tag_implicit){
457 if((type_field(node->type)==TYPE_SEQUENCE) ||
458 (type_field(node->type)==TYPE_SEQUENCE_OF) ||
459 (type_field(node->type)==TYPE_SET) ||
460 (type_field(node->type)==TYPE_SET_OF)) class|=STRUCTURED;
461 class_implicit=class;
462 tag_implicit=strtoul(p->value,NULL,10);
472 _asn1_tag_der(class_implicit,tag_implicit,der+*counter,&tag_len);
475 switch(type_field(node->type)){
477 _asn1_tag_der(UNIVERSAL,TAG_NULL,der+*counter,&tag_len);
480 _asn1_tag_der(UNIVERSAL,TAG_BOOLEAN,der+*counter,&tag_len);
483 _asn1_tag_der(UNIVERSAL,TAG_INTEGER,der+*counter,&tag_len);
485 case TYPE_ENUMERATED:
486 _asn1_tag_der(UNIVERSAL,TAG_ENUMERATED,der+*counter,&tag_len);
489 _asn1_tag_der(UNIVERSAL,TAG_OBJECT_ID,der+*counter,&tag_len);
492 if(node->type&CONST_UTC){
493 _asn1_tag_der(UNIVERSAL,TAG_UTCTime,der+*counter,&tag_len);
495 else _asn1_tag_der(UNIVERSAL,TAG_GENERALIZEDTime,der+*counter,&tag_len);
497 case TYPE_OCTET_STRING:
498 _asn1_tag_der(UNIVERSAL,TAG_OCTET_STRING,der+*counter,&tag_len);
500 case TYPE_BIT_STRING:
501 _asn1_tag_der(UNIVERSAL,TAG_BIT_STRING,der+*counter,&tag_len);
503 case TYPE_SEQUENCE: case TYPE_SEQUENCE_OF:
504 _asn1_tag_der(UNIVERSAL|STRUCTURED,TAG_SEQUENCE,der+*counter,&tag_len);
506 case TYPE_SET: case TYPE_SET_OF:
507 _asn1_tag_der(UNIVERSAL|STRUCTURED,TAG_SET,der+*counter,&tag_len);
519 return ASN_GENERIC_ERROR;
530 _asn1_extract_tag_der(node_asn *node,unsigned char *der,int *der_len)
533 int counter,len2,len3,is_tag_implicit;
534 unsigned long tag,tag_implicit=0;
535 unsigned char class,class2,class_implicit=0;
537 counter=is_tag_implicit=0;
538 if(node->type&CONST_TAG){
541 if(type_field(p->type)==TYPE_TAG){
542 if(p->type&CONST_APPLICATION) class2=APPLICATION;
543 else if(p->type&CONST_UNIVERSAL) class2=UNIVERSAL;
544 else if(p->type&CONST_PRIVATE) class2=PRIVATE;
545 else class2=CONTEXT_SPECIFIC;
547 if(p->type&CONST_EXPLICIT){
548 tag=_asn1_get_tag_der(der+counter,&class,&len2);
550 len3=_asn1_get_length_der(der+counter,&len2);
552 if(!is_tag_implicit){
553 if((class!=(class2|STRUCTURED)) || (tag!=strtoul(p->value,NULL,10)))
554 return ASN_TAG_ERROR;
556 else{ /* TAG_IMPLICIT */
557 if((class!=class_implicit) || (tag!=tag_implicit))
558 return ASN_TAG_ERROR;
563 else{ /* TAG_IMPLICIT */
564 if(!is_tag_implicit){
565 if((type_field(node->type)==TYPE_SEQUENCE) ||
566 (type_field(node->type)==TYPE_SEQUENCE_OF) ||
567 (type_field(node->type)==TYPE_SET) ||
568 (type_field(node->type)==TYPE_SET_OF)) class2|=STRUCTURED;
569 class_implicit=class2;
570 tag_implicit=strtoul(p->value,NULL,10);
580 tag=_asn1_get_tag_der(der+counter,&class,&len2);
581 if((class!=class_implicit) || (tag!=tag_implicit)) return ASN_TAG_ERROR;
584 if(type_field(node->type)==TYPE_TAG){
590 tag=_asn1_get_tag_der(der+counter,&class,&len2);
591 switch(type_field(node->type)){
593 if((class!=UNIVERSAL) || (tag!=TAG_NULL)) return ASN_DER_ERROR;
596 if((class!=UNIVERSAL) || (tag!=TAG_BOOLEAN)) return ASN_DER_ERROR;
599 if((class!=UNIVERSAL) || (tag!=TAG_INTEGER)) return ASN_DER_ERROR;
601 case TYPE_ENUMERATED:
602 if((class!=UNIVERSAL) || (tag!=TAG_ENUMERATED)) return ASN_DER_ERROR;
605 if((class!=UNIVERSAL) || (tag!=TAG_OBJECT_ID)) return ASN_DER_ERROR;
608 if(node->type&CONST_UTC){
609 if((class!=UNIVERSAL) || (tag!=TAG_UTCTime)) return ASN_DER_ERROR;
612 if((class!=UNIVERSAL) || (tag!=TAG_GENERALIZEDTime))
613 return ASN_DER_ERROR;
616 case TYPE_OCTET_STRING:
617 if((class!=UNIVERSAL) || (tag!=TAG_OCTET_STRING)) return ASN_DER_ERROR;
619 case TYPE_BIT_STRING:
620 if((class!=UNIVERSAL) || (tag!=TAG_BIT_STRING)) return ASN_DER_ERROR;
622 case TYPE_SEQUENCE: case TYPE_SEQUENCE_OF:
623 if((class!=(UNIVERSAL|STRUCTURED)) || (tag!=TAG_SEQUENCE))
624 return ASN_DER_ERROR;
626 case TYPE_SET: case TYPE_SET_OF:
627 if((class!=(UNIVERSAL|STRUCTURED)) || (tag!=TAG_SET))
628 return ASN_DER_ERROR;
634 return ASN_DER_ERROR;
646 _asn1_ordering_set(unsigned char *der,node_asn *node)
651 struct vet *next,*prev;
654 int counter,len,len2;
655 struct vet *first,*last,*p_vet,*p2_vet;
657 unsigned char class,*temp;
662 if(type_field(node->type)!=TYPE_SET) return;
665 while((type_field(p->type)==TYPE_TAG) || (type_field(p->type)==TYPE_SIZE)) p=p->right;
667 if((p==NULL) || (p->right==NULL)) return;
671 p_vet=(struct vet *)_asn1_alloca( sizeof(struct vet));
672 if (p_vet==NULL) return;
676 if(first==NULL) first=p_vet;
677 else last->next=p_vet;
680 /* tag value calculation */
681 tag=_asn1_get_tag_der(der+counter,&class,&len2);
682 p_vet->value=(class<<24)|tag;
685 /* extraction and length */
686 len2=_asn1_get_length_der(der+counter,&len);
699 if(p_vet->value>p2_vet->value){
700 /* change position */
701 temp=(unsigned char *)_asn1_alloca( p_vet->end-counter);
702 if (temp==NULL) return;
704 memcpy(temp,der+counter,p_vet->end-counter);
705 memmove(der+counter,der+p_vet->end,p2_vet->end-p_vet->end);
706 memcpy(der+p_vet->end,temp,p_vet->end-counter);
710 p_vet->value=p2_vet->value;
713 p_vet->end=counter+(p2_vet->end-p_vet->end);
721 if(p_vet!=first) p_vet->prev->next=NULL;
730 _asn1_ordering_set_of(unsigned char *der,node_asn *node)
734 struct vet *next,*prev;
737 int counter,len,len2,change;
738 struct vet *first,*last,*p_vet,*p2_vet;
740 unsigned char *temp,class;
745 if(type_field(node->type)!=TYPE_SET_OF) return;
748 while((type_field(p->type)==TYPE_TAG) || (type_field(p->type)==TYPE_SIZE)) p=p->right;
751 if((p==NULL) || (p->right==NULL)) return;
755 p_vet=(struct vet *)_asn1_alloca(sizeof(struct vet));
756 if (p_vet==NULL) return;
760 if(first==NULL) first=p_vet;
761 else last->next=p_vet;
764 /* extraction of tag and length */
765 _asn1_get_tag_der(der+counter,&class,&len);
767 len2=_asn1_get_length_der(der+counter,&len);
780 if((p_vet->end-counter)>(p2_vet->end-p_vet->end))
781 max=p_vet->end-counter;
783 max=p2_vet->end-p_vet->end;
787 if(der[counter+k]>der[p_vet->end+k]){change=1;break;}
788 else if(der[counter+k]<der[p_vet->end+k]){change=0;break;}
790 if((change==-1) && ((p_vet->end-counter)>(p2_vet->end-p_vet->end)))
794 /* change position */
795 temp=(unsigned char *)_asn1_alloca(p_vet->end-counter);
796 if (temp==NULL) return;
798 memcpy(temp,der+counter,p_vet->end-counter);
799 memmove(der+counter,der+p_vet->end,p2_vet->end-p_vet->end);
800 memcpy(der+p_vet->end,temp,p_vet->end-counter);
803 p_vet->end=counter+(p2_vet->end-p_vet->end);
811 if(p_vet!=first) p_vet->prev->next=NULL;
819 * asn1_create_der - Creates the DER encoding for the NAME structure
820 * @root: pointer to a structure
821 * @name: the name of the structure you want to encode (it must be inside *POINTER).
822 * @der: vector that will contain the DER encoding. DER must be a pointer to memory cells already allocated.
823 * @len: number of bytes of *der: der[0]..der[len-1]
826 * Creates the DER encoding for the NAME structure (inside *POINTER structure).
830 * ASN_OK\: DER encoding OK
832 * ASN_ELEMENT_NOT_FOUND\: NAME is not a valid element.
834 * ASN_VALUE_NOT_FOUND\: there is an element without a value.
837 asn1_create_der(node_asn *root,char *name,unsigned char *der,int *len)
841 int counter,counter_old,len2,len3,move,ris;
843 node=_asn1_find_node(root,name);
844 if(node==NULL) return ASN_ELEMENT_NOT_FOUND;
852 if(move!=UP) ris=_asn1_insert_tag_der(p,der,&counter);
854 switch(type_field(p->type)){
861 if((p->type&CONST_DEFAULT) && (p->value==NULL)) counter=counter_old;
864 if(p->value[0]=='F') der[counter++]=0;
865 else der[counter++]=0xFF;
869 case TYPE_INTEGER: case TYPE_ENUMERATED:
870 if((p->type&CONST_DEFAULT) && (p->value==NULL)) counter=counter_old;
872 len2=_asn1_get_length_der(p->value,&len3);
873 memcpy(der+counter,p->value,len3+len2);
879 _asn1_objectid_der(p->value,der+counter,&len2);
884 _asn1_time_der(p->value,der+counter,&len2);
888 case TYPE_OCTET_STRING:
889 len2=_asn1_get_length_der(p->value,&len3);
890 memcpy(der+counter,p->value,len3+len2);
894 case TYPE_BIT_STRING:
895 len2=_asn1_get_length_der(p->value,&len3);
896 memcpy(der+counter,p->value,len3+len2);
900 case TYPE_SEQUENCE: case TYPE_SET:
902 _asn1_ltostr(counter,temp);
903 _asn1_set_value(p,temp,strlen(temp)+1);
907 len2=strtol(p->value,NULL,10);
908 _asn1_set_value(p,NULL,0);
909 if(type_field(p->type)==TYPE_SET) _asn1_ordering_set(der+len2,p);
910 _asn1_length_der(counter-len2,temp,&len3);
911 memmove(der+len2+len3,der+len2,counter-len2);
912 memcpy(der+len2,temp,len3);
917 case TYPE_SEQUENCE_OF: case TYPE_SET_OF:
919 _asn1_ltostr(counter,temp);
920 _asn1_set_value(p,temp,strlen(temp)+1);
922 while((type_field(p->type)==TYPE_TAG) || (type_field(p->type)==TYPE_SIZE)) p=p->right;
928 else p=_asn1_find_up(p);
932 len2=strtol(p->value,NULL,10);
933 _asn1_set_value(p,NULL,0);
934 if(type_field(p->type)==TYPE_SET_OF) _asn1_ordering_set_of(der+len2,p);
935 _asn1_length_der(counter-len2,temp,&len3);
936 memmove(der+len2+len3,der+len2,counter-len2);
937 memcpy(der+len2,temp,len3);
943 len2=_asn1_get_length_der(p->value,&len3);
944 memcpy(der+counter,p->value+len3,len2);
949 move=(move==UP)?RIGHT:DOWN;
953 if((move!=DOWN) && (counter!=counter_old))
954 _asn1_complete_explicit_tag(p,der,&counter);
956 if(p==node && move!=DOWN) break;
959 if(p->down) p=p->down;
963 if(p->right) p=p->right;
966 if(move==UP) p=_asn1_find_up(p);
974 * asn1_get_der - Fill the structure *POINTER with values of a DER encoding string.
975 * @root: pointer to a structure
976 * @der: vector that contains the DER encoding.
977 * @len: number of bytes of *der: der[0]..der[len-1]
980 * Fill the structure *POINTER with values of a DER encoding string. The sructure must just be
981 * created with function 'create_stucture'.
985 * ASN_OK\: DER encoding OK
987 * ASN_ELEMENT_NOT_FOUND\: NAME is not a valid element.
989 * ASN_TAG_ERROR,ASN_DER_ERROR\: the der encoding doesn't match the structure NAME.
993 asn1_get_der(node_asn *root,unsigned char *der,int len)
995 node_asn *node,*p,*p2,*p3;
997 int counter,len2,len3,len4,move,ris;
998 unsigned char class,*temp2;
1002 if(node==NULL) return ASN_ELEMENT_NOT_FOUND;
1004 if(node->type&CONST_OPTION) return ASN_GENERIC_ERROR;
1013 if(p->type&CONST_SET){
1014 p2=_asn1_find_up(p);
1015 len2=strtol(p2->value,NULL,10);
1021 else if(counter>len2) return ASN_DER_ERROR;
1024 if((p2->type&CONST_SET) && (p2->type&CONST_NOT_USED)){ /* CONTROLLARE */
1025 if(type_field(p2->type)!=TYPE_CHOICE)
1026 ris=_asn1_extract_tag_der(p2,der+counter,&len2);
1030 ris=_asn1_extract_tag_der(p3,der+counter,&len2);
1031 if(ris==ASN_OK) break;
1032 //if(ris==ASN_ERROR_TYPE_ANY) return ASN_ERROR_TYPE_ANY;
1037 p2->type&=~CONST_NOT_USED;
1041 //else if(ris==ASN_ERROR_TYPE_ANY) return ASN_ERROR_TYPE_ANY;
1045 if(p2==NULL) return ASN_DER_ERROR;
1048 if(type_field(p->type)==TYPE_CHOICE){
1050 ris=_asn1_extract_tag_der(p->down,der+counter,&len2);
1052 while(p->down->right) asn1_delete_structure(p->down->right);
1055 else if(ris==ASN_ERROR_TYPE_ANY) return ASN_ERROR_TYPE_ANY;
1056 else asn1_delete_structure(p->down);
1058 if(p->down==NULL) return ASN_DER_ERROR;
1062 if((p->type&CONST_OPTION) || (p->type&CONST_DEFAULT)){
1063 p2=_asn1_find_up(p);
1064 len2=strtol(p2->value,NULL,10);
1065 if(counter>=len2) ris=ASN_TAG_ERROR;
1068 if(ris==ASN_OK) ris=_asn1_extract_tag_der(p,der+counter,&len2);
1070 //if(ris==ASN_ERROR_TYPE_ANY) return ASN_ERROR_TYPE_ANY;
1071 if(p->type&CONST_OPTION){
1072 p->type|=CONST_NOT_USED;
1075 else if(p->type&CONST_DEFAULT) {
1076 _asn1_set_value(p,NULL,0);
1080 //return (type_field(p->type)!=TYPE_ANY)?ASN_TAG_ERROR:ASN_ERROR_TYPE_ANY;
1081 return ASN_TAG_ERROR;
1088 switch(type_field(p->type)){
1090 if(der[counter]) return ASN_DER_ERROR;
1095 if(der[counter++]!=1) return ASN_DER_ERROR;
1096 if(der[counter++]==0) _asn1_set_value(p,"F",1);
1097 else _asn1_set_value(p,"T",1);
1100 case TYPE_INTEGER: case TYPE_ENUMERATED:
1101 len2=_asn1_get_length_der(der+counter,&len3);
1102 _asn1_set_value(p,der+counter,len3+len2);
1106 case TYPE_OBJECT_ID:
1107 _asn1_get_objectid_der(der+counter,&len2, temp, sizeof(temp));
1108 _asn1_set_value(p,temp,strlen(temp)+1);
1113 _asn1_get_time_der(der+counter,&len2,temp);
1114 _asn1_set_value(p,temp,strlen(temp)+1);
1118 case TYPE_OCTET_STRING:
1119 len2=_asn1_get_length_der(der+counter,&len3);
1120 _asn1_set_value(p,der+counter,len3+len2);
1124 case TYPE_BIT_STRING:
1125 len2=_asn1_get_length_der(der+counter,&len3);
1126 _asn1_set_value(p,der+counter,len3+len2);
1130 case TYPE_SEQUENCE: case TYPE_SET:;
1132 len2=strtol(p->value,NULL,10);
1133 _asn1_set_value(p,NULL,0);
1134 if(len2!=counter) return ASN_DER_ERROR;
1137 else{ /* move==DOWN || move==RIGHT */
1138 len3=_asn1_get_length_der(der+counter,&len2);
1140 _asn1_ltostr(counter+len3,temp);
1141 _asn1_set_value(p,temp,strlen(temp)+1);
1145 case TYPE_SEQUENCE_OF: case TYPE_SET_OF:
1147 len2=strtol(p->value,NULL,10);
1149 _asn1_append_sequence_set(p);
1151 while(p->right) p=p->right;
1155 _asn1_set_value(p,NULL,0);
1156 if(len2!=counter) return ASN_DER_ERROR;
1158 else{ /* move==DOWN || move==RIGHT */
1159 len3=_asn1_get_length_der(der+counter,&len2);
1162 _asn1_ltostr(counter+len3,temp);
1163 _asn1_set_value(p,temp,strlen(temp)+1);
1165 while((type_field(p2->type)==TYPE_TAG) || (type_field(p2->type)==TYPE_SIZE)) p2=p2->right;
1166 if(p2->right==NULL) _asn1_append_sequence_set(p);
1173 tag=_asn1_get_tag_der(der+counter,&class,&len2);
1174 len2+=_asn1_get_length_der(der+counter+len2,&len3);
1175 _asn1_length_der(len2+len3,NULL,&len4);
1176 temp2=(unsigned char *)_asn1_alloca(len2+len3+len4);
1177 if (temp2==NULL) return ASN_MEM_ERROR;
1179 _asn1_octet_der(der+counter,len2+len3,temp2,&len4);
1180 _asn1_set_value(p,temp2,len4);
1186 move=(move==UP)?RIGHT:DOWN;
1191 if(p==node && move!=DOWN) break;
1194 if(p->down) p=p->down;
1197 if((move==RIGHT) && !(p->type&CONST_SET)){
1198 if(p->right) p=p->right;
1201 if(move==UP) p=_asn1_find_up(p);
1204 _asn1_delete_not_used(root);
1206 return (counter==len)?ASN_OK:ASN_DER_ERROR;
1211 * asn1_get_start_end_der - Find the start and end point of an element in a DER encoding string.
1212 * @root: pointer to a structure
1213 * @der: vector that contains the DER encoding.
1214 * @len: number of bytes of *der: der[0]..der[len-1]
1215 * @name_element: an element of NAME structure.
1216 * @start: the position of the first byte of NAME_ELEMENT decoding (der[*start])
1217 * @end: the position of the last byte of NAME_ELEMENT decoding (der[*end])
1220 * Find the start and end point of an element in a DER encoding string. I mean that if you
1221 * have a der encoding and you have already used the function "get_der" to fill a structure, it may
1222 * happen that you want to find the piece of string concerning an element of the structure.
1224 * Example: the sequence "tbsCertificate" inside an X509 certificate.
1228 * ASN_OK\: DER encoding OK
1230 * ASN_ELEMENT_NOT_FOUND\: NAME or NAME_ELEMENT is not a valid element.
1232 * ASN_TAG_ERROR,ASN_DER_ERROR\: the der encoding doesn't match the structure NAME.
1236 asn1_get_start_end_der(node_asn *root,unsigned char *der,int len,char *name_element,int *start, int *end)
1238 node_asn *node,*node_to_find,*p,*p2,*p3;
1239 int counter,len2,len3,move,ris;
1240 unsigned char class;
1244 node_to_find=_asn1_find_node(root,name_element);
1246 if(node_to_find==NULL) return ASN_ELEMENT_NOT_FOUND;
1248 if(node_to_find==node){
1254 if(node==NULL) return ASN_ELEMENT_NOT_FOUND;
1256 if(node->type&CONST_OPTION) return ASN_GENERIC_ERROR;
1265 if(p->type&CONST_SET){
1266 p2=_asn1_find_up(p);
1267 len2=strtol(p2->value,NULL,10);
1273 else if(counter>len2) return ASN_DER_ERROR;
1276 if((p2->type&CONST_SET) && (p2->type&CONST_NOT_USED)){ /* CONTROLLARE */
1277 if(type_field(p2->type)!=TYPE_CHOICE)
1278 ris=_asn1_extract_tag_der(p2,der+counter,&len2);
1281 ris=_asn1_extract_tag_der(p3,der+counter,&len2);
1284 p2->type&=~CONST_NOT_USED;
1291 if(p2==NULL) return ASN_DER_ERROR;
1294 if(p==node_to_find) *start=counter;
1296 if(type_field(p->type)==TYPE_CHOICE){
1298 ris=_asn1_extract_tag_der(p,der+counter,&len2);
1299 if(p==node_to_find) *start=counter;
1302 if(ris==ASN_OK) ris=_asn1_extract_tag_der(p,der+counter,&len2);
1304 if(p->type&CONST_OPTION){
1305 p->type|=CONST_NOT_USED;
1308 else if(p->type&CONST_DEFAULT) {
1312 return ASN_TAG_ERROR;
1319 switch(type_field(p->type)){
1321 if(der[counter]) return ASN_DER_ERROR;
1326 if(der[counter++]!=1) return ASN_DER_ERROR;
1330 case TYPE_INTEGER: case TYPE_ENUMERATED:
1331 len2=_asn1_get_length_der(der+counter,&len3);
1335 case TYPE_OBJECT_ID:
1336 len2=_asn1_get_length_der(der+counter,&len3);
1341 len2=_asn1_get_length_der(der+counter,&len3);
1345 case TYPE_OCTET_STRING:
1346 len2=_asn1_get_length_der(der+counter,&len3);
1350 case TYPE_BIT_STRING:
1351 len2=_asn1_get_length_der(der+counter,&len3);
1355 case TYPE_SEQUENCE: case TYPE_SET:
1357 len3=_asn1_get_length_der(der+counter,&len2);
1363 case TYPE_SEQUENCE_OF: case TYPE_SET_OF:
1365 len3=_asn1_get_length_der(der+counter,&len2);
1369 while((type_field(p2->type)==TYPE_TAG) ||
1370 (type_field(p2->type)==TYPE_SIZE)) p2=p2->right;
1377 tag=_asn1_get_tag_der(der+counter,&class,&len2);
1378 len2+=_asn1_get_length_der(der+counter+len2,&len3);
1383 move=(move==UP)?RIGHT:DOWN;
1388 if((p==node_to_find) && (move==RIGHT)){
1393 if(p==node && move!=DOWN) break;
1396 if(p->down) p=p->down;
1399 if((move==RIGHT) && !(p->type&CONST_SET)){
1400 if(p->right) p=p->right;
1403 if(move==UP) p=_asn1_find_up(p);
1406 return ASN_ELEMENT_NOT_FOUND;