/*
 * Contributed to the OpenSSL Project by the American Registry for
 * Internet Numbers ("ARIN").
 */
/* ====================================================================
 * Copyright (c) 2006 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
 * are met:
 *
 * 1. Redistributions of source code must retain the above copyright
 *    notice, this list of conditions and the following disclaimer.
 *
 * 2. Redistributions in binary form must reproduce the above copyright
 *    notice, this list of conditions and the following disclaimer in
 *    the documentation and/or other materials provided with the
 *    distribution.
 *
 * 3. All advertising materials mentioning features or use of this
 *    software must display the following acknowledgment:
 *    "This product includes software developed by the OpenSSL Project
 *    for use in the OpenSSL Toolkit. (http://www.OpenSSL.org/)"
 *
 * 4. The names "OpenSSL Toolkit" and "OpenSSL Project" must not be used to
 *    endorse or promote products derived from this software without
 *    prior written permission. For written permission, please contact
 *    licensing@OpenSSL.org.
 *
 * 5. Products derived from this software may not be called "OpenSSL"
 *    nor may "OpenSSL" appear in their names without prior written
 *    permission of the OpenSSL Project.
 *
 * 6. Redistributions of any form whatsoever must retain the following
 *    acknowledgment:
 *    "This product includes software developed by the OpenSSL Project
 *    for use in the OpenSSL Toolkit (http://www.OpenSSL.org/)"
 *
 * THIS SOFTWARE IS PROVIDED BY THE OpenSSL PROJECT ``AS IS'' AND ANY
 * EXPRESSED OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
 * PURPOSE ARE DISCLAIMED.  IN NO EVENT SHALL THE OpenSSL PROJECT OR
 * ITS CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
 * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
 * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
 * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
 * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT,
 * STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
 * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED
 * OF THE POSSIBILITY OF SUCH DAMAGE.
 * ====================================================================
 *
 * This product includes cryptographic software written by Eric Young
 * (eay@cryptsoft.com).  This product includes software written by Tim
 * Hudson (tjh@cryptsoft.com).
 */

/*
 * Implementation of RFC 3779 section 3.2.
 */

#include <stdio.h>
#include <string.h>
#include "cryptlib.h"
#include <openssl/conf.h>
#include <openssl/asn1.h>
#include <openssl/asn1t.h>
#include <openssl/x509v3.h>
#include <openssl/x509.h>
#include <openssl/bn.h>

#ifndef OPENSSL_NO_RFC3779

/*
 * OpenSSL ASN.1 template translation of RFC 3779 3.2.3.
 */

ASN1_SEQUENCE(ASRange) = {
  ASN1_SIMPLE(ASRange, min, ASN1_INTEGER),
  ASN1_SIMPLE(ASRange, max, ASN1_INTEGER)
} ASN1_SEQUENCE_END(ASRange)

ASN1_CHOICE(ASIdOrRange) = {
  ASN1_SIMPLE(ASIdOrRange, u.id,    ASN1_INTEGER),
  ASN1_SIMPLE(ASIdOrRange, u.range, ASRange)
} ASN1_CHOICE_END(ASIdOrRange)

ASN1_CHOICE(ASIdentifierChoice) = {
  ASN1_SIMPLE(ASIdentifierChoice,      u.inherit,       ASN1_NULL),
  ASN1_SEQUENCE_OF(ASIdentifierChoice, u.asIdsOrRanges, ASIdOrRange)
} ASN1_CHOICE_END(ASIdentifierChoice)

ASN1_SEQUENCE(ASIdentifiers) = {
  ASN1_EXP_OPT(ASIdentifiers, asnum, ASIdentifierChoice, 0),
  ASN1_EXP_OPT(ASIdentifiers, rdi,   ASIdentifierChoice, 1)
} ASN1_SEQUENCE_END(ASIdentifiers)

IMPLEMENT_ASN1_FUNCTIONS(ASRange)
IMPLEMENT_ASN1_FUNCTIONS(ASIdOrRange)
IMPLEMENT_ASN1_FUNCTIONS(ASIdentifierChoice)
IMPLEMENT_ASN1_FUNCTIONS(ASIdentifiers)

