Add method in SignatureValidator for cert-checker 52/45352/4
authorKyungwook Tak <k.tak@samsung.com>
Wed, 5 Aug 2015 05:58:35 +0000 (14:58 +0900)
committerKyungwook Tak <k.tak@samsung.com>
Thu, 6 Aug 2015 06:59:55 +0000 (15:59 +0900)
Change-Id: I89888472754accdde4632692c80b40dca9713710
Signed-off-by: Kyungwook Tak <k.tak@samsung.com>
vcore/vcore/SignatureValidator.cpp
vcore/vcore/SignatureValidator.h

index 52f04b5..c366fd8 100644 (file)
@@ -174,7 +174,7 @@ static struct tm getMidTime(const struct tm &tb, const struct tm &ta)
        return tMid;
 }
 
-} // namespace anonymouse
+} // namespace anonymous
 
 
 
@@ -183,14 +183,10 @@ namespace ValidationCore {
 /*
  *  Prepare to check / checklist. parse xml and save info to signature data.
  *
- *  [in]  fileInfo : signature file information to check. file path should be absolute path
- *                   which is made by SignatureFinder.
  *  [out] outData  : signature data for validating and will be finally returned to client.
  */
-int prepareToCheck(const SignatureFileInfo &fileInfo, SignatureData &outData)
+int prepareToCheck(SignatureData &outData)
 {
-       outData = SignatureData(fileInfo.getFileName(), fileInfo.getFileNumber());
-
        try {
                SignatureReader xml;
                xml.initialize(outData, SIGNATURE_SCHEMA_PATH);
@@ -204,14 +200,61 @@ int prepareToCheck(const SignatureFileInfo &fileInfo, SignatureData &outData)
 }
 
 /*
+ *  Make SignatureData by parsing signature file.
+ *  and get certificate chain with attached certificate in signature
+ */
+static int makeDataBySignature(
+       const SignatureFileInfo &fileInfo,
+       bool completeWithSystemCert,
+       SignatureData &data)
+{
+       data = SignatureData(fileInfo.getFileName(), fileInfo.getFileNumber());
+
+       if (prepareToCheck(data)) {
+               LogError("Failed to prepare to check.");
+               return -1;
+       }
+
+       if (!checkRoleURI(data) || !checkProfileURI(data))
+               return -1;
+
+       try {
+               CertificateCollection collection;
+               collection.load(data.getCertList());
+
+               if (!collection.sort() || collection.empty()) {
+                       LogError("Certificates do not form valid chain.");
+                       return -1;
+               }
+
+               if (completeWithSystemCert && !collection.completeCertificateChain()) {
+                       LogError("Failed to complete cert chain with system cert");
+                       return -1;
+               }
+
+               data.setSortedCertificateList(collection.getChain());
+               return 0;
+
+       } catch (const CertificateCollection::Exception::Base &e) {
+               LogError("CertificateCollection exception : " << e.DumpToString());
+               return -1;
+       } catch (...) {
+               LogError("Unknown exception in SignatureValidator::makeChainBySignature");
+               return -1;
+       }
+}
+
+/*
  *  Same logic (check, checkList) is functionalized here.
  *
+ *  [in]  fileInfo  : file info of signature to check
  *  [in]  checkOcsp : If on, check ocsp.
  *  [out] disregard : distributor signature disregard flag.
  *  [out] context   : xml sec for validating.
  *  [out] data      : signature data for validationg and will be finally returned to client.
  */
 static SignatureValidator::Result checkInternal(
+       const SignatureFileInfo &fileInfo,
        bool checkOcsp,
        bool &disregard,
        XmlSec::XmlSecContext &context,
@@ -220,22 +263,11 @@ static SignatureValidator::Result checkInternal(
        // TODO: impl ocsp check
        (void) checkOcsp;
 
-       if (!checkRoleURI(data) || !checkProfileURI(data))
+       if (makeDataBySignature(fileInfo, true, data))
                return SignatureValidator::SIGNATURE_INVALID;
 
-       CertificateCollection collection;
-       collection.load(data.getCertList());
-
-       if (!collection.sort() || collection.empty() || !collection.completeCertificateChain()) {
-               LogWarning("Certificates do not form valid chain.");
-               return SignatureValidator::SIGNATURE_INVALID;
-       }
-
-       CertificateList sortedCertificateList = collection.getChain();
-       CertificatePtr root = sortedCertificateList.back();
-
        // Is Root CA certificate trusted?
-       CertStoreId::Set storeIdSet = createCertificateIdentifier().find(root);
+       CertStoreId::Set storeIdSet = createCertificateIdentifier().find(data.getCertList().back());
 
        LogDebug("root certificate from " << storeIdSet.typeToString() << " domain");
        if (data.isAuthorSignature()) {
@@ -259,14 +291,13 @@ static SignatureValidator::Result checkInternal(
        }
 
        data.setStorageType(storeIdSet);
-       data.setSortedCertificateList(sortedCertificateList);
 
        /*
         * We add only Root CA certificate because the rest
         * of certificates are present in signature files ;-)
         */
        context.signatureFile = data.getSignatureFileName();
-       context.certificatePtr = root;
+       context.certificatePtr = data.getCertList().back();
 
        /* certificate time check */
        ASN1_TIME* notAfterTime = data.getEndEntityCertificatePtr()->getNotAfterTime();
@@ -295,16 +326,11 @@ SignatureValidator::Result SignatureValidator::check(
        bool checkReferences,
        SignatureData &outData)
 {
-       if (prepareToCheck(fileInfo, outData)) {
-               LogError("Failed to prepare to check.");
-               return SIGNATURE_INVALID;
-       }
-
        bool disregard = false;
 
        try {
                XmlSec::XmlSecContext context;
-               Result result = checkInternal(checkOcsp, disregard, context, outData);
+               Result result = checkInternal(fileInfo, checkOcsp, disregard, context, outData);
                if (result != SIGNATURE_VERIFIED)
                        return result;
 
@@ -350,15 +376,11 @@ SignatureValidator::Result SignatureValidator::checkList(
        bool checkReferences,
        SignatureData &outData)
 {
-       if (prepareToCheck(fileInfo, outData)) {
-               LogError("Failed to prepare to check.");
-               return SIGNATURE_INVALID;
-       }
-
        bool disregard = false;
+
        try {
                XmlSec::XmlSecContext context;
-               Result result = checkInternal(checkOcsp, disregard, context, outData);
+               Result result = checkInternal(fileInfo, checkOcsp, disregard, context, outData);
                if (result != SIGNATURE_VERIFIED)
                        return result;
 
@@ -404,6 +426,20 @@ SignatureValidator::Result SignatureValidator::checkList(
        return disregard ? SIGNATURE_DISREGARD : SIGNATURE_VERIFIED;
 }
 
+SignatureValidator::Result SignatureValidator::makeChainBySignature(
+       const SignatureFileInfo &fileInfo,
+       bool completeWithSystemCert,
+       CertificateList &certList)
+{
+       SignatureData data;
+       if (makeDataBySignature(fileInfo, completeWithSystemCert, data))
+               return SIGNATURE_INVALID;
+
+       certList = data.getCertList();
+
+       return SIGNATURE_VALID;
+}
+
 
 } // namespace ValidationCore
 
index 8154f8c..60afb27 100644 (file)
@@ -24,6 +24,7 @@
 
 #include <string>
 #include <list>
+#include <vcore/Certificate.h>
 #include <vcore/SignatureData.h>
 #include <vcore/SignatureFinder.h>
 
@@ -60,6 +61,18 @@ public:
         bool checkOcsp,
         bool checkReferences,
         SignatureData &outData);
+
+    /*
+     *  @Remarks : cert list isn't completed with self-signed root CA system cert
+     *             if completeWithSystemCert is false.
+     *
+     *  return Result::SIGNATURE_VALID if success
+     *  return Result::SIGNATURE_INVALID otherwise
+     */
+    static Result makeChainBySignature(
+        const SignatureFileInfo &fileInfo,
+        bool completeWithSystemCert,
+        CertificateList &certList);
 };
 
 } // namespace ValidationCore