===== Junkers Gastherme mit Heatronic 2 und Can-Bus-Regler ===== Die Modelle mit //Heatronic 2// wurden zwischen Ende der 90er Jahre und 2010 gebaut und haben oft die Typenbezeichnung -5 oder -6, z.B. also //ZWR 18-6//, dazu kommen etliche Brennwertgeräte aus dieser Zeit. Im Zweifelsfall lohnt ein Blick in die Installationsanleitung. Diese Modelle können mit einem Can-Bus-fähigen Regler ausgestattet werden. Dieser Bus ist nicht zu verwechseln mit dem der [[hardware:channels:heating_control:gastherme_buderus|Heatronic 3]]. Achtung: Das heizungsseitige Can-Bus Modul //BM1// ist nicht standardmäßig eingebaut, sondern Teil des entsprechenden Raum- oder Außentemperaturreglers, konkret sind das die Regler //TR220//, //TA250// und //TA270//. Ohne einen dieser Regler funktioniert es nicht. Zu Hardware und der Junkers-spezifischen Implementierung des Can-Protokolles siehe: [[https://www.mikrocontroller.net/topic/81265]] Auf der Volkszähler-Seite wird natürlich ebenso ein Can-Bus-Modul benötigt, zu empfehlen ist das [[https://www.skpang.co.uk/products/pican2-can-bus-board-for-raspberry-pi-2-3|PiCan2]] Board, das speziell für den Raspberry Pi entwickelt wurde und sich 1:1 aufstecken lässt. Für Besitzer eines RPi 4 gibt es das [[https://www.skpang.co.uk/products/pican3-can-bus-board-for-raspberry-pi-4-with-3a-smps-rtc|PiCan3]], das praktischerweise auch noch über eine Real Time Clock verfügt, die ja für den "zeitlosen" Raspberry durchaus nützlich sein kann. Dazu gibt es einen passenden Schraubensatz und auch ein für diesen "Doppeldecker" passendes Gehäuse. Verbunden werden die Busmodule von der Heizung (oder auch dem Regler) mit dem Raspberry mittels einer dreiadrigen Leitung, //Can-High//, //Can-Low// und //Ground//. Da der Bus sowohl an der Heizung als auch am Regler bereits terminiert ist, sollte es nur eine kurze Stichleitung von ca. 30cm sein. Hier die Belegung auf der Junkers Seite (Klemme BM1 und TA/TR) sowie des PiCan (2/3), jeweils entsprechend der jeweiligen Anleitung des Herstellers und ohne Gewähr: Junkers --- PiCan --- empfohlene Adernfarbe 2 Can-High 1 (Gelb) 6 Can-Low 2 (Grün) 4 Ground 3 (Weiss) Keinesfalls dürfen die Anschlüsse für 24V+ (Junkers Klemme 1) sowie 12V+ (PiCan Pin 4) verbunden werden. Bei der Verdrahtung bitte sorgfältig und gewissenhaft vorgehen, denn eine falsche Belegung oder gar ein Kurzschluss kann durchaus empfindliche Elektronik zerstören. Damit der Raspberry mit dem Board kommunizieren kann, muss im ///boot/config.txt// der SPI Bus aktiviert und einige weitere Eistellungen vergenommen werden, konkret sind das folgende Zeilen: dtparam=spi=on dtoverlay=mcp2515-can0,oscillator=16000000,interrupt=25 dtoverlay=spi-bcm2835-overlay Im nächsten Schritt die Clientprogramme installieren, die auf dem Socket-Can aufsetzten, sowie den GNU Rechner ''bc'' und den BSD Mailer ''mailx'' (falls noch nicht vorhanden): apt-get install can-utils bc bsd-mailx Einmal booten, dann sollte das Board erkannt werden... zum Testen mal das Interface per Hand aufsetzen: ip link set can0 up type can bitrate 10000 listen-only on Die Bitrate ist wichtig (muss zum Gegenüber passen!), der Parameter //listen-only// stellt sicher, dass wirklich nur mitgehört wird nichts den Bus durcheinander bringt. Wenn nun ein ifconfig can0 ein Interface zeigt, inklusive ankommender Datenpakete, kann es weitergehen zum nächsten Schritt. Ein candump can0 sollte nun die eingehenden Datenpakete ausgeben, die nun anhand dieser {{:hardware:channels:heating_control:can_tabelle.xlsx|Tabelle}} ausgewertet und via Skript an die VZ [[software:middleware|Middleware]] übergeben werden können. Beispielhaft dazu das folgende Skript //canlogger.sh//, das nur als Vorlage dienen kann und an die konkrete Umgebung angepasst werden muss. Im Header werden dazu alle Werte mit Can-ID (''CANDUMP_IN''), Beschreibung (''HUMAN_INFO''), sowie die //UUID// des Volkszählers, unter der die gelesenen Werte gespeichert werden sollen (''VZ_UUIDFOR''), mit Ordnungszahl definiert. Zusätzlich gibt es die Möglichkeit, mit der Variable ''VZ_UUIDFORBS'' und einem Middleware-Kanal vom Typ //Allgemeiner Impulszähler// die Anzahl der Brennerstarts zu zählen. Gerade bei der Optimierung von Heizungsanlagen kann dies hilfreich sein. Die Variable ''MAXP'' muss der höchsten verwendeten Zahl entsprechen, also der Anzahl der verwendeten Kanäle plus, falls gewünscht, dem Eintrag für die Versendung einer Heatronic-Fehlermeldung per Email. Die Verwendung der E-Mail Funktion setzt neben dem bei den Installationsvoraussetzungen bereits genannten BSD client //mailx// auch ein funktionierendes Mailsystem mit oder ohne Internet-Anbindung voraus (z.B. //sendmail//, //postfix//, oder //exim//). Das Skript sollte die Werte des BM1 und des TA/TR, soweit sie in der Tabelle auch enthalten sind, dann korrekt umrechnen. Die im Skript bereits eingetragenen Werte sind Beispiele aus dem Anwendungsfall des Autors. #!/bin/bash # canlogger.sh V3.1 # calling the script with "test" parameter will display the values on screen instead of sending to VZ export PATH=/usr/bin:/bin case "$1" in test) echo "CAN Logger V3.1 starting on `date` in testing mode" ;; prod) echo "CAN Logger V3.1 starting on `date` in production mode" ;; *) echo "Usage: canlogger.sh {test|prod}" echo " testing mode will display values on screen" echo " production mode will send the values to the VZ Middleware" exit 3 ;; esac CANDUMPER="candump can0" MAIL_SENDER="mailfrom@address.com" MAIL_RECIPIENT="mailto@address.com" CANDUMP_IN[1]="200" HUMAN_INFO[1]="Vorlauf Max" VZ_UUIDFOR[1]="80089ae0-fa81-11e9-bdc6-b99d5fa0fe8b" CANDUMP_IN[2]="252" HUMAN_INFO[2]="Vorlauf Soll" VZ_UUIDFOR[2]="af1863e0-fa81-11e9-8d30-337b7499db8e" CANDUMP_IN[3]="201" HUMAN_INFO[3]="Vorlauf Ist" VZ_UUIDFOR[3]="cbf99f10-fa81-11e9-9709-d55e7ad0883e" CANDUMP_IN[4]="203" HUMAN_INFO[4]="Warmwasser Ist" VZ_UUIDFOR[4]="521a0ca0-fa8d-11e9-970f-752aababd342" CANDUMP_IN[5]="20A" HUMAN_INFO[5]="Heizung Ein" VZ_UUIDFOR[5]="a5958bf0-fa8f-11e9-bf34-4f7c2163b201" CANDUMP_IN[6]="209" HUMAN_INFO[6]="Brenner Ein" VZ_UUIDFOR[6]="5ec31d30-fa90-11e9-98b7-3b9f4a33ba29" CANDUMP_IN[7]="251" HUMAN_INFO[7]="Leistung Soll" VZ_UUIDFOR[7]="81f3ed90-7f7b-11ed-90c6-b747fd43b61f" CANDUMP_IN[8]="207" HUMAN_INFO[8]="Aussentemperatur" VZ_UUIDFOR[8]="xxxxxxxx-xxxx-xxxx-xxxx-xxxxxxxxxxxx" CANDUMP_IN[9]="206" HUMAN_INFO[9]="Fehlercode" VZ_UUIDFORBS="d403e120-115a-11ea-b273-05a1540bacf1" typeset -i MAXP=9 typeset -i P=1 typeset -i BR=0 typeset FC="00" while read LINE do while [[ ${P} -le ${MAXP} ]] do if [[ "$( echo -e "${LINE}" | grep "${CANDUMP_IN[${P}]}" | wc -l )" -gt 0 ]] then HEXCODE="$( echo -e ${LINE} | cut -c14-18 | sed 's/ //' )" DECVAL="$( echo -e "ibase=16;obase=A;${HEXCODE}" | bc )" if [[ ( "${CANDUMP_IN[${P}]}" == 206 ) ]] then case "$1" in test) echo -e "$( date "+%H:%M:%S") - ${HUMAN_INFO[${P}]}: ${HEXCODE} (${LINE})" ;; prod) if [[ ( "${HEXCODE}" != "$FC" ) ]] then FC=${HEXCODE} echo "Anlage prüfen: Fehler ${FC}" | mailx -r "${MAIL_SENDER} (Junkers Therme)" -s "Therme Fehler" ${MAIL_RECIPIENT} fi ;; esac break elif [[ '[20A,20B,20C,250,253,254]' =~ "${CANDUMP_IN[${P}]}" ]] then VALUE=${DECVAL} elif [[ ( "${CANDUMP_IN[${P}]}" == 209 ) ]] then VALUE=${DECVAL} if [[ ( "${DECVAL}" -eq 1 ) && ( "${BR}" -eq 0 ) ]] then BR=1 case "$1" in test) echo -e "$( date "+%H:%M:%S") - Brennerstart" ;; prod) RESPONSE="$( wget -4 -O - -q --post-data "" "http://localhost/middleware/data/${VZ_UUIDFORBS}.json" )" if [[ ! ${RESPONSE} == *rows*1* ]] then echo "Error posting to Middleware: ${RESPONSE}" fi ;; esac elif [[ ( "${DECVAL}" -eq 0 ) ]] then BR=0 fi elif [[ ( "${CANDUMP_IN[${P}]}" == 251 ) ]] then VALUE="$( echo "scale=2 ; ${DECVAL} / 255 * 100" | bc )" elif [[ ( "${CANDUMP_IN[${P}]}" == 207 ) ]] then [[ ${HEXCODE} =~ ^F...$ ]] && DECVAL="$( echo -e "ibase=16;obase=A; ${HEXCODE} - FFFF" | bc )" VALUE="$( echo "scale=2 ; ${DECVAL} / 100" | bc | sed -e 's/^-\./-0./' -e 's/^\./0./' )" else VALUE="$( echo "scale=1 ; ${DECVAL} / 2" | bc )" fi case "$1" in test) echo -e "$( date "+%H:%M:%S") - ${HUMAN_INFO[${P}]}: ${VALUE} (${LINE})" ;; prod) RESPONSE="$( wget -4 -O - -q --post-data "value=${VALUE}" "http://localhost/middleware/data/${VZ_UUIDFOR[${P}]}.json" )" if [[ ! ${RESPONSE} == *rows*1* ]] then echo "Error posting to Middleware: ${RESPONSE}" fi ;; esac fi P=${P}+1 done P=1 done < <( ${CANDUMPER} ) Wenn man das Skript dann auf dem VZ-System abgelegt hat, z.B. unter ''/home/pi/bin/'', kann man es dann auch automatisch mittels //systemd-service// starten, dazu folgende Datei nach ''/etc/systemd/system/'' kopieren: [Unit] Description=Can Logger for VZ After=mysql.service middleware.service nginx.service [Service] ExecStartPre=/sbin/ip link set can0 up type can bitrate 10000 listen-only on ExecStart=/home/pi/bin/canlogger.sh prod ExecStopPost=/sbin/ip link set can0 down ExecReload= StandardOutput=syslog Restart=always [Install] WantedBy=multi-user.target Bitte beachten dass der Pfad im ExecStart Statement auch dem tatsächlichen Pfad des Programmes entspricht. Dann sollte sich der Dienst per ''systemctl enable canlogger.service'' und ''systemctl start canlogger.service'' aktivieren lassen. Last not least ein Bild des [[software:frontends:frontend|Frontends]], was den Erfolg und auch die verwendeten [[software:middleware:einrichtung|Kanaltypen]] zeigt: {{ :hardware:channels:heating_control:can-vz.png | Frontend}} Etwas sollte man noch beachten: Damit das heizungseitige Bus-Modul alle Informationen sendet, insbesondere //Brenner- und Heizung/Pumpe Ein// (also die Betriebsstundensensoren), muss der Drehschalter des TR/TA-Reglers auf Info stehen! //**Nachtrag 12.09.2023**// - Skript bereinigt und aktualisiert, es versendet jetzt auch eine E-Mail im Falle eines Fehlercodes der Junkers-Heatronic. Dies setzt ein funktionierendes Mailsystem sowie gültige eingetragene Mail-Adressen im Skript voraus. //**Nachtrag 03.12.2023**// - Skript kann jetzt ohne Anpassung alle Werte des BM1 (Hex Werte beginnend mit 20) und des TA/TR (Hex Werte beginnend mit 25) korrekt umrechnen, soweit diese in der Tabelle enthalten sind.