Sourcecode and documentation for libtasn1-2 version 0.2.10-3sarge1
show bar | Show file versions
Search packages:
| Sourcecode archive home

structure.c

00001 /*
00002  *      Copyright (C) 2002  Fabio Fiorina
00003  *
00004  * This file is part of LIBASN1.
00005  *
00006  * The LIBTASN1 library is free software; you can redistribute it and/or
00007  * modify it under the terms of the GNU Lesser General Public   
00008  * License as published by the Free Software Foundation; either 
00009  * version 2.1 of the License, or (at your option) any later version.
00010  *
00011  * This library is distributed in the hope that it will be useful,
00012  * but WITHOUT ANY WARRANTY; without even the implied warranty of 
00013  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
00014  * Lesser General Public License for more details.
00015  *
00016  * You should have received a copy of the GNU Lesser General Public
00017  * License along with this library; if not, write to the Free Software
00018  * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307  USA
00019  */
00020 
00021 
00022 /*****************************************************/
00023 /* File: structure.c                                 */
00024 /* Description: Functions to create and delete an    */
00025 /*  ASN1 tree.                                       */
00026 /*****************************************************/
00027 
00028 
00029 #include <int.h>
00030 #include <errors.h>
00031 #include <structure.h>
00032 #include "parser_aux.h"
00033 #include "der.h"
00034 #include <gstr.h>
00035 
00036 
00037 extern char _asn1_identifierMissing[];
00038 
00039 
00040 /******************************************************/
00041 /* Function : _asn1_add_node_only                     */
00042 /* Description: creates a new NODE_ASN element.       */ 
00043 /* Parameters:                                        */
00044 /*   type: type of the new element (see TYPE_         */
00045 /*         and CONST_ constants).                     */
00046 /* Return: pointer to the new element.                */
00047 /******************************************************/
00048 node_asn *
00049 _asn1_add_node_only(unsigned int type)
00050 {
00051   node_asn *punt;
00052 
00053   punt=(node_asn *) _asn1_malloc(sizeof(node_asn));
00054   if (punt==NULL) return NULL;
00055   
00056   punt->left=NULL;
00057   punt->name=NULL;
00058   punt->type=type; 
00059   punt->value=NULL;
00060   punt->down=NULL;
00061   punt->right=NULL; 
00062 
00063   return punt;
00064 }
00065 
00066 
00067 /******************************************************************/
00068 /* Function : _asn1_find_left                                     */
00069 /* Description: returns the NODE_ASN element with RIGHT field that*/
00070 /*              points the element NODE.                          */
00071 /* Parameters:                                                    */
00072 /*   node: NODE_ASN element pointer.                              */
00073 /* Return: NULL if not found.                                     */
00074 /******************************************************************/
00075 node_asn *
00076 _asn1_find_left(node_asn *node)
00077 {
00078   if((node==NULL) || (node->left==NULL) || 
00079      (node->left->down==node)) return NULL;
00080 
00081   return node->left;  
00082 }
00083 
00084 
00085 asn1_retCode
00086 _asn1_create_static_structure(ASN1_TYPE pointer,char* output_file_name,char *vector_name)
00087 {
00088   FILE *file;  
00089   node_asn *p;
00090   unsigned long t;
00091 
00092   file=fopen( output_file_name,"w");
00093   
00094   if(file==NULL) return ASN1_FILE_NOT_FOUND;
00095 
00096   fprintf(file,"\n#include \"libtasn1.h\"\n\n");
00097   fprintf(file,"const ASN1_ARRAY_TYPE %s[]={\n",vector_name);
00098 
00099   p=pointer;
00100 
00101   while(p){
00102     fprintf(file,"  {");
00103 
00104     if(p->name) fprintf(file,"\"%s\",",p->name);
00105     else fprintf(file,"0,");
00106     
00107    t=p->type;
00108    if(p->down) t|=CONST_DOWN;
00109    if(p->right) t|=CONST_RIGHT;
00110    
00111    fprintf(file,"%lu,",t);
00112    
00113    if(p->value) fprintf(file,"\"%s\"},\n",p->value);
00114    else fprintf(file,"0},\n");
00115 
00116    if(p->down){
00117      p=p->down;
00118    }
00119    else if(p->right){
00120      p=p->right;
00121    }
00122    else{
00123      while(1){
00124        p=_asn1_find_up(p);
00125        if(p==pointer){
00126        p=NULL;
00127        break;
00128        }
00129        if(p->right){
00130        p=p->right;
00131        break;
00132        }
00133      }
00134    }
00135  }
00136 
00137  fprintf(file,"  {0,0,0}\n};\n");
00138 
00139  fclose(file);
00140 
00141  return ASN1_SUCCESS;
00142 }
00143 
00144 
00145 /**
00146   * asn1_array2tree - Creates the structures needed to manage the ASN1 definitions.
00147   * @array: specify the array that contains ASN.1 declarations
00148   * @definitions: return the pointer to the structure created by *ARRAY ASN.1 declarations
00149   * @errorDescription : return the error description.
00150   * Description:
00151   *
00152   * Creates the structures needed to manage the ASN1 definitions. ARRAY is a vector created by
00153   * 'asn1_parser_asn1_file_c' function.
00154   *
00155   * Returns:
00156   *
00157   *  ASN1_SUCCESS\: structure created correctly. 
00158   *
00159   * ASN1_ELEMENT_NOT_EMPTY\: *DEFINITIONS not ASN1_TYPE_EMPTY
00160   *
00161   * ASN1_IDENTIFIER_NOT_FOUND\: in the file there is an identifier that is not defined (see ERRORDESCRIPTION for more information).
00162   *
00163   *  ASN1_ARRAY_ERROR\: the array pointed by ARRAY is wrong.  
00164   **/
00165 asn1_retCode
00166 asn1_array2tree(const ASN1_ARRAY_TYPE *array,ASN1_TYPE *definitions,
00167                  char *errorDescription)
00168 {
00169   node_asn *p,*p_last=NULL;
00170   unsigned long k;
00171   int move;
00172   asn1_retCode result;
00173 
00174 
00175   if(*definitions != ASN1_TYPE_EMPTY)
00176     return ASN1_ELEMENT_NOT_EMPTY;
00177 
00178   move=UP;
00179 
00180   k=0;
00181   while(array[k].value || array[k].type || array[k].name){
00182     p=_asn1_add_node(array[k].type&(~CONST_DOWN));
00183     if(array[k].name) _asn1_set_name(p,array[k].name);
00184     if(array[k].value) _asn1_set_value(p,array[k].value,
00185                                        strlen(array[k].value)+1);
00186 
00187     if(*definitions==NULL) *definitions=p;
00188 
00189     if(move==DOWN) _asn1_set_down(p_last,p);
00190     else if(move==RIGHT) _asn1_set_right(p_last,p);
00191 
00192     p_last=p;
00193 
00194     if(array[k].type&CONST_DOWN) move=DOWN;
00195     else if(array[k].type&CONST_RIGHT) move=RIGHT;
00196     else{
00197       while(1){
00198       if(p_last==*definitions) break;
00199    
00200       p_last= _asn1_find_up(p_last);
00201 
00202       if(p_last==NULL) break;
00203 
00204       if(p_last->type&CONST_RIGHT){
00205         p_last->type&=~CONST_RIGHT;
00206         move=RIGHT;
00207         break;
00208       }
00209       }  /* while */
00210     }
00211     k++;
00212   }  /* while */
00213 
00214   if(p_last==*definitions){
00215     result=_asn1_check_identifier(*definitions);
00216     if(result==ASN1_SUCCESS){
00217       _asn1_change_integer_value(*definitions);
00218       _asn1_expand_object_id(*definitions);
00219     }
00220   }
00221   else{
00222     result=ASN1_ARRAY_ERROR;
00223   }
00224 
00225   if (errorDescription!=NULL) {
00226    if(result==ASN1_IDENTIFIER_NOT_FOUND) {
00227      Estrcpy(errorDescription,":: identifier '");
00228      Estrcat(errorDescription,_asn1_identifierMissing);
00229      Estrcat(errorDescription,"' not found");
00230    }
00231    else
00232      errorDescription[0]=0;
00233   }
00234   
00235   if(result != ASN1_SUCCESS){
00236     _asn1_delete_list_and_nodes();
00237     *definitions=ASN1_TYPE_EMPTY;
00238   }
00239   else
00240     _asn1_delete_list();
00241 
00242   return result;
00243 }
00244 
00245 
00246 /**
00247   * asn1_delete_structure - Deletes the structure pointed by *ROOT. 
00248   * @structure: pointer to the structure that you want to delete.
00249   * Description:
00250   * 
00251   * Deletes the structure *ROOT. 
00252   * At the end *ROOT is setted to ASN1_TYPE_EMPTY. 
00253   * 
00254   * Returns:
00255   *
00256   *   ASN1_SUCCESS\: everything OK
00257   *
00258   *   ASN1_ELEMENT_NOT_FOUND\: *root==ASN1_TYPE_EMPTY.
00259   *
00260   **/
00261 asn1_retCode
00262 asn1_delete_structure(ASN1_TYPE *structure)
00263 {
00264   node_asn *p,*p2,*p3;
00265 
00266   if(*structure==ASN1_TYPE_EMPTY) return ASN1_ELEMENT_NOT_FOUND;
00267 
00268   p=*structure;
00269   while(p){
00270     if(p->down){
00271       p=p->down;
00272     }
00273     else{   /* no down */
00274       p2=p->right;
00275       if(p!=*structure){
00276       p3=_asn1_find_up(p);
00277       _asn1_set_down(p3,p2);
00278       _asn1_remove_node(p);
00279       p=p3;
00280       }
00281       else{   /* p==root */
00282       p3=_asn1_find_left(p);
00283       if(!p3){
00284         p3=_asn1_find_up(p);
00285         if(p3) _asn1_set_down(p3,p2);
00286         else{
00287           if(p->right) p->right->left=NULL;
00288         }
00289       }
00290       else _asn1_set_right(p3,p2);
00291       _asn1_remove_node(p);
00292       p=NULL;
00293       }
00294     }
00295   }
00296 
00297   *structure=ASN1_TYPE_EMPTY;
00298   return ASN1_SUCCESS;
00299 }
00300 
00301 
00302 /**
00303   * asn1_delete_element - Deletes the element of a structure. 
00304   * @structure: pointer to the structure that contains the element you want to delete.
00305   * @element_name: element's name you want to delete.
00306   * Description:
00307   * 
00308   * Deletes the element named *element_name inside *structure. 
00309   *
00310   * Returns:
00311   *
00312   *   ASN1_SUCCESS\: everything OK
00313   *
00314   *   ASN1_ELEMENT_NOT_FOUND
00315   *
00316   **/
00317 asn1_retCode
00318 asn1_delete_element(ASN1_TYPE structure,const char *element_name)
00319 {
00320   node_asn *p2,*p3,*source_node;
00321 
00322   source_node=_asn1_find_node(structure,element_name);
00323 
00324   if(source_node==ASN1_TYPE_EMPTY) return ASN1_ELEMENT_NOT_FOUND;
00325 
00326   p2=source_node->right;
00327   p3=_asn1_find_left(source_node);
00328   if(!p3){
00329     p3=_asn1_find_up(source_node);
00330     if(p3) 
00331       _asn1_set_down(p3,p2);
00332     else
00333       if(source_node->right) source_node->right->left=NULL;
00334   }
00335   else _asn1_set_right(p3,p2);
00336 
00337   return asn1_delete_structure(&source_node);
00338 }
00339 
00340 
00341 node_asn *
00342 _asn1_copy_structure3(node_asn *source_node)
00343 {
00344   node_asn *dest_node,*p_s,*p_d,*p_d_prev;
00345   int len,len2,move;
00346 
00347   if(source_node==NULL) return NULL;
00348 
00349   dest_node=_asn1_add_node_only(source_node->type);
00350 
00351   p_s=source_node;
00352   p_d=dest_node;
00353 
00354   move=DOWN;
00355 
00356   do{
00357     if(move!=UP){
00358       if(p_s->name) _asn1_set_name(p_d,p_s->name);
00359       if(p_s->value){
00360       switch(type_field(p_s->type)){
00361       case TYPE_OCTET_STRING: case TYPE_BIT_STRING: case TYPE_GENERALSTRING: 
00362       case TYPE_INTEGER:    
00363         len2=-1;
00364         len=_asn1_get_length_der(p_s->value,p_s->value_len,&len2);
00365         if (len < 0) return NULL;
00366         _asn1_set_value(p_d,p_s->value,len+len2);
00367         break;
00368       default:
00369         _asn1_set_value(p_d,p_s->value,strlen(p_s->value)+1);
00370       }
00371       }
00372       move=DOWN;
00373     }
00374     else move=RIGHT;
00375 
00376     if(move==DOWN){
00377       if(p_s->down){
00378       p_s=p_s->down;
00379       p_d_prev=p_d;      
00380       p_d=_asn1_add_node_only(p_s->type);
00381       _asn1_set_down(p_d_prev,p_d);
00382       }
00383       else move=RIGHT;
00384     }
00385   
00386     if(p_s==source_node) break;
00387 
00388     if(move==RIGHT){
00389       if(p_s->right){
00390       p_s=p_s->right;
00391       p_d_prev=p_d;
00392       p_d=_asn1_add_node_only(p_s->type);
00393       _asn1_set_right(p_d_prev,p_d);
00394       }
00395       else move=UP;
00396     }
00397     if(move==UP){
00398       p_s=_asn1_find_up(p_s);
00399       p_d=_asn1_find_up(p_d);
00400     }
00401   }while(p_s!=source_node);
00402 
00403   return dest_node;
00404 }
00405 
00406 
00407 node_asn *
00408 _asn1_copy_structure2(node_asn *root,const char *source_name)
00409 {
00410   node_asn *source_node;
00411 
00412   source_node=_asn1_find_node(root,source_name);
00413   
00414   return _asn1_copy_structure3(source_node);
00415 
00416 }
00417 
00418 
00419 asn1_retCode 
00420 _asn1_type_choice_config(node_asn *node)
00421 {
00422   node_asn *p,*p2,*p3,*p4;
00423   int move;
00424  
00425   if(node==NULL) return ASN1_ELEMENT_NOT_FOUND;
00426 
00427   p=node;
00428   move=DOWN;
00429 
00430   while(!((p==node) && (move==UP))){
00431     if(move!=UP){
00432       if((type_field(p->type)==TYPE_CHOICE) &&
00433        (p->type&CONST_TAG)){
00434       p2=p->down;
00435       while(p2){
00436         if(type_field(p2->type)!=TYPE_TAG){
00437           p2->type|=CONST_TAG;
00438           p3=_asn1_find_left(p2);
00439           while(p3){
00440             if(type_field(p3->type)==TYPE_TAG){
00441             p4=_asn1_add_node_only(p3->type);
00442             _asn1_set_value(p4,p3->value,strlen(p3->value)+1);
00443             _asn1_set_right(p4,p2->down);
00444             _asn1_set_down(p2,p4);
00445             }
00446             p3=_asn1_find_left(p3);
00447           }
00448         }
00449         p2=p2->right;
00450       }
00451       p->type&=~(CONST_TAG);
00452       p2=p->down;
00453       while(p2){
00454         p3=p2->right;
00455         if(type_field(p2->type)==TYPE_TAG) asn1_delete_structure(&p2);
00456         p2=p3;
00457       }
00458       }
00459       move=DOWN;
00460     }
00461     else move=RIGHT;
00462     
00463     if(move==DOWN){
00464       if(p->down) p=p->down;
00465       else move=RIGHT;
00466     }
00467     
00468     if(p==node) {move=UP; continue;}
00469     
00470     if(move==RIGHT){
00471       if(p->right) p=p->right;
00472       else move=UP;
00473     }
00474     if(move==UP) p=_asn1_find_up(p);
00475   }
00476   
00477   return ASN1_SUCCESS;
00478 }
00479 
00480 
00481 asn1_retCode 
00482 _asn1_expand_identifier(node_asn **node,node_asn *root)
00483 {
00484   node_asn *p,*p2,*p3;
00485   char name2[MAX_NAME_SIZE+2];
00486   int move;
00487  
00488   if(node==NULL) return ASN1_ELEMENT_NOT_FOUND;
00489 
00490   p=*node;
00491   move=DOWN;
00492 
00493   while(!((p==*node) && (move==UP))){
00494     if(move!=UP){
00495       if(type_field(p->type)==TYPE_IDENTIFIER){
00496       _asn1_str_cpy(name2, sizeof(name2), root->name);
00497       _asn1_str_cat(name2, sizeof(name2), ".");
00498       _asn1_str_cat(name2, sizeof(name2), p->value);
00499       p2=_asn1_copy_structure2(root,name2);
00500       if(p2==NULL){
00501         return ASN1_IDENTIFIER_NOT_FOUND;
00502       }
00503       _asn1_set_name(p2,p->name);
00504       p2->right=p->right;
00505       p2->left=p->left;
00506       if(p->right) p->right->left=p2;
00507       p3=p->down;
00508       if(p3){
00509         while(p3->right) p3=p3->right;
00510         _asn1_set_right(p3,p2->down);
00511         _asn1_set_down(p2,p->down);
00512       }
00513       
00514       p3=_asn1_find_left(p);
00515       if(p3) _asn1_set_right(p3,p2);
00516       else{
00517         p3=_asn1_find_up(p);
00518         if(p3) _asn1_set_down(p3,p2);
00519         else {
00520           p2->left=NULL;
00521         }
00522       }
00523 
00524       if(p->type & CONST_SIZE) p2->type|=CONST_SIZE;
00525       if(p->type & CONST_TAG) p2->type|=CONST_TAG;
00526       if(p->type & CONST_OPTION) p2->type|=CONST_OPTION;
00527       if(p->type & CONST_DEFAULT) p2->type|=CONST_DEFAULT;
00528       if(p->type & CONST_SET) p2->type|=CONST_SET;
00529       if(p->type & CONST_NOT_USED) p2->type|=CONST_NOT_USED;
00530 
00531       if(p==*node) *node=p2;
00532       _asn1_remove_node(p);
00533       p=p2;
00534       move=DOWN;
00535       continue;
00536       }
00537       move=DOWN;
00538     }
00539     else move=RIGHT;
00540     
00541     if(move==DOWN){
00542       if(p->down) p=p->down;
00543       else move=RIGHT;
00544     }
00545     
00546     if(p==*node) {move=UP; continue;}
00547     
00548     if(move==RIGHT){
00549       if(p->right) p=p->right;
00550       else move=UP;
00551     }
00552     if(move==UP) p=_asn1_find_up(p);
00553   }
00554 
00555   return ASN1_SUCCESS;
00556 }
00557 
00558 
00559 /**
00560   * asn1_create_element - Creates a structure of type SOURCE_NAME.
00561   * @definitions: pointer to the structure returned by "parser_asn1" function 
00562   * @source_name: the name of the type of the new structure (must be inside p_structure).
00563   * @element: pointer to the structure created. 
00564   * Description:
00565   *
00566   * Creates a structure called DEST_NAME of type SOURCE_NAME.
00567   *
00568   * Returns:
00569   *
00570   *  ASN1_SUCCESS\: creation OK
00571   *
00572   *  ASN1_ELEMENT_NOT_FOUND\: SOURCE_NAME isn't known
00573   * 
00574   * Example: using "pkix.asn"
00575   *  result=asn1_create_structure(cert_def,"PKIX1.Certificate",&cert);
00576   **/
00577 asn1_retCode
00578 asn1_create_element(ASN1_TYPE definitions,const char *source_name,
00579                 ASN1_TYPE *element)
00580 {
00581   node_asn *dest_node;
00582   int res;
00583 
00584   dest_node=_asn1_copy_structure2(definitions,source_name);
00585  
00586   if(dest_node==NULL) return ASN1_ELEMENT_NOT_FOUND;
00587 
00588   _asn1_set_name(dest_node,"");
00589 
00590   res=_asn1_expand_identifier(&dest_node,definitions);
00591   _asn1_type_choice_config(dest_node);
00592 
00593   *element=dest_node;
00594 
00595   return res;
00596 }
00597 
00598 
00599 /**
00600   * asn1_print_structure - Prints on the standard output the structure's tree
00601   * @out: pointer to the output file (e.g. stdout).
00602   * @structure: pointer to the structure that you want to visit.
00603   * @name: an element of the structure
00604   * 
00605   * Prints on the standard output the structure's tree starting from the NAME element inside
00606   * the structure *POINTER. 
00607   **/
00608 void
00609 asn1_print_structure(FILE *out,ASN1_TYPE structure,const char *name,int mode)
00610 {
00611   node_asn *p,*root;
00612   int k,indent=0,len,len2,len3;
00613 
00614   if(out==NULL) return;
00615 
00616   root=_asn1_find_node(structure,name);   
00617 
00618   if(root==NULL) return;
00619 
00620   p=root;
00621   while(p){
00622     if(mode == ASN1_PRINT_ALL){
00623       for(k=0;k<indent;k++)fprintf(out," ");
00624       fprintf(out,"name:");
00625       if(p->name) fprintf(out,"%s  ",p->name);
00626       else fprintf(out,"NULL  ");
00627     }
00628     else{
00629       switch(type_field(p->type)){
00630       case TYPE_CONSTANT:
00631       case TYPE_TAG:
00632       case TYPE_SIZE:
00633       break;
00634       default:
00635       for(k=0;k<indent;k++)fprintf(out," ");
00636       fprintf(out,"name:");
00637       if(p->name) fprintf(out,"%s  ",p->name);
00638       else fprintf(out,"NULL  ");
00639       }
00640     }
00641 
00642     if(mode != ASN1_PRINT_NAME){
00643       switch(type_field(p->type)){
00644       case TYPE_CONSTANT:
00645       if(mode == ASN1_PRINT_ALL)
00646         fprintf(out,"type:CONST");break;
00647       case TYPE_TAG:
00648       if(mode == ASN1_PRINT_ALL)
00649         fprintf(out,"type:TAG");break;
00650       case TYPE_SIZE:
00651       if(mode == ASN1_PRINT_ALL)
00652         fprintf(out,"type:SIZE");break;
00653       case TYPE_DEFAULT:
00654       fprintf(out,"type:DEFAULT");break;
00655       case TYPE_NULL:
00656       fprintf(out,"type:NULL");break;
00657       case TYPE_IDENTIFIER:
00658       fprintf(out,"type:IDENTIFIER");break;
00659       case TYPE_INTEGER:
00660       fprintf(out,"type:INTEGER");break;
00661       case TYPE_ENUMERATED:
00662       fprintf(out,"type:ENUMERATED");break;
00663       case TYPE_TIME:
00664       fprintf(out,"type:TIME");break;
00665       case TYPE_BOOLEAN:
00666       fprintf(out,"type:BOOLEAN");break;
00667       case TYPE_SEQUENCE:
00668       fprintf(out,"type:SEQUENCE");break;
00669       case TYPE_BIT_STRING:
00670       fprintf(out,"type:BIT_STR");break;
00671       case TYPE_OCTET_STRING:
00672       fprintf(out,"type:OCT_STR");break;
00673       case TYPE_GENERALSTRING:
00674       fprintf(out,"type:GENERALSTRING");break;
00675       case TYPE_SEQUENCE_OF:
00676       fprintf(out,"type:SEQ_OF");break;
00677       case TYPE_OBJECT_ID:
00678       fprintf(out,"type:OBJ_ID");break;
00679       case TYPE_ANY:
00680       fprintf(out,"type:ANY");break;
00681       case TYPE_SET:
00682       fprintf(out,"type:SET");break;
00683       case TYPE_SET_OF:
00684       fprintf(out,"type:SET_OF");break;
00685       case TYPE_CHOICE:
00686       fprintf(out,"type:CHOICE");break;
00687       case TYPE_DEFINITIONS:
00688       fprintf(out,"type:DEFINITIONS");break;
00689       default:
00690       break;
00691       }
00692     }
00693 
00694     if((mode == ASN1_PRINT_NAME_TYPE_VALUE) ||
00695        (mode == ASN1_PRINT_ALL)){
00696       switch(type_field(p->type)){
00697       case TYPE_CONSTANT:
00698       if(mode == ASN1_PRINT_ALL)
00699         if(p->value) fprintf(out,"  value:%s",p->value);
00700       break;
00701       case TYPE_TAG:
00702       if(mode == ASN1_PRINT_ALL)
00703         if (p->value) fprintf(out,"  value:%s",p->value);
00704       break;
00705       case TYPE_SIZE:
00706       if(mode == ASN1_PRINT_ALL)
00707         if(p->value) fprintf(out,"  value:%s",p->value);
00708       break;
00709       case TYPE_DEFAULT:
00710       if(p->value) fprintf(out,"  value:%s",p->value);
00711       else if(p->type & CONST_TRUE)  fprintf(out,"  value:TRUE");
00712       else if(p->type & CONST_FALSE) fprintf(out,"  value:FALSE");
00713       break;
00714       case TYPE_IDENTIFIER:
00715       if(p->value) fprintf(out,"  value:%s",p->value);
00716       break;
00717       case TYPE_INTEGER:
00718       if(p->value){
00719         len2=-1;
00720         len=_asn1_get_length_der(p->value,p->value_len,&len2);
00721         fprintf(out,"  value:0x");
00722         if (len > 0)
00723           for(k=0;k<len;k++) fprintf(out,"%02x",(p->value)[k+len2]);
00724       }
00725       break;
00726       case TYPE_ENUMERATED:
00727       if(p->value){
00728         len2=-1;
00729         len=_asn1_get_length_der(p->value,p->value_len,&len2);
00730         fprintf(out,"  value:0x");
00731         if (len > 0)
00732           for(k=0;k<len;k++) fprintf(out,"%02x",(p->value)[k+len2]);
00733       }
00734       break;
00735       case TYPE_TIME:
00736       if(p->value) fprintf(out,"  value:%s",p->value);
00737       break;
00738       case TYPE_BOOLEAN:
00739       if(p->value){
00740         if(p->value[0]=='T') fprintf(out,"  value:TRUE");
00741         else if(p->value[0]=='F') fprintf(out,"  value:FALSE");
00742       }
00743       break;
00744       case TYPE_BIT_STRING:
00745       if(p->value){
00746         len2=-1;
00747         len=_asn1_get_length_der(p->value,p->value_len,&len2);
00748         if (len>0)
00749           {
00750             fprintf(out,"  value(%i):",(len-1)*8-(p->value[len2]));
00751             for(k=1;k<len;k++) fprintf(out,"%02x",(p->value)[k+len2]);
00752           }
00753       }
00754       break;
00755       case TYPE_OCTET_STRING:
00756       if(p->value){
00757         len2=-1;
00758         len=_asn1_get_length_der(p->value,p->value_len,&len2);
00759         fprintf(out,"  value:");
00760         if (len>0)
00761           for(k=0;k<len;k++) fprintf(out,"%02x",(p->value)[k+len2]);
00762       }
00763       break;
00764       case TYPE_GENERALSTRING:
00765       if(p->value){
00766         len2=-1;
00767         len=_asn1_get_length_der(p->value,p->value_len,&len2);
00768         fprintf(out,"  value:");
00769         if (len>0)
00770           for(k=0;k<len;k++) fprintf(out,"%02x",(p->value)[k+len2]);
00771       }
00772       break;
00773       case TYPE_OBJECT_ID:
00774       if(p->value) fprintf(out,"  value:%s",p->value);
00775       break;
00776       case TYPE_ANY:
00777       if(p->value){
00778         len3=-1;
00779         len2=_asn1_get_length_der(p->value,p->value_len,&len3);
00780         fprintf(out,"  value:");
00781         if (len2>0)
00782           for(k=0;k<len2;k++) fprintf(out,"%02x",(p->value)[k+len3]);
00783       }
00784       break;
00785       case TYPE_SET:
00786       case TYPE_SET_OF:
00787       case TYPE_CHOICE:
00788       case TYPE_DEFINITIONS:
00789       case TYPE_SEQUENCE_OF:
00790       case TYPE_SEQUENCE:
00791       case TYPE_NULL:
00792       break;
00793       default:
00794       break;
00795       }
00796     }
00797 
00798     if(mode==ASN1_PRINT_ALL){
00799       if(p->type&0x1FFFFF00){
00800       fprintf(out,"  attr:");
00801       if(p->type & CONST_UNIVERSAL) fprintf(out,"UNIVERSAL,");
00802       if(p->type & CONST_PRIVATE) fprintf(out,"PRIVATE,");
00803       if(p->type & CONST_APPLICATION) fprintf(out,"APPLICATION,");
00804       if(p->type & CONST_EXPLICIT) fprintf(out,"EXPLICIT,");
00805       if(p->type & CONST_IMPLICIT) fprintf(out,"IMPLICIT,");
00806       if(p->type & CONST_TAG) fprintf(out,"TAG,");
00807       if(p->type & CONST_DEFAULT) fprintf(out,"DEFAULT,");
00808       if(p->type & CONST_TRUE) fprintf(out,"TRUE,");
00809       if(p->type & CONST_FALSE) fprintf(out,"FALSE,");
00810       if(p->type & CONST_LIST) fprintf(out,"LIST,");
00811       if(p->type & CONST_MIN_MAX) fprintf(out,"MIN_MAX,");
00812       if(p->type & CONST_OPTION) fprintf(out,"OPTION,");
00813       if(p->type & CONST_1_PARAM) fprintf(out,"1_PARAM,");
00814       if(p->type & CONST_SIZE) fprintf(out,"SIZE,");
00815       if(p->type & CONST_DEFINED_BY) fprintf(out,"DEF_BY,");
00816       if(p->type & CONST_GENERALIZED) fprintf(out,"GENERALIZED,");
00817       if(p->type & CONST_UTC) fprintf(out,"UTC,");
00818       if(p->type & CONST_SET) fprintf(out,"SET,");
00819       if(p->type & CONST_NOT_USED) fprintf(out,"NOT_USED,");
00820       if(p->type & CONST_ASSIGN) fprintf(out,"ASSIGNMENT,");
00821       }
00822     }
00823 
00824     if(mode == ASN1_PRINT_ALL){
00825       fprintf(out,"\n");
00826     }
00827     else{
00828       switch(type_field(p->type)){
00829       case TYPE_CONSTANT:
00830       case TYPE_TAG:
00831       case TYPE_SIZE:
00832       break;
00833       default:
00834       fprintf(out,"\n");
00835       }
00836     }
00837 
00838     if(p->down){
00839       p=p->down;
00840       indent+=2;
00841     }
00842     else if(p==root){
00843       p=NULL;
00844       break;
00845     }
00846     else if(p->right) p=p->right;
00847     else{
00848       while(1){
00849       p=_asn1_find_up(p);
00850       if(p==root){
00851         p=NULL;
00852         break;
00853       }
00854       indent-=2;
00855       if(p->right){
00856         p=p->right;
00857         break;
00858       }
00859       }
00860     }
00861   }
00862 }
00863 
00864 
00865 
00866 /**
00867   * asn1_number_of_elements - Counts the number of elements of a structure.
00868   * @element: pointer to the root of an ASN1 structure. 
00869   * @name: the name of a sub-structure of ROOT.
00870   * @num: pointer to an integer where the result will be stored 
00871   * Description:
00872   *
00873   * Counts the number of elements of a sub-structure called NAME with names equal to "?1","?2", ...
00874   *
00875   * Returns:
00876   *
00877   *  ASN1_SUCCESS\: creation OK
00878   *  ASN1_ELEMENT_NOT_FOUND\: NAME isn't known
00879   *  ASN1_GENERIC_ERROR\: pointer num equal to NULL
00880   *
00881   **/
00882 asn1_retCode 
00883 asn1_number_of_elements(ASN1_TYPE element,const char *name,int *num)
00884 {
00885   node_asn *node,*p;
00886 
00887   if(num==NULL) return ASN1_GENERIC_ERROR;
00888 
00889   *num=0;
00890 
00891   node=_asn1_find_node(element,name);
00892   if(node==NULL) return ASN1_ELEMENT_NOT_FOUND;
00893 
00894   p=node->down;
00895 
00896   while(p){
00897     if((p->name) && (p->name[0]=='?')) (*num)++; 
00898     p=p->right;
00899   }
00900 
00901   return ASN1_SUCCESS;
00902 }
00903 
00904 
00905 /**
00906   * asn1_find_structure_from_oid - Search the structure that is defined just
00907   * after an OID definition.
00908   * @definitions: ASN1 definitions
00909   * @oidValue: value of the OID to search (e.g. "1.2.3.4").
00910   * Description:
00911   *
00912   * Search the structure that is defined just after an OID definition.
00913   *
00914   * Returns:
00915   *
00916   *   NULL when OIDVALUE not found,
00917   *
00918   *   otherwise the pointer to a constant string that contains the element 
00919   *   name defined just after the OID.
00920   *
00921   **/
00922 const char*
00923 asn1_find_structure_from_oid(ASN1_TYPE definitions,
00924                          const char *oidValue)
00925 {
00926   char definitionsName[MAX_NAME_SIZE],name[2*MAX_NAME_SIZE+1];
00927   char value[MAX_NAME_SIZE];
00928   ASN1_TYPE p;
00929   int len;
00930   asn1_retCode result;
00931 
00932   if((definitions==ASN1_TYPE_EMPTY) || (oidValue==NULL))
00933     return NULL;  /* ASN1_ELEMENT_NOT_FOUND; */
00934 
00935 
00936   strcpy(definitionsName,definitions->name);
00937   strcat(definitionsName,".");
00938 
00939   /* search the OBJECT_ID into definitions */
00940   p=definitions->down;
00941   while(p){
00942     if((type_field(p->type)==TYPE_OBJECT_ID) &&
00943        (p->type & CONST_ASSIGN)){ 
00944       strcpy(name,definitionsName);
00945       strcat(name,p->name);
00946           
00947       len=MAX_NAME_SIZE;
00948       result=asn1_read_value(definitions,name,value,&len);
00949 
00950       if((result == ASN1_SUCCESS) && (!strcmp(oidValue,value))){
00951       p=p->right;
00952       if(p==NULL)  /* reach the end of ASN1 definitions */
00953         return NULL;   /* ASN1_ELEMENT_NOT_FOUND; */
00954       
00955       return p->name;
00956       }
00957     }
00958     p=p->right;
00959   }
00960 
00961   return NULL;  /* ASN1_ELEMENT_NOT_FOUND; */
00962 }
00963 
00964 
00965 
00966 
00967 

Generated by  Doxygen 1.5.1