Tutorial: lwip with FreeRTOS and the Freescale FRDM-K64F Board

This tutorial is about how to create a lwIP project with FreeRTOS using the Kinetis SDK V1.3.0 with Kinetis Design Studio on the Freescale FRDM-K64F board.

FRDM-K64F Board with lwIP running

FRDM-K64F Board with lwIP running

I would like to thank Frank Bargstedt for providing me the many hints and steps for this tutorial. Without his contribution I think I would not have been able to create this article. THANK YOU!

Introduction

lwIP is a small Open Source TCP/IP implementation suitable for small systems. The project can be found on http://savannah.nongnu.org/projects/lwip/. The Kinetis SDK comes with an lwIP port which I’m going to use in this project. The goal is to create a project with lwIP and FreeRTOS running on the FRDM-K64F board.

Preconditions

For this project I assume you have the following available/installed (see links at the end of this article):

  1. Freescale Kinetis Design Studio (KDS) V3.0.0. Alternatively stock Eclipse with Processor Expert installed (see “Going to Mars: Building a DIY Eclipse IDE for ARM Embedded Microcontrollers“) can be used.
  2. Freescale Kinetis SDK (KSDK) V1.3.0 and Kinetis SDK Eclipse update installed in Eclipse/KDS
  3. McuOnEclipse components Components 2015-10-17.zip or later
  4. FRDM-K64F board with cables, connected to a router with DHCP

Project Creation

In KDS, use the menu File > New > Kinetis Project to create a new project.

Provide a name for the project:

Creating Project

Creating Project

Select the board:

Selecting FRDM-K64F Board

Selecting FRDM-K64F Board

Select the Kinetis SDK with Processor Expert enabled:

KSDK v1.3.0 Processor Expert Project

KSDK v1.3.0 Processor Expert Project

Then finish, and the proejct is created.

Pin Settings

The next step is to check the pin muxing and pin settings:

PinSettings

PinSettings

By default the ENET pins are not routed:

Default ENET Pins

Default ENET Pins

In a first step have all pins routed:

Routed ENET Pins

Routed ENET Pins

Next we have to configure the RMII0_MDIO pin: for this we use the context menu on that pin and select ‘Pin Functional Properties’:

Context menu on RMII0_MDIO

Context menu on RMII0_MDIO

Configure the pin for slow slew rate, enabled open drain, low drive strength, disabled passive filter, pull-up selection with enabled pull-up as below:

Pin Electrical Properties

Pin Electrical Properties

❗ Important: without the above settings the ENET will not properly work!

fsl_enet Component

Next, add the fsl_enet SDK component from the Components Library to the project:

Adding fsl_enet component

Adding fsl_enet component

This adds the component to the project. It’s settings can be at the default settings.

fsl_enet added to project

fsl_enet added to project

Clock Configuration

In this section the clock gets configured. It is important that the clock is in sync with the PHY clock which runs at 50 MHZ. The settings I need to check are in the Clock Manager:

Clock Manager

Clock Manager

By default, the project has multiple clock configurations (which are a waste of code and RAM!):

Clock Configurations

Clock Configurations

Clicking into the line and using the ‘-‘ icon I can remove the configurations:

Removing Clock Configurations

Removing Clock Configurations

I reduce it to only one and set it as the Init clock Configuration:

Reduced number of clock configurations

Reduced number of clock configurations

That configuration I set to maximum clock speed with the 50 MHz clock source:

  • Clock source: External Reference Clock with 50 MHz from EXTAL0
  • MGG Mode set to PEE
  • PLL output set to 120 MHz
  • Core Clock set to 120 MHz
  • Bus Clock set to 60 MHz
  • External Bus Clock set to 40 MHz
  • Flash Clock set to 24 MHz
Clock Management Settings

Clock Management Settings

fsl_os_abstraction

The default OS abstraction in the Kinetis SDK v1.3.0 comes with unnecessary overhead, so it needs some configuration:

fsl_os_abstraction

fsl_os_abstraction

I disable the OS Timers for bare metal mode as they are not needed:

Disabled OS Timers

Disabled OS Timers

FreeRTOS

Next, FreeRTOS gets added. I’m *not* using the FreeRTOS component which comes with the Kinetis SDK V1.3.0 as it is an older version and does not support advanced features like RTT Tracing (see “ Search Using Segger Real Time Terminal (RTT) with Eclipse“).

So I’m using the McuOnEclipse FreeRTOS component from the repository:

Adding McuOnEclipse FreeRTOS component

Adding McuOnEclipse FreeRTOS component

This adds FreeRTOS plus the Utility component to the project:

Added FreeRTOS

Added FreeRTOS

