Updates from 1.0.0-stable.
[openssl.git] / crypto / x509v3 / v3_cpols.c
index 47e08c8fb8f19ccaa2451d5bd8ffcb67631473c2..1f0798b9468f9c663d9c3c49777f6a1a94723379 100644 (file)
@@ -1,9 +1,9 @@
 /* v3_cpols.c */
-/* Written by Dr Stephen N Henson (shenson@bigfoot.com) for the OpenSSL
+/* Written by Dr Stephen N Henson (steve@openssl.org) for the OpenSSL
  * project 1999.
  */
 /* ====================================================================
- * Copyright (c) 1999 The OpenSSL Project.  All rights reserved.
+ * Copyright (c) 1999-2004 The OpenSSL Project.  All rights reserved.
  *
  * Redistribution and use in source and binary forms, with or without
  * modification, are permitted provided that the following conditions
@@ -63,6 +63,8 @@
 #include <openssl/asn1t.h>
 #include <openssl/x509v3.h>
 
+#include "pcy_int.h"
+
 /* Certificate policies extension support: this one is a bit complex... */
 
 static int i2r_certpol(X509V3_EXT_METHOD *method, STACK_OF(POLICYINFO) *pol, BIO *out, int indent);
@@ -73,16 +75,13 @@ static POLICYINFO *policy_section(X509V3_CTX *ctx,
                                 STACK_OF(CONF_VALUE) *polstrs, int ia5org);
 static POLICYQUALINFO *notice_section(X509V3_CTX *ctx,
                                        STACK_OF(CONF_VALUE) *unot, int ia5org);
-static STACK_OF(ASN1_INTEGER) *nref_nos(STACK_OF(CONF_VALUE) *nos);
-
-X509V3_EXT_METHOD v3_cpols = {
-NID_certificate_policies, 0,
-(X509V3_EXT_NEW)CERTIFICATEPOLICIES_new,
-(X509V3_EXT_FREE)CERTIFICATEPOLICIES_free,
-(X509V3_EXT_D2I)d2i_CERTIFICATEPOLICIES,
-(X509V3_EXT_I2D)i2d_CERTIFICATEPOLICIES,
-NULL, NULL,
-NULL, NULL,
+static int nref_nos(STACK_OF(ASN1_INTEGER) *nnums, STACK_OF(CONF_VALUE) *nos);
+
+const X509V3_EXT_METHOD v3_cpols = {
+NID_certificate_policies, 0,ASN1_ITEM_ref(CERTIFICATEPOLICIES),
+0,0,0,0,
+0,0,
+0,0,
 (X509V3_EXT_I2R)i2r_certpol,
 (X509V3_EXT_R2I)r2i_certpol,
 NULL
@@ -90,14 +89,14 @@ NULL
 
 ASN1_ITEM_TEMPLATE(CERTIFICATEPOLICIES) = 
        ASN1_EX_TEMPLATE_TYPE(ASN1_TFLG_SEQUENCE_OF, 0, CERTIFICATEPOLICIES, POLICYINFO)
-ASN1_ITEM_TEMPLATE_END(CERTIFICATEPOLICIES);
+ASN1_ITEM_TEMPLATE_END(CERTIFICATEPOLICIES)
 
 IMPLEMENT_ASN1_FUNCTIONS(CERTIFICATEPOLICIES)
 
 ASN1_SEQUENCE(POLICYINFO) = {
        ASN1_SIMPLE(POLICYINFO, policyid, ASN1_OBJECT),
        ASN1_SEQUENCE_OF_OPT(POLICYINFO, qualifiers, POLICYQUALINFO)
-} ASN1_SEQUENCE_END(POLICYINFO);
+} ASN1_SEQUENCE_END(POLICYINFO)
 
 IMPLEMENT_ASN1_FUNCTIONS(POLICYINFO)
 
@@ -111,21 +110,21 @@ ASN1_ADB(POLICYQUALINFO) = {
 ASN1_SEQUENCE(POLICYQUALINFO) = {
        ASN1_SIMPLE(POLICYQUALINFO, pqualid, ASN1_OBJECT),
        ASN1_ADB_OBJECT(POLICYQUALINFO)
-} ASN1_SEQUENCE_END(POLICYQUALINFO);
+} ASN1_SEQUENCE_END(POLICYQUALINFO)
 
 IMPLEMENT_ASN1_FUNCTIONS(POLICYQUALINFO)
 
 ASN1_SEQUENCE(USERNOTICE) = {
        ASN1_OPT(USERNOTICE, noticeref, NOTICEREF),
        ASN1_OPT(USERNOTICE, exptext, DISPLAYTEXT)
-} ASN1_SEQUENCE_END(USERNOTICE);
+} ASN1_SEQUENCE_END(USERNOTICE)
 
 IMPLEMENT_ASN1_FUNCTIONS(USERNOTICE)
 
 ASN1_SEQUENCE(NOTICEREF) = {
        ASN1_SIMPLE(NOTICEREF, organization, DISPLAYTEXT),
        ASN1_SEQUENCE_OF(NOTICEREF, noticenos, ASN1_INTEGER)
-} ASN1_SEQUENCE_END(NOTICEREF);
+} ASN1_SEQUENCE_END(NOTICEREF)
 
 IMPLEMENT_ASN1_FUNCTIONS(NOTICEREF)
 
