diff options
| author | Ralf Luther <luther.ralf@gmail.com> | 2019-03-27 20:23:17 +0000 |
|---|---|---|
| committer | Gerrit Code Review <gerrit2@aicp-server-3> | 2019-03-27 20:23:17 +0000 |
| commit | 1ce3a9d272e564b22a1333a1e36a3d3ab7cfab01 (patch) | |
| tree | 391382eadd4fec5bb480f2e8934fa352770221d1 /clang-r353983/include/clang/Basic/Visibility.h | |
| parent | d1d48b140bafaa8a50107292f5fce95562575765 (diff) | |
| parent | 4f56932d3416ac03f646bc1a611b3135fec2fe08 (diff) | |
Merge "Update prebuilt Clang to r353983." into p9.0HEADp9.0-backupp9.0
Diffstat (limited to 'clang-r353983/include/clang/Basic/Visibility.h')
| -rw-r--r-- | clang-r353983/include/clang/Basic/Visibility.h | 145 |
1 files changed, 145 insertions, 0 deletions
diff --git a/clang-r353983/include/clang/Basic/Visibility.h b/clang-r353983/include/clang/Basic/Visibility.h new file mode 100644 index 00000000..57d9754a --- /dev/null +++ b/clang-r353983/include/clang/Basic/Visibility.h @@ -0,0 +1,145 @@ +//===--- Visibility.h - Visibility enumeration and utilities ----*- C++ -*-===// +// +// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions. +// See https://llvm.org/LICENSE.txt for license information. +// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception +// +//===----------------------------------------------------------------------===// +/// +/// \file +/// Defines the clang::Visibility enumeration and various utility +/// functions. +/// +//===----------------------------------------------------------------------===// +#ifndef LLVM_CLANG_BASIC_VISIBILITY_H +#define LLVM_CLANG_BASIC_VISIBILITY_H + +#include "clang/Basic/Linkage.h" +#include <cassert> +#include <cstdint> + +namespace clang { + +/// Describes the different kinds of visibility that a declaration +/// may have. +/// +/// Visibility determines how a declaration interacts with the dynamic +/// linker. It may also affect whether the symbol can be found by runtime +/// symbol lookup APIs. +/// +/// Visibility is not described in any language standard and +/// (nonetheless) sometimes has odd behavior. Not all platforms +/// support all visibility kinds. +enum Visibility { + /// Objects with "hidden" visibility are not seen by the dynamic + /// linker. + HiddenVisibility, + + /// Objects with "protected" visibility are seen by the dynamic + /// linker but always dynamically resolve to an object within this + /// shared object. + ProtectedVisibility, + + /// Objects with "default" visibility are seen by the dynamic linker + /// and act like normal objects. + DefaultVisibility +}; + +inline Visibility minVisibility(Visibility L, Visibility R) { + return L < R ? L : R; +} + +class LinkageInfo { + uint8_t linkage_ : 3; + uint8_t visibility_ : 2; + uint8_t explicit_ : 1; + + void setVisibility(Visibility V, bool E) { visibility_ = V; explicit_ = E; } +public: + LinkageInfo() : linkage_(ExternalLinkage), visibility_(DefaultVisibility), + explicit_(false) {} + LinkageInfo(Linkage L, Visibility V, bool E) + : linkage_(L), visibility_(V), explicit_(E) { + assert(getLinkage() == L && getVisibility() == V && + isVisibilityExplicit() == E && "Enum truncated!"); + } + + static LinkageInfo external() { + return LinkageInfo(); + } + static LinkageInfo internal() { + return LinkageInfo(InternalLinkage, DefaultVisibility, false); + } + static LinkageInfo uniqueExternal() { + return LinkageInfo(UniqueExternalLinkage, DefaultVisibility, false); + } + static LinkageInfo none() { + return LinkageInfo(NoLinkage, DefaultVisibility, false); + } + static LinkageInfo visible_none() { + return LinkageInfo(VisibleNoLinkage, DefaultVisibility, false); + } + + Linkage getLinkage() const { return (Linkage)linkage_; } + Visibility getVisibility() const { return (Visibility)visibility_; } + bool isVisibilityExplicit() const { return explicit_; } + + void setLinkage(Linkage L) { linkage_ = L; } + + void mergeLinkage(Linkage L) { + setLinkage(minLinkage(getLinkage(), L)); + } + void mergeLinkage(LinkageInfo other) { + mergeLinkage(other.getLinkage()); + } + + void mergeExternalVisibility(Linkage L) { + Linkage ThisL = getLinkage(); + if (!isExternallyVisible(L)) { + if (ThisL == VisibleNoLinkage) + ThisL = NoLinkage; + else if (ThisL == ExternalLinkage) + ThisL = UniqueExternalLinkage; + } + setLinkage(ThisL); + } + void mergeExternalVisibility(LinkageInfo Other) { + mergeExternalVisibility(Other.getLinkage()); + } + + /// Merge in the visibility 'newVis'. + void mergeVisibility(Visibility newVis, bool newExplicit) { + Visibility oldVis = getVisibility(); + + // Never increase visibility. + if (oldVis < newVis) + return; + + // If the new visibility is the same as the old and the new + // visibility isn't explicit, we have nothing to add. + if (oldVis == newVis && !newExplicit) + return; + + // Otherwise, we're either decreasing visibility or making our + // existing visibility explicit. + setVisibility(newVis, newExplicit); + } + void mergeVisibility(LinkageInfo other) { + mergeVisibility(other.getVisibility(), other.isVisibilityExplicit()); + } + + /// Merge both linkage and visibility. + void merge(LinkageInfo other) { + mergeLinkage(other); + mergeVisibility(other); + } + + /// Merge linkage and conditionally merge visibility. + void mergeMaybeWithVisibility(LinkageInfo other, bool withVis) { + mergeLinkage(other); + if (withVis) mergeVisibility(other); + } +}; +} + +#endif // LLVM_CLANG_BASIC_VISIBILITY_H |