FreeRTOS gets configured as below:

  1. To prepare the RTOS to work with the Kinetis SDK, enable the SDK option and add the Kinetis SDK component to it:

    Enabled Kinetis SDK for RTOS

    Enabled Kinetis SDK for RTOS

  2. Verify the ARM CPU used, in the case of the FRDM-K64F it is an ARM Cortex-M4F with floating point support:

    Kinetis ARM Family Setting

    Kinetis ARM Family Setting

  3. As the rest of the SDK is using malloc()/free() too, I set the RTOS memory allocation to Scheme 3 too, with an appropriate Heap Size:

    Memory Allocation Scheme

    Memory Allocation Scheme

Enable Timers in the RTOS settings:

FreeRTOS Timers

FreeRTOS Timers

In the compiler preprocessor settings (menu Project > Properties) I need to tell the SDK that I’m using FreeRTOS with a define:

FSL_RTOS_FREE_RTOS
Added FSL_RTOS_FREE_RTOS Compiler Preprocessor Define

Added FSL_RTOS_FREE_RTOS Compiler Preprocessor Define

Generating Processor Expert Code

With all the components configured, I can generate Processor Expert code:

Generating Processor Expert Code

Generating Processor Expert Code

If this requires some file changes, a confirmation dialog might show up which I confirm with OK:

Confirm File Changes

Confirm File Changes

PHY Driver

The FRDM-K64F uses the ‘ksz8081’ PHY. To add the driver for it to my project I copy the following files

  • fsl_phy_driver.c
  • fsl_phy_driver.h

from

C:\Freescale\KSDK_1.3.0\middleware\tcpip\rtcs\source\port\phyksz8081
PHY Drivers

PHY Drivers

and add them to my project Sources folder:

Added PHY Driver

Added PHY Driver

Semihosting

I would like to use semihosting (see “Semihosting for Kinetis Design Studio V3.0.0 and GNU ARM Embedded (launchpad)“) to write messages to the debugger console instead of using a physical UART.

First, I add a file ‘fsl_debug_console.h’ to the sources:

which has defines to map debug printf calls to the normal printf:

/*
 * fsl_debug_console.h
 *
 * Map printf for semihosting implementation.
 */

#ifndef SOURCES_FSL_DEBUG_CONSOLE_H_
#define SOURCES_FSL_DEBUG_CONSOLE_H_

#define PRINTF printf
#define debug_printf printf

#endif /* SOURCES_FSL_DEBUG_CONSOLE_H_ */
fsl_debug_console added to project

fsl_debug_console added to project

To tell the linker that I’m using semihosting, I use the following linker commands:

-specs=rdimon.specs -specs=nano.specs
Semihosting Linker Commands

Semihosting Linker Commands

Kinetis SDK Utilities

The Kinetis SDK utilities and internal printf routines do not play well with semihosting, so I had to disable it:

Disabled SDK utilities

Disabled SDK utilities

This can be easily done with using the context menu on that folder and exclude the resource from build:

Excluded from Build

Excluded from Build

lwIP

In this step the lwIP stack gets added to the project. There is a port of lwIP inside the Freescale Kinetis SDK V1.3.0 folder:

lwIP in the Kinetis SDK V1.3.0

lwIP in the Kinetis SDK V1.3.0

Copy the lwip folder into the project root folder:

lwip added to project

lwip added to project

I’m not going to use IPV6, so I delete the ipv6 folders, otherwise I will get compilation errors with both ipv6 and ipv4 active:

ipv6 removed

ipv6 removed

In order to the compiler to find all the header files, I’m adding the following include paths to the compiler settings:

"..\lwip\src\include"
"..\lwip\src\include\lwip"
"..\lwip\src\include\ipv4"
"..\lwip\port"

💡 I can copy-paste paths settings to the dialog in Eclipse.

lwip include paths

lwip include paths

Application Code

As application code I add this to main.c:

#define DHCP_TIMEOUT 10

#include "lwip/api.h"
#include "lwip/tcpip.h"
#include "lwip/udp.h"
#include "lwip/dhcp.h"
#include "netif/etharp.h"
#include "ethernetif.h"

#include <string.h>
#include <stdio.h>
/* providing a debug_printf() to make the linker happy */
int debug_printf(const char *fmt_s, ...)
{
#if 0
 va_list ap;
 int result;
 /* Do nothing if the debug uart is not initialized.*/
 if (s_debugConsole.type == kDebugConsoleNone)
 {
 return -1;
 }
 va_start(ap, fmt_s);
 result = _doprint(NULL, debug_putc, -1, (char *)fmt_s, ap);
 va_end(ap);

 return result;
#else
 return -1;
#endif
}

