X-Git-Url: https://git.librecmc.org/?a=blobdiff_plain;f=crypto%2Fasn1%2Fa_strnid.c;h=6b10cff99449395ae9120713a1ac2047ac1c3f5d;hb=9ef9e78520eba0fb3d92b581dc4f895a5f464387;hp=e2e100e2eb8846d52161f94c2fcd2b0f5b977c2d;hpb=a0ad17bb6cccef6eb7ff0b25403ec2bbc0bd122e;p=oweals%2Fopenssl.git diff --git a/crypto/asn1/a_strnid.c b/crypto/asn1/a_strnid.c index e2e100e2eb..6b10cff994 100644 --- a/crypto/asn1/a_strnid.c +++ b/crypto/asn1/a_strnid.c @@ -65,7 +65,56 @@ static STACK_OF(ASN1_STRING_TABLE) *stable = NULL; static void st_free(ASN1_STRING_TABLE *tbl); -static int sk_table_cmp(ASN1_STRING_TABLE **a, ASN1_STRING_TABLE **b); +static int sk_table_cmp(const ASN1_STRING_TABLE * const *a, + const ASN1_STRING_TABLE * const *b); +static int table_cmp(const void *a, const void *b); + + +/* This is the global mask for the mbstring functions: this is use to + * mask out certain types (such as BMPString and UTF8String) because + * certain software (e.g. Netscape) has problems with them. + */ + +static unsigned long global_mask = 0xFFFFFFFFL; + +void ASN1_STRING_set_default_mask(unsigned long mask) +{ + global_mask = mask; +} + +unsigned long ASN1_STRING_get_default_mask(void) +{ + return global_mask; +} + +/* This function sets the default to various "flavours" of configuration. + * based on an ASCII string. Currently this is: + * MASK:XXXX : a numerical mask value. + * nobmp : Don't use BMPStrings (just Printable, T61). + * pkix : PKIX recommendation in RFC2459. + * utf8only : only use UTF8Strings (RFC2459 recommendation for 2004). + * default: the default value, Printable, T61, BMP. + */ + +int ASN1_STRING_set_default_mask_asc(char *p) +{ + unsigned long mask; + char *end; + if(!strncmp(p, "MASK:", 5)) { + if(!p[5]) return 0; + mask = strtoul(p + 5, &end, 0); + if(*end) return 0; + } else if(!strcmp(p, "nombstr")) + mask = ~(B_ASN1_BMPSTRING|B_ASN1_UTF8STRING); + else if(!strcmp(p, "pkix")) + mask = ~B_ASN1_T61STRING; + else if(!strcmp(p, "utf8only")) mask = B_ASN1_UTF8STRING; + else if(!strcmp(p, "default")) + mask = 0xFFFFFFFFL; + else return 0; + ASN1_STRING_set_default_mask(mask); + return 1; +} /* The following function generates an ASN1_STRING based on limits in a table. * Frequently the types and length of an ASN1_STRING are restricted by a @@ -77,13 +126,16 @@ ASN1_STRING *ASN1_STRING_set_by_NID(ASN1_STRING **out, const unsigned char *in, { ASN1_STRING_TABLE *tbl; ASN1_STRING *str = NULL; + unsigned long mask; int ret; if(!out) out = &str; - if(!stable) ASN1_STRING_TABLE_add_standard(); tbl = ASN1_STRING_TABLE_get(nid); - if(tbl) ret = ASN1_mbstring_ncopy(out, in, inlen, inform, tbl->mask, + if(tbl) { + mask = tbl->mask; + if(!(tbl->flags & STABLE_NO_MASK)) mask &= global_mask; + ret = ASN1_mbstring_ncopy(out, in, inlen, inform, tbl->mask, tbl->minsize, tbl->maxsize); - else ret = ASN1_mbstring_copy(out, in, inlen, inform, 0); + } else ret = ASN1_mbstring_copy(out, in, inlen, inform, DIRSTRING_TYPE & global_mask); if(ret <= 0) return NULL; return *out; } @@ -102,53 +154,50 @@ ASN1_STRING *ASN1_STRING_set_by_NID(ASN1_STRING **out, const unsigned char *in, #define ub_title 64 #define ub_email_address 128 +/* This table must be kept in NID order */ + static ASN1_STRING_TABLE tbl_standard[] = { -{NID_name, 1, ub_name, 0, 0}, -{NID_surname, 1, ub_name, 0, 0}, -{NID_givenName, 1, ub_name, 0, 0}, -{NID_initials, 1, ub_name, 0, 0}, -{NID_commonName, 1, ub_common_name, 0, 0}, -{NID_localityName, 1, ub_locality_name, 0, 0}, -{NID_stateOrProvinceName, 1, ub_state_name, 0, 0}, -{NID_organizationName, 1, ub_organization_name, 0, 0}, -{NID_organizationalUnitName, 1, ub_organization_unit_name, 0, 0}, -{NID_dnQualifier, -1, -1, B_ASN1_PRINTABLESTRING, 0}, -{NID_countryName, 2, 2, B_ASN1_PRINTABLESTRING, 0}, -{NID_pkcs9_emailAddress, 1, ub_email_address, B_ASN1_IA5STRING, 0}, -{NID_undef, 0, 0, 0, 0} +{NID_commonName, 1, ub_common_name, DIRSTRING_TYPE, 0}, +{NID_countryName, 2, 2, B_ASN1_PRINTABLESTRING, STABLE_NO_MASK}, +{NID_localityName, 1, ub_locality_name, DIRSTRING_TYPE, 0}, +{NID_stateOrProvinceName, 1, ub_state_name, DIRSTRING_TYPE, 0}, +{NID_organizationName, 1, ub_organization_name, DIRSTRING_TYPE, 0}, +{NID_organizationalUnitName, 1, ub_organization_unit_name, DIRSTRING_TYPE, 0}, +{NID_pkcs9_emailAddress, 1, ub_email_address, B_ASN1_IA5STRING, STABLE_NO_MASK}, +{NID_pkcs9_unstructuredName, 1, -1, PKCS9STRING_TYPE, 0}, +{NID_pkcs9_challengePassword, 1, -1, PKCS9STRING_TYPE, 0}, +{NID_pkcs9_unstructuredAddress, 1, -1, DIRSTRING_TYPE, 0}, +{NID_givenName, 1, ub_name, DIRSTRING_TYPE, 0}, +{NID_surname, 1, ub_name, DIRSTRING_TYPE, 0}, +{NID_initials, 1, ub_name, DIRSTRING_TYPE, 0}, +{NID_name, 1, ub_name, DIRSTRING_TYPE, 0}, +{NID_dnQualifier, -1, -1, B_ASN1_PRINTABLESTRING, STABLE_NO_MASK} }; -int ASN1_STRING_TABLE_add_standard(void) +static int sk_table_cmp(const ASN1_STRING_TABLE * const *a, + const ASN1_STRING_TABLE * const *b) { - static int done = 0; - ASN1_STRING_TABLE *tmp; - if(done) return 1; - if(!stable) stable = sk_ASN1_STRING_TABLE_new(sk_table_cmp); - if(!stable) { - ASN1err(ASN1_F_ASN1_STRING_TABLE_ADD_STANDARD, - ERR_R_MALLOC_FAILURE); - return 0; - } - for(tmp = tbl_standard; tmp->nid != NID_undef; tmp++) { - if(!sk_ASN1_STRING_TABLE_push(stable, tmp)) { - ASN1err(ASN1_F_ASN1_STRING_TABLE_ADD_STANDARD, - ERR_R_MALLOC_FAILURE); - return 0; - } - } - return 1; + return (*a)->nid - (*b)->nid; } -static int sk_table_cmp(ASN1_STRING_TABLE **a, ASN1_STRING_TABLE **b) +static int table_cmp(const void *a, const void *b) { - return (*a)->nid - (*b)->nid; + const ASN1_STRING_TABLE *sa = a, *sb = b; + return sa->nid - sb->nid; } ASN1_STRING_TABLE *ASN1_STRING_TABLE_get(int nid) { int idx; + ASN1_STRING_TABLE *ttmp; ASN1_STRING_TABLE fnd; fnd.nid = nid; + ttmp = (ASN1_STRING_TABLE *) OBJ_bsearch((char *)&fnd, + (char *)tbl_standard, + sizeof(tbl_standard)/sizeof(ASN1_STRING_TABLE), + sizeof(ASN1_STRING_TABLE), table_cmp); + if(ttmp) return ttmp; + if(!stable) return NULL; idx = sk_ASN1_STRING_TABLE_find(stable, &fnd); if(idx < 0) return NULL; return sk_ASN1_STRING_TABLE_value(stable, idx); @@ -160,26 +209,26 @@ int ASN1_STRING_TABLE_add(int nid, { ASN1_STRING_TABLE *tmp; char new_nid = 0; + flags &= ~STABLE_FLAGS_MALLOC; if(!stable) stable = sk_ASN1_STRING_TABLE_new(sk_table_cmp); if(!stable) { ASN1err(ASN1_F_ASN1_STRING_TABLE_ADD, ERR_R_MALLOC_FAILURE); return 0; } if(!(tmp = ASN1_STRING_TABLE_get(nid))) { - tmp = Malloc(sizeof(ASN1_STRING_TABLE)); + tmp = OPENSSL_malloc(sizeof(ASN1_STRING_TABLE)); if(!tmp) { ASN1err(ASN1_F_ASN1_STRING_TABLE_ADD, ERR_R_MALLOC_FAILURE); return 0; } - tmp->flags = STABLE_FLAGS_MALLOC; + tmp->flags = flags | STABLE_FLAGS_MALLOC; tmp->nid = nid; new_nid = 1; - } + } else tmp->flags = (tmp->flags & STABLE_FLAGS_MALLOC) | flags; if(minsize != -1) tmp->minsize = minsize; if(maxsize != -1) tmp->maxsize = maxsize; tmp->mask = mask; - tmp->flags = flags & ~STABLE_FLAGS_MALLOC; if(new_nid) sk_ASN1_STRING_TABLE_push(stable, tmp); return 1; } @@ -195,7 +244,7 @@ void ASN1_STRING_TABLE_cleanup(void) static void st_free(ASN1_STRING_TABLE *tbl) { - if(tbl->flags & STABLE_FLAGS_MALLOC) Free(tbl); + if(tbl->flags & STABLE_FLAGS_MALLOC) OPENSSL_free(tbl); } IMPLEMENT_STACK_OF(ASN1_STRING_TABLE)