日韩性视频-久久久蜜桃-www中文字幕-在线中文字幕av-亚洲欧美一区二区三区四区-撸久久-香蕉视频一区-久久无码精品丰满人妻-国产高潮av-激情福利社-日韩av网址大全-国产精品久久999-日本五十路在线-性欧美在线-久久99精品波多结衣一区-男女午夜免费视频-黑人极品ⅴideos精品欧美棵-人人妻人人澡人人爽精品欧美一区-日韩一区在线看-欧美a级在线免费观看

歡迎訪問(wèn) 生活随笔!

生活随笔

當(dāng)前位置: 首頁(yè) > 运维知识 > linux >内容正文

linux

[crypto]-30-The Armv8 Cryptographic Extension在linux中的应用

發(fā)布時(shí)間:2025/3/21 linux 25 豆豆
生活随笔 收集整理的這篇文章主要介紹了 [crypto]-30-The Armv8 Cryptographic Extension在linux中的应用 小編覺(jué)得挺不錯(cuò)的,現(xiàn)在分享給大家,幫大家做個(gè)參考.

快速鏈接:
.
👉👉👉 個(gè)人博客筆記導(dǎo)讀目錄(全部) 👈👈👈


相關(guān)推薦:
Armv8 Cryptographic Extension介紹
Linux Kernel aarch64 Crypto原理和框架介紹
Linux kernel內(nèi)核調(diào)用crypto算法的方法
Linux Kernel aarch64的ARM-CE aes-ecb的底層代碼導(dǎo)讀


說(shuō)明: 在無(wú)特別的說(shuō)明下,本文講述得都是armv8-aarch64體系、linux kernel 4.14 arm64軟件環(huán)境!

1、在linux crypto底層,實(shí)現(xiàn)aes/hash的算法有三種方式:
(1)、cpu的純軟實(shí)現(xiàn),使用cpu的ALU,x0-x30等寄存器,加加減減的計(jì)算。(本文不討論此項(xiàng))
(2)、ARM-CE,就是The Armv8 Cryptographic Extension了,調(diào)用arm-ce的指令和寄存器,進(jìn)行加加減減計(jì)算
(3)、ARM-NEON : 調(diào)用arm neon指令(128bit的寄存器v0-v31),進(jìn)行加加減減計(jì)算

再進(jìn)一步闡述ARM-CE,其實(shí)也調(diào)用NEON的浮點(diǎn)型運(yùn)算器,讀寫arm-ce的寄存器、以前使用arm-ce的指令,進(jìn)行加解密運(yùn)算。

2、需要明確一點(diǎn)
The Armv8 Cryptographic Extension provides instructions for the acceleration of encryption and decryption
Armv8 Cryptographic Extension 并不是單獨(dú)的硬件 ,只是ARM擴(kuò)展了一套寄存器和命令,依然還是cpu計(jì)算的
ARM NEON也是,也是一套寄存器和命令,依然還是cpu在下執(zhí)行

3、以aes為例,arm-ce和arm-neon的crypto的暴露給上層的接口代碼,都在下列文件中
在aes-glue.c中, 注冊(cè)了aes算法接口:

