/*
	FreeRTOS.org V5.2.0 - Copyright (C) 2003-2009 Richard Barry.

	This file is part of the FreeRTOS.org distribution.

	FreeRTOS.org is free software; you can redistribute it and/or modify it 
	under the terms of the GNU General Public License (version 2) as published
	by the Free Software Foundation and modified by the FreeRTOS exception.

	FreeRTOS.org is distributed in the hope that it will be useful,	but WITHOUT
	ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or 
	FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License for 
	more details.

	You should have received a copy of the GNU General Public License along 
	with FreeRTOS.org; if not, write to the Free Software Foundation, Inc., 59 
	Temple Place, Suite 330, Boston, MA  02111-1307  USA.

	A special exception to the GPL is included to allow you to distribute a 
	combined work that includes FreeRTOS.org without being obliged to provide
	the source code for any proprietary components.  See the licensing section
	of http://www.FreeRTOS.org for full details.


	***************************************************************************
	*                                                                         *
	* Get the FreeRTOS eBook!  See http://www.FreeRTOS.org/Documentation      *
	*                                                                         *
	* This is a concise, step by step, 'hands on' guide that describes both   *
	* general multitasking concepts and FreeRTOS specifics. It presents and   *
	* explains numerous examples that are written using the FreeRTOS API.     *
	* Full source code for all the examples is provided in an accompanying    *
	* .zip file.                                                              *
	*                                                                         *
	***************************************************************************

	1 tab == 4 spaces!

	Please ensure to read the configuration and relevant port sections of the
	online documentation.

	http://www.FreeRTOS.org - Documentation, latest information, license and
	contact details.

	http://www.SafeRTOS.com - A version that is certified for use in safety
	critical systems.

	http://www.OpenRTOS.com - Commercial support, development, porting,
	licensing and training services.
*/

/* 
 * This demo application creates six co-routines and two tasks (three including 
 * the idle task).  The co-routines execute as part of the idle task hook.
 *
 * Five of the created co-routines are the standard 'co-routine flash' 
 * co-routines contained within the Demo/Common/Minimal/crflash.c file and 
 * documented on the FreeRTOS.org WEB site.  
 *
 * The 'LCD Task' rotates a string on the LCD, delaying between each character
 * as necessitated by the slow interface, and delaying between each string just
 * long enough to enable the text to be read.
 *
 * The sixth co-routine and final task control the transmission and reception
 * of a string to UART 0.  The co-routine periodically sends the first 
 * character of the string to the UART, with the UART's TxEnd interrupt being
 * used to transmit the remaining characters.  The UART's RxEnd interrupt 
 * receives the characters and places them on a queue to be processed by the 
 * 'COMs Rx' task.  An error is latched should an unexpected character be 
 * received, or any character be received out of sequence.  
 *
 * A loopback connector is required to ensure that each character transmitted 
 * on the UART is also received on the same UART.  For test purposes the UART
 * FIFO's are not utalised in order to maximise the interrupt overhead.  Also
 * a pseudo random interval is used between the start of each transmission in 
 * order that the resultant interrupts are more randomly distributed and 
 * therefore more likely to highlight any problems.
 *
 * The flash co-routines control LED's zero to four.  LED five is toggled each
 * time the string is transmitted on the UART.  LED six is toggled each time
 * the string is CORRECTLY received on the UART.  LED seven is latched on should
 * an error be detected in any task or co-routine.
 *
 * In addition the idle task makes repetative calls to 
 * prvSetAndCheckRegisters().  This simply loads the general purpose registers 
 * with a known value, then checks each register to ensure the held value is 
 * still correct.  As a low priority task this checking routine is likely to 
 * get repeatedly swapped in and out.  A register being found to contain an 
 * incorrect value is therefore indicative of an error in the task switching 
 * mechansim.
 *
 */

/* Scheduler include files. */
#include "FreeRTOS.h"
#include "task.h"
#include "queue.h"
#include "croutine.h"

/* Demo application include files. */
#include "partest.h"
#include "crflash.h"

/* Library include files. */
#include "LM3Sxxx.h"
#include "pdc.h"

/* The time to delay between writing each character to the LCD. */
#define mainCHAR_WRITE_DELAY		( 2 / portTICK_RATE_MS )

