Index: src/mips/macro-assembler-mips.cc |
diff --git a/src/mips/macro-assembler-mips.cc b/src/mips/macro-assembler-mips.cc |
index 77d03b5554909215a4ce23324276c19efb2b3175..2072b39e7a6d7240b2236f148f34724a6a2d2926 100644 |
--- a/src/mips/macro-assembler-mips.cc |
+++ b/src/mips/macro-assembler-mips.cc |
@@ -574,12 +574,22 @@ void MacroAssembler::Subu(Register rd, Register rs, const Operand& rt) { |
void MacroAssembler::Mul(Register rd, Register rs, const Operand& rt) { |
if (rt.is_reg()) { |
- mul(rd, rs, rt.rm()); |
+ if (kArchVariant == kLoongson) { |
+ mult(rs, rt.rm()); |
+ mflo(rd); |
+ } else { |
+ mul(rd, rs, rt.rm()); |
+ } |
} else { |
// li handles the relocation. |
ASSERT(!rs.is(at)); |
li(at, rt); |
- mul(rd, rs, at); |
+ if (kArchVariant == kLoongson) { |
+ mult(rs, at); |
+ mflo(rd); |
+ } else { |
+ mul(rd, rs, at); |
+ } |
} |
} |
@@ -734,7 +744,7 @@ void MacroAssembler::Sltu(Register rd, Register rs, const Operand& rt) { |
void MacroAssembler::Ror(Register rd, Register rs, const Operand& rt) { |
- if (mips32r2) { |
+ if (kArchVariant == kMips32r2) { |
if (rt.is_reg()) { |
rotrv(rd, rs, rt.rm()); |
} else { |
@@ -922,7 +932,7 @@ void MacroAssembler::Ext(Register rt, |
ASSERT(pos < 32); |
ASSERT(pos + size < 33); |
- if (mips32r2) { |
+ if (kArchVariant == kMips32r2) { |
ext_(rt, rs, pos, size); |
} else { |
// Move rs to rt and shift it left then right to get the |
@@ -946,7 +956,7 @@ void MacroAssembler::Ins(Register rt, |
ASSERT(pos + size <= 32); |
ASSERT(size != 0); |
- if (mips32r2) { |
+ if (kArchVariant == kMips32r2) { |
ins_(rt, rs, pos, size); |
} else { |
ASSERT(!rt.is(t8) && !rs.is(t8)); |
@@ -1016,6 +1026,48 @@ void MacroAssembler::Trunc_uw_d(FPURegister fd, |
mtc1(t8, fd); |
} |
+void MacroAssembler::Trunc_w_d(FPURegister fd, FPURegister fs) { |
+ if (kArchVariant == kLoongson && fd.is(fs)) { |
+ mfc1(t8, FPURegister::from_code(fs.code() + 1)); |
+ trunc_w_d(fd, fs); |
+ mtc1(t8, FPURegister::from_code(fs.code() + 1)); |
+ } else { |
+ trunc_w_d(fd, fs); |
+ } |
+} |
+ |
+void MacroAssembler::Round_w_d(FPURegister fd, FPURegister fs) { |
+ if (kArchVariant == kLoongson && fd.is(fs)) { |
+ mfc1(t8, FPURegister::from_code(fs.code() + 1)); |
+ round_w_d(fd, fs); |
+ mtc1(t8, FPURegister::from_code(fs.code() + 1)); |
+ } else { |
+ round_w_d(fd, fs); |
+ } |
+} |
+ |
+ |
+void MacroAssembler::Floor_w_d(FPURegister fd, FPURegister fs) { |
+ if (kArchVariant == kLoongson && fd.is(fs)) { |
+ mfc1(t8, FPURegister::from_code(fs.code() + 1)); |
+ floor_w_d(fd, fs); |
+ mtc1(t8, FPURegister::from_code(fs.code() + 1)); |
+ } else { |
+ floor_w_d(fd, fs); |
+ } |
+} |
+ |
+ |
+void MacroAssembler::Ceil_w_d(FPURegister fd, FPURegister fs) { |
+ if (kArchVariant == kLoongson && fd.is(fs)) { |
+ mfc1(t8, FPURegister::from_code(fs.code() + 1)); |
+ ceil_w_d(fd, fs); |
+ mtc1(t8, FPURegister::from_code(fs.code() + 1)); |
+ } else { |
+ ceil_w_d(fd, fs); |
+ } |
+} |
+ |
void MacroAssembler::Trunc_uw_d(FPURegister fd, |
Register rs, |
@@ -1146,6 +1198,104 @@ void MacroAssembler::Move(FPURegister dst, double imm) { |
} |
+void MacroAssembler::Movz(Register rd, Register rs, Register rt) { |
+ if (kArchVariant == kLoongson) { |
+ Label done; |
+ Branch(&done, ne, rt, Operand(zero_reg)); |
+ mov(rd, rs); |
+ bind(&done); |
+ } else { |
+ movz(rd, rs, rt); |
+ } |
+} |
+ |
+ |
+void MacroAssembler::Movn(Register rd, Register rs, Register rt) { |
+ if (kArchVariant == kLoongson) { |
+ Label done; |
+ Branch(&done, eq, rt, Operand(zero_reg)); |
+ mov(rd, rs); |
+ bind(&done); |
+ } else { |
+ movn(rd, rs, rt); |
+ } |
+} |
+ |
+ |
+void MacroAssembler::Movt(Register rd, Register rs, uint16_t cc) { |
+ if (kArchVariant == kLoongson) { |
+ // Tests an FP condition code and then conditionally move rs to rd. |
+ // We do not currently use any FPU cc bit other than bit 0. |
+ ASSERT(cc == 0); |
+ ASSERT(!(rs.is(t8) || rd.is(t8))); |
+ Label done; |
+ Register scratch = t8; |
+ // For testing purposes we need to fetch content of the FCSR register and |
+ // than test its cc (floating point condition code) bit (for cc = 0, it is |
+ // 24. bit of the FCSR). |
+ cfc1(scratch, FCSR); |
+ // For the MIPS I, II and III architectures, the contents of scratch is |
+ // UNPREDICTABLE for the instruction immediately following CFC1. |
+ nop(); |
+ srl(scratch, scratch, 16); |
+ andi(scratch, scratch, 0x0080); |
+ Branch(&done, eq, scratch, Operand(zero_reg)); |
+ mov(rd, rs); |
+ bind(&done); |
+ } else { |
+ movt(rd, rs, cc); |
+ } |
+} |
+ |
+ |
+void MacroAssembler::Movf(Register rd, Register rs, uint16_t cc) { |
+ if (kArchVariant == kLoongson) { |
+ // Tests an FP condition code and then conditionally move rs to rd. |
+ // We do not currently use any FPU cc bit other than bit 0. |
+ ASSERT(cc == 0); |
+ ASSERT(!(rs.is(t8) || rd.is(t8))); |
+ Label done; |
+ Register scratch = t8; |
+ // For testing purposes we need to fetch content of the FCSR register and |
+ // than test its cc (floating point condition code) bit (for cc = 0, it is |
+ // 24. bit of the FCSR). |
+ cfc1(scratch, FCSR); |
+ // For the MIPS I, II and III architectures, the contents of scratch is |
+ // UNPREDICTABLE for the instruction immediately following CFC1. |
+ nop(); |
+ srl(scratch, scratch, 16); |
+ andi(scratch, scratch, 0x0080); |
+ Branch(&done, ne, scratch, Operand(zero_reg)); |
+ mov(rd, rs); |
+ bind(&done); |
+ } else { |
+ movf(rd, rs, cc); |
+ } |
+} |
+ |
+ |
+void MacroAssembler::Clz(Register rd, Register rs) { |
+ if (kArchVariant == kLoongson) { |
+ ASSERT(!(rd.is(t8) || rd.is(t9)) && !(rs.is(t8) || rs.is(t9))); |
+ Register mask = t8; |
+ Register scratch = t9; |
+ Label loop, end; |
+ mov(at, rs); |
+ mov(rd, zero_reg); |
+ lui(mask, 0x8000); |
+ bind(&loop); |
+ and_(scratch, at, mask); |
+ Branch(&end, ne, scratch, Operand(zero_reg)); |
+ addiu(rd, rd, 1); |
+ Branch(&loop, ne, mask, Operand(zero_reg), USE_DELAY_SLOT); |
+ srl(mask, mask, 1); |
+ bind(&end); |
+ } else { |
+ clz(rd, rs); |
+ } |
+} |
+ |
+ |
// Tries to get a signed int32 out of a double precision floating point heap |
// number. Rounds towards 0. Branch to 'not_int32' if the double is out of the |
// 32bits signed integer range. |
@@ -1236,8 +1386,8 @@ void MacroAssembler::ConvertToInt32(Register source, |
subu(scratch2, zero_reg, scratch); |
// Trick to check sign bit (msb) held in dest, count leading zero. |
// 0 indicates negative, save negative version with conditional move. |
- clz(dest, dest); |
- movz(scratch, scratch2, dest); |
+ Clz(dest, dest); |
+ Movz(scratch, scratch2, dest); |
mov(dest, scratch); |
} |
bind(&done); |
@@ -1268,16 +1418,16 @@ void MacroAssembler::EmitFPUTruncate(FPURoundingMode rounding_mode, |
// Do operation based on rounding mode. |
switch (rounding_mode) { |
case kRoundToNearest: |
- round_w_d(result, double_input); |
+ Round_w_d(result, double_input); |
break; |
case kRoundToZero: |
- trunc_w_d(result, double_input); |
+ Trunc_w_d(result, double_input); |
break; |
case kRoundToPlusInf: |
- ceil_w_d(result, double_input); |
+ Ceil_w_d(result, double_input); |
break; |
case kRoundToMinusInf: |
- floor_w_d(result, double_input); |
+ Floor_w_d(result, double_input); |
break; |
} // End of switch-statement. |
@@ -1304,7 +1454,7 @@ void MacroAssembler::EmitOutOfInt32RangeTruncate(Register result, |
// Check for Infinity and NaNs, which should return 0. |
Subu(scratch, result, HeapNumber::kExponentMask); |
- movz(result, zero_reg, scratch); |
+ Movz(result, zero_reg, scratch); |
Branch(&done, eq, scratch, Operand(zero_reg)); |
// Express exponent as delta to (number of mantissa bits + 31). |
@@ -1368,7 +1518,7 @@ void MacroAssembler::EmitOutOfInt32RangeTruncate(Register result, |
result = sign; |
sign = no_reg; |
Subu(result, zero_reg, input_high); |
- movz(result, input_high, scratch); |
+ Movz(result, input_high, scratch); |
bind(&done); |
} |