通常对代码的加密保护有硬件加密方式和软件加密方式。
AES是通常比较常用的一种有效加密方式
什么是AES加密?
从概念上来说
高级加密标准(英语:Advanced Encryption Standard,缩写:AES),在密码学中又称Rijndael加密法,是美国联邦***采用的一种区块加密标准。这个标准用来替代原先的DES,已经被多方分析且广为全世界所使用。经过五年的甄选流程,高级加密标准由美国国家标准与威廉希尔官方网站
研究院(NIST)于2001年11月26日发布于FIPS PUB 197,并在2002年5月26日成为有效的标准。2006年,高级加密标准已然成为对称密钥加密中最流行的算法之一。
Rijndael密码的设计力求满足以下3条标准:
① 抵抗所有已知的攻击。
② 在多个平台上速度快,编码紧凑。
③ 设计简单。
当前的大多数分组密码,其轮函数是Feistel结构。
Rijndael没有这种结构。
Rijndael轮函数是由3个不同的可逆均匀变换
严格地说,AES和Rijndael加密法并不完全一样(虽然在实际应用中二者可以互换),因为Rijndael加密法可以支持更大范围的区块和密钥长度:AES的区块长度固定为128 比特,密钥长度则可以是128,192或256比特;而Rijndael使用的密钥和区块长度可以是32位的整数倍,以128位为下限,256比特为上限。加密过程中使用的密钥是由Rijndael密钥生成方案产生。
大多数AES计算是在一个特别的有限域完成的。
0
|
|
|
|
AES加密过程是在一个4×4的字节矩阵上运作,这个矩阵又称为“状态(state)”,其初值就是一个明文区块(矩阵中一个元素大小就是明文区块中的一个Byte)。(Rijndael加密法因支持更大的区块,其矩阵行数可视情况增加)加密时,各轮AES加密循环(除最后一轮外)均包含4个步骤:
AddRoundKey — 矩阵中的每一个字节都与该次轮秘钥(round key)做XOR运算;每个子密钥由密钥生成方案产生。
SubBytes — 通过个非线性的替换函数,用查找表的方式把每个字节替换成对应的字节。
ShiftRows — 将矩阵中的每个横列进行循环式移位。
MixColumns — 为了充分混合矩阵中各个直行的操作。这个步骤使用线性转换来混合每列的四个字节。
最后一个加密循环中省略MixColumns步骤,而以另一个AddRoundKey取代。
|
|
|
|
|
更为深入的说明可以看看度娘O(∩_∩)O~
从实用角度来说,咱还是看看具体程序
atmel还是比较贴心的,居然给出了基于atmel芯片的加密例程
咱来实际体验下
先看看主函数
- int main(void)
- {
- uint8_t key;
- /* Initialize the SAM system */
- sysclk_init();
- board_init();
- /* Initialize the console */
- configure_console();
- /* Output example information */
- printf("-- AES Example --rn");
- printf("-- %snr", BOARD_NAME);
- printf("-- Compiled: %s %s --nr", __DATE__, __TIME__);
- /* Enable the AES module. */
- aes_get_config_defaults(&g_aes_cfg);
- aes_init(AES, &g_aes_cfg);
- aes_enable();
- /* Enable AES interrupt. */
- aes_set_callback(AES, AES_INTERRUPT_DATA_READY,
- aes_callback, 1);
- /* Display menu */
- display_menu();
- while (1) {
- scanf("%c", (char *)&key);
- switch (key) {
- case 'h':
- display_menu();
- break;
- case '1':
- printf("ECB mode encryption and decryption test.rn");
- ecb_mode_test();
- break;
- case '2':
- printf("CBC mode encryption and decryption test.rn");
- cbc_mode_test();
- break;
- case '3':
- printf("CFB128 mode encryption and decryption test.rn");
- cfb128_mode_test();
- break;
- case '4':
- printf("OFB mode encryption and decryption test.rn");
- ofb_mode_test();
- break;
- case '5':
- printf("CTR mode encryption and decryption test.rn");
- ctr_mode_test();
- break;
- case 'd':
- #if SAM4E
- printf(
- "ECB mode encryption and decryption test with DMA.rn");
- ecb_mode_test_dma();
- #else
- printf("This mode is not supported by device.rn");
- #endif
- break;
- case 'p':
- #if SAM4C || SAM4CP || SAM4CM
- printf(
- "ECB mode encryption and decryption test with PDC.rn");
- ecb_mode_test_pdc();
- #else
- printf("This mode is not supported by device.rn");
- #endif
- break;
- default:
- break;
- }
- }
- }
|
|
|
|
|
主要两部分,使能AES模式和使能AES中断
程序模块化集成的很不错,调用很方便
具体的函数在aes.c文件中
- void aes_set_callback(
- Aes *const p_aes,
- aes_interrupt_source_t source,
- aes_callback_t callback,
- uint8_t irq_level)
- {
- /* Validate arguments. */
- Assert(p_aes);
- if (source == AES_INTERRUPT_DATA_READY) {
- aes_callback_pointer[0] = callback;
- } else if (source == AES_INTERRUPT_UNSPECIFIED_REGISTER_ACCESS) {
- aes_callback_pointer[1] = callback;
- }
- #if SAM4C || SAM4CP || SAM4CM
- else if (source == AES_INTERRUPT_END_OF_RECEIVE_BUFFER) {
- aes_callback_pointer[2] = callback;
- } else if (source == AES_INTERRUPT_END_OF_TRANSMIT_BUFFER) {
- aes_callback_pointer[3] = callback;
- } else if (source == AES_INTERRUPT_RECEIVE_BUFFER_FULL) {
- aes_callback_pointer[4] = callback;
- } else if (source == AES_INTERRUPT_TRANSMIT_BUFFER_FULL) {
- aes_callback_pointer[5] = callback;
- }
- #elif SAMV70 || SAMV71 || SAME70 || SAMS70
- else if ((source == AES_INTERRUPT_TAG_READY)) {
- aes_callback_pointer[2] = callback;
- }
- #endif /* SAM4C || SAM4CP || SAM4CM */
- irq_register_handler((IRQn_Type)AES_IRQn, irq_level);
- aes_enable_interrupt(p_aes, source);
- }
|
|
|
|
|
详细的AES中断处理
- void AES_Handler(void)
- {
- uint32_t status = aes_read_interrupt_status(AES);
- uint32_t mask = aes_read_interrupt_mask(AES);
- if ((status & AES_ISR_DATRDY) && (mask & AES_IMR_DATRDY)) {
- if (aes_callback_pointer[0]) {
- aes_callback_pointer[0]();
- }
- }
- if ((status & AES_ISR_URAD) && (mask & AES_IMR_URAD)) {
- if (aes_callback_pointer[1]) {
- aes_callback_pointer[1]();
- }
- }
- #if SAM4C || SAM4CP || SAM4CM
- if ((status & AES_ISR_ENDRX) && (mask & AES_IMR_ENDRX)) {
- if (aes_callback_pointer[2]) {
- aes_callback_pointer[2]();
- }
- }
- if ((status & AES_ISR_ENDTX) && (mask & AES_IMR_ENDTX)) {
- if (aes_callback_pointer[3]) {
- aes_callback_pointer[3]();
- }
- }
- if ((status & AES_ISR_RXBUFF) && (mask & AES_IMR_RXBUFF)) {
- if (aes_callback_pointer[4]) {
- aes_callback_pointer[4]();
- }
- }
- if ((status & AES_ISR_TXBUFE) && (mask & AES_IMR_TXBUFE)) {
- if (aes_callback_pointer[5]) {
- aes_callback_pointer[5]();
- }
- }
- #elif SAMV70 || SAMV71 || SAME70 || SAMS70
- if ((status & AES_IER_TAGRDY) && (mask & AES_IER_TAGRDY)) {
- if (aes_callback_pointer[2]) {
- aes_callback_pointer[2]();
- }
- }
- #endif /* SAM4C || SAM4CP || SAM4CM */
- }
[color=rgb(51, 102, 153) !important]复制代码
其实还是通过算法调用指定的数组,不停的数据变化
整个工程很多的定义和一层层的数据处理,还是算法啊,写的不错,感兴趣的可以一起研究下
|
|
|
|
|