Chromium Code Reviews| Index: src/IceTargetLoweringMIPS32.cpp |
| diff --git a/src/IceTargetLoweringMIPS32.cpp b/src/IceTargetLoweringMIPS32.cpp |
| index c4b602463f20af75a03df68d14f4f43a92998fa5..e920e24bdac1097b6932f943b08673b5a1a0b78a 100644 |
| --- a/src/IceTargetLoweringMIPS32.cpp |
| +++ b/src/IceTargetLoweringMIPS32.cpp |
| @@ -3421,9 +3421,114 @@ void TargetDataMIPS32::lowerGlobals(const VariableDeclarationList &Vars, |
| } |
| } |
| +namespace { |
| +template <typename T> struct ConstantPoolEmitterTraits; |
| + |
| +static_assert(sizeof(uint64_t) == 8, |
| + "uint64_t is supposed to be 8 bytes wide."); |
| + |
| +// TODO(jaydeep.patil): implement the following when implementing constant |
| +// randomization: |
| +// * template <> struct ConstantPoolEmitterTraits<uint8_t> |
| +// * template <> struct ConstantPoolEmitterTraits<uint16_t> |
| +// * template <> struct ConstantPoolEmitterTraits<uint32_t> |
| +template <> struct ConstantPoolEmitterTraits<float> { |
| + using ConstantType = ConstantFloat; |
| + static constexpr Type IceType = IceType_f32; |
| + // AsmTag and TypeName can't be constexpr because llvm::StringRef is unhappy |
| + // about them being constexpr. |
| + static const char AsmTag[]; |
| + static const char TypeName[]; |
| + static uint64_t bitcastToUint64(float Value) { |
| + static_assert(sizeof(Value) == sizeof(uint32_t), |
| + "Float should be 4 bytes."); |
| + const uint32_t IntValue = Utils::bitCopy<uint32_t>(Value); |
| + return static_cast<uint64_t>(IntValue); |
| + } |
| +}; |
| +const char ConstantPoolEmitterTraits<float>::AsmTag[] = ".word"; |
| +const char ConstantPoolEmitterTraits<float>::TypeName[] = "f32"; |
| + |
| +template <> struct ConstantPoolEmitterTraits<double> { |
| + using ConstantType = ConstantDouble; |
| + static constexpr Type IceType = IceType_f64; |
| + static const char AsmTag[]; |
| + static const char TypeName[]; |
| + static uint64_t bitcastToUint64(double Value) { |
| + static_assert(sizeof(double) == sizeof(uint64_t), |
| + "Double should be 8 bytes."); |
| + return Utils::bitCopy<uint64_t>(Value); |
| + } |
| +}; |
| +const char ConstantPoolEmitterTraits<double>::AsmTag[] = ".word"; |
|
Jim Stichnoth
2016/09/19 20:50:14
I was wondering about the use of ".word" for both
jaydeep.patil
2016/09/20 07:28:27
Done.
|
| +const char ConstantPoolEmitterTraits<double>::TypeName[] = "f64"; |
| + |
| +template <typename T> |
| +void emitConstant( |
| + Ostream &Str, |
| + const typename ConstantPoolEmitterTraits<T>::ConstantType *Const) { |
| + if (!BuildDefs::dump()) |
| + return; |
| + using Traits = ConstantPoolEmitterTraits<T>; |
| + Str << Const->getLabelName(); |
| + T Value = Const->getValue(); |
| + if (Traits::IceType == IceType_f64) { |
| + uint64_t BitValue = Traits::bitcastToUint64(Value); |
| + uint32_t BitValueHi = (BitValue >> 32) & 0xffffffff; |
| + uint32_t BitValueLo = BitValue & 0xffffffff; |
| + Str << ":\n\t" << Traits::AsmTag << "\t0x"; |
| + Str.write_hex(BitValueHi); |
| + Str << "\n\t" << Traits::AsmTag << "\t0x"; |
| + Str.write_hex(BitValueLo); |
| + } else { |
| + Str << ":\n\t" << Traits::AsmTag << "\t0x"; |
| + Str.write_hex(Traits::bitcastToUint64(Value)); |
| + } |
| + Str << "\t/* " << Traits::TypeName << " " << Value << " */\n"; |
| +} |
| + |
| +template <typename T> void emitConstantPool(GlobalContext *Ctx) { |
| + if (!BuildDefs::dump()) |
| + return; |
| + using Traits = ConstantPoolEmitterTraits<T>; |
| + static constexpr size_t MinimumAlignment = 4; |
| + SizeT Align = std::max(MinimumAlignment, typeAlignInBytes(Traits::IceType)); |
| + assert((Align % 4) == 0 && "Constants should be aligned"); |
| + Ostream &Str = Ctx->getStrEmit(); |
| + ConstantList Pool = Ctx->getConstantPool(Traits::IceType); |
| + Str << "\t.section\t.rodata.cst" << Align << ",\"aM\",%progbits," << Align |
| + << "\n" |
| + << "\t.align\t" << (Align == 4 ? 2 : 3) << "\n"; |
| + if (getFlags().getReorderPooledConstants()) { |
| + // TODO(jaydeep.patil): add constant pooling. |
| + UnimplementedError(getFlags()); |
| + } |
| + for (Constant *C : Pool) { |
| + if (!C->getShouldBePooled()) { |
| + continue; |
| + } |
| + emitConstant<T>(Str, llvm::dyn_cast<typename Traits::ConstantType>(C)); |
| + } |
| +} |
| +} // end of anonymous namespace |
| + |
| void TargetDataMIPS32::lowerConstants() { |
| if (getFlags().getDisableTranslation()) |
| return; |
| + switch (getFlags().getOutFileType()) { |
| + case FT_Elf: { |
| + ELFObjectWriter *Writer = Ctx->getObjectWriter(); |
| + Writer->writeConstantPool<ConstantFloat>(IceType_f32); |
| + Writer->writeConstantPool<ConstantDouble>(IceType_f64); |
| + } break; |
| + case FT_Asm: |
| + case FT_Iasm: { |
| + OstreamLocker _(Ctx); |
| + emitConstantPool<float>(Ctx); |
| + emitConstantPool<double>(Ctx); |
| + break; |
| + } |
| + } |
| } |
| void TargetDataMIPS32::lowerJumpTables() { |