在LPC2138中移植了uCOS-II之后,串口一直不对。本来串口应该每隔1s给上位机发送20个字节的数据,但是发现,上电之后,LPC2138每次只给上位机发送一次,而且个数不定。程序如下:
/************************************************************************************************************************
** Function name: UART0Init
** Author:
** Copyright: MEI8
** Date:
** Function: 38400bit/s的波特率
** Input: NONE
** Output: NONE
************************************************************************************************************************/
void UART0Init(void)
{
uint16 frequencyDiv; //定义分频值
PINSEL0 = (PINSEL0 & (~0x0F)) | 0x05; //选择UART0功能,P0.0为TxD,P0.1为RxD
U0LCR = 0x83; //8位字符长度,1个停止位,禁止奇偶产生和校验
//禁止间隔发送
//DLAB = 1,使能访问除数锁存,这也是我们最终的目的
frequencyDiv = (Fpclk / 16) / UART0_BPS;
U0DLM = frequencyDiv / 256;
U0DLL = frequencyDiv % 256;
U0LCR = 0x03; //LCR只是修改了第七位,DLAB = 0,禁止访问除数锁存。
//与此同时,RBR接收缓冲寄存器、THR发送保持寄存器
//IER中断使能寄存器、TER发送使能寄存器可以读写
U0FCR = 0x01; //控制寄存器,使能FIFO,触发点0,即I/O一个字节
U0IER = 0x01; //中断使能寄存器,使能RBR中断,禁止THRE和Rx线状态中断
VICIntSelect = 0;
VICVectCntl0= 0x20 | 0x06;
VICVectAddr0 = (uint32)uart0_rx_isr;
VICIntEnable |= 1 << 6;
}
百思不得其解。
在实验过程中,我发现当进行下面的操作之后,程序运行正常。
//VICIntSelect = 0;
//VICVectCntl0= 0x20 | 0x06;
//VICVectAddr0 = (uint32)uart0_rx_isr;
//VICIntEnable |= 1 << 6;
可是,串口中断是上位机正常指令实时起效的保证,不可能不使用它。就算定义一个优先级最高的任务也没有中断的效果好。
为什么呢?
突然想起来,操作系统使用的定时器0作为时钟节拍,那是不是,IRQ中断的最高优先级的中断,已经被TIME0使用了呢?我把串口的中断改成了优先级为4的时候,串口的工作终于正常了。
VICIntSelect = 0;
VICVectCntl3= 0x20 | 0x06;
VICVectAddr3 = (uint32)uart0_rx_isr;
VICIntEnable |= 1 << 6;