1
0
mirror of https://github.com/DCC-EX/CommandStation-EX.git synced 2025-01-27 12:48:52 +01:00

FlasString and Timers for Uno Wifi

ALL these changes should be portable back to master
This commit is contained in:
Asbelos 2020-12-09 11:57:38 +00:00
parent d96c919fee
commit 74c22c83fc
13 changed files with 80 additions and 48 deletions

View File

@ -1,5 +1,5 @@
#ifndef ATMEGA328Timer_h #ifndef ATMEGA4809Timer_h
#define ATMEGA328Timer_h #define ATMEGA4809imer_h
#include "../VirtualTimer.h" #include "../VirtualTimer.h"
#include <Arduino.h> #include <Arduino.h>
@ -128,4 +128,5 @@ public:
extern Timer TimerA; extern Timer TimerA;
#endif #endif

View File

@ -25,7 +25,16 @@
#include <Arduino.h> #include <Arduino.h>
int inline analogReadFast(uint8_t ADCpin); int inline analogReadFast(uint8_t ADCpin);
#if defined(ARDUINO_ARCH_MEGAAVR)
int inline analogReadFast(uint8_t ADCpin)
{ byte ADC0CTRLCoriginal = ADC0.CTRLC;
ADC0.CTRLC = (ADC0CTRLCoriginal & 0b00110000) + 0b01000011;
int adc = analogRead(ADCpin);
ADC0.CTRLC = ADC0CTRLCoriginal;
return adc;
}
#else
int inline analogReadFast(uint8_t ADCpin) int inline analogReadFast(uint8_t ADCpin)
{ byte ADCSRAoriginal = ADCSRA; { byte ADCSRAoriginal = ADCSRA;
ADCSRA = (ADCSRA & B11111000) | 4; ADCSRA = (ADCSRA & B11111000) | 4;
@ -33,5 +42,5 @@ int inline analogReadFast(uint8_t ADCpin)
ADCSRA = ADCSRAoriginal; ADCSRA = ADCSRAoriginal;
return adc; return adc;
} }
#endif
#endif // COMMANDSTATION_DCC_ANALOGREADFAST_H_ #endif // COMMANDSTATION_DCC_ANALOGREADFAST_H_

View File

@ -11,7 +11,7 @@
#include "ATMEGA2560/Timer.h" #include "ATMEGA2560/Timer.h"
#elif defined(ARDUINO_AVR_UNO) #elif defined(ARDUINO_AVR_UNO)
#include "ATMEGA328/Timer.h" #include "ATMEGA328/Timer.h"
#elif defined(ARDUINO_AVR_UNO_WIFI_DEV_ED) #elif defined(ARDUINO_AVR_UNO_WIFI_REV2)
#include "ATMEGA4809/Timer.h" #include "ATMEGA4809/Timer.h"
#else #else
#error "Cannot compile - ArduinoTimers library does not support your board, or you are missing compatible build flags." #error "Cannot compile - ArduinoTimers library does not support your board, or you are missing compatible build flags."

10
DCC.cpp
View File

