由于要在公司的老产品上添加一些新的功能,这是很久前的工程师做的代码,两年前我曾用过atmega64单片机,但那是在Atmel studio 6上,现在在IAR里开发AVR还是头一次。
由于不能在线调试,只能用串口打印数据来调试代码,所以就编了一些打印函数,可是问题来了,代码运用不正常。为了便于观察,我把数据转化成16进制字符格式输出。先来看看转化函数:
点击(此处)折叠或打开
- void PrintStr(char *Strings)
- {
- char *str;
- str=Strings;
-
- while(*str!='\0')
- {
- putchar(*str);
- str++;
- }
- }
- void printHex(unsigned char c)
- {
- unsigned char numstr[16]={'0','1','2','3','4','5','6','7','8','9','A','B','C','D','E','F'};
- putchar(numstr[c>>4]);
- putchar(numstr[c&0x0f]);
- }
- void printStrLhex(char *str,void *databuf,unsigned short int num)
- {
- unsigned short int i;
- unsigned char *buf=(unsigned char *)databuf;
- PrintStr(str);
- for(i=0;i<num;i++)
- {
- printHex(buf[i]);
- }
-
- PrintStr("\r\n");
- }
函数printStrLhex()的用法是先打印一串 ,然后在后面接着打印指定指针起的n个数据的十六进制字符,比如:
unsigned char databuf[10]={1,2,3,4,5,6,7,8,9,10};
执行printStrLhex(“databuf= ”,databuf,10);后,串口输出字符串:databuf=01 02 03 04 05 06 07 08 09 0A,这个代码在STM32上能够正常运行,但是在AVR上,老是出问题,数据转十六进制部分会输出乱码,或不停的输出乱码或同一个相同的数据,有时候单片机还会复位,出现看起来是numstr数组没被初始化一样,不停的输出同一个数据像是没正常的读到指定数据的长度,复位现象又像是内存泄漏,三个问题绞在一起实在头疼,最后不numstr数组的定义到函数外,并加const 限制,打印出来的数据字符就不出现乱码了,但是有时会不停的打印数据,根本就停不下来,打印的数据也不对,也还会有复位现象。有了前面数组问题的经验,我后面也是把怀疑的目光投向了数组,把定义在函数内的数组,需要一指针传参给其他函数时的数组都加了statc限制,这回一运行一切都OK。
这是什么原因呢,我想这是编译器的问题了,人家原来在keil里面用得好好的代码,在IAR的却不行,这是编译器的问题了,加上static后问题是解决了,但是这样会让这些数字一直占着内存,大大减小了内存的利用率。
另外再贴结果常用的函数
void printHexS(void *c,unsigned short int len),将指定缓冲区的数据按指定长度以十六进制格式字符打印。
void printHexS(void *c,unsigned short int len)
{
unsigned short int i;
unsigned char *buf=(unsigned char *)c;
for(i=0;i
printHex(buf[i]);
}
PrintStr("\r\n");
}
//memset
void _memset(unsigned char* databuf,unsigned char value,unsigned short int length)
{
unsigned short int i;
if(!databuf)
return;
for(i=0;i
databuf[i]=value;
}
}
//memcpy
char _memcpy(unsigned char * dbuf,unsigned char *sbuf,unsigned short int len)
{
unsigned short int i;
if((!dbuf) || (!sbuf))
return FALSE;
for(i=0;i
dbuf[i]=sbuf[i];
}
return TRUE ;
}
//内存数据比较
char _memcmp(unsigned char * destr,unsigned char *cmpstr,unsigned short int len)
{
unsigned short int i;
for(i=0;i
if(destr[i]!=cmpstr[i])
return FALSE;
}
return TRUE;
}
//将缓冲区数据按字节颠倒。
void _memtranspose(unsigned char *databuf,unsigned short int len)
{
unsigned short int i;
unsigned char temp;
for(i=0;i
temp=databuf[i];
databuf[i]=databuf[len-i-1];
databuf[len-i-1]=temp;
}
}
这些函数在编程中使用频率很好,自己实现,不需要调用系统库函数。