From fcb05fcf4353702f06a11fab103f7769bcb82e62 Mon Sep 17 00:00:00 2001 From: Saksham Puri <84263133+Saksham-P@users.noreply.github.com> Date: Mon, 22 Jul 2024 16:38:24 -0600 Subject: [PATCH 01/19] Replaced all flash driver code for NAND chip Replaced all previous code for FLASH driver for NAND flash module. --- firmware/Core/Inc/littlefs/flash_driver.h | 54 +-- firmware/Core/Src/littlefs/flash_benchmark.c | 2 +- firmware/Core/Src/littlefs/flash_driver.c | 317 +++++++++++++++--- .../Core/Src/littlefs/flash_testing_demos.c | 2 +- firmware/Core/Src/littlefs/littlefs_driver.c | 2 +- .../Src/telecommands/flash_telecommand_defs.c | 2 +- 6 files changed, 309 insertions(+), 70 deletions(-) diff --git a/firmware/Core/Inc/littlefs/flash_driver.h b/firmware/Core/Inc/littlefs/flash_driver.h index 11db2a776..0f66de0f8 100644 --- a/firmware/Core/Inc/littlefs/flash_driver.h +++ b/firmware/Core/Inc/littlefs/flash_driver.h @@ -8,44 +8,50 @@ #include "littlefs/lfs.h" - /*----------------------------- CONFIG VARIABLES ----------------------------- */ - -// number of CS pins available +// Number of CS pins available #define FLASH_NUMBER_OF_FLASH_DEVICES 8 // TODO: update to 8, or 10 with FRAM maybe -#define FLASH_CHIP_SIZE_BYTES 67108864 // 64MiB // TODO: update -/*-----------------------------COMMAND VARIABLES-----------------------------*/ -// All comments in this section refer to the "S25FL512S 512Mb (64MB)" Datasheet by Infineon +// Total size of a singular Memory Module in bytes +#define FLASH_CHIP_SIZE_BYTES 134217728 // 128MiB // TODO: update + +/*-------------------------------FLASH FEATURES-------------------------------*/ +// Features that can be accessed using Get Feature command + +static const uint8_t FLASH_FEAT_BLOCK_LOCK = 0xA0; // Block Lock -static const uint8_t FLASH_CMD_READ_3_BYTE_ADDR = 0x03; // Read - Section 9.4.1 -static const uint8_t FLASH_CMD_READ_4_BYTE_ADDR = 0x13; // Read - Section 9.4.1 +static const uint8_t FLASH_FEAT_CONFIG = 0xB0; // Configuration Register + +static const uint8_t FLASH_FEAT_STATUS = 0xC0; // Status Register + +static const uint8_t FLASH_FEAT_DIE_SELECT = 0xD0; // Die Select + +/*-----------------------------COMMAND VARIABLES-----------------------------*/ +// All comments in this section refer to the "MT29F1G 1Gib (128MiB)" Datasheet by Micron -static const uint8_t FLASH_CMD_WRITE_3_BYTE_ADDR = 0x02; // Page Program - Section 9.5.2 -static const uint8_t FLASH_CMD_WRITE_4_BYTE_ADDR = 0x12; // Page Program - Section 9.5.2 +static const uint8_t FLASH_CMD_PAGE_READ = 0x13; // Read Page +static const uint8_t FLASH_CMD_READ_FROM_CACHE = 0x03; // Read Page -static const uint8_t FLASH_CMD_SECTOR_ERASE_3_BYTE_ADDR = 0xD8; // Sector Erase - Section 9.6.1 -static const uint8_t FLASH_CMD_SECTOR_ERASE_4_BYTE_ADDR = 0xDC; // Sector Erase - Section 9.6.1 +static const uint8_t FLASH_CMD_PROGRAM_LOAD = 0x02; // Load Program into cache resgiters +static const uint8_t FLASH_CMD_PROGRAM_EXEC = 0x10; // Send data from cache to memory -static const uint8_t FLASH_CMD_WRITE_DISABLE = 0x04; // Write Disable - Section 9.3.9 -static const uint8_t FLASH_CMD_WRITE_ENABLE = 0x06; // Write Enable - Section 9.3.8 +static const uint8_t FLASH_CMD_BLOCK_ERASE = 0xD8; // Block Erase -static const uint8_t FLASH_CMD_READ_STATUS_REG_1 = 0x05; // Read Status 1 - Section 9.3.1, Byte Descriptions in 7.6.1 -static const uint8_t FLASH_CMD_READ_STATUS_REG_2 = 0x07; // Read Status 2 - Section 9.3.2 -static const uint8_t FLASH_CMD_CLEAR_STATUS = 0x30; // Clear Status - Section 9.3.10 +static const uint8_t FLASH_CMD_WRITE_ENABLE = 0x06; // Write Enable +static const uint8_t FLASH_CMD_WRITE_DISABLE = 0x04; // Write Disable -static const uint8_t FLASH_CMD_READ_CONFIG = 0x35; // Read Config - Section 9.3.3 +static const uint8_t FLASH_CMD_GET_FEATURES = 0x0F; // Get Features -static const uint8_t FLASH_CMD_SOFTWARE_RESET = 0xF0; // Software Reset - Section 9.9.1 +static const uint8_t FLASH_CMD_READ_ID = 0x9F; // Read ID (0x2C 0x14) -static const uint8_t FLASH_CMD_READ_ID = 0x9F; // "RDID" - Read ID - Section 9.2.2 +static const uint8_t FLASH_CMD_RESET = 0xFF; // ------------------- Status Register 1 - Byte Masks ------------------- -// Source: Section 7.6.1 +// Source: Table 5 static const uint8_t FLASH_SR1_WRITE_IN_PROGRESS_MASK = (1 << 0); static const uint8_t FLASH_SR1_WRITE_ENABLE_LATCH_MASK = (1 << 1); -static const uint8_t FLASH_SR1_PROGRAMMING_ERROR_MASK = (1 << 6); -static const uint8_t FLASH_SR1_ERASE_ERROR_MASK = (1 << 5); +static const uint8_t FLASH_SR1_PROGRAMMING_ERROR_MASK = (1 << 3); +static const uint8_t FLASH_SR1_ERASE_ERROR_MASK = (1 << 2); /*-----------------------------FLASH ERROR CODES-----------------------------*/ typedef enum { @@ -66,7 +72,7 @@ FLASH_error_enum_t FLASH_read_status_register(SPI_HandleTypeDef *hspi, uint8_t c FLASH_error_enum_t FLASH_write_enable(SPI_HandleTypeDef *hspi, uint8_t chip_number); FLASH_error_enum_t FLASH_write_disable(SPI_HandleTypeDef *hspi, uint8_t chip_number); FLASH_error_enum_t FLASH_erase(SPI_HandleTypeDef *hspi, uint8_t chip_number, lfs_block_t addr); -FLASH_error_enum_t FLASH_write(SPI_HandleTypeDef *hspi, uint8_t chip_number, lfs_block_t addr, uint8_t *packet_buffer, lfs_size_t packet_buffer_len); +FLASH_error_enum_t FLASH_write_data(SPI_HandleTypeDef *hspi, uint8_t chip_number, lfs_block_t addr, uint8_t *packet_buffer, lfs_size_t packet_buffer_len); FLASH_error_enum_t FLASH_read_data(SPI_HandleTypeDef *hspi, uint8_t chip_number, lfs_block_t addr, uint8_t *rx_buffer, lfs_size_t rx_buffer_len); FLASH_error_enum_t FLASH_is_reachable(SPI_HandleTypeDef *hspi, uint8_t chip_number); diff --git a/firmware/Core/Src/littlefs/flash_benchmark.c b/firmware/Core/Src/littlefs/flash_benchmark.c index 6b16e8376..2c8427c45 100644 --- a/firmware/Core/Src/littlefs/flash_benchmark.c +++ b/firmware/Core/Src/littlefs/flash_benchmark.c @@ -45,7 +45,7 @@ uint8_t FLASH_benchmark_erase_write_read(uint8_t chip_num, uint32_t test_data_ad } // TODO: for very large writes, split into multiple writes (instead of allocating the whole amount on the stack) const uint32_t write_send_start_time = HAL_GetTick(); - const FLASH_error_enum_t write_result = FLASH_write(hspi_ptr, chip_num, test_data_address, write_buffer, test_data_length); + const FLASH_error_enum_t write_result = FLASH_write_data(hspi_ptr, chip_num, test_data_address, write_buffer, test_data_length); if (write_result != 0) { snprintf( &response_str[strlen(response_str)], diff --git a/firmware/Core/Src/littlefs/flash_driver.c b/firmware/Core/Src/littlefs/flash_driver.c index f567f1cc2..a3a4cdd16 100644 --- a/firmware/Core/Src/littlefs/flash_driver.c +++ b/firmware/Core/Src/littlefs/flash_driver.c @@ -94,19 +94,39 @@ void FLASH_deactivate_chip_select() */ FLASH_error_enum_t FLASH_read_status_register(SPI_HandleTypeDef *hspi, uint8_t chip_number, uint8_t *buf) { + // Send GET FEATURES command FLASH_activate_chip_select(chip_number); - const HAL_StatusTypeDef tx_result = HAL_SPI_Transmit(hspi, (uint8_t *)&FLASH_CMD_READ_STATUS_REG_1, 1, FLASH_HAL_TIMEOUT_MS); - if (tx_result != HAL_OK) { + const HAL_StatusTypeDef tx_result_1 = HAL_SPI_Transmit(hspi, (uint8_t *)&FLASH_CMD_GET_FEATURES, 1, FLASH_HAL_TIMEOUT_MS); + + // If couldn't send the command, check why + if (tx_result_1 != HAL_OK) { FLASH_deactivate_chip_select(); - if (tx_result == HAL_TIMEOUT) { + if (tx_result_1 == HAL_TIMEOUT) { return FLASH_ERR_SPI_TRANSMIT_TIMEOUT; } return FLASH_ERR_SPI_TRANSMIT_FAILED; } + // Send the byte address of status register + const HAL_StatusTypeDef tx_result_2 = HAL_SPI_Transmit(hspi, (uint8_t *)&FLASH_FEAT_STATUS, 1, FLASH_HAL_TIMEOUT_MS); + + // If couldn't send the byte, check why + if (tx_result_2 != HAL_OK) { + FLASH_deactivate_chip_select(); + + if (tx_result_2 == HAL_TIMEOUT) { + return FLASH_ERR_SPI_TRANSMIT_TIMEOUT; + } + + return FLASH_ERR_SPI_TRANSMIT_FAILED; + } + + // Receive the Status Register bits const HAL_StatusTypeDef rx_result = HAL_SPI_Receive(hspi, (uint8_t *)buf, 1, FLASH_HAL_TIMEOUT_MS); + + // If couldn't receive the byte, check why if (rx_result != HAL_OK) { FLASH_deactivate_chip_select(); @@ -132,9 +152,12 @@ FLASH_error_enum_t FLASH_write_enable(SPI_HandleTypeDef *hspi, uint8_t chip_numb // Buffer to store status register value uint8_t status_reg_buffer[1] = {0}; + // Send the WRITE ENABLE Command FLASH_activate_chip_select(chip_number); const HAL_StatusTypeDef tx_result_1 = HAL_SPI_Transmit(hspi, (uint8_t *)&FLASH_CMD_WRITE_ENABLE, 1, FLASH_HAL_TIMEOUT_MS); FLASH_deactivate_chip_select(); + + // If couldn't send the command, check why if (tx_result_1 != HAL_OK) { if (tx_result_1 == HAL_TIMEOUT) { @@ -148,6 +171,7 @@ FLASH_error_enum_t FLASH_write_enable(SPI_HandleTypeDef *hspi, uint8_t chip_numb const uint32_t start_loop_time_ms = HAL_GetTick(); while (1) { + // Get status register bits const FLASH_error_enum_t read_status_result = FLASH_read_status_register(hspi, chip_number, status_reg_buffer); if (read_status_result != FLASH_ERR_OK) { FLASH_deactivate_chip_select(); @@ -187,9 +211,12 @@ FLASH_error_enum_t FLASH_write_disable(SPI_HandleTypeDef *hspi, uint8_t chip_num // Buffer to store status register value uint8_t status_reg_buffer[1] = {0}; + // Send WRITE DISABLE Command FLASH_activate_chip_select(chip_number); const HAL_StatusTypeDef tx_status = HAL_SPI_Transmit(hspi, (uint8_t *)&FLASH_CMD_WRITE_DISABLE, 1, FLASH_HAL_TIMEOUT_MS); FLASH_deactivate_chip_select(); + + // If couldn't send the command, check why if (tx_status != HAL_OK) { if (tx_status == HAL_TIMEOUT) { @@ -203,6 +230,7 @@ FLASH_error_enum_t FLASH_write_disable(SPI_HandleTypeDef *hspi, uint8_t chip_num const uint32_t start_loop_time_ms = HAL_GetTick(); while (1) { + // Get status register bits const FLASH_error_enum_t read_status_result = FLASH_read_status_register(hspi, chip_number, status_reg_buffer); if (read_status_result != FLASH_ERR_OK) { FLASH_deactivate_chip_select(); @@ -220,9 +248,11 @@ FLASH_error_enum_t FLASH_write_disable(SPI_HandleTypeDef *hspi, uint8_t chip_num return FLASH_ERR_DEVICE_BUSY_TIMEOUT; } - DEBUG_uart_print_str("DEBUG: status_reg = 0x"); - DEBUG_uart_print_array_hex(status_reg_buffer, 1); - DEBUG_uart_print_str("\n"); + if (FLASH_enable_hot_path_debug_logs) { + DEBUG_uart_print_str("DEBUG: status_reg = 0x"); + DEBUG_uart_print_array_hex(status_reg_buffer, 1); + DEBUG_uart_print_str("\n"); + } } // Should never be reached: @@ -230,10 +260,10 @@ FLASH_error_enum_t FLASH_write_disable(SPI_HandleTypeDef *hspi, uint8_t chip_num } /** - * @brief Sends Sector Erase Command + * @brief Sends Block Erase Command * @param hspi - Pointer to the SPI HAL handle * @param chip_number - the chip select number to activate - * @param addr - block number that is to be erased + * @param addr - block address that is to be erased * @retval FLASH_ERR_OK on success, < 0 on failure */ FLASH_error_enum_t FLASH_erase(SPI_HandleTypeDef *hspi, uint8_t chip_number, lfs_block_t addr) @@ -241,16 +271,18 @@ FLASH_error_enum_t FLASH_erase(SPI_HandleTypeDef *hspi, uint8_t chip_number, lfs // Split address into its 4 bytes uint8_t addr_bytes[4] = {(addr >> 24) & 0xFF, (addr >> 16) & 0xFF, (addr >> 8) & 0xFF, addr & 0xFF}; - // Send Write Enable Command + // Send WRITE ENABLE Command const FLASH_error_enum_t wren_result = FLASH_write_enable(hspi, chip_number); if (wren_result != FLASH_ERR_OK) { FLASH_deactivate_chip_select(); return wren_result; } - // Send Sector Erase Command + // Send BLOCK ERASE Command FLASH_activate_chip_select(chip_number); - const HAL_StatusTypeDef tx_result_1 = HAL_SPI_Transmit(hspi, (uint8_t *)&FLASH_CMD_SECTOR_ERASE_4_BYTE_ADDR, 1, FLASH_HAL_TIMEOUT_MS); + const HAL_StatusTypeDef tx_result_1 = HAL_SPI_Transmit(hspi, (uint8_t *)&FLASH_CMD_BLOCK_ERASE, 1, FLASH_HAL_TIMEOUT_MS); + + // If couldn't send the command, check why if (tx_result_1 != HAL_OK) { FLASH_deactivate_chip_select(); @@ -260,7 +292,11 @@ FLASH_error_enum_t FLASH_erase(SPI_HandleTypeDef *hspi, uint8_t chip_number, lfs return FLASH_ERR_SPI_TRANSMIT_FAILED; } + + // Send the address bytes const HAL_StatusTypeDef tx_result_2 = HAL_SPI_Transmit(hspi, (uint8_t *)addr_bytes, 4, FLASH_HAL_TIMEOUT_MS); + + // If couldn't send the bytes, check why if (tx_result_2 != HAL_OK) { FLASH_deactivate_chip_select(); @@ -275,10 +311,11 @@ FLASH_error_enum_t FLASH_erase(SPI_HandleTypeDef *hspi, uint8_t chip_number, lfs // Buffer to store status register value uint8_t status_reg_buffer[1] = {0}; - // Keep looping as long as device is busy (until the Write Enable Latch is active [1]) + // Keep looping as long as device is busy (until the Operation In Progress bit is active [1]) const uint32_t start_loop_time_ms = HAL_GetTick(); while (1) { + // Get status register bits const FLASH_error_enum_t read_status_result = FLASH_read_status_register(hspi, chip_number, status_reg_buffer); if (read_status_result != FLASH_ERR_OK) { FLASH_deactivate_chip_select(); @@ -302,9 +339,11 @@ FLASH_error_enum_t FLASH_erase(SPI_HandleTypeDef *hspi, uint8_t chip_number, lfs return FLASH_ERR_DEVICE_BUSY_TIMEOUT; } - DEBUG_uart_print_str("DEBUG: status_reg = 0x"); - DEBUG_uart_print_array_hex(status_reg_buffer, 1); - DEBUG_uart_print_str("\n"); + if (FLASH_enable_hot_path_debug_logs) { + DEBUG_uart_print_str("DEBUG: status_reg = 0x"); + DEBUG_uart_print_array_hex(status_reg_buffer, 1); + DEBUG_uart_print_str("\n"); + } } // Should never be reached: @@ -315,26 +354,33 @@ FLASH_error_enum_t FLASH_erase(SPI_HandleTypeDef *hspi, uint8_t chip_number, lfs * @brief Sends Page Program Command * @param hspi - Pointer to the SPI HAL handle * @param chip_number - the chip select number to activate - * @param addr - block number that is to be written + * @param addr - block address that is to be written * @param packet_buffer - Pointer to buffer containing data to write * @param packet_buffer_len - integer that indicates the size of the data to write * @retval FLASH_ERR_OK on success, < 0 on failure */ -FLASH_error_enum_t FLASH_write(SPI_HandleTypeDef *hspi, uint8_t chip_number, lfs_block_t addr, uint8_t *packet_buffer, lfs_size_t packet_buffer_len) +FLASH_error_enum_t FLASH_write_data(SPI_HandleTypeDef *hspi, uint8_t chip_number, lfs_block_t addr, uint8_t *packet_buffer, lfs_size_t packet_buffer_len) { - // Split address into its 4 bytes + // Split main address into its 4 bytes uint8_t addr_bytes[4] = {(addr >> 24) & 0xFF, (addr >> 16) & 0xFF, (addr >> 8) & 0xFF, addr & 0xFF}; + + // Define the address where data will be stored in cache register (First 4 bits are dummy bits) + // TODO: Is it fine to always have this at 0? + uint16_t cache_addr = 0x0000; + uint8_t cache_addr_bytes[2] = {(cache_addr >> 8) & 0xFF, cache_addr & 0xFF}; - // Enable WREN Command, so that we can write to the memory module + // Send WRITE ENABLE Command const FLASH_error_enum_t wren_result = FLASH_write_enable(hspi, chip_number); if (wren_result != FLASH_ERR_OK) { FLASH_deactivate_chip_select(); return wren_result; } - // Send WREN Command and the Data required with the command + // Send PROGAM LOAD Command FLASH_activate_chip_select(chip_number); - const uint8_t tx_result_1 = HAL_SPI_Transmit(hspi, (uint8_t *)&FLASH_CMD_WRITE_4_BYTE_ADDR, 1, FLASH_HAL_TIMEOUT_MS); + const uint8_t tx_result_1 = HAL_SPI_Transmit(hspi, (uint8_t *)&FLASH_CMD_PROGRAM_LOAD, 1, FLASH_HAL_TIMEOUT_MS); + + // If couldn't send the command, check why if (tx_result_1 != HAL_OK) { FLASH_deactivate_chip_select(); @@ -344,7 +390,11 @@ FLASH_error_enum_t FLASH_write(SPI_HandleTypeDef *hspi, uint8_t chip_number, lfs return FLASH_ERR_SPI_TRANSMIT_FAILED; } - const uint8_t tx_result_2 = HAL_SPI_Transmit(hspi, (uint8_t *)addr_bytes, 4, FLASH_HAL_TIMEOUT_MS); + + // Send Cache Register address + const uint8_t tx_result_2 = HAL_SPI_Transmit(hspi, (uint8_t *)cache_addr_bytes, 2, FLASH_HAL_TIMEOUT_MS); + + // If couldn't send the bytes, check why if (tx_result_2 != HAL_OK) { FLASH_deactivate_chip_select(); @@ -354,7 +404,11 @@ FLASH_error_enum_t FLASH_write(SPI_HandleTypeDef *hspi, uint8_t chip_number, lfs return FLASH_ERR_SPI_TRANSMIT_FAILED; } + + // Send the data bytes const uint8_t tx_result_3 = HAL_SPI_Transmit(hspi, (uint8_t *)packet_buffer, packet_buffer_len, FLASH_HAL_TIMEOUT_MS); + + // If couldn't send the bytes, check why if (tx_result_3 != HAL_OK) { FLASH_deactivate_chip_select(); @@ -365,10 +419,44 @@ FLASH_error_enum_t FLASH_write(SPI_HandleTypeDef *hspi, uint8_t chip_number, lfs return FLASH_ERR_SPI_TRANSMIT_FAILED; } + // TODO: If Write doesn't work as intended or not all data bits are stored + // do the status register check loop here before deactivating chip select + FLASH_deactivate_chip_select(); + + // Send PROGAM EXECUTE Command + FLASH_activate_chip_select(chip_number); + const uint8_t tx_result_4 = HAL_SPI_Transmit(hspi, (uint8_t *)&FLASH_CMD_PROGRAM_EXEC, 1, FLASH_HAL_TIMEOUT_MS); + + // If couldn't send the command, check why + if (tx_result_4 != HAL_OK) { + FLASH_deactivate_chip_select(); + + if (tx_result_4 == HAL_TIMEOUT) { + return FLASH_ERR_SPI_TRANSMIT_TIMEOUT; + } + + return FLASH_ERR_SPI_TRANSMIT_FAILED; + } + + // Send address bytes + const uint8_t tx_result_5 = HAL_SPI_Transmit(hspi, (uint8_t *)addr_bytes, 4, FLASH_HAL_TIMEOUT_MS); + + // If couldn't send the bytes, check why + if (tx_result_5 != HAL_OK) { + FLASH_deactivate_chip_select(); + + if (tx_result_5 == HAL_TIMEOUT) { + return FLASH_ERR_SPI_TRANSMIT_TIMEOUT; + } + + return FLASH_ERR_SPI_TRANSMIT_FAILED; + } + FLASH_deactivate_chip_select(); + // Buffer to store status register value uint8_t status_reg_buffer[1] = {0}; - // Keep looping as long as device is busy (until the Write Enable Latch is active [1]) + // Keep looping as long as device is busy (until the Operation In Progress bit is active [1]) const uint32_t start_loop_time_ms = HAL_GetTick(); while (1) { @@ -395,9 +483,11 @@ FLASH_error_enum_t FLASH_write(SPI_HandleTypeDef *hspi, uint8_t chip_number, lfs return FLASH_ERR_DEVICE_BUSY_TIMEOUT; } - DEBUG_uart_print_str("DEBUG: status_reg = 0x"); - DEBUG_uart_print_array_hex(status_reg_buffer, 1); - DEBUG_uart_print_str("\n"); + if (FLASH_enable_hot_path_debug_logs) { + DEBUG_uart_print_str("DEBUG: status_reg = 0x"); + DEBUG_uart_print_array_hex(status_reg_buffer, 1); + DEBUG_uart_print_str("\n"); + } } // Should never be reached: @@ -405,22 +495,28 @@ FLASH_error_enum_t FLASH_write(SPI_HandleTypeDef *hspi, uint8_t chip_number, lfs } /** - * @brief Sends Page Program Command + * @brief Sends Page Read Command * @param hspi - Pointer to the SPI HAL handle - * @param chip_number - the chip select number to activate - * @param addr - block number that is to be read - * @param rx_buffer - a to buffer where the read data will be stored - * @param rx_buffer_len - integer that indicates the capacity of `rx_buffer` + * @param chip_number - The chip select number to activate + * @param addr - Address to be read + * @param rx_buffer - A buffer where the read data will be stored + * @param rx_buffer_len - Integer that indicates the capacity of `rx_buffer` * @retval FLASH_ERR_OK on success, < 0 on failure */ FLASH_error_enum_t FLASH_read_data(SPI_HandleTypeDef *hspi, uint8_t chip_number, lfs_block_t addr, uint8_t *rx_buffer, lfs_size_t rx_buffer_len) { - // Split address into its 4 bytes - uint8_t addr_bytes[4] = {(addr >> 24) & 0xFF, (addr >> 16) & 0xFF, (addr >> 8) & 0xFF, addr & 0xFF}; + uint8_t read_addr_bytes[4] = {(addr >> 24) & 0xFF, (addr >> 16) & 0xFF, (addr >> 8) & 0xFF, addr & 0xFF}; + + // Define the address where data will be read from in cache register (First 4 bits are dummy bits) + // TODO: Is it fine to always have this at 0? + uint16_t cache_addr = 0x0000; + uint8_t cache_addr_bytes[2] = {(cache_addr >> 8) & 0xFF, cache_addr & 0xFF}; - // Send Read Command and the data required with it + // Send PAGE READ command FLASH_activate_chip_select(chip_number); - const HAL_StatusTypeDef tx_result_1 = HAL_SPI_Transmit(hspi, (uint8_t *)&FLASH_CMD_READ_4_BYTE_ADDR, 1, FLASH_HAL_TIMEOUT_MS); + const HAL_StatusTypeDef tx_result_1 = HAL_SPI_Transmit(hspi, (uint8_t *) &FLASH_CMD_PAGE_READ, 1, FLASH_HAL_TIMEOUT_MS); + + // If couldn't send the command, check why if (tx_result_1 != HAL_OK) { FLASH_deactivate_chip_select(); @@ -430,7 +526,12 @@ FLASH_error_enum_t FLASH_read_data(SPI_HandleTypeDef *hspi, uint8_t chip_number, return FLASH_ERR_SPI_TRANSMIT_FAILED; } - const HAL_StatusTypeDef tx_result_2 = HAL_SPI_Transmit(hspi, (uint8_t *)addr_bytes, 4, FLASH_HAL_TIMEOUT_MS); + + // FIXME: Datasheet Page 16 talks about only giving 8-bit dummy values and 16-bit address, not sure how that works + // Send Address bytes + const HAL_StatusTypeDef tx_result_2 = HAL_SPI_Transmit(hspi, (uint8_t *) read_addr_bytes, 4, FLASH_HAL_TIMEOUT_MS); + + // If couldn't send the bytes, check why if (tx_result_2 != HAL_OK) { FLASH_deactivate_chip_select(); @@ -440,7 +541,89 @@ FLASH_error_enum_t FLASH_read_data(SPI_HandleTypeDef *hspi, uint8_t chip_number, return FLASH_ERR_SPI_TRANSMIT_FAILED; } + + // Set Chip Select HIGH + FLASH_deactivate_chip_select(); + + // Buffer to store status register value + uint8_t status_reg_buffer[1] = {0}; + + // Keep looping as long as device is busy (until the Operation In Progress bit is active [1]) + const uint32_t start_loop_time_ms = HAL_GetTick(); + while (1) + { + const FLASH_error_enum_t read_status_result = FLASH_read_status_register(hspi, chip_number, status_reg_buffer); + if (read_status_result != FLASH_ERR_OK) { + FLASH_deactivate_chip_select(); + return read_status_result; + } + + if ((status_reg_buffer[0] & FLASH_SR1_WRITE_IN_PROGRESS_MASK) == 0) { + // Success condition: write in progress has completed. + return FLASH_ERR_OK; + } + + // Do this comparison AFTER checking the success condition (for speed, and to avoid timing out on a success). + if (HAL_GetTick() - start_loop_time_ms > FLASH_LOOP_WRITE_TIMEOUT_MS) { + DEBUG_uart_print_str("Flash read timeout\n"); + return FLASH_ERR_DEVICE_BUSY_TIMEOUT; + } + + if (FLASH_enable_hot_path_debug_logs) { + DEBUG_uart_print_str("DEBUG: status_reg = 0x"); + DEBUG_uart_print_array_hex(status_reg_buffer, 1); + DEBUG_uart_print_str("\n"); + } + } + FLASH_deactivate_chip_select(); + + // Send READ FROM CACHE command + FLASH_activate_chip_select(chip_number); + const HAL_StatusTypeDef tx_result_3 = HAL_SPI_Transmit(hspi, (uint8_t *) &FLASH_CMD_READ_FROM_CACHE, 1, FLASH_HAL_TIMEOUT_MS); + + // If couldn't send the command, check why + if (tx_result_3 != HAL_OK) { + FLASH_deactivate_chip_select(); + + if (tx_result_3 == HAL_TIMEOUT) { + return FLASH_ERR_SPI_TRANSMIT_TIMEOUT; + } + + return FLASH_ERR_SPI_TRANSMIT_FAILED; + } + + // Send cache address bytes + const HAL_StatusTypeDef tx_result_4 = HAL_SPI_Transmit(hspi, (uint8_t *) cache_addr_bytes, 2, FLASH_HAL_TIMEOUT_MS); + + // If couldn't send the bytes, check why + if (tx_result_4 != HAL_OK) { + FLASH_deactivate_chip_select(); + + if (tx_result_4 == HAL_TIMEOUT) { + return FLASH_ERR_SPI_TRANSMIT_TIMEOUT; + } + + return FLASH_ERR_SPI_TRANSMIT_FAILED; + } + + // Send cache address bytes again just as 2 dummy bytes to use 2 8-bit clock cycles + const HAL_StatusTypeDef tx_result_5 = HAL_SPI_Transmit(hspi, (uint8_t *) cache_addr_bytes, 2, FLASH_HAL_TIMEOUT_MS); + + // If couldn't send the bytes, check why + if (tx_result_5 != HAL_OK) { + FLASH_deactivate_chip_select(); + + if (tx_result_5 == HAL_TIMEOUT) { + return FLASH_ERR_SPI_TRANSMIT_TIMEOUT; + } + + return FLASH_ERR_SPI_TRANSMIT_FAILED; + } + + // Receive the data into the buffer const HAL_StatusTypeDef rx_result_1 = HAL_SPI_Receive(hspi, (uint8_t *)rx_buffer, rx_buffer_len, FLASH_HAL_TIMEOUT_MS); + + // If couldn't receive data, check why if (rx_result_1 != HAL_OK) { FLASH_deactivate_chip_select(); @@ -450,12 +633,44 @@ FLASH_error_enum_t FLASH_read_data(SPI_HandleTypeDef *hspi, uint8_t chip_number, return FLASH_ERR_SPI_RECEIVE_FAILED; } + + // Set Chip Select HIGH FLASH_deactivate_chip_select(); - // TODO: Haven't yet implemented a way to check any errors while reading data from memory - return 0; + // TODO: Are there any other errors that can occur while reading? + return FLASH_ERR_OK; } + + + + + + + + + + + + + + + + + + + + + + + + +/** + * @brief Checks if the FLASH chip is reachable by checking it's ID + * @param hspi - Pointer to the SPI HAL handle + * @param chip_number - The chip select number to activate + * @retval FLASH_ERR_OK on success, < 0 on failure + */ FLASH_error_enum_t FLASH_is_reachable(SPI_HandleTypeDef *hspi, uint8_t chip_number) { // TODO: confirm if this works with the CS2 logical chip on each physical FLASH chip; @@ -465,9 +680,11 @@ FLASH_error_enum_t FLASH_is_reachable(SPI_HandleTypeDef *hspi, uint8_t chip_numb uint8_t rx_buffer[5]; memset(rx_buffer, 0, 5); - // Transmit the READ_ID_CMD + // Send READ ID Command FLASH_activate_chip_select(chip_number); const HAL_StatusTypeDef tx_result_1 = HAL_SPI_Transmit(hspi, tx_buffer, 1, FLASH_HAL_TIMEOUT_MS); + + // If couldn't send the command, check why if (tx_result_1 != HAL_OK) { FLASH_deactivate_chip_select(); @@ -478,8 +695,24 @@ FLASH_error_enum_t FLASH_is_reachable(SPI_HandleTypeDef *hspi, uint8_t chip_numb return FLASH_ERR_SPI_TRANSMIT_FAILED; } + // Send the command again just as a dummy byte + const HAL_StatusTypeDef tx_result_2 = HAL_SPI_Transmit(hspi, tx_buffer, 1, FLASH_HAL_TIMEOUT_MS); + + // If couldn't send the command, check why + if (tx_result_2 != HAL_OK) { + FLASH_deactivate_chip_select(); + + if (tx_result_2 == HAL_TIMEOUT) { + return FLASH_ERR_SPI_TRANSMIT_TIMEOUT; + } + + return FLASH_ERR_SPI_TRANSMIT_FAILED; + } + // Receive the response const HAL_StatusTypeDef rx_result = HAL_SPI_Receive(hspi, rx_buffer, 5, FLASH_HAL_TIMEOUT_MS); + + // If couldn't receive, checky why if (rx_result != HAL_OK) { FLASH_deactivate_chip_select(); @@ -498,7 +731,7 @@ FLASH_error_enum_t FLASH_is_reachable(SPI_HandleTypeDef *hspi, uint8_t chip_numb // rx_buffer[2] is 0x20=512 for 512 Mib (mebibits) // TODO: maybe check the capacity as well here, esp. in deployment uint8_t are_bytes_correct = 0; - if (rx_buffer[0] == 0x01 && rx_buffer[1] == 0x02) { + if (rx_buffer[0] == 0x2C && rx_buffer[1] == 0x14) { DEBUG_uart_print_str("SUCCESS: FLASH_is_reachable received IDs: "); are_bytes_correct = 1; } else { @@ -511,7 +744,7 @@ FLASH_error_enum_t FLASH_is_reachable(SPI_HandleTypeDef *hspi, uint8_t chip_numb if (!are_bytes_correct) { // error: IDs don't match - return 3; + return FLASH_ERR_UNKNOWN; } - return 0; // success + return FLASH_ERR_OK; // success } diff --git a/firmware/Core/Src/littlefs/flash_testing_demos.c b/firmware/Core/Src/littlefs/flash_testing_demos.c index bd711fcdc..28d4a6447 100644 --- a/firmware/Core/Src/littlefs/flash_testing_demos.c +++ b/firmware/Core/Src/littlefs/flash_testing_demos.c @@ -13,7 +13,7 @@ void demo_flash_write() { uint32_t num_bytes = strlen((char*)bytes_to_write); for (uint8_t i = 0; i < 2; i++) { - FLASH_error_enum_t result = FLASH_write(&hspi1, chip_num, flash_addr, bytes_to_write, num_bytes); + FLASH_error_enum_t result = FLASH_write_data(&hspi1, chip_num, flash_addr, bytes_to_write, num_bytes); if (result != 0) { DEBUG_uart_print_str("Error in FLASH_write\n"); return; diff --git a/firmware/Core/Src/littlefs/littlefs_driver.c b/firmware/Core/Src/littlefs/littlefs_driver.c index a1edfaca8..811b0ad07 100644 --- a/firmware/Core/Src/littlefs/littlefs_driver.c +++ b/firmware/Core/Src/littlefs/littlefs_driver.c @@ -34,7 +34,7 @@ int LFS_block_device_read(const struct lfs_config *c, lfs_block_t block, lfs_off */ int LFS_block_device_prog(const struct lfs_config *c, lfs_block_t block, lfs_off_t off, const void *buffer, lfs_size_t size) { - return FLASH_write( + return FLASH_write_data( hspi_lfs_ptr, LFS_get_chip_number(block), (block * c->block_size + off), diff --git a/firmware/Core/Src/telecommands/flash_telecommand_defs.c b/firmware/Core/Src/telecommands/flash_telecommand_defs.c index 25edd0e99..afb7deac0 100644 --- a/firmware/Core/Src/telecommands/flash_telecommand_defs.c +++ b/firmware/Core/Src/telecommands/flash_telecommand_defs.c @@ -202,7 +202,7 @@ uint8_t TCMDEXEC_flash_write_hex(const char *args_str, TCMD_TelecommandChannel_e uint32_t flash_addr = (uint32_t)flash_addr_u64; - FLASH_error_enum_t result = FLASH_write(&hspi1, chip_num, flash_addr, bytes_to_write, num_bytes); + FLASH_error_enum_t result = FLASH_write_data(&hspi1, chip_num, flash_addr, bytes_to_write, num_bytes); if (result != 0) { snprintf( From a44e5ac353efea9664b39cc8bcdeb60c2c1810d0 Mon Sep 17 00:00:00 2001 From: Saksham Puri <84263133+Saksham-P@users.noreply.github.com> Date: Mon, 22 Jul 2024 16:44:07 -0600 Subject: [PATCH 02/19] Updated memory module configuration Updated littlefs_helper.c configuration to use NAND memory module configuration values --- firmware/Core/Src/littlefs/littlefs_helper.c | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/firmware/Core/Src/littlefs/littlefs_helper.c b/firmware/Core/Src/littlefs/littlefs_helper.c index 6e476b8c9..2b3eaa1ae 100644 --- a/firmware/Core/Src/littlefs/littlefs_helper.c +++ b/firmware/Core/Src/littlefs/littlefs_helper.c @@ -14,8 +14,8 @@ // Variables to track LittleFS on Flash Memory Module uint8_t LFS_is_lfs_mounted = 0; -#define FLASH_CHIP_PAGE_SIZE_BYTES 512 -#define FLASH_CHIP_BLOCK_SIZE_BYTES 262144 +#define FLASH_CHIP_PAGE_SIZE_BYTES 2176 +#define FLASH_CHIP_BLOCK_SIZE_BYTES 139264 #define FLASH_LOOKAHEAD_SIZE 16 // LittleFS Buffers for reading and writing From ae68581f34033dd7e57d24a6078f415c13111b8f Mon Sep 17 00:00:00 2001 From: KaleF07 Date: Sat, 7 Sep 2024 13:03:10 -0700 Subject: [PATCH 03/19] Changes to flash_driver and flash_telecommand_defs Made changes to flash to handle full page reading and writing, added flash telecommand that unblocks block locks. --- firmware/Core/Inc/littlefs/flash_driver.h | 6 +- .../Inc/telecommands/flash_telecommand_defs.h | 8 + firmware/Core/Src/littlefs/flash_driver.c | 221 ++++++++++++++++-- .../Src/telecommands/flash_telecommand_defs.c | 76 +++++- .../telecommands/telecommand_definitions.c | 12 + 5 files changed, 299 insertions(+), 24 deletions(-) diff --git a/firmware/Core/Inc/littlefs/flash_driver.h b/firmware/Core/Inc/littlefs/flash_driver.h index 0f66de0f8..5c51ee6a5 100644 --- a/firmware/Core/Inc/littlefs/flash_driver.h +++ b/firmware/Core/Inc/littlefs/flash_driver.h @@ -41,10 +41,11 @@ static const uint8_t FLASH_CMD_WRITE_ENABLE = 0x06; // Write Enable static const uint8_t FLASH_CMD_WRITE_DISABLE = 0x04; // Write Disable static const uint8_t FLASH_CMD_GET_FEATURES = 0x0F; // Get Features +static const uint8_t FLASH_CMD_SET_FEATURES = 0x1F; // Set Features static const uint8_t FLASH_CMD_READ_ID = 0x9F; // Read ID (0x2C 0x14) -static const uint8_t FLASH_CMD_RESET = 0xFF; +static const uint8_t FLASH_CMD_RESET = 0xFF; // Reset operation // ------------------- Status Register 1 - Byte Masks ------------------- // Source: Table 5 @@ -68,7 +69,9 @@ typedef enum { /*-----------------------------DRIVER FUNCTIONS-----------------------------*/ void FLASH_activate_chip_select(uint8_t chip_number); void FLASH_deactivate_chip_select(); +FLASH_error_enum_t FLASH_unblock_block_lock(SPI_HandleTypeDef *hspi, uint8_t chip_number, uint8_t *buf); FLASH_error_enum_t FLASH_read_status_register(SPI_HandleTypeDef *hspi, uint8_t chip_number, uint8_t *buf); +FLASH_error_enum_t FLASH_read_block_lock_register(SPI_HandleTypeDef *hspi, uint8_t chip_number, uint8_t *buf); FLASH_error_enum_t FLASH_write_enable(SPI_HandleTypeDef *hspi, uint8_t chip_number); FLASH_error_enum_t FLASH_write_disable(SPI_HandleTypeDef *hspi, uint8_t chip_number); FLASH_error_enum_t FLASH_erase(SPI_HandleTypeDef *hspi, uint8_t chip_number, lfs_block_t addr); @@ -76,5 +79,6 @@ FLASH_error_enum_t FLASH_write_data(SPI_HandleTypeDef *hspi, uint8_t chip_number FLASH_error_enum_t FLASH_read_data(SPI_HandleTypeDef *hspi, uint8_t chip_number, lfs_block_t addr, uint8_t *rx_buffer, lfs_size_t rx_buffer_len); FLASH_error_enum_t FLASH_is_reachable(SPI_HandleTypeDef *hspi, uint8_t chip_number); +FLASH_error_enum_t FLASH_reset(SPI_HandleTypeDef *hspi, uint8_t chip_number); #endif /* __INCLUDE_GUARD__FLASH_DRIVER_H__ */ diff --git a/firmware/Core/Inc/telecommands/flash_telecommand_defs.h b/firmware/Core/Inc/telecommands/flash_telecommand_defs.h index ac8b83c4b..dcc333f4b 100644 --- a/firmware/Core/Inc/telecommands/flash_telecommand_defs.h +++ b/firmware/Core/Inc/telecommands/flash_telecommand_defs.h @@ -5,6 +5,8 @@ #include #include "telecommands/telecommand_definitions.h" +#define MAX_NUM_BYTES_TO_READ 2048 + uint8_t TCMDEXEC_flash_activate_each_cs(const char *args_str, TCMD_TelecommandChannel_enum_t tcmd_channel, char *response_output_buf, uint16_t response_output_buf_len); @@ -22,5 +24,11 @@ uint8_t TCMDEXEC_flash_erase(const char *args_str, TCMD_TelecommandChannel_enum_ uint8_t TCMDEXEC_flash_benchmark_erase_write_read(const char *args_str, TCMD_TelecommandChannel_enum_t tcmd_channel, char *response_output_buf, uint16_t response_output_buf_len); + +uint8_t TCMDEXEC_flash_reset(const char *args_str, TCMD_TelecommandChannel_enum_t tcmd_channel, + char *response_output_buf, uint16_t response_output_buf_len); + +uint8_t TCMDEXEC_flash_unblock_block_locks(const char *args_str, TCMD_TelecommandChannel_enum_t tcmd_channel, + char *response_output_buf, uint16_t response_output_buf_len); #endif /* __INCLUDE_GUARD__FLASH_TELECOMMAND_DEFS_H__ */ diff --git a/firmware/Core/Src/littlefs/flash_driver.c b/firmware/Core/Src/littlefs/flash_driver.c index a3a4cdd16..dcd735367 100644 --- a/firmware/Core/Src/littlefs/flash_driver.c +++ b/firmware/Core/Src/littlefs/flash_driver.c @@ -85,6 +85,79 @@ void FLASH_deactivate_chip_select() HAL_GPIO_WritePin(PIN_MEM_NCS_FRAM_1_GPIO_Port, PIN_MEM_NCS_FRAM_1_Pin, GPIO_PIN_SET); } +/** + * @brief Unblocks all blocked blocks of memory on the NAND flash memory module + * + * @param hspi - Pointer to the SPI HAL handle + * @param chip_number - the chip select number to activate + * @param buf - Pointer to a buffer to store the new Block Lock Register value. Length: 1 byte. + * @return FLASH_ERR_OK on success, < 0 on failure + * + * @note unblocking blocks of memory is necessary to write to memory + */ +FLASH_error_enum_t FLASH_unblock_block_lock(SPI_HandleTypeDef *hspi, uint8_t chip_number, uint8_t *buf) { + + static const uint8_t data_bytes = (1 << 1); + + // Send SET FEATURES command + FLASH_activate_chip_select(chip_number); + const HAL_StatusTypeDef tx_result_1 = HAL_SPI_Transmit(hspi, (uint8_t *)&FLASH_CMD_SET_FEATURES, 1, FLASH_HAL_TIMEOUT_MS); + + // If couldn't send the command, check why + if (tx_result_1 != HAL_OK) { + FLASH_deactivate_chip_select(); + + if (tx_result_1 == HAL_TIMEOUT) { + return FLASH_ERR_SPI_TRANSMIT_TIMEOUT; + } + + return FLASH_ERR_SPI_TRANSMIT_FAILED; + } + + // Send the byte address of block lock register + const HAL_StatusTypeDef tx_result_2 = HAL_SPI_Transmit(hspi, (uint8_t *)&FLASH_FEAT_BLOCK_LOCK, 1, FLASH_HAL_TIMEOUT_MS); + + // If couldn't send the byte, check why + if (tx_result_2 != HAL_OK) { + FLASH_deactivate_chip_select(); + + if (tx_result_2 == HAL_TIMEOUT) { + return FLASH_ERR_SPI_TRANSMIT_TIMEOUT; + } + + return FLASH_ERR_SPI_TRANSMIT_FAILED; + } + + // Send the data bytes of what we want the Block Lock register to be + const HAL_StatusTypeDef tx_result_3 = HAL_SPI_Transmit(hspi, (uint8_t *)&data_bytes, 1, FLASH_HAL_TIMEOUT_MS); + + // If couldn't send the byte, check why + if (tx_result_3 != HAL_OK) { + FLASH_deactivate_chip_select(); + + if (tx_result_3 == HAL_TIMEOUT) { + return FLASH_ERR_SPI_TRANSMIT_TIMEOUT; + } + + return FLASH_ERR_SPI_TRANSMIT_FAILED; + } + + // Call a function that reads the block lock register here to check if it changed anything + const FLASH_error_enum_t block_lock_result_2 = FLASH_read_block_lock_register(hspi, chip_number, buf); + if (block_lock_result_2 != FLASH_ERR_OK) { + FLASH_deactivate_chip_select(); + + if (block_lock_result_2 == FLASH_ERR_SPI_TRANSMIT_TIMEOUT) { + return FLASH_ERR_SPI_TRANSMIT_TIMEOUT; + } + + return FLASH_ERR_SPI_TRANSMIT_FAILED; + } + + FLASH_deactivate_chip_select(); + return FLASH_ERR_OK; +} + /** * @brief Read Status Register and store the values in given buffer * @param hspi - Pointer to the SPI HAL handle @@ -141,6 +214,62 @@ FLASH_error_enum_t FLASH_read_status_register(SPI_HandleTypeDef *hspi, uint8_t c return FLASH_ERR_OK; } +/** + * @brief Read Block Lock Register and store the values in given buffer + * @param hspi - Pointer to the SPI HAL handle + * @param chip_number - the chip select number to activate + * @param buf - Pointer to a buffer to store Block Lock Register value. Length: 1 byte. + * @retval FLASH_ERR_OK on success, < 0 on failure + */ +FLASH_error_enum_t FLASH_read_block_lock_register(SPI_HandleTypeDef *hspi, uint8_t chip_number, uint8_t *buf) +{ + // Send GET FEATURES command + FLASH_activate_chip_select(chip_number); + const HAL_StatusTypeDef tx_result_1 = HAL_SPI_Transmit(hspi, (uint8_t *)&FLASH_CMD_GET_FEATURES, 1, FLASH_HAL_TIMEOUT_MS); + + // If couldn't send the command, check why + if (tx_result_1 != HAL_OK) { + FLASH_deactivate_chip_select(); + + if (tx_result_1 == HAL_TIMEOUT) { + return FLASH_ERR_SPI_TRANSMIT_TIMEOUT; + } + + return FLASH_ERR_SPI_TRANSMIT_FAILED; + } + + // Send the byte address of block lock register + const HAL_StatusTypeDef tx_result_2 = HAL_SPI_Transmit(hspi, (uint8_t *)&FLASH_FEAT_BLOCK_LOCK, 1, FLASH_HAL_TIMEOUT_MS); + + // If couldn't send the byte, check why + if (tx_result_2 != HAL_OK) { + FLASH_deactivate_chip_select(); + + if (tx_result_2 == HAL_TIMEOUT) { + return FLASH_ERR_SPI_TRANSMIT_TIMEOUT; + } + + return FLASH_ERR_SPI_TRANSMIT_FAILED; + } + + // Receive the Block Lock Register bits + const HAL_StatusTypeDef rx_result = HAL_SPI_Receive(hspi, (uint8_t *)buf, 1, FLASH_HAL_TIMEOUT_MS); + + // If couldn't receive the byte, check why + if (rx_result != HAL_OK) { + FLASH_deactivate_chip_select(); + + if (rx_result == HAL_TIMEOUT) { + return FLASH_ERR_SPI_RECEIVE_TIMEOUT; + } + + return FLASH_ERR_SPI_RECEIVE_FAILED; + } + + FLASH_deactivate_chip_select(); + return FLASH_ERR_OK; +} + /** * @brief Sends Write Enable Command * @param hspi - Pointer to the SPI HAL handle @@ -269,7 +398,8 @@ FLASH_error_enum_t FLASH_write_disable(SPI_HandleTypeDef *hspi, uint8_t chip_num FLASH_error_enum_t FLASH_erase(SPI_HandleTypeDef *hspi, uint8_t chip_number, lfs_block_t addr) { // Split address into its 4 bytes - uint8_t addr_bytes[4] = {(addr >> 24) & 0xFF, (addr >> 16) & 0xFF, (addr >> 8) & 0xFF, addr & 0xFF}; + // uint8_t addr_bytes[4] = {(addr >> 24) & 0xFF, (addr >> 16) & 0xFF, (addr >> 8) & 0xFF, addr & 0xFF}; + uint8_t addr_bytes[3] = {(addr >> 16) & 0xFF, (addr >> 8) & 0xFF, addr & 0xFF}; // Send WRITE ENABLE Command const FLASH_error_enum_t wren_result = FLASH_write_enable(hspi, chip_number); @@ -294,7 +424,7 @@ FLASH_error_enum_t FLASH_erase(SPI_HandleTypeDef *hspi, uint8_t chip_number, lfs } // Send the address bytes - const HAL_StatusTypeDef tx_result_2 = HAL_SPI_Transmit(hspi, (uint8_t *)addr_bytes, 4, FLASH_HAL_TIMEOUT_MS); + const HAL_StatusTypeDef tx_result_2 = HAL_SPI_Transmit(hspi, (uint8_t *)addr_bytes, 3, FLASH_HAL_TIMEOUT_MS); // If couldn't send the bytes, check why if (tx_result_2 != HAL_OK) { @@ -361,13 +491,32 @@ FLASH_error_enum_t FLASH_erase(SPI_HandleTypeDef *hspi, uint8_t chip_number, lfs */ FLASH_error_enum_t FLASH_write_data(SPI_HandleTypeDef *hspi, uint8_t chip_number, lfs_block_t addr, uint8_t *packet_buffer, lfs_size_t packet_buffer_len) { - // Split main address into its 4 bytes - uint8_t addr_bytes[4] = {(addr >> 24) & 0xFF, (addr >> 16) & 0xFF, (addr >> 8) & 0xFF, addr & 0xFF}; + uint8_t temp_buf[1] = {0}; + const FLASH_error_enum_t temp = FLASH_read_block_lock_register(hspi, chip_number, temp_buf); + if (temp != FLASH_ERR_OK) { + FLASH_deactivate_chip_select(); + return temp; + } +/* + DEBUG_uart_print_array_hex(packet_buffer, packet_buffer_len); + DEBUG_uart_print_str("\n"); + DEBUG_uart_print_uint32((uint32_t)packet_buffer_len); + DEBUG_uart_print_str("\n"); +*/ + // DEBUG_uart_print_array_hex(packet_buffer, packet_buffer_len); + + // Split main address into its 3 bytes + uint8_t addr_bytes[3] = {(addr >> 16) & 0xFF, (addr >> 8) & 0xFF, addr & 0xFF}; // Define the address where data will be stored in cache register (First 4 bits are dummy bits) // TODO: Is it fine to always have this at 0? uint16_t cache_addr = 0x0000; - uint8_t cache_addr_bytes[2] = {(cache_addr >> 8) & 0xFF, cache_addr & 0xFF}; + uint8_t cache_addr_bytes[2] = {(cache_addr >> 8) & 0xFF, cache_addr & 0xFF}; // modify + // check for packet buffer length > 2176 (pg.29 of datasheet, program load) + // 1st byte: op code + // 2nd bye: 1st four bits dummy bytes, 2nd four bits column address + // 3rd byte: rest of column address + //4th - forward: data bits // Send WRITE ENABLE Command const FLASH_error_enum_t wren_result = FLASH_write_enable(hspi, chip_number); @@ -406,7 +555,8 @@ FLASH_error_enum_t FLASH_write_data(SPI_HandleTypeDef *hspi, uint8_t chip_number } // Send the data bytes - const uint8_t tx_result_3 = HAL_SPI_Transmit(hspi, (uint8_t *)packet_buffer, packet_buffer_len, FLASH_HAL_TIMEOUT_MS); + // const uint8_t tx_result_3 = HAL_SPI_Transmit(hspi, packet_buffer, packet_buffer_len, FLASH_HAL_TIMEOUT_MS); + const uint8_t tx_result_3 = HAL_SPI_Transmit(hspi, packet_buffer, packet_buffer_len, 50); // If couldn't send the bytes, check why if (tx_result_3 != HAL_OK) { @@ -439,7 +589,7 @@ FLASH_error_enum_t FLASH_write_data(SPI_HandleTypeDef *hspi, uint8_t chip_number } // Send address bytes - const uint8_t tx_result_5 = HAL_SPI_Transmit(hspi, (uint8_t *)addr_bytes, 4, FLASH_HAL_TIMEOUT_MS); + const uint8_t tx_result_5 = HAL_SPI_Transmit(hspi, (uint8_t *)addr_bytes, 3, FLASH_HAL_TIMEOUT_MS); // If couldn't send the bytes, check why if (tx_result_5 != HAL_OK) { @@ -505,16 +655,23 @@ FLASH_error_enum_t FLASH_write_data(SPI_HandleTypeDef *hspi, uint8_t chip_number */ FLASH_error_enum_t FLASH_read_data(SPI_HandleTypeDef *hspi, uint8_t chip_number, lfs_block_t addr, uint8_t *rx_buffer, lfs_size_t rx_buffer_len) { - uint8_t read_addr_bytes[4] = {(addr >> 24) & 0xFF, (addr >> 16) & 0xFF, (addr >> 8) & 0xFF, addr & 0xFF}; - + // uint8_t read_addr_bytes[4] = {(addr >> 24) & 0xFF, (addr >> 16) & 0xFF, (addr >> 8) & 0xFF, addr & 0xFF}; + uint8_t read_addr_bytes[3] = {0, (addr >> 8) & 0xFF, addr & 0xFF}; +/* + DEBUG_uart_print_str("Read address bytes: "); + for(int i=0; i<3; i++) { + DEBUG_uart_print_array_hex(&read_addr_bytes[i], 1); + } + DEBUG_uart_print_str("\n\n"); +*/ // Define the address where data will be read from in cache register (First 4 bits are dummy bits) // TODO: Is it fine to always have this at 0? uint16_t cache_addr = 0x0000; - uint8_t cache_addr_bytes[2] = {(cache_addr >> 8) & 0xFF, cache_addr & 0xFF}; + uint8_t cache_addr_bytes[2] = {(cache_addr >> 8) & 0xFF,cache_addr & 0xFF}; // Send PAGE READ command FLASH_activate_chip_select(chip_number); - const HAL_StatusTypeDef tx_result_1 = HAL_SPI_Transmit(hspi, (uint8_t *) &FLASH_CMD_PAGE_READ, 1, FLASH_HAL_TIMEOUT_MS); + const HAL_StatusTypeDef tx_result_1 = HAL_SPI_Transmit(hspi, (uint8_t *)&FLASH_CMD_PAGE_READ, 1, FLASH_HAL_TIMEOUT_MS); // If couldn't send the command, check why if (tx_result_1 != HAL_OK) { @@ -529,7 +686,7 @@ FLASH_error_enum_t FLASH_read_data(SPI_HandleTypeDef *hspi, uint8_t chip_number, // FIXME: Datasheet Page 16 talks about only giving 8-bit dummy values and 16-bit address, not sure how that works // Send Address bytes - const HAL_StatusTypeDef tx_result_2 = HAL_SPI_Transmit(hspi, (uint8_t *) read_addr_bytes, 4, FLASH_HAL_TIMEOUT_MS); + const HAL_StatusTypeDef tx_result_2 = HAL_SPI_Transmit(hspi, (uint8_t *)read_addr_bytes, 3, FLASH_HAL_TIMEOUT_MS); // If couldn't send the bytes, check why if (tx_result_2 != HAL_OK) { @@ -560,7 +717,8 @@ FLASH_error_enum_t FLASH_read_data(SPI_HandleTypeDef *hspi, uint8_t chip_number, if ((status_reg_buffer[0] & FLASH_SR1_WRITE_IN_PROGRESS_MASK) == 0) { // Success condition: write in progress has completed. - return FLASH_ERR_OK; + // return FLASH_ERR_OK; + break; } // Do this comparison AFTER checking the success condition (for speed, and to avoid timing out on a success). @@ -579,7 +737,7 @@ FLASH_error_enum_t FLASH_read_data(SPI_HandleTypeDef *hspi, uint8_t chip_number, // Send READ FROM CACHE command FLASH_activate_chip_select(chip_number); - const HAL_StatusTypeDef tx_result_3 = HAL_SPI_Transmit(hspi, (uint8_t *) &FLASH_CMD_READ_FROM_CACHE, 1, FLASH_HAL_TIMEOUT_MS); + const HAL_StatusTypeDef tx_result_3 = HAL_SPI_Transmit(hspi, (uint8_t *)&FLASH_CMD_READ_FROM_CACHE, 1, FLASH_HAL_TIMEOUT_MS); // If couldn't send the command, check why if (tx_result_3 != HAL_OK) { @@ -593,7 +751,7 @@ FLASH_error_enum_t FLASH_read_data(SPI_HandleTypeDef *hspi, uint8_t chip_number, } // Send cache address bytes - const HAL_StatusTypeDef tx_result_4 = HAL_SPI_Transmit(hspi, (uint8_t *) cache_addr_bytes, 2, FLASH_HAL_TIMEOUT_MS); + const HAL_StatusTypeDef tx_result_4 = HAL_SPI_Transmit(hspi, (uint8_t *)cache_addr_bytes, 2, FLASH_HAL_TIMEOUT_MS); // If couldn't send the bytes, check why if (tx_result_4 != HAL_OK) { @@ -607,7 +765,7 @@ FLASH_error_enum_t FLASH_read_data(SPI_HandleTypeDef *hspi, uint8_t chip_number, } // Send cache address bytes again just as 2 dummy bytes to use 2 8-bit clock cycles - const HAL_StatusTypeDef tx_result_5 = HAL_SPI_Transmit(hspi, (uint8_t *) cache_addr_bytes, 2, FLASH_HAL_TIMEOUT_MS); + const HAL_StatusTypeDef tx_result_5 = HAL_SPI_Transmit(hspi, (uint8_t *) cache_addr_bytes, 1, FLASH_HAL_TIMEOUT_MS); // If couldn't send the bytes, check why if (tx_result_5 != HAL_OK) { @@ -621,7 +779,8 @@ FLASH_error_enum_t FLASH_read_data(SPI_HandleTypeDef *hspi, uint8_t chip_number, } // Receive the data into the buffer - const HAL_StatusTypeDef rx_result_1 = HAL_SPI_Receive(hspi, (uint8_t *)rx_buffer, rx_buffer_len, FLASH_HAL_TIMEOUT_MS); + //const HAL_StatusTypeDef rx_result_1 = HAL_SPI_Receive(hspi, (uint8_t *)rx_buffer, rx_buffer_len, FLASH_HAL_TIMEOUT_MS); + const HAL_StatusTypeDef rx_result_1 = HAL_SPI_Receive(hspi, (uint8_t *)rx_buffer, rx_buffer_len, 50); // If couldn't receive data, check why if (rx_result_1 != HAL_OK) { @@ -637,6 +796,13 @@ FLASH_error_enum_t FLASH_read_data(SPI_HandleTypeDef *hspi, uint8_t chip_number, // Set Chip Select HIGH FLASH_deactivate_chip_select(); + DEBUG_uart_print_str("Read data: \n"); + DEBUG_uart_print_array_hex(rx_buffer, rx_buffer_len); + DEBUG_uart_print_str("\n"); + DEBUG_uart_print_str("Length of data read: "); + DEBUG_uart_print_uint32((uint32_t)rx_buffer_len); + DEBUG_uart_print_str("\n"); + // TODO: Are there any other errors that can occur while reading? return FLASH_ERR_OK; } @@ -748,3 +914,24 @@ FLASH_error_enum_t FLASH_is_reachable(SPI_HandleTypeDef *hspi, uint8_t chip_numb } return FLASH_ERR_OK; // success } + +FLASH_error_enum_t FLASH_reset(SPI_HandleTypeDef *hspi, uint8_t chip_number) +{ + FLASH_activate_chip_select(chip_number); + + uint8_t tx_buffer[1] = {FLASH_CMD_RESET}; + HAL_StatusTypeDef tx_result = HAL_SPI_Transmit(hspi, tx_buffer, 1, FLASH_HAL_TIMEOUT_MS); + + // If couldn't send the command, check why + if (tx_result != HAL_OK) { + FLASH_deactivate_chip_select(); + + if (tx_result == HAL_TIMEOUT) { + return FLASH_ERR_SPI_TRANSMIT_TIMEOUT; + } + + return FLASH_ERR_SPI_TRANSMIT_FAILED; + } + + return FLASH_ERR_OK; +} \ No newline at end of file diff --git a/firmware/Core/Src/telecommands/flash_telecommand_defs.c b/firmware/Core/Src/telecommands/flash_telecommand_defs.c index afb7deac0..a20694474 100644 --- a/firmware/Core/Src/telecommands/flash_telecommand_defs.c +++ b/firmware/Core/Src/telecommands/flash_telecommand_defs.c @@ -10,6 +10,45 @@ #include #include +uint8_t read_buf[MAX_NUM_BYTES_TO_READ]; + +/// @brief Telecommand: Unblock restricted block locks on NAND flash memory module +/// @param args_str +/// - Arg 0: Chip Number (CS number) as uint +/// @return 0 on success, >0 on error +uint8_t TCMDEXEC_flash_unblock_block_locks(const char *args_str, TCMD_TelecommandChannel_enum_t tcmd_channel, + char *response_output_buf, uint16_t response_output_buf_len) { + uint64_t chip_num; + + const uint8_t arg0_result = TCMD_extract_uint64_arg(args_str, strlen(args_str), 0, &chip_num); + + if (arg0_result != 0) { + snprintf( + response_output_buf, response_output_buf_len, + "Error parsing chip number argument: %d", arg0_result); + return 1; + } + + uint8_t read_buf[1]; + FLASH_error_enum_t comms_err = FLASH_unblock_block_lock(&hspi1, chip_num, read_buf); + if (comms_err != 0) { + snprintf( + &response_output_buf[strlen(response_output_buf)], + response_output_buf_len - strlen(response_output_buf) - 1, + "Error unblocking block locks: %d",comms_err); + return 2; + } + + // success + snprintf( + &response_output_buf[strlen(response_output_buf)], + response_output_buf_len - strlen(response_output_buf) - 1, + " Success! Result of Block Lock Register: \n 0x%02X\n", + read_buf[0]); + + return 0; +} + /// @brief Telecommand: Read bytes as hex from a flash address /// @param args_str No args. /// @return 0 always @@ -94,7 +133,8 @@ uint8_t TCMDEXEC_flash_each_is_reachable(const char *args_str, TCMD_TelecommandC /// @return 0 on success, >0 on error uint8_t TCMDEXEC_flash_read_hex(const char *args_str, TCMD_TelecommandChannel_enum_t tcmd_channel, char *response_output_buf, uint16_t response_output_buf_len) { - const uint16_t max_num_bytes = 256; + //const uint16_t max_num_bytes = 256; + //const uint16_t max_num_bytes = 2176; uint64_t chip_num, flash_addr, arg_num_bytes; uint8_t arg0_result = TCMD_extract_uint64_arg(args_str, strlen(args_str), 0, &chip_num); @@ -116,7 +156,7 @@ uint8_t TCMDEXEC_flash_read_hex(const char *args_str, TCMD_TelecommandChannel_en FLASH_NUMBER_OF_FLASH_DEVICES - 1); return 2; } - +/* if (arg_num_bytes > max_num_bytes || arg_num_bytes == 0) { snprintf( response_output_buf, response_output_buf_len, @@ -124,8 +164,8 @@ uint8_t TCMDEXEC_flash_read_hex(const char *args_str, TCMD_TelecommandChannel_en (uint32_t)arg_num_bytes, max_num_bytes); // TODO: fix this cast return 3; } - - uint8_t read_buf[max_num_bytes]; +*/ + //uint8_t read_buf[max_num_bytes]; uint32_t num_bytes = (uint32_t)arg_num_bytes; FLASH_error_enum_t result = FLASH_read_data(&hspi1, chip_num, flash_addr, read_buf, num_bytes); @@ -135,7 +175,7 @@ uint8_t TCMDEXEC_flash_read_hex(const char *args_str, TCMD_TelecommandChannel_en "Error reading flash: %d", result); return 4; } - +/* // Convert read data to hex for (uint16_t i = 0; i < num_bytes; i++) { snprintf( @@ -151,7 +191,7 @@ uint8_t TCMDEXEC_flash_read_hex(const char *args_str, TCMD_TelecommandChannel_en "\n"); } } - + */ return 0; } @@ -294,3 +334,27 @@ uint8_t TCMDEXEC_flash_benchmark_erase_write_read(const char *args_str, TCMD_Tel return result; } + +uint8_t TCMDEXEC_flash_reset(const char *args_str, TCMD_TelecommandChannel_enum_t tcmd_channel, + char *response_output_buf, uint16_t response_output_buf_len) { + uint64_t chip_num; + + const uint8_t arg0_result = TCMD_extract_uint64_arg(args_str, strlen(args_str), 0, &chip_num); + + if (arg0_result != 0) { + snprintf( + response_output_buf, response_output_buf_len, + "Error parsing chip number argument: %d", arg0_result); + return 1; + } + + const uint8_t comms_err = FLASH_reset(&hspi1, chip_num); + if (comms_err != 0) { + snprintf( + response_output_buf, response_output_buf_len, + "Error resetting flash chip: %d",comms_err); + return 2; + } + + return comms_err; +} \ No newline at end of file diff --git a/firmware/Core/Src/telecommands/telecommand_definitions.c b/firmware/Core/Src/telecommands/telecommand_definitions.c index 4adc5747f..90244a175 100644 --- a/firmware/Core/Src/telecommands/telecommand_definitions.c +++ b/firmware/Core/Src/telecommands/telecommand_definitions.c @@ -196,6 +196,18 @@ const TCMD_TelecommandDefinition_t TCMD_telecommand_definitions[] = { .number_of_args = 3, .readiness_level = TCMD_READINESS_LEVEL_FLIGHT_TESTING, }, + { + .tcmd_name = "flash_reset", + .tcmd_func = TCMDEXEC_flash_reset, + .number_of_args = 1, + .readiness_level = TCMD_READINESS_LEVEL_IN_PROGRESS, + }, + { + .tcmd_name = "flash_unblock_block_locks", + .tcmd_func = TCMDEXEC_flash_unblock_block_locks, + .number_of_args = 1, + .readiness_level = TCMD_READINESS_LEVEL_FOR_OPERATION, + }, // ****************** END SECTION: flash_telecommand_defs ****************** // ****************** SECTION: lfs_telecommand_defs ****************** From 159e9610b45e71b2d6c33a74839cb138765453b4 Mon Sep 17 00:00:00 2001 From: KaleF07 Date: Sat, 7 Sep 2024 13:26:50 -0700 Subject: [PATCH 04/19] Minor changes to flash telecommands Minor changes to flash read hex telecommand for testing, added docstring for FLASH_reset function and telecommand. --- .../Inc/telecommands/flash_telecommand_defs.h | 2 ++ firmware/Core/Src/littlefs/flash_driver.c | 10 ++++++++-- .../Src/telecommands/flash_telecommand_defs.c | 17 +++++++++++------ 3 files changed, 21 insertions(+), 8 deletions(-) diff --git a/firmware/Core/Inc/telecommands/flash_telecommand_defs.h b/firmware/Core/Inc/telecommands/flash_telecommand_defs.h index dcc333f4b..0e7a2b879 100644 --- a/firmware/Core/Inc/telecommands/flash_telecommand_defs.h +++ b/firmware/Core/Inc/telecommands/flash_telecommand_defs.h @@ -5,6 +5,8 @@ #include #include "telecommands/telecommand_definitions.h" +/*----------------------------- CONFIG VARIABLES ----------------------------- */ +// Maximum number of bytes to read from the flash #define MAX_NUM_BYTES_TO_READ 2048 uint8_t TCMDEXEC_flash_activate_each_cs(const char *args_str, TCMD_TelecommandChannel_enum_t tcmd_channel, diff --git a/firmware/Core/Src/littlefs/flash_driver.c b/firmware/Core/Src/littlefs/flash_driver.c index dcd735367..a90459c95 100644 --- a/firmware/Core/Src/littlefs/flash_driver.c +++ b/firmware/Core/Src/littlefs/flash_driver.c @@ -795,14 +795,14 @@ FLASH_error_enum_t FLASH_read_data(SPI_HandleTypeDef *hspi, uint8_t chip_number, // Set Chip Select HIGH FLASH_deactivate_chip_select(); - +/* DEBUG_uart_print_str("Read data: \n"); DEBUG_uart_print_array_hex(rx_buffer, rx_buffer_len); DEBUG_uart_print_str("\n"); DEBUG_uart_print_str("Length of data read: "); DEBUG_uart_print_uint32((uint32_t)rx_buffer_len); DEBUG_uart_print_str("\n"); - +*/ // TODO: Are there any other errors that can occur while reading? return FLASH_ERR_OK; } @@ -915,6 +915,12 @@ FLASH_error_enum_t FLASH_is_reachable(SPI_HandleTypeDef *hspi, uint8_t chip_numb return FLASH_ERR_OK; // success } +/** + * @brief Resets the NAND flash memory module + * @param hspi - Pointer to the SPI HAL handle + * @param chip_number - The chip select number to activate + * @retval FLASH_ERR_OK on success, <0 on failure + */ FLASH_error_enum_t FLASH_reset(SPI_HandleTypeDef *hspi, uint8_t chip_number) { FLASH_activate_chip_select(chip_number); diff --git a/firmware/Core/Src/telecommands/flash_telecommand_defs.c b/firmware/Core/Src/telecommands/flash_telecommand_defs.c index a20694474..e2e22b337 100644 --- a/firmware/Core/Src/telecommands/flash_telecommand_defs.c +++ b/firmware/Core/Src/telecommands/flash_telecommand_defs.c @@ -156,15 +156,15 @@ uint8_t TCMDEXEC_flash_read_hex(const char *args_str, TCMD_TelecommandChannel_en FLASH_NUMBER_OF_FLASH_DEVICES - 1); return 2; } -/* - if (arg_num_bytes > max_num_bytes || arg_num_bytes == 0) { + + if (arg_num_bytes > MAX_NUM_BYTES_TO_READ || arg_num_bytes == 0) { snprintf( response_output_buf, response_output_buf_len, "Invalid number of bytes to read: %lu. Must be 1 to %d.", - (uint32_t)arg_num_bytes, max_num_bytes); // TODO: fix this cast + (uint32_t)arg_num_bytes, MAX_NUM_BYTES_TO_READ); // TODO: fix this cast return 3; } -*/ + //uint8_t read_buf[max_num_bytes]; uint32_t num_bytes = (uint32_t)arg_num_bytes; FLASH_error_enum_t result = FLASH_read_data(&hspi1, chip_num, flash_addr, read_buf, num_bytes); @@ -175,8 +175,9 @@ uint8_t TCMDEXEC_flash_read_hex(const char *args_str, TCMD_TelecommandChannel_en "Error reading flash: %d", result); return 4; } -/* + // Convert read data to hex + // FIXME: This can't print whole page of data (2048 bytes) for (uint16_t i = 0; i < num_bytes; i++) { snprintf( &response_output_buf[strlen(response_output_buf)], @@ -191,7 +192,7 @@ uint8_t TCMDEXEC_flash_read_hex(const char *args_str, TCMD_TelecommandChannel_en "\n"); } } - */ + return 0; } @@ -335,6 +336,10 @@ uint8_t TCMDEXEC_flash_benchmark_erase_write_read(const char *args_str, TCMD_Tel return result; } +/// @brief Telecommand: Reset the flash memory module. +/// @param args_str +/// - Arg 0: Chip Number (CS number) as uint +/// @return 0 on success, >0 on error uint8_t TCMDEXEC_flash_reset(const char *args_str, TCMD_TelecommandChannel_enum_t tcmd_channel, char *response_output_buf, uint16_t response_output_buf_len) { uint64_t chip_num; From 3022e022e2aaf3c506f674d27a58cfc6dbc98699 Mon Sep 17 00:00:00 2001 From: KaleF07 Date: Tue, 10 Sep 2024 17:38:14 -0700 Subject: [PATCH 05/19] Cleaned code from testing Removed all debugging printing lines to prepare for merging. Added new timeout variable for handling HAL_SPI transmits of 2176 bytes. --- firmware/Core/Src/littlefs/flash_driver.c | 105 +++++------------- .../Src/telecommands/flash_telecommand_defs.c | 3 +- 2 files changed, 28 insertions(+), 80 deletions(-) diff --git a/firmware/Core/Src/littlefs/flash_driver.c b/firmware/Core/Src/littlefs/flash_driver.c index a90459c95..210e56d94 100644 --- a/firmware/Core/Src/littlefs/flash_driver.c +++ b/firmware/Core/Src/littlefs/flash_driver.c @@ -11,6 +11,8 @@ // 512 bytes should take 2ms at 2Mbps. // TODO: ^ investigate the HAL_SPI_Receive overhead (2ms expected, >5ms observed) #define FLASH_HAL_TIMEOUT_MS 10 +// FIXME: For sending or receiving 2176 bytes, the timeout should be >10ms. Created temporary fix for now. +#define FLASH_HAL_MAX_BYTE_TIMEOUT_MS 50 // The following timeout values are sourced from Section 11.3.1, Table 56: "CFI system interface string" // and are interpreted using: https://www.infineon.com/dgdl/Infineon-AN98488_Quick_Guide_to_Common_Flash_Interface-ApplicationNotes-v05_00-EN.pdf @@ -497,13 +499,6 @@ FLASH_error_enum_t FLASH_write_data(SPI_HandleTypeDef *hspi, uint8_t chip_number FLASH_deactivate_chip_select(); return temp; } -/* - DEBUG_uart_print_array_hex(packet_buffer, packet_buffer_len); - DEBUG_uart_print_str("\n"); - DEBUG_uart_print_uint32((uint32_t)packet_buffer_len); - DEBUG_uart_print_str("\n"); -*/ - // DEBUG_uart_print_array_hex(packet_buffer, packet_buffer_len); // Split main address into its 3 bytes uint8_t addr_bytes[3] = {(addr >> 16) & 0xFF, (addr >> 8) & 0xFF, addr & 0xFF}; @@ -513,10 +508,6 @@ FLASH_error_enum_t FLASH_write_data(SPI_HandleTypeDef *hspi, uint8_t chip_number uint16_t cache_addr = 0x0000; uint8_t cache_addr_bytes[2] = {(cache_addr >> 8) & 0xFF, cache_addr & 0xFF}; // modify // check for packet buffer length > 2176 (pg.29 of datasheet, program load) - // 1st byte: op code - // 2nd bye: 1st four bits dummy bytes, 2nd four bits column address - // 3rd byte: rest of column address - //4th - forward: data bits // Send WRITE ENABLE Command const FLASH_error_enum_t wren_result = FLASH_write_enable(hspi, chip_number); @@ -555,8 +546,7 @@ FLASH_error_enum_t FLASH_write_data(SPI_HandleTypeDef *hspi, uint8_t chip_number } // Send the data bytes - // const uint8_t tx_result_3 = HAL_SPI_Transmit(hspi, packet_buffer, packet_buffer_len, FLASH_HAL_TIMEOUT_MS); - const uint8_t tx_result_3 = HAL_SPI_Transmit(hspi, packet_buffer, packet_buffer_len, 50); + const uint8_t tx_result_3 = HAL_SPI_Transmit(hspi, packet_buffer, packet_buffer_len, FLASH_HAL_MAX_BYTE_TIMEOUT_MS); // If couldn't send the bytes, check why if (tx_result_3 != HAL_OK) { @@ -655,15 +645,8 @@ FLASH_error_enum_t FLASH_write_data(SPI_HandleTypeDef *hspi, uint8_t chip_number */ FLASH_error_enum_t FLASH_read_data(SPI_HandleTypeDef *hspi, uint8_t chip_number, lfs_block_t addr, uint8_t *rx_buffer, lfs_size_t rx_buffer_len) { - // uint8_t read_addr_bytes[4] = {(addr >> 24) & 0xFF, (addr >> 16) & 0xFF, (addr >> 8) & 0xFF, addr & 0xFF}; uint8_t read_addr_bytes[3] = {0, (addr >> 8) & 0xFF, addr & 0xFF}; -/* - DEBUG_uart_print_str("Read address bytes: "); - for(int i=0; i<3; i++) { - DEBUG_uart_print_array_hex(&read_addr_bytes[i], 1); - } - DEBUG_uart_print_str("\n\n"); -*/ + // Define the address where data will be read from in cache register (First 4 bits are dummy bits) // TODO: Is it fine to always have this at 0? uint16_t cache_addr = 0x0000; @@ -684,7 +667,6 @@ FLASH_error_enum_t FLASH_read_data(SPI_HandleTypeDef *hspi, uint8_t chip_number, return FLASH_ERR_SPI_TRANSMIT_FAILED; } - // FIXME: Datasheet Page 16 talks about only giving 8-bit dummy values and 16-bit address, not sure how that works // Send Address bytes const HAL_StatusTypeDef tx_result_2 = HAL_SPI_Transmit(hspi, (uint8_t *)read_addr_bytes, 3, FLASH_HAL_TIMEOUT_MS); @@ -717,7 +699,6 @@ FLASH_error_enum_t FLASH_read_data(SPI_HandleTypeDef *hspi, uint8_t chip_number, if ((status_reg_buffer[0] & FLASH_SR1_WRITE_IN_PROGRESS_MASK) == 0) { // Success condition: write in progress has completed. - // return FLASH_ERR_OK; break; } @@ -779,8 +760,7 @@ FLASH_error_enum_t FLASH_read_data(SPI_HandleTypeDef *hspi, uint8_t chip_number, } // Receive the data into the buffer - //const HAL_StatusTypeDef rx_result_1 = HAL_SPI_Receive(hspi, (uint8_t *)rx_buffer, rx_buffer_len, FLASH_HAL_TIMEOUT_MS); - const HAL_StatusTypeDef rx_result_1 = HAL_SPI_Receive(hspi, (uint8_t *)rx_buffer, rx_buffer_len, 50); + const HAL_StatusTypeDef rx_result_1 = HAL_SPI_Receive(hspi, (uint8_t *)rx_buffer, rx_buffer_len, FLASH_HAL_MAX_BYTE_TIMEOUT_MS); // If couldn't receive data, check why if (rx_result_1 != HAL_OK) { @@ -795,41 +775,37 @@ FLASH_error_enum_t FLASH_read_data(SPI_HandleTypeDef *hspi, uint8_t chip_number, // Set Chip Select HIGH FLASH_deactivate_chip_select(); -/* - DEBUG_uart_print_str("Read data: \n"); - DEBUG_uart_print_array_hex(rx_buffer, rx_buffer_len); - DEBUG_uart_print_str("\n"); - DEBUG_uart_print_str("Length of data read: "); - DEBUG_uart_print_uint32((uint32_t)rx_buffer_len); - DEBUG_uart_print_str("\n"); -*/ + // TODO: Are there any other errors that can occur while reading? return FLASH_ERR_OK; } +/** + * @brief Resets the NAND flash memory module + * @param hspi - Pointer to the SPI HAL handle + * @param chip_number - The chip select number to activate + * @retval FLASH_ERR_OK on success, <0 on failure + */ +FLASH_error_enum_t FLASH_reset(SPI_HandleTypeDef *hspi, uint8_t chip_number) +{ + FLASH_activate_chip_select(chip_number); + uint8_t tx_buffer[1] = {FLASH_CMD_RESET}; + HAL_StatusTypeDef tx_result = HAL_SPI_Transmit(hspi, tx_buffer, 1, FLASH_HAL_TIMEOUT_MS); + // If couldn't send the command, check why + if (tx_result != HAL_OK) { + FLASH_deactivate_chip_select(); + if (tx_result == HAL_TIMEOUT) { + return FLASH_ERR_SPI_TRANSMIT_TIMEOUT; + } + return FLASH_ERR_SPI_TRANSMIT_FAILED; + } - - - - - - - - - - - - - - - - - - + return FLASH_ERR_OK; +} /** * @brief Checks if the FLASH chip is reachable by checking it's ID @@ -914,30 +890,3 @@ FLASH_error_enum_t FLASH_is_reachable(SPI_HandleTypeDef *hspi, uint8_t chip_numb } return FLASH_ERR_OK; // success } - -/** - * @brief Resets the NAND flash memory module - * @param hspi - Pointer to the SPI HAL handle - * @param chip_number - The chip select number to activate - * @retval FLASH_ERR_OK on success, <0 on failure - */ -FLASH_error_enum_t FLASH_reset(SPI_HandleTypeDef *hspi, uint8_t chip_number) -{ - FLASH_activate_chip_select(chip_number); - - uint8_t tx_buffer[1] = {FLASH_CMD_RESET}; - HAL_StatusTypeDef tx_result = HAL_SPI_Transmit(hspi, tx_buffer, 1, FLASH_HAL_TIMEOUT_MS); - - // If couldn't send the command, check why - if (tx_result != HAL_OK) { - FLASH_deactivate_chip_select(); - - if (tx_result == HAL_TIMEOUT) { - return FLASH_ERR_SPI_TRANSMIT_TIMEOUT; - } - - return FLASH_ERR_SPI_TRANSMIT_FAILED; - } - - return FLASH_ERR_OK; -} \ No newline at end of file diff --git a/firmware/Core/Src/telecommands/flash_telecommand_defs.c b/firmware/Core/Src/telecommands/flash_telecommand_defs.c index e2e22b337..36c57b862 100644 --- a/firmware/Core/Src/telecommands/flash_telecommand_defs.c +++ b/firmware/Core/Src/telecommands/flash_telecommand_defs.c @@ -165,7 +165,6 @@ uint8_t TCMDEXEC_flash_read_hex(const char *args_str, TCMD_TelecommandChannel_en return 3; } - //uint8_t read_buf[max_num_bytes]; uint32_t num_bytes = (uint32_t)arg_num_bytes; FLASH_error_enum_t result = FLASH_read_data(&hspi1, chip_num, flash_addr, read_buf, num_bytes); @@ -177,7 +176,7 @@ uint8_t TCMDEXEC_flash_read_hex(const char *args_str, TCMD_TelecommandChannel_en } // Convert read data to hex - // FIXME: This can't print whole page of data (2048 bytes) + // FIXME: This can't print whole page of data (2048 bytes). Fix so that it can. for (uint16_t i = 0; i < num_bytes; i++) { snprintf( &response_output_buf[strlen(response_output_buf)], From 3c8b3ac6fe376a5da4bc8582d1778f91d7e5bfe5 Mon Sep 17 00:00:00 2001 From: KaleF07 Date: Thu, 12 Sep 2024 19:46:57 -0700 Subject: [PATCH 06/19] Removed Unblock_block_lock telecommand, Removed the telecommand unblock_block_locks and added automatic execution during write functions, minor changes to other flash telecommands. --- .../Inc/telecommands/flash_telecommand_defs.h | 5 +- firmware/Core/Src/littlefs/flash_driver.c | 28 ++++-- .../Src/telecommands/flash_telecommand_defs.c | 99 +++++++++---------- .../telecommands/telecommand_definitions.c | 6 -- 4 files changed, 63 insertions(+), 75 deletions(-) diff --git a/firmware/Core/Inc/telecommands/flash_telecommand_defs.h b/firmware/Core/Inc/telecommands/flash_telecommand_defs.h index 0e7a2b879..aa643d546 100644 --- a/firmware/Core/Inc/telecommands/flash_telecommand_defs.h +++ b/firmware/Core/Inc/telecommands/flash_telecommand_defs.h @@ -7,7 +7,7 @@ /*----------------------------- CONFIG VARIABLES ----------------------------- */ // Maximum number of bytes to read from the flash -#define MAX_NUM_BYTES_TO_READ 2048 +#define MAX_NUM_BYTES 2048 uint8_t TCMDEXEC_flash_activate_each_cs(const char *args_str, TCMD_TelecommandChannel_enum_t tcmd_channel, char *response_output_buf, uint16_t response_output_buf_len); @@ -29,8 +29,5 @@ uint8_t TCMDEXEC_flash_benchmark_erase_write_read(const char *args_str, TCMD_Tel uint8_t TCMDEXEC_flash_reset(const char *args_str, TCMD_TelecommandChannel_enum_t tcmd_channel, char *response_output_buf, uint16_t response_output_buf_len); - -uint8_t TCMDEXEC_flash_unblock_block_locks(const char *args_str, TCMD_TelecommandChannel_enum_t tcmd_channel, - char *response_output_buf, uint16_t response_output_buf_len); #endif /* __INCLUDE_GUARD__FLASH_TELECOMMAND_DEFS_H__ */ diff --git a/firmware/Core/Src/littlefs/flash_driver.c b/firmware/Core/Src/littlefs/flash_driver.c index 210e56d94..a1aad08aa 100644 --- a/firmware/Core/Src/littlefs/flash_driver.c +++ b/firmware/Core/Src/littlefs/flash_driver.c @@ -99,7 +99,7 @@ void FLASH_deactivate_chip_select() */ FLASH_error_enum_t FLASH_unblock_block_lock(SPI_HandleTypeDef *hspi, uint8_t chip_number, uint8_t *buf) { - static const uint8_t data_bytes = (1 << 1); + static const uint8_t data_bytes = 0x00; // Send SET FEATURES command FLASH_activate_chip_select(chip_number); @@ -399,10 +399,17 @@ FLASH_error_enum_t FLASH_write_disable(SPI_HandleTypeDef *hspi, uint8_t chip_num */ FLASH_error_enum_t FLASH_erase(SPI_HandleTypeDef *hspi, uint8_t chip_number, lfs_block_t addr) { - // Split address into its 4 bytes - // uint8_t addr_bytes[4] = {(addr >> 24) & 0xFF, (addr >> 16) & 0xFF, (addr >> 8) & 0xFF, addr & 0xFF}; + // Split address into its 3 bytes uint8_t addr_bytes[3] = {(addr >> 16) & 0xFF, (addr >> 8) & 0xFF, addr & 0xFF}; + // Set Block Lock Register to 0x00 + uint8_t block_lock_reg_buffer[1] = {0}; + const FLASH_error_enum_t block_lock_result = FLASH_unblock_block_lock(hspi, chip_number, block_lock_reg_buffer); + if (block_lock_result != FLASH_ERR_OK) { + FLASH_deactivate_chip_select(); + return block_lock_result; + } + // Send WRITE ENABLE Command const FLASH_error_enum_t wren_result = FLASH_write_enable(hspi, chip_number); if (wren_result != FLASH_ERR_OK) { @@ -493,13 +500,6 @@ FLASH_error_enum_t FLASH_erase(SPI_HandleTypeDef *hspi, uint8_t chip_number, lfs */ FLASH_error_enum_t FLASH_write_data(SPI_HandleTypeDef *hspi, uint8_t chip_number, lfs_block_t addr, uint8_t *packet_buffer, lfs_size_t packet_buffer_len) { - uint8_t temp_buf[1] = {0}; - const FLASH_error_enum_t temp = FLASH_read_block_lock_register(hspi, chip_number, temp_buf); - if (temp != FLASH_ERR_OK) { - FLASH_deactivate_chip_select(); - return temp; - } - // Split main address into its 3 bytes uint8_t addr_bytes[3] = {(addr >> 16) & 0xFF, (addr >> 8) & 0xFF, addr & 0xFF}; @@ -509,6 +509,14 @@ FLASH_error_enum_t FLASH_write_data(SPI_HandleTypeDef *hspi, uint8_t chip_number uint8_t cache_addr_bytes[2] = {(cache_addr >> 8) & 0xFF, cache_addr & 0xFF}; // modify // check for packet buffer length > 2176 (pg.29 of datasheet, program load) + // Set Block Lock Register to 0x00 + uint8_t block_lock_reg_buffer[1] = {0}; + const FLASH_error_enum_t block_lock_result = FLASH_unblock_block_lock(hspi, chip_number, block_lock_reg_buffer); + if (block_lock_result != FLASH_ERR_OK) { + FLASH_deactivate_chip_select(); + return block_lock_result; + } + // Send WRITE ENABLE Command const FLASH_error_enum_t wren_result = FLASH_write_enable(hspi, chip_number); if (wren_result != FLASH_ERR_OK) { diff --git a/firmware/Core/Src/telecommands/flash_telecommand_defs.c b/firmware/Core/Src/telecommands/flash_telecommand_defs.c index 36c57b862..ce9398104 100644 --- a/firmware/Core/Src/telecommands/flash_telecommand_defs.c +++ b/firmware/Core/Src/telecommands/flash_telecommand_defs.c @@ -10,44 +10,8 @@ #include #include -uint8_t read_buf[MAX_NUM_BYTES_TO_READ]; - -/// @brief Telecommand: Unblock restricted block locks on NAND flash memory module -/// @param args_str -/// - Arg 0: Chip Number (CS number) as uint -/// @return 0 on success, >0 on error -uint8_t TCMDEXEC_flash_unblock_block_locks(const char *args_str, TCMD_TelecommandChannel_enum_t tcmd_channel, - char *response_output_buf, uint16_t response_output_buf_len) { - uint64_t chip_num; - - const uint8_t arg0_result = TCMD_extract_uint64_arg(args_str, strlen(args_str), 0, &chip_num); - - if (arg0_result != 0) { - snprintf( - response_output_buf, response_output_buf_len, - "Error parsing chip number argument: %d", arg0_result); - return 1; - } - - uint8_t read_buf[1]; - FLASH_error_enum_t comms_err = FLASH_unblock_block_lock(&hspi1, chip_num, read_buf); - if (comms_err != 0) { - snprintf( - &response_output_buf[strlen(response_output_buf)], - response_output_buf_len - strlen(response_output_buf) - 1, - "Error unblocking block locks: %d",comms_err); - return 2; - } - - // success - snprintf( - &response_output_buf[strlen(response_output_buf)], - response_output_buf_len - strlen(response_output_buf) - 1, - " Success! Result of Block Lock Register: \n 0x%02X\n", - read_buf[0]); - - return 0; -} +uint8_t read_buf[MAX_NUM_BYTES]; +uint8_t bytes_to_write[MAX_NUM_BYTES]; /// @brief Telecommand: Read bytes as hex from a flash address /// @param args_str No args. @@ -157,11 +121,11 @@ uint8_t TCMDEXEC_flash_read_hex(const char *args_str, TCMD_TelecommandChannel_en return 2; } - if (arg_num_bytes > MAX_NUM_BYTES_TO_READ || arg_num_bytes == 0) { + if (arg_num_bytes > MAX_NUM_BYTES || arg_num_bytes == 0) { snprintf( response_output_buf, response_output_buf_len, "Invalid number of bytes to read: %lu. Must be 1 to %d.", - (uint32_t)arg_num_bytes, MAX_NUM_BYTES_TO_READ); // TODO: fix this cast + (uint32_t)arg_num_bytes, MAX_NUM_BYTES); // TODO: fix this cast return 3; } @@ -204,16 +168,15 @@ uint8_t TCMDEXEC_flash_read_hex(const char *args_str, TCMD_TelecommandChannel_en /// @return 0 on success, >0 on error uint8_t TCMDEXEC_flash_write_hex(const char *args_str, TCMD_TelecommandChannel_enum_t tcmd_channel, char *response_output_buf, uint16_t response_output_buf_len) { - const uint16_t max_num_bytes = 256; uint16_t num_bytes; - uint64_t chip_num, flash_addr_u64; + uint64_t chip_num_u64, flash_addr_u64; - uint8_t bytes_to_write[max_num_bytes]; + // uint8_t bytes_to_write[MAX_NUM_BYTES]; - const uint8_t arg0_result = TCMD_extract_uint64_arg(args_str, strlen(args_str), 0, &chip_num); + const uint8_t arg0_result = TCMD_extract_uint64_arg(args_str, strlen(args_str), 0, &chip_num_u64); const uint8_t arg1_result = TCMD_extract_uint64_arg(args_str, strlen(args_str), 1, &flash_addr_u64); const uint8_t arg2_result = TCMD_extract_hex_array_arg( - args_str, 2, bytes_to_write, max_num_bytes, &num_bytes + args_str, 2, bytes_to_write, MAX_NUM_BYTES, &num_bytes ); if (arg0_result != 0 || arg1_result != 0 || arg2_result != 0) { @@ -224,7 +187,7 @@ uint8_t TCMDEXEC_flash_write_hex(const char *args_str, TCMD_TelecommandChannel_e return 1; } - if (chip_num >= FLASH_NUMBER_OF_FLASH_DEVICES) { + if (chip_num_u64 >= FLASH_NUMBER_OF_FLASH_DEVICES) { snprintf( response_output_buf, response_output_buf_len, "Chip number is out of range. Must be 0 to %d.", @@ -239,9 +202,9 @@ uint8_t TCMDEXEC_flash_write_hex(const char *args_str, TCMD_TelecommandChannel_e FLASH_CHIP_SIZE_BYTES - 1); return 3; } - uint32_t flash_addr = (uint32_t)flash_addr_u64; - + uint8_t chip_num = (uint8_t)chip_num_u64; + uint32_t flash_addr = (uint32_t)flash_addr_u64; FLASH_error_enum_t result = FLASH_write_data(&hspi1, chip_num, flash_addr, bytes_to_write, num_bytes); if (result != 0) { @@ -267,10 +230,10 @@ uint8_t TCMDEXEC_flash_write_hex(const char *args_str, TCMD_TelecommandChannel_e /// @return 0 on success, >0 on error uint8_t TCMDEXEC_flash_erase(const char *args_str, TCMD_TelecommandChannel_enum_t tcmd_channel, char *response_output_buf, uint16_t response_output_buf_len) { - uint64_t chip_num, flash_addr; + uint64_t chip_num_u64, flash_addr_u64; - uint8_t arg0_result = TCMD_extract_uint64_arg(args_str, strlen(args_str), 0, &chip_num); - uint8_t arg1_result = TCMD_extract_uint64_arg(args_str, strlen(args_str), 1, &flash_addr); + uint8_t arg0_result = TCMD_extract_uint64_arg(args_str, strlen(args_str), 0, &chip_num_u64); + uint8_t arg1_result = TCMD_extract_uint64_arg(args_str, strlen(args_str), 1, &flash_addr_u64); if (arg0_result != 0 || arg1_result != 0) { snprintf( @@ -280,7 +243,7 @@ uint8_t TCMDEXEC_flash_erase(const char *args_str, TCMD_TelecommandChannel_enum_ return 1; } - if (chip_num >= FLASH_NUMBER_OF_FLASH_DEVICES) { + if (chip_num_u64 >= FLASH_NUMBER_OF_FLASH_DEVICES) { snprintf( response_output_buf, response_output_buf_len, "Chip number is out of range. Must be 0 to %d.", @@ -288,6 +251,9 @@ uint8_t TCMDEXEC_flash_erase(const char *args_str, TCMD_TelecommandChannel_enum_ return 2; } + uint8_t chip_num = (uint8_t)chip_num_u64; + uint32_t flash_addr = (uint32_t)flash_addr_u64; + FLASH_error_enum_t result = FLASH_erase(&hspi1, chip_num, flash_addr); if (result != 0) { @@ -297,6 +263,13 @@ uint8_t TCMDEXEC_flash_erase(const char *args_str, TCMD_TelecommandChannel_enum_ return 4; } + // success + snprintf( + &response_output_buf[strlen(response_output_buf)], + response_output_buf_len - strlen(response_output_buf) - 1, + " Successfully erased page at address %lu on chip %d.\n", + flash_addr, chip_num); + return 0; } @@ -341,9 +314,9 @@ uint8_t TCMDEXEC_flash_benchmark_erase_write_read(const char *args_str, TCMD_Tel /// @return 0 on success, >0 on error uint8_t TCMDEXEC_flash_reset(const char *args_str, TCMD_TelecommandChannel_enum_t tcmd_channel, char *response_output_buf, uint16_t response_output_buf_len) { - uint64_t chip_num; + uint64_t chip_num_u64; - const uint8_t arg0_result = TCMD_extract_uint64_arg(args_str, strlen(args_str), 0, &chip_num); + const uint8_t arg0_result = TCMD_extract_uint64_arg(args_str, strlen(args_str), 0, &chip_num_u64); if (arg0_result != 0) { snprintf( @@ -352,6 +325,15 @@ uint8_t TCMDEXEC_flash_reset(const char *args_str, TCMD_TelecommandChannel_enum_ return 1; } + if (chip_num_u64 >= FLASH_NUMBER_OF_FLASH_DEVICES) { + snprintf( + response_output_buf, response_output_buf_len, + "Chip number is out of range. Must be 0 to %d.", + FLASH_NUMBER_OF_FLASH_DEVICES - 1); + return 2; + } + + uint8_t chip_num = (uint8_t)chip_num_u64; const uint8_t comms_err = FLASH_reset(&hspi1, chip_num); if (comms_err != 0) { snprintf( @@ -360,5 +342,12 @@ uint8_t TCMDEXEC_flash_reset(const char *args_str, TCMD_TelecommandChannel_enum_ return 2; } - return comms_err; + // success + snprintf( + &response_output_buf[strlen(response_output_buf)], + response_output_buf_len - strlen(response_output_buf) - 1, + " Successfully reset chip %d.\n", + (uint8_t)chip_num); + + return 0; } \ No newline at end of file diff --git a/firmware/Core/Src/telecommands/telecommand_definitions.c b/firmware/Core/Src/telecommands/telecommand_definitions.c index 90244a175..09e14192f 100644 --- a/firmware/Core/Src/telecommands/telecommand_definitions.c +++ b/firmware/Core/Src/telecommands/telecommand_definitions.c @@ -202,12 +202,6 @@ const TCMD_TelecommandDefinition_t TCMD_telecommand_definitions[] = { .number_of_args = 1, .readiness_level = TCMD_READINESS_LEVEL_IN_PROGRESS, }, - { - .tcmd_name = "flash_unblock_block_locks", - .tcmd_func = TCMDEXEC_flash_unblock_block_locks, - .number_of_args = 1, - .readiness_level = TCMD_READINESS_LEVEL_FOR_OPERATION, - }, // ****************** END SECTION: flash_telecommand_defs ****************** // ****************** SECTION: lfs_telecommand_defs ****************** From 8259399942b24ab51a535ffaa72b632ca366fee6 Mon Sep 17 00:00:00 2001 From: parker-research <166864283+parker-research@users.noreply.github.com> Date: Mon, 16 Sep 2024 21:41:26 -0600 Subject: [PATCH 07/19] Update LFS_benchmark_write_read to write many files --- firmware/Core/Src/littlefs/littlefs_benchmark.c | 13 ++++++++++++- firmware/Core/Src/littlefs/littlefs_helper.c | 8 ++++++-- 2 files changed, 18 insertions(+), 3 deletions(-) diff --git a/firmware/Core/Src/littlefs/littlefs_benchmark.c b/firmware/Core/Src/littlefs/littlefs_benchmark.c index a06528740..83872c615 100644 --- a/firmware/Core/Src/littlefs/littlefs_benchmark.c +++ b/firmware/Core/Src/littlefs/littlefs_benchmark.c @@ -14,7 +14,18 @@ /// @param response_str_len /// @return 0 on success. >0 if there was an error. uint8_t LFS_benchmark_write_read(uint16_t write_chunk_size, uint16_t write_chunk_count, char* response_str, uint16_t response_str_len) { - const char file_name[] = "benchmark_test.txt"; + const char dir_name[] = "benchmark_write_read"; + // TODO: check if dir exists first; currently it gives a warning + LFS_make_directory(dir_name); + + char file_name[100]; + snprintf( + file_name, + sizeof(file_name), + "%s/benchmark_test_%lu.txt", + dir_name, + HAL_GetTick() + ); response_str[0] = '\0'; uint8_t expected_checksum = 0; diff --git a/firmware/Core/Src/littlefs/littlefs_helper.c b/firmware/Core/Src/littlefs/littlefs_helper.c index 2b3eaa1ae..cb7ec5ec8 100644 --- a/firmware/Core/Src/littlefs/littlefs_helper.c +++ b/firmware/Core/Src/littlefs/littlefs_helper.c @@ -214,10 +214,14 @@ int8_t LFS_make_directory(const char dir_name[]) return 1; } - int8_t make_dir_result = lfs_mkdir(&LFS_filesystem, dir_name); + const int8_t make_dir_result = lfs_mkdir(&LFS_filesystem, dir_name); if (make_dir_result < 0) { - DEBUG_uart_print_str("Error creating directory.\n"); + LOG_message( + LOG_SYSTEM_LFS, LOG_SEVERITY_WARNING, LOG_SINK_ALL, + "Error %d creating directory.", + make_dir_result + ); return make_dir_result; } From a132979c55588b9cc382103838f4845360517180 Mon Sep 17 00:00:00 2001 From: KaleF07 Date: Wed, 2 Oct 2024 13:17:21 -0700 Subject: [PATCH 08/19] Fixed improper page addressing issue Fixed issue with improper page addressing where littlefs sent page address in bytes rather than the actual page address. --- firmware/Core/Inc/littlefs/flash_driver.h | 9 ++++++--- firmware/Core/Src/littlefs/flash_driver.c | 18 +++++++++--------- firmware/Core/Src/littlefs/littlefs_driver.c | 6 +++--- firmware/Core/Src/littlefs/littlefs_helper.c | 5 +++-- 4 files changed, 21 insertions(+), 17 deletions(-) diff --git a/firmware/Core/Inc/littlefs/flash_driver.h b/firmware/Core/Inc/littlefs/flash_driver.h index 5c51ee6a5..8f97c6d30 100644 --- a/firmware/Core/Inc/littlefs/flash_driver.h +++ b/firmware/Core/Inc/littlefs/flash_driver.h @@ -15,6 +15,9 @@ // Total size of a singular Memory Module in bytes #define FLASH_CHIP_SIZE_BYTES 134217728 // 128MiB // TODO: update +//Number of pages contained within a single block of memory module +#define FLASH_CHIP_PAGES_PER_BLOCK 64 + /*-------------------------------FLASH FEATURES-------------------------------*/ // Features that can be accessed using Get Feature command @@ -74,9 +77,9 @@ FLASH_error_enum_t FLASH_read_status_register(SPI_HandleTypeDef *hspi, uint8_t c FLASH_error_enum_t FLASH_read_block_lock_register(SPI_HandleTypeDef *hspi, uint8_t chip_number, uint8_t *buf); FLASH_error_enum_t FLASH_write_enable(SPI_HandleTypeDef *hspi, uint8_t chip_number); FLASH_error_enum_t FLASH_write_disable(SPI_HandleTypeDef *hspi, uint8_t chip_number); -FLASH_error_enum_t FLASH_erase(SPI_HandleTypeDef *hspi, uint8_t chip_number, lfs_block_t addr); -FLASH_error_enum_t FLASH_write_data(SPI_HandleTypeDef *hspi, uint8_t chip_number, lfs_block_t addr, uint8_t *packet_buffer, lfs_size_t packet_buffer_len); -FLASH_error_enum_t FLASH_read_data(SPI_HandleTypeDef *hspi, uint8_t chip_number, lfs_block_t addr, uint8_t *rx_buffer, lfs_size_t rx_buffer_len); +FLASH_error_enum_t FLASH_erase(SPI_HandleTypeDef *hspi, uint8_t chip_number, lfs_block_t page); +FLASH_error_enum_t FLASH_write_data(SPI_HandleTypeDef *hspi, uint8_t chip_number, lfs_block_t page, uint8_t *packet_buffer, lfs_size_t packet_buffer_len); +FLASH_error_enum_t FLASH_read_data(SPI_HandleTypeDef *hspi, uint8_t chip_number, lfs_block_t page, uint8_t *rx_buffer, lfs_size_t rx_buffer_len); FLASH_error_enum_t FLASH_is_reachable(SPI_HandleTypeDef *hspi, uint8_t chip_number); FLASH_error_enum_t FLASH_reset(SPI_HandleTypeDef *hspi, uint8_t chip_number); diff --git a/firmware/Core/Src/littlefs/flash_driver.c b/firmware/Core/Src/littlefs/flash_driver.c index a1aad08aa..71e5b017a 100644 --- a/firmware/Core/Src/littlefs/flash_driver.c +++ b/firmware/Core/Src/littlefs/flash_driver.c @@ -394,13 +394,13 @@ FLASH_error_enum_t FLASH_write_disable(SPI_HandleTypeDef *hspi, uint8_t chip_num * @brief Sends Block Erase Command * @param hspi - Pointer to the SPI HAL handle * @param chip_number - the chip select number to activate - * @param addr - block address that is to be erased + * @param page - page number to erase the block the page is contained in * @retval FLASH_ERR_OK on success, < 0 on failure */ -FLASH_error_enum_t FLASH_erase(SPI_HandleTypeDef *hspi, uint8_t chip_number, lfs_block_t addr) +FLASH_error_enum_t FLASH_erase(SPI_HandleTypeDef *hspi, uint8_t chip_number, lfs_block_t page) { // Split address into its 3 bytes - uint8_t addr_bytes[3] = {(addr >> 16) & 0xFF, (addr >> 8) & 0xFF, addr & 0xFF}; + uint8_t addr_bytes[3] = {(page >> 16) & 0xFF, (page >> 8) & 0xFF, page & 0xFF}; // Set Block Lock Register to 0x00 uint8_t block_lock_reg_buffer[1] = {0}; @@ -493,15 +493,15 @@ FLASH_error_enum_t FLASH_erase(SPI_HandleTypeDef *hspi, uint8_t chip_number, lfs * @brief Sends Page Program Command * @param hspi - Pointer to the SPI HAL handle * @param chip_number - the chip select number to activate - * @param addr - block address that is to be written + * @param page - page number the data is to be written to * @param packet_buffer - Pointer to buffer containing data to write * @param packet_buffer_len - integer that indicates the size of the data to write * @retval FLASH_ERR_OK on success, < 0 on failure */ -FLASH_error_enum_t FLASH_write_data(SPI_HandleTypeDef *hspi, uint8_t chip_number, lfs_block_t addr, uint8_t *packet_buffer, lfs_size_t packet_buffer_len) +FLASH_error_enum_t FLASH_write_data(SPI_HandleTypeDef *hspi, uint8_t chip_number, lfs_block_t page, uint8_t *packet_buffer, lfs_size_t packet_buffer_len) { // Split main address into its 3 bytes - uint8_t addr_bytes[3] = {(addr >> 16) & 0xFF, (addr >> 8) & 0xFF, addr & 0xFF}; + uint8_t addr_bytes[3] = {(page >> 16) & 0xFF, (page >> 8) & 0xFF, page & 0xFF}; // Define the address where data will be stored in cache register (First 4 bits are dummy bits) // TODO: Is it fine to always have this at 0? @@ -646,14 +646,14 @@ FLASH_error_enum_t FLASH_write_data(SPI_HandleTypeDef *hspi, uint8_t chip_number * @brief Sends Page Read Command * @param hspi - Pointer to the SPI HAL handle * @param chip_number - The chip select number to activate - * @param addr - Address to be read + * @param page - page number to be read * @param rx_buffer - A buffer where the read data will be stored * @param rx_buffer_len - Integer that indicates the capacity of `rx_buffer` * @retval FLASH_ERR_OK on success, < 0 on failure */ -FLASH_error_enum_t FLASH_read_data(SPI_HandleTypeDef *hspi, uint8_t chip_number, lfs_block_t addr, uint8_t *rx_buffer, lfs_size_t rx_buffer_len) +FLASH_error_enum_t FLASH_read_data(SPI_HandleTypeDef *hspi, uint8_t chip_number, lfs_block_t page, uint8_t *rx_buffer, lfs_size_t rx_buffer_len) { - uint8_t read_addr_bytes[3] = {0, (addr >> 8) & 0xFF, addr & 0xFF}; + uint8_t read_addr_bytes[3] = {(page >> 16) & 0xFF, (page >> 8) & 0xFF, page & 0xFF}; // Define the address where data will be read from in cache register (First 4 bits are dummy bits) // TODO: Is it fine to always have this at 0? diff --git a/firmware/Core/Src/littlefs/littlefs_driver.c b/firmware/Core/Src/littlefs/littlefs_driver.c index 811b0ad07..6b10b420a 100644 --- a/firmware/Core/Src/littlefs/littlefs_driver.c +++ b/firmware/Core/Src/littlefs/littlefs_driver.c @@ -21,7 +21,7 @@ int LFS_block_device_read(const struct lfs_config *c, lfs_block_t block, lfs_off return FLASH_read_data( hspi_lfs_ptr, LFS_get_chip_number(block), - (block * c->block_size + off), + (((block * c->block_size) + off)/2048), (uint8_t *)buffer, size ); @@ -37,7 +37,7 @@ int LFS_block_device_prog(const struct lfs_config *c, lfs_block_t block, lfs_off return FLASH_write_data( hspi_lfs_ptr, LFS_get_chip_number(block), - (block * c->block_size + off), + (((block * c->block_size) + off)/2048), (uint8_t *)buffer, size ); @@ -53,7 +53,7 @@ int LFS_block_device_erase(const struct lfs_config *c, lfs_block_t block) return FLASH_erase( hspi_lfs_ptr, LFS_get_chip_number(block), - block * c->block_size + block * FLASH_CHIP_PAGES_PER_BLOCK ); } diff --git a/firmware/Core/Src/littlefs/littlefs_helper.c b/firmware/Core/Src/littlefs/littlefs_helper.c index cb7ec5ec8..411cb2a04 100644 --- a/firmware/Core/Src/littlefs/littlefs_helper.c +++ b/firmware/Core/Src/littlefs/littlefs_helper.c @@ -14,8 +14,9 @@ // Variables to track LittleFS on Flash Memory Module uint8_t LFS_is_lfs_mounted = 0; -#define FLASH_CHIP_PAGE_SIZE_BYTES 2176 -#define FLASH_CHIP_BLOCK_SIZE_BYTES 139264 +// NAND Flash Memory Datasheet https://www.farnell.com/datasheets/3151163.pdf +#define FLASH_CHIP_PAGE_SIZE_BYTES 2048 +#define FLASH_CHIP_BLOCK_SIZE_BYTES FLASH_CHIP_PAGE_SIZE_BYTES * FLASH_CHIP_PAGES_PER_BLOCK #define FLASH_LOOKAHEAD_SIZE 16 // LittleFS Buffers for reading and writing From 60eb9ee6fc6c1b91d9b77f213d54677bfcabb834 Mon Sep 17 00:00:00 2001 From: KaleF07 Date: Thu, 3 Oct 2024 14:45:47 -0700 Subject: [PATCH 09/19] Minor changes based on PR review Removed unnecessary lines of code and added additional helpful comments based on PR comments --- firmware/Core/Inc/telecommands/flash_telecommand_defs.h | 3 ++- firmware/Core/Src/littlefs/littlefs_driver.c | 4 ++-- firmware/Core/Src/littlefs/littlefs_helper.c | 1 + firmware/Core/Src/telecommands/flash_telecommand_defs.c | 4 ---- 4 files changed, 5 insertions(+), 7 deletions(-) diff --git a/firmware/Core/Inc/telecommands/flash_telecommand_defs.h b/firmware/Core/Inc/telecommands/flash_telecommand_defs.h index aa643d546..2773169dc 100644 --- a/firmware/Core/Inc/telecommands/flash_telecommand_defs.h +++ b/firmware/Core/Inc/telecommands/flash_telecommand_defs.h @@ -6,7 +6,8 @@ #include "telecommands/telecommand_definitions.h" /*----------------------------- CONFIG VARIABLES ----------------------------- */ -// Maximum number of bytes to read from the flash +// NAND Flash Memory Datasheet https://www.farnell.com/datasheets/3151163.pdf (pg.7) +// Each page is divided into a 2048-byte data storage region, and a 128 bytes spare area (2176 bytes total). #define MAX_NUM_BYTES 2048 uint8_t TCMDEXEC_flash_activate_each_cs(const char *args_str, TCMD_TelecommandChannel_enum_t tcmd_channel, diff --git a/firmware/Core/Src/littlefs/littlefs_driver.c b/firmware/Core/Src/littlefs/littlefs_driver.c index 6b10b420a..f8d0c6859 100644 --- a/firmware/Core/Src/littlefs/littlefs_driver.c +++ b/firmware/Core/Src/littlefs/littlefs_driver.c @@ -21,7 +21,7 @@ int LFS_block_device_read(const struct lfs_config *c, lfs_block_t block, lfs_off return FLASH_read_data( hspi_lfs_ptr, LFS_get_chip_number(block), - (((block * c->block_size) + off)/2048), + ((block * c->block_size) + off)/2048, (uint8_t *)buffer, size ); @@ -37,7 +37,7 @@ int LFS_block_device_prog(const struct lfs_config *c, lfs_block_t block, lfs_off return FLASH_write_data( hspi_lfs_ptr, LFS_get_chip_number(block), - (((block * c->block_size) + off)/2048), + ((block * c->block_size) + off)/2048, (uint8_t *)buffer, size ); diff --git a/firmware/Core/Src/littlefs/littlefs_helper.c b/firmware/Core/Src/littlefs/littlefs_helper.c index 411cb2a04..cca4483aa 100644 --- a/firmware/Core/Src/littlefs/littlefs_helper.c +++ b/firmware/Core/Src/littlefs/littlefs_helper.c @@ -15,6 +15,7 @@ uint8_t LFS_is_lfs_mounted = 0; // NAND Flash Memory Datasheet https://www.farnell.com/datasheets/3151163.pdf +// Each page is divided into a 2048-byte data storage region, and a 128 bytes spare area (2176 bytes total). #define FLASH_CHIP_PAGE_SIZE_BYTES 2048 #define FLASH_CHIP_BLOCK_SIZE_BYTES FLASH_CHIP_PAGE_SIZE_BYTES * FLASH_CHIP_PAGES_PER_BLOCK #define FLASH_LOOKAHEAD_SIZE 16 diff --git a/firmware/Core/Src/telecommands/flash_telecommand_defs.c b/firmware/Core/Src/telecommands/flash_telecommand_defs.c index ce9398104..2b0021725 100644 --- a/firmware/Core/Src/telecommands/flash_telecommand_defs.c +++ b/firmware/Core/Src/telecommands/flash_telecommand_defs.c @@ -97,8 +97,6 @@ uint8_t TCMDEXEC_flash_each_is_reachable(const char *args_str, TCMD_TelecommandC /// @return 0 on success, >0 on error uint8_t TCMDEXEC_flash_read_hex(const char *args_str, TCMD_TelecommandChannel_enum_t tcmd_channel, char *response_output_buf, uint16_t response_output_buf_len) { - //const uint16_t max_num_bytes = 256; - //const uint16_t max_num_bytes = 2176; uint64_t chip_num, flash_addr, arg_num_bytes; uint8_t arg0_result = TCMD_extract_uint64_arg(args_str, strlen(args_str), 0, &chip_num); @@ -171,8 +169,6 @@ uint8_t TCMDEXEC_flash_write_hex(const char *args_str, TCMD_TelecommandChannel_e uint16_t num_bytes; uint64_t chip_num_u64, flash_addr_u64; - // uint8_t bytes_to_write[MAX_NUM_BYTES]; - const uint8_t arg0_result = TCMD_extract_uint64_arg(args_str, strlen(args_str), 0, &chip_num_u64); const uint8_t arg1_result = TCMD_extract_uint64_arg(args_str, strlen(args_str), 1, &flash_addr_u64); const uint8_t arg2_result = TCMD_extract_hex_array_arg( From 70bea08c708075d2edffa69b1f1391c9e1471913 Mon Sep 17 00:00:00 2001 From: Saksham Puri <84263133+Saksham-P@users.noreply.github.com> Date: Sun, 6 Oct 2024 17:33:12 -0600 Subject: [PATCH 10/19] Created List Directory telecommand Current version of this telecommand doesn't store the directory information anywhere yet, only sends it through UART through debugging. --- .../Inc/telecommands/lfs_telecommand_defs.h | 3 ++ firmware/Core/Src/littlefs/littlefs_helper.c | 48 ++++++++++--------- .../Src/telecommands/lfs_telecommand_defs.c | 28 ++++++++++- .../telecommands/telecommand_definitions.c | 6 +++ 4 files changed, 62 insertions(+), 23 deletions(-) diff --git a/firmware/Core/Inc/telecommands/lfs_telecommand_defs.h b/firmware/Core/Inc/telecommands/lfs_telecommand_defs.h index cc0cdf810..d513ab155 100644 --- a/firmware/Core/Inc/telecommands/lfs_telecommand_defs.h +++ b/firmware/Core/Inc/telecommands/lfs_telecommand_defs.h @@ -14,6 +14,9 @@ uint8_t TCMDEXEC_fs_mount(const char *args_str, TCMD_TelecommandChannel_enum_t t uint8_t TCMDEXEC_fs_unmount(const char *args_str, TCMD_TelecommandChannel_enum_t tcmd_channel, char *response_output_buf, uint16_t response_output_buf_len); +uint8_t TCMDEXEC_fs_list_directory(const char *args_str, TCMD_TelecommandChannel_enum_t tcmd_channel, + char *response_output_buf, uint16_t response_output_buf_len); + uint8_t TCMDEXEC_fs_write_file(const char *args_str, TCMD_TelecommandChannel_enum_t tcmd_channel, char *response_output_buf, uint16_t response_output_buf_len); diff --git a/firmware/Core/Src/littlefs/littlefs_helper.c b/firmware/Core/Src/littlefs/littlefs_helper.c index cca4483aa..85314ae25 100644 --- a/firmware/Core/Src/littlefs/littlefs_helper.c +++ b/firmware/Core/Src/littlefs/littlefs_helper.c @@ -1,5 +1,3 @@ - - /*-----------------------------INCLUDES-----------------------------*/ #include @@ -39,7 +37,7 @@ struct lfs_config LFS_cfg = { // block device configuration .read_size = FLASH_CHIP_PAGE_SIZE_BYTES, .prog_size = FLASH_CHIP_PAGE_SIZE_BYTES, - .block_size = FLASH_CHIP_BLOCK_SIZE_BYTES, // FIXME: Clarify block Size 256KiB or 1KiB + .block_size = FLASH_CHIP_BLOCK_SIZE_BYTES, .block_count = (FLASH_CHIP_SIZE_BYTES / FLASH_CHIP_BLOCK_SIZE_BYTES), .block_cycles = 100, // TODO: ASK ABOUT THIS (HOW FREQUENT ARE WE USING THE MODULE), .cache_size = FLASH_CHIP_PAGE_SIZE_BYTES, @@ -57,7 +55,6 @@ struct lfs_file_config LFS_file_cfg = { // -----------------------------LITTLEFS FUNCTIONS----------------------------- - /** * @brief Formats Memory Module so it can successfully mount LittleFS * @param None @@ -65,14 +62,14 @@ struct lfs_file_config LFS_file_cfg = { */ int8_t LFS_format() { - int8_t result = lfs_format(&LFS_filesystem, &LFS_cfg); - if (result < 0) + int8_t format_result = lfs_format(&LFS_filesystem, &LFS_cfg); + if (format_result < 0) { - DEBUG_uart_print_str("Error formatting!\n"); - return result; + LOG_message(LOG_SYSTEM_LFS, LOG_SEVERITY_CRITICAL, LOG_all_sinks_except(LOG_SINK_FILE), "Error formatting FLASH memory!"); + return format_result; } - DEBUG_uart_print_str("Formatting successful!\n"); + LOG_message(LOG_SYSTEM_LFS, LOG_SEVERITY_NORMAL, LOG_all_sinks_except(LOG_SINK_FILE), "FLASH Memory formatting successful!"); return 0; } @@ -83,8 +80,9 @@ int8_t LFS_format() */ int8_t LFS_mount() { - if (LFS_is_lfs_mounted) { - DEBUG_uart_print_str("LittleFS already mounted!\n"); + if (LFS_is_lfs_mounted) + { + LOG_message(LOG_SYSTEM_LFS, LOG_SEVERITY_WARNING, LOG_all_sinks_except(LOG_SINK_FILE), "LittleFS already mounted!"); return 1; } @@ -92,11 +90,11 @@ int8_t LFS_mount() int8_t mount_result = lfs_mount(&LFS_filesystem, &LFS_cfg); if (mount_result < 0) { - DEBUG_uart_print_str("Mounting unsuccessful\n"); + LOG_message(LOG_SYSTEM_LFS, LOG_SEVERITY_CRITICAL, LOG_all_sinks_except(LOG_SINK_FILE), "Error mounting LittleFS!"); return mount_result; } - DEBUG_uart_print_str("Mounting successful\n"); + LOG_message(LOG_SYSTEM_LFS, LOG_SEVERITY_NORMAL, LOG_all_sinks_except(LOG_SINK_FILE), "LittleFS mounting successful!"); LFS_is_lfs_mounted = 1; return 0; } @@ -110,7 +108,7 @@ int8_t LFS_unmount() { if (!LFS_is_lfs_mounted) { - DEBUG_uart_print_str("LittleFS not mounted.\n"); + LOG_message(LOG_SYSTEM_LFS, LOG_SEVERITY_WARNING, LOG_all_sinks_except(LOG_SINK_FILE), "LittleFS not mounted!"); return 1; } @@ -118,11 +116,11 @@ int8_t LFS_unmount() const int8_t unmount_result = lfs_unmount(&LFS_filesystem); if (unmount_result < 0) { - DEBUG_uart_print_str("Error un-mounting.\n"); + LOG_message(LOG_SYSTEM_LFS, LOG_SEVERITY_CRITICAL, LOG_all_sinks_except(LOG_SINK_FILE), "Error un-mounting LittleFS!"); return unmount_result; } - DEBUG_uart_print_str("Successfully un-mounted LittleFS.\n"); + LOG_message(LOG_SYSTEM_LFS, LOG_SEVERITY_NORMAL, LOG_all_sinks_except(LOG_SINK_FILE), "LittleFS un-mounting successful!"); LFS_is_lfs_mounted = 0; return 0; } @@ -136,7 +134,7 @@ int8_t LFS_list_directory(const char root_directory[]) { if (!LFS_is_lfs_mounted) { - DEBUG_uart_print_str("LittleFS not mounted.\n"); + LOG_message(LOG_SYSTEM_LFS, LOG_SEVERITY_WARNING, LOG_all_sinks_except(LOG_SINK_FILE), "LittleFS not mounted!"); return 1; } @@ -144,22 +142,28 @@ int8_t LFS_list_directory(const char root_directory[]) int8_t open_dir_result = lfs_dir_open(&LFS_filesystem, &dir, root_directory); if (open_dir_result < 0) { - DEBUG_uart_print_str("Error opening a directory.\n"); + LOG_message(LOG_SYSTEM_LFS, LOG_SEVERITY_CRITICAL, LOG_all_sinks_except(LOG_SINK_FILE), "Error opening directory: %s", root_directory); return open_dir_result; } - // result is positive on success, 0 at the end of directory, or negative on failure. + // result is positive on success, 0 at the end of directory, or negative on failure. int8_t read_dir_result = 1; - while (read_dir_result >= 0) + DEBUG_uart_print_str("Name \t bytes\n"); + while (read_dir_result > 0) { struct lfs_info info; read_dir_result = lfs_dir_read(&LFS_filesystem, &dir, &info); DEBUG_uart_print_str(info.name); - DEBUG_uart_print_str(", "); + if (info.type == LFS_TYPE_REG) + { + DEBUG_uart_print_str("\t"); + DEBUG_uart_print_uint32(info.size); + DEBUG_uart_print_str(" bytes"); + } + DEBUG_uart_print_str("\n"); // TODO: The info struct contains information about directory contents } - DEBUG_uart_print_str("\n"); if (read_dir_result < 0) { diff --git a/firmware/Core/Src/telecommands/lfs_telecommand_defs.c b/firmware/Core/Src/telecommands/lfs_telecommand_defs.c index d3c56b0d3..437f88412 100644 --- a/firmware/Core/Src/telecommands/lfs_telecommand_defs.c +++ b/firmware/Core/Src/telecommands/lfs_telecommand_defs.c @@ -11,7 +11,6 @@ #include "telecommands/telecommand_definitions.h" #include "telecommands/telecommand_args_helpers.h" - uint8_t TCMDEXEC_fs_format_storage(const char *args_str, TCMD_TelecommandChannel_enum_t tcmd_channel, char *response_output_buf, uint16_t response_output_buf_len) { int8_t result = LFS_format(); @@ -48,6 +47,33 @@ uint8_t TCMDEXEC_fs_unmount(const char *args_str, TCMD_TelecommandChannel_enum_t return 0; } +/// @brief Telecommand: List all the files and directories within a root directory +/// @param args_str +/// - Arg 0: Root Directory path as string +uint8_t TCMDEXEC_fs_list_directory(const char *args_str, TCMD_TelecommandChannel_enum_t tcmd_channel, + char *response_output_buf, uint16_t response_output_buf_len) { + + char arg_root_directory_path[64] = {0}; //TODO: Directory name could be up to 255 bytes by default + const uint8_t parse_directory_path_result = TCMD_extract_string_arg(args_str, 0, arg_root_directory_path, sizeof(arg_root_directory_path)); + if (parse_directory_path_result != 0) { + // error parsing + snprintf( + response_output_buf, + response_output_buf_len, + "Error parsing directory path arg: Error %d", parse_directory_path_result); + return 1; + } + + int8_t list_directory_result = LFS_list_directory(arg_root_directory_path); + if (list_directory_result < 0) { + snprintf(response_output_buf, response_output_buf_len, "LittleFS List Directory Error: %d\n", list_directory_result); + return 1; + } + + // snprintf(response_output_buf, response_output_buf_len, "LittleFS Successfully Unounted!\n"); + return 0; +} + /// @brief Telecommand: Write data to a file in LittleFS /// @param args_str /// - Arg 0: File path as string diff --git a/firmware/Core/Src/telecommands/telecommand_definitions.c b/firmware/Core/Src/telecommands/telecommand_definitions.c index d3137e0f3..bdef34755 100644 --- a/firmware/Core/Src/telecommands/telecommand_definitions.c +++ b/firmware/Core/Src/telecommands/telecommand_definitions.c @@ -223,6 +223,12 @@ const TCMD_TelecommandDefinition_t TCMD_telecommand_definitions[] = { .number_of_args = 0, .readiness_level = TCMD_READINESS_LEVEL_FOR_OPERATION, }, + { + .tcmd_name = "fs_list_directory", + .tcmd_func = TCMDEXEC_fs_list_directory, + .number_of_args = 1, + .readiness_level = TCMD_READINESS_LEVEL_FOR_OPERATION, + }, { .tcmd_name = "fs_write_file", .tcmd_func = TCMDEXEC_fs_write_file, From 9ef3de5d730870025dd618a2464d16faa49a459b Mon Sep 17 00:00:00 2001 From: Saksham Puri <84263133+Saksham-P@users.noreply.github.com> Date: Tue, 15 Oct 2024 20:14:53 -0600 Subject: [PATCH 11/19] Added Telecommand to make a directory Added a telecommand for creating a directory and updated warning if trying to create a directory that already exists --- .../Inc/telecommands/lfs_telecommand_defs.h | 3 ++ firmware/Core/Src/littlefs/littlefs_helper.c | 13 +++++++-- .../Src/telecommands/lfs_telecommand_defs.c | 29 ++++++++++++++++++- .../telecommands/telecommand_definitions.c | 6 ++++ 4 files changed, 47 insertions(+), 4 deletions(-) diff --git a/firmware/Core/Inc/telecommands/lfs_telecommand_defs.h b/firmware/Core/Inc/telecommands/lfs_telecommand_defs.h index d513ab155..cb0342046 100644 --- a/firmware/Core/Inc/telecommands/lfs_telecommand_defs.h +++ b/firmware/Core/Inc/telecommands/lfs_telecommand_defs.h @@ -17,6 +17,9 @@ uint8_t TCMDEXEC_fs_unmount(const char *args_str, TCMD_TelecommandChannel_enum_t uint8_t TCMDEXEC_fs_list_directory(const char *args_str, TCMD_TelecommandChannel_enum_t tcmd_channel, char *response_output_buf, uint16_t response_output_buf_len); +uint8_t TCMDEXEC_fs_make_directory(const char *args_str, TCMD_TelecommandChannel_enum_t tcmd_channel, + char *response_output_buf, uint16_t response_output_buf_len); + uint8_t TCMDEXEC_fs_write_file(const char *args_str, TCMD_TelecommandChannel_enum_t tcmd_channel, char *response_output_buf, uint16_t response_output_buf_len); diff --git a/firmware/Core/Src/littlefs/littlefs_helper.c b/firmware/Core/Src/littlefs/littlefs_helper.c index 85314ae25..01b632dff 100644 --- a/firmware/Core/Src/littlefs/littlefs_helper.c +++ b/firmware/Core/Src/littlefs/littlefs_helper.c @@ -162,7 +162,6 @@ int8_t LFS_list_directory(const char root_directory[]) DEBUG_uart_print_str(" bytes"); } DEBUG_uart_print_str("\n"); - // TODO: The info struct contains information about directory contents } if (read_dir_result < 0) @@ -223,11 +222,19 @@ int8_t LFS_make_directory(const char dir_name[]) const int8_t make_dir_result = lfs_mkdir(&LFS_filesystem, dir_name); if (make_dir_result < 0) { - LOG_message( + if (make_dir_result == LFS_ERR_EXIST) { + LOG_message( + LOG_SYSTEM_LFS, LOG_SEVERITY_WARNING, LOG_SINK_ALL, + "Directory %d already exists.", + make_dir_result + ); + } else { + LOG_message( LOG_SYSTEM_LFS, LOG_SEVERITY_WARNING, LOG_SINK_ALL, "Error %d creating directory.", make_dir_result - ); + ); + } return make_dir_result; } diff --git a/firmware/Core/Src/telecommands/lfs_telecommand_defs.c b/firmware/Core/Src/telecommands/lfs_telecommand_defs.c index fe1b69730..161fef0f8 100644 --- a/firmware/Core/Src/telecommands/lfs_telecommand_defs.c +++ b/firmware/Core/Src/telecommands/lfs_telecommand_defs.c @@ -47,7 +47,7 @@ uint8_t TCMDEXEC_fs_unmount(const char *args_str, TCMD_TelecommandChannel_enum_t return 0; } -/// @brief Telecommand: List all the files and directories within a root directory +/// @brief Telecommand: List all the files and directories within a given directory /// @param args_str /// - Arg 0: Root Directory path as string uint8_t TCMDEXEC_fs_list_directory(const char *args_str, TCMD_TelecommandChannel_enum_t tcmd_channel, @@ -74,6 +74,33 @@ uint8_t TCMDEXEC_fs_list_directory(const char *args_str, TCMD_TelecommandChannel return 0; } +/// @brief Telecommand: Create a directory +/// @param args_str +/// - Arg 0: Directory Name +uint8_t TCMDEXEC_fs_make_directory(const char *args_str, TCMD_TelecommandChannel_enum_t tcmd_channel, + char *response_output_buf, uint16_t response_output_buf_len) { + + char arg_root_directory_path[64] = {0}; //TODO: Directory name could be up to 255 bytes by default + const uint8_t parse_directory_path_result = TCMD_extract_string_arg(args_str, 0, arg_root_directory_path, sizeof(arg_root_directory_path)); + if (parse_directory_path_result != 0) { + // error parsing + snprintf( + response_output_buf, + response_output_buf_len, + "Error parsing directory path arg: Error %d", parse_directory_path_result); + return 1; + } + + int8_t make_directory_result = LFS_make_directory(arg_root_directory_path); + if (make_directory_result < 0) { + snprintf(response_output_buf, response_output_buf_len, "LittleFS Make Directory Error: %d\n", make_directory_result); + return 1; + } + + // snprintf(response_output_buf, response_output_buf_len, "LittleFS Successfully Unounted!\n"); + return 0; +} + /// @brief Telecommand: Write data to a file in LittleFS /// @param args_str /// - Arg 0: File path as string diff --git a/firmware/Core/Src/telecommands/telecommand_definitions.c b/firmware/Core/Src/telecommands/telecommand_definitions.c index bdef34755..febc22016 100644 --- a/firmware/Core/Src/telecommands/telecommand_definitions.c +++ b/firmware/Core/Src/telecommands/telecommand_definitions.c @@ -229,6 +229,12 @@ const TCMD_TelecommandDefinition_t TCMD_telecommand_definitions[] = { .number_of_args = 1, .readiness_level = TCMD_READINESS_LEVEL_FOR_OPERATION, }, + { + .tcmd_name = "fs_make_directory", + .tcmd_func = TCMDEXEC_fs_make_directory, + .number_of_args = 1, + .readiness_level = TCMD_READINESS_LEVEL_FOR_OPERATION, + }, { .tcmd_name = "fs_write_file", .tcmd_func = TCMDEXEC_fs_write_file, From 95bea18c295ab0cbb047a96e884a10089b7ff134 Mon Sep 17 00:00:00 2001 From: Saksham Puri <84263133+Saksham-P@users.noreply.github.com> Date: Thu, 17 Oct 2024 18:48:30 -0600 Subject: [PATCH 12/19] Added offset and count for list directory function --- firmware/Core/Inc/littlefs/littlefs_helper.h | 4 +- firmware/Core/Src/littlefs/littlefs_helper.c | 70 ++++++++++++------- .../Src/telecommands/lfs_telecommand_defs.c | 24 ++++++- .../telecommands/telecommand_definitions.c | 2 +- 4 files changed, 70 insertions(+), 30 deletions(-) diff --git a/firmware/Core/Inc/littlefs/littlefs_helper.h b/firmware/Core/Inc/littlefs/littlefs_helper.h index 26caca3f0..8874e6e6b 100644 --- a/firmware/Core/Inc/littlefs/littlefs_helper.h +++ b/firmware/Core/Inc/littlefs/littlefs_helper.h @@ -24,9 +24,9 @@ extern uint8_t LFS_is_lfs_mounted; int8_t LFS_format(); int8_t LFS_mount(); int8_t LFS_unmount(); -int8_t LFS_list_directory(const char root_directory[]); -int8_t LFS_delete_file(const char file_name[]); +int8_t LFS_list_directory(const char root_directory[], uint16_t offset, int16_t count); int8_t LFS_make_directory(const char dir_name[]); +int8_t LFS_delete_file(const char file_name[]); int8_t LFS_write_file(const char file_name[], uint8_t *write_buffer, uint32_t write_buffer_len); int8_t LFS_append_file(const char file_name[], uint8_t *write_buffer, uint32_t write_buffer_len); lfs_ssize_t LFS_read_file(const char file_name[], lfs_soff_t offset, uint8_t *read_buffer, uint32_t read_buffer_len); diff --git a/firmware/Core/Src/littlefs/littlefs_helper.c b/firmware/Core/Src/littlefs/littlefs_helper.c index 01b632dff..1fa54786a 100644 --- a/firmware/Core/Src/littlefs/littlefs_helper.c +++ b/firmware/Core/Src/littlefs/littlefs_helper.c @@ -127,10 +127,12 @@ int8_t LFS_unmount() /** * @brief Lists contents of LittleFS Directory - * @param root_directory Pointer to cstring holding the root directory to open and read + * @param root_directory Pointer to cstring holding the root directory to open and read + * @param offset Number of entries to skip before listing directory + * @param count Number of entries to list in total (if 0, prints all entries) * @retval 0 on success, 1 if LFS is unmounted, negative LFS error codes on failure */ -int8_t LFS_list_directory(const char root_directory[]) +int8_t LFS_list_directory(const char root_directory[], uint16_t offset, int16_t count) { if (!LFS_is_lfs_mounted) { @@ -146,14 +148,30 @@ int8_t LFS_list_directory(const char root_directory[]) return open_dir_result; } + if (count == 0) { + count = -1; + } + // result is positive on success, 0 at the end of directory, or negative on failure. int8_t read_dir_result = 1; DEBUG_uart_print_str("Name \t bytes\n"); while (read_dir_result > 0) { + struct lfs_info info; read_dir_result = lfs_dir_read(&LFS_filesystem, &dir, &info); + if (offset > 0) { + offset--; + continue; + } + + if (count == 0) { + break; + } else { + count--; + } + DEBUG_uart_print_str(info.name); if (info.type == LFS_TYPE_REG) { @@ -182,30 +200,6 @@ int8_t LFS_list_directory(const char root_directory[]) return 0; } -/** - * @brief Removes / deletes the file specified - * @param file_name Pointer to cstring holding the file name to remove - * @retval 0 on success, 1 if LFS is unmounted, negative LFS error codes on failure - */ -int8_t LFS_delete_file(const char file_name[]) -{ - if (!LFS_is_lfs_mounted) - { - DEBUG_uart_print_str("LittleFS not mounted.\n"); - return 1; - } - - int8_t remove_result = lfs_remove(&LFS_filesystem, file_name); - if (remove_result < 0) - { - DEBUG_uart_print_str("Error removing file/directory.\n"); - return remove_result; - } - - DEBUG_uart_print_str("Successfully removed file/directory.\n"); - return 0; -} - /** * @brief Creates directory * @param dir_name Pointer to cstring holding the name of the directory @@ -242,6 +236,30 @@ int8_t LFS_make_directory(const char dir_name[]) return 0; } +/** + * @brief Removes / deletes the file specified + * @param file_name Pointer to cstring holding the file name to remove + * @retval 0 on success, 1 if LFS is unmounted, negative LFS error codes on failure + */ +int8_t LFS_delete_file(const char file_name[]) +{ + if (!LFS_is_lfs_mounted) + { + DEBUG_uart_print_str("LittleFS not mounted.\n"); + return 1; + } + + int8_t remove_result = lfs_remove(&LFS_filesystem, file_name); + if (remove_result < 0) + { + DEBUG_uart_print_str("Error removing file/directory.\n"); + return remove_result; + } + + DEBUG_uart_print_str("Successfully removed file/directory.\n"); + return 0; +} + /** * @brief Creates / Opens LittleFS File to write to the Memory Module * @param file_name - Pointer to cstring holding the file name to create or open diff --git a/firmware/Core/Src/telecommands/lfs_telecommand_defs.c b/firmware/Core/Src/telecommands/lfs_telecommand_defs.c index 161fef0f8..05b5b3778 100644 --- a/firmware/Core/Src/telecommands/lfs_telecommand_defs.c +++ b/firmware/Core/Src/telecommands/lfs_telecommand_defs.c @@ -64,7 +64,29 @@ uint8_t TCMDEXEC_fs_list_directory(const char *args_str, TCMD_TelecommandChannel return 1; } - int8_t list_directory_result = LFS_list_directory(arg_root_directory_path); + uint64_t arg_listing_offset = 0; + const uint8_t parse_listing_offset_result = TCMD_extract_uint64_arg(args_str, strlen(args_str), 1, &arg_listing_offset); + if (parse_listing_offset_result != 0) { + // error parsing + snprintf( + response_output_buf, + response_output_buf_len, + "Error parsing offset arg: Error %d", parse_listing_offset_result); + return 1; + } + + uint64_t arg_listing_count = 0; + const uint8_t parse_listing_count_result = TCMD_extract_uint64_arg(args_str, strlen(args_str), 2, &arg_listing_count); + if (parse_listing_count_result != 0) { + // error parsing + snprintf( + response_output_buf, + response_output_buf_len, + "Error parsing count arg: Error %d", parse_listing_count_result); + return 1; + } + + int8_t list_directory_result = LFS_list_directory(arg_root_directory_path, (uint16_t) arg_listing_offset, (int16_t) arg_listing_count); if (list_directory_result < 0) { snprintf(response_output_buf, response_output_buf_len, "LittleFS List Directory Error: %d\n", list_directory_result); return 1; diff --git a/firmware/Core/Src/telecommands/telecommand_definitions.c b/firmware/Core/Src/telecommands/telecommand_definitions.c index febc22016..be1d5fcad 100644 --- a/firmware/Core/Src/telecommands/telecommand_definitions.c +++ b/firmware/Core/Src/telecommands/telecommand_definitions.c @@ -226,7 +226,7 @@ const TCMD_TelecommandDefinition_t TCMD_telecommand_definitions[] = { { .tcmd_name = "fs_list_directory", .tcmd_func = TCMDEXEC_fs_list_directory, - .number_of_args = 1, + .number_of_args = 3, .readiness_level = TCMD_READINESS_LEVEL_FOR_OPERATION, }, { From 00a0ae98f3b471a0361e69d4ec597079a1945d30 Mon Sep 17 00:00:00 2001 From: Saksham Puri <84263133+Saksham-P@users.noreply.github.com> Date: Sat, 19 Oct 2024 18:00:19 -0600 Subject: [PATCH 13/19] Added documentation for list directory telecommand --- firmware/Core/Src/littlefs/littlefs_helper.c | 5 +++-- firmware/Core/Src/telecommands/lfs_telecommand_defs.c | 4 +++- 2 files changed, 6 insertions(+), 3 deletions(-) diff --git a/firmware/Core/Src/littlefs/littlefs_helper.c b/firmware/Core/Src/littlefs/littlefs_helper.c index 1fa54786a..a22c55727 100644 --- a/firmware/Core/Src/littlefs/littlefs_helper.c +++ b/firmware/Core/Src/littlefs/littlefs_helper.c @@ -134,12 +134,14 @@ int8_t LFS_unmount() */ int8_t LFS_list_directory(const char root_directory[], uint16_t offset, int16_t count) { + // Check if LFS is mounted if (!LFS_is_lfs_mounted) { LOG_message(LOG_SYSTEM_LFS, LOG_SEVERITY_WARNING, LOG_all_sinks_except(LOG_SINK_FILE), "LittleFS not mounted!"); return 1; } + // Try to open the directory lfs_dir_t dir; int8_t open_dir_result = lfs_dir_open(&LFS_filesystem, &dir, root_directory); if (open_dir_result < 0) @@ -154,11 +156,10 @@ int8_t LFS_list_directory(const char root_directory[], uint16_t offset, int16_t // result is positive on success, 0 at the end of directory, or negative on failure. int8_t read_dir_result = 1; + struct lfs_info info; DEBUG_uart_print_str("Name \t bytes\n"); while (read_dir_result > 0) { - - struct lfs_info info; read_dir_result = lfs_dir_read(&LFS_filesystem, &dir, &info); if (offset > 0) { diff --git a/firmware/Core/Src/telecommands/lfs_telecommand_defs.c b/firmware/Core/Src/telecommands/lfs_telecommand_defs.c index 05b5b3778..f9184d2cd 100644 --- a/firmware/Core/Src/telecommands/lfs_telecommand_defs.c +++ b/firmware/Core/Src/telecommands/lfs_telecommand_defs.c @@ -50,6 +50,8 @@ uint8_t TCMDEXEC_fs_unmount(const char *args_str, TCMD_TelecommandChannel_enum_t /// @brief Telecommand: List all the files and directories within a given directory /// @param args_str /// - Arg 0: Root Directory path as string +/// - Arg 1: (Offset) Number of entries to skip at the beginning +/// - Arg 2: (Count) Number entries to display uint8_t TCMDEXEC_fs_list_directory(const char *args_str, TCMD_TelecommandChannel_enum_t tcmd_channel, char *response_output_buf, uint16_t response_output_buf_len) { @@ -98,7 +100,7 @@ uint8_t TCMDEXEC_fs_list_directory(const char *args_str, TCMD_TelecommandChannel /// @brief Telecommand: Create a directory /// @param args_str -/// - Arg 0: Directory Name +/// - Arg 0: Directory Name as string uint8_t TCMDEXEC_fs_make_directory(const char *args_str, TCMD_TelecommandChannel_enum_t tcmd_channel, char *response_output_buf, uint16_t response_output_buf_len) { From b33e0439fd281fb70cff0c569fb29426f1c1aeea Mon Sep 17 00:00:00 2001 From: Saksham Puri <84263133+Saksham-P@users.noreply.github.com> Date: Sat, 19 Oct 2024 18:02:17 -0600 Subject: [PATCH 14/19] Added Name into Contributors list --- README.md | 1 + 1 file changed, 1 insertion(+) diff --git a/README.md b/README.md index fcf048f8a..0c6bc9a87 100644 --- a/README.md +++ b/README.md @@ -19,6 +19,7 @@ Please add your name to the list below in your first Pull Request! * Marko V. * Vaibhav K. * Muhammad Ali +* Saksham P. ## License and Libraries From 7970e943ddcce748f9eeb343f87be987ac3d6a36 Mon Sep 17 00:00:00 2001 From: Saksham Puri <84263133+Saksham-P@users.noreply.github.com> Date: Fri, 25 Oct 2024 18:09:28 -0600 Subject: [PATCH 15/19] Updated List Directory Algorithm Added Break statement within while loop if error reading a directory entry, and return the error after closing the directory --- firmware/Core/Src/littlefs/littlefs_helper.c | 22 +++++++++++++------- 1 file changed, 14 insertions(+), 8 deletions(-) diff --git a/firmware/Core/Src/littlefs/littlefs_helper.c b/firmware/Core/Src/littlefs/littlefs_helper.c index a22c55727..5272e4281 100644 --- a/firmware/Core/Src/littlefs/littlefs_helper.c +++ b/firmware/Core/Src/littlefs/littlefs_helper.c @@ -127,7 +127,7 @@ int8_t LFS_unmount() /** * @brief Lists contents of LittleFS Directory - * @param root_directory Pointer to cstring holding the root directory to open and read + * @param root_directory cstring holding the root directory to open and read * @param offset Number of entries to skip before listing directory * @param count Number of entries to list in total (if 0, prints all entries) * @retval 0 on success, 1 if LFS is unmounted, negative LFS error codes on failure @@ -162,6 +162,12 @@ int8_t LFS_list_directory(const char root_directory[], uint16_t offset, int16_t { read_dir_result = lfs_dir_read(&LFS_filesystem, &dir, &info); + if (read_dir_result < 0) + { + DEBUG_uart_print_str("Error reading directory contents.\n"); + break; + } + if (offset > 0) { offset--; continue; @@ -183,14 +189,10 @@ int8_t LFS_list_directory(const char root_directory[], uint16_t offset, int16_t DEBUG_uart_print_str("\n"); } - if (read_dir_result < 0) - { - DEBUG_uart_print_str("Error reading directory contents.\n"); - return read_dir_result; + if (read_dir_result >= 0) { + DEBUG_uart_print_str("Successfully Listed Directory Contents.\n"); } - DEBUG_uart_print_str("Successfully Listed Directory Contents.\n"); - int8_t close_dir_result = lfs_dir_close(&LFS_filesystem, &dir); if (close_dir_result < 0) { @@ -198,7 +200,11 @@ int8_t LFS_list_directory(const char root_directory[], uint16_t offset, int16_t return close_dir_result; } - return 0; + if (read_dir_result < 0) { + return read_dir_result; + } else { + return 0; + } } /** From 1b2d0535a139b6dcfeb159b639c9931eccb85fdb Mon Sep 17 00:00:00 2001 From: Saksham Puri <84263133+Saksham-P@users.noreply.github.com> Date: Tue, 12 Nov 2024 18:05:50 -0700 Subject: [PATCH 16/19] Added LOG_message for littlefs_helper functions All functions have some coverage of LOG_message, some don't have it entirely as they are needed to print useful information to the serial --- firmware/Core/Src/littlefs/littlefs_helper.c | 133 +++++++++--------- .../Src/telecommands/lfs_telecommand_defs.c | 2 - 2 files changed, 68 insertions(+), 67 deletions(-) diff --git a/firmware/Core/Src/littlefs/littlefs_helper.c b/firmware/Core/Src/littlefs/littlefs_helper.c index 5272e4281..17f0d18c1 100644 --- a/firmware/Core/Src/littlefs/littlefs_helper.c +++ b/firmware/Core/Src/littlefs/littlefs_helper.c @@ -63,13 +63,14 @@ struct lfs_file_config LFS_file_cfg = { int8_t LFS_format() { int8_t format_result = lfs_format(&LFS_filesystem, &LFS_cfg); - if (format_result < 0) - { + if (format_result < 0) { LOG_message(LOG_SYSTEM_LFS, LOG_SEVERITY_CRITICAL, LOG_all_sinks_except(LOG_SINK_FILE), "Error formatting FLASH memory!"); return format_result; } - LOG_message(LOG_SYSTEM_LFS, LOG_SEVERITY_NORMAL, LOG_all_sinks_except(LOG_SINK_FILE), "FLASH Memory formatting successful!"); + if (LFS_enable_hot_path_debug_logs) { + LOG_message(LOG_SYSTEM_LFS, LOG_SEVERITY_NORMAL, LOG_all_sinks_except(LOG_SINK_FILE), "FLASH Memory formatting successful!"); + } return 0; } @@ -80,21 +81,22 @@ int8_t LFS_format() */ int8_t LFS_mount() { - if (LFS_is_lfs_mounted) - { + if (LFS_is_lfs_mounted) { LOG_message(LOG_SYSTEM_LFS, LOG_SEVERITY_WARNING, LOG_all_sinks_except(LOG_SINK_FILE), "LittleFS already mounted!"); return 1; } // Variable to store status of LittleFS mounting int8_t mount_result = lfs_mount(&LFS_filesystem, &LFS_cfg); - if (mount_result < 0) - { + if (mount_result < 0) { LOG_message(LOG_SYSTEM_LFS, LOG_SEVERITY_CRITICAL, LOG_all_sinks_except(LOG_SINK_FILE), "Error mounting LittleFS!"); return mount_result; } - LOG_message(LOG_SYSTEM_LFS, LOG_SEVERITY_NORMAL, LOG_all_sinks_except(LOG_SINK_FILE), "LittleFS mounting successful!"); + if (LFS_enable_hot_path_debug_logs) { + LOG_message(LOG_SYSTEM_LFS, LOG_SEVERITY_NORMAL, LOG_all_sinks_except(LOG_SINK_FILE), "LittleFS mounting successful!"); + } + LFS_is_lfs_mounted = 1; return 0; } @@ -106,9 +108,8 @@ int8_t LFS_mount() */ int8_t LFS_unmount() { - if (!LFS_is_lfs_mounted) - { - LOG_message(LOG_SYSTEM_LFS, LOG_SEVERITY_WARNING, LOG_all_sinks_except(LOG_SINK_FILE), "LittleFS not mounted!"); + if (!LFS_is_lfs_mounted) { + LOG_message(LOG_SYSTEM_LFS, LOG_SEVERITY_CRITICAL, LOG_all_sinks_except(LOG_SINK_FILE), "LittleFS not mounted!"); return 1; } @@ -135,9 +136,8 @@ int8_t LFS_unmount() int8_t LFS_list_directory(const char root_directory[], uint16_t offset, int16_t count) { // Check if LFS is mounted - if (!LFS_is_lfs_mounted) - { - LOG_message(LOG_SYSTEM_LFS, LOG_SEVERITY_WARNING, LOG_all_sinks_except(LOG_SINK_FILE), "LittleFS not mounted!"); + if (!LFS_is_lfs_mounted) { + LOG_message(LOG_SYSTEM_LFS, LOG_SEVERITY_WARNING, LOG_all_sinks_except(LOG_SINK_FILE), "LittleFS not mounted."); return 1; } @@ -165,6 +165,7 @@ int8_t LFS_list_directory(const char root_directory[], uint16_t offset, int16_t if (read_dir_result < 0) { DEBUG_uart_print_str("Error reading directory contents.\n"); + LOG_message(LOG_SYSTEM_LFS, LOG_SEVERITY_CRITICAL, LOG_all_sinks_except(LOG_SINK_FILE), "Error reading content from directory: %s", root_directory); break; } @@ -189,20 +190,19 @@ int8_t LFS_list_directory(const char root_directory[], uint16_t offset, int16_t DEBUG_uart_print_str("\n"); } - if (read_dir_result >= 0) { - DEBUG_uart_print_str("Successfully Listed Directory Contents.\n"); - } - int8_t close_dir_result = lfs_dir_close(&LFS_filesystem, &dir); if (close_dir_result < 0) { DEBUG_uart_print_str("Error closing directory.\n"); + LOG_message(LOG_SYSTEM_LFS, LOG_SEVERITY_CRITICAL, LOG_all_sinks_except(LOG_SINK_FILE), "Error closing directory: %s", root_directory); return close_dir_result; } if (read_dir_result < 0) { return read_dir_result; } else { + DEBUG_uart_print_str("Successfully Listed Directory Contents.\n"); + LOG_message(LOG_SYSTEM_LFS, LOG_SEVERITY_NORMAL, LOG_all_sinks_except(LOG_SINK_FILE), "Successfully listed contents from directory: %s", root_directory); return 0; } } @@ -216,7 +216,7 @@ int8_t LFS_make_directory(const char dir_name[]) { if (!LFS_is_lfs_mounted) { - DEBUG_uart_print_str("LittleFS not mounted.\n"); + LOG_message(LOG_SYSTEM_LFS, LOG_SEVERITY_WARNING, LOG_all_sinks_except(LOG_SINK_FILE), "LittleFS not mounted!"); return 1; } @@ -224,22 +224,16 @@ int8_t LFS_make_directory(const char dir_name[]) if (make_dir_result < 0) { if (make_dir_result == LFS_ERR_EXIST) { - LOG_message( - LOG_SYSTEM_LFS, LOG_SEVERITY_WARNING, LOG_SINK_ALL, - "Directory %d already exists.", - make_dir_result - ); + LOG_message(LOG_SYSTEM_LFS, LOG_SEVERITY_WARNING, LOG_all_sinks_except(LOG_SINK_FILE), + "Directory %s already exists.", dir_name); } else { - LOG_message( - LOG_SYSTEM_LFS, LOG_SEVERITY_WARNING, LOG_SINK_ALL, - "Error %d creating directory.", - make_dir_result - ); + LOG_message(LOG_SYSTEM_LFS, LOG_SEVERITY_WARNING, LOG_all_sinks_except(LOG_SINK_FILE), + "Recieved error: %d while creating directory: %s.", make_dir_result, dir_name); } return make_dir_result; } - DEBUG_uart_print_str("Successfully created directory.\n"); + LOG_message(LOG_SYSTEM_LFS, LOG_SEVERITY_NORMAL, LOG_all_sinks_except(LOG_SINK_FILE), "Successfully created directory: %s", dir_name); return 0; } @@ -252,18 +246,18 @@ int8_t LFS_delete_file(const char file_name[]) { if (!LFS_is_lfs_mounted) { - DEBUG_uart_print_str("LittleFS not mounted.\n"); + LOG_message(LOG_SYSTEM_LFS, LOG_SEVERITY_WARNING, LOG_all_sinks_except(LOG_SINK_FILE), "LittleFS not mounted."); return 1; } int8_t remove_result = lfs_remove(&LFS_filesystem, file_name); if (remove_result < 0) { - DEBUG_uart_print_str("Error removing file/directory.\n"); + LOG_message(LOG_SYSTEM_LFS, LOG_SEVERITY_WARNING, LOG_all_sinks_except(LOG_SINK_FILE), "Error removing file / directory: %s", file_name); return remove_result; } - DEBUG_uart_print_str("Successfully removed file/directory.\n"); + LOG_message(LOG_SYSTEM_LFS, LOG_SEVERITY_NORMAL, LOG_all_sinks_except(LOG_SINK_FILE), "Successfully removed file / directory: %s", file_name); return 0; } @@ -278,7 +272,7 @@ int8_t LFS_write_file(const char file_name[], uint8_t *write_buffer, uint32_t wr { if (!LFS_is_lfs_mounted) { - DEBUG_uart_print_str("LittleFS not mounted.\n"); + LOG_message(LOG_SYSTEM_LFS, LOG_SEVERITY_WARNING, LOG_all_sinks_except(LOG_SINK_FILE), "LittleFS not mounted."); return 1; } @@ -288,7 +282,7 @@ int8_t LFS_write_file(const char file_name[], uint8_t *write_buffer, uint32_t wr if (open_result < 0) { - DEBUG_uart_print_str("Error opening/creating file.\n"); + LOG_message(LOG_SYSTEM_LFS, LOG_SEVERITY_WARNING, LOG_all_sinks_except(LOG_SINK_FILE), "Error opening / creating file: %s", file_name); return open_result; } @@ -302,25 +296,22 @@ int8_t LFS_write_file(const char file_name[], uint8_t *write_buffer, uint32_t wr const int8_t write_result = lfs_file_write(&LFS_filesystem, &file, write_buffer, write_buffer_len); if (write_result < 0) { - DEBUG_uart_print_str("Error writing to file!\n"); + LOG_message(LOG_SYSTEM_LFS, LOG_SEVERITY_WARNING, LOG_all_sinks_except(LOG_SINK_FILE), "Error writing to file: %s", file_name); return write_result; } - - if (LFS_enable_hot_path_debug_logs) { - DEBUG_uart_print_str("Successfully wrote data to file!\n"); - } // Close the File, the storage is not updated until the file is closed successfully const int8_t close_result = lfs_file_close(&LFS_filesystem, &file); if (close_result < 0) { - DEBUG_uart_print_str("Error closing the file!\n"); + LOG_message(LOG_SYSTEM_LFS, LOG_SEVERITY_WARNING, LOG_all_sinks_except(LOG_SINK_FILE), "Error closing file: %s", file_name); return close_result; } if (LFS_enable_hot_path_debug_logs) { DEBUG_uart_print_str("Successfully closed the file!\n"); } + LOG_message(LOG_SYSTEM_LFS, LOG_SEVERITY_WARNING, LOG_all_sinks_except(LOG_SINK_FILE), "Successfully wrote data to file: %s", file_name); return 0; } @@ -345,28 +336,26 @@ int8_t LFS_append_file(const char file_name[], uint8_t *write_buffer, uint32_t w if (open_result < 0) { - LOG_message(LOG_SYSTEM_LFS, LOG_SEVERITY_CRITICAL, LOG_all_sinks_except(LOG_SINK_FILE), "Error opening file"); + LOG_message(LOG_SYSTEM_LFS, LOG_SEVERITY_CRITICAL, LOG_all_sinks_except(LOG_SINK_FILE), "Error opening file: %s", file_name); return open_result; } const int8_t seek_result = lfs_file_seek(&LFS_filesystem, &file, 0, LFS_SEEK_END); if (seek_result < 0) { - LOG_message(LOG_SYSTEM_LFS, LOG_SEVERITY_CRITICAL, LOG_all_sinks_except(LOG_SINK_FILE), "Error seeking within file"); + LOG_message(LOG_SYSTEM_LFS, LOG_SEVERITY_CRITICAL, LOG_all_sinks_except(LOG_SINK_FILE), "Error seeking within file: %s", file_name); return seek_result; } const int8_t write_result = lfs_file_write(&LFS_filesystem, &file, write_buffer, write_buffer_len); - if (write_result < 0) - { - LOG_message(LOG_SYSTEM_LFS, LOG_SEVERITY_CRITICAL, LOG_all_sinks_except(LOG_SINK_FILE), "Error writing to file"); + if (write_result < 0) { + LOG_message(LOG_SYSTEM_LFS, LOG_SEVERITY_CRITICAL, LOG_all_sinks_except(LOG_SINK_FILE), "Error writing to file %s", file_name); return write_result; } // Close the File, the storage is not updated until the file is closed successfully const int8_t close_result = lfs_file_close(&LFS_filesystem, &file); - if (close_result < 0) - { - LOG_message(LOG_SYSTEM_LFS, LOG_SEVERITY_CRITICAL, LOG_all_sinks_except(LOG_SINK_FILE), "Error closing file"); + if (close_result < 0) { + LOG_message(LOG_SYSTEM_LFS, LOG_SEVERITY_CRITICAL, LOG_all_sinks_except(LOG_SINK_FILE), "Error closing file: %s", file_name); return close_result; } @@ -384,48 +373,50 @@ int8_t LFS_append_file(const char file_name[], uint8_t *write_buffer, uint32_t w */ lfs_ssize_t LFS_read_file(const char file_name[], lfs_soff_t offset, uint8_t *read_buffer, uint32_t read_buffer_len) { + if (!LFS_is_lfs_mounted) + { + LOG_message(LOG_SYSTEM_LFS, LOG_SEVERITY_CRITICAL, LOG_all_sinks_except(LOG_SINK_FILE), "LittleFS not mounted"); + return 1; + } + lfs_file_t file; const int8_t open_result = lfs_file_opencfg(&LFS_filesystem, &file, file_name, LFS_O_RDONLY, &LFS_file_cfg); if (open_result < 0) { // TODO: confirm behaviour is desired: this assumes filesystem as a // whole as an issue, so does not send log message to file - LOG_message(LOG_SYSTEM_LFS, LOG_SEVERITY_CRITICAL, LOG_all_sinks_except(LOG_SINK_FILE), "Error opening file to read"); + LOG_message(LOG_SYSTEM_LFS, LOG_SEVERITY_CRITICAL, LOG_all_sinks_except(LOG_SINK_FILE), "Error opening file to read: %s", file_name); return open_result; } - if (LFS_enable_hot_path_debug_logs) { - LOG_message(LOG_SYSTEM_LFS, LOG_SEVERITY_CRITICAL, LOG_SINK_ALL, "Opened file to read: %s", file_name); + LOG_message(LOG_SYSTEM_LFS, LOG_SEVERITY_NORMAL, LOG_all_sinks_except(LOG_SINK_FILE), "Opened file to read: %s", file_name); } const lfs_soff_t seek_result = lfs_file_seek(&LFS_filesystem, &file, offset, LFS_SEEK_SET); if (seek_result < 0) { - LOG_message(LOG_SYSTEM_LFS, LOG_SEVERITY_CRITICAL, LOG_all_sinks_except(LOG_SINK_FILE), "Error seeking within file"); + LOG_message(LOG_SYSTEM_LFS, LOG_SEVERITY_CRITICAL, LOG_all_sinks_except(LOG_SINK_FILE), "Error seeking within file: %s", file_name); return seek_result; } const lfs_ssize_t read_result = lfs_file_read(&LFS_filesystem, &file, read_buffer, read_buffer_len); if (read_result < 0) { - LOG_message(LOG_SYSTEM_LFS, LOG_SEVERITY_CRITICAL, LOG_all_sinks_except(LOG_SINK_FILE), "Error reading file"); + LOG_message(LOG_SYSTEM_LFS, LOG_SEVERITY_CRITICAL, LOG_all_sinks_except(LOG_SINK_FILE), "Error reading file: %s", file_name); return read_result; } - if (LFS_enable_hot_path_debug_logs) { - LOG_message(LOG_SYSTEM_LFS, LOG_SEVERITY_CRITICAL, LOG_SINK_ALL, "Successfully read file"); + LOG_message(LOG_SYSTEM_LFS, LOG_SEVERITY_NORMAL, LOG_all_sinks_except(LOG_SINK_FILE), "Successfully read file: %s", file_name); } // Close the File, the storage is not updated until the file is closed successfully const int8_t close_result = lfs_file_close(&LFS_filesystem, &file); - if (close_result < 0) - { - LOG_message(LOG_SYSTEM_LFS, LOG_SEVERITY_CRITICAL, LOG_all_sinks_except(LOG_SINK_FILE), "Error closing file"); + if (close_result < 0) { + LOG_message(LOG_SYSTEM_LFS, LOG_SEVERITY_CRITICAL, LOG_all_sinks_except(LOG_SINK_FILE), "Error closing file: %s", file_name); return close_result; } - if (LFS_enable_hot_path_debug_logs) { - LOG_message(LOG_SYSTEM_LFS, LOG_SEVERITY_CRITICAL, LOG_all_sinks_except(LOG_SINK_FILE), "Successfully close file"); + LOG_message(LOG_SYSTEM_LFS, LOG_SEVERITY_NORMAL, LOG_all_sinks_except(LOG_SINK_FILE), "Successfully closed file: %s", file_name); } return read_result; @@ -439,18 +430,30 @@ lfs_ssize_t LFS_read_file(const char file_name[], lfs_soff_t offset, uint8_t *re */ lfs_ssize_t LFS_file_size(const char file_name[]) { + if (!LFS_is_lfs_mounted) { + LOG_message(LOG_SYSTEM_LFS, LOG_SEVERITY_CRITICAL, LOG_all_sinks_except(LOG_SINK_FILE), "LittleFS not mounted"); + return 1; + } + lfs_file_t file; const int8_t open_result = lfs_file_opencfg(&LFS_filesystem, &file, file_name, LFS_O_RDONLY, &LFS_file_cfg); if (open_result < 0) { - LOG_message(LOG_SYSTEM_LFS, LOG_SEVERITY_CRITICAL, LOG_all_sinks_except(LOG_SINK_FILE), "Error opening file"); + LOG_message(LOG_SYSTEM_LFS, LOG_SEVERITY_CRITICAL, LOG_all_sinks_except(LOG_SINK_FILE), "Error opening file: %s", file_name); return open_result; } + if (LFS_enable_hot_path_debug_logs) { + LOG_message(LOG_SYSTEM_LFS, LOG_SEVERITY_NORMAL, LOG_all_sinks_except(LOG_SINK_FILE), "Successfully opened file: %s", file_name); + } + const lfs_ssize_t size = lfs_file_size(&LFS_filesystem, &file); + const int8_t close_result = lfs_file_close(&LFS_filesystem, &file); if (close_result < 0) { - LOG_message(LOG_SYSTEM_LFS, LOG_SEVERITY_CRITICAL, LOG_all_sinks_except(LOG_SINK_FILE), "Error closing file"); + LOG_message(LOG_SYSTEM_LFS, LOG_SEVERITY_CRITICAL, LOG_all_sinks_except(LOG_SINK_FILE), "Error closing file: %s", file_name); return close_result; } + if (LFS_enable_hot_path_debug_logs) { + LOG_message(LOG_SYSTEM_LFS, LOG_SEVERITY_NORMAL, LOG_all_sinks_except(LOG_SINK_FILE), "Successfully closed file: %s", file_name); + } return size; -} - +} \ No newline at end of file diff --git a/firmware/Core/Src/telecommands/lfs_telecommand_defs.c b/firmware/Core/Src/telecommands/lfs_telecommand_defs.c index f9184d2cd..74ed94f45 100644 --- a/firmware/Core/Src/telecommands/lfs_telecommand_defs.c +++ b/firmware/Core/Src/telecommands/lfs_telecommand_defs.c @@ -94,7 +94,6 @@ uint8_t TCMDEXEC_fs_list_directory(const char *args_str, TCMD_TelecommandChannel return 1; } - // snprintf(response_output_buf, response_output_buf_len, "LittleFS Successfully Unounted!\n"); return 0; } @@ -121,7 +120,6 @@ uint8_t TCMDEXEC_fs_make_directory(const char *args_str, TCMD_TelecommandChannel return 1; } - // snprintf(response_output_buf, response_output_buf_len, "LittleFS Successfully Unounted!\n"); return 0; } From 80631bc368a0b9db0069a2f4cee14609e15394e5 Mon Sep 17 00:00:00 2001 From: Saksham Puri <84263133+Saksham-P@users.noreply.github.com> Date: Tue, 3 Dec 2024 17:35:40 -0700 Subject: [PATCH 17/19] Converted to Space Indenting --- firmware/Core/Src/littlefs/littlefs_helper.c | 156 +++++++++---------- 1 file changed, 78 insertions(+), 78 deletions(-) diff --git a/firmware/Core/Src/littlefs/littlefs_helper.c b/firmware/Core/Src/littlefs/littlefs_helper.c index 17f0d18c1..1245a07c1 100644 --- a/firmware/Core/Src/littlefs/littlefs_helper.c +++ b/firmware/Core/Src/littlefs/littlefs_helper.c @@ -62,16 +62,16 @@ struct lfs_file_config LFS_file_cfg = { */ int8_t LFS_format() { - int8_t format_result = lfs_format(&LFS_filesystem, &LFS_cfg); - if (format_result < 0) { + int8_t format_result = lfs_format(&LFS_filesystem, &LFS_cfg); + if (format_result < 0) { LOG_message(LOG_SYSTEM_LFS, LOG_SEVERITY_CRITICAL, LOG_all_sinks_except(LOG_SINK_FILE), "Error formatting FLASH memory!"); - return format_result; - } - + return format_result; + } + if (LFS_enable_hot_path_debug_logs) { - LOG_message(LOG_SYSTEM_LFS, LOG_SEVERITY_NORMAL, LOG_all_sinks_except(LOG_SINK_FILE), "FLASH Memory formatting successful!"); + LOG_message(LOG_SYSTEM_LFS, LOG_SEVERITY_NORMAL, LOG_all_sinks_except(LOG_SINK_FILE), "FLASH Memory formatting successful!"); } - return 0; + return 0; } /** @@ -81,10 +81,10 @@ int8_t LFS_format() */ int8_t LFS_mount() { - if (LFS_is_lfs_mounted) { + if (LFS_is_lfs_mounted) { LOG_message(LOG_SYSTEM_LFS, LOG_SEVERITY_WARNING, LOG_all_sinks_except(LOG_SINK_FILE), "LittleFS already mounted!"); - return 1; - } + return 1; + } // Variable to store status of LittleFS mounting int8_t mount_result = lfs_mount(&LFS_filesystem, &LFS_cfg); @@ -94,7 +94,7 @@ int8_t LFS_mount() } if (LFS_enable_hot_path_debug_logs) { - LOG_message(LOG_SYSTEM_LFS, LOG_SEVERITY_NORMAL, LOG_all_sinks_except(LOG_SINK_FILE), "LittleFS mounting successful!"); + LOG_message(LOG_SYSTEM_LFS, LOG_SEVERITY_NORMAL, LOG_all_sinks_except(LOG_SINK_FILE), "LittleFS mounting successful!"); } LFS_is_lfs_mounted = 1; @@ -280,40 +280,40 @@ int8_t LFS_write_file(const char file_name[], uint8_t *write_buffer, uint32_t wr lfs_file_t file; const int8_t open_result = lfs_file_opencfg(&LFS_filesystem, &file, file_name, LFS_O_WRONLY | LFS_O_CREAT | LFS_O_TRUNC, &LFS_file_cfg); - if (open_result < 0) - { - LOG_message(LOG_SYSTEM_LFS, LOG_SEVERITY_WARNING, LOG_all_sinks_except(LOG_SINK_FILE), "Error opening / creating file: %s", file_name); - return open_result; - } - + if (open_result < 0) + { + LOG_message(LOG_SYSTEM_LFS, LOG_SEVERITY_WARNING, LOG_all_sinks_except(LOG_SINK_FILE), "Error opening / creating file: %s", file_name); + return open_result; + } + if (LFS_enable_hot_path_debug_logs) { DEBUG_uart_print_str("Opened/created a file named: '"); DEBUG_uart_print_str(file_name); DEBUG_uart_print_str("'\n"); } - // Write data to file - const int8_t write_result = lfs_file_write(&LFS_filesystem, &file, write_buffer, write_buffer_len); - if (write_result < 0) - { - LOG_message(LOG_SYSTEM_LFS, LOG_SEVERITY_WARNING, LOG_all_sinks_except(LOG_SINK_FILE), "Error writing to file: %s", file_name); - return write_result; - } - - // Close the File, the storage is not updated until the file is closed successfully - const int8_t close_result = lfs_file_close(&LFS_filesystem, &file); - if (close_result < 0) - { - LOG_message(LOG_SYSTEM_LFS, LOG_SEVERITY_WARNING, LOG_all_sinks_except(LOG_SINK_FILE), "Error closing file: %s", file_name); - return close_result; - } - + // Write data to file + const int8_t write_result = lfs_file_write(&LFS_filesystem, &file, write_buffer, write_buffer_len); + if (write_result < 0) + { + LOG_message(LOG_SYSTEM_LFS, LOG_SEVERITY_WARNING, LOG_all_sinks_except(LOG_SINK_FILE), "Error writing to file: %s", file_name); + return write_result; + } + + // Close the File, the storage is not updated until the file is closed successfully + const int8_t close_result = lfs_file_close(&LFS_filesystem, &file); + if (close_result < 0) + { + LOG_message(LOG_SYSTEM_LFS, LOG_SEVERITY_WARNING, LOG_all_sinks_except(LOG_SINK_FILE), "Error closing file: %s", file_name); + return close_result; + } + if (LFS_enable_hot_path_debug_logs) { - DEBUG_uart_print_str("Successfully closed the file!\n"); + DEBUG_uart_print_str("Successfully closed the file!\n"); } LOG_message(LOG_SYSTEM_LFS, LOG_SEVERITY_WARNING, LOG_all_sinks_except(LOG_SINK_FILE), "Successfully wrote data to file: %s", file_name); - return 0; + return 0; } /** @@ -334,32 +334,32 @@ int8_t LFS_append_file(const char file_name[], uint8_t *write_buffer, uint32_t w lfs_file_t file; const int8_t open_result = lfs_file_opencfg(&LFS_filesystem, &file, file_name, LFS_O_WRONLY | LFS_O_CREAT | LFS_O_APPEND, &LFS_file_cfg); - if (open_result < 0) - { + if (open_result < 0) + { LOG_message(LOG_SYSTEM_LFS, LOG_SEVERITY_CRITICAL, LOG_all_sinks_except(LOG_SINK_FILE), "Error opening file: %s", file_name); - return open_result; - } - + return open_result; + } + const int8_t seek_result = lfs_file_seek(&LFS_filesystem, &file, 0, LFS_SEEK_END); if (seek_result < 0) { LOG_message(LOG_SYSTEM_LFS, LOG_SEVERITY_CRITICAL, LOG_all_sinks_except(LOG_SINK_FILE), "Error seeking within file: %s", file_name); return seek_result; } - const int8_t write_result = lfs_file_write(&LFS_filesystem, &file, write_buffer, write_buffer_len); - if (write_result < 0) { + const int8_t write_result = lfs_file_write(&LFS_filesystem, &file, write_buffer, write_buffer_len); + if (write_result < 0) { LOG_message(LOG_SYSTEM_LFS, LOG_SEVERITY_CRITICAL, LOG_all_sinks_except(LOG_SINK_FILE), "Error writing to file %s", file_name); - return write_result; - } - - // Close the File, the storage is not updated until the file is closed successfully - const int8_t close_result = lfs_file_close(&LFS_filesystem, &file); - if (close_result < 0) { + return write_result; + } + + // Close the File, the storage is not updated until the file is closed successfully + const int8_t close_result = lfs_file_close(&LFS_filesystem, &file); + if (close_result < 0) { LOG_message(LOG_SYSTEM_LFS, LOG_SEVERITY_CRITICAL, LOG_all_sinks_except(LOG_SINK_FILE), "Error closing file: %s", file_name); - return close_result; - } - - return 0; + return close_result; + } + + return 0; } /** @@ -379,47 +379,47 @@ lfs_ssize_t LFS_read_file(const char file_name[], lfs_soff_t offset, uint8_t *re return 1; } - lfs_file_t file; - const int8_t open_result = lfs_file_opencfg(&LFS_filesystem, &file, file_name, LFS_O_RDONLY, &LFS_file_cfg); - if (open_result < 0) - { + lfs_file_t file; + const int8_t open_result = lfs_file_opencfg(&LFS_filesystem, &file, file_name, LFS_O_RDONLY, &LFS_file_cfg); + if (open_result < 0) + { // TODO: confirm behaviour is desired: this assumes filesystem as a // whole as an issue, so does not send log message to file LOG_message(LOG_SYSTEM_LFS, LOG_SEVERITY_CRITICAL, LOG_all_sinks_except(LOG_SINK_FILE), "Error opening file to read: %s", file_name); - return open_result; - } + return open_result; + } if (LFS_enable_hot_path_debug_logs) { LOG_message(LOG_SYSTEM_LFS, LOG_SEVERITY_NORMAL, LOG_all_sinks_except(LOG_SINK_FILE), "Opened file to read: %s", file_name); } const lfs_soff_t seek_result = lfs_file_seek(&LFS_filesystem, &file, offset, LFS_SEEK_SET); - if (seek_result < 0) - { + if (seek_result < 0) + { LOG_message(LOG_SYSTEM_LFS, LOG_SEVERITY_CRITICAL, LOG_all_sinks_except(LOG_SINK_FILE), "Error seeking within file: %s", file_name); - return seek_result; - } + return seek_result; + } - const lfs_ssize_t read_result = lfs_file_read(&LFS_filesystem, &file, read_buffer, read_buffer_len); - if (read_result < 0) - { + const lfs_ssize_t read_result = lfs_file_read(&LFS_filesystem, &file, read_buffer, read_buffer_len); + if (read_result < 0) + { LOG_message(LOG_SYSTEM_LFS, LOG_SEVERITY_CRITICAL, LOG_all_sinks_except(LOG_SINK_FILE), "Error reading file: %s", file_name); - return read_result; - } + return read_result; + } if (LFS_enable_hot_path_debug_logs) { LOG_message(LOG_SYSTEM_LFS, LOG_SEVERITY_NORMAL, LOG_all_sinks_except(LOG_SINK_FILE), "Successfully read file: %s", file_name); } - // Close the File, the storage is not updated until the file is closed successfully - const int8_t close_result = lfs_file_close(&LFS_filesystem, &file); - if (close_result < 0) { + // Close the File, the storage is not updated until the file is closed successfully + const int8_t close_result = lfs_file_close(&LFS_filesystem, &file); + if (close_result < 0) { LOG_message(LOG_SYSTEM_LFS, LOG_SEVERITY_CRITICAL, LOG_all_sinks_except(LOG_SINK_FILE), "Error closing file: %s", file_name); - return close_result; - } + return close_result; + } if (LFS_enable_hot_path_debug_logs) { LOG_message(LOG_SYSTEM_LFS, LOG_SEVERITY_NORMAL, LOG_all_sinks_except(LOG_SINK_FILE), "Successfully closed file: %s", file_name); } - return read_result; + return read_result; } /** @@ -435,8 +435,8 @@ lfs_ssize_t LFS_file_size(const char file_name[]) return 1; } - lfs_file_t file; - const int8_t open_result = lfs_file_opencfg(&LFS_filesystem, &file, file_name, LFS_O_RDONLY, &LFS_file_cfg); + lfs_file_t file; + const int8_t open_result = lfs_file_opencfg(&LFS_filesystem, &file, file_name, LFS_O_RDONLY, &LFS_file_cfg); if (open_result < 0) { LOG_message(LOG_SYSTEM_LFS, LOG_SEVERITY_CRITICAL, LOG_all_sinks_except(LOG_SINK_FILE), "Error opening file: %s", file_name); return open_result; @@ -448,10 +448,10 @@ lfs_ssize_t LFS_file_size(const char file_name[]) const lfs_ssize_t size = lfs_file_size(&LFS_filesystem, &file); const int8_t close_result = lfs_file_close(&LFS_filesystem, &file); - if (close_result < 0) { + if (close_result < 0) { LOG_message(LOG_SYSTEM_LFS, LOG_SEVERITY_CRITICAL, LOG_all_sinks_except(LOG_SINK_FILE), "Error closing file: %s", file_name); - return close_result; - } + return close_result; + } if (LFS_enable_hot_path_debug_logs) { LOG_message(LOG_SYSTEM_LFS, LOG_SEVERITY_NORMAL, LOG_all_sinks_except(LOG_SINK_FILE), "Successfully closed file: %s", file_name); } From faa3def5a86423d43f051de6a61ce5c0ad11c34a Mon Sep 17 00:00:00 2001 From: Saksham Puri <84263133+Saksham-P@users.noreply.github.com> Date: Tue, 3 Dec 2024 18:12:16 -0700 Subject: [PATCH 18/19] Converted all Debugs to LOG_message Got rid of static configuration and debug imports Folders are now displayed with '/' --- firmware/Core/Inc/config/static_config.h | 4 -- firmware/Core/Src/littlefs/littlefs_helper.c | 53 +++++--------------- 2 files changed, 13 insertions(+), 44 deletions(-) diff --git a/firmware/Core/Inc/config/static_config.h b/firmware/Core/Inc/config/static_config.h index 51dfeb119..a971228a9 100644 --- a/firmware/Core/Inc/config/static_config.h +++ b/firmware/Core/Inc/config/static_config.h @@ -8,8 +8,4 @@ /// Default: 0 (disabled) static const uint8_t FLASH_enable_hot_path_debug_logs = 0; -/// Whether to enable hot-path debug success logging in the LittleFS drivers. -/// Default: 0 (disabled) -static const uint8_t LFS_enable_hot_path_debug_logs = 0; - #endif /* __INCLUDE_GUARD__STATIC_CONFIG_H__ */ diff --git a/firmware/Core/Src/littlefs/littlefs_helper.c b/firmware/Core/Src/littlefs/littlefs_helper.c index 1245a07c1..dfa9b2a06 100644 --- a/firmware/Core/Src/littlefs/littlefs_helper.c +++ b/firmware/Core/Src/littlefs/littlefs_helper.c @@ -4,8 +4,6 @@ #include "littlefs/littlefs_helper.h" #include "littlefs/lfs.h" #include "littlefs/littlefs_driver.h" -#include "debug_tools/debug_uart.h" -#include "config/static_config.h" #include "log/log.h" /*-----------------------------VARIABLES-----------------------------*/ @@ -68,9 +66,7 @@ int8_t LFS_format() return format_result; } - if (LFS_enable_hot_path_debug_logs) { - LOG_message(LOG_SYSTEM_LFS, LOG_SEVERITY_NORMAL, LOG_all_sinks_except(LOG_SINK_FILE), "FLASH Memory formatting successful!"); - } + LOG_message(LOG_SYSTEM_LFS, LOG_SEVERITY_NORMAL, LOG_all_sinks_except(LOG_SINK_FILE), "LittleFS Memory formatting successful!"); return 0; } @@ -93,9 +89,7 @@ int8_t LFS_mount() return mount_result; } - if (LFS_enable_hot_path_debug_logs) { - LOG_message(LOG_SYSTEM_LFS, LOG_SEVERITY_NORMAL, LOG_all_sinks_except(LOG_SINK_FILE), "LittleFS mounting successful!"); - } + LOG_message(LOG_SYSTEM_LFS, LOG_SEVERITY_NORMAL, LOG_all_sinks_except(LOG_SINK_FILE), "LittleFS mounting successful!"); LFS_is_lfs_mounted = 1; return 0; @@ -157,14 +151,13 @@ int8_t LFS_list_directory(const char root_directory[], uint16_t offset, int16_t // result is positive on success, 0 at the end of directory, or negative on failure. int8_t read_dir_result = 1; struct lfs_info info; - DEBUG_uart_print_str("Name \t bytes\n"); + LOG_message(LOG_SYSTEM_LFS, LOG_SEVERITY_NORMAL, LOG_all_sinks_except(LOG_SINK_FILE), "Name \t\t Bytes"); while (read_dir_result > 0) { read_dir_result = lfs_dir_read(&LFS_filesystem, &dir, &info); if (read_dir_result < 0) { - DEBUG_uart_print_str("Error reading directory contents.\n"); LOG_message(LOG_SYSTEM_LFS, LOG_SEVERITY_CRITICAL, LOG_all_sinks_except(LOG_SINK_FILE), "Error reading content from directory: %s", root_directory); break; } @@ -180,20 +173,17 @@ int8_t LFS_list_directory(const char root_directory[], uint16_t offset, int16_t count--; } - DEBUG_uart_print_str(info.name); if (info.type == LFS_TYPE_REG) { - DEBUG_uart_print_str("\t"); - DEBUG_uart_print_uint32(info.size); - DEBUG_uart_print_str(" bytes"); + LOG_message(LOG_SYSTEM_LFS, LOG_SEVERITY_NORMAL, LOG_all_sinks_except(LOG_SINK_FILE), "%s\t%d bytes", info.name, info.size); + } else if (info.type == LFS_TYPE_DIR){ + LOG_message(LOG_SYSTEM_LFS, LOG_SEVERITY_NORMAL, LOG_all_sinks_except(LOG_SINK_FILE), "%s/", info.name); } - DEBUG_uart_print_str("\n"); } int8_t close_dir_result = lfs_dir_close(&LFS_filesystem, &dir); if (close_dir_result < 0) { - DEBUG_uart_print_str("Error closing directory.\n"); LOG_message(LOG_SYSTEM_LFS, LOG_SEVERITY_CRITICAL, LOG_all_sinks_except(LOG_SINK_FILE), "Error closing directory: %s", root_directory); return close_dir_result; } @@ -201,7 +191,6 @@ int8_t LFS_list_directory(const char root_directory[], uint16_t offset, int16_t if (read_dir_result < 0) { return read_dir_result; } else { - DEBUG_uart_print_str("Successfully Listed Directory Contents.\n"); LOG_message(LOG_SYSTEM_LFS, LOG_SEVERITY_NORMAL, LOG_all_sinks_except(LOG_SINK_FILE), "Successfully listed contents from directory: %s", root_directory); return 0; } @@ -286,11 +275,7 @@ int8_t LFS_write_file(const char file_name[], uint8_t *write_buffer, uint32_t wr return open_result; } - if (LFS_enable_hot_path_debug_logs) { - DEBUG_uart_print_str("Opened/created a file named: '"); - DEBUG_uart_print_str(file_name); - DEBUG_uart_print_str("'\n"); - } + LOG_message(LOG_SYSTEM_LFS, LOG_SEVERITY_NORMAL, LOG_all_sinks_except(LOG_SINK_FILE), "Opened/created file: %s", file_name); // Write data to file const int8_t write_result = lfs_file_write(&LFS_filesystem, &file, write_buffer, write_buffer_len); @@ -308,9 +293,7 @@ int8_t LFS_write_file(const char file_name[], uint8_t *write_buffer, uint32_t wr return close_result; } - if (LFS_enable_hot_path_debug_logs) { - DEBUG_uart_print_str("Successfully closed the file!\n"); - } + LOG_message(LOG_SYSTEM_LFS, LOG_SEVERITY_WARNING, LOG_all_sinks_except(LOG_SINK_FILE), "Successfully closed file: %s", file_name); LOG_message(LOG_SYSTEM_LFS, LOG_SEVERITY_WARNING, LOG_all_sinks_except(LOG_SINK_FILE), "Successfully wrote data to file: %s", file_name); return 0; @@ -388,9 +371,7 @@ lfs_ssize_t LFS_read_file(const char file_name[], lfs_soff_t offset, uint8_t *re LOG_message(LOG_SYSTEM_LFS, LOG_SEVERITY_CRITICAL, LOG_all_sinks_except(LOG_SINK_FILE), "Error opening file to read: %s", file_name); return open_result; } - if (LFS_enable_hot_path_debug_logs) { - LOG_message(LOG_SYSTEM_LFS, LOG_SEVERITY_NORMAL, LOG_all_sinks_except(LOG_SINK_FILE), "Opened file to read: %s", file_name); - } + LOG_message(LOG_SYSTEM_LFS, LOG_SEVERITY_NORMAL, LOG_all_sinks_except(LOG_SINK_FILE), "Opened file to read: %s", file_name); const lfs_soff_t seek_result = lfs_file_seek(&LFS_filesystem, &file, offset, LFS_SEEK_SET); if (seek_result < 0) @@ -405,9 +386,7 @@ lfs_ssize_t LFS_read_file(const char file_name[], lfs_soff_t offset, uint8_t *re LOG_message(LOG_SYSTEM_LFS, LOG_SEVERITY_CRITICAL, LOG_all_sinks_except(LOG_SINK_FILE), "Error reading file: %s", file_name); return read_result; } - if (LFS_enable_hot_path_debug_logs) { - LOG_message(LOG_SYSTEM_LFS, LOG_SEVERITY_NORMAL, LOG_all_sinks_except(LOG_SINK_FILE), "Successfully read file: %s", file_name); - } + LOG_message(LOG_SYSTEM_LFS, LOG_SEVERITY_NORMAL, LOG_all_sinks_except(LOG_SINK_FILE), "Successfully read file: %s", file_name); // Close the File, the storage is not updated until the file is closed successfully const int8_t close_result = lfs_file_close(&LFS_filesystem, &file); @@ -415,9 +394,7 @@ lfs_ssize_t LFS_read_file(const char file_name[], lfs_soff_t offset, uint8_t *re LOG_message(LOG_SYSTEM_LFS, LOG_SEVERITY_CRITICAL, LOG_all_sinks_except(LOG_SINK_FILE), "Error closing file: %s", file_name); return close_result; } - if (LFS_enable_hot_path_debug_logs) { - LOG_message(LOG_SYSTEM_LFS, LOG_SEVERITY_NORMAL, LOG_all_sinks_except(LOG_SINK_FILE), "Successfully closed file: %s", file_name); - } + LOG_message(LOG_SYSTEM_LFS, LOG_SEVERITY_NORMAL, LOG_all_sinks_except(LOG_SINK_FILE), "Successfully closed file: %s", file_name); return read_result; } @@ -441,9 +418,7 @@ lfs_ssize_t LFS_file_size(const char file_name[]) LOG_message(LOG_SYSTEM_LFS, LOG_SEVERITY_CRITICAL, LOG_all_sinks_except(LOG_SINK_FILE), "Error opening file: %s", file_name); return open_result; } - if (LFS_enable_hot_path_debug_logs) { - LOG_message(LOG_SYSTEM_LFS, LOG_SEVERITY_NORMAL, LOG_all_sinks_except(LOG_SINK_FILE), "Successfully opened file: %s", file_name); - } + LOG_message(LOG_SYSTEM_LFS, LOG_SEVERITY_NORMAL, LOG_all_sinks_except(LOG_SINK_FILE), "Successfully opened file: %s", file_name); const lfs_ssize_t size = lfs_file_size(&LFS_filesystem, &file); @@ -452,8 +427,6 @@ lfs_ssize_t LFS_file_size(const char file_name[]) LOG_message(LOG_SYSTEM_LFS, LOG_SEVERITY_CRITICAL, LOG_all_sinks_except(LOG_SINK_FILE), "Error closing file: %s", file_name); return close_result; } - if (LFS_enable_hot_path_debug_logs) { - LOG_message(LOG_SYSTEM_LFS, LOG_SEVERITY_NORMAL, LOG_all_sinks_except(LOG_SINK_FILE), "Successfully closed file: %s", file_name); - } + LOG_message(LOG_SYSTEM_LFS, LOG_SEVERITY_NORMAL, LOG_all_sinks_except(LOG_SINK_FILE), "Successfully closed file: %s", file_name); return size; } \ No newline at end of file From e88f6242b19a350f290ec53605b089d8882b997a Mon Sep 17 00:00:00 2001 From: Saksham Puri <84263133+Saksham-P@users.noreply.github.com> Date: Tue, 3 Dec 2024 18:16:51 -0700 Subject: [PATCH 19/19] Updated LOG to use long int instead of int --- firmware/Core/Src/littlefs/littlefs_helper.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/firmware/Core/Src/littlefs/littlefs_helper.c b/firmware/Core/Src/littlefs/littlefs_helper.c index dfa9b2a06..93b556a7c 100644 --- a/firmware/Core/Src/littlefs/littlefs_helper.c +++ b/firmware/Core/Src/littlefs/littlefs_helper.c @@ -175,7 +175,7 @@ int8_t LFS_list_directory(const char root_directory[], uint16_t offset, int16_t if (info.type == LFS_TYPE_REG) { - LOG_message(LOG_SYSTEM_LFS, LOG_SEVERITY_NORMAL, LOG_all_sinks_except(LOG_SINK_FILE), "%s\t%d bytes", info.name, info.size); + LOG_message(LOG_SYSTEM_LFS, LOG_SEVERITY_NORMAL, LOG_all_sinks_except(LOG_SINK_FILE), "%s\t%ld bytes", info.name, info.size); } else if (info.type == LFS_TYPE_DIR){ LOG_message(LOG_SYSTEM_LFS, LOG_SEVERITY_NORMAL, LOG_all_sinks_except(LOG_SINK_FILE), "%s/", info.name); }