![]() Studio Cadrage |
This demo -
From FreeRTOS.org V4.0.3 onwards the demo project file includes a kernel aware window in the debugger. This provides useful information on the state of each task in the system, but can slow down the debugger performance. Closing this window will permit faster debug operations.
As downloaded this demo application does not demonstrate the use of co-routines. See the co-routine documentation page for information on how co-routine functionality can be quickly added to this demonstration.
The lwIP CrossStudio demo project rtosdemo.hzp can be found in the Demo/lwIP_Demo_Rowley_ARM7 directory and should be opened from within the CrossWorks IDE.
Adam Dunkels lwIP code is located in the Demo/lwIP_Demo_Rowley_ARM7/lwip-1.1.0 directory.
The Demo/lwIP_Demo_Rowley_ARM7/EMAC directory contains the EMAC driver, and finally the Demo/lwIP_Demo_Rowley_ARM7/USB directory contains the USB CDC driver source code.
The IP address used by the demo is set by the constants emacIPADDR0 to emacIPADDR3 within the file Demo/lwIP_Demo_Rowley_ARM7/EMAC/SAM7_EMAC.h. The IP addresses used by the WEB browser computer and the prototyping board must be compatible. This can be ensured by making the first three octets of both IP addresses identical. For example, if the WEB browser computer uses IP address 192.168.100.1, then the prototyping board can be given any address in the range 192.168.100.2 to 192.168.100.254 (barring any addresses already present on the network).
SAM7_EMAC.h also contains constants that define the gateway address, the network mask, and the MAC address. You must ensure that the configured MAC address is unique on the network to which the prototyping board is being connected.
Demo/lwIP_Demo_Rowley_ARM7/EMAC/SAM7_EMAC.c contains the definition USE_RMII_INTERFACE. This must be set appropriately for your hardware. Setting USE_RMII_INTERFACE to 1 configures the MAC to operate in RMII mode. Setting USE_RMII_INTERFACE to 0 configures the MAC to operate in MII mode.
A USB connection between the target hardware and a Windows host is required if you wish to test the USB CDC driver. The target board can source its power through the same cable. The USB device will identify itself to the host as a serial COM port, then when connected continuously stream a string of characters at 115,200 baud. The data is sent to the CDC driver from an idle task hook.
The demo application uses the LEDs built onto the prototyping board so no other hardware setup is required.
Simply open the rtosdemo.eww workspace file from within the CrossWorks IDE, ensure THUMB flash debug is the selected
configuration (see picture below), then select 'Build Solution' from the IDE 'Build' menu.
When executing correctly the demo application will behave as follows:
LED DS4 is under control of the 'Check' task. Every three seconds the 'Check' task examines all the standard demo tasks in the system to ensure they are executing without error. It then toggles LED DS4. If LED DS4 is toggling every three seconds then no errors have ever been detected. The toggle rate increasing to 500ms indicates that the 'Check' task has discovered at least one error.


Direct the wizard to the directory FreeRTOS/Demo/lwIP_Demo_Rowley_ARM7/USB where the file FreeRTOSCDC.inf will instruct Windows how to communicate with the CDC device.
Once the driver has been successfully installed the SAM7X target will appear as serial COM port and continuously stream data bytes to the host.

The transmitted data can be viewed using any dumb terminal program (for example HyperTerminal) set to 115200 baud, with 8 data bits, no parity, one stop bit and no flow control.

