Quality RTOS & Embedded Software

 Real time embedded FreeRTOS RSS feed 
Real time embedded FreeRTOS mailing list 
Quick Start Supported MCUs PDF Books Trace Tools Ecosystem TCP & FAT Training


+TCP used as L3 bridge

Posted by glenenglish on April 18, 2017

Hi all I want to use my FreeRTOS+TCP device as a L3 bridge (living behind a router) That is to say, there are two boxes which are radio modems. Each end runs freertos+TCP. I know the source code pretty well Now, the implementation is trivial but has anyone done this ?

Does anyone have any suggestions on WHERE to hook in the bridge logic and keep all the other stuff happy? Essentially I have to pick it off some in

prvProcessEthernetPacket() and check if the dst addr is our addr or 'the other end' and or prvProcessIPPacket()

on the send side, I need to do the reverse of course, inject up the stream...

In the usage case, the device (modem) will be connected to a router. .The router will route traffic to the device for traffic destined to the other subnets. IE its not actually used for bridging two networks,, but for routing between networks. I find the best way to do this sort of thing using microwave links is to put routers are each end of the link (like, the other end , and run the link itself as a bridge (with its own subnet ) etc etc

anyway, requirements are pretty much the same, I use the term bridge because that's what it is doing. something else will do the routing and handle the routing tables etc


+TCP used as L3 bridge

Posted by heinbali01 on April 19, 2017

Hi Glen,

First some general information:

The IP-task sends all packets to Ethernet by calling this driver function:

~~~ BaseType_t xNetworkInterfaceOutput( pxDescriptor, t bReleaseAfterSend ); ~~~

The IP-task receives Ethernet packets by receiving eNetworkRxEvent messages in its queue ( xNetworkEventQueue ). A driver can send network buffers to that queue by calling xSendEventStructToIPTask().

Those are the two paths between +TCP and the Ethernet.

About 'internal' routing: the current implementation is simple:

  • Every target that is within the netmask is contacted directly (using ARP look-up)
  • Packets to other IP-addresses will be sent to the gateway, if any.

But every packet will finally be sent by the same xNetworkInterfaceOutput().

Now you want to route packets that come from your LAN, and forward them to a radio-connection and v.v., true?

prvProcessEthernetPacket() and check if the dst addr is our addr or 'the other end'

I think it's a good place to forward packets! prvProcessEthernetPacket() will handle every packet that has been received by NetworkInterface.c (i.e. from the LAN).

Something like the following ?

~~~ void prvProcessEthernetPacket( NetworkBufferDescriptort * const pxNetworkBuffer ) { EthernetHeadert *pxEthernetHeader; volatile eFrameProcessingResult_t eReturned;

     configASSERT( pxNetworkBuffer );
  • if( xToMyRouter( pxNetworkBuffer ) )
  • {
  • /* The packet has bee forwarded to a router. */
  • eReturned = eFrameConsumed;
  • }
  • else { /* Interpret the Ethernet frame. */ eReturned = ipCONSIDERFRAMEFORPROCESSING( pxNetworkBuffer->pucEthernetBuffer ); pxEthernetHeader = ( EthernetHeadert * ) ( pxNetworkBuffer->pucEthernetBuffer ); }

     if( eReturned == eProcessBuffer )

    } ~~~

So if the function xToMyRouter() handles / forwards the packet, it gets ownership of the network buffer ( call vReleaseNetworkBufferAndDescriptor() after use ), and it must return a non-zero value. Do not block, just queue the network buffer, in order not to hold-up the IP-task. If this approach turns out to be useful, we could make some permanent application hook here.

I suppose that you will also create a task that monitors / receives packets from the radio-connection. We miss something here. You would like to call xNetworkInterfaceOutput() directly to forward the packet to the LAN, true? But the code in NetworkInterface.c assumes that the xNetworkInterfaceOutput() function is non re-entrant. The IP-task does not have a message type to forward a packet to the LAN. We could add that type of messages:

~~~ eNetworkDownEvent, /* 0: The network interface has been lost and/or needs [re]connecting. / eNetworkRxEvent, / 1: The network interface has queued a received Ethernet frame. / eARPTimerEvent, / 2: The ARP timer expired. / eStackTxEvent, / 3: The software stack has queued a packet to transmit. / + eForwardTxPacketEvent, / 4: Blindly forward a packet by passing it to xNetworkInterfaceOutput(). / eDHCPEvent, / 5: Process the DHCP state machine. */

/* And in prvIPTask() in FreeRTOS_IP.c */

 switch( xReceivedEvent.eEventType )
     case eForwardTxPacketEvent:
         /* Set the `bReleaseAfterSend` parameter to true, to pass the ownership to the driver. */
         xNetworkInterfaceOutput( ( NetworkBufferDescriptor_t * ) xReceivedEvent.pvData, pdTRUE );


eStackTxEvent is a bit misleading, it will only handle UDP-packets. It was added at the time when the library was still called +UDP :-)

Or you could change the implementation of xNetworkInterfaceOutput() to become re-entrant.

I hope that I answered your question. Regards.

+TCP used as L3 bridge

Posted by glenenglish on April 19, 2017

Hi Hein thank you for the time to write that up.

Essentially it is a layer 3 switch with only one other destination (IE all packets != me send to radio)

Yes, on receiving data packets from the demodulator (the RX side of the MODEM) , I will write some code to push it into a queue just like a UDP packet would be, except of course, it is the 'whole packet'. (IE I wont just push out the network, they'll join a queue just like other protocols.

So I will need to add some functionality to the stack , which will be pretty easy. Whether it becomes mainline is another thing I guess, its a corner case...

I will need to learn a bit more about routers and the fine print, also (IE special behviour that the router connected to my modem-bridge expects from me) .

cheers - glen

[ Back to the top ]    [ About FreeRTOS ]    [ Sitemap ]    [ ]

Copyright (C) 2004-2010 Richard Barry. Copyright (C) 2010-2016 Real Time Engineers Ltd.
Any and all data, files, source code, html content and documentation included in the FreeRTOSTM 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.

Latest News:

FreeRTOS V9.0.0 is now available for download.

Free TCP/IP and file system demos for the RTOS

Sponsored Links

⇓ Now With No Code Size Limit! ⇓
⇑ Free Download Without Registering ⇑

FreeRTOS Partners

ARM Connected RTOS partner for all ARM microcontroller cores

Renesas Electronics Gold Alliance RTOS Partner.jpg

Microchip Premier RTOS Partner

RTOS partner of NXP for all NXP ARM microcontrollers

Atmel RTOS partner supporting ARM Cortex-M3 and AVR32 microcontrollers

STMicro RTOS partner supporting ARM7, ARM Cortex-M3, ARM Cortex-M4 and ARM Cortex-M0

Xilinx Microblaze and Zynq partner

Silicon Labs low power RTOS partner

Altera RTOS partner for Nios II and Cortex-A9 SoC

Freescale Alliance RTOS Member supporting ARM and ColdFire microcontrollers

Infineon ARM Cortex-M microcontrollers

Texas Instruments MCU Developer Network RTOS partner for ARM and MSP430 microcontrollers

Cypress RTOS partner supporting ARM Cortex-M3

Fujitsu RTOS partner supporting ARM Cortex-M3 and FM3

Microsemi (previously Actel) RTOS partner supporting ARM Cortex-M3

Atollic Partner

IAR Partner

Keil ARM Partner

Embedded Artists