本文属于《GmSSL国密加密算法库使用系列教程》之一,欢迎查看其它文章。
GmSSL是一个开源的密码工具箱,支持SM2/SM3/SM4/SM9/ZUC等国密(国家商用密码)算法、SM2国密数字证书及基于SM2证书的SSL/TLS安全通信协议,支持国密硬件密码设备,提供符合国密规范的编程接口与命令行工具,可以用于构建PKI/CA、安全通信、数据加密等符合国密标准的安全应用。GmSSL项目是OpenSSL项目的分支,并与OpenSSL保持接口兼容。因此GmSSL可以替代应用中的OpenSSL组件,并使应用自动具备基于国密的安全能力。GmSSL项目采用对商业应用友好的类BSD开源许可证,开源且可以用于闭源的商业应用。
GmSSL项目由北京大学关志副研究员的密码学研究组开发维护,项目源码托管于GitHub。自2014年发布以来,GmSSL已经在多个项目和产品中获得部署与应用,并获得2015年度“一铭杯”中国Linux软件大赛二等奖(年度最高奖项)与开源中国密码类推荐项目。GmSSL项目的核心目标是通过开源的密码技术推动国内网络空间安全建设。
以上内容摘抄自GmSSL官网:http://gmssl.org/
大家都知道OpenSSL,主要是提供国际加密算法库。但是在最新的OpenSSL 1.1.1以上版本,已经对国密算法提供了支持。
OpenSSL、GmSSL这俩提供的国密算法库,去看了下代码,代码实现是不一样的,属于条条大路通罗马。
按照此文进行安装,《Visual Studio Community 2017安装步骤(只装C++)》。
主要使用它的编译器,若已安装,则跳过。
64位ActivePerl-5.26下载地址:https://www.jb51.net/softs/27286.html#downintro2
进行安装,安装类型选择“Typical”,其他默认,最后一步安装时间较长。
在cmd中,输入命令查看perl版本号。
perl -v
表明安装成功。
nasm-2.15.05下载地址:https://www.nasm.us/pub/nasm/releasebuilds/2.15.05/win64/
以管理员身份运行nasm-2.15.05-installer-x64.exe,进行默认安装即可。
并将NASM安装目录添加至Windows系统环境变量Path中。
下载GmSSL源码:https://github.com/guanzhi/GmSSL
以管理员权限,打开VS Tools中“适用于VS 2017 的x64 本机工具命令提示”。
cd /d D:\GmSSL-master\GmSSL-master
若需生成32位,则“perl Configure VC-WIN32”。
perl Configure VC-WIN64A
nmake
若报错,参考第五节解决编译报错。
直到编译成功后继续。
nmake install
若前面不是以管理员权限运行,“适用于VS 2017 的x64 本机工具命令提示”,则此处会报错。
GmSSL默认安装路径为C:\Program Files\GmSSL
将GmSSL命令行工具路径C:\Program Files\GmSSL\bin,添加到环境变量中。
在cmd中,输入命令查看GmSSL版本。
gmssl version
至此,GmSSL安装完毕。
报错如下:
libcrypto-1_1-x64.def : error LNK2001: 无法解析的外部符号 EVP_get_ciphernames
libcrypto-1_1-x64.def : error LNK2001: 无法解析的外部符号 EVP_get_digestnames
libcrypto.lib : fatal error LNK1120: 2 个无法解析的外部命令
NMAKE : fatal error U1077: “link”: 返回代码“0x1”
原因:
EVP_get_ciphernames、EVP_get_digestnames这2个函数位于GmSSL-master\include\openssl\evp.h,似乎是没找到这2个函数的实现。
解决办法:
在GmSSL的github仓库中,在GmSSL-master/crypto/evp/names2.c文件中,历史版本有这2个函数的实现,新版本不知道什么原因,这2个函数实现被删除了。
所以,我们只需要从names2.c文件的历史版本中,将函数实现拷贝出来,追加到新names2.c文件末尾,再次重新编译即可。
具体解决步骤:
为方便大家,特意将需要拷贝的代码,列出来,如下:
static void cipher_name_len(const EVP_CIPHER *cipher, const char *from,
const char *to, void *x)
{
*((int *)x) += strlen(EVP_CIPHER_name(cipher));
}
static void cipher_name(const EVP_CIPHER *cipher, const char *from,
const char *to, void *x)
{
strcat((char *)x, EVP_CIPHER_name(cipher));
}
char *EVP_get_ciphernames(int aliases)
{
char *ret = NULL;
int len = 0;
EVP_CIPHER_do_all_sorted(cipher_name_len, &len);
ret = OPENSSL_zalloc(len);
if (!ret) {
return NULL;
}
EVP_CIPHER_do_all_sorted(cipher_name, ret);
return ret;
}
char *EVP_get_digestnames(int aliases)
{
return "sm3:sha1:sha256";
}
(1)首先将上述4个函数,追加至names2.c文件末尾。
(2)然后执行一下清除
nmake clean
(3)再执行编译
nmake
就可以发现,已经可以编译通过了。
思考:
在win下编译报这2个函数未实现,但是后来在Linux下编译,在没有改代码的前提下,居然可以直接编译通过,看来这个与平台还有关系。
若对你有帮助,欢迎点赞、收藏、评论,你的支持就是我的最大动力!!!
同时,阿超为大家准备了丰富的学习资料,欢迎关注公众号“超哥学编程”,即可领取。