The chained memory buffer implementation within the lwIP stack results in data being sent to and from the EMAC driver in multiple segments of variable length. This is in contract to the uIP stack where only a single buffer exists, and all data can be copied to and from the EMAC driver in a single segment. The EMAC driver used by the lwIP demo therefore includes more comprehensive management of EMAC peripheral than the equivalent driver used by the uIP project.
Data received by the EMAC is buffered under control of the DMA. When a buffer is available for processing an EMAC interrupt is generated. All the interrupt service routine does is signal to the EMAC driver via a semaphore that data is available for processing. The semaphore immediately unblocks the interface task which processes the data, and if necessary either generates a response or passes the data to the TCP/IP stack.
The driver blocks on the semaphore with a timeout. Therefore should no data become available for processing, the task will periodically unblock to carry out the periodic processing required by the TCP/IP stack.
The number of receive buffers available to the EMAC is set by the constant NB_RX_BUFFERS within the file Demo/lwIP_Demo_Rowley_ARM7/EMAC/emac.h. Each receive buffer is 128 bytes, this size is specific to the hardware and must not be altered.
The number of transmit buffers available to the EMAC is set by the constant NB_TX_BUFFERS also within emac.h.
Each port #defines 'portBASE_TYPE' to equal the most efficient data type for that processor. This port defines portBASE_TYPE to be of type long.
Note that vPortEndScheduler() has not been implemented.
void vASimpleISR( void ) __attribute__((interrupt("IRQ")));
void vASimpleISR( void )
{
/* ISR code goes here. */
}
Note: The method of forcing a context switch from within an ISR has changed since FreeRTOS.org V4.5.0. Unfortunately the new method requires different syntax, but is no longer dependent on the version of the compiler used, the command line switches, or the optimisation level. Changing to the method described here should therefore remove the need to make any further alterations in the future.
The example here assumes that the interrupt handler is vectored to directly - that is, there is no entry code that is common to all interrupts. Some of the other FreeRTOS.org demo applications are configured to use a common entry point as an alternative to this method.
To write an interrupt service routine that can cause a context switch:
/* Declare the wrapper function using the naked attribute.*/
void vASwitchCompatibleISR_Wrapper( void ) __attribute__ ((naked));
/* Declare the handler function as an ordinary function.*/
void vASwitchCompatibleISR_Handler( void );
/* The handler function is just an ordinary function. */
void vASwitchCompatibleISR_Handler( void )
{
portLONG lSwitchRequired = pdFALSE;
/* ISR code comes here. If the ISR wakes a task then
lSwitchRequired should be set to 1. */
/* If the ISR caused a task to unblock, and the priority
of the unblocked task is higher than the priority of the
interrupted task then the ISR should return directly into
the unblocked task. portYIELD_FROM_ISR() is used for this
purpose. */
if( lSwitchRequired )
{
portYIELD_FROM_ISR();
}
}
void vASwitchCompatibleISR_Wrapper( void )
{
/* Save the context of the interrupted task. */
portSAVE_CONTEXT();
Call the handler function. This must be a separate
function unless you can guarantee that handling the
interrupt will never use any stack space. */
vASwitchCompatibleISR_Handler();
/* Restore the context of the task that is going to
execute next. This might not be the same as the originally
interrupted task.*/
portRESTORE_CONTEXT();
}
NOTE! : The processor MUST be in supervisor mode when the scheduler is started (vTaskStartScheduler is called). The demo applications included in the FreeRTOS.org download switch to supervisor mode prior to main being called. If you are not using one of these demo application projects then ensure Supervisor mode is entered before calling vTaskStartScheduler().
Interrupt service routines always run in ARM mode. All other code will run in either ARM or THUMB mode depending on the build. It should be noted that some of the macros defined in portmacro.h can only be called from ARM mode code, and use from THUMB code will result in a compile time error. Please note that this particular demo has only been tested using THUMB mode.
Stacks have only been allocated for system/user, IRQ and SWI modes.
SWI instructions are used by the real time kernel and can therefore not be used by the application code (without modification of the kernel code).
Note that, depending on the version of GCC used, the makefile may require the optimisation level to be set to a minimum of O1. Alternatively the -fomit-frame-pointer option can be added to the CFLAGS.
Linux users please note that as I don't have access to a Linux host the makefile has only been tested on a case insensitive Win32 host. Any build problems experienced on a Linux host are likely to
be the result of a file name having incorrect capitalisation. Please let me know if any such issues are encountered so they can be rectified in future releases.
Any and all data, files, source code, html content and documentation included in the FreeRTOS.org distribution or available on this site are the exclusive property of Real Time Engineers Ltd..
See the files license.txt (included in the distribution) and this copyright notice for more information. FreeRTOSTM and FreeRTOS.orgTM are trade marks of Real Time Engineers Ltd..