static struct crypto_alg aes_algs[] = { {.cra_name = "__ecb-aes-" MODE,.cra_driver_name = "__driver-ecb-aes-" MODE,.cra_priority = 0,.cra_flags = CRYPTO_ALG_TYPE_BLKCIPHER |CRYPTO_ALG_INTERNAL,.cra_blocksize = AES_BLOCK_SIZE,.cra_ctxsize = sizeof(struct crypto_aes_ctx),.cra_alignmask = 7,.cra_type = &crypto_blkcipher_type,.cra_module = THIS_MODULE,.cra_blkcipher = {.min_keysize = AES_MIN_KEY_SIZE,.max_keysize = AES_MAX_KEY_SIZE,.ivsize = 0,.setkey = aes_setkey,.encrypt = ecb_encrypt,.decrypt = ecb_decrypt,}, }, {.cra_name = "__cbc-aes-" MODE,.cra_driver_name = "__driver-cbc-aes-" MODE,.cra_priority = 0,.cra_flags = CRYPTO_ALG_TYPE_BLKCIPHER |CRYPTO_ALG_INTERNAL,.cra_blocksize = AES_BLOCK_SIZE,.cra_ctxsize = sizeof(struct crypto_aes_ctx),.cra_alignmask = 7,.cra_type = &crypto_blkcipher_type,.cra_module = THIS_MODULE,.cra_blkcipher = {.min_keysize = AES_MIN_KEY_SIZE,.max_keysize = AES_MAX_KEY_SIZE,.ivsize = AES_BLOCK_SIZE,.setkey = aes_setkey,.encrypt = cbc_encrypt,.decrypt = cbc_decrypt,}, }, {.cra_name = "__ctr-aes-" MODE,.cra_driver_name = "__driver-ctr-aes-" MODE,.cra_priority = 0,.cra_flags = CRYPTO_ALG_TYPE_BLKCIPHER |CRYPTO_ALG_INTERNAL,.cra_blocksize = 1,.cra_ctxsize = sizeof(struct crypto_aes_ctx),.cra_alignmask = 7,.cra_type = &crypto_blkcipher_type,.cra_module = THIS_MODULE,.cra_blkcipher = {.min_keysize = AES_MIN_KEY_SIZE,.max_keysize = AES_MAX_KEY_SIZE,.ivsize = AES_BLOCK_SIZE,.setkey = aes_setkey,.encrypt = ctr_encrypt,.decrypt = ctr_encrypt,}, }, {.cra_name = "__xts-aes-" MODE,.cra_driver_name = "__driver-xts-aes-" MODE,.cra_priority = 0,.cra_flags = CRYPTO_ALG_TYPE_BLKCIPHER |CRYPTO_ALG_INTERNAL,.cra_blocksize = AES_BLOCK_SIZE,.cra_ctxsize = sizeof(struct crypto_aes_xts_ctx),.cra_alignmask = 7,.cra_type = &crypto_blkcipher_type,.cra_module = THIS_MODULE,.cra_blkcipher = {.min_keysize = 2 * AES_MIN_KEY_SIZE,.max_keysize = 2 * AES_MAX_KEY_SIZE,.ivsize = AES_BLOCK_SIZE,.setkey = xts_set_key,.encrypt = xts_encrypt,.decrypt = xts_decrypt,}, }, {.cra_name = "ecb(aes)",.cra_driver_name = "ecb-aes-" MODE,.cra_priority = PRIO,.cra_flags = CRYPTO_ALG_TYPE_ABLKCIPHER|CRYPTO_ALG_ASYNC,.cra_blocksize = AES_BLOCK_SIZE,.cra_ctxsize = sizeof(struct async_helper_ctx),.cra_alignmask = 7,.cra_type = &crypto_ablkcipher_type,.cra_module = THIS_MODULE,.cra_init = ablk_init,.cra_exit = ablk_exit,.cra_ablkcipher = {.min_keysize = AES_MIN_KEY_SIZE,.max_keysize = AES_MAX_KEY_SIZE,.ivsize = 0,.setkey = ablk_set_key,.encrypt = ablk_encrypt,.decrypt = ablk_decrypt,} }, {.cra_name = "cbc(aes)",.cra_driver_name = "cbc-aes-" MODE,.cra_priority = PRIO,.cra_flags = CRYPTO_ALG_TYPE_ABLKCIPHER|CRYPTO_ALG_ASYNC,.cra_blocksize = AES_BLOCK_SIZE,.cra_ctxsize = sizeof(struct async_helper_ctx),.cra_alignmask = 7,.cra_type = &crypto_ablkcipher_type,.cra_module = THIS_MODULE,.cra_init = ablk_init,.cra_exit = ablk_exit,.cra_ablkcipher = {.min_keysize = AES_MIN_KEY_SIZE,.max_keysize = AES_MAX_KEY_SIZE,.ivsize = AES_BLOCK_SIZE,.setkey = ablk_set_key,.encrypt = ablk_encrypt,.decrypt = ablk_decrypt,} }, {.cra_name = "ctr(aes)",.cra_driver_name = "ctr-aes-" MODE,.cra_priority = PRIO,.cra_flags = CRYPTO_ALG_TYPE_ABLKCIPHER|CRYPTO_ALG_ASYNC,.cra_blocksize = 1,.cra_ctxsize = sizeof(struct async_helper_ctx),.cra_alignmask = 7,.cra_type = &crypto_ablkcipher_type,.cra_module = THIS_MODULE,.cra_init = ablk_init,.cra_exit = ablk_exit,.cra_ablkcipher = {.min_keysize = AES_MIN_KEY_SIZE,.max_keysize = AES_MAX_KEY_SIZE,.ivsize = AES_BLOCK_SIZE,.setkey = ablk_set_key,.encrypt = ablk_encrypt,.decrypt = ablk_decrypt,} }, {.cra_name = "xts(aes)",.cra_driver_name = "xts-aes-" MODE,.cra_priority = PRIO,.cra_flags = CRYPTO_ALG_TYPE_ABLKCIPHER|CRYPTO_ALG_ASYNC,.cra_blocksize = AES_BLOCK_SIZE,.cra_ctxsize = sizeof(struct async_helper_ctx),.cra_alignmask = 7,.cra_type = &crypto_ablkcipher_type,.cra_module = THIS_MODULE,.cra_init = ablk_init,.cra_exit = ablk_exit,.cra_ablkcipher = {.min_keysize = 2 * AES_MIN_KEY_SIZE,.max_keysize = 2 * AES_MAX_KEY_SIZE,.ivsize = AES_BLOCK_SIZE,.setkey = ablk_set_key,.encrypt = ablk_encrypt,.decrypt = ablk_decrypt,} } };

