diff options
-rw-r--r-- | .gitignore | 1 | ||||
-rw-r--r-- | Makefile.am | 21 | ||||
-rw-r--r-- | src/blogc/funcvars.c | 13 | ||||
-rw-r--r-- | src/blogc/funcvars.h | 2 | ||||
-rw-r--r-- | src/blogc/renderer.c | 6 | ||||
-rw-r--r-- | tests/blogc/check_funcvars.c | 84 |
6 files changed, 117 insertions, 10 deletions
@@ -57,6 +57,7 @@ blogc*.html /tests/blogc/check_blogc.sh /tests/blogc/check_content_parser /tests/blogc/check_datetime_parser +/tests/blogc/check_funcvars /tests/blogc/check_loader /tests/blogc/check_renderer /tests/blogc/check_source_parser diff --git a/Makefile.am b/Makefile.am index 11d9605..f83d6ed 100644 --- a/Makefile.am +++ b/Makefile.am @@ -478,10 +478,31 @@ check_PROGRAMS += \ if USE_LD_WRAP check_PROGRAMS += \ + tests/blogc/check_funcvars \ tests/blogc/check_loader \ tests/common/check_stdin \ $(NULL) +tests_blogc_check_funcvars_SOURCES = \ + tests/blogc/check_funcvars.c \ + $(NULL) + +tests_blogc_check_funcvars_CFLAGS = \ + $(CMOCKA_CFLAGS) \ + $(NULL) + +tests_blogc_check_funcvars_LDFLAGS = \ + -no-install \ + -Wl,--wrap=bc_file_get_contents \ + $(NULL) +#-Wl,--wrap=bc_file_get_contents + +tests_blogc_check_funcvars_LDADD = \ + $(CMOCKA_LIBS) \ + libblogc.la \ + libblogc_common.la \ + $(NULL) + tests_blogc_check_loader_SOURCES = \ tests/blogc/check_loader.c \ $(NULL) diff --git a/src/blogc/funcvars.c b/src/blogc/funcvars.c index 25a22bf..42411e2 100644 --- a/src/blogc/funcvars.c +++ b/src/blogc/funcvars.c @@ -43,20 +43,23 @@ static const struct func_map { }; -char* -blogc_funcvars_lookup(const char *name, bc_trie_t *global) +void +blogc_funcvars_eval(bc_trie_t *global, const char *name) { + if (global == NULL || name == NULL) + return; + // protect against evaluating the same function twice in the same global // context if (NULL != bc_trie_lookup(global, name)) - return NULL; + return; for (size_t i = 0; funcs[i].variable != NULL; i++) { if (0 == strcmp(name, funcs[i].variable)) { funcs[i].func(global); - return bc_strdup(bc_trie_lookup(global, name)); + return; } } - return NULL; + return; } diff --git a/src/blogc/funcvars.h b/src/blogc/funcvars.h index f554f8d..aae1bc3 100644 --- a/src/blogc/funcvars.h +++ b/src/blogc/funcvars.h @@ -14,6 +14,6 @@ typedef void (*blogc_funcvars_func_t) (bc_trie_t*); -char* blogc_funcvars_lookup(const char *name, bc_trie_t *global); +void blogc_funcvars_eval(bc_trie_t *global, const char *name); #endif /* ___FUNCVARS_H */ diff --git a/src/blogc/renderer.c b/src/blogc/renderer.c index 2326e09..035f71b 100644 --- a/src/blogc/renderer.c +++ b/src/blogc/renderer.c @@ -106,10 +106,8 @@ blogc_format_variable(const char *name, bc_trie_t *global, bc_trie_t *local, value = foreach_var->data; } else { - value = blogc_funcvars_lookup(var, global); - if (value == NULL) { - value = blogc_get_variable(var, global, local); - } + blogc_funcvars_eval(global, var); + value = blogc_get_variable(var, global, local); } if (value == NULL) { diff --git a/tests/blogc/check_funcvars.c b/tests/blogc/check_funcvars.c new file mode 100644 index 0000000..153a870 --- /dev/null +++ b/tests/blogc/check_funcvars.c @@ -0,0 +1,84 @@ +/* + * blogc: A blog compiler. + * Copyright (C) 2014-2019 Rafael G. Martins <rafael@rafaelmartins.eng.br> + * + * This program can be distributed under the terms of the BSD License. + * See the file LICENSE. + */ + +#include <stdarg.h> +#include <stddef.h> +#include <setjmp.h> +#include <cmocka.h> +#include <stdlib.h> +#include <string.h> +#include <stdio.h> +#include "../../src/common/error.h" +#include "../../src/common/utils.h" +#include "../../src/blogc/funcvars.h" + + +char* +__wrap_bc_file_get_contents(const char *path, bool utf8, size_t *len, bc_error_t **err) +{ + assert_string_equal(path, "/proc/1/cgroup"); + assert_false(utf8); + char *rv = mock_type(char*); + *len = strlen(rv); + bc_error_t *e = mock_type(bc_error_t*); + if (e != NULL) + *err = e; + return rv; +} + + +static void +test_funcvars_eval(void **state) +{ + bc_trie_t *t = bc_trie_new(free); + blogc_funcvars_eval(t, NULL); + blogc_funcvars_eval(t, ""); + blogc_funcvars_eval(t, "BOLA"); + assert_int_equal(bc_trie_size(t), 0); + + bc_trie_insert(t, "BOLA", bc_strdup("GUDA")); + blogc_funcvars_eval(t, "BOLA"); + assert_int_equal(bc_trie_size(t), 1); + + bc_trie_free(t); +} + + +static void +test_funcvars_eval_mocked(void **state) +{ + bc_trie_t *t = bc_trie_new(free); + + // this is the only function that isn't hidden behind conditional macros + // as of when this test was written. the other functions should be tested + // separately + will_return(__wrap_bc_file_get_contents, bc_strdup("asd/docker/asd")); + will_return(__wrap_bc_file_get_contents, NULL); + blogc_funcvars_eval(t, "BLOGC_SYSINFO_INSIDE_DOCKER"); + assert_string_equal(bc_trie_lookup(t, "BLOGC_SYSINFO_INSIDE_DOCKER"), "1"); + assert_int_equal(bc_trie_size(t), 1); + + // this specific function call is cached, so calling it again should not + // call bc_file_get_contents_again + blogc_funcvars_eval(t, "BLOGC_SYSINFO_INSIDE_DOCKER"); + assert_string_equal(bc_trie_lookup(t, "BLOGC_SYSINFO_INSIDE_DOCKER"), "1"); + assert_int_equal(bc_trie_size(t), 1); + + bc_trie_free(t); +} + + +int +main(void) +{ + const UnitTest tests[] = { + unit_test(test_funcvars_eval), + unit_test(test_funcvars_eval_mocked), + }; + return run_tests(tests); +} |