目录

  • Flash编程基础知识
  • Flash Programming
  • 微信公众号

Flash编程基础知识

参考 Flash_Programming_1 for KIT_AURIX_TC397_TFT, 本例展示了如何烧写PFLASH(Program Flash memory) 和 DFLASH(Data Flash memory).

  • 数据存储单元(DMU, Data Memory Unit)控制执行在PFLASH和DFLASH上的命令序列, 连接FSI(Flash Standard Interface)和PFI(Programming Flash Interface).
  • FSI在所有闪存上执行擦除, 编程和验证操作.
  • PFI为每个PFLASH块与CPU提供唯一的点对点快速连接
  • TC39x 提供 6 Program Flash Banks(PFx) 和 2 Data Flash Banks(DFx)
  • TC3xx 具有相同扇区结构的PFLASH块PFx, PFx块大小可能不用: 3/2/1 Mbyte Program Flash Bank
  • TC39x 有5个3MB大小的PFx(PF0…PF4) 和 1个1MB大小的PF5. 每个PFx被划分为1024KB大小的物理扇区(Physical Sectors), 每个物理扇区又被划分为16KB大小的逻辑扇区(Logical Sectors)
  • TC39x具有两个数据闪存存储区DFLASH0和DFLASH1, 两者都包括多个通常用于EEPROM仿真的EEPROM扇区. 仅DFLASH0包含用于数据保护的用户配置块(UCBs, User Configuration Blocks)和1个配置扇区(CFS, Configuration Sector), 用户无法直接访问该配置扇区.
  • DFLASH EEPROM可以配置为单端模式(默认)或补码检测(incomplement sensing). 根据所选模式, 每个扇区的大小分别设置为4KB和2KB
  • 闪存中可以编程的最小数据量是页(Page), 程序闪存(Program Flash)页由32字节组成, 数据闪存(Data Flash)页由8字节组成
  • 仅在擦除操作后才能对页面进行编程
  • 可以执行擦除操作的最小单元是逻辑扇区(Logical Sector)

TC39x Program Flash Memeory:

TC39x Data Flash memory:

所有闪存操作均通过命令序列执行, DMU具有命令序列解释器(CSI, Command Sequence Interpreter)来处理命令序列, 用于对程序闪存或数据闪存进行编程的最小命令序列如下:

  • 擦除逻辑扇区待编程
  • 等待直到闪存就绪(不忙)
  • 进入页面模式
  • 等待直到闪存就绪(不忙)
  • 加载要写入页面的数据
  • 写页面
  • 等待直到闪存内存已准备就绪(不忙)

注:执行PFLASH编程或擦除的代码不应从同一PFLASH执行

PF0…PF5的地址映射为:

Address Range Size Description Read Write
A000 0000H - A02F FFFFH 3 Mbyte Program Flash 0 (PF0) Access SRIBE
A030 0000H - A05F FFFFH 3 Mbyte Program Flash 1 (PF1) Access SRIBE
A060 0000H - A08F FFFFH 3 Mbyte Program Flash 2 (PF2) Access SRIBE
A090 0000H - A0BF FFFFH 3 Mbyte Program Flash 3 (PF3) Access SRIBE
A0C0 0000H - A0EF FFFFH 3 Mbyte Program Flash 4 (PF4) Access SRIBE
A0F0 0000H - A0FF FFFFH 1 Mbyte Program Flash 5 (PF5) Access SRIBE

其中, SRIBE: A bus access is terminated with a bus error on the SRI(SRI上的总线错误终止总线访问)

DF0…DF1的地址映射为:

Address Range Size Description Read Write
AF00 0000H - AF0F FFFFH 1 Mbyte Data Flash 0 EEPROM (DF0) Host Comd. Sequence Interpreter Access Access 1)
AF10 0000H - AF3F FFFFH 3 Mbyte Reserved SRIBE SRIBE
AF40 0000H - AF40 5FFFH 24 Kbyte Data Flash 0 UCB (DF0) Access SRIBE
AF40 6000H - AF7F FFFFH - Reserved SRIBE SRIBE
AF80 0000H - AF80 FFFFH 64 Kbyte Data Flash 0 CFS (DF0) Access SRIBE
AF81 0000H - AFBF FFFFH - Reserved SRIBE SRIBE
AFC0 0000H - AFC1 FFFFH 128 Kbyte Data Flash 1 EEPROM (DF1) HSM Comd. Sequence Interpreter Access Access 2)

