1 //===-- Address.h - An aligned address -------------------------*- C++ -*-===// 2 // 3 // The LLVM Compiler Infrastructure 4 // 5 // This file is distributed under the University of Illinois Open Source 6 // License. See LICENSE.TXT for details. 7 // 8 //===----------------------------------------------------------------------===// 9 // 10 // This class provides a simple wrapper for a pair of a pointer and an 11 // alignment. 12 // 13 //===----------------------------------------------------------------------===// 14 15 #ifndef LLVM_CLANG_LIB_CODEGEN_ADDRESS_H 16 #define LLVM_CLANG_LIB_CODEGEN_ADDRESS_H 17 18 #include "llvm/IR/Constants.h" 19 #include "clang/AST/CharUnits.h" 20 21 namespace clang { 22 namespace CodeGen { 23 24 /// An aligned address. 25 class Address { 26 llvm::Value *Pointer; 27 CharUnits Alignment; 28 public: 29 Address(llvm::Value *pointer, CharUnits alignment) 30 : Pointer(pointer), Alignment(alignment) { 31 assert((!alignment.isZero() || pointer == nullptr) && 32 "creating valid address with invalid alignment"); 33 } 34 35 static Address invalid() { return Address(nullptr, CharUnits()); } 36 bool isValid() const { return Pointer != nullptr; } 37 38 llvm::Value *getPointer() const { 39 assert(isValid()); 40 return Pointer; 41 } 42 43 /// Return the type of the pointer value. 44 llvm::PointerType *getType() const { 45 return llvm::cast<llvm::PointerType>(getPointer()->getType()); 46 } 47 48 /// Return the type of the values stored in this address. 49 /// 50 /// When IR pointer types lose their element type, we should simply 51 /// store it in Address instead for the convenience of writing code. 52 llvm::Type *getElementType() const { 53 return getType()->getElementType(); 54 } 55 56 /// Return the address space that this address resides in. 57 unsigned getAddressSpace() const { 58 return getType()->getAddressSpace(); 59 } 60 61 /// Return the IR name of the pointer value. 62 llvm::StringRef getName() const { 63 return getPointer()->getName(); 64 } 65 66 /// Return the alignment of this pointer. 67 CharUnits getAlignment() const { 68 assert(isValid()); 69 return Alignment; 70 } 71 }; 72 73 /// A specialization of Address that requires the address to be an 74 /// LLVM Constant. 75 class ConstantAddress : public Address { 76 public: 77 ConstantAddress(llvm::Constant *pointer, CharUnits alignment) 78 : Address(pointer, alignment) {} 79 80 static ConstantAddress invalid() { 81 return ConstantAddress(nullptr, CharUnits()); 82 } 83 84 llvm::Constant *getPointer() const { 85 return llvm::cast<llvm::Constant>(Address::getPointer()); 86 } 87 88 ConstantAddress getBitCast(llvm::Type *ty) const { 89 return ConstantAddress(llvm::ConstantExpr::getBitCast(getPointer(), ty), 90 getAlignment()); 91 } 92 93 ConstantAddress getElementBitCast(llvm::Type *ty) const { 94 return getBitCast(ty->getPointerTo(getAddressSpace())); 95 } 96 97 static bool isaImpl(Address addr) { 98 return llvm::isa<llvm::Constant>(addr.getPointer()); 99 } 100 static ConstantAddress castImpl(Address addr) { 101 return ConstantAddress(llvm::cast<llvm::Constant>(addr.getPointer()), 102 addr.getAlignment()); 103 } 104 }; 105 106 } 107 108 // Present a minimal LLVM-like casting interface. 109 template <class U> inline U cast(CodeGen::Address addr) { 110 return U::castImpl(addr); 111 } 112 template <class U> inline bool isa(CodeGen::Address addr) { 113 return U::isaImpl(addr); 114 } 115 116 } 117 118 #endif 119