Subzero, MIPS32: Filling missing bits from genTargetHelperCallFor
Implements missing calls to runtime libraries, covering mostly
data casting.
R=stichnot@chromium.org
Review URL: https://codereview.chromium.org/2363333002 .
Patch from Srdjan Obucina <Srdjan.Obucina@imgtec.com>.
diff --git a/src/IceTargetLoweringMIPS32.cpp b/src/IceTargetLoweringMIPS32.cpp
index a6d9da8..3765c5a 100644
--- a/src/IceTargetLoweringMIPS32.cpp
+++ b/src/IceTargetLoweringMIPS32.cpp
@@ -309,16 +309,26 @@
return;
case InstCast::Fptosi:
case InstCast::Fptoui: {
- if (DestTy != IceType_i64) {
+ if ((DestTy != IceType_i32) && (DestTy != IceType_i64)) {
return;
}
+ const bool DestIs32 = DestTy == IceType_i32;
const bool DestIsSigned = CastKind == InstCast::Fptosi;
const bool Src0IsF32 = isFloat32Asserting32Or64(SrcTy);
- Operand *TargetHelper = Ctx->getRuntimeHelperFunc(
- Src0IsF32 ? (DestIsSigned ? RuntimeHelper::H_fptosi_f32_i64
- : RuntimeHelper::H_fptoui_f32_i64)
- : (DestIsSigned ? RuntimeHelper::H_fptosi_f64_i64
- : RuntimeHelper::H_fptoui_f64_i64));
+ RuntimeHelper RTHFunc = RuntimeHelper::H_Num;
+ if (DestIsSigned) {
+ if (DestIs32) {
+ return;
+ }
+ RTHFunc = Src0IsF32 ? RuntimeHelper::H_fptosi_f32_i64
+ : RuntimeHelper::H_fptosi_f64_i64;
+ } else {
+ RTHFunc = Src0IsF32 ? (DestIs32 ? RuntimeHelper::H_fptoui_f32_i32
+ : RuntimeHelper::H_fptoui_f32_i64)
+ : (DestIs32 ? RuntimeHelper::H_fptoui_f64_i32
+ : RuntimeHelper::H_fptoui_f64_i64);
+ }
+ Operand *TargetHelper = Ctx->getRuntimeHelperFunc(RTHFunc);
static constexpr SizeT MaxArgs = 1;
auto *Call = Context.insert<InstCall>(MaxArgs, Dest, TargetHelper,
NoTailCall, IsTargetHelperCall);
@@ -328,16 +338,26 @@
}
case InstCast::Sitofp:
case InstCast::Uitofp: {
- if (SrcTy != IceType_i64) {
+ if ((SrcTy != IceType_i32) && (SrcTy != IceType_i64)) {
return;
}
+ const bool SourceIs32 = SrcTy == IceType_i32;
const bool SourceIsSigned = CastKind == InstCast::Sitofp;
const bool DestIsF32 = isFloat32Asserting32Or64(Dest->getType());
- Operand *TargetHelper = Ctx->getRuntimeHelperFunc(
- DestIsF32 ? (SourceIsSigned ? RuntimeHelper::H_sitofp_i64_f32
- : RuntimeHelper::H_uitofp_i64_f32)
- : (SourceIsSigned ? RuntimeHelper::H_sitofp_i64_f64
- : RuntimeHelper::H_uitofp_i64_f64));
+ RuntimeHelper RTHFunc = RuntimeHelper::H_Num;
+ if (SourceIsSigned) {
+ if (SourceIs32) {
+ return;
+ }
+ RTHFunc = DestIsF32 ? RuntimeHelper::H_sitofp_i64_f32
+ : RuntimeHelper::H_sitofp_i64_f64;
+ } else {
+ RTHFunc = DestIsF32 ? (SourceIs32 ? RuntimeHelper::H_uitofp_i32_f32
+ : RuntimeHelper::H_uitofp_i64_f32)
+ : (SourceIs32 ? RuntimeHelper::H_uitofp_i32_f64
+ : RuntimeHelper::H_uitofp_i64_f64);
+ }
+ Operand *TargetHelper = Ctx->getRuntimeHelperFunc(RTHFunc);
static constexpr SizeT MaxArgs = 1;
auto *Call = Context.insert<InstCall>(MaxArgs, Dest, TargetHelper,
NoTailCall, IsTargetHelperCall);
@@ -2584,54 +2604,67 @@
_mov(Dest, DestR);
break;
}
- case InstCast::Fptosi: {
+ case InstCast::Fptosi:
+ case InstCast::Fptoui: {
if (llvm::isa<Variable64On32>(Dest)) {
llvm::report_fatal_error("fp-to-i64 should have been prelowered.");
return;
}
- if (Src0Ty == IceType_f32 && DestTy == IceType_i32) {
- Variable *Src0R = legalizeToReg(Src0);
- Variable *FTmp = makeReg(IceType_f32);
- _trunc_w_s(FTmp, Src0R);
- _mov(Dest, FTmp);
- } else {
- UnimplementedLoweringError(this, Instr);
- }
- break;
- }
- case InstCast::Fptoui:
- if (llvm::isa<Variable64On32>(Dest)) {
- llvm::report_fatal_error("fp-to-i64 should have been prelowered.");
- return;
+ if (DestTy != IceType_i64) {
+ if (Src0Ty == IceType_f32 && isScalarIntegerType(DestTy)) {
+ Variable *Src0R = legalizeToReg(Src0);
+ Variable *FTmp = makeReg(IceType_f32);
+ _trunc_w_s(FTmp, Src0R);
+ _mov(Dest, FTmp);
+ return;
+ }
+ if (Src0Ty == IceType_f64 && isScalarIntegerType(DestTy)) {
+ Variable *Src0R = legalizeToReg(Src0);
+ Variable *FTmp = makeReg(IceType_f64);
+ _trunc_w_d(FTmp, Src0R);
+ _mov(Dest, FTmp);
+ return;
+ }
}
UnimplementedLoweringError(this, Instr);
break;
- case InstCast::Sitofp: {
- if (llvm::isa<Variable64On32>(Dest)) {
- llvm::report_fatal_error("i64-to-fp should have been prelowered.");
- return;
- }
- if (Src0Ty == IceType_i32 && DestTy == IceType_f32) {
- Variable *Src0R = legalizeToReg(Src0);
- Variable *FTmp1 = makeReg(IceType_f32);
- Variable *FTmp2 = makeReg(IceType_f32);
- _mov(FTmp1, Src0R);
- _cvt_s_w(FTmp2, FTmp1);
- _mov(Dest, FTmp2);
- } else {
- UnimplementedLoweringError(this, Instr);
- }
- break;
}
+ case InstCast::Sitofp:
case InstCast::Uitofp: {
if (llvm::isa<Variable64On32>(Dest)) {
llvm::report_fatal_error("i64-to-fp should have been prelowered.");
return;
}
+ if (Src0Ty != IceType_i64) {
+ if (isScalarIntegerType(Src0Ty) && DestTy == IceType_f32) {
+ Variable *Src0R = legalizeToReg(Src0);
+ Variable *FTmp1 = makeReg(IceType_f32);
+ Variable *FTmp2 = makeReg(IceType_f32);
+ _mtc1(FTmp1, Src0R);
+ _cvt_s_w(FTmp2, FTmp1);
+ _mov(Dest, FTmp2);
+ return;
+ }
+ if (isScalarIntegerType(Src0Ty) && DestTy == IceType_f64) {
+ Variable *Src0R = legalizeToReg(Src0);
+ Variable *FTmp1 = makeReg(IceType_f64);
+ Variable *FTmp2 = makeReg(IceType_f64);
+ _mtc1(FTmp1, Src0R);
+ _cvt_d_w(FTmp2, FTmp1);
+ _mov(Dest, FTmp2);
+ return;
+ }
+ }
UnimplementedLoweringError(this, Instr);
break;
}
case InstCast::Bitcast: {
+ Operand *Src0 = Instr->getSrc(0);
+ if (DestTy == Src0->getType()) {
+ auto *Assign = InstAssign::create(Func, Dest, Src0);
+ lowerAssign(Assign);
+ return;
+ }
switch (DestTy) {
case IceType_NUM:
case IceType_void: