mirror of
https://github.com/sanni/cartreader.git
synced 2024-11-26 14:34:15 +01:00
Added ability to use config file for some options.
A sample `config.txt` is in the SD folder. Currently the option is disabled by default and must be enabled. Also: * Eliminated the 5V spike at boot when VSELECT is installed and enabled. See discussion #906 * Fixed a warning in `MD.ino` * Did some code cleanup, more cleanup to come.
This commit is contained in:
parent
35eca2a9f4
commit
3468703a51
@ -66,7 +66,6 @@
|
||||
*****************************************/
|
||||
|
||||
// SD Card
|
||||
#include "SdFat.h"
|
||||
SdFs sd;
|
||||
FsFile myFile;
|
||||
#ifdef global_log
|
||||
@ -2117,30 +2116,45 @@ int32_t initializeClockOffset() {
|
||||
Setup
|
||||
*****************************************/
|
||||
void setup() {
|
||||
#if !defined(enable_serial) && defined(ENABLE_UPDATER)
|
||||
ClockedSerial.begin(UPD_BAUD);
|
||||
#endif
|
||||
|
||||
// Set Button Pin PG2 to Input
|
||||
DDRG &= ~(1 << 2);
|
||||
# if defined(HW5) && !defined(ENABLE_VSELECT)
|
||||
// HW5 has status LED connected to PD7
|
||||
// Set LED Pin PD7 to Output
|
||||
/**
|
||||
* HW5 has status LED connected to PD7
|
||||
* Set LED Pin PD7 to Output
|
||||
**/
|
||||
DDRD |= (1 << 7);
|
||||
PORTD |= (1 << 7);
|
||||
# elif defined(ENABLE_VSELECT)
|
||||
/**
|
||||
* VSELECT uses pin PD7
|
||||
* Set LED Pin PD7 to Output
|
||||
**/
|
||||
DDRD |= (1 << 7);
|
||||
#else
|
||||
// HW1/2/3 have button connected to PD7
|
||||
// Set Button Pin PD7 to Input
|
||||
# else /* !defined(HW5) && !defined(HW5) */
|
||||
/**
|
||||
* HW1-3 have button connected to PD7
|
||||
* Set pin PD7 to input for button
|
||||
**/
|
||||
DDRD &= ~(1 << 7);
|
||||
#endif
|
||||
// Activate Internal Pullup Resistors
|
||||
//PORTG |= (1 << 2);
|
||||
//PORTD |= (1 << 7);
|
||||
# endif /* HW5 &| ENABLE_VSELECT */
|
||||
|
||||
// Set power to low to protect carts
|
||||
setVoltage(VOLTS_SET_3V3);
|
||||
|
||||
// Read current folder number out of eeprom
|
||||
# if defined(ENABLE_3V3FIX)
|
||||
// Set clock high during setup
|
||||
setClockScale(CLKSCALE_16MHZ);
|
||||
delay(10);
|
||||
# endif /* ENABLE_3V3FIX */
|
||||
|
||||
# if !defined(enable_serial) && defined(ENABLE_UPDATER)
|
||||
ClockedSerial.begin(UPD_BAUD);
|
||||
printVersionToSerial();
|
||||
ClockedSerial.flush();
|
||||
# endif /* ENABLE_UPDATER */
|
||||
|
||||
// Read current folder number out of the EEPROM
|
||||
EEPROM_readAnything(0, foldern);
|
||||
if (foldern < 0) foldern = 0;
|
||||
|
||||
@ -2148,50 +2162,44 @@ void setup() {
|
||||
display.begin();
|
||||
display.setContrast(40);
|
||||
display.setFont(u8g2_font_haxrcorp4089_tr);
|
||||
#endif
|
||||
# endif /* enable_LCD */
|
||||
|
||||
# ifdef enable_neopixel
|
||||
#if defined(ENABLE_3V3FIX)
|
||||
// Set power high for neopixel
|
||||
setVoltage(VOLTS_SET_5V);
|
||||
delay(10);
|
||||
#endif
|
||||
pixels.begin();
|
||||
pixels.clear();
|
||||
pixels.setPixelColor(0, pixels.Color(background_color));
|
||||
pixels.setPixelColor(1, pixels.Color(0, 0, 100));
|
||||
pixels.setPixelColor(2, pixels.Color(0, 0, 100));
|
||||
pixels.show();
|
||||
setColor_RGB(0, 0, 100);
|
||||
|
||||
// Set TX0 LED Pin(PE1) to Output for status indication during flashing for HW4
|
||||
# if !(defined(enable_serial) || defined(HW5))
|
||||
DDRE |= (1 << 1);
|
||||
#endif
|
||||
#else
|
||||
# endif /* enable_serial */
|
||||
# else /* enable_neopixel */
|
||||
# ifndef enable_LCD
|
||||
# ifdef CA_LED
|
||||
// Turn LED off
|
||||
digitalWrite(12, 1);
|
||||
digitalWrite(11, 1);
|
||||
digitalWrite(10, 1);
|
||||
#endif
|
||||
# endif /* CA_LED */
|
||||
// Configure 4 Pin RGB LED pins as output
|
||||
DDRB |= (1 << DDB6); // Red LED (pin 12)
|
||||
DDRB |= (1 << DDB5); // Green LED (pin 11)
|
||||
DDRB |= (1 << DDB4); // Blue LED (pin 10)
|
||||
#endif
|
||||
#endif
|
||||
# endif /* enable_LCD */
|
||||
# endif /* enable_neopixel */
|
||||
|
||||
#ifdef ENABLE_VSELECT
|
||||
// Set power to low to protect carts
|
||||
setVoltage(VOLTS_SET_3V3);
|
||||
#endif
|
||||
# ifdef RTC_installed
|
||||
// Start RTC
|
||||
RTCStart();
|
||||
|
||||
// Set Date/Time Callback Funtion
|
||||
SdFile::dateTimeCallback(dateTime);
|
||||
# endif /* RTC_installed */
|
||||
|
||||
# ifdef enable_OLED
|
||||
display.begin();
|
||||
//isplay.setContrast(40);
|
||||
display.setFont(u8g2_font_haxrcorp4089_tr);
|
||||
#endif
|
||||
# endif /* enable_OLED */
|
||||
|
||||
# ifdef enable_serial
|
||||
// Serial Begin
|
||||
@ -2201,18 +2209,43 @@ void setup() {
|
||||
Serial.println(F("2023 github.com/sanni"));
|
||||
// LED Error
|
||||
setColor_RGB(0, 0, 255);
|
||||
#endif
|
||||
# endif /* enable_serial */
|
||||
|
||||
// Init SD card
|
||||
if (!sd.begin(SS)) {
|
||||
display_Clear();
|
||||
# ifdef ENABLE_VSELECT
|
||||
print_STR(sd_error_STR, 1);
|
||||
println_Msg(F(""));
|
||||
println_Msg(F("Press button to enable 5V for"));
|
||||
println_Msg(F(" updating firmware..."));
|
||||
display_Update();
|
||||
wait();
|
||||
display_Clear();
|
||||
setVoltage(VOLTS_SET_5V); // Set voltage high for flashing
|
||||
println_Msg(F(" ======== UPDATE MODE ======== "));
|
||||
println_Msg(F("Waiting for update..."));
|
||||
println_Msg(F(""));
|
||||
println_Msg(F("Press button to cancel/restart."));
|
||||
display_Update();
|
||||
wait();
|
||||
resetArduino();
|
||||
# else /* !ENABLE_VSELECT */
|
||||
print_FatalError(sd_error_STR);
|
||||
# endif /* ENABLE_VSELECT */
|
||||
}
|
||||
|
||||
#if !defined(enable_serial) && defined(ENABLE_UPDATER)
|
||||
printVersionToSerial();
|
||||
ClockedSerial.flush();
|
||||
#endif
|
||||
# if defined(ENABLE_CONFIG)
|
||||
configInit();
|
||||
# if defined(global_log)
|
||||
loggingEnabled = !!configGetLong(F("oscr.logging"), 1);
|
||||
# endif /*ENABLE_CONFIG*/
|
||||
|
||||
// Change LCD background if config specified
|
||||
# ifdef enable_neopixel
|
||||
setColor_RGB(0, 0, 100);
|
||||
# endif /* enable_neopixel */
|
||||
# endif /* ENABLE_CONFIG */
|
||||
|
||||
# ifdef global_log
|
||||
if (!myLog.open("OSCR_LOG.txt", O_RDWR | O_CREAT | O_APPEND)) {
|
||||
@ -2231,22 +2264,18 @@ void setup() {
|
||||
print_Msg(F("OSCR HW5"));
|
||||
# elif defined(SERIAL_MONITOR)
|
||||
print_Msg(F("OSCR Serial"));
|
||||
#endif
|
||||
# endif /* HWn */
|
||||
print_Msg(F(" V"));
|
||||
println_Msg(ver);
|
||||
#endif
|
||||
# endif /* global_log */
|
||||
|
||||
#ifdef RTC_installed
|
||||
// Start RTC
|
||||
RTCStart();
|
||||
|
||||
// Set Date/Time Callback Funtion
|
||||
SdFile::dateTimeCallback(dateTime);
|
||||
#endif
|
||||
|
||||
// status LED ON
|
||||
// Turn status LED on
|
||||
statusLED(true);
|
||||
|
||||
# if defined(ENABLE_3V3FIX)
|
||||
setClockScale(CLKSCALE_8MHZ); // Set clock back to low after setup
|
||||
# endif /* ENABLE_3V3FIX */
|
||||
|
||||
// Start menu system
|
||||
mainMenu();
|
||||
}
|
||||
@ -2280,8 +2309,24 @@ void setColor_RGB(byte r, byte g, byte b) {
|
||||
if (r >= 100) r = 100;
|
||||
if (g >= 100) g = 100;
|
||||
if (b >= 100) b = 100;
|
||||
|
||||
pixels.clear();
|
||||
|
||||
# if defined(ENABLE_CONFIG)
|
||||
uint8_t lcdConfColor = configGetLong(F("lcd.confColor"));
|
||||
|
||||
if (lcdConfColor > 0) {
|
||||
uint8_t lcdRed = configGetLong(F("lcd.red"));
|
||||
uint8_t lcdGreen = configGetLong(F("lcd.green"));
|
||||
uint8_t lcdBlue = configGetLong(F("lcd.blue"));
|
||||
|
||||
pixels.setPixelColor(0, pixels.Color(lcdGreen, lcdRed, lcdBlue));
|
||||
} else {
|
||||
pixels.setPixelColor(0, pixels.Color(background_color));
|
||||
}
|
||||
# else /* !ENABLE_CONFIG */
|
||||
pixels.setPixelColor(0, pixels.Color(background_color));
|
||||
# endif /* ENABLE_CONFIG */
|
||||
pixels.setPixelColor(1, pixels.Color(g, r, b));
|
||||
pixels.setPixelColor(2, pixels.Color(g, r, b));
|
||||
pixels.show();
|
||||
@ -2465,7 +2510,7 @@ void print_Msg(const __FlashStringHelper* string) {
|
||||
Serial.print(string);
|
||||
#endif
|
||||
#ifdef global_log
|
||||
if (!dont_log) myLog.print(string);
|
||||
if (!dont_log && loggingEnabled) myLog.print(string);
|
||||
#endif
|
||||
}
|
||||
|
||||
@ -2494,7 +2539,7 @@ void print_Msg(const char myString[]) {
|
||||
Serial.print(myString);
|
||||
#endif
|
||||
#ifdef global_log
|
||||
if (!dont_log) myLog.print(myString);
|
||||
if (!dont_log && loggingEnabled) myLog.print(myString);
|
||||
#endif
|
||||
}
|
||||
|
||||
@ -2506,7 +2551,7 @@ void print_Msg(long unsigned int message) {
|
||||
Serial.print(message);
|
||||
#endif
|
||||
#ifdef global_log
|
||||
if (!dont_log) myLog.print(message);
|
||||
if (!dont_log && loggingEnabled) myLog.print(message);
|
||||
#endif
|
||||
}
|
||||
|
||||
@ -2518,7 +2563,7 @@ void print_Msg(byte message, int outputFormat) {
|
||||
Serial.print(message, outputFormat);
|
||||
#endif
|
||||
#ifdef global_log
|
||||
if (!dont_log) myLog.print(message, outputFormat);
|
||||
if (!dont_log && loggingEnabled) myLog.print(message, outputFormat);
|
||||
#endif
|
||||
}
|
||||
|
||||
@ -2530,7 +2575,7 @@ void print_Msg(word message, int outputFormat) {
|
||||
Serial.print(message, outputFormat);
|
||||
#endif
|
||||
#ifdef global_log
|
||||
if (!dont_log) myLog.print(message, outputFormat);
|
||||
if (!dont_log && loggingEnabled) myLog.print(message, outputFormat);
|
||||
#endif
|
||||
}
|
||||
|
||||
@ -2542,7 +2587,7 @@ void print_Msg(int message, int outputFormat) {
|
||||
Serial.print(message, outputFormat);
|
||||
#endif
|
||||
#ifdef global_log
|
||||
if (!dont_log) myLog.print(message, outputFormat);
|
||||
if (!dont_log && loggingEnabled) myLog.print(message, outputFormat);
|
||||
#endif
|
||||
}
|
||||
|
||||
@ -2554,7 +2599,7 @@ void print_Msg(long unsigned int message, int outputFormat) {
|
||||
Serial.print(message, outputFormat);
|
||||
#endif
|
||||
#ifdef global_log
|
||||
if (!dont_log) myLog.print(message, outputFormat);
|
||||
if (!dont_log && loggingEnabled) myLog.print(message, outputFormat);
|
||||
#endif
|
||||
}
|
||||
|
||||
@ -2566,7 +2611,7 @@ void print_Msg(String string) {
|
||||
Serial.print(string);
|
||||
#endif
|
||||
#ifdef global_log
|
||||
if (!dont_log) myLog.print(string);
|
||||
if (!dont_log && loggingEnabled) myLog.print(string);
|
||||
#endif
|
||||
}
|
||||
|
||||
@ -2595,7 +2640,7 @@ void println_Msg(String string) {
|
||||
Serial.println(string);
|
||||
#endif
|
||||
#ifdef global_log
|
||||
if (!dont_log) myLog.println(string);
|
||||
if (!dont_log && loggingEnabled) myLog.println(string);
|
||||
#endif
|
||||
}
|
||||
|
||||
@ -2608,7 +2653,7 @@ void println_Msg(byte message, int outputFormat) {
|
||||
Serial.println(message, outputFormat);
|
||||
#endif
|
||||
#ifdef global_log
|
||||
if (!dont_log) myLog.println(message, outputFormat);
|
||||
if (!dont_log && loggingEnabled) myLog.println(message, outputFormat);
|
||||
#endif
|
||||
}
|
||||
|
||||
@ -2638,7 +2683,7 @@ void println_Msg(const char myString[]) {
|
||||
Serial.println(myString);
|
||||
#endif
|
||||
#ifdef global_log
|
||||
if (!dont_log) myLog.println(myString);
|
||||
if (!dont_log && loggingEnabled) myLog.println(myString);
|
||||
#endif
|
||||
}
|
||||
|
||||
@ -2654,7 +2699,7 @@ void println_Msg(const __FlashStringHelper* string) {
|
||||
char myBuffer[15];
|
||||
strlcpy_P(myBuffer, (char*)string, 15);
|
||||
if ((strncmp(myBuffer, "Press Button...", 14) != 0) && (strncmp(myBuffer, "Select file", 10) != 0)) {
|
||||
if (!dont_log) myLog.println(string);
|
||||
if (!dont_log && loggingEnabled) myLog.println(string);
|
||||
}
|
||||
#endif
|
||||
}
|
||||
@ -2668,7 +2713,7 @@ void println_Msg(long unsigned int message) {
|
||||
Serial.println(message);
|
||||
#endif
|
||||
#ifdef global_log
|
||||
if (!dont_log) myLog.println(message);
|
||||
if (!dont_log && loggingEnabled) myLog.println(message);
|
||||
#endif
|
||||
}
|
||||
|
||||
@ -2680,7 +2725,7 @@ void display_Update() {
|
||||
delay(100);
|
||||
#endif
|
||||
#ifdef global_log
|
||||
if (!dont_log) myLog.flush();
|
||||
if (!dont_log && loggingEnabled) myLog.flush();
|
||||
#endif
|
||||
}
|
||||
|
||||
@ -2690,7 +2735,7 @@ void display_Clear() {
|
||||
display.setCursor(0, 8);
|
||||
#endif
|
||||
#ifdef global_log
|
||||
if (!dont_log) myLog.println("");
|
||||
if (!dont_log && loggingEnabled) myLog.println("");
|
||||
#endif
|
||||
}
|
||||
|
||||
@ -2980,41 +3025,50 @@ void checkUpdater() {
|
||||
if (ClockedSerial.available() > 0) {
|
||||
String cmd = ClockedSerial.readStringUntil('\n');
|
||||
cmd.trim();
|
||||
if (cmd == "VERCHK") {
|
||||
if (cmd == "VERCHK")
|
||||
{ // VERCHK: Gets OSCR version and features
|
||||
delay(500);
|
||||
printVersionToSerial();
|
||||
} else if (cmd == "GETCLOCK") {
|
||||
}
|
||||
else if (cmd == "GETCLOCK")
|
||||
{ // GETCLOCK: Gets the MEGA's current clock speed.
|
||||
# if defined(ENABLE_3V3FIX)
|
||||
ClockedSerial.print(F("Clock is running at "));
|
||||
ClockedSerial.print((clock == CS_16MHZ) ? 16UL : 8UL);
|
||||
ClockedSerial.println(F("MHz"));
|
||||
#else
|
||||
# else /* !ENABLE_3V3FIX */
|
||||
ClockedSerial.println(F("Dynamic clock speed (3V3FIX) is not enabled."));
|
||||
#endif
|
||||
} else if (cmd == "GETVOLTS") {
|
||||
# endif /* ENABLE_3V3FIX */
|
||||
}
|
||||
else if (cmd.substring(1, 8) == "ETVOLTS")
|
||||
{ // (G/S)ETVOLTS: Get and set the voltage.
|
||||
# if defined(ENABLE_VSELECT)
|
||||
if (cmd != "GETVOLTS") {
|
||||
switch(cmd.substring(9, 10).toInt()) {
|
||||
case 3: setVoltage(VOLTS_SET_3V3); break;
|
||||
case 5: setVoltage(VOLTS_SET_5V); break;
|
||||
}
|
||||
}
|
||||
ClockedSerial.print(F("Voltage is set to "));
|
||||
ClockedSerial.print((voltage == VOLTS_SET_5V) ? 5 : 3.3);
|
||||
ClockedSerial.println(F("V"));
|
||||
#else
|
||||
# else /* !ENABLE_VSELECT */
|
||||
ClockedSerial.println(F("Automatic voltage selection (VSELECT) is not enabled."));
|
||||
#endif
|
||||
} else if (cmd == "GETTIME") {
|
||||
#if defined(RTC_installed)
|
||||
ClockedSerial.print(F("Current Time: "));
|
||||
ClockedSerial.println(RTCStamp());
|
||||
#else
|
||||
ClockedSerial.println(F("RTC not installed"));
|
||||
#endif
|
||||
} else if (cmd.substring(0, 7) == "SETTIME") {
|
||||
# endif /* ENABLE_VSELECT */
|
||||
}
|
||||
// RTC commands
|
||||
else if (cmd.substring(1, 7) == "ETTIME")
|
||||
{ // (G/S)ETTIME: Get and set the date/time.
|
||||
# if defined(RTC_installed)
|
||||
if (cmd != "GETTIME") {
|
||||
ClockedSerial.println(F("Setting Time..."));
|
||||
rtc.adjust(DateTime(cmd.substring(8).toInt()));
|
||||
}
|
||||
ClockedSerial.print(F("Current Time: "));
|
||||
ClockedSerial.println(RTCStamp());
|
||||
#else
|
||||
# else /* !RTC_installed */
|
||||
ClockedSerial.println(F("RTC not installed"));
|
||||
#endif
|
||||
# endif /* RTC_installed */
|
||||
} else {
|
||||
ClockedSerial.println(F("OSCR: Unknown Command"));
|
||||
}
|
||||
|
@ -288,9 +288,30 @@
|
||||
|
||||
/*==== FIRMWARE OPTIONS ===========================================*/
|
||||
|
||||
/* [ Config File -------------------------------------------------- ]
|
||||
Allow changing some configuration values via a config file. You
|
||||
generally can only use the config to set options or disable
|
||||
certain featuress. It cannot be used to toggle firmware options
|
||||
on, only off.
|
||||
|
||||
Note For Developers: See OSCR.* for info.
|
||||
|
||||
Filename: config.txt
|
||||
*/
|
||||
|
||||
//#define ENABLE_CONFIG
|
||||
|
||||
/****/
|
||||
|
||||
/* [ LCD: Background Color ---------------------------------------- ]
|
||||
Set the backlight color of the LCD if you have one.
|
||||
|
||||
Can be set using config:
|
||||
lcd.confColor=1
|
||||
lcd.red=0
|
||||
lcd.green=0
|
||||
lcd.blue=0
|
||||
|
||||
PARAMETERS:
|
||||
Green, Red, Blue
|
||||
*/
|
||||
@ -332,6 +353,9 @@
|
||||
|
||||
/* [ Logging ------------------------------------------------------ ]
|
||||
Write all info to OSCR_LOG.txt in root dir
|
||||
|
||||
Can be toggled off using config:
|
||||
oscr.logging=0
|
||||
*/
|
||||
|
||||
#define global_log
|
||||
@ -367,13 +391,26 @@
|
||||
0: Output each byte once. Not supported by emulators. (default)
|
||||
1: Duplicate each byte. Usable by Kega Fusion.
|
||||
2: Same as 1 + pad with 0xFF so that the file size is 64KB.
|
||||
|
||||
**
|
||||
** DEPRECATED: Use the config file instead. See below.
|
||||
**
|
||||
*/
|
||||
|
||||
//#define use_md_conf
|
||||
|
||||
/*
|
||||
Alternatively, define it here by uncommenting and changing the
|
||||
following line. Setting both allows you to change the default.
|
||||
Configure how the MD core saves are formatted.
|
||||
|
||||
Can be set using config:
|
||||
md.sramType=0
|
||||
|
||||
If config is enabled, this option does nothing -- use the config.
|
||||
|
||||
Options:
|
||||
0: Output each byte once. Not supported by emulators. (default)
|
||||
1: Duplicate each byte. Usable by Kega Fusion.
|
||||
2: Same as 1 + pad with 0xFF so that the file size is 64KB.
|
||||
*/
|
||||
|
||||
//#define DEFAULT_VALUE_segaSram16bit 0
|
||||
@ -404,6 +441,14 @@
|
||||
You probably shouldn't change this stuff!
|
||||
*/
|
||||
|
||||
#if defined(ENABLE_CONFIG)
|
||||
# define CONFIG_FILE "config.txt"
|
||||
// Define the max length of the key=value pairs
|
||||
// Do your best not to have to increase these.
|
||||
# define CONFIG_KEY_MAX 32
|
||||
# define CONFIG_VALUE_MAX 32
|
||||
#endif
|
||||
|
||||
#if (defined(HW4) || defined(HW5))
|
||||
# define enable_LCD
|
||||
# define enable_neopixel
|
||||
|
@ -87,11 +87,20 @@ unsigned long bramSize = 0;
|
||||
// REALTEC MAPPER
|
||||
boolean realtec = 0;
|
||||
|
||||
#if defined(ENABLED_CONFIG)
|
||||
|
||||
int segaSram16bit = 0;
|
||||
|
||||
#else /* !ENABLED_CONFIG */
|
||||
|
||||
# ifndef DEFAULT_VALUE_segaSram16bit
|
||||
# define DEFAULT_VALUE_segaSram16bit 0
|
||||
#endif
|
||||
# endif /* !DEFAULT_VALUE_segaSram16bit */
|
||||
|
||||
int segaSram16bit = DEFAULT_VALUE_segaSram16bit;
|
||||
|
||||
#endif /* ENABLED_CONFIG */
|
||||
|
||||
//*****************************************
|
||||
// SONIC & KNUCKLES LOCK-ON MODE VARIABLES
|
||||
// SnKmode :
|
||||
@ -111,12 +120,15 @@ static word chksumSonic2 = 0x0635;
|
||||
/******************************************
|
||||
Configuration
|
||||
*****************************************/
|
||||
#ifdef use_md_conf
|
||||
#if defined(use_md_conf) && !defined(ENABLE_CONFIG)
|
||||
|
||||
#warning "DEPRECATED: use_md_conf is deprecated. You should use ENABLE_CONFIG instead."
|
||||
|
||||
void mdLoadConf() {
|
||||
if (myFile.open("mdconf.txt", O_READ)) {
|
||||
char line[64];
|
||||
int n;
|
||||
int i;
|
||||
unsigned int n;
|
||||
unsigned int i;
|
||||
while ((n = myFile.fgets(line, sizeof(line) - 1)) > 0) {
|
||||
// preprocess
|
||||
for (i = 0; i < n; i++) {
|
||||
@ -467,9 +479,11 @@ void setup_MD() {
|
||||
// Request 5V
|
||||
setVoltage(VOLTS_SET_5V);
|
||||
|
||||
#ifdef use_md_conf
|
||||
#if defined(ENABLE_CONFIG)
|
||||
segaSram16bit = configGetLong(F("md.sramType"));
|
||||
#elif defined(use_md_conf)
|
||||
mdLoadConf();
|
||||
#endif
|
||||
#endif /*ENABLE_CONFIG*/
|
||||
|
||||
// Set Address Pins to Output
|
||||
//A0-A7
|
||||
|
@ -7,7 +7,10 @@
|
||||
* Contains various enums, variables, etc, for the main program.
|
||||
*
|
||||
* PUBLIC FUNCTIONS :
|
||||
* void setClockScale( VOLTS )
|
||||
* void setClockScale( ClockScale )
|
||||
* VOLTS setVoltage( Voltage )
|
||||
* long configGetLong( Key, OnFailure )
|
||||
* String configGetStr( Key )
|
||||
*
|
||||
* NOTES :
|
||||
* This file is a WIP, I've been moving things into it on my local working
|
||||
@ -32,6 +35,7 @@
|
||||
* CHANGES :
|
||||
*
|
||||
* REF NO VERSION DATE WHO DETAIL
|
||||
* 13.2 2024-02-29 Ancyker Add config support
|
||||
* 12.5 2023-03-29 Ancyker Initial version
|
||||
*
|
||||
*H*/
|
||||
@ -41,7 +45,7 @@
|
||||
/*==== VARIABLES ==================================================*/
|
||||
|
||||
// Firmware Version
|
||||
char ver[5] = "13.1";
|
||||
char ver[5] = "13.2";
|
||||
|
||||
// Clock speed
|
||||
unsigned long clock = CS_16MHZ;
|
||||
@ -49,6 +53,22 @@ unsigned long clock = CS_16MHZ;
|
||||
// Voltage
|
||||
VOLTS voltage = VOLTS_SET_5V;
|
||||
|
||||
#if defined(ENABLE_CONFIG)
|
||||
|
||||
FsFile configFile;
|
||||
bool useConfig = false;
|
||||
|
||||
# if defined(global_log)
|
||||
// Logging
|
||||
bool loggingEnabled = true;
|
||||
# endif /* global_log */
|
||||
#else /* !ENABLE_CONFIG */
|
||||
# if defined(global_log)
|
||||
// Logging: Define it as true using a const instead.
|
||||
const bool loggingEnabled = true;
|
||||
# endif /* global_log */
|
||||
#endif /* ENABLE_CONFIG */
|
||||
|
||||
/*==== /VARIABLES =================================================*/
|
||||
|
||||
/*F******************************************************************
|
||||
@ -108,6 +128,7 @@ void printVersionToSerial() {}
|
||||
* INPUTS :
|
||||
* PARAMETERS:
|
||||
* VOLTS ClockScale Clock scale
|
||||
* CLKSCALE ClockScale Clock scale
|
||||
*
|
||||
* PROCESS :
|
||||
* [1] Enable clock prescaler change
|
||||
@ -139,6 +160,24 @@ void setClockScale(VOLTS __x)
|
||||
); /*[2]*/
|
||||
}
|
||||
|
||||
void setClockScale(CLKSCALE __x)
|
||||
{
|
||||
clock = (__x == CLKSCALE_16MHZ ? CS_16MHZ : CS_8MHZ);
|
||||
uint8_t __tmp = _BV(CLKPCE); /*[1]*/
|
||||
__asm__ __volatile__ (
|
||||
"in __tmp_reg__,__SREG__" "\n\t"
|
||||
"cli" "\n\t"
|
||||
"sts %1, %0" "\n\t"
|
||||
"sts %1, %2" "\n\t"
|
||||
"out __SREG__, __tmp_reg__"
|
||||
: /* no outputs */
|
||||
: "d" (__tmp),
|
||||
"M" (_SFR_MEM_ADDR(CLKPR)),
|
||||
"d" (__x)
|
||||
: "r0"
|
||||
); /*[2]*/
|
||||
}
|
||||
|
||||
/*F******************************************************************
|
||||
* NAME : VOLTS setVoltage( Voltage )
|
||||
*
|
||||
@ -263,3 +302,146 @@ VOLTS setVoltage(VOLTS newVoltage __attribute__((unused))) {
|
||||
return VOLTS_NOTENABLED;
|
||||
}
|
||||
#endif
|
||||
|
||||
#if defined(ENABLE_CONFIG)
|
||||
|
||||
/*F******************************************************************
|
||||
* NAME : void configInit()
|
||||
*
|
||||
* DESCRIPTION : Setup the config file.
|
||||
*
|
||||
*F*/
|
||||
void configInit() {
|
||||
useConfig = configFile.open(CONFIG_FILE, O_READ);
|
||||
}
|
||||
|
||||
/*F******************************************************************
|
||||
* NAME : uint8_t configFindKey( Key, Value )
|
||||
*
|
||||
* DESCRIPTION : Search for a key=value pair.
|
||||
*
|
||||
* INPUTS :
|
||||
* PARAMETERS:
|
||||
* __FlashStringHelper Key The key to get the value for.
|
||||
* char* value Variable to store the value in.
|
||||
*
|
||||
* OUTPUTS :
|
||||
* RETURN :
|
||||
* Type: uint8_t Length of the value.
|
||||
*
|
||||
* PROCESS :
|
||||
* [1] Get key length and convert to char array/string.
|
||||
* [2] Parse file line by line.
|
||||
* [3] Check if key in file matches.
|
||||
* [4] Copy string after equals character.
|
||||
* [5] Add null terminator.
|
||||
*
|
||||
* NOTES :
|
||||
* You aren't meant to use this function directly. Check the
|
||||
* functions configGetStr() and configGetLong().
|
||||
*
|
||||
*F*/
|
||||
uint8_t configFindKey(const __FlashStringHelper* searchKey, char* value) {
|
||||
if (!useConfig) return 0;
|
||||
|
||||
char key[CONFIG_KEY_MAX + 1];
|
||||
char buffer[CONFIG_KEY_MAX + CONFIG_VALUE_MAX + 4];
|
||||
int keyLen = 0;
|
||||
int valueLen = 0;
|
||||
|
||||
keyLen = strlcpy_P(key, reinterpret_cast<const char *>(searchKey), CONFIG_KEY_MAX); /*[1]*/
|
||||
|
||||
configFile.rewind();
|
||||
|
||||
while (configFile.available()) { /*[2]*/
|
||||
int bufferLen = configFile.readBytesUntil('\n', buffer, CONFIG_KEY_MAX + CONFIG_VALUE_MAX + 3);
|
||||
|
||||
if (buffer[bufferLen - 1] == '\r')
|
||||
bufferLen--;
|
||||
|
||||
if (bufferLen > (keyLen + 1)) {
|
||||
if (memcmp(buffer, key, keyLen) == 0) { /*[3]*/
|
||||
if (buffer[keyLen] == '=') { /*[4]*/
|
||||
valueLen = bufferLen - keyLen - 1;
|
||||
memcpy(&value[0], &buffer[keyLen + 1], valueLen);
|
||||
value[valueLen] = '\0'; /*[5]*/
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
return valueLen;
|
||||
}
|
||||
|
||||
/*F******************************************************************
|
||||
* NAME : String configGetStr( Key )
|
||||
*
|
||||
* DESCRIPTION : Return the value of a key as a string.
|
||||
*
|
||||
* INPUTS :
|
||||
* PARAMETERS:
|
||||
* __FlashStringHelper Key The key to get the value for.
|
||||
*
|
||||
* OUTPUTS :
|
||||
* RETURN :
|
||||
* Type: String The value of the key or an empty string.
|
||||
*
|
||||
* PROCESS :
|
||||
* [1] Find the key via configFindKey().
|
||||
* [2] Return empty if nothing was found.
|
||||
* [3] Convert to String type.
|
||||
*
|
||||
* NOTES :
|
||||
* You can use this to get strings stored in the config file.
|
||||
* Take care when allocating memory for strings. You should
|
||||
* probably use malloc for it if it's a global variable. If
|
||||
* you do, make sure to free() it after it's not needed.
|
||||
*
|
||||
*F*/
|
||||
String configGetStr(const __FlashStringHelper* key) {
|
||||
if (!useConfig) return {};
|
||||
char value[CONFIG_VALUE_MAX + 1];
|
||||
|
||||
uint8_t valueLen = configFindKey(key, value); /*[1]*/
|
||||
if (valueLen < 1) return {}; /*[2]*/
|
||||
|
||||
String stringVal(value); /*[3]*/
|
||||
|
||||
return stringVal;
|
||||
}
|
||||
|
||||
/*F******************************************************************
|
||||
* NAME : long configGetLong( Key, OnFailure )
|
||||
*
|
||||
* DESCRIPTION : Return the value of a key as an int/long.
|
||||
*
|
||||
* INPUTS :
|
||||
* PARAMETERS:
|
||||
* __FlashStringHelper Key The key to get the value for.
|
||||
* int onFail Value to return on failure. (def=0)
|
||||
*
|
||||
* OUTPUTS :
|
||||
* RETURN :
|
||||
* Type: int The value of the key or onFail.
|
||||
*
|
||||
* PROCESS :
|
||||
* [1] Find the key via configFindKey().
|
||||
* [2] Return onFail if nothing was found.
|
||||
* [3] Convert to long int type and return.
|
||||
*
|
||||
* NOTES :
|
||||
* You can specify hex, i.e. 0xFF for 255, if you want to.
|
||||
*
|
||||
*F*/
|
||||
long configGetLong(const __FlashStringHelper* key, int onFail) {
|
||||
if (!useConfig) return onFail;
|
||||
char value[CONFIG_VALUE_MAX + 1];
|
||||
|
||||
uint8_t valueLen = configFindKey(key, value); /*[1]*/
|
||||
if (valueLen < 1) return onFail; /*[2]*/
|
||||
|
||||
return strtol(value, NULL, 0); /*[3]*/
|
||||
}
|
||||
|
||||
#endif /* ENABLE_CONFIG */
|
||||
|
@ -10,6 +10,7 @@
|
||||
#include <Wire.h>
|
||||
#include <avr/pgmspace.h>
|
||||
#include <avr/wdt.h>
|
||||
#include "SdFat.h"
|
||||
|
||||
#include "Config.h"
|
||||
|
||||
@ -29,6 +30,13 @@ const uint16_t UPD_BAUD = 9600;
|
||||
const unsigned long CS_16MHZ = 16000000UL;
|
||||
const unsigned long CS_8MHZ = 8000000UL;
|
||||
|
||||
// ENUM for VSELECT & 3V3FIX
|
||||
enum CLKSCALE: uint8_t {
|
||||
// Paramters to pass to setVoltage() and setClockScale()
|
||||
CLKSCALE_16MHZ = 0, // ClockScale 0 = 16MHz
|
||||
CLKSCALE_8MHZ, // ClockScale 1 = 8MHz
|
||||
};
|
||||
|
||||
// ENUM for VSELECT & 3V3FIX
|
||||
enum VOLTS: uint8_t {
|
||||
// Paramters to pass to setVoltage() and setClockScale()
|
||||
@ -47,11 +55,37 @@ extern unsigned long clock;
|
||||
extern char ver[5];
|
||||
extern VOLTS voltage;
|
||||
|
||||
#if defined(ENABLE_CONFIG)
|
||||
/**
|
||||
* Config File Stuff
|
||||
*
|
||||
* You can register GLOBAL configuration variables in this section.
|
||||
* You should put core-specific config variables in the related file.
|
||||
**/
|
||||
|
||||
extern bool useConfig;
|
||||
# ifdef global_log
|
||||
extern bool loggingEnabled;
|
||||
# endif /* global_log */
|
||||
#else /* !ENABLE_CONFIG */
|
||||
# ifdef global_log
|
||||
extern const bool loggingEnabled;
|
||||
# endif /* global_log */
|
||||
#endif /* ENABLE_CONFIG */
|
||||
|
||||
/*==== FUNCTIONS ==================================================*/
|
||||
extern void printVersionToSerial();
|
||||
extern void setClockScale(VOLTS __x);
|
||||
extern void setClockScale(CLKSCALE __x);
|
||||
extern VOLTS setVoltage(VOLTS volts);
|
||||
|
||||
#if defined(ENABLE_CONFIG)
|
||||
extern void configInit();
|
||||
extern uint8_t configFindKey(const __FlashStringHelper* key, char* value);
|
||||
extern String configGetStr(const __FlashStringHelper* key);
|
||||
extern long configGetLong(const __FlashStringHelper* key, int onFail = 0);
|
||||
#endif /* ENABLE_CONFIG */
|
||||
|
||||
#include "ClockedSerial.h"
|
||||
|
||||
#endif /* OSCR_H_ */
|
||||
|
6
sd/config.txt
Normal file
6
sd/config.txt
Normal file
@ -0,0 +1,6 @@
|
||||
oscr.logging=1
|
||||
lcd.confColor=0
|
||||
lcd.red=0
|
||||
lcd.green=100
|
||||
lcd.blue=0
|
||||
md.sramType=0
|
Loading…
Reference in New Issue
Block a user