AskSin++ Library

Begonnen von papa, 08 September 2016, 11:11:25

Vorheriges Thema - Nächstes Thema

papa

Das wäre wirklich super.

Im Prinzip würde es ja reichen, wenn der Code auf der Console ausgegeben wird. Man kann sich das ja dann leicht in eine Datei umleiten oder kopieren oder ....

Zitat
Für den  hm-es-tx habe ich für die folgendne Felder kein xml gefunden - hat sich was am xml geändert und ich habe eine alten Stand des xml?

Die stehen ganz oben

<paramset type="MASTER" id="powermeter_iec_dev_master">
<parameter id="LOCAL_RESET_DISABLE">
<logical type="boolean" default="false"/>
<physical type="integer" interface="config" list="0" index="24" size="0.1"/>
</parameter>
<parameter id="BAUDRATE">


Und werden unten im Channel 0 dann einfach referenziert

<channels>
<channel index="0" type="MAINTENANCE" ui_flags="internal" class="maintenance" count="1">
<paramset type="MASTER" id="maint_ch_master"/>

BananaPi + CUL868 + CUL433 + HM-UART + 1Wire

Dietmar63

Ich würde die Variante als Headderdatei + cpp-Datei bevorzugen.Dann bleibt das .ino schön klein.
Ich bin bei meinen Versuchen an AskSinPP etwas zu verändern in der Headderhölle gelandet.

Sauberer scheint es zu sein, zwei Files zu schreiben.
Trotzdem sagt der Compiler mir manchmal, dass er von unvollständige Klassen nicht ableiten könne. Forwarddeklarationen sind dann auch nicht hilfreich.

Heute komme ich nicht dazu. Aber zu lange wird es mit Perl ja nicht dauern das zubauen, zumal das Parsen ja schon teilweise vorhanden ist.
Gruß Dietmar
FB7390, CUL, 2 FHT, FS20
modules: 98_WOL.pm, 98_Heating_Control.pm,   98_WeekdayTimer.pm, 98_RandomTimer.pm, 59_Twilight.pm

Dietmar63

Für den  hm-es-tx habe ich jetzt ein neueres xml gefunden.
Dort habe ich die vermissten Sachen gefunden.
Gruß Dietmar
FB7390, CUL, 2 FHT, FS20
modules: 98_WOL.pm, 98_Heating_Control.pm,   98_WeekdayTimer.pm, 98_RandomTimer.pm, 59_Twilight.pm

papa

BananaPi + CUL868 + CUL433 + HM-UART + 1Wire

Dietmar63

den Link kannte ich schon - war hier schon einmal veröffentlicht worden.
Und mit dem xml sehen die structs schon viel besser aus:


/**
* @brief Channel structs (for developers)
* Within the channel struct you will find the definition of the respective registers per channel and list.
* These information is only needed if you want to develop your own channel module, for pre defined
* channel modules all this definitions enclosed in the pre defined module. 
*/

struct s_cnl0_lst0 {
   uint8_t MASTER_ID                 :24; // 0x0a.0, s:24  d:   
   uint8_t LOCAL_RESET_DISABLE       :1;  // 0x18.0, s:1   d: false 
   uint8_t                           :7;  // 0x18.1, s:7   d:   
   uint8_t BAUDRATE                  :8;  // 0x23.0, s:8   d: 9600 Bd 
   uint8_t SERIAL_FORMAT             :8;  // 0x24.0, s:8   d: 1_7D_1P_E_1S 
   uint8_t METER_POWERMODE           :8;  // 0x25.0, s:8   d: MAINS_POWERED 
   uint8_t METER_PROTOCOLMODE        :8;  // 0x26.0, s:8   d: PROTOKOLL_MODE_D 
   uint8_t SAMPLES_PER_CYCLE         :8;  // 0x27.0, s:8   d: nF 
}; // 9 byte

