Example #1
0
        new internal static SafeLocalAllocHandle LocalAlloc(uint uFlags, uint sizetdwBytes)
        {
            SafeLocalAllocHandle safeLocalAllocHandle = CAPIMethods.LocalAlloc(uFlags, sizetdwBytes);

            if (safeLocalAllocHandle == null || safeLocalAllocHandle.IsInvalid)
            {
                throw new OutOfMemoryException();
            }

            return(safeLocalAllocHandle);
        }
Example #2
0
        internal static bool CertSetKeyProviderInfoProperty(IntPtr pCert, SafeLocalAllocHandle handle)
        {
            if (pCert == null)
            {
                throw new ArgumentNullException(nameof(pCert));
            }

            if (handle.IsInvalid)
            {
                throw new ArgumentException(nameof(handle));
            }

            new PermissionSet(PermissionState.Unrestricted).Demand();

            return(CertSetCertificateContextProperty(pCert, CAPI.CERT_KEY_PROV_INFO_PROP_ID, 0, handle));
        }
Example #3
0
        /// <summary>
        /// If the certificate has private key, this cert can be used for signing, if it does not,
        /// try to access private key stored in the CSP, if CSP provider or key container name
        /// is not provided, certificate can't be used for signing.
        /// </summary>
        /// <param name="certificate">Certificate</param>
        /// <param name="cryptoProviderName">Crypto provider name</param>
        /// <param name="keyContainerName">Key container name</param>
        /// <param name="providerType">Provider type</param>
        /// <returns></returns>
        public static bool SetPrivateKeyIfNeeded(X509Certificate2 certificate, string cryptoProviderName, string keyContainerName, int providerType = -1)
        {
            if (Certificate.HasPrivateKey(certificate))
            {
                // We got a .pfx file.
                // Silently ignore CSP name or key container if either was provided with a .pfx fle.
                return(true);
            }

            // If provider and key container names are specified, try to access private key.
            if (cryptoProviderName != null && keyContainerName != null)
            {
                try
                {
                    bool result = true;

                    if (providerType == PROV_UNINITIALIZED)
                    {
                        providerType = Certificate.GetCspType(cryptoProviderName);
                    }

                    if (providerType == PROV_UNINITIALIZED)
                    {
                        return(false);
                    }

                    // The following code will modify state of certificates from x509Store,
                    // make sure to assign private keys only to certificates that were created from a .cer files
                    if (providerType != 0)
                    {
                        CspParameters parameters;
                        parameters = new CspParameters
                        {
                            ProviderName     = cryptoProviderName,
                            ProviderType     = providerType,
                            KeyContainerName = keyContainerName,
                            KeyNumber        = (int)KeyNumber.Signature,
                            // Make sure key creation is not attempted.
                            Flags = CspProviderFlags.UseExistingKey
                        };

                        if (IsMachineCryptKey(cryptoProviderName, (uint)providerType, keyContainerName))
                        {
                            // Search only Machine key store for this private key, if not set we search only user store.
                            parameters.Flags |= CspProviderFlags.UseMachineKeyStore;
                        }

                        certificate.PrivateKey = new RSACryptoServiceProvider(parameters);
                    }
                    else
                    {
                        CAPI.CRYPT_KEY_PROV_INFO keyProvInfo = new CAPI.CRYPT_KEY_PROV_INFO
                        {
                            pwszProvName      = cryptoProviderName,
                            pwszContainerName = keyContainerName,
                            dwProvType        = (uint)providerType,
                            dwKeySpec         = (int)KeyNumber.Signature,
                            dwFlags           = IsMachineNCryptKey(cryptoProviderName, keyContainerName) ? NCryptMethods.NCRYPT_MACHINE_KEY_FLAG : (uint)0
                        };

                        using (SafeLocalAllocHandle pKeyProvInfo = CAPI.LocalAlloc(CAPI.LPTR, (uint)Marshal.SizeOf(typeof(CAPI.CRYPT_KEY_PROV_INFO))))
                        {
                            Marshal.StructureToPtr(keyProvInfo, pKeyProvInfo.DangerousGetHandle(), false);
                            result = CAPI.CertSetKeyProviderInfoProperty(certificate.Handle, pKeyProvInfo);
                            Marshal.DestroyStructure(pKeyProvInfo.DangerousGetHandle(), typeof(CAPI.CRYPT_KEY_PROV_INFO));
                        }
                    }

                    return(result);
                }
                catch (Exception e)
                {
                    if (Misc.IsCriticalException(e))
                    {
                        throw;
                    }
                    // Caller displays an error message.
                    System.Diagnostics.Debug.WriteLine(e.Message);
                }
            }

            return(false);
        }
Example #4
0
 internal static extern bool CertSetCertificateContextProperty(
     IntPtr pCertContext,
     int dwPropId,
     int dwFlags,
     SafeLocalAllocHandle pvData);