implement most nsapi expression operators

Sun, 04 Dec 2022 13:01:00 +0100

author
Olaf Wintermann <olaf.wintermann@gmail.com>
date
Sun, 04 Dec 2022 13:01:00 +0100
changeset 452
ce359a2b51fe
parent 451
edbbb3000494
child 453
4586d534f9b5

implement most nsapi expression operators

src/server/test/main.c file | annotate | diff | comparison | revisions
src/server/test/object.c file | annotate | diff | comparison | revisions
src/server/test/object.h file | annotate | diff | comparison | revisions
src/server/util/object.c file | annotate | diff | comparison | revisions
src/server/util/object.h file | annotate | diff | comparison | revisions
--- a/src/server/test/main.c	Sun Dec 04 10:20:21 2022 +0100
+++ b/src/server/test/main.c	Sun Dec 04 13:01:00 2022 +0100
@@ -90,6 +90,9 @@
     ucx_test_register(suite, test_expr_parse_expr_compare2value_expr);
     ucx_test_register(suite, test_expr_parse_expr_compare2expr_value);
     ucx_test_register(suite, test_expr_parse_expr_bracket);
+    ucx_test_register(suite, test_expr_op_defined_simple);
+    ucx_test_register(suite, test_expr_op_defined);
+    ucx_test_register(suite, test_expr_op_file_exists_simple);
     ucx_test_register(suite, test_expr_parse_expr_func_arg0);
     ucx_test_register(suite, test_expr_parse_expr_func_arg1);
     ucx_test_register(suite, test_expr_parse_expr_func_arg3);
--- a/src/server/test/object.c	Sun Dec 04 10:20:21 2022 +0100
+++ b/src/server/test/object.c	Sun Dec 04 13:01:00 2022 +0100
@@ -368,6 +368,100 @@
     pool_destroy(pool);
 }
 