/*
 * i2r method for an ASIdentifierChoice.
 */
static int i2r_ASIdentifierChoice(BIO *out,
                                  ASIdentifierChoice *choice,
                                  int indent, const char *msg)
{
    int i;
    char *s;
    if (choice == NULL)
        return 1;
    BIO_printf(out, "%*s%s:\n", indent, "", msg);
    switch (choice->type) {
    case ASIdentifierChoice_inherit:
        BIO_printf(out, "%*sinherit\n", indent + 2, "");
        break;
    case ASIdentifierChoice_asIdsOrRanges:
        for (i = 0; i < sk_ASIdOrRange_num(choice->u.asIdsOrRanges); i++) {
            ASIdOrRange *aor =
                sk_ASIdOrRange_value(choice->u.asIdsOrRanges, i);
            switch (aor->type) {
            case ASIdOrRange_id:
                if ((s = i2s_ASN1_INTEGER(NULL, aor->u.id)) == NULL)
                    return 0;
                BIO_printf(out, "%*s%s\n", indent + 2, "", s);
                OPENSSL_free(s);
                break;
            case ASIdOrRange_range:
                if ((s = i2s_ASN1_INTEGER(NULL, aor->u.range->min)) == NULL)
                    return 0;
                BIO_printf(out, "%*s%s-", indent + 2, "", s);
                OPENSSL_free(s);
                if ((s = i2s_ASN1_INTEGER(NULL, aor->u.range->max)) == NULL)
                    return 0;
                BIO_printf(out, "%s\n", s);
                OPENSSL_free(s);
                break;
            default:
                return 0;
            }
        }
        break;
    default:
        return 0;
    }
    return 1;
}

/*
 * i2r method for an ASIdentifier extension.
 */
static int i2r_ASIdentifiers(const X509V3_EXT_METHOD *method,
                             void *ext, BIO *out, int indent)
{
    ASIdentifiers *asid = ext;
    return (i2r_ASIdentifierChoice(out, asid->asnum, indent,
                                   "Autonomous System Numbers") &&
            i2r_ASIdentifierChoice(out, asid->rdi, indent,
                                   "Routing Domain Identifiers"));
}

/*
 * Sort comparision function for a sequence of ASIdOrRange elements.
 */
static int ASIdOrRange_cmp(const ASIdOrRange *const *a_,
                           const ASIdOrRange *const *b_)
{
    const ASIdOrRange *a = *a_, *b = *b_;

    OPENSSL_assert((a->type == ASIdOrRange_id && a->u.id != NULL) ||
                   (a->type == ASIdOrRange_range && a->u.range != NULL &&
                    a->u.range->min != NULL && a->u.range->max != NULL));

    OPENSSL_assert((b->type == ASIdOrRange_id && b->u.id != NULL) ||
                   (b->type == ASIdOrRange_range && b->u.range != NULL &&
                    b->u.range->min != NULL && b->u.range->max != NULL));

    if (a->type == ASIdOrRange_id && b->type == ASIdOrRange_id)
        return ASN1_INTEGER_cmp(a->u.id, b->u.id);

    if (a->type == ASIdOrRange_range && b->type == ASIdOrRange_range) {
        int r = ASN1_INTEGER_cmp(a->u.range->min, b->u.range->min);
        return r != 0 ? r : ASN1_INTEGER_cmp(a->u.range->max,
                                             b->u.range->max);
    }

    if (a->type == ASIdOrRange_id)
        return ASN1_INTEGER_cmp(a->u.id, b->u.range->min);
    else
        return ASN1_INTEGER_cmp(a->u.range->min, b->u.id);
}

/*
 * Add an inherit element.
 */
