DCC Decoder Programmierung on Main
PoM ist ein sehr nützliches Feature zum Ändern von Decoderparametern auf dem
Hauptgleis, sogar während der Fahrt.
In der NRMA-Doku RP 9.2.1 sind die "Extended Packet Formats" beschrieben.
Die Bezeichnung "Erweitertes Format" trifft die Sache gut, denn an die Stelle
der
Geschwindigkeits- und Richtungsinformation in einem Byte, treten die
"instruction-bytes", wobei es auch den Sonderfall mit 1 Byte gibt.
{preamble} 0 [ AAAAAAAA ] 0 {instruction-bytes}
0 EEEEEEEE 1
Seite 2, Zeile 80 sagt:
Each instruction (indicated by {instruction-bytes}) is defined to be:
{instruction-bytes} = CCCDDDDD,
CCCDDDDD 0 DDDDDDDD,
CCCDDDDD 0 DDDDDDDD 0 DDDDDDDD
CCC steht für drei Bit Instruktionsnummer, die 111 für
Configuration Variable Access Instruction
mit der die Programmierung auf dem Gleis
realisiert wird. Dafür sind 2 Varianten definiert, kurz für
wenige spezielle CV's und lang für (fast) alle CV-Nummern. Fast, weil nach
meiner Information die
Decoder das Ändern der Basisadresse "on the fly" (zurecht) nicht zulassen. Die
lange Form ist auf
Seite 8, Zeile 353 beschrieben:
1110CCVV 0 VVVVVVVV 0 DDDDDDDD
CC sind wiederum 2 Bit Instruktionscode: 00 = reserviert, 01
verify byte, 11 write byte und 10 für die Bit-
Manipulation. VV im ersten Byte sind die beiden MSB der 10 Bit CV-Nummer
im Folgebyte stehen
die restlichen 8 Bit. Bleibt nach das Datenbyte DDDDDDDD, das sowohl zum
Schreiben als auch
zum "Lesen" bzw. Verify benötigt wird. Beim Schreiben ist das
selbstverständlich. Auf dem DCC-
Gleis-Signal ist derzeitig noch kein bidirektionaler Datenverkehr genormt. Das
wird aber demnächst
der Fall sein (RailCom, BiDi). Im Moment bleibt nur die "Scanmethode" um zu
erfahren, welchen Wert
eine CV gespeichert hat. Der Decoder vergleicht nach dem Verify-Kommando das
übertragene Byte
mit seinem abgespeicherten und sendet bei Übereinstimmung einen "Acknowledgement"-Impuls
von
etwa 6 Millisekunden Dauer. Dazu muss natürlich ein Motor am Decoder
angeschlossen sein, den er
als "Lastwiderstand" verwendet. Nach NMRA ist der Impulsstrom > 60 mA. Dieser
Impuls wird in der
Gleiszuleitung, besser im Booster, als Spannungsabfall gemessen bzw. per
Komparator mit einer
passenden Referenzspannung verglichen.
Programmtechnisch ist das eine Schleife in der das Testbyte von 0 bis max. 255
verändert wird, und
bei "Acknowledge" der letztgesendete Wert als "Wahr" gewertet wird. Das
Verfahren dauert deshalb
unterschiedlich lang und ist deshalb im Fahrbetrieb nur sehr bedingt bis
nicht brauchbar.
Schreiben dagegen ist "straight forward" mit 2 Befehlspaketen erledigt und
erheblich schneller
als im Service-Mode. Ohne lange Präambel, Resetpakete und 6-maligem Wiederholen.
Jedes der zwei identischen Pakete hat diesen Bitstrom :
111111111111 0 AAAAAAAA 0 1110CCVV 0
VVVVVVVV 0 DDDDDDDD 0 EEEEEEEE 1
ist also 5 mal 9 Bit + 13 Bit = 58 Bit lang. Nach etwa 20 Millisekunden sollte
die CV geschrieben sein.
Das verlängert die Refresh-Zeit nicht dramatisch und ist zudem relativ selten.
EEEEEEEE ist wie üblich
das Ergebnis der EXOR-Verknüpfung der 4 Bytes.
In meinem Testprogramm verwende ich den nachstehenden Code:
//******************************************************************
//**** Programming
on main ( POM ), können nicht alle Decoder.
****
//**** Nach NMRA
braucht POM 2 Pakete für den Befehl
****
if ( dcc_pom_cv == 1)
{
dcc_byte1 = e_val[4];
// Decoder Adresse
dcc_byte2 = 0b11101100; // Commando-byte
bereitstellen
dcc_byte3 = e_val[2]-1;
// CV Adresse - 1 !!!
dcc_byte4 = e_val[3];
// CV-Wert
dcc_pruef = dcc_byte1^dcc_byte2^dcc_byte3^dcc_byte4;
for ( j = 0; j < 2; j++)
// Paket 2 mal senden
{
for (i = 0; i<14; i++)
// Synch senden >= 10 x 1-Bit
{
OCR1AL = 57;
// ergibt 58 Mikrosek., wegen 8 Takte Int.
bitsend();
}
OCR1AL = 115;
// 0-Bit senden mit 116 Mikrosekunden
bitsend();
tes = 128;
// Testbyte vorbereiten auf Bit 7
for ( i = 0; i <8; i++)
// Deco-Adresse
{
if (dcc_byte1 & tes) OCR1AL = 57;
// 1-Bit senden
else OCR1AL = 115;
// 0-Bit senden
bitsend();
tes = tes >> 1;
}
OCR1AL = 115;
// 0-Bit senden
bitsend();
tes = 128;
// Testbyte vorbereiten auf Bit 7
for ( i = 0; i <8; i++)
// Kommando senden
{
if (dcc_byte2 & tes) OCR1AL = 57;
// 1-Bit senden
else OCR1AL = 115;
// 0-Bit senden
bitsend();
tes = tes >> 1;
}
OCR1AL = 115;
// 0-Bit senden
bitsend();
tes = 128;
// Testbyte vorbereiten auf Bit 7
for ( i = 0; i <8; i++)
// CV-Adresse
{
if (dcc_byte3 & tes) OCR1AL = 57;
// 1-Bit senden
else OCR1AL = 115;
// 0-Bit senden
bitsend();
tes = tes >> 1;
}
OCR1AL = 115;
// 0-Bit senden
bitsend();
tes = 128;
// Testbyte vorbereiten auf Bit 7
for ( i = 0; i <8; i++)
// CV-Wert
{
if (dcc_byte4 & tes) OCR1AL = 57;
// 1-Bit senden
else OCR1AL = 115;
// 0-Bit senden
bitsend();
tes = tes >> 1;
}
OCR1AL = 115;
// 0-Bit senden
bitsend();
tes = 128;
// Testbyte vorbereiten auf Bit 7
for ( i = 0; i <8; i++)
// Prüfbyte
{
if (dcc_pruef & tes) OCR1AL = 57;
// 1-Bit senden
else OCR1AL = 115;
// 0-Bit senden
bitsend();
tes = tes >> 1;
}
OCR1AL = 57;
// 1-Bit senden
bitsend();
} // Ende for (zweimal senden)
dcc_pom_cv = 0;
// Auftrag fertig
} // Ende if (dcc_pom_cv == 1)
Ich habe als Testobjekt einen LokPilot V3.0 von ESU
verwendet, mit dem das einwandfrei
funktioniert. Ob sich andere Decoder auch so benehmen weiß ich aber nicht!
Jonathan Bohmer, im April 2009