PicoC, \x00 hexadecimal

Einklappen
X
 
  • Zeit
  • Anzeigen
Alles löschen
neue Beiträge
  • K.Clemens
    Smart Home'r
    • 28.08.2015
    • 92

    #1

    PicoC, \x00 hexadecimal

    I've bought a RJ45 relais board which I can control over a TCP connection.
    I'm writing a pico script where I can couple a digital input with a certain command over TCP.

    To control a relais, I have to send a hexadecimal "string?": "\x55\xAA\x00\x03\x00\x02\x01\x06".

    In the script below \x00 is a delimiter in the sprintf function.
    Is there anyone who has more experience with picoC, who can help me?

    char buffer2[1024];
    sprintf(buffer2, ""\x55\xAA\x00\x03\x00\x02\x01\x06");
    stream_write(TcpStream,buffer2,sizeof(buffer2"));

    stream_flush(TcpStream);
    sleep(5000);
    stream_close(TcpStream);
  • Jan W.
    Lox Guru
    • 30.08.2015
    • 1366

    #2
    sprintf is a string function and strings in C as well as Pico C are arrays of characters that are ended by a character with \x00, so the function is only copying the first two characters.

    You have to use "memcpy" and specify the amount of characters to copy as well as to write to the TCP stream (well you may write 1024 bytes as with "sizeof", but I'm not sure if that is desired):

    memcpy(buffer2,"\x55\xAA\x00\x03\x00\x02\x01\x06", 8);
    stream_write(TcpStream,buffer2,8);

    Jan
    Zuletzt geändert von Jan W.; 23.06.2016, 22:36.
    Miniserver v14.5.12.7, 2x Ext., 2x Relay Ext., 2x Dimmer Ext., DMX Ext., 1-Wire Ext., Gira KNX Tastsensor 3 Komfort, Gira KNX Präsenzmelder, Fenster- und Türkontakte, Loxone Regen- und Windsensor, Gira Dual Q Rauchmelder vernetzt, 1x Relais-Modul
    Loxberry: SmartMeter, MS Backup, CamConnect, Weather4Lox
    Lüftung: Helios KWL EC 370W ET mit Modbus TCP - via Pico-C
    Heizung: Stiebel Eltron WPF 5 cool (Sole-Wasser WP) mit ISG, FB-Heizung mit 18 Kreisen, Erdsonde - via modbus/TCP
    Node-RED: IKEA Tradfri

    Kommentar

    • K.Clemens
      Smart Home'r
      • 28.08.2015
      • 92

      #3
      thanks for your reply. Highly appreciated.
      I've done what you said, but still the only the first 2 are being send. The rest are 00.

      'm lurking my network with wireshark and I see that also the AA is being changed to aa.

      What I see with wireshark: 55 aa 00 00 00 00 00 00

      Kommentar

      • Jan W.
        Lox Guru
        • 30.08.2015
        • 1366

        #4
        Well "aa" in Wireshark is the same as \xAA in C, but for the zero bytes I'm unsure. Please try:

        char buffer2[1024] = {0x55, 0xAA, 0x00, 0x03, 0x00, 0x02, 0x01, 0x06, };
        stream_write(TcpStream, buffer2, 8);
        Miniserver v14.5.12.7, 2x Ext., 2x Relay Ext., 2x Dimmer Ext., DMX Ext., 1-Wire Ext., Gira KNX Tastsensor 3 Komfort, Gira KNX Präsenzmelder, Fenster- und Türkontakte, Loxone Regen- und Windsensor, Gira Dual Q Rauchmelder vernetzt, 1x Relais-Modul
        Loxberry: SmartMeter, MS Backup, CamConnect, Weather4Lox
        Lüftung: Helios KWL EC 370W ET mit Modbus TCP - via Pico-C
        Heizung: Stiebel Eltron WPF 5 cool (Sole-Wasser WP) mit ISG, FB-Heizung mit 18 Kreisen, Erdsonde - via modbus/TCP
        Node-RED: IKEA Tradfri

        Kommentar

        • K.Clemens
          Smart Home'r
          • 28.08.2015
          • 92

          #5
          the log file of Loxone gives me following error:
          2016-06-23 23:03:19.200;char buffer2[1024] = {0x55, 0xAA, 0x00, 0x03, 0x00, 0x02, 0x01, 0x06, }; ^ Programma USR IOT:81:68 expression expected

          Kommentar

          • Jan W.
            Lox Guru
            • 30.08.2015
            • 1366

            #6
            Looks that you have to initialize the full array (the code above worked in Pico C on my MacBook):

            char relais[8] = {0x55, 0xAA, 0x00, 0x03, 0x00, 0x02, 0x01, 0x06};
            stream_write(TcpStream, relais, 8);

            Cheers, Jan
            Miniserver v14.5.12.7, 2x Ext., 2x Relay Ext., 2x Dimmer Ext., DMX Ext., 1-Wire Ext., Gira KNX Tastsensor 3 Komfort, Gira KNX Präsenzmelder, Fenster- und Türkontakte, Loxone Regen- und Windsensor, Gira Dual Q Rauchmelder vernetzt, 1x Relais-Modul
            Loxberry: SmartMeter, MS Backup, CamConnect, Weather4Lox
            Lüftung: Helios KWL EC 370W ET mit Modbus TCP - via Pico-C
            Heizung: Stiebel Eltron WPF 5 cool (Sole-Wasser WP) mit ISG, FB-Heizung mit 18 Kreisen, Erdsonde - via modbus/TCP
            Node-RED: IKEA Tradfri

            Kommentar

            • K.Clemens
              Smart Home'r
              • 28.08.2015
              • 92

              #7
              Jan, the last one works! You are a life safer! Very big thanks.

              Kommentar

              • Jan W.
                Lox Guru
                • 30.08.2015
                • 1366

                #8
                Welcome! I'm glad that I was able to help. Sometimes Pico C is a bit different from "normal" C.
                Miniserver v14.5.12.7, 2x Ext., 2x Relay Ext., 2x Dimmer Ext., DMX Ext., 1-Wire Ext., Gira KNX Tastsensor 3 Komfort, Gira KNX Präsenzmelder, Fenster- und Türkontakte, Loxone Regen- und Windsensor, Gira Dual Q Rauchmelder vernetzt, 1x Relais-Modul
                Loxberry: SmartMeter, MS Backup, CamConnect, Weather4Lox
                Lüftung: Helios KWL EC 370W ET mit Modbus TCP - via Pico-C
                Heizung: Stiebel Eltron WPF 5 cool (Sole-Wasser WP) mit ISG, FB-Heizung mit 18 Kreisen, Erdsonde - via modbus/TCP
                Node-RED: IKEA Tradfri

                Kommentar

                • K.Clemens
                  Smart Home'r
                  • 28.08.2015
                  • 92

                  #9
                  Any idea what would be the best way to read incomming messages from the relais board over TCP connection.

                  stream_read(TcpStream,relais,8,100);

                  What I want to accomplish: If the relais is triggered on the relais board itself, I want to know it in Loxone.
                  Also a hexa decimal is send by relais board.

                  Kommentar

                  • Jan W.
                    Lox Guru
                    • 30.08.2015
                    • 1366

                    #10
                    I'm not sure if 100ms are long enough to wait and if the relais always sends 8 bytes, but in general the function would look like:

                    nLen = stream_read(TcpStream,relais,8,100);

                    // read content from relais if 8 bytes were received
                    if (nLen==8) {
                    if ( (relais[0]== 0x55) AND ... ) {
                    setoutput(0, ... );
                    }
                    }

                    put all statements into a loop with a sleep statement to save CPU time.

                    Cheers, Jan
                    Miniserver v14.5.12.7, 2x Ext., 2x Relay Ext., 2x Dimmer Ext., DMX Ext., 1-Wire Ext., Gira KNX Tastsensor 3 Komfort, Gira KNX Präsenzmelder, Fenster- und Türkontakte, Loxone Regen- und Windsensor, Gira Dual Q Rauchmelder vernetzt, 1x Relais-Modul
                    Loxberry: SmartMeter, MS Backup, CamConnect, Weather4Lox
                    Lüftung: Helios KWL EC 370W ET mit Modbus TCP - via Pico-C
                    Heizung: Stiebel Eltron WPF 5 cool (Sole-Wasser WP) mit ISG, FB-Heizung mit 18 Kreisen, Erdsonde - via modbus/TCP
                    Node-RED: IKEA Tradfri

                    Kommentar

                    • K.Clemens
                      Smart Home'r
                      • 28.08.2015
                      • 92

                      #11
                      hi, thanks again for your input. May I ask you for a favor? Would you be so kind to take a look at the code below?
                      The code so far results in 2 "errors":
                      2016-06-27 17:52:52.136;Creating Stream failed 2016-06-27 17:52:52.136; return; USR IOT Tuinhuis:30:0 missing main program code
                      2016-06-27 17:11:25.204; if ( response[7] == 0x01 AND response[9] == 0x88) { ^ USR IOT Tuinhuis:93:28 identifier not expected here // IP USR-IOT

                      char* IP_ADDRESS = "xxx.xxx.xxx.xxx";

                      // Port (standard port = xxxx)

                      char* PORT = "xxxx";

                      char streamname[100];
                      char buffer[1024];
                      int f1,f2,f3,f4,f5,f6,f7,f8;

                      char response[9];
                      int nLen;

                      sprintf(streamname, "/dev/tcp/%s/%s/", IP_ADDRESS, PORT);
                      STREAM* TcpStream = stream_create(streamname,0,0);

                      if (TcpStream == NULL) {

                      printf("Creating Stream failed");

                      stream_close(TcpStream);

                      return;

                      }
                      // send admin password
                      void sendCommand(char* command) {

                      if (command == "Relais1_ON") {
                      char relais[8] = {0x55, 0xAA, 0x00, 0x03, 0x00, 0x02, 0x01, 0x06};
                      stream_write(TcpStream, relais, 8);
                      stream_flush(TcpStream);
                      }
                      else if (command == "Relais1_OFF"){
                      // off command for relais 1
                      char relais2[8] = {0x55, 0xAA, 0x00, 0x03, 0x00, 0x01, 0x01, 0x05};
                      stream_write(TcpStream, relais2, 8);
                      stream_flush(TcpStream);
                      }
                      }

                      sprintf(buffer, "\x61\x64\x6D\x69\x6E\x0D\x0A");
                      stream_write(TcpStream,buffer,strlen(buffer));
                      stream_flush(TcpStream);

                      // to test
                      char relais[8] = {0x55, 0xAA, 0x00, 0x03, 0x00, 0x01, 0x01, 0x05};
                      stream_write(TcpStream, relais, 8);
                      stream_flush(TcpStream);

                      sleep (2000);

                      while (1==1) {
                      // read content from relais if 8 bytes were received
                      nLen = stream_read(TcpStream,response,9,100);
                      if (nLen==9) {
                      // command for relais 1 ON: 55 AA 00 03 00 02 01 06
                      // Response for relais 1 ON: AA 55 00 04 00 82 01 01 88
                      // command for relais 1 OFF: 55 AA 00 03 00 01 01 05
                      // Response for relais 1 OFF: AA 55 00 04 00 81 01 00 86

                      // command for relais 2 ON:55 AA 00 03 00 02 02 07
                      // Response for relais 2 ON:: AA 55 00 04 00 82 02 01 89
                      // command for relais 2 OFF: 55 AA 00 03 00 01 02 06
                      // Response for relais 2 OFF: AA 55 00 04 00 81 02 00 87

                      // command for relais 3 ON: 55 AA 00 03 00 02 03 08
                      // Response for relais 3 ON: AA 55 00 04 00 82 03 01 8A
                      // command for relais 3 OFF: 55 AA 00 03 00 01 01 05
                      // Response for relais 3 OFF: AA 55 00 04 00 81 03 00 88

                      // command for relais 5 ON: 55 AA 00 03 00 02 05 0A
                      // Response for relais 5 ON: AA 55 00 04 00 82 05 01 8C
                      // command for relais 5 OFF: 55 AA 00 03 00 01 05 09
                      // Response for relais 5 OFF: AA 55 00 04 00 81 05 00 8A



                      // command for relais 8 ON: 55 AA 00 03 00 02 08 0D
                      // Response for relais 8 ON: AA 55 00 04 00 82 08 01 8F
                      // command for relais 8 OFF: 55 AA 00 03 00 01 08 0C
                      // Response for relais 8 OFF: AA 55 00 04 00 81 08 00 8D

                      if ( response[6] == 0x82) {
                      if ( (response[7] == 0x01) AND (response[9] == 0x88)) {
                      setoutput(0,1);
                      sleep(5000);
                      sendCommand("Relais1_OFF");
                      }

                      else if ( (response[7] == 0x02) AND (response[9] == 0x89)) {
                      setoutput(0,1);
                      sleep(5000);
                      sendCommand("Relais2_OFF");
                      }
                      }
                      else if ( (response[6] == 0x81)) {
                      if ( (response[7] == "0x01") AND (response[9] == "0x86")) {
                      setoutput(0,1);
                      sleep(5000);
                      sendCommand("Relais1_ON");
                      }

                      else if ( (response[7] == "0x02") AND (response[9] == "0x87")) {
                      setoutput(0,1);
                      sleep(5000);
                      sendCommand("Relais2_ON");
                      }
                      }
                      }
                      sleep(500);
                      }



                      sleep(30000);
                      //close connection
                      stream_close(TcpStream);

                      Kommentar

                      • Jan W.
                        Lox Guru
                        • 30.08.2015
                        • 1366

                        #12
                        You are mixing the function sendCommand with the main code. If you want to use a function that code needs to be put before the first command in "main". Regarding the second error you should use && (logical AND Operator). You should also remove "" from the hex bytes in the following statements. You may not receive syntax errors, but the result will always be a false. I'm not sure if a trailing / is allowed after the port number in the string.

                        I also recommend to use a loop like in example 3 of the Loxone examples, see http://www.loxone.com/dede/service/d.../programm.html. In your code the stream_create is done before the endless loop, so any TCP error, e.g. Ethernet switch down, cable to sensor disconnected will only recover with a restart of the MS. If you put the create and close statements of the stream within the endless loop, then you just have to recreate connectivity.

                        You should also keep in mind that arrays are starting with a 0, so char response[9]; creates an array with index 0..8 ! response[9] will point to a memory position outside of the array and may cause problems or crashes to the program.

                        Instead of using a string I would recommend to use two simple integers as parameters in sendCommand. If you really want to use strings, then you have to use strcmp instead of using the compare operator equal "==". The "==" will NOT compare strings, but only compare the pointers in memory, so the result will be false in most cases. For better readability you may define constants, e.g.

                        #define RELAIS1 0
                        #define RELAIS2 1
                        #define ON 2
                        #define OFF 1
                        ...
                        and use e.g. sendCommand(RELAIS1, ON);

                        I would also recommend to move the definition of the two byte arrays "relais" to the beginning of the code and make them global. Pico C is using an interpreter and you should keep the CPU time as low as possible. The fastet code may be with two two-dimensional arrays:

                        char relaisON[8][8] = {
                        {0x55, 0xAA, 0x00, 0x03, 0x00, 0x02, 0x01, 0x06},
                        ... // here are the byte sequences for all 8 relais to switch them on
                        };

                        char relaisOFF[8][8] = {
                        ... // here are the byte sequences for all 8 relais to switch them off
                        };

                        and

                        // it is assumed that the parameters are static values and correct, so no check of the boundaries are required
                        void sendCommand(int relaisno, int state) {

                        if (state==ON) {
                        stream_write(TcpStream, relaisON[relaisno], 8);
                        } else {
                        stream_write(TcpStream, relaisOFF[relaisno], 8);
                        }
                        stream_flush(TcpStream);
                        }

                        I would also recommend to make a backup of the SD card of the MS before playing around with Pico C, so you have an easy way to go back in case the MS server crashes.

                        Kind Regards,

                        Jan
                        Miniserver v14.5.12.7, 2x Ext., 2x Relay Ext., 2x Dimmer Ext., DMX Ext., 1-Wire Ext., Gira KNX Tastsensor 3 Komfort, Gira KNX Präsenzmelder, Fenster- und Türkontakte, Loxone Regen- und Windsensor, Gira Dual Q Rauchmelder vernetzt, 1x Relais-Modul
                        Loxberry: SmartMeter, MS Backup, CamConnect, Weather4Lox
                        Lüftung: Helios KWL EC 370W ET mit Modbus TCP - via Pico-C
                        Heizung: Stiebel Eltron WPF 5 cool (Sole-Wasser WP) mit ISG, FB-Heizung mit 18 Kreisen, Erdsonde - via modbus/TCP
                        Node-RED: IKEA Tradfri

                        Kommentar

                        • K.Clemens
                          Smart Home'r
                          • 28.08.2015
                          • 92

                          #13
                          wow, big thanks for the time you put into this! Appreciate it!

                          The program seems to struggle with the double array:

                          char relaisON[8][8] = {
                          {0x55, 0xAA, 0x00, 0x03, 0x00, 0x02, 0x01, 0x06},
                          {0x55, 0xAA, 0x00, 0x03, 0x00, 0x02, 0x02, 0x07},
                          {0x55, 0xAA, 0x00, 0x03, 0x00, 0x02, 0x03, 0x08},
                          {0x55, 0xAA, 0x00, 0x03, 0x00, 0x02, 0x04, 0x09},
                          {0x55, 0xAA, 0x00, 0x03, 0x00, 0x02, 0x05, 0x0A},
                          {0x55, 0xAA, 0x00, 0x03, 0x00, 0x02, 0x06, 0x0B},
                          {0x55, 0xAA, 0x00, 0x03, 0x00, 0x02, 0x07, 0x0C},
                          {0x55, 0xAA, 0x00, 0x03, 0x00, 0x02, 0x08, 0x0D},
                          };

                          Again I get the error of "expression expected". Does this mean I have to do the following?:

                          char relaisON1[8] = {0x55, 0xAA, 0x00, 0x03, 0x00, 0x02, 0x01, 0x06};
                          char relaisON2[8] = {0x55, 0xAA, 0x00, 0x03, 0x00, 0x02, 0x02, 0x07};
                          ....

                          Furthermore, how does the counting of the inputs in bits work? I've searched google but I do not understand.
                          http://www.eng.umd.edu/~nsw/chbe250/number.htm gives the bits for a certain number.

                          Below I've extracted from https://github.com/netdata/loxone/bl...lamp/milight.c

                          input 3: 0x04
                          input 4: 0x08,
                          input 5: 0x10,
                          input 6: 0x20,

                          Why not just use below, as described on the loxone website?
                          http://www.loxone.com/enen/service/d...m-program.html (getinputevent):
                          input 3: 0x03
                          input 4: 0x04,
                          input 5: 0x05,
                          input 6: 0x06,

                          FYI, the code so far is the following:
                          Any big mistakes that you already see?

                          // IP USR-IOT

                          char* IP_ADDRESS = "xxx.xxx.xxx.xxxé;

                          // Port (standard port = xxxx)

                          char* PORT = "xxxx";

                          char streamname[100];

                          char buffer[1024];
                          int f1,f2,f3,f4,f5,f6,f7,f8;

                          char response[9];
                          int nLen;
                          int nEvents;

                          #define RELAIS1 0
                          #define RELAIS2 1
                          #define RELAIS3 2
                          #define RELAIS4 3
                          #define RELAIS5 4
                          #define RELAIS6 5
                          #define RELAIS7 6
                          #define RELAIS8 7
                          #define ON 2
                          #define OFF 1

                          // here are the byte sequences for all 8 relais to switch them on
                          char relaisON[8][8] = {
                          {0x55, 0xAA, 0x00, 0x03, 0x00, 0x02, 0x01, 0x06},
                          {0x55, 0xAA, 0x00, 0x03, 0x00, 0x02, 0x02, 0x07},
                          {0x55, 0xAA, 0x00, 0x03, 0x00, 0x02, 0x03, 0x08},
                          {0x55, 0xAA, 0x00, 0x03, 0x00, 0x02, 0x04, 0x09},
                          {0x55, 0xAA, 0x00, 0x03, 0x00, 0x02, 0x05, 0x0A},
                          {0x55, 0xAA, 0x00, 0x03, 0x00, 0x02, 0x06, 0x0B},
                          {0x55, 0xAA, 0x00, 0x03, 0x00, 0x02, 0x07, 0x0C},
                          {0x55, 0xAA, 0x00, 0x03, 0x00, 0x02, 0x08, 0x0D},
                          };

                          // here are the byte sequences for all 8 relais to switch them off
                          char relaisOFF[8][8] = {
                          {0x55, 0xAA, 0x00, 0x03, 0x00, 0x01, 0x01, 0x05},
                          {0x55, 0xAA, 0x00, 0x03, 0x00, 0x01, 0x02, 0x06},
                          {0x55, 0xAA, 0x00, 0x03, 0x00, 0x01, 0x03, 0x07},
                          {0x55, 0xAA, 0x00, 0x03, 0x00, 0x01, 0x04, 0x08},
                          {0x55, 0xAA, 0x00, 0x03, 0x00, 0x01, 0x05, 0x09},
                          {0x55, 0xAA, 0x00, 0x03, 0x00, 0x01, 0x06, 0x0A},
                          {0x55, 0xAA, 0x00, 0x03, 0x00, 0x01, 0x07, 0x0B},
                          {0x55, 0xAA, 0x00, 0x03, 0x00, 0x01, 0x08, 0x0C},
                          };

                          // it is assumed that the parameters are static values and correct, so no check of the boundaries are required
                          void sendCommand(int relaisno, int state) {
                          if (state==ON) {
                          stream_write(TcpStream, relaisON[relaisno], 8);
                          } else {
                          stream_write(TcpStream, relaisOFF[relaisno], 8);
                          }
                          stream_flush(TcpStream);
                          }

                          while(TRUE)
                          {
                          sprintf(streamname, "/dev/tcp/%s/%s/", IP_ADDRESS, PORT);
                          STREAM* TcpStream = stream_create(streamname,0,0);

                          if (TcpStream != NULL) {

                          //send password
                          char relais[7] = {0x61, 0x64, 0x6D, 0x69, 0x6E, 0x0D, 0x0A};
                          stream_write(TcpStream, relais, 7);
                          stream_flush(TcpStream);

                          // check if a relais is set active in Loxone
                          nEvents = getinputevent();
                          if (nEvents & 0xe) {
                          // Test bitwise if input 3 was changed (00000100)
                          if (nEvents & 0x04) {
                          if (getinput(0) == 1) {
                          sendCommand(1, ON);
                          } else {
                          sendCommand(1, OFF);
                          }
                          }
                          // Test bitwise if input 4 is changed (00001000)
                          if (nEvents & 0x08) {
                          if (getinput(1) == 1) {
                          sendCommand(2, ON);
                          } else {
                          sendCommand(2, OFF);
                          }
                          }
                          // Test bitwise if input 5 is changed (00010000)
                          if (nEvents & 0x10) {
                          if (getinput(2) == 1) {
                          sendCommand(3, ON);
                          } else {
                          sendCommand(3, OFF);
                          }
                          }
                          // Test bitwise if input 6 is changed (00100000)
                          if (nEvents & 0x20) {
                          if (getinput(3) == 1) {
                          sendCommand(4, ON);
                          } else {
                          sendCommand(4, OFF);
                          }
                          }
                          }

                          //check if the status of the relais is changed on the relais board itself.
                          nLen = stream_read(TcpStream,response,9,100);
                          if (nLen==9) {
                          if ((response[5] == 0x82) {
                          if ((response[6] == 0x01) && (response[8] == 0x88)){
                          setoutput(0,1);
                          }
                          if ((response[6] == 0x02) && (response[8] == 0x89)){
                          setoutput(1,1);
                          }
                          }
                          if ((response[5] == 0x81) {
                          if ((response[6] == 0x01) && (response[8] == 0x86)){
                          setoutput(0,0);
                          }
                          if ((response[6] == 0x02) && (response[8] == 0x87)){
                          setoutput(1,0);
                          }
                          }
                          }
                          }
                          stream_close(TcpStream);
                          sleep(500);
                          }
                          Zuletzt geändert von K.Clemens; 29.06.2016, 20:01.

                          Kommentar

                          • Jan W.
                            Lox Guru
                            • 30.08.2015
                            • 1366

                            #14
                            I haven't tested the my code from the previous post on the MS, but only on a PC with Pico C. It looks that two-dimensional arrays produce different results on a PC compared to a MS and they don't work as they should on a MS - neither you can initialize them nor you can work with them properly. So I have learned a lesson, too. At the end of the day it looks that you probably don't need them. You may use single-dimensional byte arrays like relaisON1 to 8 as you've posted already.

                            So far I haven't figured out why the string contains the relais number twice: 7th byte (relais number) and 8th byte (relais number plus 5). Is it a kind of checksum? It looks a bit odd. I'm also not sure how the process for the responses work. Do you read them in a round robin fashion, one after each other, so you have to read 8 times to get the status for all relais from the board?

                            Regarding the relationship between analog input numbers and the bitmask "getinputevent": it depends on the type of program, so it is different for a program with 4, 8 or 16 inputs! This is a bit tricky, because you can't just reuse your code in another program block with a different number of inputs. You have to adjust the code regarding the mask which is not that easy. From your code I assume that you are using a program with 8 inputs. The specific bitmasks for "getinputevent" look to be correct as well as the number for "getinput", but the first check if any of the analog inputs have changed need to be modified from (nEvents & 0xe) to (nEvents & 0x3b). 0x3c=0011 1100 The bitmask needs to include all single bits, so you may "OR" the specifc masks to get that number. The example from Loxone was most likely using a program with 4 inputs, so 0xe = 1110 is correct to cover the 3 analog inputs that are mentioned in the example.

                            The following code was tested on my MS and it worked. Looks that Loxone has modified sprintf, because the return code is not the length of the string written as with standard C (I was not aware of that). Therefore the b+=6 statement looks a bit ugly. You may use the printRelais function for debugging purpose, especially to verify the result codes that are returned from the board. Well you may have add a length parameter to the function to cover 9 byte results, but that should be easy.


                            char buffer[512];

                            char relaisON0[8] = {0x55, 0xAA, 0x00, 0x03, 0x00, 0x02, 0x01, 0x06};
                            char relaisON1[8] = {0x55, 0xAA, 0x00, 0x03, 0x00, 0x02, 0x02, 0x07};
                            char relaisON2[8] = {0x55, 0xAA, 0x00, 0x03, 0x00, 0x02, 0x03, 0x08};
                            char relaisON3[8] = {0x55, 0xAA, 0x00, 0x03, 0x00, 0x02, 0x04, 0x09};
                            char relaisON4[8] = {0x55, 0xAA, 0x00, 0x03, 0x00, 0x02, 0x05, 0x0A};
                            char relaisON5[8] = {0x55, 0xAA, 0x00, 0x03, 0x00, 0x02, 0x06, 0x0B};
                            char relaisON6[8] = {0x55, 0xAA, 0x00, 0x03, 0x00, 0x02, 0x07, 0x0C};
                            char relaisON7[8] = {0x55, 0xAA, 0x00, 0x03, 0x00, 0x02, 0x08, 0x0D};


                            void printRelais(char *byteseq)
                            {
                            int j;
                            char *b;

                            b=buffer;
                            memset( buffer, 0, 512);
                            sprintf( buffer, "DEBUG - byte sequence: " );
                            b+=strlen(buffer);

                            for ( j=0; j<8; j++ ) {
                            sprintf( b, "0x%02x, ",(unsigned char)(byteseq[j]) );
                            b+=6;
                            }
                            setlogtext(buffer);
                            }

                            sprintf(buffer, "START relais ");
                            setlogtext(buffer);

                            printRelais(relaisON0);
                            printRelais(relaisON1);
                            printRelais(relaisON2);
                            printRelais(relaisON3);
                            printRelais(relaisON4);
                            printRelais(relaisON5);
                            Miniserver v14.5.12.7, 2x Ext., 2x Relay Ext., 2x Dimmer Ext., DMX Ext., 1-Wire Ext., Gira KNX Tastsensor 3 Komfort, Gira KNX Präsenzmelder, Fenster- und Türkontakte, Loxone Regen- und Windsensor, Gira Dual Q Rauchmelder vernetzt, 1x Relais-Modul
                            Loxberry: SmartMeter, MS Backup, CamConnect, Weather4Lox
                            Lüftung: Helios KWL EC 370W ET mit Modbus TCP - via Pico-C
                            Heizung: Stiebel Eltron WPF 5 cool (Sole-Wasser WP) mit ISG, FB-Heizung mit 18 Kreisen, Erdsonde - via modbus/TCP
                            Node-RED: IKEA Tradfri

                            Kommentar

                            • K.Clemens
                              Smart Home'r
                              • 28.08.2015
                              • 92

                              #15
                              Zitat von Jan W.

                              Regarding the relationship between analog input numbers and the bitmask "getinputevent": it depends on the type of program, so it is different for a program with 4, 8 or 16 inputs! This is a bit tricky, because you can't just reuse your code in another program block with a different number of inputs. You have to adjust the code regarding the mask which is not that easy. From your code I assume that you are using a program with 8 inputs. The specific bitmasks for "getinputevent" look to be correct as well as the number for "getinput", but the first check if any of the analog inputs have changed need to be modified from (nEvents & 0xe) to (nEvents & 0x3b). 0x3c=0011 1100 The bitmask needs to include all single bits, so you may "OR" the specifc masks to get that number. The example from Loxone was most likely using a program with 4 inputs, so 0xe = 1110 is correct to cover the 3 analog inputs that are mentioned in the example.
                              I'm afraid I don't really follow. I'm using a program block of 16 inputs, because I need at least 8 analog inputs. The program block of 8 inputs only has 6 analog inputs.
                              If I understand correctly the first check has to be "if (nEvents & 0x3b) {"? Furthermore, how do you exactly determine the specific mask for any output? (I would assume this should be in the articles on the loxone website, but this is not the case.)


                              // Test bitwise if input 3 was changed (00000100)
                              if (nEvents & 0x04) {

                              }
                              // Test bitwise if input 4 is changed (00001000)
                              if (nEvents & 0x08) {

                              }
                              // Test bitwise if input 5 is changed (00010000)
                              if (nEvents & 0x10) {

                              }
                              // Test bitwise if input 6 is changed (00100000)
                              if (nEvents & 0x20) {

                              }

                              Kommentar

                              Lädt...