/* * * * */ #include "function_interface.h" #include "platform_interface.h" #include "base_core_user.h" #include "function.h" #include "string.h" #include "AES.h" #include "HW_MCUIO.h" //#include "stm32f4xx_hal.h" //#define E2PROM_ADDR_KEYCODE 0x100 #define STORE_AES_KEYCODE_ADDR 0x400 //len =32 #define STORE_AES_CONFIG_ADDR 0x420 //0x120 //len =3 //20200427修改,解决和IP地址存储冲突!! #define KEY_CODE_LEN 32 #define KEYCODE_LEN_HALF 16 const unsigned char Keycode_Sunvote[] ="SunVote1998&JackPei1972CoolBob99";//32字节原始密码原始数据 struct AES_STR{ unsigned char type_0_128_256; unsigned char _mcu_flag; //硬件AES; =0-->软件AES AesMcu unsigned char key_update_flag; unsigned char keycode0[KEY_CODE_LEN]; //skey0 unsigned char keycode[KEY_CODE_LEN]; //skey }; struct AES_STR aes; /* * 加密函数 * input: key -- _256_mode --128 or 256 */ static void Encrypt(unsigned char *src,unsigned char *dist,unsigned char *key,unsigned char _256_mode) { uint32_t output_len; if(_256_mode==2) _256_mode =1; //AES 256 else _256_mode =0; //AES 128 if (aes._mcu_flag==1) STM32_AES_ECB_Encrypt(src,16,key,dist,&output_len,_256_mode);//16是src长度,函数里面支持加密模式 else AES_Encrypt((char*)src,(char*)dist,(char*)key,_256_mode); } /* * 解密函数 * */ static void Decrypt(unsigned char *src,unsigned char *dist,unsigned char *key,unsigned char _256_mode) { uint32_t output_len; if(_256_mode==2) _256_mode =1; //AES 256 else _256_mode =0; //AES 128 if (aes._mcu_flag==1) STM32_AES_ECB_Decrypt(src,16,key,dist,&output_len,_256_mode); else AES_Decrypt((char*)dist,(char*)src,(char*)key,_256_mode); } /* * 获取默认的秘钥 * input:key ---对应demo中的sKey0; * note:使用AES128分别操作前后16bytes */ static void generate_default_key0_code(void) { unsigned char i; memset(aes.keycode0,0,KEY_CODE_LEN); memcpy(aes.keycode,Keycode_Sunvote,KEY_CODE_LEN); for(i=0;i>8; // src[32]=crc_tmp&0xff; // src[0]=32; // } //------------ CRC ---------------- { unsigned short crc_tmp; crc_tmp = crc16(src+5,26); src[31]=crc_tmp>>8; src[32]=crc_tmp&0xff; src[0]=32; } //--------------------------------- //0, copy memcpy(dist,src,KEY_CODE_LEN+1); //a, if( (tmp=CmdXch(src[5])) >0) dist[5] =tmp; //byte6-21 加密 if( ((dist[5]==0x41)||(dist[5]==0x42) ) &&(dist[9]==40) ){//0x13->0x41 0x14->0x42 dist[5] =0x4C; Encrypt(src+6,dist+6,aes.keycode0,aes.type_0_128_256); } else{ if(base_is_auto_match() ){//--- //dist[5] =0x4C; Encrypt(src+6,dist+6,aes.keycode0,aes.type_0_128_256); } else //--- Encrypt(src+6,dist+6,aes.keycode,aes.type_0_128_256); } //byte22-32 加密:和加密后的前11字节异或; for(i=0;i<11;i++) dist[22+i] =src[22+i]^dist[6+i]; //d, byte6-32做前后相关处理,避免全0数据容易猜出,和前一个字节异或,好恢复 for(i=7;i0) dist[5] =tmp; for(i=6;i0) || (src[32]>0) ){ crc_tmp = crc16(src+5,26); if( ((crc_tmp>>8) != src[31]) || ( (crc_tmp&0xff) != src[32]) ) return 0; } } //------------------------------ return 1; } /* * 读取AES config */ static void read_AES_config(void) { unsigned char tmp[8]; platform.e2prom_read(STORE_AES_CONFIG_ADDR,tmp,3); if(tmp[0]== 0xF5){//STORE_FLAG aes.type_0_128_256 =tmp[1]; aes.key_update_flag =tmp[2]; } else{ aes.type_0_128_256 =0; } } /* * 0x61 cmd from sdk *see protocol xxx section yy */ void process_pc_aes_config(const unsigned char *rx_pc) { unsigned char tmp[32]; if(rx_pc[3] ==24){//write config aes.type_0_128_256 =rx_pc[4]; aes.key_update_flag =rx_pc[5]; tmp[0]= 0xF5; tmp[1]= rx_pc[4]; tmp[2]= rx_pc[5]; platform.e2prom_write(STORE_AES_CONFIG_ADDR,tmp,3); } tmp[0]= aes.type_0_128_256; tmp[1]= aes.key_update_flag; user__pc_cmd_ack(0x61,23,tmp,2); } /* *快速配对时 增加aes秘钥的传送; *input :fdata = vote beacon */ void aes_load_fastmatch_data(unsigned char *fdata) { static unsigned char aes_pos=0; // unsigned char i; if(!function.AES__SW) return; if(!aes.type_0_128_256) return; //特殊处理:快速配对下的aes256加密时,byte5都变成0x13; if( base_core.get_log_mode() >3 ) fdata[5] =0x13; aes_pos ^=1; fdata[14] =aes.type_0_128_256; if(aes_pos) fdata[10] = 3; memcpy(fdata+15,aes.keycode+16*aes_pos,16); } /* *更新秘钥,快速配对启动时被调用! */ void aes_keycode_upgrade(void) { unsigned char i; if(!function.AES__SW) return; if(!aes.type_0_128_256) return; if(aes.key_update_flag)return; //判断 更新秘钥的开关 srand(HW_TIMER_Count_get( TIMER5 ));//(TIM5->CNT);//!!否则后面rand生成数字是一样的序列 for(i=0;i