struct s_cnl1_lst1 {
   uint8_t AES_ACTIVE                :1;  // 0x08.0, s:1   d: false 
   uint8_t                           :7;  // 0x08.1, s:7   d:   
   uint8_t POWER_STRING              :128; // 0x36.0, s:128 d:   
   uint8_t ENERGY_COUNTER_STRING     :128; // 0x46.0, s:128 d:   
   uint8_t TX_THRESHOLD_POWER        :24; // 0x7c.0, s:24  d: 100.00 W
   uint8_t METER_TYPE                :8;  // 0x95.0, s:8   d: UNKOWN 
   uint8_t METER_CONSTANT_IR         :16; // 0x96.0, s:16  d: nF U./kWh
   uint8_t METER_CONSTANT_GAS        :16; // 0x98.0, s:16  d: 0.01 m3/Imp.
   uint8_t METER_CONSTANT_LED        :16; // 0x9a.0, s:16  d: nF Imp./kWh
   uint8_t METER_SENSIBILITY_IR      :8;  // 0x9c.0, s:8   d: nF %
}; // 44 byte

struct s_cnl2_lst1 {
   uint8_t AES_ACTIVE                :1;  // 0x08.0, s:1   d: false 
   uint8_t                           :7;  // 0x08.1, s:7   d:   
   uint8_t POWER_STRING              :128; // 0x36.0, s:128 d:   
   uint8_t ENERGY_COUNTER_STRING     :128; // 0x46.0, s:128 d:   
   uint8_t TX_THRESHOLD_POWER        :24; // 0x7c.0, s:24  d: 100.00 W
   uint8_t METER_TYPE                :8;  // 0x95.0, s:8   d: UNKOWN 
}; // 37 byte
Gruß Dietmar
FB7390, CUL, 2 FHT, FS20
modules: 98_WOL.pm, 98_Heating_Control.pm,   98_WeekdayTimer.pm, 98_RandomTimer.pm, 59_Twilight.pm

micky0867

Zitat von: papa am 13 Februar 2017, 21:37:37
Ich habe mal eine Branch V1 im GitHub erstellt. Diese stellt den aktuellen, stabilen Stand dar und sollte für eigene Geräte genutzt werden. Hier wird es nur noch Bugfixes geben.
Im Master plane ich einige größere Umbauten, so dass es hier zu Inkompatibilitäten kommen wird.

Hmmm... habe ich bei Git was falsch verstanden?
Sind Branches nicht i.A. die Entwicklungszweige und master der letzte stabile Stand?

Micky

papa

Zitat von: micky0867 am 14 Februar 2017, 19:50:21
Hmmm... habe ich bei Git was falsch verstanden?
Sind Branches nicht i.A. die Entwicklungszweige und master der letzte stabile Stand?

Das kann man machen wie man will. Ich gehe davon aus, das es noch kleine Fixes geben wird. Deshalb der Maintenance Branch. Im Master will ich noch ein paar Sachen umbauen, um noch flexibler unterschiedliche Konfigurationen zu unterstützen.
BananaPi + CUL868 + CUL433 + HM-UART + 1Wire

Dietmar63

habe ein wenig gebastelt - sieht schon ganz gut aus, es bleibt aber noch was zu tun:


class Channel0List0Data {
   uint8_t MASTER_ID                 :24;  // 0x0a.0, s:24   d:   
   uint8_t LOCAL_RESET_DISABLE       :1;   // 0x18.0, s:1    d: false 
   uint8_t BAUDRATE                  :8;   // 0x23.0, s:8    d: 9600 Bd 
   uint8_t SERIAL_FORMAT             :8;   // 0x24.0, s:8    d: 1_7D_1P_E_1S 
   uint8_t METER_POWERMODE           :8;   // 0x25.0, s:8    d: MAINS_POWERED 
   uint8_t METER_PROTOCOLMODE        :8;   // 0x26.0, s:8    d: PROTOKOLL_MODE_D 
   uint8_t SAMPLES_PER_CYCLE         :8;   // 0x27.0, s:8    d: nF 

   // Zugriffe auf Register

};

class Channel0List0Access : public ChannelList<Channel0List0Data> {
public:
   Channel0List0Access(uint16_t a) : ChannelList(a) {}