#if 1 /* depending on the GNU tools and libraries, a custom _sbrk() is needed */
void *_sbrk ( uint32_t delta ) {
extern char end; /* Defined by the linker */
static char *heap_end;
char *prev_heap_end;

 if (heap_end == 0) {
 heap_end = &end;
 }

 prev_heap_end = heap_end;
 heap_end += delta;
 return (void *) prev_heap_end;
}
#endif

static void LwipInitTask(void* pvArguments) {
 err_t err;
 struct netif fsl_netif0;
 ip_addr_t fsl_netif0_ipaddr, fsl_netif0_netmask, fsl_netif0_gw;

 char msg[] = "This is my message";

 (void)pvArguments;

 // Init lwip stack
 tcpip_init(NULL,NULL);
 printf("%s: lwip init called ..\n", __FUNCTION__);

 // Setup IP Config for DHCP ...
 IP4_ADDR(&fsl_netif0_ipaddr, 0,0,0,0);
 IP4_ADDR(&fsl_netif0_netmask, 0,0,0,0);
 IP4_ADDR(&fsl_netif0_gw, 0,0,0,0);

 /* Add a network interface to the list of lwIP netifs. */
 netif_add(&fsl_netif0, &fsl_netif0_ipaddr, &fsl_netif0_netmask, &fsl_netif0_gw, NULL, ethernetif_init, ethernet_input);
 /* Set the network interface as the default network interface. */
 netif_set_default(&fsl_netif0);
 /* obtain the IP address, default gateway and subnet mask by using DHCP*/
 err = dhcp_start(&fsl_netif0);

 printf("%s : Started DCHP request (%s)\n", __FUNCTION__, lwip_strerr(err));

 for(int i=0; i < DHCP_TIMEOUT && fsl_netif0.dhcp->state != DHCP_BOUND; i++) {
 printf("%s : Current DHCP State : %d\n", __FUNCTION__, fsl_netif0.dhcp->state);
 // Wait a second
 vTaskDelay(1000/portTICK_PERIOD_MS);
 }

 // Make it active ...
 netif_set_up(&fsl_netif0);

 printf("%s : Interface is up : %d\n", __FUNCTION__, fsl_netif0.dhcp->state);
 printf("%s : IP %s\n", __FUNCTION__, ipaddr_ntoa(&fsl_netif0.ip_addr));
 printf("%s : NM %s\n", __FUNCTION__, ipaddr_ntoa(&fsl_netif0.netmask));
 printf("%s : GW %s\n", __FUNCTION__, ipaddr_ntoa(&fsl_netif0.gw));

 if (fsl_netif0.dhcp->state == DHCP_BOUND) {
 // Send out some UDP data
 struct netconn* pConnection;

 // Create UDP connection
 pConnection = netconn_new(NETCONN_UDP);
 // Connect to local port
 err = netconn_bind(pConnection, IP_ADDR_ANY, 12345);
 printf("%s : Bound to IP_ADDR_ANY port 12345 (%s)\n", __FUNCTION__, lwip_strerr(err));

 err = netconn_connect(pConnection, IP_ADDR_BROADCAST, 12346 );
 printf("%s : Connected to IP_ADDR_BROADCAST port 12346 (%s)\n", __FUNCTION__, lwip_strerr(err));

 for(int i = 0; i < 10; i++ ){
 struct netbuf* buf = netbuf_new();
 void* data = netbuf_alloc(buf, sizeof(msg));

 memcpy (data, msg, sizeof (msg));
 err = netconn_send(pConnection, buf);
 printf("%s : Sending to IP_ADDR_BROADCAST port 12346 (%s)\n", __FUNCTION__, lwip_strerr(err));

 netbuf_delete(buf); // De-allocate packet buffer

 // Wait a second
 vTaskDelay(1000/portTICK_PERIOD_MS);
 }

 err = netconn_disconnect(pConnection);
 printf("%s : Disconnected from IP_ADDR_BROADCAST port 12346 (%s)\n", __FUNCTION__, lwip_strerr(err));

 err = netconn_delete(pConnection);
 printf("%s : Deleted connection (%s)\n", __FUNCTION__, lwip_strerr(err));
 }
 // Wait a second
 vTaskDelay(1000/portTICK_PERIOD_MS);

 /* finish the lease of the IP address */
 err = dhcp_release(&fsl_netif0);
 printf("%s : DHCP Release (%s)\n", __FUNCTION__, lwip_strerr(err));

 for(;;) {};
}

And call it inside main() like below. An important point is that the MPU of the K64F needs to be disabled:

 printf("Welcome to the world of lwip!\r\n");

 /* Disable the mpu */
 MPU_BWR_CESR_VLD(MPU, 0);

 /* create lwIP initialization task */
 xTaskCreate(LwipInitTask,
   "LwipInitTask",
   configMINIMAL_STACK_SIZE * 4,
   (void*)NULL,
   tskIDLE_PRIORITY,
   (xTaskHandle*)NULL);

