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_certpolicyqualifier.c andre@0: * andre@0: * CertPolicyQualifier Type Functions andre@0: * andre@0: */ andre@0: andre@0: #include "pkix_pl_certpolicyqualifier.h" andre@0: andre@0: /* andre@0: * FUNCTION: pkix_pl_CertPolicyQualifier_Create andre@0: * DESCRIPTION: andre@0: * andre@0: * Creates a CertPolicyQualifier object with the OID given by "oid" andre@0: * and the ByteArray given by "qualifier", and stores it at "pObject". andre@0: * andre@0: * PARAMETERS andre@0: * "oid" andre@0: * Address of OID of the desired policyQualifierId; must be non-NULL andre@0: * "qualifier" andre@0: * Address of ByteArray with the desired value of the qualifier; andre@0: * must be non-NULL andre@0: * "pObject" andre@0: * Address where object pointer will be stored. Must be non-NULL. andre@0: * "plContext" andre@0: * Platform-specific context pointer. andre@0: * THREAD SAFETY: andre@0: * Thread Safe (see Thread Safety Definitions in Programmer's Guide) andre@0: * RETURNS: andre@0: * Returns NULL if the function succeeds. andre@0: * Returns a Fatal Error if the function fails in an unrecoverable way. andre@0: */ andre@0: PKIX_Error * andre@0: pkix_pl_CertPolicyQualifier_Create( andre@0: PKIX_PL_OID *oid, andre@0: PKIX_PL_ByteArray *qualifier, andre@0: PKIX_PL_CertPolicyQualifier **pObject, andre@0: void *plContext) andre@0: { andre@0: PKIX_PL_CertPolicyQualifier *qual = NULL; andre@0: andre@0: PKIX_ENTER(CERTPOLICYQUALIFIER, "pkix_pl_CertPolicyQualifier_Create"); andre@0: andre@0: PKIX_NULLCHECK_THREE(oid, qualifier, pObject); andre@0: andre@0: PKIX_CHECK(PKIX_PL_Object_Alloc andre@0: (PKIX_CERTPOLICYQUALIFIER_TYPE, andre@0: sizeof (PKIX_PL_CertPolicyQualifier), andre@0: (PKIX_PL_Object **)&qual, andre@0: plContext), andre@0: PKIX_COULDNOTCREATECERTPOLICYQUALIFIEROBJECT); andre@0: andre@0: PKIX_INCREF(oid); andre@0: qual->policyQualifierId = oid; andre@0: andre@0: PKIX_INCREF(qualifier); andre@0: qual->qualifier = qualifier; andre@0: andre@0: *pObject = qual; andre@0: qual = NULL; andre@0: andre@0: cleanup: andre@0: PKIX_DECREF(qual); andre@0: andre@0: PKIX_RETURN(CERTPOLICYQUALIFIER); andre@0: } andre@0: andre@0: /* andre@0: * FUNCTION: pkix_pl_CertPolicyQualifier_Destroy andre@0: * (see comments for PKIX_PL_DestructorCallback in pkix_pl_system.h) andre@0: */ andre@0: static PKIX_Error * andre@0: pkix_pl_CertPolicyQualifier_Destroy( andre@0: PKIX_PL_Object *object, andre@0: void *plContext) andre@0: { andre@0: PKIX_PL_CertPolicyQualifier *certPQ = NULL; andre@0: andre@0: PKIX_ENTER(CERTPOLICYQUALIFIER, "pkix_pl_CertPolicyQualifier_Destroy"); andre@0: andre@0: PKIX_NULLCHECK_ONE(object); andre@0: andre@0: PKIX_CHECK(pkix_CheckType andre@0: (object, PKIX_CERTPOLICYQUALIFIER_TYPE, plContext), andre@0: PKIX_OBJECTNOTCERTPOLICYQUALIFIER); andre@0: andre@0: certPQ = (PKIX_PL_CertPolicyQualifier*)object; andre@0: andre@0: PKIX_DECREF(certPQ->policyQualifierId); andre@0: PKIX_DECREF(certPQ->qualifier); andre@0: andre@0: cleanup: andre@0: andre@0: PKIX_RETURN(CERTPOLICYQUALIFIER); andre@0: } andre@0: andre@0: /* andre@0: * FUNCTION: pkix_pl_CertPolicyQualifier_ToString andre@0: * (see comments for PKIX_PL_ToStringCallback in pkix_pl_system.h) andre@0: */ andre@0: static PKIX_Error * andre@0: pkix_pl_CertPolicyQualifier_ToString( andre@0: PKIX_PL_Object *object, andre@0: PKIX_PL_String **pString, andre@0: void *plContext) andre@0: { andre@0: PKIX_PL_CertPolicyQualifier *certPQ = NULL; andre@0: char *asciiFormat = "%s:%s"; andre@0: PKIX_PL_String *formatString = NULL; andre@0: PKIX_PL_String *pqIDString = NULL; andre@0: PKIX_PL_String *pqValString = NULL; andre@0: PKIX_PL_String *outString = NULL; andre@0: andre@0: PKIX_ENTER(CERTPOLICYQUALIFIER, "pkix_pl_CertPolicyQualifier_ToString"); andre@0: andre@0: PKIX_NULLCHECK_TWO(object, pString); andre@0: andre@0: PKIX_CHECK(pkix_CheckType andre@0: (object, PKIX_CERTPOLICYQUALIFIER_TYPE, plContext), andre@0: PKIX_OBJECTNOTCERTPOLICYQUALIFIER); andre@0: andre@0: certPQ = (PKIX_PL_CertPolicyQualifier *)object; andre@0: andre@0: /* andre@0: * The policyQualifierId is required. If there is no qualifier, andre@0: * we should have a ByteArray of zero length. andre@0: */ andre@0: PKIX_NULLCHECK_TWO(certPQ->policyQualifierId, certPQ->qualifier); andre@0: andre@0: PKIX_CHECK(PKIX_PL_String_Create andre@0: (PKIX_ESCASCII, asciiFormat, 0, &formatString, plContext), andre@0: PKIX_STRINGCREATEFAILED); andre@0: andre@0: PKIX_TOSTRING(certPQ->policyQualifierId, &pqIDString, plContext, andre@0: PKIX_OIDTOSTRINGFAILED); andre@0: andre@0: PKIX_CHECK(pkix_pl_ByteArray_ToHexString andre@0: (certPQ->qualifier, &pqValString, plContext), andre@0: PKIX_BYTEARRAYTOHEXSTRINGFAILED); andre@0: andre@0: PKIX_CHECK(PKIX_PL_Sprintf andre@0: (&outString, plContext, formatString, pqIDString, pqValString), andre@0: PKIX_SPRINTFFAILED); andre@0: andre@0: *pString = outString; andre@0: andre@0: cleanup: andre@0: andre@0: PKIX_DECREF(formatString); andre@0: PKIX_DECREF(pqIDString); andre@0: PKIX_DECREF(pqValString); andre@0: PKIX_RETURN(CERTPOLICYQUALIFIER); andre@0: } andre@0: andre@0: /* andre@0: * FUNCTION: pkix_pl_CertPolicyQualifier_Hashcode andre@0: * (see comments for PKIX_PL_HashcodeCallback in pkix_pl_system.h) andre@0: */ andre@0: static PKIX_Error * andre@0: pkix_pl_CertPolicyQualifier_Hashcode( andre@0: PKIX_PL_Object *object, andre@0: PKIX_UInt32 *pHashcode, andre@0: void *plContext) andre@0: { andre@0: PKIX_PL_CertPolicyQualifier *certPQ = NULL; andre@0: PKIX_UInt32 cpidHash = 0; andre@0: PKIX_UInt32 cpqHash = 0; andre@0: andre@0: PKIX_ENTER(CERTPOLICYQUALIFIER, "pkix_pl_CertPolicyQualifier_Hashcode"); andre@0: PKIX_NULLCHECK_TWO(object, pHashcode); andre@0: andre@0: PKIX_CHECK(pkix_CheckType andre@0: (object, PKIX_CERTPOLICYQUALIFIER_TYPE, plContext), andre@0: PKIX_OBJECTNOTCERTPOLICYQUALIFIER); andre@0: andre@0: certPQ = (PKIX_PL_CertPolicyQualifier *)object; andre@0: andre@0: PKIX_NULLCHECK_TWO(certPQ->policyQualifierId, certPQ->qualifier); andre@0: andre@0: PKIX_HASHCODE(certPQ->policyQualifierId, &cpidHash, plContext, andre@0: PKIX_ERRORINOIDHASHCODE); andre@0: andre@0: PKIX_HASHCODE(certPQ->qualifier, &cpqHash, plContext, andre@0: PKIX_ERRORINBYTEARRAYHASHCODE); andre@0: andre@0: *pHashcode = cpidHash*31 + cpqHash; andre@0: andre@0: cleanup: andre@0: andre@0: PKIX_RETURN(CERTPOLICYQUALIFIER); andre@0: } andre@0: andre@0: andre@0: /* andre@0: * FUNCTION: pkix_pl_CertPolicyQualifier_Equals andre@0: * (see comments for PKIX_PL_Equals_Callback in pkix_pl_system.h) andre@0: */ andre@0: static PKIX_Error * andre@0: pkix_pl_CertPolicyQualifier_Equals( andre@0: PKIX_PL_Object *firstObject, andre@0: PKIX_PL_Object *secondObject, andre@0: PKIX_Boolean *pResult, andre@0: void *plContext) andre@0: { andre@0: PKIX_PL_CertPolicyQualifier *firstCPQ = NULL; andre@0: PKIX_PL_CertPolicyQualifier *secondCPQ = NULL; andre@0: PKIX_UInt32 secondType = 0; andre@0: PKIX_Boolean compare = PKIX_FALSE; andre@0: andre@0: PKIX_ENTER(CERTPOLICYQUALIFIER, "pkix_pl_CertPolicyQualifier_Equals"); andre@0: PKIX_NULLCHECK_THREE(firstObject, secondObject, pResult); andre@0: andre@0: /* test that firstObject is a CertPolicyQualifier */ andre@0: PKIX_CHECK(pkix_CheckType andre@0: (firstObject, PKIX_CERTPOLICYQUALIFIER_TYPE, plContext), andre@0: PKIX_FIRSTOBJECTNOTCERTPOLICYQUALIFIER); andre@0: andre@0: /* andre@0: * Since we know firstObject is a CertPolicyQualifier, andre@0: * if both references are identical, they must be equal andre@0: */ andre@0: if (firstObject == secondObject){ andre@0: *pResult = PKIX_TRUE; andre@0: goto cleanup; andre@0: } andre@0: andre@0: /* andre@0: * If secondObject isn't a CertPolicyQualifier, we andre@0: * don't throw an error. We simply return FALSE. andre@0: */ andre@0: PKIX_CHECK(PKIX_PL_Object_GetType andre@0: (secondObject, &secondType, plContext), andre@0: PKIX_COULDNOTGETTYPEOFSECONDARGUMENT); andre@0: if (secondType != PKIX_CERTPOLICYQUALIFIER_TYPE) { andre@0: *pResult = PKIX_FALSE; andre@0: goto cleanup; andre@0: } andre@0: andre@0: firstCPQ = (PKIX_PL_CertPolicyQualifier *)firstObject; andre@0: secondCPQ = (PKIX_PL_CertPolicyQualifier *)secondObject; andre@0: andre@0: /* andre@0: * Compare the value of the OID components andre@0: */ andre@0: andre@0: PKIX_NULLCHECK_TWO andre@0: (firstCPQ->policyQualifierId, secondCPQ->policyQualifierId); andre@0: andre@0: PKIX_EQUALS andre@0: (firstCPQ->policyQualifierId, andre@0: secondCPQ->policyQualifierId, andre@0: &compare, andre@0: plContext, andre@0: PKIX_OIDEQUALSFAILED); andre@0: andre@0: /* andre@0: * If the OIDs did not match, we don't need to andre@0: * compare the ByteArrays. If the OIDs did match, andre@0: * the return value is the value of the andre@0: * ByteArray comparison. andre@0: */ andre@0: if (compare) { andre@0: PKIX_NULLCHECK_TWO(firstCPQ->qualifier, secondCPQ->qualifier); andre@0: andre@0: PKIX_EQUALS andre@0: (firstCPQ->qualifier, andre@0: secondCPQ->qualifier, andre@0: &compare, andre@0: plContext, andre@0: PKIX_BYTEARRAYEQUALSFAILED); andre@0: } andre@0: andre@0: *pResult = compare; andre@0: andre@0: cleanup: andre@0: andre@0: PKIX_RETURN(CERTPOLICYQUALIFIER); andre@0: } andre@0: andre@0: /* andre@0: * FUNCTION: pkix_pl_CertPolicyQualifier_RegisterSelf andre@0: * DESCRIPTION: andre@0: * Registers PKIX_CERTPOLICYQUALIFIER_TYPE and its related andre@0: * functions with systemClasses[] andre@0: * THREAD SAFETY: andre@0: * Not Thread Safe - for performance and complexity reasons andre@0: * andre@0: * Since this function is only called by PKIX_PL_Initialize, andre@0: * which should only be called once, it is acceptable that andre@0: * this function is not thread-safe. andre@0: */ andre@0: PKIX_Error * andre@0: pkix_pl_CertPolicyQualifier_RegisterSelf(void *plContext) andre@0: { andre@0: andre@0: extern pkix_ClassTable_Entry systemClasses[PKIX_NUMTYPES]; andre@0: pkix_ClassTable_Entry entry; andre@0: andre@0: PKIX_ENTER(CERTPOLICYQUALIFIER, andre@0: "pkix_pl_CertPolicyQualifier_RegisterSelf"); andre@0: andre@0: entry.description = "CertPolicyQualifier"; andre@0: entry.objCounter = 0; andre@0: entry.typeObjectSize = sizeof(PKIX_PL_CertPolicyQualifier); andre@0: entry.destructor = pkix_pl_CertPolicyQualifier_Destroy; andre@0: entry.equalsFunction = pkix_pl_CertPolicyQualifier_Equals; andre@0: entry.hashcodeFunction = pkix_pl_CertPolicyQualifier_Hashcode; andre@0: entry.toStringFunction = pkix_pl_CertPolicyQualifier_ToString; andre@0: entry.comparator = NULL; andre@0: entry.duplicateFunction = pkix_duplicateImmutable; andre@0: andre@0: systemClasses[PKIX_CERTPOLICYQUALIFIER_TYPE] = entry; andre@0: andre@0: PKIX_RETURN(CERTPOLICYQUALIFIER); andre@0: } andre@0: andre@0: /* --Public-CertPolicyQualifier-Functions------------------------- */ andre@0: andre@0: /* andre@0: * FUNCTION: PKIX_PL_PolicyQualifier_GetPolicyQualifierId andre@0: * (see comments in pkix_pl_pki.h) andre@0: */ andre@0: PKIX_Error * andre@0: PKIX_PL_PolicyQualifier_GetPolicyQualifierId( andre@0: PKIX_PL_CertPolicyQualifier *policyQualifierInfo, andre@0: PKIX_PL_OID **pPolicyQualifierId, andre@0: void *plContext) andre@0: { andre@0: PKIX_ENTER(CERTPOLICYQUALIFIER, andre@0: "PKIX_PL_PolicyQualifier_GetPolicyQualifierId"); andre@0: andre@0: PKIX_NULLCHECK_TWO(policyQualifierInfo, pPolicyQualifierId); andre@0: andre@0: PKIX_INCREF(policyQualifierInfo->policyQualifierId); andre@0: andre@0: *pPolicyQualifierId = policyQualifierInfo->policyQualifierId; andre@0: andre@0: cleanup: andre@0: PKIX_RETURN(CERTPOLICYQUALIFIER); andre@0: } andre@0: andre@0: /* andre@0: * FUNCTION: PKIX_PL_PolicyQualifier_GetQualifier andre@0: * (see comments in pkix_pl_pki.h) andre@0: */ andre@0: PKIX_Error * andre@0: PKIX_PL_PolicyQualifier_GetQualifier( andre@0: PKIX_PL_CertPolicyQualifier *policyQualifierInfo, andre@0: PKIX_PL_ByteArray **pQualifier, andre@0: void *plContext) andre@0: { andre@0: PKIX_ENTER(CERTPOLICYQUALIFIER, "PKIX_PL_PolicyQualifier_GetQualifier"); andre@0: andre@0: PKIX_NULLCHECK_TWO(policyQualifierInfo, pQualifier); andre@0: andre@0: PKIX_INCREF(policyQualifierInfo->qualifier); andre@0: andre@0: *pQualifier = policyQualifierInfo->qualifier; andre@0: andre@0: cleanup: andre@0: PKIX_RETURN(CERTPOLICYQUALIFIER); andre@0: }