int v3_asid_add_inherit(ASIdentifiers *asid, int which)
{
    ASIdentifierChoice **choice;
    if (asid == NULL)
        return 0;
    switch (which) {
    case V3_ASID_ASNUM:
        choice = &asid->asnum;
        break;
    case V3_ASID_RDI:
        choice = &asid->rdi;
        break;
    default:
        return 0;
    }
    if (*choice == NULL) {
        if ((*choice = ASIdentifierChoice_new()) == NULL)
            return 0;
        OPENSSL_assert((*choice)->u.inherit == NULL);
        if (((*choice)->u.inherit = ASN1_NULL_new()) == NULL)
            return 0;
        (*choice)->type = ASIdentifierChoice_inherit;
    }
    return (*choice)->type == ASIdentifierChoice_inherit;
}

/*
 * Add an ID or range to an ASIdentifierChoice.
 */
int v3_asid_add_id_or_range(ASIdentifiers *asid,
                            int which, ASN1_INTEGER *min, ASN1_INTEGER *max)
{
    ASIdentifierChoice **choice;
    ASIdOrRange *aor;
    if (asid == NULL)
        return 0;
    switch (which) {
    case V3_ASID_ASNUM:
        choice = &asid->asnum;
        break;
    case V3_ASID_RDI:
        choice = &asid->rdi;
        break;
    default:
        return 0;
    }
    if (*choice != NULL && (*choice)->type == ASIdentifierChoice_inherit)
        return 0;
    if (*choice == NULL) {
        if ((*choice = ASIdentifierChoice_new()) == NULL)
            return 0;
        OPENSSL_assert((*choice)->u.asIdsOrRanges == NULL);
        (*choice)->u.asIdsOrRanges = sk_ASIdOrRange_new(ASIdOrRange_cmp);
        if ((*choice)->u.asIdsOrRanges == NULL)
            return 0;
        (*choice)->type = ASIdentifierChoice_asIdsOrRanges;
    }
    if ((aor = ASIdOrRange_new()) == NULL)
        return 0;
    if (max == NULL) {
        aor->type = ASIdOrRange_id;
        aor->u.id = min;
    } else {
        aor->type = ASIdOrRange_range;
        if ((aor->u.range = ASRange_new()) == NULL)
            goto err;
        ASN1_INTEGER_free(aor->u.range->min);
        aor->u.range->min = min;
        ASN1_INTEGER_free(aor->u.range->max);
        aor->u.range->max = max;
    }
    if (!(sk_ASIdOrRange_push((*choice)->u.asIdsOrRanges, aor)))
        goto err;
    return 1;

 err:
    ASIdOrRange_free(aor);
    return 0;
}

/*
 * Extract min and max values from an ASIdOrRange.
 */
static void extract_min_max(ASIdOrRange *aor,
                            ASN1_INTEGER **min, ASN1_INTEGER **max)
{
    OPENSSL_assert(aor != NULL && min != NULL && max != NULL);
    switch (aor->type) {
    case ASIdOrRange_id:
        *min = aor->u.id;
        *max = aor->u.id;
        return;
    case ASIdOrRange_range:
        *min = aor->u.range->min;
        *max = aor->u.range->max;
        return;
    }
}

/*
 * Check whether an ASIdentifierChoice is in canonical form.
 */
