Beispiel #1
0
        public void TestEncryptPFXFileOaepSha512()
        {
            string hashAlgorithm = PaddingHashAlgorithmNames.SHA512;
            int    paddingFlags  = PaddingFlags.OAEPPadding;

            ProviderKeyInitialize(TestProviderName1, TestKeyName1, TestAlgorithmName);

            Command encryptCommand = GenerateSetUserPFXCertificatesCommand(
                TestFilePath1,
                TestUPN1,
                securePassword,
                TestProviderName1,
                TestKeyName1,
                UserPfxPaddingScheme.OaepSha512,
                UserPfxIntendedPurpose.SmimeEncryption);

            powershell.Commands.AddCommand(encryptCommand);

            var pfxResults = powershell.Invoke <UserPFXCertificate>();

            Assert.AreEqual(pfxResults.Count(), 1);

            UserPFXCertificate userPFXResult = pfxResults.First();

            Assert.AreEqual(userPFXResult.PaddingScheme, UserPfxPaddingScheme.OaepSha512);

            ValidatePasswordDecryptable(userPFXResult, testPassword, hashAlgorithm, paddingFlags);

            ProviderKeyCleanup(TestProviderName1, TestKeyName1);
        }
Beispiel #2
0
        public void TestEncryptPFXFile()
        {
            ProviderKeyInitialize(TestProviderName1, TestKeyName1, TestAlgorithmName);

            Command encryptCommand = GenerateSetUserPFXCertificatesCommand(
                TestFilePath1,
                TestUPN1,
                securePassword,
                TestProviderName1,
                TestKeyName1,
                UserPfxPaddingScheme.None,
                UserPfxIntendedPurpose.SmimeEncryption);

            powershell.Commands.AddCommand(encryptCommand);

            var pfxResults = powershell.Invoke <UserPFXCertificate>();

            Assert.AreEqual(pfxResults.Count(), 1);

            UserPFXCertificate userPFXResult = pfxResults.First();

            Assert.AreEqual(userPFXResult.KeyName, TestKeyName1);
            Assert.AreEqual(userPFXResult.ProviderName, TestProviderName1);
            Assert.AreNotEqual(userPFXResult.EncryptedPfxPassword, testPassword);
            Assert.AreEqual(userPFXResult.UserPrincipalName, TestUPN1);
            Assert.AreEqual(userPFXResult.PaddingScheme, UserPfxPaddingScheme.None);
            Assert.AreEqual(userPFXResult.IntendedPurpose, UserPfxIntendedPurpose.SmimeEncryption);
            Assert.IsNotNull(userPFXResult.EncryptedPfxBlob);

            ValidatePasswordDecryptable(userPFXResult, testPassword, PaddingHashAlgorithmNames.SHA512, PaddingFlags.OAEPPadding);

            ProviderKeyCleanup(TestProviderName1, TestKeyName1);
        }
Beispiel #3
0
        private void ProcessSingleResponse(HttpWebRequest request, string filter)
        {
            bool     needsRetry = false;
            TimeSpan waitTime   = TimeSpan.Zero;
            double   retryAfter = 60; // TODO: get a good default wait time.

            try
            {
                using (var response = (HttpWebResponse)request.GetResponse())
                {
                    if (response.StatusCode == HttpStatusCode.OK)
                    {
                        string responseMessage = string.Empty;
                        using (StreamReader rs = new StreamReader(response.GetResponseStream()))
                        {
                            responseMessage = rs.ReadToEnd();
                        }

                        UserPFXCertificate cert = SerializationHelpers.DeserializeUserPFXCertificate(responseMessage);
                        this.WriteObject(cert);
                    }
                    else
                    {
                        this.WriteError(new ErrorRecord(new InvalidOperationException(response.StatusDescription), response.StatusCode.ToString(), ErrorCategory.InvalidResult, filter));
                    }
                }
            }
            catch (WebException we)
            {
                HttpWebResponse response = we.Response as HttpWebResponse;
                if (we.Status == WebExceptionStatus.ProtocolError && response.StatusCode == (HttpStatusCode)429)
                {
                    needsRetry = true;
                    if (response.Headers["x-ms-retry-after-ms"] != null)
                    {
                        retryAfter = double.Parse(response.Headers["x-ms-retry-after-ms"]);
                    }

                    if (response.Headers["Retry-After"] != null)
                    {
                        retryAfter = double.Parse(response.Headers["Retry-After"]);
                    }
                }
                else
                {
                    this.WriteError(new ErrorRecord(we, we.Message + " request-id:" + we.Response.Headers["request-id"], ErrorCategory.InvalidResult, filter));
                }
            }

            // Waiting until response is closed to re-use request
            if (needsRetry)
            {
                this.WriteWarning(string.Format(LogMessages.GetUserPfxTooManyRequests, retryAfter));
                Thread.Sleep(TimeSpan.FromSeconds(retryAfter));
                ProcessSingleResponse(request, filter);
            }
        }
