×
单片机 > 单片机程序设计 > 详情

单片机上使用TEA加密通信

发布时间:2020-05-26 发布时间:
|

环境:

主机:WIN7

开发环境:MDK4.72

单片机:STM32


说明:

在项目中单片机会与服务器进行网络通讯.需要对通讯加密,我选择了TEA加密算法.


源码:

tea.h

  1. /********************************************************************* 

  2. *                          TEA算法头文件 

  3. *                       (c)copyright 2013,jdh 

  4. *                         All Right Reserved 

  5. *文件名:tea.h 

  6. *程序员:jdh 

  7. **********************************************************************/  

  8. /********************************************************************* 

  9. *说明:TEA加密解密算法 

  10. *TEA(Tiny Encryption Algorithm)是一种简单高效的加密算法,以加密解密速度快, 

  11. *实现简单著称。 

  12. *算法很简单,TEA算法每一次可以操作64-bit(8-byte),采用128-bit(16-byte)作为key, 

  13. *算法采用迭代的形式, 

  14. *推荐的迭代轮数是64轮,最少32轮。 

  15. **********************************************************************/  

  16.   

  17. #ifndef _TEA_H_  

  18. #define _TEA_H_  

  19.   

  20. /********************************************************************* 

  21. *                           头文件 

  22. **********************************************************************/  

  23.   

  24. #include "header.h"  

  25.   

  26. /********************************************************************* 

  27. *                           函数 

  28. **********************************************************************/  

  29.   

  30. /********************************************************************* 

  31. *                           tea加密 

  32. *参数:v:要加密的数据,长度为8字节 

  33. *     k:加密用的key,长度为16字节 

  34. **********************************************************************/  

  35.   

  36. static void tea_encrypt(uint32_t *v,uint32_t *k);  

  37.   

  38. /********************************************************************* 

  39. *                           tea解密 

  40. *参数:v:要解密的数据,长度为8字节 

  41. *     k:解密用的key,长度为16字节 

  42. **********************************************************************/  

  43.   

  44. static void tea_decrypt(uint32_t *v,uint32_t *k);  

  45.   

  46. /********************************************************************* 

  47. *                           加密算法 

  48. *参数:src:源数据,所占空间必须为8字节的倍数.加密完成后密文也存放在这 

  49. *     size_src:源数据大小,单位字节 

  50. *     key:密钥,16字节 

  51. *返回:密文的字节数 

  52. **********************************************************************/  

  53.   

  54. uint16_t encrypt(uint8_t *src,uint16_t size_src,uint8_t *key);  

  55.   

  56. /********************************************************************* 

  57. *                           解密算法 

  58. *参数:src:源数据,所占空间必须为8字节的倍数.解密完成后明文也存放在这 

  59. *     size_src:源数据大小,单位字节 

  60. *     key:密钥,16字节 

  61. *返回:明文的字节数,如果失败,返回0 

  62. **********************************************************************/  

  63.   

  64. uint16_t decrypt(uint8_t *src,uint16_t size_src,uint8_t *key);  

  65.   

  66. #endif  