static int ASIdentifierChoice_is_canonical(ASIdentifierChoice *choice)
{
    ASN1_INTEGER *a_max_plus_one = NULL;
    BIGNUM *bn = NULL;
    int i, ret = 0;

    /*
     * Empty element or inheritance is canonical.
     */
    if (choice == NULL || choice->type == ASIdentifierChoice_inherit)
        return 1;

    /*
     * If not a list, or if empty list, it's broken.
     */
    if (choice->type != ASIdentifierChoice_asIdsOrRanges ||
        sk_ASIdOrRange_num(choice->u.asIdsOrRanges) == 0)
        return 0;

    /*
     * It's a list, check it.
     */
    for (i = 0; i < sk_ASIdOrRange_num(choice->u.asIdsOrRanges) - 1; i++) {
        ASIdOrRange *a = sk_ASIdOrRange_value(choice->u.asIdsOrRanges, i);
        ASIdOrRange *b = sk_ASIdOrRange_value(choice->u.asIdsOrRanges, i + 1);
        ASN1_INTEGER *a_min, *a_max, *b_min, *b_max;

        extract_min_max(a, &a_min, &a_max);
        extract_min_max(b, &b_min, &b_max);

        /*
         * Punt misordered list, overlapping start, or inverted range.
         */
        if (ASN1_INTEGER_cmp(a_min, b_min) >= 0 ||
            ASN1_INTEGER_cmp(a_min, a_max) > 0 ||
            ASN1_INTEGER_cmp(b_min, b_max) > 0)
            goto done;

        /*
         * Calculate a_max + 1 to check for adjacency.
         */
        if ((bn == NULL && (bn = BN_new()) == NULL) ||
            ASN1_INTEGER_to_BN(a_max, bn) == NULL ||
            !BN_add_word(bn, 1) ||
            (a_max_plus_one =
             BN_to_ASN1_INTEGER(bn, a_max_plus_one)) == NULL) {
            X509V3err(X509V3_F_ASIDENTIFIERCHOICE_IS_CANONICAL,
                      ERR_R_MALLOC_FAILURE);
            goto done;
        }

        /*
         * Punt if adjacent or overlapping.
         */
        if (ASN1_INTEGER_cmp(a_max_plus_one, b_min) >= 0)
            goto done;
    }

    /*
     * Check for inverted range.
     */
    i = sk_ASIdOrRange_num(choice->u.asIdsOrRanges) - 1;
    {
        ASIdOrRange *a = sk_ASIdOrRange_value(choice->u.asIdsOrRanges, i);
        ASN1_INTEGER *a_min, *a_max;
        if (a != NULL && a->type == ASIdOrRange_range) {
            extract_min_max(a, &a_min, &a_max);
            if (ASN1_INTEGER_cmp(a_min, a_max) > 0)
                goto done;
        }
    }

    ret = 1;

 done:
    ASN1_INTEGER_free(a_max_plus_one);
    BN_free(bn);
    return ret;
}

/*
 * Check whether an ASIdentifier extension is in canonical form.
 */
int v3_asid_is_canonical(ASIdentifiers *asid)
{
    return (asid == NULL ||
            (ASIdentifierChoice_is_canonical(asid->asnum) &&
             ASIdentifierChoice_is_canonical(asid->rdi)));
}

/*
 * Whack an ASIdentifierChoice into canonical form.
 */
