SEGGER Embedded Studio IDE移植embOS

一、背景介绍

一直以来我们项目和学习用到的最多的RTOS主要是FreeRTOS、RTT、Keil RTX。但是在SEGGER Embedded Studio(SES)上,我们还可以使用SEGGER出品的embOS系统。和FreeRTOS源码类似,我们也得做一些的移植工作。

这里郑重声明:本贴仅用于学习和非商业化应用。如果您要将embOS用于商业化项目中,还需要采购。

SEGGER的很多工具有个最大的好处就是,对于学习和爱好者是比较友好的。我们可以直接下载二进制库,根据手册稍微做一点适配就可以应用了。由于笔者目前对SEGGER的这些工具还没有那么熟悉,本次就仅仅是移植embOS,就不联合其他的工具了。

这里有关的移植的办法都是参考的手册。同时,embOS包里也有一些成型的项目可以测试。

主要参考文件都是来自embOS包的文件,有:

  1. UM01001_embOS.pdf
  2. UM01061_embOS_CortexM_ES.pdf
  3. /embOS_CortexM_ES_Obj_SFL_V5.18.0.0/Start/BoardSupport中有关的板级支持包源代码

二、任务目标

在“墨子号”开发板上运行程序。这个“墨子号”是个在马云家上买的一个小开发板,有2个485,1个CAN和若干其他的资源。图片如下所示。

Alt

调试器还是SEGGER J-link Compact。

这次的任务目标是

  1. 配置embOS的配置头文件
  2. 编译通过带embOS的代码
  3. 运行一个任务
  4. 运行一个定时器

三、技术实现

3.1 获得embOS

SEGGER embOS的官方网址下载。打开这个网址以后会发现货比较多,我这里用的是“
embOS for Cortex-M and SEGGER Embedded Studio”

在这里插入图片描述
注意:虽然我们后面在编译器上可能还是用GCC,但是这里不是上面的那个GCC的。那个GCC版本的好像是不用IDE,你自己用CMAKE那样的工具做个项目再用GCC编译的时候会用到。

下载后,解压,我们会得到一个文件夹叫“embOS_CortexM_ES_Obj_SFL_V5.18.0.0”,里面的内容如下:

在这里插入图片描述

3.2 创建SES工程

3.2.1 创建初始Solution和Project

打开SES,创建一个工程叫做embOS_Portion。创建的时候有关的IDE配置做如下的初始配置。

在这里插入图片描述
编译器默认的是SEGGER,但是我这里改成了GCC。printf函数打开“Printf Width/Precision Supported”。本程序不用堆,主栈给个512字节够启动就可以了。

跟往常一样,系统生成了一个Solution,一个Project和一个main.c。不过这次IDE升级以后,凡是在C文件中的没有被用到的但是被包含了两头文件,都给你打个波浪线。就像这样的:

在这里插入图片描述

3.2.2 制作项目文件结构

在SES中的Source Files下面创建文件夹和子文件夹,最终形成项目的文件结构。在物理上去项目文件夹内创建Source Files文件夹,在里面再创建Application,BSP,embOS这三个子文件夹。
在这里插入图片描述

3.2.3 移植embOS库和有关头文件

3.2.3.1 头文件

参考随包配送的两个pdf,分别是UM01001_embOS.pdf和UM01061_embOS_CortexM_ES.pdf。需要在工程文件夹的embOS文件夹下出现RTOS.h和OS_Config.h两个文件。那就去/embOS_CortexM_ES_Obj_SFL_V5.18.0.0/Start/Inc下面的这两个文件移动到工程文件夹的embOS/下面。

参考OS_Config.h里面的内容,我们想链接哪个库,就要定义相关的宏。

/*********************************************************************
*
*       Configuration for RTOS build and embOSView communication
*
*  In your application program, you need to let the compiler know
*  which build of embOS you are using. This is done by adding the
*  corresponding define to your preprocessor settings and linking the
*  appropriate library file.
*
*  OS_LIBMODE_XR    Extremely small release build without Round robin
*  OS_LIBMODE_R     Release build
*  OS_LIBMODE_S     Release build with stack check
*  OS_LIBMODE_SP    Release build with stack check and profiling
*  OS_LIBMODE_D     Debug build
*  OS_LIBMODE_DP    Debug build with profiling
*  OS_LIBMODE_DT    Debug build with trace
*
*  If no preprocessor setting is used, this file will select default
*  modes for debug and release configurations of your project.
*/

