Index: docs/LangRef.html =================================================================== --- docs/LangRef.html (revision 164831) +++ docs/LangRef.html (working copy) @@ -1364,11 +1364,11 @@ 8-bits. If omitted, the natural stack alignment defaults to "unspecified", which does not prevent any alignment promotions. -
The 'bitcast' instruction converts value to type @@ -5993,9 +5995,10 @@ this conversion. The conversion is done as if the value had been stored to memory and read back as type ty2. Pointer (or vector of pointers) types may only be converted to other pointer - (or vector of pointers) types with this instruction. To convert - pointers to other types, use the inttoptr or - ptrtoint instructions first.
+ (or vector of pointers) types with this instruction if the pointer sizes are + equal. To convert pointers to other types, or pointers of different sizes, + use the inttoptr or + ptrtoint instructions first.Index: include/llvm/AutoUpgrade.h =================================================================== --- include/llvm/AutoUpgrade.h (revision 164831) +++ include/llvm/AutoUpgrade.h (working copy) @@ -19,6 +19,7 @@ class GlobalVariable; class Function; class CallInst; + class BitCastInst; /// This is a more granular function that simply checks an intrinsic function /// for upgrading, and returns true if it requires upgrading. It may return @@ -39,6 +40,11 @@ /// This checks for global variables which should be upgraded. It returns true /// if it requires upgrading. bool UpgradeGlobalVariable(GlobalVariable *GV); + + // Upgrade bitcast into a PtrToInt/IntToPtr sequence of instruction if + // the bitcast is to pointers between address spaces and the pointers + // are of different sizes. + void UpgradeBitCasts(BitCastInst *BCI, Module *M); } // End llvm namespace #endif Index: include/llvm/Module.h =================================================================== --- include/llvm/Module.h (revision 164831) +++ include/llvm/Module.h (working copy) @@ -240,7 +240,7 @@ /// Get the target pointer size. /// @returns PointerSize - an enumeration for the size of the target's pointer - PointerSize getPointerSize() const; + PointerSize getPointerSize(unsigned addrSpace = 0) const; /// Get the global data context. /// @returns LLVMContext - a container for LLVM's global information Index: lib/Bitcode/Reader/BitcodeReader.cpp =================================================================== --- lib/Bitcode/Reader/BitcodeReader.cpp (revision 164831) +++ lib/Bitcode/Reader/BitcodeReader.cpp (working copy) @@ -25,6 +25,7 @@ #include "llvm/Support/DataStream.h" #include "llvm/Support/MathExtras.h" #include "llvm/Support/MemoryBuffer.h" +#include "llvm/Support/InstIterator.h" #include "llvm/OperandTraits.h" using namespace llvm; @@ -1420,6 +1421,10 @@ Function *NewFn; if (UpgradeIntrinsicFunction(FI, NewFn)) UpgradedIntrinsics.push_back(std::make_pair(FI, NewFn)); + for (inst_iterator ib = inst_begin(FI), ie = inst_end(FI); ib != ie;) { + Instruction *Inst = &(*ib); ib++; + UpgradeBitCasts(dyn_cast(Inst), TheModule); + } } // Look for global variables which need to be renamed. Index: lib/VMCore/AutoUpgrade.cpp =================================================================== --- lib/VMCore/AutoUpgrade.cpp (revision 164831) +++ lib/VMCore/AutoUpgrade.cpp (working copy) @@ -22,6 +22,7 @@ #include "llvm/Support/CFG.h" #include "llvm/Support/CallSite.h" #include "llvm/Support/ErrorHandling.h" +#include "llvm/IRBuilder.h" #include using namespace llvm; @@ -157,6 +158,47 @@ return false; } +// Upgrade bitcast into a PtrToInt/IntToPtr sequence of instruction if +// the bitcast is to pointers between address spaces and the pointers +// are of different sizes. +void llvm::UpgradeBitCasts(BitCastInst *BCI, Module *M) { + if (!BCI) return; + Type *DstTy = BCI->getType(); + Type *SrcTy = BCI->getOperand(0)->getType(); + // Don't upgrade if both types are not pointers. + if (!DstTy->isPointerTy() || !SrcTy->isPointerTy()) + return; + + PointerType *DstPtrTy = dyn_cast (DstTy); + PointerType *SrcPtrTy = dyn_cast (SrcTy); + unsigned DstAS = DstPtrTy->getAddressSpace(); + unsigned SrcAS = SrcPtrTy->getAddressSpace(); + // Don't upgrade if address spaces are equal. + if (DstAS == SrcAS) + return; + + // If we don't have a data layout string, return. + if (M->getDataLayout().empty()) return; + + // Don't upgrade if the pointer sizes are equal. + if (M->getPointerSize(DstAS) == + M->getPointerSize(SrcAS)) { + return; + } + // Now that we know we have a bitcast between pointers of different + // sizes, convert into PtrToInt/IntToPtr pair. + LLVMContext &C = BCI->getContext(); + IRBuilder<> Builder(C); + Builder.SetInsertPoint(BCI->getParent(), BCI); + // FIXME: Change to use the address space once the + // the target data changes have gone in. + Value *Rep = Builder.CreatePtrToInt(BCI->getOperand(0), + Type::getIntNTy(C, M->getPointerSize(DstAS))); + Rep = Builder.CreateIntToPtr(Rep, SrcTy); + BCI->replaceAllUsesWith(Rep); + BCI->eraseFromParent(); +} + // UpgradeIntrinsicCall - Upgrade a call to an old intrinsic to be a call the // upgraded intrinsic. All argument and return casting must be provided in // order to seamlessly integrate with existing context. Index: lib/VMCore/Module.cpp =================================================================== --- lib/VMCore/Module.cpp (revision 164831) +++ lib/VMCore/Module.cpp (working copy) @@ -83,7 +83,7 @@ } /// Target Pointer Size information. -Module::PointerSize Module::getPointerSize() const { +Module::PointerSize Module::getPointerSize(unsigned addrSpace) const { StringRef temp = DataLayout; Module::PointerSize ret = AnyPointerSize; @@ -94,6 +94,12 @@ StringRef token = TmpP.second, signalToken = TmpP.first; if (signalToken[0] == 'p') { + if (addrSpace && signalToken.size() > 1) { + unsigned addr; + signalToken.substr(1).getAsInteger(10, addr); + if (addrSpace != addr) continue; + } + int size = 0; getToken(token, ":").first.getAsInteger(10, size); if (size == 32) Index: lib/VMCore/Verifier.cpp =================================================================== --- lib/VMCore/Verifier.cpp (revision 164831) +++ lib/VMCore/Verifier.cpp (working copy) @@ -1102,6 +1102,18 @@ "Bitcast operand must not be aggregate", &I); Assert1(!DestTy->isAggregateType(), "Bitcast type must not be aggregate", &I); + if (DestTy->isPointerTy() && SrcTy->isPointerTy() + && !I.getParent()->getParent()->getParent()->getDataLayout().empty()) { + const Module *M = I.getParent()->getParent()->getParent(); + PointerType *DstPtrTy = dyn_cast (DestTy); + PointerType *SrcPtrTy = dyn_cast (SrcTy); + unsigned DstAS = DstPtrTy->getAddressSpace(); + unsigned SrcAS = SrcPtrTy->getAddressSpace(); + Assert1(M->getPointerSize(DstAS) == + M->getPointerSize(SrcAS), + "Bitcasts between pointers of different address spaces, must have " + "the same size pointers, otherwise use PtrToInt/IntToPtr.", &I); + } visitInstruction(I); }