其中:

    1. Host Command Sequence Interpreter(主机命令序列解释器)
    1. HSM Command Sequence Interpreter(HSM命令序列解释器)

Flash Programming

直接搬运官方的例程来看, 此例中, 程序闪存(PFLASH)的64个字节随后被烧写并验证. 此外, 烧写并验证了64字节的数据闪存(DFLASH). 在进行任何写操作之前, 将擦除闪存, 如果闪存烧写并验证成功, 则将打开每个测试内存的LED.

闪存中可以编程的最小数据量是页(Page), 程序闪存(Program Flash)页由32字节组成, 数据闪存(Data Flash)页由8字节组成, 所以64字节对应PFLASH的2页, DFLASH的8页.

Cpu0_Main.c 代码如下:

#include "Ifx_Types.h"
#include "IfxCpu.h"
#include "IfxScuWdt.h"IFX_ALIGN(4) IfxCpu_syncEvent g_cpuSyncEvent = 0;#include <string.h>
#include "Ifx_Types.h"
#include "IfxFlash.h"
#include "IfxCpu.h"void initLEDs(void);            /* Function that initializes the LEDs                                               */
void writeProgramFlash(void);   /* Function that flashes the Program Flash memory calling the routines from the PSPR*/
void writeDataFlash(void);      /* Function that flashes the Data Flash memory                                      */
void verifyProgramFlash(void);  /* Function that verifies the data written in the Program Flash memory              */
void verifyDataFlash(void);     /* Function that verifies the data written in the Data Flash memory                 */#define PFLASH_PAGE_LENGTH          IFXFLASH_PFLASH_PAGE_LENGTH /* 0x20 = 32 Bytes (smallest unit that can be* programmed in the Program Flash memory (PFLASH)) */
#define DFLASH_PAGE_LENGTH          IFXFLASH_DFLASH_PAGE_LENGTH /* 0x8 = 8 Bytes (smallest unit that can be* programmed in the Data Flash memory (DFLASH))    */
#define FLASH_MODULE                0                           /* Macro to select the flash (PMU) module           */
#define PROGRAM_FLASH_0             IfxFlash_FlashType_P0       /* Define the Program Flash Bank to be used         */
#define DATA_FLASH_0                IfxFlash_FlashType_D0       /* Define the Data Flash Bank to be used            */#define DATA_TO_WRITE               0x07738135                  /* Dummy data to be written into the Flash memories */#define PFLASH_STARTING_ADDRESS     0xA00E0000                  /* Address of the PFLASH where the data is written  */
#define DFLASH_STARTING_ADDRESS     0xAF000000                  /* Address of the DFLASH where the data is written  */#define PFLASH_NUM_PAGE_TO_FLASH    2                           /* Number of pages to flash in the PFLASH           */
#define PFLASH_NUM_SECTORS          1                           /* Number of PFLASH sectors to be erased            */
#define DFLASH_NUM_PAGE_TO_FLASH    8                           /* Number of pages to flash in the DFLASH           */
#define DFLASH_NUM_SECTORS          1                           /* Number of DFLASH sectors to be erased            *//* Reserved space for erase and program routines in bytes */
#define ERASESECTOR_LEN             (100)
#define WAITUNBUSY_LEN              (100)
#define ENTERPAGEMODE_LEN           (100)
#define LOADPAGE2X32_LEN            (100)
#define WRITEPAGE_LEN               (100)
#define ERASEPFLASH_LEN             (0x100)
#define WRITEPFLASH_LEN             (0x200)/* Relocation address for the erase and program routines: Program Scratch-Pad SRAM (PSPR) of CPU0 */
#define RELOCATION_START_ADDR       (0x70100000U)/* Definition of the addresses where to relocate the erase and program routines, given their reserved space */
#define ERASESECTOR_ADDR            (RELOCATION_START_ADDR)
#define WAITUNBUSY_ADDR             (ERASESECTOR_ADDR + ERASESECTOR_LEN)
#define ENTERPAGEMODE_ADDR          (WAITUNBUSY_ADDR + WAITUNBUSY_LEN)
#define LOAD2X32_ADDR               (ENTERPAGEMODE_ADDR + ENTERPAGEMODE_LEN)
#define WRITEPAGE_ADDR              (LOAD2X32_ADDR + LOADPAGE2X32_LEN)
#define ERASEPFLASH_ADDR            (WRITEPAGE_ADDR + WRITEPAGE_LEN)
#define WRITEPFLASH_ADDR            (ERASEPFLASH_ADDR + ERASEPFLASH_LEN)/* Definition of the LEDs port pins */
#define LED1                        &MODULE_P13,0               /* LED connected to Port 13, Pin 0                  */
#define LED2                        &MODULE_P13,1               /* LED connected to Port 13, Pin 1                  */#define MEM(address)                *((uint32 *)(address))      /* Macro to simplify the access to a memory address *//*********************************************************************************************************************/
/*------------------------------------------------Function Prototypes------------------------------------------------*/
/*********************************************************************************************************************/
void erasePFLASH(uint32 sectorAddr);
void writePFLASH(uint32 startingAddr);
void copyFunctionsToPSPR(void);typedef struct
{void (*eraseSectors)(uint32 sectorAddr, uint32 numSector);uint8 (*waitUnbusy)(uint32 flash, IfxFlash_FlashType flashType);uint8 (*enterPageMode)(uint32 pageAddr);void (*load2X32bits)(uint32 pageAddr, uint32 wordL, uint32 wordU);void (*writePage)(uint32 pageAddr);void (*eraseFlash)(uint32 sectorAddr);void (*writeFlash)(uint32 startingAddr);
} Function;/*********************************************************************************************************************/
/*-------------------------------------------------Global variables--------------------------------------------------*/
/*********************************************************************************************************************/
Function g_commandFromPSPR;/*********************************************************************************************************************/
/*---------------------------------------------Function Implementations----------------------------------------------*/
/*********************************************************************************************************************/
/* Function to initialize the LEDs */
void initLEDs()
{/* Configure LED1 and LED2 port pins */IfxPort_setPinMode(LED1, IfxPort_Mode_outputPushPullGeneral);IfxPort_setPinMode(LED2, IfxPort_Mode_outputPushPullGeneral);/* Turn off the LEDs (LEDs are low-level active) */IfxPort_setPinState(LED1, IfxPort_State_high);IfxPort_setPinState(LED2, IfxPort_State_high);
}/* This function copies the erase and program routines to the Program Scratch-Pad SRAM (PSPR) of the CPU0 and assigns* function pointers to them.*/
void copyFunctionsToPSPR()
{/* Copy the IfxFlash_eraseMultipleSectors() routine and assign it to a function pointer */memcpy((void *)ERASESECTOR_ADDR, (const void *)IfxFlash_eraseMultipleSectors, ERASESECTOR_LEN);g_commandFromPSPR.eraseSectors = (void *)ERASESECTOR_ADDR;/* Copy the IfxFlash_waitUnbusy() routine and assign it to a function pointer */memcpy((void *)WAITUNBUSY_ADDR, (const void *)IfxFlash_waitUnbusy, WAITUNBUSY_LEN);g_commandFromPSPR.waitUnbusy = (void *)WAITUNBUSY_ADDR;/* Copy the IfxFlash_enterPageMode() routine and assign it to a function pointer */memcpy((void *)ENTERPAGEMODE_ADDR, (const void *)IfxFlash_enterPageMode, ENTERPAGEMODE_LEN);g_commandFromPSPR.enterPageMode = (void *)ENTERPAGEMODE_ADDR;/* Copy the IfxFlash_loadPage2X32() routine and assign it to a function pointer */memcpy((void *)LOAD2X32_ADDR, (const void *)IfxFlash_loadPage2X32, LOADPAGE2X32_LEN);g_commandFromPSPR.load2X32bits = (void *)LOAD2X32_ADDR;/* Copy the IfxFlash_writePage() routine and assign it to a function pointer */memcpy((void *)WRITEPAGE_ADDR, (const void *)IfxFlash_writePage, WRITEPAGE_LEN);g_commandFromPSPR.writePage = (void *)WRITEPAGE_ADDR;/* Copy the erasePFLASH() routine and assign it to a function pointer */memcpy((void *)ERASEPFLASH_ADDR, (const void *)erasePFLASH, ERASEPFLASH_LEN);g_commandFromPSPR.eraseFlash = (void *)ERASEPFLASH_ADDR;/* Copy the erasePFLASH() routine and assign it to a function pointer */memcpy((void *)WRITEPFLASH_ADDR, (const void *)writePFLASH, WRITEPFLASH_LEN);g_commandFromPSPR.writeFlash = (void *)WRITEPFLASH_ADDR;
}/* This function erases a given sector of the Program Flash memory. The function is copied in the PSPR through* copyFunctionsToPSPR(). Because of this, inside the function, only routines from the PSPR or inline functions* can be called, otherwise a Context Type (CTYP) trap can be triggered.*/
void erasePFLASH(uint32 sectorAddr)
{/* Get the current password of the Safety WatchDog module */uint16 endInitSafetyPassword = IfxScuWdt_getSafetyWatchdogPasswordInline();/* Erase the sector */IfxScuWdt_clearSafetyEndinitInline(endInitSafetyPassword);      /* Disable EndInit protection                   */g_commandFromPSPR.eraseSectors(sectorAddr, PFLASH_NUM_SECTORS); /* Erase the given sector                       */IfxScuWdt_setSafetyEndinitInline(endInitSafetyPassword);        /* Enable EndInit protection                    *//* Wait until the sector is erased */g_commandFromPSPR.waitUnbusy(FLASH_MODULE, PROGRAM_FLASH_0);
}/* This function writes the Program Flash memory. The function is copied in the PSPR through copyFunctionsToPSPR().* Because of this, inside the function, only routines from the PSPR or inline functions can be called,* otherwise a Context Type (CTYP) trap can be triggered.*/
void writePFLASH(uint32 startingAddr)
{uint32 page;                                                /* Variable to cycle over all the pages             */uint32 offset;                                              /* Variable to cycle over all the words in a page   *//* Get the current password of the Safety WatchDog module */uint16 endInitSafetyPassword = IfxScuWdt_getSafetyWatchdogPasswordInline();/* Write all the pages */for(page = 0; page < PFLASH_NUM_PAGE_TO_FLASH; page++)              /* Loop over all the pages                  */{uint32 pageAddr = startingAddr + (page * PFLASH_PAGE_LENGTH);   /* Get the address of the page              *//* Enter in page mode */g_commandFromPSPR.enterPageMode(pageAddr);/* Wait until page mode is entered */g_commandFromPSPR.waitUnbusy(FLASH_MODULE, PROGRAM_FLASH_0);/* Write 32 bytes (8 double words) into the assembly buffer */for(offset = 0; offset < PFLASH_PAGE_LENGTH; offset += 0x8)     /* Loop over the page length                */{g_commandFromPSPR.load2X32bits(pageAddr, DATA_TO_WRITE, DATA_TO_WRITE); /* Load 2 words of 32 bits each */}/* Write the page */IfxScuWdt_clearSafetyEndinitInline(endInitSafetyPassword);      /* Disable EndInit protection               */g_commandFromPSPR.writePage(pageAddr);                          /* Write the page                           */IfxScuWdt_setSafetyEndinitInline(endInitSafetyPassword);        /* Enable EndInit protection                *//* Wait until the page is written in the Program Flash memory */g_commandFromPSPR.waitUnbusy(FLASH_MODULE, PROGRAM_FLASH_0);}
}/* This function flashes the Program Flash memory calling the routines from the PSPR */
void writeProgramFlash()
{boolean interruptState = IfxCpu_disableInterrupts(); /* Get the current state of the interrupts and disable them*//* Copy all the needed functions to the PSPR memory to avoid overwriting them during the flash execution */copyFunctionsToPSPR();/* Erase the Program Flash sector before writing */g_commandFromPSPR.eraseFlash(PFLASH_STARTING_ADDRESS);/* Write the Program Flash */g_commandFromPSPR.writeFlash(PFLASH_STARTING_ADDRESS);IfxCpu_restoreInterrupts(interruptState);            /* Restore the interrupts state                            */
}/* This function verifies if the data has been correctly written in the Program Flash */
void verifyProgramFlash()
{uint32 page;                                                /* Variable to cycle over all the pages             */uint32 offset;                                              /* Variable to cycle over all the words in a page   */uint32 errors = 0;                                          /* Variable to keep record of the errors            *//* Verify the written data */for(page = 0; page < PFLASH_NUM_PAGE_TO_FLASH; page++)                          /* Loop over all the pages      */{uint32 pageAddr = PFLASH_STARTING_ADDRESS + (page * PFLASH_PAGE_LENGTH);    /* Get the address of the page  */for(offset = 0; offset < PFLASH_PAGE_LENGTH; offset += 0x4)                 /* Loop over the page length    */{/* Check if the data in the Program Flash is correct */if(MEM(pageAddr + offset) != DATA_TO_WRITE){/* If not, count the found errors */errors++;}}}/* If the data is correct, turn on the LED1 */if(errors == 0){IfxPort_setPinState(LED1, IfxPort_State_low);}
}/* This function flashes the Data Flash memory.* It is not needed to run this function from the PSPR, thus functions from the Program Flash memory can be called* inside.*/
void writeDataFlash()
{uint32 page;                                                /* Variable to cycle over all the pages             *//* --------------- ERASE PROCESS --------------- *//* Get the current password of the Safety WatchDog module */uint16 endInitSafetyPassword = IfxScuWdt_getSafetyWatchdogPassword();/* Erase the sector */IfxScuWdt_clearSafetyEndinit(endInitSafetyPassword);        /* Disable EndInit protection                       */IfxFlash_eraseMultipleSectors(DFLASH_STARTING_ADDRESS, DFLASH_NUM_SECTORS); /* Erase the given sector           */IfxScuWdt_setSafetyEndinit(endInitSafetyPassword);          /* Enable EndInit protection                        *//* Wait until the sector is erased */IfxFlash_waitUnbusy(FLASH_MODULE, DATA_FLASH_0);/* --------------- WRITE PROCESS --------------- */for(page = 0; page < DFLASH_NUM_PAGE_TO_FLASH; page++)      /* Loop over all the pages                          */{uint32 pageAddr = DFLASH_STARTING_ADDRESS + (page * DFLASH_PAGE_LENGTH); /* Get the address of the page     *//* Enter in page mode */IfxFlash_enterPageMode(pageAddr);/* Wait until page mode is entered */IfxFlash_waitUnbusy(FLASH_MODULE, DATA_FLASH_0);/* Load data to be written in the page */IfxFlash_loadPage2X32(pageAddr, DATA_TO_WRITE, DATA_TO_WRITE); /* Load two words of 32 bits each            *//* Write the loaded page */IfxScuWdt_clearSafetyEndinit(endInitSafetyPassword);    /* Disable EndInit protection                       */IfxFlash_writePage(pageAddr);                           /* Write the page                                   */IfxScuWdt_setSafetyEndinit(endInitSafetyPassword);      /* Enable EndInit protection                        *//* Wait until the data is written in the Data Flash memory */IfxFlash_waitUnbusy(FLASH_MODULE, DATA_FLASH_0);}
}/* This function verifies if the data has been correctly written in the Data Flash */
void verifyDataFlash()
{uint32 page;                                                /* Variable to cycle over all the pages             */uint32 offset;                                              /* Variable to cycle over all the words in a page   */uint32 errors = 0;                                          /* Variable to keep record of the errors            *//* Verify the written data */for(page = 0; page < DFLASH_NUM_PAGE_TO_FLASH; page++)                          /* Loop over all the pages      */{uint32 pageAddr = DFLASH_STARTING_ADDRESS + (page * DFLASH_PAGE_LENGTH);    /* Get the address of the page  */for(offset = 0; offset < DFLASH_PAGE_LENGTH; offset += 0x4)                 /* Loop over the page length    */{/* Check if the data in the Data Flash is correct */if(MEM(pageAddr + offset) != DATA_TO_WRITE){/* If not, count the found errors */errors++;}}}/* If the data is correct, turn on the LED2 */if(errors == 0){IfxPort_setPinState(LED2, IfxPort_State_low);}
}void core0_main(void)
{IfxCpu_enableInterrupts();/* !!WATCHDOG0 AND SAFETY WATCHDOG ARE DISABLED HERE!!* Enable the watchdogs and service them periodically if it is required*/IfxScuWdt_disableCpuWatchdog(IfxScuWdt_getCpuWatchdogPassword());IfxScuWdt_disableSafetyWatchdog(IfxScuWdt_getSafetyWatchdogPassword());/* Wait for CPU sync event */IfxCpu_emitEvent(&g_cpuSyncEvent);IfxCpu_waitEvent(&g_cpuSyncEvent, 1);/* Initialize the LEDs */initLEDs();/* Flash the Program Flash memory and verify the written data */writeProgramFlash();verifyProgramFlash();/* Flash the Data Flash memory and verify the written data */writeDataFlash();verifyDataFlash();while(1){}
}