static int ASIdentifierChoice_canonize(ASIdentifierChoice *choice)
{
    ASN1_INTEGER *a_max_plus_one = NULL;
    BIGNUM *bn = NULL;
    int i, ret = 0;

    /*
     * Nothing to do for empty element or inheritance.
     */
    if (choice == NULL || choice->type == ASIdentifierChoice_inherit)
        return 1;

    /*
     * If not a list, or if empty list, it's broken.
     */
    if (choice->type != ASIdentifierChoice_asIdsOrRanges ||
        sk_ASIdOrRange_num(choice->u.asIdsOrRanges) == 0) {
        X509V3err(X509V3_F_ASIDENTIFIERCHOICE_CANONIZE,
                  X509V3_R_EXTENSION_VALUE_ERROR);
        return 0;
    }

    /*
     * We have a non-empty list.  Sort it.
     */
    sk_ASIdOrRange_sort(choice->u.asIdsOrRanges);

    /*
     * Now check for errors and suboptimal encoding, rejecting the
     * former and fixing the latter.
     */
    for (i = 0; i < sk_ASIdOrRange_num(choice->u.asIdsOrRanges) - 1; i++) {
        ASIdOrRange *a = sk_ASIdOrRange_value(choice->u.asIdsOrRanges, i);
        ASIdOrRange *b = sk_ASIdOrRange_value(choice->u.asIdsOrRanges, i + 1);
        ASN1_INTEGER *a_min, *a_max, *b_min, *b_max;

        extract_min_max(a, &a_min, &a_max);
        extract_min_max(b, &b_min, &b_max);

        /*
         * Make sure we're properly sorted (paranoia).
         */
        OPENSSL_assert(ASN1_INTEGER_cmp(a_min, b_min) <= 0);

        /*
         * Punt inverted ranges.
         */
        if (ASN1_INTEGER_cmp(a_min, a_max) > 0 ||
            ASN1_INTEGER_cmp(b_min, b_max) > 0)
            goto done;

        /*
         * Check for overlaps.
         */
        if (ASN1_INTEGER_cmp(a_max, b_min) >= 0) {
            X509V3err(X509V3_F_ASIDENTIFIERCHOICE_CANONIZE,
                      X509V3_R_EXTENSION_VALUE_ERROR);
            goto done;
        }

        /*
         * Calculate a_max + 1 to check for adjacency.
         */
        if ((bn == NULL && (bn = BN_new()) == NULL) ||
            ASN1_INTEGER_to_BN(a_max, bn) == NULL ||
            !BN_add_word(bn, 1) ||
            (a_max_plus_one =
             BN_to_ASN1_INTEGER(bn, a_max_plus_one)) == NULL) {
            X509V3err(X509V3_F_ASIDENTIFIERCHOICE_CANONIZE,
                      ERR_R_MALLOC_FAILURE);
            goto done;
        }

        /*
         * If a and b are adjacent, merge them.
         */
        if (ASN1_INTEGER_cmp(a_max_plus_one, b_min) == 0) {
            ASRange *r;
            switch (a->type) {
            case ASIdOrRange_id:
                if ((r = OPENSSL_malloc(sizeof(ASRange))) == NULL) {
                    X509V3err(X509V3_F_ASIDENTIFIERCHOICE_CANONIZE,
                              ERR_R_MALLOC_FAILURE);
                    goto done;
                }
                r->min = a_min;
                r->max = b_max;
                a->type = ASIdOrRange_range;
                a->u.range = r;
                break;
            case ASIdOrRange_range:
                ASN1_INTEGER_free(a->u.range->max);
                a->u.range->max = b_max;
                break;
            }
            switch (b->type) {
            case ASIdOrRange_id:
                b->u.id = NULL;
                break;
            case ASIdOrRange_range:
                b->u.range->max = NULL;
                break;
            }
            ASIdOrRange_free(b);
            (void)sk_ASIdOrRange_delete(choice->u.asIdsOrRanges, i + 1);
            i--;
            continue;
        }
    }

    /*
     * Check for final inverted range.
     */
    i = sk_ASIdOrRange_num(choice->u.asIdsOrRanges) - 1;
    {
        ASIdOrRange *a = sk_ASIdOrRange_value(choice->u.asIdsOrRanges, i);
        ASN1_INTEGER *a_min, *a_max;
        if (a != NULL && a->type == ASIdOrRange_range) {
            extract_min_max(a, &a_min, &a_max);
            if (ASN1_INTEGER_cmp(a_min, a_max) > 0)
                goto done;
        }
    }

    OPENSSL_assert(ASIdentifierChoice_is_canonical(choice)); /* Paranoia */

    ret = 1;

 done:
    ASN1_INTEGER_free(a_max_plus_one);
    BN_free(bn);
    return ret;
}

/*
 * Whack an ASIdentifier extension into canonical form.
 */
int v3_asid_canonize(ASIdentifiers *asid)
{
    return (asid == NULL ||
            (ASIdentifierChoice_canonize(asid->asnum) &&
             ASIdentifierChoice_canonize(asid->rdi)));
}

/*
 * v2i method for an ASIdentifier extension.
 */
