instruct.c 4.2 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208
  1. /*
  2. * (c) copyright 1987 by the Vrije Universiteit, Amsterdam, The Netherlands.
  3. * See the copyright notice in the ACK home directory, in the file "Copyright".
  4. */
  5. #ifndef NORCSID
  6. static char rcsid[]= "$Id$";
  7. #endif
  8. #include <string.h>
  9. #include "param.h"
  10. #include "instruct.h"
  11. #include "pseudo.h"
  12. #include "varinfo.h"
  13. #include "set.h"
  14. #include "expr.h"
  15. #include "iocc.h"
  16. #include <cgg_cg.h>
  17. #include "extern.h"
  18. extern int niops;
  19. extern iocc_t iops[];
  20. extern inproc;
  21. extern set_t l_sets[];
  22. extern inst_t l_instances[];
  23. extern expr_t subreg_expr(),regno_expr();
  24. struct varinfo *setcoco(int n)
  25. {
  26. struct varinfo *vi;
  27. NEW(vi,struct varinfo);
  28. vi->vi_next = VI_NULL;
  29. vi->vi_int[0] = INSSETCC;
  30. vi->vi_int[1] = n;
  31. return(vi);
  32. }
  33. struct varinfo *generase(int n)
  34. {
  35. struct varinfo *vi;
  36. NEW(vi,struct varinfo);
  37. vi->vi_next = VI_NULL;
  38. vi->vi_int[0] = INSERASE;
  39. vi->vi_int[1] = n;
  40. return(vi);
  41. }
  42. struct varinfo *genremove(int n)
  43. {
  44. struct varinfo *vi;
  45. NEW(vi,struct varinfo);
  46. vi->vi_next = VI_NULL;
  47. vi->vi_int[0] = INSREMOVE;
  48. vi->vi_int[1] = n;
  49. return(vi);
  50. }
  51. int onlyreg(int argno)
  52. {
  53. int bitno;
  54. short *sp;
  55. if (! argno) argno++;
  56. sp = l_sets[tokpatset[argno-1]].set_val;
  57. for(bitno=nregs;bitno<nregs+ntokens;bitno++)
  58. if (BIT(sp,bitno))
  59. return(0);
  60. return(1);
  61. }
  62. void makescratch(int argno)
  63. {
  64. set_t s;
  65. if (! argno) argno++;
  66. if (tokpatro[argno-1])
  67. error("Instruction destroys %%%d, not allowed here",argno);
  68. s = l_sets[tokpatset[argno-1]];
  69. BIC(s.set_val,0);
  70. tokpatset[argno-1] = setlookup(s);
  71. }
  72. struct varinfo *gen_inst(char *ident, int star)
  73. {
  74. struct varinfo *vi,*retval,*eravi;
  75. instr_p ip;
  76. struct operand *op;
  77. int i;
  78. inst_p insta;
  79. if (star && !inproc)
  80. error("Variable instruction only allowed inside proc");
  81. for (ip=l_instr;ip<l_instr+ninstr;ip++) {
  82. if(strcmp(ident,ip->i_name))
  83. continue;
  84. if (ip->i_nops!=niops)
  85. continue;
  86. for(i=0,op=ip->i_oplist;i<niops;i++,op=op->o_next) {
  87. if (!subset(iops[i].in_set,l_sets[op->o_setno].set_val,SETSIZE))
  88. goto cont;
  89. }
  90. goto found; /* oh well, one more won't hurt */
  91. cont:;
  92. }
  93. error("Such an \"%s\" does not exist",ident);
  94. return(0);
  95. found:
  96. NEW(vi,struct varinfo);
  97. vi->vi_int[0] = ip-l_instr;
  98. vi->vi_int[1] = star;
  99. vi->vi_next=0;
  100. retval = vi;
  101. for(i=0;i<niops;i++) {
  102. NEW(vi->vi_vi,struct varinfo);
  103. vi=vi->vi_vi;
  104. vi->vi_int[0] = iops[i].in_index;
  105. }
  106. vi->vi_vi = 0;
  107. vi = retval;
  108. for(i=0,op=ip->i_oplist;i<niops;i++,op=op->o_next) {
  109. if(op->o_adorn&AD_CC) {
  110. vi->vi_next = setcoco(iops[i].in_index);
  111. vi=vi->vi_next;
  112. }
  113. switch(op->o_adorn&AD_RWMASK) {
  114. default:
  115. /* Nothing possible to do */
  116. break;
  117. case AD_RO:
  118. /* It might be possible to do something
  119. * here but not now.
  120. */
  121. break;
  122. case AD_RW:
  123. case AD_WO:
  124. /* Treated the same for now */
  125. insta = &l_instances[iops[i].in_index];
  126. switch(insta->in_which) {
  127. case IN_COPY:
  128. if(insta->in_info[1]==0 && !onlyreg(insta->in_info[0]))
  129. break;
  130. makescratch(insta->in_info[0]);
  131. vi->vi_next = generase(
  132. ex_lookup(
  133. EX_SUBREG,insta->in_info[0],
  134. insta->in_info[1]
  135. )
  136. );
  137. vi = vi->vi_next;
  138. break;
  139. case IN_MEMB:
  140. vi->vi_next = generase(
  141. ex_lookup(
  142. EX_TOKFIELD,insta->in_info[0],
  143. insta->in_info[1]
  144. )
  145. );
  146. vi=vi->vi_next;
  147. break;
  148. case IN_RIDENT:
  149. vi->vi_next = generase(
  150. ex_lookup(
  151. EX_REG,insta->in_info[0],0
  152. )
  153. );
  154. vi = vi->vi_next;
  155. break;
  156. case IN_ALLOC:
  157. vi->vi_next = generase(
  158. ex_lookup(
  159. EX_ALLREG,insta->in_info[0]+1,
  160. insta->in_info[1]
  161. )
  162. );
  163. vi = vi->vi_next;
  164. break;
  165. case IN_S_DESCR:
  166. case IN_D_DESCR:
  167. { int temp;
  168. temp=ex_lookup(EX_REGVAR,insta->in_info[1],0);
  169. vi->vi_next = generase(temp);
  170. vi = vi->vi_next;
  171. vi->vi_next = genremove(temp);
  172. vi = vi->vi_next;
  173. break;
  174. }
  175. }
  176. break;
  177. }
  178. }
  179. for (eravi=ip->i_erases;eravi != VI_NULL;eravi=eravi->vi_next) {
  180. if (eravi->vi_int[0] < 0)
  181. vi->vi_next = setcoco(0);
  182. else {
  183. vi->vi_next = generase(eravi->vi_int[0]);
  184. vi=vi->vi_next;
  185. vi->vi_next = genremove(eravi->vi_int[0]);
  186. }
  187. vi=vi->vi_next;
  188. }
  189. return(retval);
  190. }