编译运行程序, 两个LED亮表示Flash操作成功.

在擦除和写PFLASH后面各打一个断点:

调试运行, Memory窗口中, 添加地址0xA00E0000, Resume程序, 第一个断点停止, 将显示0或0xEEEEEEEE, 因为它无法读取已擦除的内存, 再Resume, 第二个断点停止后, 应显示64个字节, 内容为0x07738135 :

同理, DFLASH查看地址0xAF000000:

微信公众号

欢迎扫描关注我的微信公众号, 及时获取最新文章:

AURIX TC397 Flash编程相关推荐

  1. 使用 Trace32 对 FLASH 编程

    from:   http://www.ibm.com/developerworks/cn/linux/l-trace32/ 随着软硬件复杂性的增加,在嵌入式系统开发中,调试器对项目的开发进度.质量起着 ...

  2. C语言获取norflash大小,NOR Flash 编程

    NOR Flash 编程1//************************************************************************************* ...

  3. NAND FLASH编程器烧录详解

    NAND FLASH编程器_NAND FLASH烧录器 SUPERPRO5000是西尔特出品的新一代USB接口独立式智能极速NAND FLASH编程器.具有编程速度快,烧录稳定,软件集成度高,更智能化 ...

  4. 【stm32f407】flash编程

    一.Flash介绍 不同型号的STM32F40xx/41xx,其FLASH容量也有所不同,最小的只有128K字节,最大的则达到了1024K字节.STM32F4的FLASH容量为1024K字节,如参考手 ...

  5. STM32F1_片内FLASH编程

    前言 今天总结"STM32F103  片内FLASH编程",对于学习编程的人来说"FLASH"这个词肯定很熟悉,因为FLASH主要用于存储数据.对于STM32来 ...

  6. ADSP-21565的开发详解(三)Flash编程和烧写实现脱机运行的详细说明

    硬件准备 ADSP-21565CB开发板 AD-HP530ICE仿真器 软件准备 CCES,CrossCoreUtilities 安装软件 CCES已经安装好了,我们烧写程序,要再装一个插件,就是这个 ...

  7. TMS570学习3-内部Flash编程

    QQ:971586331 软件环境: 操作系统:windows 10 IDE:CCS7.4 代码生成工具:HALCoGen 04.07.01 Flash操作库:F021FlashApi-02.01.0 ...

  8. STM32L0芯片FLASH编程示例及提醒

    关注+星标公众号,不错过精彩内容 来源 | 茶花MCU 这里就STM32L053芯片的FLASH编程做个简单演示并做些提醒,以供有需要的人参考. 一般来讲,FLASH编程主要包括擦除.代码编程.Opt ...

  9. STM32F系列单片机内部FLASH编程

    STM32F系列单片机内部含有较大容量的FLASH存储器,但没有EEPROM存储器,有时候对于参数的保存不得不另外加一片EEPROM芯片.这对于现如今大部分MCU都是FLASH+EEPROM的配置而言 ...

  10. stm32的flash编程

    有时需要存储一些数据,在复位后仍然不会丢失,这可能就会用到片上flash,stm32的片上flash结构见另一篇博客stm32的存储器与复位. 对flash的编程逻辑上是比较简单的,<flash ...

