mirror of
https://github.com/espressif/esp-idf.git
synced 2024-10-05 20:47:46 -04:00
spi_flash: Building a framework to enable HPM when flash works under high speed mode
This commit is contained in:
parent
e85c5822a2
commit
6c9c1f72bd
@ -1,5 +1,5 @@
|
||||
/*
|
||||
* SPDX-FileCopyrightText: 2015-2021 Espressif Systems (Shanghai) CO LTD
|
||||
* SPDX-FileCopyrightText: 2015-2022 Espressif Systems (Shanghai) CO LTD
|
||||
*
|
||||
* SPDX-License-Identifier: Apache-2.0
|
||||
*/
|
||||
@ -24,10 +24,12 @@
|
||||
#define CMD_RDID 0x9F
|
||||
#define CMD_WRSR 0x01
|
||||
#define CMD_WRSR2 0x31 /* Not all SPI flash uses this command */
|
||||
#define CMD_WRSR3 0x11 /* Not all SPI flash uses this command */
|
||||
#define CMD_WREN 0x06
|
||||
#define CMD_WRDI 0x04
|
||||
#define CMD_RDSR 0x05
|
||||
#define CMD_RDSR2 0x35 /* Not all SPI flash uses this command */
|
||||
#define CMD_RDSR3 0x15 /* Not all SPI flash uses this command */
|
||||
#define CMD_OTPEN 0x3A /* Enable OTP mode, not all SPI flash uses this command */
|
||||
#define CMD_RDSFDP 0x5A /* Read the SFDP of the flash */
|
||||
#define CMD_WRAP 0x77 /* Set burst with wrap command */
|
||||
|
@ -573,7 +573,7 @@ esp_err_t IRAM_ATTR __attribute__((weak)) bootloader_flash_unlock(void)
|
||||
#ifndef g_rom_spiflash_dummy_len_plus // ESP32-C3 uses a macro to access ROM data here
|
||||
extern uint8_t g_rom_spiflash_dummy_len_plus[];
|
||||
#endif
|
||||
IRAM_ATTR static uint32_t bootloader_flash_execute_command_common(
|
||||
IRAM_ATTR uint32_t bootloader_flash_execute_command_common(
|
||||
uint8_t command,
|
||||
uint32_t addr_len, uint32_t address,
|
||||
uint8_t dummy_len,
|
||||
|
@ -168,7 +168,12 @@ unsigned bootloader_read_status_8b_rdsr2(void)
|
||||
return bootloader_execute_flash_command(CMD_RDSR2, 0, 0, 8);
|
||||
}
|
||||
|
||||
unsigned bootloader_read_status_16b_rdsr_rdsr2(void)
|
||||
unsigned bootloader_read_status_8b_rdsr3(void)
|
||||
{
|
||||
return bootloader_execute_flash_command(CMD_RDSR3, 0, 0, 8);
|
||||
}
|
||||
|
||||
static unsigned read_status_16b_rdsr_rdsr2(void)
|
||||
{
|
||||
return bootloader_execute_flash_command(CMD_RDSR, 0, 0, 8) | (bootloader_execute_flash_command(CMD_RDSR2, 0, 0, 8) << 8);
|
||||
}
|
||||
@ -183,6 +188,11 @@ void bootloader_write_status_8b_wrsr2(unsigned new_status)
|
||||
bootloader_execute_flash_command(CMD_WRSR2, new_status, 8, 0);
|
||||
}
|
||||
|
||||
void bootloader_write_status_8b_wrsr3(unsigned new_status)
|
||||
{
|
||||
bootloader_execute_flash_command(CMD_WRSR3, new_status, 8, 0);
|
||||
}
|
||||
|
||||
void bootloader_write_status_16b_wrsr(unsigned new_status)
|
||||
{
|
||||
bootloader_execute_flash_command(CMD_WRSR, new_status, 16, 0);
|
||||
|
@ -22,7 +22,8 @@ else()
|
||||
if(CONFIG_IDF_TARGET_ESP32S3)
|
||||
list(APPEND srcs
|
||||
"esp32s3/spi_timing_config.c"
|
||||
"spi_flash_timing_tuning.c")
|
||||
"spi_flash_timing_tuning.c"
|
||||
"spi_flash_hpm_enable.c")
|
||||
endif()
|
||||
|
||||
# New implementation after IDF v4.0
|
||||
|
@ -187,9 +187,13 @@ esp_err_t IRAM_ATTR spi_flash_init_chip_state(void)
|
||||
#if CONFIG_ESPTOOLPY_OCT_FLASH
|
||||
return esp_opiflash_init(rom_spiflash_legacy_data->chip.device_id);
|
||||
#else
|
||||
//currently we don't need other setup for initialising Quad Flash
|
||||
#if CONFIG_IDF_TARGET_ESP32S3
|
||||
// Currently, only esp32s3 allows high performance mode.
|
||||
return spi_flash_enable_high_performance_mode();
|
||||
#else
|
||||
return ESP_OK;
|
||||
#endif
|
||||
#endif // CONFIG_IDF_TARGET_ESP32S3
|
||||
#endif // CONFIG_ESPTOOLPY_OCT_FLASH
|
||||
}
|
||||
|
||||
void spi_flash_init(void)
|
||||
|
@ -35,6 +35,7 @@
|
||||
#include "esp_flash.h"
|
||||
#include "hal/spi_flash_hal.h"
|
||||
#include "soc/soc_caps.h"
|
||||
#include "spi_flash_override.h"
|
||||
|
||||
#ifdef __cplusplus
|
||||
extern "C" {
|
||||
@ -138,6 +139,21 @@ bool spi_timing_is_tuned(void);
|
||||
*/
|
||||
void spi_flash_set_vendor_required_regs(void);
|
||||
|
||||
/**
|
||||
* @brief Enable SPI flash high performance mode.
|
||||
*
|
||||
* @return ESP_OK if success.
|
||||
*/
|
||||
esp_err_t spi_flash_enable_high_performance_mode(void);
|
||||
|
||||
/**
|
||||
* @brief Get the flash dummy through this function
|
||||
* This can be used when one flash has several dummy configurations to enable the high performance mode.
|
||||
* @note Don't forget to subtract one when assign to the register of mspi e.g. if the value you get is 4, (4-1=3) should be assigned to the register.
|
||||
*
|
||||
* @return Pointer to bootlaoder_flash_dummy_conf_t.
|
||||
*/
|
||||
const spi_flash_hpm_dummy_conf_t *spi_flash_get_dummy(void);
|
||||
|
||||
#ifdef __cplusplus
|
||||
}
|
||||
|
@ -1,16 +1,8 @@
|
||||
// Copyright 2015-2019 Espressif Systems (Shanghai) PTE LTD
|
||||
//
|
||||
// Licensed under the Apache License, Version 2.0 (the "License");
|
||||
// you may not use this file except in compliance with the License.
|
||||
// You may obtain a copy of the License at
|
||||
//
|
||||
// http://www.apache.org/licenses/LICENSE-2.0
|
||||
//
|
||||
// Unless required by applicable law or agreed to in writing, software
|
||||
// distributed under the License is distributed on an "AS IS" BASIS,
|
||||
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
// See the License for the specific language governing permissions and
|
||||
// limitations under the License.
|
||||
/*
|
||||
* SPDX-FileCopyrightText: 2015-2022 Espressif Systems (Shanghai) CO LTD
|
||||
*
|
||||
* SPDX-License-Identifier: Apache-2.0
|
||||
*/
|
||||
|
||||
#pragma once
|
||||
|
||||
@ -52,6 +44,7 @@
|
||||
#define CMD_PROGRAM_PAGE_4B 0x12
|
||||
#define CMD_SUSPEND 0x75
|
||||
#define CMD_RESUME 0x7A
|
||||
#define CMD_HPMEN 0xA3 /* Enable High Performance mode on flash */
|
||||
|
||||
#define CMD_RST_EN 0x66
|
||||
#define CMD_RST_DEV 0x99
|
||||
|
60
components/spi_flash/include/spi_flash_override.h
Normal file
60
components/spi_flash/include/spi_flash_override.h
Normal file
@ -0,0 +1,60 @@
|
||||
/*
|
||||
* SPDX-FileCopyrightText: 2020-2022 Espressif Systems (Shanghai) CO LTD
|
||||
*
|
||||
* SPDX-License-Identifier: Apache-2.0
|
||||
*/
|
||||
|
||||
#include <stdint.h>
|
||||
#include "sdkconfig.h"
|
||||
#include "esp_err.h"
|
||||
|
||||
#pragma once
|
||||
|
||||
#ifdef __cplusplus
|
||||
extern "C" {
|
||||
#endif
|
||||
|
||||
/**
|
||||
* @brief Structure for flash dummy bits.
|
||||
* For some flash chips, dummy bits are configurable under different conditions.
|
||||
*/
|
||||
typedef struct {
|
||||
uint8_t dio_dummy;
|
||||
uint8_t dout_dummy;
|
||||
uint8_t qio_dummy;
|
||||
uint8_t qout_dummy;
|
||||
uint8_t fastrd_dummy;
|
||||
} spi_flash_hpm_dummy_conf_t;
|
||||
|
||||
typedef enum {
|
||||
SPI_FLASH_HPM_NEEDED, // Means that in the certain condition, flash needs to enter the high performance mode.
|
||||
SPI_FLASH_HPM_UNNEEDED, // Means that flash doesn't need to enter the high performance mode.
|
||||
SPI_FLASH_HPM_BEYOND_LIMIT, // Means that flash has no capability to meet that condition.
|
||||
} spi_flash_requirement_t;
|
||||
|
||||
typedef void (*spi_flash_hpm_enable_fn_t)(void);
|
||||
typedef esp_err_t (*spi_flash_hpf_check_fn_t)(void);
|
||||
typedef void (*spi_flash_get_chip_dummy_fn_t)(spi_flash_hpm_dummy_conf_t *dummy_conf);
|
||||
typedef esp_err_t (*spi_flash_hpm_probe_fn_t)(uint32_t flash_id);
|
||||
typedef spi_flash_requirement_t (*spi_flash_hpm_chip_requirement_check_t)(uint32_t flash_id, uint32_t freq_mhz, int voltage_mv, int temperature);
|
||||
|
||||
typedef struct __attribute__((packed))
|
||||
{
|
||||
const char *manufacturer; /* Flash vendor */
|
||||
spi_flash_hpm_probe_fn_t probe;
|
||||
spi_flash_hpm_chip_requirement_check_t chip_hpm_requirement_check;
|
||||
spi_flash_hpm_enable_fn_t flash_hpm_enable;
|
||||
spi_flash_hpf_check_fn_t flash_hpf_check;
|
||||
spi_flash_get_chip_dummy_fn_t flash_get_dummy;
|
||||
} spi_flash_hpm_info_t;
|
||||
|
||||
/**
|
||||
* Array of known flash chips and method to enable flash high performance mode.
|
||||
*
|
||||
* Users can override this array.
|
||||
*/
|
||||
extern const spi_flash_hpm_info_t __attribute__((weak)) spi_flash_hpm_enable_list[];
|
||||
|
||||
#ifdef __cplusplus
|
||||
}
|
||||
#endif
|
@ -14,9 +14,8 @@ entries:
|
||||
if IDF_TARGET_ESP32S3 = y:
|
||||
spi_flash_timing_tuning (noflash)
|
||||
spi_timing_config (noflash)
|
||||
spi_flash_chip_mxic_opi (noflash)
|
||||
spi_flash_hpm_enable (noflash)
|
||||
|
||||
if IDF_TARGET_ESP32S3 = y && ESPTOOLPY_OCT_FLASH = y:
|
||||
spi_flash_oct_flash_init (noflash)
|
||||
|
||||
if IDF_TARGET_ESP32S3 = y :
|
||||
spi_flash_chip_mxic_opi (noflash)
|
||||
|
267
components/spi_flash/spi_flash_hpm_enable.c
Normal file
267
components/spi_flash/spi_flash_hpm_enable.c
Normal file
@ -0,0 +1,267 @@
|
||||
/*
|
||||
* SPDX-FileCopyrightText: 2020-2022 Espressif Systems (Shanghai) CO LTD
|
||||
*
|
||||
* SPDX-License-Identifier: Apache-2.0
|
||||
*/
|
||||
|
||||
#include <stdint.h>
|
||||
#include "sdkconfig.h"
|
||||
#include "esp_err.h"
|
||||
#include "esp_log.h"
|
||||
#include "spi_flash_defs.h"
|
||||
#include "esp_rom_sys.h"
|
||||
#include "esp32s3/rom/spi_flash.h"
|
||||
#include "spi_flash_override.h"
|
||||
|
||||
// TODO: These dependencies will be removed after remove bootloader_flash to G0.IDF-4609
|
||||
#include "../bootloader_support/include_bootloader/bootloader_flash_priv.h"
|
||||
|
||||
/*******************************************************************************
|
||||
* Flash high speed performance mode.
|
||||
* HPM: High performance mode.
|
||||
* HPF: High performance flag.
|
||||
*
|
||||
* Different flash chips might have different high performance strategy.
|
||||
* 1. Some flash chips send A3H to enable the HPM.
|
||||
* 2. Some flash chips write HPF bit in status register.
|
||||
* 3. Some flash chips adjust dummy cycles.
|
||||
******************************************************************************/
|
||||
|
||||
#if CONFIG_ESPTOOLPY_FLASHFREQ_120M
|
||||
#define FLASH_FREQUENCY 120
|
||||
#elif CONFIG_ESPTOOLPY_FLASHFREQ_80M
|
||||
#define FLASH_FREQUENCY 80
|
||||
#elif CONFIG_ESPTOOLPY_FLASHFREQ_40M
|
||||
#define FLASH_FREQUENCY 40
|
||||
#elif CONFIG_ESPTOOLPY_FLASHFREQ_20M
|
||||
#define FLASH_FREQUENCY 20
|
||||
#endif
|
||||
|
||||
const static char *HPM_TAG = "flash HPM";
|
||||
|
||||
// TODO: This function will be changed after remove bootloader_flash to G0.IDF-4609
|
||||
extern uint32_t bootloader_flash_execute_command_common(
|
||||
uint8_t command,
|
||||
uint32_t addr_len, uint32_t address,
|
||||
uint8_t dummy_len,
|
||||
uint8_t mosi_len, uint32_t mosi_data,
|
||||
uint8_t miso_len);
|
||||
extern unsigned bootloader_read_status_8b_rdsr3(void);
|
||||
extern void bootloader_write_status_8b_wrsr3(unsigned new_status);
|
||||
|
||||
//-----------------For flash chips which enter HPM via command-----------------------//
|
||||
|
||||
/**
|
||||
* @brief Probe the chip whether use command to enable HPM mode. Take GD as an example:
|
||||
* Some GD send 0xA3 command to enable HPM mode of the flash.
|
||||
*/
|
||||
static esp_err_t spi_flash_hpm_probe_chip_with_cmd(uint32_t flash_id)
|
||||
{
|
||||
esp_err_t ret = ESP_OK;
|
||||
switch (flash_id) {
|
||||
/* The flash listed here should enter the HPM with command 0xA3 */
|
||||
case 0xC84016:
|
||||
case 0xC84017:
|
||||
break;
|
||||
default:
|
||||
ret = ESP_ERR_NOT_FOUND;
|
||||
break;
|
||||
}
|
||||
return ret;
|
||||
}
|
||||
|
||||
static spi_flash_requirement_t spi_flash_hpm_chip_hpm_requirement_check_with_cmd(uint32_t flash_id, uint32_t freq_mhz, int voltage_mv, int temperautre)
|
||||
{
|
||||
// voltage and temperature are not been used now, to be completed in the future.
|
||||
(void)voltage_mv;
|
||||
(void)temperautre;
|
||||
spi_flash_requirement_t chip_cap = SPI_FLASH_HPM_UNNEEDED;
|
||||
switch (flash_id) {
|
||||
/* The flash listed here should enter the HPM with command 0xA3 */
|
||||
case 0xC84016:
|
||||
case 0xC84017:
|
||||
if (freq_mhz >= 80) {
|
||||
chip_cap = SPI_FLASH_HPM_NEEDED;
|
||||
}
|
||||
break;
|
||||
default:
|
||||
chip_cap = SPI_FLASH_HPM_UNNEEDED;
|
||||
break;
|
||||
}
|
||||
return chip_cap;
|
||||
}
|
||||
|
||||
/**
|
||||
* @brief Send HPMEN command (A3H)
|
||||
*/
|
||||
static void spi_flash_enable_high_performance_send_cmd(void)
|
||||
{
|
||||
uint32_t dummy = 24;
|
||||
bootloader_flash_execute_command_common(CMD_HPMEN, 0, 0, dummy, 0, 0, 0);
|
||||
// Delay for T(HPM) refering to datasheet.
|
||||
esp_rom_delay_us(20);
|
||||
}
|
||||
|
||||
/**
|
||||
* @brief Check whether flash HPM has been enabled. According to flash datasheets, majorities of
|
||||
* HPF bit are at bit-5, sr-3. But some are not. Therefore, this function is only used for those
|
||||
* HPF bit is at bit-5, sr-3.
|
||||
*/
|
||||
static esp_err_t spi_flash_high_performance_check_hpf_bit_5(void)
|
||||
{
|
||||
if((bootloader_read_status_8b_rdsr3() & (1 << 4)) == 0) {
|
||||
return ESP_FAIL;
|
||||
}
|
||||
return ESP_OK;
|
||||
}
|
||||
|
||||
//-----------------For flash chips which enter HPM via adjust dummy-----------------------//
|
||||
|
||||
/**
|
||||
* @brief Probe the chip whether adjust dummy to enable HPM mode. Take XMC as an example:
|
||||
* Adjust dummy bits to enable HPM mode of the flash. If XMC works under 80MHz, the dummy bits
|
||||
* might be 6, but when works under 120MHz, the dummy bits might be 10.
|
||||
*/
|
||||
static esp_err_t spi_flash_hpm_probe_chip_with_dummy(uint32_t flash_id)
|
||||
{
|
||||
ESP_EARLY_LOGW(HPM_TAG, "Enter HPM by reconfiguring dummy has not been fully tested");
|
||||
esp_err_t ret = ESP_OK;
|
||||
switch (flash_id) {
|
||||
/* The flash listed here should enter the HPM by adjusting dummy cycles */
|
||||
case 0x204017:
|
||||
break;
|
||||
default:
|
||||
ret = ESP_ERR_NOT_FOUND;
|
||||
break;
|
||||
}
|
||||
return ret;
|
||||
}
|
||||
|
||||
static spi_flash_requirement_t spi_flash_hpm_chip_hpm_requirement_check_with_dummy(uint32_t flash_id, uint32_t freq_mhz, int voltage_mv, int temperautre)
|
||||
{
|
||||
// voltage and temperature are not been used now, to be completed in the future.
|
||||
(void)voltage_mv;
|
||||
(void)temperautre;
|
||||
spi_flash_requirement_t chip_cap = SPI_FLASH_HPM_UNNEEDED;
|
||||
switch (flash_id) {
|
||||
/* The flash listed here should enter the HPM with command 0xA3 */
|
||||
case 0x204017:
|
||||
if (freq_mhz >= 104) {
|
||||
chip_cap = SPI_FLASH_HPM_NEEDED;
|
||||
}
|
||||
break;
|
||||
default:
|
||||
chip_cap = SPI_FLASH_HPM_UNNEEDED;
|
||||
break;
|
||||
}
|
||||
return chip_cap;
|
||||
}
|
||||
|
||||
/**
|
||||
* @brief Adjust dummy cycles. This function modifies the Dummy Cycle Bits in SR3.
|
||||
* Usually, the bits are at bit-0, bit-1, sr-3 and set DC[1:0]=[1,1].
|
||||
*
|
||||
* @note Don't forget to adjust dummy configurations for MSPI, you can get the
|
||||
* correct dummy from interface `spi_flash_hpm_get_dummy`.
|
||||
*/
|
||||
static void spi_flash_turn_high_performance_reconfig_dummy(void)
|
||||
{
|
||||
uint8_t old_status_3 = bootloader_read_status_8b_rdsr3();
|
||||
uint8_t new_status = (old_status_3 | 0x03);
|
||||
bootloader_execute_flash_command(CMD_WREN, 0, 0, 0);
|
||||
bootloader_write_status_8b_wrsr3(new_status);
|
||||
esp_rom_spiflash_wait_idle(&g_rom_flashchip);
|
||||
}
|
||||
|
||||
/**
|
||||
* @brief Check whether HPM has been enabled. This function checks the DC bits
|
||||
*/
|
||||
static esp_err_t spi_flash_high_performance_check_dummy_sr(void)
|
||||
{
|
||||
if((bootloader_read_status_8b_rdsr3() & 0x03) == 0) {
|
||||
return ESP_FAIL;
|
||||
}
|
||||
return ESP_OK;
|
||||
}
|
||||
|
||||
static void spi_flash_hpm_get_dummy_xmc(spi_flash_hpm_dummy_conf_t *dummy_conf)
|
||||
{
|
||||
dummy_conf->dio_dummy = 8;
|
||||
dummy_conf->dout_dummy = 8;
|
||||
dummy_conf->qio_dummy = 10;
|
||||
dummy_conf->qout_dummy = 8;
|
||||
dummy_conf->fastrd_dummy = 8;
|
||||
}
|
||||
|
||||
|
||||
//-----------------------generic functions-------------------------------------//
|
||||
|
||||
/**
|
||||
* @brief Default dummy for almost all flash chips. If your flash does't need to reconfigure dummy,
|
||||
* just call this function.
|
||||
*/
|
||||
void __attribute__((weak)) spi_flash_hpm_get_dummy_generic(spi_flash_hpm_dummy_conf_t *dummy_conf)
|
||||
{
|
||||
dummy_conf->dio_dummy = 4;
|
||||
dummy_conf->dout_dummy = 8;
|
||||
dummy_conf->qio_dummy = 6;
|
||||
dummy_conf->qout_dummy = 8;
|
||||
dummy_conf->fastrd_dummy = 8;
|
||||
}
|
||||
|
||||
const spi_flash_hpm_info_t __attribute__((weak)) spi_flash_hpm_enable_list[] = {
|
||||
/* vendor, chip_id, freq_threshold, temperature threshold, operation for setting high performance, reading HPF status, get dummy */
|
||||
{ "GD", spi_flash_hpm_probe_chip_with_cmd, spi_flash_hpm_chip_hpm_requirement_check_with_cmd, spi_flash_enable_high_performance_send_cmd, spi_flash_high_performance_check_hpf_bit_5, spi_flash_hpm_get_dummy_generic },
|
||||
{ "XMC", spi_flash_hpm_probe_chip_with_dummy, spi_flash_hpm_chip_hpm_requirement_check_with_dummy, spi_flash_turn_high_performance_reconfig_dummy, spi_flash_high_performance_check_dummy_sr, spi_flash_hpm_get_dummy_xmc},
|
||||
// default: do nothing, but keep the dummy get function. The first item with NULL as its probe will be the fallback.
|
||||
{ "NULL", NULL, NULL, NULL, NULL, spi_flash_hpm_get_dummy_generic},
|
||||
};
|
||||
|
||||
static const spi_flash_hpm_info_t *chip_hpm = NULL;
|
||||
static spi_flash_hpm_dummy_conf_t dummy_conf;
|
||||
|
||||
esp_err_t spi_flash_enable_high_performance_mode(void)
|
||||
{
|
||||
uint32_t flash_chip_id = g_rom_flashchip.device_id;
|
||||
uint32_t flash_freq = FLASH_FREQUENCY;
|
||||
// voltage and temperature has not been implemented, just leave an interface here. Complete in the future.
|
||||
int voltage = 0;
|
||||
int temperature = 0;
|
||||
|
||||
const spi_flash_hpm_info_t *chip = spi_flash_hpm_enable_list;
|
||||
esp_err_t ret = ESP_OK;
|
||||
while (chip->probe) {
|
||||
ret = chip->probe(flash_chip_id);
|
||||
if (ret == ESP_OK) {
|
||||
break;
|
||||
}
|
||||
chip++;
|
||||
}
|
||||
chip_hpm = chip;
|
||||
|
||||
if (ret != ESP_OK) {
|
||||
ESP_EARLY_LOGE(HPM_TAG, "Flash high performance mode hasn't been supported");
|
||||
return ret;
|
||||
}
|
||||
|
||||
if (chip_hpm->chip_hpm_requirement_check(flash_chip_id, flash_freq, voltage, temperature) == SPI_FLASH_HPM_NEEDED) {
|
||||
ESP_EARLY_LOGI(HPM_TAG, "Enabling high speed mode for chip %s", chip_hpm->manufacturer);
|
||||
chip_hpm->flash_hpm_enable();
|
||||
ESP_EARLY_LOGD(HPM_TAG, "Checking whether HPM has been executed");
|
||||
|
||||
if (chip_hpm->flash_hpf_check() != ESP_OK) {
|
||||
ESP_EARLY_LOGE(HPM_TAG, "Flash high performance mode hasn't been executed successfully");
|
||||
return ESP_FAIL;
|
||||
}
|
||||
} else if (chip_hpm->chip_hpm_requirement_check(flash_chip_id, flash_freq, voltage, temperature) == SPI_FLASH_HPM_BEYOND_LIMIT) {
|
||||
ESP_EARLY_LOGE(HPM_TAG, "Flash does not have the ability to raise to that frequency");
|
||||
return ESP_FAIL;
|
||||
}
|
||||
return ESP_OK;
|
||||
}
|
||||
|
||||
const spi_flash_hpm_dummy_conf_t *spi_flash_hpm_get_dummy(void)
|
||||
{
|
||||
chip_hpm->flash_get_dummy(&dummy_conf);
|
||||
return &dummy_conf;
|
||||
}
|
Loading…
Reference in New Issue
Block a user