pattern.c 3.5 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138
  1. /* $Id$ */
  2. /*
  3. * (c) copyright 1987 by the Vrije Universiteit, Amsterdam, The Netherlands.
  4. * See the copyright notice in the ACK home directory, in the file "Copyright".
  5. */
  6. /* p a t t e r n . c
  7. *
  8. * Deals with the pattern stuff.
  9. * it maintains a table of information about the patterns
  10. * Functions : addpattern() and printpatterns()
  11. */
  12. #include <stdlib.h>
  13. #include <stdio.h>
  14. #include <ctype.h>
  15. #include "misc.h"
  16. #include "symtab.h"
  17. struct pattern {
  18. char *p_constraint; /* constraint of this pattern */
  19. int p_lineno, /* line number of constraint */
  20. p_npat, /* # of instructions in pattern */
  21. p_nrepl; /* # of instructions in replacement */
  22. };
  23. static struct pattern *pattable, /* ptr to pattern array */
  24. *current, /* ptr to first unoccupied el of
  25. * pattern array
  26. */
  27. *maxpat; /* if beyond this, new space must
  28. * be allocated
  29. */
  30. addpattern(str,l,np,nr) char *str; {
  31. /*
  32. * Just add a pattern to the list.
  33. * "str" is the constraint, "l" is the line number,
  34. * "np" is the number of instructions in the pattern,
  35. * "nr" is the number of instructions in the replacement
  36. * Space is allocated in chunks of 50
  37. */
  38. register struct pattern *p;
  39. if (!pattable) { /* No space allocated yet */
  40. pattable = (struct pattern *) malloc(50 * sizeof *pattable);
  41. current = pattable;
  42. maxpat = pattable + 50;
  43. }
  44. if (current >= maxpat) { /* Allocate some new space */
  45. p = pattable;
  46. pattable = (struct pattern *) realloc(
  47. (char *) pattable,
  48. (unsigned) (sizeof *pattable * (50 + (maxpat - pattable))));
  49. current = pattable + (current - p);
  50. maxpat = pattable + (maxpat - p) + 50;
  51. }
  52. p = current++;
  53. p->p_constraint = str;
  54. p->p_lineno = l;
  55. p->p_npat = np;
  56. p->p_nrepl = nr;
  57. }
  58. static
  59. prconstraint(str) char *str; {
  60. /*
  61. * prints a constraint, with variable names replaced
  62. */
  63. char c;
  64. register char *p, *q;
  65. struct symtab *name;
  66. p = str;
  67. while (*p) {
  68. if (isupper(*p) || islower(*p) || *p == '_') {
  69. /*
  70. * Start of identifier
  71. */
  72. q = p + 1;
  73. while (*q && (
  74. isupper(*q) || islower(*q) || isdigit(*q) || *q == '_')) {
  75. q++;
  76. }
  77. c = *q;
  78. *q = '\0';
  79. /* Temporarily let it end with null byte */
  80. name = findident(p,LOOKING,&idtable);
  81. if (name) { /* yeah, it was a variable */
  82. fprintf(genc,"var[%d].value", name->s_num);
  83. }
  84. else if (!strcmp(p, "ANY")) {
  85. fputs("ANY.value", genc);
  86. }
  87. else fputs(p,genc);
  88. /* Now replace null byte with whatever used to be there */
  89. *q = c;
  90. p = q;
  91. }
  92. else {
  93. putc(*p,genc);
  94. p++;
  95. }
  96. }
  97. }
  98. printpatterns() {
  99. /*
  100. * Prints the pattern_descr table and generates the routine
  101. * "check_constraint"
  102. */
  103. register struct pattern *p;
  104. register i;
  105. p = pattable;
  106. i = 1;
  107. fputs("struct pattern_descr patterns[] = {\n", genc);
  108. while (p != current) {
  109. fprintf(genc," {%d,pat%d,%d,rep%d,},\n",
  110. p->p_npat, i, p->p_nrepl, i);
  111. p++;
  112. i++;
  113. }
  114. fputs("};\n", genc);
  115. fputs("int\ncheck_constraint(patno){\n\tint r;\n\tswitch(patno){\n",genc);
  116. p = pattable;
  117. while (p < current) {
  118. if (p->p_constraint) {
  119. /* The pattern has a constraint */
  120. fprintf(genc,"\tcase %d :\n",p - pattable);
  121. fprintf(genc,linedir,p->p_lineno,inpfile); /* linedirective */
  122. fputs("\tr = (",genc);
  123. prconstraint(p->p_constraint);
  124. fputs("); break;\n",genc);
  125. }
  126. p++;
  127. }
  128. fputs("\tdefault :\n\t\tr = 1;\n\t}\n\treturn r;\n}\n\n",genc);
  129. }