最新文章

  1. python 多线程日志切割+日志分析
  2. Duilib开发环境搭建
  3. springmvc(17)异步消息简介(部分)
  4. mysql中主从复制配置文件_MySQL主从复制 配置文件实例
  5. PHP单引号 ' ',没有任何意义,对所引内容不经任何处理直接拿过来
  6. MySQL的常见命令
  7. ROG游戏手机5跑分曝光:全球首发18GB超大内存
  8. 什么是IEC 61508?
  9. pcDuino的linux移植五GPIO驱动开发
  10. 23 android多线程
  11. 洛谷OJ P3368 【模板】树状数组 2
  12. 部队室内靶场有哪些硬件设备和强制性存在的系统
  13. CleanMyMac4.11.1中文完整语言版本
  14. CF1556E Equilibrium
  15. python读取歌词文本,并显示在图片上,制作视频
  16. 如何根据当前时间获取下一个整五分钟
  17. 在线影视网站分享(持续更新)
  18. 学好单片机好找工作吗?单片机学到什么程度可以找工作?
  19. 《线性代数及其应用》阅读笔记:一 1.5 线性方程组的解集
  20. 我所知道的张小龙 by和菜头

热门文章

  1. cmd贪吃蛇(cmd贪吃蛇怎么做)
  2. PHP icbc工商银行开放平台聚合支付,二维码扫码支付API云收呗对接步骤,稳步发展
  3. C++——STL容器
  4. vue在新的标签页打开pdf文件
  5. 景深与焦距、物距、像元、光圈之间的关系
  6. python怎么打开cmd-python中调用cmd
  7. python里的平方_python中的平方
  8. nmos导通流向_MOS管知识详细说明!结构,原理,技术参数详解,一定要进来看下...
  9. Easy ip 简单配置实验
  10. 《菜根谭》原文附译文