txt.c 27 KB

12345678910111213141516171819202122232425262728293031323334353637383940414243444546474849505152535455565758596061626364656667686970717273747576777879808182838485868788899091929394959697989910010110210310410510610710810911011111211311411511611711811912012112212312412512612712812913013113213313413513613713813914014114214314414514614714814915015115215315415515615715815916016116216316416516616716816917017117217317417517617717817918018118218318418518618718818919019119219319419519619719819920020120220320420520620720820921021121221321421521621721821922022122222322422522622722822923023123223323423523623723823924024124224324424524624724824925025125225325425525625725825926026126226326426526626726826927027127227327427527627727827928028128228328428528628728828929029129229329429529629729829930030130230330430530630730830931031131231331431531631731831932032132232332432532632732832933033133233333433533633733833934034134234334434534634734834935035135235335435535635735835936036136236336436536636736836937037137237337437537637737837938038138238338438538638738838939039139239339439539639739839940040140240340440540640740840941041141241341441541641741841942042142242342442542642742842943043143243343443543643743843944044144244344444544644744844945045145245345445545645745845946046146246346446546646746846947047147247347447547647747847948048148248348448548648748848949049149249349449549649749849950050150250350450550650750850951051151251351451551651751851952052152252352452552652752852953053153253353453553653753853954054154254354454554654754854955055155255355455555655755855956056156256356456556656756856957057157257357457557657757857958058158258358458558658758858959059159259359459559659759859960060160260360460560660760860961061161261361461561661761861962062162262362462562662762862963063163263363463563663763863964064164264364464564664764864965065165265365465565665765865966066166266366466566666766866967067167267367467567667767867968068168268368468568668768868969069169269369469569669769869970070170270370470570670770870971071171271371471571671771871972072172272372472572672772872973073173273373473573673773873974074174274374474574674774874975075175275375475575675775875976076176276376476576676776876977077177277377477577677777877978078178278378478578678778878979079179279379479579679779879980080180280380480580680780880981081181281381481581681781881982082182282382482582682782882983083183283383483583683783883984084184284384484584684784884985085185285385485585685785885986086186286386486586686786886987087187287387487587687787887988088188288388488588688788888989089189289389489589689789889990090190290390490590690790890991091191291391491591691791891992092192292392492592692792892993093193293393493593693793893994094194294394494594694794894995095195295395495595695795895996096196296396496596696796896997097197297397497597697797897998098198298398498598698798898999099199299399499599699799899910001001100210031004100510061007100810091010101110121013101410151016101710181019102010211022102310241025102610271028102910301031103210331034103510361037103810391040104110421043104410451046104710481049105010511052105310541055105610571058105910601061106210631064106510661067106810691070107110721073107410751076107710781079108010811082108310841085108610871088108910901091109210931094109510961097109810991100110111021103110411051106110711081109111011111112111311141115111611171118111911201121112211231124112511261127112811291130113111321133113411351136113711381139114011411142114311441145114611471148114911501151115211531154115511561157115811591160116111621163116411651166116711681169117011711172117311741175117611771178117911801181118211831184118511861187118811891190119111921193119411951196119711981199120012011202120312041205120612071208120912101211121212131214121512161217121812191220122112221223122412251226122712281229123012311232123312341235123612371238123912401241124212431244124512461247124812491250125112521253125412551256125712581259126012611262126312641265126612671268126912701271127212731274127512761277127812791280128112821283128412851286128712881289129012911292129312941295129612971298129913001301130213031304130513061307130813091310131113121313131413151316131713181319132013211322132313241325132613271328132913301331133213331334133513361337133813391340134113421343134413451346134713481349135013511352135313541355135613571358135913601361136213631364136513661367136813691370137113721373137413751376137713781379138013811382138313841385138613871388138913901391139213931394139513961397139813991400140114021403140414051406140714081409141014111412141314141415141614171418141914201421142214231424142514261427142814291430143114321433143414351436143714381439144014411442144314441445144614471448144914501451145214531454145514561457145814591460146114621463146414651466146714681469147014711472147314741475147614771478147914801481148214831484148514861487148814891490149114921493149414951496149714981499150015011502150315041505150615071508150915101511151215131514
  1. #include "gc.h"
  2. void
  3. ginit(void)
  4. {
  5. int i;
  6. Type *t;
  7. thechar = '6';
  8. thestring = "amd64";
  9. exregoffset = REGEXT;
  10. exfregoffset = FREGEXT;
  11. listinit();
  12. nstring = 0;
  13. mnstring = 0;
  14. nrathole = 0;
  15. pc = 0;
  16. breakpc = -1;
  17. continpc = -1;
  18. cases = C;
  19. firstp = P;
  20. lastp = P;
  21. tfield = types[TINT];
  22. typeword = typechlvp;
  23. typecmplx = typesu;
  24. /* TO DO */
  25. memmove(typechlpv, typechlp, sizeof(typechlpv));
  26. typechlpv[TVLONG] = 1;
  27. typechlpv[TUVLONG] = 1;
  28. zprog.link = P;
  29. zprog.as = AGOK;
  30. zprog.from.type = D_NONE;
  31. zprog.from.index = D_NONE;
  32. zprog.from.scale = 0;
  33. zprog.to = zprog.from;
  34. lregnode.op = OREGISTER;
  35. lregnode.class = CEXREG;
  36. lregnode.reg = REGTMP;
  37. lregnode.complex = 0;
  38. lregnode.addable = 11;
  39. lregnode.type = types[TLONG];
  40. qregnode = lregnode;
  41. qregnode.type = types[TVLONG];
  42. constnode.op = OCONST;
  43. constnode.class = CXXX;
  44. constnode.complex = 0;
  45. constnode.addable = 20;
  46. constnode.type = types[TLONG];
  47. vconstnode = constnode;
  48. vconstnode.type = types[TVLONG];
  49. fconstnode.op = OCONST;
  50. fconstnode.class = CXXX;
  51. fconstnode.complex = 0;
  52. fconstnode.addable = 20;
  53. fconstnode.type = types[TDOUBLE];
  54. nodsafe = new(ONAME, Z, Z);
  55. nodsafe->sym = slookup(".safe");
  56. nodsafe->type = types[TINT];
  57. nodsafe->etype = types[TINT]->etype;
  58. nodsafe->class = CAUTO;
  59. complex(nodsafe);
  60. t = typ(TARRAY, types[TCHAR]);
  61. symrathole = slookup(".rathole");
  62. symrathole->class = CGLOBL;
  63. symrathole->type = t;
  64. nodrat = new(ONAME, Z, Z);
  65. nodrat->sym = symrathole;
  66. nodrat->type = types[TIND];
  67. nodrat->etype = TVOID;
  68. nodrat->class = CGLOBL;
  69. complex(nodrat);
  70. nodrat->type = t;
  71. nodret = new(ONAME, Z, Z);
  72. nodret->sym = slookup(".ret");
  73. nodret->type = types[TIND];
  74. nodret->etype = TIND;
  75. nodret->class = CPARAM;
  76. nodret = new(OIND, nodret, Z);
  77. complex(nodret);
  78. if(0)
  79. com64init();
  80. for(i=0; i<nelem(reg); i++) {
  81. reg[i] = 1;
  82. if(i >= D_AX && i <= D_R15 && i != D_SP)
  83. reg[i] = 0;
  84. if(i >= D_X0 && i <= D_X7)
  85. reg[i] = 0;
  86. }
  87. }
  88. void
  89. gclean(void)
  90. {
  91. int i;
  92. Sym *s;
  93. reg[D_SP]--;
  94. for(i=D_AX; i<=D_R15; i++)
  95. if(reg[i])
  96. diag(Z, "reg %R left allocated", i);
  97. for(i=D_X0; i<=D_X7; i++)
  98. if(reg[i])
  99. diag(Z, "reg %R left allocated", i);
  100. while(mnstring)
  101. outstring("", 1L);
  102. symstring->type->width = nstring;
  103. symrathole->type->width = nrathole;
  104. for(i=0; i<NHASH; i++)
  105. for(s = hash[i]; s != S; s = s->link) {
  106. if(s->type == T)
  107. continue;
  108. if(s->type->width == 0)
  109. continue;
  110. if(s->class != CGLOBL && s->class != CSTATIC)
  111. continue;
  112. if(s->type == types[TENUM])
  113. continue;
  114. gpseudo(AGLOBL, s, nodconst(s->type->width));
  115. }
  116. nextpc();
  117. p->as = AEND;
  118. outcode();
  119. }
  120. void
  121. nextpc(void)
  122. {
  123. p = alloc(sizeof(*p));
  124. *p = zprog;
  125. p->lineno = nearln;
  126. pc++;
  127. if(firstp == P) {
  128. firstp = p;
  129. lastp = p;
  130. return;
  131. }
  132. lastp->link = p;
  133. lastp = p;
  134. }
  135. void
  136. gargs(Node *n, Node *tn1, Node *tn2)
  137. {
  138. long regs;
  139. Node fnxargs[20], *fnxp;
  140. regs = cursafe;
  141. fnxp = fnxargs;
  142. garg1(n, tn1, tn2, 0, &fnxp); /* compile fns to temps */
  143. curarg = 0;
  144. fnxp = fnxargs;
  145. garg1(n, tn1, tn2, 1, &fnxp); /* compile normal args and temps */
  146. cursafe = regs;
  147. }
  148. int
  149. nareg(void)
  150. {
  151. int i, n;
  152. n = 0;
  153. for(i=D_AX; i<=D_R15; i++)
  154. if(reg[i] == 0)
  155. n++;
  156. return n;
  157. }
  158. void
  159. garg1(Node *n, Node *tn1, Node *tn2, int f, Node **fnxp)
  160. {
  161. Node nod;
  162. if(n == Z)
  163. return;
  164. if(n->op == OLIST) {
  165. garg1(n->left, tn1, tn2, f, fnxp);
  166. garg1(n->right, tn1, tn2, f, fnxp);
  167. return;
  168. }
  169. if(f == 0) {
  170. if(n->complex >= FNX) {
  171. regsalloc(*fnxp, n);
  172. nod = znode;
  173. nod.op = OAS;
  174. nod.left = *fnxp;
  175. nod.right = n;
  176. nod.type = n->type;
  177. cgen(&nod, Z);
  178. (*fnxp)++;
  179. }
  180. return;
  181. }
  182. if(typesu[n->type->etype]) {
  183. regaalloc(tn2, n);
  184. if(n->complex >= FNX) {
  185. sugen(*fnxp, tn2, n->type->width);
  186. (*fnxp)++;
  187. } else
  188. sugen(n, tn2, n->type->width);
  189. return;
  190. }
  191. if(REGARG && curarg == 0 && typechlpv[n->type->etype]) {
  192. regaalloc1(tn1, n);
  193. if(n->complex >= FNX) {
  194. cgen(*fnxp, tn1);
  195. (*fnxp)++;
  196. } else
  197. cgen(n, tn1);
  198. return;
  199. }
  200. if(vconst(n) == 0) {
  201. regaalloc(tn2, n);
  202. gmove(n, tn2);
  203. return;
  204. }
  205. regalloc(tn1, n, Z);
  206. if(n->complex >= FNX) {
  207. cgen(*fnxp, tn1);
  208. (*fnxp)++;
  209. } else
  210. cgen(n, tn1);
  211. regaalloc(tn2, n);
  212. gmove(tn1, tn2);
  213. regfree(tn1);
  214. }
  215. Node*
  216. nodgconst(vlong v, Type *t)
  217. {
  218. if(!typev[t->etype])
  219. return nodconst((long)v);
  220. vconstnode.vconst = v;
  221. return &vconstnode;
  222. }
  223. Node*
  224. nodconst(long v)
  225. {
  226. constnode.vconst = v;
  227. return &constnode;
  228. }
  229. Node*
  230. nodfconst(double d)
  231. {
  232. fconstnode.fconst = d;
  233. return &fconstnode;
  234. }
  235. int
  236. isreg(Node *n, int r)
  237. {
  238. if(n->op == OREGISTER)
  239. if(n->reg == r)
  240. return 1;
  241. return 0;
  242. }
  243. int
  244. nodreg(Node *n, Node *nn, int r)
  245. {
  246. int et;
  247. *n = qregnode;
  248. n->reg = r;
  249. if(nn != Z){
  250. et = nn->type->etype;
  251. if(!typefd[et] && nn->type->width <= SZ_LONG && 0)
  252. n->type = typeu[et]? types[TUINT]: types[TINT];
  253. else
  254. n->type = nn->type;
  255. //print("nodreg %s [%s]\n", tnames[et], tnames[n->type->etype]);
  256. n->lineno = nn->lineno;
  257. }
  258. if(reg[r] == 0)
  259. return 0;
  260. if(nn != Z) {
  261. if(nn->op == OREGISTER)
  262. if(nn->reg == r)
  263. return 0;
  264. }
  265. return 1;
  266. }
  267. void
  268. regret(Node *n, Node *nn)
  269. {
  270. int r;
  271. r = REGRET;
  272. if(typefd[nn->type->etype])
  273. r = FREGRET;
  274. nodreg(n, nn, r);
  275. reg[r]++;
  276. }
  277. void
  278. regalloc(Node *n, Node *tn, Node *o)
  279. {
  280. int i;
  281. switch(tn->type->etype) {
  282. case TCHAR:
  283. case TUCHAR:
  284. case TSHORT:
  285. case TUSHORT:
  286. case TINT:
  287. case TUINT:
  288. case TLONG:
  289. case TULONG:
  290. case TVLONG:
  291. case TUVLONG:
  292. case TIND:
  293. if(o != Z && o->op == OREGISTER) {
  294. i = o->reg;
  295. if(i >= D_AX && i <= D_R15)
  296. goto out;
  297. }
  298. for(i=D_AX; i<=D_R15; i++)
  299. if(reg[i] == 0)
  300. goto out;
  301. diag(tn, "out of fixed registers");
  302. goto err;
  303. case TFLOAT:
  304. case TDOUBLE:
  305. if(o != Z && o->op == OREGISTER) {
  306. i = o->reg;
  307. if(i >= D_X0 && i <= D_X7)
  308. goto out;
  309. }
  310. for(i=D_X0; i<=D_X7; i++)
  311. if(reg[i] == 0)
  312. goto out;
  313. diag(tn, "out of float registers");
  314. goto out;
  315. }
  316. diag(tn, "unknown type in regalloc: %T", tn->type);
  317. err:
  318. i = 0;
  319. out:
  320. if(i)
  321. reg[i]++;
  322. nodreg(n, tn, i);
  323. }
  324. void
  325. regialloc(Node *n, Node *tn, Node *o)
  326. {
  327. Node nod;
  328. nod = *tn;
  329. nod.type = types[TIND];
  330. regalloc(n, &nod, o);
  331. }
  332. void
  333. regfree(Node *n)
  334. {
  335. int i;
  336. i = 0;
  337. if(n->op != OREGISTER && n->op != OINDREG)
  338. goto err;
  339. i = n->reg;
  340. if(i < 0 || i >= sizeof(reg))
  341. goto err;
  342. if(reg[i] <= 0)
  343. goto err;
  344. reg[i]--;
  345. return;
  346. err:
  347. diag(n, "error in regfree: %R", i);
  348. }
  349. void
  350. regsalloc(Node *n, Node *nn)
  351. {
  352. cursafe = align(cursafe, nn->type, Aaut3);
  353. maxargsafe = maxround(maxargsafe, cursafe+curarg);
  354. *n = *nodsafe;
  355. n->xoffset = -(stkoff + cursafe);
  356. n->type = nn->type;
  357. n->etype = nn->type->etype;
  358. n->lineno = nn->lineno;
  359. }
  360. void
  361. regaalloc1(Node *n, Node *nn)
  362. {
  363. nodreg(n, nn, REGARG);
  364. reg[REGARG]++;
  365. curarg = align(curarg, nn->type, Aarg1);
  366. curarg = align(curarg, nn->type, Aarg2);
  367. maxargsafe = maxround(maxargsafe, cursafe+curarg);
  368. }
  369. void
  370. regaalloc(Node *n, Node *nn)
  371. {
  372. curarg = align(curarg, nn->type, Aarg1);
  373. *n = *nn;
  374. n->op = OINDREG;
  375. n->reg = REGSP;
  376. n->xoffset = curarg;
  377. n->complex = 0;
  378. n->addable = 20;
  379. curarg = align(curarg, nn->type, Aarg2);
  380. maxargsafe = maxround(maxargsafe, cursafe+curarg);
  381. }
  382. void
  383. regind(Node *n, Node *nn)
  384. {
  385. if(n->op != OREGISTER) {
  386. diag(n, "regind not OREGISTER");
  387. return;
  388. }
  389. n->op = OINDREG;
  390. n->type = nn->type;
  391. }
  392. void
  393. naddr(Node *n, Adr *a)
  394. {
  395. long v;
  396. a->type = D_NONE;
  397. if(n == Z)
  398. return;
  399. switch(n->op) {
  400. default:
  401. bad:
  402. diag(n, "bad in naddr: %O %D", n->op, a);
  403. break;
  404. case OREGISTER:
  405. a->type = n->reg;
  406. a->sym = S;
  407. break;
  408. case OIND:
  409. naddr(n->left, a);
  410. if(a->type >= D_AX && a->type <= D_R15)
  411. a->type += D_INDIR;
  412. else
  413. if(a->type == D_CONST)
  414. a->type = D_NONE+D_INDIR;
  415. else
  416. if(a->type == D_ADDR) {
  417. a->type = a->index;
  418. a->index = D_NONE;
  419. } else
  420. goto bad;
  421. break;
  422. case OINDEX:
  423. a->type = idx.ptr;
  424. if(n->left->op == OADDR || n->left->op == OCONST)
  425. naddr(n->left, a);
  426. if(a->type >= D_AX && a->type <= D_R15)
  427. a->type += D_INDIR;
  428. else
  429. if(a->type == D_CONST)
  430. a->type = D_NONE+D_INDIR;
  431. else
  432. if(a->type == D_ADDR) {
  433. a->type = a->index;
  434. a->index = D_NONE;
  435. } else
  436. goto bad;
  437. a->index = idx.reg;
  438. a->scale = n->scale;
  439. a->offset += n->xoffset;
  440. break;
  441. case OINDREG:
  442. a->type = n->reg+D_INDIR;
  443. a->sym = S;
  444. a->offset = n->xoffset;
  445. break;
  446. case ONAME:
  447. a->etype = n->etype;
  448. a->type = D_STATIC;
  449. a->sym = n->sym;
  450. a->offset = n->xoffset;
  451. if(n->class == CSTATIC)
  452. break;
  453. if(n->class == CEXTERN || n->class == CGLOBL) {
  454. a->type = D_EXTERN;
  455. break;
  456. }
  457. if(n->class == CAUTO) {
  458. a->type = D_AUTO;
  459. break;
  460. }
  461. if(n->class == CPARAM) {
  462. a->type = D_PARAM;
  463. break;
  464. }
  465. goto bad;
  466. case OCONST:
  467. if(typefd[n->type->etype]) {
  468. a->type = D_FCONST;
  469. a->dval = n->fconst;
  470. break;
  471. }
  472. a->sym = S;
  473. a->type = D_CONST;
  474. if(typev[n->type->etype] || n->type->etype == TIND)
  475. a->offset = n->vconst;
  476. else
  477. a->offset = convvtox(n->vconst, typeu[n->type->etype]? TULONG: TLONG);
  478. break;
  479. case OADDR:
  480. naddr(n->left, a);
  481. if(a->type >= D_INDIR) {
  482. a->type -= D_INDIR;
  483. break;
  484. }
  485. if(a->type == D_EXTERN || a->type == D_STATIC ||
  486. a->type == D_AUTO || a->type == D_PARAM)
  487. if(a->index == D_NONE) {
  488. a->index = a->type;
  489. a->type = D_ADDR;
  490. break;
  491. }
  492. goto bad;
  493. case OADD:
  494. if(n->right->op == OCONST) {
  495. v = n->right->vconst;
  496. naddr(n->left, a);
  497. } else
  498. if(n->left->op == OCONST) {
  499. v = n->left->vconst;
  500. naddr(n->right, a);
  501. } else
  502. goto bad;
  503. a->offset += v;
  504. break;
  505. }
  506. }
  507. void
  508. gcmp(int op, Node *n, vlong val)
  509. {
  510. Node *cn, nod;
  511. cn = nodgconst(val, n->type);
  512. if(!immconst(cn)){
  513. regalloc(&nod, n, Z);
  514. gmove(cn, &nod);
  515. gopcode(op, n->type, n, &nod);
  516. regfree(&nod);
  517. }else
  518. gopcode(op, n->type, n, cn);
  519. }
  520. #define CASE(a,b) ((a<<8)|(b<<0))
  521. void
  522. gmove(Node *f, Node *t)
  523. {
  524. int ft, tt, t64, a;
  525. Node nod, nod1, nod2, nod3;
  526. Prog *p1, *p2;
  527. ft = f->type->etype;
  528. tt = t->type->etype;
  529. t64 = tt == TVLONG || tt == TUVLONG || tt == TIND;
  530. if(debug['M'])
  531. print("gop: %O %O[%s],%O[%s]\n", OAS,
  532. f->op, tnames[ft], t->op, tnames[tt]);
  533. if(typefd[ft] && f->op == OCONST) {
  534. /* TO DO: pick up special constants, possibly preloaded */
  535. if(f->fconst == 0.0){
  536. regalloc(&nod, t, t);
  537. gins(AXORPD, &nod, &nod);
  538. gmove(&nod, t);
  539. regfree(&nod);
  540. return;
  541. }
  542. }
  543. /*
  544. * load
  545. */
  546. if(f->op == ONAME || f->op == OINDREG ||
  547. f->op == OIND || f->op == OINDEX)
  548. switch(ft) {
  549. case TCHAR:
  550. a = AMOVBLSX;
  551. if(t64)
  552. a = AMOVBQSX;
  553. goto ld;
  554. case TUCHAR:
  555. a = AMOVBLZX;
  556. if(t64)
  557. a = AMOVBQZX;
  558. goto ld;
  559. case TSHORT:
  560. a = AMOVWLSX;
  561. if(t64)
  562. a = AMOVWQSX;
  563. goto ld;
  564. case TUSHORT:
  565. a = AMOVWLZX;
  566. if(t64)
  567. a = AMOVWQZX;
  568. goto ld;
  569. case TINT:
  570. case TLONG:
  571. if(typefd[tt]) {
  572. regalloc(&nod, t, t);
  573. if(tt == TDOUBLE)
  574. a = ACVTSL2SD;
  575. else
  576. a = ACVTSL2SS;
  577. gins(a, f, &nod);
  578. gmove(&nod, t);
  579. regfree(&nod);
  580. return;
  581. }
  582. a = AMOVL;
  583. if(t64)
  584. a = AMOVLQSX;
  585. goto ld;
  586. case TUINT:
  587. case TULONG:
  588. a = AMOVL;
  589. if(t64)
  590. a = AMOVLQZX; /* could probably use plain MOVL */
  591. goto ld;
  592. case TVLONG:
  593. if(typefd[tt]) {
  594. regalloc(&nod, t, t);
  595. if(tt == TDOUBLE)
  596. a = ACVTSQ2SD;
  597. else
  598. a = ACVTSQ2SS;
  599. gins(a, f, &nod);
  600. gmove(&nod, t);
  601. regfree(&nod);
  602. return;
  603. }
  604. case TUVLONG:
  605. a = AMOVQ;
  606. goto ld;
  607. case TIND:
  608. a = AMOVQ;
  609. ld:
  610. regalloc(&nod, f, t);
  611. nod.type = t64? types[TVLONG]: types[TINT];
  612. gins(a, f, &nod);
  613. gmove(&nod, t);
  614. regfree(&nod);
  615. return;
  616. case TFLOAT:
  617. a = AMOVSS;
  618. goto fld;
  619. case TDOUBLE:
  620. a = AMOVSD;
  621. fld:
  622. regalloc(&nod, f, t);
  623. if(tt != TDOUBLE && tt != TFLOAT){ /* TO DO: why is this here */
  624. prtree(f, "odd tree");
  625. nod.type = t64? types[TVLONG]: types[TINT];
  626. }
  627. gins(a, f, &nod);
  628. gmove(&nod, t);
  629. regfree(&nod);
  630. return;
  631. }
  632. /*
  633. * store
  634. */
  635. if(t->op == ONAME || t->op == OINDREG ||
  636. t->op == OIND || t->op == OINDEX)
  637. switch(tt) {
  638. case TCHAR:
  639. case TUCHAR:
  640. a = AMOVB; goto st;
  641. case TSHORT:
  642. case TUSHORT:
  643. a = AMOVW; goto st;
  644. case TINT:
  645. case TUINT:
  646. case TLONG:
  647. case TULONG:
  648. a = AMOVL; goto st;
  649. case TVLONG:
  650. case TUVLONG:
  651. case TIND:
  652. a = AMOVQ; goto st;
  653. st:
  654. if(f->op == OCONST) {
  655. gins(a, f, t);
  656. return;
  657. }
  658. fst:
  659. regalloc(&nod, t, f);
  660. gmove(f, &nod);
  661. gins(a, &nod, t);
  662. regfree(&nod);
  663. return;
  664. case TFLOAT:
  665. a = AMOVSS;
  666. goto fst;
  667. case TDOUBLE:
  668. a = AMOVSD;
  669. goto fst;
  670. }
  671. /*
  672. * convert
  673. */
  674. switch(CASE(ft,tt)) {
  675. default:
  676. /*
  677. * integer to integer
  678. ********
  679. a = AGOK; break;
  680. case CASE( TCHAR, TCHAR):
  681. case CASE( TUCHAR, TCHAR):
  682. case CASE( TSHORT, TCHAR):
  683. case CASE( TUSHORT,TCHAR):
  684. case CASE( TINT, TCHAR):
  685. case CASE( TUINT, TCHAR):
  686. case CASE( TLONG, TCHAR):
  687. case CASE( TULONG, TCHAR):
  688. case CASE( TIND, TCHAR):
  689. case CASE( TCHAR, TUCHAR):
  690. case CASE( TUCHAR, TUCHAR):
  691. case CASE( TSHORT, TUCHAR):
  692. case CASE( TUSHORT,TUCHAR):
  693. case CASE( TINT, TUCHAR):
  694. case CASE( TUINT, TUCHAR):
  695. case CASE( TLONG, TUCHAR):
  696. case CASE( TULONG, TUCHAR):
  697. case CASE( TIND, TUCHAR):
  698. case CASE( TSHORT, TSHORT):
  699. case CASE( TUSHORT,TSHORT):
  700. case CASE( TINT, TSHORT):
  701. case CASE( TUINT, TSHORT):
  702. case CASE( TLONG, TSHORT):
  703. case CASE( TULONG, TSHORT):
  704. case CASE( TIND, TSHORT):
  705. case CASE( TSHORT, TUSHORT):
  706. case CASE( TUSHORT,TUSHORT):
  707. case CASE( TINT, TUSHORT):
  708. case CASE( TUINT, TUSHORT):
  709. case CASE( TLONG, TUSHORT):
  710. case CASE( TULONG, TUSHORT):
  711. case CASE( TIND, TUSHORT):
  712. case CASE( TINT, TINT):
  713. case CASE( TUINT, TINT):
  714. case CASE( TLONG, TINT):
  715. case CASE( TULONG, TINT):
  716. case CASE( TIND, TINT):
  717. case CASE( TINT, TUINT):
  718. case CASE( TUINT, TUINT):
  719. case CASE( TLONG, TUINT):
  720. case CASE( TULONG, TUINT):
  721. case CASE( TIND, TUINT):
  722. case CASE( TUINT, TIND):
  723. case CASE( TVLONG, TUINT):
  724. case CASE( TVLONG, TULONG):
  725. case CASE( TUVLONG, TUINT):
  726. case CASE( TUVLONG, TULONG):
  727. *****/
  728. a = AMOVL;
  729. break;
  730. case CASE( TVLONG, TCHAR):
  731. case CASE( TVLONG, TSHORT):
  732. case CASE( TVLONG, TINT):
  733. case CASE( TVLONG, TLONG):
  734. case CASE( TUVLONG, TCHAR):
  735. case CASE( TUVLONG, TSHORT):
  736. case CASE( TUVLONG, TINT):
  737. case CASE( TUVLONG, TLONG):
  738. case CASE( TINT, TVLONG):
  739. case CASE( TINT, TUVLONG):
  740. case CASE( TLONG, TVLONG):
  741. case CASE( TINT, TIND):
  742. case CASE( TLONG, TIND):
  743. a = AMOVLQSX;
  744. if(f->op == OCONST) {
  745. f->vconst &= (uvlong)0xffffffffU;
  746. if(f->vconst & 0x80000000)
  747. f->vconst |= (vlong)0xffffffff << 32;
  748. a = AMOVQ;
  749. }
  750. break;
  751. case CASE( TUINT, TIND):
  752. case CASE( TUINT, TVLONG):
  753. case CASE( TUINT, TUVLONG):
  754. case CASE( TULONG, TVLONG):
  755. case CASE( TULONG, TUVLONG):
  756. case CASE( TULONG, TIND):
  757. a = AMOVL; /* same effect as AMOVLQZX */
  758. if(f->op == OCONST) {
  759. f->vconst &= (uvlong)0xffffffffU;
  760. a = AMOVQ;
  761. }
  762. break;
  763. case CASE( TIND, TVLONG):
  764. case CASE( TVLONG, TVLONG):
  765. case CASE( TUVLONG, TVLONG):
  766. case CASE( TVLONG, TUVLONG):
  767. case CASE( TUVLONG, TUVLONG):
  768. case CASE( TIND, TUVLONG):
  769. case CASE( TVLONG, TIND):
  770. case CASE( TUVLONG, TIND):
  771. case CASE( TIND, TIND):
  772. a = AMOVQ;
  773. break;
  774. case CASE( TSHORT, TINT):
  775. case CASE( TSHORT, TUINT):
  776. case CASE( TSHORT, TLONG):
  777. case CASE( TSHORT, TULONG):
  778. a = AMOVWLSX;
  779. if(f->op == OCONST) {
  780. f->vconst &= 0xffff;
  781. if(f->vconst & 0x8000)
  782. f->vconst |= 0xffff0000;
  783. a = AMOVL;
  784. }
  785. break;
  786. case CASE( TSHORT, TVLONG):
  787. case CASE( TSHORT, TUVLONG):
  788. case CASE( TSHORT, TIND):
  789. a = AMOVWQSX;
  790. if(f->op == OCONST) {
  791. f->vconst &= 0xffff;
  792. if(f->vconst & 0x8000){
  793. f->vconst |= 0xffff0000;
  794. f->vconst |= (vlong)~0 << 32;
  795. }
  796. a = AMOVL;
  797. }
  798. break;
  799. case CASE( TUSHORT,TINT):
  800. case CASE( TUSHORT,TUINT):
  801. case CASE( TUSHORT,TLONG):
  802. case CASE( TUSHORT,TULONG):
  803. a = AMOVWLZX;
  804. if(f->op == OCONST) {
  805. f->vconst &= 0xffff;
  806. a = AMOVL;
  807. }
  808. break;
  809. case CASE( TUSHORT,TVLONG):
  810. case CASE( TUSHORT,TUVLONG):
  811. case CASE( TUSHORT,TIND):
  812. a = AMOVWQZX;
  813. if(f->op == OCONST) {
  814. f->vconst &= 0xffff;
  815. a = AMOVL; /* MOVL also zero-extends to 64 bits */
  816. }
  817. break;
  818. case CASE( TCHAR, TSHORT):
  819. case CASE( TCHAR, TUSHORT):
  820. case CASE( TCHAR, TINT):
  821. case CASE( TCHAR, TUINT):
  822. case CASE( TCHAR, TLONG):
  823. case CASE( TCHAR, TULONG):
  824. a = AMOVBLSX;
  825. if(f->op == OCONST) {
  826. f->vconst &= 0xff;
  827. if(f->vconst & 0x80)
  828. f->vconst |= 0xffffff00;
  829. a = AMOVL;
  830. }
  831. break;
  832. case CASE( TCHAR, TVLONG):
  833. case CASE( TCHAR, TUVLONG):
  834. case CASE( TCHAR, TIND):
  835. a = AMOVBQSX;
  836. if(f->op == OCONST) {
  837. f->vconst &= 0xff;
  838. if(f->vconst & 0x80){
  839. f->vconst |= 0xffffff00;
  840. f->vconst |= (vlong)~0 << 32;
  841. }
  842. a = AMOVQ;
  843. }
  844. break;
  845. case CASE( TUCHAR, TSHORT):
  846. case CASE( TUCHAR, TUSHORT):
  847. case CASE( TUCHAR, TINT):
  848. case CASE( TUCHAR, TUINT):
  849. case CASE( TUCHAR, TLONG):
  850. case CASE( TUCHAR, TULONG):
  851. a = AMOVBLZX;
  852. if(f->op == OCONST) {
  853. f->vconst &= 0xff;
  854. a = AMOVL;
  855. }
  856. break;
  857. case CASE( TUCHAR, TVLONG):
  858. case CASE( TUCHAR, TUVLONG):
  859. case CASE( TUCHAR, TIND):
  860. a = AMOVBQZX;
  861. if(f->op == OCONST) {
  862. f->vconst &= 0xff;
  863. a = AMOVL; /* zero-extends to 64-bits */
  864. }
  865. break;
  866. /*
  867. * float to fix
  868. */
  869. case CASE( TFLOAT, TCHAR):
  870. case CASE( TFLOAT, TUCHAR):
  871. case CASE( TFLOAT, TSHORT):
  872. case CASE( TFLOAT, TUSHORT):
  873. case CASE( TFLOAT, TINT):
  874. case CASE( TFLOAT, TUINT):
  875. case CASE( TFLOAT, TLONG):
  876. case CASE( TFLOAT, TULONG):
  877. case CASE( TFLOAT, TVLONG):
  878. case CASE( TFLOAT, TUVLONG):
  879. case CASE( TFLOAT, TIND):
  880. case CASE( TDOUBLE,TCHAR):
  881. case CASE( TDOUBLE,TUCHAR):
  882. case CASE( TDOUBLE,TSHORT):
  883. case CASE( TDOUBLE,TUSHORT):
  884. case CASE( TDOUBLE,TINT):
  885. case CASE( TDOUBLE,TUINT):
  886. case CASE( TDOUBLE,TLONG):
  887. case CASE( TDOUBLE,TULONG):
  888. case CASE( TDOUBLE,TVLONG):
  889. case CASE( TDOUBLE,TUVLONG):
  890. case CASE( TDOUBLE,TIND):
  891. regalloc(&nod, t, Z);
  892. if(ewidth[tt] == SZ_VLONG || typeu[tt] && ewidth[tt] == SZ_INT){
  893. if(ft == TFLOAT)
  894. a = ACVTTSS2SQ;
  895. else
  896. a = ACVTTSD2SQ;
  897. }else{
  898. if(ft == TFLOAT)
  899. a = ACVTTSS2SL;
  900. else
  901. a = ACVTTSD2SL;
  902. }
  903. gins(a, f, &nod);
  904. gmove(&nod, t);
  905. regfree(&nod);
  906. return;
  907. /*
  908. * ulong to float
  909. */
  910. case CASE( TUVLONG, TDOUBLE):
  911. case CASE( TUVLONG, TFLOAT):
  912. a = ACVTSQ2SS;
  913. if(tt == TDOUBLE)
  914. a = ACVTSQ2SD;
  915. regalloc(&nod, f, f);
  916. gmove(f, &nod);
  917. regalloc(&nod1, t, t);
  918. gins(ACMPQ, &nod, nodconst(0));
  919. gins(AJLT, Z, Z);
  920. p1 = p;
  921. gins(a, &nod, &nod1);
  922. gins(AJMP, Z, Z);
  923. p2 = p;
  924. patch(p1, pc);
  925. regalloc(&nod2, f, Z);
  926. regalloc(&nod3, f, Z);
  927. gmove(&nod, &nod2);
  928. gins(ASHRQ, nodconst(1), &nod2);
  929. gmove(&nod, &nod3);
  930. gins(AANDL, nodconst(1), &nod3);
  931. gins(AORQ, &nod3, &nod2);
  932. gins(a, &nod2, &nod1);
  933. gins(tt == TDOUBLE? AADDSD: AADDSS, &nod1, &nod1);
  934. regfree(&nod2);
  935. regfree(&nod3);
  936. patch(p2, pc);
  937. regfree(&nod);
  938. regfree(&nod1);
  939. return;
  940. case CASE( TULONG, TDOUBLE):
  941. case CASE( TUINT, TDOUBLE):
  942. case CASE( TULONG, TFLOAT):
  943. case CASE( TUINT, TFLOAT):
  944. a = ACVTSQ2SS;
  945. if(tt == TDOUBLE)
  946. a = ACVTSQ2SD;
  947. regalloc(&nod, f, f);
  948. gins(AMOVLQZX, f, &nod);
  949. regalloc(&nod1, t, t);
  950. gins(a, &nod, &nod1);
  951. gmove(&nod1, t);
  952. regfree(&nod);
  953. regfree(&nod1);
  954. return;
  955. /*
  956. * fix to float
  957. */
  958. case CASE( TCHAR, TFLOAT):
  959. case CASE( TUCHAR, TFLOAT):
  960. case CASE( TSHORT, TFLOAT):
  961. case CASE( TUSHORT,TFLOAT):
  962. case CASE( TINT, TFLOAT):
  963. case CASE( TLONG, TFLOAT):
  964. case CASE( TVLONG, TFLOAT):
  965. case CASE( TIND, TFLOAT):
  966. case CASE( TCHAR, TDOUBLE):
  967. case CASE( TUCHAR, TDOUBLE):
  968. case CASE( TSHORT, TDOUBLE):
  969. case CASE( TUSHORT,TDOUBLE):
  970. case CASE( TINT, TDOUBLE):
  971. case CASE( TLONG, TDOUBLE):
  972. case CASE( TVLONG, TDOUBLE):
  973. case CASE( TIND, TDOUBLE):
  974. regalloc(&nod, t, t);
  975. if(ewidth[ft] == SZ_VLONG){
  976. if(tt == TFLOAT)
  977. a = ACVTSQ2SS;
  978. else
  979. a = ACVTSQ2SD;
  980. }else{
  981. if(tt == TFLOAT)
  982. a = ACVTSL2SS;
  983. else
  984. a = ACVTSL2SD;
  985. }
  986. gins(a, f, &nod);
  987. gmove(&nod, t);
  988. regfree(&nod);
  989. return;
  990. /*
  991. * float to float
  992. */
  993. case CASE( TFLOAT, TFLOAT):
  994. a = AMOVSS;
  995. break;
  996. case CASE( TDOUBLE,TFLOAT):
  997. a = ACVTSD2SS;
  998. break;
  999. case CASE( TFLOAT, TDOUBLE):
  1000. a = ACVTSS2SD;
  1001. break;
  1002. case CASE( TDOUBLE,TDOUBLE):
  1003. a = AMOVSD;
  1004. break;
  1005. }
  1006. if(a == AMOVQ || a == AMOVSD || a == AMOVSS || a == AMOVL && ewidth[ft] == ewidth[tt]) /* TO DO: check AMOVL */
  1007. if(samaddr(f, t))
  1008. return;
  1009. gins(a, f, t);
  1010. }
  1011. void
  1012. doindex(Node *n)
  1013. {
  1014. Node nod, nod1;
  1015. long v;
  1016. if(debug['Y'])
  1017. prtree(n, "index");
  1018. if(n->left->complex >= FNX)
  1019. print("botch in doindex\n");
  1020. regalloc(&nod, &qregnode, Z);
  1021. v = constnode.vconst;
  1022. cgen(n->right, &nod);
  1023. idx.ptr = D_NONE;
  1024. if(n->left->op == OCONST)
  1025. idx.ptr = D_CONST;
  1026. else if(n->left->op == OREGISTER)
  1027. idx.ptr = n->left->reg;
  1028. else if(n->left->op != OADDR) {
  1029. reg[D_BP]++; // cant be used as a base
  1030. regalloc(&nod1, &qregnode, Z);
  1031. cgen(n->left, &nod1);
  1032. idx.ptr = nod1.reg;
  1033. regfree(&nod1);
  1034. reg[D_BP]--;
  1035. }
  1036. idx.reg = nod.reg;
  1037. regfree(&nod);
  1038. constnode.vconst = v;
  1039. }
  1040. void
  1041. gins(int a, Node *f, Node *t)
  1042. {
  1043. if(f != Z && f->op == OINDEX)
  1044. doindex(f);
  1045. if(t != Z && t->op == OINDEX)
  1046. doindex(t);
  1047. nextpc();
  1048. p->as = a;
  1049. if(f != Z)
  1050. naddr(f, &p->from);
  1051. if(t != Z)
  1052. naddr(t, &p->to);
  1053. if(debug['g'])
  1054. print("%P\n", p);
  1055. }
  1056. void
  1057. gopcode(int o, Type *ty, Node *f, Node *t)
  1058. {
  1059. int a, et;
  1060. et = TLONG;
  1061. if(ty != T)
  1062. et = ty->etype;
  1063. if(debug['M']) {
  1064. if(f != Z && f->type != T)
  1065. print("gop: %O %O[%s],", o, f->op, tnames[et]);
  1066. else
  1067. print("gop: %O Z,", o);
  1068. if(t != Z && t->type != T)
  1069. print("%O[%s]\n", t->op, tnames[t->type->etype]);
  1070. else
  1071. print("Z\n");
  1072. }
  1073. a = AGOK;
  1074. switch(o) {
  1075. case OCOM:
  1076. a = ANOTL;
  1077. if(et == TCHAR || et == TUCHAR)
  1078. a = ANOTB;
  1079. if(et == TSHORT || et == TUSHORT)
  1080. a = ANOTW;
  1081. if(et == TVLONG || et == TUVLONG || et == TIND)
  1082. a = ANOTQ;
  1083. break;
  1084. case ONEG:
  1085. a = ANEGL;
  1086. if(et == TCHAR || et == TUCHAR)
  1087. a = ANEGB;
  1088. if(et == TSHORT || et == TUSHORT)
  1089. a = ANEGW;
  1090. if(et == TVLONG || et == TUVLONG || et == TIND)
  1091. a = ANEGQ;
  1092. break;
  1093. case OADDR:
  1094. a = ALEAQ;
  1095. break;
  1096. case OASADD:
  1097. case OADD:
  1098. a = AADDL;
  1099. if(et == TCHAR || et == TUCHAR)
  1100. a = AADDB;
  1101. if(et == TSHORT || et == TUSHORT)
  1102. a = AADDW;
  1103. if(et == TVLONG || et == TUVLONG || et == TIND)
  1104. a = AADDQ;
  1105. if(et == TFLOAT)
  1106. a = AADDSS;
  1107. if(et == TDOUBLE)
  1108. a = AADDSD;
  1109. break;
  1110. case OASSUB:
  1111. case OSUB:
  1112. a = ASUBL;
  1113. if(et == TCHAR || et == TUCHAR)
  1114. a = ASUBB;
  1115. if(et == TSHORT || et == TUSHORT)
  1116. a = ASUBW;
  1117. if(et == TVLONG || et == TUVLONG || et == TIND)
  1118. a = ASUBQ;
  1119. if(et == TFLOAT)
  1120. a = ASUBSS;
  1121. if(et == TDOUBLE)
  1122. a = ASUBSD;
  1123. break;
  1124. case OASOR:
  1125. case OOR:
  1126. a = AORL;
  1127. if(et == TCHAR || et == TUCHAR)
  1128. a = AORB;
  1129. if(et == TSHORT || et == TUSHORT)
  1130. a = AORW;
  1131. if(et == TVLONG || et == TUVLONG || et == TIND)
  1132. a = AORQ;
  1133. break;
  1134. case OASAND:
  1135. case OAND:
  1136. a = AANDL;
  1137. if(et == TCHAR || et == TUCHAR)
  1138. a = AANDB;
  1139. if(et == TSHORT || et == TUSHORT)
  1140. a = AANDW;
  1141. if(et == TVLONG || et == TUVLONG || et == TIND)
  1142. a = AANDQ;
  1143. break;
  1144. case OASXOR:
  1145. case OXOR:
  1146. a = AXORL;
  1147. if(et == TCHAR || et == TUCHAR)
  1148. a = AXORB;
  1149. if(et == TSHORT || et == TUSHORT)
  1150. a = AXORW;
  1151. if(et == TVLONG || et == TUVLONG || et == TIND)
  1152. a = AXORQ;
  1153. break;
  1154. case OASLSHR:
  1155. case OLSHR:
  1156. a = ASHRL;
  1157. if(et == TCHAR || et == TUCHAR)
  1158. a = ASHRB;
  1159. if(et == TSHORT || et == TUSHORT)
  1160. a = ASHRW;
  1161. if(et == TVLONG || et == TUVLONG || et == TIND)
  1162. a = ASHRQ;
  1163. break;
  1164. case OASASHR:
  1165. case OASHR:
  1166. a = ASARL;
  1167. if(et == TCHAR || et == TUCHAR)
  1168. a = ASARB;
  1169. if(et == TSHORT || et == TUSHORT)
  1170. a = ASARW;
  1171. if(et == TVLONG || et == TUVLONG || et == TIND)
  1172. a = ASARQ;
  1173. break;
  1174. case OASASHL:
  1175. case OASHL:
  1176. a = ASALL;
  1177. if(et == TCHAR || et == TUCHAR)
  1178. a = ASALB;
  1179. if(et == TSHORT || et == TUSHORT)
  1180. a = ASALW;
  1181. if(et == TVLONG || et == TUVLONG || et == TIND)
  1182. a = ASALQ;
  1183. break;
  1184. case OFUNC:
  1185. a = ACALL;
  1186. break;
  1187. case OASMUL:
  1188. case OMUL:
  1189. if(f->op == OREGISTER && t != Z && isreg(t, D_AX) && reg[D_DX] == 0)
  1190. t = Z;
  1191. a = AIMULL;
  1192. if(et == TVLONG || et == TUVLONG || et == TIND)
  1193. a = AIMULQ;
  1194. if(et == TFLOAT)
  1195. a = AMULSS;
  1196. if(et == TDOUBLE)
  1197. a = AMULSD;
  1198. break;
  1199. case OASMOD:
  1200. case OMOD:
  1201. case OASDIV:
  1202. case ODIV:
  1203. a = AIDIVL;
  1204. if(et == TVLONG || et == TUVLONG || et == TIND)
  1205. a = AIDIVQ;
  1206. if(et == TFLOAT)
  1207. a = ADIVSS;
  1208. if(et == TDOUBLE)
  1209. a = ADIVSD;
  1210. break;
  1211. case OASLMUL:
  1212. case OLMUL:
  1213. a = AMULL;
  1214. if(et == TVLONG || et == TUVLONG || et == TIND)
  1215. a = AMULQ;
  1216. break;
  1217. case OASLMOD:
  1218. case OLMOD:
  1219. case OASLDIV:
  1220. case OLDIV:
  1221. a = ADIVL;
  1222. if(et == TVLONG || et == TUVLONG || et == TIND)
  1223. a = ADIVQ;
  1224. break;
  1225. case OEQ:
  1226. case ONE:
  1227. case OLT:
  1228. case OLE:
  1229. case OGE:
  1230. case OGT:
  1231. case OLO:
  1232. case OLS:
  1233. case OHS:
  1234. case OHI:
  1235. a = ACMPL;
  1236. if(et == TCHAR || et == TUCHAR)
  1237. a = ACMPB;
  1238. if(et == TSHORT || et == TUSHORT)
  1239. a = ACMPW;
  1240. if(et == TVLONG || et == TUVLONG || et == TIND)
  1241. a = ACMPQ;
  1242. if(et == TFLOAT)
  1243. a = AUCOMISS;
  1244. if(et == TDOUBLE)
  1245. a = AUCOMISD;
  1246. gins(a, f, t);
  1247. switch(o) {
  1248. case OEQ: a = AJEQ; break;
  1249. case ONE: a = AJNE; break;
  1250. case OLT: a = AJLT; break;
  1251. case OLE: a = AJLE; break;
  1252. case OGE: a = AJGE; break;
  1253. case OGT: a = AJGT; break;
  1254. case OLO: a = AJCS; break;
  1255. case OLS: a = AJLS; break;
  1256. case OHS: a = AJCC; break;
  1257. case OHI: a = AJHI; break;
  1258. }
  1259. gins(a, Z, Z);
  1260. return;
  1261. }
  1262. if(a == AGOK)
  1263. diag(Z, "bad in gopcode %O", o);
  1264. gins(a, f, t);
  1265. }
  1266. int
  1267. samaddr(Node *f, Node *t)
  1268. {
  1269. return f->op == OREGISTER && t->op == OREGISTER && f->reg == t->reg;
  1270. }
  1271. void
  1272. gbranch(int o)
  1273. {
  1274. int a;
  1275. a = AGOK;
  1276. switch(o) {
  1277. case ORETURN:
  1278. a = ARET;
  1279. break;
  1280. case OGOTO:
  1281. a = AJMP;
  1282. break;
  1283. }
  1284. nextpc();
  1285. if(a == AGOK) {
  1286. diag(Z, "bad in gbranch %O", o);
  1287. nextpc();
  1288. }
  1289. p->as = a;
  1290. }
  1291. void
  1292. patch(Prog *op, long pc)
  1293. {
  1294. op->to.offset = pc;
  1295. op->to.type = D_BRANCH;
  1296. }
  1297. void
  1298. gpseudo(int a, Sym *s, Node *n)
  1299. {
  1300. nextpc();
  1301. p->as = a;
  1302. p->from.type = D_EXTERN;
  1303. p->from.sym = s;
  1304. p->from.scale = (profileflg ? 0 : NOPROF);
  1305. if(s->class == CSTATIC)
  1306. p->from.type = D_STATIC;
  1307. naddr(n, &p->to);
  1308. if(a == ADATA || a == AGLOBL)
  1309. pc--;
  1310. }
  1311. int
  1312. sconst(Node *n)
  1313. {
  1314. long v;
  1315. if(n->op == OCONST && !typefd[n->type->etype]) {
  1316. v = n->vconst;
  1317. if(v >= -32766L && v < 32766L)
  1318. return 1;
  1319. }
  1320. return 0;
  1321. }
  1322. long
  1323. exreg(Type *t)
  1324. {
  1325. long o;
  1326. if(typechlpv[t->etype]) {
  1327. if(exregoffset <= REGEXT-4)
  1328. return 0;
  1329. o = exregoffset;
  1330. exregoffset--;
  1331. return o;
  1332. }
  1333. return 0;
  1334. }
  1335. schar ewidth[NTYPE] =
  1336. {
  1337. -1, /*[TXXX]*/
  1338. SZ_CHAR, /*[TCHAR]*/
  1339. SZ_CHAR, /*[TUCHAR]*/
  1340. SZ_SHORT, /*[TSHORT]*/
  1341. SZ_SHORT, /*[TUSHORT]*/
  1342. SZ_INT, /*[TINT]*/
  1343. SZ_INT, /*[TUINT]*/
  1344. SZ_LONG, /*[TLONG]*/
  1345. SZ_LONG, /*[TULONG]*/
  1346. SZ_VLONG, /*[TVLONG]*/
  1347. SZ_VLONG, /*[TUVLONG]*/
  1348. SZ_FLOAT, /*[TFLOAT]*/
  1349. SZ_DOUBLE, /*[TDOUBLE]*/
  1350. SZ_IND, /*[TIND]*/
  1351. 0, /*[TFUNC]*/
  1352. -1, /*[TARRAY]*/
  1353. 0, /*[TVOID]*/
  1354. -1, /*[TSTRUCT]*/
  1355. -1, /*[TUNION]*/
  1356. SZ_INT, /*[TENUM]*/
  1357. };
  1358. long ncast[NTYPE] =
  1359. {
  1360. 0, /*[TXXX]*/
  1361. BCHAR|BUCHAR, /*[TCHAR]*/
  1362. BCHAR|BUCHAR, /*[TUCHAR]*/
  1363. BSHORT|BUSHORT, /*[TSHORT]*/
  1364. BSHORT|BUSHORT, /*[TUSHORT]*/
  1365. BINT|BUINT|BLONG|BULONG, /*[TINT]*/
  1366. BINT|BUINT|BLONG|BULONG, /*[TUINT]*/
  1367. BINT|BUINT|BLONG|BULONG, /*[TLONG]*/
  1368. BINT|BUINT|BLONG|BULONG, /*[TULONG]*/
  1369. BVLONG|BUVLONG|BIND, /*[TVLONG]*/
  1370. BVLONG|BUVLONG|BIND, /*[TUVLONG]*/
  1371. BFLOAT, /*[TFLOAT]*/
  1372. BDOUBLE, /*[TDOUBLE]*/
  1373. BVLONG|BUVLONG|BIND, /*[TIND]*/
  1374. 0, /*[TFUNC]*/
  1375. 0, /*[TARRAY]*/
  1376. 0, /*[TVOID]*/
  1377. BSTRUCT, /*[TSTRUCT]*/
  1378. BUNION, /*[TUNION]*/
  1379. 0, /*[TENUM]*/
  1380. };