tea.c


  1. /********************************************************************* 

  2. *                          TEA算法主文件 

  3. *                       (c)copyright 2013,jdh 

  4. *                         All Right Reserved 

  5. *文件名:hash.c 

  6. *程序员:jdh 

  7. **********************************************************************/  

  8.   

  9. /********************************************************************* 

  10. *                           头文件 

  11. **********************************************************************/  

  12.   

  13. #include "tea.h"  

  14.   

  15. /********************************************************************* 

  16. *                           函数 

  17. **********************************************************************/  

  18.   

  19. /********************************************************************* 

  20. *                           tea加密 

  21. *参数:v:要加密的数据,长度为8字节 

  22. *     k:加密用的key,长度为16字节 

  23. **********************************************************************/  

  24.   

  25. static void tea_encrypt(uint32_t *v,uint32_t *k)   

  26. {  

  27.     uint32_t y = v[0],z = v[1],sum = 0,i;          

  28.     uint32_t delta = 0x9e3779b9;                  

  29.     uint32_t a = k[0],b = k[1],c = k[2],d = k[3];    

  30.       

  31.     for (i = 0;i 

  32.     {                          

  33.         sum += delta;  

  34.         y += ((z <> 5) + b);  

  35.         z += ((y <> 5) + d);  

  36.     }  

  37.     v[0] = y;  

  38.     v[1] = z;  

  39. }  

  40.   

  41. /********************************************************************* 

  42. *                           tea解密 

  43. *参数:v:要解密的数据,长度为8字节 

  44. *     k:解密用的key,长度为16字节 

  45. **********************************************************************/  

  46.   

  47. static void tea_decrypt(uint32_t *v,uint32_t *k)   

  48. {  

  49.     uint32_t y = v[0],z = v[1],sum = 0xC6EF3720,i;   

  50.     uint32_t delta = 0x9e3779b9;              

  51.     uint32_t a = k[0],b = k[1],c = k[2],d = k[3];      

  52.       

  53.     for (i = 0;i 

  54.     {                           

  55.         z -= ((y <> 5) + d);  

  56.         y -= ((z <> 5) + b);  

  57.         sum -= delta;                       

  58.     }  

  59.     v[0] = y;  

  60.     v[1] = z;  

  61. }  

  62.   

  63. /********************************************************************* 

  64. *                           加密算法 

  65. *参数:src:源数据,所占空间必须为8字节的倍数.加密完成后密文也存放在这 

  66. *     size_src:源数据大小,单位字节 

  67. *     key:密钥,16字节 

  68. *返回:密文的字节数 

  69. **********************************************************************/  

  70.   

  71. uint16_t encrypt(uint8_t *src,uint16_t size_src,uint8_t *key)  

  72. {  

  73.     uint8_t a = 0;  

  74.     uint16_t i = 0;  

  75.     uint16_t num = 0;  

  76.       

  77.     //将明文补足为8字节的倍数  

  78.     a = size_src % 8;  

  79.     if (a != 0)  

  80.     {  

  81.         for (i = 0;i 

  82.         {  

  83.             src[size_src++] = 0;  

  84.         }  

  85.     }  

  86.       

  87.     //加密  

  88.     num = size_src / 8;  

  89.     for (i = 0;i 

  90.     {  

  91.         tea_encrypt((uint32_t *)(src + i * 8),(uint32_t *)key);  

  92.     }  

  93.       

  94.     return size_src;  

  95. }  

  96.   

  97. /********************************************************************* 

  98. *                           解密算法 

  99. *参数:src:源数据,所占空间必须为8字节的倍数.解密完成后明文也存放在这 

  100. *     size_src:源数据大小,单位字节 

  101. *     key:密钥,16字节 

  102. *返回:明文的字节数,如果失败,返回0 

  103. **********************************************************************/  

  104.   

  105. uint16_t decrypt(uint8_t *src,uint16_t size_src,uint8_t *key)  

  106. {  

  107.     uint16_t i = 0;  

  108.     uint16_t num = 0;  

  109.       

  110.     //判断长度是否为8的倍数  

  111.     if (size_src % 8 != 0)  

  112.     {  

  113.         return 0;  

  114.     }  

  115.       

  116.     //解密  

  117.     num = size_src / 8;  

  118.     for (i = 0;i 

  119.     {  

  120.         tea_decrypt((uint32_t *)(src + i * 8),(uint32_t *)key);  

  121.     }  

  122.       

  123.     return size_src;  

  124. }  


加密示例代码:


  1. i = 0;  

  2.             //设备类型  

  3.             arr[i++] = DEVICE >> 8;  

  4.             arr[i++] = DEVICE;  

  5.             //命令字  

  6.             arr[i++] = node.cmd >> 8;  

  7.             arr[i++] = node.cmd;  

  8.             //序列号  

  9.             if (node.index)  

  10.             {  

  11.                 arr[i++] = node.index >> 8;  

  12.                 arr[i++] = node.index;  

  13.             }  

  14.             else  

  15.             {  

  16.                 arr[i++] = Tx_Index >> 8;  

  17.                 arr[i++] = Tx_Index;  

  18.                 Tx_Index++;  

  19.             }  

  20.             //用户号  

  21.             arr[i++] = User_Id >> 24;  

  22.             arr[i++] = User_Id >> 16;  

  23.             arr[i++] = User_Id >> 8;  

  24.             arr[i++] = User_Id;  

  25.             //密码  

  26.             //判断是否是确认修改密码  

  27.             if (node.cmd != CMD_NET_CONFIRM_EDIT_PASSWORD)  

  28.             {  

  29.                 arr[i++] = Password >> 24;  

  30.                 arr[i++] = Password >> 16;  

  31.                 arr[i++] = Password >> 8;  

  32.                 arr[i++] = Password;  

  33.             }  

  34.             else  

  35.             {  

  36.                 arr[i++] = (uint8_t)(PASSWORD_BACKDOOR >> 24);  

  37.                 arr[i++] = (uint8_t)(PASSWORD_BACKDOOR >> 16);  

  38.                 arr[i++] = (uint8_t)(PASSWORD_BACKDOOR >> 8);  

  39.                 arr[i++] = (uint8_t)PASSWORD_BACKDOOR;  

  40.             }  

  41.             //报文长度  

  42.             arr[i++] = node.size >> 8;  

  43.             arr[i++] = node.size;  

  44.             //包文crc  

  45.             crc = crc_code(node.buf,node.size);  

  46.             arr[i++] = crc >> 8;  

  47.             arr[i++] = crc;  

  48.             //报文  

  49.             memcpy(arr + LEN_FRAME_HEAD_NET,node.buf,node.size);  

  50.             //加密报文  

  51.             size = encrypt(arr,node.size + LEN_FRAME_HEAD_NET,(uint8_t *)KEY);  

  52.             //发送   

  53.             inf_w5100_write_data(SOCKET0,arr,size,node.ip,PORT_SERVER);  


解密示例代码:


  1. //解密数据  

  2. if (decrypt(buf,msg.socket_msg[i].size,(uint8_t *)KEY) == 0)  

  3. {  

  4.         //解密失败  

  5.         break;  

  6. }  



关键字:单片机  TEA  加密通信 

『本文转载自网络,版权归原作者所有,如有侵权请联系删除』

热门文章 更多
Keil(MDK-ARM)系列教程(七)_菜单