   uint8_t                 MASTER_ID()  {};
   boolean                 MASTER_ID()  {};
   uint8_t       LOCAL_RESET_DISABLE()  {};
   boolean       LOCAL_RESET_DISABLE()  {};
   uint8_t                  BAUDRATE()  {};
   boolean                  BAUDRATE()  {};
   uint8_t             SERIAL_FORMAT()  {};
   boolean             SERIAL_FORMAT()  {};
   uint8_t           METER_POWERMODE()  {};
   boolean           METER_POWERMODE()  {};
   uint8_t        METER_PROTOCOLMODE()  {};
   boolean        METER_PROTOCOLMODE()  {};
   uint8_t         SAMPLES_PER_CYCLE()  {};
   boolean         SAMPLES_PER_CYCLE()  {};

   void defaults () {
      MASTER_ID (0);
      LOCAL_RESET_DISABLE (0);
      BAUDRATE (5);
      SERIAL_FORMAT (0);
      METER_POWERMODE (0);
      METER_PROTOCOLMODE (3);
   }
};

class Channel1List1Data {
   uint8_t AES_ACTIVE                :1;   // 0x08.0, s:1    d: false 
   uint8_t POWER_STRING              :128; // 0x36.0, s:128  d:   
   uint8_t ENERGY_COUNTER_STRING     :128; // 0x46.0, s:128  d:   
   uint8_t TX_THRESHOLD_POWER        :24;  // 0x7c.0, s:24   d: 100.00 W
   uint8_t METER_TYPE                :8;   // 0x95.0, s:8    d: UNKOWN 
   uint8_t METER_CONSTANT_IR         :16;  // 0x96.0, s:16   d: nF U./kWh
   uint8_t METER_CONSTANT_GAS        :16;  // 0x98.0, s:16   d: 0.01 m3/Imp.
   uint8_t METER_CONSTANT_LED        :16;  // 0x9a.0, s:16   d: nF Imp./kWh
   uint8_t METER_SENSIBILITY_IR      :8;   // 0x9c.0, s:8    d: nF %

   // Zugriffe auf Register

};

class Channel1List1Access : public ChannelList<Channel1List1Data> {
public:
   Channel1List1Access(uint16_t a) : ChannelList(a) {}

   uint8_t                AES_ACTIVE()  {};
   boolean                AES_ACTIVE()  {};
   uint8_t              POWER_STRING()  {};
   boolean              POWER_STRING()  {};
   uint8_t     ENERGY_COUNTER_STRING()  {};
   boolean     ENERGY_COUNTER_STRING()  {};
   uint8_t        TX_THRESHOLD_POWER()  {};
   boolean        TX_THRESHOLD_POWER()  {};
   uint8_t                METER_TYPE()  {};
   boolean                METER_TYPE()  {};
   uint8_t         METER_CONSTANT_IR()  {};
   boolean         METER_CONSTANT_IR()  {};
   uint8_t        METER_CONSTANT_GAS()  {};
   boolean        METER_CONSTANT_GAS()  {};
   uint8_t        METER_CONSTANT_LED()  {};
   boolean        METER_CONSTANT_LED()  {};
   uint8_t      METER_SENSIBILITY_IR()  {};
   boolean      METER_SENSIBILITY_IR()  {};

   void defaults () {
      AES_ACTIVE (0);
      POWER_STRING (0);
      ENERGY_COUNTER_STRING (0);
      TX_THRESHOLD_POWER (10000);
      METER_TYPE (4);
      METER_CONSTANT_GAS (10);
   }
};

class Channel2List1Data {
   uint8_t AES_ACTIVE                :1;   // 0x08.0, s:1    d: false 
   uint8_t POWER_STRING              :128; // 0x36.0, s:128  d:   
   uint8_t ENERGY_COUNTER_STRING     :128; // 0x46.0, s:128  d:   
   uint8_t TX_THRESHOLD_POWER        :24;  // 0x7c.0, s:24   d: 100.00 W
   uint8_t METER_TYPE                :8;   // 0x95.0, s:8    d: UNKOWN 

   // Zugriffe auf Register

};

class Channel2List1Access : public ChannelList<Channel2List1Data> {
public:
   Channel2List1Access(uint16_t a) : ChannelList(a) {}

