快速应用RT-Thread IAP升级功能

2023-11-11

参考官方文档

文档地址

步骤一准备bootload

进入网站选择升级的芯片配置好,下载bootloader
地址
填写分区配置
在这里插入图片描述
在这里插入图片描述

填写加密等配置

在这里插入图片描述
将 Bootloader 下载烧录到片内,烧录地址就是我们正常的启始地址0x08000000

APP项目设置及代码修改

下载RTT源码

下载地址

进入如下目录:rt-thread/bsp选择合适的平台,我这里选择rt-thread/bsp/stm32/stm32f103-atk-warshipv3
在这里插入图片描述
进入目录,右键在这打开env
在这里插入图片描述
键入命令:menuconfig回车
进入如下界面
在这里插入图片描述
SPACE选中ota
在这里插入图片描述
回车键进入二级菜单,选中如下
在这里插入图片描述
他会自动选择如下的FAL组件
在这里插入图片描述
选中如下,开启片内flash
在这里插入图片描述
通过键,选择Save,回车键,回车键,即可保存更改。
在这里插入图片描述
键入scons --target=mdk5+回车键,生成工程!
KEIL生成bin文件设置

fromelf --bin !L --output rtthread.bin

在这里插入图片描述

修改main.c

增加以下代码,设置中断向量表偏移

#define RT_APP_PART_ADDR	0x8040000/**< 目前APP*/

#define APP_VERSION		"V1.0.0"
/**
 * Function    ota_app_vtor_reconfig
 * Description Set Vector Table base location to the start addr of app(RT_APP_PART_ADDR).
*/
static int ota_app_vtor_reconfig(void)
{
    #define NVIC_VTOR_MASK   0x3FFFFF80
    /* Set the Vector Table base location by user application firmware definition */
    SCB->VTOR = RT_APP_PART_ADDR & NVIC_VTOR_MASK;

    return 0;
}
INIT_BOARD_EXPORT(ota_app_vtor_reconfig);

增加以下代码支持FAL,并初始化

#include "fal.h"//!<增加FAL组件
/*main.c中初始化FAL组件*/
fal_init();
/*打印版本号*/
rt_kprintf("The Current Vsersion is :%s\n",APP_VERSION);

增加分区表配置文件

此文件可有FAL源码中例程里找到,复制一份并修改即可

/*
 * File      : fal_cfg.h
 * This file is part of FAL (Flash Abstraction Layer) package
 * COPYRIGHT (C) 2006 - 2018, RT-Thread Development Team
 *
 *  This program is free software; you can redistribute it and/or modify
 *  it under the terms of the GNU General Public License as published by
 *  the Free Software Foundation; either version 2 of the License, or
 *  (at your option) any later version.
 *
 *  This program is distributed in the hope that it will be useful,
 *  but WITHOUT ANY WARRANTY; without even the implied warranty of
 *  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
 *  GNU General Public License for more details.
 *
 *  You should have received a copy of the GNU General Public License along
 *  with this program; if not, write to the Free Software Foundation, Inc.,
 *  51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
 *
 * Change Logs:
 * Date           Author       Notes
 * 2018-05-17     armink       the first version
 */

#ifndef _FAL_CFG_H_
#define _FAL_CFG_H_

#include <rtconfig.h>
#include <board.h>

#define NOR_FLASH_DEV_NAME             "norflash0"/**< 未使用 */

/* ===================== Flash device Configuration ========================= */
extern const struct fal_flash_dev stm32f1_onchip_flash;
//extern struct fal_flash_dev nor_flash0;/**< 未使用 */

/* flash device table */
#define FAL_FLASH_DEV_TABLE                                          \
{                                                                    \
    &stm32f1_onchip_flash,                                           \
}
/* ====================== Partition Configuration ========================== */
#ifdef FAL_PART_HAS_TABLE_CFG
/* partition table */
#define FAL_PART_TABLE                                                               \
{                                                                                    \
	{FAL_PART_MAGIC_WORD,   "bl",   	  "stm32_onchip",          0,  128*1024, 0}, \
    {FAL_PART_MAGIC_WORD,   "download",   "stm32_onchip",   128*1024,  128*1024, 0}, \
    {FAL_PART_MAGIC_WORD,   "app",     	  "stm32_onchip",   256*1024,  128*1024, 0}, \
	{FAL_PART_MAGIC_WORD,   "factory",    "stm32_onchip",   384*1024,  128*1024, 0}, \
}
#endif /* FAL_PART_HAS_TABLE_CFG */

