Max/Moritz: Sporadisch Probleme bei Senden, Fragen zum CC1101 Code

856 views
Skip to first unread message

Matthias Gehre

unread,
Dec 6, 2012, 3:32:29 PM12/6/12
to cul-...@googlegroups.com
Hallo,

das Empfangen im Moritz Modus klappt einwandfrei. Ich wüsste nicht, wann ich mal eine Nachricht nicht bekommen habe.

Leider klappt das Senden nicht so gut, d.h. sehr oft bekomme ich nach dem Senden eines Befehls an einen Heizkörper keine Ack-Nachricht zurück. (Und der Befehlt wird vom Heizkörper auch nicht umgesetzt, ist also kein Problem des Empfangens der Ack- Nachrichten).

Hat jemand eine Idee, woran man da schrauben könnte?
Preamble zu kurz? Frequenz falsch?

Ich habe mir den rf_moritz Code angeschaut
In moritz_send():
Zuerst wechseln wir in den Moritz Modus
  if(!moritz_on) {
    rf_moritz_init();
    my_delay_ms(3);             // 3ms: Found by trial and error
  }
Warum schreiben wir zwei Zeilen später
  for (uint8_t i = 0; i<60; i += 2) {

    if (pgm_read_byte( &MORITZ_CFG[i] )>0x40)
      break;

    cc1100_writeReg( pgm_read_byte(&MORITZ_CFG[i]),
                     pgm_read_byte(&MORITZ_CFG[i+1]) );
  }
nochmal die Config? Das wurde doch schon in rf_moritz_init getan?

Dann kommt
  /* start sending here already - see below why */
  ccStrobe(CC1100_STX);
Allerdings kann es passieren, dass der CC1101 wegen CCA daraufhin gar nicht in den TX mode wechselt, oder? Und kommt es nicht zu einem TX_Underflow, wenn zu diesem Zeitpunkt in der TX FIFO noch nichts drin steht?

Dann kommt
  // loop for a while > tEvent0 (this needs to be reviewed) 
  for (uint8_t i = 0; i<5; i++)
    my_delay_ms(100);
Das sendet für 500ms das Preamble, richtig? Warum nicht my_delay_ms(500)?

Dann kommt
  while( cc1100_readReg( CC1100_MARCSTATE ) != 1 )
    my_delay_ms(5);
Also wir warten, bis das Senden abgeschlossen ist. Mir scheint, als wäre dies von Errata #3 betroffen, da wir das Register lesen während es vom CC1101 geschrieben wird. Oder hat das keine Auswirkungen?

Dann kommt
  ccStrobe(CC1100_SIDLE);
Allerdings warten wir doch vorher genau darauf, dass MARCSTATE = IDLE ist. Warum dann hier nochmal setzen?

