Replaced command system with more robust system that talks to an upload utility
This commit is contained in:
parent
96058f06c2
commit
0e90b84d2e
|
@ -15,6 +15,10 @@ uint8_t memory_map_1[16] = {0b00001000, 0b10001000, 0b01001000, 0b11001000, 0b00
|
||||||
|
|
||||||
Control control;
|
Control control;
|
||||||
|
|
||||||
|
extern UART_HandleTypeDef huart2;
|
||||||
|
extern uint8_t ack[1];
|
||||||
|
extern uint8_t nack[1];
|
||||||
|
|
||||||
// @todo For some reason increasing SD_PAGES does not work
|
// @todo For some reason increasing SD_PAGES does not work
|
||||||
#define SD_PAGES 1
|
#define SD_PAGES 1
|
||||||
#define CPM_PAGE_SIZE 128
|
#define CPM_PAGE_SIZE 128
|
||||||
|
@ -49,15 +53,11 @@ uint32_t calculate_lba() {
|
||||||
|
|
||||||
void control_program_eeprom(uint8_t* data, uint16_t length) {
|
void control_program_eeprom(uint8_t* data, uint16_t length) {
|
||||||
// Take control of the bus
|
// Take control of the bus
|
||||||
printf("Taking control of bus...\n\r");
|
|
||||||
send_busrq(1);
|
send_busrq(1);
|
||||||
while (!has_busak()) {
|
while (!has_busak()) {
|
||||||
control_execute_state();
|
control_execute_state();
|
||||||
}
|
}
|
||||||
|
|
||||||
printf("Done!\n\r");
|
|
||||||
printf("Writing to ROM...\n\r");
|
|
||||||
|
|
||||||
enable_address_out(1);
|
enable_address_out(1);
|
||||||
|
|
||||||
select_device(memory_map_0[0]);
|
select_device(memory_map_0[0]);
|
||||||
|
@ -74,8 +74,6 @@ void control_program_eeprom(uint8_t* data, uint16_t length) {
|
||||||
enable_data_out(0);
|
enable_data_out(0);
|
||||||
send_rd(1);
|
send_rd(1);
|
||||||
|
|
||||||
printf("%i/%i\r", i+1, length);
|
|
||||||
|
|
||||||
for (;;) {
|
for (;;) {
|
||||||
uint8_t d = read_data();
|
uint8_t d = read_data();
|
||||||
if (d == data[i]) {
|
if (d == data[i]) {
|
||||||
|
@ -85,6 +83,9 @@ void control_program_eeprom(uint8_t* data, uint16_t length) {
|
||||||
|
|
||||||
send_rd(0);
|
send_rd(0);
|
||||||
send_memrq(0);
|
send_memrq(0);
|
||||||
|
|
||||||
|
uint8_t progress[] = {(i+1) & 0xFF, (i+1) >> 8};
|
||||||
|
HAL_UART_Transmit(&huart2, progress, sizeof(progress), HAL_MAX_DELAY);
|
||||||
}
|
}
|
||||||
|
|
||||||
enable_address_out(0);
|
enable_address_out(0);
|
||||||
|
@ -95,7 +96,7 @@ void control_program_eeprom(uint8_t* data, uint16_t length) {
|
||||||
// Restart the z80
|
// Restart the z80
|
||||||
control_reset();
|
control_reset();
|
||||||
|
|
||||||
printf("\n");
|
HAL_UART_Transmit(&huart2, ack, sizeof(ack), HAL_MAX_DELAY);
|
||||||
}
|
}
|
||||||
|
|
||||||
void handle_memrq() {
|
void handle_memrq() {
|
||||||
|
|
|
@ -15,49 +15,60 @@ typedef enum {
|
||||||
TARGET_I2C
|
TARGET_I2C
|
||||||
} UpdateTarget;
|
} UpdateTarget;
|
||||||
|
|
||||||
|
extern uint8_t ack[1];
|
||||||
|
extern uint8_t nack[1];
|
||||||
void firmware_update() {
|
void firmware_update() {
|
||||||
printf("FIRMWARE UPDATE\n\r");
|
|
||||||
|
|
||||||
UpdateTarget target;
|
UpdateTarget target;
|
||||||
HAL_UART_Receive(&huart2, &target, 1, 1000);
|
|
||||||
printf("T: %i\n\r", target);
|
|
||||||
|
|
||||||
uint8_t address = 0;
|
HAL_UART_Receive(&huart2, &target, 1, 1000);
|
||||||
if (target == TARGET_I2C) {
|
HAL_UART_Transmit(&huart2, ack, sizeof(ack), HAL_MAX_DELAY);
|
||||||
HAL_UART_Receive(&huart2, &address, 1, 1000);
|
|
||||||
printf("A: %i\n\r", address);
|
|
||||||
}
|
|
||||||
|
|
||||||
uint8_t length_buffer[2];
|
uint8_t length_buffer[2];
|
||||||
HAL_UART_Receive(&huart2, length_buffer, 2, 1000);
|
HAL_UART_Receive(&huart2, length_buffer, sizeof(length_buffer), HAL_MAX_DELAY);
|
||||||
|
HAL_UART_Transmit(&huart2, length_buffer, sizeof(length_buffer), HAL_MAX_DELAY);
|
||||||
uint16_t length = length_buffer[0] + (length_buffer[1] << 8);
|
uint16_t length = length_buffer[0] + (length_buffer[1] << 8);
|
||||||
printf("L: %i\n\r", length);
|
|
||||||
|
|
||||||
uint8_t* data = malloc(length);
|
uint8_t* data = malloc(length);
|
||||||
HAL_UART_Receive(&huart2, data, length, 1000);
|
HAL_UART_Receive(&huart2, data, length, 1000);
|
||||||
|
HAL_UART_Transmit(&huart2, ack, sizeof(ack), HAL_MAX_DELAY);
|
||||||
printf("Firmware received!\n\r");
|
|
||||||
|
|
||||||
switch (target) {
|
switch (target) {
|
||||||
case TARGET_ROM:
|
case TARGET_ROM:
|
||||||
control_program_eeprom(data, length);
|
control_program_eeprom(data, length);
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case TARGET_I2C: {
|
case TARGET_I2C: {
|
||||||
printf("Restarting target to bootloader...\n\r");
|
uint8_t address = 0;
|
||||||
// @todo Make sure that the address to reset to bootloader is the same as the bootloader address
|
HAL_UART_Receive(&huart2, &address, 1, 1000);
|
||||||
uint8_t reboot_command[] = {0x07};
|
HAL_UART_Transmit(&huart2, &address, sizeof(ack), HAL_MAX_DELAY);
|
||||||
|
|
||||||
|
if (HAL_I2C_IsDeviceReady(&hi2c1, 0x29 << 1, 10, 1000) != HAL_OK) {
|
||||||
|
HAL_UART_Transmit(&huart2, nack, sizeof(nack), HAL_MAX_DELAY);
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
HAL_UART_Transmit(&huart2, ack, sizeof(ack), HAL_MAX_DELAY);
|
||||||
|
|
||||||
|
// @todo This assumes that the target it not already in bootloader mode, otherwise this will mess things up
|
||||||
|
uint8_t reboot_command[] = {0xFF};
|
||||||
HAL_I2C_Master_Transmit(&hi2c1, address << 1, reboot_command, sizeof(reboot_command), 1000);
|
HAL_I2C_Master_Transmit(&hi2c1, address << 1, reboot_command, sizeof(reboot_command), 1000);
|
||||||
|
|
||||||
for (volatile int i = 0; i < 10000000; ++i) {}
|
while (HAL_I2C_IsDeviceReady(&hi2c1, 0x29 << 1, 10, 1000) != HAL_OK);
|
||||||
|
|
||||||
printf("Uploading to target...\n\r");
|
HAL_UART_Transmit(&huart2, ack, sizeof(ack), HAL_MAX_DELAY);
|
||||||
|
|
||||||
uint8_t upload_command[4 + length];
|
uint8_t abort_command[] = {0x00};
|
||||||
|
HAL_I2C_Master_Transmit(&hi2c1, address << 1, abort_command, sizeof(abort_command), 1000);
|
||||||
|
|
||||||
|
uint8_t version_command[] = {0x01};
|
||||||
|
HAL_I2C_Master_Transmit(&hi2c1, address << 1, version_command, sizeof(version_command), 1000);
|
||||||
|
uint8_t version_string[16] = {0};
|
||||||
|
HAL_I2C_Master_Receive(&hi2c1, address << 1, version_string, sizeof(version_string), 1000);
|
||||||
|
HAL_UART_Transmit(&huart2, version_string, sizeof(version_string), HAL_MAX_DELAY);
|
||||||
|
|
||||||
|
uint8_t upload_command[4 + 0x80];
|
||||||
upload_command[0] = 0x02;
|
upload_command[0] = 0x02;
|
||||||
upload_command[1] = 0x01;
|
upload_command[1] = 0x01;
|
||||||
|
|
||||||
printf("0/%i\r", length);
|
|
||||||
|
|
||||||
uint16_t remaining = length;
|
uint16_t remaining = length;
|
||||||
for (uint8_t offset = 0; remaining > 0; ++offset) {
|
for (uint8_t offset = 0; remaining > 0; ++offset) {
|
||||||
upload_command[2] = ((offset*0x80) >> 8) & 0xFF;
|
upload_command[2] = ((offset*0x80) >> 8) & 0xFF;
|
||||||
|
@ -71,14 +82,18 @@ void firmware_update() {
|
||||||
|
|
||||||
HAL_I2C_Master_Transmit(&hi2c1, address << 1, upload_command, sizeof(upload_command), 1000);
|
HAL_I2C_Master_Transmit(&hi2c1, address << 1, upload_command, sizeof(upload_command), 1000);
|
||||||
|
|
||||||
printf("%i/%i\r", length-remaining, length);
|
while (HAL_I2C_IsDeviceReady(&hi2c1, 0x29 << 1, 10, 1000) != HAL_OK);
|
||||||
}
|
|
||||||
|
|
||||||
printf("\n");
|
uint8_t progress[] = {(length-remaining) & 0xFF, (length-remaining) >> 8};
|
||||||
|
HAL_UART_Transmit(&huart2, progress, sizeof(progress), HAL_MAX_DELAY);
|
||||||
|
}
|
||||||
|
|
||||||
// Start application
|
// Start application
|
||||||
uint8_t start_command[] = {0x01, 0x80};
|
uint8_t start_command[] = {0x01, 0x80};
|
||||||
HAL_I2C_Master_Transmit(&hi2c1, address << 1, start_command, sizeof(start_command), 1000);
|
HAL_I2C_Master_Transmit(&hi2c1, address << 1, start_command, sizeof(start_command), 1000);
|
||||||
|
|
||||||
|
HAL_UART_Transmit(&huart2, ack, sizeof(ack), HAL_MAX_DELAY);
|
||||||
|
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
85
Src/main.c
85
Src/main.c
|
@ -74,94 +74,43 @@ static void MX_SDIO_SD_Init(void);
|
||||||
/* Private user code ---------------------------------------------------------*/
|
/* Private user code ---------------------------------------------------------*/
|
||||||
/* USER CODE BEGIN 0 */
|
/* USER CODE BEGIN 0 */
|
||||||
uint8_t byte;
|
uint8_t byte;
|
||||||
|
uint8_t ack[] = {0x01};
|
||||||
|
uint8_t nack[] = {0xFE};
|
||||||
void HAL_UART_RxCpltCallback(UART_HandleTypeDef *huart) {
|
void HAL_UART_RxCpltCallback(UART_HandleTypeDef *huart) {
|
||||||
if (huart->Instance == USART2) {
|
if (huart->Instance == USART2) {
|
||||||
static uint8_t cmd_buffer[128];
|
static uint8_t command_mode = 0;
|
||||||
static uint32_t cmd_buffer_len = 0;
|
|
||||||
|
|
||||||
if (cmd_buffer_len+1 > 128) {
|
if (command_mode) {
|
||||||
printf("\n\rCommand is too long!\n\r");
|
|
||||||
cmd_buffer_len = 0;
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
|
|
||||||
int handle_command = 0;
|
|
||||||
static int is_command = 0;
|
|
||||||
switch (byte) {
|
switch (byte) {
|
||||||
// @todo Handle \t
|
// Reboot to bootloader
|
||||||
// Backspace
|
|
||||||
case 0x08:
|
|
||||||
if (is_command) {
|
|
||||||
if (cmd_buffer_len) {
|
|
||||||
cmd_buffer_len--;
|
|
||||||
} else {
|
|
||||||
is_command = 0;
|
|
||||||
}
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
// else falltrough
|
|
||||||
|
|
||||||
// Newline
|
|
||||||
case '\r':
|
|
||||||
case '\n':
|
|
||||||
if (is_command) {
|
|
||||||
handle_command = 1;
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
// else falltrough
|
|
||||||
|
|
||||||
default:
|
|
||||||
if (!is_command && cmd_buffer_len == 0 && byte == '#') {
|
|
||||||
is_command = 1;
|
|
||||||
} else {
|
|
||||||
cmd_buffer[cmd_buffer_len] = byte;
|
|
||||||
cmd_buffer_len++;
|
|
||||||
}
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
|
|
||||||
if (!is_command) {
|
|
||||||
// ONLY SEND THE FIRST CHAR
|
|
||||||
if (cmd_buffer_len > 0) {
|
|
||||||
HAL_I2C_Master_Transmit(&hi2c1, 0x29 << 1, &byte, 1, 1000);
|
|
||||||
}
|
|
||||||
cmd_buffer_len = 0;
|
|
||||||
} else if (handle_command && is_command) {
|
|
||||||
if (cmd_buffer_len == 1) {
|
|
||||||
switch (cmd_buffer[0]) {
|
|
||||||
case 'r':
|
|
||||||
control_reset();
|
|
||||||
printf("Starting...\n\r");
|
|
||||||
break;
|
|
||||||
|
|
||||||
case 'b':
|
case 'b':
|
||||||
|
HAL_UART_Transmit(&huart2, ack, sizeof(ack), HAL_MAX_DELAY);
|
||||||
request_restart_to_bootloader();
|
request_restart_to_bootloader();
|
||||||
printf("Restarting... (bootloader)\n\r");
|
|
||||||
break;
|
break;
|
||||||
|
|
||||||
|
// Upload firmware
|
||||||
case 'u':
|
case 'u':
|
||||||
|
HAL_UART_Transmit(&huart2, ack, sizeof(ack), HAL_MAX_DELAY);
|
||||||
firmware_update();
|
firmware_update();
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case 'h':
|
// Send over for bload
|
||||||
printf("#r - (Re)start program\n\r#b - Restart (Bootloader)\n\r#u - Update\n\r#m - Mount the sd card to pc\n\r#h - Show this menu\n\r");
|
case 'l':
|
||||||
break;
|
// @todo Implement this
|
||||||
|
|
||||||
case '#':
|
|
||||||
HAL_I2C_Master_Transmit(&hi2c1, 0x29 << 1, &byte, 1, 1000);
|
|
||||||
break;
|
break;
|
||||||
|
|
||||||
default:
|
default:
|
||||||
printf("Unknown command: %c!\n\r", cmd_buffer[0]);
|
HAL_UART_Transmit(&huart2, nack, sizeof(nack), HAL_MAX_DELAY);
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
|
command_mode = 0;
|
||||||
|
} else if (byte == 0xFF) {
|
||||||
|
command_mode = 1;
|
||||||
|
HAL_UART_Transmit(&huart2, ack, sizeof(ack), HAL_MAX_DELAY);
|
||||||
} else {
|
} else {
|
||||||
printf("Unknown command!\n\r");
|
HAL_I2C_Master_Transmit(&hi2c1, 0x29 << 1, &byte, 1, 1000);
|
||||||
}
|
}
|
||||||
|
|
||||||
cmd_buffer_len = 0;
|
|
||||||
is_command = 0;
|
|
||||||
}
|
|
||||||
HAL_UART_Receive_IT(&huart2, &byte, 1);
|
HAL_UART_Receive_IT(&huart2, &byte, 1);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
Loading…
Reference in New Issue
Block a user