andre@0: /* This Source Code Form is subject to the terms of the Mozilla Public andre@0: * License, v. 2.0. If a copy of the MPL was not distributed with this andre@0: * file, You can obtain one at http://mozilla.org/MPL/2.0/. */ andre@0: /* andre@0: * pkix_pl_crldp.c andre@0: * andre@0: * Crl DP Object Functions andre@0: * andre@0: */ andre@0: andre@0: #include "pkix_pl_crldp.h" andre@0: andre@0: static PKIX_Error * andre@0: pkix_pl_CrlDp_Destroy( andre@0: PKIX_PL_Object *object, andre@0: void *plContext) andre@0: { andre@0: pkix_pl_CrlDp *crldp = NULL; andre@0: andre@0: PKIX_ENTER(CRLCHECKER, "pkix_CrlDp_Destroy"); andre@0: PKIX_NULLCHECK_ONE(object); andre@0: andre@0: /* Check that this object is a default CRL checker state */ andre@0: PKIX_CHECK( andre@0: pkix_CheckType(object, PKIX_CRLDP_TYPE, plContext), andre@0: PKIX_OBJECTNOTCRLCHECKER); andre@0: andre@0: crldp = (pkix_pl_CrlDp *)object; andre@0: if (crldp->distPointType == relativeDistinguishedName) { andre@0: CERT_DestroyName(crldp->name.issuerName); andre@0: crldp->name.issuerName = NULL; andre@0: } andre@0: crldp->nssdp = NULL; andre@0: cleanup: andre@0: PKIX_RETURN(CRLCHECKER); andre@0: } andre@0: andre@0: /* andre@0: * FUNCTION: pkix_pl_CrlDp_RegisterSelf andre@0: * andre@0: * DESCRIPTION: andre@0: * Registers PKIX_CRLDP_TYPE and its related functions andre@0: * with systemClasses[] andre@0: * andre@0: * THREAD SAFETY: andre@0: * Not Thread Safe (see Thread Safety Definitions in Programmer's Guide) andre@0: * andre@0: * Since this function is only called by PKIX_PL_Initialize, which should andre@0: * only be called once, it is acceptable that this function is not andre@0: * thread-safe. andre@0: */ andre@0: PKIX_Error * andre@0: pkix_pl_CrlDp_RegisterSelf(void *plContext) andre@0: { andre@0: extern pkix_ClassTable_Entry systemClasses[PKIX_NUMTYPES]; andre@0: pkix_ClassTable_Entry* entry = &systemClasses[PKIX_CRLDP_TYPE]; andre@0: andre@0: PKIX_ENTER(CRLCHECKER, "pkix_CrlDp_RegisterSelf"); andre@0: andre@0: entry->description = "CrlDistPoint"; andre@0: entry->typeObjectSize = sizeof(pkix_pl_CrlDp); andre@0: entry->destructor = pkix_pl_CrlDp_Destroy; andre@0: entry->duplicateFunction = pkix_duplicateImmutable; andre@0: andre@0: PKIX_RETURN(CRLCHECKER); andre@0: } andre@0: andre@0: andre@0: andre@0: PKIX_Error * andre@0: pkix_pl_CrlDp_Create( andre@0: const CRLDistributionPoint *dp, andre@0: const CERTName *certIssuerName, andre@0: pkix_pl_CrlDp **pPkixDP, andre@0: void *plContext) andre@0: { andre@0: PLArenaPool *rdnArena = NULL; andre@0: CERTName *issuerNameCopy = NULL; andre@0: pkix_pl_CrlDp *dpl = NULL; andre@0: andre@0: /* Need to save the following info to update crl cache: andre@0: * - reasons if partitioned(but can not return revocation check andre@0: * success if not all crl are downloaded) andre@0: * - issuer name if different from issuer of the cert andre@0: * - url to upload a crl if needed. andre@0: * */ andre@0: PKIX_ENTER(CRLDP, "pkix_pl_CrlDp_Create"); andre@0: PKIX_NULLCHECK_ONE(dp); andre@0: andre@0: PKIX_CHECK( andre@0: PKIX_PL_Object_Alloc(PKIX_CRLDP_TYPE, andre@0: sizeof (pkix_pl_CrlDp), andre@0: (PKIX_PL_Object **)&dpl, andre@0: plContext), andre@0: PKIX_COULDNOTCREATEOBJECT); andre@0: andre@0: dpl->nssdp = dp; andre@0: dpl->isPartitionedByReasonCode = PKIX_FALSE; andre@0: if (dp->reasons.data) { andre@0: dpl->isPartitionedByReasonCode = PKIX_TRUE; andre@0: } andre@0: if (dp->distPointType == generalName) { andre@0: dpl->distPointType = generalName; andre@0: dpl->name.fullName = dp->distPoint.fullName; andre@0: } else { andre@0: SECStatus rv; andre@0: const CERTName *issuerName = NULL; andre@0: const CERTRDN *relName = &dp->distPoint.relativeName; andre@0: andre@0: if (dp->crlIssuer) { andre@0: if (dp->crlIssuer->l.next) { andre@0: /* Violate RFC 5280: in this case crlIssuer andre@0: * should have only one name and should be andre@0: * a distinguish name. */ andre@0: PKIX_ERROR(PKIX_NOTCONFORMINGCRLDP); andre@0: } andre@0: issuerName = &dp->crlIssuer->name.directoryName; andre@0: } else { andre@0: issuerName = certIssuerName; andre@0: } andre@0: rdnArena = PORT_NewArena(DER_DEFAULT_CHUNKSIZE); andre@0: if (!rdnArena) { andre@0: PKIX_ERROR(PKIX_PORTARENAALLOCFAILED); andre@0: } andre@0: issuerNameCopy = (CERTName *)PORT_ArenaZNew(rdnArena, CERTName*); andre@0: if (!issuerNameCopy) { andre@0: PKIX_ERROR(PKIX_ALLOCERROR); andre@0: } andre@0: rv = CERT_CopyName(rdnArena, issuerNameCopy, (CERTName*)issuerName); andre@0: if (rv == SECFailure) { andre@0: PKIX_ERROR(PKIX_ALLOCERROR); andre@0: } andre@0: rv = CERT_AddRDN(issuerNameCopy, (CERTRDN*)relName); andre@0: if (rv == SECFailure) { andre@0: PKIX_ERROR(PKIX_ALLOCERROR); andre@0: } andre@0: dpl->distPointType = relativeDistinguishedName; andre@0: dpl->name.issuerName = issuerNameCopy; andre@0: rdnArena = NULL; andre@0: } andre@0: *pPkixDP = dpl; andre@0: dpl = NULL; andre@0: andre@0: cleanup: andre@0: if (rdnArena) { andre@0: PORT_FreeArena(rdnArena, PR_FALSE); andre@0: } andre@0: PKIX_DECREF(dpl); andre@0: andre@0: PKIX_RETURN(CRLDP); andre@0: }