在这个里面定义的控制宏如下所示。

#if (defined(DEBUG) && (DEBUG == 1))
  #define OS_LIBMODE_DP
#else
  #define OS_LIBMODE_R
  #define OS_VIEW_IFSELECT  OS_VIEW_DISABLED  // embOSView communication is disabled per default in release configuration
#endif

但是我这里只是为了任务目标,就不采用DP了。我们的头文件是

/*********************************************************************
*                     SEGGER Microcontroller GmbH                    *
*                        The Embedded Experts                        *
**********************************************************************
*                                                                    *
*       (c) 1995 - 2022 SEGGER Microcontroller GmbH                  *
*                                                                    *
*       Internet: segger.com  Support: support_embos@segger.com      *
*                                                                    *
**********************************************************************
*                                                                    *
*       embOS * Real time operating system                           *
*                                                                    *
*       Please note:                                                 *
*                                                                    *
*       Knowledge of this file may under no circumstances            *
*       be used to write a similar product or a real-time            *
*       operating system for in-house use.                           *
*                                                                    *
*       Thank you for your fairness !                                *
*                                                                    *
**********************************************************************
*                                                                    *
*       OS version: V5.18.0.0                                        *
*                                                                    *
**********************************************************************

-------------------------- END-OF-HEADER -----------------------------
File    : OS_Config.h
Purpose : Configuration settings for the OS build and embOSView
*/

#ifndef OS_CONFIG_H
#define OS_CONFIG_H

/*********************************************************************
*
*       Configuration for RTOS build and embOSView communication
*
*  In your application program, you need to let the compiler know
*  which build of embOS you are using. This is done by adding the
*  corresponding define to your preprocessor settings and linking the
*  appropriate library file.
*
*  OS_LIBMODE_XR    Extremely small release build without Round robin
*  OS_LIBMODE_R     Release build
*  OS_LIBMODE_S     Release build with stack check
*  OS_LIBMODE_SP    Release build with stack check and profiling
*  OS_LIBMODE_D     Debug build
*  OS_LIBMODE_DP    Debug build with profiling
*  OS_LIBMODE_DT    Debug build with trace
*
*  If no preprocessor setting is used, this file will select default
*  modes for debug and release configurations of your project.
*/

#if (defined(DEBUG) && (DEBUG == 1))
  #define OS_LIBMODE_D
#else
  #define OS_LIBMODE_R
  #define OS_VIEW_IFSELECT  OS_VIEW_DISABLED  // embOSView communication is disabled per default in release configuration
#endif

/*********************************************************************
*
*  Additional embOS compile time configuration defines when using
*  embOS sources in your project or rebuilding the embOS libraries
*  can be added here, e.g.:
*    #define OS_SUPPORT_TICKLESS  0  // Disable tickless support
*/

#endif  // OS_CONFIG_H

/*************************** End of file ****************************/

3.2.3.2 库文件

打开/embOS_CortexM_ES_Obj_SFL_V5.18.0.0/Start/Lib,会发现里面有很多的库文件。

在这里插入图片描述
我们就只需要把libos_v7m_t_vfpv4_le_d.a和libos_v7m_t_vfpv4_le_r.a两个库复制到项目文件夹下面的/Source Files/embOS/Library下面。

至于为什么是这两个库呢?这是因为,根据芯片的内核手册,ST的ARM核是ARMv7M,cortex-m4的内核里面有个FPUv4f的乘法器。ARM-CM是小端。所以我们选这两个库文件。

3.2.3.3 创建RTOSInit.c源文件

参考《UM01001_embOS.pdf》的第26章的内容和有关的例程源码文件,必须要创建RTOSInit.c文件并在里面实现有关的接口函数。下面这几个接口是必须要实现的。
在这里插入图片描述

下面这几个是可选的,但是要注意的是,那个SysTick_Handler,貌似是必须要实现的。因为通过调试我们发现,似乎系统并没有给实现一个默认的函数。如果自己不实现一个,一旦异常发生,会卡住在异常向量表。
在这里插入图片描述

这样,我们实现的RTOSInit.c源文件的源代码如下所示。

#include "RTOS.h"
#include "stm32f4xx.h"

