shuichan_old/V1.4-Chinese/STM32F103_App1/HardWare/W25Q64/w25q64.h

112 lines
4.0 KiB
C
Raw Normal View History

#ifndef __W25Q64_H
#define __W25Q64_H
#include <stdint.h>
#include "main.h"
#ifdef __cplusplus
extern "C" {
#endif
/* -------------------------------------------------
* W25Q64 SPI Flash
* SPI GPIO:
* CS -> PB4
* CLK -> PB3
* DO -> PB5 (Flash / MCU )
* DI -> PA15 (Flash / MCU )
* ------------------------------------------------- */
#define W25Q64_FLASH_SIZE (8ul * 1024 * 1024) /* 8MB */
#define W25Q64_SECTOR_SIZE 4096u
#define W25Q64_BLOCK_SIZE 65536u
#define W25Q64_PAGE_SIZE 256u
#define W25Q64_JEDEC_ID 0xEF4017u /* W25Q64JV */
/* 命令字 */
#define W25Q64_CMD_WRITE_ENABLE 0x06u
#define W25Q64_CMD_WRITE_DISABLE 0x04u
#define W25Q64_CMD_READ_STATUS1 0x05u
#define W25Q64_CMD_READ_DATA 0x03u
#define W25Q64_CMD_PAGE_PROGRAM 0x02u
#define W25Q64_CMD_SECTOR_ERASE 0x20u
#define W25Q64_CMD_BLOCK_ERASE 0xD8u
#define W25Q64_CMD_CHIP_ERASE 0xC7u
#define W25Q64_CMD_READ_ID 0x9Fu
/* 外部 Flash 分区布局(每个区 256KB足够放下 224KB 的 APP */
#define W25Q64_SLOT_SIZE 0x40000u /* 256KB */
#define W25Q64_SLOT_BACKUP_ADDR 0x000000u /* 槽 A旧版本 / 回退镜像 */
#define W25Q64_SLOT_NEW_ADDR 0x040000u /* 槽 B新下载的固件 */
/* 信息区:两个独立的 4KB 扇区,双副本冗余,必须避开固件槽 B 的 0x040000~0x07FFFF */
#define W25Q64_INFO_SECTOR_A 0x080000u
#define W25Q64_INFO_SECTOR_B 0x081000u
#define W25Q64_INFO_MAGIC 0x5741544Fu /* 'WATO' */
/* OTA 状态 */
#define W25Q64_STATE_IDLE 0u
#define W25Q64_STATE_DOWNLOADED 1u
#define W25Q64_STATE_COPYING 2u
#define W25Q64_STATE_INSTALLED 3u
#define W25Q64_STATE_ROLLBACK 4u
#define W25Q64_MAX_TRIALS 3u
#pragma pack(push, 1)
typedef struct {
uint32_t magic; /* 0x5741544F */
uint32_t sequence; /* 写入序号,越大越新 */
uint16_t new_version; /* 新版本号 */
uint32_t new_size; /* 新固件大小 */
uint16_t new_crc16; /* 新固件 MODBUS CRC16 */
uint8_t new_valid; /* 槽 B 固件是否有效 */
uint8_t update_state; /* 当前 OTA 状态 */
uint16_t boot_trial_count; /* 已尝试启动次数 */
uint8_t app_confirmed; /* APP 运行稳定后置 1 */
uint8_t reserved1;
uint16_t backup_version; /* 备份固件版本号 */
uint32_t backup_size; /* 备份固件大小 */
uint16_t backup_crc16; /* 备份固件 CRC16 */
uint8_t backup_valid; /* 槽 A 备份是否有效 */
uint8_t reserved2;
uint16_t checksum; /* 前面所有字节累加和 */
} W25Q64_OtaInfo;
#pragma pack(pop)
/* 基础 SPI Flash 操作 */
uint8_t W25Q64_Init(void);
void W25Q64_ReadID(uint8_t *id3);
uint8_t W25Q64_ReadStatus(void);
void W25Q64_WaitBusy(void);
void W25Q64_WriteEnable(void);
void W25Q64_SectorErase(uint32_t addr);
void W25Q64_BlockErase(uint32_t addr);
void W25Q64_ChipErase(void);
void W25Q64_PageProgram(uint32_t addr, const uint8_t *data, uint16_t len);
void W25Q64_Read(uint32_t addr, uint8_t *buf, uint32_t len);
void W25Q64_EraseRegion(uint32_t addr, uint32_t size);
int W25Q64_WriteBuffer(uint32_t addr, const uint8_t *data, uint32_t len);
int W25Q64_Verify(uint32_t addr, const uint8_t *data, uint32_t len);
/* OTA 专用信息区操作 */
int W25Q64_OTA_ReadInfo(W25Q64_OtaInfo *info);
int W25Q64_OTA_WriteInfo(const W25Q64_OtaInfo *info);
int W25Q64_OTA_SetNewInfo(uint16_t version, uint32_t size, uint16_t crc16);
int W25Q64_OTA_SetBackupInfo(uint32_t size, uint16_t crc16);
int W25Q64_OTA_ClearNew(void);
int W25Q64_OTA_SetState(uint8_t state);
int W25Q64_OTA_IncTrial(void);
int W25Q64_OTA_SetConfirmed(void);
int W25Q64_OTA_ClearConfirmed(void);
uint16_t W25Q64_CRC16(const uint8_t *data, uint32_t len);
#ifdef __cplusplus
}
#endif
#endif /* __W25Q64_H */