Beispiel #4
0
        private void ValidatePasswordDecryptable(UserPFXCertificate userPFXResult, string expectedPassword, string hashAlgorithm, int paddingFlags)
        {
            ManagedRSAEncryption encryptionUtility = new ManagedRSAEncryption();

            byte[] passwordBytes       = Convert.FromBase64String(userPFXResult.EncryptedPfxPassword);
            byte[] unencryptedPassword = encryptionUtility.DecryptWithLocalKey(userPFXResult.ProviderName, userPFXResult.KeyName, passwordBytes, hashAlgorithm, paddingFlags);
            string clearTextPassword   = Encoding.ASCII.GetString(unencryptedPassword);

            Assert.AreEqual(clearTextPassword, expectedPassword);
        }
        public static List <UserPFXCertificate> DeserializeUserPFXCertificateList(string value)
        {
            JsonArrayWrapper          arrayWrapper   = JsonConvert.DeserializeObject <JsonArrayWrapper>(value);
            IEnumerable <JObject>     jsonArray      = arrayWrapper.Value;
            JsonSerializer            jsonSerializer = JsonSerializer.Create(jSONSettings);
            List <UserPFXCertificate> entityList     = new List <UserPFXCertificate>();

            foreach (JObject jObject in jsonArray)
            {
                string             entityJson = jObject.ToString();
                UserPFXCertificate entity     = DeserializeUserPFXCertificate(entityJson);
                entityList.Add(entity);
            }

            return(entityList);
        }
Beispiel #6
0
        /// <summary>
        /// ProcessRecord.
        /// </summary>
        protected override void ProcessRecord()
        {
            if (!Authenticate.AuthTokenIsValid(AuthenticationResult))
            {
                this.ThrowTerminatingError(
                    new ErrorRecord(
                        new AuthenticationException("Cannot get Authentication Token"),
                        "Authentication Failure",
                        ErrorCategory.AuthenticationError,
                        AuthenticationResult));
            }

            Hashtable modulePrivateData = this.MyInvocation.MyCommand.Module.PrivateData as Hashtable;
            string    graphURI          = Authenticate.GetGraphURI(modulePrivateData);
            string    schemaVersion     = Authenticate.GetSchemaVersion(modulePrivateData);

            if ((CertificateList == null || CertificateList.Count == 0) &&
                (UserThumbprintList == null || UserThumbprintList.Count == 0) &&
                (UserList == null || UserList.Count == 0))
            {
                this.ThrowTerminatingError(
                    new ErrorRecord(
                        new ArgumentException("No Certificates specified"),
                        "Date Input Failure",
                        ErrorCategory.InvalidArgument,
                        AuthenticationResult));
            }

            if (UserThumbprintList == null)
            {
                UserThumbprintList = new List <UserThumbprint>();
            }

            if (UserList != null)
            {
                PowerShell ps = PowerShell.Create();
                ps.AddCommand("Import-Module").AddParameter("ModuleInfo", this.MyInvocation.MyCommand.Module);
                ps.Invoke();
                ps.Commands.Clear();

                ps.AddCommand("Get-IntuneUserPfxCertificate");
                ps.AddParameter("AuthenticationResult", AuthenticationResult);
                ps.AddParameter("UserList", UserList);

                foreach (PSObject result in ps.Invoke())
                {
                    UserPFXCertificate cert   = result.BaseObject as UserPFXCertificate;
                    string             userId = GetUserPFXCertificate.GetUserIdFromUpn(cert.UserPrincipalName, graphURI, schemaVersion, AuthenticationResult);
                    UserThumbprintList.Add(new UserThumbprint()
                    {
                        User = userId, Thumbprint = cert.Thumbprint
                    });
                }
            }

            if (CertificateList != null && CertificateList.Count > 0)
            {
                foreach (UserPFXCertificate cert in CertificateList)
                {
                    string userId = GetUserPFXCertificate.GetUserIdFromUpn(cert.UserPrincipalName, graphURI, schemaVersion, AuthenticationResult);
                    UserThumbprintList.Add(new UserThumbprint()
                    {
                        User = userId, Thumbprint = cert.Thumbprint
                    });
                }
            }

            successCnt = 0;
            failureCnt = 0;

            foreach (UserThumbprint userThumbprint in UserThumbprintList)
            {
                string         url = string.Format(CultureInfo.InvariantCulture, "{0}/{1}/deviceManagement/userPfxCertificates/{2}-{3}", graphURI, schemaVersion, userThumbprint.User, userThumbprint.Thumbprint);
                HttpWebRequest request;
                request = CreateWebRequest(url, AuthenticationResult);
                ProcessResponse(request, userThumbprint.User + "-" + userThumbprint.Thumbprint);
            }

            this.WriteCommandDetail(string.Format(LogMessages.RemoveCertificateSuccess, successCnt));
            if (failureCnt > 0)
            {
                this.WriteWarning(string.Format(LogMessages.RemoveCertificateFailure, successCnt));
            }
        }
