mirror of
https://github.com/Polprzewodnikowy/N64FlashcartMenu.git
synced 2024-11-22 02:29:19 +01:00
Changed config library from toml to mini.c
toml library didn't offer any way to serialize config file
This commit is contained in:
parent
02010f1cbb
commit
a7c7373d9f
@ -15,7 +15,9 @@
|
|||||||
],
|
],
|
||||||
"settings": {
|
"settings": {
|
||||||
"git.ignoredRepositories": [
|
"git.ignoredRepositories": [
|
||||||
"libdragon"
|
"libdragon",
|
||||||
|
"src/libs/mini.c",
|
||||||
|
"src/libs/minimp3"
|
||||||
]
|
]
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
6
.gitmodules
vendored
6
.gitmodules
vendored
@ -2,3 +2,9 @@
|
|||||||
path = libdragon
|
path = libdragon
|
||||||
url = https://github.com/DragonMinded/libdragon
|
url = https://github.com/DragonMinded/libdragon
|
||||||
branch = unstable
|
branch = unstable
|
||||||
|
[submodule "src/libs/mini.c"]
|
||||||
|
path = src/libs/mini.c
|
||||||
|
url = https://github.com/univrsal/mini.c.git
|
||||||
|
[submodule "src/libs/minimp3"]
|
||||||
|
path = src/libs/minimp3
|
||||||
|
url = https://github.com/lieff/minimp3.git
|
||||||
|
2
Makefile
2
Makefile
@ -20,7 +20,7 @@ SRCS = \
|
|||||||
flashcart/flashcart.c \
|
flashcart/flashcart.c \
|
||||||
flashcart/sc64/sc64_internal.c \
|
flashcart/sc64/sc64_internal.c \
|
||||||
flashcart/sc64/sc64.c \
|
flashcart/sc64/sc64.c \
|
||||||
libs/toml/toml.c \
|
libs/mini.c/src/mini.c \
|
||||||
menu/actions.c \
|
menu/actions.c \
|
||||||
menu/assets.c \
|
menu/assets.c \
|
||||||
menu/menu.c \
|
menu/menu.c \
|
||||||
|
1
src/libs/mini.c
Submodule
1
src/libs/mini.c
Submodule
@ -0,0 +1 @@
|
|||||||
|
Subproject commit f713e3c98ee2340a90334da6084c34ec2109a7e6
|
1
src/libs/minimp3
Submodule
1
src/libs/minimp3
Submodule
@ -0,0 +1 @@
|
|||||||
|
Subproject commit afb604c06bc8beb145fecd42c0ceb5bda8795144
|
File diff suppressed because it is too large
Load Diff
File diff suppressed because it is too large
Load Diff
@ -1,13 +0,0 @@
|
|||||||
# Source
|
|
||||||
https://github.com/cktan/tomlc99
|
|
||||||
|
|
||||||
# License
|
|
||||||
MIT
|
|
||||||
|
|
||||||
# Description
|
|
||||||
Used for generating and reading config files in an easy to use format.
|
|
||||||
It currently targets version 1 of the spec and the lib might need updating from time to time.
|
|
||||||
|
|
||||||
# Notes
|
|
||||||
It might be preferable to change to a submodule.
|
|
||||||
There is currently an error related to -Werror=char-subscripts, possible solutions are in https://stackoverflow.com/questions/9972359/warning-array-subscript-has-type-char but for the moment all instances of `isdigit` have been adjusted to have `(unsigned char)` in the first parameter.
|
|
2380
src/libs/toml/toml.c
2380
src/libs/toml/toml.c
File diff suppressed because it is too large
Load Diff
@ -1,175 +0,0 @@
|
|||||||
/*
|
|
||||||
MIT License
|
|
||||||
|
|
||||||
Copyright (c) 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
|
|
||||||
|
|
||||||
#ifdef _MSC_VER
|
|
||||||
#pragma warning(disable: 4996)
|
|
||||||
#endif
|
|
||||||
|
|
||||||
#include <stdint.h>
|
|
||||||
#include <stdio.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);
|
|
||||||
/* ... returns 1 if key exists in tab, 0 otherwise */
|
|
||||||
TOML_EXTERN int toml_key_exists(const toml_table_t *tab, const char *key);
|
|
||||||
/* ... 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 */
|
|
@ -2,19 +2,16 @@
|
|||||||
|
|
||||||
#include "boot/boot.h"
|
#include "boot/boot.h"
|
||||||
#include "menu/menu.h"
|
#include "menu/menu.h"
|
||||||
#include "menu/settings.h"
|
|
||||||
|
|
||||||
|
|
||||||
int main (void) {
|
int main (void) {
|
||||||
settings_t settings;
|
boot_params_t boot_params;
|
||||||
|
|
||||||
settings_load_default_state(&settings);
|
menu_run(&boot_params);
|
||||||
|
|
||||||
menu_run(&settings);
|
|
||||||
|
|
||||||
disable_interrupts();
|
disable_interrupts();
|
||||||
|
|
||||||
boot(&settings.boot_params);
|
boot(&boot_params);
|
||||||
|
|
||||||
assertf(false, "Unexpected return from 'boot' function");
|
assertf(false, "Unexpected return from 'boot' function");
|
||||||
|
|
||||||
|
@ -2,6 +2,7 @@
|
|||||||
|
|
||||||
#include <libdragon.h>
|
#include <libdragon.h>
|
||||||
|
|
||||||
|
#include "boot/boot.h"
|
||||||
#include "actions.h"
|
#include "actions.h"
|
||||||
#include "assets.h"
|
#include "assets.h"
|
||||||
#include "flashcart/flashcart.h"
|
#include "flashcart/flashcart.h"
|
||||||
@ -13,17 +14,19 @@
|
|||||||
#include "views/views.h"
|
#include "views/views.h"
|
||||||
|
|
||||||
|
|
||||||
|
#define SETTINGS_FILE_PATH "config.txt"
|
||||||
|
|
||||||
|
|
||||||
static menu_t *menu;
|
static menu_t *menu;
|
||||||
static bool boot_pending;
|
static bool boot_pending;
|
||||||
|
|
||||||
|
|
||||||
static void menu_init (settings_t *settings) {
|
static void menu_init (boot_params_t *boot_params) {
|
||||||
controller_init();
|
controller_init();
|
||||||
timer_init();
|
timer_init();
|
||||||
rtc_init();
|
rtc_init();
|
||||||
audio_init(44100, 2);
|
audio_init(44100, 2);
|
||||||
mixer_init(2);
|
mixer_init(2);
|
||||||
display_init(RESOLUTION_640x480, DEPTH_16_BPP, 2, GAMMA_NONE, ANTIALIAS_OFF);
|
|
||||||
rspq_init();
|
rspq_init();
|
||||||
rdpq_init();
|
rdpq_init();
|
||||||
|
|
||||||
@ -38,20 +41,28 @@ static void menu_init (settings_t *settings) {
|
|||||||
menu->mode = MENU_MODE_NONE;
|
menu->mode = MENU_MODE_NONE;
|
||||||
menu->next_mode = MENU_MODE_STARTUP;
|
menu->next_mode = MENU_MODE_STARTUP;
|
||||||
|
|
||||||
|
settings_set_default_state(&menu->settings);
|
||||||
|
|
||||||
menu->flashcart_error = flashcart_init();
|
menu->flashcart_error = flashcart_init();
|
||||||
if (menu->flashcart_error != FLASHCART_OK) {
|
if (menu->flashcart_error != FLASHCART_OK) {
|
||||||
menu->next_mode = MENU_MODE_FAULT;
|
menu->next_mode = MENU_MODE_FAULT;
|
||||||
} else {
|
} else {
|
||||||
// settings_load_from_file(settings);
|
settings_load_from_file(SETTINGS_FILE_PATH, &menu->settings);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
menu->boot_params = boot_params;
|
||||||
|
|
||||||
|
bool default_directory_exists = directory_exists(menu->settings.default_directory);
|
||||||
|
|
||||||
menu->browser.valid = false;
|
menu->browser.valid = false;
|
||||||
if (file_exists(settings->last_state.directory)) {
|
menu->browser.directory = path_init(default_directory_exists ? menu->settings.default_directory : NULL);
|
||||||
menu->browser.directory = path_init(settings->last_state.directory);
|
|
||||||
} else {
|
if ((get_tv_type() == TV_PAL) && menu->settings.pal60) {
|
||||||
menu->browser.directory = path_init(NULL);
|
// HACK: Set TV type to NTSC, so PAL console would output 60 Hz signal instead.
|
||||||
|
*((uint32_t *) (0x80000300)) = TV_NTSC;
|
||||||
}
|
}
|
||||||
menu->browser.show_hidden = false;
|
|
||||||
|
display_init(RESOLUTION_640x480, DEPTH_16_BPP, 2, GAMMA_NONE, ANTIALIAS_OFF);
|
||||||
}
|
}
|
||||||
|
|
||||||
static void menu_deinit (menu_t *menu) {
|
static void menu_deinit (menu_t *menu) {
|
||||||
@ -62,16 +73,16 @@ static void menu_deinit (menu_t *menu) {
|
|||||||
|
|
||||||
rdpq_close();
|
rdpq_close();
|
||||||
rspq_close();
|
rspq_close();
|
||||||
display_close();
|
|
||||||
mixer_close();
|
mixer_close();
|
||||||
audio_close();
|
audio_close();
|
||||||
rtc_close();
|
rtc_close();
|
||||||
timer_close();
|
timer_close();
|
||||||
|
display_close();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
void menu_run (settings_t *settings) {
|
void menu_run (boot_params_t *boot_params) {
|
||||||
menu_init(settings);
|
menu_init(boot_params);
|
||||||
|
|
||||||
int audio_buffer_length = audio_get_buffer_length();
|
int audio_buffer_length = audio_get_buffer_length();
|
||||||
|
|
||||||
|
@ -2,10 +2,10 @@
|
|||||||
#define MENU_H__
|
#define MENU_H__
|
||||||
|
|
||||||
|
|
||||||
#include "settings.h"
|
#include "boot/boot.h"
|
||||||
|
|
||||||
|
|
||||||
void menu_run (settings_t *settings);
|
void menu_run (boot_params_t *boot_params);
|
||||||
|
|
||||||
|
|
||||||
#endif
|
#endif
|
||||||
|
@ -2,8 +2,10 @@
|
|||||||
#define MENU_STRUCT_H__
|
#define MENU_STRUCT_H__
|
||||||
|
|
||||||
|
|
||||||
|
#include "boot/boot.h"
|
||||||
#include "flashcart/flashcart.h"
|
#include "flashcart/flashcart.h"
|
||||||
#include "path.h"
|
#include "path.h"
|
||||||
|
#include "settings.h"
|
||||||
|
|
||||||
|
|
||||||
#define BROWSER_LIST_SIZE 10000
|
#define BROWSER_LIST_SIZE 10000
|
||||||
@ -41,6 +43,8 @@ typedef struct {
|
|||||||
menu_mode_t mode;
|
menu_mode_t mode;
|
||||||
menu_mode_t next_mode;
|
menu_mode_t next_mode;
|
||||||
|
|
||||||
|
settings_t settings;
|
||||||
|
boot_params_t *boot_params;
|
||||||
flashcart_error_t flashcart_error;
|
flashcart_error_t flashcart_error;
|
||||||
|
|
||||||
struct {
|
struct {
|
||||||
@ -65,7 +69,6 @@ typedef struct {
|
|||||||
entry_t list[BROWSER_LIST_SIZE];
|
entry_t list[BROWSER_LIST_SIZE];
|
||||||
int entries;
|
int entries;
|
||||||
int selected;
|
int selected;
|
||||||
bool show_hidden;
|
|
||||||
} browser;
|
} browser;
|
||||||
} menu_t;
|
} menu_t;
|
||||||
|
|
||||||
|
@ -1,180 +1,49 @@
|
|||||||
#include <stdio.h>
|
|
||||||
#include <string.h>
|
|
||||||
#include <sys/stat.h>
|
|
||||||
#include <unistd.h>
|
|
||||||
|
|
||||||
#include <libdragon.h>
|
#include <libdragon.h>
|
||||||
|
|
||||||
#include "flashcart/flashcart.h"
|
#include "libs/mini.c/src/mini.h"
|
||||||
#include "libs/toml/toml.h"
|
#include "path.h"
|
||||||
#include "boot/boot.h"
|
|
||||||
|
|
||||||
#include "settings.h"
|
#include "settings.h"
|
||||||
|
#include "utils/fs.h"
|
||||||
|
|
||||||
|
|
||||||
void settings_load_from_file(settings_t *settings) {
|
void settings_set_default_state (settings_t *settings) {
|
||||||
FILE *fp = fopen(SC64_SETTINGS_FILEPATH, "r");
|
settings->pal60 = false;
|
||||||
if (!fp) {
|
settings->show_hidden_files = false;
|
||||||
printf("Error loading config file %s\n", SC64_SETTINGS_FILEPATH);
|
settings->default_directory = "/";
|
||||||
// Generate a default config file.
|
|
||||||
printf("Creating a new one!\n");
|
|
||||||
wait_ms(10000);
|
|
||||||
settings_load_default_state(settings);
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
|
|
||||||
char error_buffer[256];
|
|
||||||
toml_table_t *conf = toml_parse_file(fp, error_buffer, sizeof(error_buffer));
|
|
||||||
fclose(fp);
|
|
||||||
|
|
||||||
if (!conf) {
|
|
||||||
printf("Error parsing config: %s\n", error_buffer);
|
|
||||||
wait_ms(10000);
|
|
||||||
printf("Attempt a repair!\n");
|
|
||||||
settings_validate();
|
|
||||||
printf("Creating a new one!\n");
|
|
||||||
settings_load_default_state(settings);
|
|
||||||
//assertf(!conf, "Couldn't parse toml config: %s", error_buffer); // TODO: work out why and handle appropriately.
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
|
|
||||||
// Handle last_rom
|
|
||||||
toml_table_t *last_rom = toml_table_in(conf, "last_rom");
|
|
||||||
if (!last_rom) {
|
|
||||||
printf("Missing '[last_rom]' header in config\n");
|
|
||||||
wait_ms(10000);
|
|
||||||
}
|
|
||||||
else {
|
|
||||||
toml_datum_t rom_path = toml_string_in(last_rom, "rom_path");
|
|
||||||
if (!rom_path.ok) {
|
|
||||||
printf("Couldn't read 'rom_path' value in config\n");
|
|
||||||
wait_ms(10000);
|
|
||||||
}
|
|
||||||
else {
|
|
||||||
printf("Found rom path: %s\n", rom_path.u.s);
|
|
||||||
settings->last_rom.rom_path = rom_path.u.s;
|
|
||||||
}
|
|
||||||
|
|
||||||
toml_datum_t save_path = toml_string_in(last_rom, "save_path");
|
|
||||||
if (!save_path.ok) {
|
|
||||||
printf("Couldn't read 'save_path' value in config\n");
|
|
||||||
wait_ms(10000);
|
|
||||||
}
|
|
||||||
else {
|
|
||||||
printf("Found save path: %s\n", save_path.u.s);
|
|
||||||
settings->last_rom.save_path = save_path.u.s;
|
|
||||||
}
|
|
||||||
|
|
||||||
toml_datum_t tmp_save_type = toml_int_in(last_rom, "save_type");
|
|
||||||
if (!tmp_save_type.ok) {
|
|
||||||
printf("Couldn't read 'save_type' value in config\n");
|
|
||||||
wait_ms(10000);
|
|
||||||
}
|
|
||||||
else {
|
|
||||||
assertf((int)tmp_save_type.u.i < __FLASHCART_SAVE_TYPE_END, "Invalid save type in config file");
|
|
||||||
printf("Found save type: %d\n", (int)tmp_save_type.u.i);
|
|
||||||
settings->last_rom.save_type = (int)tmp_save_type.u.i;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
// Handle last_state
|
|
||||||
toml_table_t* last_state = toml_table_in(conf, "last_state");
|
|
||||||
if (!last_state) {
|
|
||||||
printf("Missing '[last_state]' header in config\n");
|
|
||||||
wait_ms(10000);
|
|
||||||
}
|
|
||||||
else {
|
|
||||||
|
|
||||||
// toml_datum_t current_directory = toml_string_in(last_state, "current_directory");
|
|
||||||
// if (!current_directory.ok) {
|
|
||||||
// printf("Couldn't read 'current_directory' value in config\n");
|
|
||||||
// printf("Defaulting to root directory.\n");
|
|
||||||
// settings->last_state.current_directory = "sd://";
|
|
||||||
// wait_ms(5000);
|
|
||||||
// }
|
|
||||||
// else {
|
|
||||||
// printf("Found current directory: %s\n", current_directory.u.s );
|
|
||||||
// settings->last_state.current_directory = current_directory.u.s;
|
|
||||||
// }
|
|
||||||
|
|
||||||
// toml_datum_t tmp_auto_load_last_rom = toml_bool_in(last_state, "auto_load");
|
|
||||||
// if (!tmp_auto_load_last_rom.ok) {
|
|
||||||
// printf("Couldn't read 'auto_load' value in config\n");
|
|
||||||
// printf("Defaulting to false.\n");
|
|
||||||
// wait_ms(5000);
|
|
||||||
// settings->last_state.auto_load_last_rom = false;
|
|
||||||
// }
|
|
||||||
// else {
|
|
||||||
// printf("Found autoload: %s\n", tmp_auto_load_last_rom.u.b ? "true" : "false");
|
|
||||||
// settings->last_state.auto_load_last_rom = tmp_auto_load_last_rom.u.b;
|
|
||||||
// }
|
|
||||||
}
|
|
||||||
|
|
||||||
// Handle boot_params
|
|
||||||
toml_table_t* boot_params = toml_table_in(conf, "boot_params");
|
|
||||||
if (!boot_params) {
|
|
||||||
printf("Missing '[boot_params]' header in config\n");
|
|
||||||
wait_ms(10000);
|
|
||||||
}
|
|
||||||
else {
|
|
||||||
|
|
||||||
}
|
|
||||||
|
|
||||||
toml_free(conf);
|
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
void settings_save(const char* filename, const settings_t* settings) {
|
void settings_save_to_file (char *path, settings_t *settings) {
|
||||||
// FILE* fp = fopen(filename, "wb");
|
path_t *config_file_path = path_init("sd:/");
|
||||||
// if (!fp) {
|
path_append(config_file_path, path);
|
||||||
// perror("Failed to open file for writing");
|
|
||||||
// return 1;
|
|
||||||
// }
|
|
||||||
|
|
||||||
|
mini_t *ini = mini_create(path_get(config_file_path));
|
||||||
|
|
||||||
// // Populate settings data...
|
mini_set_bool(ini, "menu", "pal60", settings->pal60);
|
||||||
|
mini_set_bool(ini, "menu", "show_hidden_files", settings->show_hidden_files);
|
||||||
|
mini_set_string(ini, "menu", "default_directory", settings->default_directory);
|
||||||
|
|
||||||
|
mini_save(ini);
|
||||||
|
|
||||||
// if (result != 0) {
|
mini_free(ini);
|
||||||
// fprintf(stderr, "Failed to write TOML data to file\n");
|
|
||||||
// }
|
|
||||||
|
|
||||||
|
path_free(config_file_path);
|
||||||
// fclose(fp);
|
|
||||||
|
|
||||||
// return result;
|
|
||||||
return;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
void settings_load_default_state(settings_t *settings) {
|
void settings_load_from_file (char *path, settings_t *settings) {
|
||||||
// Happens on init
|
if (!file_exists(path)) {
|
||||||
// TODO: should also happen as a last resort
|
settings_save_to_file(path, settings);
|
||||||
// Mainly if the file does not exist, or is corrupted beyond repair.
|
}
|
||||||
//#ifdef SETTINGS_SCHEMA_VERSION 1
|
|
||||||
settings->last_rom.rom_path = "";
|
|
||||||
settings->last_rom.save_path = "";
|
|
||||||
settings->last_rom.save_type = FLASHCART_SAVE_TYPE_NONE;
|
|
||||||
settings->last_rom.save_writeback = false;
|
|
||||||
|
|
||||||
settings->last_state.directory = ""; // This must not include the trailing slash on dirs!
|
path_t *config_file_path = path_init("sd:/");
|
||||||
settings->last_state.auto_load_last_rom = false;
|
path_append(config_file_path, path);
|
||||||
|
|
||||||
settings->boot_params.device_type = BOOT_DEVICE_TYPE_ROM;
|
mini_t *ini = mini_try_load(path_get(config_file_path));
|
||||||
settings->boot_params.reset_type = BOOT_RESET_TYPE_NMI;
|
|
||||||
settings->boot_params.tv_type = BOOT_TV_TYPE_PASSTHROUGH;
|
|
||||||
settings->boot_params.detect_cic_seed = true;
|
|
||||||
|
|
||||||
// Initialize other default settings...
|
settings->pal60 = mini_get_bool(ini, "menu", "pal60", false);
|
||||||
//#endif
|
settings->show_hidden_files = mini_get_bool(ini, "menu", "show_hidden_files", false);
|
||||||
}
|
settings->default_directory = strdup(mini_get_string(ini, "menu", "default_directory", "/"));
|
||||||
|
|
||||||
void settings_reset(void) {
|
mini_free(ini);
|
||||||
|
|
||||||
}
|
path_free(config_file_path);
|
||||||
|
|
||||||
void settings_validate(void) {
|
|
||||||
// Validate settings against a file schema...
|
|
||||||
// TODO: should validate against a file schema.
|
|
||||||
// Must take into account that the settings will change in future, so should be backwards compatible.
|
|
||||||
}
|
}
|
||||||
|
@ -1,41 +1,17 @@
|
|||||||
#ifndef SETTINGS_H__
|
#ifndef SETTINGS_H__
|
||||||
#define SETTINGS_H__
|
#define SETTINGS_H__
|
||||||
|
|
||||||
#include "flashcart/flashcart.h"
|
|
||||||
#include "boot/boot.h"
|
|
||||||
|
|
||||||
#define SC64_SETTINGS_FILEPATH "sd://config.sc64.toml.txt"
|
|
||||||
#define SETTINGS_SCHEMA_VERSION 1
|
|
||||||
|
|
||||||
|
|
||||||
typedef struct {
|
typedef struct {
|
||||||
char *rom_path;
|
bool pal60;
|
||||||
char *save_path;
|
bool show_hidden_files;
|
||||||
flashcart_save_type_t save_type; //TODO: should this be converted from a string, or only use an integer value?
|
char *default_directory;
|
||||||
bool save_writeback; // TODO: this is likely SC64 specific.
|
|
||||||
} settings_last_rom_t;
|
|
||||||
|
|
||||||
typedef struct {
|
|
||||||
bool auto_load_last_rom;
|
|
||||||
char* directory;
|
|
||||||
// TODO:
|
|
||||||
// Menu layout: list vs grid
|
|
||||||
// Hide extensions
|
|
||||||
// Hide hidden files and dirs
|
|
||||||
// colour scheme
|
|
||||||
// background pic
|
|
||||||
} settings_last_state_t;
|
|
||||||
|
|
||||||
typedef struct {
|
|
||||||
settings_last_rom_t last_rom;
|
|
||||||
settings_last_state_t last_state;
|
|
||||||
boot_params_t boot_params;
|
|
||||||
} settings_t;
|
} settings_t;
|
||||||
|
|
||||||
void settings_load_from_file (settings_t *settings);
|
|
||||||
void settings_save(const char* filename, const settings_t* settings);
|
void settings_set_default_state (settings_t *settings);
|
||||||
void settings_reset (void);
|
void settings_save_to_file (char *path, settings_t *settings);
|
||||||
void settings_load_default_state(settings_t *settings);
|
void settings_load_from_file (char *path, settings_t *settings);
|
||||||
void settings_validate (void);
|
|
||||||
|
|
||||||
#endif
|
#endif
|
||||||
|
@ -69,14 +69,17 @@ static bool load_directory (menu_t *menu) {
|
|||||||
if (info.fattrib & AM_SYS) {
|
if (info.fattrib & AM_SYS) {
|
||||||
continue;
|
continue;
|
||||||
}
|
}
|
||||||
if (info.fattrib & AM_HID && !menu->browser.show_hidden) {
|
if ((info.fattrib & AM_HID) && !menu->settings.show_hidden_files) {
|
||||||
continue;
|
continue;
|
||||||
}
|
}
|
||||||
|
|
||||||
entry_t *entry = &menu->browser.list[menu->browser.entries++];
|
entry_t *entry = &menu->browser.list[menu->browser.entries];
|
||||||
|
|
||||||
entry->name = strdup(info.fname);
|
entry->name = strdup(info.fname);
|
||||||
assert(entry->name != NULL);
|
if (!entry->name) {
|
||||||
|
f_closedir(&dir);
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
|
||||||
if (info.fattrib & AM_DIR) {
|
if (info.fattrib & AM_DIR) {
|
||||||
entry->type = ENTRY_TYPE_DIR;
|
entry->type = ENTRY_TYPE_DIR;
|
||||||
@ -91,6 +94,8 @@ static bool load_directory (menu_t *menu) {
|
|||||||
}
|
}
|
||||||
|
|
||||||
entry->size = info.fsize;
|
entry->size = info.fsize;
|
||||||
|
|
||||||
|
menu->browser.entries += 1;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (f_closedir(&dir) != FR_OK) {
|
if (f_closedir(&dir) != FR_OK) {
|
||||||
@ -146,9 +151,9 @@ static bool pop_directory (menu_t *menu) {
|
|||||||
}
|
}
|
||||||
|
|
||||||
static void format_size (char *buffer, int size) {
|
static void format_size (char *buffer, int size) {
|
||||||
if (size < 10000) {
|
if (size < 8 * 1024) {
|
||||||
sprintf(buffer, "%4d B ", size);
|
sprintf(buffer, "%4d B ", size);
|
||||||
} else if (size < 10000000) {
|
} else if (size < 8 * 1024 * 1024) {
|
||||||
sprintf(buffer, "%4d kB", size / 1024);
|
sprintf(buffer, "%4d kB", size / 1024);
|
||||||
} else if (size < 1 * 1024 * 1024 * 1024) {
|
} else if (size < 1 * 1024 * 1024 * 1024) {
|
||||||
sprintf(buffer, "%4d MB", size / 1024 / 1024);
|
sprintf(buffer, "%4d MB", size / 1024 / 1024);
|
||||||
@ -303,7 +308,6 @@ static void draw (menu_t *menu, surface_t *d) {
|
|||||||
text_y += layout->line_height;
|
text_y += layout->line_height;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
if (menu->browser.entries == 0) {
|
if (menu->browser.entries == 0) {
|
||||||
fragment_text_set_color(other_color);
|
fragment_text_set_color(other_color);
|
||||||
fragment_textf(text_x, text_y, "** empty directory **");
|
fragment_textf(text_x, text_y, "** empty directory **");
|
||||||
|
@ -1,6 +1,7 @@
|
|||||||
#include <libdragon.h>
|
#include <libdragon.h>
|
||||||
|
|
||||||
#include "../rom_database.h"
|
#include "../rom_database.h"
|
||||||
|
#include "boot/boot.h"
|
||||||
#include "flashcart/flashcart.h"
|
#include "flashcart/flashcart.h"
|
||||||
#include "fragments/fragments.h"
|
#include "fragments/fragments.h"
|
||||||
#include "views.h"
|
#include "views.h"
|
||||||
@ -108,6 +109,11 @@ static void load (menu_t *menu) {
|
|||||||
}
|
}
|
||||||
|
|
||||||
path_free(path);
|
path_free(path);
|
||||||
|
|
||||||
|
menu->boot_params->device_type = BOOT_DEVICE_TYPE_ROM;
|
||||||
|
menu->boot_params->reset_type = BOOT_RESET_TYPE_COLD;
|
||||||
|
menu->boot_params->tv_type = BOOT_TV_TYPE_PASSTHROUGH;
|
||||||
|
menu->boot_params->detect_cic_seed = true;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
@ -16,6 +16,15 @@ bool file_exists (char *path) {
|
|||||||
return (fr == FR_OK);
|
return (fr == FR_OK);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
bool directory_exists (char *path) {
|
||||||
|
FRESULT fr;
|
||||||
|
FILINFO fno;
|
||||||
|
|
||||||
|
fr = f_stat(path, &fno);
|
||||||
|
|
||||||
|
return ((fr == FR_OK) && (fno.fattrib & AM_DIR));
|
||||||
|
}
|
||||||
|
|
||||||
size_t file_get_size (char *path) {
|
size_t file_get_size (char *path) {
|
||||||
FILINFO fno;
|
FILINFO fno;
|
||||||
|
|
||||||
|
@ -11,6 +11,7 @@
|
|||||||
|
|
||||||
|
|
||||||
bool file_exists (char *path);
|
bool file_exists (char *path);
|
||||||
|
bool directory_exists (char *path);
|
||||||
size_t file_get_size (char *path);
|
size_t file_get_size (char *path);
|
||||||
bool file_allocate (char *path, size_t size);
|
bool file_allocate (char *path, size_t size);
|
||||||
bool file_get_sectors (char *path, uint32_t *sectors, size_t entries);
|
bool file_get_sectors (char *path, uint32_t *sectors, size_t entries);
|
||||||
|
Loading…
Reference in New Issue
Block a user