From 82c2e893e45affe918844b5cb596fff5481b92a1 Mon Sep 17 00:00:00 2001
From: erwin <>
Date: Mon, 25 Dec 2023 17:23:34 +0000
Subject: [PATCH] 10_KNX.pm: additional dpts, (Forum #122582)
git-svn-id: https://svn.fhem.de/fhem/trunk@28312 2b470e98-0d58-463d-a4d8-8e2adae1ed80
---
fhem/CHANGED | 2 ++
fhem/FHEM/10_KNX.pm | 62 ++++++++++++++++++++++++++++++++++++---------
2 files changed, 52 insertions(+), 12 deletions(-)
diff --git a/fhem/CHANGED b/fhem/CHANGED
index 632ad14cf..f49149148 100644
--- a/fhem/CHANGED
+++ b/fhem/CHANGED
@@ -1,5 +1,7 @@
# Add changes at the top of the list. Keep it in ASCII, and 80-char wide.
# Do not insert empty lines here, update check depends on it.
+ - feature: 10_KNX: additional dpt14 subtypes, Forum #122582
+ - bugfix: 00_KNXIO: fix problem IO-write queing, Forum #127792
- bugfix: 74_AutomowerConnect: Commandref corrections, fix start up warning
improve disableForIntervalls handling
- bugfix: 36_Shelly: store newkeys in helper after init
diff --git a/fhem/FHEM/10_KNX.pm b/fhem/FHEM/10_KNX.pm
index 305df3a21..6c737029a 100644
--- a/fhem/FHEM/10_KNX.pm
+++ b/fhem/FHEM/10_KNX.pm
@@ -157,11 +157,14 @@
# dpt9, dpt14: deny use of comma as dec-separator...
# fix replacebyregex
# rework KNX_scan
-# MH 202311xx replace GP_export function
+# MH 20231125 replace GP_export function
# PBP cleanup -1
# correct cmdref links for DbLog attr Fn's
# modified limit Log msg
# dpttypes optimisation (no variable case regex for numbers)
+# MH 202312xx code optimisation KNX_scan, doKNX_scan
+# adapt cmds ref set/get cmd's (new KNXIO feature - send queing)
+# additional dpts 14.xxx - see cmdref
#
# todo replace cascading if..elsif with given
# todo-11/2023 final removal of attr answerReading conversion
@@ -424,21 +427,38 @@ my %dpttypes = (
'dpt14.011' => {CODE=>'dpt14', UNIT=>q{F}, PATTERN=>qr/[-+]?(?:\d+(?:[.]\d*)?(?:e[+-]?\d+)?)/xms, MIN=>-1.4e-45, MAX=>1.7e38}, # capacitance
'dpt14.012' => {CODE=>'dpt14', UNIT=>q{C/m²}, PATTERN=>qr/[-+]?(?:\d+(?:[.]\d*)?(?:e[+-]?\d+)?)/xms, MIN=>-1.4e-45, MAX=>1.7e38}, # charge density surface
'dpt14.013' => {CODE=>'dpt14', UNIT=>q{C/m³}, PATTERN=>qr/[-+]?(?:\d+(?:[.]\d*)?(?:e[+-]?\d+)?)/xms, MIN=>-1.4e-45, MAX=>1.7e38}, # charge density volume
- 'dpt14.014' => {CODE=>'dpt14', UNIT=>q{m²N-1}, PATTERN=>qr/[-+]?(?:\d+(?:[.]\d*)?(?:e[+-]?\d+)?)/xms, MIN=>-1.4e-45, MAX=>1.7e38}, # compressibility
+ 'dpt14.014' => {CODE=>'dpt14', UNIT=>q{m²/N}, PATTERN=>qr/[-+]?(?:\d+(?:[.]\d*)?(?:e[+-]?\d+)?)/xms, MIN=>-1.4e-45, MAX=>1.7e38}, # compressibility
'dpt14.015' => {CODE=>'dpt14', UNIT=>q{S}, PATTERN=>qr/[-+]?(?:\d+(?:[.]\d*)?(?:e[+-]?\d+)?)/xms, MIN=>-1.4e-45, MAX=>1.7e38}, # conductance 1/Ohm
'dpt14.016' => {CODE=>'dpt14', UNIT=>q{S/m}, PATTERN=>qr/[-+]?(?:\d+(?:[.]\d*)?(?:e[+-]?\d+)?)/xms, MIN=>-1.4e-45, MAX=>1.7e38}, # electrical conductivity
'dpt14.017' => {CODE=>'dpt14', UNIT=>q{kg/m²}, PATTERN=>qr/[-+]?(?:\d+(?:[.]\d*)?(?:e[+-]?\d+)?)/xms, MIN=>-1.4e-45, MAX=>1.7e38}, # density
'dpt14.018' => {CODE=>'dpt14', UNIT=>q{C}, PATTERN=>qr/[-+]?(?:\d+(?:[.]\d*)?(?:e[+-]?\d+)?)/xms, MIN=>-1.4e-45, MAX=>1.7e38}, # electric charge
'dpt14.019' => {CODE=>'dpt14', UNIT=>q{A}, PATTERN=>qr/[-+]?(?:\d+(?:[.]\d*)?(?:e[+-]?\d+)?)/xms, MIN=>-1.4e-45, MAX=>1.7e38},
'dpt14.027' => {CODE=>'dpt14', UNIT=>q{V}, PATTERN=>qr/[-+]?(?:\d+(?:[.]\d*)?(?:e[+-]?\d+)?)/xms, MIN=>-1.4e-45, MAX=>1.7e38},
+ 'dpt14.031' => {CODE=>'dpt14', UNIT=>q{J}, PATTERN=>qr/[-+]?(?:\d+(?:[.]\d*)?(?:e[+-]?\d+)?)/xms, MIN=>-1.4e-45, MAX=>1.7e38}, # energy
+ 'dpt14.032' => {CODE=>'dpt14', UNIT=>q{N}, PATTERN=>qr/[-+]?(?:\d+(?:[.]\d*)?(?:e[+-]?\d+)?)/xms, MIN=>-1.4e-45, MAX=>1.7e38}, # force
'dpt14.033' => {CODE=>'dpt14', UNIT=>q{Hz}, PATTERN=>qr/[-+]?(?:\d+(?:[.]\d*)?(?:e[+-]?\d+)?)/xms, MIN=>-1.4e-45, MAX=>1.7e38},
+ 'dpt14.034' => {CODE=>'dpt14', UNIT=>q{rad/s}, PATTERN=>qr/[-+]?(?:\d+(?:[.]\d*)?(?:e[+-]?\d+)?)/xms, MIN=>-1.4e-45, MAX=>1.7e38},
'dpt14.038' => {CODE=>'dpt14', UNIT=>qq{\xCE\xA9}, ## no critic (ValuesAndExpressions::ProhibitEscapedCharacters)
- PATTERN=>qr/[-+]?(?:\d+(?:[.]\d*)?(?:e[+-]?\d+)?)/xms, MIN=>-1.4e-45, MAX=>1.7e38}, # OHM
+ PATTERN=>qr/[-+]?(?:\d+(?:[.]\d*)?(?:e[+-]?\d+)?)/xms, MIN=>-1.4e-45, MAX=>1.7e38}, # Impedance OHM
'dpt14.039' => {CODE=>'dpt14', UNIT=>q{m}, PATTERN=>qr/[-+]?(?:\d+(?:[.]\d*)?(?:e[+-]?\d+)?)/xms, MIN=>-1.4e-45, MAX=>1.7e38},
'dpt14.056' => {CODE=>'dpt14', UNIT=>q{W}, PATTERN=>qr/[-+]?(?:\d+(?:[.]\d*)?(?:e[+-]?\d+)?)/xms, MIN=>-1.4e-45, MAX=>1.7e38},
- 'dpt14.057' => {CODE=>'dpt14', UNIT=>q{cosφ}, PATTERN=>qr/[-+]?(?:\d+(?:[.]\d*)?(?:e[+-]?\d+)?)/xms, MIN=>-1.4e-45, MAX=>1.7e38},
+ 'dpt14.057' => {CODE=>'dpt14', UNIT=>q{cosφ}, PATTERN=>qr/[-+]?(?:\d+(?:[.]\d*)?(?:e[+-]?\d+)?)/xms, MIN=>-1.4e-45, MAX=>1.7e38}, # power factor
+ 'dpt14.058' => {CODE=>'dpt14', UNIT=>q{Pa}, PATTERN=>qr/[-+]?(?:\d+(?:[.]\d*)?(?:e[+-]?\d+)?)/xms, MIN=>-1.4e-45, MAX=>1.7e38},
+ 'dpt14.059' => {CODE=>'dpt14', UNIT=>qq{\xCE\xA9}, ## no critic (ValuesAndExpressions::ProhibitEscapedCharacters)
+ PATTERN=>qr/[-+]?(?:\d+(?:[.]\d*)?(?:e[+-]?\d+)?)/xms, MIN=>-1.4e-45, MAX=>1.7e38}, # Reactance OHM
+ 'dpt14.060' => {CODE=>'dpt14', UNIT=>qq{\xCE\xA9}, ## no critic (ValuesAndExpressions::ProhibitEscapedCharacters)
+ PATTERN=>qr/[-+]?(?:\d+(?:[.]\d*)?(?:e[+-]?\d+)?)/xms, MIN=>-1.4e-45, MAX=>1.7e38}, # Resistance OHM
+ 'dpt14.065' => {CODE=>'dpt14', UNIT=>q{m/s}, PATTERN=>qr/[-+]?(?:\d+(?:[.]\d*)?(?:e[+-]?\d+)?)/xms, MIN=>-1.4e-45, MAX=>1.7e38},
'dpt14.068' => {CODE=>'dpt14', UNIT=>q{°C}, PATTERN=>qr/[-+]?(?:\d+(?:[.]\d*)?(?:e[+-]?\d+)?)/xms, MIN=>-1.4e-45, MAX=>1.7e38},
+ 'dpt14.069' => {CODE=>'dpt14', UNIT=>q{K}, PATTERN=>qr/[-+]?(?:\d+(?:[.]\d*)?(?:e[+-]?\d+)?)/xms, MIN=>-1.4e-45, MAX=>1.7e38},
+ 'dpt14.070' => {CODE=>'dpt14', UNIT=>q{K}, PATTERN=>qr/[-+]?(?:\d+(?:[.]\d*)?(?:e[+-]?\d+)?)/xms, MIN=>-1.4e-45, MAX=>1.7e38},
+ 'dpt14.074' => {CODE=>'dpt14', UNIT=>q{s}, PATTERN=>qr/[-+]?(?:\d+(?:[.]\d*)?(?:e[+-]?\d+)?)/xms, MIN=>-1.4e-45, MAX=>1.7e38},
+ 'dpt14.075' => {CODE=>'dpt14', UNIT=>q{Nm}, PATTERN=>qr/[-+]?(?:\d+(?:[.]\d*)?(?:e[+-]?\d+)?)/xms, MIN=>-1.4e-45, MAX=>1.7e38},
'dpt14.076' => {CODE=>'dpt14', UNIT=>q{m³}, PATTERN=>qr/[-+]?(?:\d+(?:[.]\d*)?(?:e[+-]?\d+)?)/xms, MIN=>-1.4e-45, MAX=>1.7e38},
+ 'dpt14.077' => {CODE=>'dpt14', UNIT=>q{m³/s}, PATTERN=>qr/[-+]?(?:\d+(?:[.]\d*)?(?:e[+-]?\d+)?)/xms, MIN=>-1.4e-45, MAX=>1.7e38}, # volume flow
+ 'dpt14.078' => {CODE=>'dpt14', UNIT=>q{N}, PATTERN=>qr/[-+]?(?:\d+(?:[.]\d*)?(?:e[+-]?\d+)?)/xms, MIN=>-1.4e-45, MAX=>1.7e38}, # weight
+ 'dpt14.079' => {CODE=>'dpt14', UNIT=>q{J}, PATTERN=>qr/[-+]?(?:\d+(?:[.]\d*)?(?:e[+-]?\d+)?)/xms, MIN=>-1.4e-45, MAX=>1.7e38}, # work
+ 'dpt14.080' => {CODE=>'dpt14', UNIT=>q{VA}, PATTERN=>qr/[-+]?(?:\d+(?:[.]\d*)?(?:e[+-]?\d+)?)/xms, MIN=>-1.4e-45, MAX=>1.7e38}, # apparent power
# Access data - receive only
'dpt15' => {CODE=>'dpt15', UNIT=>q{}, PATTERN=>qr/noset/ixms, MIN=>undef, MAX=>undef, SETLIST=>'noset',
@@ -578,6 +598,7 @@ sub KNX_Define2 {
# Add pulldown for attr IODev
my $attrList = $modules{KNX}->{AttrList}; #get Attrlist from Module def
my $IODevs = KNX_chkIODev($hash); # get list of valid IO's
+# $attrList =~ s/\bIODev(?:[:])?(\S+)?/IODev:select,$IODevs/xms;
$attrList =~ s/\bIODev\b([:]\S+)?/IODev:select,$IODevs/xms;
$modules{KNX}->{AttrList} = $attrList;
@@ -2074,7 +2095,7 @@ sub main::KNX_scan {
my $option = $devhash->{GADDETAILS}->{$key}->{OPTION};
next if (defined($option) && $option =~ /(?:set|listenonly)/ixms);
$k++;
- push (@{$iohash->{Helper}->{knxscan}}, $knxdef, $key);
+ push (@{$iohash->{Helper}->{knxscan}}, qq{$knxdef $key});
}
$j++ if ($k > $k0);
}
@@ -2101,12 +2122,11 @@ sub KNX_chkIO {
sub doKNX_scan {
my $iohash = shift // return;
- my $count = scalar(@{$iohash->{Helper}->{knxscan}}); # / 2
+ my $count = scalar(@{$iohash->{Helper}->{knxscan}});
if ($count > 0 ) {
- my $devName = shift(@{$iohash->{Helper}->{knxscan}});
- my $gadName = shift(@{$iohash->{Helper}->{knxscan}});
+ my ($devName,$gadName) = split(/\s/xms, shift(@{$iohash->{Helper}->{knxscan}}),2);
KNX_Get ($defs{$devName}, $devName, $gadName);
- my $delay = ($count % 20 == 0)?2:0.3; # extra delay on each 10th request
+ my $delay = ($count % 10 == 0)?1:0.35; # extra delay on each 10th request
return InternalTimer(gettimeofday() + $delay,\&doKNX_scan,$iohash);
}
delete $iohash->{Helper}->{knxscan};
@@ -2254,6 +2274,8 @@ Examples:
All DPTs: allowed values or range of values are specified here: KNX-dpt
After successful sending, the value is stored in readings <setName> and state.
Do not use wildcards for <deviceName>, the KNX-GW/Bus might be not perfomant enough to handle that.
+ The last sentence is not true for definitions that use module KNXIO as IO-device. The KNXIO Module implements a queing
+ mechanism to prevent KNX-bus overload.
Examples: @@ -2280,8 +2302,9 @@ Examples: this might not be supported by the target KNX-device.
If the GAD is restricted in the definition with "set" or "listenonly", the execution will be refused.
The answer from the bus-device updates the readings <getName> and state.
- Do not use wildcards for <deviceName>, the KNX-GW/Bus might be not perfomant enough to handle that, - use KNX_scan cmd instead. + Do not use wildcards for <deviceName>, the KNX-GW/Bus might be not perfomant enough to handle that. + The last sentence is not true for definitions that use module KNXIO as IO-device. The KNXIO Module implements a queing + mechanism to prevent KNX-bus overload, but you can also use KNX_scan cmd instead. @@ -2528,20 +2551,35 @@ Examples: