| OLD | NEW |
| 1 //===- subzero/src/IceTargetLoweringMIPS32.cpp - MIPS32 lowering ----------===// | 1 //===- subzero/src/IceTargetLoweringMIPS32.cpp - MIPS32 lowering ----------===// |
| 2 // | 2 // |
| 3 // The Subzero Code Generator | 3 // The Subzero Code Generator |
| 4 // | 4 // |
| 5 // This file is distributed under the University of Illinois Open Source | 5 // This file is distributed under the University of Illinois Open Source |
| 6 // License. See LICENSE.TXT for details. | 6 // License. See LICENSE.TXT for details. |
| 7 // | 7 // |
| 8 //===----------------------------------------------------------------------===// | 8 //===----------------------------------------------------------------------===// |
| 9 /// | 9 /// |
| 10 /// \file | 10 /// \file |
| (...skipping 342 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 353 UnimplementedError(Func->getContext()->getFlags()); | 353 UnimplementedError(Func->getContext()->getFlags()); |
| 354 return Ctx->getConstantZero(Ty); | 354 return Ctx->getConstantZero(Ty); |
| 355 } | 355 } |
| 356 return From; | 356 return From; |
| 357 } | 357 } |
| 358 | 358 |
| 359 Variable *TargetMIPS32::makeReg(Type Type, RegNumT RegNum) { | 359 Variable *TargetMIPS32::makeReg(Type Type, RegNumT RegNum) { |
| 360 // There aren't any 64-bit integer registers for Mips32. | 360 // There aren't any 64-bit integer registers for Mips32. |
| 361 assert(Type != IceType_i64); | 361 assert(Type != IceType_i64); |
| 362 Variable *Reg = Func->makeVariable(Type); | 362 Variable *Reg = Func->makeVariable(Type); |
| 363 if (RegNum == RegNumT::NoRegister) | 363 if (RegNum.hasValue()) |
| 364 Reg->setRegNum(RegNum); |
| 365 else |
| 364 Reg->setMustHaveReg(); | 366 Reg->setMustHaveReg(); |
| 365 else | |
| 366 Reg->setRegNum(RegNum); | |
| 367 return Reg; | 367 return Reg; |
| 368 } | 368 } |
| 369 | 369 |
| 370 void TargetMIPS32::emitVariable(const Variable *Var) const { | 370 void TargetMIPS32::emitVariable(const Variable *Var) const { |
| 371 if (!BuildDefs::dump()) | 371 if (!BuildDefs::dump()) |
| 372 return; | 372 return; |
| 373 Ostream &Str = Ctx->getStrEmit(); | 373 Ostream &Str = Ctx->getStrEmit(); |
| 374 const Type FrameSPTy = IceType_i32; | 374 const Type FrameSPTy = IceType_i32; |
| 375 if (Var->hasReg()) { | 375 if (Var->hasReg()) { |
| 376 Str << '$' << getRegName(Var->getRegNum(), Var->getType()); | 376 Str << '$' << getRegName(Var->getRegNum(), Var->getType()); |
| (...skipping 869 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 1246 Context.insert<InstFakeDef>(Reg); | 1246 Context.insert<InstFakeDef>(Reg); |
| 1247 return Reg; | 1247 return Reg; |
| 1248 } else if (auto *C32 = llvm::dyn_cast<ConstantInteger32>(From)) { | 1248 } else if (auto *C32 = llvm::dyn_cast<ConstantInteger32>(From)) { |
| 1249 const uint32_t Value = C32->getValue(); | 1249 const uint32_t Value = C32->getValue(); |
| 1250 // Check if the immediate will fit in a Flexible second operand, | 1250 // Check if the immediate will fit in a Flexible second operand, |
| 1251 // if a Flexible second operand is allowed. We need to know the exact | 1251 // if a Flexible second operand is allowed. We need to know the exact |
| 1252 // value, so that rules out relocatable constants. | 1252 // value, so that rules out relocatable constants. |
| 1253 // Also try the inverse and use MVN if possible. | 1253 // Also try the inverse and use MVN if possible. |
| 1254 // Do a movw/movt to a register. | 1254 // Do a movw/movt to a register. |
| 1255 Variable *Reg; | 1255 Variable *Reg; |
| 1256 if (RegNum == RegNumT::NoRegister) | 1256 if (RegNum.hasValue()) |
| 1257 Reg = getPhysicalRegister(RegNum); |
| 1258 else |
| 1257 Reg = makeReg(Ty, RegNum); | 1259 Reg = makeReg(Ty, RegNum); |
| 1258 else | |
| 1259 Reg = getPhysicalRegister(RegNum); | |
| 1260 if (isInt<16>(int32_t(Value))) { | 1260 if (isInt<16>(int32_t(Value))) { |
| 1261 Variable *Zero = getPhysicalRegister(RegMIPS32::Reg_ZERO, Ty); | 1261 Variable *Zero = getPhysicalRegister(RegMIPS32::Reg_ZERO, Ty); |
| 1262 Context.insert<InstFakeDef>(Zero); | 1262 Context.insert<InstFakeDef>(Zero); |
| 1263 _addiu(Reg, Zero, Value); | 1263 _addiu(Reg, Zero, Value); |
| 1264 } else { | 1264 } else { |
| 1265 uint32_t UpperBits = (Value >> 16) & 0xFFFF; | 1265 uint32_t UpperBits = (Value >> 16) & 0xFFFF; |
| 1266 (void)UpperBits; | 1266 (void)UpperBits; |
| 1267 uint32_t LowerBits = Value & 0xFFFF; | 1267 uint32_t LowerBits = Value & 0xFFFF; |
| 1268 Variable *TReg = makeReg(Ty, RegNum); | 1268 Variable *TReg = makeReg(Ty, RegNum); |
| 1269 _lui(TReg, UpperBits); | 1269 _lui(TReg, UpperBits); |
| 1270 _ori(Reg, TReg, LowerBits); | 1270 _ori(Reg, TReg, LowerBits); |
| 1271 } | 1271 } |
| 1272 return Reg; | 1272 return Reg; |
| 1273 } | 1273 } |
| 1274 if (auto *Var = llvm::dyn_cast<Variable>(From)) { | 1274 if (auto *Var = llvm::dyn_cast<Variable>(From)) { |
| 1275 // Check if the variable is guaranteed a physical register. This | 1275 // Check if the variable is guaranteed a physical register. This |
| 1276 // can happen either when the variable is pre-colored or when it is | 1276 // can happen either when the variable is pre-colored or when it is |
| 1277 // assigned infinite weight. | 1277 // assigned infinite weight. |
| 1278 bool MustHaveRegister = (Var->hasReg() || Var->mustHaveReg()); | 1278 bool MustHaveRegister = (Var->hasReg() || Var->mustHaveReg()); |
| 1279 // We need a new physical register for the operand if: | 1279 // We need a new physical register for the operand if: |
| 1280 // Mem is not allowed and Var isn't guaranteed a physical | 1280 // Mem is not allowed and Var isn't guaranteed a physical |
| 1281 // register, or | 1281 // register, or |
| 1282 // RegNum is required and Var->getRegNum() doesn't match. | 1282 // RegNum is required and Var->getRegNum() doesn't match. |
| 1283 if ((!(Allowed & Legal_Mem) && !MustHaveRegister) || | 1283 if ((!(Allowed & Legal_Mem) && !MustHaveRegister) || |
| 1284 (RegNum != RegNumT::NoRegister && RegNum != Var->getRegNum())) { | 1284 (RegNum.hasValue() && RegNum != Var->getRegNum())) { |
| 1285 From = copyToReg(From, RegNum); | 1285 From = copyToReg(From, RegNum); |
| 1286 } | 1286 } |
| 1287 return From; | 1287 return From; |
| 1288 } | 1288 } |
| 1289 return From; | 1289 return From; |
| 1290 } | 1290 } |
| 1291 | 1291 |
| 1292 TargetHeaderMIPS32::TargetHeaderMIPS32(GlobalContext *Ctx) | 1292 TargetHeaderMIPS32::TargetHeaderMIPS32(GlobalContext *Ctx) |
| 1293 : TargetHeaderLowering(Ctx) {} | 1293 : TargetHeaderLowering(Ctx) {} |
| 1294 | 1294 |
| 1295 void TargetHeaderMIPS32::lower() { | 1295 void TargetHeaderMIPS32::lower() { |
| 1296 OstreamLocker L(Ctx); | 1296 OstreamLocker L(Ctx); |
| 1297 Ostream &Str = Ctx->getStrEmit(); | 1297 Ostream &Str = Ctx->getStrEmit(); |
| 1298 Str << "\t.set\t" | 1298 Str << "\t.set\t" |
| 1299 << "nomicromips\n"; | 1299 << "nomicromips\n"; |
| 1300 Str << "\t.set\t" | 1300 Str << "\t.set\t" |
| 1301 << "nomips16\n"; | 1301 << "nomips16\n"; |
| 1302 } | 1302 } |
| 1303 | 1303 |
| 1304 llvm::SmallBitVector TargetMIPS32::TypeToRegisterSet[RCMIPS32_NUM]; | 1304 llvm::SmallBitVector TargetMIPS32::TypeToRegisterSet[RCMIPS32_NUM]; |
| 1305 llvm::SmallBitVector TargetMIPS32::TypeToRegisterSetUnfiltered[RCMIPS32_NUM]; | 1305 llvm::SmallBitVector TargetMIPS32::TypeToRegisterSetUnfiltered[RCMIPS32_NUM]; |
| 1306 llvm::SmallBitVector TargetMIPS32::RegisterAliases[RegMIPS32::Reg_NUM]; | 1306 llvm::SmallBitVector TargetMIPS32::RegisterAliases[RegMIPS32::Reg_NUM]; |
| 1307 | 1307 |
| 1308 } // end of namespace MIPS32 | 1308 } // end of namespace MIPS32 |
| 1309 } // end of namespace Ice | 1309 } // end of namespace Ice |
| OLD | NEW |