letchgo 发表于 2025-6-22 15:20

【灵动微电子MM32F0121测评】-002-移植RTT-NANO

# KEIL+MM3F0121_RTT-NANO的移植

## 一、概述:

本次任务主要是移植RTT-NANO到MM32上运行,由于只有8K RAM,因此移植NANO版本的rt-thread,编译环境为keil。

## 二、官网下载rtt-nano的包

从官网下载软件包,打开后如下图所示:

!(data/attachment/forum/202506/22/150835wm4xc5ke8ee8ceaa.png "image.png")

**bsp:**保留board.c和rtconfig.h,其他的删了。

**include:**头文件目录

**components:**组件文件夹

**libcpu**:处理器相关的启动文件(mm32f0120属于cortex-m0系列,只要保留cortex-m0文件夹即可,其他都可以删除)

**src:**内核源码


## 三、KEIL添加源文件

我们需要删除和重新分类一下官网下载的文件,也可以不做改动,在KEIL中添加需要的,但由于我思维秉承文件夹和工程一致,方便后续其他开发环境使用,所以做出修改

如下图所示:

!(data/attachment/forum/202506/22/151139qe7wih3eixuk696e.png "image.png")

可能需要注意的是board.c文件的内容,以及it.c的两个重复的handler需要删除it.c中的。

期间遇到了val\_list 错误,在rtconfig.h中添加   #define RT\_USING\_LIBC便没有了错误。

如下图为KEIL添加完成之后各部分内容包含的文件:

!(data/attachment/forum/202506/22/151025by1glg1qjgemmoqm.png "image.png")!(https://bbs.21ic.com/data/attachment/forum/202506/22/151030u83mak88wt19mb5a.png "image.png")

## 四、添加keil的include

点击魔法棒,c/c++添加include相关内容

!(data/attachment/forum/202506/22/151228g6g6sflfhl629hhd.png "image.png")

## 五、需要修改的文件

需要修改的文件放到port下面了:board.c和 rtconfig.h

### board.c

里面主要是修改 RT\_HEAP\_SIZE ,根据是否启用内存堆以及芯片内存的大小来决定,注意对齐问题;

rt\_os\_tick\_callback需要放到systick\_handler里面去执行,也要注意这个中断的周期,一般为1ms,也就是rtos调度的周期。

板子初始化,主要是在前面加入时钟的初始化以及打印串口的初始化。

consel相关设置

板子初始化,主要是在前面加入时钟的初始化以及打印串口的初始化。

```
#include <rthw.h>
#include <rtthread.h>

#if defined(RT_USING_USER_MAIN) && defined(RT_USING_HEAP)
/*
* Please modify RT_HEAP_SIZE if you enable RT_USING_HEAP
* the RT_HEAP_SIZE max value = (sram size - ZI size), 1024 means 1024 bytes
*/
#define RT_HEAP_SIZE (1024+1024)
static rt_uint32_t rt_heap;

RT_WEAK void *rt_heap_begin_get(void)
{
    return (uint8_t *)rt_heap;
}

RT_WEAK void *rt_heap_end_get(void)
{
    return (uint8_t *)rt_heap + RT_HEAP_SIZE;
}
#endif

void rt_os_tick_callback(void)
{
    rt_interrupt_enter();

    rt_tick_increase();

    rt_interrupt_leave();
}

/**
* This function will initial your board.
*/
void rt_hw_board_init(void)
{
//#error "TODO 1: OS Tick Configuration."
    /*
   * TODO 1: OS Tick Configuration
   * Enable the hardware timer and call the rt_os_tick_callback function
   * periodically with the frequency RT_TICK_PER_SECOND.
   */
PLATFORM_Init();
    /* Call components board initial (use INIT_BOARD_EXPORT()) */
#ifdef RT_USING_COMPONENTS_INIT
    rt_components_board_init();
#endif

#if defined(RT_USING_USER_MAIN) && defined(RT_USING_HEAP)
    rt_system_heap_init(rt_heap_begin_get(), rt_heap_end_get());
#endif
}

#ifdef RT_USING_CONSOLE

static int uart_init(void)
{
//#error "TODO 2: Enable the hardware uart and config baudrate."
    return 0;
}
//INIT_BOARD_EXPORT(uart_init);

void rt_hw_console_output(const char *str)
{
//#error "TODO 3: Output the string 'str' through the uart."
        printf(str);
}

#endif
```

### rtconfig.h

```
/* RT-Thread config file */

#ifndef __RTTHREAD_CFG_H__
#define __RTTHREAD_CFG_H__
#define RT_USING_LIBC
// <<< Use Configuration Wizard in Context Menu >>>

// <h>Basic Configuration
// <o>Maximal level of thread priority <8-256>
//<i>Default: 32
#define RT_THREAD_PRIORITY_MAX32
// <o>OS tick per second
//<i>Default: 1000   (1ms)
#define RT_TICK_PER_SECOND1000
// <o>Alignment size for CPU architecture data access
//<i>Default: 4
#define RT_ALIGN_SIZE   4
// <o>the max length of object name<2-16>
//<i>Default: 8
#define RT_NAME_MAX    8
// <c1>Using RT-Thread components initialization
//<i>Using RT-Thread components initialization
#define RT_USING_COMPONENTS_INIT
// </c>

#define RT_USING_USER_MAIN

// <o>the stack size of main thread<1-4086>
//<i>Default: 512
#define RT_MAIN_THREAD_STACK_SIZE   512

// </h>

// <h>Debug Configuration
// <c1>enable kernel debug configuration
//<i>Default: enable kernel debug configuration
//#define RT_DEBUG
// </c>
// <o>enable components initialization debug configuration<0-1>
//<i>Default: 0
#define RT_DEBUG_INIT 1
// <c1>thread stack over flow detect
//<i> Diable Thread stack over flow detect
//#define RT_USING_OVERFLOW_CHECK
// </c>
// </h>

// <h>Hook Configuration
// <c1>using hook
//<i>using hook
//#define RT_USING_HOOK
// </c>
// <c1>using idle hook
//<i>using idle hook
//#define RT_USING_IDLE_HOOK
// </c>
// </h>

// <e>Software timers Configuration
// <i> Enables user timers
#define RT_USING_TIMER_SOFT         0
#if RT_USING_TIMER_SOFT == 0
    #undef RT_USING_TIMER_SOFT
#endif
// <o>The priority level of timer thread <0-31>
//<i>Default: 4
#define RT_TIMER_THREAD_PRIO      4
// <o>The stack size of timer thread <0-8192>
//<i>Default: 512
#define RT_TIMER_THREAD_STACK_SIZE512
// </e>

// <h>IPC(Inter-process communication) Configuration
// <c1>Using Semaphore
//<i>Using Semaphore
#define RT_USING_SEMAPHORE
// </c>
// <c1>Using Mutex
//<i>Using Mutex
//#define RT_USING_MUTEX
// </c>
// <c1>Using Event
//<i>Using Event
//#define RT_USING_EVENT
// </c>
// <c1>Using MailBox
//<i>Using MailBox
//#define RT_USING_SIGNALS
// </c>
// <c1>Using Signals
//<i>Using Signals
//#define RT_USING_MAILBOX
// </c>
// <c1>Using Message Queue
//<i>Using Message Queue
//#define RT_USING_MESSAGEQUEUE
// </c>
// </h>

// <h>Memory Management Configuration
// <c1>Memory Pool Management
//<i>Memory Pool Management
//#define RT_USING_MEMPOOL
// </c>
// <c1>Dynamic Heap Management(Algorithm: small memory )
//<i>Dynamic Heap Management
#define RT_USING_HEAP
#define RT_USING_SMALL_MEM
#define RT_USING_SMALL_MEM_AS_HEAP
// </c>
// <c1>using tiny size of memory
//<i>using tiny size of memory
//#define RT_USING_TINY_SIZE
// </c>
// </h>

// <h>Console Configuration
// <c1>Using console
//<i>Using console
#define RT_USING_CONSOLE
// </c>
// <o>the buffer size of console <1-1024>
//<i>the buffer size of console
//<i>Default: 128(128Byte)
#define RT_CONSOLEBUF_SIZE          128
// </h>

// <h>FinSH Configuration
// <c1>include finsh config
//<i>Select this choice if you using FinSH
//#include "finsh_config.h"
// </c>
// </h>

// <h>Device Configuration
// <c1>using device framework
//<i>using device framework
//#define RT_USING_DEVICE
// </c>
// </h>

// <<< end of configuration section >>>

#endif

```

## 五、运行结果

新建一个plt任务,打印不同的信息

```
int main(void)
{
plt_init();
create_task_plt();
while (1)
{

    rt_thread_mdelay(100);
    printf("app-thread run\n");
}
}
void plt_thread_entry(void *parameter)
{

while (1)
{
    plt_mainloop();
    rt_thread_mdelay(1);
}
}
void create_task_plt(void)
{
rt_thread_t tid;

tid = rt_thread_create("plt", plt_thread_entry, RT_NULL,
                         512, 1, 20);
if (tid == RT_NULL)
{
    rt_kprintf("plt thread create error tid =%d\n", tid);
}
else
{
    rt_kprintf("plt thread create success\n");
    rt_thread_startup(tid);
}
}
```

如下图为串口打印的结果:

!(data/attachment/forum/202506/22/151731ltnaggdnlgggwld5.png "image.png")

## 六、遇到的问题

主要是遇到了一个main任务无法运行的问题。

开始以为是芯片的内存太小的原因导致的,寻找了好久,又查看rtt的运行机制花了很久。

//#define RT\_USING\_HEAP

//#define RT\_USING\_SMALL\_MEM

如果定义了上方两个函数就会一直在idle.c中,无法跳转到main,最终定位是创建时无法申请到内存,但是明明heap给了2K了还是一样不行,这样的话只能静态创建main了,**再深入测试发现是rt\_malloc失败。**

最后发现必须要使能 RT\_USING\_SMALL\_MEM\_AS\_HEAP

!(data/attachment/forum/202506/22/151930p86e77gh1e1ocf7z.png "image.png")

AdaMaYun 发表于 2025-7-31 17:51

移植RTT-NANO
页: [1]
查看完整版本: 【灵动微电子MM32F0121测评】-002-移植RTT-NANO