#Forlinx
Explore tagged Tumblr posts
forlinx · 13 days ago
Text
FreeRTOS on i.MX 9352 M33 Core – Real-Time in Action!
Take your embedded systems to the next level with the Forlinx OK-MX9352-C development board. Learn how to build real-time applications on NXP's Cortex-M33 core using FreeRTOS.
Tumblr media
Featured demos include:
✅ Task + Queue communication ✅ Software timers & semaphores ✅ UART, I2C, SPI under FreeRTOS ✅ System tick hook & exception handling
Perfect for edge AI & industrial control.
0 notes
electronicsbuzz · 2 months ago
Text
0 notes
timestechnow · 3 months ago
Text
0 notes
tootimetraveltimemachine · 14 days ago
Text
FreeRTOS Design Routine Based on i.MX9352 Development Board M Core
In the embedded systems, the application of embedded real-time operating systems (RTOS) is becoming increasingly widespread. Using an RTOS can utilize CPU resources more reasonably and efficiently. As a lightweight and mature real-time operating system kernel, FreeRTOS has complete core functions, including task management, time management (such as delays and timers), synchronization mechanisms (semaphores, mutexes), inter-process communication (message queues), and so on. These features enable it to meet the needs of small and medium-sized embedded systems with relatively limited resources.
i.MX 9352 is a new generation of lightweight edge AI processor launched by NXP, which integrates 2 x Cortex-A55 cores and 1 x Cortex-M33 real-time core. Its architecture design fully reflects the balance between real-time and complex task processing capabilities. To help developers fully leverage the real-time capabilities of the i.MX 9352 M33 core, the FreeRTOS examples provided in the accompanying M-core SDK package are divided into two categories. One category introduces the features of FreeRTOS system components, such as semaphores, mutexes, and queues. The other category shows how to use peripheral interfaces in FreeRTOS. Examples from each of these two categories are selected for demonstration.
▊ Demo platform: Forlinx Embedded OK-MX9352-C Development Board
Tumblr media
1. FreeRTOS-generic
The sample code of FreeRTOS features supported by the Forlinx Embedded OK-MX9352-C is as follows:
freertos_event: Demonstration Routine for Task Event
freertos_queue: Demonstration routine for implementing inter-task communication using queue messages
freertos_mutex: Routine for using mutexes
freertos_swtimer: Usage of software timers and their callbacks.
freertos_tickless: Routine for delayed wake-up using LPTMR or wake-up by hardware interrupt.
freertos_generic: Demonstration routine for the combined use of tasks, queues, software timers, tick hooks, and semaphores.
Since the FreeRTOS_generic routine uses many FreeRTOS features, let's focus on analyzing this routine.
(1)Software implementation
The content of the example program includes: task creation, queues, software timers, system tick clocks, semaphores, and exception handling. Specifically:
Task creation:
The main function creates three tasks: a queue sending task, a queue receiving task, and a semaphore task.// Create the queue receiving task if (xTaskCreate(prvQueueReceiveTask, "Rx", configMINIMAL_STACK_SIZE + 166, NULL, mainQUEUE_RECEIVE_TASK_PRIORITY, NULL) != pdPASS) // Create the queue sending task if (xTaskCreate(prvQueueSendTask, "TX", configMINIMAL_STACK_SIZE + 166, NULL, mainQUEUE_SEND_TASK_PRIORITY, NULL) != pdPASS) // Create the semaphore task if (xTaskCreate(prvEventSemaphoreTask, "Sem", configMINIMAL_STACK_SIZE + 166, NULL, mainEVENT_SEMAPHORE_TASK_PRIORITY, NULL) != pdPASS)
Queues:
The queue sending task blocks for 200ms and then sends data to the queue. The queue receiving task blocks to read from the queue. If the data is read correctly, it prints the current number of received items in the queue.// The queue sending task blocks for 200ms and then sends data to the queue static void prvQueueSendTask(void *pvParameters) { TickType_t xNextWakeTime; const uint32_t ulValueToSend = 100UL; xNextWakeTime = xTaskGetTickCount(); for (;;) { // The task blocks until the 200ms delay ends. vTaskDelayUntil(&xNextWakeTime, mainQUEUE_SEND_PERIOD_MS); // Send data to the queue. A blocking time of 0 means it will return immediately when the queue is full. xQueueSend(xQueue, &ulValueToSend, 0); } } //The queue receives the task, and the task is blocked to read the queue. If the data is read correctly, the number received by the queue at this time is printed. static void prvQueueReceiveTask(void *pvParameters) { uint32_t ulReceivedValue; for (;;) { //The task keeps blocking until data is read from the queue xQueueReceive(xQueue, &ulReceivedValue, portMAX_DELAY); //The queue data is consistent with the sending, and the queue receiving quantity+1 outputs the queue receiving quantity at this time if (ulReceivedValue == 100UL) { ulCountOfItemsReceivedOnQueue++; PRINTF("Receive message counter: %d.\r\n", ulCountOfItemsReceivedOnQueue); } } }
Software timers:
Set the software timer period to 1 second. When the time is up, call the callback function, record the number of times, and print it via the serial port.// Create a software timer task with a time of 1 second and cyclic operation. xExampleSoftwareTimer = xTimerCreate( "LEDTimer", mainSOFTWARE_TIMER_PERIOD_MS, pdTRUE, (void *)0, vExampleTimerCallback); //Start the software timer xTimerStart(xExampleSoftwareTimer, 0); //Callback function static void vExampleTimerCallback(TimerHandle_t xTimer) { //Enter the callback function once every 1s, and the count increases ulCountOfTimerCallbackExecutions++; PRINTF("Soft timer: %d s.\r\n", ulCountOfTimerCallbackExecutions); }
System tick clock:
Set the task tick interrupt frequency by setting configTICK_RATE_HZ in the FreeRTOSConfig.h file. When starting the task scheduler, the system will calculate the value to be written to the tick counter according to another variable configCPU_CLOCK_HZ (CPU frequency) and start the timer interrupt.
// Set the system tick clock to 1000/200 = 5ms #define configTICK_RATE_HZ ((TickType_t)200)
Semaphores:
In each system tick clock interrupt, call the function vApplicationTickHook. After accumulating 500 times, which is 500 * 5ms = 2.5s, send a semaphore. After the semaphore task acquires the semaphore, it counts and prints the accumulated number of times.// The system tick is 5ms. Release the event semaphore every 500 * 5ms = 2.5s. void vApplicationTickHook(void) { BaseType_t xHigherPriorityTaskWoken = pdFALSE; static uint32_t ulCount = 0; ulCount++; if (ulCount >= 500UL) { //Release the event semaphore in the interrupt xSemaphoreGiveFromISR(xEventSemaphore, &xHigherPriorityTaskWoken); ulCount = 0UL; } } //The task blocks and waits for the semaphore. After receiving, the number of receiving times increases and is printed through the serial port. static void prvEventSemaphoreTask(void *pvParameters) { for (;;) { //Task blocks until semaphore can be acquired if (xSemaphoreTake(xEventSemaphore, portMAX_DELAY) != pdTRUE) { PRINTF("Failed to take semaphore.\r\n"); } //Accumulate the number of times the semaphore is received ulCountOfReceivedSemaphores++; PRINTF("Event task is running. Get semaphore :%d \r\n",ulCountOfReceivedSemaphores); } }
Exception handling:
When memory allocation fails, a stack error occurs, or a task is idle, the program enters the corresponding function. Users can add corresponding handling functions.// Memory allocation failure function. When memory allocation fails, the program enters this function. void vApplicationMallocFailedHook(void) { for (;;) ; } //Stack error check function, which is entered when stack overflow occurs void vApplicationStackOverflowHook(TaskHandle_t xTask, char *pcTaskName) { (void)pcTaskName; (void)xTask; for (;;) ; } // Idle task, with the lowest priority and no practical significance. It's just to keep the CPU busy. Users can add their own functions. void vApplicationIdleHook(void) { volatile size_t xFreeStackSpace; xFreeStackSpace = xPortGetFreeHeapSize(); if (xFreeStackSpace > 100) { } }
(2)Experimental Phenomenon Part
① Compile the program: Manually load the M-core program in U-Boot.
② Queue: Every 200 milliseconds, the sending task of the queue sends data, and the receiving task of the queue retrieves data. The receiving task transitions from the blocked state to the running state and prints the count.
③ Software timer: Every 1s, when the time is up, the callback function is called, and the count is printed.
④ Semaphore: Every 5ms, the system clock tick interrupt calls a function. After more than 500 times, the semaphore is released. The semaphore task acquires the semaphore, changes from the blocked state to the running state, and prints the count.
Tumblr media
2. FreeRTOS-Peripherals
The Forlinx Embedded OK-MX9352-C development board supports using FreeRTOS to drive various peripherals. The following are some example codes:
freertos_uart: FreeRTOS UART demonstration routine
freertos_lpi2c_b2b: FreeRTOS I2C demonstration routine
freertos_lpspi_b2b: FreeRTOS SPI demonstration routine
Since the freertos_uart routine uses typical FreeRTOS features, focus on analyzing this routine.
(1) Software implementation
The example program content includes: serial port initialization task, serial port sending task, and serial port receiving task. Specifically:
Serial port initialization task:
It mainly includes the initialization of serial port peripherals, sending and receiving mutexes, and sending and receiving event groups. The initialization of serial port peripherals has been demonstrated in the bare-metal running serial port example, so it will not be detailed here.// Create a serial port sending mutex. handle->txSemaphore = xSemaphoreCreateMutex(); // Create a serial port receiving mutex. handle->rxSemaphore = xSemaphoreCreateMutex(); // Create a flag group sending events handle->txEvent = xEventGroupCreate(); // Create a flag group receiving events handle->rxEvent = xEventGroupCreate();
Serial port sending:
The semaphore is obtained before sending, the sending process is started, and the sending completion event flag is set in the interrupt. After acquiring the event, the send task releases the send semaphore.//1 Get the send semaphore if (pdFALSE == xSemaphoreTake(handle->txSemaphore, 0)) { return kStatus_Fail; } handle->txTransfer.data = (uint8_t *)buffer; handle->txTransfer.dataSize = (uint32_t)length; //2 blocking transmission status = UART_TransferSendNonBlocking(handle->base, handle->t_state, &handle->txTransfer); if (status != kStatus_Success) { (void)xSemaphoreGive(handle->txSemaphore); return kStatus_Fail; } // 3. Wait for the event of transmission completion ev = xEventGroupWaitBits(handle->txEvent, RTOS_UART_COMPLETE, pdTRUE, pdFALSE, portMAX_DELAY);// Wait and evaluate multiple event flags if ((ev & RTOS_UART_COMPLETE) == 0U) { retval = kStatus_Fail; } // 4 Transmission completed, release the transmission semaphore. if (pdFALSE == xSemaphoreGive(handle->txSemaphore)) // Release the transmission semaphore. { retval = kStatus_Fail; }
Serial port receiving:
Before receiving, obtain the semaphore, call the serial port receiving function, and set the event flag in the interrupt. After the receiving task obtains the event, release the receiving semaphore.// 1. Obtain the receiving semaphore. if (pdFALSE == xSemaphoreTake(handle->rxSemaphore, portMAX_DELAY)) { return kStatus_Fail; } handle->rxTransfer.data = buffer; handle->rxTransfer.dataSize = (uint32_t)length; //2 serial port receiving function status = UART_TransferReceiveNonBlocking(handle->base, handle->t_state, &handle->rxTransfer, &n); if (status != kStatus_Success) { (void)xSemaphoreGive(handle->rxSemaphore); return kStatus_Fail; } //3 Obtain the receiving event ev = xEventGroupWaitBits(handle->rxEvent,RTOS_UART_COMPLETE | RTOS_UART_RING_BUFFER_OVERRUN | RTOS_UART_HARDWARE_BUFFER_OVERRUN, pdTRUE, pdFALSE, portMAX_DELAY); // Wait and check the event bit indicating the completion of receiving // 3.1 Hardware receiving error if ((ev & RTOS_UART_HARDWARE_BUFFER_OVERRUN) != 0U) { UART_TransferAbortReceive(handle->base, handle->t_state); (void)xEventGroupClearBits(handle->rxEvent, RTOS_UART_COMPLETE); // Clear the event bit indicating receiving completion. retval = kStatus_UART_RxHardwareOverrun; local_received = 0; } //3.2 Receiving buffer overload error else if ((ev & RTOS_UART_RING_BUFFER_OVERRUN) != 0U) { UART_TransferAbortReceive(handle->base, handle->t_state); (void)xEventGroupClearBits(handle->rxEvent, RTOS_UART_COMPLETE); // Clear the event bit indicating receiving completion. retval = kStatus_UART_RxRingBufferOverrun; local_received = 0; } //3.3 Receiving completed else if ((ev & RTOS_UART_COMPLETE) != 0U) { retval = kStatus_Success; local_received = length; } else { retval = kStatus_UART_Error; local_received = 0; } //4. Release the received signal quantity if (pdFALSE == xSemaphoreGive(handle->rxSemaphore)) { retval = kStatus_Fail; }
(2)Experimental Phenomenon Part
① Compile the program and manually load the M-core program in U-Boot.
② After the device is powered on, the serial port prints the program information. At this time, input 4 characters via the keyboard, and the M-core debugging serial port will echo. Repeating the input and echo of characters proves that the program runs successfully.
Tumblr media
The above is an example demonstration of FreeRTOS software design on the M-core of the Forlinx Embedded i.MX 9352 development board. Hope it can be helpful to all engineer friends.
0 notes
dunia-it · 6 years ago
Text
Networking SBCs run Linux on quad -A53 and -A72 NXP LS chips
Networking SBCs run Linux on quad -A53 and -A72 NXP LS chips
[ad_1]
Forlinx’s sandwich-style OK1043A-C and OK1046A SBCs run Linux on NXP’s quad -A53 LS1043A and quad -A72 LS1046A SoCs, respectively, and offer a 10GbE port and up to 6x GbE ports with optional SFP. Forlinx has posted product pages for two similar COM Express modules and carrier boards that run Linux on NXP’s networking focused LS series processors. The FET1043A-C module taps the up to…
View On WordPress
0 notes
forlinx · 18 days ago
Text
Smarter, Greener, and More Autonomous!
Tumblr media
Meet the future of outdoor automation with our intelligent lawn mowing robot solution powered by the Forlinx FET3576-C SoM, based on the Rockchip RK3576.
With an 8-core CPU, 6 TOPS NPU, AI-powered obstacle detection, and precise route planning, this main control platform is built for high-performance, eco-friendly robotic mowers.
Discover how we're transforming yard work with AI and embedded power.
Tumblr media
0 notes
forlinx · 24 days ago
Text
Setting up network services on your Forlinx OK-MX9352-C Linux platform just got easier!
Tumblr media
Learn how to quickly configure TFTP, NFS, and SSH services to streamline your embedded development workflow.
From installation to testing, this step-by-step guide covers everything you need to connect, transfer files, and remotely manage your device efficiently.
Whether you’re using Linux 6.1.36 or a similar environment, this tutorial is your go-to reference.
0 notes
forlinx · 28 days ago
Text
🚨 Prevent Electrical Fires Before They Start Did you know that up to 70% of electrical fires are preventable?
Tumblr media
Forlinx Embedded presents a smart and efficient solution for electrical fire monitoring systems powered by the FET6254-C SoM.
With real-time monitoring, fast alerts, dual-core architecture, and industrial-grade stability, this solution is ideal for residential, commercial, and industrial applications.
✅ Real-time current, voltage & temperature monitoring ✅ Reliable alerts on overheating, short circuits & more ✅ Dual-core (A-core + M-core) for mission-critical stability ✅ Rich interfaces: CAN-FD, UART, Gigabit Ethernet, LVDS ✅ Designed for industrial environments
Tumblr media
0 notes
forlinx · 1 month ago
Text
Want to customize your embedded Linux system with Buildroot on the Forlinx OK3588-C platform?
Tumblr media
This step-by-step guide walks you through compiling Buildroot 5.10.209, adding system tools like OpenCV4, and preparing a complete cross-compilation environment.
Perfect for embedded developers working with ARM64!
0 notes
forlinx · 1 month ago
Text
5-Minute Quick Guide: Set Up TFTP, NFS, and SSH on i.MX9352 with Linux 6.1
Tumblr media
Want to speed up embedded development on the Forlinx OK-MX9352-C board?
Our step-by-step guide helps you quickly configure essential network services — TFTP for file transfer, NFS for rootfs sharing, and SSH for secure remote login.
💡 Perfect for industrial IoT and edge development scenarios!
0 notes
forlinx · 2 months ago
Text
New Technical Guide for Developers!
Tumblr media
Learn how to configure the Allwinner T507 audio system with DMA channels and the powerful Audio Hub module.
This guide walks you through I2S configuration, audio routing, and testing with ALSA and TinyAlsa tools—perfect for embedded Linux audio development! 🎧
0 notes
forlinx · 2 months ago
Text
🚀 Want to give your embedded product a custom look from the very first second?
Tumblr media
Check out our step-by-step guide on how to modify the boot logo and animation on the OK3588-C Android 12 development board, powered by the Rockchip RK3588 SoM.
✅ ADB + source-level methods
✅ Full Linux & Android support
✅ Ideal for branding industrial devices
0 notes
forlinx · 2 months ago
Text
Looking for a reliable solution to monitor industrial dust in real time?
Tumblr media
Discover our advanced dust monitoring system powered by the Nuvoton MA35 processor. With support for PM1.0, PM2.5, PM10, and environmental sensors, it delivers accurate, real-time data even in harsh conditions.
✅ Multi-sensor support
✅ Real-time wired/wireless communication
✅ Ideal for smart environmental control
FET-MA35-S2 embedded system-on-module
0 notes
forlinx · 2 months ago
Text
Elevator Monitoring Just Got Smarter
Introducing the Forlinx MA35 Embedded SoM – your ultimate Industrial IoT gateway for real-time elevator monitoring and predictive maintenance.
Tumblr media
🔧 Monitors elevator motion, door status, floor position, and environmental conditions
🌐 Dual 4G connectivity for real-time cloud sync
🔥 Instant alerts for faults, smoke, or abnormal events
📉 Reduce downtime, improve safety, and optimize maintenance like never before
🔍 Compact. Reliable. Industrial-grade.
0 notes
forlinx · 2 months ago
Text
🚀 Simplify your product updates with OTA upgrades on the Forlinx OK3568-C development board!
Tumblr media
Our latest guide walks you through the full Linux OTA process on the Rockchip RK3568 platform—including packaging, flashing, and remote upgrade via SD card, USB, or FTP.
🔧 Ideal for embedded engineers looking to fix bugs or push features without manual flashing.
0 notes
forlinx · 2 months ago
Text
Introducing the FET-MX8MPQ-SMARC System on Module — Built for Real-World Edge Intelligence
Tumblr media
Looking to power your next-gen edge AI solution with industrial-grade reliability?
Meet the FET-MX8MPQ-SMARC from Forlinx Embedded — a high-performance SMARC 2.1-compliant SoM based on the NXP i.MX 8M Plus Quad-Plus processor.
✅ 4× Cortex-A53 @ 1.6 GHz + Cortex-M7 @ 800 MHz
✅ 2.3 TOPS NPU + ISP for AI vision and multimedia processing
✅ Dual-band Wi-Fi 5 + Bluetooth 5.3 built-in
✅ –40°C to +85°C industrial temperature range
✅ Preloaded with Linux 6.1.36 LTS, BSP, drivers, and sample code
✅ Compatible with all SMARC 1.x/2.x carrier boards
Whether you're building for smart cities, industrial IoT, intelligent transport, or medical devices, this module is ready for deployment at the edge.
📩 Want to learn more or request documentation?
👉 Contact us: [email protected]
0 notes