loa

Virtual machine for the Logic of Assumptions
Log | Files | Refs

commit a272042d4ccfb321eafadf888d011186be54e423
parent abcebef5736f7d34d55dd84d41428f9aa87bc7f0
Author: Juan F. Meleiro <juan@juanmeleiro.mat.br>
Date:   Sun,  7 Jan 2024 14:37:15 -0300

Add tactics for assumptions and proofs, plus reordering code

Currently, proofs are *not* verified. So that this is implemented, either
a resolution mechanism will need to be added when reaching closed goals,
or some data to refs so that the check is made at tactic application time.

Diffstat:
Mcoding/build.sh | 2+-
Mcoding/formating.c | 48++++++++++++++++++++++++++++++++++++++++++++++--
Mcoding/formating.h | 4+++-
Acoding/tactics.c | 76++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
Acoding/tactics.h | 30++++++++++++++++++++++++++++++
Mcoding/vm.c | 126++++++++++++++++++++++++++++++++++++++++++++++++-------------------------------
Mcoding/vm.h | 28+++++++++++++++++++++++++---
Mcoding/vm.txt | 5++++-
8 files changed, 262 insertions(+), 57 deletions(-)

diff --git a/coding/build.sh b/coding/build.sh @@ -1,3 +1,3 @@ #!/bin/sh -cc -Wall -Wextra -pedantic -g -o vm vm.c formating.c && ./vm +cc -Wall -Wextra -pedantic -g -o vm *.c && ./vm diff --git a/coding/formating.c b/coding/formating.c @@ -16,8 +16,13 @@ print_ref(FILE *f, struct state *st, address ref) print_symbol(f, st, resolve(st, symbol, cur.addr)); break; case ATTITUDE: + print_attitude(f, st, resolve(st, attitude, cur.addr)); break; case ASSUMPTION: + print_assumption(f, st, resolve(st, assumption, cur.addr)); + break; + case PROOF: + print_proof(f, st, resolve(st, proof, cur.addr)); break; } } else { @@ -82,6 +87,33 @@ print_attitude(FILE *f, struct state *st, struct attitude a) } void +print_assumption(FILE *f, struct state *st, struct assumption a) +{ + print_symbol(f, st, resolve(st, symbol, a.name)); + fputc('[', f); + for (size_t i = 0; i < a.nvars; i++) { + print_ref(f, st, a.vars + i); + } + fputs("]: ", f); + print_ref(f, st, a.judgment); + fputc('\n', f); + for (size_t i = 0; i < a.nsub; i++) { + fputs(" ", f); + print_ref(f, st, a.sub + i); + fputc('\n', f); + } +} + +void +print_proof(FILE *f, struct state *st, struct proof p) +{ + print_ref(f, st, p.argument); + fprintf(f, " |- "); + print_ref(f, st, p.thesis); + fputc('\n', f); +} + +void print_state(FILE *f, struct state *st) { size_t i; @@ -90,10 +122,12 @@ print_state(FILE *f, struct state *st) fprintf(f, "SYMBOLS (%ld/%ld)\n", st->nsymbols, st->csymbols); for (i = 0; i < st->nsymbols; i++) { - fprintf(f, "%ld: ", i); + if (i > 0) fputs(", ", f); + fprintf(f, "%ld: '", i); print_symbol(f, st, resolve(st, symbol, i)); - fputc('\n', f); + fputc('\'', f); } + fputc('\n', f); fprintf(f, "\nTERMS (%ld/%ld)\n", st->nterms, st->cterms); for (i = 0; i < st->nterms; i++) { @@ -119,6 +153,16 @@ print_state(FILE *f, struct state *st) print_attitude(f, st, st->attitudes[i]); } + fprintf(f, "\nASSUMPTIONS (%ld/%ld)\n", st->nassumptions, st->cassumptions); + for (i = 0; i < st->nassumptions; i++) { + print_assumption(f, st, st->assumptions[i]); + } + + fprintf(f, "\nPROOFS (%ld/%ld)\n", st->nproofs, st->cproofs); + for (i = 0; i < st->nproofs; i++) { + print_proof(f, st, st->proofs[i]); + } + fprintf(f, "\nGOALS\n"); for (struct goal *cur = st->focus; cur; cur = cur->next) { print_goal(f, st, cur); diff --git a/coding/formating.h b/coding/formating.h @@ -1,6 +1,6 @@ #include "vm.h" -#define type_variable(t) ("SJAT"[t]) +#define type_variable(t) ("SJATPR"[t]) void print_term(FILE *f, struct state *st, struct term t); void print_ref(FILE *f, struct state *st, address ref); @@ -9,3 +9,5 @@ void print_term(FILE *f, struct state *st, struct term t); void print_state(FILE *f, struct state *st); void print_goal(FILE *f, struct state *st, struct goal *g); void print_attitude(FILE *f, struct state *st, struct attitude a); +void print_assumption(FILE *f, struct state *st, struct assumption a); +void print_proof(FILE *f, struct state *st, struct proof p); diff --git a/coding/tactics.c b/coding/tactics.c @@ -0,0 +1,76 @@ +#include "tactics.h" + +void +tactic_term(struct state *st, address head, size_t arity) +{ + assert(!st->focus || resolve(st, ref, st->focus->target).type == TERM); + + address sol = create_term(st, head, arity); + struct term t = resolve(st, term, sol); + + if (st->focus) solve(st, sol); + + for (size_t i = 0; i < arity; i++) { + add_subgoal(st, t.subterms + i); + } + + commit(st); +} + +void +tactic_attitude(struct state *st, address marker, size_t nvars, size_t npres) +{ + assert(!st->focus || resolve(st, ref, st->focus->target).type == ATTITUDE); + + address sol = create_attitude(st, marker, nvars, npres); + struct attitude a = resolve(st, attitude, sol); + + if (st->focus) solve(st, sol); + + for (size_t i = 0; i < nvars; i++) + add_subgoal(st, a.vars + i); + + for (size_t i = 0; i < npres; i++) + add_subgoal(st, a.pressupositions + i); + + commit(st); +} + +void +tactic_proof(struct state *st, address thesis) +{ + assert(!st->focus || resolve(st, ref, st->focus->target).type == PROOF); + + address sol = create_proof(st, thesis); + struct proof p = resolve(st, proof, sol); + + if (st->focus) solve(st, sol); + + add_subgoal(st, p.argument); + + commit(st); +} + +void +tactic_assumption(struct state *st, address name, address marker, size_t nvars, size_t nsub) +{ + assert(!st->focus || resolve(st, ref, st->focus->target).type == ASSUMPTION); + + address sol = create_assumption(st, name, marker, nvars, nsub); + struct assumption a = resolve(st, assumption, sol); + + if (st->focus) solve(st, sol); + + for (size_t i = 0; i < nvars; i++) + add_subgoal(st, a.vars + i); + + add_subgoal(st, a.judgment); + + for (size_t i = 0; i < nsub; i++) + add_subgoal(st, a.sub + i); + + for (size_t i = 0; i < a.nproofs; i++) + add_subgoal(st, a.proofs + i); + + commit(st); +} diff --git a/coding/tactics.h b/coding/tactics.h @@ -0,0 +1,30 @@ +#include <stdlib.h> +#include <assert.h> + +#include "vm.h" + +struct term_args { + address head; + size_t arity; +}; + +struct attitude_args { + address marker; + size_t nvars; + size_t npres; +}; + +struct tactic_args { + ref_t type; + union { + struct term_args term; + struct attitude_args attitude; + }; +}; + +void tactic(struct state *st, struct tactic_args); +void tactic_term(struct state *st, address head, size_t arity); +void tactic_attitude(struct state *st, address marker, size_t nvars, size_t npres); +void tactic_assumption(struct state *st, address name, address marker, size_t nvars, size_t nsub); +void tactic_proof(struct state *st, address thesis); + diff --git a/coding/vm.c b/coding/vm.c @@ -4,6 +4,7 @@ #include "vm.h" #include "formating.h" +#include "tactics.h" /* OBJECT CREATION */ @@ -15,6 +16,8 @@ state new_state(void) init(s, symbol); init(s, term); init(s, attitude); + init(s, assumption); + init(s, proof); s.focus = NULL; s.cursor = NULL; return s; @@ -69,6 +72,37 @@ create_symbol(struct state *st, char *name) return push(st, symbol, sym); } +address +create_assumption(struct state *st, address name, address marker, size_t nvars, size_t nsub) +{ + struct attitude *att = lookup_attitude(st, marker); + assert(att != NULL); + struct assumption a = { + .name = name, + .marker = marker, + .nvars = nvars, + .nsub = nsub, + .vars = allocate_refs(st, nvars, SYMBOL), + .sub = allocate_refs(st, nsub, ASSUMPTION), + .judgment = allocate_refs(st, 1, TERM), + .nproofs = att->npres, + .proofs = allocate_refs(st, att->npres, PROOF) + }; + + return push(st, assumption, a); +} + +address +create_proof(struct state *st, address thesis) +{ + struct proof p = { + .thesis = thesis, + .argument = allocate_refs(st, 1, SYMBOL) + }; + + return push(st, proof, p); +} + /* GOAL MECHANICS */ void @@ -95,6 +129,7 @@ add_subgoal(struct state *st, address target) st->cursor = g; } g->target = target; + g->state = OPEN; } void @@ -102,7 +137,7 @@ commit(struct state *st) { if (st->cursor) { st->cursor = NULL; - } else { + } else if (st->focus) { st->focus->state = CLOSED; } } @@ -115,42 +150,15 @@ solve(struct state *st, address dest) assign(st, st->focus->target, dest); } -/* TACTICS */ - -void -tactic_term(struct state *st, address head, size_t arity) +struct attitude* +lookup_attitude(struct state *st, address name) { - assert(!st->focus || resolve(st, ref, st->focus->target).type == TERM); - - address sol = create_term(st, head, arity); - struct term t = resolve(st, term, sol); - - if (st->focus) solve(st, sol); - - for (size_t i = 0; i < arity; i++) { - add_subgoal(st, t.subterms + i); + for (size_t i = 0; i < st->nattitudes; i++) { + if (st->attitudes[i].marker == name) { + return &st->attitudes[i]; + } } - - commit(st); -} - -void -tactic_attitude(struct state *st, address marker, size_t nvars, size_t npres) -{ - assert(!st->focus || resolve(st, ref, st->focus->target).type == ATTITUDE); - - address sol = create_attitude(st, marker, nvars, npres); - struct attitude a = resolve(st, attitude, sol); - - if (st->focus) solve(st, sol); - - for (size_t i = 0; i < nvars; i++) - add_subgoal(st, a.vars + i); - - for (size_t i = 0; i < npres; i++) - add_subgoal(st, a.pressupositions + i); - - commit(st); + return NULL; } void @@ -178,30 +186,50 @@ step(struct state *st) } } +void +run(struct state *st) +{ + while (st->focus && st->focus->state == CLOSED) + step(st); +} + int main(void) { struct state s = new_state(); - address wft = create_symbol(&s, "wft"); + address wft = create_symbol(&s, "wft"); address colon = create_symbol(&s, ":"); address var_a = create_symbol(&s, "a"); address var_b = create_symbol(&s, "b"); + address type_wft = create_symbol(&s, "type-wft"); + address type = create_symbol(&s, "type"); + address is_type_wft = create_symbol(&s, "is-type-wft"); + address a_type = create_symbol(&s, "a-type"); + + tactic_attitude(&s, wft, 1, 0); run(&s); + solve(&s, var_a); run(&s); - tactic_attitude(&s, wft, 1, 0); - step(&s); - solve(&s, var_a); - step(&s); + tactic_attitude(&s, colon, 2, 1); run(&s); + solve(&s, var_a); run(&s); + solve(&s, var_b); run(&s); + tactic_term(&s, wft, 1); run(&s); + tactic_term(&s, var_b, 0); run(&s); - tactic_attitude(&s, colon, 2, 1); - solve(&s, var_a); - step(&s); - solve(&s, var_b); - step(&s); + tactic_assumption(&s, type_wft, wft, 0, 0); run(&s); tactic_term(&s, wft, 1); - step(&s); - tactic_term(&s, var_b, 0); - step(&s); - step(&s); + tactic_term(&s, type, 0); run(&s); + + tactic_assumption(&s, is_type_wft, wft, 1, 1); run(&s); + solve(&s, var_a); run(&s); + tactic_term(&s, wft, 1); run(&s); + tactic_term(&s, var_a, 0); run(&s); + tactic_assumption(&s, a_type, colon, 0, 0); run(&s); + tactic_term(&s, colon, 2); + tactic_term(&s, var_a, 0); run(&s); + tactic_term(&s, type, 0); run(&s); + + tactic_proof(&s, 5); run(&s); + solve(&s, type_wft); run(&s); print_state(stdout, &s); return 0; diff --git a/coding/vm.h b/coding/vm.h @@ -6,7 +6,8 @@ typedef enum { SYMBOL, ATTITUDE, ASSUMPTION, - TERM + TERM, + PROOF, } ref_t; typedef enum { @@ -38,6 +39,24 @@ struct term { address subterms; }; +struct assumption { + address name; + address marker; + size_t nvars; + size_t nsub; + size_t nproofs; + address proofs; + address judgment; + address vars; + address sub; + address prev; +}; + +struct proof { + address thesis; + address argument; +}; + struct goal { goal_s state; struct goal *next; @@ -77,6 +96,8 @@ struct state { list(symbol); list(term); list(attitude); + list(assumption); + list(proof); }; struct state new_state(void); @@ -84,14 +105,15 @@ address allocate_refs(struct state *st, size_t n, ref_t type); address create_term(struct state *st, address symbol, size_t nargs); address create_symbol(struct state *st, char *name); address create_attitude(struct state *st, address marker, size_t nvars, size_t npres); +address create_assumption(struct state *st, address name, address marker, size_t nvars, size_t nsub); +address create_proof(struct state *st, address thesis); void assign(struct state *st, address ref, address dest); void add_subgoal(struct state *st, address target); void commit(struct state *st); void solve(struct state *st, address dest); +struct attitude *lookup_attitude(struct state *st, address name); -void tactic_term(struct state *st, address head, size_t arity); -void tactic_attitude(struct state *st, address marker, size_t nvars, size_t npres); void step(struct state *st); diff --git a/coding/vm.txt b/coding/vm.txt @@ -1,7 +1,10 @@ NEXT STEPS ========== -- Implement goals for building terms +- [x] Implement goals for building terms +- [x] Implement attitudes +- [ ] Implement assumptions +- [ ] Implement proofs NOTES