#endif /* _FAL_CFG_H_ */

依据分区表的配置修改flash驱动

/*
 * File      : fal_flash_stm32f1_port.c
 * This file is part of FAL (Flash Abstraction Layer) package
 * COPYRIGHT (C) 2006 - 2018, RT-Thread Development Team
 *
 *  This program is free software; you can redistribute it and/or modify
 *  it under the terms of the GNU General Public License as published by
 *  the Free Software Foundation; either version 2 of the License, or
 *  (at your option) any later version.
 *
 *  This program is distributed in the hope that it will be useful,
 *  but WITHOUT ANY WARRANTY; without even the implied warranty of
 *  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
 *  GNU General Public License for more details.
 *
 *  You should have received a copy of the GNU General Public License along
 *  with this program; if not, write to the Free Software Foundation, Inc.,
 *  51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
 *
 * Change Logs:
 * Date           Author       Notes
 * 2018-01-26     armink       the first version
 */

#include <fal.h>

#include <stm32f1xx.h>

/* base address of the flash sectors */

#define FLASH_PAGE_0_ADDR			 ((uint32_t)0x08000000)	/* 物理flash原始起始页地址 */
#define FLASH_START_PAGE_ADDR		 FLASH_PAGE_0_ADDR		/* 分区表起始地址 */
#define CURRENT_PART_START_PAGE	 	 ((FLASH_START_PAGE_ADDR-FLASH_PAGE_0_ADDR)/FLASH_PAGE_SIZE)	/* 当前分区实际物理起始页 */
#define FLASH_PAGE_NUM_MAX			 ((uint32_t)255+1)
/**
 * Get the sector of a given address
 *
 * @param address flash address
 *
 * @return The sector of a given address
 */
static uint32_t stm32_get_sector(uint32_t Startaddress ,size_t size ,uint32_t *get_pages)
{
		/*记录起始页与结束页*/
    	uint32_t Startpage = 0,Endpage = 0;
		/*搜索完成标记*/
		uint8_t start_page_flag = 0,end_page_flag = 0;
		/*计算起始地址所在页*/
		if(Startaddress >= stm32f1_onchip_flash.addr)
		{
				for(uint32_t i = 0; i < FLASH_PAGE_NUM_MAX;i++)
				{
						/*计算首地址所在页*/
						if(start_page_flag == 0)
						{
							if((i*FLASH_PAGE_SIZE+FLASH_PAGE_0_ADDR+FLASH_PAGE_SIZE-1) >= Startaddress)
							{
								log_i("first erase page:%d",i);
								Startpage = i;
								start_page_flag = 1;
							}
						}
						/*计算尾地址所在页*/
						if(end_page_flag == 0)
						{
							if((i*FLASH_PAGE_SIZE+FLASH_PAGE_0_ADDR+FLASH_PAGE_SIZE-1) >= (Startaddress+size-1))
							{
								log_i("end erase page:%d",i);
								Endpage = i;
								end_page_flag = 1;
								break;
							}
						}
				}
		}
		else
		{
				/*地址非法*/
				*get_pages = 0;
				return Startpage;
		}
		/*计算地址范围内的页数*/
		*get_pages = Endpage-Startpage+1;

    return Startpage*FLASH_PAGE_SIZE+FLASH_PAGE_0_ADDR;
}

/**
 * Get the sector size
 *
 * @param sector sector
 *
 * @return sector size
 */
static uint32_t stm32_get_sector_size(uint32_t pages) 
{
	return pages*FLASH_PAGE_SIZE;	//!< 2K一页			
}
static int init(void)
{
    /* do nothing now */
		return 0;
}

static int read(long offset, uint8_t *buf, size_t size)
{
    size_t i;
    uint32_t addr = stm32f1_onchip_flash.addr + offset;
    for (i = 0; i < size; i++, addr++, buf++)
    {
        *buf = *(uint8_t *) addr;
    }

    return size;
}