4、aes-glue.c文件中并且定義了每一個(gè)接口指向的底層函數(shù), 這里根據(jù)USE_V8_CRYPTO_EXTENSIONS分為了兩中情況:
(1)、使用arm的crypto extension硬件算aes
(2)、使用arm的SIMD指令(ARM NEON)來(lái)算aes

#ifdef USE_V8_CRYPTO_EXTENSIONS #define MODE "ce" #define PRIO 300 #define aes_setkey ce_aes_setkey #define aes_expandkey ce_aes_expandkey #define aes_ecb_encrypt ce_aes_ecb_encrypt #define aes_ecb_decrypt ce_aes_ecb_decrypt #define aes_cbc_encrypt ce_aes_cbc_encrypt #define aes_cbc_decrypt ce_aes_cbc_decrypt #define aes_ctr_encrypt ce_aes_ctr_encrypt #define aes_xts_encrypt ce_aes_xts_encrypt #define aes_xts_decrypt ce_aes_xts_decrypt MODULE_DESCRIPTION("AES-ECB/CBC/CTR/XTS using ARMv8 Crypto Extensions"); #else #define MODE "neon" #define PRIO 200 #define aes_setkey crypto_aes_set_key #define aes_expandkey crypto_aes_expand_key #define aes_ecb_encrypt neon_aes_ecb_encrypt #define aes_ecb_decrypt neon_aes_ecb_decrypt #define aes_cbc_encrypt neon_aes_cbc_encrypt #define aes_cbc_decrypt neon_aes_cbc_decrypt #define aes_ctr_encrypt neon_aes_ctr_encrypt #define aes_xts_encrypt neon_aes_xts_encrypt #define aes_xts_decrypt neon_aes_xts_decrypt MODULE_DESCRIPTION("AES-ECB/CBC/CTR/XTS using ARMv8 NEON"); #endif

5、以ce_aes_cbc_encrypt為例,看下crypto extension的硬件實(shí)現(xiàn):
在aes-ce-core.S中, 由此可以看出,這里最終調(diào)用的都是aesd、aesmc…等armv8 crypto extension的匯編指令

