简体   繁体   中英

Z-wave protocol with C: Questions about Z-wave frame structure & programming in general

(Before I ask my question; I don't really know if anyone is allowed to answer my question since the Z-wave protocol is supposed to be confidential information, but if it does indeed violate against any kind of regulation then feel free to delete this post.)

I am currently trying to write a C program that simply constructs a Z-wave message consisting of raw binary data and then sends that message to a USB interface where a Z-wave controller is connected (I am using the AEOTEC Z-Stick USB dongle by Aeon Labs). I am also using this guide as a reference and trying to re-write the sample code in plain C. However, if you take a look at the guide, specifically the message he is trying to send to the USB controller:

/*
0x01, 0x09, 0x00, 0x13, nodeId, 0x03, 0x20, 0x01, state, 0x05, checksum
*/

... maybe it's just me but it seems like some information from the usual Z-wave frame is missing. My guess is that the first 4 bytes represent the Home ID followed by the node ID, but I can't make out what the '0x03' means after that, supposing that the rest after that byte represent the "Basic" command class ('0x20', 1 byte) and the corresponding "Set" application command ('0x01', 1 byte). And what does the '0x05' stand for before the checksum bit? And what about the transport header information, why isn't it included? It seems like he didn't need to include it... or maybe I'm just interpreting the packet completely wrong. Can someone enlighten me please?

Also, is it correct that you can only retrieve application-layer information fom the USB port if you read from it (f.ex. with a open() & read() command in C)?

Thank you in advance!

I think you'd save considerable time and effort by studying OpenZWave's source code . This is an open source C++ library for working with ZWave which is quite mature and feature-complete. You could easily use it from plain C.

Part of what you're asking can be seen in the Msg class constructor which constructs the start of frame (0x01), followed by message length (0x09 == 9 bytes), message type (0x00 == REQUEST), and function (FUNC_ID_ZW_SEND_DATA == 0x013), then comes the target nodeID, then comes the actual command body, which I suppose is for a basic command:

./src/Defs.h:#define COMMAND_CLASS_BASIC 0x20 :

bool Basic::SetValue
...
            Msg* msg = new Msg( "BasicCmd_Set", GetNodeId(), REQUEST, FUNC_ID_ZW_SEND_DATA, true );
            msg->SetInstance( this, _value.GetID().GetInstance() );
            msg->Append( GetNodeId() );
            msg->Append( 3 );
            msg->Append( GetCommandClassId() );
            msg->Append( BasicCmd_Set );
            msg->Append( value->GetValue() );
            msg->Append( GetDriver()->GetTransmitOptions() );
            GetDriver()->SendMsg( msg, Driver::MsgQueue_Send );
            return true;
    }

    return false;
}

Found what I was looking for. In case anyone is interested, here's what I found after days and days of googling...

Huge compilation of Z-Wave information

A bit further down on that page (directly under the Z-Wave frame description) is a description of the frame structure that is used to communicate directly with the USB controller.

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM