移植uCOS-II到MSP430一切都OK,后来加了TI的一个小的TCP/IP协议栈就老是死掉,纠结了两个晚上,现在把问题解决了。uCOS-II的运行需要一个时钟信号,也就是“心跳”信号,以此来进行系统运行和任务调度,我这里开了MSP430的看门狗中断作为“心跳”信号。第一个问题是我在创建任务之前开了总中断_EINT()函数,这就打开了看门狗中断,但是任务还没建立,怎么跑任务呢,那个看门狗时钟节拍中断就是任务切换用的,如果任务还没建立起来,也就是说任务的堆栈还没初始化,那任务指向哪里呢。这个问题找到了,但是另外一个问题又来了。当在一个任务中添加一个比较大的函数时(TCP监听处理函数)几死掉,进不了main函数,死在__data16_memzero汇编指令中。我立刻就怀疑肯定是任务堆栈设小了,堆栈溢出了,但是将这个任务堆栈改成1024依然没用,数组越界?函数时TI的,之前也用过也没问题啊。查看堆栈使用情况,设置IAR:Option->Linker->List->Generate linker listing,这样在编译时Output下就可以.map文件,里面是link数据,列出了内存、堆栈等使用情况(或者Tool/Options/Meassages/show build message:选为All就行了)。仿真发现程序死在__data16_memzero汇编指令这,通过百度此问题,解决了。
TI技术论坛一个员工这么说的:
一直在_data16_memzero里死循环可能是因为程序最开始初始化变量的时候有大数组需要初始化。导致看门狗不断复位。这个初始化的过程是在进入main之前,有2种方式你可以尝试:
1.对你的数组用__no init_定义,上电编译器不产生特殊的附加函数去初始化RAM
2. B修改IAR中Cstartup.S43文件中__program_start子程序,增加一个关闭WDT的操作或者设置WDT时间长度超过32MS
C在Project--Options--Linker--Config中选择Override default programe,并将Entry lib设置成__program_start
事实也确实如此,Cstartup.S43是MSP430的启动文件,里面默认是打开看门狗的,添加个宏定义把看门狗关闭就解决了问题。
具体操作如下:
在安装文件:C:\……\src\lib\430中找到启动文件:cstartup.s43
拷一个cstartup.s43,然后将其只读属性去掉。用记事本等打开cstartup.s43文件,看到文件内有如下语句:
#ifdef DISABLE_WATCHDOG
MOV#WDTPW + WDTHOLD, &WDTCTL
#endif
说明文件内已经有关闭看门狗的条件编译语句,只要我们定义条件,这样启动代码中的该语句就生效了,我们在文件头添加一句:
#define DISABLE_WATCHDOG
保存,然后再工程中将cstartup.s43文件添加到我们的工程当中。
在Project->Options->Linker->Config页中选择Override default programe ,并将Entry symb设置成__program_start。
把debugger->setup->Run to main销掉,这样我们就能够从启动代码开始一句一句的看了。