269 lines · c
1//===--- CodeGenTBAA.h - TBAA information for LLVM CodeGen ------*- C++ -*-===//2//3// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.4// See https://llvm.org/LICENSE.txt for license information.5// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception6//7//===----------------------------------------------------------------------===//8//9// This is the code that manages TBAA information and defines the TBAA policy10// for the optimizer to use.11//12//===----------------------------------------------------------------------===//13 14#ifndef LLVM_CLANG_LIB_CODEGEN_CODEGENTBAA_H15#define LLVM_CLANG_LIB_CODEGEN_CODEGENTBAA_H16 17#include "clang/AST/Type.h"18#include "clang/Basic/LLVM.h"19#include "llvm/ADT/DenseMap.h"20#include "llvm/IR/MDBuilder.h"21#include "llvm/IR/Metadata.h"22 23namespace clang {24 class ASTContext;25 class CodeGenOptions;26 class LangOptions;27 class MangleContext;28 class QualType;29 class Type;30 31namespace CodeGen {32class CodeGenTypes;33 34// TBAAAccessKind - A kind of TBAA memory access descriptor.35enum class TBAAAccessKind : unsigned {36 Ordinary,37 MayAlias,38 Incomplete,39};40 41// TBAAAccessInfo - Describes a memory access in terms of TBAA.42struct TBAAAccessInfo {43 TBAAAccessInfo(TBAAAccessKind Kind, llvm::MDNode *BaseType,44 llvm::MDNode *AccessType, uint64_t Offset, uint64_t Size)45 : Kind(Kind), BaseType(BaseType), AccessType(AccessType),46 Offset(Offset), Size(Size)47 {}48 49 TBAAAccessInfo(llvm::MDNode *BaseType, llvm::MDNode *AccessType,50 uint64_t Offset, uint64_t Size)51 : TBAAAccessInfo(TBAAAccessKind::Ordinary, BaseType, AccessType,52 Offset, Size)53 {}54 55 explicit TBAAAccessInfo(llvm::MDNode *AccessType, uint64_t Size)56 : TBAAAccessInfo(/* BaseType= */ nullptr, AccessType, /* Offset= */ 0, Size)57 {}58 59 TBAAAccessInfo()60 : TBAAAccessInfo(/* AccessType= */ nullptr, /* Size= */ 0)61 {}62 63 static TBAAAccessInfo getMayAliasInfo() {64 return TBAAAccessInfo(TBAAAccessKind::MayAlias,65 /* BaseType= */ nullptr, /* AccessType= */ nullptr,66 /* Offset= */ 0, /* Size= */ 0);67 }68 69 bool isMayAlias() const { return Kind == TBAAAccessKind::MayAlias; }70 71 static TBAAAccessInfo getIncompleteInfo() {72 return TBAAAccessInfo(TBAAAccessKind::Incomplete,73 /* BaseType= */ nullptr, /* AccessType= */ nullptr,74 /* Offset= */ 0, /* Size= */ 0);75 }76 77 bool isIncomplete() const { return Kind == TBAAAccessKind::Incomplete; }78 79 bool operator==(const TBAAAccessInfo &Other) const {80 return Kind == Other.Kind &&81 BaseType == Other.BaseType &&82 AccessType == Other.AccessType &&83 Offset == Other.Offset &&84 Size == Other.Size;85 }86 87 bool operator!=(const TBAAAccessInfo &Other) const {88 return !(*this == Other);89 }90 91 explicit operator bool() const {92 return *this != TBAAAccessInfo();93 }94 95 /// Kind - The kind of the access descriptor.96 TBAAAccessKind Kind;97 98 /// BaseType - The base/leading access type. May be null if this access99 /// descriptor represents an access that is not considered to be an access100 /// to an aggregate or union member.101 llvm::MDNode *BaseType;102 103 /// AccessType - The final access type. May be null if there is no TBAA104 /// information available about this access.105 llvm::MDNode *AccessType;106 107 /// Offset - The byte offset of the final access within the base one. Must be108 /// zero if the base access type is not specified.109 uint64_t Offset;110 111 /// Size - The size of access, in bytes.112 uint64_t Size;113};114 115/// CodeGenTBAA - This class organizes the cross-module state that is used116/// while lowering AST types to LLVM types.117class CodeGenTBAA {118 ASTContext &Context;119 CodeGenTypes &CGTypes;120 llvm::Module &Module;121 const CodeGenOptions &CodeGenOpts;122 const LangOptions &Features;123 std::unique_ptr<MangleContext> MangleCtx;124 125 // MDHelper - Helper for creating metadata.126 llvm::MDBuilder MDHelper;127 128 /// MetadataCache - This maps clang::Types to scalar llvm::MDNodes describing129 /// them.130 llvm::DenseMap<const Type *, llvm::MDNode *> MetadataCache;131 /// This maps clang::Types to a base access type in the type DAG.132 llvm::DenseMap<const Type *, llvm::MDNode *> BaseTypeMetadataCache;133 /// This maps TBAA access descriptors to tag nodes.134 llvm::DenseMap<TBAAAccessInfo, llvm::MDNode *> AccessTagMetadataCache;135 136 /// StructMetadataCache - This maps clang::Types to llvm::MDNodes describing137 /// them for struct assignments.138 llvm::DenseMap<const Type *, llvm::MDNode *> StructMetadataCache;139 140 llvm::MDNode *Root;141 llvm::MDNode *Char;142 llvm::SmallVector<llvm::MDNode *, 4> AnyPtrs;143 144 /// getRoot - This is the mdnode for the root of the metadata type graph145 /// for this translation unit.146 llvm::MDNode *getRoot();147 148 /// getChar - This is the mdnode for "char", which is special, and any types149 /// considered to be equivalent to it.150 llvm::MDNode *getChar();151 152 /// getAnyPtr - This is the mdnode for any pointer type of (at least) the153 /// given pointer depth.154 llvm::MDNode *getAnyPtr(unsigned PtrDepth = 1);155 156 /// CollectFields - Collect information about the fields of a type for157 /// !tbaa.struct metadata formation. Return false for an unsupported type.158 bool CollectFields(uint64_t BaseOffset,159 QualType Ty,160 SmallVectorImpl<llvm::MDBuilder::TBAAStructField> &Fields,161 bool MayAlias);162 163 /// createScalarTypeNode - A wrapper function to create a metadata node164 /// describing a scalar type.165 llvm::MDNode *createScalarTypeNode(StringRef Name, llvm::MDNode *Parent,166 uint64_t Size);167 168 /// getTypeInfoHelper - An internal helper function to generate metadata used169 /// to describe accesses to objects of the given type.170 llvm::MDNode *getTypeInfoHelper(const Type *Ty);171 172 /// getBaseTypeInfoHelper - An internal helper function to generate metadata173 /// used to describe accesses to objects of the given base type.174 llvm::MDNode *getBaseTypeInfoHelper(const Type *Ty);175 176 /// getValidBaseTypeInfo - Return metadata that describes the given base177 /// access type. The type must be suitable.178 llvm::MDNode *getValidBaseTypeInfo(QualType QTy);179 180public:181 CodeGenTBAA(ASTContext &Ctx, CodeGenTypes &CGTypes, llvm::Module &M,182 const CodeGenOptions &CGO, const LangOptions &Features);183 ~CodeGenTBAA();184 185 /// getTypeInfo - Get metadata used to describe accesses to objects of the186 /// given type.187 llvm::MDNode *getTypeInfo(QualType QTy);188 189 /// getAccessInfo - Get TBAA information that describes an access to190 /// an object of the given type.191 TBAAAccessInfo getAccessInfo(QualType AccessType);192 193 /// getVTablePtrAccessInfo - Get the TBAA information that describes an194 /// access to a virtual table pointer.195 TBAAAccessInfo getVTablePtrAccessInfo(llvm::Type *VTablePtrType);196 197 /// getTBAAStructInfo - Get the TBAAStruct MDNode to be used for a memcpy of198 /// the given type.199 llvm::MDNode *getTBAAStructInfo(QualType QTy);200 201 /// getBaseTypeInfo - Get metadata that describes the given base access202 /// type. Return null if the type is not suitable for use in TBAA access203 /// tags.204 llvm::MDNode *getBaseTypeInfo(QualType QTy);205 206 /// getAccessTagInfo - Get TBAA tag for a given memory access.207 llvm::MDNode *getAccessTagInfo(TBAAAccessInfo Info);208 209 /// mergeTBAAInfoForCast - Get merged TBAA information for the purpose of210 /// type casts.211 TBAAAccessInfo mergeTBAAInfoForCast(TBAAAccessInfo SourceInfo,212 TBAAAccessInfo TargetInfo);213 214 /// mergeTBAAInfoForConditionalOperator - Get merged TBAA information for the215 /// purpose of conditional operator.216 TBAAAccessInfo mergeTBAAInfoForConditionalOperator(TBAAAccessInfo InfoA,217 TBAAAccessInfo InfoB);218 219 /// mergeTBAAInfoForMemoryTransfer - Get merged TBAA information for the220 /// purpose of memory transfer calls.221 TBAAAccessInfo mergeTBAAInfoForMemoryTransfer(TBAAAccessInfo DestInfo,222 TBAAAccessInfo SrcInfo);223};224 225} // end namespace CodeGen226} // end namespace clang227 228namespace llvm {229 230template<> struct DenseMapInfo<clang::CodeGen::TBAAAccessInfo> {231 static clang::CodeGen::TBAAAccessInfo getEmptyKey() {232 unsigned UnsignedKey = DenseMapInfo<unsigned>::getEmptyKey();233 return clang::CodeGen::TBAAAccessInfo(234 static_cast<clang::CodeGen::TBAAAccessKind>(UnsignedKey),235 DenseMapInfo<MDNode *>::getEmptyKey(),236 DenseMapInfo<MDNode *>::getEmptyKey(),237 DenseMapInfo<uint64_t>::getEmptyKey(),238 DenseMapInfo<uint64_t>::getEmptyKey());239 }240 241 static clang::CodeGen::TBAAAccessInfo getTombstoneKey() {242 unsigned UnsignedKey = DenseMapInfo<unsigned>::getTombstoneKey();243 return clang::CodeGen::TBAAAccessInfo(244 static_cast<clang::CodeGen::TBAAAccessKind>(UnsignedKey),245 DenseMapInfo<MDNode *>::getTombstoneKey(),246 DenseMapInfo<MDNode *>::getTombstoneKey(),247 DenseMapInfo<uint64_t>::getTombstoneKey(),248 DenseMapInfo<uint64_t>::getTombstoneKey());249 }250 251 static unsigned getHashValue(const clang::CodeGen::TBAAAccessInfo &Val) {252 auto KindValue = static_cast<unsigned>(Val.Kind);253 return DenseMapInfo<unsigned>::getHashValue(KindValue) ^254 DenseMapInfo<MDNode *>::getHashValue(Val.BaseType) ^255 DenseMapInfo<MDNode *>::getHashValue(Val.AccessType) ^256 DenseMapInfo<uint64_t>::getHashValue(Val.Offset) ^257 DenseMapInfo<uint64_t>::getHashValue(Val.Size);258 }259 260 static bool isEqual(const clang::CodeGen::TBAAAccessInfo &LHS,261 const clang::CodeGen::TBAAAccessInfo &RHS) {262 return LHS == RHS;263 }264};265 266} // end namespace llvm267 268#endif269