Controller does not get ack from z-uno

Discussion about Z-Uno product. Visit http://z-uno.z-wave.me for more details.
knst08
Posts: 28
Joined: 15 Oct 2017 20:14

Controller does not get ack from z-uno

Post by knst08 »

I've set up 9 binary switches (+1 multilevel power sensor).
Controller (Fibaro HC2) registers the device without any problem, but if change switches state from controller UI fast enough e.g. turn all switches one by one or switch single one on/off several times controller losses connection with the device.

In controller logs I see

Code: Select all

1 18:41:21:1 [Error] ZWAVE: [0m[1;41m[ZwaveTransportAPI] FUNC_ID_ZW_SEND_DATA: JobID: 955 Status: TRANSMIT_COMPLETE_NO_ACK[0m
1 18:41:21:1 [Notice] DRIVER: Resend frame txCount: 3 max retry send: 3[0m
1 18:41:21:1 [Error] DRIVER: [0m[1;41mdevId: 354 nId: 49 eId: 4 jobId: 955 >> cc: Command Class Switch Binary cmd: Switch Binary Set ccWaitFor: none cmdWaitFor: none ack: false callback: 0 waitFunction: 0x0 isNeedResend: true txCount: 3 prio: 11 Security: false CRC: false MultiCmd: false bufferCmd: H: 0x60 0xD 0x4 0x4 0x25 0x1 0xFF : transmission failed. The device will be marked as dead.[0m
1 18:41:21:1 [Warning] NODE: [0m[1;33mdevID: 349 nID: 49 >> don't mark dead device[0m
If changing switch state not oftener then once per 5 seconds everything works ok.

It hardly can be a connectivity issues since there are at least 2 z-wave devices near z-uno (fibaro dimmer and relay), both operate without issues.

z-uno z-wave setup:

Code: Select all

ZUNO_SETUP_SLEEPING_MODE(ZUNO_SLEEPING_MODE_ALWAYS_AWAKE);
ZUNO_SETUP_CFGPARAMETER_HANDLER(settingsParameterChanged);

// Set up 10 channels
ZUNO_SETUP_CHANNELS(
  ZUNO_SWITCH_BINARY(getterBypass, setterBypass),
  ZUNO_SWITCH_BINARY(getterRelay0, setterRelay0),
  ZUNO_SWITCH_BINARY(getterRelay1, setterRelay1),
  ZUNO_SWITCH_BINARY(getterRelay2, setterRelay2),
  ZUNO_SWITCH_BINARY(getterRelay3, setterRelay3),
  ZUNO_SWITCH_BINARY(getterRelay4, setterRelay4),
  ZUNO_SWITCH_BINARY(getterRelay5, setterRelay5),
  ZUNO_SWITCH_BINARY(getterRelay6, setterRelay6),
  ZUNO_SWITCH_BINARY(getterRelay7, setterRelay7),
  ZUNO_SENSOR_MULTILEVEL_POWER(powerMetterGetter)
);
knst08
Posts: 28
Joined: 15 Oct 2017 20:14

Re: Controller does not get ack from z-uno

Post by knst08 »

Found the problem - due to the bug zuno was constantly sending unsolicited reports. After bug was fixed problem has gone. Obviously endless report sending was overloading the communication ether radio channel or more likely core zuno z-wave implementation.
sega66
Posts: 38
Joined: 30 Jul 2017 19:31

Re: Controller does not get ack from z-uno

Post by sega66 »

You can read more..
petergebruers
Posts: 255
Joined: 26 Jul 2015 17:29

Re: Controller does not get ack from z-uno

Post by petergebruers »

Thanks for reporting back, knst08! So you had a fast loop that called zunoSendReport()... That killed the network.
If you had used channels of type "ZUNO_SENSOR_MULTILEVEL" instead of "ZUNO_SWITCH_BINARY" you would probably not have noticed, because by default Z-Uno sends only every 30s by default, as mandated by the Z-Wave spec. But the 'binary' version is not speed-limited, probably because users want immediate feedback from switch actions :-)
sega66
Posts: 38
Joined: 30 Jul 2017 19:31

Re: Controller does not get ack from z-uno

Post by sega66 »

Thank you!
How to use a lot of "ZUNO_SWITCH_BINARY"? Can use the delay ?
petergebruers
Posts: 255
Joined: 26 Jul 2015 17:29

Re: Controller does not get ack from z-uno

Post by petergebruers »

@sega66 using many ZUNO_SWITCH_BINARY is not a problem. You only have to be careful with zunoSendReport(), call it only when necessary.

Do you have a problem at the moment? If so, can you post your code?
sega66
Posts: 38
Joined: 30 Jul 2017 19:31

Re: Controller does not get ack from z-uno

Post by sega66 »

petergebruers
Thanks for answers!
I'll give you a piece of my code that uses 4 switches. It works well, but if I add a few more switches, then I see large latencies in the Zipato controller. If necessary, I can provide all the code ...

Code: Select all

#define RelePin1 10 // выход 1-го реле
#define RelePin2 11 // выход 2-го реле
#define RelePin3 12 // выход 3-го реле
#define RelePin4 14 // выход 4-го реле

#define SWITCH_ON 0xff
#define SWITCH_OFF 0

byte switchValue1 = 0;  // Начальное значение выходов на реле. Реле вкл., когда на входе 0
byte switchValue2 = 0;
byte switchValue3 = 0;
byte switchValue4 = 0;

ZUNO_SETUP_SLEEPING_MODE(ZUNO_SLEEPING_MODE_ALWAYS_AWAKE);
ZUNO_SETUP_ASSOCIATIONS(ZUNO_ASSOCIATION_GROUP_SET_VALUE); // Send Basic Set to association group

ZUNO_SETUP_CHANNELS(

  ZUNO_SWITCH_BINARY(getterSwitch1, setterSwitch1),
  ZUNO_SWITCH_BINARY(getterSwitch2, setterSwitch2),
  ZUNO_SWITCH_BINARY(getterSwitch3, setterSwitch3),
  ZUNO_SWITCH_BINARY(getterSwitch4, setterSwitch4)
);

void setup() {

  pinMode(RelePin1, OUTPUT);
  pinMode(RelePin2, OUTPUT);
  pinMode(RelePin3, OUTPUT);
  pinMode(RelePin4, OUTPUT);
}
void loop()
{

}
void setterSwitch1(byte value) {
  digitalWrite(RelePin1, (value > 0) ? LOW : HIGH);

  switchValue1 = value;
}

byte getterSwitch1() {
  return switchValue1;
}
void setterSwitch2(byte value) {
  digitalWrite(RelePin2, (value > 0) ? LOW : HIGH);

  switchValue2 = value;
}
byte getterSwitch2() {
  return switchValue2;
}
void setterSwitch3(byte value) {
  digitalWrite(RelePin3, (value > 0) ? LOW : HIGH);

  switchValue3 = value;
}
byte getterSwitch3() {
  return switchValue3;
}
void setterSwitch4(byte value) {
  digitalWrite(RelePin4, (value > 0) ? LOW : HIGH);

  switchValue4 = value;
}
byte getterSwitch4() {
  return switchValue4;
}
[code]
petergebruers
Posts: 255
Joined: 26 Jul 2015 17:29

Re: Controller does not get ack from z-uno

Post by petergebruers »

Do you use associations? This might slow down your network. I have not toyed with associations myself on a Z-Uno, I only know they are used in the "IR2ZWave" example:

http://z-uno.z-wave.me/examples/IR2ZWave/
sega66
Posts: 38
Joined: 30 Jul 2017 19:31

Re: Controller does not get ack from z-uno

Post by sega66 »

Without the use of associations with a large number of switches response Zapato anyway slow.
petergebruers
Posts: 255
Joined: 26 Jul 2015 17:29

Re: Controller does not get ack from z-uno

Post by petergebruers »

I have tried to reproduce your problem, by writing my own 6-switch sketch and adding the Z-Uno to my RaZberry. Code below. I added lots of debug statements and timestamps, so you can verify the result.

I see no unexpected behaviour.

For example, when I press "update all" (this polls all channels) the debug output is:

Code: Select all

getterSwitch1 timestamp : 15593, value : 0.
getterSwitch1 timestamp : 15663, value : 0.
getterSwitch5 timestamp : 15734, value : 0.
getterSwitch2 timestamp : 15804, value : 0.
getterSwitch3 timestamp : 15875, value : 0.
getterSwitch4 timestamp : 15945, value : 0.
getterSwitch6 timestamp : 16015, value : 0.
Timestamp is ms since start of sketch, so reading all data took 16015 ms -15663 ms = about 0.35 seconds.

This is the debug log of clicking on "set all on":

Code: Select all

setterSwitch1 timestamp : 189507, value : 255, switchValue1 : 1.
getterSwitch1 timestamp : 189519, value : 1.
getterSwitch1 timestamp : 189528, value : 1.
getterSwitch1 timestamp : 189626, value : 1.
setterSwitch1 timestamp : 189698, value : 255, switchValue1 : 1.
getterSwitch1 timestamp : 189710, value : 1.
getterSwitch1 timestamp : 189719, value : 1.
getterSwitch1 timestamp : 189817, value : 1.
setterSwitch4 timestamp : 189878, value : 255, switchValue4 : 1.
getterSwitch4 timestamp : 189890, value : 1.
getterSwitch4 timestamp : 189967, value : 1.
setterSwitch5 timestamp : 190036, value : 255, switchValue5 : 1.
getterSwitch5 timestamp : 190048, value : 1.
getterSwitch5 timestamp : 190127, value : 1.
setterSwitch2 timestamp : 190198, value : 255, switchValue2 : 1.
getterSwitch2 timestamp : 190210, value : 1.
getterSwitch2 timestamp : 190289, value : 1.
setterSwitch3 timestamp : 190350, value : 255, switchValue3 : 1.
getterSwitch3 timestamp : 190362, value : 1.
getterSwitch3 timestamp : 190430, value : 1.
setterSwitch6 timestamp : 190491, value : 255, switchValue6 : 1.
getterSwitch6 timestamp : 190503, value : 1.
getterSwitch6 timestamp : 190580, value : 1.
This time it took 190580 - 189507 = about 1.1 second.

This seems normal to me. You might think there are too many lines, but I can explain most of them. The first channel is duplicated, but the controller does not know that and so it sets and requests the same thing twice. Then, for the other channels, a getter is shown twice because one report is unsolicited and the second one is requested by the controller. The only thing I do not understand, is why channel one getter is called three times instead of two...

In your previous post you said "I see large latencies" ... can you please try my sketch and give some numbers?

Sketch:

Code: Select all

#define SwitchOut1 10
#define SwitchOut2 11
#define SwitchOut3 12
#define SwitchOut4 13
#define SwitchOut5 14
#define SwitchOut6 15

byte switchValue1 = 0;
byte switchValue2 = 0;
byte switchValue3 = 0;
byte switchValue4 = 0;
byte switchValue5 = 0;
byte switchValue6 = 0;

ZUNO_SETUP_SLEEPING_MODE(ZUNO_SLEEPING_MODE_ALWAYS_AWAKE);

ZUNO_SETUP_CHANNELS(
  ZUNO_SWITCH_BINARY(getterSwitch1, setterSwitch1),
  ZUNO_SWITCH_BINARY(getterSwitch2, setterSwitch2),
  ZUNO_SWITCH_BINARY(getterSwitch3, setterSwitch3),
  ZUNO_SWITCH_BINARY(getterSwitch4, setterSwitch4),
  ZUNO_SWITCH_BINARY(getterSwitch5, setterSwitch5),
  ZUNO_SWITCH_BINARY(getterSwitch6, setterSwitch6)
);

// PG_DEBUG_OUT must be 10 for Serial0, 11 for Serial1, 99 for USB or
// - 1 for no debugging.
#define PG_DEBUG_OUT 99

// ****** DEBUGGING HELPER MACROS  BEGIN ****** //

#if PG_DEBUG_OUT == 10
#define PG_DEBUG_OUT_SER Serial0

#elif PG_DEBUG_OUT == 11
#define PG_DEBUG_OUT_SER Serial1

#elif PG_DEBUG_OUT == 99
#define PG_DEBUG_OUT_SER Serial

#elif PG_DEBUG_OUT == -1
#undef PG_DEBUG_OUT_SER

#else
#error "PG_DEBUG_OUT must be 10 for Serial0, 11 for Serial1, 99 for USB or \
- 1 for no debugging."
#endif

#ifdef PG_DEBUG_OUT_SER

#define PG_DEBUG_BEGIN(...) PG_DEBUG_OUT_SER.begin(__VA_ARGS__)

#define PG_DEBUG_PRN(...) PG_DEBUG_OUT_SER.print(__VA_ARGS__)
#define PG_DEBUG_PRN_NEWLINE(...) PG_DEBUG_OUT_SER.print(__VA_ARGS__);\
  PG_DEBUG_OUT_SER.print("\n")
#define PG_DEBUG_PRN_DOTNEWLINE(...) PG_DEBUG_OUT_SER.print(__VA_ARGS__);\
  PG_DEBUG_OUT_SER.print(".\n")

#define PG_DEBUG_LOG(message, ...) PG_DEBUG_OUT_SER.print(message);\
  PG_DEBUG_OUT_SER.print(__VA_ARGS__)
#define PG_DEBUG_LOG_NEWLINE(message, ...) PG_DEBUG_OUT_SER.print(message);\
  PG_DEBUG_OUT_SER.print(__VA_ARGS__);PG_DEBUG_OUT_SER.print("\n")
#define PG_DEBUG_LOG_DOTNEWLINE(message, ...) PG_DEBUG_OUT_SER.print(message);\
  PG_DEBUG_OUT_SER.print(__VA_ARGS__);PG_DEBUG_OUT_SER.print(".\n")

#else

#define PG_DEBUG_PRN(...)
#define PG_DEBUG_PRN_NEWLINE(...)
#define PG_DEBUG_PRN_DOTNEWLINE(...)
#define PG_DEBUG_LOG(message, ...)
#define PG_DEBUG_LOG_NEWLINE(message, ...)
#define PG_DEBUG_LOG_DOTNEWLINE(message, ...)

#endif

// ****** DEBUGGING HELPER MACROS END ****** //

unsigned long start;

void setup() {
  PG_DEBUG_BEGIN();
  pinMode(SwitchOut1, OUTPUT);
  pinMode(SwitchOut2, OUTPUT);
  pinMode(SwitchOut3, OUTPUT);
  pinMode(SwitchOut4, OUTPUT);
  pinMode(SwitchOut5, OUTPUT);
  pinMode(SwitchOut6, OUTPUT);
  start = millis();
}

void loop()
{
}

//----- SETTERS -----//

void setterSwitch1(byte value) {
  PG_DEBUG_LOG("setterSwitch1 timestamp : ", millis() - start);
  PG_DEBUG_LOG(", value : ", value);
  if (value > 99 && value < 254) {
    PG_DEBUG_PRN_DOTNEWLINE(", value is invalid, ignored");
    return;
  }
  switchValue1 = (value == 0) ? LOW : HIGH;
  PG_DEBUG_LOG_DOTNEWLINE(", switchValue1 : ", switchValue1);
  digitalWrite(SwitchOut1, switchValue1);
}

void setterSwitch2(byte value) {
  PG_DEBUG_LOG("setterSwitch2 timestamp : ", millis() - start);
  PG_DEBUG_LOG(", value : ", value);
  if (value > 99 && value < 254) {
    PG_DEBUG_PRN_DOTNEWLINE(", value is invalid, ignored");
    return;
  }
  switchValue2 = (value == 0) ? LOW : HIGH;
  PG_DEBUG_LOG_DOTNEWLINE(", switchValue2 : ", switchValue2);
  digitalWrite(SwitchOut2, switchValue2);
}

void setterSwitch3(byte value) {
  PG_DEBUG_LOG("setterSwitch3 timestamp : ", millis() - start);
  PG_DEBUG_LOG(", value : ", value);
  if (value > 99 && value < 254) {
    PG_DEBUG_PRN_DOTNEWLINE(", value is invalid, ignored");
    return;
  }
  switchValue3 = (value == 0) ? LOW : HIGH;
  PG_DEBUG_LOG_DOTNEWLINE(", switchValue3 : ", switchValue3);
  digitalWrite(SwitchOut3, switchValue3);
}

void setterSwitch4(byte value) {
  PG_DEBUG_LOG("setterSwitch4 timestamp : ", millis() - start);
  PG_DEBUG_LOG(", value : ", value);
  if (value > 99 && value < 254) {
    PG_DEBUG_PRN_DOTNEWLINE(", value is invalid, ignored");
    return;
  }
  switchValue4 = (value == 0) ? LOW : HIGH;
  PG_DEBUG_LOG_DOTNEWLINE(", switchValue4 : ", switchValue4);
  digitalWrite(SwitchOut4, switchValue4);
}

void setterSwitch5(byte value) {
  PG_DEBUG_LOG("setterSwitch5 timestamp : ", millis() - start);
  PG_DEBUG_LOG(", value : ", value);
  if (value > 99 && value < 254) {
    PG_DEBUG_PRN_DOTNEWLINE(", value is invalid, ignored");
    return;
  }
  switchValue5 = (value == 0) ? LOW : HIGH;
  PG_DEBUG_LOG_DOTNEWLINE(", switchValue5 : ", switchValue5);
  digitalWrite(SwitchOut5, switchValue5);
}

void setterSwitch6(byte value) {
  PG_DEBUG_LOG("setterSwitch6 timestamp : ", millis() - start);
  PG_DEBUG_LOG(", value : ", value);
  if (value > 99 && value < 254) {
    PG_DEBUG_PRN_DOTNEWLINE(", value is invalid, ignored");
    return;
  }
  switchValue6 = (value == 0) ? LOW : HIGH;
  PG_DEBUG_LOG_DOTNEWLINE(", switchValue6 : ", switchValue6);
  digitalWrite(SwitchOut6, switchValue6);
}
//----- GETTERS -----//

byte getterSwitch1() {
  PG_DEBUG_LOG("getterSwitch1 timestamp : ", millis() - start);
  PG_DEBUG_LOG_DOTNEWLINE(", value : ", switchValue1);
  return switchValue1;
}

byte getterSwitch2() {
  PG_DEBUG_LOG("getterSwitch2 timestamp : ", millis() - start);
  PG_DEBUG_LOG_DOTNEWLINE(", value : ", switchValue2);
  return switchValue2;
}

byte getterSwitch3() {
  PG_DEBUG_LOG("getterSwitch3 timestamp : ", millis() - start);
  PG_DEBUG_LOG_DOTNEWLINE(", value : ", switchValue3);
  return switchValue3;
}

byte getterSwitch4() {
  PG_DEBUG_LOG("getterSwitch4 timestamp : ", millis() - start);
  PG_DEBUG_LOG_DOTNEWLINE(", value : ", switchValue4);
  return switchValue4;
}

byte getterSwitch5() {
  PG_DEBUG_LOG("getterSwitch5 timestamp : ", millis() - start);
  PG_DEBUG_LOG_DOTNEWLINE(", value : ", switchValue5);
  return switchValue5;
}

byte getterSwitch6() {
  PG_DEBUG_LOG("getterSwitch6 timestamp : ", millis() - start);
  PG_DEBUG_LOG_DOTNEWLINE(", value : ", switchValue6);
  return switchValue6;
}

// Z-Wave spec

// ## 4.5.4 Basic Report Command; Table 17, Basic Report :: Value

// | Value dec | Value hex  | Level (%) | State    |
// | --------- | ---------- | --------- | -------- |
// | 0         | 0          | 0         | Off      |
// | 1..99     | 0x01..0x63 | 1..100    | On       |
// | 100..253  | 0x64..0xFD | reserved  | reserved |
// | 254       | 0xFE       | Unknown   | Unknown  |
// | 255       | 0xFF       | 100 (*)   | On (**)  |

// (*) for SWITCH_MULTILEVEL_SET: Restore most recent (non-zero) level.
// (**) for SWITCH_MULTILEVEL_SET: deprecated, use 1..99 instead.
Post Reply