   uint8_t                AES_ACTIVE()  {};
   boolean                AES_ACTIVE()  {};
   uint8_t              POWER_STRING()  {};
   boolean              POWER_STRING()  {};
   uint8_t     ENERGY_COUNTER_STRING()  {};
   boolean     ENERGY_COUNTER_STRING()  {};
   uint8_t        TX_THRESHOLD_POWER()  {};
   boolean        TX_THRESHOLD_POWER()  {};
   uint8_t                METER_TYPE()  {};
   boolean                METER_TYPE()  {};

   void defaults () {
      AES_ACTIVE (0);
      POWER_STRING (0);
      ENERGY_COUNTER_STRING (0);
      TX_THRESHOLD_POWER (10000);
      METER_TYPE (4);
   }
};
Gruß Dietmar
FB7390, CUL, 2 FHT, FS20
modules: 98_WOL.pm, 98_Heating_Control.pm,   98_WeekdayTimer.pm, 98_RandomTimer.pm, 59_Twilight.pm

papa

Sieht ja schon gut aus. Aber Bitfelder, die größer als der Datentyp sind, funktionieren nicht.


uint8_t MASTER_ID                 :24;  // 0x0a.0, s:24   d:   


http://en.cppreference.com/w/cpp/language/bit_field
Zitat
If the specified size of the bit field is greater than the size of its type, the value is limited by the type: a std::uint8_t b : 1000; would still hold values between 0 and 255. the extra bits become unused padding.

Zur Berechnung der Größe könnte es aber funktionieren.
BananaPi + CUL868 + CUL433 + HM-UART + 1Wire

Dietmar63

ich bin noch nicht soweit, ist nur ein Zwischenstand - hatte gestern dann keine Lust mehr.

uint8_t LOCAL_RESET_DISABLE       :1;   // 0x18.0, s:1    d: false 

benötigt man diese Felder überhaupt?
Können sie nicht einfach nur als Kommentar eingefügt werden .

Ich habe keine Stelle gefunden, wo sie angesprochen werden. Die Getter und Setter greifen direkt auf das Eprom zu.
Ich habe auch gesehen, dass du die Art und Weise wie du die Klassen gebaut hast, mit der Zeit verändert hast.

Und der Zugriff auf "string" ist mir auch noch unklar. Return "powerstring" dürfte nicht so einfach sein.
Ich denke, dass du nur das codiert hast, was du für notwendig erachtet hast - den Rest kann man wahrscheinlich einfach fortlassen.

Das Ganze ist eine gute Übung um das mit den Registern in HM zu verstehen - ich habe erst seit 12 Wochen Homematik im Einsatz und weiß noch nicht so viel darüber.

Immer der Reihe nach.
Aus AES_ACTIVE() will ich noch aesActive() machen. Dann müssen noch die Rückgabewerte und der Registerzugriff gebastelt werden - alles kein Hexenwerk.

Das Script destillRegs2 ist jedenfalls leicht umzubauen.
Gruß Dietmar
FB7390, CUL, 2 FHT, FS20
modules: 98_WOL.pm, 98_Heating_Control.pm,   98_WeekdayTimer.pm, 98_RandomTimer.pm, 59_Twilight.pm

papa

Zitat von: Dietmar63 am 17 Februar 2017, 10:27:01
benötigt man diese Felder überhaupt?
Können sie nicht einfach nur als Kommentar eingefügt werden .

Ich habe keine Stelle gefunden, wo sie angesprochen werden. Die Getter und Setter greifen direkt auf das Eprom zu.
Ich habe auch gesehen, dass du die Art und Weise wie du die Klassen gebaut hast, mit der Zeit verändert hast.

Die Felder werden nur für sizeof(Datatype) benötigt, um die benötigte Größe im Eprom zu ermitteln. Man kann aber auch gut eine static Methode sizeof() generieren, die dann einfach die Größe zurückgibt. Ich bin halt zu faul, das mit der Hand auszurechnen.

Zitat von: Dietmar63 am 17 Februar 2017, 10:27:01
Und der Zugriff auf "string" ist mir auch noch unklar. Return "powerstring" dürfte nicht so einfach sein.
Ich denke, dass du nur das codiert hast, was du für notwendig erachtet hast - den Rest kann man wahrscheinlich einfach fortlassen.

Da wird es schon interessant, wie man das Notwendige im Script erkennt.

