Mercurial > hg-old > index.cgi
diff src/expr.c @ 17:df0c4a46af8f
Started adding expression handling infrastructure
author | lost |
---|---|
date | Thu, 01 Jan 2009 02:26:26 +0000 |
parents | 1f598d89b9b0 |
children | 218aabbc3b1a |
line wrap: on
line diff
--- a/src/expr.c Thu Oct 23 03:39:29 2008 +0000 +++ b/src/expr.c Thu Jan 01 02:26:26 2009 +0000 @@ -25,82 +25,140 @@ #define __expr_c_seen__ -#include <ctype.h> +#include <stdio.h> #include <stdlib.h> #include "expr.h" -#include "lwval.h" +#include "util.h" + +lwasm_expr_stack_t *lwasm_expr_stack_create(void) +{ + lwasm_expr_stack_t *s; + + s = lwasm_alloc(sizeof(lwasm_expr_stack_t)); + s -> head = NULL; + s -> tail = NULL; + return s; +} -// parse a single term out of the expression; return NULL if -// end of expression; return LWVAL_TYPE_ERR if error -/* -The following is handled by lwasm_parse_term: +void lwasm_expr_stack_free(lwasm_expr_stack_t *s) +{ + while (s -> head) + { + s -> tail = s -> head; + s -> head = s -> head -> next; + lwasm_expr_term_free(s -> tail -> term); + lwasm_free(s -> tail); + } + lwasm_free(s); +} -- constants -- parsing a symbol -- unary - -- unary + -- () +void lwasm_expr_term_free(lwasm_expr_term_t *t) +{ + if (t) + { + if (t -> symbol) + lwasm_free(t -> symbol); + lwasm_free(t); + } +} + +lwasm_expr_term_t *lwasm_expr_term_create_oper(int oper) +{ + lwasm_expr_term_t *t; + + t = lwasm_alloc(sizeof(lwasm_expr_term_t)); + t -> term_type = LWASM_TERM_OPER; + t -> value = oper; + return t; +} -*/ -LWVAL *lwasm_parse_term(char **ptr) +lwasm_expr_term_t *lwasm_expr_term_create_int(int val) { - int sign = 1; - int s = 0; - LWVAL *rval; + lwasm_expr_term_t *t; + + t = lwasm_alloc(sizeof(lwasm_expr_term_t)); + t -> term_type = LWASM_TERM_INT; + t -> value = val; + return t; +} + +lwasm_expr_term_t *lwasm_expr_term_create_sym(char *sym) +{ + lwasm_expr_term_t *t; -start_term: - if (!**ptr || isspace(**ptr) || **ptr == ')') - return s ? lwval_construct_err(1) : NULL; + t = lwasm_alloc(sizeof(lwasm_expr_term_t)); + t -> term_type = LWASM_TERM_SYM; + t -> symbol = lwasm_strdup(sym); + return t; +} - s = 1; - // unary + - NOOP - if (**ptr == '+') +lwasm_expr_term_t *lwasm_expr_term_dup(lwasm_expr_term_t *t) +{ + switch (t -> term_type) { - (*ptr)++; - goto start_term; + case LWASM_TERM_INT: + return lwasm_expr_term_create_int(t -> value); + + case LWASM_TERM_OPER: + return lwasm_expr_term_create_oper(t -> value); + + case LWASM_TERM_SYM: + return lwasm_expr_term_create_sym(t -> symbol); + + default: + fprintf(stderr, "lwasm_expr_term_dup(): invalid term type %d\n", t -> term_type); + exit(1); + } +// can't get here +} + +void lwasm_expr_stack_push(lwasm_expr_stack_t *s, lwasm_expr_term_t *t) +{ + lwasm_expr_stack_node_t *n; + + if (!s) + { + fprintf(stderr, "lwasm_expr_stack_push(): invalid stack pointer\n"); + exit(1); } - // unary - - applied once the rest of the term is worked out - if (**ptr == '-') + n = lwasm_alloc(sizeof(lwasm_expr_stack_node_t)); + n -> next = NULL; + n -> prev = s -> tail; + n -> term = lwasm_expr_term_dup(t); + + if (s -> head) + { + s -> tail -> next = n; + s -> tail = n; + } + else { - (*ptr)++; - sign = -sign; - goto start_term; + s -> head = n; + s -> tail = n; + } +} + +lwasm_expr_term_t *lwasm_expr_stack_pop(lwasm_expr_stack_t *s) +{ + lwasm_expr_term_t *t; + lwasm_expr_stack_node_t *n; + + if (!(s -> tail)) + return NULL; + + n = s -> tail; + s -> tail = n -> prev; + if (!(n -> prev)) + { + s -> head = NULL; } - // parens - if (**ptr == '(') - { - LWVAL *v; - (*ptr)++; - rval = lwasm_parse_expr(ptr); - if (**ptr != ')') - { - lwval_destroy(rval); - return lwval_construct_err(1); - } - (*ptr)++; - goto ret; - } - - // parse an actual term here; no more futzing with expressions - -ret: - // apply negation if appropriate - if (sign < 0) - lwval_neg(rval); - return rval; + t = n -> term; + n -> term = NULL; + + lwasm_free(n); + + return t; } - -// parse an expression -LWVAL *lwasm_parse_expr(char **ptr) -{ -} - -// attempt to evaluate/simplify expression -int lwasm_eval_expr(LWVAL *expr) -{ -} - -