/* The time to delay between writing each string to the LCD. */
#define mainSTRING_WRITE_DELAY		( 400 / portTICK_RATE_MS )

/* The number of flash co-routines to create. */
#define mainNUM_FLASH_CO_ROUTINES	( 5 )

/* The length of the queue used to pass received characters to the Comms Rx
task. */
#define mainRX_QUEUE_LEN			( 5 )

/* The priority of the co-routine used to initiate the transmission of the 
string on UART 0. */
#define mainTX_CO_ROUTINE_PRIORITY	( 1 )

/* Only one co-routine is created so its index is not important. */
#define mainTX_CO_ROUTINE_INDEX		( 0 )

/* The time between transmissions of the string on UART 0.   This is pseudo
random in order to generate a bit or randomness to when the interrupts occur.*/
#define mainMIN_TX_DELAY			( 40 / portTICK_RATE_MS )
#define mainMAX_TX_DELAY			( ( portTickType ) 0x7f )
#define mainOFFSET_TIME				( ( portTickType ) 3 )

/* The time the Comms Rx task should wait to receive a character.  This should
be slightly longer than the time between transmissions.  If we do not receive
a character after this time then there must be an error in the transmission or
the timing of the transmission. */
#define mainCOMMS_RX_DELAY			( mainMAX_TX_DELAY + 20 )

/* The task priorites. */
#define mainLCD_TASK_PRIORITY		( tskIDLE_PRIORITY )
#define mainCOMMS_RX_TASK_PRIORITY	( tskIDLE_PRIORITY + 1 )

/* The LED's toggled by the various tasks. */
#define mainCOMMS_FAIL_LED			( 7 )
#define mainCOMMS_RX_LED			( 6 )
#define mainCOMMS_TX_LED			( 5 )

/* The baud rate used by the UART comms tasks/co-routine. */
#define mainBAUD_RATE				( 57600 )

/* FIFO setting for the UART.  The FIFO is not used to create a better test. */
#define mainFIFO_SET				( 0x10 )

/* The string that is transmitted on the UART contains sequentially the 
characters from mainFIRST_TX_CHAR to mainLAST_TX_CHAR. */
#define mainFIRST_TX_CHAR '0'
#define mainLAST_TX_CHAR 'z'

/* Just used to walk through the program memory in order that some random data
can be generated. */
#define mainTOTAL_PROGRAM_MEMORY ( ( unsigned portLONG * ) ( 8 * 1024 ) )
#define mainFIRST_PROGRAM_BYTES ( ( unsigned portLONG * ) 4 )

/*-----------------------------------------------------------*/

/*
 * The task that rotates text on the LCD.
 */
static void vLCDTask( void * pvParameters );

/*
 * The task that receives the characters from UART 0.
 */
static void vCommsRxTask( void * pvParameters );

/*
 * The co-routine that periodically initiates the transmission of the string on
 * the UART.
 */
static void vSerialTxCoRoutine( xCoRoutineHandle xHandle, unsigned portBASE_TYPE uxIndex );

/* 
 * Writes a string the the LCD.
 */
static void prvWriteString( const portCHAR *pcString );

/*
 * Initialisation routine for the UART.
 */
static void vSerialInit( void );

/*
 * Thread safe write to the PDC.
 */
static void prvPDCWrite( portCHAR cAddress, portCHAR cData );

/*
 * Function to simply set a known value into the general purpose registers
 * then read them back to ensure they remain set correctly.  An incorrect value
 * being indicative of an error in the task switching mechanism.
 */
void prvSetAndCheckRegisters( void );

/*
 * Latch the LED that indicates that an error has occurred. 
 */
void vSetErrorLED( void );

/*
 * Sets up the PLL and ports used by the demo.
 */
static void prvSetupHardware( void );

/*-----------------------------------------------------------*/

/* Error flag set to pdFAIL if an error is encountered in the tasks/co-routines
defined within this file. */
unsigned portBASE_TYPE uxErrorStatus = pdPASS;

/* The next character to transmit. */
static portCHAR cNextChar;

/* The queue used to transmit characters from the interrupt to the Comms Rx
task. */
static xQueueHandle xCommsQueue;

/*-----------------------------------------------------------*/

