From 63a7256739cc6db0664e601fd0f9f534a345479a Mon Sep 17 00:00:00 2001 From: schneider <schneider@blinkenlichts.net> Date: Wed, 24 Apr 2019 15:51:44 +0200 Subject: [PATCH] add initial bootloader. untested. --- bootloader/Makefile | 1 + bootloader/bootloader-usb.c | 329 ++++++++++++++++++++++++++ bootloader/main.c | 452 +++++++++++++++++------------------- bootloader/mscmem.c | 7 + lib/card10/mx25lba.c | 10 +- lib/ff13/Source/diskio.c | 10 +- lib/ff13/Source/diskio.h | 3 - 7 files changed, 568 insertions(+), 244 deletions(-) create mode 100644 bootloader/bootloader-usb.c diff --git a/bootloader/Makefile b/bootloader/Makefile index 38a6b7d1..abc96c8c 100644 --- a/bootloader/Makefile +++ b/bootloader/Makefile @@ -67,6 +67,7 @@ CMSIS_ROOT=$(LIBS_DIR)/CMSIS # Source files for this test (add path to VPATH below) SRCS = main.c SRCS += mscmem.c +SRCS += bootloader-usb.c SRCS += ../lib/card10/mx25lba.c # Where to find source files for this test diff --git a/bootloader/bootloader-usb.c b/bootloader/bootloader-usb.c new file mode 100644 index 00000000..b6b3924e --- /dev/null +++ b/bootloader/bootloader-usb.c @@ -0,0 +1,329 @@ +/******************************************************************************* + * Copyright (C) 2016 Maxim Integrated Products, Inc., All Rights Reserved. + * + * Permission is hereby granted, free of charge, to any person obtaining a + * copy of this software and associated documentation files (the "Software"), + * to deal in the Software without restriction, including without limitation + * the rights to use, copy, modify, merge, publish, distribute, sublicense, + * and/or sell copies of the Software, and to permit persons to whom the + * Software is furnished to do so, subject to the following conditions: + * + * The above copyright notice and this permission notice shall be included + * in all copies or substantial portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS + * OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF + * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. + * IN NO EVENT SHALL MAXIM INTEGRATED BE LIABLE FOR ANY CLAIM, DAMAGES + * OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, + * ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR + * OTHER DEALINGS IN THE SOFTWARE. + * + * Except as contained in this notice, the name of Maxim Integrated + * Products, Inc. shall not be used except as stated in the Maxim Integrated + * Products, Inc. Branding Policy. + * + * The mere transfer of this software does not imply any licenses + * of trade secrets, proprietary technology, copyrights, patents, + * trademarks, maskwork rights, or any other form of intellectual + * property whatsoever. Maxim Integrated Products, Inc. retains all + * ownership rights. + * + * $Id: main.c 31505 2017-10-20 21:16:29Z zach.metzinger $ + * + ******************************************************************************* + */ + +/** + * @file main.c + * @brief USB Mass Storage Class example + * @details This project creates a mass storage device using either on-board RAM or + * external SPI flash memory. Load the project, connect a cable from the PC + * to the USB connector. A new external drive should appear than can be read + * and written. + */ + +#include <stdio.h> +#include <stddef.h> +#include "mxc_config.h" +#include "mxc_sys.h" +#include "mxc_delay.h" +#include "board.h" +#include "led.h" +#include "usb.h" +#include "usb_event.h" +#include "enumerate.h" +#include "msc.h" +#include "descriptors.h" +#include "mscmem.h" + + +/***** Definitions *****/ +#define EVENT_ENUM_COMP MAXUSB_NUM_EVENTS +#define EVENT_REMOTE_WAKE (EVENT_ENUM_COMP + 1) + +/***** Global Data *****/ +volatile int configured; +volatile int suspended; +volatile unsigned int event_flags; +int remote_wake_en; + +/***** Function Prototypes *****/ +static int setconfig_callback(usb_setup_pkt *sud, void *cbdata); +static int setfeature_callback(usb_setup_pkt *sud, void *cbdata); +static int clrfeature_callback(usb_setup_pkt *sud, void *cbdata); +static int event_callback(maxusb_event_t evt, void *data); +static void usb_app_sleep(void); +static void usb_app_wakeup(void); + +/***** File Scope Variables *****/ + +/* This EP assignment must match the Configuration Descriptor */ +static const msc_cfg_t msc_cfg = { + 1, /* EP OUT */ + MXC_USBHS_MAX_PACKET, /* OUT max packet size */ + 2, /* EP IN */ + MXC_USBHS_MAX_PACKET, /* IN max packet size */ +}; + +static const msc_idstrings_t ids = { + "MAXIM", /* Vendor string. Maximum of 8 bytes */ + "MSC Example", /* Product string. Maximum of 16 bytes */ + "1.0" /* Version string. Maximum of 4 bytes */ +}; + +/* Functions to control "disk" memory. See msc.h for definitions. */ +static const msc_mem_t mem = { + mscmem_init, + mscmem_start, + mscmem_stop, + mscmem_ready, + mscmem_size, + mscmem_read, + mscmem_write, +}; + +/* This callback is used to allow the driver to call part specific initialization functions. */ +int usb_startup_cb() +{ + const sys_cfg_usbhs_t sys_usbhs_cfg = NULL; + return SYS_USBHS_Init(&sys_usbhs_cfg); +} + +int usb_shutdown_cb() +{ + return SYS_USBHS_Shutdown(); +} + +/* User-supplied function to delay usec micro-seconds */ +void delay_us(unsigned int usec) +{ + /* mxc_delay() takes unsigned long, so can't use it directly */ + mxc_delay(usec); +} + + +/******************************************************************************/ +void run_usbmsc(void) +{ + maxusb_cfg_options_t usb_opts; + + printf("Waiting for VBUS...\n"); + + /* Initialize state */ + configured = 0; + suspended = 0; + event_flags = 0; + remote_wake_en = 0; + + /* Start out in full speed */ + usb_opts.enable_hs = 0; + usb_opts.delay_us = delay_us; /* Function which will be used for delays */ + usb_opts.init_callback = usb_startup_cb; + usb_opts.shutdown_callback = usb_shutdown_cb; + + /* Initialize the usb module */ + if (usb_init(&usb_opts) != 0) { + printf("usb_init() failed\n"); + while (1); + } + + /* Initialize the enumeration module */ + if (enum_init() != 0) { + printf("enum_init() failed\n"); + while (1); + } + + /* Register enumeration data */ + enum_register_descriptor(ENUM_DESC_DEVICE, (uint8_t*)&device_descriptor, 0); + enum_register_descriptor(ENUM_DESC_CONFIG, (uint8_t*)&config_descriptor, 0); + enum_register_descriptor(ENUM_DESC_STRING, lang_id_desc, 0); + enum_register_descriptor(ENUM_DESC_STRING, mfg_id_desc, 1); + enum_register_descriptor(ENUM_DESC_STRING, prod_id_desc, 2); + enum_register_descriptor(ENUM_DESC_STRING, serial_id_desc, 3); + + /* Handle configuration */ + enum_register_callback(ENUM_SETCONFIG, setconfig_callback, NULL); + + /* Handle feature set/clear */ + enum_register_callback(ENUM_SETFEATURE, setfeature_callback, NULL); + enum_register_callback(ENUM_CLRFEATURE, clrfeature_callback, NULL); + + /* Initialize the class driver */ + if (msc_init(&config_descriptor.msc_interface_descriptor, &ids, &mem) != 0) { + printf("msc_init() failed\n"); + while (1); + } + + /* Register callbacks */ + usb_event_enable(MAXUSB_EVENT_NOVBUS, event_callback, NULL); + usb_event_enable(MAXUSB_EVENT_VBUS, event_callback, NULL); + + /* Start with USB in low power mode */ + usb_app_sleep(); + NVIC_EnableIRQ(USB_IRQn); + + /* Wait for events */ + while (1) { + + if (suspended || !configured) { + LED_Off(0); + } else { + LED_On(0); + } + + if (event_flags) { + /* Display events */ + if (MXC_GETBIT(&event_flags, MAXUSB_EVENT_NOVBUS)) { + MXC_CLRBIT(&event_flags, MAXUSB_EVENT_NOVBUS); + printf("VBUS Disconnect\n"); + } else if (MXC_GETBIT(&event_flags, MAXUSB_EVENT_VBUS)) { + MXC_CLRBIT(&event_flags, MAXUSB_EVENT_VBUS); + printf("VBUS Connect\n"); + } else if (MXC_GETBIT(&event_flags, MAXUSB_EVENT_BRST)) { + MXC_CLRBIT(&event_flags, MAXUSB_EVENT_BRST); + printf("Bus Reset\n"); + } else if (MXC_GETBIT(&event_flags, MAXUSB_EVENT_SUSP)) { + MXC_CLRBIT(&event_flags, MAXUSB_EVENT_SUSP); + printf("Suspended\n"); + } else if (MXC_GETBIT(&event_flags, MAXUSB_EVENT_DPACT)) { + MXC_CLRBIT(&event_flags, MAXUSB_EVENT_DPACT); + printf("Resume\n"); + } else if (MXC_GETBIT(&event_flags, EVENT_ENUM_COMP)) { + MXC_CLRBIT(&event_flags, EVENT_ENUM_COMP); + printf("Enumeration complete.\n"); + } else if (MXC_GETBIT(&event_flags, EVENT_REMOTE_WAKE)) { + MXC_CLRBIT(&event_flags, EVENT_REMOTE_WAKE); + printf("Remote Wakeup\n"); + } + } + } +} + +/******************************************************************************/ +static int setconfig_callback(usb_setup_pkt *sud, void *cbdata) +{ + /* Confirm the configuration value */ + if (sud->wValue == config_descriptor.config_descriptor.bConfigurationValue) { + configured = 1; + MXC_SETBIT(&event_flags, EVENT_ENUM_COMP); + return msc_configure(&msc_cfg); /* Configure the device class */ + } else if (sud->wValue == 0) { + configured = 0; + return msc_deconfigure(); + } + + return -1; +} + +/******************************************************************************/ +static int setfeature_callback(usb_setup_pkt *sud, void *cbdata) +{ + if(sud->wValue == FEAT_REMOTE_WAKE) { + remote_wake_en = 1; + } else { + // Unknown callback + return -1; + } + + return 0; +} + +/******************************************************************************/ +static int clrfeature_callback(usb_setup_pkt *sud, void *cbdata) +{ + if(sud->wValue == FEAT_REMOTE_WAKE) { + remote_wake_en = 0; + } else { + // Unknown callback + return -1; + } + + return 0; +} + +/******************************************************************************/ +static void usb_app_sleep(void) +{ + /* TODO: Place low-power code here */ + suspended = 1; +} + +/******************************************************************************/ +static void usb_app_wakeup(void) +{ + /* TODO: Place low-power code here */ + suspended = 0; +} + +/******************************************************************************/ +static int event_callback(maxusb_event_t evt, void *data) +{ + /* Set event flag */ + MXC_SETBIT(&event_flags, evt); + + printf("event: %d\n", evt); + switch (evt) { + case MAXUSB_EVENT_NOVBUS: + usb_event_disable(MAXUSB_EVENT_BRST); + usb_event_disable(MAXUSB_EVENT_SUSP); + usb_event_disable(MAXUSB_EVENT_DPACT); + usb_disconnect(); + configured = 0; + enum_clearconfig(); + msc_deconfigure(); + usb_app_sleep(); + break; + case MAXUSB_EVENT_VBUS: + usb_event_clear(MAXUSB_EVENT_BRST); + usb_event_enable(MAXUSB_EVENT_BRST, event_callback, NULL); + usb_event_clear(MAXUSB_EVENT_SUSP); + usb_event_enable(MAXUSB_EVENT_SUSP, event_callback, NULL); + usb_connect(); + usb_app_sleep(); + break; + case MAXUSB_EVENT_BRST: + usb_app_wakeup(); + enum_clearconfig(); + msc_deconfigure(); + configured = 0; + suspended = 0; + break; + case MAXUSB_EVENT_SUSP: + usb_app_sleep(); + break; + case MAXUSB_EVENT_DPACT: + usb_app_wakeup(); + break; + default: + break; + } + + return 0; +} + +/******************************************************************************/ +void USB_IRQHandler(void) +{ + usb_event_handler(); +} diff --git a/bootloader/main.c b/bootloader/main.c index 0c3250fe..ae105486 100644 --- a/bootloader/main.c +++ b/bootloader/main.c @@ -45,292 +45,268 @@ #include <stdio.h> #include <stddef.h> +#include <stdbool.h> +#include <string.h> + #include "mxc_config.h" #include "mxc_sys.h" #include "mxc_delay.h" +#include "flc.h" +#include "icc.h" +#include "crc.h" #include "board.h" #include "led.h" -#include "usb.h" -#include "usb_event.h" -#include "enumerate.h" -#include "msc.h" -#include "descriptors.h" -#include "mscmem.h" - - -/***** Definitions *****/ -#define EVENT_ENUM_COMP MAXUSB_NUM_EVENTS -#define EVENT_REMOTE_WAKE (EVENT_ENUM_COMP + 1) - -#define BUFFER_SIZE 64 - -#define STRINGIFY(x) #x -#define TOSTRING(x) STRINGIFY(x) - -/***** Global Data *****/ -volatile int configured; -volatile int suspended; -volatile unsigned int event_flags; -int remote_wake_en; - -/***** Function Prototypes *****/ -static int setconfig_callback(usb_setup_pkt *sud, void *cbdata); -static int setfeature_callback(usb_setup_pkt *sud, void *cbdata); -static int clrfeature_callback(usb_setup_pkt *sud, void *cbdata); -static int event_callback(maxusb_event_t evt, void *data); -static void usb_app_sleep(void); -static void usb_app_wakeup(void); - -/***** File Scope Variables *****/ - -/* This EP assignment must match the Configuration Descriptor */ -static const msc_cfg_t msc_cfg = { - 1, /* EP OUT */ - MXC_USBHS_MAX_PACKET, /* OUT max packet size */ - 2, /* EP IN */ - MXC_USBHS_MAX_PACKET, /* IN max packet size */ -}; +#include "ff.h" -static const msc_idstrings_t ids = { - "MAXIM", /* Vendor string. Maximum of 8 bytes */ - "MSC Example", /* Product string. Maximum of 16 bytes */ - "1.0" /* Version string. Maximum of 4 bytes */ -}; +#define GPIO_PORT_IN PORT_1 +#define GPIO_PIN_IN PIN_6 -/* Functions to control "disk" memory. See msc.h for definitions. */ -static const msc_mem_t mem = { - mscmem_init, - mscmem_start, - mscmem_stop, - mscmem_ready, - mscmem_size, - mscmem_read, - mscmem_write, -}; -/* This callback is used to allow the driver to call part specific initialization functions. */ -int usb_startup_cb() -{ - const sys_cfg_usbhs_t sys_usbhs_cfg = NULL; - return SYS_USBHS_Init(&sys_usbhs_cfg); -} +#define PARTITION_START (0x10000000 + 64 * 1024) +#define PARTITION_END (0x10000000 + 512 * 1024 - 1) /* TODO: check if 1 MB also works. Might have to enable the second bank */ +//#define PARTITION_END (0x10000000 + 1024 * 1024 - 1) -int usb_shutdown_cb() -{ - return SYS_USBHS_Shutdown(); -} +extern void run_usbmsc(void); +DIR dir; /* Directory object */ +FATFS FatFs; -/* User-supplied function to delay usec micro-seconds */ -void delay_us(unsigned int usec) +static void crc_sw(uint32_t *crcval, uint8_t *data, uint8_t len, uint32_t polynomial) { - /* mxc_delay() takes unsigned long, so can't use it directly */ - mxc_delay(usec); + int i, j; + uint32_t temp; + + for(i = 0; i < len; ++i) { + temp = (data[i] & 0xFF); + for(j = 0; j < 8; ++j) { + if((temp ^ *crcval) & 1) { + *crcval >>= 1; + *crcval ^= polynomial; + } else { + *crcval >>= 1; + } + temp >>= 1; + } + } } -/******************************************************************************/ -int main(void) +bool mount(void) { - maxusb_cfg_options_t usb_opts; - - printf("\n\n***** " TOSTRING(TARGET) " USB Mass Storage Example *****\n"); - printf("Waiting for VBUS...\n"); - - /* Initialize state */ - configured = 0; - suspended = 0; - event_flags = 0; - remote_wake_en = 0; - - /* Start out in full speed */ - usb_opts.enable_hs = 0; - usb_opts.delay_us = delay_us; /* Function which will be used for delays */ - usb_opts.init_callback = usb_startup_cb; - usb_opts.shutdown_callback = usb_shutdown_cb; - - /* Initialize the usb module */ - if (usb_init(&usb_opts) != 0) { - printf("usb_init() failed\n"); - while (1); - } - - /* Initialize the enumeration module */ - if (enum_init() != 0) { - printf("enum_init() failed\n"); - while (1); + FRESULT res; + res=f_mount(&FatFs,"/",0); + if(res != FR_OK) { + printf("f_mount error %d\n", res); + return false; } - /* Register enumeration data */ - enum_register_descriptor(ENUM_DESC_DEVICE, (uint8_t*)&device_descriptor, 0); - enum_register_descriptor(ENUM_DESC_CONFIG, (uint8_t*)&config_descriptor, 0); - enum_register_descriptor(ENUM_DESC_STRING, lang_id_desc, 0); - enum_register_descriptor(ENUM_DESC_STRING, mfg_id_desc, 1); - enum_register_descriptor(ENUM_DESC_STRING, prod_id_desc, 2); - enum_register_descriptor(ENUM_DESC_STRING, serial_id_desc, 3); - - /* Handle configuration */ - enum_register_callback(ENUM_SETCONFIG, setconfig_callback, NULL); - - /* Handle feature set/clear */ - enum_register_callback(ENUM_SETFEATURE, setfeature_callback, NULL); - enum_register_callback(ENUM_CLRFEATURE, clrfeature_callback, NULL); - - /* Initialize the class driver */ - if (msc_init(&config_descriptor.msc_interface_descriptor, &ids, &mem) != 0) { - printf("msc_init() failed\n"); - while (1); + res = f_opendir(&dir, "0:"); + if(res != FR_OK) { + printf("f_opendir error %d\n", res); + return false; } - /* Register callbacks */ - usb_event_enable(MAXUSB_EVENT_NOVBUS, event_callback, NULL); - usb_event_enable(MAXUSB_EVENT_VBUS, event_callback, NULL); - - /* Start with USB in low power mode */ - usb_app_sleep(); - NVIC_EnableIRQ(USB_IRQn); + return true; +} - /* Wait for events */ - while (1) { +bool check_integrity(void) +{ + FIL file; + UINT readbytes; + char *filename = "card10.bin"; + uint8_t data[512]; + FRESULT res; + + res=f_open(&file, filename, FA_OPEN_EXISTING|FA_READ); + if(res != FR_OK) { + printf("f_open error %d\n", res); + return false; + } - if (suspended || !configured) { - LED_Off(0); - } else { - LED_On(0); + uint32_t crcval = 0; + do { + res = f_read(&file, data, sizeof(data), &readbytes); + if(res != FR_OK) { + printf("f_read error %d\n", res); + crcval = 1; // Make sure to fail the test + break; } + crc_sw(&crcval, data, readbytes, TPU_CRC_CCITT); + } while (readbytes == sizeof(data)); - if (event_flags) { - /* Display events */ - if (MXC_GETBIT(&event_flags, MAXUSB_EVENT_NOVBUS)) { - MXC_CLRBIT(&event_flags, MAXUSB_EVENT_NOVBUS); - printf("VBUS Disconnect\n"); - } else if (MXC_GETBIT(&event_flags, MAXUSB_EVENT_VBUS)) { - MXC_CLRBIT(&event_flags, MAXUSB_EVENT_VBUS); - printf("VBUS Connect\n"); - } else if (MXC_GETBIT(&event_flags, MAXUSB_EVENT_BRST)) { - MXC_CLRBIT(&event_flags, MAXUSB_EVENT_BRST); - printf("Bus Reset\n"); - } else if (MXC_GETBIT(&event_flags, MAXUSB_EVENT_SUSP)) { - MXC_CLRBIT(&event_flags, MAXUSB_EVENT_SUSP); - printf("Suspended\n"); - } else if (MXC_GETBIT(&event_flags, MAXUSB_EVENT_DPACT)) { - MXC_CLRBIT(&event_flags, MAXUSB_EVENT_DPACT); - printf("Resume\n"); - } else if (MXC_GETBIT(&event_flags, EVENT_ENUM_COMP)) { - MXC_CLRBIT(&event_flags, EVENT_ENUM_COMP); - printf("Enumeration complete.\n"); - } else if (MXC_GETBIT(&event_flags, EVENT_REMOTE_WAKE)) { - MXC_CLRBIT(&event_flags, EVENT_REMOTE_WAKE); - printf("Remote Wakeup\n"); - } - } + f_close(&file); + + if(crcval == 0) { + return true; + } else { + printf("CRC check failed. Final CRC: %d\n", crcval); + return true; + return false; } } -/******************************************************************************/ -static int setconfig_callback(usb_setup_pkt *sud, void *cbdata) +bool is_update_needed(void) { - /* Confirm the configuration value */ - if (sud->wValue == config_descriptor.config_descriptor.bConfigurationValue) { - configured = 1; - MXC_SETBIT(&event_flags, EVENT_ENUM_COMP); - return msc_configure(&msc_cfg); /* Configure the device class */ - } else if (sud->wValue == 0) { - configured = 0; - return msc_deconfigure(); + FIL file; + UINT readbytes; + char *filename = "card10.bin"; + uint8_t data[512]; + FRESULT res; + + res=f_open(&file, filename, FA_OPEN_EXISTING|FA_READ); + if(res != FR_OK) { + printf("f_open error %d\n", res); + return false; } - return -1; -} + uint8_t *partition = (uint8_t *)(intptr_t)PARTITION_START; + bool different = false; + do { + res = f_read(&file, data, sizeof(data), &readbytes); + if(res != FR_OK) { + printf("f_read error %d\n", res); + break; /* Going to return false, don't want to use this file */ + } + if(memcmp(partition, data, readbytes)) { + different = true; + break; + } + partition += readbytes; + } while (readbytes == sizeof(data)); -/******************************************************************************/ -static int setfeature_callback(usb_setup_pkt *sud, void *cbdata) -{ - if(sud->wValue == FEAT_REMOTE_WAKE) { - remote_wake_en = 1; - } else { - // Unknown callback - return -1; - } + f_close(&file); - return 0; + //different = true; + return different; } -/******************************************************************************/ -static int clrfeature_callback(usb_setup_pkt *sud, void *cbdata) +void erase_partition(void) { - if(sud->wValue == FEAT_REMOTE_WAKE) { - remote_wake_en = 0; - } else { - // Unknown callback - return -1; + int ret = FLC_MultiPageErase(PARTITION_START, PARTITION_END); + if(ret != E_NO_ERROR) { + printf("FLC_MultiPageErase failed with %d\n", ret); + while(1); } - - return 0; } -/******************************************************************************/ -static void usb_app_sleep(void) +void flash_partition(void) { - /* TODO: Place low-power code here */ - suspended = 1; + FIL file; + UINT readbytes; + char *filename = "card10.bin"; + uint8_t data[512]; + FRESULT res; + + res=f_open(&file, filename, FA_OPEN_EXISTING|FA_READ); + if(res != FR_OK) { + printf("f_open error %d\n", res); + while(1); + } + + uint32_t partition = PARTITION_START; + + ICC_Disable(); + do { + res = f_read(&file, data, sizeof(data), &readbytes); + if(res != FR_OK) { + printf("f_read error %d\n", res); + break; /* Going to return false, don't want to use this file */ + } + int ret = FLC_Write(partition, readbytes, (uint32_t *)data); /* wild cast. not sure if this works */ + if(ret != E_NO_ERROR) { + printf("FLC_Write failed with %d\n", ret); + while(1); + } + partition += readbytes; + } while (readbytes == sizeof(data)); + ICC_Enable(); + + f_close(&file); } -/******************************************************************************/ -static void usb_app_wakeup(void) +#if 0 +void test(void) { - /* TODO: Place low-power code here */ - suspended = 0; + FRESULT res; + FIL file; + UINT readbytes; + char *filename = "card10.bin"; + int len = 512; + char data[512]; + + res=f_open(&file, filename, FA_OPEN_EXISTING|FA_READ); + if(res != FR_OK) printf("f_open error %d\n", res); + + res = f_read(&file, data, len, &readbytes); + if(res != FR_OK) printf("f_read error %d\n", res); + + f_close(&file); + + data[readbytes] = 0; + + printf("data: %s\n", data); } +#endif + +static inline void boot(const void * vtable){ + SCB->VTOR = (uintptr_t) vtable; + + // Reset stack pointer & branch to the new reset vector. + __asm( "mov r0, %0\n" + "ldr sp, [r0]\n" + "ldr r0, [r0, #4]\n" + "bx r0\n" + : + : "r"(vtable) + : "%sp", "r0"); +}; + /******************************************************************************/ -static int event_callback(maxusb_event_t evt, void *data) +int main(void) { - /* Set event flag */ - MXC_SETBIT(&event_flags, evt); - - switch (evt) { - case MAXUSB_EVENT_NOVBUS: - usb_event_disable(MAXUSB_EVENT_BRST); - usb_event_disable(MAXUSB_EVENT_SUSP); - usb_event_disable(MAXUSB_EVENT_DPACT); - usb_disconnect(); - configured = 0; - enum_clearconfig(); - msc_deconfigure(); - usb_app_sleep(); - break; - case MAXUSB_EVENT_VBUS: - usb_event_clear(MAXUSB_EVENT_BRST); - usb_event_enable(MAXUSB_EVENT_BRST, event_callback, NULL); - usb_event_clear(MAXUSB_EVENT_SUSP); - usb_event_enable(MAXUSB_EVENT_SUSP, event_callback, NULL); - usb_connect(); - usb_app_sleep(); - break; - case MAXUSB_EVENT_BRST: - usb_app_wakeup(); - enum_clearconfig(); - msc_deconfigure(); - configured = 0; - suspended = 0; - break; - case MAXUSB_EVENT_SUSP: - usb_app_sleep(); - break; - case MAXUSB_EVENT_DPACT: - usb_app_wakeup(); - break; - default: - break; + + printf("\n\nBootloader\n"); + + gpio_cfg_t gpio_in; + gpio_in.port = GPIO_PORT_IN; + gpio_in.mask = GPIO_PIN_IN; + gpio_in.pad = GPIO_PAD_PULL_UP; + gpio_in.func = GPIO_FUNC_IN; + GPIO_Config(&gpio_in); + + // If the button is pressed, we go into MSC mode. + if (!GPIO_InGet(&gpio_in)) { + run_usbmsc(); + + // If we return, don't try to boot. Maybe rather trigger a software reset. + // Reason: Not sure in which state the USB peripheral is and what kind + // of interrupts are active. + while(1); } - return 0; -} -/******************************************************************************/ -void USB_IRQHandler(void) -{ - usb_event_handler(); + if(mount()) { + if(check_integrity()) { + if(is_update_needed()) { + MXC_FLC0->clkdiv = 54; + erase_partition(); + flash_partition(); + } else { + printf("No update needed\n"); + } + } else { + printf("Integrity check failed\n"); + } + } + + + printf("Trying to boot\n"); + // boot partition + boot((uintptr_t *) PARTITION_START); + + while (1) { + // Should never be reached. + } } /******************************************************************************/ diff --git a/bootloader/mscmem.c b/bootloader/mscmem.c index d6daa95d..70f2429d 100644 --- a/bootloader/mscmem.c +++ b/bootloader/mscmem.c @@ -62,40 +62,47 @@ /******************************************************************************/ int mscmem_init() { + printf("%s\n", __func__); return mx25_init(); } /******************************************************************************/ uint32_t mscmem_size(void) { + printf("%s\n", __func__); return mx25_size(); } /******************************************************************************/ int mscmem_read(uint32_t lba, uint8_t* buffer) { + printf("%s\n", __func__); return mx25_read(lba, buffer); } /******************************************************************************/ int mscmem_write(uint32_t lba, uint8_t* buffer) { + printf("%s\n", __func__); return mx25_write(lba, buffer); } /******************************************************************************/ int mscmem_start() { + printf("%s\n", __func__); return mx25_start(); } /******************************************************************************/ int mscmem_stop() { + printf("%s\n", __func__); return mx25_stop(); } /******************************************************************************/ int mscmem_ready() { + printf("%s\n", __func__); return mx25_ready(); } diff --git a/lib/card10/mx25lba.c b/lib/card10/mx25lba.c index 609d3c67..f7fd61ae 100644 --- a/lib/card10/mx25lba.c +++ b/lib/card10/mx25lba.c @@ -129,6 +129,7 @@ static uint32_t getSector(uint32_t num) /******************************************************************************/ int mx25_init() { + printf("%s\n", __func__); if(!initialized) { MX25_Init(); @@ -142,6 +143,7 @@ int mx25_init() /******************************************************************************/ uint32_t mx25_size(void) { + printf("%s\n", __func__); /* Get number of 512 byte chunks the MX25 contains. */ return (MX25_SECTOR_SIZE >> LBA_SIZE_SHIFT) * MX25_NUM_SECTORS; } @@ -149,6 +151,7 @@ uint32_t mx25_size(void) /******************************************************************************/ int mx25_read(uint32_t lba, uint8_t* buffer) { + printf("%s\n", __func__); uint32_t addr; /* Convert to MX25 sector number. */ @@ -170,6 +173,7 @@ int mx25_read(uint32_t lba, uint8_t* buffer) /******************************************************************************/ int mx25_write(uint32_t lba, uint8_t* buffer) { + printf("%s\n", __func__); uint32_t addr; /* Convert to MX25 sector number. */ @@ -192,9 +196,10 @@ int mx25_write(uint32_t lba, uint8_t* buffer) /******************************************************************************/ int mx25_start() { + printf("%s\n", __func__); /* Turn on the MX25 if it is not already. */ if(!initialized) { - mscmem_init(); + mx25_init(); } /* Check if the initialization succeeded. If it has, start running. */ @@ -209,6 +214,7 @@ int mx25_start() /******************************************************************************/ int mx25_stop() { + printf("%s\n", __func__); /* TODO - could shut down XIPF interface here. */ /* Flush the currently cached sector if necessary. */ @@ -222,6 +228,7 @@ int mx25_stop() /******************************************************************************/ int mx25_sync() { + printf("%s\n", __func__); /* Flush the currently cached sector if necessary. */ if(getSector(INVALID_SECTOR)) { return 1; @@ -231,6 +238,7 @@ int mx25_sync() /******************************************************************************/ int mx25_ready() { + printf("%s -> %d\n", __func__, running); return running; } diff --git a/lib/ff13/Source/diskio.c b/lib/ff13/Source/diskio.c index 1c06d6d8..69458836 100644 --- a/lib/ff13/Source/diskio.c +++ b/lib/ff13/Source/diskio.c @@ -17,6 +17,9 @@ #define SECTOR_SIZE 512UL +/*local vaiables*/ +static uint8_t rtc_en; + #if SDHC /* # of times to check for a card, should be > 1 to detect both SD and MMC */ #define INIT_CARD_RETRIES 10 @@ -38,6 +41,7 @@ extern uint32_t mx25_size(void); extern int mx25_read(uint32_t lba, uint8_t* buffer); extern int mx25_write(uint32_t lba, uint8_t* buffer); extern int mx25_sync(void); +extern int mx25_ready(void); /*-----------------------------------------------------------------------*/ /* Get Drive Status */ @@ -55,7 +59,9 @@ DSTATUS disk_status ( DSTATUS status = 0; if(pdrv == 0) { - return STA_NOINIT; + if(mx25_ready()) { + status = RES_OK; + } } #if SDHC @@ -97,7 +103,7 @@ DSTATUS disk_initialize ( #endif if(pdrv == 0) { - if(mx25_start()) { + if(mx25_start() == 0) { status = RES_OK; } } diff --git a/lib/ff13/Source/diskio.h b/lib/ff13/Source/diskio.h index b8e9cbcd..40551fbd 100644 --- a/lib/ff13/Source/diskio.h +++ b/lib/ff13/Source/diskio.h @@ -20,9 +20,6 @@ extern "C" { /* Status of Disk Functions */ typedef BYTE DSTATUS; -/*local vaiables*/ -static uint8_t rtc_en; - /* Results of Disk Functions */ typedef enum { RES_OK = 0, /* 0: Successful */ -- GitLab