diff --git a/.gitignore b/.gitignore index 3e0c0844a..7b8003b30 100644 --- a/.gitignore +++ b/.gitignore @@ -1,3 +1,6 @@ /.*project /.settings /.autotools +radio/src/bootloader/.dep/ +radio/src/bootloader/bootloader_ramBoot* +*.lbm diff --git a/DONATIONS.txt b/DONATIONS.txt index 323f2e19c..359d46d80 100644 --- a/DONATIONS.txt +++ b/DONATIONS.txt @@ -343,4 +343,6 @@ Trent Ready Mark Maskiell Robert Crockford Mark Illum +David McGuire +Martyn Coles diff --git a/companion/src/CMakeLists.txt b/companion/src/CMakeLists.txt index 7c654cae6..90f4aaeb8 100644 --- a/companion/src/CMakeLists.txt +++ b/companion/src/CMakeLists.txt @@ -36,7 +36,7 @@ ELSE() MESSAGE( "SDL not found! Joysticks support will be disabled" ) ENDIF() -FIND_PACKAGE( Qt4 REQUIRED ) +FIND_PACKAGE(Qt4 4.8.4 REQUIRED) SET( QT_USE_QTNETWORK True ) SET( QT_USE_QTXML True ) INCLUDE( ${QT_USE_FILE} ) @@ -90,6 +90,13 @@ add_custom_command( WORKING_DIRECTORY ${RADIO_SRC_DIRECTORY} ) +add_custom_command( + OUTPUT ${RADIO_SRC_DIRECTORY}/stamp-opentx.h + COMMAND make stamp_header + DEPENDS ${RADIO_SRC_DIRECTORY}/Makefile + WORKING_DIRECTORY ${RADIO_SRC_DIRECTORY} +) + include_directories( ${CMAKE_CURRENT_BINARY_DIR} ${PROJECT_SOURCE_DIR}/../.. @@ -128,6 +135,7 @@ set(companion_SRCS firmwares/opentx/opentxsimulator.cpp firmwares/ersky9x/ersky9xeeprom.cpp firmwares/ersky9x/ersky9xinterface.cpp + ${RADIO_SRC_DIRECTORY}/stamp-opentx.h ${RADIO_SRC_DIRECTORY}/bitmaps/sticks.lbm ${RADIO_SRC_DIRECTORY}/translations/en.h appdata.cpp diff --git a/companion/src/burnconfigdialog.cpp b/companion/src/burnconfigdialog.cpp index a2d08fd21..b802ba414 100644 --- a/companion/src/burnconfigdialog.cpp +++ b/companion/src/burnconfigdialog.cpp @@ -15,6 +15,7 @@ burnConfigDialog::burnConfigDialog(QWidget *parent) : ui(new Ui::burnConfigDialog) { ui->setupUi(this); + setWindowIcon(CompanionIcon("configure.png")); ui->avrdude_programmer->model()->sort(0); getSettings(); diff --git a/companion/src/burndialog.cpp b/companion/src/burndialog.cpp index 617c7ea9e..d5e89805f 100644 --- a/companion/src/burndialog.cpp +++ b/companion/src/burndialog.cpp @@ -18,6 +18,7 @@ burnDialog::burnDialog(QWidget *parent, int Type, QString * fileName, bool * bac hexType(Type) { ui->setupUi(this); + setWindowIcon(CompanionIcon("write_flash.png")); if(!g.profile[g.id()].splashFile().isEmpty()){ imageSource=PROFILE; diff --git a/companion/src/customizesplashdialog.cpp b/companion/src/customizesplashdialog.cpp index 42bf463da..3e9ed21c9 100644 --- a/companion/src/customizesplashdialog.cpp +++ b/companion/src/customizesplashdialog.cpp @@ -142,7 +142,7 @@ customizeSplashDialog::customizeSplashDialog(QWidget *parent) : ui(new Ui::customizeSplashDialog) { ui->setupUi(this); - this->setWindowIcon(CompanionIcon("paint.png")); + setWindowIcon(CompanionIcon("paintbrush.png")); ui->leftLibraryButton->setIcon(CompanionIcon("library.png")); ui->rightLibraryButton->setIcon(CompanionIcon("library.png")); diff --git a/companion/src/eeprominterface.cpp b/companion/src/eeprominterface.cpp index 711b68764..d2b2358eb 100644 --- a/companion/src/eeprominterface.cpp +++ b/companion/src/eeprominterface.cpp @@ -126,11 +126,14 @@ RawSourceRange RawSource::getRange(bool singleprec) result.max = singleprec ? 1540 : 3000; break; case TELEMETRY_SOURCE_T1: + case TELEMETRY_SOURCE_T1_MAX: case TELEMETRY_SOURCE_T2: + case TELEMETRY_SOURCE_T2_MAX: result.min = -30; result.max = 225; break; case TELEMETRY_SOURCE_RPM: + case TELEMETRY_SOURCE_RPM_MAX: result.step = singleprec ? 50 : 1; result.max = singleprec ? 12750 : 20000; break; @@ -138,6 +141,7 @@ RawSourceRange RawSource::getRange(bool singleprec) result.max = 100; break; case TELEMETRY_SOURCE_SPEED: + case TELEMETRY_SOURCE_SPEED_MAX: result.step = singleprec ? 4 : 1; result.max = singleprec ? 944 : 2000; if (model && !model->frsky.imperial) { @@ -146,21 +150,26 @@ RawSourceRange RawSource::getRange(bool singleprec) } break; case TELEMETRY_SOURCE_DIST: + case TELEMETRY_SOURCE_DIST_MAX: result.step = singleprec ? 8 : 1; result.max = singleprec ? 2040 : 10000; break; case TELEMETRY_SOURCE_CELL: + case TELEMETRY_SOURCE_CELL_MIN: result.step = singleprec ? 0.02 : 0.01; result.max = 5.1; result.decimals = 2; break; case TELEMETRY_SOURCE_CELLS_SUM: + case TELEMETRY_SOURCE_CELLS_MIN: case TELEMETRY_SOURCE_VFAS: + case TELEMETRY_SOURCE_VFAS_MIN: result.step = 0.1; result.max = 25.5; result.decimals = 1; break; case TELEMETRY_SOURCE_CURRENT: + case TELEMETRY_SOURCE_CURRENT_MAX: result.step = singleprec ? 0.5 : 0.1; result.max = singleprec ? 127.5 : 200.0; result.decimals = 1; @@ -170,6 +179,7 @@ RawSourceRange RawSource::getRange(bool singleprec) result.max = singleprec ? 5100 : 10000; break; case TELEMETRY_SOURCE_POWER: + case TELEMETRY_SOURCE_POWER_MAX: result.step = singleprec ? 5 : 1; result.max = singleprec ? 1275 : 2000; break; @@ -221,12 +231,12 @@ QString RawSource::toString() QObject::tr("A1"), QObject::tr("A2"), QObject::tr("A3"), QObject::tr("A4"), QObject::tr("Alt"), QObject::tr("Rpm"), QObject::tr("Fuel"), QObject::tr("T1"), QObject::tr("T2"), QObject::tr("Speed"), QObject::tr("Dist"), QObject::tr("GPS Alt"), - QObject::tr("Cell"), QObject::tr("Cels"), QObject::tr("Vfas"), QObject::tr("Curr"), QObject::tr("Cnsp"), QObject::tr("Powr"), + QObject::tr("Cell"), QObject::tr("Cells"), QObject::tr("Vfas"), QObject::tr("Curr"), QObject::tr("Cnsp"), QObject::tr("Powr"), QObject::tr("AccX"), QObject::tr("AccY"), QObject::tr("AccZ"), QObject::tr("HDG "), QObject::tr("VSpd"), QObject::tr("ASpd"), QObject::tr("dTE"), QObject::tr("A1-"), QObject::tr("A2-"), QObject::tr("A3-"), QObject::tr("A4-"), - QObject::tr("Alt-"), QObject::tr("Alt+"), QObject::tr("Rpm+"), QObject::tr("T1+"), QObject::tr("T2+"), QObject::tr("Spd+"), QObject::tr("Dst+"), - QObject::tr("Cel-"), QObject::tr("Cels-"), QObject::tr("Vfs-"), QObject::tr("Cur+"), QObject::tr("Pwr+"), + QObject::tr("Alt-"), QObject::tr("Alt+"), QObject::tr("Rpm+"), QObject::tr("T1+"), QObject::tr("T2+"), QObject::tr("Speed+"), QObject::tr("Dist+"), + QObject::tr("Cell-"), QObject::tr("Cells-"), QObject::tr("Vfas-"), QObject::tr("Curr+"), QObject::tr("Powr+"), QObject::tr("ACC"), QObject::tr("Time"), }; diff --git a/companion/src/eeprominterface.h b/companion/src/eeprominterface.h index f4a2bc7dc..98804b3d1 100644 --- a/companion/src/eeprominterface.h +++ b/companion/src/eeprominterface.h @@ -217,6 +217,7 @@ enum TelemetrySource { TELEMETRY_SOURCE_CELL_MIN, TELEMETRY_SOURCE_CELLS_MIN, TELEMETRY_SOURCE_VFAS_MIN, + TELEMETRY_SOURCE_CURRENT_MAX, TELEMETRY_SOURCE_POWER_MAX, TELEMETRY_SOURCE_ACC, TELEMETRY_SOURCE_GPS_TIME, diff --git a/companion/src/firmwares/opentx/opentxGruvin9xsimulator.cpp b/companion/src/firmwares/opentx/opentxGruvin9xsimulator.cpp index fb101b359..bca5842ad 100644 --- a/companion/src/firmwares/opentx/opentxGruvin9xsimulator.cpp +++ b/companion/src/firmwares/opentx/opentxGruvin9xsimulator.cpp @@ -74,6 +74,7 @@ namespace Open9xGruvin9x { #include "radio/src/simpgmspace.cpp" #include "radio/src/templates.cpp" #include "radio/src/translations.cpp" +#include "radio/src/fonts.cpp" #include "radio/src/audio_avr.cpp" #include "radio/src/buzzer.cpp" #include "radio/src/targets/gruvin9x/somo14d.cpp" diff --git a/companion/src/firmwares/opentx/opentxM128simulator.cpp b/companion/src/firmwares/opentx/opentxM128simulator.cpp index a03045c2d..14100e857 100644 --- a/companion/src/firmwares/opentx/opentxM128simulator.cpp +++ b/companion/src/firmwares/opentx/opentxM128simulator.cpp @@ -73,6 +73,7 @@ namespace Open9xM128 { #include "radio/src/simpgmspace.cpp" #include "radio/src/templates.cpp" #include "radio/src/translations.cpp" +#include "radio/src/fonts.cpp" #include "radio/src/audio_avr.cpp" #include "radio/src/targets/stock/voice.cpp" #include "radio/src/telemetry/frsky.cpp" diff --git a/companion/src/firmwares/opentx/opentxSky9xsimulator.cpp b/companion/src/firmwares/opentx/opentxSky9xsimulator.cpp index 6abd60971..21d9df740 100644 --- a/companion/src/firmwares/opentx/opentxSky9xsimulator.cpp +++ b/companion/src/firmwares/opentx/opentxSky9xsimulator.cpp @@ -91,6 +91,7 @@ namespace Open9xSky9x { #include "radio/src/simpgmspace.cpp" #include "radio/src/templates.cpp" #include "radio/src/translations.cpp" +#include "radio/src/fonts.cpp" #include "radio/src/telemetry/frsky.cpp" #include "radio/src/targets/sky9x/audio_driver.cpp" #include "radio/src/audio_arm.cpp" diff --git a/companion/src/firmwares/opentx/opentxTaranisSimulator.cpp b/companion/src/firmwares/opentx/opentxTaranisSimulator.cpp index f809b3447..63b369d15 100644 --- a/companion/src/firmwares/opentx/opentxTaranisSimulator.cpp +++ b/companion/src/firmwares/opentx/opentxTaranisSimulator.cpp @@ -73,7 +73,7 @@ inline int geteepromsize() { #include "radio/src/protocols/ppm_arm.cpp" #include "radio/src/protocols/pxx_arm.cpp" #include "radio/src/protocols/dsm2_arm.cpp" -#include "radio/src/targets/taranis/pwr_driver.cpp" +#include "radio/src/targets/taranis/pwr_driver.c" #include "radio/src/eeprom_common.cpp" #include "radio/src/eeprom_conversions.cpp" #include "radio/src/eeprom_rlc.cpp" @@ -106,6 +106,7 @@ inline int geteepromsize() { #define SDCARD #include "radio/src/templates.cpp" #include "radio/src/translations.cpp" +#include "radio/src/fonts.cpp" #include "radio/src/telemetry/frsky_sport.cpp" #include "radio/src/targets/taranis/audio_driver.cpp" #include "radio/src/audio_arm.cpp" diff --git a/companion/src/firmwares/opentx/opentxeeprom.cpp b/companion/src/firmwares/opentx/opentxeeprom.cpp index 8a9744bc0..0a9de81c9 100644 --- a/companion/src/firmwares/opentx/opentxeeprom.cpp +++ b/companion/src/firmwares/opentx/opentxeeprom.cpp @@ -384,8 +384,12 @@ class TelemetrySourcesConversionTable: public ConversionTable { addConversion(1+TELEMETRY_SOURCE_T2_MAX, val++); addConversion(1+TELEMETRY_SOURCE_SPEED_MAX, val++); addConversion(1+TELEMETRY_SOURCE_DIST_MAX, val++); - addConversion(1+TELEMETRY_SOURCE_CELL_MIN, val++); - addConversion(1+TELEMETRY_SOURCE_VFAS_MIN, val++); + if (version >= 216) { + addConversion(1+TELEMETRY_SOURCE_CELL_MIN, val++); + addConversion(1+TELEMETRY_SOURCE_CELLS_MIN, val++); + addConversion(1+TELEMETRY_SOURCE_VFAS_MIN, val++); + } + addConversion(1+TELEMETRY_SOURCE_CURRENT_MAX, val++); addConversion(1+TELEMETRY_SOURCE_POWER_MAX, val++); if (IS_ARM(board) && version >= 216) { for (int i=0; i<5; i++) @@ -1008,9 +1012,15 @@ class InputField: public TransformedField { virtual void afterImport() { - if (IS_TARANIS(board) && version < 216) { - if (expo.mode) { - expo.srcRaw = RawSource(SOURCE_TYPE_STICK, expo.chn); + if (IS_TARANIS(board)) { + if (version < 216) { + if (expo.mode) { + expo.srcRaw = RawSource(SOURCE_TYPE_STICK, expo.chn); + } + } + else { + if (expo.srcRaw.type != SOURCE_TYPE_NONE) + expo.mode = 3; } } diff --git a/companion/src/firmwares/opentx/opentxsimulator.cpp b/companion/src/firmwares/opentx/opentxsimulator.cpp index 1841d22b7..05e680073 100644 --- a/companion/src/firmwares/opentx/opentxsimulator.cpp +++ b/companion/src/firmwares/opentx/opentxsimulator.cpp @@ -80,6 +80,7 @@ namespace Open9x { #include "radio/src/telemetry/frsky.cpp" #include "radio/src/templates.cpp" #include "radio/src/translations.cpp" +#include "radio/src/fonts.cpp" #include "radio/src/targets/stock/voice.cpp" #include "radio/src/buzzer.cpp" #include "radio/src/translations/tts_en.cpp" diff --git a/companion/src/helpers.cpp b/companion/src/helpers.cpp index 536921de1..52871a32e 100644 --- a/companion/src/helpers.cpp +++ b/companion/src/helpers.cpp @@ -95,31 +95,6 @@ void populateRotEncCB(QComboBox *b, int value, int renumber) b->setCurrentIndex(value); } -void populateCustomScreenFieldCB(QComboBox *b, unsigned int value, bool last=false, int hubproto=0) -{ - int telem_hub[] = {0,0,0,0,0,0,0,0,2,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,2,0,0,2,2,1,1,1,1,1,1}; - b->clear(); - - b->addItem(RawSource(SOURCE_TYPE_NONE, 0).toString()); - - for (unsigned int i = 0; i <= (last ? TELEMETRY_SOURCES_DISPLAY_COUNT : TELEMETRY_SOURCES_STATUS_COUNT); i++) { - b->addItem(RawSource(SOURCE_TYPE_TELEMETRY, i).toString()); - if (!(i>=sizeof(telem_hub)/sizeof(int) || telem_hub[i]==0 || ((telem_hub[i]>=hubproto) && hubproto!=0))) { - QModelIndex index = b->model()->index(i, 0); - QVariant v(0); - b->model()->setData(index, v, Qt::UserRole - 1); - } - } - - if (value>=sizeof(telem_hub)/sizeof(int)) - b->setCurrentIndex(0); - else if (telem_hub[value]==0 || ((telem_hub[value]>=hubproto) && hubproto!=0)) { - b->setCurrentIndex(value); - } - - b->setMaxVisibleItems(10); -} - QString getProtocolStr(const int proto) { static const char *strings[] = { "OFF", diff --git a/companion/src/helpers.h b/companion/src/helpers.h index 857d66749..53bff4d2f 100644 --- a/companion/src/helpers.h +++ b/companion/src/helpers.h @@ -88,7 +88,6 @@ void populateSwitchCB(QComboBox *b, const RawSwitch & value, unsigned long attr= void populatePhasesCB(QComboBox *b, int value); void populateGvarUseCB(QComboBox *b, unsigned int phase); -void populateCustomScreenFieldCB(QComboBox *b, unsigned int value, bool last, int hubproto); QString getProtocolStr(const int proto); QString getPhasesStr(unsigned int phases, ModelData & model); diff --git a/companion/src/modeledit/expodialog.cpp b/companion/src/modeledit/expodialog.cpp index a71d87ebf..7b04620ff 100644 --- a/companion/src/modeledit/expodialog.cpp +++ b/companion/src/modeledit/expodialog.cpp @@ -3,11 +3,12 @@ #include "eeprominterface.h" #include "helpers.h" -ExpoDialog::ExpoDialog(QWidget *parent, ModelData & model, ExpoData *expoData, int stickMode) : +ExpoDialog::ExpoDialog(QWidget *parent, ModelData & model, ExpoData *expoData, int stickMode, char * inputName) : QDialog(parent), ui(new Ui::ExpoDialog), model(model), - ed(expoData) + ed(expoData), + inputName(inputName) { ui->setupUi(this); QLabel * lb_fp[] = {ui->lb_FP0,ui->lb_FP1,ui->lb_FP2,ui->lb_FP3,ui->lb_FP4,ui->lb_FP5,ui->lb_FP6,ui->lb_FP7,ui->lb_FP8 }; @@ -76,7 +77,7 @@ ExpoDialog::ExpoDialog(QWidget *parent, ModelData & model, ExpoData *expoData, i } ui->inputName->setValidator(new QRegExpValidator(rx, this)); - ui->inputName->setText(model.inputNames[ed->chn]); + ui->inputName->setText(inputName); ui->lineName->setValidator(new QRegExpValidator(rx, this)); ui->lineName->setText(ed->name); @@ -139,7 +140,7 @@ void ExpoDialog::valuesChanged() ed->mode = ui->sideCB->currentIndex() + 1; strcpy(ed->name, ui->lineName->text().toAscii().data()); - strcpy(model.inputNames[ed->chn], ui->inputName->text().toAscii().data()); + strcpy(inputName, ui->inputName->text().toAscii().data()); ed->phases=0; for (int i=8; i>=0 ; i--) { diff --git a/companion/src/modeledit/expodialog.h b/companion/src/modeledit/expodialog.h index 2d96b130a..ddb3d750c 100644 --- a/companion/src/modeledit/expodialog.h +++ b/companion/src/modeledit/expodialog.h @@ -14,7 +14,7 @@ namespace Ui { class ExpoDialog : public QDialog { Q_OBJECT public: - ExpoDialog(QWidget *parent, ModelData & model, ExpoData *expodata, int stickMode); + ExpoDialog(QWidget *parent, ModelData & model, ExpoData *expodata, int stickMode, char * inputName); ~ExpoDialog(); protected: @@ -28,6 +28,7 @@ class ExpoDialog : public QDialog { Ui::ExpoDialog * ui; ModelData & model; ExpoData * ed; + char * inputName; GVarGroup * gvGroup; CurveGroup * curveGroup; }; diff --git a/companion/src/modeledit/flightmodes.cpp b/companion/src/modeledit/flightmodes.cpp index a5cd400a0..dffb391aa 100644 --- a/companion/src/modeledit/flightmodes.cpp +++ b/companion/src/modeledit/flightmodes.cpp @@ -194,33 +194,29 @@ void FlightMode::update() for (int i=0; isetText(model.gvars_names[i]); - if (phase.gvars[i] < 1024) { - gvValues[i]->setValue(phase.gvars[i]); - gvValues[i]->setDisabled(false); - } - else { - int idx = phase.gvars[i] - 1025; - if (idx >= i) idx++; - // TODO no!!!! - PhaseData *phasegvar = &model.phaseData[idx]; - gvValues[i]->setValue(phasegvar->gvars[i]); - gvValues[i]->setDisabled(true); + gvValues[i]->setDisabled(false); + int idx = phase.gvars[i]; + PhaseData *phasegvar = &phase; + while (idx >= 1024) { + idx -= 1025; + phasegvar = &model.phaseData[idx]; + idx = phasegvar->gvars[i]; + gvValues[i]->setDisabled(true); } + gvValues[i]->setValue(phasegvar->gvars[i]); } - for (int i=0; isetValue(phase.rotaryEncoders[i]); - reValues[i]->setDisabled(false); - } - else { - int idx = phase.rotaryEncoders[i] - 1025; - if (idx >= i) idx++; - // TODO no!!!! - PhaseData *phasere = &model.phaseData[idx]; - reValues[i]->setValue(phasere->rotaryEncoders[i]); + for (int i=0; isetDisabled(false); + int idx = phase.rotaryEncoders[i]; + PhaseData *phasere = &phase; + while (idx >= 1024) { + idx -= 1025; + phasere = &model.phaseData[idx]; + idx = phasere->rotaryEncoders[i]; reValues[i]->setDisabled(true); } + reValues[i]->setValue(phasere->rotaryEncoders[i]); } } @@ -311,21 +307,12 @@ void FlightMode::phaseGVUse_currentIndexChanged(int index) QComboBox *comboBox = qobject_cast(sender()); int gvar = comboBox->property("index").toInt(); if (index == 0) { - int value = phase.gvars[gvar]; - if (value>1024) { - value=0; - } - gvValues[gvar]->setValue(value); - gvValues[gvar]->setEnabled(true); - phase.gvars[gvar]=value; + phase.gvars[gvar]=0; } else { phase.gvars[gvar] = 1024+index; - // TOTO it's wrong!!! - int value = model.phaseData[index + (index>phaseIdx ? 0 :-1)].gvars[gvar]; - gvValues[gvar]->setValue(value); - gvValues[gvar]->setDisabled(true); } + update(); emit modified(); lock = false; } @@ -348,21 +335,12 @@ void FlightMode::phaseREUse_currentIndexChanged(int index) QComboBox *comboBox = qobject_cast(sender()); int re = comboBox->property("index").toInt(); if (index == 0) { - // TODO no!!! - int value = phase.rotaryEncoders[re]; - if (value > 1024) { - value = 0; - } - reValues[re]->setValue(value); - reValues[re]->setEnabled(true); - phase.rotaryEncoders[re] = value; + phase.rotaryEncoders[re] = 0; } else { - phase.rotaryEncoders[re] = 1024 + index; - int value = model.phaseData[index + (index>phaseIdx ? 0 :-1)].rotaryEncoders[re]; - reValues[re]->setValue(value); - reValues[re]->setDisabled(true) ; + phase.rotaryEncoders[re] = 1024 + index; ; } + update(); lock = false; emit modified(); } diff --git a/companion/src/modeledit/inputs.cpp b/companion/src/modeledit/inputs.cpp index a6e1f6eac..6096c8cdf 100644 --- a/companion/src/modeledit/inputs.cpp +++ b/companion/src/modeledit/inputs.cpp @@ -169,12 +169,18 @@ void InputsPanel::gm_openExpo(int index) if(index<0 || index>=C9X_MAX_EXPOS) return; ExpoData mixd(model.expoData[index]); + char inputName[4+1]; emit modified(); update(); + + if (GetEepromInterface()->getCapability(VirtualInputs)) + strcpy(inputName, model.inputNames[mixd.chn]); - ExpoDialog *g = new ExpoDialog(this, model, &mixd, generalSettings.stickMode); + ExpoDialog *g = new ExpoDialog(this, model, &mixd, generalSettings.stickMode, inputName); if (g->exec()) { model.expoData[index] = mixd; + if (GetEepromInterface()->getCapability(VirtualInputs)) + strcpy(model.inputNames[mixd.chn], inputName); emit modified(); update(); } diff --git a/companion/src/modeledit/modeledit.cpp b/companion/src/modeledit/modeledit.cpp index efc953736..8124e4903 100644 --- a/companion/src/modeledit/modeledit.cpp +++ b/companion/src/modeledit/modeledit.cpp @@ -22,6 +22,7 @@ ModelEdit::ModelEdit(RadioData & radioData, int modelId, bool openWizard, bool i generalSettings(radioData.generalSettings) { ui->setupUi(this); + setWindowIcon(CompanionIcon("edit.png")); restoreGeometry(g.modelEditGeo()); ui->pushButton->setIcon(CompanionIcon("simulate.png")); addTab(new Setup(this, model), tr("Setup")); diff --git a/companion/src/modeledit/telemetry.cpp b/companion/src/modeledit/telemetry.cpp index e06fe96a3..d32420db3 100644 --- a/companion/src/modeledit/telemetry.cpp +++ b/companion/src/modeledit/telemetry.cpp @@ -28,10 +28,20 @@ TelemetryAnalog::TelemetryAnalog(QWidget *parent, FrSkyChannelData & analog): update(); ui->UnitCB->setCurrentIndex(analog.type); - ui->alarm1LevelCB->setCurrentIndex(analog.alarms[0].level); - ui->alarm1GreaterCB->setCurrentIndex(analog.alarms[0].greater); - ui->alarm2LevelCB->setCurrentIndex(analog.alarms[1].level); - ui->alarm2GreaterCB->setCurrentIndex(analog.alarms[1].greater); + if (!IS_TARANIS(GetEepromInterface()->getBoard())) { + ui->alarm1LevelCB->setCurrentIndex(analog.alarms[0].level); + ui->alarm1GreaterCB->setCurrentIndex(analog.alarms[0].greater); + ui->alarm2LevelCB->setCurrentIndex(analog.alarms[1].level); + ui->alarm2GreaterCB->setCurrentIndex(analog.alarms[1].greater); + } + else { + ui->alarm1LevelCB->hide(); + ui->alarm2LevelCB->hide(); + ui->alarm1GreaterCB->hide(); + ui->alarm2GreaterCB->hide(); + ui->alarm1Label->setText(tr("Low Alarm")); + ui->alarm2Label->setText(tr("Critical Alarm")); + } if (!(GetEepromInterface()->getCapability(Telemetry) & TM_HASOFFSET)) { ui->CalibSB->hide(); @@ -281,7 +291,7 @@ TelemetryCustomScreen::TelemetryCustomScreen(QWidget *parent, ModelData & model, for (int c=0; cgetCapability(TelemetryCustomScreensFieldsPerLine); c++) { fieldsCB[l][c] = new QComboBox(this); fieldsCB[l][c]->setProperty("index", c + (l<<8)); - populateCustomScreenFieldCB(fieldsCB[l][c], screen.body.lines[l].source[c], (l<4), model.frsky.usrProto); + populateTelemetrySourceCB(fieldsCB[l][c], screen.body.lines[l].source[c], l==3, model.frsky.usrProto); ui->screenNumsLayout->addWidget(fieldsCB[l][c], l, c, 1, 1); connect(fieldsCB[l][c], SIGNAL(currentIndexChanged(int)), this, SLOT(customFieldChanged(int))); } @@ -290,7 +300,7 @@ TelemetryCustomScreen::TelemetryCustomScreen(QWidget *parent, ModelData & model, for (int l=0; l<4; l++) { barsCB[l] = new QComboBox(this); barsCB[l]->setProperty("index", l); - populateCustomScreenFieldCB(barsCB[l], screen.body.bars[l].source, false, model.frsky.usrProto); + populateTelemetrySourceCB(barsCB[l], screen.body.bars[l].source, false, model.frsky.usrProto); connect(barsCB[l], SIGNAL(currentIndexChanged(int)), this, SLOT(barSourceChanged(int))); ui->screenBarsLayout->addWidget(barsCB[l], l, 0, 1, 1); @@ -316,6 +326,31 @@ TelemetryCustomScreen::TelemetryCustomScreen(QWidget *parent, ModelData & model, update(); } +void TelemetryCustomScreen::populateTelemetrySourceCB(QComboBox *b, unsigned int value, bool last, int hubproto) +{ + int telem_hub[] = {0,0,0,0,0,0,0,0,2,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,2,0,0,2,2,1,1,1,1,1,1}; + b->clear(); + + b->addItem(RawSource(SOURCE_TYPE_NONE, 0).toString()); + + for (unsigned int i = 0; i < (last ? TELEMETRY_SOURCES_STATUS_COUNT : TELEMETRY_SOURCES_DISPLAY_COUNT); i++) { + b->addItem(RawSource(SOURCE_TYPE_TELEMETRY, i).toString()); + if (!(i>=sizeof(telem_hub)/sizeof(int) || telem_hub[i]==0 || ((telem_hub[i]>=hubproto) && hubproto!=0))) { + QModelIndex index = b->model()->index(i, 0); + QVariant v(0); + b->model()->setData(index, v, Qt::UserRole - 1); + } + } + + if (value>=sizeof(telem_hub)/sizeof(int)) + b->setCurrentIndex(0); + else if (telem_hub[value]==0 || ((telem_hub[value]>=hubproto) && hubproto!=0)) { + b->setCurrentIndex(value); + } + + b->setMaxVisibleItems(10); +} + TelemetryCustomScreen::~TelemetryCustomScreen() { delete ui; @@ -347,6 +382,8 @@ void TelemetryCustomScreen::update() void TelemetryCustomScreen::updateBar(int line) { + lock = true; + int index = screen.body.bars[line].source; barsCB[line]->setCurrentIndex(index); if (index) { @@ -372,6 +409,8 @@ void TelemetryCustomScreen::updateBar(int line) minSB[line]->setDisabled(true); maxSB[line]->setDisabled(true); } + + lock = false; } void TelemetryCustomScreen::on_screenType_currentIndexChanged(int index) @@ -393,13 +432,15 @@ void TelemetryCustomScreen::customFieldChanged(int value) void TelemetryCustomScreen::barSourceChanged(int index) { - QComboBox * cb = qobject_cast(sender()); - int line = cb->property("index").toInt(); - screen.body.bars[line].source = index; - screen.body.bars[line].barMin = 0; - screen.body.bars[line].barMax = 0; - updateBar(line); - emit modified(); + if (!lock) { + QComboBox * cb = qobject_cast(sender()); + int line = cb->property("index").toInt(); + screen.body.bars[line].source = index; + screen.body.bars[line].barMin = 0; + screen.body.bars[line].barMax = 0; + updateBar(line); + emit modified(); + } } void TelemetryCustomScreen::barMinChanged(double value) @@ -467,8 +508,16 @@ void TelemetryPanel::setup() } ui->rssiAlarm1SB->setValue(model.frsky.rssiAlarms[0].value); ui->rssiAlarm2SB->setValue(model.frsky.rssiAlarms[1].value); - ui->rssiAlarm1CB->setCurrentIndex(model.frsky.rssiAlarms[0].level); - ui->rssiAlarm2CB->setCurrentIndex(model.frsky.rssiAlarms[1].level); + if (!IS_TARANIS(GetEepromInterface()->getBoard())) { + ui->rssiAlarm1CB->setCurrentIndex(model.frsky.rssiAlarms[0].level); + ui->rssiAlarm2CB->setCurrentIndex(model.frsky.rssiAlarms[1].level); + } + else { + ui->rssiAlarm1CB->hide(); + ui->rssiAlarm2CB->hide(); + ui->rssiAlarm1Label->setText(tr("Low Alarm")); + ui->rssiAlarm2Label->setText(tr("Critical Alarm")); + } if (!GetEepromInterface()->getCapability(HasAltitudeSel)) { ui->AltitudeGPS_ChkB->hide(); diff --git a/companion/src/modeledit/telemetry.h b/companion/src/modeledit/telemetry.h index 44233f79c..cd804465a 100644 --- a/companion/src/modeledit/telemetry.h +++ b/companion/src/modeledit/telemetry.h @@ -61,6 +61,9 @@ class TelemetryCustomScreen : public ModelPanel void barMinChanged(double value); void barMaxChanged(double value); + protected: + void populateTelemetrySourceCB(QComboBox *b, unsigned int value, bool last, int hubproto); + private: void updateBar(int line); Ui::TelemetryCustomScreen * ui; diff --git a/companion/src/modeledit/telemetry.ui b/companion/src/modeledit/telemetry.ui index 6a3a6d618..6034d2c4e 100644 --- a/companion/src/modeledit/telemetry.ui +++ b/companion/src/modeledit/telemetry.ui @@ -77,7 +77,7 @@ - + 0 @@ -157,7 +157,7 @@ - + 0 diff --git a/companion/src/modeledit/telemetry_analog.ui b/companion/src/modeledit/telemetry_analog.ui index d8b713105..d09c7b421 100644 --- a/companion/src/modeledit/telemetry_analog.ui +++ b/companion/src/modeledit/telemetry_analog.ui @@ -43,7 +43,7 @@ - + 0 @@ -106,7 +106,7 @@ - + 0 diff --git a/companion/targets/windows/companion-msys.nsi.in b/companion/targets/windows/companion-msys.nsi.in index cbf3b0c34..e2f1ed51e 100644 --- a/companion/targets/windows/companion-msys.nsi.in +++ b/companion/targets/windows/companion-msys.nsi.in @@ -109,11 +109,18 @@ Section "OpenTX companion" SecDummy ${registerExtension} "$INSTDIR\companion.exe" ".hex" "HEX_File" ${registerExtension} "$INSTDIR\companion.exe" ".companion" "EEPE_File" ${registerExtension} "$INSTDIR\companion.exe" ".eepm" "EEPM_File" - ;Create uninstaller WriteUninstaller "$INSTDIR\Uninstall.exe" - + + ;Registry information for add/remove programs + WriteRegStr HKLM "Software\Microsoft\Windows\CurrentVersion\Uninstall\OpenTX" "DisplayName" "OpenTX Companion" + WriteRegStr HKLM "Software\Microsoft\Windows\CurrentVersion\Uninstall\OpenTX" "UninstallString" "$\"$INSTDIR\Uninstall.exe$\"" + WriteRegStr HKLM "Software\Microsoft\Windows\CurrentVersion\Uninstall\OpenTX" "DisplayIcon" "$\"$INSTDIR\companion.exe$\"" + WriteRegStr HKLM "Software\Microsoft\Windows\CurrentVersion\Uninstall\OpenTX" "Publisher" "OpenTX" + WriteRegStr HKLM "Software\Microsoft\Windows\CurrentVersion\Uninstall\OpenTX" "URLInfoAbout" "http://www.open-tx.org" + WriteRegStr HKLM "Software\Microsoft\Windows\CurrentVersion\Uninstall\ImageMaker" "QuietUninstallString" "$\"$INSTDIR\Uninstall.exe$\" /S" + !insertmacro MUI_STARTMENU_WRITE_BEGIN Application ;Create shortcuts @@ -178,6 +185,7 @@ Section "Uninstall" RMDir "$SMPROGRAMS\$StartMenuFolder" DeleteRegKey /ifempty HKCU "Software\companion9x" + DeleteRegKey HKLM "Software\Microsoft\Windows\CurrentVersion\Uninstall\OpenTX" SectionEnd diff --git a/companion/targets/windows/companion-vs.nsi.in b/companion/targets/windows/companion-vs.nsi.in index 7ce8351fb..ac572467e 100644 --- a/companion/targets/windows/companion-vs.nsi.in +++ b/companion/targets/windows/companion-vs.nsi.in @@ -141,6 +141,14 @@ Section "OpenTX Companion" SecDummy ;Create uninstaller WriteUninstaller "$INSTDIR\Uninstall.exe" + ;Registry information for add/remove programs + WriteRegStr HKLM "Software\Microsoft\Windows\CurrentVersion\Uninstall\OpenTX" "DisplayName" "OpenTX Companion" + WriteRegStr HKLM "Software\Microsoft\Windows\CurrentVersion\Uninstall\OpenTX" "UninstallString" "$\"$INSTDIR\Uninstall.exe$\"" + WriteRegStr HKLM "Software\Microsoft\Windows\CurrentVersion\Uninstall\OpenTX" "DisplayIcon" "$\"$INSTDIR\companion.exe$\"" + WriteRegStr HKLM "Software\Microsoft\Windows\CurrentVersion\Uninstall\OpenTX" "Publisher" "OpenTX" + WriteRegStr HKLM "Software\Microsoft\Windows\CurrentVersion\Uninstall\OpenTX" "URLInfoAbout" "http://www.open-tx.org" + WriteRegStr HKLM "Software\Microsoft\Windows\CurrentVersion\Uninstall\ImageMaker" "QuietUninstallString" "$\"$INSTDIR\Uninstall.exe$\" /S" + !insertmacro MUI_STARTMENU_WRITE_BEGIN Application ;Create shortcuts @@ -208,6 +216,7 @@ Section "Uninstall" RMDir "$SMPROGRAMS\$StartMenuFolder" DeleteRegKey /ifempty HKCU "Software\OpenTX" + DeleteRegKey HKLM "Software\Microsoft\Windows\CurrentVersion\Uninstall\OpenTX" SectionEnd diff --git a/radio/src/FatFs/ffconf.h b/radio/src/FatFs/ffconf.h index fcdf65533..48e579763 100644 --- a/radio/src/FatFs/ffconf.h +++ b/radio/src/FatFs/ffconf.h @@ -28,14 +28,20 @@ extern "C" { / object instead of the sector buffer in the individual file object for file / data transfer. This reduces memory consumption 512 bytes each file object. */ - +#if defined(BOOT) +#define _FS_READONLY 1 /* 0:Read/Write or 1:Read only */ +#else #define _FS_READONLY 0 /* 0:Read/Write or 1:Read only */ +#endif /* Setting _FS_READONLY to 1 defines read only configuration. This removes / writing functions, f_write, f_sync, f_unlink, f_mkdir, f_chmod, f_rename, / f_truncate and useless f_getfree. */ - +#if defined(BOOT) +#define _FS_MINIMIZE 1 /* 0 to 3 */ +#else #define _FS_MINIMIZE 0 /* 0 to 3 */ +#endif /* The _FS_MINIMIZE option defines minimization level to remove some functions. / / 0: Full function. @@ -45,7 +51,11 @@ extern "C" { / 3: f_lseek is removed in addition to 2. */ +#if defined(BOOT) +#define _USE_STRFUNC 0 /* 0:Disable or 1-2:Enable */ +#else #define _USE_STRFUNC 1 /* 0:Disable or 1-2:Enable */ +#endif /* To enable string functions, set _USE_STRFUNC to 1 or 2. */ @@ -186,7 +196,7 @@ extern "C" { /* A header file that defines sync object types on the O/S, such as / windows.h, ucos_ii.h and semphr.h, must be included prior to ff.h. */ -#if defined(CPUARM) +#if defined(CPUARM) && !defined(BOOT) #define _FS_REENTRANT 1 /* 0:Disable or 1:Enable */ #define _SYNC_t unsigned char /*OS_MutexID*/ /* O/S dependent type of sync object. e.g. HANDLE, OS_EVENT*, ID and etc.. */ #else diff --git a/radio/src/Makefile b/radio/src/Makefile index 4bda9060e..b4c7f048f 100644 --- a/radio/src/Makefile +++ b/radio/src/Makefile @@ -266,11 +266,16 @@ LUA = NO # Values = NO, READONLY, NOMENUS MENUS_LOCK == NO +# Include bootloader, for now only for Taranis +# Values = YES, NO +BOOTLOADER = YES + #------- END BUILD OPTIONS --------------------------- # Define programs and commands. SHELL = sh IMG2LBM = -python ../util/img2lbm.py +BIN2LBM = -python ../util/bin2lbm.py TRANSLATE = -python ../util/translate.py VERSION = 1.99 @@ -281,7 +286,7 @@ EXTRAINCDIRS = # MCU name ifneq ($(PCB), $(filter $(PCB), STD 9X 9XR STD128 9X128 9XR128 9X2561 9XR2561 GRUVIN9X MEGA2560 SKY9X TARANIS)) - $(error Sorry, the PCB $(PCB) is not supported yet in openTx) + $(error Sorry, the PCB $(PCB) is not supported yet in OpenTX) endif GVARS_VARIANT = +1 @@ -613,7 +618,11 @@ ifeq ($(PCB), TARANIS) else CPPDEFS = -DREV4 endif - LDSCRIPT = targets/taranis/stm32_flash.ld + ifeq ($(BOOTLOADER), YES) + LDSCRIPT = targets/taranis/stm32_flash_bl.ld + else + LDSCRIPT = targets/taranis/stm32_flash.ld + endif TRGT = arm-none-eabi- MCU = cortex-m3 OPT = 2 @@ -627,12 +636,13 @@ ifeq ($(PCB), TARANIS) EXTRAINCDIRS += targets/taranis/STM32_USB-Host-Device_Lib_V2.1.0/Libraries/STM32_USB_OTG_Driver/inc targets/taranis/STM32_USB-Host-Device_Lib_V2.1.0/Libraries/STM32_USB_Device_Library/Core/inc EXTRAINCDIRS += targets/taranis/STM32_USB-Host-Device_Lib_V2.1.0/Libraries/STM32_USB_Device_Library/Class/msc/inc targets/taranis/STM32_USB-Host-Device_Lib_V2.1.0/Libraries/STM32_USB_Device_Library/Class/hid/inc BOARDSRC = targets/taranis/board_taranis.cpp - EXTRABOARDSRC += targets/taranis/lcd_driver.cpp targets/taranis/aspi.cpp targets/taranis/i2c.c + EXTRABOARDSRC += targets/taranis/lcd_driver.cpp targets/taranis/aspi.c targets/taranis/i2c.c targets/taranis/delays.c SRC += CoOS/kernel/core.c CoOS/kernel/hook.c CoOS/kernel/task.c CoOS/kernel/event.c CoOS/kernel/time.c CoOS/kernel/timer.c CoOS/kernel/flag.c CoOS/kernel/mutex.c CoOS/kernel/serviceReq.c CoOS/portable/GCC/port.c CoOS/portable/arch.c + SRC += targets/taranis/pwr_driver.c targets/taranis/usb_driver.c EEPROMSRC = eeprom_common.cpp eeprom_rlc.cpp eeprom_conversions.cpp PULSESSRC = protocols/pulses_arm.cpp protocols/ppm_arm.cpp protocols/pxx_arm.cpp CPPSRC += audio_arm.cpp - CPPSRC += targets/taranis/pwr_driver.cpp targets/taranis/pulses_driver.cpp targets/taranis/keys_driver.cpp targets/taranis/adc_driver.cpp targets/taranis/trainer_driver.cpp targets/taranis/audio_driver.cpp targets/taranis/delays.cpp targets/taranis/uart3_driver.cpp targets/taranis/sport_driver.cpp + CPPSRC += targets/taranis/pulses_driver.cpp targets/taranis/keys_driver.cpp targets/taranis/adc_driver.cpp targets/taranis/trainer_driver.cpp targets/taranis/audio_driver.cpp targets/taranis/uart3_driver.cpp targets/taranis/sport_driver.cpp CPPSRC += bmp.cpp gui/view_channels.cpp gui/view_about.cpp gui/view_text.cpp SRC += targets/taranis/STM32F2xx_StdPeriph_Lib_V1.1.0/Libraries/CMSIS/Device/ST/STM32F2xx/Source/Templates/system_stm32f2xx.c SRC += targets/taranis/STM32F2xx_StdPeriph_Lib_V1.1.0/Libraries/STM32F2xx_StdPeriph_Driver/src/misc.c @@ -697,6 +707,11 @@ ifeq ($(PCB), TARANIS) CPPSRC += protocols/hubsan.cpp CPPSRC += targets/taranis/a7105_driver.cpp endif + + ifeq ($(BOOTLOADER), YES) + CPPSRC += loadboot.cpp + CPPDEFS += -DBOOTLOADER + endif endif CC = $(TRGT)gcc @@ -728,7 +743,7 @@ else TTS_SRC = $(shell sh -c "if test -f $(STD_TTS_SRC); then echo $(STD_TTS_SRC); else echo translations/tts_en.cpp; fi") endif -CPPSRC += opentx.cpp $(PULSESSRC) stamp.cpp gui/menus.cpp gui/menu_model.cpp gui/menu_general.cpp gui/view_main.cpp gui/view_statistics.cpp $(EEPROMSRC) lcd.cpp keys.cpp maths.cpp translations.cpp $(TTS_SRC) +CPPSRC += opentx.cpp $(PULSESSRC) stamp.cpp gui/menus.cpp gui/menu_model.cpp gui/menu_general.cpp gui/view_main.cpp gui/view_statistics.cpp $(EEPROMSRC) lcd.cpp keys.cpp maths.cpp translations.cpp fonts.cpp $(TTS_SRC) # Debugging format. # Native formats for AVR-GCC's -g are dwarf-2 [default] or stabs. @@ -1082,10 +1097,21 @@ all: begin gccversion sizebefore build sizeafter end # Change the build target to build a HEX file or a library. ifeq ($(ARCH), AVR) build: stamp_header tra lbm allsrc.cpp elf remallsrc hex +else ifeq ($(PCB), TARANIS) + build: stamp_header tra lbm bootloader.lbm allsrc.cpp elf remallsrc bin else build: stamp_header tra lbm allsrc.cpp elf remallsrc bin endif +# build bootloader +bootloader.lbm: bootloader/bootloader_ramBoot.bin + test -z "$$(find $^ -size +32k)" + $(BIN2LBM) $^ $@ + +.PHONY bootloader/bootloader_ramBoot.bin: + @echo "Building bootloader..." + $(MAKE) -C bootloader PCB=$(PCB) PCBREV=$(PCBREV) + tra: translations/en.h translations/cz.h translations/de.h translations/es.h translations/fi.h translations/fr.h translations/it.h translations/pl.h translations/pt.h translations/se.h lbm: fonts bitmaps/sticks.lbm @@ -1237,7 +1263,7 @@ sizeafter: @if test -f $(TARGET).elf; then echo; echo $(MSG_SIZE_AFTER); $(ELFSIZE); fi # Display compiler version information. -gccversion : +gccversion: @$(CC) --version FOXINC=-I/usr/local/include/fox-1.6 -I/usr/include/fox-1.6 \ @@ -1277,8 +1303,7 @@ endif %.eep: %.elf @echo @echo $(MSG_EEPROM) $@ - -$(OBJCOPY) -j .eeprom --set-section-flags=.eeprom="alloc,load" \ ---change-section-lma .eeprom=0 -O $(FORMAT) $< $@ + -$(OBJCOPY) -j .eeprom --set-section-flags=.eeprom="alloc,load" --change-section-lma .eeprom=0 -O $(FORMAT) $< $@ # Create a symbol table from ELF output file. %.sym: %.elf @@ -1344,6 +1369,8 @@ clean_list : $(REMOVE) *.lst $(REMOVE) allsrc.cpp $(REMOVE) stamp-opentx.h + $(REMOVE) `find . -name "*.lbm"` + $(MAKE) -C bootloader clean #### Install diff --git a/radio/src/bootloader/Makefile b/radio/src/bootloader/Makefile new file mode 100644 index 000000000..1e98fe3d9 --- /dev/null +++ b/radio/src/bootloader/Makefile @@ -0,0 +1,342 @@ +# +# !!!! Do NOT edit this makefile with an editor which replace tabs by spaces !!!! +# +############################################################################################## +# +# On command line: +# +# make all = Create project +# +# make clean = Clean project files. +# +# To rebuild project do "make clean" and "make all". +# + +############################################################################################## +# Start of default section +# + +TRGT = arm-none-eabi- +CC = $(TRGT)gcc +CP = $(TRGT)objcopy +CLSS = $(TRGT)objdump +AS = $(TRGT)as +#gcc -x assembler-with-cpp +BIN = $(CP) -O ihex +BINX = $(CP) -O binary + +OBJDIR = . + +MCU = cortex-m3 + +# List all default C defines here, like -D_DEBUG=1 +DDEFS = + +# List all default ASM defines here, like -D_DEBUG=1 +DADEFS = + +# List all default directories to look for include files here +DINCDIR = + +# List the default directory to look for the libraries here +DLIBDIR = + +# List all default libraries here +DLIBS = + +MEMORIES = sram + +EXT = STD + +# +# End of default section +############################################################################################## + +############################################################################################## +# Start of user section +# + +# +# Define project name and Ram/Flash mode here +PROJECT = bootloader + +ifeq ($(PCB), TARANIS) +RUN_FROM_FLASH = 0 + else + ifeq ($(PCB), X9D) + RUN_FROM_FLASH = 0 + else + RUN_FROM_FLASH = 1 + endif +endif + +# PCB revision +PCBREV = + +EXTRAINCDIRS = + +# +# Define linker script file here +# +ifeq ($(RUN_FROM_FLASH), 1) + ifeq ($(REVX), 1) + LDSCRIPT = sam3s8c_boot.ld + FULL_PRJ = $(PROJECT)_flash8 + EXTRAINCDIRS += include +# EXTRAINCDIRS += ../ + else + LDSCRIPT = sam3s4c_boot.ld + FULL_PRJ = $(PROJECT)_flash4 + EXTRAINCDIRS += include +# EXTRAINCDIRS += ../ + endif + TRGT = arm-none-eabi- + CPPDEFS += -DPCBSKY + UDEFS = -Dat91sam3s8 + + # If REVX board + ifeq ($(REVX), 1) + CPPDEFS += -DREVX + endif + + CPPDEFS += -DREVB + +else + ifeq ($(PCB), TARANIS) + ARCH = ARM + LDSCRIPT = ../targets/taranis/stm32_ramBoot.ld + TRGT = arm-none-eabi- + CPPDEFS += -DHSE_VALUE=12000000 + CPPDEFS += -DPCBTARANIS + FULL_PRJ = $(PROJECT)_ramBoot + EXTRAINCDIRS += ../targets/taranis/STM32F2xx_StdPeriph_Lib_V1.1.0/Libraries/STM32F2xx_StdPeriph_Driver/inc + EXTRAINCDIRS += ../targets/taranis/STM32F2xx_StdPeriph_Lib_V1.1.0/Libraries/CMSIS/Device/ST/STM32F2xx/Include + EXTRAINCDIRS += ../targets/taranis/STM32_USB-Host-Device_Lib_V2.1.0/Libraries/STM32_USB_OTG_Driver/inc + EXTRAINCDIRS += ../targets/taranis/STM32_USB-Host-Device_Lib_V2.1.0/Libraries/STM32_USB_Device_Library/Core/inc + EXTRAINCDIRS += ../targets/taranis/STM32_USB-Host-Device_Lib_V2.1.0/Libraries/STM32_USB_Device_Library/Class/msc/inc + EXTRAINCDIRS += ../targets/taranis + EXTRAINCDIRS += ../fonts/std + + ifeq ($(PCBREV), REV3) + CPPDEFS += -DREV3 + else ifeq ($(PCBREV), REV4a) + CPPDEFS += -DREV4a + else + CPPDEFS += -DREV4 + endif + + endif +endif + + +# List all user C define here, like -D_DEBUG=1 + +# Define ASM defines here +UADEFS = + +ifeq ($(PCB), TARANIS) +SRC = ../targets/taranis/STM32F2xx_StdPeriph_Lib_V1.1.0/Libraries/CMSIS/Device/ST/STM32F2xx/Source/Templates/system_stm32f2xx.c \ + ../targets/taranis/i2c.c \ + ../targets/taranis/delays.c \ + ../targets/taranis/STM32F2xx_StdPeriph_Lib_V1.1.0/Libraries/STM32F2xx_StdPeriph_Driver/src/stm32f2xx_rcc.c \ + ../targets/taranis/STM32F2xx_StdPeriph_Lib_V1.1.0/Libraries/STM32F2xx_StdPeriph_Driver/src/stm32f2xx_gpio.c \ + ../targets/taranis/STM32F2xx_StdPeriph_Lib_V1.1.0/Libraries/STM32F2xx_StdPeriph_Driver/src/stm32f2xx_spi.c \ + ../targets/taranis/STM32F2xx_StdPeriph_Lib_V1.1.0/Libraries/STM32F2xx_StdPeriph_Driver/src/misc.c \ + ../FatFs/ff.c \ + ../FatFs/option/ccsbcs.c \ + ../targets/taranis/STM32_USB-Host-Device_Lib_V2.1.0/Libraries/STM32_USB_OTG_Driver/src/usb_core.c \ + ../targets/taranis/STM32_USB-Host-Device_Lib_V2.1.0/Libraries/STM32_USB_OTG_Driver/src/usb_dcd.c \ + ../targets/taranis/STM32_USB-Host-Device_Lib_V2.1.0/Libraries/STM32_USB_OTG_Driver/src/usb_dcd_int.c \ + ../targets/taranis/STM32_USB-Host-Device_Lib_V2.1.0/Libraries/STM32_USB_Device_Library/Core/src/usbd_core.c \ + ../targets/taranis/STM32_USB-Host-Device_Lib_V2.1.0/Libraries/STM32_USB_Device_Library/Core/src/usbd_ioreq.c \ + ../targets/taranis/STM32_USB-Host-Device_Lib_V2.1.0/Libraries/STM32_USB_Device_Library/Core/src/usbd_req.c \ + ../targets/taranis/STM32_USB-Host-Device_Lib_V2.1.0/Libraries/STM32_USB_Device_Library/Class/msc/src/usbd_msc_data.c \ + ../targets/taranis/STM32_USB-Host-Device_Lib_V2.1.0/Libraries/STM32_USB_Device_Library/Class/msc/src/usbd_msc_scsi.c \ + ../targets/taranis/STM32_USB-Host-Device_Lib_V2.1.0/Libraries/STM32_USB_Device_Library/Class/msc/src/usbd_msc_bot.c \ + ../targets/taranis/STM32_USB-Host-Device_Lib_V2.1.0/Libraries/STM32_USB_Device_Library/Class/msc/src/usbd_msc_core.c \ + ../targets/taranis/usbd_desc.c \ + ../targets/taranis/aspi.c \ + ../targets/taranis/usb_bsp.c \ + ../targets/taranis/usb_driver.c \ + ../targets/taranis/pwr_driver.c + +CPPSRC = ../targets/taranis/lcd_driver.cpp \ + ../targets/taranis/keys_driver.cpp \ + ../targets/taranis/diskio.cpp \ + ../targets/taranis/usbd_usr.cpp \ + ../targets/taranis/usbd_storage_msd.cpp \ + ../lcd.cpp \ + ../keys.cpp \ + ../fonts.cpp \ + boot.cpp + +# List ASM source files here +ASRC = ../targets/taranis/STM32F2xx_StdPeriph_Lib_V1.1.0/Libraries/CMSIS/Device/ST/STM32F2xx/Source/Templates/gcc_ride7/startup_stm32f2xx.s + +else + +# List C source files here +SRC = core_cm3.c \ + board_lowlevel.c \ + crt.c \ + usb/device/core/USBD_UDP.c usb/device/core/USBDDriver.c usb/device/core/USBDCallbacks.c \ + usb/device/massstorage/MSDDriver.c usb/device/massstorage/MSDDStateMachine.c \ + usb/device/massstorage/MSDLun.c usb/device/massstorage/MSDDriverDescriptors.c usb/device/massstorage/SBCMethods.c \ + usb/common/core/USBEndpointDescriptor.c usb/common/core/USBGenericRequest.c \ + usb/common/core/USBFeatureRequest.c usb/common/core/USBInterfaceRequest.c usb/common/core/USBGetDescriptorRequest.c \ + usb/common/core/USBSetAddressRequest.c usb/common/core/USBSetConfigurationRequest.c \ + usb/common/core/USBConfigurationDescriptor.c usb/common/core/USBGenericDescriptor.c \ + MEDSdcard.c \ + vectors_sam3s.c + +CPPSRC = lcdboot.cpp \ + ff.cpp \ + diskio.cpp \ + driversboot.cpp \ + logicioboot.cpp \ + sdcard_driver.cpp \ + massstorage.cpp \ + bootsamEeprom.cpp \ + ff_lfn.cpp \ + power.cpp \ + boot.cpp + +# List ASM source files here +ASRC = + +endif + +# List all user directories here +UINCDIR = ./inc +# \ +# ./cmsis/core \ +# ./cmsis/device + +# List the user directory to look for the libraries here +ULIBDIR = + +# List all user libraries here +ULIBS = + +# Define optimisation level here +OPT = -Os + +# +# End of user defines +############################################################################################## + + +VPATH = $(DIRS) + +INCDIR = $(patsubst %,-I%,$(DINCDIR) $(UINCDIR)) +LIBDIR = $(patsubst %,-L%,$(DLIBDIR) $(ULIBDIR)) + +ifeq ($(RUN_FROM_FLASH), 0) +DEFS = $(DDEFS) $(UDEFS) -DRUN_FROM_FLASH=0 +else +DEFS = $(DDEFS) $(UDEFS) -DRUN_FROM_FLASH=1 +endif + +ADEFS = $(DADEFS) $(UADEFS) + +AXOBJS = $(ASRC:%.s=%.o) +CXOBJS = $(SRC:%.c=%.o) +CPPXOBJS = $(CPPSRC:%.cpp=%.o) + +LIBS = $(DLIBS) $(ULIBS) +MCFLAGS = -mcpu=$(MCU) + +#ASFLAGS = $(MCFLAGS) -g -gdwarf-2 -Wa,-amhls=$(OBJDIR)/$(notdir $(<:.s=.lst)) $(ADEFS) +CPFLAGS = $(MCFLAGS) $(OPT) -gdwarf-2 -mthumb -fomit-frame-pointer -Wall -Wstrict-prototypes -fverbose-asm $(DEFS) +LDFLAGS = $(MCFLAGS) -mthumb -nostartfiles -T$(LDSCRIPT) -Wl,-Map=$(FULL_PRJ).map,--cref,--no-warn-mismatch $(LIBDIR) +CPPFLAGS = $(MCFLAGS) $(OPT) -gdwarf-2 -mthumb -fomit-frame-pointer -Wall -fverbose-asm $(DEFS) + +CPPFLAGS += $(CPPDEFS) +CPFLAGS += $(CPPDEFS) +CPFLAGS += $(patsubst %,-I%,$(EXTRAINCDIRS)) + +AOBJS = $(patsubst %,$(OBJDIR)/%,$(notdir $(AXOBJS) )) +COBJS = $(patsubst %,$(OBJDIR)/%,$(notdir $(CXOBJS) )) +CPPOBJS = $(patsubst %,$(OBJDIR)/%,$(notdir $(CPPXOBJS) )) +DIRS = $(sort $(dir $(AXOBJS) $(CXOBJS) $(CPPXOBJS) ) ) + + +CPPDEFS += -DCPUARM + +# If serial Debug required +ifeq ($(DEBUG), 1) + CPPDEFS += -DDEBUG +endif + +CPPDEFS += -DBOOT + +# Generate dependency information +CPFLAGS += -MD -MP -MF .dep/$(@F).d +CPPFLAGS += -MD -MP -MF .dep/$(@F).d +CPPFLAGS += $(patsubst %,-I%,$(EXTRAINCDIRS)) + +# +# makefile rules +# + +all: size_before $(OBJS) $(COBJS) $(CPPOBJS) $(FULL_PRJ).elf $(FULL_PRJ).hex $(FULL_PRJ).lss $(FULL_PRJ).bin size + +#begin: +# @echo $(AXOBJS) $(CXOBJS) $(CPPXOBJS) +# @echo +# @echo $(OBJS) $(COBJS) $(CPPOBJS) +# @echo +# @echo $(DIRS) + +size_before: +# arm-none-eabi-size $(FULL_PRJ).elf + @if test -f $(FULL_PRJ).elf; then arm-none-eabi-size $(FULL_PRJ).elf; fi + +size: +# arm-none-eabi-size $(FULL_PRJ).elf + @if test -f $(FULL_PRJ).elf; then arm-none-eabi-size $(FULL_PRJ).elf; fi + +$(CPPOBJS) : $(OBJDIR)/%.o : %.cpp + $(CC) -c $(CPPFLAGS) -fno-exceptions -I . $(INCDIR) $< -o $@ + +$(COBJS) : $(OBJDIR)/%.o : %.c + $(CC) -c $(CPFLAGS) -I . $(INCDIR) $< -o $@ + + +$(AOBJS) : $(OBJDIR)/%.o : %.s + $(AS) -c $(ASFLAGS) $< -o $@ + +%elf: $(AOBJS) $(COBJS) $(CPPOBJS) + $(CC) $(AOBJS) $(COBJS) $(CPPOBJS) $(LDFLAGS) $(LIBS) -o $@ + +# Create extended listing file from ELF output file. +%.lss: %.elf + $(CLSS) -h -S $< > $@ + +%hex: %elf + $(BIN) $< $@ + +%bin: %elf + $(BINX) $< $@ + +# $(PROJECT)_flash8 +# $(PROJECT)_flash4 +# $(PROJECT)_ramBootS +# $(PROJECT)_ramBootT + +clean: + -rm -f *.o + -rm -f *.elf + -rm -f *.map + -rm -f *.hex + -rm -f *.bin + -rm -f *.lss + -rm -fR .dep + + +# +# Include the dependency files, should be the last of the makefile +# +-include $(shell mkdir .dep 2>/dev/null) $(wildcard .dep/*) + +# *** EOF *** diff --git a/radio/src/bootloader/boot.cpp b/radio/src/bootloader/boot.cpp new file mode 100644 index 000000000..fe7b9daa1 --- /dev/null +++ b/radio/src/bootloader/boot.cpp @@ -0,0 +1,944 @@ +/**************************************************************************** + * Copyright (c) 2014 by Michael Blandford. All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * 3. Neither the name of the author nor the names of its contributors may + * be used to endorse or promote products derived from this software + * without specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS + * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT + * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS + * FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL + * THE COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, + * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, + * BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS + * OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED + * AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, + * OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF + * THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF + * SUCH DAMAGE. + * + **************************************************************************** + * Other Authors: + * - Andre Bernet + * - Bertrand Songis + * - Bryan J. Rentoul (Gruvin) + * - Cameron Weeks + * - Erez Raviv + * - Jean-Pierre Parisy + * - Karl Szmutny + * - Michal Hlavinka + * - Pat Mackenzie + * - Philip Moss + * - Rob Thomson + * - Romolo Manfredini + * - Thomas Husterer + * + ****************************************************************************/ + +/*---------------------------------------------------------------------------- + * Headers + *----------------------------------------------------------------------------*/ + +#include +#include +#include + +#if defined(PCBTARANIS) +#include "stm32f2xx_flash.h" +#endif + +#include "board_taranis.h" +#include "../pwr.h" +#include "../lcd.h" +#include "../keys.h" +#include "../sdcard.h" +#include "../FatFs/ff.h" +#include "../FatFs/diskio.h" +#include "../translations/en.h" + +#if defined(PCBTARANIS) + #define BOOTLOADER_TITLE "Boot Loader - FrSky Taranis" + #define BOOT_KEY_UP KEY_PLUS + #define BOOT_KEY_DOWN KEY_MINUS + #define BOOT_KEY_LEFT KEY_MENU + #define BOOT_KEY_RIGHT KEY_PAGE + #define BOOT_KEY_MENU KEY_ENTER + #define BOOT_KEY_EXIT KEY_EXIT + #define DISPLAY_CHAR_WIDTH 35 +#elif defined(PCBSKY9X) + #define BOOTLOADER_TITLE "Boot Loader - Sky9x" +#endif + +#define BOOTLOADER_SIZE 0x8000 + +#if defined(PCBTARANIS) + #define FIRMWARE_ADDRESS 0x08000000 +#elif defined(PCBSKY9X) + #define FIRMWARE_ADDRESS 0x00400000 +#endif + +// states +enum BootLoaderStates { + ST_START, + ST_FLASH_MENU, + ST_DIR_CHECK, + ST_OPEN_DIR, + ST_FILE_LIST, + ST_FLASH_CHECK, + ST_FLASHING, + ST_FLASH_DONE, + ST_USB, + ST_REBOOT, +}; + +/*---------------------------------------------------------------------------- + * Local variables + *----------------------------------------------------------------------------*/ + +uint32_t FirmwareSize; + +uint32_t Master_frequency; +volatile uint8_t Tenms; +uint8_t EE_timer; + +TCHAR FlashFilename[60]; +FIL FlashFile; +DIR Dj; +FILINFO Finfo; + +TCHAR Filenames[20][50]; +uint32_t FileSize[20]; +uint32_t FnStartIndex; +uint32_t Valid; + +uint32_t FlashSize; + +uint32_t FlashBlocked = 1; +uint32_t LockBits; + +uint32_t Block_buffer[1024]; +UINT BlockCount; + +#if defined(PCBSKY9X) + extern int32_t EblockAddress; +#endif + +extern uint32_t EepromBlocked; + +extern void init_spi(void); +extern void writeBlock(void); + +/*---------------------------------------------------------------------------- + * Global functions + *----------------------------------------------------------------------------*/ + +#if defined(PCBSKY9X) +// Starts TIMER0 at full speed (MCK/2) for delay timing +// @ 36MHz this is 18MHz +// This was 6 MHz, we may need to slow it to TIMER_CLOCK2 (MCK/8=4.5 MHz) +void start_timer0() +{ + register Tc *ptc; + + PMC->PMC_PCER0 |= 0x00800000L; // Enable peripheral clock to TC0 + + ptc = TC0;// Tc block 0 (TC0-2) + ptc->TC_BCR = 0;// No sync + ptc->TC_BMR = 2; + ptc->TC_CHANNEL[0].TC_CMR = 0x00008001;// Waveform mode MCK/8 for 36MHz osc.(Upset be write below) + ptc->TC_CHANNEL[0].TC_RC = 0xFFF0; + ptc->TC_CHANNEL[0].TC_RA = 0; + ptc->TC_CHANNEL[0].TC_CMR = 0x00008040;// 0000 0000 0000 0000 1000 0000 0100 0000, stop at regC, 18MHz + ptc->TC_CHANNEL[0].TC_CCR = 5;// Enable clock and trigger it (may only need trigger) +} + +void stop_timer0( void ) +{ + TC0->TC_CHANNEL[0].TC_CCR = TC_CCR0_CLKDIS; // Disable clock +} + +void delay2ms() +{ + TC0->TC_CHANNEL[0].TC_CCR = 5;// Enable clock and trigger it (may only need trigger) + while ( TC0->TC_CHANNEL[0].TC_CV < 36000 )// 2mS, Value depends on MCK/2 (used 18MHz) + { + // Wait + } +} +#endif + +#if defined(PCBTARANIS) +uint32_t isFirmwareStart(uint32_t *block) +{ + if ((block[0] & 0xFFFC0000) != 0x20000000) { + return 0; + } + if ((block[1] & 0xFFF00000) != 0x08000000) { + return 0; + } + if ((block[2] & 0xFFF00000) != 0x08000000) { + return 0; + } + return 1; +} +#elif defined(PCBSKY9X) +uint32_t isFirmwareStart( uint32_t *block ) +{ + if ((block[0] & 0xFFFE3000) != 0x20000000 ) { + return 0; + } + if ((block[1] & 0xFFF80000) != 0x00400000) { + return 0; + } + if ((block[2] & 0xFFF80000) != 0x00400000) { + return 0; + } + return 1; +} +#endif + +#if defined(PCBSKY9X) + +uint32_t (*IAP_Function)(uint32_t, uint32_t); + +uint32_t program( uint32_t *address, uint32_t *buffer ) // size is 256 bytes +{ + uint32_t FlashSectorNum; + uint32_t flash_cmd = 0; + uint32_t i; +// uint32_t flash_status = 0; + // uint32_t EFCIndex = 0; // 0:EEFC0, 1: EEFC1 + /* Initialize the function pointer (retrieve function address from NMI vector) */ + + if ((uint32_t) address == FIRMWARE_START+BOOTLOADER_SIZE) { + if (isFirmwareStart(buffer)) + FlashBlocked = 0; + else + FlashBlocked = 1; + } + + if (FlashBlocked) { + return 1; + } + + // Always initialise this here, setting a default doesn't seem to work + IAP_Function = (uint32_t (*)(uint32_t, uint32_t)) *(( uint32_t *)0x00800008); + FlashSectorNum = (uint32_t) address; + FlashSectorNum >>= 8;// page size is 256 bytes + FlashSectorNum &= 2047;// max page number + + /* Send data to the sector here */ + for ( i = 0; i < 64; i += 1 ) + { + *address++ = *buffer++; + } + + /* build the command to send to EEFC */ + flash_cmd = (0x5A << 24) | (FlashSectorNum << 8) | 0x03; //AT91C_MC_FCMD_EWP ; + + __disable_irq(); + /* Call the IAP function with appropriate command */ + i = IAP_Function( 0, flash_cmd ); + __enable_irq(); + return i; +} + +uint32_t readLockBits() +{ + // Always initialise this here, setting a default doesn't seem to work + IAP_Function = (uint32_t (*)(uint32_t, uint32_t)) *(( uint32_t *)0x00800008); + + uint32_t flash_cmd = (0x5A << 24) | 0x0A;//AT91C_MC_FCMD_GLB ; + __disable_irq(); + (void) IAP_Function( 0, flash_cmd ); + __enable_irq(); + return EFC->EEFC_FRR; +} + +void clearLockBits() +{ + uint32_t i; + uint32_t flash_cmd = 0; + + // Always initialise this here, setting a default doesn't seem to work + IAP_Function = (uint32_t (*)(uint32_t, uint32_t)) *(( uint32_t *)0x00800008); + for ( i = 0; i < 16; i += 1 ) + { + flash_cmd = (0x5A << 24) | ((128*i) << 8) | 0x09; //AT91C_MC_FCMD_CLB ; + __disable_irq(); + /* Call the IAP function with appropriate command */ + (void) IAP_Function( 0, flash_cmd ); + __enable_irq(); + } +} +#endif + +void interrupt10ms(void) +{ + Tenms |= 1; // 10 mS has passed + + uint8_t enuk = KEY_MENU; + uint8_t in = ~readKeys(); + + for (int i = 1; i < 7; i++) { + uint8_t value = in & (1 << i); + keys[enuk].input(value, (EnumKeys) enuk); + ++enuk; + } +} + +#if defined(PCBSKY9X) +void init10msTimer() +{ + register Tc *ptc; + register uint32_t timer; + + PMC->PMC_PCER0 |= 0x02000000L; // Enable peripheral clock to TC2 + + timer = Master_frequency / 12800;// MCK/128 and 100 Hz + + ptc = TC0;// Tc block 0 (TC0-2) + ptc->TC_BCR = 0;// No sync + ptc->TC_BMR = 0; + ptc->TC_CHANNEL[2].TC_CMR = 0x00008000;// Waveform mode + ptc->TC_CHANNEL[2].TC_RC = timer;// 10 Hz + ptc->TC_CHANNEL[2].TC_RA = timer >> 1; + ptc->TC_CHANNEL[2].TC_CMR = 0x0009C003;// 0000 0000 0000 1001 1100 0000 0000 0011 + // MCK/128, set @ RA, Clear @ RC waveform + ptc->TC_CHANNEL[2].TC_CCR = 5;// Enable clock and trigger it (may only need trigger) + + NVIC_EnableIRQ(TC2_IRQn); + TC0->TC_CHANNEL[2].TC_IER = TC_IER0_CPCS; +} + +extern "C" void TC2_IRQHandler() +{ + register uint32_t dummy; + + /* Clear status bit to acknowledge interrupt */ + dummy = TC0->TC_CHANNEL[2].TC_SR; + (void) dummy; // Discard value - prevents compiler warning + + interrupt10ms(); + +} +#endif + +#if defined(PCBTARANIS) +void init10msTimer() +{ + // Timer14 + RCC->APB1ENR |= RCC_APB1ENR_TIM14EN; // Enable clock + TIM14->ARR = 9999; // 10mS + TIM14->PSC = (PERI1_FREQUENCY * TIMER_MULT_APB1) / 1000000 - 1; // 1uS from 12MHz + TIM14->CCER = 0; + TIM14->CCMR1 = 0; + TIM14->EGR = 0; + TIM14->CR1 = 5; + TIM14->DIER |= 1; + NVIC_EnableIRQ(TIM8_TRG_COM_TIM14_IRQn); +} + +extern "C" void TIM8_TRG_COM_TIM14_IRQHandler() +{ + TIM14->SR &= ~TIM_SR_UIF; + interrupt10ms(); +} + +void init_hw_timer() +{ + // Timer13 + RCC->APB1ENR |= RCC_APB1ENR_TIM13EN; // Enable clock + TIM13->ARR = 65535; + TIM13->PSC = (PERI1_FREQUENCY * TIMER_MULT_APB1) / 10000000 - 1;// 0.1uS from 12MHz + TIM13->CCER = 0; + TIM13->CCMR1 = 0; + TIM13->EGR = 0; + TIM13->CR1 = 1; +} + +// delay in units of 0.1 uS up to 6.5535 mS +void hw_delay(uint16_t time) +{ + TIM13->CNT = 0; + TIM13->EGR = 1; // Re-start counter + while ( TIM13->CNT < time) { + // wait + } +} + +//After reset, write is not allowed in the Flash control register (FLASH_CR) to protect the +//Flash memory against possible unwanted operations due, for example, to electric +//disturbances. The following sequence is used to unlock this register: +//1. Write KEY1 = 0x45670123 in the Flash key register (FLASH_KEYR) +//2. Write KEY2 = 0xCDEF89AB in the Flash key register (FLASH_KEYR) +//Any wrong sequence will return a bus error and lock up the FLASH_CR register until the +//next reset. +//The FLASH_CR register can be locked again by software by setting the LOCK bit in the +//FLASH_CR register. +void unlockFlash() +{ + FLASH->KEYR = 0x45670123; + FLASH->KEYR = 0xCDEF89AB; +} + +void waitFlashIdle() +{ + while (FLASH->SR & FLASH_FLAG_BSY) { + wdt_reset(); + } +} + +#define SECTOR_MASK ((uint32_t)0xFFFFFF07) + +void eraseSector(uint32_t sector) +{ + waitFlashIdle(); + + FLASH->CR &= CR_PSIZE_MASK; + FLASH->CR |= FLASH_PSIZE_WORD; + FLASH->CR &= SECTOR_MASK; + FLASH->CR |= FLASH_CR_SER | (sector << 3); + FLASH->CR |= FLASH_CR_STRT; + + /* Wait for operation to be completed */ + waitFlashIdle(); + + /* if the erase operation is completed, disable the SER Bit */ + FLASH->CR &= (~FLASH_CR_SER); + FLASH->CR &= SECTOR_MASK; +} + +uint32_t program(uint32_t *address, uint32_t *buffer) // size is 256 bytes +{ + uint32_t i; + + if ((uint32_t) address == 0x08008000) { + if (isFirmwareStart(buffer)) { + FlashBlocked = 0; + } + else { + FlashBlocked = 1; + } + } + + if (FlashBlocked) { + return 1; + } + + if ((uint32_t) address == 0x08008000) { + eraseSector(2); + } + if ((uint32_t) address == 0x0800C000) { + eraseSector(3); + } + if ((uint32_t) address == 0x08010000) { + eraseSector(4); + } + if ((uint32_t) address == 0x08020000) { + eraseSector(5); + } + if ((uint32_t) address == 0x08040000) { + eraseSector(6); + } + if ((uint32_t) address == 0x08060000) { + eraseSector(7); + } + + // Now program the 256 bytes + + for (i = 0; i < 64; i += 1) { + /* Device voltage range supposed to be [2.7V to 3.6V], the operation will + be done by word */ + + // Wait for last operation to be completed + waitFlashIdle(); + + FLASH->CR &= CR_PSIZE_MASK; + FLASH->CR |= FLASH_PSIZE_WORD; + FLASH->CR |= FLASH_CR_PG; + + *address = *buffer; + + /* Wait for operation to be completed */ + waitFlashIdle(); + FLASH->CR &= (~FLASH_CR_PG); + + /* Check the written value */ + if (*address != *buffer) { + /* Flash content doesn't match SRAM content */ + return 2; + } + /* Increment FLASH destination address */ + address += 1; + buffer += 1; + } + return 0; +} + +#endif + +uint8_t *cpystr(uint8_t *dest, uint8_t *source) +{ + while ((*dest++ = *source++)) + ; + return dest - 1; +} + +FRESULT readBinDir(DIR *dj, FILINFO *fno) +{ + FRESULT fr; + uint32_t loop; + do { + loop = 0; + fr = f_readdir(dj, fno); // First entry + + if (fr != FR_OK || fno->fname[0] == 0) { + break; + } + if (*fno->lfname == 0) { + cpystr((uint8_t *) fno->lfname, (uint8_t *) fno->fname); // Copy 8.3 name + } + int32_t len = strlen(fno->lfname) - 4; + if (len < 0) { + loop = 1; + } + if (fno->lfname[len] != '.') { + loop = 1; + } + if ((fno->lfname[len + 1] != 'b') && (fno->lfname[len + 1] != 'B')) { + loop = 1; + } + if ((fno->lfname[len + 2] != 'i') && (fno->lfname[len + 2] != 'I')) { + loop = 1; + } + if ((fno->lfname[len + 3] != 'n') && (fno->lfname[len + 3] != 'N')) { + loop = 1; + } + + } while (loop); + return fr; +} + +uint32_t fillNames(uint32_t index) +{ + uint32_t i; + FRESULT fr; + Finfo.lfname = Filenames[0]; + Finfo.lfsize = 48; + fr = f_readdir(&Dj, 0); // rewind + fr = f_readdir(&Dj, &Finfo); // Skip . + fr = f_readdir(&Dj, &Finfo); // Skip .. + i = 0; + while (i <= index) { + fr = readBinDir(&Dj, &Finfo); // First entry + FileSize[0] = Finfo.fsize; + i += 1; + if (fr == FR_NO_FILE) { + return 0; + } + } + for (i = 1; i < 7; i += 1) { + Finfo.lfname = Filenames[i]; + fr = readBinDir(&Dj, &Finfo); // First entry + FileSize[i] = Finfo.fsize; + if (fr != FR_OK || Finfo.fname[0] == 0) { + break; + } + } + return i; +} + +FRESULT openFirmwareFile(uint32_t index) +{ + cpystr(cpystr((uint8_t *)FlashFilename, (uint8_t *)FIRMWARES_PATH "/"), (uint8_t *) Filenames[index]); + f_open(&FlashFile, FlashFilename, FA_READ); + f_lseek(&FlashFile, BOOTLOADER_SIZE); + return f_read(&FlashFile, (BYTE *) Block_buffer, 4096, &BlockCount); +} + +int menuFlashFile(uint32_t index, uint8_t event) +{ + FRESULT fr; + + lcd_putsLeft(2*FH, INDENT "Flash file " FIRMWARES_PATH "/"); + lcd_putsnAtt(lcdLastPos, 2*FH, Filenames[index], DISPLAY_CHAR_WIDTH, 0); + + if (Valid == 0) { + // Validate file here + // return 3 if invalid + fr = openFirmwareFile(index); + fr = f_close(&FlashFile); + Valid = 1; + if (isFirmwareStart(Block_buffer) == 0) { + Valid = 2; + } + } + + if (Valid == 2) { + lcd_putsLeft(4*FH, INDENT "Not a valid firmware!"); + if (event == EVT_KEY_FIRST(BOOT_KEY_EXIT) || event == EVT_KEY_FIRST(BOOT_KEY_MENU)) { + return 0; + } + return -1; + } + + lcd_putsLeft(6*FH, INDENT "[Enter Long] to confirm"); + + if (event == EVT_KEY_LONG(BOOT_KEY_MENU)) { + fr = openFirmwareFile(index); + FirmwareSize = FileSize[index]; + if (fr != FR_OK) { + return 0; // File open error + } + return 1; + } + else if (event == EVT_KEY_FIRST(BOOT_KEY_EXIT)) { + return 0; + } + + return -1; +} + +extern Key keys[]; + +static uint32_t PowerUpDelay; + +int main() +{ + uint8_t index = 0; +#if defined(PCBTARANIS) + uint8_t TenCount = 2; +#endif + uint8_t maxhsize = DISPLAY_CHAR_WIDTH; + FRESULT fr; + uint32_t state = ST_START; + uint32_t nameCount = 0; + uint32_t vpos = 0; + uint32_t hpos = 0; + uint32_t firmwareAddress = FIRMWARE_ADDRESS; + uint32_t firmwareWritten = 0; + +#if defined(PCBTARANIS) + wdt_reset(); + RCC->AHB1ENR |= RCC_AHB1ENR_GPIOAEN; // Enable portA clock +#endif + + pwrInit(); + +#if defined(PCBSKY9X) + MATRIX->CCFG_SYSIO |= 0x000000F0L; // Disable syspins, enable B4,5,6,7 +#endif + +#if defined(PCBSKY9X) + init_SDcard(); + PIOC->PIO_PER = PIO_PC25; // Enable bit C25 (USB-detect) + start_timer0(); +#endif + + lcdInit(); +#if defined(PCBSKY9X) + extern uint8_t OptrexDisplay; + OptrexDisplay = 1; +#endif + lcd_clear(); + lcd_putsLeft(0, BOOTLOADER_TITLE); + lcd_hline(0, 10, LCD_W); + lcdRefresh(); +#if defined(PCBSKY9X) + OptrexDisplay = 0; + lcdRefresh(); +#endif + +#if defined(PCBTARANIS) + keysInit(); + I2C_EE_Init(); + init_hw_timer(); +#endif + + __enable_irq(); + init10msTimer(); + +#if defined(PCBSKY9X) + EblockAddress = -1; + init_spi(); +#endif + +#if defined(PCBSKY9X) + uint32_t chip_id = CHIPID->CHIPID_CIDR; + FlashSize = ( (chip_id >> 8 ) & 0x000F ) == 9 ? 256 : 512; +#elif defined(PCBTARANIS) + FlashSize = 512; +#endif + +#if defined(PCBSKY9X) + LockBits = readLockBits(); + if (LockBits) { + clearLockBits(); + } +#endif + +#if defined(PCBTARANIS) + // SD card detect pin + sdInit(); + unlockFlash(); + usbInit(); + usbStart(); +#endif + + for (;;) { + wdt_reset(); + + if (Tenms) { + wdt_reset(); // Retrigger hardware watchdog + + if (EE_timer) { + if (--EE_timer == 0) { +#if defined(PCBSKY9X) + writeBlock(); +#endif + } + } + + Tenms = 0; + + lcd_clear(); + lcd_putsLeft(0, BOOTLOADER_TITLE); + lcd_hline(0, 10, LCD_W); + + uint8_t event = getEvent(); + + if (usbPlugged()) { + state = ST_USB; + } + + if (state == ST_START) { + lcd_putsLeft(2*FH, "\004Flash a firmware from the SD card"); + lcd_putsLeft(3*FH, "\004Exit"); + lcd_invert_line(2+vpos); + lcd_putsLeft(6*FH, INDENT "Or plug a USB cable for Massstorage"); + if (event == EVT_KEY_FIRST(BOOT_KEY_DOWN) || event == EVT_KEY_FIRST(BOOT_KEY_UP)) { + vpos = (vpos+1) & 0x01; + } + else if (event == EVT_KEY_FIRST(BOOT_KEY_MENU)) { + if (vpos == 0) + state = ST_FLASH_MENU; + else + state = ST_REBOOT; + } + } + + if (state == ST_USB) { + lcd_putsLeft(4*FH, CENTER "\010U S B"); + if (usbPlugged() == 0) { + vpos = 0; + state = ST_START; + } +#if defined(PCBSKY9X) + usbMassStorage(); + lcd_putc( 0, 6*FH, 'F' ); + lcd_putc( 6, 6*FH, '0' + FlashBlocked ); + lcd_putc( 0, 7*FH, 'E' ); + lcd_putc( 6, 7*FH, '0' + EepromBlocked ); +#endif + } + + if (state == ST_FLASH_MENU) { + sdInit(); + state = ST_DIR_CHECK; + } + + else if (state == ST_DIR_CHECK) { + fr = f_chdir(FIRMWARES_PATH); + if (fr == FR_OK) { + state = ST_OPEN_DIR; + } + else { + lcd_putsLeft(2*FH, INDENT "No firmware in " FIRMWARES_PATH " directory"); + if (event == EVT_KEY_FIRST(BOOT_KEY_EXIT) || event == EVT_KEY_FIRST(BOOT_KEY_MENU)) { + vpos = 0; + state = ST_START; + } + } + } + + if (state == ST_OPEN_DIR) { + index = 0; + fr = f_opendir(&Dj, "."); + if (fr == FR_OK) { + state = ST_FILE_LIST; + nameCount = fillNames(0); + hpos = 0; + vpos = 0; + } + } + + if (state == ST_FILE_LIST) { + uint32_t limit = 6; + if (nameCount < limit) { + limit = nameCount; + } + maxhsize = 0; + for (uint32_t i=0; i maxhsize) { + maxhsize = x; + } + if (x > DISPLAY_CHAR_WIDTH) { + if (hpos + DISPLAY_CHAR_WIDTH > x) { + x = x - DISPLAY_CHAR_WIDTH; + } + else { + x = hpos; + } + } + else { + x = 0; + } + lcd_putsnAtt(INDENT_WIDTH, 16 + FH * i, &Filenames[i][x], DISPLAY_CHAR_WIDTH, 0); + } + + if (event == EVT_KEY_REPT(BOOT_KEY_DOWN) || event == EVT_KEY_FIRST(BOOT_KEY_DOWN)) { + if (vpos < limit - 1) { + vpos += 1; + } + else { + if (nameCount > limit) { + index += 1; + nameCount = fillNames(index); + } + } + } + else if (event == EVT_KEY_REPT(BOOT_KEY_UP) || event == EVT_KEY_FIRST(BOOT_KEY_UP)) { + if (vpos > 0) { + vpos -= 1; + } + else { + if (index) { + index -= 1; + nameCount = fillNames(index); + } + } + } +#if !defined(PCBTARANIS) + else if (event == EVT_KEY_REPT(BOOT_KEY_RIGHT) || event == EVT_KEY_FIRST(BOOT_KEY_RIGHT)) { + if (hpos + DISPLAY_CHAR_WIDTH < maxhsize) { + hpos += 1; + } + } + else if (event == EVT_KEY_REPT(BOOT_KEY_LEFT) || event == EVT_KEY_FIRST(BOOT_KEY_LEFT)) { + if (hpos) { + hpos -= 1; + } + } +#endif + else if (event == EVT_KEY_FIRST(BOOT_KEY_MENU)) { + // Select file to flash + state = ST_FLASH_CHECK; + Valid = 0; + } + else if (event == EVT_KEY_FIRST(BOOT_KEY_EXIT)) { + state = ST_START; + vpos = 0; + } + + lcd_invert_line(2 + vpos); + } + + else if (state == ST_FLASH_CHECK) { + int result = menuFlashFile(vpos, event); + FirmwareSize = FileSize[vpos] - BOOTLOADER_SIZE; + if (result == 0) { + // canceled + state = ST_FILE_LIST; + } + else if (result == 1) { + // confirmed + firmwareAddress = FIRMWARE_ADDRESS + BOOTLOADER_SIZE; + firmwareWritten = 0; + state = ST_FLASHING; + } + } + + if (state == ST_FLASHING) { + // Commit to flashing + uint32_t blockOffset = 0; + lcd_putsLeft(2*FH, INDENT "Flashing..."); + while (BlockCount) { + program((uint32_t *) firmwareAddress, &Block_buffer[blockOffset]); // size is 256 bytes + blockOffset += 64; // 32-bit words (256 bytes) + firmwareAddress += 256; + if (BlockCount > 256) { + BlockCount -= 256; + } + else { + BlockCount = 0; + } + } + firmwareWritten += 4; // 4K blocks + + lcd_rect(INDENT_WIDTH, 6*FH+4, 202, 3); + lcd_hline(INDENT_WIDTH, 6*FH+5, (200*firmwareWritten/(FlashSize-32)), FORCE); + + fr = f_read(&FlashFile, (BYTE *)Block_buffer, sizeof(Block_buffer), &BlockCount); + if (BlockCount == 0) { + state = ST_FLASH_DONE; + } + if (firmwareWritten >= FlashSize - 32) { + state = ST_FLASH_DONE; // Backstop + } + } + + if (state == ST_FLASH_DONE) { + lcd_putsLeft(2*FH, INDENT "Flashing Complete"); + if (event == EVT_KEY_FIRST(BOOT_KEY_EXIT) || event == EVT_KEY_FIRST(BOOT_KEY_MENU)) { + state = ST_START; + vpos = 0; + } + } + + if (event == EVT_KEY_LONG(BOOT_KEY_EXIT)) { + state = ST_REBOOT; + } + + if (--TenCount == 0) { + TenCount = 2; + lcdRefresh(); + } + + if (PowerUpDelay < 20) { // 200 mS + PowerUpDelay += 1; + } + else { + sdPoll10ms(); + } + } + + if (pwrCheck() == e_power_off && state != ST_FLASHING && state != ST_USB) { + pwrOff(); + for (;;) { + // Wait for power to go off + } + } + + if (state == ST_REBOOT) { + if ((~readKeys() & 0x7E) == 0) { + NVIC_SystemReset(); + } + } + } + + return 0; +} + diff --git a/radio/src/eeprom_rlc.h b/radio/src/eeprom_rlc.h index db285a6fe..76bf5cdff 100644 --- a/radio/src/eeprom_rlc.h +++ b/radio/src/eeprom_rlc.h @@ -34,11 +34,16 @@ * */ -#ifndef eeprom_avr_h -#define eeprom_avr_h +#ifndef eeprom_rlc_h +#define eeprom_rlc_h #include +// TODO duplicated +#ifndef PACK +#define PACK( __Declaration__ ) __Declaration__ __attribute__((__packed__)) +#endif + #if defined(PCBTARANIS) #define blkid_t uint16_t #if !defined(EESIZE) @@ -67,7 +72,7 @@ #define BS 16 #endif -PACK(struct DirEnt{ +PACK(struct DirEnt { blkid_t startBlk; uint16_t size:12; uint16_t typ:4; @@ -79,7 +84,7 @@ PACK(struct DirEnt{ #define EEFS_EXTRA_FIELDS #endif -PACK(struct EeFs{ +PACK(struct EeFs { uint8_t version; blkid_t mySize; blkid_t freeList; diff --git a/radio/src/fonts.cpp b/radio/src/fonts.cpp new file mode 100755 index 000000000..5c1ec8bc4 --- /dev/null +++ b/radio/src/fonts.cpp @@ -0,0 +1,163 @@ +/* + * Authors (alphabetical order) + * - Andre Bernet + * - Andreas Weitl + * - Bertrand Songis + * - Bryan J. Rentoul (Gruvin) + * - Cameron Weeks + * - Erez Raviv + * - Gabriel Birkus + * - Jean-Pierre Parisy + * - Karl Szmutny + * - Michael Blandford + * - Michal Hlavinka + * - Pat Mackenzie + * - Philip Moss + * - Rob Thomson + * - Romolo Manfredini + * - Thomas Husterer + * + * opentx is based on code named + * gruvin9x by Bryan J. Rentoul: http://code.google.com/p/gruvin9x/, + * er9x by Erez Raviv: http://code.google.com/p/er9x/, + * and the original (and ongoing) project by + * Thomas Husterer, th9x: http://code.google.com/p/th9x/ + * + * This program is free software; you can redistribute it and/or modify + * it under the terms of the GNU General Public License version 2 as + * published by the Free Software Foundation. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + */ + +#include "opentx.h" + +const pm_uchar font_5x7[] PROGMEM = { +#if defined (CPUARM) +#include "font_05x07.lbm" +#else +#include "font_05x07_avr.lbm" +#endif +#if defined(TRANSLATIONS_DE) +#include "font_de_05x07.lbm" +#elif defined(TRANSLATIONS_CZ) +#include "font_cz_05x07.lbm" +#elif defined(TRANSLATIONS_ES) +#include "font_es_05x07.lbm" +#elif defined(TRANSLATIONS_FI) +#include "font_fi_05x07.lbm" +#elif defined(TRANSLATIONS_FR) +#include "font_fr_05x07.lbm" +#elif defined(TRANSLATIONS_IT) +#include "font_it_05x07.lbm" +#elif defined(TRANSLATIONS_PL) +#include "font_pl_05x07.lbm" +#elif defined(TRANSLATIONS_PT) +#include "font_pt_05x07.lbm" +#elif defined(TRANSLATIONS_SE) +#include "font_se_05x07.lbm" +#endif +}; + +#if defined(BOLD_FONT) && (!defined(CPUM64) || defined(EXTSTD)) +const pm_uchar font_5x7_B[] PROGMEM = { +#include "font_05x07_B_compressed.lbm" +}; +#endif + +#if !defined(BOOT) +const pm_uchar font_10x14[] PROGMEM = { +#include "font_10x14_compressed.lbm" +#if defined(CPUARM) + #if defined(TRANSLATIONS_DE) + #include "font_de_10x14.lbm" + #elif defined(TRANSLATIONS_CZ) + #include "font_cz_10x14.lbm" + #elif defined(TRANSLATIONS_ES) + #include "font_es_10x14.lbm" + #elif defined(TRANSLATIONS_FI) + #include "font_fi_10x14.lbm" + #elif defined(TRANSLATIONS_FR) + #include "font_fr_10x14.lbm" + #elif defined(TRANSLATIONS_IT) + #include "font_it_10x14.lbm" + #elif defined(TRANSLATIONS_PL) + #include "font_pl_10x14.lbm" + #elif defined(TRANSLATIONS_PT) + #include "font_pt_10x14.lbm" + #elif defined(TRANSLATIONS_SE) + #include "font_se_10x14.lbm" + #endif +#endif +}; +#endif + +#if defined(CPUARM) && !defined(BOOT) +const pm_uchar font_3x5[] PROGMEM = { +#include "font_03x05.lbm" +}; + +const pm_uchar font_4x6[] PROGMEM = { +#include "font_04x06.lbm" +#if defined(TRANSLATIONS_DE) +#include "font_de_04x06.lbm" +#elif defined(TRANSLATIONS_CZ) +#include "font_cz_04x06.lbm" +#elif defined(TRANSLATIONS_ES) +#include "font_es_04x06.lbm" +#elif defined(TRANSLATIONS_FI) +#include "font_fi_04x06.lbm" +#elif defined(TRANSLATIONS_FR) +#include "font_fr_04x06.lbm" +#elif defined(TRANSLATIONS_IT) +#include "font_it_04x06.lbm" +#elif defined(TRANSLATIONS_PL) +#include "font_pl_04x06.lbm" +#elif defined(TRANSLATIONS_PT) +#include "font_pt_04x06.lbm" +#elif defined(TRANSLATIONS_SE) +#include "font_se_04x06.lbm" +#endif +}; + +const pm_uchar font_8x10[] PROGMEM = { +#include "font_08x10.lbm" +#if defined(TRANSLATIONS_DE) +#include "font_de_08x10.lbm" +#elif defined(TRANSLATIONS_CZ) +#include "font_cz_08x10.lbm" +#elif defined(TRANSLATIONS_ES) +#include "font_es_08x10.lbm" +#elif defined(TRANSLATIONS_FI) +#include "font_fi_08x10.lbm" +#elif defined(TRANSLATIONS_FR) +#include "font_fr_08x10.lbm" +#elif defined(TRANSLATIONS_IT) +#include "font_it_08x10.lbm" +#elif defined(TRANSLATIONS_PL) +#include "font_pl_08x10.lbm" +#elif defined(TRANSLATIONS_PT) +#include "font_pt_08x10.lbm" +#elif defined(TRANSLATIONS_SE) +#include "font_se_08x10.lbm" +#endif +}; + +const pm_uchar font_4x6_extra[] PROGMEM = { +#include "font_04x06_extra.lbm" +}; + +const pm_uchar font_5x7_extra[] PROGMEM = { +#include "font_05x07_extra.lbm" +}; + +const pm_uchar font_10x14_extra[] PROGMEM = { +#include "font_10x14_extra.lbm" +}; + +#endif + diff --git a/radio/src/fonts.h b/radio/src/fonts.h new file mode 100755 index 000000000..f254800dc --- /dev/null +++ b/radio/src/fonts.h @@ -0,0 +1,57 @@ +/* + * Authors (alphabetical order) + * - Andre Bernet + * - Andreas Weitl + * - Bertrand Songis + * - Bryan J. Rentoul (Gruvin) + * - Cameron Weeks + * - Erez Raviv + * - Gabriel Birkus + * - Jean-Pierre Parisy + * - Karl Szmutny + * - Michael Blandford + * - Michal Hlavinka + * - Pat Mackenzie + * - Philip Moss + * - Rob Thomson + * - Romolo Manfredini + * - Thomas Husterer + * + * opentx is based on code named + * gruvin9x by Bryan J. Rentoul: http://code.google.com/p/gruvin9x/, + * er9x by Erez Raviv: http://code.google.com/p/er9x/, + * and the original (and ongoing) project by + * Thomas Husterer, th9x: http://code.google.com/p/th9x/ + * + * This program is free software; you can redistribute it and/or modify + * it under the terms of the GNU General Public License version 2 as + * published by the Free Software Foundation. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + */ + +#ifndef fonts_h +#define fonts_h + +extern const pm_uchar font_5x7[]; +extern const pm_uchar font_10x14[]; + +#if defined(BOLD_FONT) && (!defined(CPUM64) || defined(EXTSTD)) && !defined(BOOT) + #define BOLD_SPECIFIC_FONT + extern const pm_uchar font_5x7_B[]; +#endif + +#if defined(CPUARM) +extern const pm_uchar font_3x5[]; +extern const pm_uchar font_4x6[]; +extern const pm_uchar font_8x10[]; +extern const pm_uchar font_5x7_extra[]; +extern const pm_uchar font_10x14_extra[]; +extern const pm_uchar font_4x6_extra[]; +#endif + +#endif diff --git a/radio/src/gtests.cpp b/radio/src/gtests.cpp index dbb8df463..22e53b688 100644 --- a/radio/src/gtests.cpp +++ b/radio/src/gtests.cpp @@ -42,7 +42,10 @@ void doMixerCalculations(); -#define MODEL_RESET() memset(&g_model, 0, sizeof(g_model)) +#define MODEL_RESET() \ + memset(&g_model, 0, sizeof(g_model)); \ + extern bool s_mixer_first_run_done; \ + s_mixer_first_run_done = false; #define MIXER_RESET() \ memset(channelOutputs, 0, sizeof(channelOutputs)); \ @@ -62,6 +65,7 @@ uint16_t anaIn(uint8_t chan) return 0; } +#if !defined(PCBTARANIS) TEST(Trims, greaterTrimLink) { MODEL_RESET(); @@ -88,6 +92,7 @@ TEST(Trims, infiniteChainedTrims) setTrimValue(3, 0, TRIM_EXTENDED_MAX+3); // link to FP2 trim EXPECT_EQ(getRawTrimValue(getTrimFlightPhase(0, 2), 0), 32); } +#endif TEST(outdezNAtt, test_unsigned) { @@ -565,16 +570,18 @@ TEST(Mixer, SlowOnSwitch) g_model.mixData[0].srcRaw = MIXSRC_MAX; g_model.mixData[0].weight = 100; g_model.mixData[0].swtch = SWSRC_THR; - g_model.mixData[0].speedUp = 10; - g_model.mixData[0].speedDown = 10; + g_model.mixData[0].speedUp = SLOW_STEP*5; + g_model.mixData[0].speedDown = SLOW_STEP*5; + s_mixer_first_run_done = true; + perOut(e_perout_mode_normal, 0); EXPECT_EQ(chans[0], 0); simuSetSwitch(0, 1); CHECK_SLOW_MOVEMENT(0, +1, 250); - simuSetSwitch(0, 0); + simuSetSwitch(0, -1); CHECK_SLOW_MOVEMENT(0, -1, 250); } @@ -587,11 +594,12 @@ TEST(Mixer, SlowUpOnSwitch) g_model.mixData[0].srcRaw = MIXSRC_MAX; g_model.mixData[0].weight = 100; g_model.mixData[0].swtch = SWSRC_THR; - g_model.mixData[0].speedUp = 10; + g_model.mixData[0].speedUp = SLOW_STEP*5; g_model.mixData[0].speedDown = 0; simuSetSwitch(0, 0); perOut(e_perout_mode_normal, 0); + s_mixer_first_run_done = true; EXPECT_EQ(chans[0], 0); simuSetSwitch(0, 1); @@ -605,20 +613,22 @@ TEST(Mixer, SlowUpOnSwitch) simuSetSwitch(0, 1); CHECK_SLOW_MOVEMENT(0, +1, 100); } +#endif TEST(Mixer, SlowOnPhase) { MODEL_RESET(); MIXER_RESET(); - g_model.phaseData[1].swtch = SWSRC_THR; + g_model.phaseData[1].swtch = TR(SWSRC_THR, SWSRC_SA0); g_model.mixData[0].destCh = 0; g_model.mixData[0].mltpx = MLTPX_ADD; g_model.mixData[0].srcRaw = MIXSRC_MAX; g_model.mixData[0].weight = 100; g_model.mixData[0].phases = 0x2 + 0x4 + 0x8 + 0x10 /*only enabled in phase 0*/; - g_model.mixData[0].speedUp = 10; - g_model.mixData[0].speedDown = 10; + g_model.mixData[0].speedUp = SLOW_STEP*5; + g_model.mixData[0].speedDown = SLOW_STEP*5; + s_mixer_first_run_done = true; s_perout_flight_phase = 0; perOut(e_perout_mode_normal, 0); EXPECT_EQ(chans[0], 0); @@ -629,20 +639,26 @@ TEST(Mixer, SlowOnPhase) CHECK_SLOW_MOVEMENT(0, -1, 250); } +#if !defined(CPUARM) TEST(Mixer, SlowOnSwitchAndPhase) { MODEL_RESET(); MIXER_RESET(); - g_model.phaseData[1].swtch = SWSRC_THR; + g_model.phaseData[1].swtch = TR(SWSRC_THR, SWSRC_SA0); g_model.mixData[0].destCh = 0; g_model.mixData[0].mltpx = MLTPX_ADD; g_model.mixData[0].srcRaw = MIXSRC_MAX; g_model.mixData[0].weight = 100; - g_model.mixData[0].swtch = SWSRC_THR; + g_model.mixData[0].swtch = TR(SWSRC_THR, SWSRC_SA0); +#if defined(CPUARM) + g_model.mixData[0].phases = 0x2 + 0x4 + 0x8 + 0x10 + 0x20 + 0x40 + 0x80 + 0x100 /*only enabled in phase 0*/; +#else g_model.mixData[0].phases = 0x2 + 0x4 + 0x8 + 0x10 /*only enabled in phase 0*/; - g_model.mixData[0].speedUp = 10; - g_model.mixData[0].speedDown = 10; +#endif + g_model.mixData[0].speedUp = SLOW_STEP*5; + g_model.mixData[0].speedDown = SLOW_STEP*5; + s_mixer_first_run_done = true; perOut(e_perout_mode_normal, 0); EXPECT_EQ(chans[0], 0); @@ -650,25 +666,26 @@ TEST(Mixer, SlowOnSwitchAndPhase) s_perout_flight_phase = 0; CHECK_SLOW_MOVEMENT(0, +1, 250); - simuSetSwitch(0, 0); + simuSetSwitch(0, -1); s_perout_flight_phase = 1; CHECK_SLOW_MOVEMENT(0, -1, 250); } #endif -#if !defined(PCBTARANIS) TEST(Mixer, SlowOnSwitchSource) { MODEL_RESET(); MIXER_RESET(); g_model.mixData[0].destCh = 0; g_model.mixData[0].mltpx = MLTPX_ADD; - g_model.mixData[0].srcRaw = MIXSRC_THR; + g_model.mixData[0].srcRaw = TR(MIXSRC_THR, MIXSRC_SA); g_model.mixData[0].weight = 100; - g_model.mixData[0].speedUp = 10; - g_model.mixData[0].speedDown = 10; + g_model.mixData[0].speedUp = SLOW_STEP*5; + g_model.mixData[0].speedDown = SLOW_STEP*5; - simuSetSwitch(0, 0); + s_mixer_first_run_done = true; + + simuSetSwitch(0, -1); CHECK_SLOW_MOVEMENT(0, -1, 250); EXPECT_EQ(chans[0], -CHANNEL_MAX); @@ -676,6 +693,22 @@ TEST(Mixer, SlowOnSwitchSource) CHECK_SLOW_MOVEMENT(0, +1, 500); } +TEST(Mixer, SlowDisabledOnStartup) +{ + MODEL_RESET(); + MIXER_RESET(); + g_model.mixData[0].destCh = 0; + g_model.mixData[0].mltpx = MLTPX_ADD; + g_model.mixData[0].srcRaw = MIXSRC_MAX; + g_model.mixData[0].weight = 100; + g_model.mixData[0].speedUp = SLOW_STEP*5; + g_model.mixData[0].speedDown = SLOW_STEP*5; + + perOut(e_perout_mode_normal, 0); + EXPECT_EQ(chans[0], CHANNEL_MAX); +} + +#if !defined(PCBTARANIS) TEST(Mixer, SlowAndDelayOnReplace3POSSource) { MODEL_RESET(); @@ -685,9 +718,11 @@ TEST(Mixer, SlowAndDelayOnReplace3POSSource) g_model.mixData[0].srcRaw = MIXSRC_3POS; g_model.mixData[0].weight = 100; g_model.mixData[0].delayUp = 10; - g_model.mixData[0].speedUp = 10; - g_model.mixData[0].speedDown = 10; + g_model.mixData[0].speedUp = SLOW_STEP*5; + g_model.mixData[0].speedDown = SLOW_STEP*5; + s_mixer_first_run_done = true; + simuSetSwitch(3, -1); CHECK_SLOW_MOVEMENT(0, -1, 250); EXPECT_EQ(chans[0], -CHANNEL_MAX); @@ -717,7 +752,7 @@ TEST(Mixer, SlowOnSwitchReplace) g_model.mixData[1].srcRaw = MIXSRC_MAX; g_model.mixData[1].weight = 100; g_model.mixData[1].swtch = SWSRC_THR; - g_model.mixData[1].speedDown = 10; + g_model.mixData[1].speedDown = SLOW_STEP*5; simuSetSwitch(0, 0); perOut(e_perout_mode_normal, 1); @@ -745,16 +780,19 @@ TEST(Mixer, NoTrimOnInactiveMix) g_model.mixData[0].srcRaw = MIXSRC_Thr; g_model.mixData[0].weight = 100; g_model.mixData[0].swtch = SWSRC_THR; - g_model.mixData[0].speedUp = 10; - g_model.mixData[0].speedDown = 10; + g_model.mixData[0].speedUp = SLOW_STEP*5; + g_model.mixData[0].speedDown = SLOW_STEP*5; setTrimValue(0, 2, 256); + s_mixer_first_run_done = true; + simuSetSwitch(0, 1); CHECK_SLOW_MOVEMENT(0, 1, 100); - simuSetSwitch(0, 0); + simuSetSwitch(0, -1); CHECK_SLOW_MOVEMENT(0, -1, 100); } +#endif TEST(Mixer, SlowOnMultiply) { @@ -768,20 +806,21 @@ TEST(Mixer, SlowOnMultiply) g_model.mixData[1].mltpx = MLTPX_MUL; g_model.mixData[1].srcRaw = MIXSRC_MAX; g_model.mixData[1].weight = 100; - g_model.mixData[1].swtch = SWSRC_THR; - g_model.mixData[1].speedUp = 10; - g_model.mixData[1].speedDown = 10; + g_model.mixData[1].swtch = TR(SWSRC_THR, SWSRC_SA0); + g_model.mixData[1].speedUp = SLOW_STEP*5; + g_model.mixData[1].speedDown = SLOW_STEP*5; + + s_mixer_first_run_done = true; simuSetSwitch(0, 1); CHECK_SLOW_MOVEMENT(0, 1, 250); - simuSetSwitch(0, 0); + simuSetSwitch(0, -1); CHECK_NO_MOVEMENT(0, CHANNEL_MAX, 250); simuSetSwitch(0, 1); CHECK_NO_MOVEMENT(0, CHANNEL_MAX, 250); } -#endif TEST(Curves, LinearIntpol) { diff --git a/radio/src/gui/menu_general.cpp b/radio/src/gui/menu_general.cpp index 5f2ade988..f83806fec 100644 --- a/radio/src/gui/menu_general.cpp +++ b/radio/src/gui/menu_general.cpp @@ -432,12 +432,8 @@ void menuGeneralSetup(uint8_t event) case ITEM_SETUP_CONTRAST: lcd_putsLeft(y, STR_CONTRAST); lcd_outdezAtt(RADIO_SETUP_2ND_COLUMN, y, g_eeGeneral.contrast, attr|LEFT); - if(attr) { -#if defined(PCBTARANIS) - CHECK_INCDEC_GENVAR(event, g_eeGeneral.contrast, 0, 45); -#else - CHECK_INCDEC_GENVAR(event, g_eeGeneral.contrast, 10, 45); -#endif + if (attr) { + CHECK_INCDEC_GENVAR(event, g_eeGeneral.contrast, CONTRAST_MIN, CONTRAST_MAX); lcdSetContrast(); } break; @@ -601,24 +597,16 @@ void menuGeneralSetup(uint8_t event) #endif #if defined(MAVLINK) - case ITEM_MAVLINK_BAUD: - g_eeGeneral.mavbaud = selectMenuItem(RADIO_SETUP_2ND_COLUMN, //Y - y, // Y - STR_MAVLINK_BAUD_LABEL, // pm_char *label - STR_MAVLINK_BAUDS, // pm_char *values -// PSTR("4800""9600""14400""19200""38400""57600""76800""115200"), - g_eeGeneral.mavbaud, // value - 0, // min - 7, // max - attr, // attr - event); // event - break; + case ITEM_MAVLINK_BAUD: + g_eeGeneral.mavbaud = selectMenuItem(RADIO_SETUP_2ND_COLUMN, y, STR_MAVLINK_BAUD_LABEL, STR_MAVLINK_BAUDS, PSTR("4800""9600""14400""19200""38400""57600""76800""115200"), g_eeGeneral.mavbaud, 0, 7, attr, event); + break; #endif case ITEM_SETUP_RX_CHANNEL_ORD: lcd_putsLeft(y, STR_RXCHANNELORD); // RAET->AETR - for (uint8_t i=1; i<=4; i++) + for (uint8_t i=1; i<=4; i++) { putsChnLetter(RADIO_SETUP_2ND_COLUMN - FW + i*FW, y, channel_order(i), attr); + } if (attr) CHECK_INCDEC_GENVAR(event, g_eeGeneral.templateSetup, 0, 23); break; @@ -629,7 +617,9 @@ void menuGeneralSetup(uint8_t event) case ITEM_SETUP_STICK_MODE: lcd_putcAtt(2*FW, y, '1'+g_eeGeneral.stickMode, attr); - for (uint8_t i=0; i<4; i++) putsMixerSource((6+4*i)*FW, y, MIXSRC_Rud + pgm_read_byte(modn12x3 + 4*g_eeGeneral.stickMode + i), 0); + for (uint8_t i=0; i<4; i++) { + putsMixerSource((6+4*i)*FW, y, MIXSRC_Rud + pgm_read_byte(modn12x3 + 4*g_eeGeneral.stickMode + i), 0); + } if (attr && s_editMode>0) { CHECK_INCDEC_GENVAR(event, g_eeGeneral.stickMode, 0, 3); } diff --git a/radio/src/gui/menu_model.cpp b/radio/src/gui/menu_model.cpp index bea52b0ce..61cba0a89 100644 --- a/radio/src/gui/menu_model.cpp +++ b/radio/src/gui/menu_model.cpp @@ -870,13 +870,13 @@ enum menuModelSetupItems { ITEM_MODEL_EXTENDED_LIMITS, ITEM_MODEL_EXTENDED_TRIMS, ITEM_MODEL_TRIM_INC, + CASE_PCBTARANIS(ITEM_MODEL_THROTTLE_LABEL) ITEM_MODEL_THROTTLE_REVERSED, ITEM_MODEL_THROTTLE_TRACE, ITEM_MODEL_THROTTLE_TRIM, + CASE_PCBTARANIS(ITEM_MODEL_PREFLIGHT_LABEL) + CASE_PCBTARANIS(ITEM_MODEL_CHECKLIST_DISPLAY) ITEM_MODEL_THROTTLE_WARNING, -#if defined(PCBTARANIS) - ITEM_MODEL_CHECKLIST_DISPLAY, -#endif ITEM_MODEL_SWITCHES_WARNING, CASE_PCBTARANIS(ITEM_MODEL_POT_WARNING) ITEM_MODEL_BEEP_CENTER, @@ -964,7 +964,7 @@ void menuModelSetup(uint8_t event) #define POT_WARN_ITEMS() ((g_model.nPotsToWarn >> 6) ? (uint8_t)NUM_POTS : (uint8_t)0) bool CURSOR_ON_CELL = (m_posHorz >= 0); - MENU_TAB({ 0, 0, CASE_PCBTARANIS(0) 2, IF_PERSISTENT_TIMERS(0) 0, 0, 2, IF_PERSISTENT_TIMERS(0) 0, 0, 0, 1, 0, 0, 0, 0, 0, CASE_PCBTARANIS(0) 7, POT_WARN_ITEMS(), NAVIGATION_LINE_BY_LINE|(NUM_STICKS+NUM_POTS+NUM_ROTARY_ENCODERS-1), LABEL(InternalModule), 0, IF_PORT1_ON(1), IF_PORT1_ON(IS_D8_RX(0) ? (uint8_t)1 : (uint8_t)2), IF_PORT1_ON(FAILSAFE_ROWS(0)), LABEL(ExternalModule), (g_model.externalModule==MODULE_TYPE_XJT || IS_MODULE_DSM2(EXTERNAL_MODULE)) ? (uint8_t)1 : (uint8_t)0, PORT2_CHANNELS_ROWS(), (IS_MODULE_XJT(1) && IS_D8_RX(1)) ? (uint8_t)1 : (IS_MODULE_PPM(1) || IS_MODULE_XJT(1) || IS_MODULE_DSM2(1)) ? (uint8_t)2 : HIDDEN_ROW, IF_PORT2_XJT(FAILSAFE_ROWS(1)), LABEL(Trainer), 0, TRAINER_CHANNELS_ROWS(), IF_TRAINER_ON(2)}); + MENU_TAB({ 0, 0, CASE_PCBTARANIS(0) 2, IF_PERSISTENT_TIMERS(0) 0, 0, 2, IF_PERSISTENT_TIMERS(0) 0, 0, 0, 1, 0,CASE_PCBTARANIS(LABEL(Throttle)) 0, 0, 0,CASE_PCBTARANIS(LABEL(PreflightCheck)) CASE_PCBTARANIS(0) 0, 7, POT_WARN_ITEMS(), NAVIGATION_LINE_BY_LINE|(NUM_STICKS+NUM_POTS+NUM_ROTARY_ENCODERS-1), LABEL(InternalModule), 0, IF_PORT1_ON(1), IF_PORT1_ON(IS_D8_RX(0) ? (uint8_t)1 : (uint8_t)2), IF_PORT1_ON(FAILSAFE_ROWS(0)), LABEL(ExternalModule), (g_model.externalModule==MODULE_TYPE_XJT || IS_MODULE_DSM2(EXTERNAL_MODULE)) ? (uint8_t)1 : (uint8_t)0, PORT2_CHANNELS_ROWS(), (IS_MODULE_XJT(1) && IS_D8_RX(1)) ? (uint8_t)1 : (IS_MODULE_PPM(1) || IS_MODULE_XJT(1) || IS_MODULE_DSM2(1)) ? (uint8_t)2 : HIDDEN_ROW, IF_PORT2_XJT(FAILSAFE_ROWS(1)), LABEL(Trainer), 0, TRAINER_CHANNELS_ROWS(), IF_TRAINER_ON(2)}); #elif defined(CPUM64) #define CURSOR_ON_CELL (true) #define MODEL_SETUP_MAX_LINES ((IS_PPM_PROTOCOL(protocol)||IS_DSM2_PROTOCOL(protocol)||IS_PXX_PROTOCOL(protocol)) ? 1+ITEM_MODEL_SETUP_MAX : ITEM_MODEL_SETUP_MAX) @@ -1121,6 +1121,12 @@ void menuModelSetup(uint8_t event) g_model.trimInc = selectMenuItem(MODEL_SETUP_2ND_COLUMN, y, STR_TRIMINC, STR_VTRIMINC, g_model.trimInc, -2, 2, attr, event); break; +#if defined(PCBTARANIS) + case ITEM_MODEL_THROTTLE_LABEL: + lcd_putsLeft(y, STR_THROTTLE_LABEL); + break; +#endif + case ITEM_MODEL_THROTTLE_REVERSED: g_model.throttleReversed = onoffMenuItem(g_model.throttleReversed, MODEL_SETUP_2ND_COLUMN, y, STR_THROTTLEREVERSE, attr, event ) ; break; @@ -1142,16 +1148,20 @@ void menuModelSetup(uint8_t event) g_model.thrTrim = onoffMenuItem(g_model.thrTrim, MODEL_SETUP_2ND_COLUMN, y, STR_TTRIM, attr, event); break; - case ITEM_MODEL_THROTTLE_WARNING: - g_model.disableThrottleWarning = !onoffMenuItem(!g_model.disableThrottleWarning, MODEL_SETUP_2ND_COLUMN, y, STR_THROTTLEWARNING, attr, event); - break; - #if defined(PCBTARANIS) + case ITEM_MODEL_PREFLIGHT_LABEL: + lcd_putsLeft(y, STR_PREFLIGHT); + break; + case ITEM_MODEL_CHECKLIST_DISPLAY: g_model.displayText = onoffMenuItem(g_model.displayText, MODEL_SETUP_2ND_COLUMN, y, STR_CHECKLIST, attr, event); break; #endif + case ITEM_MODEL_THROTTLE_WARNING: + g_model.disableThrottleWarning = !onoffMenuItem(!g_model.disableThrottleWarning, MODEL_SETUP_2ND_COLUMN, y, STR_THROTTLEWARNING, attr, event); + break; + case ITEM_MODEL_SWITCHES_WARNING: { lcd_putsLeft(y, STR_SWITCHWARNING); @@ -1201,9 +1211,9 @@ void menuModelSetup(uint8_t event) uint8_t swactive = !(g_model.nSwToWarn & 1 << i); #if defined(PCBTARANIS) c = "\300-\301"[states & 0x03]; - lcd_putcAtt(MODEL_SETUP_2ND_COLUMN+i*(2*FW), y, 'A'+i, line && (m_posHorz == i) ? INVERS : 0); - if (swactive) lcd_putc(MODEL_SETUP_2ND_COLUMN+i*(2*FW)+FWNUM, y, c); - lcd_putsAtt(MODEL_SETUP_2ND_COLUMN+((NUM_SWITCHES-1)*2*FW+2), y, PSTR("<]"), (m_posHorz == NUM_SWITCHES-1 && !s_noHi) ? line : 0); + lcd_putcAtt(MODEL_SETUP_2ND_COLUMN+i*(2*FW+1), y, 'A'+i, line && (m_posHorz == i) ? INVERS : 0); + if (swactive) lcd_putc(MODEL_SETUP_2ND_COLUMN+i*(2*FW+1)+FWNUM+1, y, c); + lcd_putsAtt(MODEL_SETUP_2ND_COLUMN+((NUM_SWITCHES-1)*2*FW+8), y, PSTR("<]"), (m_posHorz == NUM_SWITCHES-1 && !s_noHi) ? line : 0); states >>= 2; #else attr = 0; diff --git a/radio/src/keys.cpp b/radio/src/keys.cpp index 3c76e5bba..c6f7c4096 100644 --- a/radio/src/keys.cpp +++ b/radio/src/keys.cpp @@ -37,6 +37,7 @@ #include "opentx.h" uint8_t s_evt; +struct t_inactivity inactivity = {0}; #if defined(CPUARM) uint8_t getEvent(bool trim) @@ -97,7 +98,9 @@ void Key::input(bool val, EnumKeys enuk) break; case KSTATE_RPTDELAY: // gruvin: delay state before first key repeat - if(m_cnt == KEY_LONG_DELAY) putEvent(EVT_KEY_LONG(enuk)); + if (m_cnt == KEY_LONG_DELAY) { + putEvent(EVT_KEY_LONG(enuk)); + } if (m_cnt == 40) { m_state = 16; m_cnt = 0; @@ -108,17 +111,19 @@ void Key::input(bool val, EnumKeys enuk) case 8: case 4: case 2: - if(m_cnt >= 48) { //3 6 12 24 48 pulses in every 480ms + if (m_cnt >= 48) { //3 6 12 24 48 pulses in every 480ms m_state >>= 1; m_cnt = 0; } // no break case 1: - if( (m_cnt & (m_state-1)) == 0) putEvent(EVT_KEY_REPT(enuk)); + if ((m_cnt & (m_state-1)) == 0) { + putEvent(EVT_KEY_REPT(enuk)); + } break; case KSTATE_PAUSE: //pause - if(m_cnt >= 64) { + if (m_cnt >= 64) { m_state = 8; m_cnt = 0; } diff --git a/radio/src/keys.h b/radio/src/keys.h new file mode 100755 index 000000000..350ab81d5 --- /dev/null +++ b/radio/src/keys.h @@ -0,0 +1,231 @@ +/* + * Authors (alphabetical order) + * - Andre Bernet + * - Andreas Weitl + * - Bertrand Songis + * - Bryan J. Rentoul (Gruvin) + * - Cameron Weeks + * - Erez Raviv + * - Gabriel Birkus + * - Jean-Pierre Parisy + * - Karl Szmutny + * - Michael Blandford + * - Michal Hlavinka + * - Pat Mackenzie + * - Philip Moss + * - Rob Thomson + * - Romolo Manfredini + * - Thomas Husterer + * + * opentx is based on code named + * gruvin9x by Bryan J. Rentoul: http://code.google.com/p/gruvin9x/, + * er9x by Erez Raviv: http://code.google.com/p/er9x/, + * and the original (and ongoing) project by + * Thomas Husterer, th9x: http://code.google.com/p/th9x/ + * + * This program is free software; you can redistribute it and/or modify + * it under the terms of the GNU General Public License version 2 as + * published by the Free Software Foundation. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + */ + +#ifndef keys_h +#define keys_h + +enum EnumKeys { + KEY_MENU, + KEY_EXIT, +#if defined(PCBTARANIS) + KEY_ENTER, + KEY_PAGE, + KEY_PLUS, + KEY_MINUS, +#else + KEY_DOWN, + KEY_UP, + KEY_RIGHT, + KEY_LEFT, +#endif + + TRM_BASE, + TRM_LH_DWN = TRM_BASE, + TRM_LH_UP, + TRM_LV_DWN, + TRM_LV_UP, + TRM_RV_DWN, + TRM_RV_UP, + TRM_RH_DWN, + TRM_RH_UP, + +#if ROTARY_ENCODERS > 0 || defined(ROTARY_ENCODER_NAVIGATION) + BTN_REa, +#endif +#if ROTARY_ENCODERS > 0 + BTN_REb, +#endif + + NUM_KEYS, + SW_BASE=NUM_KEYS, + +#if defined(PCBTARANIS) + SW_SA0=SW_BASE, + SW_SA1, + SW_SA2, + SW_SB0, + SW_SB1, + SW_SB2, + SW_SC0, + SW_SC1, + SW_SC2, + SW_SD0, + SW_SD1, + SW_SD2, + SW_SE0, + SW_SE1, + SW_SE2, + SW_SF0, + SW_SF2, + SW_SG0, + SW_SG1, + SW_SG2, + SW_SH0, + SW_SH2, +#else + SW_ID0=SW_BASE, + SW_ID1, + SW_ID2, +#if defined(EXTRA_3POS) + SW_ID3, + SW_ID4, + SW_ID5, +#endif + + SW_THR, + SW_RUD, + SW_ELE, + SW_AIL, + SW_GEA, + SW_TRN, +#endif + +}; + +#define EVT_KEY_MASK(e) ((e) & 0x1f) + +#define _MSK_KEY_BREAK 0x20 +#define _MSK_KEY_REPT 0x40 +#define _MSK_KEY_FIRST 0x60 +#define _MSK_KEY_LONG 0x80 + +#define EVT_KEY_BREAK(key) ((key)|_MSK_KEY_BREAK) +#define EVT_KEY_FIRST(key) ((key)|_MSK_KEY_FIRST) +#define EVT_KEY_REPT(key) ((key)|_MSK_KEY_REPT) +#define EVT_KEY_LONG(key) ((key)|_MSK_KEY_LONG) + +#define IS_KEY_BREAK(evt) (((evt)&0xe0) == _MSK_KEY_BREAK) +#define IS_KEY_FIRST(evt) (((evt)&0xe0) == _MSK_KEY_FIRST) +#define IS_KEY_LONG(evt) (((evt)&0xe0) == _MSK_KEY_LONG) + +#define EVT_ENTRY 0xbf +#define EVT_ENTRY_UP 0xbe +#define EVT_MENU_UP 0xbd + +#if defined(PCBTARANIS) + #define EVT_ROTARY_BREAK EVT_KEY_BREAK(KEY_ENTER) + #define EVT_ROTARY_LONG EVT_KEY_LONG(KEY_ENTER) +#else + #define EVT_ROTARY_BREAK 0xcf + #define EVT_ROTARY_LONG 0xce + #define EVT_ROTARY_LEFT 0xdf + #define EVT_ROTARY_RIGHT 0xde +#endif + +#if defined(PCBTARANIS) + #define IS_ROTARY_LEFT(evt) (evt==EVT_KEY_FIRST(KEY_MINUS) || evt==EVT_KEY_REPT(KEY_MINUS)) + #define IS_ROTARY_RIGHT(evt) (evt==EVT_KEY_FIRST(KEY_PLUS) || evt==EVT_KEY_REPT(KEY_PLUS)) + #define IS_ROTARY_UP(evt) (evt==EVT_KEY_FIRST(KEY_PLUS) || evt==EVT_KEY_REPT(KEY_PLUS)) + #define IS_ROTARY_DOWN(evt) (evt==EVT_KEY_FIRST(KEY_MINUS) || evt==EVT_KEY_REPT(KEY_MINUS)) + #define IS_ROTARY_BREAK(evt) (evt==EVT_KEY_BREAK(KEY_ENTER)) + #define IS_ROTARY_LONG(evt) (evt==EVT_KEY_LONG(KEY_ENTER)) + #define IS_ROTARY_EVENT(evt) (0) + #define CASE_EVT_ROTARY_BREAK /*case EVT_KEY_BREAK(KEY_ENTER):*/ + #define CASE_EVT_ROTARY_LONG /*case EVT_KEY_LONG(KEY_ENTER):*/ + #define CASE_EVT_ROTARY_LEFT case EVT_KEY_FIRST(KEY_MOVE_DOWN): case EVT_KEY_REPT(KEY_MOVE_DOWN): + #define CASE_EVT_ROTARY_RIGHT case EVT_KEY_FIRST(KEY_MOVE_UP): case EVT_KEY_REPT(KEY_MOVE_UP): +#elif defined(ROTARY_ENCODER_NAVIGATION) + #define IS_ROTARY_LEFT(evt) (evt == EVT_ROTARY_LEFT) + #define IS_ROTARY_RIGHT(evt) (evt == EVT_ROTARY_RIGHT) + #define IS_ROTARY_UP(evt) IS_ROTARY_LEFT(evt) + #define IS_ROTARY_DOWN(evt) IS_ROTARY_RIGHT(evt) + #define IS_ROTARY_BREAK(evt) (evt == EVT_ROTARY_BREAK) + #define IS_ROTARY_LONG(evt) (evt == EVT_ROTARY_LONG) + #define IS_ROTARY_EVENT(evt) (EVT_KEY_MASK(evt) >= 0x0e) + #define CASE_EVT_ROTARY_BREAK case EVT_ROTARY_BREAK: + #define CASE_EVT_ROTARY_LONG case EVT_ROTARY_LONG: + #define CASE_EVT_ROTARY_LEFT case EVT_ROTARY_LEFT: + #define CASE_EVT_ROTARY_RIGHT case EVT_ROTARY_RIGHT: +#else + #define IS_ROTARY_LEFT(evt) (0) + #define IS_ROTARY_RIGHT(evt) (0) + #define IS_ROTARY_UP(evt) (0) + #define IS_ROTARY_DOWN(evt) (0) + #define IS_ROTARY_BREAK(evt) (0) + #define IS_ROTARY_LONG(evt) (0) + #define IS_ROTARY_EVENT(evt) (0) + #define CASE_EVT_ROTARY_BREAK + #define CASE_EVT_ROTARY_LONG + #define CASE_EVT_ROTARY_LEFT + #define CASE_EVT_ROTARY_RIGHT +#endif + +class Key +{ +#define FILTERBITS 4 + +#ifdef SIMU + #define FFVAL 1 +#else + #define FFVAL ((1< 0; } + void pauseEvents() { m_state = KSTATE_PAUSE; m_cnt = 0; } + void killEvents() { m_state = KSTATE_KILLED; } +}; + +extern Key keys[NUM_KEYS]; + +extern uint8_t s_evt; + +#define putEvent(evt) s_evt = evt + +void clearKeyEvents(); +void pauseEvents(uint8_t enuk); +void killEvents(uint8_t enuk); + +#if defined(CPUARM) + uint8_t getEvent(bool trim=false); +#else + uint8_t getEvent(); +#endif + +uint8_t keyDown(); + +#endif diff --git a/radio/src/lcd.cpp b/radio/src/lcd.cpp index 0bfd78820..ca7389578 100644 --- a/radio/src/lcd.cpp +++ b/radio/src/lcd.cpp @@ -49,42 +49,6 @@ void lcd_clear() memset(displayBuf, 0, sizeof(displayBuf)); } -void lcd_img(xcoord_t x, uint8_t y, const pm_uchar * img, uint8_t idx, LcdFlags att) -{ - const pm_uchar *q = img; -#if LCD_W >= 260 - xcoord_t w = pgm_read_byte(q++); - if (w == 255) w += pgm_read_byte(q++); -#else - uint8_t w = pgm_read_byte(q++); -#endif - uint8_t hb = (pgm_read_byte(q++)+7)/8; - bool inv = (att & INVERS) ? true : (att & BLINK ? BLINK_ON_PHASE : false); - q += idx*w*hb; - for (uint8_t yb = 0; yb < hb; yb++) { - uint8_t *p = &displayBuf[ (y / 8 + yb) * LCD_W + x ]; - for (xcoord_t i=0; i= 260 + xcoord_t w = pgm_read_byte(q++); + if (w == 255) w += pgm_read_byte(q++); +#else + uint8_t w = pgm_read_byte(q++); +#endif + uint8_t hb = (pgm_read_byte(q++)+7)/8; + bool inv = (att & INVERS) ? true : (att & BLINK ? BLINK_ON_PHASE : false); + q += idx*w*hb; + for (uint8_t yb = 0; yb < hb; yb++) { + uint8_t *p = &displayBuf[ (y / 8 + yb) * LCD_W + x ]; + for (xcoord_t i=0; i + +#ifdef PCBSKY +#include "AT91SAM3S4.h" +#endif + +#ifdef PCBTARANIS +#include "stm32f2xx.h" +#include "stm32f2xx_gpio.h" +#endif + +#if defined(PCBTARANIS) +void bwdt_reset() +{ + IWDG->KR = 0xAAAA; // reload +} +#endif + +#if defined(PCBTARANIS) + +__attribute__ ((section(".bootrodata"), used)) +void _bootStart(void); + +__attribute__ ((section(".isr_boot_vector"), used)) +const uint32_t BootVectors[] = { (uint32_t) &_estack, + (uint32_t) (void (*)(void)) ((unsigned long) &_bootStart) }; +#endif + +#if defined(PCBTARANIS) +__attribute__ ((section(".bootrodata.*"), used)) +#endif + +#ifdef PCBSKY +__attribute__ ((section(".bootrodata"), used)) +#endif + +const uint8_t BootCode[] = { +#include "bootloader.lbm" +}; + +#if defined(PCBTARANIS) + +__attribute__ ((section(".bootrodata"), used)) + +void _bootStart() +{ + RCC->AHB1ENR |= RCC_AHB1ENR_GPIOCEN; // Enable portC clock + RCC->AHB1ENR |= RCC_AHB1ENR_GPIOEEN; // Enable portE clock + + GPIOC->PUPDR = 0x00000004; + GPIOE->PUPDR = 0x00000040; + + uint32_t i; + for (i = 0; i < 50000; i += 1) { + bwdt_reset(); + } + + if ((GPIOE->IDR & 0x00000008) == 0) { + if ((GPIOC->IDR & 0x00000002) == 0) { + // Bootloader needed + const uint8_t *src; + uint8_t *dest; + uint32_t size; + + bwdt_reset(); + size = sizeof(BootCode); + src = BootCode; + dest = (uint8_t *) 0x20000000; + + for (; size; size -= 1) { + *dest++ = *src++; + } + // Could check for a valid copy to RAM here + // Go execute bootloader + bwdt_reset(); + + uint32_t address = *(uint32_t *) 0x20000004; + + ((void (*)(void)) (address))(); // Go execute the loaded application + + } + } +// run_application() ; + asm(" mov.w r1, #134217728"); + // 0x8000000 + asm(" add.w r1, #32768"); + // 0x8000 + + asm(" movw r0, #60680"); + // 0xED08 + asm(" movt r0, #57344"); + // 0xE000 + asm(" str r1, [r0, #0]"); + // Set the VTOR + + asm("ldr r0, [r1, #0]"); + // Stack pointer value + asm("msr msp, r0"); + // Set it + asm("ldr r0, [r1, #4]"); + // Reset address + asm("mov.w r1, #1"); + asm("orr r0, r1"); + // Set lsbit + asm("bx r0"); + // Execute application +} +#endif + diff --git a/radio/src/myeeprom.h b/radio/src/myeeprom.h index c87086de5..119c69f87 100644 --- a/radio/src/myeeprom.h +++ b/radio/src/myeeprom.h @@ -540,20 +540,14 @@ PACK(typedef struct t_LimitData { #define MLTPX_REP 2 #if defined(CPUARM) -// highest bit used for small values in mix 128 --> 8 bit is enough -#define GV1_SMALL 128 -// highest bit used for large values in mix 4096 --> 12 bits is used (type for weight and offset has even 16 bits) -#define GV1_LARGE 4096 -// the define GV1_LARGE marks the highest bit value used for this variables -// because this would give too big numbers for ARM, we limit it further for offset and weight -// must be smaller than GV1_LARGE - RESERVE_RANGE_FOR_GVARS -1 +#define GV1_SMALL 128 +#define GV1_LARGE 512 #define GV_RANGE_WEIGHT 500 #define GV_RANGE_OFFSET 500 - -#define DELAY_STEP 10 -#define SLOW_STEP 10 -#define DELAY_MAX (25*DELAY_STEP) /* 25 seconds */ -#define SLOW_MAX (25*SLOW_STEP) /* 25 seconds */ +#define DELAY_STEP 10 +#define SLOW_STEP 10 +#define DELAY_MAX (25*DELAY_STEP) /* 25 seconds */ +#define SLOW_MAX (25*SLOW_STEP) /* 25 seconds */ #if defined(PCBTARANIS) PACK(typedef struct t_MixData { uint8_t destCh; diff --git a/radio/src/opentx.cpp b/radio/src/opentx.cpp index a8090a9aa..6e179bd5c 100644 --- a/radio/src/opentx.cpp +++ b/radio/src/opentx.cpp @@ -45,7 +45,6 @@ int16_t anas [NUM_INPUTS] = {0}; int16_t trims[NUM_STICKS] = {0}; int32_t chans[NUM_CHNOUT] = {0}; BeepANACenter bpanaCenter = 0; -struct t_inactivity inactivity = {0}; int24_t act [MAX_MIXERS] = {0}; SwOn swOn [MAX_MIXERS]; // TODO better name later... @@ -1973,8 +1972,8 @@ uint8_t getGVarFlightPhase(uint8_t phase, uint8_t idx) int16_t getGVarValue(int16_t x, int16_t min, int16_t max, int8_t phase) { - if (GV_IS_GV_VALUE(x,min,max)) { - int8_t idx = GV_INDEX_CALCULATION(x,max); + if (GV_IS_GV_VALUE(x, min, max)) { + int8_t idx = GV_INDEX_CALCULATION(x, max); int8_t mul = 1; if (idx < 0) { @@ -1984,7 +1983,6 @@ int16_t getGVarValue(int16_t x, int16_t min, int16_t max, int8_t phase) x = GVAR_VALUE(idx, getGVarFlightPhase(phase, idx)) * mul; } - return limit(min, x, max); } @@ -2105,6 +2103,8 @@ getvalue_t convert8bitsTelemValue(uint8_t channel, ls_telemetry_value_t value) break; case TELEM_CURRENT: case TELEM_POWER: + case TELEM_MAX_CURRENT: + case TELEM_MAX_POWER: result = value * 5; break; case TELEM_CONSUMPTION: @@ -2982,6 +2982,8 @@ void resetTimer(uint8_t idx) timerState.val_10ms = 0 ; } +bool s_mixer_first_run_done = false; + void resetAll() { static bool firstReset = true; @@ -3000,6 +3002,7 @@ void resetAll() } s_last_switch_value = 0; + s_mixer_first_run_done = false; SKIP_AUTOMATIC_PROMPTS(); @@ -3351,12 +3354,14 @@ uint8_t fnSwitchDuration[NUM_CFN] = { 0 }; inline void playCustomFunctionFile(CustomFnData *sd, uint8_t id) { - char filename[sizeof(SOUNDS_PATH)+sizeof(sd->play.name)+sizeof(SOUNDS_EXT)] = SOUNDS_PATH "/"; - strncpy(filename+SOUNDS_PATH_LNG_OFS, currentLanguagePack->id, 2); - strncpy(filename+sizeof(SOUNDS_PATH), sd->play.name, sizeof(sd->play.name)); - filename[sizeof(SOUNDS_PATH)+sizeof(sd->play.name)] = '\0'; - strcat(filename+sizeof(SOUNDS_PATH), SOUNDS_EXT); - PLAY_FILE(filename, sd->func==FUNC_BACKGND_MUSIC ? PLAY_BACKGROUND : 0, id); + if (sd->play.name[0] != '\0') { + char filename[sizeof(SOUNDS_PATH)+sizeof(sd->play.name)+sizeof(SOUNDS_EXT)] = SOUNDS_PATH "/"; + strncpy(filename+SOUNDS_PATH_LNG_OFS, currentLanguagePack->id, 2); + strncpy(filename+sizeof(SOUNDS_PATH), sd->play.name, sizeof(sd->play.name)); + filename[sizeof(SOUNDS_PATH)+sizeof(sd->play.name)] = '\0'; + strcat(filename+sizeof(SOUNDS_PATH), SOUNDS_EXT); + PLAY_FILE(filename, sd->func==FUNC_BACKGND_MUSIC ? PLAY_BACKGROUND : 0, id); + } } #endif @@ -3852,21 +3857,21 @@ void perOut(uint8_t mode, uint8_t tick10ms) // the unit of the stored value is the value from md->speedUp or md->speedDown divide SLOW_STEP seconds; e.g. value 4 means 4/SLOW_STEP = 2 seconds for CPU64 // because we get a tick each 10msec, we need 100 ticks for one second // the value in md->speedXXX gives the time it should take to do a full movement from -100 to 100 therefore 200%. This equals 2048 in recalculated internal range - if (tick10ms) { + if (tick10ms || !s_mixer_first_run_done) { // only if already time is passed add or substract a value according the speed configured int32_t rate = (int32_t) tick10ms << (DEL_MULT_SHIFT+11); // = DEL_MULT*2048*tick10ms // rate equals a full range for one second; if less time is passed rate is accordingly smaller // if one second passed, rate would be 2048 (full motion)*256(recalculated weight)*100(100 ticks needed for one second) int32_t currentValue = ((int32_t) v< 0) { - if (md->speedUp > 0) { + if (s_mixer_first_run_done && md->speedUp > 0) { // if a speed upwards is defined recalculate the new value according configured speed; the higher the speed the smaller the add value is int32_t newValue = tact+rate/((int16_t)(100/SLOW_STEP)*md->speedUp); if (newValuespeedDown > 0) { + if (s_mixer_first_run_done && md->speedDown > 0) { // see explanation in speedUp int32_t newValue = tact-rate/((int16_t)(100/SLOW_STEP)*md->speedDown); if (newValue>currentValue) currentValue = newValue; // Endposition; prevent toggling around the destination @@ -4089,6 +4094,8 @@ void doMixerCalculations() perOut(e_perout_mode_normal, tick10ms); } + s_mixer_first_run_done = true; + //========== FUNCTIONS =============== // must be done after mixing because some functions use the inputs/channels values // must be done before limits because of the applyLimit function: it checks for safety switches which would be not initialized otherwise diff --git a/radio/src/opentx.h b/radio/src/opentx.h index 5c86d0dd3..d1fc73358 100644 --- a/radio/src/opentx.h +++ b/radio/src/opentx.h @@ -297,83 +297,6 @@ extern void boardInit(); #define NUM_STICKS 4 -enum EnumKeys { - KEY_MENU, - KEY_EXIT, -#if defined(PCBTARANIS) - KEY_ENTER, - KEY_PAGE, - KEY_PLUS, - KEY_MINUS, -#else - KEY_DOWN, - KEY_UP, - KEY_RIGHT, - KEY_LEFT, -#endif - - TRM_BASE, - TRM_LH_DWN = TRM_BASE, - TRM_LH_UP, - TRM_LV_DWN, - TRM_LV_UP, - TRM_RV_DWN, - TRM_RV_UP, - TRM_RH_DWN, - TRM_RH_UP, - -#if ROTARY_ENCODERS > 0 || defined(ROTARY_ENCODER_NAVIGATION) - BTN_REa, -#endif -#if ROTARY_ENCODERS > 0 - BTN_REb, -#endif - - NUM_KEYS, - SW_BASE=NUM_KEYS, - -#if defined(PCBTARANIS) - SW_SA0=SW_BASE, - SW_SA1, - SW_SA2, - SW_SB0, - SW_SB1, - SW_SB2, - SW_SC0, - SW_SC1, - SW_SC2, - SW_SD0, - SW_SD1, - SW_SD2, - SW_SE0, - SW_SE1, - SW_SE2, - SW_SF0, - SW_SF2, - SW_SG0, - SW_SG1, - SW_SG2, - SW_SH0, - SW_SH2, -#else - SW_ID0=SW_BASE, - SW_ID1, - SW_ID2, -#if defined(EXTRA_3POS) - SW_ID3, - SW_ID4, - SW_ID5, -#endif - - SW_THR, - SW_RUD, - SW_ELE, - SW_AIL, - SW_GEA, - SW_TRN, -#endif - -}; #if defined(PCBTARANIS) #define NUM_SWITCHES 8 @@ -587,35 +510,6 @@ extern uint8_t stickMode; extern uint8_t channel_order(uint8_t x); -class Key -{ -#define FILTERBITS 4 - -#ifdef SIMU - #define FFVAL 1 -#else - #define FFVAL ((1< 0; } - void pauseEvents() { m_state = KSTATE_PAUSE; m_cnt = 0; } - void killEvents() { m_state = KSTATE_KILLED; } -}; - -extern Key keys[NUM_KEYS]; - enum BaseCurves { CURVE_NONE, CURVE_X_GT0, @@ -630,77 +524,9 @@ enum BaseCurves { #define THRCHK_DEADBAND 16 #if defined(FSPLASH) || defined(XSPLASH) -#define SPLASH_TIMEOUT (g_eeGeneral.splashMode == 0 ? 60000/*infinite=10mn*/ : ((4*100) * (g_eeGeneral.splashMode & 0x03))) + #define SPLASH_TIMEOUT (g_eeGeneral.splashMode == 0 ? 60000/*infinite=10mn*/ : ((4*100) * (g_eeGeneral.splashMode & 0x03))) #else -#define SPLASH_TIMEOUT (4*100) // 4 seconds -#endif - -#define EVT_KEY_MASK(e) ((e) & 0x1f) - -#define _MSK_KEY_BREAK 0x20 -#define _MSK_KEY_REPT 0x40 -#define _MSK_KEY_FIRST 0x60 -#define _MSK_KEY_LONG 0x80 - -#define EVT_KEY_BREAK(key) ((key)|_MSK_KEY_BREAK) -#define EVT_KEY_FIRST(key) ((key)|_MSK_KEY_FIRST) -#define EVT_KEY_REPT(key) ((key)|_MSK_KEY_REPT) -#define EVT_KEY_LONG(key) ((key)|_MSK_KEY_LONG) - -#define IS_KEY_BREAK(evt) (((evt)&0xe0) == _MSK_KEY_BREAK) -#define IS_KEY_FIRST(evt) (((evt)&0xe0) == _MSK_KEY_FIRST) -#define IS_KEY_LONG(evt) (((evt)&0xe0) == _MSK_KEY_LONG) - -#define EVT_ENTRY 0xbf -#define EVT_ENTRY_UP 0xbe -#define EVT_MENU_UP 0xbd - -#if defined(PCBTARANIS) - #define EVT_ROTARY_BREAK EVT_KEY_BREAK(KEY_ENTER) - #define EVT_ROTARY_LONG EVT_KEY_LONG(KEY_ENTER) -#else - #define EVT_ROTARY_BREAK 0xcf - #define EVT_ROTARY_LONG 0xce - #define EVT_ROTARY_LEFT 0xdf - #define EVT_ROTARY_RIGHT 0xde -#endif - -#if defined(PCBTARANIS) - #define IS_ROTARY_LEFT(evt) (evt==EVT_KEY_FIRST(KEY_MINUS) || evt==EVT_KEY_REPT(KEY_MINUS)) - #define IS_ROTARY_RIGHT(evt) (evt==EVT_KEY_FIRST(KEY_PLUS) || evt==EVT_KEY_REPT(KEY_PLUS)) - #define IS_ROTARY_UP(evt) (evt==EVT_KEY_FIRST(KEY_PLUS) || evt==EVT_KEY_REPT(KEY_PLUS)) - #define IS_ROTARY_DOWN(evt) (evt==EVT_KEY_FIRST(KEY_MINUS) || evt==EVT_KEY_REPT(KEY_MINUS)) - #define IS_ROTARY_BREAK(evt) (evt==EVT_KEY_BREAK(KEY_ENTER)) - #define IS_ROTARY_LONG(evt) (evt==EVT_KEY_LONG(KEY_ENTER)) - #define IS_ROTARY_EVENT(evt) (0) - #define CASE_EVT_ROTARY_BREAK /*case EVT_KEY_BREAK(KEY_ENTER):*/ - #define CASE_EVT_ROTARY_LONG /*case EVT_KEY_LONG(KEY_ENTER):*/ - #define CASE_EVT_ROTARY_LEFT case EVT_KEY_FIRST(KEY_MOVE_DOWN): case EVT_KEY_REPT(KEY_MOVE_DOWN): - #define CASE_EVT_ROTARY_RIGHT case EVT_KEY_FIRST(KEY_MOVE_UP): case EVT_KEY_REPT(KEY_MOVE_UP): -#elif defined(ROTARY_ENCODER_NAVIGATION) - #define IS_ROTARY_LEFT(evt) (evt == EVT_ROTARY_LEFT) - #define IS_ROTARY_RIGHT(evt) (evt == EVT_ROTARY_RIGHT) - #define IS_ROTARY_UP(evt) IS_ROTARY_LEFT(evt) - #define IS_ROTARY_DOWN(evt) IS_ROTARY_RIGHT(evt) - #define IS_ROTARY_BREAK(evt) (evt == EVT_ROTARY_BREAK) - #define IS_ROTARY_LONG(evt) (evt == EVT_ROTARY_LONG) - #define IS_ROTARY_EVENT(evt) (EVT_KEY_MASK(evt) >= 0x0e) - #define CASE_EVT_ROTARY_BREAK case EVT_ROTARY_BREAK: - #define CASE_EVT_ROTARY_LONG case EVT_ROTARY_LONG: - #define CASE_EVT_ROTARY_LEFT case EVT_ROTARY_LEFT: - #define CASE_EVT_ROTARY_RIGHT case EVT_ROTARY_RIGHT: -#else - #define IS_ROTARY_LEFT(evt) (0) - #define IS_ROTARY_RIGHT(evt) (0) - #define IS_ROTARY_UP(evt) (0) - #define IS_ROTARY_DOWN(evt) (0) - #define IS_ROTARY_BREAK(evt) (0) - #define IS_ROTARY_LONG(evt) (0) - #define IS_ROTARY_EVENT(evt) (0) - #define CASE_EVT_ROTARY_BREAK - #define CASE_EVT_ROTARY_LONG - #define CASE_EVT_ROTARY_LEFT - #define CASE_EVT_ROTARY_RIGHT + #define SPLASH_TIMEOUT (4*100) // 4 seconds #endif #if defined(PCBTARANIS) @@ -734,6 +560,7 @@ struct t_inactivity uint16_t counter; uint8_t sum; }; + extern struct t_inactivity inactivity; #if defined(PXX) @@ -754,25 +581,8 @@ void str2zchar(char *dest, const char *src, int size); void zchar2str(char *dest, const char *src, int size); #endif -extern uint8_t s_evt; -#define putEvent(evt) s_evt = evt -void clearKeyEvents(); -void pauseEvents(uint8_t enuk); -void killEvents(uint8_t enuk); -#if defined(CPUARM) - uint8_t getEvent(bool trim); -#else - uint8_t getEvent(); -#endif - -uint8_t keyDown(); - -enum PowerState { - e_power_on, - e_power_trainer, - e_power_usb, - e_power_off -}; +#include "keys.h" +#include "pwr.h" bool switchState(EnumKeys enuk); uint8_t trimDown(uint8_t idx); @@ -1111,7 +921,7 @@ template void swap(t & a, t & b) { t tmp = b; b = a; a = tmp; } uint16_t isqrt32(uint32_t n); #endif -#if defined(CPUARM) +#if defined(CPUARM) && !defined(BOOT) #if !defined(SIMU) extern "C" { #include @@ -1514,6 +1324,7 @@ enum AUDIO_SOUNDS { #endif #include "translations.h" +#include "fonts.h" #if defined(HAPTIC) #include "haptic.h" @@ -1632,7 +1443,7 @@ extern union ReusableBuffer reusableBuffer; void checkFlashOnBeep(); #if defined(FRSKY) || defined(CPUARM) -FORCEINLINE void convertUnit(getvalue_t & val, uint8_t & unit); +void convertUnit(getvalue_t & val, uint8_t & unit); // TODO check FORCEINLINE on stock void putsTelemetryValue(xcoord_t x, uint8_t y, lcdint_t val, uint8_t unit, uint8_t att); #else #define convertUnit(...) diff --git a/radio/src/pwr.h b/radio/src/pwr.h new file mode 100755 index 000000000..b6816d590 --- /dev/null +++ b/radio/src/pwr.h @@ -0,0 +1,47 @@ +/* + * Authors (alphabetical order) + * - Andre Bernet + * - Andreas Weitl + * - Bertrand Songis + * - Bryan J. Rentoul (Gruvin) + * - Cameron Weeks + * - Erez Raviv + * - Gabriel Birkus + * - Jean-Pierre Parisy + * - Karl Szmutny + * - Michael Blandford + * - Michal Hlavinka + * - Pat Mackenzie + * - Philip Moss + * - Rob Thomson + * - Romolo Manfredini + * - Thomas Husterer + * + * opentx is based on code named + * gruvin9x by Bryan J. Rentoul: http://code.google.com/p/gruvin9x/, + * er9x by Erez Raviv: http://code.google.com/p/er9x/, + * and the original (and ongoing) project by + * Thomas Husterer, th9x: http://code.google.com/p/th9x/ + * + * This program is free software; you can redistribute it and/or modify + * it under the terms of the GNU General Public License version 2 as + * published by the Free Software Foundation. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + */ + +#ifndef pwr_h +#define pwr_h + +enum PowerState { + e_power_on, + e_power_trainer, + e_power_usb, + e_power_off +}; + +#endif diff --git a/radio/src/sdcard.h b/radio/src/sdcard.h index ccbad5fa6..1a216562c 100644 --- a/radio/src/sdcard.h +++ b/radio/src/sdcard.h @@ -47,6 +47,7 @@ #define SYSTEM_SUBDIR "SYSTEM" // no trailing slash = important #define BITMAPS_PATH ROOT_PATH "BMP" #define SCRIPTS_PATH ROOT_PATH "SCRIPTS" +#define FIRMWARES_PATH ROOT_PATH "FIRMWARES" #define MODELS_EXT ".bin" #define LOGS_EXT ".csv" @@ -62,6 +63,7 @@ extern const pm_char * openLogs(); extern void closeLogs(); extern void writeLogs(); +#if !defined(BOOT) inline const pm_char *SDCARD_ERROR(FRESULT result) { if (result == FR_NOT_READY) @@ -69,6 +71,7 @@ inline const pm_char *SDCARD_ERROR(FRESULT result) else return STR_SDCARD_ERROR; } +#endif #if defined(PCBTARANIS) #define O9X_FOURCC 0x3378396F // o9x for Taranis diff --git a/radio/src/simpgmspace.cpp b/radio/src/simpgmspace.cpp index b00c96be7..8b941be1f 100644 --- a/radio/src/simpgmspace.cpp +++ b/radio/src/simpgmspace.cpp @@ -101,12 +101,12 @@ sem_t *eeprom_write_sem; #if defined(PCBTARANIS) #define SWITCH_CASE(swtch, pin, mask) \ case swtch: \ - if (state) pin &= ~(mask); else pin |= (mask); \ + if (state > 0) pin &= ~(mask); else pin |= (mask); \ break; #else #define SWITCH_CASE(swtch, pin, mask) \ case swtch: \ - if (state) pin |= (mask); else pin &= ~(mask); \ + if (state > 0) pin |= (mask); else pin &= ~(mask); \ break; #endif #define SWITCH_3_CASE(swtch, pin1, pin2, mask1, mask2) \ @@ -116,13 +116,13 @@ sem_t *eeprom_write_sem; break; #define KEY_CASE(key, pin, mask) \ case key: \ - if (state) pin &= ~mask; else pin |= mask;\ + if (state > 0) pin &= ~mask; else pin |= mask;\ break; #define TRIM_CASE KEY_CASE #else #define SWITCH_CASE(swtch, pin, mask) \ case swtch: \ - if (state) pin &= ~(mask); else pin |= (mask); \ + if (state > 0) pin &= ~(mask); else pin |= (mask); \ break; #define SWITCH_3_CASE(swtch, pin1, pin2, mask1, mask2) \ case swtch: \ @@ -131,7 +131,7 @@ sem_t *eeprom_write_sem; break; #define KEY_CASE(key, pin, mask) \ case key: \ - if (state) pin |= (mask); else pin &= ~(mask);\ + if (state > 0) pin |= (mask); else pin &= ~(mask);\ break; #define TRIM_CASE KEY_CASE #endif @@ -638,6 +638,7 @@ void lcdRefresh() #if defined(PCBTARANIS) void usbStart() { } +int usbPlugged() { return false; } void USART_DeInit(USART_TypeDef* ) { } ErrorStatus RTC_SetTime(uint32_t RTC_Format, RTC_TimeTypeDef* RTC_TimeStruct) { return SUCCESS; } ErrorStatus RTC_SetDate(uint32_t RTC_Format, RTC_DateTypeDef* RTC_DateStruct) { return SUCCESS; } diff --git a/radio/src/targets/sky9x/sam3s4c_flash.ld b/radio/src/targets/sky9x/sam3s4c_flash.ld index fd8241a61..247bf4b1b 100644 --- a/radio/src/targets/sky9x/sam3s4c_flash.ld +++ b/radio/src/targets/sky9x/sam3s4c_flash.ld @@ -71,9 +71,15 @@ SECTIONS */ .text : { - _stext = .; /* Provide the name for the start of this section */ + FILL(0xFFFF) - CREATE_OBJECT_SYMBOLS + CREATE_OBJECT_SYMBOLS + + *(.bootrodata) + *(.bootrodata.*) + + . = ALIGN(32768); /* Align the start of the exidx part */ + _stext = .; /* Provide the name for the start of this section */ KEEP(*(.vectors)) *(.text) @@ -129,11 +135,8 @@ SECTIONS . = ALIGN(4); /* Align the end of the section */ } > RAM - _ebss = .; /* Provide the name for the end of this section */ + _ebss = .; /* Provide the name for the end of this section */ - . = ALIGN(4); /* Align the end of the section */ - __end = .; - _end = .; /* * The ".stack" section is our stack. diff --git a/radio/src/targets/taranis/STM32F2xx_StdPeriph_Lib_V1.1.0/Libraries/CMSIS/Device/ST/STM32F2xx/Source/Templates/system_stm32f2xx.c b/radio/src/targets/taranis/STM32F2xx_StdPeriph_Lib_V1.1.0/Libraries/CMSIS/Device/ST/STM32F2xx/Source/Templates/system_stm32f2xx.c index 654bb5fcf..367091dd2 100644 --- a/radio/src/targets/taranis/STM32F2xx_StdPeriph_Lib_V1.1.0/Libraries/CMSIS/Device/ST/STM32F2xx/Source/Templates/system_stm32f2xx.c +++ b/radio/src/targets/taranis/STM32F2xx_StdPeriph_Lib_V1.1.0/Libraries/CMSIS/Device/ST/STM32F2xx/Source/Templates/system_stm32f2xx.c @@ -232,7 +232,12 @@ void SystemInit(void) #ifdef VECT_TAB_SRAM SCB->VTOR = SRAM_BASE | VECT_TAB_OFFSET; /* Vector Table Relocation in Internal SRAM */ #else - SCB->VTOR = FLASH_BASE | VECT_TAB_OFFSET; /* Vector Table Relocation in Internal FLASH */ + #if defined(BOOTLOADER) || defined(BOOT) + extern uint32_t g_pfnVectors ; + SCB->VTOR = (uint32_t) &g_pfnVectors ; /* Vector Table Relocation in Internal FLASH */ + #else + SCB->VTOR = FLASH_BASE | VECT_TAB_OFFSET; /* Vector Table Relocation in Internal FLASH */ + #endif #endif } diff --git a/radio/src/targets/taranis/STM32F2xx_StdPeriph_Lib_V1.1.0/Libraries/STM32F2xx_StdPeriph_Driver/src/stm32f2xx_spi.c b/radio/src/targets/taranis/STM32F2xx_StdPeriph_Lib_V1.1.0/Libraries/STM32F2xx_StdPeriph_Driver/src/stm32f2xx_spi.c index 033475e68..0a42a0f2c 100644 --- a/radio/src/targets/taranis/STM32F2xx_StdPeriph_Lib_V1.1.0/Libraries/STM32F2xx_StdPeriph_Driver/src/stm32f2xx_spi.c +++ b/radio/src/targets/taranis/STM32F2xx_StdPeriph_Lib_V1.1.0/Libraries/STM32F2xx_StdPeriph_Driver/src/stm32f2xx_spi.c @@ -113,8 +113,8 @@ */ /* Includes ------------------------------------------------------------------*/ -#include "stm32f2xx_spi.h" -#include "stm32f2xx_rcc.h" +#include "../inc/stm32f2xx_spi.h" +#include "../inc/stm32f2xx_rcc.h" /** @addtogroup STM32F2xx_StdPeriph_Driver * @{ diff --git a/radio/src/targets/taranis/aspi.cpp b/radio/src/targets/taranis/aspi.c similarity index 88% rename from radio/src/targets/taranis/aspi.cpp rename to radio/src/targets/taranis/aspi.c index b03d54a6d..f75cb4a02 100644 --- a/radio/src/targets/taranis/aspi.cpp +++ b/radio/src/targets/taranis/aspi.c @@ -10,8 +10,7 @@ ****************************************************************************** */ -#include "../opentx.h" -#include "./STM32F2xx_StdPeriph_Lib_V1.1.0/Libraries/STM32F2xx_StdPeriph_Driver/inc/stm32f2xx_gpio.h" +#include "board_taranis.h" /** **********send command to lcd************** diff --git a/radio/src/targets/taranis/aspi.h b/radio/src/targets/taranis/aspi.h index cd42e7eb6..a3f4f829f 100644 --- a/radio/src/targets/taranis/aspi.h +++ b/radio/src/targets/taranis/aspi.h @@ -11,6 +11,10 @@ #ifndef _ASPI_H_ #define _ASPI_H_ +#ifdef __cplusplus +extern "C" { +#endif + #include "./STM32F2xx_StdPeriph_Lib_V1.1.0/Libraries/CMSIS/Device/ST/STM32F2xx/Include/stm32f2xx.h" #define __no_operation __NOP @@ -33,5 +37,9 @@ void AspiCmd(u8 Command_Byte); void AspiData(u8 Para_data); +#ifdef __cplusplus +} +#endif + #endif diff --git a/radio/src/targets/taranis/audio_driver.cpp b/radio/src/targets/taranis/audio_driver.cpp index d0b0508aa..15d6fdd37 100644 --- a/radio/src/targets/taranis/audio_driver.cpp +++ b/radio/src/targets/taranis/audio_driver.cpp @@ -36,7 +36,7 @@ #include "../../opentx.h" -bool dacIdle = true; +int dacIdle = 1; void setSampleRate(uint32_t frequency) { @@ -96,7 +96,7 @@ void dacInit() bool dacQueue(AudioBuffer *buffer) { if (dacIdle) { - dacIdle = false; + dacIdle = 0; DMA1_Stream5->CR &= ~DMA_SxCR_EN ; // Disable DMA channel DMA1->HIFCR = DMA_HIFCR_CTCIF5 | DMA_HIFCR_CHTIF5 | DMA_HIFCR_CTEIF5 | DMA_HIFCR_CDMEIF5 | DMA_HIFCR_CFEIF5 ; // Write ones to clear bits DMA1_Stream5->M0AR = CONVERT_PTR(buffer->data); @@ -111,6 +111,20 @@ bool dacQueue(AudioBuffer *buffer) } } +void dacStart() +{ + DMA1->HIFCR = DMA_HIFCR_CTCIF5 | DMA_HIFCR_CHTIF5 | DMA_HIFCR_CTEIF5 | DMA_HIFCR_CDMEIF5 | DMA_HIFCR_CFEIF5 ; // Write ones to clear bits + DMA1_Stream5->CR |= DMA_SxCR_CIRC | DMA_SxCR_EN ; // Enable DMA channel + DAC->SR = DAC_SR_DMAUDR1 ; // Write 1 to clear flag + DAC->CR |= DAC_CR_EN1 | DAC_CR_DMAEN1 ; // Enable DAC +} + +void dacStop() +{ + DMA1_Stream5->CR &= ~DMA_SxCR_CIRC ; +} + + // Sound routines void audioInit() { @@ -149,7 +163,7 @@ extern "C" void DMA1_Stream5_IRQHandler() DAC->SR = DAC_SR_DMAUDR1; // Write 1 to clear flag } else { - dacIdle = true; + dacIdle = 1; } } #endif diff --git a/radio/src/targets/taranis/audio_driver.h b/radio/src/targets/taranis/audio_driver.h index 0a79ea75d..e357e8627 100644 --- a/radio/src/targets/taranis/audio_driver.h +++ b/radio/src/targets/taranis/audio_driver.h @@ -37,25 +37,14 @@ #ifndef audio_driver_h #define audio_driver_h -extern void audioInit( void ) ; -extern void audioEnd( void ) ; +void audioInit( void ) ; +void audioEnd( void ) ; +void dacStart(); +void dacStop(); extern void setSampleRate(uint32_t frequency); -extern bool dacIdle; - -inline void dacStart() -{ - DMA1->HIFCR = DMA_HIFCR_CTCIF5 | DMA_HIFCR_CHTIF5 | DMA_HIFCR_CTEIF5 | DMA_HIFCR_CDMEIF5 | DMA_HIFCR_CFEIF5 ; // Write ones to clear bits - DMA1_Stream5->CR |= DMA_SxCR_CIRC | DMA_SxCR_EN ; // Enable DMA channel - DAC->SR = DAC_SR_DMAUDR1 ; // Write 1 to clear flag - DAC->CR |= DAC_CR_EN1 | DAC_CR_DMAEN1 ; // Enable DAC -} - -inline void dacStop() -{ - DMA1_Stream5->CR &= ~DMA_SxCR_CIRC ; -} +extern int dacIdle; #define VOLUME_LEVEL_MAX 23 #define VOLUME_LEVEL_DEF 12 diff --git a/radio/src/targets/taranis/board_taranis.cpp b/radio/src/targets/taranis/board_taranis.cpp index 754f6e6c1..5266f1c98 100644 --- a/radio/src/targets/taranis/board_taranis.cpp +++ b/radio/src/targets/taranis/board_taranis.cpp @@ -44,22 +44,6 @@ extern "C" { volatile uint32_t Tenms ; // TODO to remove everywhere / use a #define -#define PIN_MODE_MASK 0x0003 -#define PIN_INPUT 0x0000 -#define PIN_OUTPUT 0x0001 -#define PIN_PERIPHERAL 0x0002 -#define PIN_ANALOG 0x0003 -#define PIN_PULL_MASK 0x000C -#define PIN_PULLUP 0x0004 -#define PIN_NO_PULLUP 0x0000 -#define PIN_PULLDOWN 0x0008 -#define PIN_NO_PULLDOWN 0x0000 -#define PIN_PERI_MASK 0x00F0 -#define PIN_PUSHPULL 0x0000 -#define PIN_ODRAIN 0x8000 -#define PIN_PORT_MASK 0x0700 -#define PIN_SPEED_MASK 0x6000 - #if !defined(SIMU) void configure_pins( uint32_t pins, uint16_t config ) { @@ -106,32 +90,6 @@ void configure_pins( uint32_t pins, uint16_t config ) } #endif -bool usbPlugged(void) -{ - return GPIO_ReadInputDataBit(GPIOA, PIN_FS_VBUS); -} - -#if !defined(SIMU) -extern "C" { -USB_OTG_CORE_HANDLE USB_OTG_dev; - -void OTG_FS_IRQHandler(void) -{ - USBD_OTG_ISR_Handler (&USB_OTG_dev); -} -} - -void usbInit() -{ - USB_OTG_BSP_Init(&USB_OTG_dev); -} - -void usbStart() -{ - USBD_Init(&USB_OTG_dev, USB_OTG_FS_CORE_ID, &USR_desc, &USBD_MSC_cb, &USR_cb); -} -#endif - void watchdogInit(unsigned int duration) { IWDG->KR = 0x5555 ; // Unlock registers diff --git a/radio/src/targets/taranis/board_taranis.h b/radio/src/targets/taranis/board_taranis.h index 4bbd2fde0..6a1a1e783 100644 --- a/radio/src/targets/taranis/board_taranis.h +++ b/radio/src/targets/taranis/board_taranis.h @@ -37,6 +37,10 @@ #ifndef board_taranis_h #define board_taranis_h +#ifdef __cplusplus +extern "C" { +#endif + #include "STM32F2xx_StdPeriph_Lib_V1.1.0/Libraries/STM32F2xx_StdPeriph_Driver/inc/stm32f2xx_rcc.h" #include "STM32F2xx_StdPeriph_Lib_V1.1.0/Libraries/STM32F2xx_StdPeriph_Driver/inc/stm32f2xx_gpio.h" #include "STM32F2xx_StdPeriph_Lib_V1.1.0/Libraries/STM32F2xx_StdPeriph_Driver/inc/stm32f2xx_spi.h" @@ -45,17 +49,23 @@ #include "STM32F2xx_StdPeriph_Lib_V1.1.0/Libraries/STM32F2xx_StdPeriph_Driver/inc/stm32f2xx_dma.h" #include "STM32F2xx_StdPeriph_Lib_V1.1.0/Libraries/STM32F2xx_StdPeriph_Driver/inc/stm32f2xx_usart.h" #include "STM32F2xx_StdPeriph_Lib_V1.1.0/Libraries/CMSIS/Device/ST/STM32F2xx/Include/stm32f2xx.h" -extern "C" { #include "STM32_USB-Host-Device_Lib_V2.1.0/Libraries/STM32_USB_Device_Library/Class/msc/inc/usbd_msc_core.h" #include "STM32_USB-Host-Device_Lib_V2.1.0/Libraries/STM32_USB_Device_Library/Core/inc/usbd_usr.h" #include "usbd_desc.h" #include "usb_conf.h" #include "usbd_conf.h" -} + #include "hal.h" #include "aspi.h" #include "i2c.h" + +#ifdef __cplusplus +} +#endif + +#if !defined(BOOT) #include "audio_driver.h" +#endif #define PERI1_FREQUENCY 30000000 #define PERI2_FREQUENCY 60000000 @@ -65,6 +75,22 @@ extern "C" { #define JACK_PPM_OUT() #define JACK_PPM_IN() +#define PIN_MODE_MASK 0x0003 +#define PIN_INPUT 0x0000 +#define PIN_OUTPUT 0x0001 +#define PIN_PERIPHERAL 0x0002 +#define PIN_ANALOG 0x0003 +#define PIN_PULL_MASK 0x000C +#define PIN_PULLUP 0x0004 +#define PIN_NO_PULLUP 0x0000 +#define PIN_PULLDOWN 0x0008 +#define PIN_NO_PULLDOWN 0x0000 +#define PIN_PERI_MASK 0x00F0 +#define PIN_PUSHPULL 0x0000 +#define PIN_ODRAIN 0x8000 +#define PIN_PORT_MASK 0x0700 +#define PIN_SPEED_MASK 0x6000 + void configure_pins( uint32_t pins, uint16_t config ); #define strcpy_P strcpy @@ -75,7 +101,7 @@ extern uint16_t sessionTimer; #define SLAVE_MODE() (g_model.trainerMode == 1) #define TRAINER_CONNECTED() (GPIO_ReadInputDataBit(GPIOTRNDET, PIN_TRNDET) == Bit_RESET) -void delaysInit(); +void delaysInit(void); #define DEBUG_BAUDRATE 115200 #define SPORT_BAUDRATE 57600 @@ -97,11 +123,11 @@ void delay_01us(uint16_t nb); #define SD_GET_SIZE_MB() (0) #define SD_GET_BLOCKNR() (0) #define SD_GET_SPEED() (0) - void sdInit(); - void sdDone(); - void sdPoll10ms(); + void sdInit(void); + void sdDone(void); + void sdPoll10ms(void); #define sdMountPoll() - uint32_t sdMounted(); + uint32_t sdMounted(void); #define SD_CARD_PRESENT() (~SD_PRESENT_GPIO->IDR & SD_PRESENT_GPIO_Pin) #endif @@ -116,15 +142,15 @@ void init_dsm2( uint32_t module_index ); void disable_dsm2( uint32_t module_index ); // Trainer driver -void init_trainer_ppm(); -void stop_trainer_ppm(); -void init_trainer_capture(); -void stop_trainer_capture(); +void init_trainer_ppm(void); +void stop_trainer_ppm(void); +void init_trainer_capture(void); +void stop_trainer_capture(void); // Keys driver -void keysInit(); -uint32_t readKeys(); -uint32_t readTrims(); +void keysInit(void); +uint32_t readKeys(void); +uint32_t readTrims(void); #define TRIMS_PRESSED() (readTrims()) #define KEYS_PRESSED() (~readKeys()) #define DBLKEYS_PRESSED_RGT_LFT(i) ((in & ((2<CCR1 != 0) // USB driver +int usbPlugged(void); #define BOOTLOADER_REQUEST() (0) #define usbBootloader() void usbInit(void); void usbStart(void); -bool usbPlugged(void); + +#ifdef __cplusplus +} +#endif // EEPROM driver #if !defined(SIMU) diff --git a/radio/src/targets/taranis/delays.cpp b/radio/src/targets/taranis/delays.c similarity index 94% rename from radio/src/targets/taranis/delays.cpp rename to radio/src/targets/taranis/delays.c index 256f431ed..756db1ed7 100644 --- a/radio/src/targets/taranis/delays.cpp +++ b/radio/src/targets/taranis/delays.c @@ -34,7 +34,7 @@ * */ -#include "../../opentx.h" +#include "board_taranis.h" void delaysInit(void) { diff --git a/radio/src/targets/taranis/diskio.cpp b/radio/src/targets/taranis/diskio.cpp index d9586804f..6cb17c7f0 100644 --- a/radio/src/targets/taranis/diskio.cpp +++ b/radio/src/targets/taranis/diskio.cpp @@ -35,9 +35,10 @@ */ #include -#include "../FatFs/diskio.h" -#include "../FatFs/ff.h" -#include "../CoOS/kernel/CoOS.h" +#include "board_taranis.h" +#include "../../FatFs/diskio.h" +#include "../../FatFs/ff.h" +#include "../../CoOS/kernel/CoOS.h" #include "hal.h" /* Definitions for MMC/SDC command */ @@ -93,6 +94,7 @@ uint32_t transSpeed; */ /*-----------------------------------------------------------------------*/ /* Lock / unlock functions */ /*-----------------------------------------------------------------------*/ +#if !defined(BOOT) int ff_cre_syncobj (BYTE vol, _SYNC_t *mutex) { *mutex = CoCreateMutex(); @@ -114,6 +116,7 @@ int ff_del_syncobj (_SYNC_t mutex) { return 1; } +#endif static const DWORD socket_state_mask_cp = (1 << 0); static const DWORD socket_state_mask_wp = (1 << 1); @@ -124,7 +127,6 @@ DSTATUS Stat = STA_NOINIT; /* Disk status */ static volatile DWORD Timer1, Timer2; /* 100Hz decrement timers */ -static BYTE CardType; /* Card type flags */ enum speed_setting { INTERFACE_SLOW, INTERFACE_FAST }; @@ -178,12 +180,10 @@ static void card_power(BYTE on) on=on; } -#if (STM32_SD_DISK_IOCTRL == 1) static int chk_power(void) { return 1; /* fake powered */ } -#endif /*-----------------------------------------------------------------------*/ /* Transmit/Receive a byte to MMC via SPI (Platform dependent) */ @@ -433,30 +433,29 @@ void power_on (void) static void power_off (void) { - GPIO_InitTypeDef GPIO_InitStructure; - if (!(Stat & STA_NOINIT)) { - SELECT(); - wait_ready(); - release_spi(); - } + if (!(Stat & STA_NOINIT)) { + SELECT(); + wait_ready(); + release_spi(); + } - SPI_I2S_DeInit(SPI_SD); - SPI_Cmd(SPI_SD, DISABLE); - RCC_APBPeriphClockCmd_SPI_SD(RCC_APBPeriph_SPI_SD, DISABLE); - - //All SPI-Pins to input with weak internal pull-downs - GPIO_InitStructure.GPIO_Pin = GPIO_Pin_SPI_SD_SCK | GPIO_Pin_SPI_SD_MISO | GPIO_Pin_SPI_SD_MOSI; - GPIO_InitStructure.GPIO_Mode = GPIO_Mode_IN; + SPI_I2S_DeInit(SPI_SD); + SPI_Cmd(SPI_SD, DISABLE); + RCC_APBPeriphClockCmd_SPI_SD(RCC_APBPeriph_SPI_SD, DISABLE); + + //All SPI-Pins to input with weak internal pull-downs + GPIO_InitStructure.GPIO_Pin = GPIO_Pin_SPI_SD_SCK | GPIO_Pin_SPI_SD_MISO + | GPIO_Pin_SPI_SD_MOSI; + GPIO_InitStructure.GPIO_Mode = GPIO_Mode_IN; GPIO_InitStructure.GPIO_OType = GPIO_OType_PP; GPIO_InitStructure.GPIO_PuPd = GPIO_PuPd_DOWN; - GPIO_Init(GPIO_SPI_SD, &GPIO_InitStructure); + GPIO_Init(GPIO_SPI_SD, &GPIO_InitStructure); - card_power(0); + card_power(0); - Stat |= STA_NOINIT; /* Set STA_NOINIT */ - + Stat |= STA_NOINIT; /* Set STA_NOINIT */ } /*-----------------------------------------------------------------------*/ @@ -501,7 +500,6 @@ BOOL rcvr_datablock ( /* Send a data packet to MMC */ /*-----------------------------------------------------------------------*/ -#if _FS_READONLY == 0 static BOOL xmit_datablock ( const BYTE *buff, /* 512 byte data block to be transmitted */ @@ -537,8 +535,6 @@ BOOL xmit_datablock ( return TRUE; } -#endif /* _READONLY */ - /*-----------------------------------------------------------------------*/ @@ -655,7 +651,6 @@ DSTATUS disk_initialize ( /*-----------------------------------------------------------------------*/ /* Get Disk Status */ /*-----------------------------------------------------------------------*/ - DSTATUS disk_status ( BYTE drv /* Physical drive number (0) */ ) @@ -665,7 +660,6 @@ DSTATUS disk_status ( } - /*-----------------------------------------------------------------------*/ /* Read Sector(s) */ /*-----------------------------------------------------------------------*/ @@ -675,14 +669,23 @@ int8_t SD_ReadSectors(uint8_t *buff, uint32_t sector, uint32_t count) { if (!(CardType & CT_BLOCK)) sector *= 512; /* Convert to byte address if needed */ - if (send_cmd(CMD18, sector) == 0) { /* READ_MULTIPLE_BLOCK */ - do { - if (!rcvr_datablock(buff, 512)) { - break; + if (count == 1) { /* Single block read */ + if (send_cmd(CMD17, sector) == 0) { /* READ_SINGLE_BLOCK */ + if (rcvr_datablock(buff, 512)) { + count = 0; } - buff += 512; - } while (--count); - send_cmd(CMD12, 0); /* STOP_TRANSMISSION */ + } + } + else { /* Multiple block read */ + if (send_cmd(CMD18, sector) == 0) { /* READ_MULTIPLE_BLOCK */ + do { + if (!rcvr_datablock(buff, 512)) { + break; + } + buff += 512; + } while (--count); + send_cmd(CMD12, 0); /* STOP_TRANSMISSION */ + } } release_spi(); @@ -700,29 +703,9 @@ DRESULT disk_read ( if (drv || !count) return RES_PARERR; if (Stat & STA_NOINIT) return RES_NOTRDY; - if (!(CardType & CT_BLOCK)) sector *= 512; /* Convert to byte address if needed */ + SD_ReadSectors(buff, sector, count); - if (count == 1) { /* Single block read */ - if (send_cmd(CMD17, sector) == 0) { /* READ_SINGLE_BLOCK */ - if (rcvr_datablock(buff, 512)) { - count = 0; - } - } - } - else { /* Multiple block read */ - if (send_cmd(CMD18, sector) == 0) { /* READ_MULTIPLE_BLOCK */ - do { - if (!rcvr_datablock(buff, 512)) { - break; - } - buff += 512; - } while (--count); - send_cmd(CMD12, 0); /* STOP_TRANSMISSION */ - } - } - release_spi(); - - return count ? RES_ERROR : RES_OK; + return RES_OK; } @@ -731,8 +714,6 @@ DRESULT disk_read ( /* Write Sector(s) */ /*-----------------------------------------------------------------------*/ -#if _FS_READONLY == 0 - // TODO quick & dirty int8_t SD_WriteSectors(uint8_t *buff, uint32_t sector, uint32_t count) { @@ -752,6 +733,8 @@ int8_t SD_WriteSectors(uint8_t *buff, uint32_t sector, uint32_t count) return 0; } +#if _FS_READONLY == 0 + DRESULT disk_write ( BYTE drv, /* Physical drive number (0) */ const BYTE *buff, /* Pointer to the data to be written */ @@ -793,7 +776,6 @@ DRESULT disk_write ( /* Miscellaneous Functions */ /*-----------------------------------------------------------------------*/ -#if (STM32_SD_DISK_IOCTRL == 1) DRESULT disk_ioctl ( BYTE drv, /* Physical drive number (0) */ BYTE ctrl, /* Control code */ @@ -919,7 +901,6 @@ DRESULT disk_ioctl ( return res; } -#endif /* _USE_IOCTL != 0 */ /*-----------------------------------------------------------------------*/ @@ -966,7 +947,16 @@ FATFS g_FATFS_Obj; FIL g_telemetryFile = {0}; #endif -void sdInit() +#if defined(BOOT) +void sdInit(void) +{ + if (f_mount(0, &g_FATFS_Obj) == FR_OK) { + f_chdir("/"); + } +} +#else +// TODO shouldn't be there! +void sdInit(void) { if (f_mount(0, &g_FATFS_Obj) == FR_OK) { referenceSystemAudioFiles(); @@ -989,6 +979,7 @@ void sdDone() f_mount(0, 0); // unmount SD } } +#endif uint32_t sdMounted() { diff --git a/radio/src/targets/taranis/hal.h b/radio/src/targets/taranis/hal.h index f559ae171..592feb2c7 100644 --- a/radio/src/targets/taranis/hal.h +++ b/radio/src/targets/taranis/hal.h @@ -307,7 +307,9 @@ #define STM32_SD_DISK_IOCTRL_FORCE 0 //DMA -#define STM32_SD_USE_DMA //Enable the DMA for SD +#if !defined(BOOT) +#define STM32_SD_USE_DMA //Enable the DMA for SD +#endif #ifdef STM32_SD_USE_DMA #define DMA_Channel_SPI_SD_RX DMA1_Stream3 diff --git a/radio/src/targets/taranis/i2c.c b/radio/src/targets/taranis/i2c.c index df9b616c4..91bd70cbe 100644 --- a/radio/src/targets/taranis/i2c.c +++ b/radio/src/targets/taranis/i2c.c @@ -10,7 +10,7 @@ ****************************************************************************** */ -#include "../opentx.h" +#include "board_taranis.h" #define I2C_delay() delay_01us(100); @@ -44,7 +44,7 @@ static void I2C_GPIO_Configuration(void) SCL_H; } -short I2C_START() +short I2C_START(void) { SDA_H; I2C_delay(); @@ -59,7 +59,7 @@ short I2C_START() return 1; } -void I2C_STOP() +void I2C_STOP(void) { SCL_L; I2C_delay(); @@ -71,7 +71,7 @@ void I2C_STOP() I2C_delay(); } -void I2C_ACK() +void I2C_ACK(void) { SCL_L; I2C_delay(); @@ -82,7 +82,8 @@ void I2C_ACK() SCL_L; I2C_delay(); } -void I2C_NO_ACK() + +void I2C_NO_ACK(void) { SCL_L; I2C_delay(); @@ -94,7 +95,7 @@ void I2C_NO_ACK() I2C_delay(); } -short I2C_WAIT_ACK() +short I2C_WAIT_ACK(void) { short i=50; SCL_L; @@ -103,7 +104,7 @@ short I2C_WAIT_ACK() I2C_delay(); SCL_H; I2C_delay(); - while(i) { + while (i) { if(SDA_read) { I2C_delay(); i--; @@ -138,7 +139,7 @@ void I2C_SEND_DATA(char SendByte) I2C_delay(); } -char I2C_READ() +char I2C_READ(void) { short i=8; char ReceiveByte=0; @@ -158,7 +159,7 @@ char I2C_READ() return ReceiveByte; } -void I2C_EE_Init() +void I2C_EE_Init(void) { /* GPIO Periph clock enable */ RCC_AHB1PeriphClockCmd(I2C_EE_GPIO_CLK, ENABLE); diff --git a/radio/src/targets/taranis/i2c.h b/radio/src/targets/taranis/i2c.h index b872dbc7f..75f75e7e2 100644 --- a/radio/src/targets/taranis/i2c.h +++ b/radio/src/targets/taranis/i2c.h @@ -33,6 +33,10 @@ #define WP_H do{I2C_EE_WP_GPIO->BSRRL = I2C_EE_WP;}while(0) #define WP_L do{I2C_EE_WP_GPIO->BSRRH = I2C_EE_WP;}while(0) +#ifdef __cplusplus +extern "C" { +#endif + /* Exported functions ------------------------------------------------------- */ void I2C_EE_Init(void); void I2C_EE_ByteWrite(uint8_t* pBuffer, uint16_t WriteAddr); @@ -42,7 +46,11 @@ void I2C_EE_BufferRead(uint8_t* pBuffer, uint16_t ReadAddr, uint16_t NumByteToRe void I2C_EE_WaitEepromStandbyState(void); void I2C_set_volume(register uint8_t volume); -uint8_t I2C_read_volume(); +uint8_t I2C_read_volume(void); + +#ifdef __cplusplus +} +#endif #endif /* __I2C_EE_H */ diff --git a/radio/src/targets/taranis/lcd_driver.cpp b/radio/src/targets/taranis/lcd_driver.cpp index 991fb952b..e9e3c1129 100644 --- a/radio/src/targets/taranis/lcd_driver.cpp +++ b/radio/src/targets/taranis/lcd_driver.cpp @@ -9,11 +9,11 @@ ****************************************************************************** */ -#include "../opentx.h" +#include "../../opentx.h" #define WriteData(x) AspiData(x) #define WriteCommand(x) AspiCmd(x) -#define CONTRAST_OFS 5 +#define CONTRAST_OFS 5 static void LCD_Init() { @@ -21,7 +21,11 @@ static void LCD_Init() AspiCmd(0x25); //Temperature compensation curve definition: 0x25 = -0.05%/oC AspiCmd(0xEA); //set bias=1/10 :Command table NO.27 AspiCmd(0x81); //Set Vop - AspiCmd(g_eeGeneral.contrast+CONTRAST_OFS); //0--255 +#if defined(BOOT) + AspiCmd(CONTRAST_OFS+25); +#else + AspiCmd(CONTRAST_OFS+g_eeGeneral.contrast); +#endif AspiCmd(0xA6); //inverse display off AspiCmd(0xD1); //SET RGB:Command table NO.21 .SET RGB or BGR. D1=RGB AspiCmd(0xD5); //set color mode 4K and 12bits :Command table NO.22 diff --git a/radio/src/targets/taranis/pwr_driver.cpp b/radio/src/targets/taranis/pwr_driver.c similarity index 92% rename from radio/src/targets/taranis/pwr_driver.cpp rename to radio/src/targets/taranis/pwr_driver.c index dd43832c6..2df7d5d2b 100644 --- a/radio/src/targets/taranis/pwr_driver.cpp +++ b/radio/src/targets/taranis/pwr_driver.c @@ -34,26 +34,8 @@ * */ -#include "../../opentx.h" - -void pwrOff() -{ - GPIO_ResetBits(GPIOPWR,PIN_MCU_PWR); -} - -uint32_t pwrCheck() -{ -#if defined(SIMU) - return e_power_on; -#else - if (GPIO_ReadInputDataBit(GPIOPWR, PIN_PWR_STATUS) == Bit_RESET) - return e_power_on; - else if (usbPlugged()) - return e_power_usb; - else - return e_power_off; -#endif -} +#include "board_taranis.h" +#include "../../pwr.h" void pwrInit() { @@ -101,5 +83,25 @@ void pwrInit() #endif // Soft power ON - GPIO_SetBits(GPIOPWR,PIN_MCU_PWR); + GPIO_SetBits(GPIOPWR, PIN_MCU_PWR); +} + +void pwrOff() +{ + GPIO_ResetBits(GPIOPWR, PIN_MCU_PWR); +} + +// TODO enums should be UPPERCASE +uint32_t pwrCheck() +{ +#if defined(SIMU) + return e_power_on; +#else + if (GPIO_ReadInputDataBit(GPIOPWR, PIN_PWR_STATUS) == Bit_RESET) + return e_power_on; + else if (usbPlugged()) + return e_power_usb; + else + return e_power_off; +#endif } diff --git a/radio/src/targets/taranis/stm32_flash_bl.ld b/radio/src/targets/taranis/stm32_flash_bl.ld new file mode 100644 index 000000000..da01f5785 --- /dev/null +++ b/radio/src/targets/taranis/stm32_flash_bl.ld @@ -0,0 +1,176 @@ +/* +***************************************************************************** +** +** File : stm32_flash.ld +** +** Abstract : Linker script for STM32F205 Device with +** 0.5MByte FLASH, 128KByte SRAM +** +** Set heap size, stack size and stack location according +** to application requirements. +** +** Set memory bank area and size if external memory is used. +** +** Target : STMicroelectronics STM32 +** +** Environment : Atollic TrueSTUDIO(R) +** +** Distribution: The file is distributed “as is,” without any warranty +** of any kind. +** +** (c)Copyright Atollic AB. +** You may use this file as-is or modify it according to the needs of your +** project. Distribution of this file (unmodified or modified) is not +** permitted. Atollic AB permit registered Atollic TrueSTUDIO(R) users the +** rights to distribute the assembled, compiled & linked contents of this +** file as part of an application binary file, provided that it is built +** using the Atollic TrueSTUDIO(R) toolchain. +** +***************************************************************************** +*/ + +/* Entry Point */ +ENTRY(Reset_Handler) + +/* Highest address of the user mode stack */ +_estack = 0x20020000; /* end of 128K SRAM */ + +/* Generate a link error if heap and stack don't fit into RAM */ +_Min_Heap_Size = 0; /* required amount of heap */ +_Min_Stack_Size = 0x200; /* required amount of stack */ + +/* Specify the memory areas */ +MEMORY +{ + FLASH (rx) : ORIGIN = 0x08000000, LENGTH = 512K + RAM (xrw) : ORIGIN = 0x20000000, LENGTH = 128K + MEMORY_B1 (rx) : ORIGIN = 0x60000000, LENGTH = 0K +} + +/* Define output sections */ +SECTIONS +{ + /* The startup code goes first into FLASH */ + + /* The program code and other data goes into FLASH */ + .text : + { + FILL(0xFFFF) + + CREATE_OBJECT_SYMBOLS + + KEEP(*(.isr_boot_vector)) /* Startup code */ + *(.bootrodata) + *(.bootrodata.*) + + . = ALIGN(32768); /* Align the start of the main program */ + _stext = .; /* Provide the name for the start of this section */ + . = ALIGN(4); + KEEP(*(.isr_vector)) /* Startup code */ + *(.text) /* .text sections (code) */ + *(.text*) /* .text* sections (code) */ + *(.rodata) /* .rodata sections (constants, strings, etc.) */ + *(.rodata*) /* .rodata* sections (constants, strings, etc.) */ + *(.glue_7) /* glue arm to thumb code */ + *(.glue_7t) /* glue thumb to arm code */ + *(.eh_frame) + + KEEP (*(.init)) + KEEP (*(.fini)) + + . = ALIGN(4); + _etext = .; /* define a global symbols at end of code */ + } >FLASH + + + .ARM.extab : { *(.ARM.extab* .gnu.linkonce.armextab.*) } >FLASH + .ARM : { + __exidx_start = .; + *(.ARM.exidx*) + __exidx_end = .; + } >FLASH + + .preinit_array : + { + PROVIDE_HIDDEN (__preinit_array_start = .); + KEEP (*(.preinit_array*)) + PROVIDE_HIDDEN (__preinit_array_end = .); + } >FLASH + .init_array : + { + PROVIDE_HIDDEN (__init_array_start = .); + KEEP (*(SORT(.init_array.*))) + KEEP (*(.init_array*)) + PROVIDE_HIDDEN (__init_array_end = .); + } >FLASH + .fini_array : + { + PROVIDE_HIDDEN (__fini_array_start = .); + KEEP (*(.fini_array*)) + KEEP (*(SORT(.fini_array.*))) + PROVIDE_HIDDEN (__fini_array_end = .); + } >FLASH + + /* used by the startup to initialize data */ + _sidata = .; + + /* Initialized data sections goes into RAM, load LMA copy after code */ + .data : AT ( _sidata ) + { + . = ALIGN(4); + _sdata = .; /* create a global symbol at data start */ + *(.data) /* .data sections */ + *(.data*) /* .data* sections */ + + . = ALIGN(4); + _edata = .; /* define a global symbol at data end */ + } >RAM + + /* Uninitialized data section */ + . = ALIGN(4); + .bss : + { + /* This is used by the startup in order to initialize the .bss secion */ + _sbss = .; /* define a global symbol at bss start */ + __bss_start__ = _sbss; + *(.bss) + *(.bss*) + *(COMMON) + + . = ALIGN(4); + _ebss = .; /* define a global symbol at bss end */ + __bss_end__ = _ebss; + } >RAM + + PROVIDE ( end = _ebss ); + PROVIDE ( _end = _ebss ); + + /* User_heap_stack section, used to check that there is enough RAM left */ + ._user_heap_stack : + { + . = ALIGN(4); + . = . + _Min_Heap_Size; + . = . + _Min_Stack_Size; + . = ALIGN(4); + } >RAM + + /* MEMORY_bank1 section, code must be located here explicitly */ + /* Example: extern int foo(void) __attribute__ ((section (".mb1text"))); */ + .memory_b1_text : + { + *(.mb1text) /* .mb1text sections (code) */ + *(.mb1text*) /* .mb1text* sections (code) */ + *(.mb1rodata) /* read-only data (constants) */ + *(.mb1rodata*) + } >MEMORY_B1 + + /* Remove information from the standard libraries */ + /DISCARD/ : + { + libc.a ( * ) + libm.a ( * ) + libgcc.a ( * ) + } + + .ARM.attributes 0 : { *(.ARM.attributes) } +} diff --git a/radio/src/targets/taranis/stm32_ramBoot.ld b/radio/src/targets/taranis/stm32_ramBoot.ld new file mode 100644 index 000000000..d8a0b2e1f --- /dev/null +++ b/radio/src/targets/taranis/stm32_ramBoot.ld @@ -0,0 +1,153 @@ +/* +***************************************************************************** +** +** File : stm32_flashboot.ld +** +** Abstract : Linker script for STM32F205 Device with +** 0.5MByte FLASH, 128KByte SRAM +** +** Set heap size, stack size and stack location according +** to application requirements. +** +** Set memory bank area and size if external memory is used. +** +** Target : STMicroelectronics STM32 +** +***************************************************************************** +*/ + +/* Entry Point */ +ENTRY(Reset_Handler) + +/* Highest address of the user mode stack */ +_estack = 0x20020000; /* end of 128K SRAM */ + +/* Generate a link error if heap and stack don't fit into RAM */ +_Min_Heap_Size = 0; /* required amount of heap */ +_Min_Stack_Size = 0x200; /* required amount of stack */ + +/* Specify the memory areas */ +MEMORY +{ + FLASH (rx) : ORIGIN = 0x08000000, LENGTH = 512K + RAM (xrw) : ORIGIN = 0x20000000, LENGTH = 128K + MEMORY_B1 (rx) : ORIGIN = 0x60000000, LENGTH = 0K +} + +/* Define output sections */ +SECTIONS +{ + /* The startup code goes first into FLASH */ + + /* The program code and other data goes into FLASH */ + .text : + { + . = ALIGN(4); + KEEP(*(.isr_vector)) /* Startup code */ + *(.text) /* .text sections (code) */ + *(.text*) /* .text* sections (code) */ + *(.rodata) /* .rodata sections (constants, strings, etc.) */ + *(.rodata*) /* .rodata* sections (constants, strings, etc.) */ + *(.glue_7) /* glue arm to thumb code */ + *(.glue_7t) /* glue thumb to arm code */ + *(.eh_frame) + + KEEP (*(.init)) + KEEP (*(.fini)) + + . = ALIGN(4); + _etext = .; /* define a global symbols at end of code */ + } >RAM + + + .ARM.extab : { *(.ARM.extab* .gnu.linkonce.armextab.*) } >RAM + .ARM : { + __exidx_start = .; + *(.ARM.exidx*) + __exidx_end = .; + } >RAM + + .preinit_array : + { + PROVIDE_HIDDEN (__preinit_array_start = .); + KEEP (*(.preinit_array*)) + PROVIDE_HIDDEN (__preinit_array_end = .); + } >RAM + .init_array : + { + PROVIDE_HIDDEN (__init_array_start = .); + KEEP (*(SORT(.init_array.*))) + KEEP (*(.init_array*)) + PROVIDE_HIDDEN (__init_array_end = .); + } >RAM + .fini_array : + { + PROVIDE_HIDDEN (__fini_array_start = .); + KEEP (*(.fini_array*)) + KEEP (*(SORT(.fini_array.*))) + PROVIDE_HIDDEN (__fini_array_end = .); + } >RAM + + /* used by the startup to initialize data */ + _sidata = .; + + /* Initialized data sections goes into RAM, load LMA copy after code */ + .data : AT ( _sidata ) + { + . = ALIGN(4); + _sdata = .; /* create a global symbol at data start */ + *(.data) /* .data sections */ + *(.data*) /* .data* sections */ + + . = ALIGN(4); + _edata = .; /* define a global symbol at data end */ + } >RAM + + /* Uninitialized data section */ + . = ALIGN(4); + .bss : + { + /* This is used by the startup in order to initialize the .bss secion */ + _sbss = .; /* define a global symbol at bss start */ + __bss_start__ = _sbss; + *(.bss) + *(.bss*) + *(COMMON) + + . = ALIGN(4); + _ebss = .; /* define a global symbol at bss end */ + __bss_end__ = _ebss; + } >RAM + + PROVIDE ( end = _ebss ); + PROVIDE ( _end = _ebss ); + + /* User_heap_stack section, used to check that there is enough RAM left */ + ._user_heap_stack : + { + . = ALIGN(4); + . = . + _Min_Heap_Size; + . = . + _Min_Stack_Size; + . = ALIGN(4); + } >RAM + + /* MEMORY_bank1 section, code must be located here explicitly */ + /* Example: extern int foo(void) __attribute__ ((section (".mb1text"))); */ + .memory_b1_text : + { + *(.mb1text) /* .mb1text sections (code) */ + *(.mb1text*) /* .mb1text* sections (code) */ + *(.mb1rodata) /* read-only data (constants) */ + *(.mb1rodata*) + } >MEMORY_B1 + + /* Remove information from the standard libraries */ + /DISCARD/ : + { + libc.a ( * ) + libm.a ( * ) + libgcc.a ( * ) + } + + .ARM.attributes 0 : { *(.ARM.attributes) } +} diff --git a/radio/src/targets/taranis/usb_driver.c b/radio/src/targets/taranis/usb_driver.c new file mode 100755 index 000000000..ea9ca3bde --- /dev/null +++ b/radio/src/targets/taranis/usb_driver.c @@ -0,0 +1,61 @@ +/* + * Authors (alphabetical order) + * - Andre Bernet + * - Andreas Weitl + * - Bertrand Songis + * - Bryan J. Rentoul (Gruvin) + * - Cameron Weeks + * - Erez Raviv + * - Gabriel Birkus + * - Jean-Pierre Parisy + * - Karl Szmutny + * - Michael Blandford + * - Michal Hlavinka + * - Pat Mackenzie + * - Philip Moss + * - Rob Thomson + * - Romolo Manfredini + * - Thomas Husterer + * + * opentx is based on code named + * gruvin9x by Bryan J. Rentoul: http://code.google.com/p/gruvin9x/, + * er9x by Erez Raviv: http://code.google.com/p/er9x/, + * and the original (and ongoing) project by + * Thomas Husterer, th9x: http://code.google.com/p/th9x/ + * + * This program is free software; you can redistribute it and/or modify + * it under the terms of the GNU General Public License version 2 as + * published by the Free Software Foundation. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + */ + +#include "board_taranis.h" +#include "STM32_USB-Host-Device_Lib_V2.1.0/Libraries/STM32_USB_OTG_Driver/inc/usb_dcd_int.h" +#include "STM32_USB-Host-Device_Lib_V2.1.0/Libraries/STM32_USB_OTG_Driver/inc/usb_bsp.h" + +int usbPlugged(void) +{ + return GPIO_ReadInputDataBit(GPIOA, PIN_FS_VBUS); +} + +USB_OTG_CORE_HANDLE USB_OTG_dev; + +void OTG_FS_IRQHandler(void) +{ + USBD_OTG_ISR_Handler (&USB_OTG_dev); +} + +void usbInit() +{ + USB_OTG_BSP_Init(&USB_OTG_dev); +} + +void usbStart() +{ + USBD_Init(&USB_OTG_dev, USB_OTG_FS_CORE_ID, &USR_desc, &USBD_MSC_cb, &USR_cb); +} diff --git a/radio/src/targets/taranis/usbd_storage_msd.cpp b/radio/src/targets/taranis/usbd_storage_msd.cpp index a11301c1e..79ddf8619 100644 --- a/radio/src/targets/taranis/usbd_storage_msd.cpp +++ b/radio/src/targets/taranis/usbd_storage_msd.cpp @@ -26,8 +26,8 @@ */ /* Includes ------------------------------------------------------------------*/ -#include "../opentx.h" -#include "../FatFs/diskio.h" +#include "../../opentx.h" +#include "../../FatFs/diskio.h" #include "board_taranis.h" extern "C" { @@ -35,8 +35,6 @@ extern "C" { #include "usbd_msc_mem.h" #include "usb_conf.h" -void eeprom_read_block (void *pointer_ram, uint16_t pointer_eeprom, size_t size); - #define STORAGE_LUN_NBR 2 #define BLOCKSIZE 512 @@ -205,14 +203,11 @@ int8_t STORAGE_Read (uint8_t lun, uint16_t blk_len) { if (lun == 1) { - if (fat12Read(buf, blk_addr, blk_len) != 0) { + if (fat12Read(buf, blk_addr, blk_len) != 0) return -1; - } } else { - if (SD_ReadSectors(buf, - blk_addr, - blk_len) != 0) { + if (SD_ReadSectors(buf, blk_addr, blk_len) != 0) { return -1; } } @@ -240,9 +235,7 @@ int8_t STORAGE_Write (uint8_t lun, return -1; } else { - if (SD_WriteSectors(buf, - blk_addr, - blk_len) != 0) + if (SD_WriteSectors(buf, blk_addr, blk_len) != 0) return -1; } diff --git a/radio/src/targets/taranis/usbd_usr.cpp b/radio/src/targets/taranis/usbd_usr.cpp index 32fedc43c..26187ef41 100644 --- a/radio/src/targets/taranis/usbd_usr.cpp +++ b/radio/src/targets/taranis/usbd_usr.cpp @@ -26,7 +26,7 @@ */ /* Includes ------------------------------------------------------------------*/ -#include "../opentx.h" +#include "../../opentx.h" extern "C" { #include "usbd_usr.h" @@ -119,7 +119,9 @@ void USBD_USR_DeviceConnected (void) */ void USBD_USR_DeviceDisconnected (void) { +#if !defined(BOOT) NVIC_SystemReset(); +#endif } diff --git a/radio/src/translations.cpp b/radio/src/translations.cpp index b003a4336..586c1e3f8 100644 --- a/radio/src/translations.cpp +++ b/radio/src/translations.cpp @@ -114,9 +114,9 @@ const pm_char STR_OPEN9X[] PROGMEM = ISTR(VTRAINERMODES) #endif #if defined(MAVLINK) - ISTR(MAVLINK_BAUDS) - ISTR(MAVLINK_AC_MODES) - ISTR(MAVLINK_AP_MODES) + ISTR(MAVLINK_BAUDS) + ISTR(MAVLINK_AC_MODES) + ISTR(MAVLINK_AP_MODES) #endif ; @@ -496,8 +496,10 @@ const pm_char STR_VIEW_TEXT[] PROGMEM = "View text"; const pm_char STR_VIEW_CHANNELS[] PROGMEM = "View Channels"; const pm_char STR_VIEW_NOTES[] PROGMEM = "View Notes"; const pm_char STR_POTWARNING[] PROGMEM = TR_POTWARNING; + const pm_char STR_PREFLIGHT[] PROGMEM = TR_PREFLIGHT; const pm_char STR_CHECKLIST[] PROGMEM = TR_CHECKLIST; const pm_char STR_UART3MODE[] PROGMEM = TR_UART3MODE; + const pm_char STR_THROTTLE_LABEL[] PROGMEM = TR_THROTTLE_LABEL; #endif #if MENUS_LOCK == 1 @@ -576,126 +578,4 @@ const pm_char STR_VIEW_TEXT[] PROGMEM = "View text"; const pm_char STR_ABOUT_PARENTS_4[] PROGMEM = TR_ABOUT_PARENTS_4; #endif -const pm_uchar font_5x7[] PROGMEM = { -#if defined (CPUARM) -#include "font_05x07.lbm" -#else -#include "font_05x07_avr.lbm" -#endif -#if defined(TRANSLATIONS_DE) -#include "font_de_05x07.lbm" -#elif defined(TRANSLATIONS_CZ) -#include "font_cz_05x07.lbm" -#elif defined(TRANSLATIONS_ES) -#include "font_es_05x07.lbm" -#elif defined(TRANSLATIONS_FI) -#include "font_fi_05x07.lbm" -#elif defined(TRANSLATIONS_FR) -#include "font_fr_05x07.lbm" -#elif defined(TRANSLATIONS_IT) -#include "font_it_05x07.lbm" -#elif defined(TRANSLATIONS_PL) -#include "font_pl_05x07.lbm" -#elif defined(TRANSLATIONS_PT) -#include "font_pt_05x07.lbm" -#elif defined(TRANSLATIONS_SE) -#include "font_se_05x07.lbm" -#endif -}; - -#if !defined(CPUM64) || defined(EXTSTD) -const pm_uchar font_5x7_B[] PROGMEM = { -#include "font_05x07_B_compressed.lbm" -}; -#endif - -const pm_uchar font_10x14[] PROGMEM = { -#include "font_10x14_compressed.lbm" -#if defined(CPUARM) - #if defined(TRANSLATIONS_DE) - #include "font_de_10x14.lbm" - #elif defined(TRANSLATIONS_CZ) - #include "font_cz_10x14.lbm" - #elif defined(TRANSLATIONS_ES) - #include "font_es_10x14.lbm" - #elif defined(TRANSLATIONS_FI) - #include "font_fi_10x14.lbm" - #elif defined(TRANSLATIONS_FR) - #include "font_fr_10x14.lbm" - #elif defined(TRANSLATIONS_IT) - #include "font_it_10x14.lbm" - #elif defined(TRANSLATIONS_PL) - #include "font_pl_10x14.lbm" - #elif defined(TRANSLATIONS_PT) - #include "font_pt_10x14.lbm" - #elif defined(TRANSLATIONS_SE) - #include "font_se_10x14.lbm" - #endif -#endif -}; - -#if defined(CPUARM) -const pm_uchar font_3x5[] PROGMEM = { -#include "font_03x05.lbm" -}; - -const pm_uchar font_4x6[] PROGMEM = { -#include "font_04x06.lbm" -#if defined(TRANSLATIONS_DE) -#include "font_de_04x06.lbm" -#elif defined(TRANSLATIONS_CZ) -#include "font_cz_04x06.lbm" -#elif defined(TRANSLATIONS_ES) -#include "font_es_04x06.lbm" -#elif defined(TRANSLATIONS_FI) -#include "font_fi_04x06.lbm" -#elif defined(TRANSLATIONS_FR) -#include "font_fr_04x06.lbm" -#elif defined(TRANSLATIONS_IT) -#include "font_it_04x06.lbm" -#elif defined(TRANSLATIONS_PL) -#include "font_pl_04x06.lbm" -#elif defined(TRANSLATIONS_PT) -#include "font_pt_04x06.lbm" -#elif defined(TRANSLATIONS_SE) -#include "font_se_04x06.lbm" -#endif -}; - -const pm_uchar font_8x10[] PROGMEM = { -#include "font_08x10.lbm" -#if defined(TRANSLATIONS_DE) -#include "font_de_08x10.lbm" -#elif defined(TRANSLATIONS_CZ) -#include "font_cz_08x10.lbm" -#elif defined(TRANSLATIONS_ES) -#include "font_es_08x10.lbm" -#elif defined(TRANSLATIONS_FI) -#include "font_fi_08x10.lbm" -#elif defined(TRANSLATIONS_FR) -#include "font_fr_08x10.lbm" -#elif defined(TRANSLATIONS_IT) -#include "font_it_08x10.lbm" -#elif defined(TRANSLATIONS_PL) -#include "font_pl_08x10.lbm" -#elif defined(TRANSLATIONS_PT) -#include "font_pt_08x10.lbm" -#elif defined(TRANSLATIONS_SE) -#include "font_se_08x10.lbm" -#endif -}; - -const pm_uchar font_4x6_extra[] PROGMEM = { -#include "font_04x06_extra.lbm" -}; - -const pm_uchar font_5x7_extra[] PROGMEM = { -#include "font_05x07_extra.lbm" -}; - -const pm_uchar font_10x14_extra[] PROGMEM = { -#include "font_10x14_extra.lbm" -}; - -#endif diff --git a/radio/src/translations.h b/radio/src/translations.h index 1f46fcb0a..da9098734 100644 --- a/radio/src/translations.h +++ b/radio/src/translations.h @@ -73,9 +73,9 @@ #define EOFS(x) ( OFS_##x + sizeof(TR_##x) ) #if LCD_W >= 212 - #define TR(x,y) y + #define TR(x, y) y #else - #define TR(x,y) x + #define TR(x, y) x #endif // The non-0-terminated-strings @@ -547,21 +547,6 @@ extern const pm_char STR_RESET_BTN[]; #define STR_UPDATE_LIST STR_DELAYDOWN #endif -extern const pm_uchar font_5x7[]; -extern const pm_uchar font_10x14[]; -#if !defined(CPUM64) || defined(EXTSTD) -extern const pm_uchar font_5x7_B[]; -#endif - -#if defined(CPUARM) -extern const pm_uchar font_3x5[]; -extern const pm_uchar font_4x6[]; -extern const pm_uchar font_8x10[]; -extern const pm_uchar font_5x7_extra[]; -extern const pm_uchar font_10x14_extra[]; -extern const pm_uchar font_4x6_extra[]; -#endif - extern const pm_char STR_WARNING[]; extern const pm_char STR_EEPROMWARN[]; extern const pm_char STR_THROTTLEWARN[]; @@ -611,7 +596,7 @@ extern const pm_char STR_SD_SECTORS[]; extern const pm_char STR_SD_SIZE[]; extern const pm_char STR_TYPE[]; extern const pm_char STR_GLOBAL_VARS[]; -extern const pm_char STR_GLOBAL_V[]; +extern const pm_char STR_GLOBAL_V[]; extern const pm_char STR_GLOBAL_VAR[]; extern const pm_char STR_OWN[]; extern const pm_char STR_ROTARY_ENCODER[]; @@ -687,8 +672,10 @@ extern const pm_char STR_VIEW_TEXT[]; extern const pm_char STR_VIEW_CHANNELS[]; extern const pm_char STR_VIEW_NOTES[]; extern const pm_char STR_POTWARNING[]; + extern const pm_char STR_PREFLIGHT[]; extern const pm_char STR_CHECKLIST[]; extern const pm_char STR_UART3MODE[]; + extern const pm_char STR_THROTTLE_LABEL[]; #endif #if MENUS_LOCK == 1 diff --git a/radio/src/translations/cz.h.txt b/radio/src/translations/cz.h.txt index 96504d9a1..dbe10d791 100644 --- a/radio/src/translations/cz.h.txt +++ b/radio/src/translations/cz.h.txt @@ -72,7 +72,7 @@ #define TR_UART3MODES "OFF\0 ""S-Port Mirror\0 ""Debug\0 " #define LEN_POTTYPES "\017" -#define TR_POTTYPES "Pot\0 ""Multipos Switch" +#define TR_POTTYPES "None\0 ""Pot\0 ""Multipos Switch" #define LEN_DATETIME "\006" #define TR_DATETIME "DATUM:""ČAS: " @@ -330,7 +330,7 @@ #define TR_VTEMPLATES "Smazat mixy\0\0""Zákl. 4kanál\0""Sticky-T-Cut\0""V-Tail \0""Elevon\\Delta\0""eCCPM \0""Heli Setup \0""Servo Test \0" #define LEN_VSWASHTYPE "\004" -#define TR_VSWASHTYPE "--- ""120 ""120X""140 ""90\0" +#define TR_VSWASHTYPE "---\0""120\0""120X""140\0""90\0" #define LEN_VKEYS "\005" #define TR_VKEYS TR("Menu\0""Exit\0""Dolů\0""Nhoru""Vprvo""Vlevo", "Menu\0""Exit\0""Enter""Page\0""Plus\0""Mínus") @@ -445,8 +445,8 @@ #define TR_ELIMITS TR("Limit+25%", "Kanál +/- 125%") #define TR_ETRIMS TR("širšíTrim", "Široký trim") #define TR_TRIMINC TR("KrokTrimu", "Krok trimu") -#define TR_TTRACE TR("StopaPlyn", "Stopař plynu") -#define TR_TTRIM TR("TrimPlynu", "TrimPlyn-volnoběh") +#define TR_TTRACE TR("StopaPlyn", INDENT "Stopař plynu") +#define TR_TTRIM TR("TrimPlynu", INDENT "Trim-volnoběh") #define TR_BEEPCTR "(\043)Středy" #define TR_PROTO INDENT"Protokol" #define TR_PPMFRAME "PPM frame" @@ -509,7 +509,8 @@ #define TR_MEMORYWARNING INDENT"Plná pamět'" #define TR_ALARMWARNING INDENT"Vypnutý zvuk" #define TR_RENAVIG "Navig. RotEnc" -#define TR_THROTTLEREVERSE TR("ReversPlyn", "Revers plynu") +#define TR_THROTTLE_LABEL "Plyn" +#define TR_THROTTLEREVERSE TR("ReversPlyn", INDENT"Revers plynu") #define TR_MINUTEBEEP TR(INDENT"Minuta", INDENT"Oznamovat minuty") #define TR_BEEPCOUNTDOWN INDENT"Odpočet" #define TR_PERSISTENT INDENT"Trvalé" @@ -518,9 +519,9 @@ #define TR_BLONBRIGHTNESS INDENT"Jas Zap." #define TR_BLOFFBRIGHTNESS INDENT"Jas Vyp." #define TR_SPLASHSCREEN "úvodníLogo" -#define TR_THROTTLEWARNING "(\043)Plyn" -#define TR_SWITCHWARNING "(\043)Spínače" -#define TR_POTWARNING TR("Pot Warn.","Pot Warning") +#define TR_THROTTLEWARNING TR("(\043)Plyn", INDENT "(\043)Plyn") +#define TR_SWITCHWARNING TR("(\043)Spínače", INDENT "(\043)Spínače") +#define TR_POTWARNING TR("Pot Warn.", INDENT "Pot Warning") #define TR_TIMEZONE "časové pásmo" #define TR_RXCHANNELORD TR("Pořadí kanálů", "Výchozí pořadí kanálů") #define TR_SLAVE "Podřízený" @@ -715,7 +716,8 @@ #define TR_LOWALARM INDENT "Nízký Alarm" #define TR_CRITICALALARM INDENT "Kritický Alarm" #define TR_PERSISTENT_MAH INDENT "Store mAh" -#define TR_CHECKLIST "Display Checklist" +#define TR_PREFLIGHT "Preflight Checks" +#define TR_CHECKLIST INDENT "Display Checklist" #define TR_FAS_OFFSET TR(INDENT "FAS Ofs", INDENT "FAS Offset") #define TR_UART3MODE "Serial port" diff --git a/radio/src/translations/de.h.txt b/radio/src/translations/de.h.txt index 10706d1bc..31ef5569e 100644 --- a/radio/src/translations/de.h.txt +++ b/radio/src/translations/de.h.txt @@ -69,7 +69,7 @@ #define TR_UART3MODES "AUS\0 ""S-Port Data Out\0""Debug\0 " #define LEN_POTTYPES "\017" -#define TR_POTTYPES "Poti\0 ""Stufen-Schalter " +#define TR_POTTYPES "None\0 ""Poti\0 ""Stufen-Schalter " #define LEN_DATETIME "\005" #define TR_DATETIME "DATE:""ZEIT:" @@ -447,8 +447,8 @@ #define TR_ELIMITS TR("Erw.Limit","Erweit. Limits") #define TR_ETRIMS TR("Erw.Trims","Erweit. Trimmung") #define TR_TRIMINC TR("Trim Schr.","Trimm Schritte") -#define TR_TTRACE TR("Gasquelle","Gas Verfolgung") -#define TR_TTRIM TR("Gastrim","Gas Trimmung") +#define TR_TTRACE TR("Gasquelle", INDENT "Gas Verfolgung") +#define TR_TTRIM TR("Gastrim", INDENT "Gas Trimmung") #define TR_BEEPCTR TR("Mitt.Piep","Mittelst. Pieps") #define TR_PROTO TR(INDENT"Proto.",INDENT"Protokoll") #define TR_PPMFRAME "PPM Einst." @@ -511,7 +511,8 @@ #define TR_MEMORYWARNING INDENT"Speicher voll" #define TR_ALARMWARNING INDENT"Ton aus" #define TR_RENAVIG "Drehgeb. Navig." -#define TR_THROTTLEREVERSE TR("Gas invers", "Vollgas hinten?") //Änderung wg TH9x, Taranis +#define TR_THROTTLE_LABEL "Gas" +#define TR_THROTTLEREVERSE TR("Gas invers", INDENT "Vollgas hinten?") //Änderung wg TH9x, Taranis #define TR_MINUTEBEEP TR(INDENT"Minute",INDENT"Jede Minute") #define TR_BEEPCOUNTDOWN INDENT"Countdown" #define TR_PERSISTENT TR(INDENT"M-Zeit",INDENT"Modell Zeit") @@ -520,9 +521,9 @@ #define TR_BLONBRIGHTNESS INDENT"An Helligkeit" #define TR_BLOFFBRIGHTNESS INDENT"Aus Helligkeit" #define TR_SPLASHSCREEN "Startbild" -#define TR_THROTTLEWARNING "Gas Alarm" -#define TR_SWITCHWARNING TR("Sch. Alarm","Schalter Alarm") -#define TR_POTWARNING TR("Pot Warn.","Poti Warnung") +#define TR_THROTTLEWARNING TR("Gas Alarm", INDENT "Gas Alarm") +#define TR_SWITCHWARNING TR("Sch. Alarm", INDENT "Schalter Alarm") +#define TR_POTWARNING TR("Pot Warn.", INDENT "Poti Warnung") #define TR_TIMEZONE TR("Zeitzone","GPS Zeit Zone") #define TR_RXCHANNELORD TR("Kanalanordnung","Kanalvoreinstellung") #define TR_SLAVE "Schüler PPM1-8 als Ausgang" @@ -717,7 +718,8 @@ #define TR_LOWALARM INDENT "Low Alarm" #define TR_CRITICALALARM INDENT "Kritisch Alarm" #define TR_PERSISTENT_MAH INDENT "Speichern mAh" -#define TR_CHECKLIST "Display Checklist" +#define TR_PREFLIGHT "Preflight Checks" +#define TR_CHECKLIST INDENT "Display Checklist" #define TR_FAS_OFFSET TR(INDENT "FAS Ofs", INDENT "FAS Offset") #define TR_UART3MODE "Serial Port" diff --git a/radio/src/translations/en.h.txt b/radio/src/translations/en.h.txt index d2cced3eb..8c7b85a81 100644 --- a/radio/src/translations/en.h.txt +++ b/radio/src/translations/en.h.txt @@ -455,8 +455,8 @@ #define TR_ELIMITS TR("E.Limits", "Extended Limits") #define TR_ETRIMS TR("E.Trims", "Extended Trims") #define TR_TRIMINC "Trim Step" -#define TR_TTRACE TR("T-Source", "Throttle Source") -#define TR_TTRIM TR("T-Trim", "Throttle Trim") +#define TR_TTRACE TR("T-Source", INDENT "Timer Source") +#define TR_TTRIM TR("T-Trim", INDENT "Trim Idle Only") #define TR_BEEPCTR TR("Ctr Beep", "Center Beep") #define TR_PROTO TR(INDENT "Proto", INDENT "Protocol") #define TR_PPMFRAME TR("PPM frame", INDENT "PPM frame") @@ -519,7 +519,8 @@ #define TR_MEMORYWARNING INDENT "Memory Low" #define TR_ALARMWARNING INDENT "Sound Off" #define TR_RENAVIG "RotEnc Navig" -#define TR_THROTTLEREVERSE TR("T-Reverse", "Throttle reverse") +#define TR_THROTTLE_LABEL "Throttle" +#define TR_THROTTLEREVERSE TR("T-Reverse", INDENT "Reverse") #define TR_MINUTEBEEP TR(INDENT "Minute",INDENT "Minute call") #define TR_BEEPCOUNTDOWN INDENT "Countdown" #define TR_PERSISTENT TR(INDENT "Persist.",INDENT "Persistent") @@ -528,9 +529,9 @@ #define TR_BLONBRIGHTNESS INDENT "ON Brightness" #define TR_BLOFFBRIGHTNESS INDENT "OFF Brightness" #define TR_SPLASHSCREEN "Splash screen" -#define TR_THROTTLEWARNING TR("T-Warning","Throttle Warning") -#define TR_SWITCHWARNING TR("S-Warning","Switch Warning") -#define TR_POTWARNING TR("Pot Warn.","Pot Warning") +#define TR_THROTTLEWARNING TR("T-Warning", INDENT "Throttle State") +#define TR_SWITCHWARNING TR("S-Warning", INDENT "Switch Positions") +#define TR_POTWARNING TR("Pot Warn.", INDENT "Pot Positions") #define TR_TIMEZONE TR("Time Zone","GPS Time zone") #define TR_RXCHANNELORD TR("Rx Channel Ord","Default channel order") #define TR_SLAVE "Slave" @@ -725,7 +726,8 @@ #define TR_LOWALARM INDENT "Low Alarm" #define TR_CRITICALALARM INDENT "Critical Alarm" #define TR_PERSISTENT_MAH INDENT "Store mAh" -#define TR_CHECKLIST "Display Checklist" +#define TR_PREFLIGHT "Preflight Checks" +#define TR_CHECKLIST INDENT "Display Checklist" #define TR_FAS_OFFSET TR(INDENT "FAS Ofs", INDENT "FAS Offset") #define TR_UART3MODE "Serial port" diff --git a/radio/src/translations/es.h.txt b/radio/src/translations/es.h.txt index d0a5630cc..a54fd03f8 100644 --- a/radio/src/translations/es.h.txt +++ b/radio/src/translations/es.h.txt @@ -72,7 +72,7 @@ #define TR_UART3MODES "OFF\0 ""S-Port Mirror\0 ""Debug\0 " #define LEN_POTTYPES "\017" -#define TR_POTTYPES "Pot\0 ""Multipos Switch" +#define TR_POTTYPES "None\0 ""Pot\0 ""Multipos Switch" #define LEN_DATETIME "\005" #define TR_DATETIME "DATA:""HORA:" @@ -445,8 +445,8 @@ #define TR_ELIMITS TR("E.Limite","Ampliar Limites") #define TR_ETRIMS TR("E.Trims","Ampliar Trims") #define TR_TRIMINC "Paso Trim" -#define TR_TTRACE TR("Fuente-A","Fuente Acelerad") -#define TR_TTRIM TR("Trim-A","Trim Acelerad") +#define TR_TTRACE TR("Fuente-A", INDENT "Fuente Acelerad") +#define TR_TTRIM TR("Trim-A", INDENT "Trim Acelerad") #define TR_BEEPCTR TR("Ctr Beep","Center Beep") #define TR_PROTO TR(INDENT"Proto",INDENT"Protocol") #define TR_PPMFRAME "Trama PPM" @@ -509,7 +509,8 @@ #define TR_MEMORYWARNING INDENT"Memoria Baja" #define TR_ALARMWARNING INDENT"Sin Sonido" #define TR_RENAVIG "RotEnc Navig" -#define TR_THROTTLEREVERSE TR("Invert_Acel", "Invertir Acel.") +#define TR_THROTTLE_LABEL "Throttle" +#define TR_THROTTLEREVERSE TR("Invert_Acel", INDENT "Invertir Acel.") #define TR_MINUTEBEEP TR(INDENT"Minuto",INDENT"Cada Minuto") #define TR_BEEPCOUNTDOWN INDENT"Cuentaatras" #define TR_PERSISTENT TR(INDENT"Persist.",INDENT"Persistente") @@ -518,9 +519,9 @@ #define TR_BLONBRIGHTNESS INDENT"MAS Brillo" #define TR_BLOFFBRIGHTNESS INDENT"MENOS Brillo" #define TR_SPLASHSCREEN "Ptalla.inicio" -#define TR_THROTTLEWARNING TR("Aviso-A", "Aviso Acelerador") -#define TR_SWITCHWARNING TR("Aviso-I", "Aviso Intrptor") -#define TR_POTWARNING TR("Pot Warn.","Pot Warning") +#define TR_THROTTLEWARNING TR("Aviso-A", INDENT "Aviso Acelerador") +#define TR_SWITCHWARNING TR("Aviso-I", INDENT "Aviso Intrptor") +#define TR_POTWARNING TR("Pot Warn.", INDENT "Pot Warning") #define TR_TIMEZONE TR("Zona Hora", "GPS Zona Hora") #define TR_RXCHANNELORD TR("Rx Orden canal", "Orden habitual canales") #define TR_SLAVE "Esclavo" @@ -715,7 +716,8 @@ #define TR_LOWALARM INDENT "Alarma baja" #define TR_CRITICALALARM INDENT "Alarma Critica" #define TR_PERSISTENT_MAH INDENT "Valor mAh" -#define TR_CHECKLIST "Display Checklist" +#define TR_PREFLIGHT "Preflight Checks" +#define TR_CHECKLIST INDENT "Display Checklist" #define TR_FAS_OFFSET TR(INDENT "FAS Ofs", INDENT "FAS Offset") #define TR_UART3MODE "Serial port" diff --git a/radio/src/translations/fi.h.txt b/radio/src/translations/fi.h.txt index 26ed4bc58..53543c3bc 100644 --- a/radio/src/translations/fi.h.txt +++ b/radio/src/translations/fi.h.txt @@ -72,7 +72,7 @@ #define TR_UART3MODES "POIS\0 ""S-Port Pelik\0 ""Debug\0 " #define LEN_POTTYPES "\017" -#define TR_POTTYPES "Potikka\0 ""Monias. Kytkin\0" +#define TR_POTTYPES "None\0 ""Potikka\0 ""Monias. Kytkin\0" #define LEN_DATETIME "\005" #define TR_DATETIME "PÄIV:""AIKA:" @@ -445,8 +445,8 @@ #define TR_ELIMITS TR("E.Limits", "Extended Limits") #define TR_ETRIMS TR("E.Trims", "Extended Trims") #define TR_TRIMINC "Trim Step" -#define TR_TTRACE TR("T-Source", "Throttle Source") -#define TR_TTRIM TR("T-Trim", "Throttle Trim") +#define TR_TTRACE TR("T-Source", INDENT "Throttle Source") +#define TR_TTRIM TR("T-Trim", INDENT "Throttle Trim") #define TR_BEEPCTR TR("Ctr Beep", "Center Beep") #define TR_PROTO TR(INDENT "Proto", INDENT "Protocol") #define TR_PPMFRAME TR("PPM frame", INDENT "PPM frame") @@ -509,7 +509,8 @@ #define TR_MEMORYWARNING INDENT"Memory Low" #define TR_ALARMWARNING INDENT"Sound Off" #define TR_RENAVIG "RotEnc Navig" -#define TR_THROTTLEREVERSE TR("T-Reverse", "Throttle reverse") +#define TR_THROTTLE_LABEL "Throttle" +#define TR_THROTTLEREVERSE TR("T-Reverse", INDENT "Throttle reverse") #define TR_MINUTEBEEP TR(INDENT"Minute",INDENT"Minute call") #define TR_BEEPCOUNTDOWN INDENT"Countdown" #define TR_PERSISTENT TR(INDENT"Persist.",INDENT"Persistent") @@ -518,9 +519,9 @@ #define TR_BLONBRIGHTNESS INDENT"ON Brightness" #define TR_BLOFFBRIGHTNESS INDENT"OFF Brightness" #define TR_SPLASHSCREEN "Splash screen" -#define TR_THROTTLEWARNING TR("T-Warning","Throttle Warning") -#define TR_SWITCHWARNING TR("S-Warning","Switch Warning") -#define TR_POTWARNING TR("Pot Warn.","Pot Warning") +#define TR_THROTTLEWARNING TR("T-Warning", INDENT "Throttle Warning") +#define TR_SWITCHWARNING TR("S-Warning", INDENT "Switch Warning") +#define TR_POTWARNING TR("Pot Warn.", INDENT "Pot Warning") #define TR_TIMEZONE TR("Time Zone","GPS Time zone") #define TR_RXCHANNELORD TR("Rx Channel Ord","Default channel order") #define TR_SLAVE "Slave" @@ -715,7 +716,8 @@ #define TR_LOWALARM INDENT "Low Alarm" #define TR_CRITICALALARM INDENT "Critical Alarm" #define TR_PERSISTENT_MAH INDENT "Store mAh" -#define TR_CHECKLIST "Display Checklist" +#define TR_PREFLIGHT "Preflight Checks" +#define TR_CHECKLIST INDENT "Display Checklist" #define TR_FAS_OFFSET TR(INDENT "FAS Ofs", INDENT "FAS Offset") #define TR_UART3MODE "Serial port" diff --git a/radio/src/translations/fr.h.txt b/radio/src/translations/fr.h.txt index b28416cee..64c9e8225 100644 --- a/radio/src/translations/fr.h.txt +++ b/radio/src/translations/fr.h.txt @@ -83,8 +83,8 @@ #define LEN_VTRIMINC TR("\006","\013") #define TR_VTRIMINC TR("Expo\0 ""ExFin\0""Fin\0 ""Moyen\0""Gros\0 ","Exponentiel""Extra Fin\0 ""Fin\0 ""Moyen\0 ""Grossier\0 ") -#define LEN_VBEEPCOUNTDOWN "\006" -#define TR_VBEEPCOUNTDOWN "SilentBeeps\0Voice\0" +#define LEN_VBEEPCOUNTDOWN "\007" +#define TR_VBEEPCOUNTDOWN "Silence""Bips\0 ""Voix\0 " #define LEN_RETA123 "\001" @@ -149,7 +149,7 @@ #if defined(PCBTARANIS) #define TR_CSWTIMER "Tempo" - #define TR_CSWSTICKY "Bist." + #define TR_CSWSTICKY "Bistb" #define TR_CSWRANGE "Plage" #define TR_CSWSTAY "Flanc" #else @@ -172,9 +172,9 @@ #define LEN_VCSWFUNC "\005" #if defined(CPUARM) -#define TR_VCSWFUNC "---\0 " TR_CSWEQUAL "a{x\0 ""a>x\0 ""ax""|a|b\0 ""ax\0 ""ax""|a|b\0 ""ax\0 ""ax""|a|b\0 ""ax\0 ""ax""|a|b\0 ""a + + + + diff --git a/speaker/App.xaml.cs b/speaker/App.xaml.cs new file mode 100644 index 000000000..431106446 --- /dev/null +++ b/speaker/App.xaml.cs @@ -0,0 +1,32 @@ +/* This file is part of OpenTX Speaker. + * OpenTX Speaker is free software: you can redistribute it and/or modify + * it under the terms of the GNU General Public License as published by + * the Free Software Foundation, either version 3 of the License, or + * (at your option) any later version. + + * OpenTX Speaker is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + + * You should have received a copy of the GNU General Public License + * along with Foobar. If not, see . + * + * Copyright 2014 Kjell Kernen */ + +using System; +using System.Collections.Generic; +using System.Configuration; +using System.Data; +using System.Linq; +using System.Windows; + +namespace OpenTXspeak +{ + /// + /// Interaction logic for App.xaml + /// + public partial class App : Application + { + } +} diff --git a/speaker/GPLv3_Logo.png b/speaker/GPLv3_Logo.png new file mode 100644 index 000000000..8f2ec4b35 Binary files /dev/null and b/speaker/GPLv3_Logo.png differ diff --git a/speaker/MainWindow.xaml b/speaker/MainWindow.xaml new file mode 100644 index 000000000..9ed94b625 --- /dev/null +++ b/speaker/MainWindow.xaml @@ -0,0 +1,120 @@ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +