Merge pull request #215 from jboone/spiflash_read_fix
hackrf_spiflash read fix
This commit is contained in:
@ -243,3 +243,25 @@ void w25q80bv_program(uint32_t addr, uint32_t len, const uint8_t* data)
|
|||||||
w25q80bv_page_program(addr, len, data);
|
w25q80bv_page_program(addr, len, data);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void w25q80bv_read(uint32_t addr, uint32_t len, uint8_t* const data)
|
||||||
|
{
|
||||||
|
uint32_t i;
|
||||||
|
|
||||||
|
/* do nothing if we would overflow the flash */
|
||||||
|
if ((len > W25Q80BV_NUM_BYTES) || (addr > W25Q80BV_NUM_BYTES)
|
||||||
|
|| ((addr + len) > W25Q80BV_NUM_BYTES))
|
||||||
|
return;
|
||||||
|
|
||||||
|
w25q80bv_wait_while_busy();
|
||||||
|
|
||||||
|
gpio_clear(PORT_SSP0_SSEL, PIN_SSP0_SSEL);
|
||||||
|
ssp_transfer(SSP0_NUM, W25Q80BV_FAST_READ);
|
||||||
|
ssp_transfer(SSP0_NUM, (addr >> 16) & 0xFF);
|
||||||
|
ssp_transfer(SSP0_NUM, (addr >> 8) & 0xFF);
|
||||||
|
ssp_transfer(SSP0_NUM, (addr >> 0) & 0xFF);
|
||||||
|
ssp_transfer(SSP0_NUM, 0xFF);
|
||||||
|
for (i = 0; i < len; i++)
|
||||||
|
data[i] = ssp_transfer(SSP0_NUM, 0xFF);
|
||||||
|
gpio_set(PORT_SSP0_SSEL, PIN_SSP0_SSEL);
|
||||||
|
}
|
||||||
|
@ -27,6 +27,8 @@
|
|||||||
#define W25Q80BV_NUM_PAGES 4096U
|
#define W25Q80BV_NUM_PAGES 4096U
|
||||||
#define W25Q80BV_NUM_BYTES 1048576U
|
#define W25Q80BV_NUM_BYTES 1048576U
|
||||||
|
|
||||||
|
#define W25Q80BV_READ_DATA 0x03
|
||||||
|
#define W25Q80BV_FAST_READ 0x0b
|
||||||
#define W25Q80BV_WRITE_ENABLE 0x06
|
#define W25Q80BV_WRITE_ENABLE 0x06
|
||||||
#define W25Q80BV_CHIP_ERASE 0xC7
|
#define W25Q80BV_CHIP_ERASE 0xC7
|
||||||
#define W25Q80BV_READ_STATUS1 0x05
|
#define W25Q80BV_READ_STATUS1 0x05
|
||||||
@ -51,5 +53,6 @@ void w25q80bv_chip_erase(void);
|
|||||||
void w25q80bv_program(uint32_t addr, uint32_t len, const uint8_t* data);
|
void w25q80bv_program(uint32_t addr, uint32_t len, const uint8_t* data);
|
||||||
uint8_t w25q80bv_get_device_id(void);
|
uint8_t w25q80bv_get_device_id(void);
|
||||||
void w25q80bv_get_unique_id(w25q80bv_unique_id_t* unique_id);
|
void w25q80bv_get_unique_id(w25q80bv_unique_id_t* unique_id);
|
||||||
|
void w25q80bv_read(uint32_t addr, uint32_t len, uint8_t* const data);
|
||||||
|
|
||||||
#endif//__W25Q80BV_H__
|
#endif//__W25Q80BV_H__
|
||||||
|
@ -47,6 +47,7 @@
|
|||||||
#include "sgpio_isr.h"
|
#include "sgpio_isr.h"
|
||||||
#include "usb_bulk_buffer.h"
|
#include "usb_bulk_buffer.h"
|
||||||
#include "si5351c.h"
|
#include "si5351c.h"
|
||||||
|
#include "w25q80bv.h"
|
||||||
|
|
||||||
static volatile transceiver_mode_t _transceiver_mode = TRANSCEIVER_MODE_OFF;
|
static volatile transceiver_mode_t _transceiver_mode = TRANSCEIVER_MODE_OFF;
|
||||||
|
|
||||||
@ -224,6 +225,9 @@ int main(void) {
|
|||||||
#endif
|
#endif
|
||||||
cpu_clock_init();
|
cpu_clock_init();
|
||||||
|
|
||||||
|
/* Code is not running from SPI flash, initialize for flash read/write over USB */
|
||||||
|
w25q80bv_setup();
|
||||||
|
|
||||||
usb_set_descriptor_by_serial_number();
|
usb_set_descriptor_by_serial_number();
|
||||||
|
|
||||||
usb_set_configuration_changed_cb(usb_configuration_changed);
|
usb_set_configuration_changed_cb(usb_configuration_changed);
|
||||||
|
@ -33,14 +33,10 @@ uint8_t spiflash_buffer[W25Q80BV_PAGE_LEN];
|
|||||||
usb_request_status_t usb_vendor_request_erase_spiflash(
|
usb_request_status_t usb_vendor_request_erase_spiflash(
|
||||||
usb_endpoint_t* const endpoint, const usb_transfer_stage_t stage)
|
usb_endpoint_t* const endpoint, const usb_transfer_stage_t stage)
|
||||||
{
|
{
|
||||||
//FIXME This should refuse to run if executing from SPI flash.
|
|
||||||
|
|
||||||
if (stage == USB_TRANSFER_STAGE_SETUP) {
|
if (stage == USB_TRANSFER_STAGE_SETUP) {
|
||||||
w25q80bv_setup();
|
|
||||||
/* only chip erase is implemented */
|
/* only chip erase is implemented */
|
||||||
w25q80bv_chip_erase();
|
w25q80bv_chip_erase();
|
||||||
usb_transfer_schedule_ack(endpoint->in);
|
usb_transfer_schedule_ack(endpoint->in);
|
||||||
//FIXME probably should undo w25q80bv_setup()
|
|
||||||
}
|
}
|
||||||
return USB_REQUEST_STATUS_OK;
|
return USB_REQUEST_STATUS_OK;
|
||||||
}
|
}
|
||||||
@ -51,8 +47,6 @@ usb_request_status_t usb_vendor_request_write_spiflash(
|
|||||||
uint32_t addr = 0;
|
uint32_t addr = 0;
|
||||||
uint16_t len = 0;
|
uint16_t len = 0;
|
||||||
|
|
||||||
//FIXME This should refuse to run if executing from SPI flash.
|
|
||||||
|
|
||||||
if (stage == USB_TRANSFER_STAGE_SETUP) {
|
if (stage == USB_TRANSFER_STAGE_SETUP) {
|
||||||
addr = (endpoint->setup.value << 16) | endpoint->setup.index;
|
addr = (endpoint->setup.value << 16) | endpoint->setup.index;
|
||||||
len = endpoint->setup.length;
|
len = endpoint->setup.length;
|
||||||
@ -62,7 +56,6 @@ usb_request_status_t usb_vendor_request_write_spiflash(
|
|||||||
} else {
|
} else {
|
||||||
usb_transfer_schedule_block(endpoint->out, &spiflash_buffer[0], len,
|
usb_transfer_schedule_block(endpoint->out, &spiflash_buffer[0], len,
|
||||||
NULL, NULL);
|
NULL, NULL);
|
||||||
w25q80bv_setup();
|
|
||||||
return USB_REQUEST_STATUS_OK;
|
return USB_REQUEST_STATUS_OK;
|
||||||
}
|
}
|
||||||
} else if (stage == USB_TRANSFER_STAGE_DATA) {
|
} else if (stage == USB_TRANSFER_STAGE_DATA) {
|
||||||
@ -75,7 +68,6 @@ usb_request_status_t usb_vendor_request_write_spiflash(
|
|||||||
} else {
|
} else {
|
||||||
w25q80bv_program(addr, len, &spiflash_buffer[0]);
|
w25q80bv_program(addr, len, &spiflash_buffer[0]);
|
||||||
usb_transfer_schedule_ack(endpoint->in);
|
usb_transfer_schedule_ack(endpoint->in);
|
||||||
//FIXME probably should undo w25q80bv_setup()
|
|
||||||
return USB_REQUEST_STATUS_OK;
|
return USB_REQUEST_STATUS_OK;
|
||||||
}
|
}
|
||||||
} else {
|
} else {
|
||||||
@ -86,10 +78,8 @@ usb_request_status_t usb_vendor_request_write_spiflash(
|
|||||||
usb_request_status_t usb_vendor_request_read_spiflash(
|
usb_request_status_t usb_vendor_request_read_spiflash(
|
||||||
usb_endpoint_t* const endpoint, const usb_transfer_stage_t stage)
|
usb_endpoint_t* const endpoint, const usb_transfer_stage_t stage)
|
||||||
{
|
{
|
||||||
uint32_t i;
|
|
||||||
uint32_t addr;
|
uint32_t addr;
|
||||||
uint16_t len;
|
uint16_t len;
|
||||||
uint8_t* u8_addr_pt;
|
|
||||||
|
|
||||||
if (stage == USB_TRANSFER_STAGE_SETUP)
|
if (stage == USB_TRANSFER_STAGE_SETUP)
|
||||||
{
|
{
|
||||||
@ -99,12 +89,7 @@ usb_request_status_t usb_vendor_request_read_spiflash(
|
|||||||
|| ((addr + len) > W25Q80BV_NUM_BYTES)) {
|
|| ((addr + len) > W25Q80BV_NUM_BYTES)) {
|
||||||
return USB_REQUEST_STATUS_STALL;
|
return USB_REQUEST_STATUS_STALL;
|
||||||
} else {
|
} else {
|
||||||
/* TODO flush SPIFI "cache" before to read the SPIFI memory */
|
w25q80bv_read(addr, len, &spiflash_buffer[0]);
|
||||||
u8_addr_pt = (uint8_t*)(addr + SPIFI_DATA_UNCACHED_BASE);
|
|
||||||
for(i=0; i<len; i++)
|
|
||||||
{
|
|
||||||
spiflash_buffer[i] = u8_addr_pt[i];
|
|
||||||
}
|
|
||||||
usb_transfer_schedule_block(endpoint->in, &spiflash_buffer[0], len,
|
usb_transfer_schedule_block(endpoint->in, &spiflash_buffer[0], len,
|
||||||
NULL, NULL);
|
NULL, NULL);
|
||||||
return USB_REQUEST_STATUS_OK;
|
return USB_REQUEST_STATUS_OK;
|
||||||
|
Reference in New Issue
Block a user