使用PFX文件生成具有强名称的COM互操作程序集
我正在尝试使用PFX文件创建一个具有强名称的COM互操作程序集。使用PFX文件生成具有强名称的COM互操作程序集,com,interop,cryptography,com-interop,public-key-encryption,Com,Interop,Cryptography,Com Interop,Public Key Encryption,我正在尝试使用PFX文件创建一个具有强名称的COM互操作程序集。 TlbImp.exe对使用“sn.exe-k”(包含公钥和私钥)创建的SNK文件非常满意,但问题是我有一个PFX文件… 我可以使用sn.exe-p将公钥从PFX导出到SNK,但它只导出公钥,而TlbImp.exe根本不喜欢。我可以同时导出公钥和私钥吗? 我尝试使用 sn.exe-i MyCompany.pfx xyz 然后使用 TlbImp.exe/keycontainer:xyz…, 但这给了我 TlbImp:错误TI0000:
TlbImp.exe对使用“sn.exe-k”(包含公钥和私钥)创建的SNK文件非常满意,但问题是我有一个PFX文件…
我可以使用sn.exe-p将公钥从PFX导出到SNK,但它只导出公钥,而TlbImp.exe根本不喜欢。我可以同时导出公钥和私钥吗?
我尝试使用
sn.exe-i MyCompany.pfx xyz
然后使用
TlbImp.exe/keycontainer:xyz…,
但这给了我
TlbImp:错误TI0000:指定的强名称参数无效 我能做什么?
谢谢大家! 更新:奥列格的答案和下面的实用程序运行得非常好。 PFX文件(重新导出后)可成功用于提取 与tlbimp.exe(tlbimp.exe)一起使用的公钥(sn.exe-p) /publickey:xyz.pub)。然后可以使用PFX文件对互操作进行重新签名 dll(sn.exe-R) 科摩多真的把球落在了这个上面。下面是转储文件(certutil.exe) -原始和固定pfx文件的dump-v xyz.pfx): 之前: 证书密钥证明信息财产ID(2):
密钥容器={36BDD7BD-F295-47B2-B9E7-C25BD5B4313E}
唯一容器名称: bf63afd9ba3fb912ccd3423c6486e5fc_25e0623f-f712-49e2-abda-f31f014b5dae
Provider=Microsoft增强加密提供程序v1.0
ProviderType=1
标志=0
KeySpec=1——AT_KEYEXCHANGE
…
私钥:
PRIVATEKEYBLOB
版本:2
aiKeyAlg:0xa400
计算RSA密钥
算法类:0xa000(5)ALG类密钥交换
算法类型:0x400(2)ALG_Type_RSA
算法子id:0x0(0)ALG_SID_RSA_ANY
之后: 证书密钥证明信息财产ID(2):
密钥容器={DBA6454E-F6D2-4F0B-AB1B-9E4F7C0E139C}
唯一容器名称: d2d09f87081c1af7c4225889f1af2250_25e0623f-f712-49e2-abda-f31f014b5dae
Provider=Microsoft增强加密提供程序v1.0
ProviderType=1
标志=0
KeySpec=2——AT_签名 …
私钥:
PRIVATEKEYBLOB
版本:2
aiKeyAlg:0x2400
计算符号
算法类:0x2000(1)ALG_类签名
算法类型:0x400(2)ALG_Type_RSA
算法子id:0x0(0)ALG_SID_RSA_ANY
尝试执行以下操作
sn.exe -p MyCompany.pfx MyCompany.pub
tlbimp.exe My.dll /delaysign /publickey:MyCompany.pub /out:Interop.My.dll
sn.exe -R Interop.My.dll MyCompany.pfx
如果从COM DLL的tlb文件创建主互操作程序集,则将以
tlbimp.exe My.tlb /primary /delaysign /publickey:MyCompany.pub /out:Interop.My.dll
您还可以使用互操作程序集的代码签名:
signtool.exe sign /f MyCompany.pfx /p password /t http://timestamp.verisign.com/scripts/timstamp.dll /v Interop.My.dll
更新:我找到了您出现问题的原因。首先,我应该解释(或提醒)密钥容器的一个功能
私钥存在于密钥容器中。密钥容器可以位于本地硬盘上文件夹%APPDATA%\Microsoft\Crypto\RSA\YourUserSid
中的某个文件中。同样,密钥容器可以是PFX文件的一部分。在这两种情况下一个密钥容器最多可以保存两个私钥:一个用于数字签名(AT_签名
)和另一个用于密钥交换(AT_密钥交换
)。您可以查看函数参数以了解更多详细信息。两个密钥可以完全不同。例如,您可以在一个密钥容器的数字签名中持有4096大小的私钥,并在同一容器的密钥交换部分持有另一个2048大小的私钥
证书具有its中的CERT\u KEY\u PROV\u PROP\u ID
。它保存了dwKeySpec
(值为AT\u签名
,AT\u密钥交换
或其他类似的AT\u密钥交换| AT\u签名
)字段与其他字段一起使用的结构pwszzannerName
(le-fe9728d2-af26-4f15-9be0-48c5af6f21dc
)pwszProvName
(dwProvType
)(PROV_RSA_FULL
),因此可以从证书中完整引用密钥
问题是您拥有的证书的密钥保存在容器的密钥交换部分,而不是数字签名部分。使用SignTool.exe
tool时没有问题,但是使用tlbimp.exe
时会出现错误
TlbImp:错误TI1000:类型库导入程序遇到错误
意外异常:System.Security.SecurityException-无效
程序集公钥。(HRESULT的异常:0x8013141E)
我想这是通过Tucows获得的Comodo或可能是Comodo证书的常见问题
CN = UTN-USERFirst-Object
OU = http://www.usertrust.com
O = The USERTRUST Network
L = Salt Lake City
S = UT
C = US
要重现我描述的问题,您可以执行以下步骤:
1) 创建密钥对,将其保存在新密钥容器的密钥交换中,并创建用于创建密钥对的自签名证书。例如,我们可以使用MakeCert.exe
的以下参数来执行此操作:
MakeCert.exe-pe-ss MY-a sha1-cy authority-len 2048-e 12/31/2020
-r-n“CN=我的公司根权限,O=我的公司,C=DE”-eku 1.3.6.1.5.5.7.3.3-天空交易所-len 2048-sk myKeyContainer
在上面的示例中,我们使用显式指定的名称'myKeyContainer'
将新密钥保存在密钥容器中,以便于将来查找和检查。实际上,不指定参数,容器名称将根据新GUID自动生成
2) 使用“证书”管理单元将新创建的证书从MMC.EXE导出为PFX文件。导出过程中必须选择密码。Altern
ChangeKeyProvInfo.exe "Dmitry Streblechenko"
...
CERT_KEY_PROV_INFO_PROP_ID(2):
...
KeySpec = 1 -- AT_KEYEXCHANGE
...
Private Key:
PRIVATEKEYBLOB
Version: 2
aiKeyAlg: 0xa400
CALG_RSA_KEYX
Algorithm Class: 0xa000(5) ALG_CLASS_KEY_EXCHANGE
...
Encryption test passed
...
CERT_KEY_PROV_INFO_PROP_ID(2):
...
KeySpec = 2 -- AT_SIGNATURE
...
Private Key:
PRIVATEKEYBLOB
Version: 2
aiKeyAlg: 0x2400
CALG_RSA_SIGN
Algorithm Class: 0x2000(1) ALG_CLASS_SIGNATURE
...
Signature test passed