list.c 3.9 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282
  1. #define EXTERN
  2. #include "gc.h"
  3. void
  4. listinit(void)
  5. {
  6. fmtinstall('A', Aconv);
  7. fmtinstall('B', Bconv);
  8. fmtinstall('P', Pconv);
  9. fmtinstall('S', Sconv);
  10. fmtinstall('D', Dconv);
  11. fmtinstall('R', Rconv);
  12. }
  13. int
  14. Bconv(Fmt *fp)
  15. {
  16. char str[STRINGSZ], ss[STRINGSZ], *s;
  17. Bits bits;
  18. int i;
  19. str[0] = 0;
  20. bits = va_arg(fp->args, Bits);
  21. while(bany(&bits)) {
  22. i = bnum(bits);
  23. if(str[0])
  24. strcat(str, " ");
  25. if(var[i].sym == S) {
  26. sprint(ss, "$%ld", var[i].offset);
  27. s = ss;
  28. } else
  29. s = var[i].sym->name;
  30. if(strlen(str) + strlen(s) + 1 >= STRINGSZ)
  31. break;
  32. strcat(str, s);
  33. bits.b[i/32] &= ~(1L << (i%32));
  34. }
  35. return fmtstrcpy(fp, str);
  36. }
  37. int
  38. Pconv(Fmt *fp)
  39. {
  40. char str[STRINGSZ];
  41. Prog *p;
  42. p = va_arg(fp->args, Prog*);
  43. if(p->as == ADATA)
  44. sprint(str, " %A %D/%d,%D",
  45. p->as, &p->from, p->from.scale, &p->to);
  46. else if(p->as == ATEXT)
  47. sprint(str, " %A %D,%d,%D",
  48. p->as, &p->from, p->from.scale, &p->to);
  49. else
  50. sprint(str, " %A %D,%D",
  51. p->as, &p->from, &p->to);
  52. return fmtstrcpy(fp, str);
  53. }
  54. int
  55. Aconv(Fmt *fp)
  56. {
  57. int i;
  58. i = va_arg(fp->args, int);
  59. return fmtstrcpy(fp, anames[i]);
  60. }
  61. int
  62. Dconv(Fmt *fp)
  63. {
  64. char str[40], s[20];
  65. Adr *a;
  66. int i;
  67. a = va_arg(fp->args, Adr*);
  68. i = a->type;
  69. if(i >= D_INDIR) {
  70. if(a->offset)
  71. sprint(str, "%ld(%R)", a->offset, i-D_INDIR);
  72. else
  73. sprint(str, "(%R)", i-D_INDIR);
  74. goto brk;
  75. }
  76. switch(i) {
  77. default:
  78. if(a->offset)
  79. sprint(str, "$%ld,%R", a->offset, i);
  80. else
  81. sprint(str, "%R", i);
  82. break;
  83. case D_NONE:
  84. str[0] = 0;
  85. break;
  86. case D_BRANCH:
  87. sprint(str, "%ld(PC)", a->offset-pc);
  88. break;
  89. case D_EXTERN:
  90. sprint(str, "%s+%ld(SB)", a->sym->name, a->offset);
  91. break;
  92. case D_STATIC:
  93. sprint(str, "%s<>+%ld(SB)", a->sym->name,
  94. a->offset);
  95. break;
  96. case D_AUTO:
  97. sprint(str, "%s+%ld(SP)", a->sym->name, a->offset);
  98. break;
  99. case D_PARAM:
  100. if(a->sym)
  101. sprint(str, "%s+%ld(FP)", a->sym->name, a->offset);
  102. else
  103. sprint(str, "%ld(FP)", a->offset);
  104. break;
  105. case D_CONST:
  106. sprint(str, "$%ld", a->offset);
  107. break;
  108. case D_FCONST:
  109. sprint(str, "$(%.17e)", a->dval);
  110. break;
  111. case D_SCONST:
  112. sprint(str, "$\"%S\"", a->sval);
  113. break;
  114. case D_ADDR:
  115. a->type = a->index;
  116. a->index = D_NONE;
  117. sprint(str, "$%D", a);
  118. a->index = a->type;
  119. a->type = D_ADDR;
  120. goto conv;
  121. }
  122. brk:
  123. if(a->index != D_NONE) {
  124. sprint(s, "(%R*%d)", (int)a->index, (int)a->scale);
  125. strcat(str, s);
  126. }
  127. conv:
  128. return fmtstrcpy(fp, str);
  129. }
  130. char* regstr[] =
  131. {
  132. "AL", /*[D_AL]*/
  133. "CL",
  134. "DL",
  135. "BL",
  136. "AH",
  137. "CH",
  138. "DH",
  139. "BH",
  140. "AX", /*[D_AX]*/
  141. "CX",
  142. "DX",
  143. "BX",
  144. "SP",
  145. "BP",
  146. "SI",
  147. "DI",
  148. "F0", /*[D_F0]*/
  149. "F1",
  150. "F2",
  151. "F3",
  152. "F4",
  153. "F5",
  154. "F6",
  155. "F7",
  156. "CS", /*[D_CS]*/
  157. "SS",
  158. "DS",
  159. "ES",
  160. "FS",
  161. "GS",
  162. "GDTR", /*[D_GDTR]*/
  163. "IDTR", /*[D_IDTR]*/
  164. "LDTR", /*[D_LDTR]*/
  165. "MSW", /*[D_MSW] */
  166. "TASK", /*[D_TASK]*/
  167. "CR0", /*[D_CR]*/
  168. "CR1",
  169. "CR2",
  170. "CR3",
  171. "CR4",
  172. "CR5",
  173. "CR6",
  174. "CR7",
  175. "DR0", /*[D_DR]*/
  176. "DR1",
  177. "DR2",
  178. "DR3",
  179. "DR4",
  180. "DR5",
  181. "DR6",
  182. "DR7",
  183. "TR0", /*[D_TR]*/
  184. "TR1",
  185. "TR2",
  186. "TR3",
  187. "TR4",
  188. "TR5",
  189. "TR6",
  190. "TR7",
  191. "NONE", /*[D_NONE]*/
  192. };
  193. int
  194. Rconv(Fmt *fp)
  195. {
  196. char str[20];
  197. int r;
  198. r = va_arg(fp->args, int);
  199. if(r >= D_AL && r <= D_NONE)
  200. sprint(str, "%s", regstr[r-D_AL]);
  201. else
  202. sprint(str, "gok(%d)", r);
  203. return fmtstrcpy(fp, str);
  204. }
  205. int
  206. Sconv(Fmt *fp)
  207. {
  208. int i, c;
  209. char str[30], *p, *a;
  210. a = va_arg(fp->args, char*);
  211. p = str;
  212. for(i=0; i<sizeof(double); i++) {
  213. c = a[i] & 0xff;
  214. if(c >= 'a' && c <= 'z' ||
  215. c >= 'A' && c <= 'Z' ||
  216. c >= '0' && c <= '9') {
  217. *p++ = c;
  218. continue;
  219. }
  220. *p++ = '\\';
  221. switch(c) {
  222. default:
  223. if(c < 040 || c >= 0177)
  224. break; /* not portable */
  225. p[-1] = c;
  226. continue;
  227. case 0:
  228. *p++ = 'z';
  229. continue;
  230. case '\\':
  231. case '"':
  232. *p++ = c;
  233. continue;
  234. case '\n':
  235. *p++ = 'n';
  236. continue;
  237. case '\t':
  238. *p++ = 't';
  239. continue;
  240. }
  241. *p++ = (c>>6) + '0';
  242. *p++ = ((c>>3) & 7) + '0';
  243. *p++ = (c & 7) + '0';
  244. }
  245. *p = 0;
  246. return fmtstrcpy(fp, str);
  247. }