@ -17,9 +17,9 @@
* You should have received a copy of the GNU General Public License * You should have received a copy of the GNU General Public License
* along with CommandStation. If not, see <https://www.gnu.org/licenses/>. * along with CommandStation. If not, see <https://www.gnu.org/licenses/>.
*/ */
#include "DIAG.h"
#include "DCC.h" #include "DCC.h"
#include "DCCWaveform.h" #include "DCCWaveform.h"
#include "DIAG.h"
#include "EEStore.h" #include "EEStore.h"
#include "GITHUB_SHA.h" #include "GITHUB_SHA.h"
#include "version.h" #include "version.h"
@ -43,10 +43,10 @@ const byte FN_GROUP_3=0x04;
const byte FN_GROUP_4=0x08; const byte FN_GROUP_4=0x08;
const byte FN_GROUP_5=0x10; const byte FN_GROUP_5=0x10;
__FlashStringHelper* DCC::shieldName=NULL; FSH* DCC::shieldName=NULL;
void DCC::begin(const __FlashStringHelper* motorShieldName, MotorDriver * mainDriver, MotorDriver* progDriver, byte timerNumber) { void DCC::begin(const FSH* motorShieldName, MotorDriver * mainDriver, MotorDriver* progDriver, byte timerNumber) {
shieldName=(__FlashStringHelper*)motorShieldName; shieldName=(FSH*)motorShieldName;
DIAG(F("<iDCC-EX V-%S / %S / %S G-%S>\n"), F(VERSION), F(ARDUINO_TYPE), shieldName, F(GITHUB_SHA)); DIAG(F("<iDCC-EX V-%S / %S / %S G-%S>\n"), F(VERSION), F(ARDUINO_TYPE), shieldName, F(GITHUB_SHA));
// Load stuff from EEprom // Load stuff from EEprom
@ -228,7 +228,7 @@ void DCC::setProgTrackBoost(bool on) {
DCCWaveform::progTrackBoosted=on; DCCWaveform::progTrackBoosted=on;
} }
__FlashStringHelper* DCC::getMotorShieldName() { FSH* DCC::getMotorShieldName() {
return shieldName; return shieldName;
} }

10
DCC.h
View File

@ -21,7 +21,7 @@
#include <Arduino.h> #include <Arduino.h>
#include "MotorDriver.h" #include "MotorDriver.h"
#include "MotorDrivers.h" #include "MotorDrivers.h"
#include "FSH.h"
typedef void (*ACK_CALLBACK)(int result); typedef void (*ACK_CALLBACK)(int result);
enum ackOp enum ackOp
@ -60,7 +60,7 @@ const byte MAX_LOCOS = 50;
class DCC class DCC
{ {
public: public:
static void begin(const __FlashStringHelper *motorShieldName, MotorDriver *mainDriver, MotorDriver *progDriver, byte timerNumber = 1); static void begin(const FSH *motorShieldName, MotorDriver *mainDriver, MotorDriver *progDriver, byte timerNumber = 1);
static void loop(); static void loop();
// Public DCC API functions // Public DCC API functions
@ -94,7 +94,7 @@ public:
static void forgetAllLocos(); // removes all speed reminders static void forgetAllLocos(); // removes all speed reminders
static void displayCabList(Print *stream); static void displayCabList(Print *stream);
static __FlashStringHelper *getMotorShieldName(); static FSH *getMotorShieldName();
private: private:
struct LOCO struct LOCO
@ -110,7 +110,7 @@ private:
static void setFunctionInternal(int cab, byte fByte, byte eByte); static void setFunctionInternal(int cab, byte fByte, byte eByte);
static bool issueReminder(int reg); static bool issueReminder(int reg);
static int nextLoco; static int nextLoco;
static __FlashStringHelper *shieldName; static FSH *shieldName;
static LOCO speedTable[MAX_LOCOS]; static LOCO speedTable[MAX_LOCOS];
static byte cv1(byte opcode, int cv); static byte cv1(byte opcode, int cv);
@ -155,7 +155,7 @@ private:
#define ARDUINO_TYPE "NANO" #define ARDUINO_TYPE "NANO"
#elif defined(ARDUINO_AVR_MEGA2560) #elif defined(ARDUINO_AVR_MEGA2560)
#define ARDUINO_TYPE "MEGA" #define ARDUINO_TYPE "MEGA"
#elif defined(ARDUINO_AVR_UNO_WIFI_DEV_ED) #elif defined(ARDUINO_AVR_UNO_WIFI_REV2)
#define ARDUINO_TYPE "UNOWIFIR2" #define ARDUINO_TYPE "UNOWIFIR2"
#else #else
#error CANNOT COMPILE - DCC++ EX ONLY WORKS WITH AN ARDUINO UNO, NANO 328, OR ARDUINO MEGA 1280/2560 #error CANNOT COMPILE - DCC++ EX ONLY WORKS WITH AN ARDUINO UNO, NANO 328, OR ARDUINO MEGA 1280/2560

View File

@ -41,7 +41,7 @@ void DCCWaveform::begin(MotorDriver * mainDriver, MotorDriver * progDriver, byte
progTrack.setPowerMode(POWERMODE::OFF); progTrack.setPowerMode(POWERMODE::OFF);
switch (timerNumber) { switch (timerNumber) {
case 1: interruptTimer= &TimerA; break; case 1: interruptTimer= &TimerA; break;
#ifndef ARDUINO_AVR_UNO_WIFI_DEV_ED #ifndef ARDUINO_AVR_UNO_WIFI_REV2
case 2: interruptTimer= &TimerB; break; case 2: interruptTimer= &TimerB; break;
#ifndef ARDUINO_AVR_UNO #ifndef ARDUINO_AVR_UNO
case 3: interruptTimer= &TimerC; break; case 3: interruptTimer= &TimerC; break;

1
DIAG.h
View File

@ -18,6 +18,7 @@
*/ */
#ifndef DIAG_h #ifndef DIAG_h
#define DIAG_h #define DIAG_h
#include "StringFormatter.h" #include "StringFormatter.h"
#define DIAG StringFormatter::diag #define DIAG StringFormatter::diag
#define LCD StringFormatter::lcd #define LCD StringFormatter::lcd

9
FSH.h Normal file
View File

@ -0,0 +1,9 @@
#ifndef FSH_h
#define FSH_h
#include <Arduino.h>
#if defined(ARDUINO_ARCH_MEGAAVR)
typedef char FSH;
#else
typedef __FlashStringHelper FSH;
#endif
#endif

View File

@ -28,7 +28,7 @@
Print * StringFormatter::diagSerial= &Serial; Print * StringFormatter::diagSerial= &Serial;
#elif defined(ARDUINO_ARCH_MEGAAVR) #elif defined(ARDUINO_ARCH_MEGAAVR)
Print * StringFormatter::diagSerial=&Serial; Print * StringFormatter::diagSerial=&Serial;
#define __FlashStringHelper char #define FSH char
#endif #endif
#include "LCDDisplay.h" #include "LCDDisplay.h"
@ -40,14 +40,14 @@ bool Diag::WITHROTTLE=false;
bool Diag::ETHERNET=false; bool Diag::ETHERNET=false;
void StringFormatter::diag( const __FlashStringHelper* input...) { void StringFormatter::diag( const FSH* input...) {
if (!diagSerial) return; if (!diagSerial) return;
va_list args; va_list args;
va_start(args, input); va_start(args, input);
send2(diagSerial,input,args); send2(diagSerial,input,args);
} }
void StringFormatter::lcd(byte row, const __FlashStringHelper* input...) { void StringFormatter::lcd(byte row, const FSH* input...) {
va_list args; va_list args;
// Issue the LCD as a diag first // Issue the LCD as a diag first
@ -62,19 +62,19 @@ void StringFormatter::lcd(byte row, const __FlashStringHelper* input...) {
send2(LCDDisplay::lcdDisplay,input,args); send2(LCDDisplay::lcdDisplay,input,args);
} }
void StringFormatter::send(Print * stream, const __FlashStringHelper* input...) { void StringFormatter::send(Print * stream, const FSH* input...) {
va_list args; va_list args;
va_start(args, input); va_start(args, input);
send2(stream,input,args); send2(stream,input,args);
} }
void StringFormatter::send(Print & stream, const __FlashStringHelper* input...) { void StringFormatter::send(Print & stream, const FSH* input...) {
va_list args; va_list args;
va_start(args, input); va_start(args, input);
send2(&stream,input,args); send2(&stream,input,args);
} }
void StringFormatter::send2(Print * stream,const __FlashStringHelper* format, va_list args) { void StringFormatter::send2(Print * stream,const FSH* format, va_list args) {
// thanks to Jan Turoň https://arduino.stackexchange.com/questions/56517/formatting-strings-in-arduino-for-output // thanks to Jan Turoň https://arduino.stackexchange.com/questions/56517/formatting-strings-in-arduino-for-output
@ -97,8 +97,8 @@ void StringFormatter::send2(Print * stream,const __FlashStringHelper* format, va
case 'c': stream->print((char) va_arg(args, int)); break; case 'c': stream->print((char) va_arg(args, int)); break;
case 's': stream->print(va_arg(args, char*)); break; case 's': stream->print(va_arg(args, char*)); break;
case 'e': printEscapes(stream,va_arg(args, char*)); break; case 'e': printEscapes(stream,va_arg(args, char*)); break;
case 'E': printEscapes(stream,(const __FlashStringHelper*)va_arg(args, char*)); break; case 'E': printEscapes(stream,(const FSH*)va_arg(args, char*)); break;
case 'S': stream->print((const __FlashStringHelper*)va_arg(args, char*)); break; case 'S': stream->print((const FSH*)va_arg(args, char*)); break;
case 'd': printPadded(stream,va_arg(args, int), formatWidth, formatLeft); break; case 'd': printPadded(stream,va_arg(args, int), formatWidth, formatLeft); break;
case 'l': printPadded(stream,va_arg(args, long), formatWidth, formatLeft); break; case 'l': printPadded(stream,va_arg(args, long), formatWidth, formatLeft); break;
case 'b': stream->print(va_arg(args, int), BIN); break; case 'b': stream->print(va_arg(args, int), BIN); break;
@ -138,7 +138,7 @@ void StringFormatter::printEscapes(Print * stream,char * input) {
} }
} }
void StringFormatter::printEscapes(Print * stream, const __FlashStringHelper * input) { void StringFormatter::printEscapes(Print * stream, const FSH * input) {
if (!stream) return; if (!stream) return;
char* flash=(char*)input; char* flash=(char*)input;

View File

@ -19,12 +19,10 @@
#ifndef StringFormatter_h #ifndef StringFormatter_h
#define StringFormatter_h #define StringFormatter_h
#include <Arduino.h> #include <Arduino.h>
#include "FSH.h"
#if defined(ARDUINO_ARCH_SAMD) #if defined(ARDUINO_ARCH_SAMD)
// Some processors use a gcc compiler that renames va_list!!! // Some processors use a gcc compiler that renames va_list!!!
#include <cstdarg> #include <cstdarg>
#elif defined(ARDUINO_ARCH_MEGAAVR)
#define __FlashStringHelper char
#endif #endif
#include "LCDDisplay.h" #include "LCDDisplay.h"
@ -41,22 +39,22 @@ class Diag {
class StringFormatter class StringFormatter
{ {
public: public:
static void send(Print * serial, const __FlashStringHelper* input...); static void send(Print * serial, const FSH* input...);
static void send(Print & serial, const __FlashStringHelper* input...); static void send(Print & serial, const FSH* input...);
static void printEscapes(Print * serial,char * input); static void printEscapes(Print * serial,char * input);
static void printEscapes(Print * serial,const __FlashStringHelper* input); static void printEscapes(Print * serial,const FSH* input);
static void printEscape(Print * serial, char c); static void printEscape(Print * serial, char c);
// DIAG support // DIAG support
static Print * diagSerial; static Print * diagSerial;
static void diag( const __FlashStringHelper* input...); static void diag( const FSH* input...);
static void lcd(byte row, const __FlashStringHelper* input...); static void lcd(byte row, const FSH* input...);
static void printEscapes(char * input); static void printEscapes(char * input);
static void printEscape( char c); static void printEscape( char c);
private: private:
static void send2(Print * serial, const __FlashStringHelper* input,va_list args); static void send2(Print * serial, const FSH* input,va_list args);
static void printPadded(Print* stream, long value, byte width, bool formatLeft); static void printPadded(Print* stream, long value, byte width, bool formatLeft);
}; };

View File

@ -32,6 +32,19 @@ ISR(TIMER5_OVF_vect)
TimerD.isrCallback(); TimerD.isrCallback();
} }
#elif defined(ARDUINO_ARCH_MEGAAVR) // Todo: add other 328 boards for compatibility
#include "ATMEGA4809/Timer.h"
Timer TimerA(1);
ISR(TIMER1_OVF_vect)
{
TimerA.isrCallback();
}
#elif defined(ARDUINO_AVR_UNO) // Todo: add other 328 boards for compatibility #elif defined(ARDUINO_AVR_UNO) // Todo: add other 328 boards for compatibility
#include "ATMEGA328/Timer.h" #include "ATMEGA328/Timer.h"

View File

@ -52,9 +52,9 @@ Stream * WifiInterface::wifiStream;
#endif #endif
bool WifiInterface::setup(long serial_link_speed, bool WifiInterface::setup(long serial_link_speed,
const __FlashStringHelper *wifiESSID, const FSH *wifiESSID,
const __FlashStringHelper *wifiPassword, const FSH *wifiPassword,
const __FlashStringHelper *hostname, const FSH *hostname,
const int port) { const int port) {
wifiSerialState wifiUp = WIFI_NOAT; wifiSerialState wifiUp = WIFI_NOAT;
@ -103,8 +103,8 @@ bool WifiInterface::setup(long serial_link_speed,
return connected; return connected;
} }
wifiSerialState WifiInterface::setup(Stream & setupStream, const __FlashStringHelper* SSid, const __FlashStringHelper* password, wifiSerialState WifiInterface::setup(Stream & setupStream, const FSH* SSid, const FSH* password,
const __FlashStringHelper* hostname, int port) { const FSH* hostname, int port) {
wifiSerialState wifiState; wifiSerialState wifiState;
static uint8_t ntry = 0; static uint8_t ntry = 0;
ntry++; ntry++;
@ -135,8 +135,8 @@ wifiSerialState WifiInterface::setup(Stream & setupStream, const __FlashStringH
#pragma GCC diagnostic ignored "-Wunused-variable" #pragma GCC diagnostic ignored "-Wunused-variable"
#pragma GCC diagnostic ignored "-Wunused-parameter" #pragma GCC diagnostic ignored "-Wunused-parameter"
#endif #endif
wifiSerialState WifiInterface::setup2(const __FlashStringHelper* SSid, const __FlashStringHelper* password, wifiSerialState WifiInterface::setup2(const FSH* SSid, const FSH* password,
const __FlashStringHelper* hostname, int port) { const FSH* hostname, int port) {
bool ipOK = false; bool ipOK = false;
bool oldCmd = false; bool oldCmd = false;

View File

@ -19,6 +19,7 @@
*/ */
#ifndef WifiInterface_h #ifndef WifiInterface_h
#define WifiInterface_h #define WifiInterface_h
#include "FSH.h"
#include "config.h" #include "config.h"
#include "DCCEXParser.h" #include "DCCEXParser.h"
#include <Arduino.h> #include <Arduino.h>
@ -31,20 +32,20 @@ class WifiInterface
public: public:
static bool setup(long serial_link_speed, static bool setup(long serial_link_speed,
const __FlashStringHelper *wifiESSID, const FSH *wifiESSID,
const __FlashStringHelper *wifiPassword, const FSH *wifiPassword,
const __FlashStringHelper *hostname, const FSH *hostname,
const int port = 2560); const int port = 2560);
static void loop(); static void loop();
static void ATCommand(const byte *command); static void ATCommand(const byte *command);
private: private:
static wifiSerialState setup(Stream &setupStream, const __FlashStringHelper *SSSid, const __FlashStringHelper *password, static wifiSerialState setup(Stream &setupStream, const FSH *SSSid, const FSH *password,
const __FlashStringHelper *hostname, int port); const FSH *hostname, int port);
static Stream *wifiStream; static Stream *wifiStream;
static DCCEXParser parser; static DCCEXParser parser;
static wifiSerialState setup2(const __FlashStringHelper *SSSid, const __FlashStringHelper *password, static wifiSerialState setup2(const FSH *SSSid, const FSH *password,
const __FlashStringHelper *hostname, int port); const FSH *hostname, int port);
static bool checkForOK(const unsigned int timeout, const char *waitfor, bool echo, bool escapeEcho = true); static bool checkForOK(const unsigned int timeout, const char *waitfor, bool echo, bool escapeEcho = true);
static bool connected; static bool connected;
static bool closeAfter; static bool closeAfter;