使用GetRSAPrivateKey和.net核心以编程方式设置智能卡PIN

问题描述 投票:0回答:1

多年以来,我一直使用此link处的扩展方法来访问智能卡上的证书并以编程方式提供PIN,而无需向用户打开请求PIN掩码。现在,随着新版本的.net core不再起作用,因此我正在尝试对其进行修复。

我知道现在有了新版本的框架,最好使用

RSA rsa = certificate.GetRSAPrivateKey();

但是以这种方式,我无法访问调用提供PIN的本机方法所需的CspKeyContainerInfo(KeyContainerName,ProviderName,ProviderType)

是否可以使用RSA对象访问相同的信息?

或者是否有更好/更新的方法通过程序提供智能卡的PIN?

c# .net .net-core x509certificate core
1个回答
0
投票

您拥有的代码仅在Windows CAPI提供了私钥时才有效。如果私钥是Windows CNG提供的,则需要使用它的CNG形式。

private static RSA GetRSAPrivateKeyWithPin(this X509Certificate2 cert, string pin)
{
    RSA rsa = cert.GetRSAPrivateKey();

    if (rsa is RSACryptoServiceProvider rsaCsp)
    {
        // Current code
        SetPin(rsaCsp);
        return rsa;
    }

    if (rsa is RSACng rsaCng)
    {
        // Set the PIN, an explicit null terminator is required to this Unicode/UCS-2 string.

        byte[] propertyBytes;

        if (pin[pin.Length - 1] == '\0')
        {
            propertyBytes = Encoding.Unicode.GetBytes(pin);
        }
        else
        {
            propertyBytes = new byte[Encoding.Unicode.GetByteCount(pin) + 2];
            Encoding.Unicode.GetBytes(pin, 0, pin.Length, propertyBytes, 0);
        }

        const string NCRYPT_PIN_PROPERTY = "SmartCardPin";

        CngProperty pinProperty = new CngProperty(
            NCRYPT_PIN_PROPERTY,
            propertyBytes,
            CngPropertyOptions.None);

        rsaCng.Key.SetProperty(pinProperty);
        return rsa;
    }

    // If you're on macOS or Linux neither of the above will hit. There's
    // also no standard model for setting a PIN on either of those OS families.
    rsa.Dispose();
    throw new NotSupportedException($"Don't know how to set the PIN for {rsa.GetType().FullName}");
}

https://stackoverflow.com/a/42630670/6535399复制的RSACng PIN设置代码;因为这个问题似乎具有更好的发现,而且答案在这里更为笼统。

© www.soinside.com 2019 - 2024. All rights reserved.