/* Copyright (c) 2012 The Chromium OS Authors. All rights reserved. * Use of this source code is governed by a BSD-style license that can be * found in the LICENSE file. */ /* Flash memory module for Chrome EC */ #ifndef __CROS_EC_FLASH_H #define __CROS_EC_FLASH_H #include "common.h" #include "ec_commands.h" /* For EC_FLASH_PROTECT_* flags */ #ifdef CONFIG_FLASH_MULTIPLE_REGION extern struct ec_flash_bank const flash_bank_array[ CONFIG_FLASH_REGION_TYPE_COUNT]; /* * Return the bank the offset is in. * Return -1 if the offset is not at the beginning of that bank. */ int flash_bank_index(int offset); /* * Number of banks between offset and offset+size. * * offset and offset + size should be addresses at the beginning of bank: * 0 32 * +-------------------+--------... * | bank 0 | bank 1 ... * +-------------------+--------... * In that case, begin = 0, end = 1, return is 1. * otherwise, this is an error: * 0 32 64 * +----------+--------+--------... * | bank 0 | bank 1 ... * +----------+--------+--------... * begin = 0, end = -1.... * The idea is to prevent erasing more than you think. */ int flash_bank_count(int offset, int size); /* * Return the size of the specified bank in bytes. * Return -1 if the bank is too large. */ int flash_bank_size(int bank); /* Number of physical flash banks */ #define PHYSICAL_BANKS CONFIG_FLASH_MULTIPLE_REGION /* WP region offset and size in units of flash banks */ #define WP_BANK_OFFSET flash_bank_index(CONFIG_WP_STORAGE_OFF) #define WP_BANK_COUNT \ (flash_bank_count(CONFIG_WP_STORAGE_OFF, CONFIG_WP_STORAGE_SIZE)) #else /* CONFIG_FLASH_MULTIPLE_REGION */ /* Number of physical flash banks */ #ifndef PHYSICAL_BANKS #define PHYSICAL_BANKS (CONFIG_FLASH_SIZE / CONFIG_FLASH_BANK_SIZE) #endif /* WP region offset and size in units of flash banks */ #define WP_BANK_OFFSET (CONFIG_WP_STORAGE_OFF / CONFIG_FLASH_BANK_SIZE) #ifndef WP_BANK_COUNT #define WP_BANK_COUNT (CONFIG_WP_STORAGE_SIZE / CONFIG_FLASH_BANK_SIZE) #endif #endif /* CONFIG_FLASH_MULTIPLE_REGION */ /* Persistent protection state flash offset / size / bank */ #if defined(CONFIG_FLASH_PSTATE) && defined(CONFIG_FLASH_PSTATE_BANK) #ifdef CONFIG_FLASH_MULTIPLE_REGION #error "Not supported." #endif #ifndef PSTATE_BANK #define PSTATE_BANK (CONFIG_FW_PSTATE_OFF / CONFIG_FLASH_BANK_SIZE) #endif #ifndef PSTATE_BANK_COUNT #define PSTATE_BANK_COUNT (CONFIG_FW_PSTATE_SIZE / CONFIG_FLASH_BANK_SIZE) #endif #else /* CONFIG_FLASH_PSTATE && CONFIG_FLASH_PSTATE_BANK */ #define PSTATE_BANK_COUNT 0 #endif /* CONFIG_FLASH_PSTATE && CONFIG_FLASH_PSTATE_BANK */ #ifdef CONFIG_ROLLBACK /* * ROLLBACK region offset and size in units of flash banks. */ #define ROLLBACK_BANK_OFFSET (CONFIG_ROLLBACK_OFF / CONFIG_FLASH_BANK_SIZE) #define ROLLBACK_BANK_COUNT (CONFIG_ROLLBACK_SIZE / CONFIG_FLASH_BANK_SIZE) #endif /* This enum is useful to identify different regions during verification. */ enum flash_region { FLASH_REGION_RW = 0, FLASH_REGION_RO, #ifdef CONFIG_ROLLBACK FLASH_REGION_ROLLBACK, #endif FLASH_REGION_COUNT }; /*****************************************************************************/ /* Low-level methods, for use by flash_common. */ /** * Read from physical flash. * * @param offset Flash offset to write. * @param size Number of bytes to write. * @param data Destination buffer for data. Must be 32-bit aligned. */ int flash_physical_read(int offset, int size, char *data); /** * Write to physical flash. * * Offset and size must be a multiple of CONFIG_FLASH_WRITE_SIZE. * * @param offset Flash offset to write. * @param size Number of bytes to write. * @param data Data to write to flash. Must be 32-bit aligned. */ int flash_physical_write(int offset, int size, const char *data); /** * Erase physical flash. * * Offset and size must be a multiple of CONFIG_FLASH_ERASE_SIZE. * * @param offset Flash offset to erase. * @param size Number of bytes to erase. */ int flash_physical_erase(int offset, int size); /** * Read physical write protect setting for a flash bank. * * @param bank Bank index to check. * @return non-zero if bank is protected until reboot. */ int flash_physical_get_protect(int bank); /** * Return flash protect state flags from the physical layer. * * This should only be called by flash_get_protect(). * * Uses the EC_FLASH_PROTECT_* flags from ec_commands.h */ uint32_t flash_physical_get_protect_flags(void); /** * Enable/disable protecting firmware/pstate at boot. * * @param new_flags to protect (only EC_FLASH_PROTECT_*_AT_BOOT are * taken care of) * @return non-zero if error. */ int flash_physical_protect_at_boot(uint32_t new_flags); /** * Protect flash now. * * @param all Protect all (=1) or just read-only and pstate (=0). * @return non-zero if error. */ int flash_physical_protect_now(int all); /** * Force reload of flash protection bits. * * Some EC architectures (STM32L) only load the bits from option bytes at * power-on reset or via a special command. This issues that command if * possible, which triggers a power-on reboot. * * Only returns (with EC_ERROR_ACCESS_DENIED) if the command is locked. */ int flash_physical_force_reload(void); /** * Restore flash physical layer state after sysjump. * * @return non-zero if restored. */ int flash_physical_restore_state(void); /** * Return the valid flash protect flags. * * @return a combination of EC_FLASH_PROTECT_* flags from ec_commands.h */ uint32_t flash_physical_get_valid_flags(void); /** * Return the writable flash protect flags. * * @param cur_flags The current flash protect flags. * @return a combination of EC_FLASH_PROTECT_* flags from ec_commands.h */ uint32_t flash_physical_get_writable_flags(uint32_t cur_flags); /*****************************************************************************/ /* Low-level common code for use by flash modules. */ /** * Check if a region of flash is erased * * It is assumed that an erased region has all bits set to 1. * * @param offset Flash offset to check * @param size Number of bytes to check (word-aligned) * @return 1 if erased, 0 if not erased */ int flash_is_erased(uint32_t offset, int size); /** * Enable write protect for the specified range. * * Once write protect is enabled, it will STAY enabled until the system is * hard-rebooted with the hardware write protect pin deasserted. If the write * protect pin is deasserted, the protect setting is ignored, and the entire * flash will be writable. * * @param new_flags to protect (only EC_FLASH_PROTECT_*_AT_BOOT are * taken care of) * @return EC_SUCCESS, or nonzero if error. */ int flash_protect_at_boot(uint32_t new_flags); /*****************************************************************************/ /* High-level interface for use by other modules. */ /** * Initialize the module. * * Applies at-boot protection settings if necessary. */ int flash_pre_init(void); /** * Return the usable size of flash in bytes. Note that this may be smaller * than the physical flash size. */ int flash_get_size(void); /** * Get the physical memory address of a flash offset * * This is used for direct flash access. We assume that the flash is * contiguous from this start address through to the end of the usable * flash. * * This function returns -1 if offset + size_req extends beyond the end * of flash, the offset is out of range, or if either size_req or offset * are not aligned to 'align'. * * @param offset Flash offset to get address of * @param size_req Number of bytes requested * @param align Ensure offset and size_req are aligned to given * power of two. * @param ptrp If not NULL, returns a pointer to this flash offset * in memory, unless function fails, iwc it is unset. * @return size of flash region available at *ptrp, or -1 on error */ int flash_dataptr(int offset, int size_req, int align, const char **ptrp); /** * Read from flash. * * If flash is mapped (CONFIG_MAPPED_STORAGE), it is usually more efficient to * use flash_dataptr() to get a pointer directly to the flash memory rather * than use flash_read(), since the former saves a memcpy() operation. * * @param offset Flash offset to write. * @param size Number of bytes to write. * @param data Destination buffer for data. Must be 32-bit aligned. */ int flash_read(int offset, int size, char *data); /** * Write to flash. * * Offset and size must be a multiple of CONFIG_FLASH_WRITE_SIZE. * * @param offset Flash offset to write. * @param size Number of bytes to write. * @param data Data to write to flash. Must be 32-bit aligned. */ int flash_write(int offset, int size, const char *data); /** * Erase flash. * * Offset and size must be a multiple of CONFIG_FLASH_ERASE_SIZE. * * @param offset Flash offset to erase. * @param size Number of bytes to erase. */ int flash_erase(int offset, int size); /** * Return the flash protect state. * * Uses the EC_FLASH_PROTECT_* flags from ec_commands.h */ uint32_t flash_get_protect(void); /** * Set the flash protect state. * * @param mask Bits in flags to apply. * @param flags New values for flags. */ int flash_set_protect(uint32_t mask, uint32_t flags); /** * Get the serial number from flash. * * @return char * ascii serial number string. * NULL if error. */ const char *flash_read_pstate_serial(void); /** * Set the serial number in flash. * * @param serialno ascii serial number string. * * @return success status. */ int flash_write_pstate_serial(const char *serialno); /** * Lock or unlock HW necessary for mapped storage read. * * @param lock 1 to lock, 0 to unlock. */ #ifdef CONFIG_EXTERNAL_STORAGE void flash_lock_mapped_storage(int lock); #else static inline void flash_lock_mapped_storage(int lock) { }; #endif /* CONFIG_EXTERNAL_STORAGE */ /** * Select flash for performing flash operations. Board should implement this * if some steps needed be done before flash operation can succeed. * * @param select 1 to select flash, 0 to deselect (disable). * @return EC_RES_* status code. */ int board_flash_select(int select); #endif /* __CROS_EC_FLASH_H */