📄 demo_tx.c
字号:
//*---------------------------------------------------------------------------
//* File Name : demo_tx.c
//*
//* Description : This is a demo of porting the AT91 microcontroller
//* to the ThreadX real-time kernel. It fully compatible
//* with new AT91 library and fully support AT91's AIC
//* features.
//*
//* It includes examples of four threads of different
//* priorities, message queues, semaphores, and event
//* flags.
//*
//* George Zhang : 08/30/2000
//* 10/12/2000
//*---------------------------------------------------------------------------
#define AT91_DEBUG_NONE
/* Include the AT91_Lab */
#ifndef AT91_DEBUG_NONE
#include <stdio.h>
#endif
#include "drivers/terminal/terminal.h"
#include "periph/usart/usart.h"
#include "parts/m40400/lib_m40400.h"
#include "targets/eb01/eb01.h"
#include "tx_api.h"
#define BAUDS38400 53
#define DEMO_STACK_SIZE 1024
/* Define the ThreadX object control blocks... */
TX_THREAD thread_0;
TX_THREAD thread_1;
TX_THREAD thread_2;
TX_THREAD thread_3;
TX_QUEUE queue_0;
TX_SEMAPHORE semaphore_0;
TX_EVENT_FLAGS_GROUP event_flags_0;
/* Define the counters used in the demo application... */
ULONG thread_0_counter;
ULONG thread_1_counter;
ULONG thread_2_counter;
ULONG thread_3_counter;
/* Terminal declaration */
TerminalDataDesc terminal_data_1;
TerminalDesc terminal_1;
char str[TERMINAL_SIZE_BUFFER];
const char str_test[30] = "AT91 RS232 TEST: 38400 BAUD";
const char str_send[10] = "USART0: ";
const char str_IRQ0[8] = "IRQ0! ";
const char str_error[40] = "TERMINAL OVERFLOW: 256 character max! ";
const char CR[2] = {0x0D,0x0A};
/* Define thread prototypes. */
void thread_0_entry(ULONG thread_input);
void thread_1_entry(ULONG thread_input);
void thread_2_entry(ULONG thread_input);
void thread_3_entry(ULONG thread_input);
extern void __at91_usart0_handler(void);
extern void __at91_irq0_handler(void);
/* Define main entry point. */
int main(void)
{
/* Pin I/O initialisation */
at91_pio_open (&PIO_DESC, LED_MASK, PIO_OUTPUT);
at91_pio_write (&PIO_DESC, LED_MASK, PIO_CLEAR_OUT );
/* Enter the ThreadX kernel. */
tx_kernel_enter();
}
/* Define what the initial system looks like. */
void tx_application_define(void *first_unused_memory)
{
CHAR *pointer;
/* Put first available memory address into a character pointer. */
pointer = (CHAR *) first_unused_memory;
/* Put system definition stuff in here, e.g. thread creates and
other assorted create information. */
/* Create the ALL threads. */
tx_thread_create(&thread_0, "thread 0", thread_0_entry, 0,
pointer, DEMO_STACK_SIZE,
1, 1, TX_NO_TIME_SLICE, TX_AUTO_START);
pointer = pointer + DEMO_STACK_SIZE;
tx_thread_create(&thread_1, "thread 1", thread_1_entry, 1,
pointer, DEMO_STACK_SIZE,
2, 2, TX_NO_TIME_SLICE, TX_AUTO_START);
pointer = pointer + DEMO_STACK_SIZE;
tx_thread_create(&thread_2, "thread 2", thread_2_entry, 2,
pointer, DEMO_STACK_SIZE,
12, 12, TX_NO_TIME_SLICE, TX_AUTO_START);
pointer = pointer + DEMO_STACK_SIZE;
tx_thread_create(&thread_3, "thread 3", thread_3_entry, 3,
pointer, DEMO_STACK_SIZE,
12, 12, TX_NO_TIME_SLICE, TX_AUTO_START);
pointer = pointer + DEMO_STACK_SIZE;
/* Create the message queue shared by threads 2 and IRQ0. */
tx_queue_create(&queue_0, "queue 0", TX_1_ULONG, pointer,
100*sizeof(ULONG));
pointer = pointer + (100*sizeof(ULONG));
/* Create the semaphore for USART0 used by threads 2 and 3. */
tx_semaphore_create(&semaphore_0, "semaphore 0", 1);
/* Create the event flags group used by threads 3 and USART0. */
tx_event_flags_create(&event_flags_0, "event flags 0");
}
/* Define the test threads. */
/* This thread simply blinks LED1. */
void thread_0_entry(ULONG thread_input)
{
while(1)
{
at91_pio_write ( &PIO_DESC, LED1, PIO_SET_OUT );
tx_thread_sleep(10); //* Sleep for 10 ticks.
at91_pio_write ( &PIO_DESC, LED1, PIO_CLEAR_OUT );
tx_thread_sleep(10); //* Sleep for 10 ticks.
/* Increment the thread counter. */
thread_0_counter++;
#ifndef AT91_DEBUG_NONE
tx_interrupt_control(TX_INT_DISABLE); // nest IRQs
printf("Task 0 loop: %d\n",thread_0_counter);
tx_interrupt_control(TX_INT_ENABLE); // re-enable IRQs
#endif
}
}
/* This thread simply blinks LED3. */
void thread_1_entry(ULONG thread_input)
{
while(1)
{
at91_pio_write ( &PIO_DESC, LED3, PIO_SET_OUT );
tx_thread_sleep(20); //* Sleep for 20 ticks.
at91_pio_write ( &PIO_DESC, LED3, PIO_CLEAR_OUT );
tx_thread_sleep(60); //* Sleep for 60 ticks.
/* Increment the thread counter. */
thread_1_counter++;
#ifndef AT91_DEBUG_NONE
tx_interrupt_control(TX_INT_DISABLE); // nest IRQs
printf("Task 1 loop: %d\n",thread_1_counter);
tx_interrupt_control(TX_INT_ENABLE); // re-enable IRQs
#endif
}
}
/* This thread demonstrats the message queuing from IRQ0 ISR.*/
void thread_2_entry(ULONG thread_input)
{
UINT status, i;
ULONG received_message;
/* IRQ0 initialisation */
at91_extirq_open(&IRQ0_DESC,2,0x60, __at91_irq0_handler);
while(1)
{
/* Retrieve a message from the queue. */
status = tx_queue_receive(&queue_0, &received_message, TX_WAIT_FOREVER);
/* Get the semaphore. */
status = tx_semaphore_get(&semaphore_0, TX_WAIT_FOREVER);
/* send "IRQ0!" messages to USART0. */
for(i=0; i<strlen(str_IRQ0); i++)
at91_terminal_write(&terminal_1,&str_IRQ0[i]);
at91_terminal_write(&terminal_1, &CR[0]);
at91_terminal_write(&terminal_1, &CR[1]);
//* enable TXRDY interrupt to send messages immediately
terminal_1.usart_desc->usart_base->US_IER = terminal_1.usart_desc->usart_base->US_IMR | 0x02;
/* Release the semaphore. */
status = tx_semaphore_put(&semaphore_0);
/* To demonstration the message queuing, continual press SW5 several times */
at91_pio_write ( &PIO_DESC, LED2, PIO_SET_OUT );
tx_thread_sleep(20); //* Sleep for 20 ticks.
at91_pio_write ( &PIO_DESC, LED2, PIO_CLEAR_OUT );
tx_thread_sleep(40); //* Sleep for 40 ticks.
at91_pio_write ( &PIO_DESC, LED2, PIO_SET_OUT );
tx_thread_sleep(20); //* Sleep for 20 ticks.
at91_pio_write ( &PIO_DESC, LED2, PIO_CLEAR_OUT );
/* Increment the thread counter. */
thread_2_counter++;
#ifndef AT91_DEBUG_NONE
tx_interrupt_control(TX_INT_DISABLE); // nest IRQs
printf("Task 2 loop: %d\n",thread_2_counter);
tx_interrupt_control(TX_INT_ENABLE); // re-enable IRQs
#endif
}
}
/*
This thread configure the Terminal to send and receive under interrupt
on the USART 0. The byte format is : start + 8 data (without parity) + 1
stop. The baud rate is counter is 53 : 38400 bauds with MCKI = 32.768 MHz
When a character is received, it is echoed in the interrupt handler and
stored in a buffer. When the CR character is received, it is echoed and
all buffer is transmitted. The size of the buffer is limited at
TERMINAL_SIZE_BUFFER = 256. When more than 256 characters are received,
an error message is displayed when the character CR is received.
*/
void thread_3_entry(ULONG thread_input)
{
UINT i, status;
ULONG actual_flags;
CHAR *pt_str = str;
/* Terminal initialisation */
terminal_1.usart_desc = &USART0_DESC;
terminal_1.term_data = &terminal_data_1;
terminal_1.baud_rate = (u_int) BAUDS38400;
terminal_1.format = (u_int) US_ASYNC_MODE;
terminal_1.terminal_asm_handler = __at91_usart0_handler;
/* Open terminal */
at91_terminal_open(&terminal_1);
/* Transmit str_test */
for(i=0; i<strlen(str_test); i++)
at91_terminal_write(&terminal_1,&str_test[i]);
at91_terminal_write(&terminal_1, &CR[0]);
at91_terminal_write(&terminal_1, &CR[1]);
/* USART0 IRQ initialisation */
at91_irq_open(USART0_DESC.periph_id,5,0x40, __at91_usart0_handler);
/* Enable RXRDY et TXRDY interrupt */
terminal_1.usart_desc->usart_base->US_IER = 0x03;
while(1)
{
/* Wait for event flag 0. */
status = tx_event_flags_get(&event_flags_0, 0x1, TX_OR_CLEAR,
&actual_flags, TX_WAIT_FOREVER);
if (at91_terminal_read(&terminal_1,pt_str) != 0)
{
if (*pt_str == 0x0D || (terminal_data_1.error != 0))
{
/* Get the semaphore. */
status = tx_semaphore_get(&semaphore_0, TX_WAIT_FOREVER);
/* Send str_send */
at91_terminal_write(&terminal_1, &CR[0]);
at91_terminal_write(&terminal_1, &CR[1]);
for(i=0; i<strlen(str_send); i++)
at91_terminal_write(&terminal_1,&str_send[i]);
/* Send received string */
pt_str = str;
while ((*pt_str != 0x0D) && (terminal_data_1.error ==0))
{
at91_terminal_write(&terminal_1, pt_str);
pt_str++;
}
/* if overflow error */
if (terminal_data_1.error != 0)
{
/* Send error string */
for(i=0; i<40; i++)
at91_terminal_write(&terminal_1,&str_error[i]);
/* reset error flag */
terminal_data_1.error = 0;
}
at91_terminal_write(&terminal_1, &CR[0]);
at91_terminal_write(&terminal_1, &CR[1]);
pt_str = str;
/* enable TXRDY interrupt */
terminal_1.usart_desc->usart_base->US_IER = terminal_1.usart_desc->usart_base->US_IMR | 0x02;
/* Release the semaphore. */
status = tx_semaphore_put(&semaphore_0);
}
else pt_str++;
}
/* Increment the thread counter. */
thread_3_counter++;
#ifndef AT91_DEBUG_NONE
tx_interrupt_control(TX_INT_DISABLE); // nest IRQs
printf("Task 3 loop: %d\n", thread_3_counter);
tx_interrupt_control(TX_INT_ENABLE); // re-enable IRQs
#endif
}
}
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -