for.c 1.9 KB

1234567891011121314151617181920212223242526272829303132333435363738394041424344454647484950515253545556575859606162636465666768697071727374757677787980818283848586878889909192939495
  1. #include <stdio.h>
  2. #include <stdlib.h>
  3. #include "pic.h"
  4. #include "y.tab.h"
  5. #define SLOP 1.001
  6. typedef struct {
  7. char *var; /* index variable */
  8. double to; /* limit */
  9. double by;
  10. int op; /* operator */
  11. char *str; /* string to push back */
  12. } For;
  13. For forstk[10]; /* stack of for loops */
  14. For *forp = forstk; /* pointer to current top */
  15. void setfval(char *, double);
  16. void nextfor(void);
  17. void forloop(char *var, double from, double to, int op,
  18. double by, char *str) /* set up a for loop */
  19. {
  20. dprintf("# for %s from %g to %g by %c %g \n",
  21. var, from, to, op, by);
  22. if (++forp >= forstk+10)
  23. ERROR "for loop nested too deep" FATAL;
  24. forp->var = var;
  25. forp->to = to;
  26. forp->op = op;
  27. forp->by = by;
  28. forp->str = str;
  29. setfval(var, from);
  30. nextfor();
  31. unput('\n');
  32. }
  33. void nextfor(void) /* do one iteration of a for loop */
  34. {
  35. /* BUG: this should depend on op and direction */
  36. if (getfval(forp->var) > SLOP * forp->to) { /* loop is done */
  37. free(forp->str);
  38. if (--forp < forstk)
  39. ERROR "forstk popped too far" FATAL;
  40. } else { /* another iteration */
  41. pushsrc(String, "\nEndfor\n");
  42. pushsrc(String, forp->str);
  43. }
  44. }
  45. void endfor(void) /* end one iteration of for loop */
  46. {
  47. struct symtab *p = lookup(forp->var);
  48. switch (forp->op) {
  49. case '+':
  50. case ' ':
  51. p->s_val.f += forp->by;
  52. break;
  53. case '-':
  54. p->s_val.f -= forp->by;
  55. break;
  56. case '*':
  57. p->s_val.f *= forp->by;
  58. break;
  59. case '/':
  60. p->s_val.f /= forp->by;
  61. break;
  62. }
  63. nextfor();
  64. }
  65. char *ifstat(double expr, char *thenpart, char *elsepart)
  66. {
  67. dprintf("if %g then <%s> else <%s>\n", expr, thenpart, elsepart? elsepart : "");
  68. if (expr) {
  69. unput('\n');
  70. pushsrc(Free, thenpart);
  71. pushsrc(String, thenpart);
  72. unput('\n');
  73. if (elsepart)
  74. free(elsepart);
  75. return thenpart; /* to be freed later */
  76. } else {
  77. free(thenpart);
  78. if (elsepart) {
  79. unput('\n');
  80. pushsrc(Free, elsepart);
  81. pushsrc(String, elsepart);
  82. unput('\n');
  83. }
  84. return elsepart;
  85. }
  86. }