#define OS_TIMER_FREQ (168000000u) // Peripheral clock for timer
#define OS_TICK_FREQ (1000u) // System tick frequency
#define OS_INT_FREQ (OS_TICK_FREQ) // Timer interrupt frequency

#if (OS_VIEW_IFSELECT == OS_VIEW_IF_JLINK)
  const OS_U32 OS_JLINKMEM_BufferSize = 32u;  // Size of the communication buffer for JLINKMEM
#else
  const OS_U32 OS_JLINKMEM_BufferSize = 0u;   // Buffer not used
#endif

static unsigned int _OS_GetHWTimerCycles(void) {
  return SysTick->VAL;
}
static unsigned int _OS_GetHWTimer_IntPending(void) {
  return SCB->ICSR & SCB_ICSR_PENDSTSET_Msk;
}
void SysTick_Handler(void) {
  OS_INT_EnterNestable();
  OS_TICK_Handle();
  OS_INT_LeaveNestable();
}

void OS_InitHW(void) {
  SystemCoreClockUpdate();
  SysTick_Config(SystemCoreClock / OS_INT_FREQ);
  NVIC_SetPriority(SysTick_IRQn, (1u << __NVIC_PRIO_BITS) - 2u);

  OS_SYSTIMER_CONFIG SysTimerConfig = {
    SystemCoreClock / OS_TICK_FREQ,
    OS_INT_FREQ,
    OS_TIMER_DOWNCOUNTING,
    _OS_GetHWTimerCycles,
    _OS_GetHWTimer_IntPending
  };

  OS_INT_IncDI();
//
// Initialize timer for embOS
//
//
// Setup timing information
//
  OS_TIME_ConfigSysTimer(&SysTimerConfig);
//
// Initialize communication for embOSView
//
  OS_INT_DecRI();
}

void OS_Idle(void) { // Idle loop: No task is ready to execute
  while (1) { // Nothing to do ... wait for interrupt
  }
}

void OS_COM_Send1(OS_U8 c) {
}

这个文件里就是要实现6个函数。其中最主要的工作量是实现void OS_InitHW(void)函数。这个函数

  1. 在这个函数里面要初始化SysTick异常处理
  2. 构造用于设置RTOS时钟的OS_SYSTIMER_CONFIG结构体。
  3. 调用OS_TIME_ConfigSysTimer(OS_SYSTIMER_CONFIG*)函数设置RTOS的系统时钟。
  4. OS_INT_IncDI()OS_INT_DecRI()这两个函数目前还不清楚功能。只是模板上的东西,就放在上面就好

其次要注意的函数有void SysTick_Handler(void)。我这里直接采用了模板的代码。

3.2.3.4 OS_Error.c文件

这个文件用于编译Debug目标用的。直接去板级移植包里搞一个就可以了

3.2.4 测试用例

参考了一下手册,我用主函数直接做了测试


#include "RTOS.h"

static OS_STACKPTR int StackHP[128], StackLP[128]; // Task stacks
static OS_TASK TCBHP, TCBLP; // Task control blocks
static OS_TIMER Timer0, Timer1;
static void Callback0(void) {
  OS_TIMER_Restart(&Timer0);
}
static void Callback1(void) {
  OS_TIMER_Restart(&Timer1);
}
static void HPTask(void) {
  while (1) {
    OS_TASK_Delay(50);
  }
}
static void LPTask(void) {
  while (1) {
    OS_TASK_Delay(200);
  }
}

int main(void) {
  OS_Init();
  OS_InitHW();
  OS_TASK_Create(&TCBHP, "HP Task", 100, HPTask, StackHP, sizeof(StackHP), 2);
  OS_TASK_Create(&TCBLP, "LP Task", 100, LPTask, StackLP, sizeof(StackLP), 2);
  OS_TIMER_CREATE(&Timer0, Callback0, 50u);
  OS_TIMER_CREATE(&Timer1, Callback1, 200u);
  
  OS_Start();
  return 0;
}

/*************************** End of file ****************************/

检查一下是否有error出现。我这几次编译都没有出现任何问题。

3.3 测试

编译、链接、运行。
在进程和软定时器回调函数里面下断,会发现可以正常进入。
在这里插入图片描述

四、结论

经过上述的步骤,可以成功在SEGGER Embedded Studio上使用embOS。

  • 12
    点赞
  • 24
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值