Einfache Klasse für USB-Dongle Revolt PX-1674-675

Mit Perl Elektrogeräte bzw. Funksteckdosen PX-1672-675, PX-1673-675 schalten

Auf einer Win32-Maschine wird der USB-Stick über libusb-win32-devices angesteuert. Für die Instanzerstellung ist also der Stick mit dem zur LibUSB mitgelliefeten InfWizard als USB-Device einzurichten. Der optionale Debug-Modus veranlasst eine print-Ausgabe der an den Stick gesendeten Bytesequenz als Hex-Dump.

my $px = PxCMD->new(
    exe     => 'D:/home/tools/pxhex.exe',
    address => 0x1A85
);

Auf einer Adresse können bis zu 6 Geräte (Steckdosen) angelernt werden (Peering). Zur Auslösung eines Schaltvorganges ist die Geräte-ID anzugeben. Sofern das nicht der Fall ist, werden alle Geräte, die auf diese Adresse (Hauscode) angelernt wurden, geschaltet.

$px->On(1); # Schaltet Steckdose 1 On
            # ===Payload===
            # 1A 85 F0 70 20 0A 00 18

$px->Off(); # schaltet die ganze Gruppe ab
            # ===Payload===
            # 1A 85 10 50 20 0A 00 18

# Ebenfalls möglich
$px->switch('On', 1); # Schaltet Steckdose 1 On
$px->switch('Off');   # Schaltet die Gruppe Off

Perl Source für das Modul PxCMD


# Einfache Klasse für USB-Dongle PX-1674-675
# Steckdosen PX-1672-675, PX-1673-675
# Wrapper für die Binary/Bulk-Transfer

package PxCMD;

use strict;
use warnings;
use bytes;
use Carp;
use Shell qw(pxhex); # Zeile 60

# Gruppenschaltung, bis zu 6 Geräte sind möglich
sub new{
    my $class = shift;
    my %cfg = (
        exe     => '',
        address => 0x1A85,
        debug   => 0,
    @_);

    return bless{
        EXE   => $cfg{exe},
        DEBUG => $cfg{debug}, 
        ADDR  => $cfg{address},
        CMD   => {
            1     => { On => 0xF0, Off => 0xE0 },
            2     => { On => 0xD0, Off => 0xC0 },
            3     => { On => 0xB0, Off => 0xA0 },
            4     => { On => 0x90, Off => 0x80 },
            5     => { On => 0x70, Off => 0x60 },
            6     => { On => 0x50, Off => 0x40 },
            group => { On => 0x20, Off => 0x10 },
        },
    }, $class;
}

# On|Off|switch
# Übergeben wird die Gerätenummer
# Ansonsten wird die Gruppe geschaltet
# __ANON__
my $OnOff = sub{
    my $self = shift;
    my $dest = shift;    
    my $devnr = shift || 'group';
    my $payload = $self->_payload($devnr, $dest);

    my $param = join(" ", map{sprintf("%02X", $_)}unpack "C*", $payload);
    if($self->{DEBUG}){
        return $param;
    }
    else{
        if( $self->{EXE} ){
            my $P;
            open $P, "|$self->{EXE} $param";
            close $P;
        }
        else{
            return pxhex(map{sprintf("%02X", $_)}unpack "C*", $payload);            
        }
    }
};
############################ Private ######################################
sub _payload{
    my $self  = shift;
    my $devnr = shift;
    my $dest  = shift;
    
    my $cmd = $self->{CMD}{$devnr}{$dest} || croak "CMD '$dest' for device '$devnr' not found";
    my ($b1, $b2) = unpack "CC", pack "n", $self->{ADDR};
    my $chk = 255 - ($b1 + $b2 + $cmd) % 256;
    return pack "C8", $b1,$b2,$cmd,$chk,0x20,0x0A,0x00,0x18;
}

# On || Off || switch über eine anonyme Funktion
sub AUTOLOAD{
    my $self = shift;
    my $name = our $AUTOLOAD =~ /::(\w+)$/ ? $1 : '';
    if( $name eq 'On' || $name eq 'Off' ){
        $self->$OnOff($name, @_);
    }
    elsif( $name eq 'switch'){
        $self->$OnOff(@_);
    }
    else{ die "Unbekannte Funktion: '$name'!\n" }
}
sub DESTROY{}
1;#########################################################################
__END__
package main;
my $px = PxCMD->new(
    address => 0x1A85,
);
print $px->Off;


Datenschutzerklärung: Diese Seite dient rein privaten Zwecken. Auf den für diese Domäne installierten Seiten werden grundsätzlich keine personenbezogenen Daten erhoben. Das Loggen der Zugriffe mit Ihrer Remote Adresse erfolgt beim Provider soweit das technisch erforderlich ist. s​os­@rolf­rost.de.