diff --git a/examples/platform/k32w/app/ldscripts/chip-k32w061-linker.ld b/examples/platform/k32w/app/ldscripts/chip-k32w061-linker.ld index 477040162d2fd9..7aaf99c46d3d25 100644 --- a/examples/platform/k32w/app/ldscripts/chip-k32w061-linker.ld +++ b/examples/platform/k32w/app/ldscripts/chip-k32w061-linker.ld @@ -44,8 +44,8 @@ BOOT_RESUME_STACK_SIZE = 1024; going to sleep is more important than the total available stack size */ STACK_SIZE = (4096 - 32); -MEM_RAM0_BASE = 0x4000400; -MEM_RAM0_SIZE = 0x0015c00; +MEM_RAM0_BASE = 0x4000400; +MEM_RAM0_SIZE = 0x0015c00; MEMORY { @@ -62,32 +62,24 @@ __top_RAM0 = MEM_RAM0_BASE + MEM_RAM0_SIZE; /* 87K bytes */ /* To be improved. At this moment the second RAM bank is dedicated entirely to heap. */ HEAP_SIZE = DEFINED(HEAP_SIZE) ? HEAP_SIZE : 0xF000; -/*** flash memory characteristics definitions required for OTA ***/ -m_flash_start = 0x00000000; -m_flash_end = 0x0009FFFF; -m_flash_size = 0x000A0000; -m_sector_size = 512; -m_fsl_prodInfo_size = m_sector_size; +/* set external flash properties - external flash is present on the DK6 board */ +m_ext_flash_size = 0x00100000; +m_ext_flash_base = 0x00000000; +m_ext_flash_sector_size = 4096; -m_fsl_prodInfo_end = m_flash_size - 17 * m_sector_size - 1; -m_fsl_prodInfo_start = m_fsl_prodInfo_end - m_fsl_prodInfo_size + 1; +NVMSectorCountLink = 63; -NV_STORAGE_MAX_SECTORS = 63; -NV_STORAGE_SIZE = NV_STORAGE_MAX_SECTORS * m_sector_size; -NV_STORAGE_START_ADDRESS = m_fsl_prodInfo_start - 1; -NV_STORAGE_END_ADDRESS = NV_STORAGE_START_ADDRESS - NV_STORAGE_SIZE + 1; +NV_STORAGE_SIZE = NVMSectorCountLink * m_ext_flash_sector_size; +NV_STORAGE_MAX_SECTORS = NVMSectorCountLink; +NV_STORAGE_SECTOR_SIZE = m_ext_flash_sector_size; +NV_STORAGE_START_ADDRESS = m_ext_flash_size - 1; +NV_STORAGE_END_ADDRESS = NV_STORAGE_START_ADDRESS - NV_STORAGE_SIZE + 1; -INT_STORAGE_END = NV_STORAGE_START_ADDRESS - 1; -INT_STORAGE_START = 0x48000; -INT_STORAGE_SIZE = INT_STORAGE_END - INT_STORAGE_START; +m_app_size = 0x00a0000; /* 640K */ -FREESCALE_PROD_DATA_BASE_ADDR = m_fsl_prodInfo_start; -INT_STORAGE_SECTOR_SIZE = m_sector_size; -m_app_size = 0xA0000; /* 640K: to accommodate all libs in debug */ - -__ram_vector_table__ = 1; -vector_table_size = 0x120; -M_VECTOR_RAM_SIZE = DEFINED(__ram_vector_table__) ? vector_table_size : 0x0; +__ram_vector_table__ = 1; +vector_table_size = 0x120; +M_VECTOR_RAM_SIZE = DEFINED(__ram_vector_table__) ? vector_table_size : 0x0; ENTRY(ResetISR) @@ -328,5 +320,6 @@ SECTIONS PROVIDE(Chip_LOWPOWER_ChipSoftwareReset = 0x03003fa1); __StackLimit = _vStackTop - STACK_SIZE; - ASSERT(__StackLimit >= _end_boot_resume_stack, "Possible stack corruption with data/bss/boot_stack") + /* ASSERT(__StackLimit >= _end_boot_resume_stack, "Possible stack corruption with data/bss/boot_stack") */ + ASSERT(_etext < NV_STORAGE_START_ADDRESS, "Application does not fit into flash!") } diff --git a/third_party/k32w_sdk/k32w_sdk.gni b/third_party/k32w_sdk/k32w_sdk.gni index 5684e5a765728d..80d4dc3eb04655 100644 --- a/third_party/k32w_sdk/k32w_sdk.gni +++ b/third_party/k32w_sdk/k32w_sdk.gni @@ -74,6 +74,7 @@ template("k32w_sdk") { "${k32w_sdk_root}/middleware/wireless/bluetooth/host/config", "${k32w_sdk_root}/middleware/wireless/bluetooth/host/interface", "${k32w_sdk_root}/middleware/wireless/framework/Common", + "${k32w_sdk_root}/middleware/wireless/framework/Flash/External/Interface", "${k32w_sdk_root}/middleware/wireless/framework/Flash/Internal", "${k32w_sdk_root}/middleware/wireless/framework/FunctionLib", "${k32w_sdk_root}/middleware/wireless/framework/GPIO", @@ -107,7 +108,7 @@ template("k32w_sdk") { "${k32w_sdk_root}/middleware/wireless/ble_controller/lib/lib_ble_controller.a", "${k32w_sdk_root}//middleware/wireless/bluetooth/host/lib/lib_ble_5-0_host_peripheral_cm4_noFP.a", "${k32w_sdk_root}/middleware/wireless/ieee-802.15.4/lib/libMiniMac_Dynamic_MMAC.a", - "${k32w_sdk_root}/middleware/wireless/framework/PDM/Library/libPDM.a", + "${k32w_sdk_root}/middleware/wireless/framework/PDM/Library/libPDM_extFlash.a", "${k32w_sdk_root}/middleware/wireless/framework/SecLib/lib_crypto_m4.a", "${k32w_sdk_root}/middleware/wireless/framework/XCVR/lib/libRadio.a", ] @@ -127,6 +128,9 @@ template("k32w_sdk") { "gTotalHeapSize_c=0xF000", "gUartDebugConsole_d=1", "gUsePdm_d=1", + "PDM_EXT_FLASH=1", + "gEepromType_d=gEepromDevice_MX25R8035F_c", + "gOTA_externalFlash_d=1", "gLEDSupported_d", "gKeyBoardSupported_d", "gPdmNbSegments=63", @@ -257,6 +261,7 @@ template("k32w_sdk") { "${k32w_sdk_root}/middleware/wireless/bluetooth/host/config/ble_globals.c", "${k32w_sdk_root}/middleware/wireless/framework/Common/MicroInt_arm_sdk2.c", "${k32w_sdk_root}/middleware/wireless/framework/Flash/Internal/Flash_Adapter.c", + "${k32w_sdk_root}/middleware/wireless/framework/Flash/External/Source/Eeprom_MX25R8035F.c", "${k32w_sdk_root}/middleware/wireless/framework/FunctionLib/FunctionLib.c", "${k32w_sdk_root}/middleware/wireless/framework/GPIO/GPIO_Adapter.c", "${k32w_sdk_root}/middleware/wireless/framework/Keyboard/Source/Keyboard.c", diff --git a/third_party/k32w_sdk/sdk_fixes/Eeprom_MX25R8035F.c b/third_party/k32w_sdk/sdk_fixes/Eeprom_MX25R8035F.c new file mode 100644 index 00000000000000..51badaeed526b7 --- /dev/null +++ b/third_party/k32w_sdk/sdk_fixes/Eeprom_MX25R8035F.c @@ -0,0 +1,934 @@ +/*! ********************************************************************************* +* Copyright (c) 2015, Freescale Semiconductor, Inc. +* Copyright 2016-2017, 2019 NXP +* All rights reserved. +* +* \file +* +* This is a source file which implements the driver for the MX25R8035F memory. +* +* SPDX-License-Identifier: BSD-3-Clause +********************************************************************************** */ + + +/*! ********************************************************************************* +************************************************************************************* +* Include +************************************************************************************* +********************************************************************************** */ +#include "EmbeddedTypes.h" +#include "Eeprom.h" +#include "FunctionLib.h" + +#include "Panic.h" +#include "fsl_os_abstraction.h" + +#if gEepromType_d == gEepromDevice_MX25R8035F_c + +#include "fsl_spifi.h" +#if gLoggingActive_d +#include "dbg_logging.h" +#endif +#include "fsl_debug_console.h" + +/*! ********************************************************************************* +************************************************************************************* +* Private macros +************************************************************************************* +********************************************************************************** */ +#ifndef gEepromWriteEnable_d +#define gEepromWriteEnable_d 1 +#endif + +static osaSemaphoreId_t mExtEepromSemaphoreId; + +#define IS_WORD_ALIGNED(x) (((uint32_t)(x) & 0x3) == 0) +#define IS_PAGE_ALIGNED(x) (((uint32_t)(x) & (EEPROM_PAGE_SIZE-1)) == 0) +#define SECTOR_ADDR(x) ( ( (uint32_t)(x) / EEPROM_SECTOR_SIZE) * EEPROM_SECTOR_SIZE) +#define IS_SECTOR_ALIGNED(x) (((uint32_t)(x) & (EEPROM_SECTOR_SIZE-1)) == 0) +#define SECTOR_NUMBER(x) ((uint32_t)(x) / EEPROM_SECTOR_SIZE) + +#define BLOCK_ADDR(x) ( ( (uint32_t)(x) / EEPROM_BLOCK_SIZE) * EEPROM_BLOCK_SIZE) +#define IS_BLOCK_ALIGNED(x) (((uint32_t)(x) & (EEPROM_BLOCK_SIZE-1)) == 0) +#define BLOCK_NUMBER(x) ((uint32_t)(x) / EEPROM_BLOCK_SIZE) + +#define EEPROM_BLOCK2_SIZE (EEPROM_BLOCK_SIZE*2) +#define BLOCK2_ADDR(x) ( ( (uint32_t)(x) / EEPROM_BLOCK2_SIZE) * EEPROM_BLOCK2_SIZE) +#define IS_BLOCK2_ALIGNED(x) (((uint32_t)(x) & (EEPROM_BLOCK2_SIZE-1)) == 0) + + + + + + +/* Control Commands */ +#define EEPROM_RDSR 0x05 +#define EEPROM_RDSFDR 0x5A +#define EEPROM_WREN 0x06 +#define EEPROM_WRDI 0x04 +#define EEPROM_RDCR 0x15 +#define EEPROM_WRSR 0x01 +#define EEPROM_RDID 0x9F +#define EEPROM_RES 0xAB +#define EEPROM_REMS 0x90 +#define EEPROM_DP 0xB9 + +/* Read Commands */ +#define EEPROM_READ 0x03 +#define EEPROM_FAST_READ 0x0B +#define EEPROM_2READ 0xBB +#define EEPROM_DREAD 0x3B +#define EEPROM_4READ 0xEB +#define EEPROM_QREAD 0x6B + +/* Erase Commands */ +#define EEPROM_ERASE_4K 0x20 +#define EEPROM_ERASE_32K 0x52 +#define EEPROM_ERASE_64K 0xD8 +#define EEPROM_ERASE_ALL 0x60 + +/* Write Commands */ +#define EEPROM_WRITE_PAGE 0x02 +#define EEPROM_WRITE_QPAGE 0x38 + +/* Status Flags */ +#define EEPROM_BUSY_FLAG_MASK 0x01 +#define EEPROM_WEL_FLAG_MASK 0x02 + +#define EEPROM_PAGE_SIZE (256) +#define EEPROM_SECTOR_SIZE (4*1024) +#define EEPROM_BLOCK_SIZE (32*1024) +#define EEPROM_PAGE_MASK (EEPROM_PAGE_SIZE - 1) + +/* address mask */ +#define ADDRESS_MASK 0x000000FF + +/* SPI config */ +#ifndef gEepromSpiInstance_c +#define gEepromSpiInstance_c 1 +#endif + +/* Commands (see command array below) */ +#define CMD_SPIFI_DREAD (0) +#define CMD_SPIFI_DPROGRAM_PAGE (1) +#define CMD_SPIFI_QREAD (2) +#define CMD_SPIFI_QPROGRAM_PAGE (3) +#define CMD_SPIFI_GET_STATUS (4) +#define CMD_SPIFI_ERASE_SECTOR (5) +#define CMD_SPIFI_ERASE_BLOCK_32K (6) +#define CMD_SPIFI_ERASE_ALL (7) +#define CMD_SPIFI_WRITE_ENABLE (8) +#define CMD_SPIFI_WRITE_REGISTER (9) +#define CMD_SPIFI_ERASE_BLOCK_64K (10) +#define CMD_SPIFI_READ_ID (11) +#define CMD_SPIFI_DP (12) +#define CMD_SPIFI_RES (13) +#define CMD_SPIFI_NUM (14) + +// Flash type: including XT25F08B and MX25R8035F +#define FLASH_MX25R8035F_ID 0x1428C2 +#define FLASH_XT25F08B_ID 0x14400B +#define FLASH_UNKNOWN_ID 0xffffff + +/****************************************************************************** +******************************************************************************* +* Private Prototypes +******************************************************************************* +******************************************************************************/ +#if (gFlashEraseDuringWrite == 1) +static ee_err_t EEPROM_PrepareForWrite(uint32_t NoOfBytes, uint32_t Addr); +#endif +#if gEepromWriteEnable_d +static ee_err_t EEPROM_WritePage(uint32_t NoOfBytes, uint32_t Addr, uint8_t *Outbuf); +static void EEPROM_WriteEnable(void); +#endif +static uint32_t EEPROM_ReadStatusReq(void); +static uint32_t EEPROM_ReadIDReq(void); +static uint32_t EEPROM_ReadResReq(void); + + + +#define MX25_SR_WIP_POS 0 /* Write In Progress */ +#define MX25_SR_WEL_POS 1 /* Write Enable Latch */ +#define MX25_SR_BP_POS 2 /* Level of Protected block */ +#define MX25_SR_BP_WIDTH 4 +#define MX25_SR_BP_MASK (((1<AHBCLKCTRLSET[0] = SYSCON_AHBCLKCTRLSET0_SPIFI_CLK_SET_MASK; + BOARD_SetSpiFi_LowPowerEnter(); + } + else + { + initialized = 1; + } + while (EEPROM_isBusy()); + } + + return status; +} + +/****************************************************************************** +* NAME: EEPROM_DeInit +* DESCRIPTION: De-Initializes the EEPROM peripheral +* PARAMETERS: None +* RETURN: ee_ok - if the EEPROM has been de-initialized successfully +* ee_error - otherwise +******************************************************************************/ +ee_err_t EEPROM_DeInit(void) +{ + if (initialized) + { + OSA_SemaphoreWait(mExtEepromSemaphoreId, osaWaitForever_c); + + SPIFI_SetCommand(SPIFI, &command[CMD_SPIFI_DP]); + SPIFI_Deinit(SPIFI); + SYSCON->AHBCLKCTRLSET[0] = SYSCON_AHBCLKCTRLSET0_SPIFI_CLK_SET_MASK; + BOARD_SetSpiFi_LowPowerEnter(); + initialized = 0; + + OSA_SemaphorePost(mExtEepromSemaphoreId); + OSA_SemaphoreDestroy(mExtEepromSemaphoreId); + } + return ee_ok; +} + +/*! ********************************************************************************* +* \brief Erase all memory to 0xFF +* +* \return ee_err_t. +* +********************************************************************************** */ +#if gEepromWriteEnable_d +ee_err_t EEPROM_ChipErase(void) +{ +#if defined gFlashBlockBitmap_d + uint32_t i; +#endif + + EEPROM_DBG_LOG(""); + + OSA_SemaphoreWait(mExtEepromSemaphoreId, osaWaitForever_c); + + /* Wait for idle state : check before operation in order to let previous + * operation terminate rather than blocking */ + while (EEPROM_isBusy()); + + /* Enable write */ + EEPROM_WriteEnable(); + + /* Erase command */ + SPIFI_SetCommand(SPIFI, &command[CMD_SPIFI_ERASE_ALL]); + + OSA_SemaphorePost(mExtEepromSemaphoreId); + +#if defined gFlashBlockBitmap_d + /* Mark Flash as erased */ + for (i = 0; i < NumberOfElements(mHandle.EraseBitmap); i++) + { + mHandle.EraseBitmap[i] = 0xFF; + } +#endif + + + return ee_ok; +} +#endif + +/*! ********************************************************************************* +* \brief Erase a block of memory to 0xFF +* +* \param[in] Addr Start memory address +* \param[in] size The size of the block: either 4096 or 32768 +* +* \return ee_err_t. +* +********************************************************************************** */ +#if gEepromWriteEnable_d +ee_err_t EEPROM_EraseBlock(uint32_t Addr, uint32_t block_size) +{ + uint8_t cmd; +#if defined gFlashBlockBitmap_d + uint32_t i = Addr / block_size; +#endif + + EEPROM_DBG_LOG(""); + + OSA_SemaphoreWait(mExtEepromSemaphoreId, osaWaitForever_c); + + while (EEPROM_isBusy()); + + EEPROM_WriteEnable(); + + switch (block_size) + { + case EEPROM_SECTOR_SIZE: + cmd = CMD_SPIFI_ERASE_SECTOR; +#if defined gFlashBlockBitmap_d + mHandle.EraseBitmap[i / 8] |= 1 << (i % 8); +#endif + break; + case EEPROM_BLOCK_SIZE: + cmd = CMD_SPIFI_ERASE_BLOCK_32K; +#if defined gFlashBlockBitmap_d + mHandle.EraseBitmap[i] = 0xFF; +#endif + break; + case EEPROM_BLOCK2_SIZE: + cmd = CMD_SPIFI_ERASE_BLOCK_64K; +#if defined gFlashBlockBitmap_d + i = Addr/(block_size/2); + mHandle.EraseBitmap[i] = 0xFF; + mHandle.EraseBitmap[i+1] = 0xFF; +#endif + break; + default: + OSA_SemaphorePost(mExtEepromSemaphoreId); + return ee_error; + } + + /* Set block address: any address within the block is acceptable to the MX25R8035F */ + SPIFI_SetCommandAddress(SPIFI, FSL_FEATURE_SPIFI_START_ADDR + Addr); + + /* Erase sector or block */ + SPIFI_SetCommand(SPIFI, &command[cmd]); + + OSA_SemaphorePost(mExtEepromSemaphoreId); + + return ee_ok; +} + + +ee_err_t EEPROM_EraseArea(uint32_t *Addr, int32_t *size, bool non_blocking) +{ + ee_err_t status = ee_error; + uint32_t sz; + int32_t remain_sz = (int32_t)*size; + uint32_t erase_addr = *Addr; + + EEPROM_DBG_LOG(""); + + + do { + bool skip = false; + +#if defined gFlashBlockBitmap_d + uint32_t block_nb; + uint32_t sect_nb; +#endif + if (!IS_SECTOR_ALIGNED(erase_addr)) + { + status = ee_error; + break; + } + if (remain_sz == 0) + { + status = ee_error; + break; + } + erase_addr = SECTOR_ADDR(Addr); + for (erase_addr = *Addr; remain_sz > 0; ) + { + OSA_SemaphoreWait(mExtEepromSemaphoreId, osaWaitForever_c); + + if (non_blocking && EEPROM_isBusy()) + { + status = ee_busy; + OSA_SemaphorePost(mExtEepromSemaphoreId); + break; + } + + OSA_SemaphorePost(mExtEepromSemaphoreId); + +#if defined gFlashBlockBitmap_d + block_nb = BLOCK_NUMBER(erase_addr); +#endif + sz = EEPROM_SECTOR_SIZE; + + if ((IS_BLOCK2_ALIGNED(erase_addr) && (remain_sz >= EEPROM_BLOCK2_SIZE))) /* EEPROM_BLOCK_SIZE*2 */ + { +#if defined gFlashBlockBitmap_d + if ((mHandle.EraseBitmap[block_nb]) != 0xff) + { + sz = EEPROM_BLOCK_SIZE; + if ((mHandle.EraseBitmap[block_nb+1]) != 0xff) /* group 2 consecutive 32k blocks in one single 64k block */ + sz += EEPROM_BLOCK_SIZE; + } + else + skip = true; +#else + sz = EEPROM_BLOCK2_SIZE; +#endif /* gFlashBlockBitmap_d */ + } + else if ((IS_BLOCK_ALIGNED(erase_addr) && (remain_sz >= EEPROM_BLOCK_SIZE))) /* EEPROM_BLOCK_SIZE */ + { +#if defined gFlashBlockBitmap_d + if ((mHandle.EraseBitmap[block_nb] ) == 0) + sz = EEPROM_BLOCK_SIZE; + else + skip = true; +#else + sz = EEPROM_BLOCK_SIZE; +#endif /* gFlashBlockBitmap_d */ + + } + else /* necessarily 4k aligned */ + { +#if defined gFlashBlockBitmap_d + sect_nb = SECTOR_NUMBER(erase_addr); + if ((mHandle.EraseBitmap[block_nb] & (1 << (sect_nb%8) ) ) == 0) + sz = EEPROM_SECTOR_SIZE; + else + skip = true; +#else +#endif /* gFlashBlockBitmap_d */ + } + if (!skip) + { + EEPROM_DBG_LOG("Erasing block Addr=%x sz=%d", erase_addr, sz); + status = EEPROM_EraseBlock(erase_addr, sz); + if (status != ee_ok) break; + } + erase_addr += sz; + remain_sz -= sz; + } + status = ee_ok; + } while (0); + + *Addr = erase_addr; + *size = remain_sz; + return status; +} + +ee_err_t EEPROM_EraseNextBlock(uint32_t Addr, uint32_t size) +{ + ee_err_t status = ee_error; + uint8_t alignment = 0; + uint32_t block_size = EEPROM_SECTOR_SIZE; + uint32_t erase_addr; + EEPROM_DBG_LOG(""); + + do { + if (size<=EEPROM_SECTOR_SIZE) + { + block_size = EEPROM_SECTOR_SIZE; + alignment = 12; + } + else if (size<=EEPROM_BLOCK_SIZE) + { + block_size = EEPROM_BLOCK_SIZE; + alignment = 15; + } + else + { + block_size = EEPROM_BLOCK2_SIZE; + alignment = 16; + } + erase_addr = Addr; + erase_addr = ((erase_addr + (block_size-1)) >> alignment << alignment); + if ((size != 0) && (erase_addr < (Addr + size))) + { + status = EEPROM_EraseBlock(erase_addr, block_size); + if (status != ee_ok) break; + //while (EEPROM_isBusy()); + } + status = ee_ok;; + } while (0); + return status; +} + +ee_err_t EEPROM_SectorAlignmentAfterReset(uint32_t Addr) +{ + ee_err_t status = ee_error; +#if gEepromSupportReset + uint32_t nbBytesToCopy =0; + do + { + /* The address given should be aligned on EEPROM_PAGE_SIZE */ + if (Addr % EEPROM_PAGE_SIZE != 0) + break; + nbBytesToCopy = Addr % gEepromParams_SectorSize_c; + /* If the address is aligned on gEepromParams_SectorSize_c, nothing to do */ + if (nbBytesToCopy != 0) + { + /* copy only the necessary bytes in RAM*/ + if (EEPROM_ReadData(nbBytesToCopy, Addr-nbBytesToCopy, sectorRamBuffer) != ee_ok) + break; + /* Erase the sector */ + if (EEPROM_EraseBlock(Addr-nbBytesToCopy, EEPROM_SECTOR_SIZE) != ee_ok) + break; + /* Write the necessary bytes */ + if (EEPROM_WriteData(nbBytesToCopy, Addr-nbBytesToCopy, sectorRamBuffer) != ee_ok) + break; + } + status = ee_ok; + } while (0); +#endif + return status; +} + +#endif /* gEepromWriteEnable_d */ + +/*! ********************************************************************************* +* \brief Write a data buffer into the external memory, at a given address +* +* \param[in] NoOfBytes Number of bytes to write +* \param[in] Addr Start memory address +* \param[in] inbuf Pointer to the data +* +* \return ee_err_t. +* +********************************************************************************** */ +#if gEepromWriteEnable_d +ee_err_t EEPROM_WriteData(uint32_t NoOfBytes, uint32_t Addr, uint8_t *Outbuf) +{ + ee_err_t retval = ee_ok; + + uint32_t bytes; + + if (NoOfBytes > 0) + { + /* Will erase the sectors needed if they have not been erased during this + * session. A bit useless as it doesn't cope with an ongoing OTA that spans + * several sessions and it can't spot when you're overwriting data that is + * already there */ +#if (gFlashEraseDuringWrite == 1) + retval = EEPROM_PrepareForWrite(NoOfBytes, Addr); +#endif + + if (retval == ee_ok) + { + while ((Addr & EEPROM_PAGE_MASK) + NoOfBytes > EEPROM_PAGE_MASK) + { + bytes = EEPROM_PAGE_SIZE - (Addr & EEPROM_PAGE_MASK); + EEPROM_DBG_LOG(""); + retval = EEPROM_WritePage(bytes, Addr, Outbuf); + NoOfBytes -= bytes; + Addr += bytes; + Outbuf += bytes; + + if (retval != ee_ok) + { + break; + } + } + + retval = EEPROM_WritePage(NoOfBytes, Addr, Outbuf); + } + } + return retval; +} +#endif /* gEepromWriteEnable_d */ + +void EEPROM_SetRead(void) +{ + + OSA_SemaphoreWait(mExtEepromSemaphoreId, osaWaitForever_c); + + while (EEPROM_isBusy()); + + /* Set start address */ + SPIFI_SetCommandAddress(SPIFI, FSL_FEATURE_SPIFI_START_ADDR ); + + /* Enable read */ + if (CHIP_USING_SPIFI_DUAL_MODE()) + { + SPIFI_SetMemoryCommand(SPIFI, &command[CMD_SPIFI_DREAD]); + } + else + { + SPIFI_SetMemoryCommand(SPIFI, &command[CMD_SPIFI_QREAD]); + } + + OSA_SemaphorePost(mExtEepromSemaphoreId); +} + + + +/*! ********************************************************************************* +* \brief Reads a data buffer from the external memory, from a given address +* +* \param[in] NoOfBytes Number of bytes to read +* \param[in] Addr Start memory address +* \param[in] inbuf Pointer to a location where to store the read data +* +* \return ee_err_t. +* +********************************************************************************** */ +ee_err_t EEPROM_ReadData(uint16_t NoOfBytes, uint32_t Addr, uint8_t *inbuf) +{ + + OSA_SemaphoreWait(mExtEepromSemaphoreId, osaWaitForever_c); + + while (EEPROM_isBusy()); + + /* Set start address */ + SPIFI_SetCommandAddress(SPIFI, FSL_FEATURE_SPIFI_START_ADDR + Addr); + + /* Enable read */ + if (CHIP_USING_SPIFI_DUAL_MODE()) + { + SPIFI_SetMemoryCommand(SPIFI, &command[CMD_SPIFI_DREAD]); + } + else + { + SPIFI_SetMemoryCommand(SPIFI, &command[CMD_SPIFI_QREAD]); + } + uint8_t * flash_addr = (uint8_t*)(FSL_FEATURE_SPIFI_START_ADDR + Addr); + + FLib_MemCpy((void *)inbuf, (void *)flash_addr, NoOfBytes); + + /* Reset the SPIFI to switch to command mode */ + SPIFI_ResetCommand(SPIFI); + + OSA_SemaphorePost(mExtEepromSemaphoreId); + + return ee_ok; +} + + + +/*! ********************************************************************************* +* \brief Check if the memory controller is busy +* +* \return TRUE/FALSE. +* +********************************************************************************** */ +uint8_t EEPROM_isBusy(void) +{ + return (EEPROM_ReadStatusReq() & EEPROM_BUSY_FLAG_MASK) == EEPROM_BUSY_FLAG_MASK; +} + +/*! ********************************************************************************* +************************************************************************************* +* Private Functions +************************************************************************************* +********************************************************************************** */ + +/*! ********************************************************************************* +* \brief Read the memory controller status register +* +* \return status register. +* +********************************************************************************** */ +static uint32_t EEPROM_ReadStatusReq(void) +{ + SPIFI_SetCommand(SPIFI, &command[CMD_SPIFI_GET_STATUS]); + while ((SPIFI->STAT & SPIFI_STAT_INTRQ_MASK) == 0U) + { + } + return SPIFI_ReadPartialWord(SPIFI, command[CMD_SPIFI_GET_STATUS].dataLen); +} + +/*! ********************************************************************************* +* \brief Read ID register +* +* \return ID register. +* +********************************************************************************** */ +static uint32_t EEPROM_ReadIDReq(void) +{ + SPIFI_SetCommand(SPIFI, &command[CMD_SPIFI_READ_ID]); + while ((SPIFI->STAT & SPIFI_STAT_INTRQ_MASK) == 0U) + { + } + return SPIFI_ReadPartialWord(SPIFI, command[CMD_SPIFI_READ_ID].dataLen); +} + +/*! ********************************************************************************* +* \brief Read Electronic Signature +* +* \return Electronic Signature. +* +********************************************************************************** */ +static uint32_t EEPROM_ReadResReq(void) +{ + uint32_t result = 0; + SPIFI_SetCommand(SPIFI, &command[CMD_SPIFI_RES]); + while ((SPIFI->STAT & SPIFI_STAT_INTRQ_MASK) == 0U) + { + } + result = SPIFI_ReadPartialWord(SPIFI, command[CMD_SPIFI_RES].dataLen); + /* + * The spec of FLASH_XT25F08B_ID requires a time duration of a least 20us before accepting + * any new command after a release from Power-Down + */ + CLOCK_uDelay(21); + return result; +} + +/*! ********************************************************************************* +* \brief Enabled Write/Erase access for the next operation +* +********************************************************************************** */ +#if gEepromWriteEnable_d +static void EEPROM_WriteEnable(void) +{ + SPIFI_SetCommand(SPIFI, &command[CMD_SPIFI_WRITE_ENABLE]); +} +#endif /* gEepromWriteEnable_d */ + +/*! ********************************************************************************* +* \brief Prepare the memory for write operations (bits must be in erased state) +* +* \param[in] NoOfBytes Number of bytes to write +* \param[in] Addr Start memory address +* +* \return ee_err_t. +* +********************************************************************************** */ +#if (gFlashEraseDuringWrite == 1) +static ee_err_t EEPROM_PrepareForWrite(uint32_t NoOfBytes, uint32_t Addr) +{ + uint32_t i; + ee_err_t ret = ee_ok; + uint32_t startBlk, endBlk; + + /* Obtain the range of sectors */ + startBlk = Addr / EEPROM_SECTOR_SIZE; + endBlk = (Addr + NoOfBytes - 1) / EEPROM_SECTOR_SIZE; + + /* Check if each sector needs erase */ + for (i = startBlk; i <= endBlk; i++) + { + if ((mHandle.EraseBitmap[i/8] & (1 << (i%8) ) ) == 0) + { + ret = EEPROM_EraseBlock(i * EEPROM_SECTOR_SIZE, EEPROM_SECTOR_SIZE); + + if (ret != ee_ok) + { + break; + } + } + } + + return ret; +} +#endif /* (gFlashEraseDuringWrite == 1) */ + + +#if gEepromWriteEnable_d + +void EepromWritePage(uint32_t NoOfBytes, uint32_t Addr, uint8_t *Outbuf) +{ + EEPROM_DBG_LOG("Addr=%x", Addr); +#ifdef gFlashBlockBitmap_d + int sector_index; + uint32_t startBlk, endBlk; + + /* Obtain the range of sectors */ + startBlk = Addr / EEPROM_SECTOR_SIZE; + endBlk = (Addr + NoOfBytes - 1) / EEPROM_SECTOR_SIZE; + + /* Mark each sector as written */ + for (sector_index = startBlk; sector_index <= endBlk; sector_index++) + { + mHandle.EraseBitmap[sector_index/8] &= ~ (1 << (sector_index%8)); + } +#endif /* gFlashBlockBitmap_d */ + + OSA_SemaphoreWait(mExtEepromSemaphoreId, osaWaitForever_c); + + EEPROM_WriteEnable(); + SPIFI_SetCommandAddress(SPIFI, Addr + FSL_FEATURE_SPIFI_START_ADDR); + + if (CHIP_USING_SPIFI_DUAL_MODE()) + { + command[CMD_SPIFI_DPROGRAM_PAGE].dataLen = NoOfBytes; + SPIFI_SetCommand(SPIFI, &command[CMD_SPIFI_DPROGRAM_PAGE]); + } + else + { + command[CMD_SPIFI_QPROGRAM_PAGE].dataLen = NoOfBytes; + SPIFI_SetCommand(SPIFI, &command[CMD_SPIFI_QPROGRAM_PAGE]); + } + SPIFI_WriteBuffer(SPIFI, Outbuf, NoOfBytes); + + OSA_SemaphorePost(mExtEepromSemaphoreId); +} + +/*! ********************************************************************************* +* \brief Writes maximum 256 bytes into a memory page +* +* \param[in] NoOfBytes Number of bytes to write into thr page +* \param[in] Addr Start memory address +* \param[in] Outbuf Pointer to the data to be written +* +* \return ee_err_t. +* +********************************************************************************** */ +static ee_err_t EEPROM_WritePage(uint32_t NoOfBytes, uint32_t Addr, uint8_t *Outbuf) +{ + EEPROM_DBG_LOG(""); + + if (NoOfBytes > 0) + { + OSA_SemaphoreWait(mExtEepromSemaphoreId, osaWaitForever_c); + + while (EEPROM_isBusy()); + + OSA_SemaphorePost(mExtEepromSemaphoreId); + + EepromWritePage(NoOfBytes, Addr, Outbuf); + } + + return ee_ok; +} + +#endif /* gEepromWriteEnable_d */ +#endif /* gEepromType_d == gEepromDevice_MX25R8035F_c */ + diff --git a/third_party/k32w_sdk/sdk_fixes/openthread-core-k32w061-config.h b/third_party/k32w_sdk/sdk_fixes/openthread-core-k32w061-config.h deleted file mode 100755 index e9327c5dbd8c1f..00000000000000 --- a/third_party/k32w_sdk/sdk_fixes/openthread-core-k32w061-config.h +++ /dev/null @@ -1,226 +0,0 @@ -/* - * Copyright (c) 2019, The OpenThread Authors. - * All rights reserved. - * - * Redistribution and use in source and binary forms, with or without - * modification, are permitted provided that the following conditions are met: - * 1. Redistributions of source code must retain the above copyright - * notice, this list of conditions and the following disclaimer. - * 2. Redistributions in binary form must reproduce the above copyright - * notice, this list of conditions and the following disclaimer in the - * documentation and/or other materials provided with the distribution. - * 3. Neither the name of the copyright holder nor the - * names of its contributors may be used to endorse or promote products - * derived from this software without specific prior written permission. - * - * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" - * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE - * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE - * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE - * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR - * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF - * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS - * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN - * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) - * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE - * POSSIBILITY OF SUCH DAMAGE. - */ - -/** - * @file - * This file includes k32w061 compile-time configuration constants - * for OpenThread. - */ - -#ifndef OPENTHREAD_CORE_K32W061_CONFIG_H_ -#define OPENTHREAD_CORE_K32W061_CONFIG_H_ - -/** - * @def OPENTHREAD_CONFIG_LOG_OUTPUT - * - */ -#ifndef OPENTHREAD_CONFIG_LOG_OUTPUT /* allow command line override */ -#define OPENTHREAD_CONFIG_LOG_OUTPUT OPENTHREAD_CONFIG_LOG_OUTPUT_PLATFORM_DEFINED -#endif - -/** - * @def OPENTHREAD_CONFIG_PLATFORM_INFO - * - * The platform-specific string to insert into the OpenThread version string. - * - */ -#ifndef OPENTHREAD_CONFIG_PLATFORM_INFO -#define OPENTHREAD_CONFIG_PLATFORM_INFO "K32W061" -#endif - -/** - * @def SETTINGS_CONFIG_BASE_ADDRESS - * - * The base address of settings. - * - */ -#ifndef SETTINGS_CONFIG_BASE_ADDRESS -#define SETTINGS_CONFIG_BASE_ADDRESS 0 -#endif - -/** - * @def SETTINGS_CONFIG_PAGE_SIZE - * - * The page size of settings. - * - */ -#ifndef SETTINGS_CONFIG_PAGE_SIZE -#define SETTINGS_CONFIG_PAGE_SIZE 0x200 -#endif - -/** - * @def SETTINGS_CONFIG_PAGE_NUM - * - * The page number of settings. - * - */ -#ifndef SETTINGS_CONFIG_PAGE_NUM -#define SETTINGS_CONFIG_PAGE_NUM 64 -#endif - -/** - * @def RADIO_CONFIG_SRC_MATCH_ENTRY_NUM - * - * The number of source address table entries. - * - */ -#ifndef RADIO_CONFIG_SRC_MATCH_ENTRY_NUM -#define RADIO_CONFIG_SRC_MATCH_ENTRY_NUM 128 -#endif - -/** - * @def OPENTHREAD_CONFIG_NCP_HDLC_ENABLE - * - * Define to 1 to enable NCP HDLC support. - * - */ -#ifndef OPENTHREAD_CONFIG_NCP_HDLC_ENABLE -#define OPENTHREAD_CONFIG_NCP_HDLC_ENABLE 1 -#endif - -/** - * @def OPENTHREAD_SETTINGS_RAM - * - * Define to 1 if you want to use K32W061 Flash implementation. - * - */ -#ifndef OPENTHREAD_SETTINGS_RAM -#define OPENTHREAD_SETTINGS_RAM 0 -#endif - -/** - * @def OPENTHREAD_CONFIG_NCP_TX_BUFFER_SIZE - * - * The size of NCP message buffer in bytes. - * - */ -#ifndef OPENTHREAD_CONFIG_NCP_TX_BUFFER_SIZE -#define OPENTHREAD_CONFIG_NCP_TX_BUFFER_SIZE 1024 -#endif - -/** - * @def OPENTHREAD_CONFIG_HEAP_INTERNAL_SIZE - * - * The size of heap buffer when DTLS is enabled. - * - */ -#ifndef OPENTHREAD_CONFIG_HEAP_INTERNAL_SIZE -#define OPENTHREAD_CONFIG_HEAP_INTERNAL_SIZE (2048 * sizeof(void *)) -#endif - -/** - * @def OPENTHREAD_CONFIG_COAP_API_ENABLE - * - * Define to 1 to enable the CoAP API. - * - */ -#ifndef OPENTHREAD_CONFIG_COAP_API_ENABLE -#define OPENTHREAD_CONFIG_COAP_API_ENABLE 1 -#endif - -/** - * @def OPENTHREAD_CONFIG_JOINER_ENABLE - * - * Define to 1 to enable Joiner support. - * - */ -#ifndef OPENTHREAD_CONFIG_JOINER_ENABLE -#define OPENTHREAD_CONFIG_JOINER_ENABLE 1 -#endif - -/** - * @def OPENTHREAD_CONFIG_COMMISSIONER_ENABLE - * - * Define to 1 to enable Commissioner support. - * - */ -#ifndef OPENTHREAD_CONFIG_COMMISSIONER_ENABLE -#define OPENTHREAD_CONFIG_COMMISSIONER_ENABLE 1 -#endif - -/** - * @def OPENTHREAD_CONFIG_UDP_FORWARD_ENABLE - * - * Define to 1 to enable UDP forward support. - * - */ -#ifndef OPENTHREAD_CONFIG_UDP_FORWARD_ENABLE -#define OPENTHREAD_CONFIG_UDP_FORWARD_ENABLE 1 -#endif - -/** - * @def OPENTHREAD_CONFIG_BORDER_ROUTER_ENABLE - * - * Define to 1 to enable the Border Router service. - * - */ -#ifndef OPENTHREAD_CONFIG_BORDER_ROUTER_ENABLE -#define OPENTHREAD_CONFIG_BORDER_ROUTER_ENABLE 1 -#endif - -/** - * @def OPENTHREAD_CONFIG_DHCP6_CLIENT_ENABLE - * - * Define to 1 to enable the DHCP CLIENT service. - * - */ -#ifndef OPENTHREAD_CONFIG_DHCP6_CLIENT_ENABLE -#define OPENTHREAD_CONFIG_DHCP6_CLIENT_ENABLE 1 -#endif - -/** - * @def OPENTHREAD_CONFIG_DHCP6_SERVER_ENABLE - * - * Define to 1 to enable the DHCP SERVER service. - * - */ -#ifndef OPENTHREAD_CONFIG_DHCP6_SERVER_ENABLE -#define OPENTHREAD_CONFIG_DHCP6_SERVER_ENABLE 1 -#endif - -/** - * @def OPENTHREAD_CONFIG_TIME_SYNC_ENABLE - * - * Define as 1 to enable the time synchronization service feature. - * - */ -#ifndef OPENTHREAD_CONFIG_TIME_SYNC_ENABLE -#define OPENTHREAD_CONFIG_TIME_SYNC_ENABLE 0 -#endif - -/** - * @def OPENTHREAD_CONFIG_DIAG_ENABLE - * - * Define as 1 to enable the diag feature. - * - */ -#ifndef OPENTHREAD_CONFIG_DIAG_ENABLE -#define OPENTHREAD_CONFIG_DIAG_ENABLE 0 -#endif - -#endif // OPENTHREAD_CORE_K32W061_CONFIG_H_ diff --git a/third_party/k32w_sdk/sdk_fixes/patch_k32w_sdk.sh b/third_party/k32w_sdk/sdk_fixes/patch_k32w_sdk.sh index e1673233262fc4..02eb1901132c31 100755 --- a/third_party/k32w_sdk/sdk_fixes/patch_k32w_sdk.sh +++ b/third_party/k32w_sdk/sdk_fixes/patch_k32w_sdk.sh @@ -12,8 +12,7 @@ cp ./third_party/k32w_sdk/sdk_fixes/pin_mux.c "$K32W061_SDK_ROOT"/boards/k32w061 cp ./third_party/k32w_sdk/sdk_fixes/ntag_driver.h "$K32W061_SDK_ROOT"/middleware/ntag_i2c_plus/HAL_NTAG/inc/ cp ./third_party/k32w_sdk/sdk_fixes/HAL_I2C_jn_fsl.h "$K32W061_SDK_ROOT"/middleware/ntag_i2c_plus/HAL_I2C/inc/ cp ./third_party/k32w_sdk/sdk_fixes/SerialManager.c "$K32W061_SDK_ROOT"/middleware/wireless/framework/SerialManager/Source/ -cp ./third_party/k32w_sdk/sdk_fixes/system.c ./third_party/openthread/ot-nxp/src/k32w/platform/ -cp ./third_party/k32w_sdk/sdk_fixes/openthread-core-k32w061-config.h ./third_party/openthread/ot-nxp/src/k32w/k32w061 +cp ./third_party/k32w_sdk/sdk_fixes/Eeprom_MX25R8035F.c "$K32W061_SDK_ROOT"/middleware/wireless/framework/Flash/External/Source echo "K32W SDK Master Release 3 was patched!" exit 0 diff --git a/third_party/k32w_sdk/sdk_fixes/system.c b/third_party/k32w_sdk/sdk_fixes/system.c deleted file mode 100644 index b54414978a5bfb..00000000000000 --- a/third_party/k32w_sdk/sdk_fixes/system.c +++ /dev/null @@ -1,141 +0,0 @@ -/* - * Copyright (c) 2019, The OpenThread Authors. - * All rights reserved. - * - * Redistribution and use in source and binary forms, with or without - * modification, are permitted provided that the following conditions are met: - * 1. Redistributions of source code must retain the above copyright - * notice, this list of conditions and the following disclaimer. - * 2. Redistributions in binary form must reproduce the above copyright - * notice, this list of conditions and the following disclaimer in the - * documentation and/or other materials provided with the distribution. - * 3. Neither the name of the copyright holder nor the - * names of its contributors may be used to endorse or promote products - * derived from this software without specific prior written permission. - * - * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" - * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE - * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE - * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE - * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR - * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF - * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS - * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN - * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) - * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE - * POSSIBILITY OF SUCH DAMAGE. - */ - -/** - * @file - * This file includes the platform-specific initializers. - * - */ -#include "board.h" -#include "clock_config.h" -#include "pin_mux.h" -#include "platform-k32w.h" -#include "utils/uart.h" - -#include "MemManager.h" - -#include -#include - -otInstance * sInstance; -OT_TOOL_WEAK uint32_t gInterruptDisableCount = 0; - -void otSysInit(int argc, char * argv[]) -{ - bool bHwInit = true; - - if ((argc == 1) && (!strcmp(argv[0], "app"))) - { - bHwInit = false; - } - - if (bHwInit) - { - /* Security code to allow debug access */ - SYSCON->CODESECURITYPROT = 0x87654320; - - BOARD_BootClockRUN(); - BOARD_InitPins(); - K32WRandomInit(); - MEM_Init(); - } - - K32WAlarmInit(); - K32WRadioInit(); - -#if (OPENTHREAD_CONFIG_LOG_OUTPUT == OPENTHREAD_CONFIG_LOG_OUTPUT_PLATFORM_DEFINED) || \ - (OPENTHREAD_CONFIG_LOG_OUTPUT == OPENTHREAD_CONFIG_LOG_OUTPUT_NCP_SPINEL) - K32WLogInit(); -#endif -} - -bool otSysPseudoResetWasRequested(void) -{ - return false; -} - -void otSysDeinit(void) {} - -void otSysProcessDrivers(otInstance * aInstance) -{ - K32WRadioProcess(aInstance); - K32WUartProcess(); - K32WAlarmProcess(aInstance); -} - -WEAK void otSysEventSignalPending(void) -{ - /* Intentionally left empty */ -} - -/*FUNCTION********************************************************************** - * - * Function Name : OSA_InterruptEnable - * Description : self explanatory. - * - *END**************************************************************************/ -OT_TOOL_WEAK void OSA_InterruptEnable(void) -{ - if (gInterruptDisableCount > 0) - { - gInterruptDisableCount--; - - if (gInterruptDisableCount == 0) - { - __enable_irq(); - } - /* call core API to enable the global interrupt*/ - } -} -/*FUNCTION********************************************************************** - * - * Function Name : OSA_InterruptDisable - * Description : self explanatory. - * - *END**************************************************************************/ -OT_TOOL_WEAK void OSA_InterruptDisable(void) -{ - /* call core API to disable the global interrupt*/ - __disable_irq(); - - /* update counter*/ - gInterruptDisableCount++; -} - -/*FUNCTION********************************************************************** - * - * Function Name : OSA_InstallIntHandler - * Description : This function is used to install interrupt handler. - * - *END**************************************************************************/ -OT_TOOL_WEAK void OSA_InstallIntHandler(uint32_t IRQNumber, void (*handler)(void)) -{ -#ifdef ENABLE_RAM_VECTOR_TABLE - InstallIRQHandler((IRQn_Type) IRQNumber, (uint32_t) handler); -#endif -}