diff --git a/lib/libesp32/berry/src/be_introspectlib.c b/lib/libesp32/berry/src/be_introspectlib.c index a87ce3932..4f98f2d94 100644 --- a/lib/libesp32/berry/src/be_introspectlib.c +++ b/lib/libesp32/berry/src/be_introspectlib.c @@ -70,12 +70,15 @@ static int m_findmember(bvm *vm) if (top >= 3) { protected = !be_tobool(vm, 3); } - if (top >= 2) { - if (protected && (be_isinstance(vm, 1) || be_ismodule(vm, 1) || be_isclass(vm, 1)) && be_isstring(vm, 2)) { - int ret = be_execprotected(vm, &m_findmember_protected, (void*) be_tostring(vm, 2)); - if (ret == BE_OK) { - be_return(vm); + if (top >= 2 && be_isstring(vm, 2)) { + if (protected) { + if (be_isinstance(vm, 1) || be_ismodule(vm, 1) || be_isclass(vm, 1)) { + int ret = be_execprotected(vm, &m_findmember_protected, (void*) be_tostring(vm, 2)); + if (ret == BE_OK) { + be_return(vm); + } } + be_return_nil(vm); } else { /* run unprotected */ if (be_getmember(vm, 1, be_tostring(vm, 2))) { diff --git a/lib/libesp32/berry_tasmota/src/embedded/zigbee_zb_coord.be b/lib/libesp32/berry_tasmota/src/embedded/zigbee_zb_coord.be index aab49d271..58a81ca60 100644 --- a/lib/libesp32/berry_tasmota/src/embedded/zigbee_zb_coord.be +++ b/lib/libesp32/berry_tasmota/src/embedded/zigbee_zb_coord.be @@ -17,12 +17,23 @@ class zb_coord : zb_coord_ntv raise "value_error", "instance required" end if self._handlers - self._handlers.push(h) - else + if self._handlers.find(h) == nil # make it idempotent + self._handlers.push(h) + end + else self._handlers = [h] end end + def remove_handler(h) + if self._handlers + var idx = self._handlers.find(h) + if idx != nil + self._handlers.remove(idx) + end + end + end + # dispatch incomind events # # event_type: diff --git a/lib/libesp32/berry_tasmota/src/embedded/zigbee_zcl_attribute.be b/lib/libesp32/berry_tasmota/src/embedded/zigbee_zcl_attribute.be index e58c463d9..361826787 100644 --- a/lib/libesp32/berry_tasmota/src/embedded/zigbee_zcl_attribute.be +++ b/lib/libesp32/berry_tasmota/src/embedded/zigbee_zcl_attribute.be @@ -46,7 +46,7 @@ class zcl_attribute : zcl_attribute_ntv elif k == "key" return self._get_key() else - return super(self).member(k) + return super(self).member(k) # natural mapping end end diff --git a/lib/libesp32/berry_tasmota/src/solidify/solidified_zigbee_zb_coord.h b/lib/libesp32/berry_tasmota/src/solidify/solidified_zigbee_zb_coord.h index 10dc93c33..425e256a3 100644 --- a/lib/libesp32/berry_tasmota/src/solidify/solidified_zigbee_zb_coord.h +++ b/lib/libesp32/berry_tasmota/src/solidify/solidified_zigbee_zb_coord.h @@ -50,16 +50,17 @@ be_local_closure(zb_coord_add_handler, /* name */ 0, /* has sup protos */ NULL, /* no sub protos */ 1, /* has constants */ - ( &(const bvalue[ 5]) { /* constants */ + ( &(const bvalue[ 6]) { /* constants */ /* K0 */ be_nested_str_weak(instance), /* K1 */ be_nested_str_weak(value_error), /* K2 */ be_nested_str_weak(instance_X20required), /* K3 */ be_nested_str_weak(_handlers), - /* K4 */ be_nested_str_weak(push), + /* K4 */ be_nested_str_weak(find), + /* K5 */ be_nested_str_weak(push), }), be_str_weak(add_handler), &be_const_str_solidified, - ( &(const binstruction[18]) { /* code */ + ( &(const binstruction[25]) { /* code */ 0x60080004, // 0000 GETGBL R2 G4 0x5C0C0200, // 0001 MOVE R3 R1 0x7C080200, // 0002 CALL R2 1 @@ -67,17 +68,24 @@ be_local_closure(zb_coord_add_handler, /* name */ 0x780A0000, // 0004 JMPF R2 #0006 0xB0060302, // 0005 RAISE 1 K1 K2 0x88080103, // 0006 GETMBR R2 R0 K3 - 0x780A0004, // 0007 JMPF R2 #000D + 0x780A000B, // 0007 JMPF R2 #0014 0x88080103, // 0008 GETMBR R2 R0 K3 0x8C080504, // 0009 GETMET R2 R2 K4 0x5C100200, // 000A MOVE R4 R1 0x7C080400, // 000B CALL R2 2 - 0x70020003, // 000C JMP #0011 - 0x60080012, // 000D GETGBL R2 G18 - 0x7C080000, // 000E CALL R2 0 - 0x400C0401, // 000F CONNECT R3 R2 R1 - 0x90020602, // 0010 SETMBR R0 K3 R2 - 0x80000000, // 0011 RET 0 + 0x4C0C0000, // 000C LDNIL R3 + 0x1C080403, // 000D EQ R2 R2 R3 + 0x780A0003, // 000E JMPF R2 #0013 + 0x88080103, // 000F GETMBR R2 R0 K3 + 0x8C080505, // 0010 GETMET R2 R2 K5 + 0x5C100200, // 0011 MOVE R4 R1 + 0x7C080400, // 0012 CALL R2 2 + 0x70020003, // 0013 JMP #0018 + 0x60080012, // 0014 GETGBL R2 G18 + 0x7C080000, // 0015 CALL R2 0 + 0x400C0401, // 0016 CONNECT R3 R2 R1 + 0x90020602, // 0017 SETMBR R0 K3 R2 + 0x80000000, // 0018 RET 0 }) ) ); @@ -195,6 +203,47 @@ be_local_closure(zb_coord_dispatch, /* name */ /*******************************************************************/ +/******************************************************************** +** Solidified function: remove_handler +********************************************************************/ +be_local_closure(zb_coord_remove_handler, /* name */ + be_nested_proto( + 6, /* nstack */ + 2, /* argc */ + 2, /* varg */ + 0, /* has upvals */ + NULL, /* no upvals */ + 0, /* has sup protos */ + NULL, /* no sub protos */ + 1, /* has constants */ + ( &(const bvalue[ 3]) { /* constants */ + /* K0 */ be_nested_str_weak(_handlers), + /* K1 */ be_nested_str_weak(find), + /* K2 */ be_nested_str_weak(remove), + }), + be_str_weak(remove_handler), + &be_const_str_solidified, + ( &(const binstruction[14]) { /* code */ + 0x88080100, // 0000 GETMBR R2 R0 K0 + 0x780A000A, // 0001 JMPF R2 #000D + 0x88080100, // 0002 GETMBR R2 R0 K0 + 0x8C080501, // 0003 GETMET R2 R2 K1 + 0x5C100200, // 0004 MOVE R4 R1 + 0x7C080400, // 0005 CALL R2 2 + 0x4C0C0000, // 0006 LDNIL R3 + 0x200C0403, // 0007 NE R3 R2 R3 + 0x780E0003, // 0008 JMPF R3 #000D + 0x880C0100, // 0009 GETMBR R3 R0 K0 + 0x8C0C0702, // 000A GETMET R3 R3 K2 + 0x5C140400, // 000B MOVE R5 R2 + 0x7C0C0400, // 000C CALL R3 2 + 0x80000000, // 000D RET 0 + }) + ) +); +/*******************************************************************/ + + /******************************************************************** ** Solidified class: zb_coord ********************************************************************/ @@ -202,12 +251,13 @@ extern const bclass be_class_zb_coord_ntv; be_local_class(zb_coord, 1, &be_class_zb_coord_ntv, - be_nested_map(4, + be_nested_map(5, ( (struct bmapnode*) &(const bmapnode[]) { - { be_const_key_weak(dispatch, 1), be_const_closure(zb_coord_dispatch_closure) }, - { be_const_key_weak(add_handler, 2), be_const_closure(zb_coord_add_handler_closure) }, - { be_const_key_weak(_handlers, -1), be_const_var(0) }, - { be_const_key_weak(init, 0), be_const_closure(zb_coord_init_closure) }, + { be_const_key_weak(init, -1), be_const_closure(zb_coord_init_closure) }, + { be_const_key_weak(remove_handler, 2), be_const_closure(zb_coord_remove_handler_closure) }, + { be_const_key_weak(add_handler, -1), be_const_closure(zb_coord_add_handler_closure) }, + { be_const_key_weak(dispatch, -1), be_const_closure(zb_coord_dispatch_closure) }, + { be_const_key_weak(_handlers, 1), be_const_var(0) }, })), be_str_weak(zb_coord) ); diff --git a/tasmota/tasmota_xdrv_driver/xdrv_52_3_berry_zigbee.ino b/tasmota/tasmota_xdrv_driver/xdrv_52_3_berry_zigbee.ino index 7e93e3751..1fca11afe 100644 --- a/tasmota/tasmota_xdrv_driver/xdrv_52_3_berry_zigbee.ino +++ b/tasmota/tasmota_xdrv_driver/xdrv_52_3_berry_zigbee.ino @@ -255,22 +255,23 @@ extern "C" { extern const be_ctypes_structure_t be_zigbee_zcl_attribute_struct = { sizeof(Z_attribute), /* size in bytes */ - 10, /* number of elements */ + 11, /* number of elements */ nullptr, - (const be_ctypes_structure_item_t[10]) { + (const be_ctypes_structure_item_t[11]) { { "_attr_id", offsetof(Z_attribute, attr_id), 0, 0, ctypes_u16, 0 }, { "_cluster", offsetof(Z_attribute, cluster), 0, 0, ctypes_u16, 0 }, { "_cmd", offsetof(Z_attribute, attr_id), 0, 0, ctypes_u8, 0 }, // low 8 bits of attr_id { "_cmd_general", offsetof(Z_attribute, attr_id) + 1, 1, 1, ctypes_u8, 0 }, // bit #1 of byte+1 { "_direction", offsetof(Z_attribute, attr_id) + 1, 0, 1, ctypes_u8, 0 }, // bit #0 of byte+1 { "_iscmd", offsetof(Z_attribute, key_is_cmd), 0, 0, ctypes_u8, 0 }, - { "attr_multiplier", offsetof(Z_attribute, attr_multiplier), 0, 0, ctypes_i8, 0 }, - { "attr_divider", offsetof(Z_attribute, attr_divider), 0, 0, ctypes_i8, 0 }, - { "attr_type", offsetof(Z_attribute, attr_type), 0, 0, ctypes_u8, 0 }, + { "attr_multiplier", offsetof(Z_attribute, attr_multiplier), 0, 0, ctypes_u32, 0 }, + { "attr_divider", offsetof(Z_attribute, attr_divider), 0, 0, ctypes_u32, 0 }, + { "attr_type", offsetof(Z_attribute, attr_type), 0, 0, ctypes_i32, 0 }, // { "key", offsetof(Z_attribute, key), 0, 0, ctypes_ptr32, 0 }, // { "key_is_pmem", offsetof(Z_attribute, key_is_pmem), 0, 0, ctypes_u8, 0 }, // { "key_is_str", offsetof(Z_attribute, key_is_str), 0, 0, ctypes_u8, 0 }, { "key_suffix", offsetof(Z_attribute, key_suffix), 0, 0, ctypes_u8, 0 }, + { "manuf", offsetof(Z_attribute, manuf), 0, 0, ctypes_u16, 0 }, // { "type", offsetof(Z_attribute, type), 0, 0, ctypes_u8, 0 }, // { "val_float", offsetof(Z_attribute, val), 0, 0, ctypes_float, 0 }, // { "val_i32", offsetof(Z_attribute, val), 0, 0, ctypes_i32, 0 },