static void *v2i_ASIdentifiers(const struct v3_ext_method *method,
                               struct v3_ext_ctx *ctx,
                               STACK_OF(CONF_VALUE) *values)
{
    ASN1_INTEGER *min = NULL, *max = NULL;
    ASIdentifiers *asid = NULL;
    int i;

    if ((asid = ASIdentifiers_new()) == NULL) {
        X509V3err(X509V3_F_V2I_ASIDENTIFIERS, ERR_R_MALLOC_FAILURE);
        return NULL;
    }

    for (i = 0; i < sk_CONF_VALUE_num(values); i++) {
        CONF_VALUE *val = sk_CONF_VALUE_value(values, i);
        int i1, i2, i3, is_range, which;

        /*
         * Figure out whether this is an AS or an RDI.
         */
        if (!name_cmp(val->name, "AS")) {
            which = V3_ASID_ASNUM;
        } else if (!name_cmp(val->name, "RDI")) {
            which = V3_ASID_RDI;
        } else {
            X509V3err(X509V3_F_V2I_ASIDENTIFIERS,
                      X509V3_R_EXTENSION_NAME_ERROR);
            X509V3_conf_err(val);
            goto err;
        }

        /*
         * Handle inheritance.
         */
        if (!strcmp(val->value, "inherit")) {
            if (v3_asid_add_inherit(asid, which))
                continue;
            X509V3err(X509V3_F_V2I_ASIDENTIFIERS,
                      X509V3_R_INVALID_INHERITANCE);
            X509V3_conf_err(val);
            goto err;
        }

        /*
         * Number, range, or mistake, pick it apart and figure out which.
         */
        i1 = strspn(val->value, "0123456789");
        if (val->value[i1] == '\0') {
            is_range = 0;
        } else {
            is_range = 1;
            i2 = i1 + strspn(val->value + i1, " \t");
            if (val->value[i2] != '-') {
                X509V3err(X509V3_F_V2I_ASIDENTIFIERS,
                          X509V3_R_INVALID_ASNUMBER);
                X509V3_conf_err(val);
                goto err;
            }
            i2++;
            i2 = i2 + strspn(val->value + i2, " \t");
            i3 = i2 + strspn(val->value + i2, "0123456789");
            if (val->value[i3] != '\0') {
                X509V3err(X509V3_F_V2I_ASIDENTIFIERS,
                          X509V3_R_INVALID_ASRANGE);
                X509V3_conf_err(val);
                goto err;
            }
        }

        /*
         * Syntax is ok, read and add it.
         */
        if (!is_range) {
            if (!X509V3_get_value_int(val, &min)) {
                X509V3err(X509V3_F_V2I_ASIDENTIFIERS, ERR_R_MALLOC_FAILURE);
                goto err;
            }
        } else {
            char *s = BUF_strdup(val->value);
            if (s == NULL) {
                X509V3err(X509V3_F_V2I_ASIDENTIFIERS, ERR_R_MALLOC_FAILURE);
                goto err;
            }
            s[i1] = '\0';
            min = s2i_ASN1_INTEGER(NULL, s);
            max = s2i_ASN1_INTEGER(NULL, s + i2);
            OPENSSL_free(s);
            if (min == NULL || max == NULL) {
                X509V3err(X509V3_F_V2I_ASIDENTIFIERS, ERR_R_MALLOC_FAILURE);
                goto err;
            }
            if (ASN1_INTEGER_cmp(min, max) > 0) {
                X509V3err(X509V3_F_V2I_ASIDENTIFIERS,
                          X509V3_R_EXTENSION_VALUE_ERROR);
                goto err;
            }
        }
        if (!v3_asid_add_id_or_range(asid, which, min, max)) {
            X509V3err(X509V3_F_V2I_ASIDENTIFIERS, ERR_R_MALLOC_FAILURE);
            goto err;
        }
        min = max = NULL;
    }

    /*
     * Canonize the result, then we're done.
     */
    if (!v3_asid_canonize(asid))
        goto err;
    return asid;

 err:
    ASIdentifiers_free(asid);
    ASN1_INTEGER_free(min);
    ASN1_INTEGER_free(max);
    return NULL;
}

/*
 * OpenSSL dispatch.
 */
const X509V3_EXT_METHOD v3_asid = {
    NID_sbgp_autonomousSysNum,  /* nid */
    0,                          /* flags */
    ASN1_ITEM_ref(ASIdentifiers), /* template */
    0, 0, 0, 0,                 /* old functions, ignored */
    0,                          /* i2s */
    0,                          /* s2i */
    0,                          /* i2v */
    v2i_ASIdentifiers,          /* v2i */
    i2r_ASIdentifiers,          /* i2r */
    0,                          /* r2i */
    NULL                        /* extension-specific data */
};

