diff --git a/docs/Doxyfile.in b/docs/Doxyfile.in index 9ba5366..fdbe71c 100644 --- a/docs/Doxyfile.in +++ b/docs/Doxyfile.in @@ -103,10 +103,11 @@ SHOW_NAMESPACES = YES FILE_VERSION_FILTER = LAYOUT_FILE = CITE_BIB_FILES = @CMAKE_CURRENT_SOURCE_DIR@/protocol/artistic/ARTISTIC.bib \ + @CMAKE_CURRENT_SOURCE_DIR@/protocol/citp/CITP.bib \ + @CMAKE_CURRENT_SOURCE_DIR@/protocol/enttec/ENTTEC.bib \ @CMAKE_CURRENT_SOURCE_DIR@/protocol/esta/ESTA.bib \ @CMAKE_CURRENT_SOURCE_DIR@/protocol/ietf/IETF.bib \ - @CMAKE_CURRENT_SOURCE_DIR@/protocol/osc/OSC.bib \ - @CMAKE_CURRENT_SOURCE_DIR@/protocol/citp/CITP.bib + @CMAKE_CURRENT_SOURCE_DIR@/protocol/osc/OSC.bib #--------------------------------------------------------------------------- # Configuration options related to warning and progress messages #--------------------------------------------------------------------------- diff --git a/protocol/CMakeLists.txt b/protocol/CMakeLists.txt index 4fe8bab..2a14105 100644 --- a/protocol/CMakeLists.txt +++ b/protocol/CMakeLists.txt @@ -22,6 +22,9 @@ add_subdirectory(ietf) # Artistic License add_subdirectory(artistic) +# Enttec +add_subdirectory(enttec) + # OpenSoundControl add_subdirectory(osc) diff --git a/protocol/README.md b/protocol/README.md index 31c2391..24c8d23 100644 --- a/protocol/README.md +++ b/protocol/README.md @@ -29,6 +29,14 @@ downloaded from the publishers website. [Specification 1.1](opensoundcontrol.stanford.edu/spec-1_1.html) +## ENTTEC + +[ENTTEC](www.enttec.com) + +[DMX USB Pro](www.enttec.com/product/lighting-communication-protocols/dmx512/dmx-usb-pro/) + +[API V1.44](cdn.enttec.com/pdf/assets/70304/70304_DMX_USB_PRO_API.pdf) + ## CITP The [CITP Protocol](www.lewlight.com/citp-protocol) website appears to diff --git a/protocol/enttec/CMakeLists.txt b/protocol/enttec/CMakeLists.txt new file mode 100644 index 0000000..fe711b2 --- /dev/null +++ b/protocol/enttec/CMakeLists.txt @@ -0,0 +1,2 @@ +# DMX USB Pro 1.44 +add_subdirectory(dmx-usb-pro) diff --git a/protocol/enttec/ENTTEC.bib b/protocol/enttec/ENTTEC.bib new file mode 100644 index 0000000..00e9b58 --- /dev/null +++ b/protocol/enttec/ENTTEC.bib @@ -0,0 +1,7 @@ +@manual{DMXUSBPro, + key = "DMX-USB-Pro 1.44", + title = "DMX USB Pro Widget API Specification 1.44", + organization = ENTTEC Pty/Ltd, + year = 2007, + address = "Melbourne", +} diff --git a/protocol/enttec/dmx-usb-pro/CMakeLists.txt b/protocol/enttec/dmx-usb-pro/CMakeLists.txt new file mode 100644 index 0000000..44aa9ed --- /dev/null +++ b/protocol/enttec/dmx-usb-pro/CMakeLists.txt @@ -0,0 +1,13 @@ +project(${PROJECT_NAME}-dmxusbpro VERSION 1.44.0 LANGUAGES CXX) + +add_library(${PROJECT_NAME} SHARED) +add_library(ENTTEC::Pro ALIAS ${PROJECT_NAME}) + +target_sources(${PROJECT_NAME} + PUBLIC + pro.h + ) + +set_target_properties(${PROJECT_NAME} PROPERTIES LINKER_LANGUAGE CXX) +set_target_properties(${PROJECT_NAME} PROPERTIES VERSION ${PROJECT_VERSION}) +target_include_directories(${PROJECT_NAME} PUBLIC ${CMAKE_CURRENT_SOURCE_DIR}) diff --git a/protocol/enttec/dmx-usb-pro/pro.h b/protocol/enttec/dmx-usb-pro/pro.h new file mode 100644 index 0000000..24a9559 --- /dev/null +++ b/protocol/enttec/dmx-usb-pro/pro.h @@ -0,0 +1,321 @@ +/* + pro.h + + Copyright (c) 2023 Kevin Matz (kevin.matz@gmail.com) + + Permission is hereby granted, free of charge, to any person obtaining a copy + of this software and associated documentation files (the "Software"), to deal + in the Software without restriction, including without limitation the rights + to use, copy, modify, merge, publish, distribute, sublicense, and/or sell + copies of the Software, and to permit persons to whom the Software is + furnished to do so, subject to the following conditions: + + The above copyright notice and this permission notice shall be included in all + copies or substantial portions of the Software. + + THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR + IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, + FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE + AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER + LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, + OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE + SOFTWARE. +*/ +#pragma once + +#include +#include +#include + +namespace ENTTEC { +namespace PRO { + +struct ApplicationMessage; + +/** + * @brief Application Message Format + * + * \cite DMXUSBPro The PC based application program communicates with the Widget. + */ +struct Message { + uint8_t label; //!< Label to identify the type of message. + std::shared_ptr message; //!< Data +}; + +const uint8_t START_DELIMITER = 0x7e; //!< Start of message delimiter +const uint8_t END_DELIMITER = 0xe7; //!< End of message delimiter + + +/** + * @brief Firmware Varieties + * + * \cite DMXUSBPro The Widget firmware version identifies the set of application messages that + * are supported by the firmware. The Widget will ignore any unsupported application messages. + */ +enum FIRMWARE_TYPE { + FwUnknown = 0, + FwDMX = 1, //!< Normal DMX firmware. + FwRDM = 2, //!< RDM firmware + FwSniffer = 3 //!< RDM Sniffer firmware +}; + + +/** + * @brief Application Messages + */ +enum MESSAGE_LABEL { + OpReprogramFirmware = 1, //!< Reprogram Firmware Request + OpProgramFlashPage = 2, //!< Program Flash Page Request / Reply + OpGetWidgetParameters = 3, //!< Get Widget Parameters Request / Reply + OpSetWidgetParameters = 4, //!< Set Widget Parameters Request + OpRecievedDmxPacket = 5, //!< Received DMX Packet + OpOutputOnlySendDMX = 6, //!< Output Only Send DMX Packet Request + OpSendRDMData = 7, //!< Send RDM Packet Request + OpRecieveDMXOnChange = 8, //!< Receive DMX on Change + OpRecievedDMXChanged = 9, //!< Received DMX Change Of State Packet + OpGetWidgetSerial = 10, //!< Get Widget Serial Number Request / Reply + OpSendRDMDiscovery = 11 //!< Send RDM Discovery Request +}; + + +/** + * @brief The ApplicationMessage class + * + * Base type of each message data. + */ +struct ApplicationMessage +{ +}; + + +/** + * @brief 1. Reprogram Firmware Request (Label = 1, no data) + * + * \cite DMXUSBPro This message requests the Widget firmware to run the Widget bootstrap to + * enable reprogramming of the Widget firmware. + */ +struct MsgReprogramFirmware + : public ApplicationMessage +{ +}; + + +/** + * @brief 2. Program Flash Page Request (Label=2) + * + * \cite DMXUSBPro This message programs one Flash page of the Widget firmware. The Flash + * pages must be programmed in order from first to last Flash page, with the contents of + * the firmware binary file. + */ +struct MsgProgramFlashPageRequest + : public ApplicationMessage +{ + uint8_t page[64]; //!< One page of firmware binary file. +}; + + +/** + * @brief 3. Program Flash Page Reply (Label=2) + * + * \cite DMXUSBPro The Widget sends this message to the PC on completion of the + * Program Flash Page request. + */ +struct MsgProgramFlashPageReply + : public ApplicationMessage +{ + bool success; //!< Success character array product +}; + +const char SUCCESS_OK[4] = {'T','R','U','E'}; //!< Firmware page write success +const char SUCCESS_FAIL[4] = {'F','A','L','S'}; //!< Firmware page write failure + + +/** + * @brief 4. Get Widget Parameters Request (Label=3) + * + * \cite DMXUSBPro This message requests the Widget configuration. + */ +struct MsgGetWidgetParametersRequest + : public ApplicationMessage +{ + uint16_t user_configuration_size = 0; //!< user configuration size in bytes +}; + +const uint16_t USER_CONFIGURATION_MAX = 508; //!< maximum user configuration size + + +/** + * @brief 5. Get Widget Parameters Request (Label=3) + * + * \cite DMXUSBPro The Widget sends this message to the PC in response to the Get + * Widget Parameters request. + */ +struct MsgGetWidgetParametersReply + : public ApplicationMessage +{ + union { + uint16_t version; + struct { + uint8_t fw_rev; + uint8_t fw_type; + }; + }; + uint8_t break_time; //!< interval count of the DMX output BREAK + uint8_t mab_time; //!< interval count of the DMX output MARK AFTER BREAK + uint8_t rate; //!< DMX output rate in packets per second. + std::vector user_data; //!< user defined configuration data +}; + +const float DMX_BREAK_INTERVAL = 10.67; //!< microseconds, resolution of the BREAK interval +const uint8_t DMX_BREAK_MIN = 9; //!< minimum BREAK intervals +const uint8_t DMX_BREAK_MAX = 127; //!< maximum BREAK intervals + +const float DMX_MAB_INTERVAL = 10.67; //!< microseconds, resolution of the MAB interval +const uint8_t DMX_MAB_MIN = 1; //!< minimum MAB intervals +const uint8_t DMX_MAB_MAX = 127; //!< maximum MAB intervals + +const uint8_t DMX_RATE_MIN = 1; //!< maximum DMX refresh rate +const uint8_t DMX_RATE_MAX = 40; //!< minimum DMX refresh rate + + +/** + * @brief 6. Set Widget Parameters Request (Label=4) + * + * \cite DMXUSBPro This message sets the Widget configuration. + */ +struct MsgSetWidgetParametersRequest + : public ApplicationMessage +{ + uint8_t break_time; //!< interval count of the DMX output BREAK + uint8_t mab_time; //!< interval count of the DMX output MARK AFTER BREAK + uint8_t rate; //!< DMX output rate in packets per second. + std::vector user_data; //!< user defined configuration data +}; + + +/** + * @brief 7. Received DMX Packet (Label=5) + * + * \cite DMXUSBPro The Widget sends this message to the PC unsolicited, whenever the + * Widget receives a DMX or RDM packet from the DMX port, and the Receive DMX on Change + * mode is 'Send always'. + */ +struct MsgRecievedDmxPacket + : public ApplicationMessage +{ + union { + uint8_t rx_corrupted; //!< When this is 0, the DMX data is valid. + struct { + bool rx_queue_overflow : 1; + bool rx_overrun : 1; + }; + }; + std::vector data; //!< Received DMX data beginning with the start code. +}; + + +/** + * @brief 8. Output Only Send DMX Packet Request (Label=6) + * + * \cite DMXUSBPro This message requests the Widget to periodically send a DMX packet out + * of the Widget DMX port at the configured DMX output rate. + */ +struct MsgOutputOnlySendDMX + : public ApplicationMessage +{ + std::vector data; //!< DMX data to send, beginning with the start code. +}; + +const uint8_t DMX_LAST_SLOT_MIN = 24; //!< length of the shortest supported universe + + +/** + * @brief 9. Send RDM Packet Request (Label=7) + * + * \cite DMXUSBPro This message requests the Widget to send an RDM packet out of + * the Widget DMX port, and then change the DMX port direction to input, so that RDM or + * DMX packets can be received. + */ +struct MsgSendRDMData + : public ApplicationMessage +{ + std::vector data; //!< RDM data to send, beginning with the start code. +}; + + +enum DMX_RX_MODE { + RxNotifyAlways = 0, //!< Always send RX'd over USB + RxNotifyOnChange = 1 //!< Only send changed date over USB +}; + + +/** + * @brief 10. Receive DMX on Change (label = 8) + * + * \cite DMXUSBPro This message requests the Widget send a DMX packet to the PC only when + * the DMX values change on the input port. + * + * By default the widget will always send, if you want to send on change it must be enabled + * by sending this message. + */ +struct MsgRecieveDMXOnChange + : public ApplicationMessage +{ + DMX_RX_MODE mode = RxNotifyAlways; //!< Always (default), or OnChange +}; + + +/** + * @brief 11.Received DMX Change Of State Packet (Label=9) + * + * \cite DMXUSBPro The Widget sends one or more instances of this message to the PC unsolicited, + * whenever the Widget receives a changed DMX packet from the DMX port, and the Receive DMX on + * Change mode is 'Send on data change only'. + */ +struct MsgRecievedDMXChanged + : public ApplicationMessage +{ + uint8_t start; //!< Start changed byte number. + uint8_t changed[5]; //!< Changed bit array. + std::vector data; //!< Changed DMX data byte data. +}; + + +/** + * @brief 12.Get Widget Serial Number Request (Label = 10, no data) + * + * \cite DMXUSBPro This message requests the Widget serial number. + */ +struct MsgGetWidgetSerialRequest + : public ApplicationMessage +{ +}; + + +/** + * @brief 13.Get Widget Serial Number Reply (Label = 10) + * + * \cite DMXUSBPro The Widget sends this message to the PC in response to the Get Widget + * Serial Number request. + */ +struct MsgGetWidgetSerialReply + : public ApplicationMessage +{ + uint32_t serial; //!< BCD serial number. +}; + + +/** + * @brief 14. Send RDM Discovery Request (Label=11) + * + * \cite DMXUSBPro This message requests the Widget to send an RDM Discovery Request packet + * out of the Widget DMX port, and then receive an RDM Discovery Response. + */ +struct MsgSendRDMDiscovery + : public ApplicationMessage +{ + uint8_t request[38]; //!< DISC_UNIQUE_BRANCH RDM request packet to send. +}; + +} // namespace PRO +} // namespace ENTTEC