int main( void )
{
	/* Create the queue used to communicate between the UART ISR and the Comms
	Rx task. */
	xCommsQueue = xQueueCreate( mainRX_QUEUE_LEN, sizeof( portCHAR ) );

	/* Setup the ports used by the demo and the clock. */
	prvSetupHardware();

	/* Create the co-routines that flash the LED's. */
	vStartFlashCoRoutines( mainNUM_FLASH_CO_ROUTINES );

	/* Create the co-routine that initiates the transmission of characters
	on the UART. */
	xCoRoutineCreate( vSerialTxCoRoutine, mainTX_CO_ROUTINE_PRIORITY, mainTX_CO_ROUTINE_INDEX );

	/* Create the LCD and Comms Rx tasks. */
	xTaskCreate( vLCDTask, "LCD", configMINIMAL_STACK_SIZE, NULL, mainLCD_TASK_PRIORITY, NULL );
	xTaskCreate( vCommsRxTask, "CMS", configMINIMAL_STACK_SIZE, NULL, mainCOMMS_RX_TASK_PRIORITY, NULL );

	/* Start the scheduler running the tasks and co-routines just created. */
	vTaskStartScheduler();

	/* Should not get here unless we did not have enough memory to start the
	scheduler. */
	for( ;; );
}
/*-----------------------------------------------------------*/

static void prvSetupHardware( void )
{
	/* Setup the PLL. */
	SysCtlClockSet( SYSCTL_SYSDIV_10 | SYSCTL_USE_PLL | SYSCTL_OSC_MAIN | SYSCTL_XTAL_6MHZ );

	/* Initialise the hardware used to talk to the LCD, LED's and UART. */
	PDCInit();
	vParTestInitialise();
	vSerialInit();
}
/*-----------------------------------------------------------*/

void vApplicationIdleHook( void )
{
	/* The co-routines are executed in the idle task using the idle task 
	hook. */
	for( ;; )
	{
		/* Schedule the co-routines. */
		vCoRoutineSchedule();

		/* Run the register check function between each co-routine. */
		prvSetAndCheckRegisters();
	}
}
/*-----------------------------------------------------------*/

static void prvWriteString( const portCHAR *pcString )
{
	/* Write pcString to the LED, pausing between each character. */
	prvPDCWrite(PDC_LCD_CSR, LCD_CLEAR);        
	while( *pcString )
	{
		vTaskDelay( mainCHAR_WRITE_DELAY );
		prvPDCWrite( PDC_LCD_RAM, *pcString );
		pcString++;
	}
}
/*-----------------------------------------------------------*/

void vLCDTask( void * pvParameters )
{
unsigned portBASE_TYPE uxIndex;
const unsigned portCHAR ucCFGData[] = {	
											0x30,   /* Set data bus to 8-bits. */
											0x30,
											0x30,
											0x3C,   /* Number of lines/font. */
											0x08,   /* Display off. */
											0x01,   /* Display clear. */
											0x06,   /* Entry mode [cursor dir][shift]. */
											0x0C	/* Display on [display on][curson on][blinking on]. */
									  };  

/* The strings that are written to the LCD. */
const portCHAR *pcStringsToDisplay[] = {										
											"Stellaris",
											"Demo",
											"One",
											"www.FreeRTOS.org",
											""
									   };

	/* Configure the LCD. */
	uxIndex = 0;
	while( uxIndex < sizeof( ucCFGData ) )
	{
		prvPDCWrite( PDC_LCD_CSR, ucCFGData[ uxIndex ] );
		uxIndex++;
		vTaskDelay( mainCHAR_WRITE_DELAY );
	}

	/* Turn the LCD Backlight on. */
	prvPDCWrite( PDC_CSR, 0x01 );

	/* Clear display. */
	vTaskDelay( mainCHAR_WRITE_DELAY );
	prvPDCWrite( PDC_LCD_CSR, LCD_CLEAR ); 

	uxIndex = 0;
	for( ;; )    
	{
		/* Display the string on the LCD. */
		prvWriteString( pcStringsToDisplay[ uxIndex ] );
		
		/* Move on to the next string - wrapping if necessary. */
		uxIndex++;
		if( *( pcStringsToDisplay[ uxIndex ] ) == 0x00 )
		{
			uxIndex = 0;
			/* Longer pause on the last string to be sent. */
			vTaskDelay( mainSTRING_WRITE_DELAY * 2 );
		}

		/* Wait until it is time to move onto the next string. */
		vTaskDelay( mainSTRING_WRITE_DELAY );
	}
}
/*-----------------------------------------------------------*/