static int write(long offset, const uint8_t *buf, size_t size)
{
    size_t i;
    uint32_t read_data;
    uint32_t addr = stm32f1_onchip_flash.addr + offset;

    HAL_FLASH_Unlock();
    __HAL_FLASH_GET_FLAG(
    FLASH_FLAG_EOP | FLASH_FLAG_WRPERR | FLASH_FLAG_PGERR
            | FLASH_FLAG_OPTVERR);
	uint16_t data = 0;
    for (i = 0; i < size; i++)
    {
        /* write data */
		log_i("write addr:0x%04X",addr);
		data = *(buf+i);
		if((i+1) < size)
		{
				i++;
				data |= ((uint16_t)*(buf+i)<<8);
		}
		else
		{
				data &= 0x00FF;
		}
        HAL_FLASH_Program(FLASH_TYPEPROGRAM_HALFWORD ,addr, data);
		read_data = *(uint16_t *) addr;
		addr += 2;
        
        /* check data */
        if (read_data != data)
        {
			log_i("data unmatched read data:%d",read_data);
            return -1;
        }
    }
    HAL_FLASH_Lock();

    return size;
}

static int erase(long offset, size_t size)
{
    HAL_StatusTypeDef flash_status;
    size_t erased_size = 0;
    
    uint32_t addr = stm32f1_onchip_flash.addr + offset;
	FLASH_EraseInitTypeDef erase_config = {0};
	uint32_t erasepages = 0;
	uint32_t error;
    /* start erase */
    HAL_FLASH_Unlock();
    __HAL_FLASH_GET_FLAG(
    FLASH_FLAG_EOP | FLASH_FLAG_WRPERR | FLASH_FLAG_PGERR
            | FLASH_FLAG_OPTVERR);
    /* it will stop when erased size is greater than setting size */
		
	/*擦除页地址*/
	erase_config.PageAddress = stm32_get_sector(addr ,size ,&erasepages);
	log_i("erase page addr:0x%08X,PAGES:%d",erase_config.PageAddress,erasepages);
	
	/*所属BANK*/
	erase_config.Banks = FLASH_BANK_1;
	/*按页擦除*/
	erase_config.TypeErase = FLASH_TYPEERASE_PAGES;
	/*擦除页数量*/
	erase_config.NbPages = erasepages;
	log_i("erase page number:%d",erasepages);
	flash_status = HAL_FLASHEx_Erase(&erase_config, &error);
	if (flash_status != HAL_OK)
	{
		log_i("erase error");
		return -1;
	}
	erased_size += stm32_get_sector_size(erasepages);
	log_i("erase size:%d",erased_size);
	
    HAL_FLASH_Lock();

    return size;
}

const struct fal_flash_dev stm32f1_onchip_flash =
{
    .name       = "stm32_onchip",
    .addr       = FLASH_START_PAGE_ADDR,
    .len        = 512*1024,
    .blk_size   = FLASH_PAGE_SIZE,
    .ops        = {init, read, write, erase},
    .write_gran = 32
};
  • 完成,读,写,擦除的调用接口即可!
  • 编写的依据自己的芯片,可能每个芯片以页区分,也有以扇区区分,块区分不尽相同,各自编写。
  • 以上编写以512KBflash总大小,2KB为一页,16bit单次写入,按页擦除,按字节读取,编写的驱动

第一次烧录进单片机

修改分散加载文件

在这里插入图片描述
编译下载烧录,运行可以看到串口打印的信息
在这里插入图片描述

无法烧录的情况

确认以下
在这里插入图片描述

升级包文件准备及升级

第二次使用打包器打包

  • 修改下main.c中的版本号,改为V1.0.1任意即可,方便看出程序已升级
  • 编译,打包
    在这里插入图片描述

串口连接Xshell

在 msh 命令行中输入 ymodem_ota 命令后,点击鼠标右键,然后在菜单栏找到用 YMODEM 发送选项发送文件
在这里插入图片描述

备份区烧录

  1. 与app程序一致无需单独设置
  2. 编译后的bin文件同样使用打包器打包成rpl文件,因为打包器会对其压缩加密操作,否则无法使用
  3. rpl文件更改后缀名为xx.bin使用烧写器烧录进flash的factory分区起始地址
  4. 保持按下恢复出厂设置按键情况下,启动芯片会由bootload将factory分区恢复到app分区中
  5. 完成!

下载注意大小端问题以及flash中存放地址

预期写入 1 2 3 4 5依次存放在8020008往后中
在这里插入图片描述
在这里插入图片描述
最后的结果可以看出,高地址高位数据
地址8020009数据1
为小端模式

所以应该这样
在这里插入图片描述
测试flash正常命令:
参考FAL说明

fal erase 0 4096
fal write 8 1 2 3 4 5
fal read 0 64

在这里插入图片描述

重启软件即可升级完成!

本文内容由网友自发贡献,版权归原作者所有,本站不承担相应法律责任。如您发现有涉嫌抄袭侵权的内容,请联系:hwhale#tublm.com(使用前将#替换为@)

