Introduction You can create a self-signed cert to allow you to sign your own Powershell scripts. Using unsigned scripts requires you t...
Introduction
You can create a self-signed cert to allow you to sign your own Powershell scripts. Using unsigned scripts requires you to completely disable Windows security measures that protect against running unwanted Powershell code, which would be bad. This method allows you to avoid disabling this code-signed policy.
Everything we do below uses a Powershell prompt, not a command prompt.
Background on certs:
Certificates are given their authority by certificate authorities (CAs). CAs confirm whether or not a certificate is valid. When your computer attempts to use a certificate, it confirms the validity of the certificate by requesting a "trusted" CA validate the certificate.
Certificates are given their authority by certificate authorities (CAs). CAs confirm whether or not a certificate is valid. When your computer attempts to use a certificate, it confirms the validity of the certificate by requesting a "trusted" CA validate the certificate.
You can pay a CA to sign a cert for you, or use a process called self-signing to: create your own CA, then create your own certificate, and then sign your certificate with your own CA.
Windows stores information about which CAs are valid in the certificate store (again, in the "trusted CA list"). For our purposes this is CurrentUser>Trusted Root Certification Authorities>Certificates.
Separately, Windows stores certificates in the certificate store. For our purposes this is CurrentUser>Personal>Certificates and CurrentUser>Personal>Certificates.
Steps (9 total)
https://www.microsoft.com/en-us/download/details.aspx?id=8279
This is the link to download the SDK for Windows 7.
This is the link to download the SDK for Windows 7.
We'll use makecert to create both the CA cert and your personal cert.
Pro tip: the SDK failed to install for me until i uninstalled all previous versions of Visual Studio
Start > right-click Computer > Properties
click Advanced system settings
Advanced tab > Environment Variables...
User variables > PATH entry > Edit...
Add C:\Program Files\Microsoft SDKs\Windows\v7.1\bin to your path.
click Advanced system settings
Advanced tab > Environment Variables...
User variables > PATH entry > Edit...
Add C:\Program Files\Microsoft SDKs\Windows\v7.1\bin to your path.
If you've never done this before, you'll typically want to add on to the end of the existing entry. To do this, add a semicolon to the end, and then paste in the new entry at the end. So you'll end up with something like:
otherdirectoriesthatalreadyexisted;C:\Program Files\Microsoft SDKs\Windows\v7.1\bin
Now you have access to makecert in Powershell (because we have the SDK in place).
makecert -n "CN=PowerShell Local Certificate Root" -a sha1 -eku 1.3.6.1.5.5.7.3.3 -r -sv root.pvk root.cer -ss Root -sr localMachine
Error: Save encoded certificate to store failed => 0x5 (5)
Failed
Failed
Despite the failure error, this seems to have worked for me.
----
Alternatively,
makecert -n "CN=TempCA" -r -sv TempCA.pvk TempCA.cer
open certmgr.msc
under CurrentUser>Trusted Root Certification Authorities, right click Certificates
select All Tasks > Import
under CurrentUser>Trusted Root Certification Authorities, right click Certificates
select All Tasks > Import
find the file you just created, import it
makecert -pe -n "CN=PowerShell User" -ss MY -a sha1 -eku 1.3.6.1.5.5.7.3.3 -iv root.pvk -ic root.cer
Succeeded
If you refresh certmgr.msc, you should now see the Powershell User cert in CurrentUser>Personal>Certificates.
Ok, great. You've created your own CA, and then created and signed a cert using your CA. Almost done!
--
Alternatively,
makecert -sk SignedByCA -iv TempCA.pvk -n "CN=SignedByCA" -ic TempCA.cer SignedByCA.cer -sr currentuser -ss My
you should now see the SignedByCA cert in CurrentUser>Personal>Certificates
If not, you can import the SignedByCA.cer into the Personal Certificates manually (see last step for example).
(the default state in Windows is to not run any scripts, signed or not)
Start Menu > type "powershell" > right-click powershell and select Run as Administrator...
set-executionpolicy allsigned
yes/confirm
yes/confirm
gci cert:\CurrentUser\My -codesigning
If this is blank, you may be unable to use the next step to sign your script. Blank means Windows is unaware of any available personal certs that can be used for signing code.
Two commands, we'll set a variable ($cert) and then use it:
$cert = @(Get-ChildItem cert:\CurrentUser\My -CodeSigning)[0]
Set-AuthenticodeSignature .\your-script.ps1 $cert
Set-AuthenticodeSignature .\your-script.ps1 $cert
Should output something like:
Directory: C:\xxxxxx
SignerCertificate Status Path
----------------- ------ ----
12B3xxxxxxxxxxxxxxxxxx Valid yourscript.ps1
----------------- ------ ----
12B3xxxxxxxxxxxxxxxxxx Valid yourscript.ps1
----
Alternatively,
signtool sign /a <yourscriptpathandname>
should output:
Done Adding Additional Store
Successfully signed: .\backup-docs.ps1
Done Adding Additional Store
Successfully signed: .\backup-docs.ps1
Right-click and Edit your script from Windows Explorer, your script will open in the powershell_ise (Powershell Code Editor). You should see a big block of text below your script - this is the signature you've just applied.
If you click the green > play icon, your script should run. Previously, if the script was not signed, the run would fail with an unsigned code error.
References
- https://www.digicert.com/code-signing/signcode-signtool-command-line.htm
- http://blogs.technet.com/b/heyscriptingguy/archive/2010/06/17/hey-scripting-guy-how-can-i-sign-windows-powershell-scripts-with-an-enterprise-windows-pki-part-2-of-2.aspx
- https://technet.microsoft.com/en-us/magazine/2008.04.powershell.aspx
- https://msdn.microsoft.com/en-us/library/ms733813(v=vs.110).aspx
No comments
Post a Comment