Home » openCR入门教程 » OpenCR入门教程-Bootloader介绍

OpenCR入门教程-Bootloader介绍

说明

  • 本教程介绍OpenCR板中Bootloader的基本功能,启动方式和通讯协议等特点

简介

  • Bootloader负责初始化电路板以及下载固件并将其执行到OpenCR的闪存中

  • OpenCR板上主MCU的STM32F7xx支持DFU(Device Firmware Upgrade)

  • 其使MCU的内置引导加载程序可以通过USB来使用DFU协议,主要用于引导加载程序的初始化,恢复模式和引导加载程序的更新

  • 同时其最大的优势是使用户能够通过USB使用引导加载程序,而无需使用其他JTAG设备

  • 使用嵌入式MCU中的DFU模式写入固件,而无需写入/调试设备(例如STLink)

Item Description
Supported OS Windows, Linux, Mac
Compiler gcc arm 5.4 2016q2

请输入图片描述

  • USB Port

    • 连接到PC并识别为串行端口

    • 用于通过bootloader下载固件的通信接口

  • PUSH SW2

    • 通电时长按该按钮则会启动bootloader

    • 若通电时未按下按钮且闪传存在着固件,则直接执行固件,否则会启动bootloader

Memory Map

  • OpenCR中使用的STM32F746具有1024KB的内部闪存,每个区域的定义如下

  • bootloader位于最低闪传地址,并且在打开电源并复位时会首先执行bootloader

请输入图片描述

Boot Sequence

请输入图片描述

  • 如果openCR板通电或复位时,按下SW2按钮,则它将在bootloader状态下等待来自PC的命令

  • 若未按下SW2按钮且固件位于闪存的固件区域中,其会执行该固件。

Communication Protocol

  • MavLink

  • 在bootloader中使用的通信协议为MavLink

  • MAVLink的初衷主要是用于无人机上,但它的通用性和可移植性非常好,它也可以应用于其它很多场合

  • 更多相关资料,请参阅:http://qgroundcontrol.org/mavlink/start

  • Composition of Commands

<?xml version="1.0"?>
<mavlink>
        <!--<include>common.xml</include>-->
        <!-- NOTE: If the included file already contains a version tag, remove the version tag here, else uncomment to enable. -->
<!--<version>3</version>-->
<enums>
</enums>
<messages>
 <message id="150" name="ACK">
  <description></description>
  <field type="uint8_t"    name="msg_id"></field>
  <field type="uint16_t"   name="err_code"></field>
  <field type="uint8_t"    name="length"></field>
  <field type="uint8_t[16]" name="data"></field>
 </message>
</messages>
      ... omit ...
</mavlink>
  • 其最终定义的xml文件已添加到官方github

  • The defined xml file should be converted to the command code of the language you want to use through the MavLink utility. Download the MavLink utility source code from github below.

  • MavLink是用Python编写的,并且需要Python 2.7或更高版本

$ sudo apt-get install python-tk
$ sudo apt-get install python-future
$ python mavgenerate.py
  • When you run MAVLink Generator, a GUI screen will appear, select the XML file already created in XML, set the language to C, and set the protocol version to 1.0. If you select the folder name for output in Out, and select Generate, a function header file that can use the command added based on the xml file is created and can be used in the firmware

请输入图片描述

  • 最终生成的通信代码可以在官方Github里找到

  • bootloader通过MavLink协议下载并执行固件的命令如下

void cmd_read_version( msg_t *p_msg );
void cmd_read_board_name( msg_t *p_msg );
void cmd_jump_to_fw( msg_t *p_msg );
void cmd_flash_fw_write_packet( msg_t *p_msg );
void cmd_flash_fw_write_begin( msg_t *p_msg );
void cmd_flash_fw_write_end( msg_t *p_msg );
void cmd_flash_fw_write_block( msg_t *p_msg );
void cmd_flash_fw_erase( msg_t *p_msg );
void cmd_flash_fw_verify( msg_t *p_msg );
void cmd_flash_fw_read_block( msg_t *p_msg );
  • Download Sequence

  • bootloader的主要功能是从PC接收固件文件,将其存储在闪存中,并执行存储的固件

  • 下载顺序如下图,从图中可以检查程序如何进行以及如何进行
    请输入图片描述
    请输入图片描述

  • Message Processing

  • In the code actually implemented, the main function calls the msg_process_vcp() function for message processing. In this case, if there is data coming from USB, msg_recv function is called to parse the message, and if any command is received, it returns TRUE to call the corresponding command function.

    int main(void)
    {
    tTime = millis();
    while(1)
    {
    msg_process_vcp();
    }
    }

    void msg_process_vcp(void)
    {
    BOOL ret;
    uint8_t ch;
    msg_t msg;

  while(vcp_is_available())
  {
    ch = vcp_getch();
    ret = msg_recv( 0, ch, &msg );

    if( ret == TRUE )
    {
      switch( msg.p_msg->msgid )
      {
        case MAVLINK_MSG_ID_READ_VERSION:
          cmd_read_version(&msg);
          break;

        case MAVLINK_MSG_ID_READ_BOARD_NAME:
          cmd_read_board_name(&msg);
          break;

        ... omit ...

       default:
         cmd_send_error(&msg, ERR_INVALID_CMD);
         break;
      }
    }
  }
}
  • For example, the Mavlink_msg_read_version_decode() function parses the message data into the data structure of the command. If the field Responsive to parsed mav_data is active, it sends the boot loader version and revision via the ACK command.

请输入图片描述

void cmd_read_version( msg_t *p_msg )
{
  err_code_t err_code = OK;
  mavlink_ack_t     mav_ack;
  mavlink_read_version_t mav_data;


  mavlink_msg_read_version_decode(p_msg->p_msg, &mav_data);


  if( mav_data.resp == 1 )
  {
    mav_ack.msg_id   = p_msg->p_msg->msgid;
    mav_ack.err_code = err_code;
    mav_ack.data[0] = boot_version;
    mav_ack.data[1] = boot_version>>8;
    mav_ack.data[2] = boot_version>>16;
    mav_ack.data[3] = boot_version>>24;
    mav_ack.data[4] = boot_revision;
    mav_ack.data[5] = boot_revision>>8;
    mav_ack.data[6] = boot_revision>>16;
    mav_ack.data[7] = boot_revision>>24;
    mav_ack.length  = 8;
    resp_ack(p_msg->ch, &mav_ack);
  }
}
  • Folder Structure
Item Contents
bin Save obj and bin files generated after build
common->bsp Includes board-specific functions (LED / BUTTON / USB, etc.)
common->hal Hardware independent function folders on the board
common->lib Libraries used externally or publicly
msg->mavlink Communication protocol source generated by Xml
msg->xml The xml file folder where you defined the command
src Function folder required for boot loader function

请输入图片描述

纠错,疑问,交流: 请进入讨论区点击加入Q群

获取最新文章: 扫一扫右上角的二维码加入“创客智造”公众号


标签: none