Top👍
genau das war mein Fehler.
Jetzt funktioniert die Auswertung lokal.
Wenn alles sauber verbaut ist, wird es noch vorgestellt.
Top👍
genau das war mein Fehler.
Jetzt funktioniert die Auswertung lokal.
Wenn alles sauber verbaut ist, wird es noch vorgestellt.
Hallo,
ich möchte Tasmota auf einem ESP32 als BLE->MQTT Bridge benutzen, um meinen Radonsensor „Radoneye RD200“ in fhem einzubinden. Das Lesen des Radonwerts per Skript funktioniert und über den Bereich >E kann ich auch auf den relevanten Teil der Antwort mit radon=sb(rad 4 8) zugreifen:
Script: performs "BLEOp M:xxxxxxxxxxxx/1 s:00001523-1212-efde-1523-785feabcd123 c:00001525-1212-efde-1523-785feabcd123 w:0x50 r go"
MQT: tele/DVES_5EC8D4/BLE = {"BLEOperation":{"opid":"456","stat":"3","state":"DONEREAD","MAC":"xxxxxxxxxxxx","svc":"00001523-1212-efde-1523-785feabcd123","char":"00001525-1212-efde-1523-785feabcd123","read":"50105C8FA23FA4709D3F00000000070008000000"}}
radon = 5C8FA23F
Nun wäre es noch schön, den Radonwert radon = 5C8FA23F direkt in Tasmota in eine Dezimalzahl umzuwandeln. Der hex-Wert ist eine Gleitkommadarstellung nach IEEE 754, little endian.
Ich könnte nun versuchen, mit den im Script-Editor vorhandenen Möglichkeiten den Hex-Wert in binär umzuwandeln, daraus Exponent und Mantisse zu bestimmen und schließlich die Dezimalzahl ermitteln. Ich frage mich aber, ob es nicht über irgendeine Funktion die ich übersehen habe viel einfacher geht.
Hat jemand eine Idee?
Hat jemand eine Idee?
Hallo, fürs konvertieren
hd("hstr") = converts hex number string to a decimal number
in deinem fall zB
radondez=hd(radon)
Hallo,
leider ist das nicht was ich suche. hd("hstr") wandelt nur hex in dezimal um, z.B. hd(„A“)=10.00. Der Sensor gibt aber eine Gleitkommazahl nach IEEE754 aus.
In Python würde man z.B. struct.unpack verwenden. Mit den Möglichkeiten im Script Editor ist es aufwendiger, falls es keine spezielle Funktion irgendwo dafür gibt:
Read (hex): 50103333B33F7B14CE3F000000000000
Teil der den Wert enthält extrahieren (hex): 3333B33F
Der Wert muss nach binär konvertiert werden, wobei auch die Endianness geändert werden muss 3333B33F -> 3FB33333
3FB33333 -> 00111111101100110011001100110011
Das erste Bit ist das Vorzeichen, dann folgen 8 Bit für den Exponenten und schließlich die Mantisse. Die wieder von binär nach dezimal wandeln und die Gleitkommazahl berechnen (und mit 37 multiplizieren, um von pCi/L nach Bq/m^3 umzurechnen)
mantissa (hex): 333333
mantissa (dec): man=1.40
exponent: exp=0.97
decimal value in Bq/m3 = (Vorzeichen * 2^exp*(man/2^23+1)*37 =50.30
Im Prinzip klappt das mit dem folgenden Skript. Allerdings ist es ungenau, weil pow( x y) bei mir nicht richtig rechnet:
pow(2 0)=0.97 oder pow(3 2)= 8.74
Hm, …
Vielleicht könnte ich die Decodierung im sml Protokoll nutzen – mal sehen
Script (geht natürlich noch hübscher...)
>D 32
;strings
rad=""
dec=""
s=""
e=""
m=""
timer=0
val=0
;loop parameters
i=0
j=0
k=0
;IEEE754 exponent, mantissa
exp=1
man=0
>S
timer+=1
if timer>=30
then
print timer=%timer%
timer=0
=>BLEOp M:xxxxxxxxxxxx/1 s:00001523-1212-efde-1523-785feabcd123 c:00001525-1212-efde-1523-785feabcd123 w:0x50 r go
=#cov
endif
>E
rad=BLEOperation#read
;convert value from IEEE754 to decimal
#cov
is(0 "0000|0001|0010|0011|0100|0101|0110|0111|1000|1001|1010|1011|1100|1101|1110|1111|")
is1(0 "0|1|2|3|4|5|6|7|8|9|A|B|C|D|E|F|")
dec=""
s=""
e=""
m=""
print hex reading: %rad%
for i 11 5 -2
;binary value of re-ordered hex
dec+=is[hd(sb(rad i-1 1))+1]+is[hd(sb(rad i 1))+1]
next
rad=sb(rad 4 8)
print hex value: %rad%
print binary value: %dec%
;calc mantissa
m="0"+sb(dec 9 23)
;make hex again
for i 0 5 1
;loop nesting using subroutine
=#nest(m 4*i)
next
man=hd(s)/8388608+1
print mantissa (hex): %s%
print mantissa: %man%
;calc exponent
s=""
m=sb(dec 1 8)
=#nest(m 0)
=#nest(m 3)
exp=pow(2 hd(s)-127)
print exponent: %exp%
;sign (btw. should be 0, as value is always positive)
if "1"==sb(dec 0 1)
then val=-1*exp*man*37
else val=1*exp*man*37
endif
print decimal value in Bq/m3: %val%
;test pw(x y)
exp=pow(3 2)
print pow(3 2)=%exp%
#nest(m k)
for j 1 16 1
if is[j]==sb(m k 4)
then s+=is1[j]
break
endif
next
Alles anzeigen
Ausgabe
23:29:48.810 timer=30.00
23:29:48.813 Script: performs "BLEOp M:xxxxxxxxxxxx/1 s:00001523-1212-efde-1523-785feabcd123 c:00001525-1212-efde-1523-785feabcd123 w:0x50 r go"
23:29:48.832 MQT: stat/DVES_5EC8D4/RESULT = {"BLEOp":{"opid":116,"u":0}}
23:29:48.837 hex reading: 50103333B33F7B14CE3F000000000500
23:29:48.845 hex value: 3333B33F
23:29:48.848 binary value: 00111111101100110011001100110011
23:29:48.861 mantissa (hex): 333333
23:29:48.864 mantissa: 1.40
23:29:48.874 exponent: 0.97
23:29:48.878 decimal value in Bq/m3: 50.30
23:29:48.882 pow(3 2)=8.74
Alles anzeigen
Hallo irhexin
Anbei scripter Version mit einer Hex to float Konvertierung
res=hf("5C8FA23F")
oder bei reverse byte order
res=hf("3FA28F5C" r)
die pow Function ist eine sehr ungenaue Schätzung da die genaue power Funktion extrem viel Code und Rechenzeit verbrauchen würde.
Gruß Gerhard
Hallo Gerhard,
das ist natürlich klasse – vielen Dank! Es kann ein paar Tage dauern, bis ich zum Testen komme. Dann melde ich mich noch einmal.
Viele Grüße,
Gunnar
Hallo Gerhard,
erst dachte ich es funktioniert nicht, aber es lag nur an der Byte-order:
22:49:39.845 res=hf("3F800000") = 0.00
22:49:39.847 res=hf("0000803F", r)= 1.00
Ich hätte es genau anders herum erwartet: "3F800000" sollte m.E. "1" entsprechen.
Viele Grüße,
Gunnar
Hallo,
dieser Beitrag hier hat mir schon viel geholfen, dafür schon mal großen Dank.
Ziel ist es mit dem Ändern einer Variable einen bestimmten Teil des Scripts via MQTT auszuführen.
Das klappt soweit und mit dem MQTT Kommando
cmnd/tasmota_xxxxxx/script mit der Payload ">TSD" bzw. ">TRC" (Script siehe unten)
Mein Problem ist nun die Serielle Kommunikation (Natürlich ist meine Tasmota Version mit enstprechnden Modulen "gebacken")
<SNIP>
#ifndef USE_SCRIPT
#define USE_SCRIPT // adds about 17k flash size, variable ram size
#endif
#ifdef USE_RULES
#undef USE_RULES
#endif
#ifndef USE_SCRIPT_SERIAL
#define USE_SCRIPT_SERIAL
#endif
#ifndef USE_BUTTON_EVENT
#define USE_BUTTON_EVENT
#endif
#ifndef SCRIPT_POWER_SECTION
#define SCRIPT_POWER_SECTION
#endif
#ifndef USE_SCRIPT_WEB_DISPLAY
#define USE_SCRIPT_WEB_DISPLAY
#endif
#ifndef SUPPORT_MQTT_EVENT
#define SUPPORT_MQTT_EVENT
#endif
#ifndef USE_SCRIPT_SUB_COMMAND
#define USE_SCRIPT_SUB_COMMAND
#endif
#ifndef USE_SCRIPT_STATUS
#define USE_SCRIPT_STATUS
#endif
Die Doku zur Seriellen Kommunikation ist die folgende:
Serial IO support #define USE_SCRIPT_SERIAL
so(RXPIN TXPIN BR)
open serial port with RXPIN, TXPIN and baudrate BR with 8N1 serial mode (-1 for pin means dont use)
so(RXPIN TXPIN BR MMM)
open serial port with RXPIN, TXPIN and baudrate BR and serial mode e.g 7E2 (all 3 modechars must be specified)
so(RXPIN TXPIN BR MMM BSIZ)
open serial port with RXPIN, TXPIN and baudrate BR and serial mode e.g 7E2 (all 3 modechars must be specified) ans serial IRW buffer size
sc()
close serial port
sw(STR)
write the string STR to serial port
swb(NUM)
write the number char code NUM to serial port
sa()
returns number of bytes available on port
sr()
read a string from serial port, all available chars up to string size
sr(X)
read a string from serial port until charcode X, all available chars up to string size or until charcode X
srb()
read a number char code from serial port
sp()
read a number char code from serial port, dont remove it from serial input (peek)
Leider habe ich es bisher nicht geschaft irgendetwas gescheit so senden oder zu empfangen.
Daher ist meine Vermutung das ich die RX/TX Pins nicht ordendlich angegeben habe.
TX und RX ist physikalisch auf die beiden orignal Pins am Wemos D1 Mini dafür (TX GPIO1/Rx GPIO3) gelegt und die sind in TASMOTA "Module parameters" auch entsprechend gesetzt.
Befor ich das Serial logging mit "Seriallog 0" abgeklemmt habe wurde mir das Logging am angeschlossenen Terminal (Minicom 115220 8N1) angezeigt, daher gehe ich davon aus das die physikalische Verkabelung mit dem USB Serial-Wandler an dem das Minicom-Terminal hängt O.K. ist.
Ich habe als TX/RX Pins schon getestet: Pysikalischer Pin am Wemos D1 Mini also 15/16, GPIO Pins am ESP8266 1/3 bzw. D1/D3 Ich habe auch TX/RX schon mal auf andere PINS D5/D6 umgelegt (sowohl phkysikalisch als auch in den TASMOTA "Module parameters" und im Script aber auch ohne Erfolg.
Frage nun, hat jemand schon Erfahrungen mit Serieller Kommunikation (senden und empfangen) mit TASMOTA Script (erfolgreich) realisiert und kann weiterhelfen)
# Mein Script zur Zeit (TX und RX Pins beim senden und empfangen unterschiedlich gesetzt, da ich hauptsäschlich am Senden gerabeitet und getestet habe!)
>D
TOUT=0
TSD=0
TRC=0
>S
if upd[TSD]>0
then
=>print Transmit received
so(3 1 115200)
delay(50)
sw(135)
=>Publish tele/tasmota_xxxxxx/TSTATUS TRANSMIT
ransmit
delay(50)
sc()
endif
if upd[TRC]>0
then
=>print Read received
so(15 16 115200)
delay(50)
sw(149 1 21)
delay(100)
TOUT = sr()
=>Publish tele/tasmota_xxxxx/TSTATUS RECEIVED %TOUT%
delay(50)
sc()
endif
Im Vorraus schon mal vielen Dank
Der FreiFunker
Hallo,
du darfst in Tasmota PIN setup nichts definieren, nur im Script.
wenn du was empfangen willst must du den seriellen port in >B öffnen und offen lassen.
wenn du nur senden willst kannst du immer öffnen und danach wieder schliessen
Gruß Gerhard
Hallo Gerhard,
danke für die Info.
Also in >B beim Boot den Port öffnen und nicht wieder schliessen.
Aber wie setze ich die PIN's? GPIO oder Pin am IC?
Der FreiFunker
Es wird nur eine serielle Schnittstelle zugleich unterstützt.
Wenn du die in >B öffnest gibst du ja die Pins an, die verwendet werden sollen.
Wenn du nur Senden willst kann du aber auch 2 verschiedene Pins Sets benutzen weil du bei close die Pins ja wieder freigibst.
Vielleicht solltest du mal erklären was genau du bezwecken willst.
Eine Serielle Schnittstelle reicht mir.
Aber: Aber wie setze ich die PIN's? im Script?
GPIO oder Pin am IC?
Also ganz konkret, wie muss die Zeile:
so(RXPIN TXPIN BR)<br>
aussehen wenn ich beim Wemos D1 Mini an den Originalen TX / RX Pins hänge und eine BR von 115200 brauche?
so(?? ?? 115200) ?????????????????????????????????
Um Deine Frage zu beantworten was ich erreichen möchte.
Es geht darum einen Roomba Staubsauger Roboter mittels Serieller Komandos Smart-Home fähig zu machen.
Dazu ist "interaktion" über die Seriellen Schnittstelle des Gerätes nötig, sprich Kommandos senden (In Zahlenform)
Und auch die Antwort auf ein Kommando (Status) zurück zu bekommen.
Der FreiFunker
du musst einfach die GPIO Nummer (nicht die D Nummer von WEMOS) angeben.
das hast du doch oben schon richtig eingestellt
so(3 1 115200)
am besten erst mal was senden und am PC am Terminal überwachen.
die Steuerung deines Saugers sollte machbar sein.
Hallo,
ich habe die Vorschläge jetzt mal umgesetzt und fast den ganzen Tag gestern rumgetestet:
Aktuelles Tasmota Skript:
>D
TOUT=0
TSD=0
TRC=0
>B
so(3 1 115200)
delay(50)
=>print Serial setup done so(3 1 115200)
>S
if upd[TSD]>0
then
=>print Transmit received
so(3 1 115200)
delay(50)
sw(135)
=>Publish tele/tasmota_xxxxxx/TSTATUS TRANSMIT transmit
delay(50)
endif
if upd[TRC]>0
then
=>print Read received
so(15 16 115200)
delay(50)
sw(149 1 21)
delay(100)
TOUT = sr()
=>Publish tele/tasmota_xxxxx/TSTATUS RECEIVED %TOUT%
delay(50)
endif
MINICOM Terminal Output:
ets Jan 8 2013,rst cause:2, boot mode:(3,6)
load 0x4010f000, len 3584, room 16
tail 0
chksum 0xb0
csum 0xb0
v3969889e
~ld
00:00:00.001 HDW: ESP8266EX
00:00:00.050 CFG: Loaded from flash at F9, Count 67
TASMOTA GUI Log:
00:00:00.064 Project tasmota - Tasmota Version 9.5.0.8(tasmota)-2_7_4_9(2022-01-21T09:59:35)
00:00:00.067 Script: nv=3, tv=0, vns=13, ram=62
00:00:00.119 Serial setup done so(3 1 115200)
00:00:00.557 WIF: Connecting to AP1 tyrconnell24 Channel 11 BSSId 10:XX:XX:E6:XX:71 in mode 11n as tasmota-xxxxxx-7157...
00:00:01.752 WIF: Connected
00:00:02.004 HTP: Web server active on tasmota-xxxxxx-7157 with IP address 192.168.1.20
10:35:47.013 MQT: Attempting connection...
10:35:47.329 MQT: TLS connected in 313 ms, max ThunkStack used 3700
10:35:47.330 MQT: Connected
10:35:47.344 MQT: tele/tasmota_xxxxxx/LWT = Online (retained)
10:35:47.351 MQT: cmnd/tasmota_xxxxxx/POWER =
10:35:47.441 MQT: tele/tasmota_1xxxxxx/INFO1 = {"Info1":{"Module":"Generic","Version":"9.5.0.8(tasmota)","FallbackTopic":"cmnd/DVES_xxxxxx_fb/","GroupTopic":"cmnd/tasmotas/"}}
10:35:47.456 MQT: tele/tasmota_1xxxxxx/INFO2 = {"Info2":{"WebServerMode":"Admin","Hostname":"tasmota-xxxxxx-7157","IPAddress":"192.168.1.20"}}
10:35:47.474 MQT: tele/tasmota_1xxxxxx/INFO3 = {"Info3":{"RestartReason":"Software/System restart"}}
10:35:50.446 QPC: Reset
10:35:51.440 MQT: tele/tasmota_1xxxxxx/STATE = {"Time":"2022-01-24T10:35:51","Uptime":"0T00:00:09","UptimeSec":9,"Heap":18,"SleepMode":"Dynamic","Sleep":50,"LoadAvg":19,"MqttCount":1,"Wifi":{"AP":1,"SSId":"txxxxxx4","BSSId":"10:XX:XX:E6:XX:71","Channel":10,"Mode":"11n","RSSI":38,"Signal":-81,"LinkCount":1,"Downtime":"0T00:00:03"}}
10:36:39.483 MQT: stat/tasmota_xxxxxx/RESULT = {"Script":">TSD"}
10:36:40.371 Transmit received
10:36:40.423 Script: performs "Publish tele/tasmota_xxxxxx/TSTATUS TRANSMIT transmit"
10:36:40.437 MQT: tele/tasmota_xxxxxx/TSTATUS = TRANSMIT transmit
Was sich zeigt ist das die Entscheidung in Script funktioniert, es aber zu keinem Empfang im Terminal kommt.
Die "Bootmeldung" kommt interessanterweise durch auch mit "seriallog 0"
Die Frage nun was mache ich falsch?
Ich würde erwarten das ich:
a.) Im Terminal vom booten nichts sehe
b.) Im Terminal eine 135 ankommt (Ich hab auch gesteren zum test mal Buchstaben gesendet, gleiches Verhalten)
Ich fürchte immer noch das mein Setup nicht sauber ist.
Hat das schon mal jemand erfolgreich gemacht?
Der FreiFunker
dein script hat Fehler. du öffnest den port 3 mal!
fang doch mal ganz einfach an.
>D
>B
so(3 1 115200)
>S
if upsecs%10==0
then
sw("hallo welt")
print write
endif
Hallo,
Du hast damit recht das ich den Port 3 mal geöffnet habe.
Manchmal sieht man den Wald vor lauter Bämen nicht.
Leider habe ich mit Deinem ganz einfachen Script genau das selbe Verhalten:
MINICOM Terminal Output:
load 0x4010f000, len 3584, room 16
tail 0
chksum 0xb0
csum 0xb0
v3969889e
~ld
00:00:00.001 HDW: ESP8266EX
00:00:00.050 CFG: Loaded from flash at F6, Count 78
TASMOTA GUI Log:
15:13:33.504 MQT: tele/tasmota_xxxxxx/INFO3 = {"Info3":{"RestartReason":"Software/System restart"}}
15:13:36.473 QPC: Reset
15:13:37.397 MQT: tele/tasmota_xxxxxx/STATE = {"Time":"2022-01-24T15:13:37","Uptime":"0T00:00:09","UptimeSec":9,"Heap":18,"SleepMode":"Dynamic","Sleep":50,"LoadAvg":19,"MqttCount":1,"Wifi":{"AP":1,"SSId":"txxxxxx4","BSSId":"10:XX:XX:E6:XX:71","Channel":11,"Mode":"11n","RSSI":50,"Signal":-75,"LinkCount":1,"Downtime":"0T00:00:03"}}
15:13:38.411 write
15:13:48.387 write
15:13:58.411 write
15:14:08.384 write
15:14:18.405 write
Es wird immer noch die Boot Meldung ausgegeben und es erscheint kein "hallo welt" alle 10 Sekunden.
Der FreiFunker
ok, genau dieses mini script funktioniert bei mir (auf einem WEMOS d1 und auf einen ESP32)
Danke für die Bestätigung bzw. die Hilfe.
Denn dann konnte es ja eigendlich nur noch an TASMOTA selbst liegen.
Ich habe also nun noch einmal TASMOTA ganz frisch compiliert (Project tasmota - Tasmota Version 2022.01.3(tasmota)-2_7_4_9(2022-01-24T15:31:29)) und
auf den Wemos D1 Mini geflasht.
Und siehe da, jetzt geht auch das Mini-Script.
War wohl ein schon gefixter Bug.
Mittlerweile läuft auch meine Skript Kreation, wichtig waren hier die " " innerhalb der Klammer beim sw("text")
Und wenn es einen CR also ein "Carrige Return" braucht, damit der Befehl auch ausgeführt wird dann tut es ein \n hinter dem Kommando.
Villeicht hilft das ja dem einen oder anderen irgendwie weiter.
Ich sage auf jeden Fall noch mal herzlichen Dank für die Geduld und die Hilfe.
Nächste Hürde wird das "Einlesen" der Rückgabe.
Der FreiFunker
Hallo zusammen,
ich benutz einen ESP8266 unter Tasmota um meinen Stromzähler auszulesen.
Dank Scripting und SML funktioniert das auch super.
Leider verliert der Tasmota sein Gedächtnis abundan nach einem Verlust der Versorgungspannung (Sicherung, etc...).
Die vordefinierten Werte im Image (wie SSID, Passphrase, usw.) behält er natürlich und startet dann auch entsprechend.
Allerdings sind Script und "Script enable" danach auf Default.
Kann man auch "Script enable" und den Inhalt (Source) des Scripts irgendwie fest ins Image eindefinieren ??
Danke.
VG
verliert der Tasmota sein Gedächtnis abundan nach einem Verlust der Versorgungspannung
Hallo, normal geht da nichts verloren,
ein Script wird aber disabled bei fehlern / exceptions /reboots
würde Reset 5 mal ausführen, evtl neu flashen
und Script nach Möglichkeit kürzen / verändern.
fest ins Image eindefinieren kenne ich nur bei Rules.