instruct.c 4.2 KB

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