After that, the RTOS gets started with vTaskStartScheduler().

Example Session

With this, I can build, download and debug the application. With the network cable plugged in, the application writes the status to the semihosting console. It starts with a DHCP request and then does some IP broadcasts and at the end releases the address and closes the connection:

Welcome to the world of lwip!
LwipInitTask: lwip init called ..
LwipInitTask : Started DCHP request (Ok.)
LwipInitTask : Current DHCP State : 6
LwipInitTask : Current DHCP State : 6
LwipInitTask : Current DHCP State : 6
LwipInitTask : Current DHCP State : 8
LwipInitTask : Interface is up : 10
LwipInitTask : IP 192.168.0.123
LwipInitTask : NM 255.255.255.0
LwipInitTask : GW 192.168.0.1
LwipInitTask : Bound to IP_ADDR_ANY port 12345 (Ok.)
LwipInitTask : Connected to IP_ADDR_BROADCAST port 12346 (Ok.)
LwipInitTask : Sending to IP_ADDR_BROADCAST port 12346 (Ok.)
LwipInitTask : Sending to IP_ADDR_BROADCAST port 12346 (Ok.)
LwipInitTask : Sending to IP_ADDR_BROADCAST port 12346 (Ok.)
LwipInitTask : Sending to IP_ADDR_BROADCAST port 12346 (Ok.)
LwipInitTask : Sending to IP_ADDR_BROADCAST port 12346 (Ok.)
LwipInitTask : Sending to IP_ADDR_BROADCAST port 12346 (Ok.)
LwipInitTask : Sending to IP_ADDR_BROADCAST port 12346 (Ok.)
LwipInitTask : Sending to IP_ADDR_BROADCAST port 12346 (Ok.)
LwipInitTask : Sending to IP_ADDR_BROADCAST port 12346 (Ok.)
LwipInitTask : Sending to IP_ADDR_BROADCAST port 12346 (Ok.)
LwipInitTask : Disconnected from IP_ADDR_BROADCAST port 12346 (Ok.)
LwipInitTask : Deleted connection (Ok.)
LwipInitTask : DHCP Release (Ok.)
lwip session

lwip session

Possible Problems

