I have found this answer, but it doesn't seem to work when trying to create a wildcard certificate.
I have taken the following steps:
Added a certificate to my server with the Powershell command.
New-SelfSignedCertificate -DnsName myhostname01,*.myhostname01 -CertStoreLocation Cert:\LocalMachine\My
(I slightly censored the URL to avoid potentially unsafe situations).
Next, I used the SSL certificate in a binding on my IIS server.
I visited the page in Chrome. As expected, the certificate is marked unsafe.
I saved a local copy of the certificate, and manually added a copy of of the certificate to my Chrome trusted CA's. However, the certificate is still not recognized:
The details of the certificate look like this:
Now, the certificates and URL I am visiting and have set up in my hosts file are all the same. There are no spelling errors. My question: am I using New-SelfSignedCertificate wrong? Or am I doing something wrong somewhere else?
For anyone else who might arrive at this question clinging onto what's left of their sanity, the answer that ended up working for me was this:
New-SelfSignedCertificate -Subject *.my.domain -DnsName my.domain, *.my.domain -CertStoreLocation Cert:\LocalMachine\My -NotAfter (Get-Date).AddYears(10)
A SSL wild card certificate should have one subject with the wildcard and the rest of the DNS names should be in the Subject Alternative Name, which is provided by the DNSName parameter. I believe the example below will do what you want.
Example
New-SelfSignedCertificate -Subject *.myhostname01 -DnsName myhostname01 -CertStoreLocation Cert:\LocalMachine\My
dir Cert:\LocalMachine\My\ | Where-Object {$_.Subject -eq 'CN=*.myhostname01'} | ForEach-Object {
[PSCustomObject] #{
Subject = $_.Subject
SAN = $_.DnsNameList
}
}
Result
Subject SAN
------- ---
CN=*.myhostname01 {myhostname01}
References
Wikipedia - Wildcard Certicate
Technet - New-SelfSignedCertificate
Related
I am generating self-signed .pfx certificates for a java application running on a couple of Windows servers. These certificates will be imported into their respective java keystores.
My question is: Can I generate a self-signed certificates for server2, server3 and server4 on server1? Is there anything in a certificate, apart from the dns name, that would bind it to the machine on which it was generated?
My concern is that if I generate the certificate for server2 on server1, the certificate will still be somehow bound to server 1 only.
I am using the following powershell script to generate the certificates:
$cert = New-SelfSignedCertificate -keyfriendlyname server1 -certstorelocation cert:\localmachine\my -dnsname server1.mydomain.com
Export-PfxCertificate -cert ‘cert:\localMachine\my\’ -FilePath C:\Certificates\server1.pfx -Password dummypassword
My idea was to simplify the process of generating the certificates by running the script on a single server and just altering the dnsname, alias and file name for each certificate.
You can generate a certificate on any machine for any machine, just set the common name correctly (certificate's CN field).
See parameter -Subject of the PowerShell command
Note that moving private keys around is a bad practice, you should instead generate the key-pair on the same machine that it is to be used by.
p12 file with 7 certificates in it.
Following the instruction that came along with the cert file, we have to use MMC and a password to import all certs into a personal store.Instruction also says to check mark private key exportable.
in order to automate this, I tried using certutil -importpfx but that only added 4 out of 7 certificates. I am unable to see other 3 certs. The diff i noticed is the imported certs are the ones with "ext issuing CA" and missing certs are with "issuing CA" in the Subject .
Any pointers please
I found an alternate solution using powershell instead of certutil .
Import-pfx with flag -exportable imported all the certs.
Import-PfxCertificate -CertStoreLocation Cert:\LocalMachine\My -Password $Securepwd -FilePath $findP12Cert.FullName -Exportable -Verbose
I have a question, basically I have a file one txt and another one xml, I would like to sign those files with self signed certificate using Powershell.
Is there a way to do it?
My steps would be like that?
First create a self signed certificate with powershell
Then use that certificate in Powershell to sign the documents
Is that correct?
Any idea how to do that?
After the document is signed do I have to provide to another party this self sigend certificate to be able to open the files right? Or how will it work?
Accidentally, all my scripts are signed with an issued certificate, and it's my cmdlets to sign:
$cert = Get-ChildItem Cert:\CurrentUser\My -CodeSigningCert
Set-AuthenticodeSignature _path_to_my_script_ $cert -HashAlgorithm `
sha256 -TimestampServer "http://timestamp.digicert.com"
As to certificate, an issued one is recommended, rather than a self-signed one, it's not very expensive.
If you want to use a self-signed certificate, I think this cmdlet helps you:
New-SelfSignedCertificate -FriendlyName "My Cert" -KeyUsage DigitalSignature -KeyUsageProperty Sign -KeyLength 2018 -KeyAlgorithm sha256 -Type CodeSigningCert -Subject "CN=System Error,e=mymail#mail.com"
I never created self-signed certificate on a personal computer, so this cmdlet is not verified. :(
If you have further questions, please let me know. :)
PowerShell 4.0
makecert tool has the -eku option for describing the enhanced key usage object identifiers (OIDs) into the certificate. It allows to make the certificates for code signing and for other purposes. But it is not a cmdlet.
New PowerShell versions have the New-SelfSignedCertificate cmdlet for local testing of the scripts. But it creates the certificate that can't be used for code signing:
New-SelfSignedCertificate -DnsName www.SomeSite.com -CertStoreLocation Cert:\CurrentUser\My
I don't see an option which is similar of -eku.
How can I set the destination of my new Self-Signed Certificate (created through New-SelfSignedCertificate cmdlet) for possibility of its use for code signing? Or is it possible to do the same via other cmdlet?
The version of New-SelfSignedCertificate on PS 4 is rather basic.
However Powershell v5 has the parameters that you would require to create specific keys.
Specifically a Keyusage parameter that takes
-- CertSign
-- CRLSign
-- DataEncipherment
-- DecipherOnly
-- DigitalSiganture
-- EncipherOnly
-- KeyAgreement
-- KeyEncipherment
-- None (default)
-- NonRepudiation
and a KeyUsageProperty taking
-- All
-- Decrypt
-- KeyAgreement
-- None (default)
-- Sign
Are you specifically tied to v4? If you can upgrade to v5 you should be able to achieve what you need.
Reviving this question as I was also looking for an answer to set Enhanced Key Usage (EKU) field for code signing using PowerShell New-SelfSignedCertificate command.
It can be done using the -TextExtension parameter to set EKU value. As an example, the following PowerShell (tested on PowerShell 5.1) script allows to create a 3-years self signed code signing certificate with extended key usage (and export it from the current user's certificates store to pfx file format):
# Enhanced Key Usage
$EKU = "2.5.29.37"
$EKU_CODE_SIGNING = "1.3.6.1.5.5.7.3.3"
$certificate = New-SelfSignedCertificate -Subject "CN=Testing Code Signing,E=info#mycompany.com,O=My Company" `
-FriendlyName "My Code Signing Certificate" `
-NotAfter (Get-Date).AddYears(3) `
-CertStoreLocation Cert:\CurrentUser\My `
-TextExtension #("$EKU={text}$EKU_CODE_SIGNING")
$password = ConvertTo-SecureString -String "mypassword" -Force -AsPlainText
Export-PfxCertificate -Cert "Cert:\CurrentUser\My\$($certificate.Thumbprint)" -FilePath "codesigning.pfx" -Password $password
Note: As a shortcut, the -Type CodeSigningCert parameter can be specified with the New-SelfSignedCertificate command instead of explicitly adding the EKU_CODE_SIGNING string to the -TextExtension parameter.
You can use PS' cert provider to access different cert stores (user vs machine), but that won't help with your OID problem. I suggest you look at .NET support for X509 certs. Google ".net x509 certificate" and you'll find the X509Certificate class on MSDN. From there read the class documentation and any overview documentation to see if creation of OIDs is supported. If .NET doesn't support it then you'd have to use P/Invoke to invoke native Windows CNG (cryptography next generation) APIs
I have to sign remote scripts with a certificate from the remote machine from which I have a .pfx file.
I would like to automate the scripting by supplying the password to the Get-PfxCertificate programmatically.
So the question is:
Is it possible to somehow supply programmatically the required password to
Get-PfxCertificate?
$CertPath = "my.pfx"
$CertPass = "mypw"
$Cert = New-Object System.Security.Cryptography.X509Certificates.X509Certificate2($CertPath, $CertPass)
Set-AuthenticodeSignature -Certificate $Cert -TimeStampServer http://timestamp.verisign.com/scripts/timstamp.dll -FilePath $OutputFilename
Make sure you have the proper permissions otherwise you won't be able to create an instance of the X509Certificate2 object.
I did a bit of checking around on this and couldn't find a clean way to provide the password programmatically. I suspect it is meant to be this way for security reasons. Either that or the PowerShell development team just blew it by not including a Credential parameter for this cmdlet. The only other option I can think of is to use someting like SendKeys to send the individual password character key presses to the PowerShell console at the right time via a background job (blech - just threw up in my mouth a little). :-)
Another way of doing this is by loading your certificate directly from your certificate store using PS Providers. Use Get-PSProviders to determine available PSProviders on your machine.
Once you have cert provider loaded, you can now get the certificate using Get-ChildItem
Launch certmgr.msc from run to launch the certificate store
Assuming that your certificate is stored under Personal folder in your cert store and has "Company Name" set in the subject property of the certificate, and there is only certificate in that folder with Company Name in the subject - you can get the certificate like so
$my_cert = Get-ChildItem cert:\CurrentUser\My | ? {$_.Subject -match "Company Name"}
$my_cert will be your certificate object that you can pass directly to Set-AuthenticodeSignature cmdlet
Set-AuthenticodeSignature -Certificate $my_cert -FilePath fqn_to_dll.dll -Timestampserver "http://timestampurl"
post signing, you can retrieve the sign status by querying on the Status property for "Valid" or not like
$result = Set-AuthenticodeSignature -Certificate $my_cert -FilePath fqn_to_dll.dll -Timestampserver "http://timestampurl" | Select Status
if(-Not ($result -eq "Valid")){
Write-Output "Error Signing file: Status: $($result.Status)"
}