From e8ee9c6cd770ea6ad9fc372d54d68d99185691e2 Mon Sep 17 00:00:00 2001 From: Tristan Krause Date: Thu, 27 Jun 2019 16:19:27 +0200 Subject: [PATCH] =?UTF-8?q?aufger=C3=A4umt?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- README.md | 3 +- control/examples/servo/main.cpp | 2 +- control/src/cli.cpp | 4 +- control/src/drv/b15f.cpp | 88 +++++++++++++++++++++------------ control/src/drv/b15f.h | 43 +++++++++++----- 5 files changed, 94 insertions(+), 46 deletions(-) diff --git a/README.md b/README.md index ccb64f4..21931a8 100644 --- a/README.md +++ b/README.md @@ -17,5 +17,6 @@ Die Projekt-Dokumentation befindet sich unter [github pages](https://devfix.gith - [x] Servo ansteuert - [x] Interrupt Counter - [x] mem16 testen -- [ ] autocheck request size +- [x] autocheck request size +- [ ] Raspberry Pi test diff --git a/control/examples/servo/main.cpp b/control/examples/servo/main.cpp index 81cd6dc..408b0d0 100644 --- a/control/examples/servo/main.cpp +++ b/control/examples/servo/main.cpp @@ -1,7 +1,7 @@ #include /* - * Dieses Beispiel steuert einen Servo an PB3 an. + * Dieses Beispiel steuert einen Servo an PB2 an. * */ int main() diff --git a/control/src/cli.cpp b/control/src/cli.cpp index 32ae9ab..bbab408 100644 --- a/control/src/cli.cpp +++ b/control/src/cli.cpp @@ -84,7 +84,6 @@ void init() std::cout << std::endl << "Starte in 3s ..." << std::endl; sleep(3); #endif - B15F::setAbortHandler(&abort_handler); // init all ncurses stuff initscr(); @@ -101,6 +100,9 @@ void init() // set view context View::setWinContext(newwin(WIN_HEIGHT, WIN_WIDTH, 0, 0)); + + // set graphical error handler + B15F::setAbortHandler(&abort_handler); } diff --git a/control/src/drv/b15f.cpp b/control/src/drv/b15f.cpp index a456c5b..f7deca9 100644 --- a/control/src/drv/b15f.cpp +++ b/control/src/drv/b15f.cpp @@ -171,7 +171,6 @@ void B15F::abort(std::exception &ex) errorhandler(ex); else { - std::cerr << "NOTICE: B15F::errorhandler not set" << std::endl; std::cout << ex.what() << std::endl; throw DriverException(ex.what()); } @@ -190,45 +189,51 @@ void B15F::setAbortHandler(errorhandler_t func) * Steuerbefehle für B15 * *************************/ -bool B15F::activateSelfTestMode() +void B15F::activateSelfTestMode() { uint8_t rq[] = { RQ_SELF_TEST }; + + assertRequestLength(rq, RQ_SELF_TEST); usart.transmit(&rq[0], 0, sizeof(rq)); uint8_t aw; usart.receive(&aw, 0, sizeof(aw)); - return aw == MSG_OK; + assertCode(aw, MSG_OK); } -bool B15F::digitalWrite0(uint8_t port) +void B15F::digitalWrite0(uint8_t port) { uint8_t rq[] = { RQ_DIGITAL_WRITE_0, port }; + + assertRequestLength(rq, RQ_DIGITAL_WRITE_0); usart.transmit(&rq[0], 0, sizeof(rq)); uint8_t aw; usart.receive(&aw, 0, sizeof(aw)); - return aw == MSG_OK; + assertCode(aw, MSG_OK); } -bool B15F::digitalWrite1(uint8_t port) +void B15F::digitalWrite1(uint8_t port) { uint8_t rq[] = { RQ_DIGITAL_WRITE_1, port }; + + assertRequestLength(rq, RQ_DIGITAL_WRITE_1); usart.transmit(&rq[0], 0, sizeof(rq)); uint8_t aw; usart.receive(&aw, 0, sizeof(aw)); - return aw == MSG_OK; + assertCode(aw, MSG_OK); } uint8_t B15F::digitalRead0() @@ -238,6 +243,8 @@ uint8_t B15F::digitalRead0() { RQ_DIGITAL_READ_0 }; + + assertRequestLength(rq, RQ_DIGITAL_READ_0); usart.transmit(&rq[0], 0, sizeof(rq)); uint8_t aw; @@ -252,6 +259,8 @@ uint8_t B15F::digitalRead1() { RQ_DIGITAL_READ_1 }; + + assertRequestLength(rq, RQ_DIGITAL_READ_1); usart.transmit(&rq[0], 0, sizeof(rq)); uint8_t aw; @@ -266,6 +275,8 @@ uint8_t B15F::readDipSwitch() { RQ_READ_DIP_SWITCH }; + + assertRequestLength(rq, RQ_READ_DIP_SWITCH); usart.transmit(&rq[0], 0, sizeof(rq)); uint8_t aw; @@ -276,7 +287,7 @@ uint8_t B15F::readDipSwitch() return aw; } -bool B15F::analogWrite0(uint16_t value) +void B15F::analogWrite0(uint16_t value) { uint8_t rq[] = { @@ -284,14 +295,16 @@ bool B15F::analogWrite0(uint16_t value) static_cast(value & 0xFF), static_cast(value >> 8) }; + + assertRequestLength(rq, RQ_ANALOG_WRITE_0); usart.transmit(&rq[0], 0, sizeof(rq)); uint8_t aw; usart.receive(&aw, 0, sizeof(aw)); - return aw == MSG_OK; + assertCode(aw, MSG_OK); } -bool B15F::analogWrite1(uint16_t value) +void B15F::analogWrite1(uint16_t value) { uint8_t rq[] = { @@ -299,11 +312,13 @@ bool B15F::analogWrite1(uint16_t value) static_cast(value & 0xFF), static_cast(value >> 8) }; + + assertRequestLength(rq, RQ_ANALOG_WRITE_1); usart.transmit(&rq[0], 0, sizeof(rq)); uint8_t aw; usart.receive(&aw, 0, sizeof(aw)); - return aw == MSG_OK; + assertCode(aw, MSG_OK); } uint16_t B15F::analogRead(uint8_t channel) @@ -318,6 +333,7 @@ uint16_t B15F::analogRead(uint8_t channel) channel }; + assertRequestLength(rq, RQ_ANALOG_READ); usart.transmit(&rq[0], 0, sizeof(rq)); uint16_t aw; @@ -328,8 +344,7 @@ uint16_t B15F::analogRead(uint8_t channel) return aw; } -void -B15F::analogSequence(uint8_t channel_a, uint16_t *buffer_a, uint32_t offset_a, uint8_t channel_b, uint16_t *buffer_b, +void B15F::analogSequence(uint8_t channel_a, uint16_t *buffer_a, uint32_t offset_a, uint8_t channel_b, uint16_t *buffer_b, uint32_t offset_b, uint16_t start, int16_t delta, uint16_t count) { // prepare pointers @@ -351,6 +366,7 @@ B15F::analogSequence(uint8_t channel_a, uint16_t *buffer_a, uint32_t offset_a, u static_cast(count >> 8) }; + assertRequestLength(rq, RQ_ADC_DAC_STROKE); usart.transmit(&rq[0], 0, sizeof(rq)); for (uint16_t i = 0; i < count; i++) @@ -382,8 +398,7 @@ B15F::analogSequence(uint8_t channel_a, uint16_t *buffer_a, uint32_t offset_a, u uint8_t aw; usart.receive(&aw, 0, sizeof(aw)); - if(aw != MSG_OK) - abort("Sequenz unterbrochen"); + assertCode(aw, MSG_OK); } uint8_t B15F::pwmSetFrequency(uint32_t freq) @@ -399,6 +414,7 @@ uint8_t B15F::pwmSetFrequency(uint32_t freq) static_cast((freq >> 24) & 0xFF) }; + assertRequestLength(rq, RQ_PWM_SET_FREQ); usart.transmit(&rq[0], 0, sizeof(rq)); uint8_t aw; @@ -406,7 +422,7 @@ uint8_t B15F::pwmSetFrequency(uint32_t freq) return aw; } -bool B15F::pwmSetValue(uint8_t value) +void B15F::pwmSetValue(uint8_t value) { usart.clearInputBuffer(); @@ -416,14 +432,15 @@ bool B15F::pwmSetValue(uint8_t value) value }; + assertRequestLength(rq, RQ_PWM_SET_VALUE); usart.transmit(&rq[0], 0, sizeof(rq)); uint8_t aw; usart.receive(&aw, 0, sizeof(aw)); - return aw == MSG_OK; + assertCode(aw, MSG_OK); } -bool B15F::setMem8(volatile uint8_t* adr, uint8_t val) +void B15F::setMem8(volatile uint8_t* adr, uint8_t val) { usart.clearInputBuffer(); @@ -435,11 +452,12 @@ bool B15F::setMem8(volatile uint8_t* adr, uint8_t val) val }; + assertRequestLength(rq, RQ_SET_MEM_8); usart.transmit(&rq[0], 0, sizeof(rq)); uint8_t aw; usart.receive(&aw, 0, sizeof(aw)); - return aw == val; + assertCode(aw, MSG_OK); } uint8_t B15F::getMem8(volatile uint8_t* adr) @@ -453,6 +471,7 @@ uint8_t B15F::getMem8(volatile uint8_t* adr) static_cast(reinterpret_cast(adr) >> 8) }; + assertRequestLength(rq, RQ_GET_MEM_8); usart.transmit(&rq[0], 0, sizeof(rq)); uint8_t aw; @@ -460,7 +479,7 @@ uint8_t B15F::getMem8(volatile uint8_t* adr) return aw; } -bool B15F::setMem16(volatile uint16_t* adr, uint16_t val) +void B15F::setMem16(volatile uint16_t* adr, uint16_t val) { usart.clearInputBuffer(); @@ -473,11 +492,12 @@ bool B15F::setMem16(volatile uint16_t* adr, uint16_t val) static_cast(val >> 8) }; + assertRequestLength(rq, RQ_SET_MEM_16); usart.transmit(&rq[0], 0, sizeof(rq)); uint16_t aw; usart.receive(reinterpret_cast(&aw), 0, sizeof(aw)); - return aw == val; + assertCode(aw, MSG_OK); } uint16_t B15F::getMem16(volatile uint16_t* adr) @@ -491,6 +511,7 @@ uint16_t B15F::getMem16(volatile uint16_t* adr) static_cast(reinterpret_cast(adr) >> 8) }; + assertRequestLength(rq, RQ_GET_MEM_16); usart.transmit(&rq[0], 0, sizeof(rq)); uint16_t aw; @@ -498,9 +519,9 @@ uint16_t B15F::getMem16(volatile uint16_t* adr) return aw; } -bool B15F::setRegister(volatile uint8_t* adr, uint8_t val) +void B15F::setRegister(volatile uint8_t* adr, uint8_t val) { - return setMem8(adr, val); + setMem8(adr, val); } uint8_t B15F::getRegister(volatile uint8_t* adr) @@ -517,6 +538,7 @@ uint16_t* B15F::getInterruptCounterOffset() RQ_COUNTER_OFFSET }; + assertRequestLength(rq, RQ_COUNTER_OFFSET); usart.transmit(&rq[0], 0, sizeof(rq)); uint16_t aw; @@ -533,6 +555,7 @@ void B15F::setServoEnabled(void) RQ_SERVO_ENABLE }; + assertRequestLength(rq, RQ_SERVO_ENABLE); usart.transmit(&rq[0], 0, sizeof(rq)); uint8_t aw; @@ -549,6 +572,7 @@ void B15F::setServoDisabled(void) RQ_SERVO_DISABLE }; + assertRequestLength(rq, RQ_SERVO_DISABLE); usart.transmit(&rq[0], 0, sizeof(rq)); uint8_t aw; @@ -569,7 +593,8 @@ void B15F::setServoPosition(uint16_t pos) static_cast(pos & 0xFF), static_cast(pos >> 8) }; - + + assertRequestLength(rq, RQ_SERVO_SET_POS); usart.transmit(&rq[0], 0, sizeof(rq)); uint8_t aw; @@ -593,7 +618,14 @@ B15F::B15F() void B15F::init() { - std::string device = exec("bash -c 'ls /dev/ttyUSB*'"); +#ifdef __arm__ + // Raspberry Pi serial interface + std::string device = exec("bash -c 'ls /dev/ttyAMA* 2> /dev/null'"); +#else + // normal PC serial interface + std::string device = exec("bash -c 'ls /dev/ttyUSB* 2> /dev/null'"); +#endif + while (device.find(' ') != std::string::npos || device.find('\n') != std::string::npos || device.find('\t') != std::string::npos) device.pop_back(); @@ -635,9 +667,3 @@ void B15F::init() std::cout << PRE << "AVR Firmware Version: " << info[0] << " um " << info[1] << " Uhr (" << info[2] << ")" << std::endl; } - -void B15F::assertCode(uint8_t& code, uint8_t expectation) const -{ - if(code != expectation) - throw DriverException("Ungültige Antwort erhalten: " + std::to_string((int) code) + " (erwartet: " + std::to_string((int) expectation) + ")"); -} diff --git a/control/src/drv/b15f.h b/control/src/drv/b15f.h index 28b410f..65110cf 100644 --- a/control/src/drv/b15f.h +++ b/control/src/drv/b15f.h @@ -130,21 +130,21 @@ public: * WICHTIG: Es darf dabei nichts an den Klemmen angeschlossen sein! * \throws DriverException */ - bool activateSelfTestMode(void); + void activateSelfTestMode(void); /** * Setzt den Wert des digitalen Ausgabeports 0 * \param port Wert für gesamten Port * \throws DriverException */ - bool digitalWrite0(uint8_t); + void digitalWrite0(uint8_t); /** * Setzt den Wert des digitalen Ausgabeports 1 * \param port Wert für gesamten Port * \throws DriverException */ - bool digitalWrite1(uint8_t); + void digitalWrite1(uint8_t); /** * Liest den Wert des digitalen Eingabeports 0 @@ -172,14 +172,14 @@ public: * \param port 10-Bit Wert * \throws DriverException */ - bool analogWrite0(uint16_t port); + void analogWrite0(uint16_t port); /** * Setzt den Wert des Digital-Analog-Converters (DAC / DAU) 1 * \param port 10-Bit Wert * \throws DriverException */ - bool analogWrite1(uint16_t port); + void analogWrite1(uint16_t port); /** * Liest den Wert des Analog-Digital-Converters (ADC / ADU) @@ -221,7 +221,7 @@ public: * \param value PWM Wert [0..TOP] * \throws DriverException */ - bool pwmSetValue(uint8_t value); + void pwmSetValue(uint8_t value); /** * Setzt direkt den Wert einer MCU Speicherzelle der Größe 8 Bit. @@ -231,7 +231,7 @@ public: * \param val Neuer Wert für die Zelle * \return true, falls Vorgang erfolgreich */ - bool setMem8(volatile uint8_t* adr, uint8_t val); + void setMem8(volatile uint8_t* adr, uint8_t val); /** * Liefert den Wert einer MCU Speicherzelle der Größe 8 Bit. @@ -247,9 +247,9 @@ public: * *Wichtig:* bei einer falschen Adresse kann das Board 15 ernsthaften Schaden nehmen! * \param adr Speicheradresse * \param val Neuer Wert für die Zelle - * \return true, falls Vorgang erfolgreich + * \throws DriverException */ - bool setMem16(volatile uint16_t* adr, uint16_t val); + void setMem16(volatile uint16_t* adr, uint16_t val); /** * Liefert den Wert einer MCU Speicherzelle der Größe 16 Bit. @@ -264,9 +264,9 @@ public: * *Wichtig:* bei einer falschen Adresse kann das Board 15 ernsthaften Schaden nehmen! * \param adr Speicheradresse * \param val Neuer Wert für das Register - * \return true, falls Vorgang erfolgreich + * \throws DriverException */ - bool setRegister(volatile uint8_t* adr, uint8_t val); + void setRegister(volatile uint8_t* adr, uint8_t val); /** * Diese Funktion ist ein Alias für getMem8(). @@ -283,17 +283,20 @@ public: /** * Aktiviert das Servo Signal an PB2 und Initialisiert es mit 1,5ms Pulselänge. + * \throws DriverException */ void setServoEnabled(void); /** * Deaktiviert das Servo Signal an PB2. + * \throws DriverException */ void setServoDisabled(void); /** * Setzt die Pulselänge des Servo Signals und damit die Position. * \param pos Pulselänge des Signals in Mikrosekunden + * \throws DriverException */ void setServoPosition(uint16_t pos); @@ -326,7 +329,23 @@ private: * Wirft eine Exception, falls der Code ungleich dem erwarteten Wert ist. * \throws DriverException */ - void assertCode(uint8_t& code, uint8_t expectation) const; + template + void assertCode(CodeType& code, ExpectationType expectation) const + { + if(code != static_cast(expectation)) + throw DriverException("Ungültige Antwort erhalten: " + std::to_string((int) code) + " (erwartet: " + std::to_string((int) expectation) + ")"); + } + + /** + * Wirft eine Exception, falls die Request die falsche Länge hat. + * \throws DriverException + */ + template + void assertRequestLength(uint8_t (&)[RequestLength], uint8_t rq_num) + { + if(RequestLength != rq_len[rq_num]) + throw DriverException("Ungültige Request Länge: " + std::to_string(RequestLength) + " (erwartet: " + std::to_string(rq_len[rq_num]) + ")"); + } USART usart; //!< USART Instanz für serielle Verbindung static B15F* instance; //!< private Instanz für Singleton