mirror of
https://github.com/fhem/fhem-mirror.git
synced 2025-04-17 11:26:03 +00:00
10_ZWave.pm: versionClassRequest + wakeupNoMoreInformation (#Forum: 39525)
git-svn-id: https://svn.fhem.de/fhem/trunk@9102 2b470e98-0d58-463d-a4d8-8e2adae1ed80
This commit is contained in:
parent
2c058b0019
commit
39a3586597
@ -7,6 +7,7 @@ use strict;
|
||||
use warnings;
|
||||
use SetExtensions;
|
||||
use Compress::Zlib;
|
||||
use Time::HiRes qw( gettimeofday );
|
||||
|
||||
sub ZWave_Parse($$@);
|
||||
sub ZWave_Set($@);
|
||||
@ -309,8 +310,9 @@ my %zwave_class = (
|
||||
parse => { "..8503(..)(..)..(.*)" => '"assocGroup_$1:Max $2 Nodes $3"'},
|
||||
init => { ORDER=>10, CMD=> '"set $NAME associationAdd 1 $CTRLID"' } },
|
||||
VERSION => { id => '86',
|
||||
set => { versionClassRequest => 'ZWave_versionClassRequest($hash,"%s")'},
|
||||
get => { version => "11",
|
||||
versionClass => "13%02x" },
|
||||
versionClass => 'ZWave_versionClassGet("%s")' },
|
||||
parse => { "078612(..........)" => 'sprintf("version:Lib %d Prot '.
|
||||
'%d.%d App %d.%d", unpack("C*",pack("H*","$1")))',
|
||||
"098612(..............)" => 'sprintf("version:Lib %d Prot '.
|
||||
@ -418,7 +420,7 @@ ZWave_Initialize($)
|
||||
$hash->{UndefFn} = "ZWave_Undef";
|
||||
$hash->{ParseFn} = "ZWave_Parse";
|
||||
$hash->{AttrList} = "IODev do_not_notify:1,0 noExplorerFrames:1,0 ".
|
||||
"ignore:1,0 dummy:1,0 showtime:1,0 classes $readingFnAttributes";
|
||||
"ignore:1,0 dummy:1,0 showtime:1,0 classes vclasses $readingFnAttributes";
|
||||
map { $zwave_id2class{lc($zwave_class{$_}{id})} = $_ } keys %zwave_class;
|
||||
|
||||
$hash->{FW_detailFn} = "ZWave_fhemwebFn";
|
||||
@ -453,7 +455,7 @@ ZWave_Define($$)
|
||||
AssignIoPort($hash); # FIXME: should take homeId into account
|
||||
|
||||
if(@a) { # Autocreate: set the classes, execute the init calls
|
||||
$hash->{lastMsgTimestamp} = time(); # device is awake.
|
||||
$hash->{lastMsgTimestamp} = gettimeofday(); # device is awake.
|
||||
ZWave_SetClasses($homeId, $id, undef, $a[0]);
|
||||
}
|
||||
return undef;
|
||||
@ -631,7 +633,7 @@ ZWave_Cmd($$@)
|
||||
$cmdFmt = $ncmd if(defined($ncmd));
|
||||
}
|
||||
|
||||
Log3 $name, 2, "ZWave $type $name $cmd";
|
||||
Log3 $name, 2, "ZWave $type $name $cmd ".join(" ", @a);
|
||||
|
||||
my ($baseClasses, $baseHash) = ($classes, $hash);
|
||||
if($id =~ m/(..)(..)/) { # Multi-Channel, encapsulate
|
||||
@ -660,7 +662,7 @@ ZWave_Cmd($$@)
|
||||
$baseHash->{WakeUp} = \@arr;
|
||||
}
|
||||
my $awake = ($baseHash->{lastMsgTimestamp} &&
|
||||
time() - $baseHash->{lastMsgTimestamp} < 3);
|
||||
gettimeofday() - $baseHash->{lastMsgTimestamp} < 3);
|
||||
|
||||
if(!$awake) {
|
||||
push @{$baseHash->{WakeUp}}, $data.$id;
|
||||
@ -841,6 +843,62 @@ ZWave_meterSupportedParse($$)
|
||||
" $meter_reset_text";
|
||||
}
|
||||
|
||||
sub
|
||||
ZWave_versionClassRequest($$)
|
||||
{
|
||||
my ($hash, $answer) = @_;
|
||||
my $name = $hash->{NAME};
|
||||
|
||||
if($answer =~ m/^048614(..)(..)$/i) { # Parse part
|
||||
my $v = $hash->{versionhash};
|
||||
$v->{$zwave_id2class{lc($1)}} = $2;
|
||||
foreach my $class (keys %{$v}) {
|
||||
next if($v->{$class} ne "");
|
||||
my $r = ZWave_Set($hash, $name, "versionClassRequest", $class);
|
||||
return;
|
||||
}
|
||||
$attr{$hash->{NAME}}{vclasses} =
|
||||
join(" ", map { "$_:$v->{$_}" } sort keys %{$v});
|
||||
delete($hash->{versionhash});
|
||||
}
|
||||
|
||||
if($answer ne "%s" && $hash->{versionhash}) { # get next
|
||||
return("", sprintf('13%02x', hex($zwave_class{$answer}{id})))
|
||||
if($zwave_class{$answer});
|
||||
return("versionClassRequest needs no parameter", "");
|
||||
}
|
||||
|
||||
return("versionClassRequest needs no parameter", "")
|
||||
if($answer ne "%s" && !$hash->{versionhash});
|
||||
|
||||
return("another versionClassRequest is already running", "")
|
||||
if(defined($hash->{versionhash}));
|
||||
|
||||
# User part: called with no parameters
|
||||
my %h = map { $_ => "" }
|
||||
grep { $_ !~ m/^MARK$/ && $_ !~ m/^UNKNOWN/ }
|
||||
split(" ", AttrVal($name, "classes", ""));
|
||||
$hash->{versionhash} = \%h;
|
||||
foreach my $class (keys %h) {
|
||||
next if($h{$class} ne "");
|
||||
return("", sprintf('13%02x', hex($zwave_class{$class}{id})));
|
||||
}
|
||||
return("Should not happen", "");
|
||||
}
|
||||
|
||||
sub
|
||||
ZWave_versionClassGet($)
|
||||
{
|
||||
my ($class) = @_;
|
||||
|
||||
return("", sprintf('13%02x', $class))
|
||||
if($class =~ m/\d+/);
|
||||
return("", sprintf('13%02x', hex($zwave_class{$class}{id})))
|
||||
if($zwave_class{$class});
|
||||
return ("versionClass needs a class as parameter", "") if($class eq "%s");
|
||||
return ("Unknown class $class", "");
|
||||
}
|
||||
|
||||
sub
|
||||
ZWave_multilevelParse($$$)
|
||||
{
|
||||
@ -1592,6 +1650,21 @@ ZWave_getHash($$$)
|
||||
return $ptr;
|
||||
}
|
||||
|
||||
sub
|
||||
ZWave_wakeupTimer($)
|
||||
{
|
||||
my ($hash) = @_;
|
||||
my $now = gettimeofday();
|
||||
if($now - $hash->{lastMsgTimestamp} > 1) { # wakeupNoMoreInformation
|
||||
if($hash->{STATE} ne "TRANSMIT_NO_ACK") {
|
||||
my $nodeId = $hash->{id};
|
||||
IOWrite($hash, "00", "13${nodeId}02840805");
|
||||
}
|
||||
} else {
|
||||
InternalTimer($now+0.1, "ZWave_wakeupTimer", $hash, 0);
|
||||
}
|
||||
}
|
||||
|
||||
sub
|
||||
ZWave_sendWakeup($)
|
||||
{
|
||||
@ -1604,17 +1677,9 @@ ZWave_sendWakeup($)
|
||||
Log3 $hash, 4, "Sending stored command: $wuCmd";
|
||||
}
|
||||
@{$hash->{WakeUp}}=();
|
||||
#send a final wakeupNoMoreInformation
|
||||
my $nodeId = $hash->{id};
|
||||
Log3 $hash, 4, "Sending wakeupNoMoreInformation to node: $nodeId";
|
||||
IOWrite($hash, "00", "13${nodeId}02840805");
|
||||
|
||||
} else { # Wait for commands via notify
|
||||
InternalTimer(gettimeofday()+1, sub($) {
|
||||
my $nodeId = $hash->{id};
|
||||
IOWrite($hash, "00", "13${nodeId}02840805");
|
||||
}, $hash, 0);
|
||||
}
|
||||
|
||||
InternalTimer(gettimeofday()+01, "ZWave_wakeupTimer", $hash, 0);
|
||||
}
|
||||
|
||||
###################################
|
||||
@ -1682,7 +1747,7 @@ ZWave_Parse($$@)
|
||||
my $dh = $modules{ZWave}{defptr}{"$homeId $1"};
|
||||
return "" if(!$dh);
|
||||
|
||||
$dh->{lastMsgTimestamp} = time();
|
||||
$dh->{lastMsgTimestamp} = gettimeofday();
|
||||
|
||||
if($iodev->{addSecure}) {
|
||||
my $classes = AttrVal($dh->{NAME}, "classes", "");
|
||||
@ -1707,7 +1772,7 @@ ZWave_Parse($$@)
|
||||
my $hash = $modules{ZWave}{defptr}{"$homeId $id"};
|
||||
if($hash) {
|
||||
ZWave_sendWakeup($hash) if($hash);
|
||||
$hash->{lastMsgTimestamp} = time();
|
||||
$hash->{lastMsgTimestamp} = gettimeofday();
|
||||
if(!$ret) {
|
||||
readingsSingleUpdate($hash, "CMD", $cmd, 1); # forum:20884
|
||||
return $hash->{NAME};
|
||||
@ -1799,6 +1864,7 @@ ZWave_Parse($$@)
|
||||
}
|
||||
|
||||
|
||||
$baseHash->{lastMsgTimestamp} = gettimeofday();
|
||||
my $name = $hash->{NAME};
|
||||
my @event;
|
||||
my @args = ($arg); # MULTI_CMD handling
|
||||
@ -1821,6 +1887,11 @@ ZWave_Parse($$@)
|
||||
next;
|
||||
}
|
||||
|
||||
if($className eq "VERSION" && defined($hash->{versionhash})) {
|
||||
ZWave_versionClassRequest($hash, $arg);
|
||||
return "";
|
||||
}
|
||||
|
||||
my $ptr = ZWave_getHash($hash, $className, "parse");
|
||||
if(!$ptr) {
|
||||
push @event, "UNPARSED:$className $arg";
|
||||
@ -1840,7 +1911,6 @@ ZWave_Parse($$@)
|
||||
}
|
||||
|
||||
ZWave_sendWakeup($baseHash) if($arg =~ m/^028407/);
|
||||
$baseHash->{lastMsgTimestamp} = time();
|
||||
|
||||
return "" if(!@event);
|
||||
|
||||
@ -2174,6 +2244,14 @@ s2Hex($)
|
||||
available (deleted) and 1 for set (occupied). code is a hexadecimal string.
|
||||
</li>
|
||||
|
||||
<br><br><b>Class VERSION</b>
|
||||
<li>versionClassRequest<br>
|
||||
executes "get devicename versionClass class" for each class from the
|
||||
classes attribute in the background without generating events, and sets the
|
||||
vclasses attribute at the end.
|
||||
</li>
|
||||
|
||||
|
||||
<br><br><b>Class WAKE_UP</b>
|
||||
<li>wakeupInterval value nodeId<br>
|
||||
Set the wakeup interval of battery operated devices to the given value in
|
||||
@ -2378,7 +2456,7 @@ s2Hex($)
|
||||
return the version information of this node in the form:<br>
|
||||
Lib A Prot x.y App a.b
|
||||
</li>
|
||||
<li>versionClass classId<br>
|
||||
<li>versionClass classId or className<br>
|
||||
return the supported command version for the requested class
|
||||
</li>
|
||||
|
||||
@ -2415,6 +2493,10 @@ s2Hex($)
|
||||
set/get commands depends on it. It contains a space separated list of
|
||||
class names (capital letters).
|
||||
</li>
|
||||
<li><a href="#vclasses">vclasses</a>
|
||||
This is the result of the "set DEVICE versionClassRequest" command, and
|
||||
contains the version information for each of the supported classes.
|
||||
</li>
|
||||
<li><a href="#noExplorerFrames">noExplorerFrames</a>
|
||||
turn off the use of Explorer Frames
|
||||
</li>
|
||||
|
Loading…
x
Reference in New Issue
Block a user