Beispiel #7
0
        private void ProcessResponse(HttpWebRequest request, UserPFXCertificate cert)
        {
            bool     needsRetry = false;
            TimeSpan waitTime   = TimeSpan.Zero;
            double   retryAfter = 60; // TODO: get a good default wait time.

            try
            {
                using (var response = (HttpWebResponse)request.GetResponse())
                {
                    if ((int)response.StatusCode >= 200 && (int)response.StatusCode <= 299)
                    {
                        successCnt++;
                    }
                    else
                    {
                        string responseMessage;
                        using (var rawStream = response.GetResponseStream())
                            using (var responseReader = new StreamReader(rawStream, Encoding.UTF8))
                            {
                                responseMessage = responseReader.ReadToEnd();
                            }

                        failureCnt++;

                        this.WriteError(
                            new ErrorRecord(
                                new InvalidOperationException(string.Format(LogMessages.ImportCertificateFailureWithThumbprint, cert.Thumbprint, response.StatusCode, Environment.NewLine, responseMessage)),
                                "Import Failure:" + responseMessage,
                                ErrorCategory.WriteError,
                                cert));
                    }
                }
            }
            catch (WebException we)
            {
                HttpWebResponse response = we.Response as HttpWebResponse;
                if (we.Status == WebExceptionStatus.ProtocolError && response.StatusCode == (HttpStatusCode)429)
                {
                    needsRetry = true;
                    if (response.Headers["x-ms-retry-after-ms"] != null)
                    {
                        retryAfter = double.Parse(response.Headers["x-ms-retry-after-ms"]);
                    }

                    if (response.Headers["Retry-After"] != null)
                    {
                        retryAfter = double.Parse(response.Headers["Retry-After"]);
                    }
                }
                else
                {
                    failureCnt++;

                    var resp = new StreamReader(we.Response.GetResponseStream()).ReadToEnd();

                    dynamic obj = JsonConvert.DeserializeObject(resp);

                    string messageFromServer;
                    if (obj.error != null)
                    {
                        messageFromServer = obj.error.message.ToString();
                    }
                    else
                    {
                        messageFromServer = String.Format("Failed to deserialize response {0}", resp);
                    }

                    this.WriteDebug(string.Format("Error Message: {0}", messageFromServer));

                    this.WriteError(
                        new ErrorRecord(
                            we,
                            "\n\n Error Message" + messageFromServer + "\n\n request-id:" + we.Response.Headers["request-id"],
                            ErrorCategory.WriteError,
                            cert));
                }
            }

            // Waiting until response is closed to re-use request
            if (needsRetry)
            {
                this.WriteWarning(string.Format(LogMessages.GetUserPfxTooManyRequests, retryAfter));
                Thread.Sleep(TimeSpan.FromSeconds(retryAfter));
                ProcessResponse(request, cert);
            }
        }
        public static string SerializeUserPFXCertificate(UserPFXCertificate cert)
        {
            string json = JsonConvert.SerializeObject(cert, Formatting.Indented, jSONSettings);

            return(json);
        }
        protected override void ProcessRecord()
        {
            byte[] pfxData;
            if (this.ParameterSetName == PFXBase64String)
            {
                pfxData = Convert.FromBase64String(Base64EncodedPfx);
            }
            else
            {
                pfxData = File.ReadAllBytes(PathToPfxFile);
            }

            X509Certificate2 pfxCert = new X509Certificate2();

            try
            {
                pfxCert.Import(pfxData, PfxPassword, X509KeyStorageFlags.DefaultKeySet);
            }
            catch (CryptographicException ex)
            {
                if (ex.HResult == ErrorCodeCantOpenFile)
                {
                    ThrowTerminatingError(
                        new ErrorRecord(
                            new ArgumentException(
                                string.Format("Could not Read Thumbprint on file at path: '{0}'. File must be a certificate.", PathToPfxFile), ex),
                            Guid.NewGuid().ToString(),
                            ErrorCategory.InvalidArgument,
                            null));
                }
                else if (ex.HResult == ErrorCodeNetworkPasswordIncorrect)
                {
                    ThrowTerminatingError(
                        new ErrorRecord(
                            new ArgumentException("Could not Read Thumbprint. Verify Password is Correct.", ex),
                            Guid.NewGuid().ToString(),
                            ErrorCategory.InvalidArgument,
                            null));
                }
                else
                {
                    ThrowTerminatingError(
                        new ErrorRecord(
                            new ArgumentException("Could not Read Thumbprint. Unknown Cause", ex),
                            Guid.NewGuid().ToString(),
                            ErrorCategory.InvalidArgument,
                            null));
                }
            }

            ManagedRSAEncryption encryptUtility = new ManagedRSAEncryption();

            byte[]   password             = new byte[PfxPassword.Length];
            GCHandle pinnedPasswordHandle = GCHandle.Alloc(password, GCHandleType.Pinned);

            byte[] encryptedPassword = null;
            try
            {
                ConvertSecureStringToByteArray(PfxPassword, ref password);

                string hashAlgorithm;
                int    paddingFlags;

                switch (PaddingScheme)
                {
                case UserPfxPaddingScheme.Pkcs1:
                case UserPfxPaddingScheme.OaepSha1:
                    ThrowTerminatingError(
                        new ErrorRecord(
                            new ArgumentException("Pkcs1 and OaepSha1 are no longer supported."),
                            Guid.NewGuid().ToString(),
                            ErrorCategory.InvalidArgument,
                            null));
                    return;

                case UserPfxPaddingScheme.OaepSha256:
                    hashAlgorithm = PaddingHashAlgorithmNames.SHA256;
                    paddingFlags  = PaddingFlags.OAEPPadding;
                    break;

                case UserPfxPaddingScheme.OaepSha384:
                    hashAlgorithm = PaddingHashAlgorithmNames.SHA384;
                    paddingFlags  = PaddingFlags.OAEPPadding;
                    break;

                case UserPfxPaddingScheme.None:
                    PaddingScheme = UserPfxPaddingScheme.OaepSha512;
                    goto default;       // Since C# doesn't allow switch-case fall-through!

                case UserPfxPaddingScheme.OaepSha512:
                default:
                    hashAlgorithm = PaddingHashAlgorithmNames.SHA512;
                    paddingFlags  = PaddingFlags.OAEPPadding;
                    break;
                }

                if (KeyFilePath != null)
                {
                    encryptedPassword = encryptUtility.EncryptWithFileKey(KeyFilePath, password, hashAlgorithm, paddingFlags);
                }
                else
                {
                    encryptedPassword = encryptUtility.EncryptWithLocalKey(ProviderName, KeyName, password, hashAlgorithm, paddingFlags);
                }
            }
            finally
            {
                if (password != null)
                {
                    password.ZeroFill();
                }

                if (pinnedPasswordHandle.IsAllocated)
                {
                    pinnedPasswordHandle.Free();
                }
            }

            string encryptedPasswordString = Convert.ToBase64String(encryptedPassword);

            UserPFXCertificate userPfxCertifiate = new UserPFXCertificate();

            userPfxCertifiate.Thumbprint           = pfxCert.Thumbprint.ToLowerInvariant();
            userPfxCertifiate.IntendedPurpose      = (UserPfxIntendedPurpose)IntendedPurpose;
            userPfxCertifiate.PaddingScheme        = (UserPfxPaddingScheme)PaddingScheme;
            userPfxCertifiate.KeyName              = KeyName;
            userPfxCertifiate.UserPrincipalName    = UPN;
            userPfxCertifiate.ProviderName         = ProviderName;
            userPfxCertifiate.StartDateTime        = Convert.ToDateTime(pfxCert.GetEffectiveDateString(), CultureInfo.CurrentCulture);
            userPfxCertifiate.ExpirationDateTime   = Convert.ToDateTime(pfxCert.GetExpirationDateString(), CultureInfo.CurrentCulture);
            userPfxCertifiate.CreatedDateTime      = DateTime.Now;
            userPfxCertifiate.LastModifiedDateTime = DateTime.Now;
            userPfxCertifiate.EncryptedPfxPassword = encryptedPasswordString;
            userPfxCertifiate.EncryptedPfxBlob     = pfxData;

            WriteObject(userPfxCertifiate);
        }