背景:为了防止私钥泄露,公司里只有少数几个人才能访问到私钥。其他同事开发时,也需要编译,但不又能给他们密钥,我们就需要使用延迟签名技术了。
1. 创建密钥对
sn -k mykeyfile.pfx
无密码保护,该文件需要安全保管
2. 安装密钥对到于强名称 CSP 中容器
sn -i mykeyfile.pfx mykeycontainer
3. 提取公钥文件
sn -p mykeyfile.pfx mykeyfile.pub
4. 显示公钥标记
(短,2780ccd10d57b246这种),用于-Vr选项
sn -q -t mykeyfile.pub
5. 显示完整公钥
用于assembly: InternalsVisibleTo的PublicKey
sn -q -tp mykeyfile.pub
6. 使CLR暂时信任程序集的内容
注册要跳过验证的程序集,使CLR暂时信任程序集的内容,不对它进行哈希处理,也不对哈希值进行比较。这使程序集能顺利安装到GAC(如果有必要的话)。现在,可以生成引用了这个程序集的其他程序集,并可随意测试程序集,否则会报错(程序签名无效或被串改)。注意,在每台开发用的机器上,以下命令行都只需执行一次,不必在每次生成程序集时都重复这一步:
sn -Vr MyAssembly.dll
或所有这个PublicKey的程序集sn-Vr *,2780ccd10d57b246
7. 设置项目为延迟签名
命令行方式:csc/keyfile: mykeyfile.pub /delaysign MyAssembly.cs
UI方式:在项目中,选择签名文件选择mykeyfile.pub, 然后钩上“延迟签名”
8. 真正发布
结束一个程序集的开发和测试之后,需要正式对其进行签名,以便打包和部署它。为了对程序集进行签名,要再次使用SN.exe实用程序,但这一次换用-R开关,并指定包含了私钥的文件的名称。-R开关指示SN.exe对文件内容进行哈希处理,用私钥对其进行签名,并将RSA数字签名嵌入文件中之前预留的空间。经过这一步之后,就可以部署完全签好名的程序集。在开发和测试机器上,不要忘记使用SN.exe的-Vu或-Vx命令行开关来重新启用对这个程序集的验证。
sn -Vu MyAssembly.dll
sn -Vu *,2780ccd10d57b246
使用 infile 中的密钥对,为先前已签名的程序集或延迟签名的程序集重新签名。
SN.exe -R MyAssembly.dll mykeyfile.pfx
使用 container 中的密钥对,为先前已签名的程序集或延迟签名的程序集重新签名。
SN.exe -Rc MyAssembly.dll mykeycontainer
重新编译方式
msbuild/p:KeyPairContainer=mykeycontainer,PublicKeyFile="<完整路径> \mykeyfile.pub"
如果公钥/私钥对在一个CSP容器中,必须为CSC.exe、AL.exe和SN.exe程序指定不同的开关。编译时(CSC.exe),要指定/keycontainer开关,而不是/keyfile开关;链接时(AL.exe),要指定/keyname开关,而不是/keyfile开关;使用强名称程序(SN.exe)对一个延迟签名的程序集进行重新签名时,要指定-Rc开关,而不是-R开关。
重要提示 打包一个程序集前,只要你希望对它执行其他任何操作,延迟签名都非常有用。例如,可能想要对自己的程序集运行一个混淆器(obfuscator)程序。程序集在完全签名后,便不能再对它运行混淆器,否则哈希值就不正确了。所以,要想混淆一个程序集文件,或者进行其他形式的"生成后"(post-build)操作,就应该使用延迟签名,执行所有必要的"生成后"操作,再用-R或-Rc开关运行SN.exe,最终完成对程序集的签名。