clang 24.0.0git
ModuleUtils.cpp
Go to the documentation of this file.
1//===--- ModuleUtils.cpp - Shared module emission queries -----------------===//
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-exception
6//
7//===----------------------------------------------------------------------===//
8
10#include "clang/AST/Attr.h"
12
13namespace clang::CodeGenUtils {
14
16 bool NoCommon) {
17 // Don't give variables common linkage if -fno-common was specified unless it
18 // was overridden by a NoCommon attribute.
19 if ((NoCommon || D->hasAttr<NoCommonAttr>()) && !D->hasAttr<CommonAttr>())
20 return true;
21
22 // C11 6.9.2/2:
23 // A declaration of an identifier for an object that has file scope without
24 // an initializer, and without a storage-class specifier or with the
25 // storage-class specifier static, constitutes a tentative definition.
26 if (D->getInit() || D->hasExternalStorage())
27 return true;
28
29 // A variable cannot be both common and exist in a section.
30 if (D->hasAttr<SectionAttr>())
31 return true;
32
33 // A variable cannot be both common and exist in a section.
34 // We don't try to determine which is the right section in the front-end.
35 // If no specialized section name is applicable, it will resort to default.
36 if (D->hasAttr<PragmaClangBSSSectionAttr>() ||
37 D->hasAttr<PragmaClangDataSectionAttr>() ||
38 D->hasAttr<PragmaClangRelroSectionAttr>() ||
39 D->hasAttr<PragmaClangRodataSectionAttr>())
40 return true;
41
42 // Thread local vars aren't considered common linkage.
43 if (D->getTLSKind())
44 return true;
45
46 // Tentative definitions marked with WeakImportAttr are true definitions.
47 if (D->hasAttr<WeakImportAttr>())
48 return true;
49
50 // A variable cannot be both common and exist in a comdat.
51 if (shouldBeInCOMDAT(Ctx, *D))
52 return true;
53
54 // Declarations with a required alignment do not have common linkage in MSVC
55 // mode.
56 if (Ctx.getTargetInfo().getCXXABI().isMicrosoft()) {
57 if (D->hasAttr<AlignedAttr>())
58 return true;
59 QualType VarType = D->getType();
60 if (Ctx.isAlignmentRequired(VarType))
61 return true;
62
63 if (const auto *RD = VarType->getAsRecordDecl()) {
64 for (const FieldDecl *FD : RD->fields()) {
65 if (FD->isBitField())
66 continue;
67 if (FD->hasAttr<AlignedAttr>())
68 return true;
69 if (Ctx.isAlignmentRequired(FD->getType()))
70 return true;
71 }
72 }
73 }
74
75 // Microsoft's link.exe doesn't support alignments greater than 32 bytes for
76 // common symbols, so symbols with greater alignment requirements cannot be
77 // common.
78 // Other COFF linkers (ld.bfd and LLD) support arbitrary power-of-two
79 // alignments for common symbols via the aligncomm directive, so this
80 // restriction only applies to MSVC environments.
81 if (Ctx.getTargetInfo().getTriple().isKnownWindowsMSVCEnvironment() &&
84 return true;
85
86 return false;
87}
88
89bool shouldBeInCOMDAT(const ASTContext &Ctx, const Decl &D) {
90 if (!Ctx.getTargetInfo().getTriple().supportsCOMDAT())
91 return false;
92
93 if (D.hasAttr<SelectAnyAttr>())
94 return true;
95
97 if (auto *VD = dyn_cast<VarDecl>(&D))
99 else
101
102 switch (Linkage) {
103 case GVA_Internal:
106 return false;
108 case GVA_StrongODR:
109 return true;
110 }
111 llvm_unreachable("No such linkage");
112}
113
114} // namespace clang::CodeGenUtils
Holds long-lived AST nodes (such as types and decls) that can be referred to throughout the semantic ...
Definition ASTContext.h:239
GVALinkage GetGVALinkageForFunction(const FunctionDecl *FD) const
bool isAlignmentRequired(const Type *T) const
Determine if the alignment the type has was required using an alignment attribute.
int64_t toBits(CharUnits CharSize) const
Convert a size in characters to a size in bits.
GVALinkage GetGVALinkageForVariable(const VarDecl *VD) const
unsigned getTypeAlignIfKnown(QualType T, bool NeedsPreferredAlignment=false) const
Return the alignment of a type, in bits, or 0 if the type is incomplete and we cannot determine the a...
const TargetInfo & getTargetInfo() const
Definition ASTContext.h:969
static CharUnits fromQuantity(QuantityType Quantity)
Construct a CharUnits quantity from a raw integer type.
Definition CharUnits.h:58
Decl - This represents one declaration (or definition), e.g.
Definition DeclBase.h:86
bool hasAttr() const
Definition DeclBase.h:585
Represents a member of a struct/union/class.
Definition Decl.h:3295
A (possibly-)qualified type.
Definition TypeBase.h:938
bool isMicrosoft() const
Is this ABI an MSVC-compatible ABI?
const llvm::Triple & getTriple() const
Returns the target triple of the primary target.
TargetCXXABI getCXXABI() const
Get the C++ ABI currently in use.
RecordDecl * getAsRecordDecl() const
Retrieves the RecordDecl this type refers to.
Definition Type.h:41
QualType getType() const
Definition Decl.h:724
Represents a variable declaration or definition.
Definition Decl.h:933
TLSKind getTLSKind() const
Definition Decl.cpp:2148
const Expr * getInit() const
Definition Decl.h:1392
bool hasExternalStorage() const
Returns true if a variable has extern or private_extern storage.
Definition Decl.h:1239
Defines the clang::TargetInfo interface.
bool isVarDeclStrongDefinition(const ASTContext &Ctx, const VarDecl *D, bool NoCommon)
Check whether D is a strong definition, and thus must not be given common linkage.
bool shouldBeInCOMDAT(const ASTContext &Ctx, const Decl &D)
Check whether D should be emitted into a COMDAT group.
GVALinkage
A more specific kind of linkage than enum Linkage.
Definition Linkage.h:72
@ GVA_StrongODR
Definition Linkage.h:77
@ GVA_StrongExternal
Definition Linkage.h:76
@ GVA_AvailableExternally
Definition Linkage.h:74
@ GVA_DiscardableODR
Definition Linkage.h:75
@ GVA_Internal
Definition Linkage.h:73
Linkage
Describes the different kinds of linkage (C++ [basic.link], C99 6.2.2) that an entity may have.
Definition Linkage.h:24
U cast(CodeGen::Address addr)
Definition Address.h:327