Danach kommt
  if(moritz_on) {
    ccRX();
In ccRX() passiert u.a. EIMSK |= _BV(CC1100_INT). In rf_moritz_init wird genau das Bit aber nicht gesetzt. Was hat das für Auswirkungen?

Noch eine allgemeine Frage: Warum wird nicht TXOFF=RX, RXOFF=RX
in der Config gesetzt? Dann würde man sich ein paar ccStrobe() zum Wechseln in den RX Modus nach dem Senden/Empfangen sparen.

Viele Grüße,
Matthias

Dirk Tostmann

unread,
Dec 7, 2012, 4:24:15 PM12/7/12
to cul-...@googlegroups.com

Am 06.12.2012 um 21:32 schrieb Matthias Gehre:

Dann kommt
  // loop for a while > tEvent0 (this needs to be reviewed)  
  for (uint8_t i = 0; i<5; i++)
    my_delay_ms(100);
Das sendet für 500ms das Preamble, richtig? Warum nicht my_delay_ms(500)? 

Das Senden für Max! wurde noch nicht optimiert. Fakt ist, dass die Aktoren WOR (WakeOnRadio) verwenden und nur circa jede Sekunden aufwachen um zu sehen ob ein Trägersignal da ist. Daher müsste man die oben stehende Loop eher auf eine Sekunde Dauerträger verlängern!!! Das kann man aber aus Gründen des Dutycyles nicht! Zum Testen kann man also mal auf 1 Sekunde gehen, dann müsste man sich aber was anderes einfallen lassen zu Erkennen, wann die Thermostate aufwachen. 
Noch haben wir das in culfw nicht gemacht, Vielleicht gibt es ja sowas wie ein globales Heartbeat … 

Der Rest mit Init und den Strobes kann man machen wie man gern möchte - Problem ist aber das WOR wie oben kurz erläutert - die Aktoren hören praktisch nicht immer zu ...

Matthias Gehre

unread,
Dec 7, 2012, 6:34:39 PM12/7/12
to cul-...@googlegroups.com
Danke für deine Antwort, sehr erhellend!

Wenn der Cube mit den Max Devices funkt, dann kriegt er immer sofort ein Ack. D.h. irgendwo her muss der Cube wissen, wann genau die Devices empfangen.

Es gibt auch einen ominösen WakeUp Befehl im Max Rf Protokol. Vielleicht dient der dazu, die Aufwachzeiten des Gerätes mit dem Cube zu synchronisieren? Andererseits führt ein Neustart (power-cycle) des Cube nicht zu irgendwelchen rf Paketen, also scheint es keine Synchronisation
über solche Pakete zu geben.

Oder vielleicht kann man aus den Empfangszeiten der Broadcasts darauf schließen?


--
To unsubscribe from this group, send email to
cul-fans+u...@googlegroups.com

Matthias Gehre

unread,
Dec 7, 2012, 10:23:33 PM12/7/12
to cul-...@googlegroups.com
Nach Vfg 40/2010 heißt es
  868,0 - 868,6  : Es sind Frequenzzugangs- und
  Störungsminderungstechniken einzusetzen, deren Leistung
  mindestens den Techniken entspricht, die in den gemäß
  Richtlinie 1999/5/EG bzw. des FTEG verabschiedeten harmo-
  nisierten Normen vorgesehen sind. Alternativ kann ein maxi-
  maler Arbeitszyklus (2) von 1% verwendet werden.
Und
  (2) Arbeitszyklus (relative Frequenzbelegungsdauer oder duty cycle in %) ist definiert als anteilsmäßiger aktiver
  Sendebetrieb innerhalb einer Zeitdauer von einer Stunde zu einem beliebigen Zeitpunkt.

Wenn ich das richtig verstehe, spricht nichts gegen ein 1 Sekunden Preamble, solange man weniger als 36 Sekunden pro Stunde funkt.
Und falls man Störungsminderungstechniken einsetzt, brauch man auf die Dauer gar nicht achten. Und listen-before-talk ala CCA ist doch bereits in rf_moritz aktiviert.

Dirk Tostmann

unread,
Dec 8, 2012, 4:32:10 PM12/8/12
to cul-...@googlegroups.com

Am 08.12.2012 um 00:34 schrieb Matthias Gehre:

> Oder vielleicht kann man aus den Empfangszeiten der Broadcasts darauf schließen?

Hätten wir ein Manual wären wir schlauer - so bleibt nur Kreativität und Probieren mit viel Zeitaufwand ...

Matthias Gehre

unread,
Dec 8, 2012, 5:15:43 PM12/8/12
to cul-...@googlegroups.com
Kann man nicht SCK und SO zwischen CC1100 und dem IC auf einem der Max Bausätze abgreifen
und dann mitschneiden, was die als Configuration auf den CC1100 laden? Dann hätte man ja alle interessanten Parameter.
Der Fensterkontakt scheint dafür perfekt. Es gibt sogar zugängliche Lötstellen, um sich dort ran zuhängen.

Leider ist meine praktische Erfahrung damit sehr gering. Wäre das durchführbar? Außerdem habe ich keinen
Mikrokontroller rumliegen, den man anschließen könnte.


Matthias Gehre

unread,
Dec 9, 2012, 2:10:06 PM12/9/12
to cul-...@googlegroups.com
Ich hab nochmal in eine andere Richtung probiert. Der Cube zeigt über das LAN interface
seinen aktuellen duty cycle an (=1% Regel).
Er startet nach langem Idle bei 0, beim Senden eines Befehls erhöht er sich um jeweils 3,
und sobald er 100 erreicht, sendet der Cube keine Pakete mehr (mit CUL überprüft). Über die Zeit wird dann der
duty cycle wieder weniger.

D.h. es sind 100/3 = 33 Pakete pro Stunde erlaubt. 33 Pakete füllen also 1% von einer Stunde aus,
macht 1.01 Sekunden pro Paket. Genau die Länge die man braucht, um auf jeden Fall Wake-On-Radio zu triggern.
Zufall?

Dann kann ich doch auch die knapp 1 Sekunden Präambel senden. Ich würde dann auch die 1%-Regel gleich mit implementieren,
momentan kann rf_moritz soviel senden wie es will.
Oder hab ich was übersehen?

Dirk Tostmann

unread,
Dec 9, 2012, 3:19:32 PM12/9/12
to cul-...@googlegroups.com

Die Init Sequenz gibt's hier:

http://www.mikrocontroller.net/topic/244432#2824930

Am 08.12.2012 um 23:15 schrieb Matthias Gehre:

> Kann man nicht SCK und SO zwischen CC1100 und dem IC auf einem der Max Bausätze abgreifen

Ich denke das Timing bekommt man eher "erkannt" wenn man ein paar Aktoren im Einsatz hat und da mal nachschaut was nach RESET passiert um die Synchronität herzustellen ...

Matthias Gehre

unread,
Dec 9, 2012, 3:31:20 PM12/9/12
to cul-...@googlegroups.com
Mit der Init sequence ist das Timing zwischen den Wakeups genau 1 Sekunde. (750/26Mhz * EVENT0 * 2^(5*WOR_RES) mit EVENT0 = 34667 und WOR_RES = 0)


Ich hab mal die culfw so modifiziert, dass ich immer einen Interrupt bekomme, sobald das sync word erkannt wurde,
und habe dann die timings ausgeben lassen. Der Cube sendet _nicht_ in einem 1 Sekunden takt. Auch nicht nach einem factoryReset/neu anlernen der Devices. Das war auch meine erste Vermutung, aber der Cube scheint keinerlei Synchronität nach dem Paaren zu halten.

Gepaart mit der Beobachtung, dass er nur 33 Sendevorgänge pro Stunde zulässt, liegt doch nahe, dass der Cube
tatsächlich 1 Sekunde lang funkt, um die Geräte auszuwecken.


Dirk Tostmann

unread,
Dec 9, 2012, 4:12:19 PM12/9/12
to cul-...@googlegroups.com

Am 09.12.2012 um 21:31 schrieb Matthias Gehre:

> Gepaart mit der Beobachtung, dass er nur 33 Sendevorgänge pro Stunde zulässt, liegt doch nahe, dass der Cube
> tatsächlich 1 Sekunde lang funkt, um die Geräte auszuwecken.

... das wäre besonders im Mischbetrieb mit FS20 riskant da die ja dann auch nix mehr mitbekommen.
Daher hatte ich es auf 500ms gesetzt, als Kompromiss sozusagen ....

Fensterkontakte / Wandthermo müssten das aber folglich auch so machen um das Ventil zu erreichen, das kann ich mir eigentlich nicht vorstellen ....

Matthias Gehre

unread,
Dec 9, 2012, 4:48:35 PM12/9/12
to cul-...@googlegroups.com
Mit dem 500ms erreiche ich oft die MAX devices nicht.
Mit einem 1 Sekunden Präambel immer.

Ich kann ja noch ein paar Werte dazwischen testen.

Matthias Gehre

unread,
Dec 9, 2012, 5:27:01 PM12/9/12
to cul-...@googlegroups.com
Ist den sicher, dass
http://www.mikrocontroller.net/topic/244432#2824930
die Init Sequenz ist, die auf den MAX devices läuft?

Da dort MCSM2 (0x16) den Wert 0x07 hat,
wäre MCSM2.RX_TIME = 7 und damit würde der WOR Modus nie schlafen (sondern solange warten bis ein Paket kommt).
Scheint mir eher so, als wäre das die Config die man für den CUL braucht.

Dirk Tostmann

unread,
Dec 9, 2012, 5:50:59 PM12/9/12
to cul-...@googlegroups.com

Am 09.12.2012 um 23:27 schrieb Matthias Gehre:

> Da dort MCSM2 (0x16) den Wert 0x07 hat,
> wäre MCSM2.RX_TIME = 7 und damit würde der WOR Modus nie schlafen (sondern solange warten bis ein Paket kommt).
> Scheint mir eher so, als wäre das die Config die man für den CUL braucht.

Das macht ein Max-Aktor auf SPI aus Sicht des Prozessors (immer Reg setzten, dann rücklesen):

00 08 80 00
02 46 82 00
04 C6 84 00
05 26 85 00
0B 06 8B 00
10 C8 90 00
11 93 91 00
12 03 92 00
15 34 95 00
17 00 97 00
18 18 98 00
19 16 99 00
1B 43 9B 00
21 56 A1 00
25 00 A5 00
26 11 A6 00
0D 21 8D 00
0E 65 8E 00
0F 6A 8F 00
07 4C 87 00
16 1C 96 00
20 78 A0 00
1E 87 9E 00
1F 6B 9F 00
29 59 A9 00
2C 81 AC 00
2D 35 AD 00
3E C3 BE 00

Dann auf Empfang gehen:

3A - SFRX

und schlafen:

38 - SWOR

...

Matthias Gehre

unread,
Dec 10, 2012, 2:22:10 PM12/10/12
to cul-...@googlegroups.com

Sehr gut, danke! Von welchem Aktor genau ist diese Init sequence?

Mir scheint, nämlich das die Fensterkontakte überhaupt nicht aufwachen. Daher hält der Cube sie nach dem Pairing mit ständigen WakeUp Nachrichten wach, bis die ganze Konfiguration (association, groupId etc) abgeschlossen ist. Und wenn man mit der offiziellen Max Software ein factoryReset vom Fensterkontakt machen möchte, dann soll man den Kontakt einmal betätigen. Tatsächlich sendet der Cube auch das factoryReset Paket genau nachdem der Kontakt die ShutterContactState Paket ankam. Wohl um den Fensterkontakt noch wach zu erwischen.

Hab ein paar Dinge ins FHEM Wiki
http://www.fhemwiki.de/wiki/MAX
im letzten Abschnitt unter Internals vermerkt. Insbesondere hab ich aus der CC1100 Configuration die Timings berechnet.


...

Dirk Tostmann

unread,
Dec 10, 2012, 7:40:26 PM12/10/12
to cul-...@googlegroups.com

Am 10.12.2012 um 20:22 schrieb Matthias Gehre:

> Sehr gut, danke! Von welchem Aktor genau ist diese Init sequence?

Das müsste von einem Wandthermosthat sein ...

>
> Hab ein paar Dinge ins FHEM Wiki
> http://www.fhemwiki.de/wiki/MAX
> im letzten Abschnitt unter Internals vermerkt. Insbesondere hab ich aus der CC1100 Configuration die Timings berechnet.
>

Bin mir nicht ganz sicher ob es dahin gehört. Das dürfte den Anwender eher verwirren. Besser wäre es irgendwo bei fhz4linux.info ...

Grüsse!

Claus Mößner

unread,
Apr 19, 2015, 4:04:56 PM4/19/15
to cul-...@googlegroups.com, gehre.m...@gmail.com
Hallo,
bin mir nicht sicher ob ich hier an der richtigen stelle bin.
Habe mir das rf_moritz modul angeschaut um zu lernen wie Diese in der culfw aufgebaut sind.
(ich bin gerade am Implementerien einer Empfangsroutine für das Kopp Free Control Protokoll).

Dabei ist mir folgendes aufgefallen:
Folgender Code im Modul rf_moritz.c ist, wenn ich das richtig verstehe, nicht korrekt.

   //errata #1 does not affect us, because we wait until packet is completely received
    enc[0] = cc1100_readReg( CC1100_RXFIFO ) & 0x7f; // read len

Um die Anzahl der Daten im Fifo zu ermitteln wird das Register RXFIFO anstelle von RXBYTES abgefragt.
Bei meiner Empfangsroutine hat das zu unerklärlichen Effekten geführt. Nach ändern von RXFIFO auf RXBYTES funktionierte in meiner eigenen Implementierung alles wie gewünscht.

Gruß
Claus


Broxi Nagil

unread,
May 9, 2015, 12:04:51 PM5/9/15
to cul-...@googlegroups.com, gehre.m...@gmail.com
Also ich erkenne keine Effekte. Ich habe die 1.64 aus dem SVN, welche auch auf CC1100_RXFIFO steht. Funktioniert hier ohne Probleme mit MORITZ/MAX!. Evtl. eine Eigenart des MORITZ die Länge im RXFIFO stehen zu haben ?

Claus Mößner

unread,
May 9, 2015, 4:03:24 PM5/9/15
to cul-...@googlegroups.com
Hi,
ja, ich hab mir das jetzt nochmal angeschaut.
Max/Moritz benutzt flexible Blocklängen, dann ist das erste Byte im Fifo die Blocklänge.

Sorry für die Verwirrung, ich hätte vielleicht besser zuerst nochmal das CC1101 Datenblatt lesen sollen.
Fazit: es gibt kein Problem.

Gruß
Claus
Reply all
Reply to author
Forward
0 new messages