static void vCommsRxTask( void * pvParameters )
{
static portCHAR cRxedChar, cExpectedChar;

	/* Set the char we expect to receive to the start of the string. */
	cExpectedChar = mainFIRST_TX_CHAR;

	for( ;; )
	{
		/* Wait for a character to be received. */
		xQueueReceive( xCommsQueue, ( void * ) &cRxedChar, mainCOMMS_RX_DELAY );

		/* Was the character recived (if any) the expected character. */
		if( cRxedChar != cExpectedChar )
		{
			/* Got an unexpected character.  This can sometimes occur when
			reseting the system using the debugger leaving characters already
			in the UART regsters. */
			uxErrorStatus = pdFAIL;

			/* Resync by waiting for the end of the current string. */
			while( cRxedChar != mainLAST_TX_CHAR )
			{
				while( !xQueueReceive( xCommsQueue, ( void * ) &cRxedChar, portMAX_DELAY ) );
			}

			/* The next expected character is the start of the string again. */
			cExpectedChar = mainFIRST_TX_CHAR;
		}
		else
		{
			if( cExpectedChar == mainLAST_TX_CHAR )
			{
				/* We have reached the end of the string - we now expect to 
				receive the first character in the string again.   The LED is 
				toggled to indicate that the entire string was received without
				error. */
				vParTestToggleLED( mainCOMMS_RX_LED );
				cExpectedChar = mainFIRST_TX_CHAR;
			}
			else
			{
				/* We got the expected character, we now expect to receive the
				next character in the string. */
				cExpectedChar++;
			}
		}
	}
}
/*-----------------------------------------------------------*/

static void vSerialTxCoRoutine( xCoRoutineHandle xHandle, unsigned portBASE_TYPE uxIndex )
{
portTickType xDelayPeriod;
static unsigned portLONG *pulRandomBytes = mainFIRST_PROGRAM_BYTES;

	/* Co-routine MUST start with a call to crSTART. */
	crSTART( xHandle );

	for(;;)
    {	
		/* Was the previously transmitted string received correctly? */
		if( uxErrorStatus != pdPASS )
		{
			/* An error was encountered so set the error LED. */
			vSetErrorLED();
		}

		/* The next character to Tx is the first in the string. */
		cNextChar = mainFIRST_TX_CHAR;

		UARTIntDisable( UART0_BASE, UART_INT_TX );
		{
			/* Send the first character. */
			if( !( HWREG( UART0_BASE + UART_O_FR ) & UART_FR_TXFF ) )
			{
				HWREG( UART0_BASE + UART_O_DR ) = cNextChar;
			}

			/* Move the variable to the char to Tx on so the ISR transmits
			the next character in the string once this one has completed. */
			cNextChar++;
		}
		UARTIntEnable(UART0_BASE, UART_INT_TX);

		/* Toggle the LED to show a new string is being transmitted. */
        vParTestToggleLED( mainCOMMS_TX_LED );

		/* Delay before we start the string off again.  A pseudo-random delay
		is used as this will provide a better test. */
		xDelayPeriod = xTaskGetTickCount() + ( *pulRandomBytes );

		pulRandomBytes++;
		if( pulRandomBytes > mainTOTAL_PROGRAM_MEMORY )
		{
			pulRandomBytes = mainFIRST_PROGRAM_BYTES;
		}

		/* Make sure we don't wait too long... */
		xDelayPeriod &= mainMAX_TX_DELAY;

		/* ...but we do want to wait. */
		if( xDelayPeriod < mainMIN_TX_DELAY )
		{
			xDelayPeriod = mainMIN_TX_DELAY;
		}

		/* Block for the random(ish) time. */
		crDELAY( xHandle, xDelayPeriod );
    }

	/* Co-routine MUST end with a call to crEND. */
	crEND();
}
/*-----------------------------------------------------------*/

