发一个RL-ARM的UART例程,采用队列缓冲,动态分配内存。
本帖最后由 luoyiming1984 于 2012-9-11 00:22 编辑采用LPC2142芯片,有点老了,keil4最新版。
UART采用了16字节FIFO和队列buffer的方式,UartRead支持接收超时。
两个任务,因为保密的需要,我把FLASH,LCM,无线通信的驱动全部扣了(不要扁我,人不为己天诛地灭)。
一个任务是接收Uart数据,一个是把收到的发出来。
每个任务的堆栈分配,我用的动态分配,这样在删除任务时,可以把内存也删除掉。
那能看到啥? 没有人看吗??
MARK一下~~· 能整个stm32上的串口的? roguebear2012 发表于 2012-9-21 21:23 static/image/common/back.gif
能整个stm32上的串口的?
已经做好了,连续收发鸭梨不大 luoyiming1984 发表于 2012-9-22 11:45 static/image/common/back.gif
已经做好了,连续收发鸭梨不大
我来贴个。keil测试通过,感觉效率不太高啊。
兄台把你的整上来……
/*----------------------------------------------------------------------------
* Name: Usart.c
* Purpose: USART usage for STM32
* Version: V1.00
*----------------------------------------------------------------------------
* This file is part of the uVision/ARM development tools.
* This software may only be used under the terms of a valid, current,
* end user licence from KEIL for a compatible version of KEIL software
* development tools. Nothing else gives you the right to use this software.
*
* Copyright (c) 2005-2007 Keil Software. All rights reserved.
*----------------------------------------------------------------------------*/
#include <stm32f10x_conf.h>
/* 注意: 打开 RXNE TXE 中断*/
#define USARTx USART1
#define USARTx_IRQHandler USART1_IRQHandler
/*----------------------------------------------------------------------------
Notes:
The length of the receive and transmit buffers must be a power of 2.
Each buffer has a next_in and a next_out index.
If next_in = next_out, the buffer is empty.
(next_in - next_out) % buffer_size = the number of characters in the buffer.
*----------------------------------------------------------------------------*/
#define TBUF_SIZE 256 /*** Must be a power of 2 (2,4,8,16,32,64,128,256,512,...) ***/
#define RBUF_SIZE 256 /*** Must be a power of 2 (2,4,8,16,32,64,128,256,512,...) ***/
/*----------------------------------------------------------------------------
*----------------------------------------------------------------------------*/
#if TBUF_SIZE < 2
#error TBUF_SIZE is too small.It must be larger than 1.
#elif ((TBUF_SIZE & (TBUF_SIZE-1)) != 0)
#error TBUF_SIZE must be a power of 2.
#endif
#if RBUF_SIZE < 2
#error RBUF_SIZE is too small.It must be larger than 1.
#elif ((RBUF_SIZE & (RBUF_SIZE-1)) != 0)
#error RBUF_SIZE must be a power of 2.
#endif
/*----------------------------------------------------------------------------
*----------------------------------------------------------------------------*/
struct buf_st {
unsigned int in; // Next In Index
unsigned int out; // Next Out Index
char buf ; // Buffer
};
static struct buf_st rbuf = { 0, 0, 0};
#define SIO_RBUFLEN ((unsigned short)(rbuf.in - rbuf.out))
static struct buf_st tbuf = { 0, 0, 0};
#define SIO_TBUFLEN ((unsigned short)(tbuf.in - tbuf.out))
static unsigned int tx_restart = 1; // NZ if TX restart is required
/*----------------------------------------------------------------------------
USARTx_IRQHandler
Handles USARTx global interrupt request.
*----------------------------------------------------------------------------*/
void USARTx_IRQHandler (void) {
volatile unsigned int IIR;
struct buf_st *p;
IIR = USARTx->SR;
if (IIR & USART_FLAG_RXNE) { // read interrupt
USARTx->SR &= ~USART_FLAG_RXNE; // clear interrupt
p = &rbuf;
if (((p->in - p->out) & ~(RBUF_SIZE-1)) == 0) {
p->buf = (USARTx->DR & 0x1FF);
p->in++;
}
}
if (IIR & USART_FLAG_TXE) {
USARTx->SR &= ~USART_FLAG_TXE; // clear interrupt
p = &tbuf;
if (p->in != p->out) {
USARTx->DR = (p->buf & 0x1FF);
p->out++;
tx_restart = 0;
}
else {
tx_restart = 1;
USARTx->CR1 &= ~USART_FLAG_TXE; // disable TX interrupt if nothing to send
}
}
}
/*------------------------------------------------------------------------------
SenChar
transmit a character
*------------------------------------------------------------------------------*/
int SendChar (int c) {
struct buf_st *p = &tbuf;
// If the buffer is full, return an error value
if (SIO_TBUFLEN >= TBUF_SIZE)
return (-1);
p->buf = c; // Add data to the transmit buffer.
p->in++;
if (tx_restart) { // If transmit interrupt is disabled, enable it
tx_restart = 0;
USARTx->CR1 |= USART_FLAG_TXE; // enable TX interrupt
}
return (0);
}
/*------------------------------------------------------------------------------
GetKey
receive a character
*------------------------------------------------------------------------------*/
int GetKey (void) {
struct buf_st *p = &rbuf;
if (SIO_RBUFLEN == 0)
return (-1);
return (p->buf [(p->out++) & (RBUF_SIZE - 1)]);
}
/*------------------------------------------------------------------------------
buffer_Init
initialize the buffers
*------------------------------------------------------------------------------*/
void buffer_Init (void) {
tbuf.in = 0; // Clear com buffer indexes
tbuf.out = 0;
tx_restart = 1;
rbuf.in = 0;
rbuf.out = 0;
}
#if 0
/*----------------------------------------------------------------------------
Demo function
*----------------------------------------------------------------------------*/
int main (void) {
buffer_Init(); // init RX / TX buffers
stm32_Init (); // STM32 setup
printf ("\r\n\r\nInterrupt driven Serial I/O Example\r\n\r\n");
while (1) { // Loop forever
printf ("Press a key. ");
printf ("You pressed '%c'.\r\n\r\n", getchar () );
} // end while
} // end main
#endif
借鉴下,学习啦
页:
[1]