diff options
author | Harald Welte <laforge@gnumonks.org> | 2017-02-28 00:21:45 +0100 |
---|---|---|
committer | Harald Welte <laforge@gnumonks.org> | 2017-02-28 01:10:23 +0100 |
commit | 32852bc1d90cd7e27264509c19db47dedd9fac19 (patch) | |
tree | 34a22b98fce3617434f3fd46e3e524625f9a1c65 | |
parent | edf9c9d32215a044124af229c498502a7a32f389 (diff) |
DFU: towards a more complete implementation
* we now actually route the EP0 control requests in DFU mode to the
correct handler (weak linker symbols are tricky)
* we now actually call code to read/write data from/to RAM/FLASH
-rw-r--r-- | firmware/apps/dfu/main.c | 98 | ||||
-rw-r--r-- | firmware/atmel_softpack_libraries/usb/device/dfu/dfu_driver.c | 10 | ||||
-rw-r--r-- | firmware/atmel_softpack_libraries/usb/device/dfu/dfu_runtime.c | 6 | ||||
-rw-r--r-- | firmware/libboard/common/include/board_common.h | 1 | ||||
-rw-r--r-- | firmware/libcommon/source/usb.c | 6 |
5 files changed, 108 insertions, 13 deletions
diff --git a/firmware/apps/dfu/main.c b/firmware/apps/dfu/main.c index 9b2facf..af595ac 100644 --- a/firmware/apps/dfu/main.c +++ b/firmware/apps/dfu/main.c @@ -4,19 +4,105 @@ #include "usb/common/dfu/usb_dfu.h" #include "manifest.h" +#define ALTIF_RAM 0 +#define ALTIF_FLASH 1 + unsigned int g_unique_id[4]; /*---------------------------------------------------------------------------- * Callbacks *----------------------------------------------------------------------------*/ -#if 0 -void USBDDriverCallbacks_ConfigurationChanged(uint8_t cfgnum) +#define RAM_ADDR(offset) (IRAM_ADDR + BOARD_DFU_RAM_SIZE + offset) +#define FLASH_ADDR(offset) (IFLASH_ADDR + BOARD_DFU_BOOT_SIZE + offset) + +#define IFLASH_END ((uint8_t *)IFLASH_ADDR + IFLASH_SIZE) +#define IRAM_END ((uint8_t *)IRAM_ADDR + IRAM_SIZE) + +/* incoming call-back: Host has transfered 'len' bytes (stored at + * 'data'), which we shall write to 'offset' into the partition + * associated with 'altif'. Guaranted to be les than + * BOARD_DFU_PAGE_SIZE */ +int USBDFU_handle_dnload(uint8_t altif, unsigned int offset, + uint8_t *data, unsigned int len) { - TRACE_INFO_WP("cfgChanged%d ", cfgnum); - simtrace_config = cfgnum; + uint32_t addr; + int rc; + + printf("dnload(altif=%u, offset=%u, len=%u\n\r", altif, offset, len); + + switch (altif) { + case ALTIF_RAM: + addr = RAM_ADDR(offset); + if (addr > IRAM_ADDR + IRAM_SIZE) { + g_dfu.state = DFU_STATE_dfuERROR; + g_dfu.status = DFU_STATUS_errADDRESS; + return DFU_RET_STALL; + } + memcpy((void *)addr, data, len); + return DFU_RET_ZLP; + case ALTIF_FLASH: + addr = FLASH_ADDR(offset); + if (addr > IFLASH_ADDR + IFLASH_SIZE) { + g_dfu.state = DFU_STATE_dfuERROR; + g_dfu.status = DFU_STATUS_errADDRESS; + return DFU_RET_STALL; + } + rc = FLASHD_Write(addr, data, len); + if (rc != 0) { + /* FIXME: set error codes */ + return DFU_RET_STALL; + } + return DFU_RET_ZLP; + default: + /* FIXME: set error codes */ + TRACE_ERROR("DFU download for unknown AltIf %d\n\r", altif); + return DFU_RET_STALL; + } } -#endif + +/* incoming call-back: Host has requested to read back 'req_len' bytes + * starting from 'offset' of the firmware * associated with partition + * 'altif' */ +int USBDFU_handle_upload(uint8_t altif, unsigned int offset, + uint8_t *data, unsigned int req_len) +{ + uint32_t addr; + + printf("upload(altif=%u, offset=%u, len=%u)", altif, offset, req_len); + + switch (altif) { + case ALTIF_RAM: + addr = RAM_ADDR(offset); + if (addr > IRAM_ADDR + IRAM_SIZE) { + g_dfu.state = DFU_STATE_dfuERROR; + g_dfu.status = DFU_STATUS_errADDRESS; + return -1; + } + if ((uint8_t *)addr + req_len > IRAM_END) + req_len = IRAM_END - (uint8_t *)addr; + memcpy(data, (void *)addr, req_len); + break; + case ALTIF_FLASH: + addr = FLASH_ADDR(offset); + if (addr > IFLASH_ADDR + IFLASH_SIZE) { + g_dfu.state = DFU_STATE_dfuERROR; + g_dfu.status = DFU_STATUS_errADDRESS; + return -1; + } + if ((uint8_t *)addr + req_len > IFLASH_END) + req_len = IFLASH_END - (uint8_t *)addr; + memcpy(data, (void *)addr, req_len); + break; + default: + TRACE_ERROR("DFU upload for unknown AltIf %d\n\r", altif); + /* FIXME: set error codes */ + return -1; + } + printf("=%u\r\n", req_len); + return req_len; +} + /* returns '1' in case we should break any endless loop */ static void check_exec_dbg_cmd(void) @@ -70,7 +156,7 @@ extern int main(void) while (USBD_GetState() < USBD_STATE_CONFIGURED) { check_exec_dbg_cmd(); -#if 0 +#if 1 if (i >= MAX_USB_ITER * 3) { TRACE_ERROR("Resetting board (USB could " "not be configured)\r\n"); diff --git a/firmware/atmel_softpack_libraries/usb/device/dfu/dfu_driver.c b/firmware/atmel_softpack_libraries/usb/device/dfu/dfu_driver.c index 217ec09..08fda6d 100644 --- a/firmware/atmel_softpack_libraries/usb/device/dfu/dfu_driver.c +++ b/firmware/atmel_softpack_libraries/usb/device/dfu/dfu_driver.c @@ -438,15 +438,18 @@ out: } } +/* we assume the caller has enabled the required clock/PLL for USB */ void USBDFU_Initialize(const USBDDriverDescriptors *pDescriptors) { /* We already start in DFU idle mode */ g_dfu.state = DFU_STATE_dfuIDLE; USBDDriver_Initialize(&usbdDriver, pDescriptors, if_altsettings); - USBD_Init(); + USBD_Connect(); //USBD_ConfigureSpeed(1); + + NVIC_EnableIRQ(UDP_IRQn); } void USBDFU_SwitchToApp(void) @@ -464,3 +467,8 @@ void USBDFU_SwitchToApp(void) //BootIntoApp(); NVIC_SystemReset(); } + +void USBDCallbacks_RequestReceived(const USBGenericRequest *request) +{ + USBDFU_DFU_RequestHandler(request); +} diff --git a/firmware/atmel_softpack_libraries/usb/device/dfu/dfu_runtime.c b/firmware/atmel_softpack_libraries/usb/device/dfu/dfu_runtime.c index 0102650..3bf7aa5 100644 --- a/firmware/atmel_softpack_libraries/usb/device/dfu/dfu_runtime.c +++ b/firmware/atmel_softpack_libraries/usb/device/dfu/dfu_runtime.c @@ -187,3 +187,9 @@ void DFURT_SwitchToDFU(void) toDFU(); } + +void USBDCallbacks_RequestReceived(const USBGenericRequest *request) +{ + /* FIXME: integration with CCID control point reqeusts */ + USBDFU_Runtime_RequestHandler(request); +} diff --git a/firmware/libboard/common/include/board_common.h b/firmware/libboard/common/include/board_common.h index 9943ae1..9a7c8d8 100644 --- a/firmware/libboard/common/include/board_common.h +++ b/firmware/libboard/common/include/board_common.h @@ -113,6 +113,7 @@ #define BOARD_USB_DFU #define BOARD_DFU_BOOT_SIZE (16 * 1024) +#define BOARD_DFU_RAM_SIZE (2 * 1024) #define BOARD_DFU_PAGE_SIZE 512 #define BOARD_DFU_NUM_IF 2 diff --git a/firmware/libcommon/source/usb.c b/firmware/libcommon/source/usb.c index 66f1de8..1d37914 100644 --- a/firmware/libcommon/source/usb.c +++ b/firmware/libcommon/source/usb.c @@ -821,9 +821,3 @@ void SIMtrace_USB_Initialize(void) NVIC_EnableIRQ(UDP_IRQn); } - -void USBDCallbacks_RequestReceived(const USBGenericRequest *request) -{ - /* FIXME: integration with CCID control point reqeusts */ - USBDFU_Runtime_RequestHandler(request); -} |