mirror of
https://github.com/ldc-developers/ldc.git
synced 2025-05-05 09:31:03 +03:00
Merge pull request #3808 from JohanEngelen/gh3802
Fix issue #3802 - Fix size_t size for 32bit ABI on 64bit architectures.
This commit is contained in:
commit
d38c576919
5 changed files with 52 additions and 21 deletions
|
@ -728,6 +728,8 @@ void registerPredefinedTargetVersions() {
|
||||||
// Set versions for arch bitwidth
|
// Set versions for arch bitwidth
|
||||||
if (gDataLayout->getPointerSizeInBits() == 64) {
|
if (gDataLayout->getPointerSizeInBits() == 64) {
|
||||||
VersionCondition::addPredefinedGlobalIdent("D_LP64");
|
VersionCondition::addPredefinedGlobalIdent("D_LP64");
|
||||||
|
} else if (triple.isArch64Bit()) {
|
||||||
|
VersionCondition::addPredefinedGlobalIdent("D_X32");
|
||||||
} else if (triple.isArch16Bit()) {
|
} else if (triple.isArch16Bit()) {
|
||||||
VersionCondition::addPredefinedGlobalIdent("D_P16");
|
VersionCondition::addPredefinedGlobalIdent("D_P16");
|
||||||
}
|
}
|
||||||
|
|
|
@ -210,16 +210,16 @@ struct LLVM_LIBRARY_VISIBILITY AllocationOpt : public LibCallOptimization {
|
||||||
// This module will also be used in jit runtime
|
// This module will also be used in jit runtime
|
||||||
// copy these function here to avoid dependencies on rest of compiler
|
// copy these function here to avoid dependencies on rest of compiler
|
||||||
LLIntegerType *DtoSize_t(llvm::LLVMContext &context,
|
LLIntegerType *DtoSize_t(llvm::LLVMContext &context,
|
||||||
const llvm::Triple &triple) {
|
const llvm::DataLayout &DL) {
|
||||||
// the type of size_t does not change once set
|
// the type of size_t does not change once set
|
||||||
static LLIntegerType *t = nullptr;
|
static LLIntegerType *t = nullptr;
|
||||||
if (t == nullptr) {
|
if (t == nullptr) {
|
||||||
|
const auto ptrsize = DL.getPointerSize();
|
||||||
if (triple.isArch64Bit()) {
|
if (ptrsize == 8) {
|
||||||
t = LLType::getInt64Ty(context);
|
t = LLType::getInt64Ty(context);
|
||||||
} else if (triple.isArch32Bit()) {
|
} else if (ptrsize == 4) {
|
||||||
t = LLType::getInt32Ty(context);
|
t = LLType::getInt32Ty(context);
|
||||||
} else if (triple.isArch16Bit()) {
|
} else if (ptrsize == 2) {
|
||||||
t = LLType::getInt16Ty(context);
|
t = LLType::getInt16Ty(context);
|
||||||
} else {
|
} else {
|
||||||
llvm_unreachable("Unsupported size_t width");
|
llvm_unreachable("Unsupported size_t width");
|
||||||
|
@ -229,9 +229,8 @@ LLIntegerType *DtoSize_t(llvm::LLVMContext &context,
|
||||||
}
|
}
|
||||||
|
|
||||||
llvm::ConstantInt *DtoConstSize_t(llvm::LLVMContext &context,
|
llvm::ConstantInt *DtoConstSize_t(llvm::LLVMContext &context,
|
||||||
const llvm::Triple &targetTriple,
|
const llvm::DataLayout &DL, uint64_t i) {
|
||||||
uint64_t i) {
|
return LLConstantInt::get(DtoSize_t(context, DL), i, false);
|
||||||
return LLConstantInt::get(DtoSize_t(context, targetTriple), i, false);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
/// ArraySliceCopyOpt - Turn slice copies into llvm.memcpy when safe
|
/// ArraySliceCopyOpt - Turn slice copies into llvm.memcpy when safe
|
||||||
|
@ -272,13 +271,11 @@ struct LLVM_LIBRARY_VISIBILITY ArraySliceCopyOpt : public LibCallOptimization {
|
||||||
|
|
||||||
// Equal length and the pointers definitely don't alias, so it's safe to
|
// Equal length and the pointers definitely don't alias, so it's safe to
|
||||||
// replace the call with memcpy
|
// replace the call with memcpy
|
||||||
auto Size =
|
auto size = Sz != llvm::MemoryLocation::UnknownSize
|
||||||
Sz != llvm::MemoryLocation::UnknownSize
|
? DtoConstSize_t(Callee->getContext(),
|
||||||
? DtoConstSize_t(
|
Callee->getParent()->getDataLayout(), Sz)
|
||||||
Callee->getContext(),
|
: B.CreateMul(DstLength, ElemSz);
|
||||||
llvm::Triple(Callee->getParent()->getTargetTriple()), Sz)
|
return EmitMemCpy(CI->getOperand(0), CI->getOperand(2), size, 1, B);
|
||||||
: B.CreateMul(DstLength, ElemSz);
|
|
||||||
return EmitMemCpy(CI->getOperand(0), CI->getOperand(2), Size, 1, B);
|
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
|
||||||
|
|
|
@ -90,7 +90,7 @@ void Target::_init(const Param ¶ms) {
|
||||||
classinfosize = 0; // unused
|
classinfosize = 0; // unused
|
||||||
maxStaticDataSize = std::numeric_limits<unsigned long long>::max();
|
maxStaticDataSize = std::numeric_limits<unsigned long long>::max();
|
||||||
|
|
||||||
c.longsize = triple.isArch64Bit() && !isMSVC ? 8 : 4;
|
c.longsize = (ptrsize == 8) && !isMSVC ? 8 : 4;
|
||||||
c.long_doublesize = realsize;
|
c.long_doublesize = realsize;
|
||||||
c.wchar_tsize = triple.isOSWindows() ? 2 : 4;
|
c.wchar_tsize = triple.isOSWindows() ? 2 : 4;
|
||||||
|
|
||||||
|
|
|
@ -16,6 +16,7 @@
|
||||||
#include "dmd/id.h"
|
#include "dmd/id.h"
|
||||||
#include "dmd/init.h"
|
#include "dmd/init.h"
|
||||||
#include "dmd/module.h"
|
#include "dmd/module.h"
|
||||||
|
#include "dmd/target.h"
|
||||||
#include "driver/cl_options.h"
|
#include "driver/cl_options.h"
|
||||||
#include "gen/abi.h"
|
#include "gen/abi.h"
|
||||||
#include "gen/arrays.h"
|
#include "gen/arrays.h"
|
||||||
|
@ -298,13 +299,11 @@ LLIntegerType *DtoSize_t() {
|
||||||
// the type of size_t does not change once set
|
// the type of size_t does not change once set
|
||||||
static LLIntegerType *t = nullptr;
|
static LLIntegerType *t = nullptr;
|
||||||
if (t == nullptr) {
|
if (t == nullptr) {
|
||||||
auto triple = global.params.targetTriple;
|
if (target.ptrsize == 8) {
|
||||||
|
|
||||||
if (triple->isArch64Bit()) {
|
|
||||||
t = LLType::getInt64Ty(gIR->context());
|
t = LLType::getInt64Ty(gIR->context());
|
||||||
} else if (triple->isArch32Bit()) {
|
} else if (target.ptrsize == 4) {
|
||||||
t = LLType::getInt32Ty(gIR->context());
|
t = LLType::getInt32Ty(gIR->context());
|
||||||
} else if (triple->isArch16Bit()) {
|
} else if (target.ptrsize == 2) {
|
||||||
t = LLType::getInt16Ty(gIR->context());
|
t = LLType::getInt16Ty(gIR->context());
|
||||||
} else {
|
} else {
|
||||||
llvm_unreachable("Unsupported size_t width");
|
llvm_unreachable("Unsupported size_t width");
|
||||||
|
|
33
tests/compilable/arch64bit_abi32bit_gh3802.d
Normal file
33
tests/compilable/arch64bit_abi32bit_gh3802.d
Normal file
|
@ -0,0 +1,33 @@
|
||||||
|
// Tests compilation for 64-bit architecture with 32-bit word size ABI.
|
||||||
|
// Triple examples: mips64el-linux-gnuabin32, x86_64-linux-gnux32
|
||||||
|
// Targeting x86 because that's the most widely available target in our CI/developer systems.
|
||||||
|
|
||||||
|
// REQUIRES: target_X86
|
||||||
|
// RUN: %ldc -mtriple=x86_64-linux-gnux32 -O -c %s
|
||||||
|
|
||||||
|
static assert((void*).sizeof == 4);
|
||||||
|
static assert(size_t.sizeof == 4);
|
||||||
|
static assert(ptrdiff_t.sizeof == 4);
|
||||||
|
|
||||||
|
version (D_LP64) static assert(0);
|
||||||
|
version (D_X32) { /* expected */ } else static assert(0);
|
||||||
|
|
||||||
|
bool equals(string lhs, string rhs)
|
||||||
|
{
|
||||||
|
foreach (const i; 0 .. lhs.length) {}
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
|
// test _d_array_slice_copy optimization IR pass (requires -O)
|
||||||
|
auto test_ArraySliceCopyOpt()
|
||||||
|
{
|
||||||
|
static void copy(int[] a, int[] b)
|
||||||
|
{
|
||||||
|
a[] = b[];
|
||||||
|
}
|
||||||
|
|
||||||
|
int[2] a = [1, 2];
|
||||||
|
int[2] b = [3, 4];
|
||||||
|
copy(a, b);
|
||||||
|
return a;
|
||||||
|
}
|
Loading…
Add table
Add a link
Reference in a new issue