Merged cpm22 and bios, and layed foundation for different disk types
This commit is contained in:
parent
100abbfa70
commit
c20b587580
175
Inc/toml.h
Normal file
175
Inc/toml.h
Normal file
|
@ -0,0 +1,175 @@
|
||||||
|
/*
|
||||||
|
MIT License
|
||||||
|
|
||||||
|
Copyright (c) 2017 - 2019 CK Tan
|
||||||
|
https://github.com/cktan/tomlc99
|
||||||
|
|
||||||
|
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 THE
|
||||||
|
AUTHORS OR COPYRIGHT HOLDERS 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.
|
||||||
|
*/
|
||||||
|
#ifndef TOML_H
|
||||||
|
#define TOML_H
|
||||||
|
|
||||||
|
|
||||||
|
#include <stdio.h>
|
||||||
|
#include <stdint.h>
|
||||||
|
|
||||||
|
|
||||||
|
#ifdef __cplusplus
|
||||||
|
#define TOML_EXTERN extern "C"
|
||||||
|
#else
|
||||||
|
#define TOML_EXTERN extern
|
||||||
|
#endif
|
||||||
|
|
||||||
|
typedef struct toml_timestamp_t toml_timestamp_t;
|
||||||
|
typedef struct toml_table_t toml_table_t;
|
||||||
|
typedef struct toml_array_t toml_array_t;
|
||||||
|
typedef struct toml_datum_t toml_datum_t;
|
||||||
|
|
||||||
|
/* Parse a file. Return a table on success, or 0 otherwise.
|
||||||
|
* Caller must toml_free(the-return-value) after use.
|
||||||
|
*/
|
||||||
|
TOML_EXTERN toml_table_t* toml_parse_file(FILE* fp,
|
||||||
|
char* errbuf,
|
||||||
|
int errbufsz);
|
||||||
|
|
||||||
|
/* Parse a string containing the full config.
|
||||||
|
* Return a table on success, or 0 otherwise.
|
||||||
|
* Caller must toml_free(the-return-value) after use.
|
||||||
|
*/
|
||||||
|
TOML_EXTERN toml_table_t* toml_parse(char* conf, /* NUL terminated, please. */
|
||||||
|
char* errbuf,
|
||||||
|
int errbufsz);
|
||||||
|
|
||||||
|
/* Free the table returned by toml_parse() or toml_parse_file(). Once
|
||||||
|
* this function is called, any handles accessed through this tab
|
||||||
|
* directly or indirectly are no longer valid.
|
||||||
|
*/
|
||||||
|
TOML_EXTERN void toml_free(toml_table_t* tab);
|
||||||
|
|
||||||
|
|
||||||
|
/* Timestamp types. The year, month, day, hour, minute, second, z
|
||||||
|
* fields may be NULL if they are not relevant. e.g. In a DATE
|
||||||
|
* type, the hour, minute, second and z fields will be NULLs.
|
||||||
|
*/
|
||||||
|
struct toml_timestamp_t {
|
||||||
|
struct { /* internal. do not use. */
|
||||||
|
int year, month, day;
|
||||||
|
int hour, minute, second, millisec;
|
||||||
|
char z[10];
|
||||||
|
} __buffer;
|
||||||
|
int *year, *month, *day;
|
||||||
|
int *hour, *minute, *second, *millisec;
|
||||||
|
char* z;
|
||||||
|
};
|
||||||
|
|
||||||
|
|
||||||
|
/*-----------------------------------------------------------------
|
||||||
|
* Enhanced access methods
|
||||||
|
*/
|
||||||
|
struct toml_datum_t {
|
||||||
|
int ok;
|
||||||
|
union {
|
||||||
|
toml_timestamp_t* ts; /* ts must be freed after use */
|
||||||
|
char* s; /* string value. s must be freed after use */
|
||||||
|
int b; /* bool value */
|
||||||
|
int64_t i; /* int value */
|
||||||
|
double d; /* double value */
|
||||||
|
} u;
|
||||||
|
};
|
||||||
|
|
||||||
|
/* on arrays: */
|
||||||
|
/* ... retrieve size of array. */
|
||||||
|
TOML_EXTERN int toml_array_nelem(const toml_array_t* arr);
|
||||||
|
/* ... retrieve values using index. */
|
||||||
|
TOML_EXTERN toml_datum_t toml_string_at(const toml_array_t* arr, int idx);
|
||||||
|
TOML_EXTERN toml_datum_t toml_bool_at(const toml_array_t* arr, int idx);
|
||||||
|
TOML_EXTERN toml_datum_t toml_int_at(const toml_array_t* arr, int idx);
|
||||||
|
TOML_EXTERN toml_datum_t toml_double_at(const toml_array_t* arr, int idx);
|
||||||
|
TOML_EXTERN toml_datum_t toml_timestamp_at(const toml_array_t* arr, int idx);
|
||||||
|
/* ... retrieve array or table using index. */
|
||||||
|
TOML_EXTERN toml_array_t* toml_array_at(const toml_array_t* arr, int idx);
|
||||||
|
TOML_EXTERN toml_table_t* toml_table_at(const toml_array_t* arr, int idx);
|
||||||
|
|
||||||
|
/* on tables: */
|
||||||
|
/* ... retrieve the key in table at keyidx. Return 0 if out of range. */
|
||||||
|
TOML_EXTERN const char* toml_key_in(const toml_table_t* tab, int keyidx);
|
||||||
|
/* ... retrieve values using key. */
|
||||||
|
TOML_EXTERN toml_datum_t toml_string_in(const toml_table_t* arr, const char* key);
|
||||||
|
TOML_EXTERN toml_datum_t toml_bool_in(const toml_table_t* arr, const char* key);
|
||||||
|
TOML_EXTERN toml_datum_t toml_int_in(const toml_table_t* arr, const char* key);
|
||||||
|
TOML_EXTERN toml_datum_t toml_double_in(const toml_table_t* arr, const char* key);
|
||||||
|
TOML_EXTERN toml_datum_t toml_timestamp_in(const toml_table_t* arr, const char* key);
|
||||||
|
/* .. retrieve array or table using key. */
|
||||||
|
TOML_EXTERN toml_array_t* toml_array_in(const toml_table_t* tab,
|
||||||
|
const char* key);
|
||||||
|
TOML_EXTERN toml_table_t* toml_table_in(const toml_table_t* tab,
|
||||||
|
const char* key);
|
||||||
|
|
||||||
|
/*-----------------------------------------------------------------
|
||||||
|
* lesser used
|
||||||
|
*/
|
||||||
|
/* Return the array kind: 't'able, 'a'rray, 'v'alue, 'm'ixed */
|
||||||
|
TOML_EXTERN char toml_array_kind(const toml_array_t* arr);
|
||||||
|
|
||||||
|
/* For array kind 'v'alue, return the type of values
|
||||||
|
i:int, d:double, b:bool, s:string, t:time, D:date, T:timestamp, 'm'ixed
|
||||||
|
0 if unknown
|
||||||
|
*/
|
||||||
|
TOML_EXTERN char toml_array_type(const toml_array_t* arr);
|
||||||
|
|
||||||
|
/* Return the key of an array */
|
||||||
|
TOML_EXTERN const char* toml_array_key(const toml_array_t* arr);
|
||||||
|
|
||||||
|
/* Return the number of key-values in a table */
|
||||||
|
TOML_EXTERN int toml_table_nkval(const toml_table_t* tab);
|
||||||
|
|
||||||
|
/* Return the number of arrays in a table */
|
||||||
|
TOML_EXTERN int toml_table_narr(const toml_table_t* tab);
|
||||||
|
|
||||||
|
/* Return the number of sub-tables in a table */
|
||||||
|
TOML_EXTERN int toml_table_ntab(const toml_table_t* tab);
|
||||||
|
|
||||||
|
/* Return the key of a table*/
|
||||||
|
TOML_EXTERN const char* toml_table_key(const toml_table_t* tab);
|
||||||
|
|
||||||
|
/*--------------------------------------------------------------
|
||||||
|
* misc
|
||||||
|
*/
|
||||||
|
TOML_EXTERN int toml_utf8_to_ucs(const char* orig, int len, int64_t* ret);
|
||||||
|
TOML_EXTERN int toml_ucs_to_utf8(int64_t code, char buf[6]);
|
||||||
|
TOML_EXTERN void toml_set_memutil(void* (*xxmalloc)(size_t),
|
||||||
|
void (*xxfree)(void*));
|
||||||
|
|
||||||
|
|
||||||
|
/*--------------------------------------------------------------
|
||||||
|
* deprecated
|
||||||
|
*/
|
||||||
|
/* A raw value, must be processed by toml_rto* before using. */
|
||||||
|
typedef const char* toml_raw_t;
|
||||||
|
TOML_EXTERN toml_raw_t toml_raw_in(const toml_table_t* tab, const char* key);
|
||||||
|
TOML_EXTERN toml_raw_t toml_raw_at(const toml_array_t* arr, int idx);
|
||||||
|
TOML_EXTERN int toml_rtos(toml_raw_t s, char** ret);
|
||||||
|
TOML_EXTERN int toml_rtob(toml_raw_t s, int* ret);
|
||||||
|
TOML_EXTERN int toml_rtoi(toml_raw_t s, int64_t* ret);
|
||||||
|
TOML_EXTERN int toml_rtod(toml_raw_t s, double* ret);
|
||||||
|
TOML_EXTERN int toml_rtod_ex(toml_raw_t s, double* ret, char* buf, int buflen);
|
||||||
|
TOML_EXTERN int toml_rtots(toml_raw_t s, toml_timestamp_t* ret);
|
||||||
|
|
||||||
|
|
||||||
|
#endif /* TOML_H */
|
1
Makefile
1
Makefile
|
@ -43,6 +43,7 @@ Src/disk.c \
|
||||||
Src/control.c \
|
Src/control.c \
|
||||||
Src/profiling.c \
|
Src/profiling.c \
|
||||||
Src/io.c \
|
Src/io.c \
|
||||||
|
Src/toml.c \
|
||||||
Src/stm32f4xx_it.c \
|
Src/stm32f4xx_it.c \
|
||||||
Src/stm32f4xx_hal_msp.c \
|
Src/stm32f4xx_hal_msp.c \
|
||||||
Drivers/STM32F4xx_HAL_Driver/Src/stm32f4xx_hal_rcc.c \
|
Drivers/STM32F4xx_HAL_Driver/Src/stm32f4xx_hal_rcc.c \
|
||||||
|
|
84
Src/disk.c
84
Src/disk.c
|
@ -2,12 +2,16 @@
|
||||||
#include <stdio.h>
|
#include <stdio.h>
|
||||||
#include <string.h>
|
#include <string.h>
|
||||||
#include "fatfs.h"
|
#include "fatfs.h"
|
||||||
|
#include "ff.h"
|
||||||
|
#include "toml.h"
|
||||||
#include "disk.h"
|
#include "disk.h"
|
||||||
|
|
||||||
#define CPM_RECORD_SIZE 128
|
#define CPM_RECORD_SIZE 128
|
||||||
#define CPM_RECORDS_PER_BLOCK 128
|
#define CPM_RECORDS_PER_BLOCK 128
|
||||||
#define CPM_BLOCK_SIZE CPM_RECORD_SIZE*CPM_RECORDS_PER_BLOCK
|
#define CPM_BLOCK_SIZE CPM_RECORD_SIZE*CPM_RECORDS_PER_BLOCK
|
||||||
|
|
||||||
|
// @todo Properly deal with errors
|
||||||
|
|
||||||
struct DirtyBlock {
|
struct DirtyBlock {
|
||||||
uint32_t block;
|
uint32_t block;
|
||||||
struct DirtyBlock* next;
|
struct DirtyBlock* next;
|
||||||
|
@ -27,6 +31,12 @@ typedef struct {
|
||||||
struct DirtyBlock* dirty_block;
|
struct DirtyBlock* dirty_block;
|
||||||
} Storage;
|
} Storage;
|
||||||
|
|
||||||
|
enum DiskType {
|
||||||
|
DISK_UNKNOWN,
|
||||||
|
DISK_RAW,
|
||||||
|
DISK_CPM,
|
||||||
|
} disk_type = DISK_RAW;
|
||||||
|
|
||||||
Storage storage;
|
Storage storage;
|
||||||
|
|
||||||
uint8_t disk_read_byte() {
|
uint8_t disk_read_byte() {
|
||||||
|
@ -58,12 +68,9 @@ void disk_write_byte(uint8_t value) {
|
||||||
if (storage.lba == 0) {
|
if (storage.lba == 0) {
|
||||||
snprintf(filename, 128, "0:loader.bin");
|
snprintf(filename, 128, "0:loader.bin");
|
||||||
offset = storage.lba - 0;
|
offset = storage.lba - 0;
|
||||||
} else if (storage.lba >= 1 && storage.lba < 45) {
|
} else if (storage.lba >= 1 && storage.lba < 256) {
|
||||||
snprintf(filename, 128, "0:cpm22.bin");
|
snprintf(filename, 128, "0:system.bin");
|
||||||
offset = storage.lba - 1;
|
offset = storage.lba - 1;
|
||||||
} else if (storage.lba >= 45 && storage.lba < 51) {
|
|
||||||
snprintf(filename, 128, "0:bios.bin");
|
|
||||||
offset = storage.lba - 45;
|
|
||||||
} else if (storage.lba >= 256 && storage.lba < 384) {
|
} else if (storage.lba >= 256 && storage.lba < 384) {
|
||||||
offset = storage.lba - 256;
|
offset = storage.lba - 256;
|
||||||
|
|
||||||
|
@ -301,12 +308,9 @@ void disk_receive_command(uint8_t command) {
|
||||||
if (storage.lba == 0) {
|
if (storage.lba == 0) {
|
||||||
snprintf(filename, 128, "0:loader.bin");
|
snprintf(filename, 128, "0:loader.bin");
|
||||||
offset = storage.lba - 0;
|
offset = storage.lba - 0;
|
||||||
} else if (storage.lba >= 1 && storage.lba < 45) {
|
} else if (storage.lba >= 1 && storage.lba < 256) {
|
||||||
snprintf(filename, 128, "0:cpm22.bin");
|
snprintf(filename, 128, "0:system.bin");
|
||||||
offset = storage.lba - 1;
|
offset = storage.lba - 1;
|
||||||
} else if (storage.lba >= 45 && storage.lba < 51) {
|
|
||||||
snprintf(filename, 128, "0:bios.bin");
|
|
||||||
offset = storage.lba - 45;
|
|
||||||
} else if (storage.lba >= 256 && storage.lba < 384) {
|
} else if (storage.lba >= 256 && storage.lba < 384) {
|
||||||
offset = storage.lba - 256;
|
offset = storage.lba - 256;
|
||||||
storage.size = 128;
|
storage.size = 128;
|
||||||
|
@ -517,6 +521,66 @@ void disk_init() {
|
||||||
printf("File error: %i\n\r", fr);
|
printf("File error: %i\n\r", fr);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
disk_type = DISK_RAW;
|
||||||
|
|
||||||
|
// @todo Get rid of all the nesting
|
||||||
|
FIL file;
|
||||||
|
fr = f_open(&file, "0:disk.tml", FA_READ);
|
||||||
|
if (fr == FR_OK) {
|
||||||
|
// @todo Do not hardcode size
|
||||||
|
char buffer[4096];
|
||||||
|
unsigned int bytes_read;
|
||||||
|
fr = f_read(&file, buffer, 4096-1, &bytes_read);
|
||||||
|
if (fr) {
|
||||||
|
printf("File error: %i\n\r", fr);
|
||||||
|
}
|
||||||
|
// Null terminate the string
|
||||||
|
buffer[bytes_read] = 0x00;
|
||||||
|
|
||||||
|
char errbuf[200];
|
||||||
|
toml_table_t* conf = toml_parse(buffer, errbuf, sizeof(errbuf));
|
||||||
|
|
||||||
|
fr = f_close(&file);
|
||||||
|
if (fr) {
|
||||||
|
printf("File error: %i\n\r", fr);
|
||||||
|
}
|
||||||
|
|
||||||
|
if (conf) {
|
||||||
|
toml_datum_t type = toml_string_in(conf, "type");
|
||||||
|
if (type.ok) {
|
||||||
|
if (!strcmp(type.u.s, "raw")) {
|
||||||
|
disk_type = DISK_RAW;
|
||||||
|
} else if (!strcmp(type.u.s, "cpm")) {
|
||||||
|
disk_type = DISK_CPM;
|
||||||
|
} else {
|
||||||
|
disk_type = DISK_UNKNOWN;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
} else {
|
||||||
|
printf("TOML Error: %s\n\r", errbuf);
|
||||||
|
}
|
||||||
|
|
||||||
|
} else {
|
||||||
|
printf("File error: %i\n\r", fr);
|
||||||
|
}
|
||||||
|
|
||||||
|
// @todo This is just for show
|
||||||
|
// Instead we need to make a jump table for every function
|
||||||
|
// Based on the disk_type the main function jumps to the correct sub function
|
||||||
|
switch (disk_type) {
|
||||||
|
case DISK_RAW:
|
||||||
|
printf("Raw disk, unimplemented!\n\r");
|
||||||
|
break;
|
||||||
|
|
||||||
|
case DISK_CPM:
|
||||||
|
printf("CPM disk, implemtened\n\r");
|
||||||
|
break;
|
||||||
|
|
||||||
|
default:
|
||||||
|
printf("Unknown disk type\n\r");
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
|
||||||
disk_get_entries();
|
disk_get_entries();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
2305
Src/toml.c
Normal file
2305
Src/toml.c
Normal file
File diff suppressed because it is too large
Load Diff
Loading…
Reference in New Issue
Block a user