目录
一. 前言
二. 进制转换和格式控制
十进制转为十六进制函数
十六进制字符串转换成十六进制数组
把字符串中的空格符号删除
比较两个数组之间是否相同
命令响应数据中查找关键字
16位数据高低字节互换
三. 算法类
MD5
CRC效验
BBC效验
四. 完整文件
tool.c
tool.h
搞嵌入式开发的小伙伴,平时主要就是用到的C语言,当然我们很多时候再处理数据的时候需要用到一下进制的转换和一些效验方法,今天我整理了一些我常用的一些工具类分享给大家,希望对大家有所帮助
/*********************************************************************************
* @Function : 十进制转为十六进制函数
* @Input : <*value>,为要被转换的十进制
* : ,转换完成保存的十六进制的位置
* : ,参数为转换后十六进制的长度
* @Output : None
* @Return : None
* @Others : None
* @Date : 2022-10-10
**********************************************************************************/
void NumToHex(U32 value, char buffer[], int length)
{
U32 i=(sizeof(unsigned int)*2);
U32 temp;
int j=0;
while(i--)
{
temp = (value&(0xf<<(4*i)))>>(4*i);
if(temp>9)
buffer[j] = 'A'+temp-10;
else
buffer[j] = '0'+temp;
j++;
}
buffer[length] = '\0';
}
/*********************************************************************************
* @Function : 十六进制字符串转换成十六进制数组
* @Input : <*str>,字符串输入
* : <*out>,十六进制数组输出缓冲区
* : <*outlen>,十六进制数组长度
* @Output : None
* @Return : 数组长度
* @Others : 十六进制数组长度
* @Date : 2022-08-23
**********************************************************************************/
U32 StringToHex(char *str, U8 *out, U32 *outlen)
{
char *p = str;
char high = 0, low = 0;
int tmplen = strlen(p), cnt = 0;
tmplen = strlen(p);
while(cnt < (tmplen / 2))
{
high = ((*p > '9') && ((*p <= 'F') || (*p <= 'f'))) ? *p - 48 - 7 : *p - 48;
low = (*(++ p) > '9' && ((*p <= 'F') || (*p <= 'f'))) ? *(p) - 48 - 7 : *(p) - 48;
out[cnt] = ((high & 0x0f) << 4 | (low & 0x0f));
p ++;
cnt ++;
}
if(tmplen % 2 != 0) out[cnt] = ((*p > '9') && ((*p <= 'F') || (*p <= 'f'))) ? *p - 48 - 7 : *p - 48;
if(outlen != NULL) *outlen = tmplen / 2 + tmplen % 2;
return tmplen / 2 + tmplen % 2;
}
/*********************************************************************************
* @Function : 把字符串中的空格符号删除
* @Input : ,字符串内容 如:{123 abcA BC}
* @Output : None
* @Return : 返回 返回的hex内容
* @Others : None
* @Date : 2022-06-30
**********************************************************************************/
char * delete_str_blank(char *str)
{
char *p=str;
int i=0;
while(*p)
{
if(*p!=' ')
str[i++]=*p;
p++;
}
str[i]='\0';
return str;
}
/*********************************************************************************
* @Function : 比较两个数组之间是否相同
* @Input : ,比较数组
* : ,被比较数组
* @Output : None
* @Return : 返回两数组数据相同,返回两数组数据不同
* @Others : None
* @Date : 2022-08-26
**********************************************************************************/
mySta Compare_Array_Data(U8 Array1[256], U8 Array2[256])
{
U8 i = 0,j = 0;
U8 flag = 0;
U8 Array1_len =sizeof((const char*) Array1);//获取数组一长度
U8 Array2_len =sizeof((const char*) Array1);//获取数组二长度
if(Array1_len == Array2_len){
for(i=0; i
/*********************************************************************************
* @Function : 命令响应数据中查找关键字
* @Input : ,字符串内容
* : ,被检索的关键字
* @Output : None
* @Return : 返回<1>找到关键字,返回<0>未找到
* @Others : None
* @Date : 2022-08-23
**********************************************************************************/
mySta find_keyword_matching(U8 *UartRecvBuf, U8 *keyword)
{
/* 检索检索到关键词 */
if (( bool ) strstr ( (char*)UartRecvBuf, (char*)keyword))
{
return MY_SUCCESSFUL;
}
return MY_FAIL;
}
/*********************************************************************************
* @Function : 16位数据高低字节互换
* @Input : pData,数据
* : size,数据的大小 单位字节
* @Output : None
* @Return : None
* @Others : None
* : 同步设备寄存器中的信息
* @Date : 2022-04-05
**********************************************************************************/
void data_max_to_min( U16 *pData, U8 size )
{
U8 i = 0;
U16 tempData = 0 ;
for( i = 0; i < size / 2; i ++ )
{
tempData = (U16)(*( pData + i ) >> 8 );//获取高字节
tempData |= (U16)(*( pData + i ) << 8 );//获取低字节
*( pData + i ) = tempData;
}
}
md5.h
#ifndef __MD5_H
#define __MD5_H
typedef struct
{
unsigned int count[2];
unsigned int state[4];
unsigned char buffer[64];
}MD5_CTX;
#define F(x,y,z) ((x & y) | (~x & z))
#define G(x,y,z) ((x & z) | (y & ~z))
#define H(x,y,z) (x^y^z)
#define I(x,y,z) (y ^ (x | ~z))
#define ROTATE_LEFT(x,n) ((x << n) | (x >> (32-n)))
#define FF(a,b,c,d,x,s,ac) \
{ \
a += F(b,c,d) + x + ac; \
a = ROTATE_LEFT(a,s); \
a += b; \
}
#define GG(a,b,c,d,x,s,ac) \
{ \
a += G(b,c,d) + x + ac; \
a = ROTATE_LEFT(a,s); \
a += b; \
}
#define HH(a,b,c,d,x,s,ac) \
{ \
a += H(b,c,d) + x + ac; \
a = ROTATE_LEFT(a,s); \
a += b; \
}
#define II(a,b,c,d,x,s,ac) \
{ \
a += I(b,c,d) + x + ac; \
a = ROTATE_LEFT(a,s); \
a += b; \
}
void MD5Init(MD5_CTX *context);
void MD5Update(MD5_CTX *context,unsigned char *input,unsigned int inputlen);
void MD5Final(MD5_CTX *context,unsigned char digest[16]);
void MD5Transform(unsigned int state[4],unsigned char block[64]);
void MD5Encode(unsigned char *output,unsigned int *input,unsigned int len);
void MD5Decode(unsigned int *output,unsigned char *input,unsigned int len);
#endif /* __MD5_H */
md5.c
#include
#include "string.h"
#include "md5.h"
unsigned char PADDING[]={0x80,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,
0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0};
/********************************************************
* 名 称: MD5Init()
* 功 能: 初始化MD5结构体
* 入口参数:
context:要初始化的MD5结构体
* 出口参数: 无
*********************************************************/
void MD5Init(MD5_CTX *context)
{
context->count[0] = 0;
context->count[1] = 0;
context->state[0] = 0x67452301;
context->state[1] = 0xEFCDAB89;
context->state[2] = 0x98BADCFE;
context->state[3] = 0x10325476;
}
/*********************************************************
* 名 称: MD5Update()
* 功 能: 将要加密的信息传递给初始化过的MD5结构体,无返回值
* 入口参数:
context:初始化过了的MD5结构体
input:需要加密的信息,可以任意长度
inputLen:指定input的长度
* 出口参数: 无
*********************************************************/
void MD5Update(MD5_CTX *context,unsigned char *input,unsigned int inputlen)
{
unsigned int i = 0,index = 0,partlen = 0;
index = (context->count[0] >> 3) & 0x3F;
partlen = 64 - index;
context->count[0] += inputlen << 3;
if(context->count[0] < (inputlen << 3))
context->count[1]++;
context->count[1] += inputlen >> 29;
if(inputlen >= partlen)
{
memcpy(&context->buffer[index],input,partlen);
MD5Transform(context->state,context->buffer);
for(i = partlen;i+64 <= inputlen;i+=64)
MD5Transform(context->state,&input[i]);
index = 0;
}
else
{
i = 0;
}
memcpy(&context->buffer[index],&input[i],inputlen-i);
}
/*********************************************************
* 名 称: MD5Update()
* 功 能: 将加密结果存储到,无返回值
* 入口参数:
context:初始化过了的MD5结构体
digest :加密过的结果
* 出口参数: 无
*********************************************************/
void MD5Final(MD5_CTX *context,unsigned char digest[16])
{
unsigned int index = 0,padlen = 0;
unsigned char bits[8];
index = (context->count[0] >> 3) & 0x3F;
padlen = (index < 56)?(56-index):(120-index);
MD5Encode(bits,context->count,8);
MD5Update(context,PADDING,padlen);
MD5Update(context,bits,8);
MD5Encode(digest,context->state,16);
}
void MD5Encode(unsigned char *output,unsigned int *input,unsigned int len)
{
unsigned int i = 0,j = 0;
while(j < len)
{
output[j] = input[i] & 0xFF;
output[j+1] = (input[i] >> 8) & 0xFF;
output[j+2] = (input[i] >> 16) & 0xFF;
output[j+3] = (input[i] >> 24) & 0xFF;
i++;
j+=4;
}
}
void MD5Decode(unsigned int *output,unsigned char *input,unsigned int len)
{
unsigned int i = 0,j = 0;
while(j < len)
{
output[i] = (input[j]) |
(input[j+1] << 8) |
(input[j+2] << 16) |
(input[j+3] << 24);
i++;
j+=4;
}
}
void MD5Transform(unsigned int state[4],unsigned char block[64])
{
unsigned int a = state[0];
unsigned int b = state[1];
unsigned int c = state[2];
unsigned int d = state[3];
unsigned int x[64];
MD5Decode(x,block,64);
FF(a, b, c, d, x[ 0], 7, 0xd76aa478); /* 1 */
FF(d, a, b, c, x[ 1], 12, 0xe8c7b756); /* 2 */
FF(c, d, a, b, x[ 2], 17, 0x242070db); /* 3 */
FF(b, c, d, a, x[ 3], 22, 0xc1bdceee); /* 4 */
FF(a, b, c, d, x[ 4], 7, 0xf57c0faf); /* 5 */
FF(d, a, b, c, x[ 5], 12, 0x4787c62a); /* 6 */
FF(c, d, a, b, x[ 6], 17, 0xa8304613); /* 7 */
FF(b, c, d, a, x[ 7], 22, 0xfd469501); /* 8 */
FF(a, b, c, d, x[ 8], 7, 0x698098d8); /* 9 */
FF(d, a, b, c, x[ 9], 12, 0x8b44f7af); /* 10 */
FF(c, d, a, b, x[10], 17, 0xffff5bb1); /* 11 */
FF(b, c, d, a, x[11], 22, 0x895cd7be); /* 12 */
FF(a, b, c, d, x[12], 7, 0x6b901122); /* 13 */
FF(d, a, b, c, x[13], 12, 0xfd987193); /* 14 */
FF(c, d, a, b, x[14], 17, 0xa679438e); /* 15 */
FF(b, c, d, a, x[15], 22, 0x49b40821); /* 16 */
/* Round 2 */
GG(a, b, c, d, x[ 1], 5, 0xf61e2562); /* 17 */
GG(d, a, b, c, x[ 6], 9, 0xc040b340); /* 18 */
GG(c, d, a, b, x[11], 14, 0x265e5a51); /* 19 */
GG(b, c, d, a, x[ 0], 20, 0xe9b6c7aa); /* 20 */
GG(a, b, c, d, x[ 5], 5, 0xd62f105d); /* 21 */
GG(d, a, b, c, x[10], 9, 0x2441453); /* 22 */
GG(c, d, a, b, x[15], 14, 0xd8a1e681); /* 23 */
GG(b, c, d, a, x[ 4], 20, 0xe7d3fbc8); /* 24 */
GG(a, b, c, d, x[ 9], 5, 0x21e1cde6); /* 25 */
GG(d, a, b, c, x[14], 9, 0xc33707d6); /* 26 */
GG(c, d, a, b, x[ 3], 14, 0xf4d50d87); /* 27 */
GG(b, c, d, a, x[ 8], 20, 0x455a14ed); /* 28 */
GG(a, b, c, d, x[13], 5, 0xa9e3e905); /* 29 */
GG(d, a, b, c, x[ 2], 9, 0xfcefa3f8); /* 30 */
GG(c, d, a, b, x[ 7], 14, 0x676f02d9); /* 31 */
GG(b, c, d, a, x[12], 20, 0x8d2a4c8a); /* 32 */
/* Round 3 */
HH(a, b, c, d, x[ 5], 4, 0xfffa3942); /* 33 */
HH(d, a, b, c, x[ 8], 11, 0x8771f681); /* 34 */
HH(c, d, a, b, x[11], 16, 0x6d9d6122); /* 35 */
HH(b, c, d, a, x[14], 23, 0xfde5380c); /* 36 */
HH(a, b, c, d, x[ 1], 4, 0xa4beea44); /* 37 */
HH(d, a, b, c, x[ 4], 11, 0x4bdecfa9); /* 38 */
HH(c, d, a, b, x[ 7], 16, 0xf6bb4b60); /* 39 */
HH(b, c, d, a, x[10], 23, 0xbebfbc70); /* 40 */
HH(a, b, c, d, x[13], 4, 0x289b7ec6); /* 41 */
HH(d, a, b, c, x[ 0], 11, 0xeaa127fa); /* 42 */
HH(c, d, a, b, x[ 3], 16, 0xd4ef3085); /* 43 */
HH(b, c, d, a, x[ 6], 23, 0x4881d05); /* 44 */
HH(a, b, c, d, x[ 9], 4, 0xd9d4d039); /* 45 */
HH(d, a, b, c, x[12], 11, 0xe6db99e5); /* 46 */
HH(c, d, a, b, x[15], 16, 0x1fa27cf8); /* 47 */
HH(b, c, d, a, x[ 2], 23, 0xc4ac5665); /* 48 */
/* Round 4 */
II(a, b, c, d, x[ 0], 6, 0xf4292244); /* 49 */
II(d, a, b, c, x[ 7], 10, 0x432aff97); /* 50 */
II(c, d, a, b, x[14], 15, 0xab9423a7); /* 51 */
II(b, c, d, a, x[ 5], 21, 0xfc93a039); /* 52 */
II(a, b, c, d, x[12], 6, 0x655b59c3); /* 53 */
II(d, a, b, c, x[ 3], 10, 0x8f0ccc92); /* 54 */
II(c, d, a, b, x[10], 15, 0xffeff47d); /* 55 */
II(b, c, d, a, x[ 1], 21, 0x85845dd1); /* 56 */
II(a, b, c, d, x[ 8], 6, 0x6fa87e4f); /* 57 */
II(d, a, b, c, x[15], 10, 0xfe2ce6e0); /* 58 */
II(c, d, a, b, x[ 6], 15, 0xa3014314); /* 59 */
II(b, c, d, a, x[13], 21, 0x4e0811a1); /* 60 */
II(a, b, c, d, x[ 4], 6, 0xf7537e82); /* 61 */
II(d, a, b, c, x[11], 10, 0xbd3af235); /* 62 */
II(c, d, a, b, x[ 2], 15, 0x2ad7d2bb); /* 63 */
II(b, c, d, a, x[ 9], 21, 0xeb86d391); /* 64 */
state[0] += a;
state[1] += b;
state[2] += c;
state[3] += d;
}
循环校验码(CRC码):是数据通信领域中最常用的一种差错校验码,其特征是信息字段和校验字段的长度可以任意选定。
//用于CRC校验
const U8 auchCRCHi[]={
0x00, 0xC1, 0x81, 0x40, 0x01, 0xC0, 0x80, 0x41, 0x01, 0xC0, 0x80, 0x41, 0x00, 0xC1, 0x81,
0x40, 0x01, 0xC0, 0x80, 0x41, 0x00, 0xC1, 0x81, 0x40, 0x00, 0xC1, 0x81, 0x40, 0x01, 0xC0,
0x80, 0x41, 0x01, 0xC0, 0x80, 0x41, 0x00, 0xC1, 0x81, 0x40, 0x00, 0xC1, 0x81, 0x40, 0x01,
0xC0, 0x80, 0x41, 0x00, 0xC1, 0x81, 0x40, 0x01, 0xC0, 0x80, 0x41, 0x01, 0xC0, 0x80, 0x41,
0x00, 0xC1, 0x81, 0x40, 0x01, 0xC0, 0x80, 0x41, 0x00, 0xC1, 0x81, 0x40, 0x00, 0xC1, 0x81,
0x40, 0x01, 0xC0, 0x80, 0x41, 0x00, 0xC1, 0x81, 0x40, 0x01, 0xC0, 0x80, 0x41, 0x01, 0xC0,
0x80, 0x41, 0x00, 0xC1, 0x81, 0x40, 0x00, 0xC1, 0x81, 0x40, 0x01, 0xC0, 0x80, 0x41, 0x01,
0xC0, 0x80, 0x41, 0x00, 0xC1, 0x81, 0x40, 0x01, 0xC0, 0x80, 0x41, 0x00, 0xC1, 0x81, 0x40,
0x00, 0xC1, 0x81, 0x40, 0x01, 0xC0, 0x80, 0x41, 0x01, 0xC0, 0x80, 0x41, 0x00, 0xC1, 0x81,
0x40, 0x00, 0xC1, 0x81, 0x40, 0x01, 0xC0, 0x80, 0x41, 0x00, 0xC1, 0x81, 0x40, 0x01, 0xC0,
0x80, 0x41, 0x01, 0xC0, 0x80, 0x41, 0x00, 0xC1, 0x81, 0x40, 0x00, 0xC1, 0x81, 0x40, 0x01,
0xC0, 0x80, 0x41, 0x01, 0xC0, 0x80, 0x41, 0x00, 0xC1, 0x81, 0x40, 0x01, 0xC0, 0x80, 0x41,
0x00, 0xC1, 0x81, 0x40, 0x00, 0xC1, 0x81, 0x40, 0x01, 0xC0, 0x80, 0x41, 0x00, 0xC1, 0x81,
0x40, 0x01, 0xC0, 0x80, 0x41, 0x01, 0xC0, 0x80, 0x41, 0x00, 0xC1, 0x81, 0x40, 0x01, 0xC0,
0x80, 0x41, 0x00, 0xC1, 0x81, 0x40, 0x00, 0xC1, 0x81, 0x40, 0x01, 0xC0, 0x80, 0x41, 0x01,
0xC0, 0x80, 0x41, 0x00, 0xC1, 0x81, 0x40, 0x00, 0xC1, 0x81, 0x40, 0x01, 0xC0, 0x80, 0x41,
0x00, 0xC1, 0x81, 0x40, 0x01, 0xC0, 0x80, 0x41, 0x01, 0xC0, 0x80, 0x41, 0x00, 0xC1, 0x81,
0x40};
const U8 auchCRCLo[]=
{
0x00, 0xC0, 0xC1, 0x01, 0xC3, 0x03, 0x02, 0xC2, 0xC6, 0x06, 0x07, 0xC7, 0x05, 0xC5, 0xC4,
0x04, 0xCC, 0x0C, 0x0D, 0xCD, 0x0F, 0xCF, 0xCE, 0x0E, 0x0A, 0xCA, 0xCB, 0x0B, 0xC9, 0x09,
0x08, 0xC8, 0xD8, 0x18, 0x19, 0xD9, 0x1B, 0xDB, 0xDA, 0x1A, 0x1E, 0xDE, 0xDF, 0x1F, 0xDD,
0x1D, 0x1C, 0xDC, 0x14, 0xD4, 0xD5, 0x15, 0xD7, 0x17, 0x16, 0xD6, 0xD2, 0x12, 0x13, 0xD3,
0x11, 0xD1, 0xD0, 0x10, 0xF0, 0x30, 0x31, 0xF1, 0x33, 0xF3, 0xF2, 0x32, 0x36, 0xF6, 0xF7,
0x37, 0xF5, 0x35, 0x34, 0xF4, 0x3C, 0xFC, 0xFD, 0x3D, 0xFF, 0x3F, 0x3E, 0xFE, 0xFA, 0x3A,
0x3B, 0xFB, 0x39, 0xF9, 0xF8, 0x38, 0x28, 0xE8, 0xE9, 0x29, 0xEB, 0x2B, 0x2A, 0xEA, 0xEE,
0x2E, 0x2F, 0xEF, 0x2D, 0xED, 0xEC, 0x2C, 0xE4, 0x24, 0x25, 0xE5, 0x27, 0xE7, 0xE6, 0x26,
0x22, 0xE2, 0xE3, 0x23, 0xE1, 0x21, 0x20, 0xE0, 0xA0, 0x60, 0x61, 0xA1, 0x63, 0xA3, 0xA2,
0x62, 0x66, 0xA6, 0xA7, 0x67, 0xA5, 0x65, 0x64, 0xA4, 0x6C, 0xAC, 0xAD, 0x6D, 0xAF, 0x6F,
0x6E, 0xAE, 0xAA, 0x6A, 0x6B, 0xAB, 0x69, 0xA9, 0xA8, 0x68, 0x78, 0xB8, 0xB9, 0x79, 0xBB,
0x7B, 0x7A, 0xBA, 0xBE, 0x7E, 0x7F, 0xBF, 0x7D, 0xBD, 0xBC, 0x7C, 0xB4, 0x74, 0x75, 0xB5,
0x77, 0xB7, 0xB6, 0x76, 0x72, 0xB2, 0xB3, 0x73, 0xB1, 0x71, 0x70, 0xB0, 0x50, 0x90, 0x91,
0x51, 0x93, 0x53, 0x52, 0x92, 0x96, 0x56, 0x57, 0x97, 0x55, 0x95, 0x94, 0x54, 0x9C, 0x5C,
0x5D, 0x9D, 0x5F, 0x9F, 0x9E, 0x5E, 0x5A, 0x9A, 0x9B, 0x5B, 0x99, 0x59, 0x58, 0x98, 0x88,
0x48, 0x49, 0x89, 0x4B, 0x8B, 0x8A, 0x4A, 0x4E, 0x8E, 0x8F, 0x4F, 0x8D, 0x4D, 0x4C, 0x8C,
0x44, 0x84, 0x85, 0x45, 0x87, 0x47, 0x46, 0x86, 0x82, 0x42, 0x43, 0x83, 0x41, 0x81, 0x80,
0x40
};
/*********************************************************************************
* @Function : 计算数据的CRC校验值
* @Input : buf,将计算CRC校验的数据
* : len,目标数据长度
* @Output : None
* @Return : None
* @Others : None
* @Date : 2022-03-30
**********************************************************************************/
U16 Chkcrc( U8 *buf, U16 len )
{
U8 uchCRCHi=0xff;
U8 uchCRCLo=0xff;
U16 uindex;
U16 uwModbus_back;
while( len-- )
{
uindex = uchCRCHi ^ *buf++;
uchCRCHi = uchCRCLo ^ auchCRCHi[uindex];
uchCRCLo = auchCRCLo[ uindex ];
}
uwModbus_back = uchCRCHi << 8 | uchCRCLo;
return( uwModbus_back );
}
BCC(Block Check Character//信息组校验码),因校验码是将所有的数据异或得出结果,故称为异或校验。具体算法(将每一个字节的数据,一般是两个16进制的字符,进行异或后即得到校验码)
/*********************************************************************************
* @Function : 计算数据的BBC校验数据
* @Input : initData,初始校验值
* : pdata,需要计算的数据开始地址
* : len,数据长度
* @Output : None
* @Return : bcc_check_data
* @Others : None
* @Date : 2022-03-04
**********************************************************************************/
U8 bcc_check(U8 bcc_check_data,U8 *Pdata, U16 len)
{
while(len)
{
bcc_check_data ^= (*Pdata);
--len;
++Pdata;
}
return bcc_check_data;
}
#include "tool.h"
#include
#include
#include
#include
#include
/********************************************************************************
* @file tool.c
* @function 工具类
* @brief 系统通用
* @attention 该文件主要提供一下封装好了的工具类,例如文字查询,CRC算法等
* @version V1.0
* @Author HR
* @date 2022/08/05
********************************************************************************/
//用于CRC校验
const U8 auchCRCHi[]={
0x00, 0xC1, 0x81, 0x40, 0x01, 0xC0, 0x80, 0x41, 0x01, 0xC0, 0x80, 0x41, 0x00, 0xC1, 0x81,
0x40, 0x01, 0xC0, 0x80, 0x41, 0x00, 0xC1, 0x81, 0x40, 0x00, 0xC1, 0x81, 0x40, 0x01, 0xC0,
0x80, 0x41, 0x01, 0xC0, 0x80, 0x41, 0x00, 0xC1, 0x81, 0x40, 0x00, 0xC1, 0x81, 0x40, 0x01,
0xC0, 0x80, 0x41, 0x00, 0xC1, 0x81, 0x40, 0x01, 0xC0, 0x80, 0x41, 0x01, 0xC0, 0x80, 0x41,
0x00, 0xC1, 0x81, 0x40, 0x01, 0xC0, 0x80, 0x41, 0x00, 0xC1, 0x81, 0x40, 0x00, 0xC1, 0x81,
0x40, 0x01, 0xC0, 0x80, 0x41, 0x00, 0xC1, 0x81, 0x40, 0x01, 0xC0, 0x80, 0x41, 0x01, 0xC0,
0x80, 0x41, 0x00, 0xC1, 0x81, 0x40, 0x00, 0xC1, 0x81, 0x40, 0x01, 0xC0, 0x80, 0x41, 0x01,
0xC0, 0x80, 0x41, 0x00, 0xC1, 0x81, 0x40, 0x01, 0xC0, 0x80, 0x41, 0x00, 0xC1, 0x81, 0x40,
0x00, 0xC1, 0x81, 0x40, 0x01, 0xC0, 0x80, 0x41, 0x01, 0xC0, 0x80, 0x41, 0x00, 0xC1, 0x81,
0x40, 0x00, 0xC1, 0x81, 0x40, 0x01, 0xC0, 0x80, 0x41, 0x00, 0xC1, 0x81, 0x40, 0x01, 0xC0,
0x80, 0x41, 0x01, 0xC0, 0x80, 0x41, 0x00, 0xC1, 0x81, 0x40, 0x00, 0xC1, 0x81, 0x40, 0x01,
0xC0, 0x80, 0x41, 0x01, 0xC0, 0x80, 0x41, 0x00, 0xC1, 0x81, 0x40, 0x01, 0xC0, 0x80, 0x41,
0x00, 0xC1, 0x81, 0x40, 0x00, 0xC1, 0x81, 0x40, 0x01, 0xC0, 0x80, 0x41, 0x00, 0xC1, 0x81,
0x40, 0x01, 0xC0, 0x80, 0x41, 0x01, 0xC0, 0x80, 0x41, 0x00, 0xC1, 0x81, 0x40, 0x01, 0xC0,
0x80, 0x41, 0x00, 0xC1, 0x81, 0x40, 0x00, 0xC1, 0x81, 0x40, 0x01, 0xC0, 0x80, 0x41, 0x01,
0xC0, 0x80, 0x41, 0x00, 0xC1, 0x81, 0x40, 0x00, 0xC1, 0x81, 0x40, 0x01, 0xC0, 0x80, 0x41,
0x00, 0xC1, 0x81, 0x40, 0x01, 0xC0, 0x80, 0x41, 0x01, 0xC0, 0x80, 0x41, 0x00, 0xC1, 0x81,
0x40};
const U8 auchCRCLo[]=
{
0x00, 0xC0, 0xC1, 0x01, 0xC3, 0x03, 0x02, 0xC2, 0xC6, 0x06, 0x07, 0xC7, 0x05, 0xC5, 0xC4,
0x04, 0xCC, 0x0C, 0x0D, 0xCD, 0x0F, 0xCF, 0xCE, 0x0E, 0x0A, 0xCA, 0xCB, 0x0B, 0xC9, 0x09,
0x08, 0xC8, 0xD8, 0x18, 0x19, 0xD9, 0x1B, 0xDB, 0xDA, 0x1A, 0x1E, 0xDE, 0xDF, 0x1F, 0xDD,
0x1D, 0x1C, 0xDC, 0x14, 0xD4, 0xD5, 0x15, 0xD7, 0x17, 0x16, 0xD6, 0xD2, 0x12, 0x13, 0xD3,
0x11, 0xD1, 0xD0, 0x10, 0xF0, 0x30, 0x31, 0xF1, 0x33, 0xF3, 0xF2, 0x32, 0x36, 0xF6, 0xF7,
0x37, 0xF5, 0x35, 0x34, 0xF4, 0x3C, 0xFC, 0xFD, 0x3D, 0xFF, 0x3F, 0x3E, 0xFE, 0xFA, 0x3A,
0x3B, 0xFB, 0x39, 0xF9, 0xF8, 0x38, 0x28, 0xE8, 0xE9, 0x29, 0xEB, 0x2B, 0x2A, 0xEA, 0xEE,
0x2E, 0x2F, 0xEF, 0x2D, 0xED, 0xEC, 0x2C, 0xE4, 0x24, 0x25, 0xE5, 0x27, 0xE7, 0xE6, 0x26,
0x22, 0xE2, 0xE3, 0x23, 0xE1, 0x21, 0x20, 0xE0, 0xA0, 0x60, 0x61, 0xA1, 0x63, 0xA3, 0xA2,
0x62, 0x66, 0xA6, 0xA7, 0x67, 0xA5, 0x65, 0x64, 0xA4, 0x6C, 0xAC, 0xAD, 0x6D, 0xAF, 0x6F,
0x6E, 0xAE, 0xAA, 0x6A, 0x6B, 0xAB, 0x69, 0xA9, 0xA8, 0x68, 0x78, 0xB8, 0xB9, 0x79, 0xBB,
0x7B, 0x7A, 0xBA, 0xBE, 0x7E, 0x7F, 0xBF, 0x7D, 0xBD, 0xBC, 0x7C, 0xB4, 0x74, 0x75, 0xB5,
0x77, 0xB7, 0xB6, 0x76, 0x72, 0xB2, 0xB3, 0x73, 0xB1, 0x71, 0x70, 0xB0, 0x50, 0x90, 0x91,
0x51, 0x93, 0x53, 0x52, 0x92, 0x96, 0x56, 0x57, 0x97, 0x55, 0x95, 0x94, 0x54, 0x9C, 0x5C,
0x5D, 0x9D, 0x5F, 0x9F, 0x9E, 0x5E, 0x5A, 0x9A, 0x9B, 0x5B, 0x99, 0x59, 0x58, 0x98, 0x88,
0x48, 0x49, 0x89, 0x4B, 0x8B, 0x8A, 0x4A, 0x4E, 0x8E, 0x8F, 0x4F, 0x8D, 0x4D, 0x4C, 0x8C,
0x44, 0x84, 0x85, 0x45, 0x87, 0x47, 0x46, 0x86, 0x82, 0x42, 0x43, 0x83, 0x41, 0x81, 0x80,
0x40
};
/*********************************************************************************
* @Function : 命令响应数据中查找关键字
* @Input : ,字符串内容
* : ,被检索的关键字
* @Output : None
* @Return : 返回<1>找到关键字,返回<0>未找到
* @Others : None
* @Date : 2022-08-23
**********************************************************************************/
mySta find_keyword_matching(U8 *UartRecvBuf, U8 *keyword)
{
/* 检索检索到关键词 */
if (( bool ) strstr ( (char*)UartRecvBuf, (char*)keyword))
{
return MY_SUCCESSFUL;
}
return MY_FAIL;
}
/*********************************************************************************
* @Function : 比较两个数组之间是否相同
* @Input : ,比较数组
* : ,被比较数组
* @Output : None
* @Return : 返回两数组数据相同,返回两数组数据不同
* @Others : None
* @Date : 2022-08-26
**********************************************************************************/
mySta Compare_Array_Data(U8 Array1[256], U8 Array2[256])
{
U8 i = 0,j = 0;
U8 flag = 0;
U8 Array1_len =sizeof((const char*) Array1);//获取数组一长度
U8 Array2_len =sizeof((const char*) Array1);//获取数组二长度
if(Array1_len == Array2_len){
for(i=0; i,字符串内容 如:{123 abcA BC}
* @Output : None
* @Return : 返回 返回的hex内容
* @Others : None
* @Date : 2022-06-30
**********************************************************************************/
char * delete_str_blank(char *str)
{
char *p=str;
int i=0;
while(*p)
{
if(*p!=' ')
str[i++]=*p;
p++;
}
str[i]='\0';
return str;
}
/*********************************************************************************
* @Function : 十进制转为十六进制函数
* @Input : <*value>,为要被转换的十进制
* : ,转换完成保存的十六进制的位置
* : ,参数为转换后十六进制的长度
* @Output : None
* @Return : None
* @Others : None
* @Date : 2022-10-10
**********************************************************************************/
void NumToHex(U32 value, char buffer[], int length)
{
U32 i=(sizeof(unsigned int)*2);
U32 temp;
int j=0;
while(i--)
{
temp = (value&(0xf<<(4*i)))>>(4*i);
if(temp>9)
buffer[j] = 'A'+temp-10;
else
buffer[j] = '0'+temp;
j++;
}
buffer[length] = '\0';
}
/*********************************************************************************
* @Function : 十六进制字符串转换成十六进制数组
* @Input : <*str>,字符串输入
* : <*out>,十六进制数组输出缓冲区
* : <*outlen>,十六进制数组长度
* @Output : None
* @Return : 数组长度
* @Others : 十六进制数组长度
* @Date : 2022-08-23
**********************************************************************************/
U32 StringToHex(char *str, U8 *out, U32 *outlen)
{
char *p = str;
char high = 0, low = 0;
int tmplen = strlen(p), cnt = 0;
tmplen = strlen(p);
while(cnt < (tmplen / 2))
{
high = ((*p > '9') && ((*p <= 'F') || (*p <= 'f'))) ? *p - 48 - 7 : *p - 48;
low = (*(++ p) > '9' && ((*p <= 'F') || (*p <= 'f'))) ? *(p) - 48 - 7 : *(p) - 48;
out[cnt] = ((high & 0x0f) << 4 | (low & 0x0f));
p ++;
cnt ++;
}
if(tmplen % 2 != 0) out[cnt] = ((*p > '9') && ((*p <= 'F') || (*p <= 'f'))) ? *p - 48 - 7 : *p - 48;
if(outlen != NULL) *outlen = tmplen / 2 + tmplen % 2;
return tmplen / 2 + tmplen % 2;
}
/*********************************************************************************
* @Function : 计算数据的CRC校验值
* @Input : buf,将计算CRC校验的数据
* : len,目标数据长度
* @Output : None
* @Return : None
* @Others : None
* @Date : 2022-03-30
**********************************************************************************/
U16 Chkcrc( U8 *buf, U16 len )
{
U8 uchCRCHi=0xff;
U8 uchCRCLo=0xff;
U16 uindex;
U16 uwModbus_back;
while( len-- )
{
uindex = uchCRCHi ^ *buf++;
uchCRCHi = uchCRCLo ^ auchCRCHi[uindex];
uchCRCLo = auchCRCLo[ uindex ];
}
uwModbus_back = uchCRCHi << 8 | uchCRCLo;
return( uwModbus_back );
}
/*********************************************************************************
* @Function : 计算数据的BBC校验数据
* @Input : initData,初始校验值
* : pdata,需要计算的数据开始地址
* : len,数据长度
* @Output : None
* @Return : bcc_check_data
* @Others : None
* @Date : 2022-03-04
**********************************************************************************/
U8 bcc_check(U8 bcc_check_data,U8 *Pdata, U16 len)
{
while(len)
{
bcc_check_data ^= (*Pdata);
--len;
++Pdata;
}
return bcc_check_data;
}
/*********************************************************************************
* @Function : 16位数据高低字节互换
* @Input : pData,数据
* : size,数据的大小 单位字节
* @Output : None
* @Return : None
* @Others : None
* : 同步设备寄存器中的信息
* @Date : 2022-04-05
**********************************************************************************/
void data_max_to_min( U16 *pData, U8 size )
{
U8 i = 0;
U16 tempData = 0 ;
for( i = 0; i < size / 2; i ++ )
{
tempData = (U16)(*( pData + i ) >> 8 );//获取高字节
tempData |= (U16)(*( pData + i ) << 8 );//获取低字节
*( pData + i ) = tempData;
}
}
#ifndef __TOOL_H
#define __TOOL_H
typedef unsigned char U8;
typedef signed char S8;
typedef unsigned short U16;
typedef signed short S16;
typedef unsigned int U32;
typedef signed int S32;
typedef float F32;
/*********************************************************************************
* @Function : 串口日志打印开关
* @Input : PRINTF_TURN_ON=0 ;关闭日志打印模式
* PRINTF_TURN_ON=1 :打开日志打印模式
* @Date : 2022-08-25
**********************************************************************************/
#define PRINTF_TURN_ON 1
/*********************************************************************************
* @Function : 串口2接收日志消息日志打印
* @Input : USARE5_TURN_ON=0 ;关闭日志打印模式
* USARE5_TURN_ON=1 :打开日志打印模式
* @Date : 2022-08-25
**********************************************************************************/
#define USARE2_TURN_ON 1
/*********************************************************************************
* @Function : 串口3接收日志消息日志打印
* @Input : USARE4_TURN_ON=0 ;关闭日志打印模式
* USARE4_TURN_ON=1 :打开日志打印模式
* @Date : 2022-08-25
**********************************************************************************/
#define USARE3_TURN_ON 0
/*********************************************************************************
* @Function : 串口4接收日志消息日志打印
* @Input : USARE4_TURN_ON=0 ;关闭日志打印模式
* USARE4_TURN_ON=1 :打开日志打印模式
* @Date : 2022-08-25
**********************************************************************************/
#define USARE4_TURN_ON 0
/*********************************************************************************
* @Function : 串口5接收日志消息日志打印
* @Input : USARE5_TURN_ON=0 ;关闭日志打印模式
* USARE5_TURN_ON=1 :打开日志打印模式
* @Date : 2022-08-25
**********************************************************************************/
#define USARE5_TURN_ON 1
//自定义使能开关
typedef enum
{
MY_ENABLE,
MY_DISABLE
}myEN;
//自定义布尔类型
typedef enum
{
MY_TRUE,
MY_FALSE
}myBool;
//自定义开关控制类型
typedef enum
{
POWER_ON,
POWER_OFF,
POWER_PAUSE //暂停
}switchEN;
//自定义执行结果类型
typedef enum
{
MY_SUCCESSFUL = 0x01,
MY_FAIL = 0x00
}mySta;
/*********************************************************************************
* @Function : 命令响应数据中查找关键字
* @Input : ,字符串内容
* : ,被检索的关键字
* @Output : None
* @Return : 返回<1>找到关键字,返回<0>未找到
* @Others : None
* @Date : 2022-08-23
**********************************************************************************/
mySta find_keyword_matching(U8 *UartRecvBuf, U8 *keyword);
/*********************************************************************************
* @Function : 比较两个数组之间是否相同
* @Input : ,数组一
* : ,数组二
* @Output : None
* @Return : 返回两数组数据相同,返回两数组数据不同
* @Others : None
* @Date : 2022-08-26
**********************************************************************************/
mySta Compare_Array_Data(U8 Array1[256], U8 Array2[256]);
/*********************************************************************************
* @Function : 把字符串中的空格符号删除
* @Input : ,字符串内容 如:{123 abcA BC}
* @Output : None
* @Return : 返回 返回的hex内容
* @Others : None
* @Date : 2022-06-30
**********************************************************************************/
char * delete_str_blank(char *str);
/*********************************************************************************
* @Function : 十六进制字符串转换成十六进制数组
* @Input : <*str>,字符串输入
* : <*out>,十六进制数组输出缓冲区
* : <*outlen>,十六进制数组长度
* @Output : None
* @Return : 返回<1>找到关键字,返回<0>未找到
* @Others : 十六进制数组长度
* @Date : 2022-08-23
**********************************************************************************/
U32 StringToHex(char *str, U8 *out, U32 *outlen);
/*********************************************************************************
* @Function : 十进制转为十六进制函数
* @Input : <*value>,为要被转换的十进制
* : ,转换完成保存的十六进制的位置
* : ,参数为转换后十六进制的长度
* @Output : None
* @Return : None
* @Others : None
* @Date : 2022-10-10
**********************************************************************************/
void NumToHex(U32 value, char buffer[], int length);
/*********************************************************************************
* @Function : 计算数据的CRC校验值
* @Input : buf,将计算CRC校验的数据
* : len,目标数据长度
* @Output : None
* @Return : None
* @Others : None
* @Date : 2022-03-30
**********************************************************************************/
U16 Chkcrc( U8 *buf, U16 len );
/*********************************************************************************
* @Function : 计算数据的BBC校验数据
* @Input : initData,初始校验值
* : pdata,需要计算的数据开始地址
* : len,数据长度
* @Output : None
* @Return : None
* @Others : None
* @Date : 2022-03-04
**********************************************************************************/
U8 bcc_check(U8 bcc_check_data,U8 *Pdata, U16 len);
/*********************************************************************************
* @Function : 16位数据高低字节互换
* @Input : pData,数据
* : size,数据的大小 单位字节
* @Output : None
* @Return : None
* @Others : None
* : 同步设备寄存器中的信息
* @Date : 2022-04-05
**********************************************************************************/
void data_max_to_min( U16 *pData, U8 size );
#endif /* __TOOL_H */