ENTRY(ce_aes_cbc_encrypt)push {r4-r6, lr}ldrd r4, r5, [sp, #16]vld1.8 {q0}, [r5]prepare_key r2, r3 .Lcbcencloop:vld1.8 {q1}, [r1, :64]! @ get next pt blockveor q0, q0, q1 @ ..and xor with ivbl aes_encryptvst1.8 {q0}, [r0, :64]!subs r4, r4, #1bne .Lcbcencloopvst1.8 {q0}, [r5]pop {r4-r6, pc} ENDPROC(ce_aes_cbc_encrypt) aes_encrypt:add ip, r2, #32 @ 3rd round key .Laes_encrypt_tweak:do_block enc_dround, enc_fround ENDPROC(aes_encrypt) .macro enc_dround, key1, key2 enc_round q0, \key1 enc_round q0, \key2 .endm .macro enc_round, state, key aese.8 \state, \key aesmc.8 \state, \state .endm

6、以ce_aes_cbc_encrypt為例,看下NEON的硬件實(shí)現(xiàn):
在aes-neon.S/aes-modes.S中, 由此可以看出,這里最終操作的都是v0-v31等128bit的SIMD寄存器

AES_ENTRY(aes_cbc_encrypt)cbz w6, .Lcbcencloopld1 {v0.16b}, [x5] /* get iv */enc_prepare w3, x2, x6/* do preload for encryption */.macro enc_prepare, ignore0, ignore1, tempprepare .LForward_Sbox, .LForward_ShiftRows, \temp.endm /* preload the entire Sbox */ .macro prepare, sbox, shiftrows, temp adr \temp, \sbox movi v12.16b, #0x40 ldr q13, \shiftrows movi v14.16b, #0x1b ld1 {v16.16b-v19.16b}, [\temp], #64 ld1 {v20.16b-v23.16b}, [\temp], #64 ld1 {v24.16b-v27.16b}, [\temp], #64 ld1 {v28.16b-v31.16b}, [\temp] .endm

7、疑問(wèn)與答案
kernel進(jìn)程A在cpu0上跑的時(shí)候,被調(diào)度了,此時(shí)會(huì)將通用寄存器(如x0-x30,sp,pc等)保存起來(lái),然后調(diào)度。等再回來(lái)時(shí),(假設(shè)被cpu1接著執(zhí)行了)再恢復(fù)下這些寄存器。程序就可以接著跑。
調(diào)度時(shí)只是保存了x0-x30等通用寄存器,并沒(méi)有保存NEON寄存器v0-v31、ARM-CE的寄存器。
假如kernel線程A正在cpu0上執(zhí)行浮點(diǎn)型運(yùn)算(ARM NEON運(yùn)算),然后被調(diào)度了(沒(méi)有保存v0-v31),等再回來(lái)時(shí)是cpu1再來(lái)執(zhí)行該線程,那么怎么可以回復(fù)之前的狀態(tài)呢?

答案在Documentation/arm/kernel_mode_neon.txt中:
Use only NEON instructions, or VFP instructions that don’t rely on support
(1)Isolate your NEON code in a separate compilation unit, and compile it with ‘-mfpu=neon -mfloat-abi=softfp’
(2)Put kernel_neon_begin() and kernel_neon_end() calls around the calls into your NEON code
(3)Don’t sleep in your NEON code, and be aware that it will be executed with preemption disabled

也就是說(shuō)在執(zhí)行NEON的代碼中 ,需要使用kernel_neon_begin()/kernel_neon_end()包上,這樣這段代碼就不會(huì)被搶占、屬于原子操作了。就沒(méi)有調(diào)度之說(shuō)了
示例:請(qǐng)看arch/arnm64/crypto/aes-glue.c,在該代碼中,在調(diào)用ARM-NEON或ARM-CE時(shí),都是使用kernel_neon_begin()/kernel_neon_end()包上了

如下列代碼所示,arm-neon和arm-ce的ecb_encrypt都是調(diào)用的下列函數(shù),然后aes_ecb_encrypt是一個(gè)宏,有USE_V8_CRYPTO_EXTENSIONS宏來(lái)決定,其要么指向ARM-CE的函數(shù),要么指向ARM-NEON的函數(shù)
ecb_encrypt的主體是被kernel_neon_begin()/kernel_neon_end()包裹著的,所以這段函數(shù)是原子操作。

static int ecb_encrypt(struct blkcipher_desc *desc, struct scatterlist *dst,struct scatterlist *src, unsigned int nbytes) {struct crypto_aes_ctx *ctx = crypto_blkcipher_ctx(desc->tfm);int err, first, rounds = 6 + ctx->key_length / 4;struct blkcipher_walk walk;unsigned int blocks;desc->flags &= ~CRYPTO_TFM_REQ_MAY_SLEEP;blkcipher_walk_init(&walk, dst, src, nbytes);err = blkcipher_walk_virt(desc, &walk);kernel_neon_begin();for (first = 1; (blocks = (walk.nbytes / AES_BLOCK_SIZE)); first = 0) {aes_ecb_encrypt(walk.dst.virt.addr, walk.src.virt.addr,(u8 *)ctx->key_enc, rounds, blocks, first);err = blkcipher_walk_done(desc, &walk, walk.nbytes % AES_BLOCK_SIZE);}kernel_neon_end();return err; }

8、userspace調(diào)用、物理地址的連續(xù)性、對(duì)齊、block
linux kernel crypto和用戶空間通過(guò)netlink交互,在linux kernel的algif_skcipher.c程序中,會(huì)將userspace sock傳來(lái)的數(shù)據(jù),保存在scatterlist結(jié)構(gòu)體(離散的物理塊).
然后在aes-ce-glue.c中,依次對(duì)每一塊連續(xù)的物理地址數(shù)據(jù)調(diào)用底層的加解密函數(shù)
在底層的加解密函數(shù)中,需要自行解決對(duì)齊的處理、分block的處理


相關(guān)推薦:
?????????[crypto]-01-對(duì)稱加解密AES原理概念詳解
?????????[crypto]-02-非對(duì)稱加解密RSA原理概念詳解
?????????[crypto]-03-數(shù)字摘要HASH原理概念詳解
?????????[crypto]-04-國(guó)產(chǎn)密碼算法(國(guó)密算法sm2/sm3/sm4)介紹
?????????[crypto]-05-轉(zhuǎn)載:PKCS #1 RSA Encryption Version 1.5介紹
?????????[crypto]-05.1-PKCS PKCS#1 PKCS#7 PKCS#11的介紹
?????????[crypto]-06-CA證書介紹和使用方法


?????????[crypto]-30-The Armv8 Cryptographic Extension在linux中的應(yīng)用
?????????[crypto]-31-crypto engion的學(xué)習(xí)和總結(jié)


?????????[crypto]-50-base64_encode和base64_decode的C語(yǔ)言實(shí)現(xiàn)
?????????[crypto]-51-RSA私鑰pem轉(zhuǎn)換成der, 在將der解析出n e d p q dp dq qp
?????????[crypto]-52-python3中rsa(簽名驗(yàn)簽加密解密)aes(ecb cbc ctr)hmac的使用,以及unittest測(cè)試用
?????????[crypto]-53-openssl命令行的使用(aes/rsa簽名校驗(yàn)/rsa加密解密/hmac)


?????????[crypto]-90-crypto的一些術(shù)語(yǔ)和思考

總結(jié)

以上是生活随笔為你收集整理的[crypto]-30-The Armv8 Cryptographic Extension在linux中的应用的全部?jī)?nèi)容,希望文章能夠幫你解決所遇到的問(wèn)題。