+UCX_TEST(test_expr_op_defined_simple) {
+    pool_handle_t *pool = pool_create();
+    
+    CxList *tokens = cxLinkedListCreate(pool_allocator(pool), cx_cmp_ptr, sizeof(cxstring));
+    cxstring token = cx_str("defined");
+    cxListAdd(tokens, &token);
+    
+    token = cx_str("$testvar1");
+    cxListAdd(tokens, &token);
+    
+    UCX_TEST_BEGIN;
+    
+    size_t pos = 0;
+    NSAPIExpression *expr = expr_parse_logical_expr(pool, tokens, &pos);
+    
+    UCX_TEST_ASSERT(pos == 2, "wrong token pos");
+    UCX_TEST_ASSERT(expr, "expression is null");
+    UCX_TEST_ASSERT(expr->type == NSAPI_EXPRESSION_UNARY, "wrong type");
+    UCX_TEST_ASSERT(expr->operator == NSAPI_EXPRESSION_VALUE_DEFINED, "wrong operator");
+    UCX_TEST_ASSERT(expr->left, "missing left operand");
+    UCX_TEST_ASSERT(expr->left->type == NSAPI_EXPRESSION_VARIABLE, "operand is not a variable");
+    
+    UCX_TEST_END;
+    
+    pool_destroy(pool);
+}
+
+UCX_TEST(test_expr_op_defined) {
+    pool_handle_t *pool = pool_create();
+    
+    CxList *tokens = cxLinkedListCreate(pool_allocator(pool), cx_cmp_ptr, sizeof(cxstring));
+    cxstring token = cx_str("true");
+    cxListAdd(tokens, &token);
+    
+    token = cx_str("==");
+    cxListAdd(tokens, &token);
+    
+    token = cx_str("not");
+    cxListAdd(tokens, &token);
+    
+    token = cx_str("defined");
+    cxListAdd(tokens, &token);
+    
+    token = cx_str("$var");
+    cxListAdd(tokens, &token);
+    
+    UCX_TEST_BEGIN;
+    
+    size_t pos = 0;
+    NSAPIExpression *expr = expr_parse_logical_expr(pool, tokens, &pos);
+    
+    UCX_TEST_ASSERT(pos == 5, "wrong token pos");
+    UCX_TEST_ASSERT(expr, "expression is null");
+    UCX_TEST_ASSERT(expr->operator == NSAPI_EXPRESSION_EQ, "wrong operator");
+    UCX_TEST_ASSERT(expr->left, "missing left");
+    UCX_TEST_ASSERT(expr->right, "missing right");
+    UCX_TEST_ASSERT(expr->left->type == NSAPI_EXPRESSION_BOOL, "left expression is not a bool");
+    UCX_TEST_ASSERT(expr->right->operator == NSAPI_EXPRESSION_NOT, "right: wrong operator");
+    UCX_TEST_ASSERT(expr->right->left, "not op: missing left");
+    UCX_TEST_ASSERT(expr->right->left->operator == NSAPI_EXPRESSION_VALUE_DEFINED, "missing defined operator");
+    
+    UCX_TEST_END;
+    
+    pool_destroy(pool);
+}
+
+UCX_TEST(test_expr_op_file_exists_simple) {
+    pool_handle_t *pool = pool_create();
+    
+    CxList *tokens = cxLinkedListCreate(pool_allocator(pool), cx_cmp_ptr, sizeof(cxstring));
+    cxstring token = cx_str("-e");
+    cxListAdd(tokens, &token);
+    
+    token = cx_str("\"/path/file\"");
+    cxListAdd(tokens, &token);
+    
+    UCX_TEST_BEGIN;
+    
+    size_t pos = 0;
+    NSAPIExpression *expr = expr_parse_logical_expr(pool, tokens, &pos);
+    
+    UCX_TEST_ASSERT(pos == 2, "wrong token pos");
+    UCX_TEST_ASSERT(expr, "expression is null");
+    UCX_TEST_ASSERT(expr->type == NSAPI_EXPRESSION_UNARY, "wrong type");
+    UCX_TEST_ASSERT(expr->operator == NSAPI_EXPRESSION_FILE_DIR_EXISTS, "wrong operator");
+    UCX_TEST_ASSERT(expr->left, "missing left operand");
+    UCX_TEST_ASSERT(expr->left->type == NSAPI_EXPRESSION_STRING, "operand is not a string");
+    UCX_TEST_ASSERT(!cx_strcmp(expr->left->value.str, cx_str("/path/file")), "wrong string operand");
+    
+    UCX_TEST_END;
+    
+    pool_destroy(pool);
+}
+
 UCX_TEST(test_expr_parse_expr_func_arg0) {
     pool_handle_t *pool = pool_create();
     
--- a/src/server/test/object.h	Sun Dec 04 10:20:21 2022 +0100
+++ b/src/server/test/object.h	Sun Dec 04 13:01:00 2022 +0100
@@ -51,6 +51,10 @@
 
 UCX_TEST(test_expr_parse_expr_bracket);
 
+UCX_TEST(test_expr_op_defined_simple);
+UCX_TEST(test_expr_op_defined);
+UCX_TEST(test_expr_op_file_exists_simple);
+
 UCX_TEST(test_expr_parse_expr_func_arg0);
 UCX_TEST(test_expr_parse_expr_func_arg1);
 UCX_TEST(test_expr_parse_expr_func_arg3);
--- a/src/server/util/object.c	Sun Dec 04 10:20:21 2022 +0100
+++ b/src/server/util/object.c	Sun Dec 04 13:01:00 2022 +0100
@@ -168,13 +168,15 @@
         return NSAPI_EXPRESSION_DIV;
     } else if(!cx_strcmp(token, cx_str("%"))) {
         return NSAPI_EXPRESSION_MOD;
-    } else if(!cx_strcmp(token, cx_str("not"))) {
+    } else if(!cx_strcmp(token, cx_str("."))) {
+        return NSAPI_EXPRESSION_STRCAT;
+    } else if(!cx_strcmp(token, cx_str("not")) || !cx_strcmp(token, cx_str("!"))) {
         return NSAPI_EXPRESSION_NOT;
-    } else if(!cx_strcmp(token, cx_str("and"))) {
+    } else if(!cx_strcmp(token, cx_str("and")) || !cx_strcmp(token, cx_str("&&"))) {
         return NSAPI_EXPRESSION_AND;
-    } else if(!cx_strcmp(token, cx_str("or"))) {
+    } else if(!cx_strcmp(token, cx_str("or")) || !cx_strcmp(token, cx_str("||"))) {
         return NSAPI_EXPRESSION_OR;
-    } else if(!cx_strcmp(token, cx_str("xor"))) {
+    } else if(!cx_strcmp(token, cx_str("xor")) || !cx_strcmp(token, cx_str("^"))) {
         return NSAPI_EXPRESSION_XOR;
     } else if(!cx_strcmp(token, cx_str("=="))) {
         return NSAPI_EXPRESSION_EQ;
@@ -188,6 +190,26 @@
         return NSAPI_EXPRESSION_GE;
     } else if(!cx_strcmp(token, cx_str("<="))) {
         return NSAPI_EXPRESSION_LE;
+    } else if(!cx_strcmp(token, cx_str("="))) {
+        return NSAPI_EXPRESSION_WILDCARD_MATCH;
+    } else if(!cx_strcmp(token, cx_str("=~"))) {
+        return NSAPI_EXPRESSION_REGEX_MATCH;
+    } else if(!cx_strcmp(token, cx_str("!~"))) {
+        return NSAPI_EXPRESSION_REGEX_MISMATCH;
+    } else if(!cx_strcmp(token, cx_str("defined"))) {
+        return NSAPI_EXPRESSION_VALUE_DEFINED;
+    } else if(!cx_strcmp(token, cx_str("-d"))) {
+        return NSAPI_EXPRESSION_DIR_EXISTS;
+    } else if(!cx_strcmp(token, cx_str("-e"))) {
+        return NSAPI_EXPRESSION_FILE_DIR_EXISTS;
+    } else if(!cx_strcmp(token, cx_str("-f"))) {
+        return NSAPI_EXPRESSION_FILE_EXISTS;
+    } else if(!cx_strcmp(token, cx_str("-l"))) {
+        return NSAPI_EXPRESSION_SYMLINK_EXISTS;
+    } else if(!cx_strcmp(token, cx_str("-r"))) {
+        return NSAPI_EXPRESSION_FILE_READABLE;
+    } else if(!cx_strcmp(token, cx_str("-s"))) {
+        return NSAPI_EXPRESSION_FILE_SIZE;
     }
     return NSAPI_EXPRESSION_NOOP;
 }
