github.com/ader1990/go@v0.0.0-20140630135419-8c24447fa791/src/cmd/8g/gsubr.c (about)

     1  // Derived from Inferno utils/8c/txt.c
     2  // http://code.google.com/p/inferno-os/source/browse/utils/8c/txt.c
     3  //
     4  //	Copyright © 1994-1999 Lucent Technologies Inc.  All rights reserved.
     5  //	Portions Copyright © 1995-1997 C H Forsyth (forsyth@terzarima.net)
     6  //	Portions Copyright © 1997-1999 Vita Nuova Limited
     7  //	Portions Copyright © 2000-2007 Vita Nuova Holdings Limited (www.vitanuova.com)
     8  //	Portions Copyright © 2004,2006 Bruce Ellis
     9  //	Portions Copyright © 2005-2007 C H Forsyth (forsyth@terzarima.net)
    10  //	Revisions Copyright © 2000-2007 Lucent Technologies Inc. and others
    11  //	Portions Copyright © 2009 The Go Authors.  All rights reserved.
    12  //
    13  // Permission is hereby granted, free of charge, to any person obtaining a copy
    14  // of this software and associated documentation files (the "Software"), to deal
    15  // in the Software without restriction, including without limitation the rights
    16  // to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
    17  // copies of the Software, and to permit persons to whom the Software is
    18  // furnished to do so, subject to the following conditions:
    19  //
    20  // The above copyright notice and this permission notice shall be included in
    21  // all copies or substantial portions of the Software.
    22  //
    23  // THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
    24  // IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
    25  // FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.  IN NO EVENT SHALL THE
    26  // AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
    27  // LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
    28  // OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
    29  // THE SOFTWARE.
    30  
    31  #include <u.h>
    32  #include <libc.h>
    33  #include "gg.h"
    34  #include "../../pkg/runtime/funcdata.h"
    35  
    36  // TODO(rsc): Can make this bigger if we move
    37  // the text segment up higher in 8l for all GOOS.
    38  // At the same time, can raise StackBig in ../../pkg/runtime/stack.h.
    39  uint32 unmappedzero = 4096;
    40  
    41  #define	CASE(a,b)	(((a)<<16)|((b)<<0))
    42  
    43  void
    44  clearp(Prog *p)
    45  {
    46  	p->as = AEND;
    47  	p->from.type = D_NONE;
    48  	p->from.index = D_NONE;
    49  	p->to.type = D_NONE;
    50  	p->to.index = D_NONE;
    51  	p->pc = pcloc;
    52  	pcloc++;
    53  }
    54  
    55  static int ddumped;
    56  static Prog *dfirst;
    57  static Prog *dpc;
    58  
    59  /*
    60   * generate and return proc with p->as = as,
    61   * linked into program.  pc is next instruction.
    62   */
    63  Prog*
    64  prog(int as)
    65  {
    66  	Prog *p;
    67  
    68  	if(as == ADATA || as == AGLOBL) {
    69  		if(ddumped)
    70  			fatal("already dumped data");
    71  		if(dpc == nil) {
    72  			dpc = mal(sizeof(*dpc));
    73  			dfirst = dpc;
    74  		}
    75  		p = dpc;
    76  		dpc = mal(sizeof(*dpc));
    77  		p->link = dpc;
    78  	} else {
    79  		p = pc;
    80  		pc = mal(sizeof(*pc));
    81  		clearp(pc);
    82  		p->link = pc;
    83  	}
    84  
    85  	if(lineno == 0) {
    86  		if(debug['K'])
    87  			warn("prog: line 0");
    88  	}
    89  
    90  	p->as = as;
    91  	p->lineno = lineno;
    92  	return p;
    93  }
    94  
    95  void
    96  dumpdata(void)
    97  {
    98  	ddumped = 1;
    99  	if(dfirst == nil)
   100  		return;
   101  	newplist();
   102  	*pc = *dfirst;
   103  	pc = dpc;
   104  	clearp(pc);
   105  }
   106  
   107  /*
   108   * generate a branch.
   109   * t is ignored.
   110   * likely values are for branch prediction:
   111   *	-1 unlikely
   112   *	0 no opinion
   113   *	+1 likely
   114   */
   115  Prog*
   116  gbranch(int as, Type *t, int likely)
   117  {
   118  	Prog *p;
   119  
   120  	USED(t);
   121  	p = prog(as);
   122  	p->to.type = D_BRANCH;
   123  	p->to.u.branch = P;
   124  	if(likely != 0) {
   125  		p->from.type = D_CONST;
   126  		p->from.offset = likely > 0;
   127  	}
   128  	return p;
   129  }
   130  
   131  /*
   132   * patch previous branch to jump to to.
   133   */
   134  void
   135  patch(Prog *p, Prog *to)
   136  {
   137  	if(p->to.type != D_BRANCH)
   138  		fatal("patch: not a branch");
   139  	p->to.u.branch = to;
   140  	p->to.offset = to->pc;
   141  }
   142  
   143  Prog*
   144  unpatch(Prog *p)
   145  {
   146  	Prog *q;
   147  
   148  	if(p->to.type != D_BRANCH)
   149  		fatal("unpatch: not a branch");
   150  	q = p->to.u.branch;
   151  	p->to.u.branch = P;
   152  	p->to.offset = 0;
   153  	return q;
   154  }
   155  
   156  /*
   157   * start a new Prog list.
   158   */
   159  Plist*
   160  newplist(void)
   161  {
   162  	Plist *pl;
   163  
   164  	pl = linknewplist(ctxt);
   165  	
   166  	pc = mal(sizeof(*pc));
   167  	clearp(pc);
   168  	pl->firstpc = pc;
   169  
   170  	return pl;
   171  }
   172  
   173  void
   174  gused(Node *n)
   175  {
   176  	gins(ANOP, n, N);	// used
   177  }
   178  
   179  Prog*
   180  gjmp(Prog *to)
   181  {
   182  	Prog *p;
   183  
   184  	p = gbranch(AJMP, T, 0);
   185  	if(to != P)
   186  		patch(p, to);
   187  	return p;
   188  }
   189  
   190  void
   191  ggloblnod(Node *nam)
   192  {
   193  	Prog *p;
   194  
   195  	p = gins(AGLOBL, nam, N);
   196  	p->lineno = nam->lineno;
   197  	p->from.sym->gotype = linksym(ngotype(nam));
   198  	p->to.sym = nil;
   199  	p->to.type = D_CONST;
   200  	p->to.offset = nam->type->width;
   201  	if(nam->readonly)
   202  		p->from.scale = RODATA;
   203  	if(nam->type != T && !haspointers(nam->type))
   204  		p->from.scale |= NOPTR;
   205  }
   206  
   207  void
   208  gargsize(int32 size)
   209  {
   210  	Node n1, n2;
   211  	
   212  	nodconst(&n1, types[TINT32], PCDATA_ArgSize);
   213  	nodconst(&n2, types[TINT32], size);
   214  	gins(APCDATA, &n1, &n2);
   215  }
   216  
   217  void
   218  ggloblsym(Sym *s, int32 width, int dupok, int rodata)
   219  {
   220  	Prog *p;
   221  
   222  	p = gins(AGLOBL, N, N);
   223  	p->from.type = D_EXTERN;
   224  	p->from.index = D_NONE;
   225  	p->from.sym = linksym(s);
   226  	p->to.type = D_CONST;
   227  	p->to.index = D_NONE;
   228  	p->to.offset = width;
   229  	if(dupok)
   230  		p->from.scale |= DUPOK;
   231  	if(rodata)
   232  		p->from.scale |= RODATA;
   233  }
   234  
   235  void
   236  gtrack(Sym *s)
   237  {
   238  	Prog *p;
   239  	
   240  	p = gins(AUSEFIELD, N, N);
   241  	p->from.type = D_EXTERN;
   242  	p->from.index = D_NONE;
   243  	p->from.sym = linksym(s);
   244  }
   245  
   246  int
   247  isfat(Type *t)
   248  {
   249  	if(t != T)
   250  	switch(t->etype) {
   251  	case TSTRUCT:
   252  	case TARRAY:
   253  	case TSTRING:
   254  	case TINTER:	// maybe remove later
   255  		return 1;
   256  	}
   257  	return 0;
   258  }
   259  
   260  /*
   261   * naddr of func generates code for address of func.
   262   * if using opcode that can take address implicitly,
   263   * call afunclit to fix up the argument.
   264   */
   265  void
   266  afunclit(Addr *a, Node *n)
   267  {
   268  	if(a->type == D_ADDR && a->index == D_EXTERN) {
   269  		a->type = D_EXTERN;
   270  		a->index = D_NONE;
   271  		a->sym = linksym(n->sym);
   272  	}
   273  }
   274  
   275  /*
   276   * return Axxx for Oxxx on type t.
   277   */
   278  int
   279  optoas(int op, Type *t)
   280  {
   281  	int a;
   282  
   283  	if(t == T)
   284  		fatal("optoas: t is nil");
   285  
   286  	a = AGOK;
   287  	switch(CASE(op, simtype[t->etype])) {
   288  	default:
   289  		fatal("optoas: no entry %O-%T", op, t);
   290  		break;
   291  
   292  	case CASE(OADDR, TPTR32):
   293  		a = ALEAL;
   294  		break;
   295  
   296  	case CASE(OEQ, TBOOL):
   297  	case CASE(OEQ, TINT8):
   298  	case CASE(OEQ, TUINT8):
   299  	case CASE(OEQ, TINT16):
   300  	case CASE(OEQ, TUINT16):
   301  	case CASE(OEQ, TINT32):
   302  	case CASE(OEQ, TUINT32):
   303  	case CASE(OEQ, TINT64):
   304  	case CASE(OEQ, TUINT64):
   305  	case CASE(OEQ, TPTR32):
   306  	case CASE(OEQ, TPTR64):
   307  	case CASE(OEQ, TFLOAT32):
   308  	case CASE(OEQ, TFLOAT64):
   309  		a = AJEQ;
   310  		break;
   311  
   312  	case CASE(ONE, TBOOL):
   313  	case CASE(ONE, TINT8):
   314  	case CASE(ONE, TUINT8):
   315  	case CASE(ONE, TINT16):
   316  	case CASE(ONE, TUINT16):
   317  	case CASE(ONE, TINT32):
   318  	case CASE(ONE, TUINT32):
   319  	case CASE(ONE, TINT64):
   320  	case CASE(ONE, TUINT64):
   321  	case CASE(ONE, TPTR32):
   322  	case CASE(ONE, TPTR64):
   323  	case CASE(ONE, TFLOAT32):
   324  	case CASE(ONE, TFLOAT64):
   325  		a = AJNE;
   326  		break;
   327  
   328  	case CASE(OLT, TINT8):
   329  	case CASE(OLT, TINT16):
   330  	case CASE(OLT, TINT32):
   331  	case CASE(OLT, TINT64):
   332  		a = AJLT;
   333  		break;
   334  
   335  	case CASE(OLT, TUINT8):
   336  	case CASE(OLT, TUINT16):
   337  	case CASE(OLT, TUINT32):
   338  	case CASE(OLT, TUINT64):
   339  		a = AJCS;
   340  		break;
   341  
   342  	case CASE(OLE, TINT8):
   343  	case CASE(OLE, TINT16):
   344  	case CASE(OLE, TINT32):
   345  	case CASE(OLE, TINT64):
   346  		a = AJLE;
   347  		break;
   348  
   349  	case CASE(OLE, TUINT8):
   350  	case CASE(OLE, TUINT16):
   351  	case CASE(OLE, TUINT32):
   352  	case CASE(OLE, TUINT64):
   353  		a = AJLS;
   354  		break;
   355  
   356  	case CASE(OGT, TINT8):
   357  	case CASE(OGT, TINT16):
   358  	case CASE(OGT, TINT32):
   359  	case CASE(OGT, TINT64):
   360  		a = AJGT;
   361  		break;
   362  
   363  	case CASE(OGT, TUINT8):
   364  	case CASE(OGT, TUINT16):
   365  	case CASE(OGT, TUINT32):
   366  	case CASE(OGT, TUINT64):
   367  	case CASE(OLT, TFLOAT32):
   368  	case CASE(OLT, TFLOAT64):
   369  		a = AJHI;
   370  		break;
   371  
   372  	case CASE(OGE, TINT8):
   373  	case CASE(OGE, TINT16):
   374  	case CASE(OGE, TINT32):
   375  	case CASE(OGE, TINT64):
   376  		a = AJGE;
   377  		break;
   378  
   379  	case CASE(OGE, TUINT8):
   380  	case CASE(OGE, TUINT16):
   381  	case CASE(OGE, TUINT32):
   382  	case CASE(OGE, TUINT64):
   383  	case CASE(OLE, TFLOAT32):
   384  	case CASE(OLE, TFLOAT64):
   385  		a = AJCC;
   386  		break;
   387  
   388  	case CASE(OCMP, TBOOL):
   389  	case CASE(OCMP, TINT8):
   390  	case CASE(OCMP, TUINT8):
   391  		a = ACMPB;
   392  		break;
   393  
   394  	case CASE(OCMP, TINT16):
   395  	case CASE(OCMP, TUINT16):
   396  		a = ACMPW;
   397  		break;
   398  
   399  	case CASE(OCMP, TINT32):
   400  	case CASE(OCMP, TUINT32):
   401  	case CASE(OCMP, TPTR32):
   402  		a = ACMPL;
   403  		break;
   404  
   405  	case CASE(OAS, TBOOL):
   406  	case CASE(OAS, TINT8):
   407  	case CASE(OAS, TUINT8):
   408  		a = AMOVB;
   409  		break;
   410  
   411  	case CASE(OAS, TINT16):
   412  	case CASE(OAS, TUINT16):
   413  		a = AMOVW;
   414  		break;
   415  
   416  	case CASE(OAS, TINT32):
   417  	case CASE(OAS, TUINT32):
   418  	case CASE(OAS, TPTR32):
   419  		a = AMOVL;
   420  		break;
   421  
   422  	case CASE(OADD, TINT8):
   423  	case CASE(OADD, TUINT8):
   424  		a = AADDB;
   425  		break;
   426  
   427  	case CASE(OADD, TINT16):
   428  	case CASE(OADD, TUINT16):
   429  		a = AADDW;
   430  		break;
   431  
   432  	case CASE(OADD, TINT32):
   433  	case CASE(OADD, TUINT32):
   434  	case CASE(OADD, TPTR32):
   435  	case CASE(OADDPTR, TPTR32):
   436  		a = AADDL;
   437  		break;
   438  
   439  	case CASE(OSUB, TINT8):
   440  	case CASE(OSUB, TUINT8):
   441  		a = ASUBB;
   442  		break;
   443  
   444  	case CASE(OSUB, TINT16):
   445  	case CASE(OSUB, TUINT16):
   446  		a = ASUBW;
   447  		break;
   448  
   449  	case CASE(OSUB, TINT32):
   450  	case CASE(OSUB, TUINT32):
   451  	case CASE(OSUB, TPTR32):
   452  		a = ASUBL;
   453  		break;
   454  
   455  	case CASE(OINC, TINT8):
   456  	case CASE(OINC, TUINT8):
   457  		a = AINCB;
   458  		break;
   459  
   460  	case CASE(OINC, TINT16):
   461  	case CASE(OINC, TUINT16):
   462  		a = AINCW;
   463  		break;
   464  
   465  	case CASE(OINC, TINT32):
   466  	case CASE(OINC, TUINT32):
   467  	case CASE(OINC, TPTR32):
   468  		a = AINCL;
   469  		break;
   470  
   471  	case CASE(ODEC, TINT8):
   472  	case CASE(ODEC, TUINT8):
   473  		a = ADECB;
   474  		break;
   475  
   476  	case CASE(ODEC, TINT16):
   477  	case CASE(ODEC, TUINT16):
   478  		a = ADECW;
   479  		break;
   480  
   481  	case CASE(ODEC, TINT32):
   482  	case CASE(ODEC, TUINT32):
   483  	case CASE(ODEC, TPTR32):
   484  		a = ADECL;
   485  		break;
   486  
   487  	case CASE(OCOM, TINT8):
   488  	case CASE(OCOM, TUINT8):
   489  		a = ANOTB;
   490  		break;
   491  
   492  	case CASE(OCOM, TINT16):
   493  	case CASE(OCOM, TUINT16):
   494  		a = ANOTW;
   495  		break;
   496  
   497  	case CASE(OCOM, TINT32):
   498  	case CASE(OCOM, TUINT32):
   499  	case CASE(OCOM, TPTR32):
   500  		a = ANOTL;
   501  		break;
   502  
   503  	case CASE(OMINUS, TINT8):
   504  	case CASE(OMINUS, TUINT8):
   505  		a = ANEGB;
   506  		break;
   507  
   508  	case CASE(OMINUS, TINT16):
   509  	case CASE(OMINUS, TUINT16):
   510  		a = ANEGW;
   511  		break;
   512  
   513  	case CASE(OMINUS, TINT32):
   514  	case CASE(OMINUS, TUINT32):
   515  	case CASE(OMINUS, TPTR32):
   516  		a = ANEGL;
   517  		break;
   518  
   519  	case CASE(OAND, TINT8):
   520  	case CASE(OAND, TUINT8):
   521  		a = AANDB;
   522  		break;
   523  
   524  	case CASE(OAND, TINT16):
   525  	case CASE(OAND, TUINT16):
   526  		a = AANDW;
   527  		break;
   528  
   529  	case CASE(OAND, TINT32):
   530  	case CASE(OAND, TUINT32):
   531  	case CASE(OAND, TPTR32):
   532  		a = AANDL;
   533  		break;
   534  
   535  	case CASE(OOR, TINT8):
   536  	case CASE(OOR, TUINT8):
   537  		a = AORB;
   538  		break;
   539  
   540  	case CASE(OOR, TINT16):
   541  	case CASE(OOR, TUINT16):
   542  		a = AORW;
   543  		break;
   544  
   545  	case CASE(OOR, TINT32):
   546  	case CASE(OOR, TUINT32):
   547  	case CASE(OOR, TPTR32):
   548  		a = AORL;
   549  		break;
   550  
   551  	case CASE(OXOR, TINT8):
   552  	case CASE(OXOR, TUINT8):
   553  		a = AXORB;
   554  		break;
   555  
   556  	case CASE(OXOR, TINT16):
   557  	case CASE(OXOR, TUINT16):
   558  		a = AXORW;
   559  		break;
   560  
   561  	case CASE(OXOR, TINT32):
   562  	case CASE(OXOR, TUINT32):
   563  	case CASE(OXOR, TPTR32):
   564  		a = AXORL;
   565  		break;
   566  
   567  	case CASE(OLROT, TINT8):
   568  	case CASE(OLROT, TUINT8):
   569  		a = AROLB;
   570  		break;
   571  
   572  	case CASE(OLROT, TINT16):
   573  	case CASE(OLROT, TUINT16):
   574  		a = AROLW;
   575  		break;
   576  
   577  	case CASE(OLROT, TINT32):
   578  	case CASE(OLROT, TUINT32):
   579  	case CASE(OLROT, TPTR32):
   580  		a = AROLL;
   581  		break;
   582  
   583  	case CASE(OLSH, TINT8):
   584  	case CASE(OLSH, TUINT8):
   585  		a = ASHLB;
   586  		break;
   587  
   588  	case CASE(OLSH, TINT16):
   589  	case CASE(OLSH, TUINT16):
   590  		a = ASHLW;
   591  		break;
   592  
   593  	case CASE(OLSH, TINT32):
   594  	case CASE(OLSH, TUINT32):
   595  	case CASE(OLSH, TPTR32):
   596  		a = ASHLL;
   597  		break;
   598  
   599  	case CASE(ORSH, TUINT8):
   600  		a = ASHRB;
   601  		break;
   602  
   603  	case CASE(ORSH, TUINT16):
   604  		a = ASHRW;
   605  		break;
   606  
   607  	case CASE(ORSH, TUINT32):
   608  	case CASE(ORSH, TPTR32):
   609  		a = ASHRL;
   610  		break;
   611  
   612  	case CASE(ORSH, TINT8):
   613  		a = ASARB;
   614  		break;
   615  
   616  	case CASE(ORSH, TINT16):
   617  		a = ASARW;
   618  		break;
   619  
   620  	case CASE(ORSH, TINT32):
   621  		a = ASARL;
   622  		break;
   623  
   624  	case CASE(OHMUL, TINT8):
   625  	case CASE(OMUL, TINT8):
   626  	case CASE(OMUL, TUINT8):
   627  		a = AIMULB;
   628  		break;
   629  
   630  	case CASE(OHMUL, TINT16):
   631  	case CASE(OMUL, TINT16):
   632  	case CASE(OMUL, TUINT16):
   633  		a = AIMULW;
   634  		break;
   635  
   636  	case CASE(OHMUL, TINT32):
   637  	case CASE(OMUL, TINT32):
   638  	case CASE(OMUL, TUINT32):
   639  	case CASE(OMUL, TPTR32):
   640  		a = AIMULL;
   641  		break;
   642  
   643  	case CASE(OHMUL, TUINT8):
   644  		a = AMULB;
   645  		break;
   646  
   647  	case CASE(OHMUL, TUINT16):
   648  		a = AMULW;
   649  		break;
   650  
   651  	case CASE(OHMUL, TUINT32):
   652  	case CASE(OHMUL, TPTR32):
   653  		a = AMULL;
   654  		break;
   655  
   656  	case CASE(ODIV, TINT8):
   657  	case CASE(OMOD, TINT8):
   658  		a = AIDIVB;
   659  		break;
   660  
   661  	case CASE(ODIV, TUINT8):
   662  	case CASE(OMOD, TUINT8):
   663  		a = ADIVB;
   664  		break;
   665  
   666  	case CASE(ODIV, TINT16):
   667  	case CASE(OMOD, TINT16):
   668  		a = AIDIVW;
   669  		break;
   670  
   671  	case CASE(ODIV, TUINT16):
   672  	case CASE(OMOD, TUINT16):
   673  		a = ADIVW;
   674  		break;
   675  
   676  	case CASE(ODIV, TINT32):
   677  	case CASE(OMOD, TINT32):
   678  		a = AIDIVL;
   679  		break;
   680  
   681  	case CASE(ODIV, TUINT32):
   682  	case CASE(ODIV, TPTR32):
   683  	case CASE(OMOD, TUINT32):
   684  	case CASE(OMOD, TPTR32):
   685  		a = ADIVL;
   686  		break;
   687  
   688  	case CASE(OEXTEND, TINT16):
   689  		a = ACWD;
   690  		break;
   691  
   692  	case CASE(OEXTEND, TINT32):
   693  		a = ACDQ;
   694  		break;
   695  	}
   696  	return a;
   697  }
   698  
   699  #define FCASE(a, b, c)  (((a)<<16)|((b)<<8)|(c))
   700  int
   701  foptoas(int op, Type *t, int flg)
   702  {
   703  	int et, a;
   704  
   705  	a = AGOK;
   706  	et = simtype[t->etype];
   707  
   708  	if(use_sse)
   709  		goto sse;
   710  
   711  	// If we need Fpop, it means we're working on
   712  	// two different floating-point registers, not memory.
   713  	// There the instruction only has a float64 form.
   714  	if(flg & Fpop)
   715  		et = TFLOAT64;
   716  
   717  	// clear Frev if unneeded
   718  	switch(op) {
   719  	case OADD:
   720  	case OMUL:
   721  		flg &= ~Frev;
   722  		break;
   723  	}
   724  
   725  	switch(FCASE(op, et, flg)) {
   726  	case FCASE(OADD, TFLOAT32, 0):
   727  		return AFADDF;
   728  	case FCASE(OADD, TFLOAT64, 0):
   729  		return AFADDD;
   730  	case FCASE(OADD, TFLOAT64, Fpop):
   731  		return AFADDDP;
   732  
   733  	case FCASE(OSUB, TFLOAT32, 0):
   734  		return AFSUBF;
   735  	case FCASE(OSUB, TFLOAT32, Frev):
   736  		return AFSUBRF;
   737  
   738  	case FCASE(OSUB, TFLOAT64, 0):
   739  		return AFSUBD;
   740  	case FCASE(OSUB, TFLOAT64, Frev):
   741  		return AFSUBRD;
   742  	case FCASE(OSUB, TFLOAT64, Fpop):
   743  		return AFSUBDP;
   744  	case FCASE(OSUB, TFLOAT64, Fpop|Frev):
   745  		return AFSUBRDP;
   746  
   747  	case FCASE(OMUL, TFLOAT32, 0):
   748  		return AFMULF;
   749  	case FCASE(OMUL, TFLOAT64, 0):
   750  		return AFMULD;
   751  	case FCASE(OMUL, TFLOAT64, Fpop):
   752  		return AFMULDP;
   753  
   754  	case FCASE(ODIV, TFLOAT32, 0):
   755  		return AFDIVF;
   756  	case FCASE(ODIV, TFLOAT32, Frev):
   757  		return AFDIVRF;
   758  
   759  	case FCASE(ODIV, TFLOAT64, 0):
   760  		return AFDIVD;
   761  	case FCASE(ODIV, TFLOAT64, Frev):
   762  		return AFDIVRD;
   763  	case FCASE(ODIV, TFLOAT64, Fpop):
   764  		return AFDIVDP;
   765  	case FCASE(ODIV, TFLOAT64, Fpop|Frev):
   766  		return AFDIVRDP;
   767  
   768  	case FCASE(OCMP, TFLOAT32, 0):
   769  		return AFCOMF;
   770  	case FCASE(OCMP, TFLOAT32, Fpop):
   771  		return AFCOMFP;
   772  	case FCASE(OCMP, TFLOAT64, 0):
   773  		return AFCOMD;
   774  	case FCASE(OCMP, TFLOAT64, Fpop):
   775  		return AFCOMDP;
   776  	case FCASE(OCMP, TFLOAT64, Fpop2):
   777  		return AFCOMDPP;
   778  	
   779  	case FCASE(OMINUS, TFLOAT32, 0):
   780  		return AFCHS;
   781  	case FCASE(OMINUS, TFLOAT64, 0):
   782  		return AFCHS;
   783  	}
   784  
   785  	fatal("foptoas %O %T %#x", op, t, flg);
   786  	return 0;
   787  
   788  sse:
   789  	switch(CASE(op, et)) {
   790  	default:
   791  		fatal("foptoas-sse: no entry %O-%T", op, t);
   792  		break;
   793  
   794  	case CASE(OCMP, TFLOAT32):
   795  		a = AUCOMISS;
   796  		break;
   797  
   798  	case CASE(OCMP, TFLOAT64):
   799  		a = AUCOMISD;
   800  		break;
   801  
   802  	case CASE(OAS, TFLOAT32):
   803  		a = AMOVSS;
   804  		break;
   805  
   806  	case CASE(OAS, TFLOAT64):
   807  		a = AMOVSD;
   808  		break;
   809  
   810  	case CASE(OADD, TFLOAT32):
   811  		a = AADDSS;
   812  		break;
   813  
   814  	case CASE(OADD, TFLOAT64):
   815  		a = AADDSD;
   816  		break;
   817  
   818  	case CASE(OSUB, TFLOAT32):
   819  		a = ASUBSS;
   820  		break;
   821  
   822  	case CASE(OSUB, TFLOAT64):
   823  		a = ASUBSD;
   824  		break;
   825  
   826  	case CASE(OMUL, TFLOAT32):
   827  		a = AMULSS;
   828  		break;
   829  
   830  	case CASE(OMUL, TFLOAT64):
   831  		a = AMULSD;
   832  		break;
   833  
   834  	case CASE(ODIV, TFLOAT32):
   835  		a = ADIVSS;
   836  		break;
   837  
   838  	case CASE(ODIV, TFLOAT64):
   839  		a = ADIVSD;
   840  		break;
   841  	}
   842  	return a;
   843  }
   844  
   845  
   846  static	int	resvd[] =
   847  {
   848  //	D_DI,	// for movstring
   849  //	D_SI,	// for movstring
   850  
   851  	D_AX,	// for divide
   852  	D_CX,	// for shift
   853  	D_DX,	// for divide
   854  	D_SP,	// for stack
   855  
   856  	D_BL,	// because D_BX can be allocated
   857  	D_BH,
   858  };
   859  
   860  void
   861  ginit(void)
   862  {
   863  	int i;
   864  
   865  	for(i=0; i<nelem(reg); i++)
   866  		reg[i] = 1;
   867  	for(i=D_AX; i<=D_DI; i++)
   868  		reg[i] = 0;
   869  	for(i=D_X0; i<=D_X7; i++)
   870  		reg[i] = 0;
   871  	for(i=0; i<nelem(resvd); i++)
   872  		reg[resvd[i]]++;
   873  }
   874  
   875  uintptr regpc[D_NONE];
   876  
   877  void
   878  gclean(void)
   879  {
   880  	int i;
   881  
   882  	for(i=0; i<nelem(resvd); i++)
   883  		reg[resvd[i]]--;
   884  
   885  	for(i=D_AX; i<=D_DI; i++)
   886  		if(reg[i])
   887  			yyerror("reg %R left allocated at %ux", i, regpc[i]);
   888  	for(i=D_X0; i<=D_X7; i++)
   889  		if(reg[i])
   890  			yyerror("reg %R left allocated\n", i);
   891  }
   892  
   893  int32
   894  anyregalloc(void)
   895  {
   896  	int i, j;
   897  
   898  	for(i=D_AX; i<=D_DI; i++) {
   899  		if(reg[i] == 0)
   900  			goto ok;
   901  		for(j=0; j<nelem(resvd); j++)
   902  			if(resvd[j] == i)
   903  				goto ok;
   904  		return 1;
   905  	ok:;
   906  	}
   907  	for(i=D_X0; i<=D_X7; i++)
   908  		if(reg[i])
   909  			return 1;
   910  	return 0;
   911  }
   912  
   913  /*
   914   * allocate register of type t, leave in n.
   915   * if o != N, o is desired fixed register.
   916   * caller must regfree(n).
   917   */
   918  void
   919  regalloc(Node *n, Type *t, Node *o)
   920  {
   921  	int i, et;
   922  
   923  	if(t == T)
   924  		fatal("regalloc: t nil");
   925  	et = simtype[t->etype];
   926  
   927  	switch(et) {
   928  	case TINT64:
   929  	case TUINT64:
   930  		fatal("regalloc64");
   931  
   932  	case TINT8:
   933  	case TUINT8:
   934  	case TINT16:
   935  	case TUINT16:
   936  	case TINT32:
   937  	case TUINT32:
   938  	case TPTR32:
   939  	case TPTR64:
   940  	case TBOOL:
   941  		if(o != N && o->op == OREGISTER) {
   942  			i = o->val.u.reg;
   943  			if(i >= D_AX && i <= D_DI)
   944  				goto out;
   945  		}
   946  		for(i=D_AX; i<=D_DI; i++)
   947  			if(reg[i] == 0)
   948  				goto out;
   949  
   950  		fprint(2, "registers allocated at\n");
   951  		for(i=D_AX; i<=D_DI; i++)
   952  			fprint(2, "\t%R\t%#lux\n", i, regpc[i]);
   953  		yyerror("out of fixed registers");
   954  		goto err;
   955  
   956  	case TFLOAT32:
   957  	case TFLOAT64:
   958  		if(!use_sse) {
   959  			i = D_F0;
   960  			goto out;
   961  		}
   962  		if(o != N && o->op == OREGISTER) {
   963  			i = o->val.u.reg;
   964  			if(i >= D_X0 && i <= D_X7)
   965  				goto out;
   966  		}
   967  		for(i=D_X0; i<=D_X7; i++)
   968  			if(reg[i] == 0)
   969  				goto out;
   970  		fprint(2, "registers allocated at\n");
   971  		for(i=D_X0; i<=D_X7; i++)
   972  			fprint(2, "\t%R\t%#lux\n", i, regpc[i]);
   973  		fatal("out of floating registers");
   974  	}
   975  	yyerror("regalloc: unknown type %T", t);
   976  
   977  err:
   978  	nodreg(n, t, 0);
   979  	return;
   980  
   981  out:
   982  	if (i == D_SP)
   983  		print("alloc SP\n");
   984  	if(reg[i] == 0) {
   985  		regpc[i] = (uintptr)getcallerpc(&n);
   986  		if(i == D_AX || i == D_CX || i == D_DX || i == D_SP) {
   987  			dump("regalloc-o", o);
   988  			fatal("regalloc %R", i);
   989  		}
   990  	}
   991  	reg[i]++;
   992  	nodreg(n, t, i);
   993  }
   994  
   995  void
   996  regfree(Node *n)
   997  {
   998  	int i;
   999  	
  1000  	if(n->op == ONAME)
  1001  		return;
  1002  	if(n->op != OREGISTER && n->op != OINDREG)
  1003  		fatal("regfree: not a register");
  1004  	i = n->val.u.reg;
  1005  	if(i == D_SP)
  1006  		return;
  1007  	if(i < 0 || i >= nelem(reg))
  1008  		fatal("regfree: reg out of range");
  1009  	if(reg[i] <= 0)
  1010  		fatal("regfree: reg not allocated");
  1011  	reg[i]--;
  1012  	if(reg[i] == 0 && (i == D_AX || i == D_CX || i == D_DX || i == D_SP))
  1013  		fatal("regfree %R", i);
  1014  }
  1015  
  1016  /*
  1017   * initialize n to be register r of type t.
  1018   */
  1019  void
  1020  nodreg(Node *n, Type *t, int r)
  1021  {
  1022  	if(t == T)
  1023  		fatal("nodreg: t nil");
  1024  
  1025  	memset(n, 0, sizeof(*n));
  1026  	n->op = OREGISTER;
  1027  	n->addable = 1;
  1028  	ullmancalc(n);
  1029  	n->val.u.reg = r;
  1030  	n->type = t;
  1031  }
  1032  
  1033  /*
  1034   * initialize n to be indirect of register r; n is type t.
  1035   */
  1036  void
  1037  nodindreg(Node *n, Type *t, int r)
  1038  {
  1039  	nodreg(n, t, r);
  1040  	n->op = OINDREG;
  1041  }
  1042  
  1043  Node*
  1044  nodarg(Type *t, int fp)
  1045  {
  1046  	Node *n;
  1047  	NodeList *l;
  1048  	Type *first;
  1049  	Iter savet;
  1050  
  1051  	// entire argument struct, not just one arg
  1052  	switch(t->etype) {
  1053  	default:
  1054  		fatal("nodarg %T", t);
  1055  
  1056  	case TSTRUCT:
  1057  		if(!t->funarg)
  1058  			fatal("nodarg: TSTRUCT but not funarg");
  1059  		n = nod(ONAME, N, N);
  1060  		n->sym = lookup(".args");
  1061  		n->type = t;
  1062  		first = structfirst(&savet, &t);
  1063  		if(first == nil)
  1064  			fatal("nodarg: bad struct");
  1065  		if(first->width == BADWIDTH)
  1066  			fatal("nodarg: offset not computed for %T", t);
  1067  		n->xoffset = first->width;
  1068  		n->addable = 1;
  1069  		break;
  1070  
  1071  	case TFIELD:
  1072  		if(fp == 1 && t->sym != S && !isblanksym(t->sym)) {
  1073  			for(l=curfn->dcl; l; l=l->next) {
  1074  				n = l->n;
  1075  				if((n->class == PPARAM || n->class == PPARAMOUT) && n->sym == t->sym)
  1076  					return n;
  1077  			}
  1078  		}
  1079  
  1080  		n = nod(ONAME, N, N);
  1081  		n->type = t->type;
  1082  		n->sym = t->sym;
  1083  		if(t->width == BADWIDTH)
  1084  			fatal("nodarg: offset not computed for %T", t);
  1085  		n->xoffset = t->width;
  1086  		n->addable = 1;
  1087  		n->orig = t->nname;
  1088  		break;
  1089  	}
  1090  	
  1091  	// Rewrite argument named _ to __,
  1092  	// or else the assignment to _ will be
  1093  	// discarded during code generation.
  1094  	if(isblank(n))
  1095  		n->sym = lookup("__");
  1096  
  1097  	switch(fp) {
  1098  	default:
  1099  		fatal("nodarg %T %d", t, fp);
  1100  
  1101  	case 0:		// output arg
  1102  		n->op = OINDREG;
  1103  		n->val.u.reg = D_SP;
  1104  		break;
  1105  
  1106  	case 1:		// input arg
  1107  		n->class = PPARAM;
  1108  		break;
  1109  	}
  1110  
  1111  	n->typecheck = 1;
  1112  	return n;
  1113  }
  1114  
  1115  /*
  1116   * generate
  1117   *	as $c, reg
  1118   */
  1119  void
  1120  gconreg(int as, vlong c, int reg)
  1121  {
  1122  	Node n1, n2;
  1123  
  1124  	nodconst(&n1, types[TINT64], c);
  1125  	nodreg(&n2, types[TINT64], reg);
  1126  	gins(as, &n1, &n2);
  1127  }
  1128  
  1129  /*
  1130   * swap node contents
  1131   */
  1132  void
  1133  nswap(Node *a, Node *b)
  1134  {
  1135  	Node t;
  1136  
  1137  	t = *a;
  1138  	*a = *b;
  1139  	*b = t;
  1140  }
  1141  
  1142  /*
  1143   * return constant i node.
  1144   * overwritten by next call, but useful in calls to gins.
  1145   */
  1146  Node*
  1147  ncon(uint32 i)
  1148  {
  1149  	static Node n;
  1150  
  1151  	if(n.type == T)
  1152  		nodconst(&n, types[TUINT32], 0);
  1153  	mpmovecfix(n.val.u.xval, i);
  1154  	return &n;
  1155  }
  1156  
  1157  /*
  1158   * Is this node a memory operand?
  1159   */
  1160  int
  1161  ismem(Node *n)
  1162  {
  1163  	switch(n->op) {
  1164  	case OITAB:
  1165  	case OSPTR:
  1166  	case OLEN:
  1167  	case OCAP:
  1168  	case OINDREG:
  1169  	case ONAME:
  1170  	case OPARAM:
  1171  	case OCLOSUREVAR:
  1172  		return 1;
  1173  	}
  1174  	return 0;
  1175  }
  1176  
  1177  Node sclean[10];
  1178  int nsclean;
  1179  
  1180  /*
  1181   * n is a 64-bit value.  fill in lo and hi to refer to its 32-bit halves.
  1182   */
  1183  void
  1184  split64(Node *n, Node *lo, Node *hi)
  1185  {
  1186  	Node n1;
  1187  	int64 i;
  1188  
  1189  	if(!is64(n->type))
  1190  		fatal("split64 %T", n->type);
  1191  
  1192  	if(nsclean >= nelem(sclean))
  1193  		fatal("split64 clean");
  1194  	sclean[nsclean].op = OEMPTY;
  1195  	nsclean++;
  1196  	switch(n->op) {
  1197  	default:
  1198  		if(!dotaddable(n, &n1)) {
  1199  			igen(n, &n1, N);
  1200  			sclean[nsclean-1] = n1;
  1201  		}
  1202  		n = &n1;
  1203  		goto common;
  1204  	case ONAME:
  1205  		if(n->class == PPARAMREF) {
  1206  			cgen(n->heapaddr, &n1);
  1207  			sclean[nsclean-1] = n1;
  1208  			// fall through.
  1209  			n = &n1;
  1210  		}
  1211  		goto common;
  1212  	case OINDREG:
  1213  	common:
  1214  		*lo = *n;
  1215  		*hi = *n;
  1216  		lo->type = types[TUINT32];
  1217  		if(n->type->etype == TINT64)
  1218  			hi->type = types[TINT32];
  1219  		else
  1220  			hi->type = types[TUINT32];
  1221  		hi->xoffset += 4;
  1222  		break;
  1223  
  1224  	case OLITERAL:
  1225  		convconst(&n1, n->type, &n->val);
  1226  		i = mpgetfix(n1.val.u.xval);
  1227  		nodconst(lo, types[TUINT32], (uint32)i);
  1228  		i >>= 32;
  1229  		if(n->type->etype == TINT64)
  1230  			nodconst(hi, types[TINT32], (int32)i);
  1231  		else
  1232  			nodconst(hi, types[TUINT32], (uint32)i);
  1233  		break;
  1234  	}
  1235  }
  1236  
  1237  void
  1238  splitclean(void)
  1239  {
  1240  	if(nsclean <= 0)
  1241  		fatal("splitclean");
  1242  	nsclean--;
  1243  	if(sclean[nsclean].op != OEMPTY)
  1244  		regfree(&sclean[nsclean]);
  1245  }
  1246  
  1247  /*
  1248   * set up nodes representing fp constants
  1249   */
  1250  Node zerof;
  1251  Node two64f;
  1252  Node two63f;
  1253  
  1254  void
  1255  bignodes(void)
  1256  {
  1257  	static int did;
  1258  
  1259  	if(did)
  1260  		return;
  1261  	did = 1;
  1262  
  1263  	two64f = *ncon(0);
  1264  	two64f.type = types[TFLOAT64];
  1265  	two64f.val.ctype = CTFLT;
  1266  	two64f.val.u.fval = mal(sizeof *two64f.val.u.fval);
  1267  	mpmovecflt(two64f.val.u.fval, 18446744073709551616.);
  1268  
  1269  	two63f = two64f;
  1270  	two63f.val.u.fval = mal(sizeof *two63f.val.u.fval);
  1271  	mpmovecflt(two63f.val.u.fval, 9223372036854775808.);
  1272  
  1273  	zerof = two64f;
  1274  	zerof.val.u.fval = mal(sizeof *zerof.val.u.fval);
  1275  	mpmovecflt(zerof.val.u.fval, 0);
  1276  }
  1277  
  1278  void
  1279  memname(Node *n, Type *t)
  1280  {
  1281  	tempname(n, t);
  1282  	strcpy(namebuf, n->sym->name);
  1283  	namebuf[0] = '.';	// keep optimizer from registerizing
  1284  	n->sym = lookup(namebuf);
  1285  	n->orig->sym = n->sym;
  1286  }
  1287  
  1288  static void floatmove(Node *f, Node *t);
  1289  static void floatmove_387(Node *f, Node *t);
  1290  static void floatmove_sse(Node *f, Node *t);
  1291  
  1292  void
  1293  gmove(Node *f, Node *t)
  1294  {
  1295  	int a, ft, tt;
  1296  	Type *cvt;
  1297  	Node r1, r2, flo, fhi, tlo, thi, con;
  1298  
  1299  	if(debug['M'])
  1300  		print("gmove %N -> %N\n", f, t);
  1301  
  1302  	ft = simsimtype(f->type);
  1303  	tt = simsimtype(t->type);
  1304  	cvt = t->type;
  1305  	
  1306  	if(iscomplex[ft] || iscomplex[tt]) {
  1307  		complexmove(f, t);
  1308  		return;
  1309  	}
  1310  	if(isfloat[ft] || isfloat[tt]) {
  1311  		floatmove(f, t);
  1312  		return;
  1313  	}
  1314  
  1315  	// cannot have two integer memory operands;
  1316  	// except 64-bit, which always copies via registers anyway.
  1317  	if(isint[ft] && isint[tt] && !is64(f->type) && !is64(t->type) && ismem(f) && ismem(t))
  1318  		goto hard;
  1319  
  1320  	// convert constant to desired type
  1321  	if(f->op == OLITERAL) {
  1322  		convconst(&con, t->type, &f->val);
  1323  		f = &con;
  1324  		ft = simsimtype(con.type);
  1325  	}
  1326  
  1327  	// value -> value copy, only one memory operand.
  1328  	// figure out the instruction to use.
  1329  	// break out of switch for one-instruction gins.
  1330  	// goto rdst for "destination must be register".
  1331  	// goto hard for "convert to cvt type first".
  1332  	// otherwise handle and return.
  1333  
  1334  	switch(CASE(ft, tt)) {
  1335  	default:
  1336  		goto fatal;
  1337  
  1338  	/*
  1339  	 * integer copy and truncate
  1340  	 */
  1341  	case CASE(TINT8, TINT8):	// same size
  1342  	case CASE(TINT8, TUINT8):
  1343  	case CASE(TUINT8, TINT8):
  1344  	case CASE(TUINT8, TUINT8):
  1345  		a = AMOVB;
  1346  		break;
  1347  
  1348  	case CASE(TINT16, TINT8):	// truncate
  1349  	case CASE(TUINT16, TINT8):
  1350  	case CASE(TINT32, TINT8):
  1351  	case CASE(TUINT32, TINT8):
  1352  	case CASE(TINT16, TUINT8):
  1353  	case CASE(TUINT16, TUINT8):
  1354  	case CASE(TINT32, TUINT8):
  1355  	case CASE(TUINT32, TUINT8):
  1356  		a = AMOVB;
  1357  		goto rsrc;
  1358  
  1359  	case CASE(TINT64, TINT8):	// truncate low word
  1360  	case CASE(TUINT64, TINT8):
  1361  	case CASE(TINT64, TUINT8):
  1362  	case CASE(TUINT64, TUINT8):
  1363  		split64(f, &flo, &fhi);
  1364  		nodreg(&r1, t->type, D_AX);
  1365  		gmove(&flo, &r1);
  1366  		gins(AMOVB, &r1, t);
  1367  		splitclean();
  1368  		return;
  1369  
  1370  	case CASE(TINT16, TINT16):	// same size
  1371  	case CASE(TINT16, TUINT16):
  1372  	case CASE(TUINT16, TINT16):
  1373  	case CASE(TUINT16, TUINT16):
  1374  		a = AMOVW;
  1375  		break;
  1376  
  1377  	case CASE(TINT32, TINT16):	// truncate
  1378  	case CASE(TUINT32, TINT16):
  1379  	case CASE(TINT32, TUINT16):
  1380  	case CASE(TUINT32, TUINT16):
  1381  		a = AMOVW;
  1382  		goto rsrc;
  1383  
  1384  	case CASE(TINT64, TINT16):	// truncate low word
  1385  	case CASE(TUINT64, TINT16):
  1386  	case CASE(TINT64, TUINT16):
  1387  	case CASE(TUINT64, TUINT16):
  1388  		split64(f, &flo, &fhi);
  1389  		nodreg(&r1, t->type, D_AX);
  1390  		gmove(&flo, &r1);
  1391  		gins(AMOVW, &r1, t);
  1392  		splitclean();
  1393  		return;
  1394  
  1395  	case CASE(TINT32, TINT32):	// same size
  1396  	case CASE(TINT32, TUINT32):
  1397  	case CASE(TUINT32, TINT32):
  1398  	case CASE(TUINT32, TUINT32):
  1399  		a = AMOVL;
  1400  		break;
  1401  
  1402  	case CASE(TINT64, TINT32):	// truncate
  1403  	case CASE(TUINT64, TINT32):
  1404  	case CASE(TINT64, TUINT32):
  1405  	case CASE(TUINT64, TUINT32):
  1406  		split64(f, &flo, &fhi);
  1407  		nodreg(&r1, t->type, D_AX);
  1408  		gmove(&flo, &r1);
  1409  		gins(AMOVL, &r1, t);
  1410  		splitclean();
  1411  		return;
  1412  
  1413  	case CASE(TINT64, TINT64):	// same size
  1414  	case CASE(TINT64, TUINT64):
  1415  	case CASE(TUINT64, TINT64):
  1416  	case CASE(TUINT64, TUINT64):
  1417  		split64(f, &flo, &fhi);
  1418  		split64(t, &tlo, &thi);
  1419  		if(f->op == OLITERAL) {
  1420  			gins(AMOVL, &flo, &tlo);
  1421  			gins(AMOVL, &fhi, &thi);
  1422  		} else {
  1423  			nodreg(&r1, t->type, D_AX);
  1424  			nodreg(&r2, t->type, D_DX);
  1425  			gins(AMOVL, &flo, &r1);
  1426  			gins(AMOVL, &fhi, &r2);
  1427  			gins(AMOVL, &r1, &tlo);
  1428  			gins(AMOVL, &r2, &thi);
  1429  		}
  1430  		splitclean();
  1431  		splitclean();
  1432  		return;
  1433  
  1434  	/*
  1435  	 * integer up-conversions
  1436  	 */
  1437  	case CASE(TINT8, TINT16):	// sign extend int8
  1438  	case CASE(TINT8, TUINT16):
  1439  		a = AMOVBWSX;
  1440  		goto rdst;
  1441  	case CASE(TINT8, TINT32):
  1442  	case CASE(TINT8, TUINT32):
  1443  		a = AMOVBLSX;
  1444  		goto rdst;
  1445  	case CASE(TINT8, TINT64):	// convert via int32
  1446  	case CASE(TINT8, TUINT64):
  1447  		cvt = types[TINT32];
  1448  		goto hard;
  1449  
  1450  	case CASE(TUINT8, TINT16):	// zero extend uint8
  1451  	case CASE(TUINT8, TUINT16):
  1452  		a = AMOVBWZX;
  1453  		goto rdst;
  1454  	case CASE(TUINT8, TINT32):
  1455  	case CASE(TUINT8, TUINT32):
  1456  		a = AMOVBLZX;
  1457  		goto rdst;
  1458  	case CASE(TUINT8, TINT64):	// convert via uint32
  1459  	case CASE(TUINT8, TUINT64):
  1460  		cvt = types[TUINT32];
  1461  		goto hard;
  1462  
  1463  	case CASE(TINT16, TINT32):	// sign extend int16
  1464  	case CASE(TINT16, TUINT32):
  1465  		a = AMOVWLSX;
  1466  		goto rdst;
  1467  	case CASE(TINT16, TINT64):	// convert via int32
  1468  	case CASE(TINT16, TUINT64):
  1469  		cvt = types[TINT32];
  1470  		goto hard;
  1471  
  1472  	case CASE(TUINT16, TINT32):	// zero extend uint16
  1473  	case CASE(TUINT16, TUINT32):
  1474  		a = AMOVWLZX;
  1475  		goto rdst;
  1476  	case CASE(TUINT16, TINT64):	// convert via uint32
  1477  	case CASE(TUINT16, TUINT64):
  1478  		cvt = types[TUINT32];
  1479  		goto hard;
  1480  
  1481  	case CASE(TINT32, TINT64):	// sign extend int32
  1482  	case CASE(TINT32, TUINT64):
  1483  		split64(t, &tlo, &thi);
  1484  		nodreg(&flo, tlo.type, D_AX);
  1485  		nodreg(&fhi, thi.type, D_DX);
  1486  		gmove(f, &flo);
  1487  		gins(ACDQ, N, N);
  1488  		gins(AMOVL, &flo, &tlo);
  1489  		gins(AMOVL, &fhi, &thi);
  1490  		splitclean();
  1491  		return;
  1492  
  1493  	case CASE(TUINT32, TINT64):	// zero extend uint32
  1494  	case CASE(TUINT32, TUINT64):
  1495  		split64(t, &tlo, &thi);
  1496  		gmove(f, &tlo);
  1497  		gins(AMOVL, ncon(0), &thi);
  1498  		splitclean();
  1499  		return;
  1500  	}
  1501  
  1502  	gins(a, f, t);
  1503  	return;
  1504  
  1505  rsrc:
  1506  	// requires register source
  1507  	regalloc(&r1, f->type, t);
  1508  	gmove(f, &r1);
  1509  	gins(a, &r1, t);
  1510  	regfree(&r1);
  1511  	return;
  1512  
  1513  rdst:
  1514  	// requires register destination
  1515  	regalloc(&r1, t->type, t);
  1516  	gins(a, f, &r1);
  1517  	gmove(&r1, t);
  1518  	regfree(&r1);
  1519  	return;
  1520  
  1521  hard:
  1522  	// requires register intermediate
  1523  	regalloc(&r1, cvt, t);
  1524  	gmove(f, &r1);
  1525  	gmove(&r1, t);
  1526  	regfree(&r1);
  1527  	return;
  1528  
  1529  fatal:
  1530  	// should not happen
  1531  	fatal("gmove %N -> %N", f, t);
  1532  }
  1533  
  1534  static void
  1535  floatmove(Node *f, Node *t)
  1536  {
  1537  	Node r1, r2, t1, t2, tlo, thi, con, f0, f1, ax, dx, cx;
  1538  	Type *cvt;
  1539  	int ft, tt;
  1540  	Prog *p1, *p2, *p3;
  1541  
  1542  	ft = simsimtype(f->type);
  1543  	tt = simsimtype(t->type);
  1544  	cvt = t->type;
  1545  
  1546  	// cannot have two floating point memory operands.
  1547  	if(isfloat[ft] && isfloat[tt] && ismem(f) && ismem(t))
  1548  		goto hard;
  1549  
  1550  	// convert constant to desired type
  1551  	if(f->op == OLITERAL) {
  1552  		convconst(&con, t->type, &f->val);
  1553  		f = &con;
  1554  		ft = simsimtype(con.type);
  1555  
  1556  		// some constants can't move directly to memory.
  1557  		if(ismem(t)) {
  1558  			// float constants come from memory.
  1559  			if(isfloat[tt])
  1560  				goto hard;
  1561  		}
  1562  	}
  1563  
  1564  	// value -> value copy, only one memory operand.
  1565  	// figure out the instruction to use.
  1566  	// break out of switch for one-instruction gins.
  1567  	// goto rdst for "destination must be register".
  1568  	// goto hard for "convert to cvt type first".
  1569  	// otherwise handle and return.
  1570  
  1571  	switch(CASE(ft, tt)) {
  1572  	default:
  1573  		if(use_sse)
  1574  			floatmove_sse(f, t);
  1575  		else
  1576  			floatmove_387(f, t);
  1577  		return;
  1578  
  1579  	// float to very long integer.
  1580  	case CASE(TFLOAT32, TINT64):
  1581  	case CASE(TFLOAT64, TINT64):
  1582  		if(f->op == OREGISTER) {
  1583  			cvt = f->type;
  1584  			goto hardmem;
  1585  		}
  1586  		nodreg(&r1, types[ft], D_F0);
  1587  		if(ft == TFLOAT32)
  1588  			gins(AFMOVF, f, &r1);
  1589  		else
  1590  			gins(AFMOVD, f, &r1);
  1591  
  1592  		// set round to zero mode during conversion
  1593  		memname(&t1, types[TUINT16]);
  1594  		memname(&t2, types[TUINT16]);
  1595  		gins(AFSTCW, N, &t1);
  1596  		gins(AMOVW, ncon(0xf7f), &t2);
  1597  		gins(AFLDCW, &t2, N);
  1598  		if(tt == TINT16)
  1599  			gins(AFMOVWP, &r1, t);
  1600  		else if(tt == TINT32)
  1601  			gins(AFMOVLP, &r1, t);
  1602  		else
  1603  			gins(AFMOVVP, &r1, t);
  1604  		gins(AFLDCW, &t1, N);
  1605  		return;
  1606  
  1607  	case CASE(TFLOAT32, TUINT64):
  1608  	case CASE(TFLOAT64, TUINT64):
  1609  		if(!ismem(f)) {
  1610  			cvt = f->type;
  1611  			goto hardmem;
  1612  		}
  1613  		bignodes();
  1614  		nodreg(&f0, types[ft], D_F0);
  1615  		nodreg(&f1, types[ft], D_F0 + 1);
  1616  		nodreg(&ax, types[TUINT16], D_AX);
  1617  
  1618  		if(ft == TFLOAT32)
  1619  			gins(AFMOVF, f, &f0);
  1620  		else
  1621  			gins(AFMOVD, f, &f0);
  1622  
  1623  		// if 0 > v { answer = 0 }
  1624  		gins(AFMOVD, &zerof, &f0);
  1625  		gins(AFUCOMIP, &f0, &f1);
  1626  		p1 = gbranch(optoas(OGT, types[tt]), T, 0);
  1627  		// if 1<<64 <= v { answer = 0 too }
  1628  		gins(AFMOVD, &two64f, &f0);
  1629  		gins(AFUCOMIP, &f0, &f1);
  1630  		p2 = gbranch(optoas(OGT, types[tt]), T, 0);
  1631  		patch(p1, pc);
  1632  		gins(AFMOVVP, &f0, t);	// don't care about t, but will pop the stack
  1633  		split64(t, &tlo, &thi);
  1634  		gins(AMOVL, ncon(0), &tlo);
  1635  		gins(AMOVL, ncon(0), &thi);
  1636  		splitclean();
  1637  		p1 = gbranch(AJMP, T, 0);
  1638  		patch(p2, pc);
  1639  
  1640  		// in range; algorithm is:
  1641  		//	if small enough, use native float64 -> int64 conversion.
  1642  		//	otherwise, subtract 2^63, convert, and add it back.
  1643  
  1644  		// set round to zero mode during conversion
  1645  		memname(&t1, types[TUINT16]);
  1646  		memname(&t2, types[TUINT16]);
  1647  		gins(AFSTCW, N, &t1);
  1648  		gins(AMOVW, ncon(0xf7f), &t2);
  1649  		gins(AFLDCW, &t2, N);
  1650  
  1651  		// actual work
  1652  		gins(AFMOVD, &two63f, &f0);
  1653  		gins(AFUCOMIP, &f0, &f1);
  1654  		p2 = gbranch(optoas(OLE, types[tt]), T, 0);
  1655  		gins(AFMOVVP, &f0, t);
  1656  		p3 = gbranch(AJMP, T, 0);
  1657  		patch(p2, pc);
  1658  		gins(AFMOVD, &two63f, &f0);
  1659  		gins(AFSUBDP, &f0, &f1);
  1660  		gins(AFMOVVP, &f0, t);
  1661  		split64(t, &tlo, &thi);
  1662  		gins(AXORL, ncon(0x80000000), &thi);	// + 2^63
  1663  		patch(p3, pc);
  1664  		splitclean();
  1665  		// restore rounding mode
  1666  		gins(AFLDCW, &t1, N);
  1667  
  1668  		patch(p1, pc);
  1669  		return;
  1670  
  1671  	/*
  1672  	 * integer to float
  1673  	 */
  1674  	case CASE(TINT64, TFLOAT32):
  1675  	case CASE(TINT64, TFLOAT64):
  1676  		if(t->op == OREGISTER)
  1677  			goto hardmem;
  1678  		nodreg(&f0, t->type, D_F0);
  1679  		gins(AFMOVV, f, &f0);
  1680  		if(tt == TFLOAT32)
  1681  			gins(AFMOVFP, &f0, t);
  1682  		else
  1683  			gins(AFMOVDP, &f0, t);
  1684  		return;
  1685  
  1686  	case CASE(TUINT64, TFLOAT32):
  1687  	case CASE(TUINT64, TFLOAT64):
  1688  		// algorithm is:
  1689  		//	if small enough, use native int64 -> float64 conversion.
  1690  		//	otherwise, halve (rounding to odd?), convert, and double.
  1691  		nodreg(&ax, types[TUINT32], D_AX);
  1692  		nodreg(&dx, types[TUINT32], D_DX);
  1693  		nodreg(&cx, types[TUINT32], D_CX);
  1694  		tempname(&t1, f->type);
  1695  		split64(&t1, &tlo, &thi);
  1696  		gmove(f, &t1);
  1697  		gins(ACMPL, &thi, ncon(0));
  1698  		p1 = gbranch(AJLT, T, 0);
  1699  		// native
  1700  		nodreg(&r1, types[tt], D_F0);
  1701  		gins(AFMOVV, &t1, &r1);
  1702  		if(tt == TFLOAT32)
  1703  			gins(AFMOVFP, &r1, t);
  1704  		else
  1705  			gins(AFMOVDP, &r1, t);
  1706  		p2 = gbranch(AJMP, T, 0);
  1707  		// simulated
  1708  		patch(p1, pc);
  1709  		gmove(&tlo, &ax);
  1710  		gmove(&thi, &dx);
  1711  		p1 = gins(ASHRL, ncon(1), &ax);
  1712  		p1->from.index = D_DX;	// double-width shift DX -> AX
  1713  		p1->from.scale = 0;
  1714  		gins(AMOVL, ncon(0), &cx);
  1715  		gins(ASETCC, N, &cx);
  1716  		gins(AORL, &cx, &ax);
  1717  		gins(ASHRL, ncon(1), &dx);
  1718  		gmove(&dx, &thi);
  1719  		gmove(&ax, &tlo);
  1720  		nodreg(&r1, types[tt], D_F0);
  1721  		nodreg(&r2, types[tt], D_F0 + 1);
  1722  		gins(AFMOVV, &t1, &r1);
  1723  		gins(AFMOVD, &r1, &r1);
  1724  		gins(AFADDDP, &r1, &r2);
  1725  		if(tt == TFLOAT32)
  1726  			gins(AFMOVFP, &r1, t);
  1727  		else
  1728  			gins(AFMOVDP, &r1, t);
  1729  		patch(p2, pc);
  1730  		splitclean();
  1731  		return;
  1732  	}
  1733  
  1734  hard:
  1735  	// requires register intermediate
  1736  	regalloc(&r1, cvt, t);
  1737  	gmove(f, &r1);
  1738  	gmove(&r1, t);
  1739  	regfree(&r1);
  1740  	return;
  1741  
  1742  hardmem:
  1743  	// requires memory intermediate
  1744  	tempname(&r1, cvt);
  1745  	gmove(f, &r1);
  1746  	gmove(&r1, t);
  1747  	return;
  1748  }
  1749  
  1750  static void
  1751  floatmove_387(Node *f, Node *t)
  1752  {
  1753  	Node r1, t1, t2;
  1754  	Type *cvt;
  1755  	Prog *p1, *p2, *p3;
  1756  	int a, ft, tt;
  1757  
  1758  	ft = simsimtype(f->type);
  1759  	tt = simsimtype(t->type);
  1760  	cvt = t->type;
  1761  
  1762  	switch(CASE(ft, tt)) {
  1763  	default:
  1764  		goto fatal;
  1765  
  1766  	/*
  1767  	* float to integer
  1768  	*/
  1769  	case CASE(TFLOAT32, TINT16):
  1770  	case CASE(TFLOAT32, TINT32):
  1771  	case CASE(TFLOAT32, TINT64):
  1772  	case CASE(TFLOAT64, TINT16):
  1773  	case CASE(TFLOAT64, TINT32):
  1774  	case CASE(TFLOAT64, TINT64):
  1775  		if(t->op == OREGISTER)
  1776  			goto hardmem;
  1777  		nodreg(&r1, types[ft], D_F0);
  1778  		if(f->op != OREGISTER) {
  1779  			if(ft == TFLOAT32)
  1780  				gins(AFMOVF, f, &r1);
  1781  			else
  1782  				gins(AFMOVD, f, &r1);
  1783  		}
  1784  
  1785  		// set round to zero mode during conversion
  1786  		memname(&t1, types[TUINT16]);
  1787  		memname(&t2, types[TUINT16]);
  1788  		gins(AFSTCW, N, &t1);
  1789  		gins(AMOVW, ncon(0xf7f), &t2);
  1790  		gins(AFLDCW, &t2, N);
  1791  		if(tt == TINT16)
  1792  			gins(AFMOVWP, &r1, t);
  1793  		else if(tt == TINT32)
  1794  			gins(AFMOVLP, &r1, t);
  1795  		else
  1796  			gins(AFMOVVP, &r1, t);
  1797  		gins(AFLDCW, &t1, N);
  1798  		return;
  1799  
  1800  	case CASE(TFLOAT32, TINT8):
  1801  	case CASE(TFLOAT32, TUINT16):
  1802  	case CASE(TFLOAT32, TUINT8):
  1803  	case CASE(TFLOAT64, TINT8):
  1804  	case CASE(TFLOAT64, TUINT16):
  1805  	case CASE(TFLOAT64, TUINT8):
  1806  		// convert via int32.
  1807  		tempname(&t1, types[TINT32]);
  1808  		gmove(f, &t1);
  1809  		switch(tt) {
  1810  		default:
  1811  			fatal("gmove %T", t);
  1812  		case TINT8:
  1813  			gins(ACMPL, &t1, ncon(-0x80));
  1814  			p1 = gbranch(optoas(OLT, types[TINT32]), T, -1);
  1815  			gins(ACMPL, &t1, ncon(0x7f));
  1816  			p2 = gbranch(optoas(OGT, types[TINT32]), T, -1);
  1817  			p3 = gbranch(AJMP, T, 0);
  1818  			patch(p1, pc);
  1819  			patch(p2, pc);
  1820  			gmove(ncon(-0x80), &t1);
  1821  			patch(p3, pc);
  1822  			gmove(&t1, t);
  1823  			break;
  1824  		case TUINT8:
  1825  			gins(ATESTL, ncon(0xffffff00), &t1);
  1826  			p1 = gbranch(AJEQ, T, +1);
  1827  			gins(AMOVL, ncon(0), &t1);
  1828  			patch(p1, pc);
  1829  			gmove(&t1, t);
  1830  			break;
  1831  		case TUINT16:
  1832  			gins(ATESTL, ncon(0xffff0000), &t1);
  1833  			p1 = gbranch(AJEQ, T, +1);
  1834  			gins(AMOVL, ncon(0), &t1);
  1835  			patch(p1, pc);
  1836  			gmove(&t1, t);
  1837  			break;
  1838  		}
  1839  		return;
  1840  
  1841  	case CASE(TFLOAT32, TUINT32):
  1842  	case CASE(TFLOAT64, TUINT32):
  1843  		// convert via int64.
  1844  		cvt = types[TINT64];
  1845  		goto hardmem;
  1846  
  1847  	/*
  1848  	 * integer to float
  1849  	 */
  1850  	case CASE(TINT16, TFLOAT32):
  1851  	case CASE(TINT16, TFLOAT64):
  1852  	case CASE(TINT32, TFLOAT32):
  1853  	case CASE(TINT32, TFLOAT64):
  1854  	case CASE(TINT64, TFLOAT32):
  1855  	case CASE(TINT64, TFLOAT64):
  1856  		if(t->op != OREGISTER)
  1857  			goto hard;
  1858  		if(f->op == OREGISTER) {
  1859  			cvt = f->type;
  1860  			goto hardmem;
  1861  		}
  1862  		switch(ft) {
  1863  		case TINT16:
  1864  			a = AFMOVW;
  1865  			break;
  1866  		case TINT32:
  1867  			a = AFMOVL;
  1868  			break;
  1869  		default:
  1870  			a = AFMOVV;
  1871  			break;
  1872  		}
  1873  		break;
  1874  
  1875  	case CASE(TINT8, TFLOAT32):
  1876  	case CASE(TINT8, TFLOAT64):
  1877  	case CASE(TUINT16, TFLOAT32):
  1878  	case CASE(TUINT16, TFLOAT64):
  1879  	case CASE(TUINT8, TFLOAT32):
  1880  	case CASE(TUINT8, TFLOAT64):
  1881  		// convert via int32 memory
  1882  		cvt = types[TINT32];
  1883  		goto hardmem;
  1884  
  1885  	case CASE(TUINT32, TFLOAT32):
  1886  	case CASE(TUINT32, TFLOAT64):
  1887  		// convert via int64 memory
  1888  		cvt = types[TINT64];
  1889  		goto hardmem;
  1890  
  1891  	/*
  1892  	 * float to float
  1893  	 */
  1894  	case CASE(TFLOAT32, TFLOAT32):
  1895  	case CASE(TFLOAT64, TFLOAT64):
  1896  		// The way the code generator uses floating-point
  1897  		// registers, a move from F0 to F0 is intended as a no-op.
  1898  		// On the x86, it's not: it pushes a second copy of F0
  1899  		// on the floating point stack.  So toss it away here.
  1900  		// Also, F0 is the *only* register we ever evaluate
  1901  		// into, so we should only see register/register as F0/F0.
  1902  		if(ismem(f) && ismem(t))
  1903  			goto hard;
  1904  		if(f->op == OREGISTER && t->op == OREGISTER) {
  1905  			if(f->val.u.reg != D_F0 || t->val.u.reg != D_F0)
  1906  				goto fatal;
  1907  			return;
  1908  		}
  1909  		a = AFMOVF;
  1910  		if(ft == TFLOAT64)
  1911  			a = AFMOVD;
  1912  		if(ismem(t)) {
  1913  			if(f->op != OREGISTER || f->val.u.reg != D_F0)
  1914  				fatal("gmove %N", f);
  1915  			a = AFMOVFP;
  1916  			if(ft == TFLOAT64)
  1917  				a = AFMOVDP;
  1918  		}
  1919  		break;
  1920  
  1921  	case CASE(TFLOAT32, TFLOAT64):
  1922  		if(ismem(f) && ismem(t))
  1923  			goto hard;
  1924  		if(f->op == OREGISTER && t->op == OREGISTER) {
  1925  			if(f->val.u.reg != D_F0 || t->val.u.reg != D_F0)
  1926  				goto fatal;
  1927  			return;
  1928  		}
  1929  		if(f->op == OREGISTER)
  1930  			gins(AFMOVDP, f, t);
  1931  		else
  1932  			gins(AFMOVF, f, t);
  1933  		return;
  1934  
  1935  	case CASE(TFLOAT64, TFLOAT32):
  1936  		if(ismem(f) && ismem(t))
  1937  			goto hard;
  1938  		if(f->op == OREGISTER && t->op == OREGISTER) {
  1939  			tempname(&r1, types[TFLOAT32]);
  1940  			gins(AFMOVFP, f, &r1);
  1941  			gins(AFMOVF, &r1, t);
  1942  			return;
  1943  		}
  1944  		if(f->op == OREGISTER)
  1945  			gins(AFMOVFP, f, t);
  1946  		else
  1947  			gins(AFMOVD, f, t);
  1948  		return;
  1949  	}
  1950  
  1951  	gins(a, f, t);
  1952  	return;
  1953  
  1954  hard:
  1955  	// requires register intermediate
  1956  	regalloc(&r1, cvt, t);
  1957  	gmove(f, &r1);
  1958  	gmove(&r1, t);
  1959  	regfree(&r1);
  1960  	return;
  1961  
  1962  hardmem:
  1963  	// requires memory intermediate
  1964  	tempname(&r1, cvt);
  1965  	gmove(f, &r1);
  1966  	gmove(&r1, t);
  1967  	return;
  1968  
  1969  fatal:
  1970  	// should not happen
  1971  	fatal("gmove %lN -> %lN", f, t);
  1972  	return;
  1973  }
  1974  
  1975  static void
  1976  floatmove_sse(Node *f, Node *t)
  1977  {
  1978  	Node r1;
  1979  	Type *cvt;
  1980  	int a, ft, tt;
  1981  
  1982  	ft = simsimtype(f->type);
  1983  	tt = simsimtype(t->type);
  1984  
  1985  	switch(CASE(ft, tt)) {
  1986  	default:
  1987  		// should not happen
  1988  		fatal("gmove %N -> %N", f, t);
  1989  		return;
  1990  	/*
  1991  	* float to integer
  1992  	*/
  1993  	case CASE(TFLOAT32, TINT16):
  1994  	case CASE(TFLOAT32, TINT8):
  1995  	case CASE(TFLOAT32, TUINT16):
  1996  	case CASE(TFLOAT32, TUINT8):
  1997  	case CASE(TFLOAT64, TINT16):
  1998  	case CASE(TFLOAT64, TINT8):
  1999  	case CASE(TFLOAT64, TUINT16):
  2000  	case CASE(TFLOAT64, TUINT8):
  2001  		// convert via int32.
  2002  		cvt = types[TINT32];
  2003  		goto hard;
  2004  
  2005  	case CASE(TFLOAT32, TUINT32):
  2006  	case CASE(TFLOAT64, TUINT32):
  2007  		// convert via int64.
  2008  		cvt = types[TINT64];
  2009  		goto hardmem;
  2010  
  2011  	case CASE(TFLOAT32, TINT32):
  2012  		a = ACVTTSS2SL;
  2013  		goto rdst;
  2014  
  2015  	case CASE(TFLOAT64, TINT32):
  2016  		a = ACVTTSD2SL;
  2017  		goto rdst;
  2018  
  2019  	/*
  2020  	 * integer to float
  2021  	 */
  2022  	case CASE(TINT8, TFLOAT32):
  2023  	case CASE(TINT8, TFLOAT64):
  2024  	case CASE(TINT16, TFLOAT32):
  2025  	case CASE(TINT16, TFLOAT64):
  2026  	case CASE(TUINT16, TFLOAT32):
  2027  	case CASE(TUINT16, TFLOAT64):
  2028  	case CASE(TUINT8, TFLOAT32):
  2029  	case CASE(TUINT8, TFLOAT64):
  2030  		// convert via int32 memory
  2031  		cvt = types[TINT32];
  2032  		goto hard;
  2033  
  2034  	case CASE(TUINT32, TFLOAT32):
  2035  	case CASE(TUINT32, TFLOAT64):
  2036  		// convert via int64 memory
  2037  		cvt = types[TINT64];
  2038  		goto hardmem;
  2039  
  2040  	case CASE(TINT32, TFLOAT32):
  2041  		a = ACVTSL2SS;
  2042  		goto rdst;
  2043  
  2044  	case CASE(TINT32, TFLOAT64):
  2045  		a = ACVTSL2SD;
  2046  		goto rdst;
  2047  
  2048  	/*
  2049  	 * float to float
  2050  	 */
  2051  	case CASE(TFLOAT32, TFLOAT32):
  2052  		a = AMOVSS;
  2053  		break;
  2054  
  2055  	case CASE(TFLOAT64, TFLOAT64):
  2056  		a = AMOVSD;
  2057  		break;
  2058  
  2059  	case CASE(TFLOAT32, TFLOAT64):
  2060  		a = ACVTSS2SD;
  2061  		goto rdst;
  2062  
  2063  	case CASE(TFLOAT64, TFLOAT32):
  2064  		a = ACVTSD2SS;
  2065  		goto rdst;
  2066  	}
  2067  
  2068  	gins(a, f, t);
  2069  	return;
  2070  
  2071  hard:
  2072  	// requires register intermediate
  2073  	regalloc(&r1, cvt, t);
  2074  	gmove(f, &r1);
  2075  	gmove(&r1, t);
  2076  	regfree(&r1);
  2077  	return;
  2078  
  2079  hardmem:
  2080  	// requires memory intermediate
  2081  	tempname(&r1, cvt);
  2082  	gmove(f, &r1);
  2083  	gmove(&r1, t);
  2084  	return;
  2085  
  2086  rdst:
  2087  	// requires register destination
  2088  	regalloc(&r1, t->type, t);
  2089  	gins(a, f, &r1);
  2090  	gmove(&r1, t);
  2091  	regfree(&r1);
  2092  	return;
  2093  }
  2094  
  2095  int
  2096  samaddr(Node *f, Node *t)
  2097  {
  2098  
  2099  	if(f->op != t->op)
  2100  		return 0;
  2101  
  2102  	switch(f->op) {
  2103  	case OREGISTER:
  2104  		if(f->val.u.reg != t->val.u.reg)
  2105  			break;
  2106  		return 1;
  2107  	}
  2108  	return 0;
  2109  }
  2110  /*
  2111   * generate one instruction:
  2112   *	as f, t
  2113   */
  2114  Prog*
  2115  gins(int as, Node *f, Node *t)
  2116  {
  2117  	Prog *p;
  2118  	Addr af, at;
  2119  	int w;
  2120  
  2121  	if(as == AFMOVF && f && f->op == OREGISTER && t && t->op == OREGISTER)
  2122  		fatal("gins MOVF reg, reg");
  2123  	if(as == ACVTSD2SS && f && f->op == OLITERAL)
  2124  		fatal("gins CVTSD2SS const");
  2125  	if(as == AMOVSD && t && t->op == OREGISTER && t->val.u.reg == D_F0)
  2126  		fatal("gins MOVSD into F0");
  2127  
  2128  	switch(as) {
  2129  	case AMOVB:
  2130  	case AMOVW:
  2131  	case AMOVL:
  2132  		if(f != N && t != N && samaddr(f, t))
  2133  			return nil;
  2134  		break;
  2135  	
  2136  	case ALEAL:
  2137  		if(f != N && isconst(f, CTNIL))
  2138  			fatal("gins LEAL nil %T", f->type);
  2139  		break;
  2140  	}
  2141  
  2142  	memset(&af, 0, sizeof af);
  2143  	memset(&at, 0, sizeof at);
  2144  	if(f != N)
  2145  		naddr(f, &af, 1);
  2146  	if(t != N)
  2147  		naddr(t, &at, 1);
  2148  	p = prog(as);
  2149  	if(f != N)
  2150  		p->from = af;
  2151  	if(t != N)
  2152  		p->to = at;
  2153  	if(debug['g'])
  2154  		print("%P\n", p);
  2155  
  2156  	w = 0;
  2157  	switch(as) {
  2158  	case AMOVB:
  2159  		w = 1;
  2160  		break;
  2161  	case AMOVW:
  2162  		w = 2;
  2163  		break;
  2164  	case AMOVL:
  2165  		w = 4;
  2166  		break;
  2167  	}
  2168  
  2169  	if(1 && w != 0 && f != N && (af.width > w || at.width > w)) {
  2170  		dump("bad width from:", f);
  2171  		dump("bad width to:", t);
  2172  		fatal("bad width: %P (%d, %d)\n", p, af.width, at.width);
  2173  	}
  2174  
  2175  	return p;
  2176  }
  2177  
  2178  /*
  2179   * generate code to compute n;
  2180   * make a refer to result.
  2181   */
  2182  void
  2183  naddr(Node *n, Addr *a, int canemitcode)
  2184  {
  2185  	Sym *s;
  2186  
  2187  	a->scale = 0;
  2188  	a->index = D_NONE;
  2189  	a->type = D_NONE;
  2190  	a->gotype = nil;
  2191  	a->node = N;
  2192  	if(n == N)
  2193  		return;
  2194  
  2195  	switch(n->op) {
  2196  	default:
  2197  		fatal("naddr: bad %O %D", n->op, a);
  2198  		break;
  2199  
  2200  	case OREGISTER:
  2201  		a->type = n->val.u.reg;
  2202  		a->sym = nil;
  2203  		break;
  2204  
  2205  	case OINDREG:
  2206  		a->type = n->val.u.reg+D_INDIR;
  2207  		a->sym = linksym(n->sym);
  2208  		a->offset = n->xoffset;
  2209  		break;
  2210  
  2211  	case OPARAM:
  2212  		// n->left is PHEAP ONAME for stack parameter.
  2213  		// compute address of actual parameter on stack.
  2214  		a->etype = n->left->type->etype;
  2215  		a->width = n->left->type->width;
  2216  		a->offset = n->xoffset;
  2217  		a->sym = linksym(n->left->sym);
  2218  		a->type = D_PARAM;
  2219  		a->node = n->left->orig;
  2220  		break;
  2221  
  2222  	case OCLOSUREVAR:
  2223  		if(!curfn->needctxt)
  2224  			fatal("closurevar without needctxt");
  2225  		a->type = D_DX+D_INDIR;
  2226  		a->offset = n->xoffset;
  2227  		a->sym = nil;
  2228  		break;
  2229  
  2230  	case OCFUNC:
  2231  		naddr(n->left, a, canemitcode);
  2232  		a->sym = linksym(n->left->sym);
  2233  		break;
  2234  
  2235  	case ONAME:
  2236  		a->etype = 0;
  2237  		a->width = 0;
  2238  		if(n->type != T) {
  2239  			a->etype = simtype[n->type->etype];
  2240  			dowidth(n->type);
  2241  			a->width = n->type->width;
  2242  		}
  2243  		a->offset = n->xoffset;
  2244  		s = n->sym;
  2245  		a->node = n->orig;
  2246  		//if(a->node >= (Node*)&n)
  2247  		//	fatal("stack node");
  2248  		if(s == S)
  2249  			s = lookup(".noname");
  2250  		if(n->method) {
  2251  			if(n->type != T)
  2252  			if(n->type->sym != S)
  2253  			if(n->type->sym->pkg != nil)
  2254  				s = pkglookup(s->name, n->type->sym->pkg);
  2255  		}
  2256  
  2257  		switch(n->class) {
  2258  		default:
  2259  			fatal("naddr: ONAME class %S %d\n", n->sym, n->class);
  2260  		case PEXTERN:
  2261  			a->type = D_EXTERN;
  2262  			break;
  2263  		case PAUTO:
  2264  			a->type = D_AUTO;
  2265  			break;
  2266  		case PPARAM:
  2267  		case PPARAMOUT:
  2268  			a->type = D_PARAM;
  2269  			break;
  2270  		case PFUNC:
  2271  			a->index = D_EXTERN;
  2272  			a->type = D_ADDR;
  2273  			s = funcsym(s);
  2274  			break;
  2275  		}
  2276  		a->sym = linksym(s);
  2277  		break;
  2278  
  2279  	case OLITERAL:
  2280  		switch(n->val.ctype) {
  2281  		default:
  2282  			fatal("naddr: const %lT", n->type);
  2283  			break;
  2284  		case CTFLT:
  2285  			a->type = D_FCONST;
  2286  			a->u.dval = mpgetflt(n->val.u.fval);
  2287  			break;
  2288  		case CTINT:
  2289  		case CTRUNE:
  2290  			a->sym = nil;
  2291  			a->type = D_CONST;
  2292  			a->offset = mpgetfix(n->val.u.xval);
  2293  			break;
  2294  		case CTSTR:
  2295  			datagostring(n->val.u.sval, a);
  2296  			break;
  2297  		case CTBOOL:
  2298  			a->sym = nil;
  2299  			a->type = D_CONST;
  2300  			a->offset = n->val.u.bval;
  2301  			break;
  2302  		case CTNIL:
  2303  			a->sym = nil;
  2304  			a->type = D_CONST;
  2305  			a->offset = 0;
  2306  			break;
  2307  		}
  2308  		break;
  2309  
  2310  	case OADDR:
  2311  		naddr(n->left, a, canemitcode);
  2312  		if(a->type >= D_INDIR) {
  2313  			a->type -= D_INDIR;
  2314  			break;
  2315  		}
  2316  		if(a->type == D_EXTERN || a->type == D_STATIC ||
  2317  		   a->type == D_AUTO || a->type == D_PARAM)
  2318  			if(a->index == D_NONE) {
  2319  				a->index = a->type;
  2320  				a->type = D_ADDR;
  2321  				break;
  2322  			}
  2323  		fatal("naddr: OADDR\n");
  2324  	
  2325  	case OITAB:
  2326  		// itable of interface value
  2327  		naddr(n->left, a, canemitcode);
  2328  		if(a->type == D_CONST && a->offset == 0)
  2329  			break;	// len(nil)
  2330  		a->etype = tptr;
  2331  		a->width = widthptr;
  2332  		break;
  2333  
  2334  	case OSPTR:
  2335  		// pointer in a string or slice
  2336  		naddr(n->left, a, canemitcode);
  2337  		if(a->type == D_CONST && a->offset == 0)
  2338  			break;	// ptr(nil)
  2339  		a->etype = simtype[tptr];
  2340  		a->offset += Array_array;
  2341  		a->width = widthptr;
  2342  		break;
  2343  
  2344  	case OLEN:
  2345  		// len of string or slice
  2346  		naddr(n->left, a, canemitcode);
  2347  		if(a->type == D_CONST && a->offset == 0)
  2348  			break;	// len(nil)
  2349  		a->etype = TUINT32;
  2350  		a->offset += Array_nel;
  2351  		a->width = 4;
  2352  		break;
  2353  
  2354  	case OCAP:
  2355  		// cap of string or slice
  2356  		naddr(n->left, a, canemitcode);
  2357  		if(a->type == D_CONST && a->offset == 0)
  2358  			break;	// cap(nil)
  2359  		a->etype = TUINT32;
  2360  		a->offset += Array_cap;
  2361  		a->width = 4;
  2362  		break;
  2363  
  2364  //	case OADD:
  2365  //		if(n->right->op == OLITERAL) {
  2366  //			v = n->right->vconst;
  2367  //			naddr(n->left, a, canemitcode);
  2368  //		} else
  2369  //		if(n->left->op == OLITERAL) {
  2370  //			v = n->left->vconst;
  2371  //			naddr(n->right, a, canemitcode);
  2372  //		} else
  2373  //			goto bad;
  2374  //		a->offset += v;
  2375  //		break;
  2376  
  2377  	}
  2378  }
  2379  
  2380  int
  2381  dotaddable(Node *n, Node *n1)
  2382  {
  2383  	int o;
  2384  	int64 oary[10];
  2385  	Node *nn;
  2386  
  2387  	if(n->op != ODOT)
  2388  		return 0;
  2389  
  2390  	o = dotoffset(n, oary, &nn);
  2391  	if(nn != N && nn->addable && o == 1 && oary[0] >= 0) {
  2392  		*n1 = *nn;
  2393  		n1->type = n->type;
  2394  		n1->xoffset += oary[0];
  2395  		return 1;
  2396  	}
  2397  	return 0;
  2398  }
  2399  
  2400  void
  2401  sudoclean(void)
  2402  {
  2403  }
  2404  
  2405  int
  2406  sudoaddable(int as, Node *n, Addr *a)
  2407  {
  2408  	USED(as);
  2409  	USED(n);
  2410  	USED(a);
  2411  
  2412  	return 0;
  2413  }