PadLock AES内核测试模块(二)
PadLock AES内核测试模块(2)

四、源码实现
主要关键的函数说完了,下面结合具体的源码进一步分析:
我通过编译Linux内核模块实现,两个文件:tcrypt.c和Makefile。直接通过make、make install就可以实现。
tcrypt.c: #include <linux/module.h> #include <linux/crypto.h> #include <linux/kernel.h> #include <linux/init.h> #include <linux/scatterlist.h> #include <linux/slab.h> #include <linux/highmem.h> static void my_test_cipher(void) //实现函数 { unsigned int ret; int i; /*必须要用数组,如果用*code这种方式就会输出不正确的数据,还请大神们帮忙解答*/ char code[17] = "1234567887654321"; char *key = "0123456789abcdef";//关键key char *iv = "1234567887654321";//设置iv值 struct scatterlist sgd;//散集序列,输出 struct scatterlist sgs;//散集序列,输入 struct scatterlist sgl;//散集序列,解密后输出 char last_mem[17]; char dst_mem[17]; char *out = NULL; char *result = NULL; char *src = NULL; struct crypto_blkcipher *tfm; struct blkcipher_desc desc; memset(last_mem,0,17); memset(dst_mem,0,17); /*分配块加密上下文 cbc(aes)表示模式,也可以ofb(aes)等,通常第一个参数为0,第三个参数表示加密模式, */ tfm = crypto_alloc_blkcipher("cbc(aes)", 0, CRYPTO_ALG_ASYNC); desc.tfm = tfm; desc.flags = 0; /*设置散集序列,将Linux内核中虚拟内存的数据传送到散集序列供dma应用,其中dst_mem,code,last_mem是我们自己设定的值,后面的16表示数据长度大小*/ sg_init_one(&sgd,dst_mem,16); sg_init_one(&sgs,code,16); sg_init_one(&sgl,last_mem,16); crypto_blkcipher_setkey(tfm,key,16);//设置key crypto_blkcipher_set_iv(tfm,iv,16);//设置iv /*将sgs(散集序列,物理内存)映射到Linux内核的虚拟内存中,目的是我们可以显示其数据*/ src = kmap(sg_page(&sgs))+sgs.offset; printk("the orgin is\n"); for(i = 0 ;i < sgs.length;i++){ printk("%c\n",src[i]); } //加密 ret = crypto_blkcipher_encrypt(&desc,&sgd,&sgs,sgs.length); if (!ret) { printk("AES encrypt success*************************\n"); out = kmap(sg_page(&sgd))+sgd.offset; printk("the encrypt is:\n"); for(i = 0;i<sgd.length;i++){ printk("%c\n",out[i]); } } else{ printk("the encrypt is wrong\n"); return ; } crypto_blkcipher_setkey(tfm,key,16); crypto_blkcipher_set_iv(tfm,iv,16); //解密 ret = crypto_blkcipher_decrypt(&desc,&sgl,&sgd,sgd.length); if(!ret){ printk(KERN_INFO"hw aes decrypt is success\n"); result = kmap(sg_page(&sgl))+sgl.offset; for(i = 0; i < sgl.length;i++){ printk("%c\n",result[i]); } } else{ printk("the decrypt is wrong\n"); return; } crypto_free_blkcipher(tfm);
<span style="white-space:pre"> </span>kunmap(sg_page(&sgs));
<span style="white-space:pre"> </span>kunmap(sg_page(&sgd)); } static int __init tcrypt_mod_init(void) { my_test_cipher(); return 0; } /* * If an init function is provided, an exit function must also be provided * to allow module unload. */ static void __exit tcrypt_mod_fini(void) { } module_init(tcrypt_mod_init); module_exit(tcrypt_mod_fini); //MODULE_PARM_DESC(sec, "Length in seconds of speed tests " // "(defaults to zero which uses CPU cycles instead)"); MODULE_LICENSE("GPL"); MODULE_DESCRIPTION("Quick & dirty crypto testing module"); MODULE_AUTHOR("dachuan"); Makefile: KONAME = tcrypt.o IFTEST=$(shell lsmod | grep tcrypt | wc -l) KERNELDIR := /lib/modules/$(shell uname -r)/build PWD :=$(shell pwd) obj-m:=$(KONAME) module: make -C $(KERNELDIR) M=$(PWD) test_install : ifeq ($(IFTEST),1) rmmod tcrypt insmod tcrypt.ko else insmod tcrypt.ko endif install: test_install .PHONY:install clean: rm *.o *.mod.c modules.order Module.symvers .*.cmd *.ko rm -rf .tmp_versions
五、实验
首先进入带有tcrypt.c makefile的文件夹:
输入命令:
make
make install
利用dmesg查看Linux内核信息:
参考文献
[1]http://blog.****.net/sonicling/article/details/6275898 Linux内核块设备加密分析