@@ -140,7 +139,15 @@ static STACK_OF(POLICYINFO) *r2i_certpol(X509V3_EXT_METHOD *method,
        CONF_VALUE *cnf;
        int i, ia5org;
        pols = sk_POLICYINFO_new_null();
+       if (pols == NULL) {
+               X509V3err(X509V3_F_R2I_CERTPOL, ERR_R_MALLOC_FAILURE);
+               return NULL;
+       }
        vals =  X509V3_parse_list(value);
+       if (vals == NULL) {
+               X509V3err(X509V3_F_R2I_CERTPOL, ERR_R_X509V3_LIB);
+               goto err;
+       }
        ia5org = 0;
        for(i = 0; i < sk_CONF_VALUE_num(vals); i++) {
                cnf = sk_CONF_VALUE_value(vals, i);
@@ -174,11 +181,16 @@ static STACK_OF(POLICYINFO) *r2i_certpol(X509V3_EXT_METHOD *method,
                        pol = POLICYINFO_new();
                        pol->policyid = pobj;
                }
-               sk_POLICYINFO_push(pols, pol);
+               if (!sk_POLICYINFO_push(pols, pol)){
+                       POLICYINFO_free(pol);
+                       X509V3err(X509V3_F_R2I_CERTPOL, ERR_R_MALLOC_FAILURE);
+                       goto err;
+               }
        }
        sk_CONF_VALUE_pop_free(vals, X509V3_conf_free);
        return pols;
        err:
+       sk_CONF_VALUE_pop_free(vals, X509V3_conf_free);
        sk_POLICYINFO_pop_free(pols, POLICYINFO_free);
        return NULL;
 }
