Move out of mapping to increase performance

This commit is contained in:
Stephan Hadinger 2022-09-10 12:05:48 +02:00
parent 5c4aab6dc1
commit 13027cc623
2 changed files with 46 additions and 33 deletions

View File

@ -4,7 +4,6 @@
* To use: `import tasmota` * To use: `import tasmota`
*******************************************************************/ *******************************************************************/
#include "be_constobj.h" #include "be_constobj.h"
#include "be_mapping.h"
#include "be_ctypes.h" #include "be_ctypes.h"
extern struct TasmotaGlobal_t TasmotaGlobal; extern struct TasmotaGlobal_t TasmotaGlobal;
@ -55,8 +54,7 @@ extern int l_setpower(bvm *vm);
extern int l_getswitch(bvm *vm); extern int l_getswitch(bvm *vm);
extern int l_i2cenabled(bvm *vm); extern int l_i2cenabled(bvm *vm);
extern int tasm_find_op(bvm *vm);
extern int32_t tasm_find_op(const char* hay, bbool second_phase); BE_FUNC_CTYPE_DECLARE(tasm_find_op, "i", "-sb");
/******************************************************************** /********************************************************************
** Solidified function: add_driver ** Solidified function: add_driver
@ -2608,7 +2606,7 @@ class be_class_tasmota (scope: global, name: Tasmota) {
add_fast_loop, closure(Tasmota_add_fast_loop_closure) add_fast_loop, closure(Tasmota_add_fast_loop_closure)
remove_fast_loop, closure(Tasmota_remove_fast_loop_closure) remove_fast_loop, closure(Tasmota_remove_fast_loop_closure)
cmd, closure(Tasmota_cmd_closure) cmd, closure(Tasmota_cmd_closure)
_find_op, ctype_func(tasm_find_op) // new C version for finding a rule operator _find_op, func(tasm_find_op) // new C version for finding a rule operator
find_key_i, closure(Tasmota_find_key_i_closure) find_key_i, closure(Tasmota_find_key_i_closure)
find_op, closure(Tasmota_find_op_closure) find_op, closure(Tasmota_find_op_closure)
add_rule, closure(Tasmota_add_rule_closure) add_rule, closure(Tasmota_add_rule_closure)

View File

@ -404,51 +404,66 @@ extern "C" {
// takes a string, an offset to start the search from, and works in 2 modes. // takes a string, an offset to start the search from, and works in 2 modes.
// mode1 (false): loog for the first char of an operato // mode1 (false): loog for the first char of an operato
// mode2 (true): finds the last char of the operator // mode2 (true): finds the last char of the operator
int32_t tasm_find_op(const char* hay, bbool second_phase) { int32_t tasm_find_op(bvm *vm);
const char *c = hay; // starting point int32_t tasm_find_op(bvm *vm) {
int32_t ret = 0; int32_t top = be_top(vm); // Get the number of arguments
if (!second_phase) { bool second_phase = false;
// search for `=`, `==`, `!=`, `!==`, `<`, `<=`, `>`, `>=` int32_t ret = -1;
while (*c) { if (top >= 2 && be_isstring(vm, 2)) {
const char *c = be_tostring(vm, 2);
if (top >= 3) {
second_phase = be_tobool(vm, 3);
}
if (!second_phase) {
int32_t idx = 0;
// search for `=`, `==`, `!=`, `!==`, `<`, `<=`, `>`, `>=`
while (*c && ret < 0) {
switch (c[0]) {
case '=':
case '<':
case '>':
ret = idx;
break; // anything starting with `=`, `<` or `>` is a valid operator
case '!':
if (c[1] == '=') {
ret = idx; // needs to start with `!=`
}
break;
default:
break;
}
c++;
idx++;
}
} else {
// second phase
switch (c[0]) { switch (c[0]) {
case '=':
case '<': case '<':
case '>': case '>':
return ret; // anything starting with `=`, `<` or `>` is a valid operator case '=':
if (c[1] != '=') { ret = 1; } // `<` or `>` or `=`
else { ret = 2; } // `<=` or `>=` or `==`
break;
case '!': case '!':
if (c[1] == '=') { if (c[1] != '=') { ; } // this is invalid if isolated `!`
return ret; // needs to start with `!=` if (c[2] != '=') { ret = 2; } // `!=`
} else { ret = 3; } // `!==`
break; break;
default: default:
break; break;
} }
c++;
ret++;
} }
return -1; // no operator found
} else {
switch (c[0]) {
case '<':
case '>':
case '=':
if (c[1] != '=') { return ret + 1; } // `<` or `>` or `=`
else { return ret + 2; } // `<=` or `>=` or `==`
case '!':
if (c[1] != '=') { return -1; } // this is invalid if isolated `!`
if (c[2] != '=') { return ret + 2; } // `!=`
else { return ret + 3; } // `!==`
default:
break;
}
return -1;
} }
be_pushint(vm, ret);
be_return(vm);
} }
/* /*
# test patterns # test patterns
assert(tasmota._find_op("aaa#bbc==23",false) == 7) assert(tasmota._find_op("aaa#bbc==23",false) == 7)
assert(tasmota._find_op("==23",true) == 2) assert(tasmota._find_op("==23",true) == 2)
assert(tasmota._find_op(">23",true) == 1)
assert(tasmota._find_op("aaa#bbc!23",false) == -1) assert(tasmota._find_op("aaa#bbc!23",false) == -1)
*/ */