Zitat von: Dietmar63 am 17 Februar 2017, 10:27:01
Aus AES_ACTIVE() will ich noch aesActive() machen. Dann müssen noch die Rückgabewerte und der Registerzugriff gebastelt werden - alles kein Hexenwerk.

Die Schreibweise wäre mir auf jeden Fall lieber. Sollte auch nicht allzu schwer sein.
BananaPi + CUL868 + CUL433 + HM-UART + 1Wire

Pelle

Hallo,

ich habe mittlerweile die AskSin++ auf einem PanStamp Avr2 erfolgreich im Betrieb genommen (mit dem HM-WDS10-TH-O example).
Danke für die tolle Library.
Dabei hatte ich das Problem, dass keine Nachrichten gesendet wurden, sobald der Stromsparmodus aktiv wurde. Es wurden also 5 Nachrichten nach einem Pairing gesendet, danach kamen keine mehr in FHEM an. Das entspricht genau der Zeit, die AskSin++ aktiv bleibt ohne zu schlafen nach einem Pairing.

Ich habe den Fehler jetzt behoben. Folgendes ist vermutlich schief gelaufen:

- Ein Paket wird gesendet.
- In der Senderoutine (Radio.cpp CC1101::sndData()) wird nicht korrekt bis zum erfolgreichen Senden gewartet
- hal.radio.setIdle(); wird aufgerufen, bevor das Paket erfolgreich versendet wurde.

Das Problem liegt in Zeile 134 von Radio.cpp:


if( readReg(CC1101_MARCSTATE, CC1101_STATUS) != MARCSTATE_TX) {
break; //neither in RX nor TX, probably some error
}


Hier wird die Warteschleife auch abgebrochen, wenn sich die State-Machine vom CC1101 in einem anderen Status als MARCSTATE_TX befindet. Zu diesem Zeitpunkt befindet sich der CC1101 aber noch im Status 0x08 (Calibrate), so dass die Warteschliefe sofort abgebrochen wird.
Ein entfernen fixt das Problem.

Der zweite Fehle ist nun das CC1101_MCSM1 Register, welches für den TXOFF_MODE Idle setzt, so dass MARCSTATE_RX nie erreicht werden kann.

Abhilfe schafft hier (in Zeile 146 Radio.cpp ersetzen):


if( readReg(CC1101_MARCSTATE, CC1101_STATUS) == MARCSTATE_IDLE)
    break;


oder das Setzen von


CC1101_MCSM1,    0x17


in Zeile 71 (NewAskSin setzt das Register genau so), so dass das Radio nach TX in RX wechselt.


Nach der Fehlersuche habe ich dann auch gesehen, dass in NewAskSin eine geschlossenes Issue steht welche eine ähnliches Phänomen beschreibt: https://github.com/trilu2000/NewAskSin/issues/20

papa

Danke für die Fehlermeldung. Nummer 1 ist mir klar. Bei Nummer 2 bin ich mir nicht sicher, wo das hin soll.

Wie ich gesehen habe, verwendest Du den Master Branch. Dieser befindet sich gerade um Umbau, um demnächst STM32/Marple Mini besser unterstützen zu können. Dort wird gerade viel geändert. Für Anwendungen sollte der V1 Branch verwendet werden, da hier nur noch Bugfixes eingespielt werden.

Der Master verwendet jetzt übrigens die EnableInterrupt-Library anstelle der PinChangeInt-Library.
BananaPi + CUL868 + CUL433 + HM-UART + 1Wire

Pelle

Ohh stimmt,

Zeile 146 war falsch. Richtig ist Zeile 132:


if( readReg(CC1101_MARCSTATE, CC1101_STATUS) == MARCSTATE_RX)
    break;


ersetzen durch

if( readReg(CC1101_MARCSTATE, CC1101_STATUS) == MARCSTATE_IDLE)
    break;


wenn das Radio nach dem Senden in Idle wechseln soll, dann kann das CC1101_MCSM1 so bleiben.
Soll nach dem Senden direkt in den Empfangsmodus gewechselt werden, das Register CC1101_MCSM1 auf 0x17 und Zeile 132 kann so bleiben.

papa

Danke - habe ich in beiden Branches geändert.
BananaPi + CUL868 + CUL433 + HM-UART + 1Wire