我试图使用Powershell的.NET RSACryptoServiceProvider类的SignData方法。
在Windows 10 / Powershell 5.1 / .NET 4.7上,以下代码可靠地运行:
$toSign = [System.Text.Encoding]::UTF8.GetBytes("ABCDE")
$cert = New-Object System.Security.Cryptography.X509Certificates.X509Certificate2
$cert.import("c:\ps\GAdmin\apiaccess.pfx","notasecret","Exportable,PersistKeySet")
$cert | fl *
$params = New-Object System.Security.Cryptography.CspParameters
$params.KeyContainerName = $cert.PrivateKey.CspKeyContainerInfo.KeyContainerName
$params.ProviderName = "Microsoft Enhanced RSA and AES Cryptographic Provider"
$params
$cert.PrivateKey.CspKeyContainerInfo.KeyNumber
$params.KeyNumber = 1
$rsa = New-Object System.Security.Cryptography.RSACryptoServiceProvider($params)
$tosign
$rsa.SignData($toSign,"SHA256")
但是,在使用.NET Core / Powershell Core的Linux(或Windows)上,我遇到了问题。我可以实例化一个RSACryptoServiceProvider,但SignData错误输出:
$cert = Get-PfxCertificate ./apiaccess.pfx -Password (ConvertTo-SecureString "notasecret" -AsPlainText -Force)
$rsa = $cert.PrivateKey
$rsa.SignData($toSign,"SHA256")
无法找到" SignData"和参数计数:" 2"。 在行:1个字符:1 + $ rsa.SignData($ toSign," SHA256") + ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ + CategoryInfo:NotSpecified:(:) [],MethodException + FullyQualifiedErrorId:MethodCountCouldNotFindBest
检查方法定义 - 似乎需要填充参数:
($rsa | get-member SignData).Definition
byte [] SignData(byte [] data,System.Security.Cryptography.HashAlgorithmName hashAlgorithm,System.Security.Cryptography.RSASignaturePadding padding),byte [] SignData(byte [] data,int offset,int count,System。 Security.Cryptography.HashAlgorithmName hashAlgorithm,System.Security.Cryptography.RSASignaturePadding padding),byte [] SignData(System.IO.Stream data,System.Security.Cryptography.HashAlgorithmName hashAlgorithm,System.Security.Cryptography.RSASignaturePadding padding)
所以我的问题是:如何指定填充并从Powershell Core调用SignData?
答案 0 :(得分:2)
$cert.PrivateKey
可能返回RSACryptoServiceProvider以外的内容。你真的应该避免调用那个属性,并且应该用$cert.GetRSAPrivateKey()
替换它(或者你期望密钥的任何算法......如果你弄错了它会返回null
所以异常不是一个问题)。并不是说它会有所帮助,除了它保证永远不会在Linux上返回RSACryptoServiceProvider(并且“几乎保证”不会在Windows上返回它)。虽然它将解决你在Windows上重新解释CSP参数的需要。
而不是叫'
$rsa.SignData($toSign, "SHA256")
你应该致电
$rsa.SignData(
$toSign,
System.Security.Cryptography.HashAlgorithmNames.SHA256,
System.Security.Cryptography.RSASignaturePadding.Pkcs1)
我实际上并不知道后两个参数的powershell-ese,希望我对该语言语法的理解足以解锁你。这里的“SHA256”和“Pkcs1”都是属性,所以如果它让你的代码更漂亮,你可以将它们保存到本地。