Das Protokoll FT1.2
Der Datenaustausch zwischen Power-Line-Modem und JControl-System findet über das standardisierte FT1.2-Protokoll statt (IEC EN60870-5-1). Dieses ist in der Klasse FT1_2 der JControl API bereits implementiert und kann von Anwendungsprogrammen direkt verwendet werden. Das FT1.2-Protokoll sorgt für eine sichere Datenkommunikation, indem automatisch Prüfsummen berechnet und verifiziert werden. Bei Übertragungsfehlern werden die Datenpakete bis zu 3 mal wiederholt.
Das Grundgerüst
Der folgende Quelltext kann als allgemeines Grundgerüst für Anwendungen mit Power-Line-Kommunikation herangezogen werden. Er zeigt, wie die FT1_2-Klasse initialisiert und ein FT1_2EventListener installiert wird. Der Listener ist erforderlich, um eingehende Power-Line-Datagramme auf Java-Ebene zu empfangen.
| 1 | import java.io.IOException; |
| 2 | |
| 3 | import jcontrol.comm.FT1_2; |
| 4 | import jcontrol.comm.FT1_2EventListener; |
| 5 | import jcontrol.comm.RS232Selector; |
| 6 | import jcontrol.io.Buzzer; |
| 7 | |
| 8 | /** |
| 9 | * <p>Basic code for power-line communication using the <code>class |
| 10 | * FT1_2</code>.</p> |
| 11 | * |
| 12 | * <p>(C) DOMOLOGIC Home Automation GmbH 2003</p> |
| 13 | */ |
| 14 | public class PowerLineExample_Base implements FT1_2EventListener { |
| 15 | |
| 16 | /** FT1.2 protocol */ |
| 17 | static FT1_2 ft12; |
| 18 | |
| 19 | /** System buzzer */ |
| 20 | Buzzer buzzer = new Buzzer(); |
| 21 | |
| 22 | /** |
| 23 | * Init FT1.2 protocol |
| 24 | */ |
| 25 | public PowerLineExample_Base() { |
| 26 | // switch RS232 to power-line modem |
| 27 | RS232Selector.selectPort(RS232Selector.INTERNAL); |
| 28 | |
| 29 | try { |
| 30 | // instantiate FT1_2 protocol |
| 31 | ft12 = new FT1_2(); |
| 32 | // set ourself as the FT1_2EventListener |
| 33 | ft12.setListener(this); |
| 34 | } catch (java.io.IOException e) { |
| 35 | // 2 second error beep |
| 36 | buzzer.on((short)300, (short)2000); |
| 37 | // read errorcode to reset error flag |
| 38 | ft12.errorCode(); |
| 39 | } |
| 40 | } |
| 41 | |
| 42 | |
| 43 | /** |
| 44 | * FT1.2 event listener. This method is called any time |
| 45 | * a power-line datagram drops in. |
| 46 | * |
| 47 | * @see jcontrol.comm.FT1_2EventListener#onIndication(byte[], int) |
| 48 | */ |
| 49 | public void onIndication(byte[] udat, int control) { |
| 50 | try { |
| 51 | switch(control){ |
| 52 | case FT1_2.CF_PRM_SEND_UDAT: |
| 53 | ft12.sendACK(udat); |
| 54 | break; |
| 55 | case FT1_2.CF_PRM_REQ_STATUS: |
| 56 | ft12.sendResponse(null); |
| 57 | break; |
| 58 | case FT1_2.CF_PRM_REQ_CLASS1: |
| 59 | byte[] buf=new byte[10]; |
| 60 | ft12.sendResponse(buf); |
| 61 | break; |
| 62 | } |
| 63 | } catch(IOException e){} |
| 64 | } |
| 65 | |
| 66 | |
| 67 | /** |
| 68 | * Main method. Program execution starts here. |
| 69 | */ |
| 70 | public static void main(String[] args) { |
| 71 | new PowerLineExample_Base(); |
| 72 | } |
| 73 | } |
Listing 1: PowerLineExample_Base.java
Zur Initialisierung der FT1.2-Kommunikation genügt die Instantiierung des Konstruktors. Um den RS232-Port des JControl/PLUI mit dem integrierten Power-Line-Modem zu verbinden, muss die Methode selectPort der Klasse RS232Selector mit dem Parameter RS232Selector.INTERNAL aufgerufen werden. Die Methode onIndication() wird von FT1_2 jedesmal aufgerufen, wenn Daten vom Power-Line-Modem (oder auch BCU, Bus Control Unit) empfangen wurden. Dabei kann es sich um eine der folgenden drei Kommunikationstypen handeln:
-
CF_PRM_SEND_UDAT: Ein user datagram wurde empfangen. Dieses kann beliebige Daten enthalten, die von einer entfernten Applikation über Power-Line gesendet wurden. Der Empfang solcher UDATs ist der Normalfall und wird für den Austausch von Steuer- und Regelkommandos mit anderen Power-Line-Geräten verwendet. UDATs werden außerdem benutzt, um den Erfolg oder Misserfolg eines Kommunikationsversuchs zu quittieren.
-
CF_PRM_REQ_STATUS: Dies ist ein FT1.2-Statusrequest. Er sollte durch einen Aufruf der Methode sendResponse(null) beantwortet werden.
-
CF_PRM_REQ_CLASS1:: Auch dies ist eine FT1.2-protokollspezifische Anfrage, die hier nicht näher erläutert werden soll. Die korrekte Antwort ist sendResponse(buf).