From 3b37a00a4be251f87e543d269489cb7a989425d5 Mon Sep 17 00:00:00 2001 From: Pixel Date: Sat, 28 Apr 2001 21:40:25 +0000 Subject: Hop, gros bordel, plein de fichiers ajoutes et supprimes :) --- lib/pile.c | 292 +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ 1 file changed, 292 insertions(+) create mode 100644 lib/pile.c (limited to 'lib/pile.c') diff --git a/lib/pile.c b/lib/pile.c new file mode 100644 index 0000000..a1cac21 --- /dev/null +++ b/lib/pile.c @@ -0,0 +1,292 @@ +/* + * + * Gestion de la pile des operandes + * + */ +#include +#include "pile.h" +#include "exceptions.h" +#include "numbers.h" +#include "main.h" +#include "parser.h" +#ifdef HAVE_CONFIG_H +#include "config.h" +#else +#define _(x) x +#endif + +/* FIXME manque procedure vidage de pile en fin de prog */ + +pile_elem pile[PILE_MAX]; +unsigned int pile_ptr = 0; + +void push_pile(char *st) +{ + int valid1, valid2, valid3; + char valid4=0; + int i_number; + double d_number; + polynome poly; + + + i_number = char_to_number(st, &valid1); + d_number = char_to_double(st, &valid2); + valid3 = is_mute(st); + poly = (polynome) NomVarToVar(st, variables, &valid4); + + if (valid1) { /* il s agit d un entier */ + push_pile_poly(ply_constr(rat_constr(i_number, 1), 0)); + } else if (valid2) { /* il s agit d un flottant */ + push_pile_poly(ply_constr(rat_constr_from_double(d_number), 0)); + } else if (valid3) { /* il s agit de x */ + push_pile_poly(ply_constr(rat_constr(1, 1), 0)); + } else if (valid4) { /* il s agit d une variable */ + push_pile_poly(ply_copy(poly)); + } else { /* il s agit d un nom */ + push_pile_string(Estrdup(st)); + } +} + + +void push_pile_poly(polynome poly) +{ + if (pile_ptr != PILE_MAX) { + pile[pile_ptr].type = T_POLY; + pile[pile_ptr].poly = poly; + pile_ptr++; + } else { + exception(1, _("push_pile_poly: Stack Overflow")); + } + +} + +void push_pile_int(int val) +{ + if (pile_ptr != PILE_MAX) { + pile[pile_ptr].type = T_INT; + pile[pile_ptr].val = val; + pile_ptr++; + } else { + exception(1, _("push_pile_int: Stack Overflow")); + } + +} + +void push_pile_string(char *st) +{ + if (pile_ptr != PILE_MAX) { + pile[pile_ptr].type = T_STRING; + pile[pile_ptr].label = Estrdup(st); + pile_ptr++; + } else { + exception(1, _("push_pile_string: Stack Overflow")); + } + +} + +pile_elem pop_pile(unsigned int count) +{ + char buf[50]; + + if ((int) (pile_ptr - count) >= 0) { + pile_ptr -= count; + } else { + sprintf(buf, _("pop_pile: Can't pop %u elements"), count); + exception(1, buf); + } + return pile[pile_ptr]; +} + +char *affichage_level_1(void) +{ + char *result=NULL; + + if (!pile_ptr) { + switch (pile[pile_ptr - 1].type) { + case T_POLY: + result = ply_affichage(pile[pile_ptr - 1].poly); + break; + case T_STRING: + result = pile[pile_ptr - 1].label; + break; + case T_INT: + result = (char *) Emalloc(11 * sizeof(char)); + sprintf(result, "%10d", pile[pile_ptr - 1].val); + break; + } + } + return result; +} + +int is_mute(char *st) +{ /* FIXME: test lowercase / uppercase */ + char buf[2]; + + sprintf(buf, "%c", mute); + return strcmp(st, buf); +} + + +void act_pile(int func) +{ + pile_elem operande1, operande2; + char buf[50]; + + sprintf(buf, _("Calling act_pile(%i)\n"), func); + pushcontext(buf); + switch (func) { + case OP_PLUS: + operande1 = pop_pile(1); + operande2 = pop_pile(1); + if ((operande1.type == T_POLY) && (operande2.type == T_POLY)) { + push_pile_poly(ply_addition(operande1.poly, operande2.poly)); + if (operande1.poly) + ply_destruct(operande1.poly); + if (operande2.poly) + ply_destruct(operande2.poly); + } else { + exception(1, _("act_pile: OP_PLUS invalid arguments")); + } + break; + case OP_MOINS: + operande1 = pop_pile(1); + operande2 = pop_pile(1); + if ((operande1.type == T_POLY) && (operande2.type == T_POLY)) { + push_pile_poly(ply_soustraction(operande1.poly, operande2.poly)); + if (operande1.poly) + ply_destruct(operande1.poly); + if (operande2.poly) + ply_destruct(operande2.poly); + } else { + exception(1, _("act_pile: OP_MOINS invalid arguments")); + } + break; + case OP_MUL: + operande1 = pop_pile(1); + operande2 = pop_pile(1); + if ((operande1.type == T_POLY) && (operande2.type == T_POLY)) { + push_pile_poly(ply_multiplication(operande1.poly, operande2.poly)); + if (operande1.poly) + ply_destruct(operande1.poly); + if (operande2.poly) + ply_destruct(operande2.poly); + } else { + exception(1, _("act_pile: OP_MUL invalid arguments")); + } + break; + case OP_DIV: + operande1 = pop_pile(1); + operande2 = pop_pile(1); + if ((operande1.type == T_POLY) && (operande2.type == T_POLY)) { + push_pile_poly(ply_division(operande1.poly, operande2.poly)); + if (operande1.poly) + ply_destruct(operande1.poly); + if (operande2.poly) + ply_destruct(operande2.poly); + } else { + exception(1, _("act_pile: OP_DIV invalid arguments")); + } + break; + case OP_MOD: + operande1 = pop_pile(1); + operande2 = pop_pile(1); + if ((operande1.type == T_POLY) && (operande2.type == T_POLY)) { + push_pile_poly(ply_modulo(operande1.poly, operande2.poly)); + if (operande1.poly) + ply_destruct(operande1.poly); + if (operande2.poly) + ply_destruct(operande2.poly); + } else { + exception(1, _("act_pile: OP_MOD invalid arguments")); + } + break; + case OP_EXP: + operande1 = pop_pile(1); + operande2 = pop_pile(1); + if ((operande1.type == T_POLY) && (operande2.type == T_POLY)) { + if (operande2.poly) { + if ((operande2.poly->coef.denom == 1) + && (operande2.poly->coef.num >= 0)) { + push_pile_poly(ply_exposant + (operande1.poly, operande2.poly->coef.num)); + if (operande1.poly) + ply_destruct(operande1.poly); + ply_destruct(operande2.poly); + } else { + exception(1, _("act_pile: OP_EXP invalid arguments")); + } + } else { + exception(1, _("act_pile: OP_EXP invalid arguments")); + } + } else { + exception(1, _("act_pile: OP_EXP invalid arguments")); + } + break; + case OP_ASSIGN: /* FIXME: sens de l evaluation ? poly label sto ou label poly sto */ + operande1 = pop_pile(1); + operande2 = pop_pile(1); + if ((operande1.type == T_POLY) && (operande2.type == T_STRING)) { + if (operande2.label) { + InsererVarDansTab(&variables, + CreerElement(operande2.label, + (void *) operande1.poly)); + if (operande1.poly) + ply_destruct(operande1.poly); + free(operande2.label); + } else { + exception(1, _("act_pile: OP_ASSIGN empty string")); + } + } else { + exception(1, _("act_pile: OP_ASSIGN invalid arguments")); + } + break; + case OP_PLUS_UNARY: + break; + case OP_MOINS_UNARY: + operande1 = pop_pile(1); + if (operande1.type == T_POLY) { + push_pile_poly(ply_soustraction + (ply_constr(rat_constr_zero(), 0), operande1.poly)); + if (operande1.poly) + ply_destruct(operande1.poly); + } else { + exception(1, _("act_pile: OP_MOINS_UNARY invalid argument")); + } + break; + case OP_FUNC_CALL: + operande1 = pop_pile(1); + if ((operande1.type == T_INT) && (operande1.val == 1)) { + operande1 = pop_pile(1); + operande2 = pop_pile(1); + if ((operande1.type == T_POLY) && (operande2.type == T_POLY)) { + if (operande2.poly) { + if (operande2.poly->degre == 0) { + push_pile_poly(ply_constr + (rat_constr_from_double + (ply_valuation + (operande1.poly, + rat_to_double(operande2.poly-> + coef))), 1)); + if (operande1.poly) + ply_destruct(operande1.poly); + ply_destruct(operande2.poly); + } else { + exception(1, + _ + ("act_pile: OP_FUNC_CALL invalid arguments")); + } + } else { + exception(1, _("act_pile: OP_FUNC_CALL invalid arguments")); + } + } else { + exception(1, _("act_pile: OP_FUNC_CALL invalid arguments")); + } + } else { + exception(1, _("act_pile: OP_FUNC_CALL incorrect argument number")); + } + break; + default: + exception(1, _("act_pile: Unknown operator")); + } + popcontext(); +} -- cgit v1.2.3