[CRYPT32] Sync with Wine Staging 1.9.23. Jérôme, please review as we no longer have...
authorAmine Khaldi <amine.khaldi@reactos.org>
Tue, 22 Nov 2016 17:05:59 +0000 (17:05 +0000)
committerAmine Khaldi <amine.khaldi@reactos.org>
Tue, 22 Nov 2016 17:05:59 +0000 (17:05 +0000)
svn path=/trunk/; revision=73346

reactos/dll/win32/crypt32/chain.c
reactos/dll/win32/crypt32/crypt32.spec
reactos/dll/win32/crypt32/crypt32_private.h
reactos/dll/win32/crypt32/main.c
reactos/dll/win32/crypt32/regstore.c
reactos/dll/win32/crypt32/rootstore.c
reactos/dll/win32/crypt32/store.c
reactos/media/doc/README.WINE

index b64f121..45bb8f3 100644 (file)
@@ -2697,10 +2697,20 @@ static void CRYPT_VerifyChainRevocation(PCERT_CHAIN_CONTEXT chain,
                     revocationPara.pIssuerCert =
                      chain->rgpChain[i]->rgpElement[j + 1]->pCertContext;
                 else
-                    revocationPara.pIssuerCert = NULL;
+                    revocationPara.pIssuerCert = certToCheck;
+
                 ret = CertVerifyRevocation(X509_ASN_ENCODING,
                  CERT_CONTEXT_REVOCATION_TYPE, 1, (void **)&certToCheck,
                  revocationFlags, &revocationPara, &revocationStatus);
+
+                if (!ret && revocationStatus.dwError == CRYPT_E_NO_REVOCATION_CHECK &&
+                    revocationPara.pIssuerCert == certToCheck)
+                {
+                    FIXME("Unable to find CRL for CA certificate\n");
+                    ret = TRUE;
+                    revocationStatus.dwError = 0;
+                }
+
                 if (!ret)
                 {
                     PCERT_CHAIN_ELEMENT element = CRYPT_FindIthElementInChain(
index 0d2a477..b5ce48c 100644 (file)
@@ -78,6 +78,7 @@
 @ stdcall CertRDNValueToStrA(long ptr ptr long)
 @ stdcall CertRDNValueToStrW(long ptr ptr long)
 @ stdcall CertRegisterPhysicalStore(ptr long wstr ptr ptr)
+@ stdcall CertRegisterSystemStore(ptr long ptr ptr)
 @ stdcall CertRemoveEnhancedKeyUsageIdentifier(ptr str)
 @ stdcall CertRemoveStoreFromCollection(ptr ptr)
 @ stdcall CertSaveStore(ptr long long long ptr long)
 @ stdcall CryptUnprotectMemory(ptr long long)
 @ stdcall CryptUnregisterDefaultOIDFunction(long str wstr)
 @ stdcall CryptUnregisterOIDFunction(long str str)
+@ stdcall CertUnregisterSystemStore(ptr long)
 @ stub CryptUnregisterOIDInfo
 @ stdcall CryptVerifyCertificateSignature(long long ptr long ptr)
 @ stdcall CryptVerifyCertificateSignatureEx(long long long ptr long ptr long ptr)
index 75c0497..9ef8655 100644 (file)
@@ -365,7 +365,11 @@ WINECRYPT_CERTSTORE *CRYPT_FileNameOpenStoreA(HCRYPTPROV hCryptProv,
  DWORD dwFlags, const void *pvPara) DECLSPEC_HIDDEN;
 WINECRYPT_CERTSTORE *CRYPT_FileNameOpenStoreW(HCRYPTPROV hCryptProv,
  DWORD dwFlags, const void *pvPara) DECLSPEC_HIDDEN;
-WINECRYPT_CERTSTORE *CRYPT_RootOpenStore(HCRYPTPROV hCryptProv, DWORD dwFlags) DECLSPEC_HIDDEN;
+
+void CRYPT_ImportSystemRootCertsToReg(void) DECLSPEC_HIDDEN;
+BOOL CRYPT_SerializeContextsToReg(HKEY key, DWORD flags, const WINE_CONTEXT_INTERFACE *contextInterface,
+    HCERTSTORE memStore) DECLSPEC_HIDDEN;
+
 BOOL CRYPT_IsCertificateSelfSigned(PCCERT_CONTEXT cert) DECLSPEC_HIDDEN;
 
 /* Allocates and initializes a certificate chain engine, but without creating
index 66d2b89..8f2902e 100644 (file)
@@ -40,7 +40,6 @@ BOOL WINAPI DllMain(HINSTANCE hInst, DWORD fdwReason, PVOID pvReserved)
             if (pvReserved) break;
             crypt_oid_free();
             crypt_sip_free();
-            root_store_free();
             default_chain_engine_free();
             if (hDefProv) CryptReleaseContext(hDefProv, 0);
             break;
index 783149c..ba4b439 100644 (file)
@@ -174,7 +174,7 @@ static void CRYPT_RegReadFromReg(HKEY key, HCERTSTORE store)
 }
 
 /* Hash is assumed to be 20 bytes in length (a SHA-1 hash) */
-static BOOL CRYPT_WriteSerializedToReg(HKEY key, const BYTE *hash, const BYTE *buf,
+static BOOL CRYPT_WriteSerializedToReg(HKEY key, DWORD flags, const BYTE *hash, const BYTE *buf,
  DWORD len)
 {
     WCHAR asciiHash[20 * 2 + 1];
@@ -183,7 +183,7 @@ static BOOL CRYPT_WriteSerializedToReg(HKEY key, const BYTE *hash, const BYTE *b
     BOOL ret;
 
     CRYPT_HashToStr(hash, asciiHash);
-    rc = RegCreateKeyExW(key, asciiHash, 0, NULL, 0, KEY_ALL_ACCESS, NULL,
+    rc = RegCreateKeyExW(key, asciiHash, 0, NULL, flags, KEY_ALL_ACCESS, NULL,
      &subKey, NULL);
     if (!rc)
     {
@@ -200,7 +200,7 @@ static BOOL CRYPT_WriteSerializedToReg(HKEY key, const BYTE *hash, const BYTE *b
     return ret;
 }
 
-static BOOL CRYPT_SerializeContextsToReg(HKEY key,
+BOOL CRYPT_SerializeContextsToReg(HKEY key, DWORD flags,
  const WINE_CONTEXT_INTERFACE *contextInterface, HCERTSTORE memStore)
 {
     const void *context = NULL;
@@ -227,7 +227,7 @@ static BOOL CRYPT_SerializeContextsToReg(HKEY key,
                 {
                     ret = contextInterface->serialize(context, 0, buf, &size);
                     if (ret)
-                        ret = CRYPT_WriteSerializedToReg(key, hash, buf, size);
+                        ret = CRYPT_WriteSerializedToReg(key, flags, hash, buf, size);
                 }
                 CryptMemFree(buf);
             }
@@ -282,8 +282,7 @@ static BOOL CRYPT_RegWriteToReg(WINE_REGSTOREINFO *store)
                 }
                 LeaveCriticalSection(&store->cs);
             }
-            ret = CRYPT_SerializeContextsToReg(key, interfaces[i],
-             store->memStore);
+            ret = CRYPT_SerializeContextsToReg(key, 0, interfaces[i], store->memStore);
             RegCloseKey(key);
         }
         else
index e0a85e9..48b072e 100644 (file)
@@ -428,53 +428,6 @@ static BOOL import_certs_from_path(LPCSTR path, HCERTSTORE store,
     return ret;
 }
 
-static BOOL WINAPI CRYPT_RootWriteCert(HCERTSTORE hCertStore,
- PCCERT_CONTEXT cert, DWORD dwFlags)
-{
-    /* The root store can't have certs added */
-    return FALSE;
-}
-
-static BOOL WINAPI CRYPT_RootDeleteCert(HCERTSTORE hCertStore,
- PCCERT_CONTEXT cert, DWORD dwFlags)
-{
-    /* The root store can't have certs deleted */
-    return FALSE;
-}
-
-static BOOL WINAPI CRYPT_RootWriteCRL(HCERTSTORE hCertStore,
- PCCRL_CONTEXT crl, DWORD dwFlags)
-{
-    /* The root store can have CRLs added.  At worst, a malicious application
-     * can DoS itself, as the changes aren't persisted in any way.
-     */
-    return TRUE;
-}
-
-static BOOL WINAPI CRYPT_RootDeleteCRL(HCERTSTORE hCertStore,
- PCCRL_CONTEXT crl, DWORD dwFlags)
-{
-    /* The root store can't have CRLs deleted */
-    return FALSE;
-}
-
-static void *rootProvFuncs[] = {
-    NULL, /* CERT_STORE_PROV_CLOSE_FUNC */
-    NULL, /* CERT_STORE_PROV_READ_CERT_FUNC */
-    CRYPT_RootWriteCert,
-    CRYPT_RootDeleteCert,
-    NULL, /* CERT_STORE_PROV_SET_CERT_PROPERTY_FUNC */
-    NULL, /* CERT_STORE_PROV_READ_CRL_FUNC */
-    CRYPT_RootWriteCRL,
-    CRYPT_RootDeleteCRL,
-    NULL, /* CERT_STORE_PROV_SET_CRL_PROPERTY_FUNC */
-    NULL, /* CERT_STORE_PROV_READ_CTL_FUNC */
-    NULL, /* CERT_STORE_PROV_WRITE_CTL_FUNC */
-    NULL, /* CERT_STORE_PROV_DELETE_CTL_FUNC */
-    NULL, /* CERT_STORE_PROV_SET_CTL_PROPERTY_FUNC */
-    NULL, /* CERT_STORE_PROV_CONTROL_FUNC */
-};
-
 static const char * const CRYPT_knownLocations[] = {
  "/etc/ssl/certs/ca-certificates.crt",
  "/etc/ssl/certs",
@@ -783,68 +736,65 @@ static void read_trusted_roots_from_known_locations(HCERTSTORE store)
 
 static HCERTSTORE create_root_store(void)
 {
-    HCERTSTORE root = NULL;
     HCERTSTORE memStore = CertOpenStore(CERT_STORE_PROV_MEMORY,
      X509_ASN_ENCODING, 0, CERT_STORE_CREATE_NEW_FLAG, NULL);
 
     if (memStore)
     {
-        CERT_STORE_PROV_INFO provInfo = {
-         sizeof(CERT_STORE_PROV_INFO),
-         sizeof(rootProvFuncs) / sizeof(rootProvFuncs[0]),
-         rootProvFuncs,
-         NULL,
-         0,
-         NULL
-        };
-
         read_trusted_roots_from_known_locations(memStore);
         add_ms_root_certs(memStore);
-        root = CRYPT_ProvCreateStore(0, memStore, &provInfo);
-#ifdef __REACTOS__
-        {
-            HCERTSTORE regStore = CertOpenStore(CERT_STORE_PROV_SYSTEM_W, 0, 0, CERT_SYSTEM_STORE_LOCAL_MACHINE, L"AuthRoot");
-            if (regStore)
-            {
-                HCERTSTORE collStore = CertOpenStore(CERT_STORE_PROV_COLLECTION, 0, 0,
-                    CERT_STORE_CREATE_NEW_FLAG, NULL);
-                CertAddStoreToCollection(collStore, regStore, 0, 0);
-                CertAddStoreToCollection(collStore, root, 0, 0);
-                root = collStore;
-            }
-        }
-#endif
     }
-    TRACE("returning %p\n", root);
-    return root;
+
+    TRACE("returning %p\n", memStore);
+    return memStore;
 }
 
-static WINECRYPT_CERTSTORE *CRYPT_rootStore;
+static const WCHAR certs_root_pathW[] =
+ {'S','o','f','t','w','a','r','e','\\','M','i','c','r','o','s','o','f','t','\\',
+  'S','y','s','t','e','m','C','e','r','t','i','f','i','c','a','t','e','s','\\',
+  'R','o','o','t','\\', 'C','e','r','t','i','f','i','c','a','t','e','s', 0};
+static const WCHAR semaphoreW[] =
+ {'c','r','y','p','t','3','2','_','r','o','o','t','_','s','e','m','a','p','h','o','r','e',0};
 
-WINECRYPT_CERTSTORE *CRYPT_RootOpenStore(HCRYPTPROV hCryptProv, DWORD dwFlags)
+void CRYPT_ImportSystemRootCertsToReg(void)
 {
-    TRACE("(%ld, %08x)\n", hCryptProv, dwFlags);
+    HCERTSTORE store = NULL;
+    HKEY key;
+    LONG rc;
+    HANDLE hsem;
+
+    static BOOL root_certs_imported = FALSE;
+
+    if (root_certs_imported)
+        return;
 
-    if (dwFlags & CERT_STORE_DELETE_FLAG)
+    hsem = CreateSemaphoreW( NULL, 0, 1, semaphoreW);
+    if (!hsem)
     {
-        WARN("root store can't be deleted\n");
-        SetLastError(ERROR_ACCESS_DENIED);
-        return NULL;
+        ERR("Failed to create semaphore\n");
+        return;
     }
-    if (!CRYPT_rootStore)
-    {
-        HCERTSTORE root = create_root_store();
 
-        InterlockedCompareExchangePointer((PVOID *)&CRYPT_rootStore, root,
-         NULL);
-        if (CRYPT_rootStore != root)
-            CertCloseStore(root, 0);
+    if(GetLastError() == ERROR_ALREADY_EXISTS)
+        WaitForSingleObject(hsem, INFINITE);
+    else
+    {
+        if ((store = create_root_store()))
+        {
+            rc = RegCreateKeyExW(HKEY_LOCAL_MACHINE, certs_root_pathW, 0, NULL, 0,
+                KEY_ALL_ACCESS, NULL, &key, 0);
+            if (!rc)
+            {
+                if (!CRYPT_SerializeContextsToReg(key, REG_OPTION_VOLATILE, pCertInterface, store))
+                    ERR("Failed to import system certs into registry, %08x\n", GetLastError());
+                RegCloseKey(key);
+            }
+            CertCloseStore(store, 0);
+        } else
+            ERR("Failed to create root store\n");
     }
-    CRYPT_rootStore->vtbl->addref(CRYPT_rootStore);
-    return CRYPT_rootStore;
-}
 
-void root_store_free(void)
-{
-    CertCloseStore(CRYPT_rootStore, 0);
+    root_certs_imported = TRUE;
+    ReleaseSemaphore(hsem, 1, NULL);
+    CloseHandle(hsem);
 }
index b0a77f6..7910635 100644 (file)
@@ -411,21 +411,15 @@ static WINECRYPT_CERTSTORE *CRYPT_SysRegOpenStoreW(HCRYPTPROV hCryptProv,
         SetLastError(E_INVALIDARG);
         return NULL;
     }
-    /* FIXME:  In Windows, the root store (even the current user location) is
-     * protected:  adding to it or removing from it present a user interface,
-     * and the keys are owned by the system process, not the current user.
-     * Wine's registry doesn't implement access controls, so a similar
-     * mechanism isn't possible yet.
-     */
-    if ((dwFlags & CERT_SYSTEM_STORE_LOCATION_MASK) ==
-     CERT_SYSTEM_STORE_LOCAL_MACHINE && !lstrcmpiW(storeName, rootW))
-        return CRYPT_RootOpenStore(hCryptProv, dwFlags);
 
     switch (dwFlags & CERT_SYSTEM_STORE_LOCATION_MASK)
     {
     case CERT_SYSTEM_STORE_LOCAL_MACHINE:
         root = HKEY_LOCAL_MACHINE;
         base = CERT_LOCAL_MACHINE_SYSTEM_STORE_REGPATH;
+        /* If the HKLM\Root certs are requested, expressing system certs into the registry */
+        if (!lstrcmpiW(storeName, rootW))
+            CRYPT_ImportSystemRootCertsToReg();
         break;
     case CERT_SYSTEM_STORE_CURRENT_USER:
         root = HKEY_CURRENT_USER;
@@ -1377,6 +1371,51 @@ BOOL WINAPI CertRegisterPhysicalStore(const void *pvSystemStore, DWORD dwFlags,
     return FALSE;
 }
 
+BOOL WINAPI CertRegisterSystemStore(const void *pvSystemStore, DWORD dwFlags,
+  PCERT_SYSTEM_STORE_INFO pStoreInfo, void *pvReserved)
+{
+    HCERTSTORE hstore;
+
+    if (dwFlags & CERT_SYSTEM_STORE_RELOCATE_FLAG )
+    {
+        FIXME("(%p, %08x, %p, %p): flag not supported\n", pvSystemStore, dwFlags, pStoreInfo, pvReserved);
+        return FALSE;
+    }
+
+    TRACE("(%s, %08x, %p, %p)\n", debugstr_w(pvSystemStore), dwFlags, pStoreInfo, pvReserved);
+
+    hstore = CertOpenStore(CERT_STORE_PROV_SYSTEM_REGISTRY_W, 0, 0, dwFlags, pvSystemStore);
+    if (hstore)
+    {
+        CertCloseStore(hstore, 0);
+        return TRUE;
+    }
+
+    return FALSE;
+}
+
+BOOL WINAPI CertUnregisterSystemStore(void *pvSystemStore, DWORD dwFlags)
+{
+    HCERTSTORE hstore;
+
+    if (dwFlags & CERT_SYSTEM_STORE_RELOCATE_FLAG)
+    {
+        FIXME("(%p, %08x): flag not supported\n", pvSystemStore, dwFlags);
+        return FALSE;
+    }
+    TRACE("(%s, %08x)\n", debugstr_w(pvSystemStore), dwFlags);
+
+    hstore = CertOpenStore(CERT_STORE_PROV_SYSTEM_REGISTRY_W, 0, 0, dwFlags | CERT_STORE_OPEN_EXISTING_FLAG, pvSystemStore);
+    if (hstore == NULL)
+        return FALSE;
+
+    hstore = CertOpenStore(CERT_STORE_PROV_SYSTEM_REGISTRY_W, 0, 0, dwFlags | CERT_STORE_DELETE_FLAG, pvSystemStore);
+    if (hstore == NULL && GetLastError() == 0)
+        return TRUE;
+
+    return FALSE;
+}
+
 static void EmptyStore_addref(WINECRYPT_CERTSTORE *store)
 {
     TRACE("(%p)\n", store);
index 7e6b5c4..c317566 100644 (file)
@@ -58,7 +58,7 @@ reactos/dll/win32/comctl32            # Synced to WineStaging-1.9.23
 reactos/dll/win32/comdlg32            # Synced to WineStaging-1.9.23
 reactos/dll/win32/compstui            # Synced to WineStaging-1.9.11
 reactos/dll/win32/credui              # Synced to WineStaging-1.9.16
-reactos/dll/win32/crypt32             # Synced to WineStaging-1.9.16
+reactos/dll/win32/crypt32             # Synced to WineStaging-1.9.23
 reactos/dll/win32/cryptdlg            # Synced to WineStaging-1.9.11
 reactos/dll/win32/cryptdll            # Synced to WineStaging-1.9.11
 reactos/dll/win32/cryptnet            # Synced to WineStaging-1.9.11