mach.c 4.8 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263
  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. */
  6. #ifndef NORCSID
  7. static char rcs_m[]= "$Id$" ;
  8. static char rcs_mh[]= ID_MH ;
  9. #endif
  10. #include <stb.h>
  11. /*
  12. * machine dependent back end routines for the Intel 80386
  13. */
  14. con_part(sz,w) register sz; word w; {
  15. while (part_size % sz)
  16. part_size++;
  17. if (part_size == TEM_WSIZE)
  18. part_flush();
  19. if (sz == 1 || sz == 2) {
  20. w &= (sz == 1 ? 0xFF : 0xFFFF);
  21. w <<= 8 * part_size;
  22. part_word |= w;
  23. } else {
  24. assert(sz == 4);
  25. part_word = w;
  26. }
  27. part_size += sz;
  28. }
  29. con_mult(sz) word sz; {
  30. long l;
  31. if (sz != 4)
  32. fatal("bad icon/ucon size");
  33. l = atol(str);
  34. fprintf(codefile,"\t.data4 %ld\n", l);
  35. }
  36. #define CODE_GENERATOR
  37. #define IEEEFLOAT
  38. #define FL_MSL_AT_LOW_ADDRESS 0
  39. #define FL_MSW_AT_LOW_ADDRESS 0
  40. #define FL_MSB_AT_LOW_ADDRESS 0
  41. #include <con_float>
  42. /*
  43. string holstr(n) word n; {
  44. sprintf(str,hol_off,n,holno);
  45. return(mystrcpy(str));
  46. }
  47. */
  48. #ifdef REGVARS
  49. full lbytes;
  50. #endif
  51. prolog(nlocals) full nlocals; {
  52. fputs("push ebp\nmov ebp,esp\n", codefile);
  53. #ifdef REGVARS
  54. lbytes = nlocals;
  55. #else
  56. #ifdef NOTDEF
  57. probably not better on 386.
  58. switch(nlocals) {
  59. case 8:
  60. fputs("push eax\n", codefile);
  61. /* fall through */
  62. case 4:
  63. fputs("push eax\n", codefile);
  64. break;
  65. default:
  66. #endif
  67. fprintf(codefile, "sub\tesp,%ld\n",nlocals);
  68. #ifdef NOTDEF
  69. break;
  70. }
  71. #endif
  72. #endif
  73. }
  74. #ifdef REGVARS
  75. long si_off;
  76. long di_off;
  77. int firstreg;
  78. regscore(off, size, typ, score, totyp)
  79. long off;
  80. {
  81. if (size != 4) return -1;
  82. score -= 1;
  83. score += score;
  84. if (typ == reg_pointer || typ == reg_loop) score += (score >> 2);
  85. score -= 2; /* cost of saving */
  86. if (off >= 0) score -= 3;
  87. return score;
  88. }
  89. i_regsave()
  90. {
  91. si_off = -1;
  92. di_off = -1;
  93. firstreg = 0;
  94. }
  95. f_regsave()
  96. {
  97. if (si_off != di_off) {
  98. if (si_off == -lbytes) lbytes -= 4;
  99. if (di_off == -lbytes) lbytes -= 4;
  100. if (si_off == -lbytes) lbytes -= 4;
  101. }
  102. if (lbytes) fprintf(codefile, "sub\tesp,%ld\n",(long) lbytes);
  103. if (firstreg == 1) {
  104. fputs("push edi\n", codefile);
  105. if (si_off != -1) fputs("push esi\n", codefile);
  106. }
  107. else if (firstreg == -1) {
  108. fputs("push esi\n", codefile);
  109. if (di_off != -1) fputs("push edi\n", codefile);
  110. }
  111. if (si_off >= 0)
  112. fprintf(codefile, "mov esi,%ld(ebp)\n", si_off);
  113. if (di_off >= 0)
  114. fprintf(codefile, "mov edi,%ld(ebp)\n", di_off);
  115. }
  116. regsave(regstr, off, size)
  117. char *regstr;
  118. long off;
  119. {
  120. if (strcmp(regstr, "esi") == 0) {
  121. if (! firstreg) firstreg = -1;
  122. si_off = off;
  123. }
  124. else {
  125. if (! firstreg) firstreg = 1;
  126. di_off = off;
  127. }
  128. }
  129. regreturn()
  130. {
  131. if (firstreg == 1) {
  132. if (si_off != -1) fputs("pop esi\n", codefile);
  133. fputs("pop edi\n", codefile);
  134. }
  135. else if (firstreg == -1) {
  136. if (di_off != -1) fputs("pop edi\n", codefile);
  137. fputs("pop esi\n", codefile);
  138. }
  139. fputs("leave\nret\n", codefile);
  140. }
  141. #endif /* REGVARS */
  142. #ifdef MACH_OPTIONS
  143. static int gdb_flag = 0;
  144. static char *fp_hook_nam;
  145. mach_option(s)
  146. char *s;
  147. {
  148. if (! strcmp(s, "-gdb")) {
  149. gdb_flag = 1;
  150. }
  151. else if (s[1] == 'F') {
  152. fp_hook_nam = &s[2];
  153. }
  154. else {
  155. error("Unknown flag %s", s);
  156. }
  157. }
  158. #endif /* MACH_OPTIONS */
  159. mes(type) word type ; {
  160. int argt, a1, a2 ;
  161. switch ( (int)type ) {
  162. case ms_ext :
  163. for (;;) {
  164. switch ( argt=getarg(
  165. ptyp(sp_cend)|ptyp(sp_pnam)|sym_ptyp) ) {
  166. case sp_cend :
  167. return ;
  168. default:
  169. strarg(argt) ;
  170. fprintf(codefile, ".define %s\n",argstr) ;
  171. break ;
  172. }
  173. }
  174. case ms_stb:
  175. argt = getarg(str_ptyp | cst_ptyp);
  176. if (argt == sp_cstx)
  177. fputs(".symb \"\", ", codefile);
  178. else {
  179. fprintf(codefile, ".symb \"%s\", ", str);
  180. argt = getarg(cst_ptyp);
  181. }
  182. a1 = argval;
  183. argt = getarg(cst_ptyp);
  184. a2 = argval;
  185. argt = getarg(cst_ptyp|nof_ptyp|sof_ptyp|ilb_ptyp|pro_ptyp);
  186. #ifdef MACH_OPTIONS
  187. if (gdb_flag) {
  188. if (a1 == N_PSYM) {
  189. /* Change offset from AB into offset from
  190. the frame pointer (bp).
  191. */
  192. argval += 8;
  193. }
  194. }
  195. #endif
  196. fprintf(codefile, "%s, 0x%x, %d\n", strarg(argt), a1, a2);
  197. argt = getarg(end_ptyp);
  198. break;
  199. case ms_std:
  200. argt = getarg(str_ptyp | cst_ptyp);
  201. if (argt == sp_cstx)
  202. str[0] = '\0';
  203. else {
  204. argt = getarg(cst_ptyp);
  205. }
  206. swtxt();
  207. if (argval == N_SLINE
  208. #ifdef MACH_OPTIONS
  209. && ! gdb_flag
  210. #endif
  211. ) {
  212. fputs("call ___u_LiB\n", codefile);
  213. cleanregs(); /* debugger might change variables */
  214. }
  215. fprintf(codefile, ".symd \"%s\", 0x%x,", str, (int) argval);
  216. argt = getarg(cst_ptyp);
  217. fprintf(codefile, "%d\n", (int) argval);
  218. argt = getarg(end_ptyp);
  219. break;
  220. #ifdef MACH_OPTIONS
  221. case ms_flt:
  222. if (fp_hook_nam) {
  223. part_flush();
  224. ex_ap(fp_hook_nam);
  225. }
  226. /* fall through */
  227. #endif
  228. default :
  229. while ( getarg(any_ptyp) != sp_cend ) ;
  230. break ;
  231. }
  232. }
  233. char *segname[] = {
  234. ".sect .text", /* SEGTXT */
  235. ".sect .data", /* SEGCON */
  236. ".sect .rom", /* SEGROM */
  237. ".sect .bss" /* SEGBSS */
  238. };