如果覺(jué)得生活随笔網(wǎng)站內(nèi)容還不錯(cuò),歡迎將生活随笔推薦給好友。

主站蜘蛛池模板: 欧美成人二区 | 色综合久久中文字幕无码 | 超碰自拍 | 一区二区在线免费观看视频 | 久久99这里只有精品 | 国产一二区在线 | 伊人网站在线观看 | 国产精品大片 | www.av免费 | 欧美乱强伦 | 熟女少妇内射日韩亚洲 | 国产白袜脚足j棉袜在线观看 | 9久久9毛片又大又硬又粗 | 国产美女主播视频 | 亚洲一区二区三区四区在线播放 | 国产一级在线观看视频 | 九九九九精品九九九九 | 日韩精品2区 | 欧美日韩一区二区三区四区五区六区 | 99综合网 | 久久avav | 欧美三级不卡 | 国产视频第一区 | 高清不卡一区 | 夜夜操天天爽 | 琪琪色影音先锋 | 非洲一级片 | av男人的天堂网 | 99热视 | 草草视频在线 | 日韩成人免费在线视频 | 日韩电影在线一区二区 | 夜夜躁狠狠躁 | 一级大片免费 | 精品少妇一区二区三区在线观看 | 护士的小嫩嫩好紧好爽 | zzji欧美大片| 操极品美女| 久久精品这里 | 欧美人与性动交a欧美精品 日韩免费高清视频 | 9l视频自拍九色9l视频 | 性――交――性――乱a | 99九九热 | 国产一国产二 | 被黑人啪到哭的番号922在线 | 日韩一区二区免费播放 | 视频在线不卡 | 欧美日韩亚洲一区二区 | 欧美永久免费 | aaa国产视频 | 欧美成人免费网站 | 中文字幕日韩无 | 欧洲亚洲综合 | 国产又黄又爽 | 最近中文字幕免费mv视频7 | 国产小视频免费 | 亚洲欧美日韩精品久久 | 激情婷婷色 | 久久电影一区 | 日韩中文字幕在线视频 | 久久久久久98| 国产伦一区二区三区 | 亚洲xxxx18| 国产在线视频福利 | 精品一久久 | 欧美成人片在线 | 成人免费毛片嘿嘿连载 | 亚洲第一视频在线播放 | 九九综合网 | 亚洲免费在线 | 人妻精品一区二区在线 | 天天色影综合网 | 国产人妖在线观看 | 精品999视频| 成人超碰 | 色老头一区二区三区 | 黄色一级片 | 做爰视频毛片视频 | 亚洲最大黄色 | va视频在线 | 成人免费看片98欧美 | 亚洲爱视频 | 视频在线观看电影完整版高清免费 | 日韩专区一区二区三区 | 精品久久精品久久 | 女人性做爰100部免费 | 自拍偷拍激情 | 国模精品一区二区三区 | 色秀视频在线观看 | 国产精品无码一区二区三区三 | 成人av网站在线观看 | 亚洲大片 | 狠狠五月天 | 色呦呦网站入口 | 在线观看高清视频 | 狠狠网站| 蜜桃成人在线视频 | 欧美精品大片 | 少妇无内裤下蹲露大唇视频 |