如何从OpenSSL中的perl脚本生成程序集文件

在OpenSSL(版本1.1.0e)的开源代码中,我看到一些函数定义是由文件夹中存在的perl文件生成的。 在加密中每个文件夹中的build.info文件中,他们写了一些行来从相应的.pl生成.s。

例如:

crypto/aes/build.info生成crypto/aes/build.info

 GENERATE[aesp8-ppc.s]=asm/aesp8-ppc.pl $(PERLASM_SCHEME) 

crypto/build.info生成crypto/build.info

 GENERATE[ppccpuid.s]=ppccpuid.pl $(PERLASM_SCHEME) 

而且在主Makefile(生成的makefile)中,有一些行如下:

 crypto/aes/aes-x86_64.o: crypto/aes/aes-x86_64.s $(CC) -I. -Icrypto/include -Iinclude $(CFLAGS) $(LIB_CFLAGS) -MMD -MF crypto/aes/aes-x86_64.d.tmp -MT $@ -c -o $@ crypto/aes/aes-x86_64.s @touch crypto/aes/aes-x86_64.d.tmp @if cmp crypto/aes/aes-x86_64.d.tmp crypto/aes/aes-x86_64.d > /dev/null 2> /dev/null; then \ rm -f crypto/aes/aes-x86_64.d.tmp; \ else \ mv crypto/aes/aes-x86_64.d.tmp crypto/aes/aes-x86_64.d; \ fi 

其次是:

 crypto/aes/aes-x86_64.s: crypto/aes/asm/aes-x86_64.pl CC="$(CC)" $(PERL) crypto/aes/asm/aes-x86_64.pl $(PERLASM_SCHEME) $@ 

任何人都可以解释.s文件是如何生成的? 我需要在我的项目中的Makefile中添加它们,以解决由.pl文件生成定义的函数的undefined reference错误。

如何从OpenSSL中的Perl脚本生成程序集文件…

使用xlat程序生成汇编语言文件。 对于Power8设备,文件是perlasm目录中的perlasm 。 它由crypto/aes/asm目录中的aesp8-ppc.pl使用。

这是你如何翻译它。 我在编译农场的GCC112上工作,这是ppc64le。

 git clone https://github.com/openssl/openssl.git mkdir cryptogams cp ./openssl/crypto/perlasm/ppc-xlate.pl cryptogams/ cp ./openssl/crypto/aes/asm/aesp8-ppc.pl cryptogams/ cd cryptogams/ chmod +x *.pl ./aesp8-ppc.pl ppc64le aesp8-ppc.s 

aesp8-ppc.pl生成一个纯汇编语言源文件,因此使用little *.s命名输出文件。 有时翻译包含C预处理器语句,它需要一个很大的*.S (但不是在这种情况下)。

aesp8-ppc.pl的第二个参数叫做flavor 。 在上面的命令中是ppc64le 。 味道做两件事。 首先,它选择32位或64位。 其次,它选择little-endian或big-endian。 一定要正确的味道。

一旦你有了aesp8-ppc.s ,就可以用GCC编译和汇编源文件。

 gcc -mcpu=power8 -c aesp8-ppc.s 

然后:

 $ objdump --disassemble aesp8-ppc.o aesp8-ppc.o: file format elf64-powerpcle ... 0000000000000420 : 420: c1 ff 21 f8 stdu r1,-64(r1) 424: a6 02 48 7d mflr r10 428: 50 00 41 f9 std r10,80(r1) 42c: 75 fc ff 4b bl a0  430: a6 03 48 7d mtlr r10 434: 00 00 03 2c cmpwi r3,0 438: 68 00 c2 40 bne- 4a0  43c: 36 20 07 55 rlwinm r7,r8,4,0,27 440: 10 ff 65 38 addi r3,r5,-240 444: 7e f8 08 55 rlwinm r8,r8,31,1,31 448: 14 3a a3 7c add r5,r3,r7 44c: a6 03 09 7d mtctr r8 ... 

此时您有一个目标文件,但您不知道API签名或如何使用它。 要了解下一步该做什么,您必须objdump然后grep OpenSSL源以查看它们如何使用它。

 $ nm aesp8-ppc.o | grep ' T ' 00000000000006c0 T aes_p8_cbc_encrypt 0000000000001140 T aes_p8_ctr32_encrypt_blocks 00000000000005c0 T aes_p8_decrypt 00000000000004c0 T aes_p8_encrypt 0000000000000420 T aes_p8_set_decrypt_key 00000000000000a0 T aes_p8_set_encrypt_key 0000000000001d00 T aes_p8_xts_decrypt 0000000000001a60 T aes_p8_xts_encrypt 

您对四个函数aes_p8_set_encrypt_keyaes_p8_set_decrypt_keyaes_p8_encryptaes_p8_decrypt

我将帮助你完成第一个: aes_p8_set_encrypt_key

 $ cd openssl $ grep -nIR aes_p8_set_encrypt_key crypto/evp/e_aes.c:153:# define HWAES_set_encrypt_key aes_p8_set_encrypt_key $ grep -nIR HWAES_set_encrypt_key ... crypto/evp/e_aes.c:2515:int HWAES_set_encrypt_key(const unsigned char *userKey, const int bits, ... $ cat -n crypto/evp/e_aes.c ... 2515 int HWAES_set_encrypt_key(const unsigned char *userKey, const int bits, 2516 AES_KEY *key); 

泡沫,冲洗,重复AES_KEYaes_p8_set_decrypt_keyaes_p8_encryptaes_p8_decrypt

最终你会得到一个像Cryptogams中所示的标题 OpenSSL wiki上的AES 。 Cryptogams | AES是为ARMv4编写的,但同样适用于Power8。


退一步,你试图在Power8上使用AES的Cryptogams实现。 Cryptogams是Andy Polyakov为其他开发人员提供高速加密的项目。

安迪双重许可他的工作。 一个许可证是OpenSSL许可证,因为Andy适用于OpenSSL。 第二个许可证是BSD风格的许可证,没有OpenSSL的负担。

Andy的公共资源来自GitHub | dot-asm 。 不幸的是,Andy的大部分工作都没有上传,因此您必须将其从OpenSSL中删除。 而且更不幸的是,没有任何记录,所以你必须在OpenSSL源中做相当多的戳戳和刺激。

据我所知,有两个地方可以查找使用Cryptogams和Power8加密的文档。 首先是OpenSSL wiki页面Cryptogams | AES 。 Cryptogams | AES是ARMv4的教程,但它也适用于Power 8。 我写了维基文章,所以错误和遗漏是我的错误。

第二个看GitHub和Noloader | POWER8加密 。 我帮助维护Crypto ++和POWER8加密书是我的知识转储。 POWER8一书包含第7章中的Cryptogams SHA。

POWER8加密书由Bill Schmidt和我编写,因为在Power8上使用AES和SHA时我们找不到文档。 比尔施密特在IBM工作,甚至他也无法获得文档,因为没有。 我们所能找到的只是来自IBM工程师的博客文章,其中遗漏了细节。