@@ -280,6 +302,14 @@
         exp->type = NSAPI_EXPRESSION_UNARY;
         exp->left = expr_parser_pop(parser);
         exp->right = NULL; 
+    } else if(exp->operator == NSAPI_EXPRESSION_CALL) {
+        // identifiers are added as call, but if they land here, it is
+        // actually just an identifier
+        exp->operator = NSAPI_EXPRESSION_NOOP;
+        exp->left = NULL;
+        exp->right = NULL;
+        exp->type = NSAPI_EXPRESSION_IDENTIFIER;
+        exp->value.identifier = op->identifier;
     } else {
         // binary operator
         exp->type = NSAPI_EXPRESSION_BINARY;
@@ -287,7 +317,7 @@
         exp->left = expr_parser_pop(parser);
     }
     
-    if(!exp->left && !exp->right) {
+    if(!exp->left && !exp->right && exp->operator != NSAPI_EXPRESSION_NOOP) {
         return 1; // error
     }
     
--- a/src/server/util/object.h	Sun Dec 04 10:20:21 2022 +0100
+++ b/src/server/util/object.h	Sun Dec 04 13:01:00 2022 +0100
@@ -145,10 +145,9 @@
     NSAPI_EXPRESSION_NOOP = 0,
     NSAPI_EXPRESSION_CALL,
     NSAPI_EXPRESSION_ARG,
-    NSAPI_EXPRESSION_NOT,
-    NSAPI_EXPRESSION_AND,
-    NSAPI_EXPRESSION_OR,
-    NSAPI_EXPRESSION_XOR,
+    NSAPI_EXPRESSION_WILDCARD_MATCH,
+    NSAPI_EXPRESSION_REGEX_MATCH,
+    NSAPI_EXPRESSION_REGEX_MISMATCH,
     NSAPI_EXPRESSION_EQ,
     NSAPI_EXPRESSION_NEQ,
     NSAPI_EXPRESSION_GT,
@@ -159,12 +158,25 @@
     NSAPI_EXPRESSION_SUB,
     NSAPI_EXPRESSION_MUL,
     NSAPI_EXPRESSION_DIV,
-    NSAPI_EXPRESSION_MOD
+    NSAPI_EXPRESSION_MOD,
+    NSAPI_EXPRESSION_STRCAT,
+    NSAPI_EXPRESSION_NOT,
+    NSAPI_EXPRESSION_AND,
+    NSAPI_EXPRESSION_OR,
+    NSAPI_EXPRESSION_XOR,
+    NSAPI_EXPRESSION_VALUE_DEFINED,
+    NSAPI_EXPRESSION_DIR_EXISTS,
+    NSAPI_EXPRESSION_FILE_DIR_EXISTS,
+    NSAPI_EXPRESSION_FILE_EXISTS,
+    NSAPI_EXPRESSION_SYMLINK_EXISTS,
+    NSAPI_EXPRESSION_FILE_READABLE,
+    NSAPI_EXPRESSION_FILE_SIZE
 };
 
 union NSAPIExpressionValue {
     cxstring str;
     cxstring var;
+    cxstring identifier;
     int64_t  i;
     double   f;
     int      b;

mercurial