From: Nikos Mavrogiannopoulos Date: Sat, 7 Jul 2001 18:03:47 +0000 (+0000) Subject: Updated ASN.1 Parser (Fabio - commited by me). X-Git-Tag: gnutls_0_1_9~63 X-Git-Url: http://git.ipfire.org/gitweb.cgi?a=commitdiff_plain;h=d45e5c2692b94fc7debd9cff199e12eaf6bb3792;p=thirdparty%2Fgnutls.git Updated ASN.1 Parser (Fabio - commited by me). --- diff --git a/NEWS b/NEWS index 59440bcf27..16abe5e92a 100644 --- a/NEWS +++ b/NEWS @@ -2,6 +2,7 @@ Version 0.1.5 - Corrected bug(s) in ChangeCipherSpec packet (fixes renegotiate) - SRP is updated to conform to the newest draft. - Added support for DNSNAME extension. +- Reentracy fixes in ASN.1 Parsing. Version 0.1.4 (22/06/2001) - Corrected (srp) base64 encoding. diff --git a/doc/ASN1.readme.txt b/doc/ASN1.readme.txt index 52c80ebdeb..97cec549e1 100644 --- a/doc/ASN1.readme.txt +++ b/doc/ASN1.readme.txt @@ -11,13 +11,14 @@ INTRODUCTION ------------ -This file wants to be only the first introduction to the parser I developed, that is also -in his first version. -So I ask you to let me know whether this kind of interface (software functions) is useful or not. -I know also that this is not the correct format for GNU documentation, but in this moment -I prefer to have a feedback as soon as possible. - -I forgot, thanks for your patience reading my 'black and white' writing (and speaking). +This file describes the second version of ASN.1 parser I developed. +The main difference from the previous version is the use of pointers. +Other differences are: +- write_value function for type ANY +- the introduction of ENUMERATED type, +- negative integer are allowed in ASN.1 syntax files, +- PKIX1Implicit88.txt instead of Certificate.txt for the Certificate description + FILE LIST @@ -26,13 +27,14 @@ ASN.readme.txt this file ASN.y bison input file ASN.tab.c bison output file CertificateExample.c example based on Appendix D.1 of rfc2459 +CrlExample.c example based on Appendix D.4 of rfc2459 gnutls_asn1.c functions for ASN1 parser and for reading and setting elements' value gnutls_asn1.h contains constants for the gnutls_asn1.c. Must be included in files that use ASN1 parser. gnutls_der.c functions for der encoding creation and analysis gnutls_der.h contains constants for the gnutls_der.c. Must be included in files that use ASN1 parser. -Certificate.txt certificate and CRL structures +PKIX1Implicit88.txt certificate and CRL structures Makefile how to create 'CertificateExample' @@ -56,10 +58,9 @@ The ASN.1 declarations must have this form: The token "::=" must be separate from others elements, so this is a wrong declaration: Version ::=INTEGER the correct one is : Version ::= INTEGER -In this parser is not possible to use negative numbers: - version INTEGER default -1 -- not allowed Here is the list of types that the parser can manage: INTEGER + ENUMERATED BOOLEAN OBJECT IDENTIFIER NULL @@ -74,7 +75,7 @@ Here is the list of types that the parser can manage: CHOICE ANY ANY DEFINED BY -This version doesn't manage REAL and ENUMERATED types. It also not allow the use of +This version doesn't manage REAL type. It also not allow the use of "EXPORT" and "IMPORT" sections. The SIZE constraints are allowed but no check is done on them. @@ -116,11 +117,14 @@ The name "?LAST" indicates the last element of a SET_OF or SEQUENCE_OF. FUNCTIONS --------- - int parser_asn1(char *file_name); + int parser_asn1(char *file_name,node_asn **pointer); -------------------------------- Creates the structures needed to manage the definitions included in *FILE_NAME file. -Input Parameters: +Input Parameter: char *file_name: specify the path and the name of file that contains ASN.1 declarations. +Output Parameter: + node_asn **pointer : return the pointer to the structure created from + "file_name" ASN.1 declarations. Return Value: ASN_OK: the file has a correct syntax and every identifier is known. ASN_FILE_NOT_FOUND: an error occured while opening FILE_NAME. @@ -128,25 +132,29 @@ Return Value: ASN_IDENTIFIER_NOT_FOUND: in the file there is an identifier that is not defined. - int create_structure(char *dest_name,char *source_name); + int create_structure(node_asn *p_structure,char *source_name,node_asn **pointer, + char *dest_name,); ------------------------------------------------------- Creates a structure called DEST_NAME of type SOURCE_NAME. Input Parameters: - char *dest_name: the name of the new structure. It must be different from any other structure - or type already created. - char *source_name: the name of the type to use to create the structure. + node_asn *p_structure: pointer to the structure returned by "parser_asn1" function + char *source_name: the name of the type of the new structure (must be inside p_structure). + char *dest_name: the name of the new structure. +Output Parameter: + node_asn **pointer : pointer to the structure created. Return Value: ASN_OK: creation OK ASN_ELEMENT_NOT_FOUND: SOURCE_NAME isn't known -Example: using "Certificate.txt" - result=create_structure("certificate1","PKIX1Explicit88.Certificate"); +Example: using "PKIX1Implicit88.txt" + result=create_structure(cert_def,"PKIX1Implicit88.Certificate",&cert,"certificate1"); - int write_value(char *name,unsigned char *value,int len); + int write_value(node_asn *pointer,char *name,unsigned char *value,int len); -------------------------------------------------------- Set the value of one element inside a structure. Input Parameters: - char *name: the name of the element inside a structure that you want to set. + node_asn *pointer: pointer to a structure + char *name: the name of the element inside the structure that you want to set. unsigned char *value: vector used to specify the value to set. int len: number of bytes of *value to use to set the value: value[0]..value[len-1] Return Value: @@ -159,6 +167,7 @@ Examples: description for each type value[0]=0xFF value[1]=0xFF , len=2 -> integer=-1 value[0]=0x01 , len=1 -> integer= 1 value[0]=0x00 value[1]=0x01 , len=2 -> integer= 1 + ENUMERATED: as INTEGER (but only with not negative numbers) BOOLEAN: VALUE must be the null terminated string "TRUE" or "FALSE" and LEN != 0 value="TRUE" , len=1 -> boolean=TRUE value="FALSE" , len=1 -> boolean=FALSE @@ -184,29 +193,29 @@ Examples: description for each type value="\xCF" , len=6 -> bit string="110011" (six bits) CHOICE: if NAME indicates a choice type, VALUE must specify one of the alternatives with a null terminated string. LEN != 0 - Using "Certificate.txt": - result=write_value("certificate1.tbsCertificate.subject","rdnSequence",1); - ANY: VALUE (null terminated string) indicates the type that must be used instead of ANY. + Using "PKIX1Implicit88.txt": + result=write_value(cert,"certificate1.tbsCertificate.subject","rdnSequence",1); + ANY: VALUE indicates the der encoding of a structure. LEN != 0 - value="X520name" , len=1 -> type ANY becomes X520name SEQUENCE OF: VALUE must be the null terminated string "NEW" and LEN != 0. With this instruction another element is appended in the sequence. The name of this element will be "?1" if it's the first one, "?2" for the second and so on. - Using "Certificate.txt": - result=write_value("certificate1.tbsCertificate.subject.rdnSequence","NEW",1); + Using "PKIX1Implicit88.txt": + result=write_value(cert,"certificate1.tbsCertificate.subject.rdnSequence","NEW",1); SET OF: the same as SEQUENCE OF. - Using "Certificate.txt": - result=write_value("certificate1.tbsCertificate.subject.rdnSequence.?LAST","NEW",1); + Using "PKIX1Implicit88.txt": + result=write_value(cert,"certificate1.tbsCertificate.subject.rdnSequence.?LAST","NEW",1); If an element is OPTIONAL and you want to delete it, you must use the value=NULL and len=0. - Using "Certificate.txt": - result=write_value("certificate1.tbsCertificate.issuerUniqueID",NULL,0); + Using "PKIX1Implicit88.txt": + result=write_value(cert,"certificate1.tbsCertificate.issuerUniqueID",NULL,0); - int read_value(char *name,unsigned char *value,int *len); + int read_value(node_asn *pointer,char *name,unsigned char *value,int *len); -------------------------------------------------------- Returns the value of one element inside a structure. Input Parameters: + node_asn *pointer: pointer to a structure char *name: the name of the element inside a structure that you want to read. Output Parameters: unsigned char *value: vector that will contain the element's content. @@ -220,6 +229,7 @@ Examples: a description for each type INTEGER: VALUE will contain a two's complement form integer. integer=-1 -> value[0]=0xFF , len=1 integer=1 -> value[0]=0x01 , len=1 + ENUMERATED: as INTEGER (but only with not negative numbers) BOOLEAN: VALUE will be the null terminated string "TRUE" or "FALSE" and LEN=5 or LEN=6 OBJECT IDENTIFIER: VALUE will be a null terminated string with each number separated by a blank (i.e. "1 2 3 543 1"). @@ -241,11 +251,12 @@ means that this element wasn't present in the der encoding that created the stru The first element of a SEQUENCE_OF or SET_OF is named "?1". The second one "?2" and so on. - int create_der(char *name,unsigned char *der,int *len); + int create_der(node_asn *pointer,char *name,unsigned char *der,int *len); ------------------------------------------------------ -Creates the DER encoding for the NAME structure. +Creates the DER encoding for the NAME structure (inside *POINTER structure). Input Parameters: - char *name: the name of the structure you want to encode. + node_asn *pointer: pointer to a structure + char *name: the name of the structure you want to encode (it must be inside *POINTER). Output Parameters: unsigned char *der: vector that will contain the DER encoding. DER must be a pointer to memory cells already allocated. @@ -256,12 +267,12 @@ Return Value: ASN_VALUE_NOT_FOUND: there is an element without a value. - int get_der(char *name,unsigned char *der,int len); + int get_der(node_asn *pointer,char *name,unsigned char *der,int len); -------------------------------------------------- -Fill the structure NAME with values of a DER encoding string. The sructure must just be +Fill the structure *POINTER with values of a DER encoding string. The sructure must just be created with function 'create_stucture'. Input Parameters: - char *name: the name of the structure that you want to fill. + node_asn *pointer: pointer to the structure that you want to fill. unsigned char *der: vector that contains the DER encoding. int len: number of bytes of *der: der[0]..der[len-1] Return Value: @@ -270,14 +281,14 @@ Return Value: ASN_TAG_ERROR, ASN_DER_ERROR: the der encoding doesn't match the structure NAME. - int get_start_end_der(char *name,unsigned char *der,int len,char *name_element,int *start, int *end); + int get_start_end_der(node_asn *pointer,unsigned char *der,int len,char *name_element,int *start, int *end); ---------------------------------------------------------------------------------------------------- Find the start and end point of an element in a DER encoding string. I mean that if you have a der encoding and you have already used the function "get_der" to fill a structure, it may happen that you want to find the piece of string concerning an element of the structure. Example: the sequence "tbsCertificate" inside an X509 certificate. Input Parameters: - char *name: the name of the structure that is already setted with DER string. + node_asn *pointer: the pointer to the structure that is already setted with DER string. unsigned char *der: vector that contains the DER encoding. int len: number of bytes of *der: der[0]..der[len-1] char *name_element: an element of NAME structure. @@ -290,35 +301,36 @@ Return Value: ASN_TAG_ERROR, ASN_DER_ERROR: the der encoding doesn't match the structure NAME. - int delete_structure(char *name); + int delete_structure(node_asn *pointer); --------------------------------- -Deletes the structure NAME. +Deletes the structure *POINTER. Input Parameters: - char *name: the name of the structure that you want to delete. + node_asn *pointer: pointer to the structure that you want to delete. Return Value: ASN_OK: everything OK - ASN_ELEMENT_NOT_FOUND: wasn't find the NAME element. + ASN_ELEMENT_NOT_FOUND: pointer==NULL. - void visit_tree(char *name); + void visit_tree(node_asn *pointer,char *name); --------------------------- -Prints on the standard output the structure's tree starting from the NAME element. +Prints on the standard output the structure's tree starting from the NAME element inside +the structure *POINTER. FUTURE DEVELOPMENTS ------------------- -If this parser and this kind of interface is useful, I want to: -1. intoduce the REAL and ENUMERATED types -2. allow negative numbers in ASN.1 files. -3. allow an easiest way to set INTEGER and OBJECT IDENTFIER using constant names instead of +1. allow an easiest way to set INTEGER and OBJECT IDENTFIER using constant names instead of numbers. I mean it will be possible set an OID with a string like "dsa-with-sha" or an INTEGER with "v1" (see 'Version' type in the Certificate structure) -4. improve the error signaling with strings that give you more details. +2. use a prefix for functions (e.g. gnuasn1_) +3. Create a parser that creates C static functions to avoid files for initialization. +4. type REAL +5. improve the error signaling with strings that give you more details. Examples: in case of ASN1 syntax error you will have the line number where the error is, if creating a der encoding the result is ASN_VALUE_NOT_FOUND you will have the name of the element without the value. -5. improve the 'visit_tree' function and change the output from stdout to a null terminated +6. improve the 'visit_tree' function and change the output from stdout to a null terminated string. diff --git a/lib/Makefile.am b/lib/Makefile.am index ad83c5b515..bd911873fe 100644 --- a/lib/Makefile.am +++ b/lib/Makefile.am @@ -15,7 +15,7 @@ EXTRA_DIST = debug.h gnutls_compress.h defines.h \ crypt.h libgnutls-config.in libgnutls.m4 gnutls.h.in gnutls_errors_int.h \ cert_asn1.h cert_der.h gnutls_datum.h auth_x509.h gnutls_gcry.h \ ext_dnsname.h gnutls_pk.h gnutls_record.h gnutls_cert.h \ - gnutls_privkey.h gnutls_constate.h + gnutls_privkey.h gnutls_constate.h gnutls_global.h lib_LTLIBRARIES = libgnutls.la libgnutls_la_SOURCES = gnutls_record.c gnutls_compress.c debug.c \ gnutls_cipher.c gnutls_buffers.c gnutls_handshake.c gnutls_num.c \ diff --git a/lib/auth_rsa.c b/lib/auth_rsa.c index 16467ab1f6..76755a0e34 100644 --- a/lib/auth_rsa.c +++ b/lib/auth_rsa.c @@ -30,6 +30,7 @@ #include #include #include +#include #include "debug.h" int gen_rsa_certificate(GNUTLS_KEY, opaque **); @@ -69,14 +70,15 @@ static int _gnutls_get_rsa_params(GNUTLS_KEY key, RSA_Params * params, int ret = 0, result; opaque str[5 * 1024]; int len = sizeof(str); - - if (create_structure("rsa_params", "PKIX1Explicit88.Certificate") + node_asn *srsa, *spk; + + if (create_structure( _gnutls_get_pkcs(), "PKIX1Implicit88.Certificate", &srsa, "rsa_params") != ASN_OK) { gnutls_assert(); return GNUTLS_E_ASN1_ERROR; } - result = get_der("rsa_params", cert.data, cert.size); + result = get_der( srsa, cert.data, cert.size); if (result != ASN_OK) { /* couldn't decode DER */ gnutls_assert(); @@ -87,12 +89,12 @@ static int _gnutls_get_rsa_params(GNUTLS_KEY key, RSA_Params * params, len = sizeof(str) - 1; result = read_value - ("rsa_params.tbsCertificate.subjectPublicKeyInfo.algorithm.algorithm", + (srsa, "rsa_params.tbsCertificate.subjectPublicKeyInfo.algorithm.algorithm", str, &len); if (result != ASN_OK) { gnutls_assert(); - delete_structure("rsa_params"); + delete_structure(srsa); return GNUTLS_E_ASN1_PARSING_ERROR; } @@ -100,9 +102,9 @@ static int _gnutls_get_rsa_params(GNUTLS_KEY key, RSA_Params * params, len = sizeof(str) - 1; result = read_value - ("rsa_params.tbsCertificate.subjectPublicKeyInfo.subjectPublicKey", + (srsa, "rsa_params.tbsCertificate.subjectPublicKeyInfo.subjectPublicKey", str, &len); - delete_structure("rsa_params"); + delete_structure(srsa); if (result != ASN_OK) { gnutls_assert(); @@ -110,31 +112,37 @@ static int _gnutls_get_rsa_params(GNUTLS_KEY key, RSA_Params * params, } if (create_structure - ("rsa_public_key", - "PKIX1Explicit88.RSAPublicKey") != ASN_OK) { + ( _gnutls_get_pkix(), + "PKIX1Implicit88.RSAPublicKey", &spk, "rsa_public_key") != ASN_OK) { gnutls_assert(); return GNUTLS_E_ASN1_ERROR; } - result = get_der("rsa_public_key", str, len / 8); + if (len % 8 != 0) { + gnutls_assert(); + delete_structure(spk); + return GNUTLS_E_UNIMPLEMENTED_FEATURE; + } + + result = get_der(spk, str, len / 8); if (result != ASN_OK) { gnutls_assert(); - delete_structure("rsa_public_key"); + delete_structure(spk); return GNUTLS_E_ASN1_PARSING_ERROR; } len = sizeof(str) - 1; - result = read_value("rsa_public_key.modulus", str, &len); + result = read_value(spk, "rsa_public_key.modulus", str, &len); if (result != ASN_OK) { gnutls_assert(); - delete_structure("rsa_public_key"); + delete_structure(spk); return GNUTLS_E_ASN1_PARSING_ERROR; } if (gcry_mpi_scan(mod, GCRYMPI_FMT_USG, str, &len) != 0) { gnutls_assert(); - delete_structure("rsa_public_key"); + delete_structure(spk); return GNUTLS_E_MPI_SCAN_FAILED; } @@ -142,16 +150,16 @@ static int _gnutls_get_rsa_params(GNUTLS_KEY key, RSA_Params * params, if (gnutls_set_datum (¶ms->rsa_modulus, str, len) < 0) { gnutls_assert(); - delete_structure("rsa_public_key"); + delete_structure(spk); return GNUTLS_E_MEMORY_ERROR; } len = sizeof(str) - 1; result = - read_value("rsa_public_key.publicExponent", str, &len); + read_value(spk, "rsa_public_key.publicExponent", str, &len); if (result != ASN_OK) { gnutls_assert(); - delete_structure("rsa_public_key"); + delete_structure(spk); if (params != NULL) gnutls_free_datum(¶ms->rsa_modulus); _gnutls_mpi_release(mod); @@ -163,7 +171,7 @@ static int _gnutls_get_rsa_params(GNUTLS_KEY key, RSA_Params * params, _gnutls_mpi_release(mod); if (params != NULL) gnutls_free_datum(¶ms->rsa_modulus); - delete_structure("rsa_public_key"); + delete_structure(spk); return GNUTLS_E_MPI_SCAN_FAILED; } if (params != NULL) @@ -174,11 +182,11 @@ static int _gnutls_get_rsa_params(GNUTLS_KEY key, RSA_Params * params, if (params != NULL) gnutls_free_datum(¶ms-> rsa_modulus); - delete_structure("rsa_public_key"); + delete_structure(spk); return GNUTLS_E_MEMORY_ERROR; } - delete_structure("rsa_public_key"); + delete_structure(spk); ret = 0; @@ -189,7 +197,7 @@ static int _gnutls_get_rsa_params(GNUTLS_KEY key, RSA_Params * params, gnutls_assert(); ret = GNUTLS_E_X509_CERTIFICATE_ERROR; - delete_structure("rsa_params"); + delete_structure(srsa); } diff --git a/lib/cert_ASN.y b/lib/cert_ASN.y index 5ead3f0c30..1dd4ae8692 100755 --- a/lib/cert_ASN.y +++ b/lib/cert_ASN.y @@ -8,12 +8,14 @@ %{ -#include -#include +#include +#include +#include "cert_asn1.h" -FILE *file_asn1; /* Pointer to the to parse */ +FILE *file_asn1; /* Pointer to file to parse */ extern int parse_mode; int result_parse; +node_asn *p_tree; %} @@ -61,6 +63,7 @@ int result_parse; %token GeneralizedTime %token FROM %token IMPORTS +%token ENUMERATED %type octet_string_def constant constant_list type_assig_right %type integer_def type_assig type_assig_list sequence_def type_def @@ -69,8 +72,8 @@ int result_parse; %type constant_def type_constant type_constant_list definitions %type definitions_id Time bit_element bit_element_list set_def %type identifier_list imports_def tag_type tag type_assig_right_tag -%type type_assig_right_tag_default -%type num_identifier +%type type_assig_right_tag_default enumerated_def +%type pos_num neg_num pos_neg_num pos_neg_identifier num_identifier %type class explicit_implicit %% @@ -79,13 +82,29 @@ input: /* empty */ | input definitions ; +pos_num : NUM {strcpy($$,$1);} + | '+' NUM {strcpy($$,$2);} +; + +neg_num : '-' NUM {strcpy($$,"-"); + strcat($$,$2);} +; + +pos_neg_num : pos_num {strcpy($$,$1);} + | neg_num {strcpy($$,$1);} +; + num_identifier : NUM {strcpy($$,$1);} | IDENTIFIER {strcpy($$,$1);} ; -constant: '(' NUM ')' {$$=add_node(TYPE_CONSTANT); +pos_neg_identifier : pos_neg_num {strcpy($$,$1);} + | IDENTIFIER {strcpy($$,$1);} +; + +constant: '(' pos_neg_num ')' {$$=add_node(TYPE_CONSTANT); set_value($$,$2,strlen($2)+1);} - | IDENTIFIER'('NUM')' {$$=add_node(TYPE_CONSTANT); + | IDENTIFIER'('pos_neg_num')' {$$=add_node(TYPE_CONSTANT); set_name($$,$1); set_value($$,$3,strlen($3)+1);} ; @@ -131,7 +150,7 @@ tag : tag_type {$$=$1;} | tag_type IMPLICIT {$$=mod_type($1,CONST_IMPLICIT);} ; -default : DEFAULT num_identifier {$$=add_node(TYPE_DEFAULT); +default : DEFAULT pos_neg_identifier {$$=add_node(TYPE_DEFAULT); set_value($$,$2,strlen($2)+1);} | DEFAULT TRUE {$$=add_node(TYPE_DEFAULT|CONST_TRUE);} | DEFAULT FALSE {$$=add_node(TYPE_DEFAULT|CONST_FALSE);} @@ -139,7 +158,7 @@ default : DEFAULT num_identifier {$$=add_node(TYPE_DEFAULT); integer_def: INTEGER {$$=add_node(TYPE_INTEGER);} | INTEGER'{'constant_list'}' {$$=add_node(TYPE_INTEGER|CONST_LIST); - set_down($$,$3);} + set_down($$,$3);} | integer_def'('num_identifier'.''.'num_identifier')' {$$=add_node(TYPE_INTEGER|CONST_MIN_MAX); set_down($$,add_node(TYPE_SIZE)); @@ -187,6 +206,11 @@ bit_string_def : BIT STRING {$$=add_node(TYPE_BIT_STRING);} set_down($$,$4);} ; +enumerated_def : ENUMERATED'{'bit_element_list'}' + {$$=add_node(TYPE_ENUMERATED|CONST_LIST); + set_down($$,$3);} +; + object_def : OBJECT STR_IDENTIFIER {$$=add_node(TYPE_OBJECT_ID);} ; @@ -196,6 +220,7 @@ type_assig_right: IDENTIFIER {$$=add_node(TYPE_IDENTIFIER); set_value($$,$1,strlen($1)+1); set_down($$,$2);} | integer_def {$$=$1;} + | enumerated_def {$$=$1;} | boolean_def {$$=$1;} | Time | octet_string_def {$$=$1;} @@ -217,7 +242,7 @@ type_assig_right_tag : type_assig_right {$$=$1;} type_assig_right_tag_default : type_assig_right_tag {$$=$1;} | type_assig_right_tag default {$$=mod_type($1,CONST_DEFAULT); set_right($2,get_down($$)); - set_down($$,$2);} + set_down($$,$2);} | type_assig_right_tag OPTIONAL {$$=mod_type($1,CONST_OPTION);} ; @@ -260,17 +285,17 @@ any_def : ANY {$$=add_node(TYPE_ANY);} type_def : IDENTIFIER "::=" type_assig_right_tag {$$=set_name($3,$1);} ; -constant_def : IDENTIFIER OBJECT STR_IDENTIFIER "::=" '{' obj_constant_list '}' - {$$=add_node(TYPE_OBJECT_ID); +constant_def : IDENTIFIER OBJECT STR_IDENTIFIER "::=" '{'obj_constant_list'}' + {$$=add_node(TYPE_OBJECT_ID|CONST_ASSIGN); set_name($$,$1); set_down($$,$6);} | IDENTIFIER IDENTIFIER "::=" '{' obj_constant_list '}' - {$$=add_node(TYPE_OBJECT_ID|CONST_1_PARAM); + {$$=add_node(TYPE_OBJECT_ID|CONST_ASSIGN|CONST_1_PARAM); set_name($$,$1); set_value($$,$2,strlen($2)+1); set_down($$,$5);} | IDENTIFIER INTEGER "::=" NUM - {$$=add_node(TYPE_INTEGER); + {$$=add_node(TYPE_INTEGER|CONST_ASSIGN); set_name($$,$1); set_value($$,$4,strlen($4)+1);} ; @@ -311,9 +336,18 @@ definitions: definitions_id if($7==NULL) set_right($1,$8); else {set_right($7,$8);set_right($1,$7);} set_down($$,$1); - if(parse_mode==PARSE_MODE_CREATE){ - check_asn(get_name($$), CHECK_DEFAULT_TAG_TYPE); - result_parse=check_asn(get_name($$), CHECK_TYPE);}} + if(parse_mode==PARSE_MODE_CREATE){ + set_default_tag($$); + change_integer_value($$); + type_set_config($$); + result_parse=check_identifier($$); + if(result_parse==ASN_IDENTIFIER_NOT_FOUND) + delete_structure($$); + else{ + expand_object_id($$); + p_tree=$$; + } + }} ; %% @@ -328,14 +362,14 @@ const char *key_word[]={"::=","OPTIONAL","INTEGER","SIZE","OCTET","STRING" ,"BOOLEAN","TRUE","FALSE","APPLICATION","ANY","DEFINED" ,"SET","BY","EXPLICIT","IMPLICIT","DEFINITIONS","TAGS" ,"BEGIN","END","UTCTime","GeneralizedTime","FROM" - ,"IMPORTS","NULL"}; + ,"IMPORTS","NULL","ENUMERATED"}; const int key_word_token[]={ASSIG,OPTIONAL,INTEGER,SIZE,OCTET,STRING ,SEQUENCE,BIT,UNIVERSAL,PRIVATE,OPTIONAL ,DEFAULT,CHOICE,OF,OBJECT,STR_IDENTIFIER ,BOOLEAN,TRUE,FALSE,APPLICATION,ANY,DEFINED ,SET,BY,EXPLICIT,IMPLICIT,DEFINITIONS,TAGS ,BEGIN,END,UTCTime,GeneralizedTime,FROM - ,IMPORTS,TOKEN_NULL}; + ,IMPORTS,TOKEN_NULL,ENUMERATED}; /*************************************************************/ /* Function: yylex */ @@ -353,7 +387,21 @@ yylex() while((c=fgetc(file_asn1))==' ' || c=='\t' || c=='\n'); if(c==EOF) return 0; if(c=='(' || c==')' || c=='[' || c==']' || - c=='{' || c=='}' || c==',' || c=='.') return c; + c=='{' || c=='}' || c==',' || c=='.' || + c=='+') return c; + if(c=='-'){ + if((c=fgetc(file_asn1))!='-'){ + ungetc(c,file_asn1); + return '-'; + } + else{ + /* A comment finishes at the end of line */ + counter=0; + while((c=fgetc(file_asn1))!=EOF && c!='\n'); + if(c==EOF) return 0; + else continue; /* repeat the search */ + } + } string[counter++]=c; while(!((c=fgetc(file_asn1))==EOF || c==' '|| c=='\t' || c=='\n' || c=='(' || c==')' || c=='[' || c==']' || @@ -364,16 +412,6 @@ yylex() ungetc(c,file_asn1); string[counter]=0; - /* Is STRING the beginning of a comment? */ - if(!strcmp(string,"--")) - { - /* A comment finishes at the end of line */ - counter=0; - while((c=fgetc(file_asn1))!=EOF && c!='\n'); - if(c==EOF) return 0; - else continue; /* repeat the search */ - } - /* Is STRING a number? */ for(k=0;k -#include -#include +#include "cert_asn1.h" +#include "cert_der.h" -/*****************************************/ -/* Function : parser_asn1 */ -/* Description: defined in fine "ASN.y" */ -/* used to parse a file. */ -/*****************************************/ -int parser_asn1(char *file_name); - -node_asn *node_list=NULL; /* Pointer to the first element ot the list */ int parse_mode; @@ -36,8 +28,7 @@ add_node(unsigned int type) punt=(node_asn *) malloc(sizeof(node_asn)); - punt->list=node_list; - node_list=punt; + punt->left=NULL; punt->name=NULL; punt->type=type; punt->value=NULL; @@ -95,6 +86,7 @@ set_right(node_asn *node,node_asn *right) if(node==NULL) return node; node->right=right; + if(right) right->left=node; return node; } @@ -127,6 +119,7 @@ set_down(node_asn *node,node_asn *down) if(node==NULL) return node; node->down=down; + if(down) down->left=node; return node; } @@ -165,55 +158,15 @@ remove_node(node_asn *node) if(node==NULL) return; - if(node==node_list){ - punt=node_list; - node_list=punt->list; - } - else{ - punt=node_list; - while(punt && (punt!=node)){ - punt_prev=punt; - punt=punt->list; - } - if(punt==NULL) return; - punt_prev->list=punt->list; - } - free(punt->name); - free(punt->value); -} - -void -visit_list() -{ - node_asn *p; - - p=node_list; - while(p){ - printf("name:"); - if(p->name) printf("%s ",p->name); - else printf("NULL "); - switch(p->type){ - case TYPE_CONSTANT: - printf("type:CONST value:%s\n",p->value); - break; - case TYPE_INTEGER: - printf("type:INTEGER\n"); - break; - case TYPE_SEQUENCE: - printf("type:SEQUENCE\n"); - break; - default: - printf("type:ERROR\n"); - break; - } - p=p->list; - } + free(node->name); + free(node->value); + free(node); } node_asn * -find_node(char *name) +find_node(node_asn *pointer,char *name) { node_asn *p; char *n_start,*n_end,n[128]; @@ -232,11 +185,11 @@ find_node(char *name) strcpy(n,n_start); n_start=NULL; } - - p=node_list; + + p=pointer; while(p){ if((p->name) && (!strcmp(p->name,n))) break; - else p=p->list; + else p=p->right; } if(p==NULL) return NULL; @@ -278,56 +231,37 @@ find_node(char *name) node_asn * find_left(node_asn *node) { - node_asn *p; - - p=node_list; - - while(p){ - if(p->right==node) return p; - p=p->list; - } + if((node==NULL) || (node->left==NULL) || + (node->left->down==node)) return NULL; - return NULL; + return node->left; } node_asn * find_up(node_asn *node) { - node_asn *p,*p_left; + node_asn *p; if(node==NULL) return NULL; - p_left=node; - - /* look for the most left element of node , result P */ - do{ - p=p_left; - p_left=find_left(p_left); - }while(p_left); + p=node; - /* look for the upper element of p_left */ - p_left=p; - p=node_list; - while(p){ - if(p->down==p_left) return p; - p=p->list; - } + while((p->left!=NULL) && (p->left->right==p)) p=p->left; - return NULL; + return p->left; } - void -visit_tree(char *name) +visit_tree(node_asn *pointer,char *name) { node_asn *p,*root; int k,indent=0,len,len2,len3; unsigned char class; unsigned long tag; - root=find_node(name); + root=find_node(pointer,name); if(root==NULL) return; @@ -360,6 +294,14 @@ visit_tree(char *name) for(k=0;kvalue)[k+len2]); } break; + case TYPE_ENUMERATED: + printf("ENUMERATED"); + if(p->value){ + len=get_length_der(p->value,&len2); + printf(" value:0x"); + for(k=0;kvalue)[k+len2]); + } + break; case TYPE_TIME: printf("TIME"); if(p->value) printf(" value:%s",p->value); @@ -416,10 +358,9 @@ visit_tree(char *name) case TYPE_ANY: printf("ANY"); if(p->value){ - tag=get_tag_der(p->value,&class,&len2); - len2+=get_length_der(p->value+len2,&len3); + len2=get_length_der(p->value,&len3); printf(" value:"); - for(k=0;kvalue)[k]); + for(k=0;kvalue)[k+len3]); } break; @@ -462,6 +403,7 @@ visit_tree(char *name) if(p->type & CONST_IMPORTS) printf("IMPORTS,"); if(p->type & CONST_SET) printf("SET,"); if(p->type & CONST_NOT_USED) printf("NOT_USED,"); + if(p->type & CONST_ASSIGN) printf("ASSIGNEMENT,"); } printf("\n"); @@ -470,12 +412,12 @@ visit_tree(char *name) p=p->down; indent+=2; } + else if(p==root){ + p=NULL; + break; + } else if(p->right) p=p->right; else{ - if(p==root){ - p=NULL; - break; - } while(1){ p=find_up(p); if(p==root){ @@ -493,7 +435,7 @@ visit_tree(char *name) } int -delete_tree2(node_asn *root) +delete_structure(node_asn *root) { node_asn *p,*p2,*p3; @@ -508,7 +450,7 @@ delete_tree2(node_asn *root) p2=p->right; if(p!=root){ p3=find_up(p); - p3->down=p2; + set_down(p3,p2); remove_node(p); p=p3; } @@ -516,9 +458,12 @@ delete_tree2(node_asn *root) p3=find_left(p); if(!p3){ p3=find_up(p); - if(p3) p3->down=p2; + if(p3) set_down(p3,p2); + else{ + if(p->right) p->right->left=NULL; + } } - else p3->right=p2; + else set_right(p3,p2); remove_node(p); p=NULL; } @@ -528,16 +473,19 @@ delete_tree2(node_asn *root) } +/* int -delete_structure(char *root_name) +delete_structure(node_asn *root,char *name) { - node_asn *p,*p2,*p3,*root; + node_asn *p; + + p=find_node(root,name); - root=find_node(root_name); - if(root==NULL) return ASN_ELEMENT_NOT_FOUND; + if(p==NULL) return ASN_ELEMENT_NOT_FOUND; - return delete_tree2(root); + return delete_structure(p); } +*/ #define UP 1 @@ -554,12 +502,10 @@ copy_structure3(node_asn *source_node) if(source_node==NULL) return NULL; dest_node=add_node(source_node->type); - + p_s=source_node; p_d=dest_node; - if(p_s->down==NULL) return dest_node; - move=DOWN; do{ @@ -567,9 +513,10 @@ copy_structure3(node_asn *source_node) if(p_s->name) set_name(p_d,p_s->name); if(p_s->value){ switch(type_field(p_s->type)){ - case TYPE_OCTET_STRING: case TYPE_BIT_STRING: + case TYPE_OCTET_STRING: case TYPE_BIT_STRING: + case TYPE_INTEGER: case TYPE_DEFAULT: len=get_length_der(p_s->value,&len2); - set_value(p_d,p_s->value,len2); + set_value(p_d,p_s->value,len+len2); break; default: set_value(p_d,p_s->value,strlen(p_s->value)+1); @@ -588,6 +535,9 @@ copy_structure3(node_asn *source_node) } else move=RIGHT; } + + if(p_s==source_node) break; + if(move==RIGHT){ if(p_s->right){ p_s=p_s->right; @@ -608,25 +558,30 @@ copy_structure3(node_asn *source_node) node_asn * -copy_structure2(char *source_name) +copy_structure2(node_asn *root,char *source_name) { node_asn *source_node; - source_node=find_node(source_name); - + source_node=find_node(root,source_name); + return copy_structure3(source_node); + } int -create_structure(char *dest_name,char *source_name) +create_structure(node_asn *root,char *source_name,node_asn **pointer,char *dest_name) { node_asn *dest_node; int res; char *end,n[129]; - dest_node=copy_structure2(source_name); + *pointer=NULL; + + dest_node=copy_structure2(root,source_name); + if(dest_node==NULL) return ASN_ELEMENT_NOT_FOUND; + set_name(dest_node,dest_name); end=strchr(source_name,'.'); @@ -638,10 +593,13 @@ create_structure(char *dest_name,char *source_name) strcpy(n,source_name); } - res=expand_asn(dest_name,n); + res=expand_identifier(&dest_node,root); + type_choice_config(dest_node); + + change_integer_value(dest_node); + + *pointer=dest_node; - check_asn(dest_name,CHECK_INTEGER); - return res; } @@ -659,7 +617,7 @@ append_sequence_set(node_asn *node) while((type_field(p->type)==TYPE_TAG) || (type_field(p->type)==TYPE_SIZE)) p=p->right; p2=copy_structure3(p); while(p->right) p=p->right; - p->right=p2; + set_right(p,p2); temp=(char *) malloc(10); if(p->name==NULL) strcpy(temp,"?1"); else{ @@ -676,18 +634,18 @@ append_sequence_set(node_asn *node) int -write_value(char *name,unsigned char *value,int len) +write_value(node_asn *node_root,char *name,unsigned char *value,int len) { node_asn *node,*p,*p2; unsigned char *temp,val[4]; int len2,k,negative; unsigned char *root,*n_end; - node=find_node(name); + node=find_node(node_root,name); if(node==NULL) return ASN_ELEMENT_NOT_FOUND; if((node->type & CONST_OPTION) && (value==NULL) && (len==0)){ - delete_structure(name); + delete_structure(node); return ASN_OK; } @@ -713,12 +671,15 @@ write_value(char *name,unsigned char *value,int len) } else return ASN_VALUE_NOT_VALID; break; - case TYPE_INTEGER: + case TYPE_INTEGER: case TYPE_ENUMERATED: if(len==0) return ASN_VALUE_NOT_VALID; if(value[0]&0x80) negative=1; else negative=0; + if(negative && (type_field(node->type)==TYPE_ENUMERATED)) + return ASN_VALUE_NOT_VALID; + for(k=0;kname,value)){ p2=node->down; while(p2){ - if(p2!=p) delete_tree2(p2); - p2=p2->right; + if(p2!=p){delete_structure(p2); p2=node->down;} + else p2=p2->right; } break; } @@ -808,31 +769,39 @@ write_value(char *name,unsigned char *value,int len) } if(!p) return ASN_ELEMENT_NOT_FOUND; - n_end=strchr(value,'.'); + /* n_end=strchr(value,'.'); if(n_end){ root=(char *)malloc(n_end-value+1); memcpy(root,value,n_end-value); root[n_end-value]=0; expand_asn(name,root); free(root); - } + }*/ + break; case TYPE_ANY: - p=copy_structure2(value); + length_der(len,NULL,&len2); + temp=(unsigned char *)malloc(len+len2); + octet_der(value,len,temp,&len2); + set_value(node,temp,len2); + free(temp); + + /* + p=copy_structure2(p,value); if(p==NULL) return ASN_VALUE_NOT_VALID; set_name(p,node->name); set_right(p,node->right); p2=node->down; if(p2){ while(p2->right) p2=p2->right; - p2->right=p->down; - p->down=node->down; + set_right(p2,p->down); + set_down(p,node->down); } p2=find_left(node); - if(p2) p2->right=p; + if(p2) set_right(p2,p); else{ p2=find_up(node); - p2->down=p; + set_down(p2,p); } if(node->type & CONST_TAG) p->type|=CONST_TAG; if(node->type & CONST_OPTION) p->type|=CONST_OPTION; @@ -843,9 +812,12 @@ write_value(char *name,unsigned char *value,int len) root=(char *)malloc(n_end-value+1); memcpy(root,value,n_end-value); root[n_end-value]=0; - expand_asn(name,root); + expand_identifier(name,root); + type_choice_config(name); free(root); } + */ + break; case TYPE_SEQUENCE_OF: case TYPE_SET_OF: if(strcmp(value,"NEW")) return ASN_VALUE_NOT_VALID; @@ -861,19 +833,20 @@ write_value(char *name,unsigned char *value,int len) int -read_value(char *name,unsigned char *value,int *len) +read_value(node_asn *root,char *name,unsigned char *value,int *len) { node_asn *node,*p; int len2,len3; unsigned long tag; unsigned char class; - node=find_node(name); + node=find_node(root,name); if(node==NULL) return ASN_ELEMENT_NOT_FOUND; if((type_field(node->type)!=TYPE_NULL) && (type_field(node->type)!=TYPE_CHOICE) && - !(node->type&CONST_DEFAULT) && (node->value==NULL)) + !(node->type&CONST_DEFAULT) && !(node->type&CONST_ASSIGN) && + (node->value==NULL)) return ASN_VALUE_NOT_FOUND; switch(type_field(node->type)){ @@ -892,7 +865,7 @@ read_value(char *name,unsigned char *value,int *len) else strcpy(value,"FALSE"); *len=strlen(value)+1; break; - case TYPE_INTEGER: + case TYPE_INTEGER: case TYPE_ENUMERATED: if((node->type&CONST_DEFAULT) && (node->value==NULL)){ p=node->down; while(type_field(p->type)!=TYPE_DEFAULT) p=p->right; @@ -901,7 +874,20 @@ read_value(char *name,unsigned char *value,int *len) else get_octet_der(node->value,&len2,value,len); break; case TYPE_OBJECT_ID: - strcpy(value,node->value); + if(node->type&CONST_ASSIGN){ + strcpy(value,""); + p=node->down; + while(p){ + if(type_field(p->type)==TYPE_CONSTANT){ + strcat(value,p->value); + strcat(value," "); + } + p=p->right; + } + value[strlen(value)-1]=0; + } + else strcpy(value,node->value); + *len=strlen(value)+1; break; case TYPE_TIME: @@ -919,10 +905,9 @@ read_value(char *name,unsigned char *value,int *len) *len=strlen(value)+1; break; case TYPE_ANY: - tag=get_tag_der(node->value,&class,&len2); - len2+=get_length_der((node->value)+len2,&len3); - memcpy(value,node->value,len3+len2); - *len=len3+len2; + len2=get_length_der(node->value,&len3); + memcpy(value,node->value+len3,len2); + *len=len2; break; default: return ASN_ELEMENT_NOT_FOUND; @@ -933,85 +918,162 @@ read_value(char *name,unsigned char *value,int *len) int -check_asn(char *name,int check) +set_default_tag(node_asn *node) { - node_asn *node,*p,*p2; - char name2[129],negative; - unsigned char val[4],val2[5],temp; - int k,len; + node_asn *p; - node=find_node(name); - if(node==NULL) return ASN_ELEMENT_NOT_FOUND; + if((node==NULL) || (type_field(node->type)!=TYPE_DEFINITIONS)) + return ASN_ELEMENT_NOT_FOUND; p=node; while(p){ + if((type_field(p->type)==TYPE_TAG) && + !(p->type&CONST_EXPLICIT) && + !(p->type&CONST_IMPLICIT)){ + if(node->type&CONST_EXPLICIT) p->type|=CONST_EXPLICIT; + else p->type|=CONST_IMPLICIT; + } - switch(check){ - case CHECK_TYPE: - if(type_field(p->type)==TYPE_IDENTIFIER){ - strcpy(name2,name);strcat(name2,".");strcat(name2,p->value); - p2=find_node(name2); - if(p2==NULL) return ASN_IDENTIFIER_NOT_FOUND; + if(p->down){ + p=p->down; + } + else if(p->right) p=p->right; + else{ + while(1){ + p=find_up(p); + if(p==node){ + p=NULL; + break; + } + if(p->right){ + p=p->right; + break; + } } - break; - case CHECK_NOT_USED: - if(p->type&CONST_NOT_USED){ - p2=NULL; - if(p!=node){ - p2=find_left(p); - if(!p2) p2=find_up(p); + } + } + + return ASN_OK; +} + + +int +check_identifier(node_asn *node) +{ + node_asn *p,*p2; + char name2[129]; + + if(node==NULL) return ASN_ELEMENT_NOT_FOUND; + + p=node; + while(p){ + if(type_field(p->type)==TYPE_IDENTIFIER){ + strcpy(name2,node->name);strcat(name2,".");strcat(name2,p->value); + p2=find_node(node,name2); + if(p2==NULL){printf("%s\n",name2); return ASN_IDENTIFIER_NOT_FOUND;} + } + else if((type_field(p->type)==TYPE_OBJECT_ID) && + (p->type&CONST_ASSIGN)){ + p2=p->down; + if(p2 && (type_field(p2->type)==TYPE_CONSTANT)){ + if(p2->value && !isdigit(p2->value[0])){ + strcpy(name2,node->name);strcat(name2,".");strcat(name2,p2->value); + p2=find_node(node,name2); + if(!p2 || (type_field(p2->type)!=TYPE_OBJECT_ID) || + !(p2->type&CONST_ASSIGN)) + {printf("%s\n",name2); return ASN_IDENTIFIER_NOT_FOUND;} } - delete_tree2(p); - p=p2; - } - break; - case CHECK_DEFAULT_TAG_TYPE: - if(type_field(p->type)==TYPE_DEFINITIONS) p2=p; - else if((type_field(p->type)==TYPE_TAG) && - !(p->type&CONST_EXPLICIT) && - !(p->type&CONST_IMPLICIT)){ - if(p2->type&CONST_EXPLICIT) p->type|=CONST_EXPLICIT; - else p->type|=CONST_IMPLICIT; } - break; - case CHECK_INTEGER: - if(type_field(p->type)==TYPE_INTEGER){ - if(p->type&CONST_DEFAULT){ - p=p->down; - while(type_field(p->type)!=TYPE_DEFAULT) p=p->right; + } + + if(p->down){ + p=p->down; + } + else if(p->right) p=p->right; + else{ + while(1){ + p=find_up(p); + if(p==node){ + p=NULL; + break; } - if(p->value){ - *((long*)val)=strtol(p->value,NULL,10); - for(k=0;k<2;k++){ - temp=val[k]; - val[k]=val[3-k]; - val[3-k]=temp; - } - - if(val[0]&0x80) negative=1; - else negative=0; + if(p->right){ + p=p->right; + break; + } + } + } + } + + return ASN_OK; +} + + +int +change_integer_value(node_asn *node) +{ + node_asn *p,*p2; + char negative; + unsigned char val[4],val2[5],temp; + int len,k,force_exit; - for(k=0;k<3;k++) - if(negative && (val[k]!=0xFF)) break; - else if(!negative && val[k]) break; + if(node==NULL) return ASN_ELEMENT_NOT_FOUND; - length_der(4-k,NULL,&len); - octet_der(val+k,4-k,val2,&len); - set_value(p,val2,len); + p=node; + while(p){ + if((type_field(p->type)==TYPE_INTEGER) || (p->type&CONST_DEFAULT)){ + if(p->type&CONST_DEFAULT){ + p=p->down; + while(type_field(p->type)!=TYPE_DEFAULT) p=p->right; + if(!(p->type&CONST_TRUE) && !(p->type&CONST_FALSE)){ + force_exit=0; + for(k=0;kvalue);k++) + if(!isdigit(p->value[k]) && (p->value[k]!='-')) + {force_exit=1;break;} + if(force_exit){ + p2=find_up(p); + p2=p2->down; + while(p2){ + if((type_field(p2->type)==TYPE_CONSTANT) && + !strcmp(p->value,p2->name)) break; + p2=p2->right; + } + if(p2) set_value(p,p2->value,strlen(p2->value)+1); + } } } - default: - break; + if(p->value){ + *((long*)val)=strtol(p->value,NULL,10); + for(k=0;k<2;k++){ + temp=val[k]; + val[k]=val[3-k]; + val[3-k]=temp; + } + + if(val[0]&0x80) negative=1; + else negative=0; + + for(k=0;k<3;k++){ + if(negative && (val[k]!=0xFF)) break; + else if(!negative && val[k]) break; + } + + if((negative && !(val[k]&0x80)) || + (!negative && (val[k]&0x80))) k--; + + octet_der(val+k,4-k,val2,&len); + set_value(p,val2,len); + } } - if(!p) break; /* reach node */ - if(p->down){ p=p->down; } - else if(p->right) p=p->right; else{ - while(1){ + if(p==node) p=NULL; + else if(p->right) p=p->right; + else{ + while(1){ p=find_up(p); if(p==node){ p=NULL; @@ -1021,6 +1083,7 @@ check_asn(char *name,int check) p=p->right; break; } + } } } } @@ -1030,41 +1093,90 @@ check_asn(char *name,int check) int -expand_asn(char *name,char *root) +delete_not_used(node_asn *node) { - node_asn *node,*p,*p2,*p3,*p4; - char name_root[129],name2[129],*c; - int move; + node_asn *p,*p2; - node=find_node(name); if(node==NULL) return ASN_ELEMENT_NOT_FOUND; - strcpy(name_root,root); - p=node; + while(p){ + if(p->type&CONST_NOT_USED){ + p2=NULL; + if(p!=node){ + p2=find_left(p); + if(!p2) p2=find_up(p); + } + delete_structure(p); + p=p2; + } + + if(!p) break; /* reach node */ + + if(p->down){ + p=p->down; + } + else{ + if(p==node) p=NULL; + else if(p->right) p=p->right; + else{ + while(1){ + p=find_up(p); + if(p==node){ + p=NULL; + break; + } + if(p->right){ + p=p->right; + break; + } + } + } + } + } + return ASN_OK; +} + + + +int +expand_identifier(node_asn **node,node_asn *root) +{ + node_asn *p,*p2,*p3; + char name2[129]; + int move; + + if(node==NULL) return ASN_ELEMENT_NOT_FOUND; + + p=*node; move=DOWN; - while(!((p==node) && (move==UP))){ + while(!((p==*node) && (move==UP))){ if(move!=UP){ if(type_field(p->type)==TYPE_IDENTIFIER){ - strcpy(name2,name_root);strcat(name2,".");strcat(name2,p->value); - p2=copy_structure2(name2); - if(p2==NULL) return ASN_IDENTIFIER_NOT_FOUND; + strcpy(name2,root->name);strcat(name2,".");strcat(name2,p->value); + p2=copy_structure2(root,name2); + if(p2==NULL) return ASN_IDENTIFIER_NOT_FOUND; set_name(p2,p->name); - set_right(p2,p->right); + p2->right=p->right; + p2->left=p->left; + if(p->right) p->right->left=p2; p3=p->down; - if(p3){ while(p3->right) p3=p3->right; - p3->right=p2->down; - p2->down=p->down; + set_right(p3,p2->down); + set_down(p2,p->down); } p3=find_left(p); - if(p3) p3->right=p2; + if(p3) set_right(p3,p2); else{ p3=find_up(p); - p3->down=p2; + if(p3) set_down(p3,p2); + else { + // node_list=p2; + p2->left=NULL; + } } if(p->type & CONST_SIZE) p2->type|=CONST_SIZE; @@ -1074,14 +1186,50 @@ expand_asn(char *name,char *root) if(p->type & CONST_SET) p2->type|=CONST_SET; if(p->type & CONST_NOT_USED) p2->type|=CONST_NOT_USED; - if(p==node) node=p2; + if(p==*node) *node=p2; remove_node(p); p=p2; move=DOWN; continue; } - else if((type_field(p->type)==TYPE_CHOICE) && - (p->type&CONST_TAG)){ + move=DOWN; + } + else move=RIGHT; + + if(move==DOWN){ + if(p->down) p=p->down; + else move=RIGHT; + } + + if(p==*node) {move=UP; continue;} + + if(move==RIGHT){ + if(p->right) p=p->right; + else move=UP; + } + if(move==UP) p=find_up(p); + } + + return ASN_OK; +} + + + +int +type_choice_config(node_asn *node) +{ + node_asn *p,*p2,*p3,*p4; + int move; + + if(node==NULL) return ASN_ELEMENT_NOT_FOUND; + + p=node; + move=DOWN; + + while(!((p==node) && (move==UP))){ + if(move!=UP){ + if((type_field(p->type)==TYPE_CHOICE) && + (p->type&CONST_TAG)){ p2=p->down; while(p2){ if(type_field(p2->type)!=TYPE_TAG){ @@ -1091,8 +1239,8 @@ expand_asn(char *name,char *root) if(type_field(p3->type)==TYPE_TAG){ p4=add_node(p3->type); set_value(p4,p3->value,strlen(p3->value)+1); - p4->right=p2->down; - p2->down=p4; + set_right(p4,p2->down); + set_down(p2,p4); } p3=find_left(p3); } @@ -1103,12 +1251,46 @@ expand_asn(char *name,char *root) p2=p->down; while(p2){ p3=p2->right; - if(type_field(p2->type)==TYPE_TAG) delete_tree2(p2); + if(type_field(p2->type)==TYPE_TAG) delete_structure(p2); p2=p3; } - move=DOWN; } - else if(type_field(p->type)==TYPE_SET){ + move=DOWN; + } + else move=RIGHT; + + if(move==DOWN){ + if(p->down) p=p->down; + else move=RIGHT; + } + + if(p==node) {move=UP; continue;} + + if(move==RIGHT){ + if(p->right) p=p->right; + else move=UP; + } + if(move==UP) p=find_up(p); + } + + return ASN_OK; +} + + +int +type_set_config(node_asn *node) +{ + node_asn *p,*p2; + int move; + + if(node==NULL) return ASN_ELEMENT_NOT_FOUND; + + p=node; + move=DOWN; + + while(!((p==node) && (move==UP))){ + if(move!=UP){ + if(type_field(p->type)==TYPE_SET){ p2=p->down; while(p2){ if(type_field(p2->type)!=TYPE_TAG) @@ -1116,7 +1298,6 @@ expand_asn(char *name,char *root) p2=p2->right; } } - move=DOWN; } else move=RIGHT; @@ -1139,3 +1320,81 @@ expand_asn(char *name,char *root) } +int +expand_object_id(node_asn *node) +{ + node_asn *p,*p2,*p3,*p4,*p5; + char name_root[129],name2[129],*c; + int move; + + if(node==NULL) return ASN_ELEMENT_NOT_FOUND; + + strcpy(name_root,node->name); + + p=node; + move=DOWN; + + while(!((p==node) && (move==UP))){ + if(move!=UP){ + if((type_field(p->type)==TYPE_OBJECT_ID) && (p->type&CONST_ASSIGN)){ + p2=p->down; + if(p2 && (type_field(p2->type)==TYPE_CONSTANT)){ + if(p2->value && !isdigit(p2->value[0])){ + strcpy(name2,name_root);strcat(name2,".");strcat(name2,p2->value); + p3=find_node(node,name2); + if(!p3 || (type_field(p3->type)!=TYPE_OBJECT_ID) || + !(p3->type&CONST_ASSIGN)) return ASN_ELEMENT_NOT_FOUND; + set_down(p,p2->right); + remove_node(p2); + p2=p; + p4=p3->down; + while(p4){ + if(type_field(p4->type)==TYPE_CONSTANT){ + p5=add_node(TYPE_CONSTANT); + set_name(p5,p4->name); + set_value(p5,p4->value,strlen(p4->value)+1); + if(p2==p){ + set_right(p5,p->down); + set_down(p,p5); + } + else{ + set_right(p5,p2->right); + set_right(p2,p5); + } + p2=p5; + } + p4=p4->right; + } + move=DOWN; + continue; + } + } + } + move=DOWN; + } + else move=RIGHT; + + if(move==DOWN){ + if(p->down) p=p->down; + else move=RIGHT; + } + + if(p==node) {move=UP; continue;} + + if(move==RIGHT){ + if(p->right) p=p->right; + else move=UP; + } + if(move==UP) p=find_up(p); + } + + return ASN_OK; +} + + + + + + + + diff --git a/lib/cert_asn1.h b/lib/cert_asn1.h index 6d8be13f2e..fb4a48731c 100755 --- a/lib/cert_asn1.h +++ b/lib/cert_asn1.h @@ -32,6 +32,7 @@ #define TYPE_CHOICE 18 #define TYPE_IMPORTS 19 #define TYPE_NULL 20 +#define TYPE_ENUMERATED 21 /***********************************************************************/ @@ -66,12 +67,7 @@ #define CONST_NOT_USED (1<<26) #define CONST_SET (1<<27) - - -#define CHECK_TYPE 1 -#define CHECK_NOT_USED 2 -#define CHECK_INTEGER 3 -#define CHECK_DEFAULT_TAG_TYPE 4 +#define CONST_ASSIGN (1<<28) #define ASN_OK 0 @@ -93,12 +89,12 @@ /* that rappresent an ASN.1 DEFINITION. */ /******************************************************/ typedef struct node_asn_struct{ - struct node_asn_struct *list; /* Pointer to the next list element */ char *name; /* Node name */ unsigned int type; /* Node type */ unsigned char *value; /* Node value */ struct node_asn_struct *down; /* Pointer to the son node */ struct node_asn_struct *right; /* Pointer to the brother node */ + struct node_asn_struct *left; /* Pointer to the next list element */ } node_asn; @@ -142,38 +138,44 @@ get_down(node_asn *node); node_asn * mod_type(node_asn *node,unsigned int value); +void +append_tree(node_asn *node); + node_asn * -find_node(char *name); +find_node(node_asn *pointer,char *name); node_asn * find_up(node_asn *node); -int -write_value(char *name,unsigned char *value,int len); int -read_value(char *name,unsigned char *value,int *len); +parser_asn1(char *file_name,node_asn **pointer); +int +create_structure(node_asn *root,char *source_name,node_asn **pointer, + char *dest_name); + +int +delete_structure(node_asn *root); int -check_asn(char *name,int check); +write_value(node_asn *root,char *name,unsigned char *value,int len); int -expand_asn(char *name,char *root); +read_value(node_asn *root,char *name,unsigned char *value,int *len); + + +#endif + + + + + + -int -delete_tree2(node_asn *root); -int -append_sequence_set(node_asn *node); -int -create_structure(char *dest_name,char *source_name); -int -delete_structure(char *root_name); -int parser_asn1(char *file_name); -#endif diff --git a/lib/cert_der.c b/lib/cert_der.c index ebd0a0e606..1447975dfe 100644 --- a/lib/cert_der.c +++ b/lib/cert_der.c @@ -2,10 +2,13 @@ /* File: gnutls_der.c */ /* Description: Functions to manage DER encoding */ /*****************************************************/ + +#include +#include +#include -#include -#include -#include +#include "cert_der.h" +#include "cert_asn1.h" #define TAG_BOOLEAN 0x01 #define TAG_INTEGER 0x02 @@ -16,6 +19,7 @@ #define TAG_UTCTime 0x17 #define TAG_GENERALIZEDTime 0x18 #define TAG_OBJECT_ID 0x06 +#define TAG_ENUMERATED 0x0A #define TAG_NULL 0x05 @@ -294,8 +298,9 @@ objectid_der(unsigned char *str,unsigned char *der,int *der_len) *n_end=0; val=strtoul(n_start,NULL,10); counter++; + if(counter==1) val1=val; - if(counter==2){ + else if(counter==2){ der[0]=40*val1+val; *der_len=1; } @@ -489,6 +494,9 @@ insert_tag_der(node_asn *node,unsigned char *der,int *counter) case TYPE_INTEGER: tag_der(UNIVERSAL,TAG_INTEGER,der+*counter,&tag_len); break; + case TYPE_ENUMERATED: + tag_der(UNIVERSAL,TAG_ENUMERATED,der+*counter,&tag_len); + break; case TYPE_OBJECT_ID: tag_der(UNIVERSAL,TAG_OBJECT_ID,der+*counter,&tag_len); break; @@ -516,6 +524,9 @@ insert_tag_der(node_asn *node,unsigned char *der,int *counter) case TYPE_CHOICE: tag_len=0; break; + case TYPE_ANY: + tag_len=0; + break; default: return ASN_GENERIC_ERROR; } @@ -600,6 +611,9 @@ extract_tag_der(node_asn *node,unsigned char *der,int *der_len) case TYPE_INTEGER: if((class!=UNIVERSAL) || (tag!=TAG_INTEGER)) return ASN_DER_ERROR; break; + case TYPE_ENUMERATED: + if((class!=UNIVERSAL) || (tag!=TAG_ENUMERATED)) return ASN_DER_ERROR; + break; case TYPE_OBJECT_ID: if((class!=UNIVERSAL) || (tag!=TAG_OBJECT_ID)) return ASN_DER_ERROR; break; @@ -808,13 +822,13 @@ ordering_set_of(unsigned char *der,node_asn *node) int -create_der(char *name,unsigned char *der,int *len) +create_der(node_asn *root,char *name,unsigned char *der,int *len) { node_asn *node,*p,*p2,*p3; char temp[20]; int counter,counter_old,len2,len3,len4,move,ris; - node=find_node(name); + node=find_node(root,name); if(node==NULL) return ASN_ELEMENT_NOT_FOUND; counter=0; @@ -840,7 +854,7 @@ create_der(char *name,unsigned char *der,int *len) } move=RIGHT; break; - case TYPE_INTEGER: + case TYPE_INTEGER: case TYPE_ENUMERATED: if((p->type&CONST_DEFAULT) && (p->value==NULL)) counter=counter_old; else{ len2=get_length_der(p->value,&len3); @@ -914,7 +928,10 @@ create_der(char *name,unsigned char *der,int *len) } break; case TYPE_ANY: - return ASN_ERROR_TYPE_ANY; + len2=get_length_der(p->value,&len3); + memcpy(der+counter,p->value+len3,len2); + counter+=len2; + move=RIGHT; break; default: move=(move==UP)?RIGHT:DOWN; @@ -943,22 +960,20 @@ create_der(char *name,unsigned char *der,int *len) int -get_der(char *name,unsigned char *der,int len) +get_der(node_asn *root,unsigned char *der,int len) { node_asn *node,*p,*p2,*p3; char temp[128]; - int counter,len2,len3,move,ris; - unsigned char class; + int counter,len2,len3,len4,move,ris; + unsigned char class,*temp2; unsigned int tag; long val; - node=find_node(name); + node=root; if(node==NULL) return ASN_ELEMENT_NOT_FOUND; if(node->type&CONST_OPTION) return ASN_GENERIC_ERROR; - expand_asn(name,""); - counter=0; move=DOWN; p=node; @@ -1005,11 +1020,11 @@ get_der(char *name,unsigned char *der,int len) while(p->down){ ris=extract_tag_der(p->down,der+counter,&len2); if(ris==ASN_OK){ - while(p->down->right) delete_tree2(p->down->right); + while(p->down->right) delete_structure(p->down->right); break; } else if(ris==ASN_ERROR_TYPE_ANY) return ASN_ERROR_TYPE_ANY; - else delete_tree2(p->down); + else delete_structure(p->down); } if(p->down==NULL) return ASN_DER_ERROR; p=p->down; @@ -1053,7 +1068,7 @@ get_der(char *name,unsigned char *der,int len) else set_value(p,"T",1); move=RIGHT; break; - case TYPE_INTEGER: + case TYPE_INTEGER: case TYPE_ENUMERATED: len2=get_length_der(der+counter,&len3); set_value(p,der+counter,len3+len2); counter+=len3+len2; @@ -1135,10 +1150,13 @@ get_der(char *name,unsigned char *der,int len) case TYPE_ANY: tag=get_tag_der(der+counter,&class,&len2); len2+=get_length_der(der+counter+len2,&len3); - set_value(p,der+counter,len3+len2); - counter+=len3+len2; + length_der(len2+len3,NULL,&len4); + temp2=(unsigned char *)malloc(len2+len3+len4); + octet_der(der+counter,len2+len3,temp2,&len4); + set_value(p,temp2,len4); + free(temp2); + counter+=len2+len3; move=RIGHT; - // return ASN_ERROR_TYPE_ANY; break; default: move=(move==UP)?RIGHT:DOWN; @@ -1159,7 +1177,7 @@ get_der(char *name,unsigned char *der,int len) if(move==UP) p=find_up(p); } - check_asn(name,CHECK_NOT_USED); + delete_not_used(root); return (counter==len)?ASN_OK:ASN_DER_ERROR; } @@ -1167,7 +1185,7 @@ get_der(char *name,unsigned char *der,int len) int -get_start_end_der(char *name,unsigned char *der,int len,char *name_element,int *start, int *end) +get_start_end_der(node_asn *root,unsigned char *der,int len,char *name_element,int *start, int *end) { node_asn *node,*node_to_find,*p,*p2,*p3; char temp[128]; @@ -1176,8 +1194,8 @@ get_start_end_der(char *name,unsigned char *der,int len,char *name_element,int * unsigned int tag; long val; - node=find_node(name); - node_to_find=find_node(name_element); + node=root; + node_to_find=find_node(root,name_element); if(node_to_find==NULL) return ASN_ELEMENT_NOT_FOUND; @@ -1191,8 +1209,6 @@ get_start_end_der(char *name,unsigned char *der,int len,char *name_element,int * if(node->type&CONST_OPTION) return ASN_GENERIC_ERROR; - expand_asn(name,""); - counter=0; move=DOWN; p=node; @@ -1265,7 +1281,7 @@ get_start_end_der(char *name,unsigned char *der,int len,char *name_element,int * counter++; move=RIGHT; break; - case TYPE_INTEGER: + case TYPE_INTEGER: case TYPE_ENUMERATED: len2=get_length_der(der+counter,&len3); counter+=len3+len2; move=RIGHT; diff --git a/lib/cert_der.h b/lib/cert_der.h index 7209ad65c1..eff46ec559 100644 --- a/lib/cert_der.h +++ b/lib/cert_der.h @@ -7,6 +7,8 @@ #ifndef _GNUTLS_DER_H #define _GNUTLS_DER_H +#include "cert_asn1.h" + #define UNIVERSAL 0x00 #define APPLICATION 0x40 #define CONTEXT_SPECIFIC 0x80 @@ -14,12 +16,6 @@ #define STRUCTURED 0x20 -int -create_der(char *name,unsigned char *der,int *len); - -int -get_der(char *name,unsigned char *der,int len); - void octet_der(unsigned char *str,int str_len,unsigned char *der,int *der_len); @@ -32,16 +28,18 @@ bit_der(unsigned char *str,int bit_len,unsigned char *der,int *der_len); void get_bit_der(unsigned char *der,int *der_len,unsigned char *str,int *bit_len); -void -length_der(unsigned long len,unsigned char *ans,int *ans_len); - -unsigned int -get_tag_der(unsigned char *der,unsigned char *class,int *len); +int +create_der(node_asn *root,char *name,unsigned char *der,int *len); -unsigned long -get_length_der(unsigned char *der,int *len); +int +get_der(node_asn *root,unsigned char *der,int len); -char * -ltostr(long v,char *str); +int +get_start_end_der(node_asn *root,unsigned char *der,int len,char *name_element,int *start, int *end); #endif + + + + + diff --git a/lib/gnutls_cert.c b/lib/gnutls_cert.c index 85a52edd6c..d9ffa04b5e 100644 --- a/lib/gnutls_cert.c +++ b/lib/gnutls_cert.c @@ -28,6 +28,7 @@ #include #include #include +#include /* KX mappings to PK algorithms */ typedef struct { @@ -217,26 +218,27 @@ static int _read_rsa_params(opaque * der, int dersize, MPI ** params) { opaque str[5 * 1024]; int len, result; + node_asn *spk; if (create_structure - ("rsa_public_key", "PKIX1Explicit88.RSAPublicKey") != ASN_OK) { + ( _gnutls_get_pkcs(), "PKCS-1.RSAPublicKey", &spk, "rsa_public_key") != ASN_OK) { gnutls_assert(); return GNUTLS_E_ASN1_ERROR; } - result = get_der("rsa_public_key", der, dersize); + result = get_der ( spk, der, dersize); if (result != ASN_OK) { gnutls_assert(); - delete_structure("rsa_public_key"); + delete_structure(spk); return GNUTLS_E_ASN1_PARSING_ERROR; } len = sizeof(str) - 1; - result = read_value("rsa_public_key.modulus", str, &len); + result = read_value(spk, "rsa_public_key.modulus", str, &len); if (result != ASN_OK) { gnutls_assert(); - delete_structure("rsa_public_key"); + delete_structure(spk); return GNUTLS_E_ASN1_PARSING_ERROR; } @@ -246,17 +248,17 @@ static int _read_rsa_params(opaque * der, int dersize, MPI ** params) if (gcry_mpi_scan(&(*params)[0], GCRYMPI_FMT_USG, str, &len) != 0) { gnutls_assert(); gnutls_free((*params)); - delete_structure("rsa_public_key"); + delete_structure(spk); return GNUTLS_E_MPI_SCAN_FAILED; } len = sizeof(str) - 1; - result = read_value("rsa_public_key.publicExponent", str, &len); + result = read_value(spk, "rsa_public_key.publicExponent", str, &len); if (result != ASN_OK) { gnutls_assert(); _gnutls_mpi_release(&(*params)[0]); gnutls_free((*params)); - delete_structure("rsa_public_key"); + delete_structure(spk); return GNUTLS_E_ASN1_PARSING_ERROR; } @@ -265,92 +267,114 @@ static int _read_rsa_params(opaque * der, int dersize, MPI ** params) gnutls_assert(); _gnutls_mpi_release(&(*params)[0]); gnutls_free((*params)); - delete_structure("rsa_public_key"); + delete_structure(spk); return GNUTLS_E_MPI_SCAN_FAILED; } - delete_structure("rsa_public_key"); + delete_structure(spk); return 0; } - - #define _READ( str, OID, NAME, res) \ if(strcmp(str, OID)==0){ \ - strcpy( str, "PKIX1Explicit88.X520"); \ + strcpy( str, "PKIX1Implicit88.X520"); \ strcat( str, NAME); \ strcpy( name2, "temp-structure-"); \ strcat( name2, NAME); \ - if ( (result = create_structure( name2, str)) != ASN_OK) { \ + if ( (result = create_structure( _gnutls_get_pkix(), str, &tmpasn, name2)) != ASN_OK) { \ gnutls_assert(); \ return GNUTLS_E_ASN1_ERROR; \ } \ len = sizeof(str) - 1; \ - if (read_value(name3,str,&len) != ASN_OK) { \ - delete_structure( name2); \ + if (read_value( tmpasn, name3, str,&len) != ASN_OK) { \ + delete_structure( tmpasn); \ continue; \ } \ - if (get_der( name2, str, len) != ASN_OK) { \ - delete_structure( name2); \ + if (get_der( tmpasn, str, len) != ASN_OK) { \ + delete_structure( tmpasn); \ continue; \ } \ strcpy( name3,name2); \ len = sizeof(str) - 1; \ - if (read_value( name3, str, &len) != ASN_OK) { /* CHOICE */ \ - delete_structure( name2); \ + if (read_value( tmpasn, name3, str, &len) != ASN_OK) { /* CHOICE */ \ + delete_structure( tmpasn); \ continue; \ } \ strcat( name3, "."); \ strcat( name3, str); \ len = sizeof(str) - 1; \ - if (read_value(name3,str,&len) != ASN_OK) { \ - delete_structure( name2); \ + if (read_value( tmpasn, name3, str,&len) != ASN_OK) { \ + delete_structure( tmpasn); \ continue; \ } \ str[len]=0; \ + fprintf(stderr, "XXX - %s: %s\n", name3, str); \ res = strdup(str); \ - delete_structure(name2); \ + delete_structure( tmpasn); \ } +/* this function will convert up to 3 digit + * numbers to characters. + */ +static void int2str(int k, char* data) { + if (k > 999) data[0] = 0; + else sprintf( data, "%d", k); +} + /* This function will attempt to read a Name * ASN.1 structure. (Taken from Fabio's samples!) * --nmav */ -static int _get_Name_type(char *root, gnutls_cert * gCert) +static int _get_Name_type( node_asn *rasn, char *root, gnutls_cert * gCert) { int k, k2, result, len; char name[128], str[1024], name2[128], counter[5], name3[128]; - k = 1; + k = 0; do { + k++; + strcpy(name, root); strcat(name, ".rdnSequence.?"); - ltostr(k, counter); + int2str(k, counter); strcat(name, counter); len = sizeof(str) - 1; - result = read_value(name, str, &len); - if (result == ASN_ELEMENT_NOT_FOUND) + result = read_value( rasn, name, str, &len); + + /* move to next + */ + if (result == ASN_VALUE_NOT_FOUND) continue; + + if (result != ASN_OK) { break; - k2 = 1; + } + + k2 = 0; do { + k2++; + strcpy(name2, name); strcat(name2, ".?"); - ltostr(k2, counter); + int2str(k2, counter); strcat(name2, counter); len = sizeof(str) - 1; - result = read_value(name2, str, &len); - if (result == ASN_ELEMENT_NOT_FOUND) + result = read_value( rasn, name2, str, &len); + + if (result==ASN_VALUE_NOT_FOUND) continue; + + if (result != ASN_OK) break; + strcpy(name3, name2); strcat(name3, ".type"); len = sizeof(str) - 1; - result = read_value(name3, str, &len); + result = read_value( rasn, name3, str, &len); if (result != ASN_OK) { gnutls_assert(); @@ -360,10 +384,10 @@ static int _get_Name_type(char *root, gnutls_cert * gCert) strcat(name3, ".value"); if (result == ASN_OK) { -/* _READ(str, "2 5 4 6", "countryName", - * gCert->country); - * This one fails (with SIGSEGV). - */ + node_asn *tmpasn; + + _READ(str, "2 5 4 6", "countryName", + gCert->country); _READ(str, "2 5 4 10", "OrganizationName", gCert->organization); _READ(str, "2 5 4 11", @@ -377,27 +401,30 @@ static int _get_Name_type(char *root, gnutls_cert * gCert) "StateOrProvinceName", gCert->state_or_province_name); } - k2++; } while (1); - k++; } while (1); - return 0; + + if (result==ASN_ELEMENT_NOT_FOUND) + return 0; + else {fprintf(stderr, "result: %d\n", result); + return GNUTLS_E_ASN1_PARSING_ERROR;} } int _gnutls_cert2gnutlsCert(gnutls_cert * gCert, gnutls_datum derCert) { int result; + node_asn *c2; opaque str[5 * 1024]; int len = sizeof(str); - if (create_structure("certificate3", "PKIX1Explicit88.Certificate") + if (create_structure( _gnutls_get_pkix(), "PKIX1Implicit88.Certificate", &c2, "certificate2") != ASN_OK) { gnutls_assert(); return GNUTLS_E_ASN1_ERROR; } - result = get_der("certificate3", derCert.data, derCert.size); + result = get_der( c2, derCert.data, derCert.size); if (result != ASN_OK) { /* couldn't decode DER */ gnutls_assert(); @@ -408,12 +435,12 @@ int _gnutls_cert2gnutlsCert(gnutls_cert * gCert, gnutls_datum derCert) len = sizeof(str) - 1; result = read_value - ("certificate3.tbsCertificate.subjectPublicKeyInfo.algorithm.algorithm", + (c2, "certificate2.tbsCertificate.subjectPublicKeyInfo.algorithm.algorithm", str, &len); if (result != ASN_OK) { gnutls_assert(); - delete_structure("certificate3"); + delete_structure(c2); return GNUTLS_E_ASN1_PARSING_ERROR; } @@ -426,7 +453,7 @@ int _gnutls_cert2gnutlsCert(gnutls_cert * gCert, gnutls_datum derCert) len = sizeof(str) - 1; result = read_value - ("certificate3.tbsCertificate.subjectPublicKeyInfo.subjectPublicKey", + (c2, "certificate2.tbsCertificate.subjectPublicKeyInfo.subjectPublicKey", str, &len); if (result != ASN_OK) { @@ -445,7 +472,7 @@ int _gnutls_cert2gnutlsCert(gnutls_cert * gCert, gnutls_datum derCert) * currently not supported */ gnutls_assert(); - delete_structure("certificate3"); + delete_structure(c2); return GNUTLS_E_UNIMPLEMENTED_FEATURE; } @@ -459,15 +486,15 @@ int _gnutls_cert2gnutlsCert(gnutls_cert * gCert, gnutls_datum derCert) gCert->organizational_unit_name = NULL; gCert->locality_name = NULL; gCert->state_or_province_name = NULL; + if ((result = - _get_Name_type("certificate3.tbsCertificate.subject", - gCert)) < 0) { + _get_Name_type( c2, "certificate2.tbsCertificate.subject", gCert)) < 0) { gnutls_assert(); - delete_structure("certificate3"); + delete_structure(c2); return result; } - delete_structure("certificate3"); + delete_structure(c2); if (gnutls_set_datum(&gCert->raw, derCert.data, derCert.size) < 0) { gnutls_assert(); diff --git a/lib/gnutls_global.c b/lib/gnutls_global.c index 15e969e9b2..cd2fe72204 100644 --- a/lib/gnutls_global.c +++ b/lib/gnutls_global.c @@ -28,6 +28,16 @@ static void* old_sig_handler; ssize_t (*recv_func)( SOCKET, void*, size_t, int); ssize_t (*send_func)( SOCKET,const void*, size_t, int); +static node_asn *PKIX1_ASN; +static node_asn *PKCS1_ASN; + +node_asn* _gnutls_get_pkix() { + return PKIX1_ASN; +} + +node_asn* _gnutls_get_pkcs() { + return PKCS1_ASN; +} int gnutls_is_secure_memory(const void* mem) { return 0; @@ -64,13 +74,13 @@ int gnutls_global_init(char* PKIX, char* PKCS1) * version. */ - result = parser_asn1(PKIX); + result = parser_asn1(PKIX, &PKIX1_ASN); if (result != ASN_OK) { return GNUTLS_E_ASN1_PARSING_ERROR; } - result = parser_asn1(PKCS1); + result = parser_asn1(PKCS1, &PKCS1_ASN); if (result != ASN_OK) { return GNUTLS_E_PARSING_ERROR; @@ -91,6 +101,7 @@ void gnutls_global_deinit() { #ifdef HAVE_SIGNAL signal( SIGPIPE, old_sig_handler); #endif - + delete_structure( PKCS1_ASN); + delete_structure( PKIX1_ASN); } diff --git a/lib/gnutls_int.h b/lib/gnutls_int.h index 399342659b..adccc6413a 100644 --- a/lib/gnutls_int.h +++ b/lib/gnutls_int.h @@ -30,9 +30,9 @@ #define HARD_DEBUG #define BUFFERS_DEBUG #define RECORD_DEBUG -#define HANDSHAKE_DEBUG +#define HANDSHAKE_DEBUG*/ #define DEBUG -*/ + #define SOCKET int #define LIST ... diff --git a/lib/gnutls_privkey.c b/lib/gnutls_privkey.c index 5770a60077..9d456ac934 100644 --- a/lib/gnutls_privkey.c +++ b/lib/gnutls_privkey.c @@ -28,6 +28,7 @@ #include #include #include +#include /* Converts an RSA PKCS#1 key to * an internal structure (gnutls_private_key) @@ -36,19 +37,20 @@ int _gnutls_pkcs1key2gnutlsKey(gnutls_private_key * pkey, gnutls_datum cert) { int result; opaque str[5*1024]; int len = sizeof(str); - + node_asn *pkcs_asn; + pkey->pk_algorithm = GNUTLS_PK_RSA; /* we do return 2 MPIs */ pkey->params = gnutls_malloc(2*sizeof(MPI)); - if (create_structure("rsakey", "PKCS-1.RSAPrivateKey")!=ASN_OK) { + if (create_structure( _gnutls_get_pkcs(), "PKCS-1.RSAPrivateKey", &pkcs_asn, "rsakey")!=ASN_OK) { gnutls_assert(); return GNUTLS_E_ASN1_ERROR; } - result = get_der("rsakey", cert.data, cert.size); + result = get_der( pkcs_asn, cert.data, cert.size); if (result != ASN_OK) { gnutls_assert(); return GNUTLS_E_ASN1_PARSING_ERROR; @@ -56,26 +58,26 @@ int _gnutls_pkcs1key2gnutlsKey(gnutls_private_key * pkey, gnutls_datum cert) { len = sizeof(str) - 1; result = - read_value("rsakey.privateExponent", str, &len); + read_value( pkcs_asn, "rsakey.privateExponent", str, &len); if (result != ASN_OK) { gnutls_assert(); - delete_structure("rsakey"); + delete_structure(pkcs_asn); return GNUTLS_E_ASN1_PARSING_ERROR; } if (gcry_mpi_scan( &pkey->params[0], /* u */ GCRYMPI_FMT_USG, str, &len) != 0) { gnutls_assert(); - delete_structure("rsakey"); + delete_structure(pkcs_asn); return GNUTLS_E_MPI_SCAN_FAILED; } len = sizeof(str) - 1; result = - read_value("rsakey.modulus", str, &len); + read_value( pkcs_asn, "rsakey.modulus", str, &len); if (result != ASN_OK) { gnutls_assert(); - delete_structure("rsakey"); + delete_structure(pkcs_asn); _gnutls_mpi_release( &pkey->params[0]); return GNUTLS_E_ASN1_PARSING_ERROR; } @@ -83,12 +85,12 @@ int _gnutls_pkcs1key2gnutlsKey(gnutls_private_key * pkey, gnutls_datum cert) { if (gcry_mpi_scan( &pkey->params[1], /* A */ GCRYMPI_FMT_USG, str, &len) != 0) { gnutls_assert(); - delete_structure("rsakey"); + delete_structure(pkcs_asn); _gnutls_mpi_release( &pkey->params[0]); return GNUTLS_E_MPI_SCAN_FAILED; } - delete_structure("rsakey"); + delete_structure(pkcs_asn); if (gnutls_set_datum( &pkey->raw, cert.data, cert.size) < 0) { _gnutls_mpi_release(&pkey->params[0]); diff --git a/src/CertificateExample.c b/src/CertificateExample.c index 33424f86f8..063dba73d7 100644 --- a/src/CertificateExample.c +++ b/src/CertificateExample.c @@ -18,10 +18,11 @@ /* "C=US O=gov" */ /******************************************************/ void -get_Name_type(char *root, char *answer) +get_Name_type(node_asn *cert_def,node_asn *cert,char *root, char *answer) { int k,k2,result,len; char name[128],str[1024],name2[128],counter[5],name3[128]; + node_asn *value; answer[0]=0; k=1; @@ -30,7 +31,7 @@ get_Name_type(char *root, char *answer) strcat(name,".rdnSequence.?"); ltostr(k,counter); strcat(name,counter); - result=read_value(name,str,&len); + result=read_value(cert,name,str,&len); if(result==ASN_ELEMENT_NOT_FOUND) break; k2=1; do{ @@ -38,55 +39,55 @@ get_Name_type(char *root, char *answer) strcat(name2,".?"); ltostr(k2,counter); strcat(name2,counter); - result=read_value(name2,str,&len); + result=read_value(cert,name2,str,&len); if(result==ASN_ELEMENT_NOT_FOUND) break; strcpy(name3,name2); strcat(name3,".type"); - result=read_value(name3,str,&len); + result=read_value(cert,name3,str,&len); strcpy(name3,name2); strcat(name3,".value"); if(result==ASN_OK){ if(!strcmp(str,"2 5 4 6")){ - create_structure("certificate2-subject-C","PKIX1Explicit88.X520OrganizationName"); //X520countryName"); - read_value(name3,str,&len); - get_der("certificate2-subject-C",str,len); + create_structure(cert_def,"PKIX1Implicit88.X520OrganizationName",&value,"certificate2-subject-C"); //X520countryName"); + read_value(cert,name3,str,&len); + get_der(value,str,len); strcpy(name3,"certificate2-subject-C"); - read_value(name3,str,&len); /* CHOICE */ + read_value(value,name3,str,&len); /* CHOICE */ strcat(name3,"."); strcat(name3,str); - read_value(name3,str,&len); + read_value(value,name3,str,&len); str[len]=0; strcat(answer," C="); strcat(answer,str); - delete_structure("certificate2-subject-C"); + delete_structure(value); } else if(!strcmp(str,"2 5 4 10")){ - create_structure("certificate2-subject-O","PKIX1Explicit88.X520OrganizationName"); - read_value(name3,str,&len); - get_der("certificate2-subject-O",str,len); + create_structure(cert_def,"PKIX1Implicit88.X520OrganizationName",&value,"certificate2-subject-O"); + read_value(cert,name3,str,&len); + get_der(value,str,len); strcpy(name3,"certificate2-subject-O"); - read_value(name3,str,&len); /* CHOICE */ + read_value(value,name3,str,&len); /* CHOICE */ strcat(name3,"."); strcat(name3,str); - read_value(name3,str,&len); + read_value(value,name3,str,&len); str[len]=0; strcat(answer," O="); strcat(answer,str); - delete_structure("certificate2-subject-O"); + delete_structure(value); } else if(!strcmp(str,"2 5 4 11")){ - create_structure("certificate2-subject-OU","PKIX1Explicit88.X520OrganizationalUnitName"); - read_value(name3,str,&len); - get_der("certificate2-subject-OU",str,len); + create_structure(cert_def,"PKIX1Implicit88.X520OrganizationalUnitName",&value,"certificate2-subject-OU"); + read_value(cert,name3,str,&len); + get_der(value,str,len); strcpy(name3,"certificate2-subject-OU"); - read_value(name3,str,&len); /* CHOICE */ + read_value(value,name3,str,&len); /* CHOICE */ strcat(name3,"."); strcat(name3,str); - read_value(name3,str,&len); + read_value(value,name3,str,&len); str[len]=0; strcat(answer," OU="); strcat(answer,str); - delete_structure("certificate2-subject-OU"); + delete_structure(value); } } k2++; @@ -106,160 +107,186 @@ get_Name_type(char *root, char *answer) /* int *der_len: number of bytes of der string */ /******************************************************/ void -create_certificate(unsigned char *der,int *der_len) +create_certificate(node_asn *cert_def,unsigned char *der,int *der_len) { int result,k,len; unsigned char str[1024],*str2; + node_asn *cert1,*value,*param,*constr; - - result=create_structure("certificate1","PKIX1Explicit88.Certificate"); + result=create_structure(cert_def,"PKIX1Implicit88.Certificate",&cert1,"certificate1"); /* Use the next 3 lines to visit the empty certificate */ /* printf("-----------------\n"); - visit_tree("certificate1"); + visit_tree(cert1,"certificate1"); printf("-----------------\n"); */ /* version: 2 */ str[0]=0x02; - result=write_value("certificate1.tbsCertificate.version",str,1); + result=write_value(cert1,"certificate1.tbsCertificate.version",str,1); /* serialNumber: 17 */ str[0]=17; - result=write_value("certificate1.tbsCertificate.serialNumber",str,1); + result=write_value(cert1,"certificate1.tbsCertificate.serialNumber",str,1); /* signature: dsa-with-sha */ - result=write_value("certificate1.tbsCertificate.signature.algorithm","1 2 840 10040 4 3",17); + result=write_value(cert1,"certificate1.tbsCertificate.signature.algorithm","1 2 840 10040 4 3",1); - result=write_value("certificate1.tbsCertificate.signature.parameters",NULL,0); + result=write_value(cert1,"certificate1.tbsCertificate.signature.parameters",NULL,0); + /* issuer: Country="US" Organization="gov" OrganizationUnit="nist" */ - result=write_value("certificate1.tbsCertificate.issuer","rdnSequence",12); + result=write_value(cert1,"certificate1.tbsCertificate.issuer","rdnSequence",12); - result=write_value("certificate1.tbsCertificate.issuer.rdnSequence","NEW",4); - result=write_value("certificate1.tbsCertificate.issuer.rdnSequence.?LAST","NEW",4); + result=write_value(cert1,"certificate1.tbsCertificate.issuer.rdnSequence","NEW",1); + result=write_value(cert1,"certificate1.tbsCertificate.issuer.rdnSequence.?LAST","NEW",1); /* C */ - result=write_value("certificate1.tbsCertificate.issuer.rdnSequence.?LAST.?LAST.type","2 5 4 6",8); - result=write_value("certificate1.tbsCertificate.issuer.rdnSequence.?LAST.?LAST.value", - "PKIX1Explicit88.X520countryName",13); - result=write_value("certificate1.tbsCertificate.issuer.rdnSequence.?LAST.?LAST.value","US",2); + result=write_value(cert1,"certificate1.tbsCertificate.issuer.rdnSequence.?LAST.?LAST.type","2 5 4 6",1); + result=create_structure(cert_def,"PKIX1Implicit88.X520countryName", + &value,"countryName"); + result=write_value(value,"countryName","US",2); + result=create_der(value,"countryName",der,der_len); + delete_structure(value); + result=write_value(cert1,"certificate1.tbsCertificate.issuer.rdnSequence.?LAST.?LAST.value",der,*der_len); - result=write_value("certificate1.tbsCertificate.issuer.rdnSequence","NEW",4); - result=write_value("certificate1.tbsCertificate.issuer.rdnSequence.?LAST","NEW",4); + result=write_value(cert1,"certificate1.tbsCertificate.issuer.rdnSequence","NEW",1); + result=write_value(cert1,"certificate1.tbsCertificate.issuer.rdnSequence.?LAST","NEW",1); /* O */ - result=write_value("certificate1.tbsCertificate.issuer.rdnSequence.?LAST.?LAST.type","2 5 4 10",8); - result=write_value("certificate1.tbsCertificate.issuer.rdnSequence.?LAST.?LAST.value", - "PKIX1Explicit88.X520OrganizationName",13); - result=write_value("certificate1.tbsCertificate.issuer.rdnSequence.?LAST.?LAST.value", - "printableString",1); - result=write_value("certificate1.tbsCertificate.issuer.rdnSequence.?LAST.?LAST.value.printableString", - "gov",3); - - result=write_value("certificate1.tbsCertificate.issuer.rdnSequence","NEW",4); - result=write_value("certificate1.tbsCertificate.issuer.rdnSequence.?LAST","NEW",4); + result=write_value(cert1,"certificate1.tbsCertificate.issuer.rdnSequence.?LAST.?LAST.type","2 5 4 10",1); + result=create_structure(cert_def,"PKIX1Implicit88.X520OrganizationName", + &value,"OrgName"); + result=write_value(value,"OrgName","printableString",1); + result=write_value(value,"OrgName.printableString","gov",3); + result=create_der(value,"OrgName",der,der_len); + delete_structure(value); + result=write_value(cert1,"certificate1.tbsCertificate.issuer.rdnSequence.?LAST.?LAST.value",der,*der_len); + + + result=write_value(cert1,"certificate1.tbsCertificate.issuer.rdnSequence","NEW",1); + result=write_value(cert1,"certificate1.tbsCertificate.issuer.rdnSequence.?LAST","NEW",1); + /* OU */ - result=write_value("certificate1.tbsCertificate.issuer.rdnSequence.?LAST.?LAST.type","2 5 4 11",8); - result=write_value("certificate1.tbsCertificate.issuer.rdnSequence.?LAST.?LAST.value", - "PKIX1Explicit88.X520OrganizationalUnitName",13); - result=write_value("certificate1.tbsCertificate.issuer.rdnSequence.?LAST.?LAST.value", - "printableString",1); - result=write_value("certificate1.tbsCertificate.issuer.rdnSequence.?LAST.?LAST.value.printableString", - "nist",4); + result=write_value(cert1,"certificate1.tbsCertificate.issuer.rdnSequence.?LAST.?LAST.type","2 5 4 11",1); + result=create_structure(cert_def,"PKIX1Implicit88.X520OrganizationalUnitName",&value,"OrgUnitName"); + result=write_value(value,"OrgUnitName","printableString",1); + result=write_value(value,"OrgUnitName.printableString","nist",4); + result=create_der(value,"OrgUnitName",der,der_len); + delete_structure(value); + result=write_value(cert1,"certificate1.tbsCertificate.issuer.rdnSequence.?LAST.?LAST.value",der,*der_len); + /* validity */ - result=write_value("certificate1.tbsCertificate.validity.notBefore","utcTime",1); - result=write_value("certificate1.tbsCertificate.validity.notBefore.utcTime","970630000000Z",1); + result=write_value(cert1,"certificate1.tbsCertificate.validity.notBefore","utcTime",1); + result=write_value(cert1,"certificate1.tbsCertificate.validity.notBefore.utcTime","970630000000Z",1); - result=write_value("certificate1.tbsCertificate.validity.notAfter","utcTime",1); - result=write_value("certificate1.tbsCertificate.validity.notAfter.utcTime","971231000000Z",1); + result=write_value(cert1,"certificate1.tbsCertificate.validity.notAfter","utcTime",1); + result=write_value(cert1,"certificate1.tbsCertificate.validity.notAfter.utcTime","971231000000Z",1); /* subject: Country="US" Organization="gov" OrganizationUnit="nist" */ - result=write_value("certificate1.tbsCertificate.subject","rdnSequence",1); + result=write_value(cert1,"certificate1.tbsCertificate.subject","rdnSequence",1); - result=write_value("certificate1.tbsCertificate.subject.rdnSequence","NEW",1); - result=write_value("certificate1.tbsCertificate.subject.rdnSequence.?LAST","NEW",1); + result=write_value(cert1,"certificate1.tbsCertificate.subject.rdnSequence","NEW",1); + result=write_value(cert1,"certificate1.tbsCertificate.subject.rdnSequence.?LAST","NEW",1); /* C */ - result=write_value("certificate1.tbsCertificate.subject.rdnSequence.?LAST.?LAST.type","2 5 4 6",1); - result=write_value("certificate1.tbsCertificate.subject.rdnSequence.?LAST.?LAST.value", - "PKIX1Explicit88.X520countryName",13); - result=write_value("certificate1.tbsCertificate.subject.rdnSequence.?LAST.?LAST.value","US",2); + result=write_value(cert1,"certificate1.tbsCertificate.subject.rdnSequence.?LAST.?LAST.type","2 5 4 6",1); + result=create_structure(cert_def,"PKIX1Implicit88.X520countryName", + &value,"countryName"); + result=write_value(value,"countryName","US",2); + result=create_der(value,"countryName",der,der_len); + delete_structure(value); + result=write_value(cert1,"certificate1.tbsCertificate.subject.rdnSequence.?LAST.?LAST.value",der,*der_len); + - result=write_value("certificate1.tbsCertificate.subject.rdnSequence","NEW",4); - result=write_value("certificate1.tbsCertificate.subject.rdnSequence.?LAST","NEW",4); + result=write_value(cert1,"certificate1.tbsCertificate.subject.rdnSequence","NEW",4); + result=write_value(cert1,"certificate1.tbsCertificate.subject.rdnSequence.?LAST","NEW",4); /* O */ - result=write_value("certificate1.tbsCertificate.subject.rdnSequence.?LAST.?LAST.type","2 5 4 10",8); - result=write_value("certificate1.tbsCertificate.subject.rdnSequence.?LAST.?LAST.value", - "PKIX1Explicit88.X520OrganizationName",13); - result=write_value("certificate1.tbsCertificate.subject.rdnSequence.?LAST.?LAST.value", - "printableString",1); - result=write_value("certificate1.tbsCertificate.subject.rdnSequence.?LAST.?LAST.value.printableString", - "gov",3); - - result=write_value("certificate1.tbsCertificate.subject.rdnSequence","NEW",4); - result=write_value("certificate1.tbsCertificate.subject.rdnSequence.?LAST","NEW",4); + result=write_value(cert1,"certificate1.tbsCertificate.subject.rdnSequence.?LAST.?LAST.type","2 5 4 10",8); + result=create_structure(cert_def,"PKIX1Implicit88.X520OrganizationName", + &value,"OrgName"); + result=write_value(value,"OrgName","printableString",1); + result=write_value(value,"OrgName.printableString","gov",3); + result=create_der(value,"OrgName",der,der_len); + delete_structure(value); + result=write_value(cert1,"certificate1.tbsCertificate.subject.rdnSequence.?LAST.?LAST.value",der,*der_len); + + + result=write_value(cert1,"certificate1.tbsCertificate.subject.rdnSequence","NEW",4); + result=write_value(cert1,"certificate1.tbsCertificate.subject.rdnSequence.?LAST","NEW",4); /* OU */ - result=write_value("certificate1.tbsCertificate.subject.rdnSequence.?LAST.?LAST.type","2 5 4 11",8); - result=write_value("certificate1.tbsCertificate.subject.rdnSequence.?LAST.?LAST.value", - "PKIX1Explicit88.X520OrganizationalUnitName",13); - result=write_value("certificate1.tbsCertificate.subject.rdnSequence.?LAST.?LAST.value", - "printableString",1); - result=write_value("certificate1.tbsCertificate.subject.rdnSequence.?LAST.?LAST.value.printableString", - "nist",4); + result=write_value(cert1,"certificate1.tbsCertificate.subject.rdnSequence.?LAST.?LAST.type","2 5 4 11",8); + result=create_structure(cert_def,"PKIX1Implicit88.X520OrganizationalUnitName",&value,"OrgUnitName"); + result=write_value(value,"OrgUnitName","printableString",1); + result=write_value(value,"OrgUnitName.printableString","nist",4); + result=create_der(value,"OrgUnitName",der,der_len); + delete_structure(value); + result=write_value(cert1,"certificate1.tbsCertificate.subject.rdnSequence.?LAST.?LAST.value",der,*der_len); /* subjectPublicKeyInfo: dsa with parameters=Dss-Parms */ - result=write_value("certificate1.tbsCertificate.subjectPublicKeyInfo.algorithm.algorithm","1 2 840 10040 4 1",1); - result=write_value("certificate1.tbsCertificate.subjectPublicKeyInfo.algorithm.parameters","Dss-Parms",1); + result=write_value(cert1,"certificate1.tbsCertificate.subjectPublicKeyInfo.algorithm.algorithm","1 2 840 10040 4 1",1); + result=create_structure(cert_def,"PKIX1Implicit88.Dss-Parms",¶m,"parameters"); str2="\xd4\x38"; /* only an example */ - result=write_value("certificate1.tbsCertificate.subjectPublicKeyInfo.algorithm.parameters.p",str2,128); + result=write_value(param,"parameters.p",str2,128); str2="\xd4\x38"; /* only an example */ - result=write_value("certificate1.tbsCertificate.subjectPublicKeyInfo.algorithm.parameters.q",str2,20); + result=write_value(param,"parameters.q",str2,20); str2="\xd4\x38"; /* only an example */ - result=write_value("certificate1.tbsCertificate.subjectPublicKeyInfo.algorithm.parameters.g",str2,128); + result=write_value(param,"parameters.g",str2,128); + result=create_der(param,"parameters",der,der_len); + delete_structure(param); + result=write_value(cert1,"certificate1.tbsCertificate.subjectPublicKeyInfo.algorithm.parameters",der,*der_len); + /* subjectPublicKey */ str2="\x02\x81"; /* only an example */ - result=write_value("certificate1.tbsCertificate.subjectPublicKeyInfo.subjectPublicKey",str2,1048); + result=write_value(cert1,"certificate1.tbsCertificate.subjectPublicKeyInfo.subjectPublicKey",str2,1048); - result=write_value("certificate1.tbsCertificate.issuerUniqueID",NULL,0); /* NO OPTION */ - result=write_value("certificate1.tbsCertificate.subjectUniqueID",NULL,0); /* NO OPTION */ + result=write_value(cert1,"certificate1.tbsCertificate.issuerUniqueID",NULL,0); /* NO OPTION */ + result=write_value(cert1,"certificate1.tbsCertificate.subjectUniqueID",NULL,0); /* NO OPTION */ /* extensions */ - result=write_value("certificate1.tbsCertificate.extensions","NEW",1); - result=write_value("certificate1.tbsCertificate.extensions.?LAST.extnID","2 5 29 19",1); /* basicConstraints */ - result=write_value("certificate1.tbsCertificate.extensions.?LAST.critical","TRUE",1); - str2="\x30\x03\x01\x01\xff"; /* only an example */ - result=write_value("certificate1.tbsCertificate.extensions.?LAST.extnValue",str2,5); - - result=write_value("certificate1.tbsCertificate.extensions","NEW",1); - result=write_value("certificate1.tbsCertificate.extensions.?LAST.extnID","2 5 29 14",1); /* subjectKeyIdentifier */ - result=write_value("certificate1.tbsCertificate.extensions.?LAST.critical","FALSE",1); + result=write_value(cert1,"certificate1.tbsCertificate.extensions","NEW",1); + result=write_value(cert1,"certificate1.tbsCertificate.extensions.?LAST.extnID","2 5 29 19",1); /* basicConstraints */ + result=write_value(cert1,"certificate1.tbsCertificate.extensions.?LAST.critical","TRUE",1); + result=create_structure(cert_def,"PKIX1Implicit88.BasicConstraints",&constr, + "basicConstraints1"); + result=write_value(constr,"basicConstraints1.cA","TRUE",1); + result=write_value(constr,"basicConstraints1.pathLenConstraint",NULL,0); + result=create_der(constr,"basicConstraints1",der,der_len); + result=delete_structure(constr); + result=write_value(cert1,"certificate1.tbsCertificate.extensions.?LAST.extnValue",der,*der_len); + + + result=write_value(cert1,"certificate1.tbsCertificate.extensions","NEW",1); + result=write_value(cert1,"certificate1.tbsCertificate.extensions.?LAST.extnID","2 5 29 14",1); /* subjectKeyIdentifier */ + result=write_value(cert1,"certificate1.tbsCertificate.extensions.?LAST.critical","FALSE",1); str2="\x04\x14\xe7\x26\xc5"; /* only an example */ - result=write_value("certificate1.tbsCertificate.extensions.?LAST.extnValue",str2,22); + result=write_value(cert1,"certificate1.tbsCertificate.extensions.?LAST.extnValue",str2,22); + /* signatureAlgorithm: dsa-with-sha */ - result=write_value("certificate1.signatureAlgorithm.algorithm","1 2 840 10040 4 3",1); - result=write_value("certificate1.signatureAlgorithm.parameters",NULL,0); /* NO OPTION */ + result=write_value(cert1,"certificate1.signatureAlgorithm.algorithm","1 2 840 10040 4 3",1); + result=write_value(cert1,"certificate1.signatureAlgorithm.parameters",NULL,0); /* NO OPTION */ + /* signature */ - result=create_der("certificate1.tbsCertificate",der,der_len); + result=create_der(cert1,"certificate1.tbsCertificate",der,der_len); if(result!=ASN_OK){ printf("\n'tbsCertificate' encoding creation: ERROR\n"); - return; + // return; } /* add the lines for the signature on der[0]..der[der_len-1]: result in str2 */ - result=write_value("certificate1.signature",str2,368); /* dsa-with-sha */ + result=write_value(cert1,"certificate1.signature",str2,368); /* dsa-with-sha */ /* Use the next 3 lines to visit the certificate */ /* printf("-----------------\n"); - visit_tree("certificate1"); + visit_tree(cert1,"certificate1"); printf("-----------------\n"); */ - result=create_der("certificate1",der,der_len); + result=create_der(cert1,"certificate1",der,der_len); if(result!=ASN_OK){ printf("\n'certificate1' encoding creation: ERROR\n"); return; @@ -271,7 +298,7 @@ create_certificate(unsigned char *der,int *der_len) printf("\n-----------------\n"); /* Clear the "certificate1" structure */ - delete_structure("certificate1"); + delete_structure(cert1); } @@ -286,16 +313,16 @@ create_certificate(unsigned char *der,int *der_len) /* int der_len: number of bytes of der string */ /******************************************************/ void -get_certificate(unsigned char *der,int der_len) +get_certificate(node_asn *cert_def,unsigned char *der,int der_len) { int result,len,start,end; unsigned char str[1024]; + node_asn *cert2; + create_structure(cert_def,"PKIX1Implicit88.Certificate",&cert2,"certificate2"); - create_structure("certificate2","PKIX1Explicit88.Certificate"); + result=get_der(cert2,der,der_len); - result=get_der("certificate2",der,der_len); - if(result!=ASN_OK){ printf("Problems with DER encoding\n"); return; @@ -303,36 +330,37 @@ get_certificate(unsigned char *der,int der_len) /* issuer */ - get_Name_type("certificate2.tbsCertificate.issuer",str); + get_Name_type(cert_def,cert2,"certificate2.tbsCertificate.issuer",str); printf("certificate2:\nissuer =%s\n",str); /* subject */ - get_Name_type("certificate2.tbsCertificate.subject",str); + get_Name_type(cert_def,cert2,"certificate2.tbsCertificate.subject",str); printf("subject=%s\n",str); /* Verify sign */ - result=read_value("certificate2.signatureAlgorithm.algorithm",str,&len); + result=read_value(cert2,"certificate2.signatureAlgorithm.algorithm" + ,str,&len); if(!strcmp(str,"1 2 840 10040 4 3")){ /* dsa-with-sha */ - result=get_start_end_der("certificate2",der,der_len, + result=get_start_end_der(cert2,der,der_len, "certificate2.tbsCertificate",&start,&end); /* add the lines to calculate the sha on der[start]..der[end] */ - result=read_value("certificate2.signature",str,&len); + result=read_value(cert2,"certificate2.signature",str,&len); /* compare the previous value to signature ( with issuer public key) */ } /* Use the next 3 lines to visit the certificate */ - /* printf("-----------------\n"); - visit_tree("certificate2"); + /* printf("-----------------\n"); + visit_tree(cert2,"certificate2"); printf("-----------------\n"); */ /* Clear the "certificate2" structure */ - delete_structure("certificate2"); + delete_structure(cert2); } @@ -348,8 +376,9 @@ main(void) { int result,der_len; unsigned char der[1024]; + node_asn *PKIX1Implicit88; - result=parser_asn1("pkix.asn"); + result=parser_asn1("pkix.asn",&PKIX1Implicit88); if(result==ASN_SYNTAX_ERROR){ printf("PARSE ERROR\n"); @@ -361,18 +390,18 @@ main(void) } - /* Use the following 3 lines to visit the PKIX1Explicit structures */ + /* Use the following 3 lines to visit the PKIX1Implicit structures */ /* printf("-----------------\n"); - visit_tree("PKIX1Explicit88"); + visit_tree(PKIX1Implicit88,"PKIX1Implicit88"); printf("-----------------\n"); */ - create_certificate(der,&der_len); + create_certificate(PKIX1Implicit88,der,&der_len); - get_certificate(der,der_len); + get_certificate(PKIX1Implicit88,der,der_len); - /* Clear the "PKIX1Explicit88" structures */ - delete_structure("PKIX1Explicit88"); + /* Clear the "PKIX1Implicit88" structures */ + delete_structure(PKIX1Implicit88); return; } diff --git a/src/Makefile.am b/src/Makefile.am index abc1bac3b3..bb815c8547 100644 --- a/src/Makefile.am +++ b/src/Makefile.am @@ -1,5 +1,5 @@ EXTRA_DIST = port.h prime.gaa crypt.gaa crypt-gaa.h README.crypt prime-gaa.h \ - README tpasswd tpasswd.conf pkcs1.asn pkix.asn + README tpasswd tpasswd.conf pkcs1.asn pkix.asn cert.pem key.pem INCLUDES = -I../lib diff --git a/src/pkix.asn b/src/pkix.asn index aef812c57a..513790e83c 100644 --- a/src/pkix.asn +++ b/src/pkix.asn @@ -1,18 +1,320 @@ -PKIX1Explicit88 {iso(1) identified-organization(3) dod(6) internet(1) - security(5) mechanisms(5) pkix(7) id-mod(0) id-pkix1-explicit-88(1)} +PKIX1Implicit88 {iso(1) identified-organization(3) dod(6) internet(1) + security(5) mechanisms(5) pkix(7) id-mod(0) id-pkix1-implicit-88(2)} -DEFINITIONS EXPLICIT TAGS ::= +DEFINITIONS IMPLICIT TAGS ::= BEGIN --- EXPORTS ALL -- --- IMPORTS NONE -- +-- ISO arc for standard certificate and CRL extensions + +id-ce OBJECT IDENTIFIER ::= {joint-iso-ccitt(2) ds(5) 29} + + +-- authority key identifier OID and syntax + +id-ce-authorityKeyIdentifier OBJECT IDENTIFIER ::= { id-ce 35 } + +AuthorityKeyIdentifier ::= SEQUENCE { + keyIdentifier [0] KeyIdentifier OPTIONAL, + authorityCertIssuer [1] GeneralNames OPTIONAL, + authorityCertSerialNumber [2] CertificateSerialNumber OPTIONAL } + -- authorityCertIssuer and authorityCertSerialNumber shall both + -- be present or both be absgent + +KeyIdentifier ::= OCTET STRING + +-- subject key identifier OID and syntax + +id-ce-subjectKeyIdentifier OBJECT IDENTIFIER ::= { id-ce 14 } + +SubjectKeyIdentifier ::= KeyIdentifier + +-- key usage extension OID and syntax + +id-ce-keyUsage OBJECT IDENTIFIER ::= { id-ce 15 } + +KeyUsage ::= BIT STRING { + digitalSignature (0), + nonRepudiation (1), + keyEncipherment (2), + dataEncipherment (3), + keyAgreement (4), + keyCertSign (5), + cRLSign (6), + encipherOnly (7), + decipherOnly (8) } + +-- private key usage period extension OID and syntax + +id-ce-privateKeyUsagePeriod OBJECT IDENTIFIER ::= { id-ce 16 } + +PrivateKeyUsagePeriod ::= SEQUENCE { + notBefore [0] GeneralizedTime OPTIONAL, + notAfter [1] GeneralizedTime OPTIONAL } + -- either notBefore or notAfter shall be present + +-- certificate policies extension OID and syntax + +id-ce-certificatePolicies OBJECT IDENTIFIER ::= { id-ce 32 } + +CertificatePolicies ::= SEQUENCE SIZE (1..MAX) OF PolicyInformation + +PolicyInformation ::= SEQUENCE { + policyIdentifier CertPolicyId, + policyQualifiers SEQUENCE SIZE (1..MAX) OF + PolicyQualifierInfo OPTIONAL } + +CertPolicyId ::= OBJECT IDENTIFIER + +PolicyQualifierInfo ::= SEQUENCE { + policyQualifierId PolicyQualifierId, + qualifier ANY DEFINED BY policyQualifierId } + +-- Implementations that recognize additional policy qualifiers shall +-- augment the following definition for PolicyQualifierId + +PolicyQualifierId ::= + OBJECT IDENTIFIER -- ( id-qt-cps | id-qt-unotice ) + +-- CPS pointer qualifier + +CPSuri ::= IA5String + +-- user notice qualifier + +UserNotice ::= SEQUENCE { + noticeRef NoticeReference OPTIONAL, + explicitText DisplayText OPTIONAL} + +NoticeReference ::= SEQUENCE { + organization DisplayText, + noticeNumbers SEQUENCE OF INTEGER } + +DisplayText ::= CHOICE { + visibleString VisibleString (SIZE (1..200)), + bmpString BMPString (SIZE (1..200)), + utf8String UTF8String (SIZE (1..200)) } + +-- policy mapping extension OID and syntax + +id-ce-policyMappings OBJECT IDENTIFIER ::= { id-ce 33 } + +PolicyMappings ::= SEQUENCE SIZE (1..MAX) OF SEQUENCE { + issuerDomainPolicy CertPolicyId, + subjectDomainPolicy CertPolicyId } + +-- subject alternative name extension OID and syntax + +id-ce-subjectAltName OBJECT IDENTIFIER ::= { id-ce 17 } + +SubjectAltName ::= GeneralNames + +GeneralNames ::= SEQUENCE SIZE (1..MAX) OF GeneralName + +GeneralName ::= CHOICE { + otherName [0] AnotherName, + rfc822Name [1] IA5String, + dNSName [2] IA5String, + x400Address [3] ORAddress, + directoryName [4] Name, + ediPartyName [5] EDIPartyName, + uniformResourceIdentifier [6] IA5String, + iPAddress [7] OCTET STRING, + registeredID [8] OBJECT IDENTIFIER } + +-- AnotherName replaces OTHER-NAME ::= TYPE-IDENTIFIER, as +-- TYPE-IDENTIFIER is not supported in the '88 ASN.1 syntax + +AnotherName ::= SEQUENCE { + type-id OBJECT IDENTIFIER, + value [0] EXPLICIT ANY DEFINED BY type-id } + +EDIPartyName ::= SEQUENCE { + nameAssigner [0] DirectoryString OPTIONAL, + partyName [1] DirectoryString } + +-- issuer alternative name extension OID and syntax + +id-ce-issuerAltName OBJECT IDENTIFIER ::= { id-ce 18 } + +IssuerAltName ::= GeneralNames + +id-ce-subjectDirectoryAttributes OBJECT IDENTIFIER ::= { id-ce 9 } + +SubjectDirectoryAttributes ::= SEQUENCE SIZE (1..MAX) OF Attribute + +-- basic constraints extension OID and syntax + +id-ce-basicConstraints OBJECT IDENTIFIER ::= { id-ce 19 } + +BasicConstraints ::= SEQUENCE { + cA BOOLEAN DEFAULT FALSE, + pathLenConstraint INTEGER (0..MAX) OPTIONAL } + +-- name constraints extension OID and syntax + +id-ce-nameConstraints OBJECT IDENTIFIER ::= { id-ce 30 } + +NameConstraints ::= SEQUENCE { + permittedSubtrees [0] GeneralSubtrees OPTIONAL, + excludedSubtrees [1] GeneralSubtrees OPTIONAL } + +GeneralSubtrees ::= SEQUENCE SIZE (1..MAX) OF GeneralSubtree + +GeneralSubtree ::= SEQUENCE { + base GeneralName, + minimum [0] BaseDistance DEFAULT 0, + maximum [1] BaseDistance OPTIONAL } + +BaseDistance ::= INTEGER (0..MAX) + +-- policy constraints extension OID and syntax + +id-ce-policyConstraints OBJECT IDENTIFIER ::= { id-ce 36 } + +PolicyConstraints ::= SEQUENCE { + requireExplicitPolicy [0] SkipCerts OPTIONAL, + inhibitPolicyMapping [1] SkipCerts OPTIONAL } + +SkipCerts ::= INTEGER (0..MAX) + +-- CRL distribution points extension OID and syntax + +id-ce-cRLDistributionPoints OBJECT IDENTIFIER ::= {id-ce 31} + +CRLDistPointsSyntax ::= SEQUENCE SIZE (1..MAX) OF DistributionPoint + +DistributionPoint ::= SEQUENCE { + distributionPoint [0] DistributionPointName OPTIONAL, + reasons [1] ReasonFlags OPTIONAL, + cRLIssuer [2] GeneralNames OPTIONAL } + +DistributionPointName ::= CHOICE { + fullName [0] GeneralNames, + nameRelativeToCRLIssuer [1] RelativeDistinguishedName } + + + +ReasonFlags ::= BIT STRING { + unused (0), + keyCompromise (1), + cACompromise (2), + affiliationChanged (3), + superseded (4), + cessationOfOperation (5), + certificateHold (6) } + +-- extended key usage extension OID and syntax + +id-ce-extKeyUsage OBJECT IDENTIFIER ::= {id-ce 37} + +ExtKeyUsageSyntax ::= SEQUENCE SIZE (1..MAX) OF KeyPurposeId + +KeyPurposeId ::= OBJECT IDENTIFIER + +-- extended key purpose OIDs +id-kp-serverAuth OBJECT IDENTIFIER ::= { id-kp 1 } +id-kp-clientAuth OBJECT IDENTIFIER ::= { id-kp 2 } +id-kp-codeSigning OBJECT IDENTIFIER ::= { id-kp 3 } +id-kp-emailProtection OBJECT IDENTIFIER ::= { id-kp 4 } +id-kp-ipsecEndSystem OBJECT IDENTIFIER ::= { id-kp 5 } +id-kp-ipsecTunnel OBJECT IDENTIFIER ::= { id-kp 6 } +id-kp-ipsecUser OBJECT IDENTIFIER ::= { id-kp 7 } +id-kp-timeStamping OBJECT IDENTIFIER ::= { id-kp 8 } + +-- authority info access + +id-pe-authorityInfoAccess OBJECT IDENTIFIER ::= { id-pe 1 } + +AuthorityInfoAccessSyntax ::= + SEQUENCE SIZE (1..MAX) OF AccessDescription + +AccessDescription ::= SEQUENCE { + accessMethod OBJECT IDENTIFIER, + accessLocation GeneralName } + +-- CRL number extension OID and syntax + +id-ce-cRLNumber OBJECT IDENTIFIER ::= { id-ce 20 } + +CRLNumber ::= INTEGER (0..MAX) + +-- issuing distribution point extension OID and syntax + +id-ce-issuingDistributionPoint OBJECT IDENTIFIER ::= { id-ce 28 } + +IssuingDistributionPoint ::= SEQUENCE { + distributionPoint [0] DistributionPointName OPTIONAL, + onlyContainsUserCerts [1] BOOLEAN DEFAULT FALSE, + onlyContainsCACerts [2] BOOLEAN DEFAULT FALSE, + onlySomeReasons [3] ReasonFlags OPTIONAL, + indirectCRL [4] BOOLEAN DEFAULT FALSE } + + +id-ce-deltaCRLIndicator OBJECT IDENTIFIER ::= { id-ce 27 } + +-- deltaCRLIndicator ::= BaseCRLNumber + +BaseCRLNumber ::= CRLNumber + +-- CRL reasons extension OID and syntax + +id-ce-cRLReasons OBJECT IDENTIFIER ::= { id-ce 21 } + +CRLReason ::= ENUMERATED { + unspecified (0), + keyCompromise (1), + cACompromise (2), + affiliationChanged (3), + superseded (4), + cessationOfOperation (5), + certificateHold (6), + removeFromCRL (8) } + +-- certificate issuer CRL entry extension OID and syntax + +id-ce-certificateIssuer OBJECT IDENTIFIER ::= { id-ce 29 } + +CertificateIssuer ::= GeneralNames + +-- hold instruction extension OID and syntax + +id-ce-holdInstructionCode OBJECT IDENTIFIER ::= { id-ce 23 } + +HoldInstructionCode ::= OBJECT IDENTIFIER + +-- ANSI x9 holdinstructions + +-- ANSI x9 arc holdinstruction arc +holdInstruction OBJECT IDENTIFIER ::= + {joint-iso-itu-t(2) member-body(2) us(840) x9cm(10040) 2} + +-- ANSI X9 holdinstructions referenced by this standard +id-holdinstruction-none OBJECT IDENTIFIER ::= + {holdInstruction 1} -- deprecated +id-holdinstruction-callissuer OBJECT IDENTIFIER ::= + {holdInstruction 2} +id-holdinstruction-reject OBJECT IDENTIFIER ::= + {holdInstruction 3} + +-- invalidity date CRL entry extension OID and syntax + +id-ce-invalidityDate OBJECT IDENTIFIER ::= { id-ce 24 } + +InvalidityDate ::= GeneralizedTime + + +-- -------------------------------------- +-- EXPLICIT +-- -------------------------------------- -- UNIVERSAL Types defined in '93 and '98 ASN.1 -- but required by this specification +VisibleString ::= [UNIVERSAL 26] IMPLICIT OCTET STRING + NumericString ::= [UNIVERSAL 18] IMPLICIT OCTET STRING IA5String ::= [UNIVERSAL 22] IMPLICIT OCTET STRING @@ -218,7 +520,7 @@ Certificate ::= SEQUENCE { signature BIT STRING } TBSCertificate ::= SEQUENCE { - version [0] Version DEFAULT 0, -- v1 + version [0] EXPLICIT Version DEFAULT 0, --v1, serialNumber CertificateSerialNumber, signature AlgorithmIdentifier, issuer Name, @@ -229,7 +531,7 @@ TBSCertificate ::= SEQUENCE { -- If present, version shall be v2 or v3 subjectUniqueID [2] IMPLICIT UniqueIdentifier OPTIONAL, -- If present, version shall be v2 or v3 - extensions [3] Extensions OPTIONAL + extensions [3] EXPLICIT Extensions OPTIONAL -- If present, version shall be v3 -- } @@ -281,7 +583,7 @@ TBSCertList ::= SEQUENCE { crlEntryExtensions Extensions OPTIONAL -- if present, shall be v2 } OPTIONAL, - crlExtensions [0] Extensions OPTIONAL + crlExtensions [0] EXPLICIT Extensions OPTIONAL -- if present, shall be v2 -- } @@ -308,11 +610,6 @@ md5WithRSAEncryption OBJECT IDENTIFIER ::= { pkcs-1 4 } sha1WithRSAEncryption OBJECT IDENTIFIER ::= { pkcs-1 5 } -RSAPublicKey ::= SEQUENCE { - modulus INTEGER, - publicExponent INTEGER -} - id-dsa-with-sha1 OBJECT IDENTIFIER ::= { iso(1) member-body(2) us(840) x9-57 (10040) x9algorithm(4) 3 } @@ -361,16 +658,16 @@ ORAddress ::= SEQUENCE { BuiltInStandardAttributes ::= SEQUENCE { country-name CountryName OPTIONAL, administration-domain-name AdministrationDomainName OPTIONAL, - network-address [0] NetworkAddress OPTIONAL, + network-address [0] EXPLICIT NetworkAddress OPTIONAL, -- see also extended-network-address - terminal-identifier [1] TerminalIdentifier OPTIONAL, - private-domain-name [2] PrivateDomainName OPTIONAL, - organization-name [3] OrganizationName OPTIONAL, + terminal-identifier [1] EXPLICIT TerminalIdentifier OPTIONAL, + private-domain-name [2] EXPLICIT PrivateDomainName OPTIONAL, + organization-name [3] EXPLICIT OrganizationName OPTIONAL, -- see also teletex-organization-name - numeric-user-identifier [4] NumericUserIdentifier OPTIONAL, - personal-name [5] PersonalName OPTIONAL, + numeric-user-identifier [4] EXPLICIT NumericUserIdentifier OPTIONAL, + personal-name [5] EXPLICIT PersonalName OPTIONAL, -- see also teletex-personal-name - organizational-unit-names [6] OrganizationalUnitNames OPTIONAL + organizational-unit-names [6] EXPLICIT OrganizationalUnitNames OPTIONAL -- see also teletex-organizational-unit-names -- } @@ -380,7 +677,7 @@ CountryName ::= [APPLICATION 1] CHOICE { iso-3166-alpha2-code PrintableString (SIZE (ub-country-name-alpha-length)) } -AdministrationDomainName ::= [APPLICATION 2] CHOICE { +AdministrationDomainName ::= [APPLICATION 2] EXPLICIT CHOICE { numeric NumericString (SIZE (0..ub-domain-name-length)), printable PrintableString (SIZE (0..ub-domain-name-length)) } @@ -435,8 +732,8 @@ ExtensionAttributes ::= SET SIZE (1..ub-extension-attributes) OF ExtensionAttribute ExtensionAttribute ::= SEQUENCE { - extension-attribute-type [0] INTEGER (0..ub-extension-attributes), - extension-attribute-value [1] + extension-attribute-type [0] EXPLICIT INTEGER (0..ub-extension-attributes), + extension-attribute-value [1] EXPLICIT ANY DEFINED BY extension-attribute-type } -- Extension types and attribute values @@ -458,11 +755,11 @@ TeletexOrganizationName ::= teletex-personal-name INTEGER ::= 4 TeletexPersonalName ::= SET { - surname [0] TeletexString (SIZE (1..ub-surname-length)), - given-name [1] TeletexString + surname [0] EXPLICIT TeletexString (SIZE (1..ub-surname-length)), + given-name [1] EXPLICIT TeletexString (SIZE (1..ub-given-name-length)) OPTIONAL, - initials [2] TeletexString (SIZE (1..ub-initials-length)) OPTIONAL, - generation-qualifier [3] TeletexString (SIZE + initials [2] EXPLICIT TeletexString (SIZE (1..ub-initials-length)) OPTIONAL, + generation-qualifier [3] EXPLICIT TeletexString (SIZE (1..ub-generation-qualifier-length)) OPTIONAL } teletex-organizational-unit-names INTEGER ::= 5 @@ -552,10 +849,10 @@ extended-network-address INTEGER ::= 22 ExtendedNetworkAddress ::= CHOICE { e163-4-address SEQUENCE { - number [0] NumericString (SIZE (1..ub-e163-4-number-length)), - sub-address [1] NumericString + number [0] EXPLICIT NumericString (SIZE (1..ub-e163-4-number-length)), + sub-address [1] EXPLICIT NumericString (SIZE (1..ub-e163-4-sub-address-length)) OPTIONAL }, - psap-address [0] PresentationAddress } + psap-address [0] EXPLICIT PresentationAddress } PresentationAddress ::= SEQUENCE { pSelector [0] EXPLICIT OCTET STRING OPTIONAL, @@ -638,4 +935,14 @@ ub-x121-address-length INTEGER ::= 16 -- bound should be allowed. -END \ No newline at end of file + +END + + + + + + + + + diff --git a/src/serv.c b/src/serv.c index 65359d5248..d3f00908f3 100644 --- a/src/serv.c +++ b/src/serv.c @@ -87,7 +87,7 @@ GNUTLS_STATE initialize_state() * purposes. */ gnutls_set_cipher_priority(state, GNUTLS_NULL_CIPHER, - GNUTLS_RIJNDAEL_CBC, GNUTLS_ARCFOUR, GNUTLS_3DES_CBC, 0); + GNUTLS_RIJNDAEL_CBC, GNUTLS_3DES_CBC, 0); gnutls_set_compression_priority(state, GNUTLS_ZLIB, GNUTLS_NULL_COMPRESSION, 0); gnutls_set_kx_priority(state, GNUTLS_KX_DHE_RSA, GNUTLS_KX_RSA, GNUTLS_KX_SRP, GNUTLS_KX_DH_ANON, 0);