@@ -229,6 +241,8 @@ static POLICYINFO *policy_section(X509V3_CTX *ctx,
                        qual = notice_section(ctx, unot, ia5org);
                        X509V3_section_free(ctx, unot);
                        if(!qual) goto err;
+                       if(!pol->qualifiers) pol->qualifiers =
+                                                sk_POLICYQUALINFO_new_null();
                        if(!sk_POLICYQUALINFO_push(pol->qualifiers, qual))
                                                                 goto merr;
                } else {
@@ -258,7 +272,7 @@ static POLICYINFO *policy_section(X509V3_CTX *ctx,
 static POLICYQUALINFO *notice_section(X509V3_CTX *ctx,
                                        STACK_OF(CONF_VALUE) *unot, int ia5org)
 {
-       int i;
+       int i, ret;
        CONF_VALUE *cnf;
        USERNOTICE *not;
        POLICYQUALINFO *qual;
@@ -278,8 +292,8 @@ static POLICYQUALINFO *notice_section(X509V3_CTX *ctx,
                                if(!(nref = NOTICEREF_new())) goto merr;
                                not->noticeref = nref;
                        } else nref = not->noticeref;
-                       if(ia5org) nref->organization = M_ASN1_IA5STRING_new();
-                       else nref->organization = M_ASN1_VISIBLESTRING_new();
+                       if(ia5org) nref->organization->type = V_ASN1_IA5STRING;
+                       else nref->organization->type = V_ASN1_VISIBLESTRING;
                        if(!ASN1_STRING_set(nref->organization, cnf->value,
                                                 strlen(cnf->value))) goto merr;
                } else if(!strcmp(cnf->name, "noticeNumbers")) {
@@ -295,12 +309,12 @@ static POLICYQUALINFO *notice_section(X509V3_CTX *ctx,
                                X509V3_conf_err(cnf);
                                goto err;
                        }
-                       nref->noticenos = nref_nos(nos);
+                       ret = nref_nos(nref->noticenos, nos);
                        sk_CONF_VALUE_pop_free(nos, X509V3_conf_free);
-                       if(!nref->noticenos) goto err;
+                       if (!ret)
+                               goto err;
                } else {
                        X509V3err(X509V3_F_NOTICE_SECTION,X509V3_R_INVALID_OPTION);
-
                        X509V3_conf_err(cnf);
                        goto err;
                }
@@ -322,15 +336,13 @@ static POLICYQUALINFO *notice_section(X509V3_CTX *ctx,
        return NULL;
 }
 
-static STACK_OF(ASN1_INTEGER) *nref_nos(STACK_OF(CONF_VALUE) *nos)
+static int nref_nos(STACK_OF(ASN1_INTEGER) *nnums, STACK_OF(CONF_VALUE) *nos)
 {
-       STACK_OF(ASN1_INTEGER) *nnums;
        CONF_VALUE *cnf;
        ASN1_INTEGER *aint;
 
        int i;
 
-       if(!(nnums = sk_ASN1_INTEGER_new_null())) goto merr;
        for(i = 0; i < sk_CONF_VALUE_num(nos); i++) {
                cnf = sk_CONF_VALUE_value(nos, i);
                if(!(aint = s2i_ASN1_INTEGER(NULL, cnf->name))) {
@@ -339,14 +351,14 @@ static STACK_OF(ASN1_INTEGER) *nref_nos(STACK_OF(CONF_VALUE) *nos)
                }
                if(!sk_ASN1_INTEGER_push(nnums, aint)) goto merr;
        }
-       return nnums;
+       return 1;
 
        merr:
-       X509V3err(X509V3_F_NOTICE_SECTION,ERR_R_MALLOC_FAILURE);
+       X509V3err(X509V3_F_NREF_NOS,ERR_R_MALLOC_FAILURE);
 
        err:
        sk_ASN1_INTEGER_pop_free(nnums, ASN1_STRING_free);
-       return NULL;
+       return 0;
 }
 
 
@@ -423,3 +435,23 @@ static void print_notice(BIO *out, USERNOTICE *notice, int indent)
                                                         notice->exptext->data);
 }
 
+void X509_POLICY_NODE_print(BIO *out, X509_POLICY_NODE *node, int indent)
+       {
+       const X509_POLICY_DATA *dat = node->data;
+
+       BIO_printf(out, "%*sPolicy: ", indent, "");
+                       
+       i2a_ASN1_OBJECT(out, dat->valid_policy);
+       BIO_puts(out, "\n");
+       BIO_printf(out, "%*s%s\n", indent + 2, "",
+               node_data_critical(dat) ? "Critical" : "Non Critical");
+       if (dat->qualifier_set)
+               print_qualifiers(out, dat->qualifier_set, indent + 2);
+       else
+               BIO_printf(out, "%*sNo Qualifiers\n", indent + 2, "");
+       }
+
+
+IMPLEMENT_STACK_OF(X509_POLICY_NODE)
+IMPLEMENT_STACK_OF(X509_POLICY_DATA)
+