After publishing this article, there has been a problem report in the community (https://community.nxp.com/thread/381894). The problem is if the received frames are handled in an interrupt context and passed up the lwip stack. This causes problems with reentrance and can cause an assertion.

The solution is to set the following define to zero in <Kinetis SDK>\platform\drivers\inc\fsl_enet_driver.h

#ifndef ENET_RECEIVE_ALL_INTERRUPT
  #define ENET_RECEIVE_ALL_INTERRUPT  0
#endif

Summary

A long-time-waiting thing on my to-do list finally has been accomplished: It takes many pieces to build the basis of a network IP application, and lwip for sure is a good and well documented open source project. With the help of Processor Expert many aspects of the networking application get simplified, and after some tweaks the Kinetis SDK is now working too.

The project created in this tutorial is on GitHub: https://github.com/ErichStyger/mcuoneclipse/tree/master/Examples/KDS/FRDM-K64F120M/FRDM-K64F_lwIP_FreeRTOS.

Happy Networking 🙂

Links

72 thoughts on “Tutorial: lwip with FreeRTOS and the Freescale FRDM-K64F Board

  1. Hi
    I have tried following your tutorial and i have downloaded your example from git but i always get stuck in mallocFailhook. I get stuck in LwipInitTask so the program is started. Does anyone have any idea in what could be wrong.
    Thanks for a great tutorial.

    Best regards
    Andreas

    Like

    • Hi Andreas,

      Did you change the FreeRTOS Memory Allocation Scheme to “Scheme 3” ? Normally this should take care of your problem.

      Regards

      Frank

      Like

        • You need to make sure you have enough heap allocated. If you are using Heap3 (which you should use): make sure you have enough heap allocated in the linker file. Have you checked this?

          Like

    • As I wasn’t able to reply to your last post (Regarding the linker options). I don’t think that you missed some linker options, if you have the ones given “–specs=rdimon.specs –specs=nano.specs”.
      I recreated the project based on the above tutorial and I didn’t see any problems (Besides some problems with the “Application Code”, as the one in this posting currently is having some trouble .. So I used the code from github.)

      Previously I had the same problem, with the code getting stuck in the “mallocFailed” hook, but this was due to the “wrong” scheme (The FreeRTOS component used has the default set to “Scheme 2” and for some reason it always got stuck in the failed hook). After changing the scheme to “Scheme 3”, regenerating the Processor Expert Code and recompiling everything it worked okay.

      Regards

      Frank

      Like

      • Another thought I have: I’m using the 4.9q2 GNU ARM Embedded toolchain, and that might have an impact. Using heap Scheme3 means that the normal malloc()/free() is used, and and the FreeRTOS heap size has no effect. Instead, the heap needs to be allocated somewhere. I have now set the heap size in Processor Expert CPU component > Build Optiosn > Generate Link File > Heap Size to 0x2000 (8 kByte). The heap size is defined usually in the linker file with HEAP_SIZE, so make sure you have at least 8 KByte allocated there.

        Like

        • lwIP has defined its own heap size in lwipopts.h:
          #define MEM_SIZE (12*1024)
          and has in opt.h a setting to use its own malloc (and not the one from libc):
          /**
          * MEM_LIBC_MALLOC==1: Use malloc/free/realloc provided by your C-library
          * instead of the lwip internal allocator. Can save code size if you
          * already use it.
          */
          #ifndef MEM_LIBC_MALLOC
          #define MEM_LIBC_MALLOC 0
          #endif
          So with this, lwIP is using its own heap for its data stuctures.
          Still, with Scheme3 (using malloc()) FreeRTOS needs some heap from the clib.

          I have in my linker file this:
          HEAP_SIZE = DEFINED(__heap_size__) ? __heap_size__ : 0x2000;
          where the 0x2000 comes from the Processor Expert CPU component.
          Having a heap size set to zero, in my case the heap will start at 0x2000’0000 and just grow, without checking for the heap end (a problem in the _sbrk() implementation I have on GitHub). It actually should check against __HeapLimit 😦

          Like

      • Hi again
        I have now tried to update the toolchain to 4.9q2 and it seems to work now.

        Thanks again for all the answers!

        regards
        Andreas

        Like

    • Andreas,

      Something to check (because it bit my team) is if you have included the sbrk() function replacement. The KDS SDK uses the GCC libraries to create a runtime. The version of sbrk in GCC does a test of the proposed heap top against the current stack pointer and will return error if they cross. With lwIP, each task has their stack allocated from the heap so this test will fail when your tasks try to malloc memory. The fsl_misc_utilities.c file has a version of sbrk() that will work with lwIP.

      Note that Erich wrote an article about this last year:

      FreeRTOS, malloc() and SP check with GNU Tools

      Like

      • Hi
        Yes I have this piece of code activated in main.c

        #if 1 /* depending on the GNU tools and libraries, a custom _sbrk() is needed */
        void *_sbrk ( uint32_t delta )
        {
        extern char end; /* Defined by the linker */
        static char *heap_end;
        char *prev_heap_end;

        if (heap_end == 0) {
        heap_end = &end;
        }

        prev_heap_end = heap_end;
        heap_end += delta;
        return (void *) prev_heap_end;
        }
        #endif

        regards
        Andreas

        Like

      • Hi all! This worked for me also! I had to add -z muldefs option to the linker settings as instructed above. Otherwise, the linker will complain about multiple definitions.

        Like

  2. Hi
    i have now tried the same code on my computer at home with another installation and it worked perfectly there. I have to look into what installation of the toolchain I have on the different computers. At least I have one installation where it works.

    Thanks for all the tips about the problem.

    Best regards
    Andreas

    Like

  3. Hi,

    can one of you tell me which version of lwip freescale decided to package into the KSDK installation?
    Can’t find a version number in the source files.

    Like

  4. After attempting to follow along I discovered the version of Eclipse you used was not the same as the latest: PE 3.0+PE3.0.1 update +KSDK 1.3.0 with your components from this month along with the project from 11/13/2015, well the whole Git thing.
    In your example the settings are in a spreadsheet like format the current version has tabs and windows and the setting names are not the same or missing.
    Then I read about the issues with examples on MCUonEclipse and downloaded the projects.
    The Project:
    X#include “FreeRTOS.h”
    ?#include “semphr.h”
    ?#include “event_groups.h”
    So I notice FreeRTOS doesn’t appear to be in your project?
    Any thoughts?

    Like

    • I moved on from KDS 3.0 to DYI with 32-bit MARS.1 now the issue is worse:
      Description Resource Path Location Type
      Error in the inherited component settings (Runtime Counter LDD) FRDM-K64F_lwIP_FreeRTOS FRTOS1/Runtime Counter LDD Processor Expert Problem
      ERROR: This component is not supported in Kinetis SDK project mode FRDM-K64F_lwIP_FreeRTOS RTOSCNTRLDD1 Processor Expert Problem
      Generator: ERROR: There are errors in the project, please review components configuration. It is not possible to generate code. FRDM-K64F_lwIP_FreeRTOS Code Generator Processor Expert Problem
      HW doesn’t support this feature (Counter direction) FRDM-K64F_lwIP_FreeRTOS RTOSCNTRLDD1/Counter direction Processor Expert Problem
      HW doesn’t support this feature (Counter restart) FRDM-K64F_lwIP_FreeRTOS RTOSCNTRLDD1/Counter restart Processor Expert Problem
      The component is not supported for selected processor (Component name) FRDM-K64F_lwIP_FreeRTOS RTOSCNTRLDD1/Component name Processor Expert Problem
      This interrupt is required (Interrupt) FRDM-K64F_lwIP_FreeRTOS RTOSCNTRLDD1/Interrupt Processor Expert Problem
      Type ‘xTaskHandle’ could not be resolved Events.c /FRDM-K64F_lwIP_FreeRTOS/Sources line 55 Semantic Error
      Unassigned peripheral (Counter frequency) FRDM-K64F_lwIP_FreeRTOS RTOSCNTRLDD1/Counter frequency Processor Expert Problem
      Unassigned peripheral (Counter) FRDM-K64F_lwIP_FreeRTOS RTOSCNTRLDD1/Counter Processor Expert Problem
      Unassigned peripheral (Overrun period) FRDM-K64F_lwIP_FreeRTOS RTOSCNTRLDD1/Overrun period Processor Expert Problem
      Invalid project path: Include path not found (D:MCUEclipseExampExamplesKDSFRDM-K64F120MFRDM-K64F_lwIP_FreeRTOSGenerated_CodeSDKplatformdevicesMK64F12startup). FRDM-K64F_lwIP_FreeRTOS pathentry Path Entry Problem

      I can’t find any information is the project about this.

      Like

      • Thanks for the quick responce. When I restarted my new install of eclipse 32-bit it hung so I had to start it in a new workspace. I Imported the project and told it to MOVE the files this time and here are the new errors:
        Description Resource Path Location Type
        Invalid project path: Include path not found (C:UsersKevinwork32FRDM-K64F_lwIP_FreeRTOSGenerated_CodeSDKplatformdevicesMK64F12startup). FRDM-K64F_lwIP_FreeRTOS pathentry Path Entry Problem
        That is it, one error, so the ‘linking’ thing is doing something.

        If I leave Eclipse running all the time I can save and make changes but when I close it, when it restarts and tries to open the project it hangs without leaving a .log file. Does it in 32/64-bit on my workstation and my PC with only one CPU and a SLED drive.
        Both computers have Windows 10.

        Like

        • Hi Kevin,
          I’m not running Windows 10 (I only have it on an old notebook installed for tests), but have not seen something like this. You don’t need to move/copy the files, simply import it into the workspace (no need for copy). Does that path/folder exist on your system? Maybe there is a Windows 10 security setting or something preventing the compiler to find that path?

          Like

  5. I think I FINALLY found the problem with the ‘HANG’ while starting Eclipse: Close all Projects before exiting. I have hunted around but have not found anything about exiting Eclipse. More on this in a few days after it runs for a while, both the 32 and 64 bit version.

    When I first Imported the Project FRDM-K64F_lwIP_FreeRTOS I didn’t check the Copy projects into workspace option and that choice caused many errors with the ‘path’. The location was D:MCUEclipseExampExamplesKDSFRDM-K64F120MFRDM-K64F_lwIP_FreeRTOS

    When I Imported the Project FRDM-K64F_lwIP_FreeRTOS with Copy checked I only got one error:
    Invalid project path: Include path not found (C:UsersKevinmcu64FRDM-K64F_lwIP_FreeRTOSGenerated_CodeSDKplatformdevicesMK64F12startup).

    Since I’ve never generated code maybe that’s the problem?
    Note: This path is R/W/X for Eclipse.

    Like

  6. I see some errors when compiling
    ../Generated_Code/UTIL1.h:844:1: error: unknown type name ‘byte’
    ../Generated_Code/UTIL1.c:2039:1: error: unknown type name ‘byte’
    multiple definition of `_write’
    multiple definition of `_sbrk’

    Like

  7. Hi Eric,

    Excellent article!

    Have you ever considered creating an embedded component for lwip?
    Id like to try to do it myself, but it might be a long learning curve for me.
    Any suggestions?

    Best regards,

    Like

      • Hi Erich,
        Maybe we can use interleaved sampling 🙂

        Do you happen to work for NXP? My company have a good relationship with Freescale, now NXP. We are a design house specialized in IoT products and we’re based in Brazil.

        Best Regards,

        Like

  8. Hello Erich,

    I tried your tutorial to use the ethernet connection of the FRDM – K64F !

    For all setup I haven’t had any problems but during the development of your application code I just get to see the “Welcome to the world of lwip ” in my P & E Semihosting Console…
    And I would like an IP address of my card is that possible?

    thank you for your time

    Like

  9. I’m having some trouble with the very first step; Pin Settings. I have installed Design Studio (3.2.0), I have built an SDK using the online NXP Kinetis Expert System Configuration Tool (SDK_2.0_FRDM-K64F), created a new project in Design Studio and pointed it at the SDK (note: the Rapid Application Development dialog did not appear), downloaded the latest mcuoneclipse components (Components 2016-02-07) and imported both files by selecting Processor Expert –> Import Component(s) from within Design Studio. I added the components to “My Components”. I also selected Processor Expert –> Show Views. I built the project (FRDM-K64F_lwIP_FreeRTOS) which was successful. Once I select the project, the Components view is no longer greyed out. The issue is that I cannot see anything in the componeents view. There is another view which shows my component library. Under My Components there are folders for CPU External Devices, CPU Internal Peripherals, Operating System, Software and SW. At the bottom of this view I see; “No project focused, filtering disabled”. Any suggestions? I’m keen to work through this project, then have a go at building my own Eclipse IDE. I assume I can do this in Linux?

    Like

      • Hi Erich. Thank you for your quick response. What I am trying to do is learn FreeRTOS. I will soon be using it on a STM32 (custom made board) but right now I have a K64F. Which is what brought me to your post. I would prefer to setup my own IDE (ideally Eclipse) so I fully understand what i’m using and how it all pieces together. I see in your post on setting up an Eclipse IDE that you also use version 1.3 of the SDK. For my first time setting this up, do you recommend I start with v1.3? Also, I assume your course materials are not publicly available?

        Like

        • Hi Matthew,
          on FreeRTOS.org there are pretty good tutorials, plus there is a FreeRTOS guide you could get from there. And yes, it is pretty easy to setup your own IDE. As for the SDK: I recommend the v2.0. The v1.3 is difficult to use and understand. But it is up to you.

          Like

        • And about the course material: I have not published that to the public, and it probably does not make a lot of sense. Because there is are a lot of black/whiteboarding and labs in the course. So without being there, it does not make much sense. but maybe you could register for the next university course? 😉

          Like

  10. Hi Erich

    First of all thanks for this Tutorial. I am new to this world of Kinetis. I come from MSP430 world.

    I did all the steps as you have explained. But when I compile I get an error of make

    makefile:79: recipe for target ‘FRDM-K64F_lwIP_FreeRTOS.elf’ failed
    make: *** [FRDM-K64F_lwIP_FreeRTOS.elf] Error 1

    Probably is one configuration that I´ve missed, but I can´t find what I did wrong.

    Regards Fernando from Buenos Aires Argentina

    Like

    • Hi Fernando,
      Welcome to the ARM world! Are you using the latest project and files from GitHub? have you generated Processor Expert code first (right click on the .pe file in the project root, then use ‘Generate processor expert code’)? Other than that, make sure you have done a ‘clean’ (select the project, then use the menu Project > Clean.
      I hope this helps,
      Erich

      Like

      • Hi Erich,
        Thanks for your response. I will try from zero playing attention to the points you have mentioned.

        Regards

        Like

  11. Hi Erich,

    It is a great article.
    I tried to run this project. I built it on a DIY Eclipse but Neon instead of Mars and with all of the current components:
    The current NXP custom built 1.3 SDK doesn’t contain the \middleware\tcpip\rtcs directory at all, so I needed to install the old standalone release.
    I’m using the Segger J-Link firmware and drivers as I can’t install the P&E Eclipse plug-in on the CDT 9.1
    And my problem:
    The board starts with the compiled code but it hangs in the very moment when it receive the IP address from DHCP. So I see three “LwipInitTask : Current DHCP State : 6” messages, than nothing. If the ethernet cable removed, it goes further and finish the DHCP round with timeout.
    I tried the ENET_RECEIVE_ALL_INTERRUPT solution you mentioned, but it make it worst. The DHCP request process not even start. If I pause the debugger when the DHCP hanged, it stops in the port.c line 896:
    configASSERT(((*portNVIC_INT_CTRL) & portVECTACTIVE_MASK)==0);

    Do you have any idea, what could be the problem?

    Thanks,
    Zoltan

    Like

    • Hi Zoltan,
      Using Neon should not make a difference. But are you using a different compiler too? That might make a difference, even a possible compiler bug?
      I have not upgraded or changed the SDK for that project, so it sounds based on your feedback there are problems with the newer SDK.
      That assert means that the interrupt priorities of FreeRTOS and the interrupts of the system are not configured properly. What it means is that you called an API function which is not supposed to be called from an interrupt. See https://mcuoneclipse.com/2016/08/28/arm-cortex-m-interrupts-and-freertos-part-3/ and the part 2 and 1 of the series about the ARM Cortex interrupt system.
      I hope this helps,
      Erich

      Like

      • Hi Erich,

        Thank you for your answer. I tried to use the actual gcc: 5.4 2016q3. Then I reverted on project level to the 4.9 2015q2 as it was mentioned earlier in the comments.
        I’ll give a try to changing it on wrokspace level, who knows what mistake I mad with it.
        Regarding the SDK I’ll try to change it to the standalone 1.3 as I seen differences between the standalone and the built one.
        Thank you for the interrupt articeles, I’ll read through, hopefully I’ll get some thoughts to the right direction.

        Regards,
        Zoltan

        Like

  12. Hey Erich, I’m having a problem with the main. It’s giving me an error on this part:
    void *_sbrk ( uint32_t delta ) {
    extern char end; /* Defined by the linker */
    static char *heap_end;
    char *prev_heap_end;

    if (heap_end == 0) {
    heap_end = &end;
    }

    prev_heap_end = heap_end;
    heap_end += delta;
    return (void *) prev_heap_end;
    }
    #endif

    The report is:
    c:/freescale/kds_v3/toolchain/bin/../lib/gcc/arm-none-eabi/4.8.4/../../../../arm-none-eabi/lib/armv7e-m/fpulibrdimon_s.a(rdimon-syscalls.o): In function `_sbrk’:
    syscalls.c:(.text._sbrk+0x0): multiple definition of `_sbrk’
    ./Sources/main.o:C:Userselivaworkspace1.kdsCONTROLADOORDebug/../Sources/main.c:77: first defined here
    collect2.exe: error: ld returned 1 exit status

    Can you help me?

    Like

      • Thanks for your reply Erich. This is my first time wornking with FreeRTOS and Embedded. So now I’ve got a problem, when I compile and debug is executing and stoping at this point if I connect the Ethernet wire:

        “P&E Semihosting Console
        Welcome to the world of lwip!
        LwipInitTask: lwip init called ..
        LwipInitTask : Started DCHP request (Ok.)”

        I’m trying to use this board to my University Project, but it is so difficult for a beginer.

        Like

        • I’m affraid, but you have to step through the code to find out what is going on. I recommend that you use the board first with a dedicated small network (e.g. just with a router and the board attached).

          Like

  13. Hello Eric Sir,

    It is a great article.
    I tried to run this project. But I am not able to debug the code as I am getting following statement on console window:-

    CMD>RE

    Initializing.
    Target has been RESET and is active.

    and aside main window I am getting this:-

    No source available for “0x540”

    I am using OpenSDA debugger… on FRDM K64f board…

    Thank you…

    Like

    • ‘OpenSDA’ debugger does not tell me much, as it could be P&E, Segger or CMSIS-DAP (do not use CMSIS-DAP would be my recommendation).
      Have you debugged your application, does it reach main()?
      Other than that, you have to debug/step through your code to find out what is going on. And avoid any printf() calls.

      Like

  14. Hi Erich, nice article.
    It´s my first time using processor expert, I used to do the initialization by myself but this is a lot more confortable.
    I´m following your guide, but I got a problema while compiling the project, it says:

    fatal error: fsl_os_abstraction_bm.h: No such file or directory

    I noted that this abstraction_bm file is the one that is shown up in the confirmation dialog after making the processor expert code, don´t know if thats the cause of the problem.

    Hope you have any idea about this error.

    Like

    • Hi Jorge,
      it seems that you are using the Kinetis SDK OS version. In that case, you need to have that fsl_os_abstraction_bm.h file present in your project.
      I would first try to regenerate processor expert code (context menu on the .pe file).
      I hope this helps,
      Erich

      Like

  15. Pingback: Easter Weekend Apple Juice Brined Pulled Pork Smoked on Beech Wood | MCU on Eclipse

  16. Hi Erich,
    I tried to follow the tutorial but come to a problem:

    I used the same setup, with difference to use your newest MCU components with FRTOS 10.1.1 and KDS 3.2 with SDK 1.3.

    When running the program I got stuck at “LwipInitTask : Started DCHP request (Ok.)” like an another post here before.
    It stopps at configASSERT( ucCurrentPriority >= ucMaxSysCallPriority );
    I debugged and found out to set the ethernet-receive interrupt to a higher level than MaxSysCallPriority helps. So I added this:

    NVIC_SetPriority(ENET_Receive_IRQn, 5);
    And the program runs now. But I have doubts it is a good Idea to have the enet rx interrupt at such a low priroity in application.
    You have maybe a idea to work arround? I could provide my project file if it helps.
    br, Hans

    Like

What do you think?

This site uses Akismet to reduce spam. Learn how your comment data is processed.