src/cpu/mips/vm/assembler_mips.hpp

Tue, 31 May 2016 00:22:06 -0400

author
aoqi
date
Tue, 31 May 2016 00:22:06 -0400
changeset 16
3cedde979d75
parent 14
92759d406e78
child 29
6c147e7e4605
permissions
-rw-r--r--

[Code Reorganization] load_two_bytes_from_at_bcp -> get_2_byte_integer_at_bcp
remove useless MacroAssembler::store_two_byts_to_at_bcp
change MacroAssembler::load_two_bytes_from_at_bcp to InterpreterMacroAssembler::get_2_byte_integer_at_bcp
change MacroAssembler::get_4_byte_integer_at_bcp to InterpreterMacroAssembler::get_4_byte_integer_at_bcp

     1 /*
     2  * Copyright (c) 1997, 2013, Oracle and/or its affiliates. All rights reserved.
     3  * Copyright (c) 2015, 2016, Loongson Technology. All rights reserved.
     4  * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
     5  *
     6  * This code is free software; you can redistribute it and/or modify it
     7  * under the terms of the GNU General Public License version 2 only, as
     8  * published by the Free Software Foundation.
     9  *
    10  * This code is distributed in the hope that it will be useful, but WITHOUT
    11  * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
    12  * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
    13  * version 2 for more details (a copy is included in the LICENSE file that
    14  * accompanied this code).
    15  *
    16  * You should have received a copy of the GNU General Public License version
    17  * 2 along with this work; if not, write to the Free Software Foundation,
    18  * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
    19  *
    20  * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
    21  * or visit www.oracle.com if you need additional information or have any
    22  * questions.
    23  *
    24  */
    26 #ifndef CPU_MIPS_VM_ASSEMBLER_MIPS_HPP
    27 #define CPU_MIPS_VM_ASSEMBLER_MIPS_HPP
    29 #include "asm/register.hpp"
    31 class BiasedLockingCounters;
    34 // Note: A register location is represented via a Register, not
    35 //       via an address for efficiency & simplicity reasons.
    37 class ArrayAddress;
    39 class Address VALUE_OBJ_CLASS_SPEC {
    41 public:
    42   enum ScaleFactor {
    43     no_scale = -1,
    44     times_1  =  0,
    45     times_2  =  1,
    46     times_4  =  2,
    47     times_8  =  3,
    48     times_ptr = LP64_ONLY(times_8) NOT_LP64(times_4)
    49   };
    51   static ScaleFactor times(int size) {
    52     assert(size >= 1 && size <= 8 && is_power_of_2(size), "bad scale size");
    53     if (size == 8)  return times_8;
    54     if (size == 4)  return times_4;
    55     if (size == 2)  return times_2;
    56     return times_1;
    57   }
    59  private:
    60   Register         _base;
    61   Register         _index;
    62   ScaleFactor      _scale;
    63   int              _disp;
    64   RelocationHolder _rspec;
    66   // Easily misused constructors make them private
    67   // %%% can we make these go away?
    68   //FIXME aoqi
    69   //NOT_LP64(Address(address loc, RelocationHolder spec);)
    70   Address(address loc, RelocationHolder spec);
    71   Address(int disp, address loc, relocInfo::relocType rtype);
    72   Address(int disp, address loc, RelocationHolder spec);
    74  public:
    76  int disp() { return _disp; }
    77   // creation
    78   Address()
    79     : _base(noreg),
    80       _index(noreg),
    81       _scale(no_scale),
    82       _disp(0) {
    83   }
    85   // No default displacement otherwise Register can be implicitly
    86   // converted to 0(Register) which is quite a different animal.
    88   Address(Register base, int disp)
    89     : _base(base),
    90       _index(noreg),
    91       _scale(no_scale),
    92       _disp(disp) {
    93   }
    95   Address(Register base) 
    96    : _base(base),
    97      _index(noreg),
    98      _scale(no_scale),
    99      _disp(0) {
   100   }
   102   Address(Register base, Register index, ScaleFactor scale, int disp = 0)
   103     : _base (base),
   104       _index(index),
   105       _scale(scale),
   106       _disp (disp) {
   107     assert(!index->is_valid() == (scale == Address::no_scale),
   108            "inconsistent address");
   109   }
   111   // The following two overloads are used in connection with the
   112   // ByteSize type (see sizes.hpp).  They simplify the use of
   113   // ByteSize'd arguments in assembly code. Note that their equivalent
   114   // for the optimized build are the member functions with int disp
   115   // argument since ByteSize is mapped to an int type in that case.
   116   //
   117   // Note: DO NOT introduce similar overloaded functions for WordSize
   118   // arguments as in the optimized mode, both ByteSize and WordSize
   119   // are mapped to the same type and thus the compiler cannot make a
   120   // distinction anymore (=> compiler errors).
   122 #ifdef ASSERT
   123   Address(Register base, ByteSize disp)
   124     : _base(base),
   125       _index(noreg),
   126       _scale(no_scale),
   127       _disp(in_bytes(disp)) {
   128   }
   130   Address(Register base, Register index, ScaleFactor scale, ByteSize disp)
   131     : _base(base),
   132       _index(index),
   133       _scale(scale),
   134       _disp(in_bytes(disp)) {
   135     assert(!index->is_valid() == (scale == Address::no_scale),
   136            "inconsistent address");
   137   }
   138 #endif // ASSERT
   140   // accessors
   141   bool        uses(Register reg) const { return _base == reg || _index == reg; }
   142   Register    base()             const { return _base;  }
   143   Register    index()            const { return _index; }
   144   ScaleFactor scale()            const { return _scale; }
   145   int         disp()             const { return _disp;  }
   147   // Convert the raw encoding form into the form expected by the constructor for
   148   // Address.  An index of 4 (rsp) corresponds to having no index, so convert
   149   // that to noreg for the Address constructor.
   150   //static Address make_raw(int base, int index, int scale, int disp);
   152   static Address make_array(ArrayAddress);
   154 /*
   155  private:
   156   bool base_needs_rex() const {
   157     return _base != noreg && _base->encoding() >= 8;
   158   }
   160   bool index_needs_rex() const {
   161     return _index != noreg &&_index->encoding() >= 8;
   162   }
   164   relocInfo::relocType reloc() const { return _rspec.type(); }
   165 */
   166   friend class Assembler;
   167   friend class MacroAssembler;
   168   friend class LIR_Assembler; // base/index/scale/disp
   169 };
   172 // Calling convention
   173 class Argument VALUE_OBJ_CLASS_SPEC {
   174  private:
   175 	int _number;
   176  public:
   177 	enum {
   178 #ifdef _LP64
   179 	  n_register_parameters = 8,   // 8 integer registers used to pass parameters
   180 	  n_float_register_parameters = 8   // 4 float registers used to pass parameters
   181 #else
   182 	    n_register_parameters = 4,   // 4 integer registers used to pass parameters
   183 	  n_float_register_parameters = 4   // 4 float registers used to pass parameters
   184 #endif
   185 	};
   187 	Argument(int number):_number(number){ }
   188 	Argument successor() {return Argument(number() + 1);}
   190 	int number()const {return _number;}
   191 	bool is_Register()const {return _number < n_register_parameters;}
   192 	bool is_FloatRegister()const {return _number < n_float_register_parameters;}
   194 	Register as_Register()const {
   195 		assert(is_Register(), "must be a register argument");
   196 		return ::as_Register(A0->encoding() + _number);
   197 	}
   198 	FloatRegister  as_FloatRegister()const {
   199 		assert(is_FloatRegister(), "must be a float register argument");
   200 		return ::as_FloatRegister(F12->encoding() + _number);
   201 	}
   203 	Address as_caller_address()const {return Address(SP, (number() LP64_ONLY( -n_register_parameters)) * wordSize);}
   204 };
   208 //
   209 // AddressLiteral has been split out from Address because operands of this type
   210 // need to be treated specially on 32bit vs. 64bit platforms. By splitting it out
   211 // the few instructions that need to deal with address literals are unique and the
   212 // MacroAssembler does not have to implement every instruction in the Assembler
   213 // in order to search for address literals that may need special handling depending
   214 // on the instruction and the platform. As small step on the way to merging i486/amd64
   215 // directories.
   216 //
   217 class AddressLiteral VALUE_OBJ_CLASS_SPEC {
   218   friend class ArrayAddress;
   219   RelocationHolder _rspec;
   220   // Typically we use AddressLiterals we want to use their rval
   221   // However in some situations we want the lval (effect address) of the item.
   222   // We provide a special factory for making those lvals.
   223   bool _is_lval;
   225   // If the target is far we'll need to load the ea of this to
   226   // a register to reach it. Otherwise if near we can do rip
   227   // relative addressing.
   229   address          _target;
   231  protected:
   232   // creation
   233   AddressLiteral()
   234     : _is_lval(false),
   235       _target(NULL)
   236   {}
   238   public:
   240   AddressLiteral(address target, relocInfo::relocType rtype);
   242   AddressLiteral(address target, RelocationHolder const& rspec)
   243     : _rspec(rspec),
   244       _is_lval(false),
   245       _target(target)
   246   {}
   247 #ifdef _LP64
   248    // 32-bit complains about a multiple declaration for int*.
   249    AddressLiteral(intptr_t* addr, relocInfo::relocType rtype = relocInfo::none)
   250      : _target((address) addr),
   251        _rspec(rspec_from_rtype(rtype, (address) addr)) {}
   252 #endif
   255   AddressLiteral addr() {
   256     AddressLiteral ret = *this;
   257     ret._is_lval = true;
   258     return ret;
   259   }
   262  private:
   264   address target() { return _target; }
   265   bool is_lval() { return _is_lval; }
   267   relocInfo::relocType reloc() const { return _rspec.type(); }
   268   const RelocationHolder& rspec() const { return _rspec; }
   270   friend class Assembler;
   271   friend class MacroAssembler;
   272   friend class Address;
   273   friend class LIR_Assembler;
   274  RelocationHolder rspec_from_rtype(relocInfo::relocType rtype, address addr) {
   275    switch (rtype) {
   276    case relocInfo::external_word_type:
   277      return external_word_Relocation::spec(addr);
   278    case relocInfo::internal_word_type:
   279     return internal_word_Relocation::spec(addr);
   280    case relocInfo::opt_virtual_call_type:
   281     return opt_virtual_call_Relocation::spec();
   282    case relocInfo::static_call_type:
   283      return static_call_Relocation::spec();
   284    case relocInfo::runtime_call_type:
   285      return runtime_call_Relocation::spec();
   286    case relocInfo::poll_type:
   287    case relocInfo::poll_return_type:
   288      return Relocation::spec_simple(rtype);
   289    case relocInfo::none:
   290    case relocInfo::oop_type:
   291      // Oops are a special case. Normally they would be their own section
   292      // but in cases like icBuffer they are literals in the code stream that
   293      // we don't have a section for. We use none so that we get a literal address
   294      // which is always patchable.
   295      return RelocationHolder();
   296    default: 
   297      ShouldNotReachHere();
   298      return RelocationHolder();
   299  }
   300 }
   302 };
   304 // Convience classes
   305 class RuntimeAddress: public AddressLiteral {
   307   public:
   309   RuntimeAddress(address target) : AddressLiteral(target, relocInfo::runtime_call_type) {}
   311 };
   313 class OopAddress: public AddressLiteral {
   315   public:
   317   OopAddress(address target) : AddressLiteral(target, relocInfo::oop_type){}
   319 };
   321 class ExternalAddress: public AddressLiteral {
   323   public:
   325   ExternalAddress(address target) : AddressLiteral(target, relocInfo::external_word_type){}
   327 };
   329 class InternalAddress: public AddressLiteral {
   331   public:
   333   InternalAddress(address target) : AddressLiteral(target, relocInfo::internal_word_type) {}
   335 };
   337 // x86 can do array addressing as a single operation since disp can be an absolute
   338 // address amd64 can't. We create a class that expresses the concept but does extra
   339 // magic on amd64 to get the final result
   341 class ArrayAddress VALUE_OBJ_CLASS_SPEC {
   342   private:
   344   AddressLiteral _base;
   345   Address        _index;
   347   public:
   349   ArrayAddress() {};
   350   ArrayAddress(AddressLiteral base, Address index): _base(base), _index(index) {};
   351   AddressLiteral base() { return _base; }
   352   Address index() { return _index; }
   354 };
   356 const int FPUStateSizeInWords = NOT_LP64(27) LP64_ONLY( 512 / wordSize);
   358 // The MIPS LOONGSON Assembler: Pure assembler doing NO optimizations on the instruction
   359 // level ; i.e., what you write is what you get. The Assembler is generating code into 
   360 // a CodeBuffer.
   362 class Assembler : public AbstractAssembler  {
   363   friend class AbstractAssembler; // for the non-virtual hack
   364   friend class LIR_Assembler; // as_Address()
   365   friend class StubGenerator;
   367   public:
   368   enum ops {
   369 		special_op  = 0x00,
   370 		regimm_op   = 0x01,
   371   	j_op        = 0x02,
   372   	jal_op      = 0x03,
   373 	  beq_op      = 0x04,
   374 	  bne_op      = 0x05,
   375 	  blez_op     = 0x06,
   376 	  bgtz_op     = 0x07,
   377 	  addi_op     = 0x08,
   378 	  addiu_op    = 0x09,
   379 	  slti_op     = 0x0a,
   380 	  sltiu_op    = 0x0b,
   381 	  andi_op     = 0x0c,
   382 	  ori_op      = 0x0d,
   383 	  xori_op     = 0x0e,
   384 	  lui_op      = 0x0f,
   385 	  cop0_op     = 0x10,
   386 	  cop1_op     = 0x11,
   387 	  cop2_op     = 0x12,
   388 	  cop3_op     = 0x13,
   389 	  beql_op     = 0x14,
   390 	  bnel_op     = 0x15,
   391 	  blezl_op    = 0x16,
   392 	  bgtzl_op    = 0x17,
   393 	  daddi_op    = 0x18,
   394 	  daddiu_op   = 0x19,
   395 	  ldl_op      = 0x1a,
   396 	  ldr_op      = 0x1b,
   397 	  lb_op       = 0x20,
   398 	  lh_op       = 0x21,
   399 	  lwl_op      = 0x22,
   400 	  lw_op       = 0x23,
   401 	  lbu_op      = 0x24,
   402 	  lhu_op      = 0x25,
   403     lwr_op      = 0x26,
   404     lwu_op      = 0x27,
   405     sb_op       = 0x28,
   406     sh_op       = 0x29,
   407     swl_op      = 0x2a,
   408 	  sw_op       = 0x2b,
   409 	  sdl_op      = 0x2c,
   410 	  sdr_op      = 0x2d,
   411 	  swr_op      = 0x2e,
   412 	  cache_op    = 0x2f,
   413 	  ll_op       = 0x30,
   414 	  lwc1_op     = 0x31,
   415 	  lld_op      = 0x34,
   416 	  ldc1_op     = 0x35,
   417 	  ld_op       = 0x37,
   418 	  sc_op       = 0x38,
   419 	  swc1_op     = 0x39,
   420 	  scd_op      = 0x3c,
   421 	  sdc1_op     = 0x3d,
   422 	  sd_op       = 0x3f
   423   };
   425 	static	const char *ops_name[];
   427 	//special family, the opcode is in low 6 bits. 
   428 	enum special_ops {
   429 		sll_op			= 0x00,
   430 		srl_op			= 0x02,
   431 		sra_op			= 0x03,
   432 		sllv_op			= 0x04,
   433 		srlv_op			= 0x06,
   434 		srav_op 		= 0x07,
   435 		jr_op				= 0x08,
   436 		jalr_op			= 0x09,
   437 		syscall_op	= 0x0c,
   438 		break_op		= 0x0d,
   439 		sync_op			= 0x0f,
   440 		mfhi_op			= 0x10,
   441 		mthi_op			= 0x11,
   442 		mflo_op			= 0x12,
   443 		mtlo_op			= 0x13,
   444 		dsllv_op		= 0x14,
   445 		dsrlv_op		= 0x16,
   446 		dsrav_op		= 0x17,
   447 		mult_op			= 0x18,
   448 		multu_op 		= 0x19,
   449 		div_op			= 0x1a,
   450 		divu_op			= 0x1b,
   451 		dmult_op		= 0x1c,
   452 		dmultu_op		= 0x1d,
   453 		ddiv_op			= 0x1e,
   454 		ddivu_op		= 0x1f,
   455 		add_op			= 0x20,
   456 		addu_op			= 0x21,
   457 		sub_op			= 0x22,
   458 		subu_op			= 0x23,
   459 		and_op			= 0x24,
   460 		or_op				= 0x25,
   461 		xor_op			= 0x26,
   462 		nor_op			= 0x27,
   463 		slt_op			= 0x2a,
   464 		sltu_op			= 0x2b,
   465 		dadd_op			= 0x2c,
   466 		daddu_op		= 0x2d,
   467 		dsub_op			= 0x2e,
   468 		dsubu_op		= 0x2f,
   469 		tge_op			= 0x30,
   470 		tgeu_op			= 0x31,
   471 		tlt_op			= 0x32,
   472 		tltu_op			= 0x33,
   473 		teq_op			= 0x34,
   474 		tne_op			= 0x36,
   475 		dsll_op			= 0x38,
   476 		dsrl_op			= 0x3a,
   477 		dsra_op			= 0x3b,
   478 		dsll32_op		= 0x3c,
   479 		dsrl32_op		= 0x3e,
   480 		dsra32_op		= 0x3f
   481 	};
   483 	static	const char* special_name[]; 
   485 	//regimm family, the opcode is in rt[16...20], 5 bits
   486 	enum regimm_ops {
   487 		bltz_op			= 0x00,
   488 		bgez_op			= 0x01,
   489 		bltzl_op		= 0x02,
   490 		bgezl_op		= 0x03,
   491 		tgei_op			= 0x08,
   492 		tgeiu_op		= 0x09,
   493 		tlti_op			= 0x0a,
   494 		tltiu_op		= 0x0b,
   495 		teqi_op			= 0x0c,
   496 		tnei_op			= 0x0e,
   497 		bltzal_op		= 0x10,
   498 		bgezal_op		= 0x11,
   499 		bltzall_op	= 0x12,
   500 		bgezall_op	= 0x13,
   501 	};
   503 	static	const char* regimm_name[]; 
   505 	//copx family,the op in rs, 5 bits
   506 	enum cop_ops {
   507 		mf_op				= 0x00,
   508 		dmf_op			= 0x01,
   509 		cf_op				= 0x02,
   510 		mt_op				= 0x04,
   511 		dmt_op			= 0x05,
   512 		ct_op				= 0x06,
   513 		bc_op				= 0x08,
   514 		single_fmt	= 0x10,
   515 		double_fmt	= 0x11,
   516 		word_fmt		= 0x14,
   517 		long_fmt		= 0x15
   518 	};
   520 	enum bc_ops {
   521 		bcf_op			= 0x00,
   522 		bct_op			= 0x01,
   523 		bcfl_op			= 0x02,
   524 		bctl_op			= 0x03,
   525 	};
   527 	enum c_conds {
   528 		f_cond			= 0x30,
   529 		un_cond			= 0x31,
   530 		eq_cond			= 0x32,
   531 		ueq_cond		= 0x33,
   532 		olt_cond		= 0x34,
   533 		ult_cond		= 0x35,
   534 		ole_cond		= 0x36,
   535 		ule_cond		= 0x37,
   536 		sf_cond			= 0x38,
   537 		ngle_cond		= 0x39,
   538 		seq_cond		= 0x3a,
   539 		ngl_cond		= 0x3b,
   540 		lt_cond			= 0x3c,
   541 		nge_cond		= 0x3d,
   542 		le_cond			= 0x3e,
   543 		ngt_cond		= 0x3f
   544 	};
   546 	//low 6 bits of cp1 instruction
   547 	enum float_ops {
   548 		fadd_op			= 0x00,
   549 		fsub_op			= 0x01,
   550 		fmul_op			= 0x02,
   551 		fdiv_op			= 0x03,
   552 		fsqrt_op		= 0x04,
   553 		fabs_op			= 0x05,
   554 		fmov_op			= 0x06,
   555 		fneg_op			= 0x07,
   556 		froundl_op	= 0x08,
   557 		ftruncl_op	= 0x09,
   558 		fceill_op		= 0x0a,
   559 		ffloorl_op	= 0x0b,
   560 		froundw_op 	= 0x0c,
   561 		ftruncw_op	= 0x0d,
   562 		fceilw_op 	= 0x0e,
   563 		ffloorw_op	= 0x0f,
   564 		fcvts_op		= 0x20,
   565 		fcvtd_op		= 0x21,
   566 		fcvtw_op		= 0x24,
   567 		fcvtl_op		= 0x25,
   568 		fpll_op		=0x2c,
   569 		fplu_op		=0x2d,
   570 		fpul_op		=0x2e,
   571 		fpuu_op		=0x2f,
   573 	};
   575   /* 2013.10.16 Jin: merge from OpenJDK 8 */
   576   enum WhichOperand {
   577     // input to locate_operand, and format code for relocations
   578     imm_operand  = 0,            // embedded 32-bit|64-bit immediate operand
   579     disp32_operand = 1,          // embedded 32-bit displacement or address
   580     call32_operand = 2,          // embedded 32-bit self-relative displacement
   581 #ifndef _LP64
   582     _WhichOperand_limit = 3
   583 #else
   584      narrow_oop_operand = 3,     // embedded 32-bit immediate narrow oop
   585     _WhichOperand_limit = 4
   586 #endif
   587   };
   589        /* Godson3 extension */
   590        enum godson3_ops {
   591                gsldx_op        = (0x36 << 26) | 0x3,
   592                gslwx_op        = (0x36 << 26) | 0x2,
   593        };
   595 	static const char* float_name[]; 
   597 	static int opcode(int insn) { return (insn>>26)&0x3f; }
   598 	static int rs(int insn) { return (insn>>21)&0x1f; }
   599 	static int rt(int insn) { return (insn>>16)&0x1f; }
   600 	static int rd(int insn) { return (insn>>11)&0x1f; }
   601 	static int sa(int insn) { return (insn>>6)&0x1f; }
   602 	static int special(int insn) { return insn&0x3f; }
   603 	static int imm_off(int insn) { return (short)low16(insn); }
   605 	static int low  (int x, int l) { return bitfield(x, 0, l); }
   606 	static int low16(int x)        { return low(x, 16); }
   607 	static int low26(int x)        { return low(x, 26); }
   609 protected:
   610 	//help methods for instruction ejection
   612 	//I-Type (Immediate)
   613 	// 31				 26 25        21 20      16 15    													0
   614 	//|   opcode   |			rs		|    rt    |						immediat						 |
   615 	//| 					 |						|					 |																 |
   616 	//			6							5					  5					 					16
   617 	static int insn_ORRI(int op, int rs, int rt, int imm) { return (op<<26) | (rs<<21) | (rt<<16) | low16(imm); } 
   619 	//R-Type (Register)
   620 	// 31				  26 25       21 20      16 15      11 10				 6 5			  0
   621 	//|   special   |			rs		|    rt    |	  rd	  | 		0		  |	 opcode  |
   622 	//| 0 0 0 0 0 0 |						|					 |					| 0 0 0 0 0 | 				 |
   623 	//			6							5					  5					 5					5						6
   624 	static int insn_RRRO(int rs, int rt, int rd,   int op) { return (rs<<21) | (rt<<16) | (rd<<11)  | op; }
   625 	static int insn_RRSO(int rt, int rd, int sa,   int op) { return (rt<<16) | (rd<<11) | (sa<<6)   | op; }
   626 	static int insn_RRCO(int rs, int rt, int code, int op) { return (rs<<21) | (rt<<16) | (code<<6) | op; }
   628 	static int insn_COP0(int op, int rt, int rd) { return (cop0_op<<26) | (op<<21) | (rt<<16) | (rd<<11); }
   629 	static int insn_COP1(int op, int rt, int fs) { return (cop1_op<<26) | (op<<21) | (rt<<16) | (fs<<11); }
   631 	static int insn_F3RO(int fmt, int ft, int fs, int fd, int func) { 
   632 		return (cop1_op<<26) | (fmt<<21) | (ft<<16) | (fs<<11) | (fd<<6) | func;
   633 	}
   636 	//static int low  (int x, int l) { return bitfield(x, 0, l); }
   637 	//static int low16(int x)        { return low(x, 16); }
   638 	//static int low26(int x)        { return low(x, 26); }
   640 	static int high  (int x, int l) { return bitfield(x, 32-l, l); }
   641 	static int high16(int x)        { return high(x, 16); }
   642 	static int high6 (int x)        { return high(x, 6); }
   644 	//get the offset field of jump/branch instruction
   645 	int offset(address entry) { 
   646 		assert(is_simm16((entry - pc() - 4) / 4), "change this code");
   647 		if (!is_simm16((entry - pc() - 4) / 4)) {
   648 			tty->print_cr("!!! is_simm16: %x", (entry - pc() - 4) / 4);
   649 		}
   650 		return (entry - pc() - 4) / 4; 
   651 	}
   654 public:
   655 	using AbstractAssembler::offset;
   657 	//sign expand with the sign bit is h
   658 	static int expand(int x, int h) { return -(x & (1<<h)) | x;	}
   660 	// mips lui/addiu is both sign extended, so if you wan't to use off32/imm32, you have to use the follow three
   661 	// by yjl 6/22/2005
   662 	static int split_low(int x) {
   663 		return (x & 0xffff);
   664 	}
   666 	static int split_high(int x) {
   667 		return ( (x >> 16) + ((x & 0x8000) != 0) ) & 0xffff;
   668 	}
   670 	static int merge(int low, int high) {
   671 		return expand(low, 15) + (high<<16);
   672 	}
   674 #ifdef _LP64
   675 	static intptr_t merge(intptr_t x0, intptr_t x16, intptr_t x32, intptr_t x48) {
   676 	  return (x48 << 48) | (x32 << 32) | (x16 << 16) | x0;
   677 	  /*
   678 	     return ((intptr_t)(long_at(0) & 0xffff) << 48) 
   679 	     + expand((intptr_t)(long_at(4) & 0xffff) << 32, 47)
   680 	     + expand((intptr_t)(long_at(12) & 0xffff) << 16, 31)
   681 	     + expand((intptr_t)(long_at(20) & 0xffff), 15);
   682 	     return expand(low, 15) + (high<<16);
   683 	   */
   684 	}
   685 #endif
   687 	// modified by spark 2005/08/18
   688 	static bool is_simm  (int x, int nbits) { return -( 1 << nbits-1 )  <= x   &&   x  <  ( 1 << nbits-1 ); }
   689 	static bool is_simm16(int x)            { return is_simm(x, 16); }
   691 	// test if imm can be coded in a instruction with 16-bit imm/off
   692 	// by yjl 6/23/2005
   693 	/*static bool fit_in_insn(int imm) {
   694 		return imm == (short)imm;
   695 	}*/
   697 	static bool fit_in_jal(int offset) {
   698 		return is_simm(offset, 26);
   699 	}
   702 	// test if entry can be filled in the jl/jal, 
   703 	// must be used just before you emit jl/jal 
   704 	// by yjl 6/27/2005 
   705 	bool fit_int_jal(address entry) {
   706 		return fit_in_jal(offset(entry));
   707 	}
   709 	bool fit_int_branch(address entry) {
   710 		return is_simm16(offset(entry));
   711 	}
   713 protected:
   714 #ifdef ASSERT
   715 	  #define CHECK_DELAY
   716 #endif
   717 #ifdef CHECK_DELAY
   718 	enum Delay_state { no_delay, at_delay_slot, filling_delay_slot } delay_state;
   719 #endif
   721 public:
   722 	void assert_not_delayed() {
   723 #ifdef CHECK_DELAY
   724 		assert_not_delayed("next instruction should not be a delay slot");
   725 #endif
   726 	}
   728 	void assert_not_delayed(const char* msg) {
   729 #ifdef CHECK_DELAY
   730 		//guarantee( delay_state == no_delay, msg );
   731 		//aoqi_test
   732 		if(delay_state != no_delay){
   733 		tty->print_cr("%s:%d, pc: %lx", __func__, __LINE__, pc());
   734 		}
   735 		assert(delay_state == no_delay, msg);
   736 #endif		
   737 	}
   739 protected:
   740 	// Delay slot helpers
   741 	// cti is called when emitting control-transfer instruction,
   742 	// BEFORE doing the emitting.
   743 	// Only effective when assertion-checking is enabled.
   745 	// called when emitting cti with a delay slot, AFTER emitting
   746 	void has_delay_slot() {
   747 #ifdef CHECK_DELAY
   748 		assert_not_delayed("just checking");
   749 		delay_state = at_delay_slot;
   750 #endif
   751 	}
   753 public:
   754 	Assembler* delayed() {
   755 #ifdef CHECK_DELAY
   756 		guarantee( delay_state == at_delay_slot, "delayed instructition is not in delay slot");
   757 		delay_state = filling_delay_slot;
   758 #endif
   759 		return this;						
   760 	}
   762 	void flush() {
   763 #ifdef CHECK_DELAY
   764 		guarantee( delay_state == no_delay, "ending code with a delay slot");
   765 #endif
   766 		AbstractAssembler::flush();
   767 	}
   769 	inline void emit_long(int);  // shadows AbstractAssembler::emit_long
   770 	inline void emit_data(int x) { emit_long(x); }
   771 	inline void emit_data(int, RelocationHolder const&);
   772 	inline void emit_data(int, relocInfo::relocType rtype);		
   773 	inline void check_delay();
   776   // Generic instructions
   777   // Does 32bit or 64bit as needed for the platform. In some sense these
   778   // belong in macro assembler but there is no need for both varieties to exist
   780 #ifndef _LP64
   781 	void add(Register rd, Register rs, Register rt)  { emit_long(insn_RRRO((int)rs->encoding(), (int)rt->encoding(), (int)rd->encoding(), add_op)); }
   782 	void addi(Register rt, Register rs, int imm)     { emit_long(insn_ORRI(addi_op, (int)rs->encoding(), (int)rt->encoding(), imm)); }
   783 	void addiu(Register rt, Register rs, int imm)    { emit_long(insn_ORRI(addiu_op, (int)rs->encoding(), (int)rt->encoding(), imm)); }
   784 	void addu(Register rd, Register rs, Register rt) { emit_long(insn_RRRO((int)rs->encoding(), (int)rt->encoding(), (int)rd->encoding(), addu_op)); }
   785 #else
   786 	void add(Register rd, Register rs, Register rt)  { dadd	  (rd, rs, rt); }
   787 	void add32(Register rd, Register rs, Register rt) { emit_long(insn_RRRO((int)rs->encoding(), (int)rt->encoding(), (int)rd->encoding(), add_op)); }
   788 	void addu32(Register rd, Register rs, Register rt) { emit_long(insn_RRRO((int)rs->encoding(), (int)rt->encoding(), (int)rd->encoding(), addu_op)); }
   789 	void addiu32(Register rt, Register rs, int imm)    { emit_long(insn_ORRI(addiu_op, (int)rs->encoding(), (int)rt->encoding(), imm)); }
   790 	void addi(Register rt, Register rs, int imm)     { daddi  (rt, rs, imm);}
   791 	void addiu(Register rt, Register rs, int imm)    { daddiu (rt, rs, imm);}
   792 	void addu(Register rd, Register rs, Register rt) { daddu  (rd, rs, rt);	}
   793 #endif
   795 	void andr(Register rd, Register rs, Register rt) { emit_long(insn_RRRO((int)rs->encoding(), (int)rt->encoding(), (int)rd->encoding(), and_op)); }
   796 	void andi(Register rt, Register rs, int imm)     { emit_long(insn_ORRI(andi_op, (int)rs->encoding(), (int)rt->encoding(), imm)); }
   798 	void beq    (Register rs, Register rt, int off) { emit_long(insn_ORRI(beq_op, (int)rs->encoding(), (int)rt->encoding(), off)); has_delay_slot(); }
   799 	void beql   (Register rs, Register rt, int off) { emit_long(insn_ORRI(beql_op, (int)rs->encoding(), (int)rt->encoding(), off)); has_delay_slot(); }
   800 	void bgez   (Register rs, int off) { emit_long(insn_ORRI(regimm_op, (int)rs->encoding(), bgez_op, off)); has_delay_slot(); }
   801 	void bgezal (Register rs, int off) { emit_long(insn_ORRI(regimm_op, (int)rs->encoding(), bgezal_op, off)); has_delay_slot(); }
   802 	void bgezall(Register rs, int off) { emit_long(insn_ORRI(regimm_op, (int)rs->encoding(), bgezall_op, off)); has_delay_slot(); }
   803 	void bgezl  (Register rs, int off) { emit_long(insn_ORRI(regimm_op, (int)rs->encoding(), bgezl_op, off)); has_delay_slot(); }
   804 	void bgtz   (Register rs, int off) { emit_long(insn_ORRI(bgtz_op,   (int)rs->encoding(), 0, off)); has_delay_slot(); }
   805 	void bgtzl  (Register rs, int off) { emit_long(insn_ORRI(bgtzl_op,  (int)rs->encoding(), 0, off)); has_delay_slot(); }
   806 	void blez   (Register rs, int off) { emit_long(insn_ORRI(blez_op,   (int)rs->encoding(), 0, off)); has_delay_slot(); }
   807 	void blezl  (Register rs, int off) { emit_long(insn_ORRI(blezl_op,  (int)rs->encoding(), 0, off)); has_delay_slot(); }
   808 	void bltz   (Register rs, int off) { emit_long(insn_ORRI(regimm_op, (int)rs->encoding(), bltz_op, off)); has_delay_slot(); }
   809 	void bltzal (Register rs, int off) { emit_long(insn_ORRI(regimm_op, (int)rs->encoding(), bltzal_op, off)); has_delay_slot(); }
   810 	void bltzall(Register rs, int off) { emit_long(insn_ORRI(regimm_op, (int)rs->encoding(), bltzall_op, off)); has_delay_slot(); }
   811 	void bltzl  (Register rs, int off) { emit_long(insn_ORRI(regimm_op, (int)rs->encoding(), bltzl_op, off)); has_delay_slot(); }
   812 	void bne    (Register rs, Register rt, int off) { emit_long(insn_ORRI(bne_op,  (int)rs->encoding(), (int)rt->encoding(), off)); has_delay_slot(); }
   813 	void bnel   (Register rs, Register rt, int off) { emit_long(insn_ORRI(bnel_op, (int)rs->encoding(), (int)rt->encoding(), off)); has_delay_slot(); }
   814 	void brk    (int code) { emit_long(break_op | (code<<16)); }
   816 	void beq    (Register rs, Register rt, address entry) { beq(rs, rt, offset(entry)); }
   817 	void beql   (Register rs, Register rt, address entry) { beql(rs, rt, offset(entry));}
   818 	void bgez   (Register rs, address entry) { bgez   (rs, offset(entry)); }
   819 	void bgezal (Register rs, address entry) { bgezal (rs, offset(entry)); }
   820 	void bgezall(Register rs, address entry) { bgezall(rs, offset(entry)); }
   821 	void bgezl  (Register rs, address entry) { bgezl  (rs, offset(entry)); }
   822 	void bgtz   (Register rs, address entry) { bgtz   (rs, offset(entry)); }
   823 	void bgtzl  (Register rs, address entry) { bgtzl  (rs, offset(entry)); }
   824 	void blez   (Register rs, address entry) { blez   (rs, offset(entry)); }
   825 	void blezl  (Register rs, address entry) { blezl  (rs, offset(entry)); }
   826 	void bltz   (Register rs, address entry) { bltz   (rs, offset(entry)); }
   827 	void bltzal (Register rs, address entry) { bltzal (rs, offset(entry)); }
   828 	void bltzall(Register rs, address entry) { bltzall(rs, offset(entry)); }
   829 	void bltzl  (Register rs, address entry) { bltzl  (rs, offset(entry)); }
   830 	void bne    (Register rs, Register rt, address entry) { bne(rs, rt, offset(entry)); }
   831 	void bnel   (Register rs, Register rt, address entry) { bnel(rs, rt, offset(entry)); }
   833 	void beq    (Register rs, Register rt, Label& L) { beq(rs, rt, target(L)); }
   834 	void beql   (Register rs, Register rt, Label& L) { beql(rs, rt, target(L)); }
   835 	void bgez   (Register rs, Label& L){ bgez   (rs, target(L)); }
   836 	void bgezal (Register rs, Label& L){ bgezal (rs, target(L)); }
   837 	void bgezall(Register rs, Label& L){ bgezall(rs, target(L)); }
   838 	void bgezl  (Register rs, Label& L){ bgezl  (rs, target(L)); }
   839 	void bgtz   (Register rs, Label& L){ bgtz   (rs, target(L)); }
   840 	void bgtzl  (Register rs, Label& L){ bgtzl  (rs, target(L)); }
   841 	void blez   (Register rs, Label& L){ blez   (rs, target(L)); }
   842 	void blezl  (Register rs, Label& L){ blezl  (rs, target(L)); }
   843 	void bltz   (Register rs, Label& L){ bltz   (rs, target(L)); }
   844 	void bltzal (Register rs, Label& L){ bltzal (rs, target(L)); }
   845 	void bltzall(Register rs, Label& L){ bltzall(rs, target(L)); }
   846 	void bltzl  (Register rs, Label& L){ bltzl  (rs, target(L)); }
   847 	void bne    (Register rs, Register rt, Label& L){ bne(rs, rt, target(L)); }
   848 	void bnel   (Register rs, Register rt, Label& L){ bnel(rs, rt, target(L)); }
   850 	void dadd  (Register rd, Register rs, Register rt) { emit_long(insn_RRRO((int)rs->encoding(), (int)rt->encoding(), (int)rd->encoding(), dadd_op)); }
   851 	void daddi (Register rt, Register rs, int imm)     { emit_long(insn_ORRI(daddi_op,  (int)rs->encoding(), (int)rt->encoding(), imm)); }
   852 	void daddiu(Register rt, Register rs, int imm)     { emit_long(insn_ORRI(daddiu_op, (int)rs->encoding(), (int)rt->encoding(), imm)); }
   853 	void daddu (Register rd, Register rs, Register rt) { emit_long(insn_RRRO((int)rs->encoding(), (int)rt->encoding(), (int)rd->encoding(), daddu_op)); }
   854 	void ddiv  (Register rs, Register rt)              { emit_long(insn_RRRO((int)rs->encoding(), (int)rt->encoding(), 0, ddiv_op));	}
   855 	void ddivu (Register rs, Register rt)              { emit_long(insn_RRRO((int)rs->encoding(), (int)rt->encoding(), 0, ddivu_op)); }
   856 // Do mult and div need both 32-bit and 64-bit version? FIXME aoqi
   857 //#ifndef _LP64
   858 #if 1
   859 	void div   (Register rs, Register rt)              { emit_long(insn_RRRO((int)rs->encoding(), (int)rt->encoding(), 0, div_op)); }
   860 	void divu  (Register rs, Register rt)              { emit_long(insn_RRRO((int)rs->encoding(), (int)rt->encoding(), 0, divu_op)); }
   861 #else
   862 	void div   (Register rs, Register rt)              { ddiv (rs, rt);}
   863 	void divu  (Register rs, Register rt)              { ddivu(rs, rt);}
   864 #endif
   865 	void dmfc0 (Register rt, FloatRegister rd)         { emit_long(insn_COP0(dmf_op, (int)rt->encoding(), (int)rd->encoding())); }
   866 	void dmtc0 (Register rt, FloatRegister rd)         { emit_long(insn_COP0(dmt_op, (int)rt->encoding(), (int)rd->encoding())); }
   867 	void dmult (Register rs, Register rt)              { emit_long(insn_RRRO((int)rs->encoding(), (int)rt->encoding(), 0, dmult_op)); }
   868 	void dmultu(Register rs, Register rt)              { emit_long(insn_RRRO((int)rs->encoding(), (int)rt->encoding(), 0, dmultu_op)); }
   869 	void dsll  (Register rd, Register rt , int sa)     { emit_long(insn_RRSO((int)rt->encoding(), (int)rd->encoding(), sa, dsll_op)); }
   870 	void dsllv (Register rd, Register rt, Register rs) { emit_long(insn_RRRO((int)rs->encoding(), (int)rt->encoding(), (int)rd->encoding(), dsllv_op)); }	
   871 	void dsll32(Register rd, Register rt , int sa)     { emit_long(insn_RRSO((int)rt->encoding(), (int)rd->encoding(), sa, dsll32_op)); }
   872 	void dsra  (Register rd, Register rt , int sa)     { emit_long(insn_RRSO((int)rt->encoding(), (int)rd->encoding(), sa, dsra_op)); }
   873 	void dsrav (Register rd, Register rt, Register rs) { emit_long(insn_RRRO((int)rs->encoding(), (int)rt->encoding(), (int)rd->encoding(), dsrav_op)); }	
   874 	void dsra32(Register rd, Register rt , int sa)     { emit_long(insn_RRSO((int)rt->encoding(), (int)rd->encoding(), sa, dsra32_op)); }
   875 	void dsrl  (Register rd, Register rt , int sa)     { emit_long(insn_RRSO((int)rt->encoding(), (int)rd->encoding(), sa, dsrl_op)); }
   876 	void dsrlv (Register rd, Register rt, Register rs)  { emit_long(insn_RRRO((int)rs->encoding(), (int)rt->encoding(), (int)rd->encoding(), dsrlv_op)); }	
   877 	void dsrl32(Register rd, Register rt , int sa)     { emit_long(insn_RRSO((int)rt->encoding(), (int)rd->encoding(), sa, dsrl32_op)); }
   878 	void dsub  (Register rd, Register rs, Register rt) { emit_long(insn_RRRO((int)rs->encoding(), (int)rt->encoding(), (int)rd->encoding(), dsub_op)); }
   879 	void dsubu (Register rd, Register rs, Register rt) { emit_long(insn_RRRO((int)rs->encoding(), (int)rt->encoding(), (int)rd->encoding(), dsubu_op)); }
   881 	void b(int off)       { beq(R0, R0, off); }
   882 	void b(address entry) { b(offset(entry)); }
   883 	void b(Label& L)      { b(target(L)); }
   885 	void j(address entry);
   886 	void jal(address entry);
   888 	void jalr(Register rd, Register rs) { emit_long( ((int)rs->encoding()<<21) | ((int)rd->encoding()<<11) | jalr_op); has_delay_slot(); }
   889 	void jalr(Register rs)              { jalr(RA, rs); }
   890 	void jalr()                         { jalr(T9); }
   892 	void jr(Register rs) { emit_long(((int)rs->encoding()<<21) | jr_op); has_delay_slot(); }
   894 	void lb (Register rt, Register base, int off) { emit_long(insn_ORRI(lb_op,  (int)base->encoding(), (int)rt->encoding(), off)); }
   895 	void lbu(Register rt, Register base, int off) { emit_long(insn_ORRI(lbu_op, (int)base->encoding(), (int)rt->encoding(), off)); }
   896 	void ld (Register rt, Register base, int off) { emit_long(insn_ORRI(ld_op,  (int)base->encoding(), (int)rt->encoding(), off)); }
   897 	void ldl(Register rt, Register base, int off) { emit_long(insn_ORRI(ldl_op, (int)base->encoding(), (int)rt->encoding(), off)); }
   898 	void ldr(Register rt, Register base, int off) { emit_long(insn_ORRI(ldr_op, (int)base->encoding(), (int)rt->encoding(), off)); }
   899 	void lh (Register rt, Register base, int off) { emit_long(insn_ORRI(lh_op,  (int)base->encoding(), (int)rt->encoding(), off)); }
   900 	void lhu(Register rt, Register base, int off) { emit_long(insn_ORRI(lhu_op, (int)base->encoding(), (int)rt->encoding(), off)); }
   901 	void ll (Register rt, Register base, int off) { emit_long(insn_ORRI(ll_op,  (int)base->encoding(), (int)rt->encoding(), off)); }
   902 	void lld(Register rt, Register base, int off) { emit_long(insn_ORRI(lld_op, (int)base->encoding(), (int)rt->encoding(), off)); }
   903 	void lui(Register rt, int imm)                { emit_long(insn_ORRI(lui_op, 0, (int)rt->encoding(), imm)); }
   904 	void lw (Register rt, Register base, int off) { emit_long(insn_ORRI(lw_op,  (int)base->encoding(), (int)rt->encoding(), off)); }
   905 	void lwl(Register rt, Register base, int off) { emit_long(insn_ORRI(lwl_op, (int)base->encoding(), (int)rt->encoding(), off)); }
   906 	void lwr(Register rt, Register base, int off) { emit_long(insn_ORRI(lwr_op, (int)base->encoding(), (int)rt->encoding(), off)); }
   907 	void lwu(Register rt, Register base, int off) { emit_long(insn_ORRI(lwu_op, (int)base->encoding(), (int)rt->encoding(), off)); }
   909 	void lb (Register rt, Address src);
   910 	void lbu(Register rt, Address src);
   911 	void ld (Register rt, Address src);
   912 	void ldl(Register rt, Address src);
   913 	void ldr(Register rt, Address src);
   914 	void lh (Register rt, Address src);
   915 	void lhu(Register rt, Address src);
   916 	void ll (Register rt, Address src);
   917 	void lld(Register rt, Address src);
   918 	void lw (Register rt, Address src);
   919 	void lwl(Register rt, Address src);
   920 	void lwr(Register rt, Address src);
   921 	void lwu(Register rt, Address src);
   922 	void lea(Register rt, Address src);
   924 	void mfc0 (Register rt, Register rd) { emit_long(insn_COP0(mf_op, (int)rt->encoding(), (int)rd->encoding())); }
   925 	void mfhi (Register rd)              { emit_long( ((int)rd->encoding()<<11) | mfhi_op ); }	
   926 	void mflo (Register rd)              { emit_long( ((int)rd->encoding()<<11) | mflo_op ); }	
   927 	void mtc0 (Register rt, Register rd) { emit_long(insn_COP0(mt_op, (int)rt->encoding(), (int)rd->encoding())); }
   928 	void mthi (Register rs)              { emit_long( ((int)rs->encoding()<<21) | mthi_op ); }	
   929 	void mtlo (Register rs)              { emit_long( ((int)rs->encoding()<<21) | mtlo_op ); }	
   930 // Do mult and div need both 32-bit and 64-bit version? FIXME aoqi
   931 //#ifndef _LP64
   932 #if 1
   933 	void mult (Register rs, Register rt) { emit_long(insn_RRRO((int)rs->encoding(), (int)rt->encoding(), 0, mult_op)); }
   934 	void multu(Register rs, Register rt) { emit_long(insn_RRRO((int)rs->encoding(), (int)rt->encoding(), 0, multu_op)); }
   935 #else
   936 	void mult (Register rs, Register rt) { dmult  (rs, rt); }
   937 	void multu(Register rs, Register rt) { dmultu (rs, rt); }
   938 #endif
   940 	void nor(Register rd, Register rs, Register rt) { emit_long(insn_RRRO((int)rs->encoding(), (int)rt->encoding(), (int)rd->encoding(), nor_op)); }
   942 	void orr(Register rd, Register rs, Register rt) { emit_long(insn_RRRO((int)rs->encoding(), (int)rt->encoding(), (int)rd->encoding(), or_op)); }
   943 	void ori(Register rt, Register rs, int imm)     { emit_long(insn_ORRI(ori_op, (int)rs->encoding(), (int)rt->encoding(), imm)); }
   945 	void sb   (Register rt, Register base, int off)     { emit_long(insn_ORRI(sb_op,    (int)base->encoding(), (int)rt->encoding(), off)); }
   946 	void sc   (Register rt, Register base, int off)     { emit_long(insn_ORRI(sc_op,    (int)base->encoding(), (int)rt->encoding(), off)); }
   947 	void scd  (Register rt, Register base, int off)     { emit_long(insn_ORRI(scd_op,   (int)base->encoding(), (int)rt->encoding(), off)); }
   948 	void sd   (Register rt, Register base, int off)     { emit_long(insn_ORRI(sd_op,    (int)base->encoding(), (int)rt->encoding(), off)); }
   949 	void sdl  (Register rt, Register base, int off)     { emit_long(insn_ORRI(sdl_op,   (int)base->encoding(), (int)rt->encoding(), off)); }
   950 	void sdr  (Register rt, Register base, int off)     { emit_long(insn_ORRI(sdr_op,   (int)base->encoding(), (int)rt->encoding(), off)); }
   951 	void sh   (Register rt, Register base, int off)     { emit_long(insn_ORRI(sh_op,    (int)base->encoding(), (int)rt->encoding(), off)); }
   952 //#ifndef _LP64
   953 #if 1
   954 	void sll  (Register rd, Register rt ,  int sa)      { emit_long(insn_RRSO((int)rt->encoding(),  (int)rd->encoding(),   sa,      sll_op)); }
   955 	void sllv (Register rd, Register rt,   Register rs) { emit_long(insn_RRRO((int)rs->encoding(),  (int)rt->encoding(),   (int)rd->encoding(), sllv_op)); }
   956 #else
   957 	void sll  (Register rd, Register rt ,  int sa)      { dsll  (rd, rt, sa);}
   958 	void sllv (Register rd, Register rt,   Register rs) { dsllv (rd, rt, rs); }
   959 #endif
   960 	void slt  (Register rd, Register rs,   Register rt) { emit_long(insn_RRRO((int)rs->encoding(),  (int)rt->encoding(),   (int)rd->encoding(), slt_op)); }	
   961 	void slti (Register rt, Register rs,   int imm)     { emit_long(insn_ORRI(slti_op,  (int)rs->encoding(),   (int)rt->encoding(), imm)); }
   962 	void sltiu(Register rt, Register rs,   int imm)     { emit_long(insn_ORRI(sltiu_op, (int)rs->encoding(),   (int)rt->encoding(), imm)); }
   963 	void sltu (Register rd, Register rs,   Register rt) { emit_long(insn_RRRO((int)rs->encoding(),  (int)rt->encoding(),   (int)rd->encoding(), sltu_op)); }	
   964 //#ifndef _LP64
   965 #if 1
   966 	void sra  (Register rd, Register rt ,  int sa)      { emit_long(insn_RRSO((int)rt->encoding(),  (int)rd->encoding(),   sa,      sra_op)); }
   967 	void srav (Register rd, Register rt,   Register rs) { emit_long(insn_RRRO((int)rs->encoding(),  (int)rt->encoding(),   (int)rd->encoding(), srav_op)); }	
   968 	void srl  (Register rd, Register rt ,  int sa)      { emit_long(insn_RRSO((int)rt->encoding(),  (int)rd->encoding(),   sa,      srl_op)); }
   969 	void srlv (Register rd, Register rt,   Register rs) { emit_long(insn_RRRO((int)rs->encoding(),  (int)rt->encoding(),   (int)rd->encoding(), srlv_op)); }	
   970 #else
   971 	void sra  (Register rd, Register rt ,  int sa)      { dsra  (rd, rt, sa); }
   972 	void srav (Register rd, Register rt,   Register rs) { dsrav (rd, rt, rs); }
   973 	void srl  (Register rd, Register rt ,  int sa)      { dsrl  (rd, rt, sa); }
   974 	void srlv (Register rd, Register rt,   Register rs) { dsrlv (rd, rt, rs); }	
   975 #endif
   976 #ifndef _LP64
   977 	void sub  (Register rd, Register rs,   Register rt) { emit_long(insn_RRRO((int)rs->encoding(),  (int)rt->encoding(),   (int)rd->encoding(), sub_op)); }
   978 	void subu (Register rd, Register rs,   Register rt) { emit_long(insn_RRRO((int)rs->encoding(),  (int)rt->encoding(),   (int)rd->encoding(), subu_op)); }
   979 #else
   980 	void sub  (Register rd, Register rs,   Register rt) { dsub  (rd, rs, rt); }
   981 	void subu (Register rd, Register rs,   Register rt) { dsubu (rd, rs, rt); }
   982 	void subu32 (Register rd, Register rs,   Register rt) { emit_long(insn_RRRO((int)rs->encoding(),  (int)rt->encoding(),   (int)rd->encoding(), subu_op)); }
   983 #endif
   984 	void sw   (Register rt, Register base, int off)     { emit_long(insn_ORRI(sw_op,    (int)base->encoding(), (int)rt->encoding(), off)); }
   985 	void swl  (Register rt, Register base, int off)     { emit_long(insn_ORRI(swl_op,   (int)base->encoding(), (int)rt->encoding(), off)); }
   986 	void swr  (Register rt, Register base, int off)     { emit_long(insn_ORRI(swr_op,   (int)base->encoding(), (int)rt->encoding(), off)); }
   987 	void sync ()                                        { emit_long(sync_op); }
   988 	void syscall(int code)                              { emit_long( (code<<6) | syscall_op ); }
   990 	void sb(Register rt, Address dst);
   991 	void sc(Register rt, Address dst);
   992 	void scd(Register rt, Address dst);
   993 	void sd(Register rt, Address dst);
   994 	void sdl(Register rt, Address dst);
   995 	void sdr(Register rt, Address dst);
   996 	void sh(Register rt, Address dst);
   997 	void sw(Register rt, Address dst);
   998 	void swl(Register rt, Address dst);
   999 	void swr(Register rt, Address dst);
  1001 	void teq  (Register rs, Register rt, int code) { emit_long(insn_RRCO((int)rs->encoding(),   (int)rt->encoding(), code, teq_op)); }
  1002 	void teqi (Register rs, int imm)               { emit_long(insn_ORRI(regimm_op, (int)rs->encoding(), teqi_op, imm)); }
  1003 	void tge  (Register rs, Register rt, int code) { emit_long(insn_RRCO((int)rs->encoding(),   (int)rt->encoding(), code, tge_op)); }
  1004 	void tgei (Register rs, int imm)               { emit_long(insn_ORRI(regimm_op, (int)rs->encoding(), tgei_op, imm)); }
  1005 	void tgeiu(Register rs, int imm)               { emit_long(insn_ORRI(regimm_op, (int)rs->encoding(), tgeiu_op, imm)); }
  1006 	void tgeu (Register rs, Register rt, int code) { emit_long(insn_RRCO((int)rs->encoding(),   (int)rt->encoding(), code, tgeu_op)); }
  1007 	void tlt  (Register rs, Register rt, int code) { emit_long(insn_RRCO((int)rs->encoding(),   (int)rt->encoding(), code, tlt_op)); }
  1008 	void tlti (Register rs, int imm)               { emit_long(insn_ORRI(regimm_op, (int)rs->encoding(), tlti_op, imm)); }
  1009 	void tltiu(Register rs, int imm)               { emit_long(insn_ORRI(regimm_op, (int)rs->encoding(), tltiu_op, imm)); }
  1010 	void tltu (Register rs, Register rt, int code) { emit_long(insn_RRCO((int)rs->encoding(),   (int)rt->encoding(), code, tltu_op)); }
  1011 	void tne  (Register rs, Register rt, int code) { emit_long(insn_RRCO((int)rs->encoding(),   (int)rt->encoding(), code, tne_op)); }
  1012 	void tnei (Register rs, int imm)               { emit_long(insn_ORRI(regimm_op, (int)rs->encoding(), tnei_op, imm)); }
  1014 	void xorr(Register rd, Register rs, Register rt) { emit_long(insn_RRRO((int)rs->encoding(), (int)rt->encoding(), (int)rd->encoding(), xor_op)); }
  1015 	void xori(Register rt, Register rs, int imm) { emit_long(insn_ORRI(xori_op, (int)rs->encoding(), (int)rt->encoding(), imm)); }
  1017 	void nop() 				      { emit_long(0); }
  1018 	//float instructions for mips
  1019 	void abs_s(FloatRegister fd, FloatRegister fs) { emit_long(insn_F3RO(single_fmt, 0, (int)fs->encoding(), (int)fd->encoding(), fabs_op));}
  1020 	void abs_d(FloatRegister fd, FloatRegister fs) { emit_long(insn_F3RO(double_fmt, 0, (int)fs->encoding(), (int)fd->encoding(), fabs_op));}
  1021 	void add_s(FloatRegister fd, FloatRegister fs, FloatRegister ft) { emit_long(insn_F3RO(single_fmt, (int)ft->encoding(), (int)fs->encoding(), (int)fd->encoding(), fadd_op));}
  1022 	void add_d(FloatRegister fd, FloatRegister fs, FloatRegister ft) { emit_long(insn_F3RO(double_fmt, (int)ft->encoding(), (int)fs->encoding(), (int)fd->encoding(), fadd_op));}
  1024 	void bc1f (int off) { emit_long(insn_ORRI(cop1_op, bc_op, bcf_op, off)); has_delay_slot(); }
  1025 	void bc1fl(int off) {	emit_long(insn_ORRI(cop1_op, bc_op, bcfl_op, off)); has_delay_slot(); }
  1026 	void bc1t (int off) { emit_long(insn_ORRI(cop1_op, bc_op, bct_op, off)); has_delay_slot(); }
  1027 	void bc1tl(int off) {	emit_long(insn_ORRI(cop1_op, bc_op, bctl_op, off));	has_delay_slot(); }
  1029 	void bc1f (address entry) { bc1f(offset(entry)); }
  1030 	void bc1fl(address entry) {	bc1fl(offset(entry)); }
  1031 	void bc1t (address entry) { bc1t(offset(entry)); }
  1032 	void bc1tl(address entry) {	bc1tl(offset(entry)); }
  1034 	void bc1f (Label& L) { bc1f(target(L)); }
  1035 	void bc1fl(Label& L) {	bc1fl(target(L)); }
  1036 	void bc1t (Label& L) { bc1t(target(L)); }
  1037 	void bc1tl(Label& L) {	bc1tl(target(L)); }
  1039 	void c_f_s   (FloatRegister fs, FloatRegister ft) { emit_long(insn_F3RO(single_fmt, (int)ft->encoding(), (int)fs->encoding(), 0, f_cond)); }
  1040 	void c_f_d   (FloatRegister fs, FloatRegister ft) { emit_long(insn_F3RO(double_fmt, (int)ft->encoding(), (int)fs->encoding(), 0, f_cond)); }
  1041 	void c_un_s  (FloatRegister fs, FloatRegister ft) { emit_long(insn_F3RO(single_fmt, (int)ft->encoding(), (int)fs->encoding(), 0, un_cond)); }
  1042 	void c_un_d  (FloatRegister fs, FloatRegister ft) { emit_long(insn_F3RO(double_fmt, (int)ft->encoding(), (int)fs->encoding(), 0, un_cond)); }
  1043 	void c_eq_s  (FloatRegister fs, FloatRegister ft) { emit_long(insn_F3RO(single_fmt, (int)ft->encoding(), (int)fs->encoding(), 0, eq_cond)); }
  1044 	void c_eq_d  (FloatRegister fs, FloatRegister ft) { emit_long(insn_F3RO(double_fmt, (int)ft->encoding(), (int)fs->encoding(), 0, eq_cond)); }
  1045 	void c_ueq_s (FloatRegister fs, FloatRegister ft) { emit_long(insn_F3RO(single_fmt, (int)ft->encoding(), (int)fs->encoding(), 0, ueq_cond)); }
  1046 	void c_ueq_d (FloatRegister fs, FloatRegister ft) { emit_long(insn_F3RO(double_fmt, (int)ft->encoding(), (int)fs->encoding(), 0, ueq_cond)); }
  1047 	void c_olt_s (FloatRegister fs, FloatRegister ft) { emit_long(insn_F3RO(single_fmt, (int)ft->encoding(), (int)fs->encoding(), 0, olt_cond)); }
  1048 	void c_olt_d (FloatRegister fs, FloatRegister ft) { emit_long(insn_F3RO(double_fmt, (int)ft->encoding(), (int)fs->encoding(), 0, olt_cond)); }
  1049 	void c_ult_s (FloatRegister fs, FloatRegister ft) { emit_long(insn_F3RO(single_fmt, (int)ft->encoding(), (int)fs->encoding(), 0, ult_cond)); }
  1050 	void c_ult_d (FloatRegister fs, FloatRegister ft) { emit_long(insn_F3RO(double_fmt, (int)ft->encoding(), (int)fs->encoding(), 0, ult_cond)); }
  1051 	void c_ole_s (FloatRegister fs, FloatRegister ft) { emit_long(insn_F3RO(single_fmt, (int)ft->encoding(), (int)fs->encoding(), 0, ole_cond)); }
  1052 	void c_ole_d (FloatRegister fs, FloatRegister ft) { emit_long(insn_F3RO(double_fmt, (int)ft->encoding(), (int)fs->encoding(), 0, ole_cond)); }
  1053 	void c_ule_s (FloatRegister fs, FloatRegister ft) { emit_long(insn_F3RO(single_fmt, (int)ft->encoding(), (int)fs->encoding(), 0, ule_cond)); }
  1054 	void c_ule_d (FloatRegister fs, FloatRegister ft) { emit_long(insn_F3RO(double_fmt, (int)ft->encoding(), (int)fs->encoding(), 0, ule_cond)); }
  1055 	void c_sf_s  (FloatRegister fs, FloatRegister ft) { emit_long(insn_F3RO(single_fmt, (int)ft->encoding(), (int)fs->encoding(), 0, sf_cond)); }
  1056 	void c_sf_d  (FloatRegister fs, FloatRegister ft) { emit_long(insn_F3RO(double_fmt, (int)ft->encoding(), (int)fs->encoding(), 0, sf_cond)); }
  1057 	void c_ngle_s(FloatRegister fs, FloatRegister ft) { emit_long(insn_F3RO(single_fmt, (int)ft->encoding(), (int)fs->encoding(), 0, ngle_cond)); }
  1058 	void c_ngle_d(FloatRegister fs, FloatRegister ft) { emit_long(insn_F3RO(double_fmt, (int)ft->encoding(), (int)fs->encoding(), 0, ngle_cond)); }
  1059 	void c_seq_s (FloatRegister fs, FloatRegister ft) { emit_long(insn_F3RO(single_fmt, (int)ft->encoding(), (int)fs->encoding(), 0, seq_cond)); }
  1060 	void c_seq_d (FloatRegister fs, FloatRegister ft) { emit_long(insn_F3RO(double_fmt, (int)ft->encoding(), (int)fs->encoding(), 0, seq_cond)); }
  1061 	void c_ngl_s (FloatRegister fs, FloatRegister ft) { emit_long(insn_F3RO(single_fmt, (int)ft->encoding(), (int)fs->encoding(), 0, ngl_cond)); }
  1062 	void c_ngl_d (FloatRegister fs, FloatRegister ft) { emit_long(insn_F3RO(double_fmt, (int)ft->encoding(), (int)fs->encoding(), 0, ngl_cond)); }
  1063 	void c_lt_s  (FloatRegister fs, FloatRegister ft) { emit_long(insn_F3RO(single_fmt, (int)ft->encoding(), (int)fs->encoding(), 0, lt_cond)); }
  1064 	void c_lt_d  (FloatRegister fs, FloatRegister ft) { emit_long(insn_F3RO(double_fmt, (int)ft->encoding(), (int)fs->encoding(), 0, lt_cond)); }
  1065 	void c_nge_s (FloatRegister fs, FloatRegister ft) { emit_long(insn_F3RO(single_fmt, (int)ft->encoding(), (int)fs->encoding(), 0, nge_cond)); }
  1066 	void c_nge_d (FloatRegister fs, FloatRegister ft) { emit_long(insn_F3RO(double_fmt, (int)ft->encoding(), (int)fs->encoding(), 0, nge_cond)); }
  1067 	void c_le_s  (FloatRegister fs, FloatRegister ft) { emit_long(insn_F3RO(single_fmt, (int)ft->encoding(), (int)fs->encoding(), 0, le_cond)); }
  1068 	void c_le_d  (FloatRegister fs, FloatRegister ft) { emit_long(insn_F3RO(double_fmt, (int)ft->encoding(), (int)fs->encoding(), 0, le_cond)); }
  1069 	void c_ngt_s (FloatRegister fs, FloatRegister ft) { emit_long(insn_F3RO(single_fmt, (int)ft->encoding(), (int)fs->encoding(), 0, ngt_cond)); }
  1070 	void c_ngt_d (FloatRegister fs, FloatRegister ft) { emit_long(insn_F3RO(double_fmt, (int)ft->encoding(), (int)fs->encoding(), 0, ngt_cond)); }
  1072 	void ceil_l_s(FloatRegister fd, FloatRegister fs) { emit_long(insn_F3RO(single_fmt, 0, (int)fs->encoding(), (int)fd->encoding(), fceill_op)); }
  1073 	void ceil_l_d(FloatRegister fd, FloatRegister fs) { emit_long(insn_F3RO(double_fmt, 0, (int)fs->encoding(), (int)fd->encoding(), fceill_op)); }
  1074 	void ceil_w_s(FloatRegister fd, FloatRegister fs) { emit_long(insn_F3RO(single_fmt, 0, (int)fs->encoding(), (int)fd->encoding(), fceilw_op)); }
  1075 	void ceil_w_d(FloatRegister fd, FloatRegister fs) { emit_long(insn_F3RO(double_fmt, 0, (int)fs->encoding(), (int)fd->encoding(), fceilw_op)); }
  1076 	void cfc1(Register rt, FloatRegister fs) { emit_long(insn_COP1(cf_op, (int)rt->encoding(), (int)fs->encoding())); }
  1077 	void ctc1(Register rt, FloatRegister fs) { emit_long(insn_COP1(ct_op, (int)rt->encoding(), (int)fs->encoding())); }
  1078 	void cfc1(Register rt, int fs) { emit_long(insn_COP1(cf_op, (int)rt->encoding(), fs)); }
  1079 	void ctc1(Register rt, int fs) { emit_long(insn_COP1(ct_op, (int)rt->encoding(), fs)); }
  1081 	void cvt_d_s(FloatRegister fd, FloatRegister fs) { emit_long(insn_F3RO(single_fmt, 0, (int)fs->encoding(), (int)fd->encoding(), fcvtd_op)); }
  1082 	void cvt_d_w(FloatRegister fd, FloatRegister fs) { emit_long(insn_F3RO(word_fmt, 0, (int)fs->encoding(), (int)fd->encoding(), fcvtd_op)); }
  1083 	void cvt_d_l(FloatRegister fd, FloatRegister fs) { emit_long(insn_F3RO(long_fmt, 0, (int)fs->encoding(), (int)fd->encoding(), fcvtd_op)); }
  1084 	void cvt_l_s(FloatRegister fd, FloatRegister fs) { emit_long(insn_F3RO(single_fmt, 0, (int)fs->encoding(), (int)fd->encoding(), fcvtl_op)); }
  1085 	void cvt_l_w(FloatRegister fd, FloatRegister fs) { emit_long(insn_F3RO(word_fmt, 0, (int)fs->encoding(), (int)fd->encoding(), fcvtl_op)); }
  1086 	void cvt_l_d(FloatRegister fd, FloatRegister fs) { emit_long(insn_F3RO(double_fmt, 0, (int)fs->encoding(), (int)fd->encoding(), fcvtl_op)); }
  1087 	void cvt_s_d(FloatRegister fd, FloatRegister fs) { emit_long(insn_F3RO(double_fmt, 0, (int)fs->encoding(), (int)fd->encoding(), fcvts_op)); }
  1088 	void cvt_s_w(FloatRegister fd, FloatRegister fs) { emit_long(insn_F3RO(word_fmt, 0, (int)fs->encoding(), (int)fd->encoding(), fcvts_op)); }
  1089 	void cvt_s_l(FloatRegister fd, FloatRegister fs) { emit_long(insn_F3RO(long_fmt, 0, (int)fs->encoding(), (int)fd->encoding(), fcvts_op)); }
  1090 	void cvt_w_s(FloatRegister fd, FloatRegister fs) { emit_long(insn_F3RO(single_fmt, 0, (int)fs->encoding(), (int)fd->encoding(), fcvtw_op)); }
  1091 	void cvt_w_d(FloatRegister fd, FloatRegister fs) { emit_long(insn_F3RO(double_fmt, 0, (int)fs->encoding(), (int)fd->encoding(), fcvtw_op)); }
  1092 	void cvt_w_l(FloatRegister fd, FloatRegister fs) { emit_long(insn_F3RO(long_fmt, 0, (int)fs->encoding(), (int)fd->encoding(), fcvtw_op)); }
  1093 	void pll(FloatRegister fd, FloatRegister fs, FloatRegister ft) { emit_long(insn_F3RO(long_fmt, (int)ft->encoding(), (int)fs->encoding(), (int)fd->encoding(), fpll_op)); }
  1094 	void plu(FloatRegister fd, FloatRegister fs, FloatRegister ft) { emit_long(insn_F3RO(long_fmt, (int)ft->encoding(), (int)fs->encoding(), (int)fd->encoding(), fplu_op)); }
  1095 	void pul(FloatRegister fd, FloatRegister fs, FloatRegister ft) { emit_long(insn_F3RO(long_fmt, (int)ft->encoding(), (int)fs->encoding(), (int)fd->encoding(), fpul_op)); }
  1096 	void puu(FloatRegister fd, FloatRegister fs, FloatRegister ft) { emit_long(insn_F3RO(long_fmt, (int)ft->encoding(), (int)fs->encoding(), (int)fd->encoding(), fpuu_op)); }
  1098 	void div_s(FloatRegister fd, FloatRegister fs, FloatRegister ft) { emit_long(insn_F3RO(single_fmt, (int)ft->encoding(), (int)fs->encoding(), (int)fd->encoding(), fdiv_op)); }
  1099 	void div_d(FloatRegister fd, FloatRegister fs, FloatRegister ft) { emit_long(insn_F3RO(double_fmt, (int)ft->encoding(), (int)fs->encoding(), (int)fd->encoding(), fdiv_op)); }
  1100 	void dmfc1(Register rt, FloatRegister fs) { emit_long(insn_COP1(dmf_op, (int)rt->encoding(), (int)fs->encoding())); }
  1101 	void dmtc1(Register rt, FloatRegister fs) { emit_long(insn_COP1(dmt_op, (int)rt->encoding(), (int)fs->encoding())); }
  1103 	void floor_l_s(FloatRegister fd, FloatRegister fs) { emit_long(insn_F3RO(single_fmt, 0, (int)fs->encoding(), (int)fd->encoding(), ffloorl_op)); }
  1104 	void floor_l_d(FloatRegister fd, FloatRegister fs) { emit_long(insn_F3RO(double_fmt, 0, (int)fs->encoding(), (int)fd->encoding(), ffloorl_op)); }
  1105 	void floor_w_s(FloatRegister fd, FloatRegister fs) { emit_long(insn_F3RO(single_fmt, 0, (int)fs->encoding(), (int)fd->encoding(), ffloorw_op)); }
  1106 	void floor_w_d(FloatRegister fd, FloatRegister fs) { emit_long(insn_F3RO(double_fmt, 0, (int)fs->encoding(), (int)fd->encoding(), ffloorw_op)); }
  1108 	void ldc1(FloatRegister ft, Register base, int off) { emit_long(insn_ORRI(ldc1_op, (int)base->encoding(), (int)ft->encoding(), off)); }
  1109 	void lwc1(FloatRegister ft, Register base, int off) { emit_long(insn_ORRI(lwc1_op, (int)base->encoding(), (int)ft->encoding(), off)); }
  1110 	void ldc1(FloatRegister ft, Address src);
  1111 	void lwc1(FloatRegister ft, Address src);
  1113 	void mfc1(Register rt, FloatRegister fs) { emit_long(insn_COP1(mf_op, (int)rt->encoding(), (int)fs->encoding())); }
  1114 	void mov_s(FloatRegister fd, FloatRegister fs) { emit_long(insn_F3RO(single_fmt, 0, (int)fs->encoding(), (int)fd->encoding(), fmov_op)); }
  1115 	void mov_d(FloatRegister fd, FloatRegister fs) { emit_long(insn_F3RO(double_fmt, 0, (int)fs->encoding(), (int)fd->encoding(), fmov_op)); }
  1116 	void mtc1(Register rt, FloatRegister fs) { emit_long(insn_COP1(mt_op, (int)rt->encoding(), (int)fs->encoding())); }
  1117 	void mul_s(FloatRegister fd, FloatRegister fs, FloatRegister ft) { emit_long(insn_F3RO(single_fmt, (int)ft->encoding(), (int)fs->encoding(), (int)fd->encoding(), fmul_op)); }
  1118 	void mul_d(FloatRegister fd, FloatRegister fs, FloatRegister ft) { emit_long(insn_F3RO(double_fmt, (int)ft->encoding(), (int)fs->encoding(), (int)fd->encoding(), fmul_op)); }
  1120 	void neg_s(FloatRegister fd, FloatRegister fs) { emit_long(insn_F3RO(single_fmt, 0, (int)fs->encoding(), (int)fd->encoding(), fneg_op)); }
  1121 	void neg_d(FloatRegister fd, FloatRegister fs) { emit_long(insn_F3RO(double_fmt, 0, (int)fs->encoding(), (int)fd->encoding(), fneg_op)); }
  1123 	void round_l_s(FloatRegister fd, FloatRegister fs) { emit_long(insn_F3RO(single_fmt, 0, (int)fs->encoding(), (int)fd->encoding(), froundl_op)); }
  1124 	void round_l_d(FloatRegister fd, FloatRegister fs) { emit_long(insn_F3RO(double_fmt, 0, (int)fs->encoding(), (int)fd->encoding(), froundl_op)); }
  1125 	void round_w_s(FloatRegister fd, FloatRegister fs) { emit_long(insn_F3RO(single_fmt, 0, (int)fs->encoding(), (int)fd->encoding(), froundw_op)); }
  1126 	void round_w_d(FloatRegister fd, FloatRegister fs) { emit_long(insn_F3RO(double_fmt, 0, (int)fs->encoding(), (int)fd->encoding(), froundw_op)); }
  1128 	void sdc1(FloatRegister ft, Register base, int off) { emit_long(insn_ORRI(sdc1_op, (int)base->encoding(), (int)ft->encoding(), off)); }
  1129 	void sdc1(FloatRegister ft, Address dst);
  1130 	void sqrt_s(FloatRegister fd, FloatRegister fs) { emit_long(insn_F3RO(single_fmt, 0, (int)fs->encoding(), (int)fd->encoding(), fsqrt_op)); }
  1131 	void sqrt_d(FloatRegister fd, FloatRegister fs) { emit_long(insn_F3RO(double_fmt, 0, (int)fs->encoding(), (int)fd->encoding(), fsqrt_op)); }
  1132 	void sub_s(FloatRegister fd, FloatRegister fs, FloatRegister ft) { emit_long(insn_F3RO(single_fmt, (int)ft->encoding(), (int)fs->encoding(), (int)fd->encoding(), fsub_op)); }
  1133 	void sub_d(FloatRegister fd, FloatRegister fs, FloatRegister ft) { emit_long(insn_F3RO(double_fmt, (int)ft->encoding(), (int)fs->encoding(), (int)fd->encoding(), fsub_op)); }
  1134 	void swc1(FloatRegister ft, Register base, int off) { emit_long(insn_ORRI(swc1_op, (int)base->encoding(), (int)ft->encoding(), off)); }
  1135 	void swc1(FloatRegister ft, Address dst);
  1137 	void trunc_l_s(FloatRegister fd, FloatRegister fs) { emit_long(insn_F3RO(single_fmt, 0, (int)fs->encoding(), (int)fd->encoding(), ftruncl_op)); }
  1138 	void trunc_l_d(FloatRegister fd, FloatRegister fs) { emit_long(insn_F3RO(double_fmt, 0, (int)fs->encoding(), (int)fd->encoding(), ftruncl_op)); }
  1139 	void trunc_w_s(FloatRegister fd, FloatRegister fs) { emit_long(insn_F3RO(single_fmt, 0, (int)fs->encoding(), (int)fd->encoding(), ftruncw_op)); }
  1140 	void trunc_w_d(FloatRegister fd, FloatRegister fs) { emit_long(insn_F3RO(double_fmt, 0, (int)fs->encoding(), (int)fd->encoding(), ftruncw_op)); }
  1142 	void int3();
  1143 	static void print_instruction(int);
  1144 	int patched_branch(int dest_pos, int inst, int inst_pos);
  1145 	int branch_destination(int inst, int pos);
  1147 	/* Godson3 extension */
  1148 	void gsldx(Register rt, Register base, Register index, int off) {
  1149 		assert(is_simm(off, 8), "gsldx: off exceeds 8 bits");
  1150 		emit_long(gsldx_op | ((int)base->encoding() << 21) | ((int)rt->encoding() << 16) | ((int)index->encoding() << 11) | (off << 3));
  1153 	void gslwx(Register rt, Register base, Register index, int off) {
  1154 		assert(is_simm(off, 8), "gslwx: off exceeds 8 bits");
  1155 		emit_long(gslwx_op | ((int)base->encoding() << 21) | ((int)rt->encoding() << 16) | ((int)index->encoding() << 11) | (off << 3));
  1158 public:
  1159 	// Creation
  1160 	Assembler(CodeBuffer* code) : AbstractAssembler(code) {
  1161 #ifdef CHECK_DELAY
  1162 	  delay_state = no_delay;
  1163 #endif
  1166   // Decoding
  1167   static address locate_operand(address inst, WhichOperand which);
  1168   static address locate_next_instruction(address inst);
  1169 };
  1172 // MacroAssembler extends Assembler by frequently used macros.
  1173 //
  1174 // Instructions for which a 'better' code sequence exists depending
  1175 // on arguments should also go in here.
  1177 class MacroAssembler: public Assembler {
  1178   friend class LIR_Assembler;
  1179   friend class Runtime1;      // as_Address()
  1181 public:
  1182 static intptr_t	i[32];
  1183 static float	f[32];
  1184 static void print(outputStream *s);
  1186 static int i_offset(unsigned int k);
  1187 static int f_offset(unsigned int k);
  1189 static void save_registers(MacroAssembler *masm);
  1190 static void restore_registers(MacroAssembler *masm);
  1192  protected:
  1194   Address as_Address(AddressLiteral adr);
  1195   Address as_Address(ArrayAddress adr);
  1197   // Support for VM calls
  1198   //
  1199   // This is the base routine called by the different versions of call_VM_leaf. The interpreter
  1200   // may customize this version by overriding it for its purposes (e.g., to save/restore
  1201   // additional registers when doing a VM call).
  1202 #ifdef CC_INTERP
  1203   // c++ interpreter never wants to use interp_masm version of call_VM
  1204   #define VIRTUAL
  1205 #else
  1206   #define VIRTUAL virtual
  1207 #endif
  1209   VIRTUAL void call_VM_leaf_base(
  1210     address entry_point,               // the entry point
  1211     int     number_of_arguments        // the number of arguments to pop after the call
  1212   );
  1214   // This is the base routine called by the different versions of call_VM. The interpreter
  1215   // may customize this version by overriding it for its purposes (e.g., to save/restore
  1216   // additional registers when doing a VM call).
  1217   //
  1218   // If no java_thread register is specified (noreg) than rdi will be used instead. call_VM_base
  1219   // returns the register which contains the thread upon return. If a thread register has been
  1220   // specified, the return value will correspond to that register. If no last_java_sp is specified
  1221   // (noreg) than rsp will be used instead.
  1222   VIRTUAL void call_VM_base(           // returns the register containing the thread upon return
  1223     Register oop_result,               // where an oop-result ends up if any; use noreg otherwise
  1224     Register java_thread,              // the thread if computed before     ; use noreg otherwise
  1225     Register last_java_sp,             // to set up last_Java_frame in stubs; use noreg otherwise
  1226     address  entry_point,              // the entry point
  1227     int      number_of_arguments,      // the number of arguments (w/o thread) to pop after the call
  1228     bool     check_exceptions          // whether to check for pending exceptions after return
  1229   );
  1231   // These routines should emit JVMTI PopFrame and ForceEarlyReturn handling code.
  1232   // The implementation is only non-empty for the InterpreterMacroAssembler,
  1233   // as only the interpreter handles PopFrame and ForceEarlyReturn requests.
  1234   virtual void check_and_handle_popframe(Register java_thread);
  1235   virtual void check_and_handle_earlyret(Register java_thread);
  1237   void call_VM_helper(Register oop_result, address entry_point, int number_of_arguments, bool check_exceptions = true);
  1239   // helpers for FPU flag access
  1240   // tmp is a temporary register, if none is available use noreg
  1241   //void save_rax   (Register tmp);
  1242   //void restore_rax(Register tmp);
  1244  public:
  1245   MacroAssembler(CodeBuffer* code) : Assembler(code) {}
  1247   // Support for NULL-checks
  1248   //
  1249   // Generates code that causes a NULL OS exception if the content of reg is NULL.
  1250   // If the accessed location is M[reg + offset] and the offset is known, provide the
  1251   // offset. No explicit code generation is needed if the offset is within a certain
  1252   // range (0 <= offset <= page_size).
  1253   // use "teq 83, reg" in mips now, by yjl 6/20/2005
  1254   void null_check(Register reg, int offset = -1);
  1255   static bool needs_explicit_null_check(intptr_t offset);
  1257 	// Required platform-specific helpers for Label::patch_instructions.
  1258   // They _shadow_ the declarations in AbstractAssembler, which are undefined.
  1259   void pd_patch_instruction(address branch, address target);
  1261   // Alignment
  1262   void align(int modulus);
  1264   // Misc
  1265   //void fat_nop(); // 5 byte nop
  1267   // Stack frame creation/removal
  1268   void enter();
  1269   void leave();
  1271   // Support for getting the JavaThread pointer (i.e.; a reference to thread-local information)
  1272   // The pointer will be loaded into the thread register.
  1273   void get_thread(Register thread);
  1276   // Support for VM calls
  1277   //
  1278   // It is imperative that all calls into the VM are handled via the call_VM macros.
  1279   // They make sure that the stack linkage is setup correctly. call_VM's correspond
  1280   // to ENTRY/ENTRY_X entry points while call_VM_leaf's correspond to LEAF entry points.
  1283   void call_VM(Register oop_result,
  1284                address entry_point,
  1285                bool check_exceptions = true);
  1286   void call_VM(Register oop_result,
  1287                address entry_point,
  1288                Register arg_1,
  1289                bool check_exceptions = true);
  1290   void call_VM(Register oop_result,
  1291                address entry_point,
  1292                Register arg_1, Register arg_2,
  1293                bool check_exceptions = true);
  1294   void call_VM(Register oop_result,
  1295                address entry_point,
  1296                Register arg_1, Register arg_2, Register arg_3,
  1297                bool check_exceptions = true);
  1298   // Super call_VM calls - correspond to MacroAssembler::call_VM(_leaf) calls
  1299   void super_call_VM_leaf(address entry_point);
  1300   void super_call_VM_leaf(address entry_point, Register arg_1);
  1301   void super_call_VM_leaf(address entry_point, Register arg_1, Register arg_2);
  1302   void super_call_VM_leaf(address entry_point,
  1303                           Register arg_1, Register arg_2, Register arg_3);
  1305   // Overloadings with last_Java_sp
  1306   void call_VM(Register oop_result,
  1307                Register last_java_sp,
  1308                address entry_point,
  1309                int number_of_arguments = 0,
  1310                bool check_exceptions = true);
  1311   void call_VM(Register oop_result,
  1312                Register last_java_sp,
  1313                address entry_point,
  1314                Register arg_1, bool
  1315                check_exceptions = true);
  1316   void call_VM(Register oop_result,
  1317                Register last_java_sp,
  1318                address entry_point,
  1319                Register arg_1, Register arg_2,
  1320                bool check_exceptions = true);
  1321   void call_VM(Register oop_result,
  1322                Register last_java_sp,
  1323                address entry_point,
  1324                Register arg_1, Register arg_2, Register arg_3,
  1325                bool check_exceptions = true);
  1327   void call_VM_leaf(address entry_point,
  1328                     int number_of_arguments = 0);
  1329   void call_VM_leaf(address entry_point,
  1330                     Register arg_1);
  1331   void call_VM_leaf(address entry_point,
  1332                     Register arg_1, Register arg_2);
  1333   void call_VM_leaf(address entry_point,
  1334                     Register arg_1, Register arg_2, Register arg_3);
  1336   // last Java Frame (fills frame anchor)
  1337   void set_last_Java_frame(Register thread,
  1338                            Register last_java_sp,
  1339                            Register last_java_fp,
  1340                            address last_java_pc);
  1342   // thread in the default location (r15_thread on 64bit)
  1343   void set_last_Java_frame(Register last_java_sp,
  1344                            Register last_java_fp,
  1345                            address last_java_pc);
  1347   void reset_last_Java_frame(Register thread, bool clear_fp, bool clear_pc);
  1349   // thread in the default location (r15_thread on 64bit)
  1350   void reset_last_Java_frame(bool clear_fp, bool clear_pc);
  1352   // Stores
  1353   void store_check(Register obj);                // store check for obj - register is destroyed afterwards
  1354   void store_check(Register obj, Address dst);   // same as above, dst is exact store location (reg. is destroyed)
  1357   void g1_write_barrier_pre(Register obj,
  1358 #ifndef _LP64
  1359                             Register thread,
  1360 #endif
  1361                             Register tmp,
  1362                             Register tmp2,
  1363                             bool     tosca_live);
  1364   void g1_write_barrier_post(Register store_addr,
  1365                              Register new_val,
  1366 #ifndef _LP64
  1367                              Register thread,
  1368 #endif
  1369                              Register tmp,
  1370                              Register tmp2);
  1374   // split store_check(Register obj) to enhance instruction interleaving
  1375   void store_check_part_1(Register obj);
  1376   void store_check_part_2(Register obj);
  1378   // C 'boolean' to Java boolean: x == 0 ? 0 : 1
  1379   void c2bool(Register x);
  1380   //add for compressedoops
  1381   void load_klass(Register dst, Register src);
  1382   void store_klass(Register dst, Register src);
  1383   void load_prototype_header(Register dst, Register src);
  1384 /*
  1385   // C++ bool manipulation
  1387   void movbool(Register dst, Address src);
  1388   void movbool(Address dst, bool boolconst);
  1389   void movbool(Address dst, Register src);
  1390   void testbool(Register dst);
  1392   // oop manipulations
  1393   void load_klass(Register dst, Register src);
  1394   void store_klass(Register dst, Register src);
  1396   void load_prototype_header(Register dst, Register src);*/
  1398 #ifdef _LP64
  1399   void store_klass_gap(Register dst, Register src);
  1401   void load_heap_oop(Register dst, Address src);
  1402   void store_heap_oop(Address dst, Register src);
  1403   void encode_heap_oop(Register r);
  1404   void decode_heap_oop(Register r);
  1405   void encode_heap_oop_not_null(Register r);
  1406   void decode_heap_oop_not_null(Register r);
  1407   void encode_heap_oop_not_null(Register dst, Register src);
  1408   void decode_heap_oop_not_null(Register dst, Register src);
  1410   void encode_klass_not_null(Register r);
  1411   void decode_klass_not_null(Register r);
  1412   void encode_klass_not_null(Register dst, Register src);
  1413   void decode_klass_not_null(Register dst, Register src);
  1415   //void set_narrow_oop(Register dst, jobject obj);
  1417   // Returns the byte size of the instructions generated by decode_klass_not_null()
  1418   // when compressed klass pointers are being used.
  1419   static int instr_size_for_decode_klass_not_null();
  1421   // if heap base register is used - reinit it with the correct value
  1422   void reinit_heapbase();
  1423   DEBUG_ONLY(void verify_heapbase(const char* msg);)
  1425 #endif // _LP64
  1427   void incrementl(Register reg, int value = 1);
  1429   void decrementl(Register reg, int value = 1);
  1431 /*
  1432   // Int division/remainder for Java
  1433   // (as idivl, but checks for special case as described in JVM spec.)
  1434   // returns idivl instruction offset for implicit exception handling
  1435   int corrected_idivl(Register reg);
  1437   // Long division/remainder for Java
  1438   // (as idivq, but checks for special case as described in JVM spec.)
  1439   // returns idivq instruction offset for implicit exception handling
  1440   int corrected_idivq(Register reg);
  1441 */
  1443   void int3();
  1444 /*
  1445   // Long operation macros for a 32bit cpu
  1446   // Long negation for Java
  1447   void lneg(Register hi, Register lo);
  1449   // Long multiplication for Java
  1450   // (destroys contents of eax, ebx, ecx and edx)
  1451   void lmul(int x_rsp_offset, int y_rsp_offset); // rdx:rax = x * y
  1453   // Long shifts for Java
  1454   // (semantics as described in JVM spec.)
  1455   void lshl(Register hi, Register lo);                               // hi:lo << (rcx & 0x3f)
  1456   void lshr(Register hi, Register lo, bool sign_extension = false);  // hi:lo >> (rcx & 0x3f)
  1458   // Long compare for Java
  1459   // (semantics as described in JVM spec.)
  1460   void lcmp2int(Register x_hi, Register x_lo, Register y_hi, Register y_lo); // x_hi = lcmp(x, y)
  1463   // misc
  1464 */
  1465   // Sign extension
  1466 #ifdef _LP64
  1467   void sign_extend_short(Register reg) 	{ dsll32(reg, reg, 16); dsra32(reg, reg, 16); }
  1468   void sign_extend_byte(Register reg)	{ dsll32(reg, reg, 24); dsra32(reg, reg, 24); }
  1469 #else
  1470   void sign_extend_short(Register reg) 	{ sll(reg, reg, 16); sra(reg, reg, 16); }
  1471   void sign_extend_byte(Register reg)	{ sll(reg, reg, 24); sra(reg, reg, 24); }
  1472 #endif
  1473   void rem_s(FloatRegister fd, FloatRegister fs, FloatRegister ft, FloatRegister tmp);
  1474 	void rem_d(FloatRegister fd, FloatRegister fs, FloatRegister ft, FloatRegister tmp);
  1476   // Inlined sin/cos generator for Java; must not use CPU instruction
  1477   // directly on Intel as it does not have high enough precision
  1478   // outside of the range [-pi/4, pi/4]. Extra argument indicate the
  1479   // number of FPU stack slots in use; all but the topmost will
  1480   // require saving if a slow case is necessary. Assumes argument is
  1481   // on FP TOS; result is on FP TOS.  No cpu registers are changed by
  1482   // this code.
  1483   void trigfunc(char trig, int num_fpu_regs_in_use = 1);
  1484 /*
  1485   // branch to L if FPU flag C2 is set/not set
  1486   // tmp is a temporary register, if none is available use noreg
  1487   void jC2 (Register tmp, Label& L);
  1488   void jnC2(Register tmp, Label& L);
  1490   // Pop ST (ffree & fincstp combined)
  1491   void fpop();
  1493   // pushes double TOS element of FPU stack on CPU stack; pops from FPU stack
  1494   void push_fTOS();
  1496   // pops double TOS element from CPU stack and pushes on FPU stack
  1497   void pop_fTOS();
  1499   void empty_FPU_stack();
  1501   void push_IU_state();
  1502   void pop_IU_state();
  1504   void push_FPU_state();
  1505   void pop_FPU_state();
  1507   void push_CPU_state();
  1508   void pop_CPU_state();
  1510   // Round up to a power of two
  1511   void round_to(Register reg, int modulus);
  1513   // Callee saved registers handling
  1514   void push_callee_saved_registers();
  1515   void pop_callee_saved_registers();
  1516 */
  1517   // allocation
  1518   void eden_allocate(
  1519     Register obj,                      // result: pointer to object after successful allocation
  1520     Register var_size_in_bytes,        // object size in bytes if unknown at compile time; invalid otherwise
  1521     int      con_size_in_bytes,        // object size in bytes if   known at compile time
  1522     Register t1,                       // temp register
  1523     Register t2,
  1524     Label&   slow_case                 // continuation point if fast allocation fails
  1525   );
  1526   void tlab_allocate(
  1527     Register obj,                      // result: pointer to object after successful allocation
  1528     Register var_size_in_bytes,        // object size in bytes if unknown at compile time; invalid otherwise
  1529     int      con_size_in_bytes,        // object size in bytes if   known at compile time
  1530     Register t1,                       // temp register
  1531     Register t2,                       // temp register
  1532     Label&   slow_case                 // continuation point if fast allocation fails
  1533     );
  1534   void tlab_refill(Label& retry_tlab, Label& try_eden, Label& slow_case);
  1536   //----
  1537   //  void set_word_if_not_zero(Register reg); // sets reg to 1 if not zero, otherwise 0
  1540   // Debugging
  1542   // only if +VerifyOops
  1543   void verify_oop(Register reg, const char* s = "broken oop");
  1544   void verify_oop_addr(Address addr, const char * s = "broken oop addr");
  1545   void verify_oop_subroutine();
  1546   // TODO: verify method and klass metadata (compare against vptr?)
  1547   void _verify_method_ptr(Register reg, const char * msg, const char * file, int line) {}
  1548   void _verify_klass_ptr(Register reg, const char * msg, const char * file, int line){}
  1550   #define verify_method_ptr(reg) _verify_method_ptr(reg, "broken method " #reg, __FILE__, __LINE__)
  1551   #define verify_klass_ptr(reg) _verify_klass_ptr(reg, "broken klass " #reg, __FILE__, __LINE__)
  1553   // only if +VerifyFPU
  1554   void verify_FPU(int stack_depth, const char* s = "illegal FPU state");
  1556   // prints msg, dumps registers and stops execution
  1557   void stop(const char* msg);
  1559   // prints msg and continues
  1560   void warn(const char* msg);
  1562   static void debug(char* msg/*, RegistersForDebugging* regs*/);
  1563   static void debug32(int rdi, int rsi, int rbp, int rsp, int rbx, int rdx, int rcx, int rax, int eip, char* msg);
  1564   static void debug64(char* msg, int64_t pc, int64_t regs[]);
  1566   void print_reg(Register reg);
  1567   void print_reg(FloatRegister reg);
  1568   //void os_breakpoint();
  1570   void untested()                                { stop("untested"); }
  1572   void unimplemented(const char* what = "")      { char* b = new char[1024];  jio_snprintf(b, sizeof(b), "unimplemented: %s", what);  stop(b); }
  1574   void should_not_reach_here()                   { stop("should not reach here"); }
  1576   void print_CPU_state();
  1578   // Stack overflow checking
  1579   void bang_stack_with_offset(int offset) {
  1580     // stack grows down, caller passes positive offset
  1581     assert(offset > 0, "must bang with negative offset");
  1582     if (offset <= 32768) {
  1583       sw(A0, SP, -offset);
  1584     } else {
  1585 #ifdef _LP64
  1586       li(AT, offset);
  1587       dsub(AT, SP, AT);
  1588 #else
  1589       move(AT, offset);
  1590       sub(AT, SP, AT);
  1591 #endif
  1592       sw(A0, AT, 0);
  1596   	// Writes to stack successive pages until offset reached to check for
  1597   	// stack overflow + shadow pages.  Also, clobbers tmp
  1598   	void bang_stack_size(Register size, Register tmp);
  1599         virtual RegisterOrConstant delayed_value_impl(intptr_t* delayed_value_addr,
  1600                                                        Register tmp,
  1601                                                        int offset);
  1603   	// Support for serializing memory accesses between threads
  1604   	void serialize_memory(Register thread, Register tmp);
  1606   	//void verify_tlab();
  1607   	void verify_tlab(Register t1, Register t2);
  1609   	// Biased locking support
  1610   	// lock_reg and obj_reg must be loaded up with the appropriate values.
  1611   	// swap_reg must be rax, and is killed.
  1612   	// tmp_reg is optional. If it is supplied (i.e., != noreg) it will
  1613   	// be killed; if not supplied, push/pop will be used internally to
  1614   	// allocate a temporary (inefficient, avoid if possible).
  1615   	// Optional slow case is for implementations (interpreter and C1) which branch to
  1616   	// slow case directly. Leaves condition codes set for C2's Fast_Lock node.
  1617   	// Returns offset of first potentially-faulting instruction for null
  1618   	// check info (currently consumed only by C1). If
  1619   	// swap_reg_contains_mark is true then returns -1 as it is assumed
  1620   	// the calling code has already passed any potential faults.
  1621   	int biased_locking_enter(Register lock_reg, Register obj_reg,
  1622 			  Register swap_reg, Register tmp_reg,
  1623 			  bool swap_reg_contains_mark,
  1624 			  Label& done, Label* slow_case = NULL,
  1625 			  BiasedLockingCounters* counters = NULL);
  1626 	void biased_locking_exit (Register obj_reg, Register temp_reg, Label& done);
  1629   // Calls
  1631 	void call(address entry);
  1632 	void call(address entry, relocInfo::relocType rtype); 
  1633 	void call(address entry, RelocationHolder& rh); 
  1634 	// Emit the CompiledIC call idiom
  1635 	void ic_call(address entry);
  1637 	void jmp(address entry);
  1638 	void jmp(address entry, relocInfo::relocType rtype);
  1640 	// Argument ops
  1641 	/*inline void store_int_argument(Register s, Argument& a);
  1642 	inline void store_long_argument(Register s, Argument& a);
  1643 	inline void store_float_argument(FloatRegister s, Argument& a);
  1644 	inline void store_double_argument(FloatRegister s, Argument& a);
  1645 	inline void store_ptr_argument(Register s, Argument& a);*/
  1646 inline void store_int_argument(Register s, Argument &a) {
  1647         if(a.is_Register()) {
  1648                 move(a.as_Register(), s);
  1649         } else {
  1650                 sw(s, a.as_caller_address());
  1654 inline void store_long_argument(Register s, Argument &a) {
  1655         Argument a1 = a.successor();
  1656         if(a.is_Register() && a1.is_Register()) {
  1657                 move(a.as_Register(), s);
  1658                 move(a.as_Register(), s);
  1659         } else {
  1660                 sd(s, a.as_caller_address());
  1664 inline void store_float_argument(FloatRegister s, Argument &a) {
  1665         if(a.is_Register()) {
  1666                 mov_s(a.as_FloatRegister(), s);
  1667         } else {
  1668                 swc1(s, a.as_caller_address());
  1671 inline void store_double_argument(FloatRegister s, Argument &a) {
  1672         if(a.is_Register()) {
  1673                 mov_d(a.as_FloatRegister(), s);
  1674         } else {
  1675                 sdc1(s, a.as_caller_address());
  1679 inline void store_ptr_argument(Register s, Argument &a) {
  1680   if(a.is_Register()) {
  1681     move(a.as_Register(), s);
  1682   } else {
  1683     st_ptr(s, a.as_caller_address());
  1687   // Load and store values by size and signed-ness
  1688   void load_sized_value(Register dst, Address src, size_t size_in_bytes, bool is_signed, Register dst2 = noreg);
  1689   void store_sized_value(Address dst, Register src, size_t size_in_bytes, Register src2 = noreg);
  1691   // interface method calling
  1692   void lookup_interface_method(Register recv_klass,
  1693                                Register intf_klass,
  1694                                RegisterOrConstant itable_index,
  1695                                Register method_result,
  1696                                Register scan_temp,
  1697                                Label& no_such_interface);
  1698   // virtual method calling
  1699   void lookup_virtual_method(Register recv_klass,
  1700                              RegisterOrConstant vtable_index,
  1701                              Register method_result);
  1703 	// ld_ptr will perform lw for 32 bit VMs and ld for 64 bit VMs
  1704 	// st_ptr will perform sw for 32 bit VMs and sd for 64 bit VMs
  1705 	inline void ld_ptr(Register rt, Address a){
  1706          #ifdef _LP64
  1707          ld(rt, a.base(), a.disp());
  1708          #else
  1709          lw(rt, a.base(), a.disp());
  1710          #endif
  1712 	inline void ld_ptr(Register rt, Register base, int offset16){
  1713          #ifdef _LP64
  1714          ld(rt, base, offset16);
  1715          #else
  1716          lw(rt, base, offset16);
  1717          #endif
  1720 	inline void st_ptr(Register rt, Address a){
  1721         #ifdef _LP64
  1722          sd(rt, a.base(), a.disp());
  1723         #else
  1724          sw(rt, a.base(), a.disp());
  1725         #endif
  1727 	inline void st_ptr(Register rt, Register base, int offset16) {
  1728         #ifdef _LP64
  1729           sd(rt, base, offset16);
  1730         #else
  1731           sw(rt, base, offset16);
  1732         #endif
  1736 	void ld_ptr(Register rt, Register offset, Register base);
  1737 	void st_ptr(Register rt, Register offset, Register base);
  1739 	// ld_long will perform lw for 32 bit VMs and ld for 64 bit VMs
  1740 	// st_long will perform sw for 32 bit VMs and sd for 64 bit VMs
  1741 	inline void ld_long(Register rt, Register base, int offset16);
  1742 	inline void st_long(Register rt, Register base, int offset16);
  1743 	inline void ld_long(Register rt, Address a);
  1744 	inline void st_long(Register rt, Address a);
  1747 	void ld_long(Register rt, Register offset, Register base);
  1748 	void st_long(Register rt, Register offset, Register base);
  1749 	// Regular vs. d* versions
  1750 	inline void addu_long(Register rd, Register rs, Register rt) {
  1751         #ifdef _LP64
  1752          daddu(rd, rs, rt);
  1753         #else
  1754          addu(rd, rs, rt);
  1755         #endif
  1757 	inline void addu_long(Register rd, Register rs, long imm32_64) {
  1758         #ifdef _LP64
  1759          daddiu(rd, rs, imm32_64);
  1760         #else
  1761          addiu(rd, rs, imm32_64);
  1762         #endif
  1766 	// Floating
  1767  public:
  1768 	// swap the two byte of the low 16-bit halfword
  1769 	// this directive will use AT, be sure the high 16-bit of reg is zero
  1770 	// by yjl 6/28/2005
  1771 	void hswap(Register reg);
  1772   	void huswap(Register reg);
  1774 	// convert big endian integer to little endian integer
  1775   // by yjl 6/29/2005
  1776   	void swap(Register reg);
  1778   // implement the x86 instruction semantic
  1779   // if c_reg == *dest then *dest <= x_reg
  1780 	// else c_reg <= *dest
  1781 	// the AT indicate if xchg occurred, 1 for xchged, else  0
  1782 	// by yjl 6/28/2005
  1783 	void cmpxchg(Register x_reg, Address dest, Register c_reg);
  1784 #ifdef _LP64
  1785 	void cmpxchg32(Register x_reg, Address dest, Register c_reg);
  1786 #endif
  1787 	void cmpxchg8(Register x_regLo, Register x_regHi, Address dest, Register c_regLo, Register c_regHi);
  1791 	void round_to(Register reg, int modulus) {
  1792 		assert_different_registers(reg, AT);
  1793 		increment(reg, modulus - 1);
  1794 		move(AT, - modulus);
  1795 		andr(reg, reg, AT);
  1798 	//pop & push, added by aoqi
  1799 #ifdef _LP64
  1800 	void extend_sign(Register rh, Register rl) { stop("extend_sign"); }
  1801 	void neg(Register reg) { dsubu(reg, R0, reg); }
  1802 	void push (Register reg)      { sd  (reg, SP, -8); daddi(SP, SP, -8); }
  1803 	void push (FloatRegister reg) { sdc1(reg, SP, -8); daddi(SP, SP, -8); }
  1804 	void pop  (Register reg)      { ld  (reg, SP, 0);  daddi(SP, SP, 8); }
  1805 	void pop  (FloatRegister reg) { ldc1(reg, SP, 0);  daddi(SP, SP, 8); }
  1806 	void pop  ()                  { daddi(SP, SP, 8); }
  1807 	void pop2 ()                  { daddi(SP, SP, 16); }
  1808 #else
  1809 	void extend_sign(Register rh, Register rl) { sra(rh, rl, 31); }
  1810 	void neg(Register reg) { subu(reg, R0, reg); }
  1811 	void push (Register reg)      { sw  (reg, SP, -4); addi(SP, SP, -4); }
  1812 	void push (FloatRegister reg) { swc1(reg, SP, -4); addi(SP, SP, -4); }
  1813 	void pop  (Register reg)      { lw  (reg, SP, 0);  addi(SP, SP, 4); }
  1814 	void pop  (FloatRegister reg) { lwc1(reg, SP, 0);  addi(SP, SP, 4); }
  1815 	void pop  ()                  { addi(SP, SP, 4); }
  1816 	void pop2 ()                  { addi(SP, SP, 8); }
  1817 #endif
  1818 	void push2(Register reg1, Register reg2);
  1819 	void pop2 (Register reg1, Register reg2);
  1820 	void dpush (Register reg)     { sd  (reg, SP, -8); daddi(SP, SP, -8); }
  1821 	void dpop  (Register reg)     { ld  (reg, SP, 0);  daddi(SP, SP, 8); }
  1823 	/* branches may exceed 16-bit offset */
  1824 	void b_far(address entry);
  1825 	void b_far(Label& L);
  1827 	void bne_far    (Register rs, Register rt, address entry);
  1828 	void bne_far    (Register rs, Register rt, Label& L);
  1830 	void beq_far    (Register rs, Register rt, address entry);
  1831 	void beq_far    (Register rs, Register rt, Label& L);
  1833 	//move an 32-bit immediate to Register
  1834 	void move(Register reg, int imm32)  { li32(reg, imm32); }
  1835 	void li	(Register rd, long imm);
  1836 	void li	(Register rd, address addr) { li(rd, (long)addr); }
  1837 	//replace move(Register reg, int imm)
  1838 	void li32(Register rd, int imm32); // sign-extends to 64 bits on mips64
  1839 #ifdef _LP64
  1840 	void dli(Register rd, long imm) { li(rd, imm); }
  1841 	void li64(Register rd, long imm);
  1842 	void li48(Register rd, long imm);
  1843 #endif
  1845 #ifdef _LP64
  1846 	void move(Register rd, Register rs)   { dadd(rd, rs, R0); }
  1847 	void move_u32(Register rd, Register rs)   { addu32(rd, rs, R0); }
  1848 #else
  1849 	void move(Register rd, Register rs)   { add(rd, rs, R0); }
  1850 #endif
  1851 	void dmove(Register rd, Register rs)  { dadd(rd, rs, R0); }
  1853 #ifdef _LP64
  1854   	void shl(Register reg, int sa)        { dsll(reg, reg, sa); }
  1855   	void shr(Register reg, int sa)        { dsrl(reg, reg, sa); }
  1856   	void sar(Register reg, int sa)        { dsra(reg, reg, sa); }
  1857 #else
  1858   	void shl(Register reg, int sa)        { sll(reg, reg, sa); }
  1859   	void shr(Register reg, int sa)        { srl(reg, reg, sa); }
  1860   	void sar(Register reg, int sa)        { sra(reg, reg, sa); }
  1861 #endif
  1863 #ifndef PRODUCT
  1864   static void pd_print_patched_instruction(address branch) {
  1865   jint stub_inst = *(jint*) branch;
  1866   print_instruction(stub_inst);
  1867   ::tty->print("%s", " (unresolved)");
  1870 #endif
  1872 	// the follow two might use AT register, be sure you have no meanful data in AT before you call them
  1873 	// by yjl 6/23/2005
  1874 	void increment(Register reg, int imm);
  1875 	void decrement(Register reg, int imm);
  1877 	//FIXME 
  1878   	void empty_FPU_stack(){/*need implemented*/};
  1880 //we need 2 fun to save and resotre general register
  1881 	void pushad();
  1882 	void popad();
  1884   // Test sub_klass against super_klass, with fast and slow paths.
  1886   // The fast path produces a tri-state answer: yes / no / maybe-slow.
  1887   // One of the three labels can be NULL, meaning take the fall-through.
  1888   // If super_check_offset is -1, the value is loaded up from super_klass.
  1889   // No registers are killed, except temp_reg.
  1890   void check_klass_subtype_fast_path(Register sub_klass,
  1891                                      Register super_klass,
  1892                                      Register temp_reg,
  1893                                      Label* L_success,
  1894                                      Label* L_failure,
  1895                                      Label* L_slow_path,
  1896                 RegisterOrConstant super_check_offset = RegisterOrConstant(-1));
  1898   // The rest of the type check; must be wired to a corresponding fast path.
  1899   // It does not repeat the fast path logic, so don't use it standalone.
  1900   // The temp_reg and temp2_reg can be noreg, if no temps are available.
  1901   // Updates the sub's secondary super cache as necessary.
  1902   // If set_cond_codes, condition codes will be Z on success, NZ on failure.
  1903   void check_klass_subtype_slow_path(Register sub_klass,
  1904                                      Register super_klass,
  1905                                      Register temp_reg,
  1906                                      Register temp2_reg,
  1907                                      Label* L_success,
  1908                                      Label* L_failure,
  1909                                      bool set_cond_codes = false);
  1911    // Simplified, combined version, good for typical uses.
  1912    // Falls through on failure.
  1913    void check_klass_subtype(Register sub_klass,
  1914                             Register super_klass,
  1915                             Register temp_reg,
  1916                             Label& L_success);
  1918   // method handles (JSR 292)
  1919   Address argument_address(RegisterOrConstant arg_slot, int extra_slot_offset = 0);
  1921   void get_vm_result  (Register oop_result, Register thread);
  1922   void get_vm_result_2(Register metadata_result, Register thread);
  1923 #undef VIRTUAL
  1925 };
  1927 /**
  1928  * class SkipIfEqual:
  1930  * Instantiating this class will result in assembly code being output that will
  1931  * jump around any code emitted between the creation of the instance and it's
  1932  * automatic destruction at the end of a scope block, depending on the value of
  1933  * the flag passed to the constructor, which will be checked at run-time.
  1934  */
  1935 class SkipIfEqual {
  1936  private:
  1937   MacroAssembler* _masm;
  1938   Label _label;
  1940  public:
  1941    SkipIfEqual(MacroAssembler*, const bool* flag_addr, bool value);
  1942    ~SkipIfEqual();
  1943 };
  1945 #ifdef ASSERT
  1946 inline bool AbstractAssembler::pd_check_instruction_mark() { return true; }
  1947 #endif
  1949 #endif // CPU_MIPS_VM_ASSEMBLER_MIPS_HPP

mercurial