快速应用RT-Thread IAP升级功能 的相关文章

  • NRF52840 用RTT打印log配置方法

    1 在sdk config h中配置两个宏 xff1a NRF LOG ENABLED 1 NRF LOG BACKEND RTT ENABLED 1 2 需要初始化NRF LOG static void log init void ret
  • STM32---串口实现在应用程序的固件更新(IAP)

    背景 xff1a 在产品发布后 xff0c 可能需要对固件进行更新或者升级 xff0c 那么在影响产品正常运行的情况下 xff0c 如果升级固件呢 xff1f 理论 xff1a 下面的所有理论部分内容参考 STM32开发指南 什么是IAP
  • 【STM32】IAP下载程序分析

    IAP下载程序分析 IAP基本原理STM32启动流程程序跳转代码实现总结 IAP基本原理 要实现STM32的IAP xff08 在应用编程 xff09 xff0c 需要分别建立bootloader和app工程 这里的bootloader程序
  • ICP、ISP、IAP、JTAG、SWD下载方式

    目录 ICP ISP IAP JTAG SWD下载方式 概述 JTAG SWD ICP ISP IAP ISP与ICP的差别 ISP和IAP的差别 ICP ISP IAP JTAG SWD下载方式 概述 JTAG和SWD是一种标准协议 xf
  • 【STM32---IAP】基于CAN总线的BootLoader上下位机设计

    IAP开发 下位机STM32 43 上位机Linux 一 准备工作二 IAP系统开发2 1 IAP简介2 2 IAP下位机开发2 2 1 刷写文件选择2 2 2 Bootloader程序框架2 2 3 Bootloader程序开发2 2 3
  • 12.RTT-IIC设备-AHT10温湿度传感器

    本系列博客更新结束啦 xff01 完结啦 xff01 xff01 xff01 撒花 xff01 xff01 xff01 关于RTT的设备和驱动专题更新完毕啦 xff0c 本期是最后一期 一段学习旅途的结束意味着下一段学习冒险的开始 虽然本系
  • stm32之iap实现应用(基于串口,上位机,详细源码)

    开发环境 Window 7 开发工具 Keil uVision4 硬件 stm32f103c8t6 篇幅略长 前面文字很多 主要是希望能让小白们理解 后面就是实现步骤 包括实现的代码 在研发调试的时候我们一般用烧录器下载代码 对于stm32
  • 基于ARM Cortex-M0+内核的bootloader程序升级原理及代码解析

    本文主要讲述BootLoader程序升级原理及一些代码的解析 力图用通俗易懂的语言描述清楚BootLoader升级的主要关键点 BootLoader 升级原理概述 首次接触这一块时 有一个概念叫IAP 在应用编程 通俗一点讲便是通过一段已有
  • 使用WIFI连接新大陆云平台(基于RT_Thread操作系统)

    前言 使用RT Thread Studio 连接WIFI 首先我们需要配置WIFI 具体的配置参考上面这篇文章 下面将会讲述使用WIFI连接到新大陆云平台 相关的AT指令 1 设置WIFI为Station模式 AT CWMODE 1 2 重
  • 【N32L40X】学习笔记14-在RT-thread系统中读取eeprom数据

    eeprom 说明 eeprom介绍 AT24C01A 1K串行EEPROM 内部组织16页8字节 1K需要一个7位数据字地址进行随机字寻址 AT24C02 2K串行EEPROM 内部组织32页8字节 2K需要一个8位数据字地址进行随机字寻
  • STM32F4 RTC-Alarm 的使用(RT-Thread操作系统)

    文章目录 1 工程的创建和配置 1 1 CubeMX 的配置 1 1 1 时钟源的选择 1 1 2 Debug 引脚配置 1 1 3 控制台串口的配置 1 1 4 RTC的配置 1 1 5 时钟树配置 1 1 6 代码生成 1 2 RT T
  • 内核7-线程间同步

    目录 1 信号量 1 1 信号量机制 1 2 信号量的使用场合 1 2 1 线程同步 1 2 2 锁 1 2 3 中断与线程的同步 1 2 4 资源计数 1 3 信号量控制块 1 4 函数 1 4 1 rt sem init 函数 1 4
  • IAP与APP(一):两个固件使用Keil5默认设置编译后,利用J-Flash偏移APP的地址然后合并IAP烧写,运行时出现在跳转APP时无限重启的现象

    最近做了个在线升级 并没有使用系统 芯片 STM32F103C8T6 环境 Keil 5 STM32CubeMX 5 2 1 跳转和写FLASH在网上一搜其实不少 主要注意要重定向中断向量表和跳转前要关闭所有中断 在写好IAP和APP两个固
  • STM32在应用编程(IAP)详解

    什么是IAP STM32单片机的程序烧写有多种方法 分别为 JTAG SW ISP IAP gt JTAG的方式需要专用的烧写工具 在产品布置到现场后 更新产品程序比较麻烦 gt ISP即为 在系统编程 In System Programm
  • STM32 之八 在线升级(IAP)超详细图解 及 需要注意的问题解决

    IAP 是啥 IAP In Application Programming 即在应用编程 也就是用户可以使用自己的程序对MCU的中的运行程序进行更新 而无需借助于外部烧写器 其实ST官网也给出了IAP的示例程序 感兴趣的可以直接去官网搜索
  • 正点原子STM32 H743完成RT Thread下的LAN8720 网卡驱动 LWIP跑起来

    目前RT官网对H743的支持力度还不理想 本想按照F407的搞定网卡的套路来搞定H743的网卡 因为phy也是LAN 8720 以为会很轻松 没想到却是一条遍布荆棘的路 好在已经有不少大佬做了不少工作 终于在巨人肩膀人完成了网卡的驱动 能p
  • STM32在线升级 (IAP)

    来自QQ群 Linux 技术分享 311078264 打开链接加入QQ群 https jq qq com wv 1027 k 5Gr3bAx 此文档由elikang整理 为了文章简单直接 许多细节未能在文章中体现 如有疑问请进群讨论 STM
  • RT-Thread操作系统 AT组件源码分析(以 EC20 为例)

    文章目录 1 AT 组件 1 1 AT 组件调试信息级别设置 1 2 AT 命令打印使能设置 1 3 GPRS 网络注册状态检查 1 4 EC200x 是否能连接外网日志输出 1 5 AT 设备注册过程 1 6 AT 设备类注册过程 1 7
  • RT-Thread 内核基础(六)

    RT Thread内核配置示例 RT Thread的一个重要特性是高度可裁剪性 支持对内核进行精细调整 对组件进行灵活拆卸 配置主要是通过修改工程目录下的rtconfig h文件来进行 用户可以通过打开 关闭该文件中的宏定义来对代码进行条件
  • RT-Thread 内核基础(四)

    自动初始化机制 自动初始化机制是指初始化函数不需要被显示调用 只需要在函数定义处通过宏定义的方式进行申明 就会在系统启动过程中被执行 例如在串口驱动中调用一个宏定义告知系统初始化需要调用的函数 代码如下 int rt hw usart in