static void vSerialInit( void )
{
	/* Enable the UART.  GPIOA has already been initialised. */
	SysCtlPeripheralEnable(SYSCTL_PERIPH_UART0);

	/* Set GPIO A0 and A1 as peripheral function.  They are used to output the
	UART signals. */
	GPIODirModeSet( GPIO_PORTA_BASE, GPIO_PIN_0 | GPIO_PIN_1, GPIO_DIR_MODE_HW );

	/* Configure the UART for 8-N-1 operation. */
	UARTConfigSet( UART0_BASE, mainBAUD_RATE, UART_CONFIG_WLEN_8 | UART_CONFIG_PAR_NONE | UART_CONFIG_STOP_ONE );

	/* We dont want to use the fifo.  This is for test purposes to generate
	as many interrupts as possible. */
	HWREG( UART0_BASE + UART_O_LCR_H ) &= ~mainFIFO_SET;

	/* Enable both Rx and Tx interrupts. */
	HWREG( UART0_BASE + UART_O_IM ) |= ( UART_INT_TX | UART_INT_RX );
	IntEnable( INT_UART0 );
}
/*-----------------------------------------------------------*/

void vUART_ISR(void)
{
unsigned portLONG ulStatus;
portCHAR cRxedChar;
portBASE_TYPE xHigherPriorityTaskWoken = pdFALSE;

	/* What caused the interrupt. */
	ulStatus = UARTIntStatus( UART0_BASE, pdTRUE );

	/* Clear the interrupt. */
	UARTIntClear( UART0_BASE, ulStatus );

	/* Was an Rx interrpt pending? */
	if( ulStatus & UART_INT_RX )
	{
		if( ( HWREG(UART0_BASE + UART_O_FR ) & UART_FR_RXFF ) )
		{
			/* Get the char from the buffer and post it onto the queue of
			Rxed chars.  Posting the character should wake the task that is 
			blocked on the queue waiting for characters. */
			cRxedChar = ( portCHAR ) HWREG( UART0_BASE + UART_O_DR );
			xQueueSendFromISR( xCommsQueue, &cRxedChar, &xHigherPriorityTaskWoken );
		}		
	}

	/* Was a Tx interrupt pending? */
	if( ulStatus & UART_INT_TX )
	{
		/* Send the next character in the string.  We are not using the FIFO. */
		if( cNextChar <= mainLAST_TX_CHAR )
		{
			if( !( HWREG( UART0_BASE + UART_O_FR ) & UART_FR_TXFF ) )
			{
				HWREG( UART0_BASE + UART_O_DR ) = cNextChar;
			}
			cNextChar++;
		}
	}
	
	/* If a task was woken by the character being received then we force
	a context switch to occur in case the task is of higher priority than
	the currently executing task (i.e. the task that this interrupt 
	interrupted.) */
	portEND_SWITCHING_ISR( xHigherPriorityTaskWoken );
}
/*-----------------------------------------------------------*/

static void prvPDCWrite( portCHAR cAddress, portCHAR cData )
{
	vTaskSuspendAll();
	{
		PDCWrite( cAddress, cData );
	}
	xTaskResumeAll();
}
/*-----------------------------------------------------------*/

void vSetErrorLED( void )
{
	vParTestSetLED( mainCOMMS_FAIL_LED, pdTRUE );
}
/*-----------------------------------------------------------*/

__asm void prvSetAndCheckRegisters( void )
{
	extern vSetErrorLED

	/* Fill the general purpose registers with known values. */
	mov r11, #10
	add r0, r11, #1
	add r1, r11, #2
	add r2, r11, #3
	add r3, r11, #4
	add r4, r11, #5
	add r5, r11, #6
	add r6, r11, #7
	add r7, r11, #8
	add r8, r11, #9
	add r9, r11, #10
	add r10, r11, #11
	add r12, r11, #12

	/* Check the values are as expected. */
	cmp r11, #10
	bne set_error_led
	cmp r0, #11
	bne set_error_led
	cmp r1, #12
	bne set_error_led
	cmp r2, #13
	bne set_error_led
	cmp r3, #14
	bne set_error_led
	cmp r4, #15
	bne set_error_led
	cmp r5, #16
	bne set_error_led
	cmp r6, #17
	bne set_error_led
	cmp r7, #18
	bne set_error_led
	cmp r8, #19
	bne set_error_led
	cmp r9, #20
	bne set_error_led
	cmp r10, #21
	bne set_error_led
	cmp r12, #22
	bne set_error_led
	bx lr

set_error_led;
	push {r14}
	ldr r1, =vSetErrorLED
	blx r1
	pop {r14}
	bx lr;
}
/*-----------------------------------------------------------*/