/*
 * Figure out whether extension uses inheritance.
 */
int v3_asid_inherits(ASIdentifiers *asid)
{
    return (asid != NULL &&
            ((asid->asnum != NULL &&
              asid->asnum->type == ASIdentifierChoice_inherit) ||
             (asid->rdi != NULL &&
              asid->rdi->type == ASIdentifierChoice_inherit)));
}

/*
 * Figure out whether parent contains child.
 */
static int asid_contains(ASIdOrRanges *parent, ASIdOrRanges *child)
{
    ASN1_INTEGER *p_min, *p_max, *c_min, *c_max;
    int p, c;

    if (child == NULL || parent == child)
        return 1;
    if (parent == NULL)
        return 0;

    p = 0;
    for (c = 0; c < sk_ASIdOrRange_num(child); c++) {
        extract_min_max(sk_ASIdOrRange_value(child, c), &c_min, &c_max);
        for (;; p++) {
            if (p >= sk_ASIdOrRange_num(parent))
                return 0;
            extract_min_max(sk_ASIdOrRange_value(parent, p), &p_min, &p_max);
            if (ASN1_INTEGER_cmp(p_max, c_max) < 0)
                continue;
            if (ASN1_INTEGER_cmp(p_min, c_min) > 0)
                return 0;
            break;
        }
    }

    return 1;
}

/*
 * Test whether a is a subet of b.
 */
int v3_asid_subset(ASIdentifiers *a, ASIdentifiers *b)
{
    return (a == NULL ||
            a == b ||
            (b != NULL &&
             !v3_asid_inherits(a) &&
             !v3_asid_inherits(b) &&
             asid_contains(b->asnum->u.asIdsOrRanges,
                           a->asnum->u.asIdsOrRanges) &&
             asid_contains(b->rdi->u.asIdsOrRanges,
                           a->rdi->u.asIdsOrRanges)));
}

/*
 * Validation error handling via callback.
 */
# define validation_err(_err_)           \
  do {                                  \
    if (ctx != NULL) {                  \
      ctx->error = _err_;               \
      ctx->error_depth = i;             \
      ctx->current_cert = x;            \
      ret = ctx->verify_cb(0, ctx);     \
    } else {                            \
      ret = 0;                          \
    }                                   \
    if (!ret)                           \
      goto done;                        \
  } while (0)

/*
 * Core code for RFC 3779 3.3 path validation.
 */
