loa

Virtual machine for the Logic of Assumptions
git clone git://juanmeleiro.mat.br/loa
Log | Files | Refs

commit 337437a00c033fd7b9e1bd278af9b66a64cb8c55
parent dea162504bae1c6a215381d5055fa5ad23fff8ab
Author: Juan F. Meleiro <juan@juanmeleiro.mat.br>
Date:   Sat, 27 Apr 2024 00:12:46 -0300

Add result field in gardeners

Diffstat:
Mcoding/default.test.do | 2+-
Mcoding/gardener.c | 40+++++++++++++++++++++++++++++++---------
Mcoding/gardener.h | 8+++++---
Mcoding/gardener.test.c | 64++++++++++++++++++++++++++++++++++++++++++----------------------
Dcoding/metaschema.c | 28----------------------------
Dcoding/metaschema.h | 28----------------------------
Dcoding/metaschema.test.c | 64----------------------------------------------------------------
Mcoding/model.test.c | 32+++++++++++---------------------
Mcoding/schema.test.c | 9++-------
9 files changed, 92 insertions(+), 183 deletions(-)

diff --git a/coding/default.test.do b/coding/default.test.do @@ -3,5 +3,5 @@ headers=*.h src=$(ls *.c | grep -v .test.c) redo-ifchange $src $headers -cc -g -fmax-errors=1 $src $1.c -o $3 >&2 +cc -g -Wall -Wextra -fmax-errors=1 $src $1.c -o $3 >&2 ./$3 >&2 || exit 1 diff --git a/coding/gardener.c b/coding/gardener.c @@ -13,6 +13,7 @@ struct gardener { stack *treestack; stack *schemastack; gardener_status error; + tree *result; }; /* GETTERS */ @@ -41,6 +42,12 @@ get_error(gardener *g) return g->error; } +tree* +result(gardener *g) +{ + return g->result; +} + /* SETTERS */ void @@ -59,6 +66,7 @@ new_gardener(schema* s) g->error = false; g->treestack = new_stack(); g->schemastack = new_stack(); + g->result = NULL; push(g->schemastack, g->top); return g; } @@ -67,6 +75,7 @@ new_gardener(schema* s) void fill(gardener* g, symbol key, symbol value) { + ensure(g, (get_cur_tree(g) != NULL), NON_START_OP_ON_EMPTY_STACK); tree *new = new_leaf(value); set_subtree(get_cur_tree(g), key, new); } @@ -75,8 +84,9 @@ fill(gardener* g, symbol key, symbol value) void sub(gardener* g, symbol key, symbol constructor) { - schema *cur_schema = get_cur_schema(g); + tree *cur = get_cur_tree(g); + ensure(g, (cur != NULL), NON_START_OP_ON_EMPTY_STACK); symbol head = get_head(get_cur_tree(g)); ensure(g, has_key(cur_schema, head, key), SUB_INVALID_KEY); @@ -94,6 +104,7 @@ void start(gardener* g, symbol c) { ensure(g, is_empty(g->treestack), START_ON_NONEMPTY_STACK); + ensure(g, (g->result == NULL), START_AFTER_RESULT); tree *t = new_node(c); push(g->treestack, t); } @@ -102,10 +113,14 @@ start(gardener* g, symbol c) void done(gardener* g) { - ensure(g, (!is_empty(g->treestack)), DONE_ON_EMPTY_STACK); + tree *res; + ensure(g, (!is_empty(g->treestack)), NON_START_OP_ON_EMPTY_STACK); ensure(g, check(get_cur_schema(g), get_cur_tree(g)), DONE_ON_INVALID_TREE); - pop(g->treestack); + res = pop(g->treestack); pop(g->schemastack); + + if (is_empty(g->treestack)) + g->result = res; } void @@ -115,32 +130,39 @@ show(FILE *f, gardener *g) tree *cur = get_cur_tree(g); if (cur == NULL) return; symbol head = get_head(cur); - bool err = get_error(g); fprintf(f, "schema %s\n", repr(get_name(s))); fprintf(f, "head %s\n", repr(head)); size_t num = get_amount_of_required_keys(s, head); symbol *keys = get_required_keys(s, head); for (size_t i = 0; i < num; i++) { - if (!get_subtree(cur, keys[i])) - if (takes_leaf(s, head, keys[i])) + if (!get_subtree(cur, keys[i])) { + if (takes_leaf(s, head, keys[i])) { fprintf(f, "symbol %s\n", repr(keys[i])); - else + } else { fprintf(f, "goal %s %s\n", repr(get_name(get_subschema(s, head, keys[i]))), repr(keys[i])); + } + } } switch (get_error(g)) { case SUB_INVALID_KEY: fprintf(f, "error SUB_INVALID_KEY"); break; - case DONE_ON_EMPTY_STACK: - fprintf(f, "error DONE_ON_EMPTY_STACK"); + case NON_START_OP_ON_EMPTY_STACK: + fprintf(f, "error NON_START_OP_ON_EMPTY_STACK"); break; case START_ON_NONEMPTY_STACK: fprintf(f, "error START_ON_NONEMPTY_STACK"); break; + case START_AFTER_RESULT: + fprintf(f, "error START_AFTER_RESULT"); + break; case SUB_WITH_INVALID_CONSTRUCTOR: fprintf(f, "error SUB_WITH_INVALID_CONSTRUCTOR"); break; + case DONE_ON_INVALID_TREE: + fprintf(f, "error DONE_ON_INVALID_TREE"); + break; case OK: break; } diff --git a/coding/gardener.h b/coding/gardener.h @@ -5,21 +5,23 @@ typedef enum { OK, SUB_INVALID_KEY, - DONE_ON_EMPTY_STACK, START_ON_NONEMPTY_STACK, SUB_WITH_INVALID_CONSTRUCTOR, - DONE_ON_INVALID_TREE + DONE_ON_INVALID_TREE, + START_AFTER_RESULT, + NON_START_OP_ON_EMPTY_STACK } gardener_status; typedef struct gardener gardener; gardener* new_gardener(schema*); gardener_status get_error(gardener*); +tree* result(gardener*); void fill(gardener*, symbol key, symbol value); void sub(gardener*, symbol key, symbol constructor); void done(gardener*); -void sup(gardener*, symbol key, symbol constructor); +// void sup(gardener*, symbol key, symbol constructor); void start(gardener*, symbol constructor); void show(FILE *f, gardener*); diff --git a/coding/gardener.test.c b/coding/gardener.test.c @@ -6,11 +6,44 @@ #include "schema.h" #include "gardener.h" +void +test_new_gardener(void) +{ + schema *s = new_schema(intern("test")); + gardener *g = new_gardener(s); + + assert(get_error(g) == OK); + assert(result(g) == NULL); +} + +void +test_non_start_at_start(void) +{ + schema *s = new_schema(intern("test")); + gardener *g = new_gardener(s); + fill(g, intern("c"), intern("v")); + assert(get_error(g) == NON_START_OP_ON_EMPTY_STACK); + sub(g, intern("c"), intern("v")); + assert(get_error(g) == NON_START_OP_ON_EMPTY_STACK); +} + +void +test_start_after_result_fail(void) +{ + schema *s = new_schema(intern("test")); + add_constructor(s, intern("nil")); + gardener *g = new_gardener(s); + + start(g, intern("nil")); + done(g); + assert(get_error(g) == OK); + start(g, intern("nil")); + assert(get_error(g) == START_AFTER_RESULT); +} + bool test_empty_constructor_success(void) { - bool res = true; - symbol c = intern("c"); schema *s = new_schema(intern("test")); add_constructor(s, c); @@ -19,9 +52,7 @@ test_empty_constructor_success(void) start(g, c); done(g); - res &= !get_error(g); - - return res; + return get_error(g) == OK; } bool @@ -33,14 +64,12 @@ test_empty_constructor_empty_tree_fail(void) gardener *g = new_gardener(s); done(g); - return get_error(g) == DONE_ON_EMPTY_STACK; + return get_error(g) == NON_START_OP_ON_EMPTY_STACK; } bool test_double_deep_schema_fail(void) { - bool res = true; - schema *s = new_schema(intern("test0")); symbol c = intern("c"); add_constructor(s, c); @@ -56,16 +85,13 @@ test_double_deep_schema_fail(void) start(g, c); done(g); - res &= (get_error(g) == DONE_ON_INVALID_TREE); - return res; + return get_error(g) == DONE_ON_INVALID_TREE; } bool test_double_deep_schema_success(void) { - bool res = true; - symbol c = intern("c"); symbol d = intern("d"); symbol k = intern("k"); @@ -83,16 +109,13 @@ test_double_deep_schema_success(void) sub(g, k, d); done(g); - res &= !get_error(g); - return res; + return get_error(g) == OK; } bool test_triple_deep_schema_fail(void) { - bool res = true; - symbol c = intern("c"); symbol d = intern("d"); symbol k = intern("k"); @@ -111,16 +134,13 @@ test_triple_deep_schema_fail(void) sub(g, k, d); done(g); - res &= get_error(g); - return res; + return get_error(g) == DONE_ON_INVALID_TREE; } bool test_triple_deep_schema_success(void) { - bool res = true; - schema *s = new_schema(intern("test0")); symbol c = intern("c"); add_constructor(s, c); @@ -138,14 +158,14 @@ test_triple_deep_schema_success(void) sub(g, k, d); fill(g, k, k); done(g); - res &= !get_error(g); - return res; + return get_error(g) == OK; } int main() { + test_new_gardener(); assert(test_empty_constructor_success()); assert(test_empty_constructor_empty_tree_fail()); assert(test_double_deep_schema_fail()); diff --git a/coding/metaschema.c b/coding/metaschema.c @@ -1,28 +0,0 @@ -#include <stdio.h> -#include <stdlib.h> - -#include "metaschema.h" -#include "schema.h" - -assoc* -metacompile(metaschema *m, size_t len) -{ - assoc *a = new_assoc(); - - /* 1st: Create all schemas */ - for (size_t i = 0; i < len; i++) { - schema *s = new_schema(intern(m[i].name)); - assoc_set(a, intern(m[i].name), s); - } - - /* 2nd: Add all constructors */ - for (size_t i = 0; i < len; i++) { - schema *s = assoc_get(a, intern(m[i].name)); - for (size_t j = 0; j < SIZE(m[i].constructors); j++) { - printf("Adding constructor %s\n", m[i].constructors[j].head); - add_constructor(s, intern(m[i].constructors[j].head)); - } - } - - return a; -} diff --git a/coding/metaschema.h b/coding/metaschema.h @@ -1,28 +0,0 @@ -#include <stdlib.h> - -#include "assoc.h" -#include "schema.h" - -#define metalen(M) (sizeof(M)/sizeof(metaschema)) -#define SIZE(X) (sizeof(X)/sizeof(X[0])) - -typedef struct metaschema metaschema; -typedef struct metaconstructor metaconstructor; -typedef struct metakey metakey; - -struct metaschema { - char *name; - struct metaconstructor *constructors; -}; - -struct metaconstructor { - char *head; - struct metakey *keys; -}; - -struct metakey { - char *key; - char *subschema; -}; - -assoc* metacompile(metaschema*, size_t); diff --git a/coding/metaschema.test.c b/coding/metaschema.test.c @@ -1,64 +0,0 @@ -#include <stdio.h> -#include <assert.h> - -#include "metaschema.h" - -void -test_empty_metaschema(void) -{ - metaschema m[] = {}; - assoc *a = metacompile(m, metalen(m)); - assert(a); - assert(get_amount_of_keys(a) == 0); -} - -void -test_empty_schemas(void) -{ - metaschema m[] = { - { .name = "test", - .constructors = (metaconstructor[]){} - }, - { .name = "test2", - .constructors = (metaconstructor[]){} - }, - { .name = "test3", - .constructors = (metaconstructor[]){} - } - }; - assoc *a = metacompile(m, metalen(m)); - assert(get_amount_of_keys(a) == metalen(m)); - assert(assoc_get(a, intern("test"))); - assert(assoc_get(a, intern("test2"))); - assert(assoc_get(a, intern("test3"))); -} - -void -test_empty_constructors(void) -{ - metaschema m[] = { - { .name = "test", - .constructors = (metaconstructor[]){ - { .head = "constr0", - .keys = (metakey[]){} - }, - { .head = "constr1", - .keys = (metakey[]){} - } - } - } - }; - assoc *a = metacompile(m, metalen(m)); - schema *s = assoc_get(a, intern("test")); - assert(is_constructor(s, intern("constr0"))); - assert(is_constructor(s, intern("constr1"))); -} - -int -main() -{ - test_empty_metaschema(); - test_empty_schemas(); - test_empty_constructors(); - return 0; -} diff --git a/coding/model.test.c b/coding/model.test.c @@ -24,7 +24,6 @@ void test_context(void) { schema *ctx = schema(context); - bool res = true; assert (has_key (ctx, I("attitude"), I("name") )); assert (has_key (ctx, I("attitude"), I("vars") )); @@ -96,26 +95,17 @@ test_use(void) { gardener *g = new_gardener(schema(context)); - start(g, I("attitude")); - assert(get_error(g) == OK); - fill(g, I("name"), I("wft")); - assert(get_error(g) == OK); - sub(g, I("vars"), I("var")); - assert(get_error(g) == OK); - fill(g, I("name"), I("a")); - assert(get_error(g) == OK); - sub(g, I("rest"), I("nil")); - assert(get_error(g) == OK); - done(g); - assert(get_error(g) == OK); - done(g); - assert(get_error(g) == OK); - sub(g, I("pressupositions"), I("nil")); - assert(get_error(g) == OK); - done(g); - assert(get_error(g) == OK); - done(g); - assert(get_error(g) == OK); + start (g, I("attitude") ); assert(get_error(g) == OK); + fill (g, I("name"), I("wft") ); assert(get_error(g) == OK); + sub (g, I("vars"), I("var") ); assert(get_error(g) == OK); + fill (g, I("name"), I("a") ); assert(get_error(g) == OK); + sub (g, I("rest"), I("nil") ); assert(get_error(g) == OK); + done (g ); assert(get_error(g) == OK); + done (g ); assert(get_error(g) == OK); + sub (g, I("pressupositions"), I("nil") ); assert(get_error(g) == OK); + done (g ); assert(get_error(g) == OK); + done (g ); assert(get_error(g) == OK); + show(stdout, g); } diff --git a/coding/schema.test.c b/coding/schema.test.c @@ -40,7 +40,7 @@ test_set_and_query_leaf(void) return takes_leaf(s, c, a); } -bool +void test_leaf_exists(void) { assert(LEAF != NULL); @@ -63,18 +63,13 @@ test_listing_all_keys(void) return good; } -bool -test_check(void) -{ -} - int main() { assert(test_name()); assert(test_set_and_get_subschema()); assert(test_set_and_query_leaf()); - assert(test_leaf_exists()); + test_leaf_exists(); assert(test_listing_all_keys()); return 0; }