随机推荐

  • Vue简易登陆页面

    目录 1 效果展示 2 Vue代码 3 存点图片 1 效果展示 2 Vue代码
  • selenium练习实例

    1 项目流程 2 中心调度 中心调度 defmain try total search total int re compile d search total group 1 fori inrange 2 total 1 next page
  • 一分钟解决Chrome浏览器主页被hao123、360和2345篡改简单有效方法

    当你打开浏览器看到各种首页跳转的页面 对于强迫症的我是不能接受的 各种情况都碰到了 现在给出解决方法 按照下面的方式去排查就可以一定能解决你的问题 如果不行的话你来打我呀 如果问题解决了希望你能推荐给其他人 提示 检查下杀毒软件有没有绑定浏
  • Raft一致性算法分析与总结

    Raft简介 Raft是一个用于日志复制 同步的一致性算法 它提供了和Paxos一样的功能和性能 但是它的算法结构与Paxos不同 这使得Raft相比Paxos更好理解 并且更容易构建实际的系统 为了强调可理解性 Raft将一致性算法分解为
  • 跨平台传输结构体的注意事项

    1 什么是跨平台 1 这里的平台是按照CPU的位数来划分 分为32位CPU和64位CPU 不同位数CPU的差异会影响到结构体的解析 2 在实际嵌入式开发中 存在 主芯片 从芯片 的多CPU的产品 或者数据需要在不同位数CPU的机器上传输 3
  • 矩阵乘法——基于GPU的并行编程模型CUDA程序设计

    矩阵乘法 基于GPU的并行编程模型CUDA程序设计 目录 矩阵乘法 基于GPU的并行编程模型CUDA程序设计 1 题目描述 2 设计思路 实验环境 3 源码 3 1 串行程序 3 2 并行程序 3 3 性能对比与分析 1 题目描述 题目1
  • 二分图笔记

    什么是二分图 二分图一般针对无向图问题 一张图中 如果能够把全部的点分到两个集合中 保证两个集合内部没有任何边 图中的边只存在于两个集合之间 即为二分图 判断二分图 1 染色法 即用两种颜色对于这张图进行染色 相邻的结点颜色不同 如果没有矛
  • 结构重参数化之二:RepVGG

    论文 RepVGG Making VGG style ConvNets Great Again 代码 GitHub DingXiaoH RepVGG RepVGG Making VGG style ConvNets Great Again
  • Vue中实现图片下载到本地功能和导出(下载)excel文件功能:

    一 实现图片下载到本地功能 需求 将勾选的列表项的id传给后台 让后台处理并下载对应的图片 1 后台接口 下载图片zip GET download 请求数据类型 application x www form urlencoded 响应数据类
  • 神武3手游微信月礼包服务器,千万红包雨豪礼送不停 《神武3》端手游今日同步上线...

    神武3 双端今日 11月24日 同步上线 公测盛典活动全面开启 新服齐开 还有海量礼包 千万红包雨以及神兽 iPAD等各种大礼等你来拿 神武3 今日公测 公测新服齐开 千万红包雨来袭 神武3 端游 手游今日同步上线之际 新服齐开 其中 端游
  • 【HDLBits 刷题 6】Circuits(2)Sequential Logic---Latches and Filp Flops

    目录 写在前面 Latches and Filp Flops Dff Dff8 Dff8r Dff8p Dff8ar Dff16e D Latch DFF1 DFF2 DFF gate Mux and DFF1 Mux and DFF2 D
  • fedora图形界面与命令行模式切换方法

    fedora 进入命令行 终端 startx 在图形界面的控制台上输入 init 3 即可停止 xwindow 如果无法返回到终端 可以按住 alt ctrl f2 f6启动到新的控制台 然后结束掉tty1上的xwindow 结束xwind
  • 二维数组 A[m][n] 按行优先和按列优先的 下标地址转换公式

    设二维数组 A m n 按行优先存储 每个元素占 p 个字节 则 Loc i j 的地址为 i n j p 第 i 行前面有 i 行 每行有 n 个元素 加上 第 i 行的的 j 个元素 所以地址 为 i n j p 1 若 j 从下标 1
  • 【Windows系统5分钟搭建Linux环境】

    安装 Linux 虚拟机 第1步 下载 VirtualBox 第2步 下载 Vagrant 第3步 拉取Linux虚拟机镜像 第4步 网络配置 网络地址转换 端口转发 注意 电脑需要开启 CPU 虚拟化 电脑开机时 进入BIOS界面设置 第
  • SpringSecurity学习笔记(十一)CSRF攻击以及CORS跨域

    参考视频 什么是CSRF CSRF 跨站请求伪造 也可称为一站式攻击 也可写作XSRF 按照字面意思来理解 跨站请求伪造 意思就是说用户登录了A网站之后 会话没有过期 然后登录了B网站 这个时候B网站中的请求访问了A网站 这个时候A网站就会
  • STM32 基础系列教程 44 - FSMC_LCD

    前言 TFT LCD 即薄膜晶体管液晶显示器 其英文全称为 Thin Film Transistor Liquid Crystal Display TFT LCD 与无源 TN LCD STN LCD 的简单矩阵不同 它在液晶显示屏的每一个
  • c++智能指针

    智能指针 智能指针也是模版 在头文件
  • Vue 引入路径正确的,但一直报错: Already included file name ‘××ב differs from file name ‘××ב only in casing.

    Vue 引入路径 import from 报错 引入的文件名和地址都是正确的 但是还是报错误 Already included file name differs from file name only in casing 这时候我们只要把
  • 爬虫 第七讲 MongoDB

    文章目录 爬虫 第七讲 MongoDB SQL和NoSQL的主要区别 MongoDB的优势 1 无数据结构限制 2 大数据量和高性能 3 良好的支持 MongoDB在Ubuntu中安装 MongoDB在Windows中安装 MongoDB概
  • 快速应用RT-Thread IAP升级功能

    快速应用RT Thread IAP升级功能 参考官方文档 步骤一准备bootload APP项目设置及代码修改 下载RTT源码 修改main c 增加分区表配置文件 依据分区表的配置修改flash驱动 第一次烧录进单片机 修改分散加载文件