void CopyPatchToFlash(void) { flash_unlock(); flash_Erase_sector(11); int src_addr = PATCHMAINLOC; int flash_addr = PATCHFLASHLOC; int c; for (c = 0; c < PATCHFLASHSIZE;) { flash_ProgramWord(flash_addr, *(int32_t *)src_addr); src_addr += 4; flash_addr += 4; c += 4; } // verify src_addr = PATCHMAINLOC; flash_addr = PATCHFLASHLOC; int err = 0; for (c = 0; c < PATCHFLASHSIZE;) { if (*(int32_t *)flash_addr != *(int32_t *)src_addr) err++; src_addr += 4; flash_addr += 4; c += 4; } if (err) { while (1) { // flash verify fail } } AckPending = 1; }
int main(void) { DMA1_Stream0->CR=0; DMA1_Stream1->CR=0; DMA1_Stream2->CR=0; DMA1_Stream3->CR=0; DMA1_Stream4->CR=0; DMA1_Stream5->CR=0; DMA1_Stream6->CR=0; DMA1_Stream7->CR=0; DMA2_Stream0->CR=0; DMA2_Stream1->CR=0; DMA2_Stream2->CR=0; DMA2_Stream3->CR=0; DMA2_Stream4->CR=0; DMA2_Stream5->CR=0; DMA2_Stream6->CR=0; DMA2_Stream7->CR=0; palClearPad(GPIOD,7); // disable USBH power // copy vector table memcpy((char *)0x20000000, (const char *)&_vectors, 0x200); // remap SRAM1 to 0x00000000 SYSCFG->MEMRMP |= 0x03; // FMC_SDRAMDeInit(0); // RCC->AHB3RSTR |= 1; //RCC_AHB3RSTR_FMCRST RCC->AHB3ENR |= 1; //RCC_AHB3ENR_FMCEN; // HAL_DeInit(); // HAL_Init(); watchdog_feed(); halInit(); // float usb inputs, hope the host notices detach... palSetPadMode(GPIOA, 11, PAL_MODE_INPUT); palSetPadMode(GPIOA, 12, PAL_MODE_INPUT); // setup LEDs palSetPadMode(LED1_PORT,LED1_PIN,PAL_MODE_OUTPUT_PUSHPULL); palSetPad(LED1_PORT,LED1_PIN); #ifdef LED2_PIN palSetPadMode(LED2_PORT,LED2_PIN,PAL_MODE_OUTPUT_PUSHPULL); #endif chSysInit(); watchdog_feed(); configSDRAM(); #ifdef SERIALDEBUG // SD2 for serial debug output palSetPadMode(GPIOA, 3, PAL_MODE_ALTERNATE(7) | PAL_MODE_INPUT); // RX palSetPadMode(GPIOA, 2, PAL_MODE_OUTPUT_PUSHPULL); // TX palSetPadMode(GPIOA, 2, PAL_MODE_ALTERNATE(7)); // TX // 115200 baud static const SerialConfig sd2Cfg = {115200, 0, 0, 0}; sdStart(&SD2, &sd2Cfg); #endif DBGPRINTCHAR('a'); uint32_t pbuf[16]; SDRAM_ReadBuffer(&pbuf[0], 0 + 0x050000, 16); DBGPRINTCHAR('x'); watchdog_feed(); uint32_t *sdram32 = (uint32_t *)SDRAM_BANK_ADDR; uint8_t *sdram8 = (uint8_t *)SDRAM_BANK_ADDR; if ((sdram8[0] != 'f') || (sdram8[1] != 'l') || (sdram8[2] != 'a') || (sdram8[3] != 's') || (sdram8[4] != 'c') || (sdram8[5] != 'o') || (sdram8[6] != 'p') || (sdram8[7] != 'y')) { DispayAbortErr(1); } DBGPRINTCHAR('b'); uint32_t flength = sdram32[2]; uint32_t fcrc = sdram32[3]; if (flength > 1 * 1024 * 1024) { DispayAbortErr(2); } DBGPRINTCHAR('c'); DBGPRINTHEX(flength); uint32_t ccrc = CalcCRC32((uint8_t *)(SDRAM_BANK_ADDR + 0x010), flength); DBGPRINTCHAR('d'); DBGPRINTHEX(ccrc); DBGPRINTHEX(fcrc); if (ccrc != fcrc) { DispayAbortErr(3); } DBGPRINTCHAR('e'); // unlock sequence FLASH->KEYR = 0x45670123; FLASH->KEYR = 0xCDEF89AB; uint32_t i; for (i = 0; i < 12; i++) { flash_Erase_sector(i); LCD_drawStringN(0, 3, "Erased sector", 128); LCD_drawNumber3D(80, 3, i); refresh_LCD(); palWritePad(LED2_PORT,LED2_PIN,1); chThdSleepMilliseconds(100); palWritePad(LED2_PORT,LED2_PIN,0); DBGPRINTCHAR('f'); DBGPRINTHEX(i); } DBGPRINTCHAR('g'); DBGPRINTHEX(flength); ccrc = CalcCRC32((uint8_t *)(SDRAM_BANK_ADDR + 0x010), flength); DBGPRINTCHAR('h'); DBGPRINTHEX(ccrc); DBGPRINTHEX(fcrc); if (ccrc != fcrc) { DispayAbortErr(4); } DBGPRINTCHAR('i'); int destptr = FLASH_BASE_ADDR; // flash base adress uint32_t *srcptr = (uint32_t *)(SDRAM_BANK_ADDR + 0x010); // sdram base adress + header offset for (i = 0; i < (flength + 3) / 4; i++) { uint32_t d = *srcptr; flash_ProgramWord(destptr, d); if ((FLASH->SR != 0) && (FLASH->SR != 1)) { DBGPRINTCHAR('z'); DBGPRINTHEX(FLASH->SR); } // DBGPRINTHEX(f); if ((i & 0xFFF) == 0) { palWritePad(LED2_PORT,LED2_PIN,1); chThdSleepMilliseconds(100); palWritePad(LED2_PORT,LED2_PIN,0); DBGPRINTCHAR('j'); DBGPRINTHEX(destptr); DBGPRINTHEX(*(srcptr)); } destptr += 4; srcptr++; } DBGPRINTCHAR('k'); ccrc = CalcCRC32((uint8_t *)(FLASH_BASE_ADDR), flength); DBGPRINTCHAR('l'); DBGPRINTHEX(ccrc); DBGPRINTHEX(fcrc); if (ccrc != fcrc) { DispayAbortErr(5); } DBGPRINTCHAR('\r'); DBGPRINTCHAR('\n'); DBGPRINTCHAR('S'); DBGPRINTCHAR('U'); DBGPRINTCHAR('C'); DBGPRINTCHAR('C'); DBGPRINTCHAR('E'); DBGPRINTCHAR('S'); DBGPRINTCHAR('S'); DBGPRINTCHAR('\r'); DBGPRINTCHAR('\n'); chThdSleepMilliseconds(1000); NVIC_SystemReset(); return 0; }