static int v3_asid_validate_path_internal(X509_STORE_CTX *ctx,
                                          STACK_OF(X509) *chain,
                                          ASIdentifiers *ext)
{
    ASIdOrRanges *child_as = NULL, *child_rdi = NULL;
    int i, ret = 1, inherit_as = 0, inherit_rdi = 0;
    X509 *x;

    OPENSSL_assert(chain != NULL && sk_X509_num(chain) > 0);
    OPENSSL_assert(ctx != NULL || ext != NULL);
    OPENSSL_assert(ctx == NULL || ctx->verify_cb != NULL);

    /*
     * Figure out where to start.  If we don't have an extension to
     * check, we're done.  Otherwise, check canonical form and
     * set up for walking up the chain.
     */
    if (ext != NULL) {
        i = -1;
        x = NULL;
    } else {
        i = 0;
        x = sk_X509_value(chain, i);
        OPENSSL_assert(x != NULL);
        if ((ext = x->rfc3779_asid) == NULL)
            goto done;
    }
    if (!v3_asid_is_canonical(ext))
        validation_err(X509_V_ERR_INVALID_EXTENSION);
    if (ext->asnum != NULL) {
        switch (ext->asnum->type) {
        case ASIdentifierChoice_inherit:
            inherit_as = 1;
            break;
        case ASIdentifierChoice_asIdsOrRanges:
            child_as = ext->asnum->u.asIdsOrRanges;
            break;
        }
    }
    if (ext->rdi != NULL) {
        switch (ext->rdi->type) {
        case ASIdentifierChoice_inherit:
            inherit_rdi = 1;
            break;
        case ASIdentifierChoice_asIdsOrRanges:
            child_rdi = ext->rdi->u.asIdsOrRanges;
            break;
        }
    }

    /*
     * Now walk up the chain.  Extensions must be in canonical form, no
     * cert may list resources that its parent doesn't list.
     */
    for (i++; i < sk_X509_num(chain); i++) {
        x = sk_X509_value(chain, i);
        OPENSSL_assert(x != NULL);
        if (x->rfc3779_asid == NULL) {
            if (child_as != NULL || child_rdi != NULL)
                validation_err(X509_V_ERR_UNNESTED_RESOURCE);
            continue;
        }
        if (!v3_asid_is_canonical(x->rfc3779_asid))
            validation_err(X509_V_ERR_INVALID_EXTENSION);
        if (x->rfc3779_asid->asnum == NULL && child_as != NULL) {
            validation_err(X509_V_ERR_UNNESTED_RESOURCE);
            child_as = NULL;
            inherit_as = 0;
        }
        if (x->rfc3779_asid->asnum != NULL &&
            x->rfc3779_asid->asnum->type ==
            ASIdentifierChoice_asIdsOrRanges) {
            if (inherit_as
                || asid_contains(x->rfc3779_asid->asnum->u.asIdsOrRanges,
                                 child_as)) {
                child_as = x->rfc3779_asid->asnum->u.asIdsOrRanges;
                inherit_as = 0;
            } else {
                validation_err(X509_V_ERR_UNNESTED_RESOURCE);
            }
        }
        if (x->rfc3779_asid->rdi == NULL && child_rdi != NULL) {
            validation_err(X509_V_ERR_UNNESTED_RESOURCE);
            child_rdi = NULL;
            inherit_rdi = 0;
        }
        if (x->rfc3779_asid->rdi != NULL &&
            x->rfc3779_asid->rdi->type == ASIdentifierChoice_asIdsOrRanges) {
            if (inherit_rdi ||
                asid_contains(x->rfc3779_asid->rdi->u.asIdsOrRanges,
                              child_rdi)) {
                child_rdi = x->rfc3779_asid->rdi->u.asIdsOrRanges;
                inherit_rdi = 0;
            } else {
                validation_err(X509_V_ERR_UNNESTED_RESOURCE);
            }
        }
    }

    /*
     * Trust anchor can't inherit.
     */
    OPENSSL_assert(x != NULL);
    if (x->rfc3779_asid != NULL) {
        if (x->rfc3779_asid->asnum != NULL &&
            x->rfc3779_asid->asnum->type == ASIdentifierChoice_inherit)
            validation_err(X509_V_ERR_UNNESTED_RESOURCE);
        if (x->rfc3779_asid->rdi != NULL &&
            x->rfc3779_asid->rdi->type == ASIdentifierChoice_inherit)
            validation_err(X509_V_ERR_UNNESTED_RESOURCE);
    }

 done:
    return ret;
}

# undef validation_err

/*
 * RFC 3779 3.3 path validation -- called from X509_verify_cert().
 */
int v3_asid_validate_path(X509_STORE_CTX *ctx)
{
    return v3_asid_validate_path_internal(ctx, ctx->chain, NULL);
}

/*
 * RFC 3779 3.3 path validation of an extension.
 * Test whether chain covers extension.
 */
int v3_asid_validate_resource_set(STACK_OF(X509) *chain,
                                  ASIdentifiers *ext, int allow_inheritance)
{
    if (ext == NULL)
        return 1;
    if (chain == NULL || sk_X509_num(chain) == 0)
        return 0;
    if (!allow_inheritance && v3_asid_inherits(ext))
        return 0;
    return v3_asid_validate_path_internal(NULL, chain, ext);
}

#endif                          /* OPENSSL_NO_RFC3779 */
