Audit of every #include directive in flang/lib/ and flang/include/flang/: - Remove 423 #include directives (293 from lib/ translation units, 23 from lib-private headers, 107 from public headers) that are not needed: no entity declared by the removed header is used - directly or in any conditional-compilation branch (Windows, macOS, ARM/PowerPC, REAL(16)/REAL(2) configuration macros) - in the including file, and for headers no consumer in flang/lib, flang/tools, flang/unittests, or flang-rt relies on the include as a re-export. Load-bearing includes were examined and retained: textual .inc/.def expansions, tablegen pass-header declaration/definition pairings, dialect headers carrying generated-op interface dependencies, config-macro providers (e.g. float128.h ahead of matmul-instances.inc guards), and ADL formatting machinery (Evaluate/formatting.h). - Add 5 missing direct #includes in lib translation units that used entities only via now-removed transitive includes, and drop one vestigial 'using namespace Fortran::runtime;' whose declaring header no longer arrives transitively (nothing namespace-qualified from it was used), per the include rules in flang/docs/C++style.md. Assisted-by: AI
212 lines
9.4 KiB
C++
212 lines
9.4 KiB
C++
//===-- Optimizer/Support/InternalNames.h -----------------------*- 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
|
|
//
|
|
//===----------------------------------------------------------------------===//
|
|
|
|
#ifndef FORTRAN_OPTIMIZER_SUPPORT_INTERNALNAMES_H
|
|
#define FORTRAN_OPTIMIZER_SUPPORT_INTERNALNAMES_H
|
|
|
|
#include "llvm/ADT/ArrayRef.h"
|
|
#include "llvm/ADT/StringRef.h"
|
|
#include <cstdint>
|
|
|
|
namespace fir {
|
|
|
|
static constexpr llvm::StringRef kNameSeparator = ".";
|
|
static constexpr llvm::StringRef kBoundsSeparator = ".b.";
|
|
static constexpr llvm::StringRef kComponentSeparator = ".c.";
|
|
static constexpr llvm::StringRef kComponentInitSeparator = ".di.";
|
|
static constexpr llvm::StringRef kDataPtrInitSeparator = ".dp.";
|
|
static constexpr llvm::StringRef kTypeDescriptorSeparator = ".dt.";
|
|
static constexpr llvm::StringRef kKindParameterSeparator = ".kp.";
|
|
static constexpr llvm::StringRef kLenKindSeparator = ".lpk.";
|
|
static constexpr llvm::StringRef kLenParameterSeparator = ".lv.";
|
|
static constexpr llvm::StringRef kNameStringSeparator = ".n.";
|
|
static constexpr llvm::StringRef kProcPtrSeparator = ".p.";
|
|
static constexpr llvm::StringRef kSpecialBindingSeparator = ".s.";
|
|
static constexpr llvm::StringRef kBindingTableSeparator = ".v.";
|
|
static constexpr llvm::StringRef boxprocSuffix = "UnboxProc";
|
|
static constexpr llvm::StringRef kDerivedTypeInitSuffix = "DerivedInit";
|
|
|
|
/// Internal name mangling of identifiers
|
|
///
|
|
/// In order to generate symbolically referencable artifacts in a ModuleOp,
|
|
/// it is required that those symbols be uniqued. This is a simple interface
|
|
/// for converting Fortran symbols into unique names.
|
|
///
|
|
/// This is intentionally bijective. Given a symbol's parse name, type, and
|
|
/// scope-like information, we can generate a uniqued (mangled) name. Given a
|
|
/// uniqued name, we can return the symbol parse name, type of the symbol, and
|
|
/// any scope-like information for that symbol.
|
|
struct NameUniquer {
|
|
enum class IntrinsicType { CHARACTER, COMPLEX, INTEGER, LOGICAL, REAL };
|
|
|
|
/// The sort of the unique name
|
|
enum class NameKind {
|
|
NOT_UNIQUED,
|
|
BLOCK_DATA_NAME,
|
|
COMMON,
|
|
CONSTANT,
|
|
DERIVED_TYPE,
|
|
DISPATCH_TABLE,
|
|
GENERATED,
|
|
INTRINSIC_TYPE_DESC,
|
|
NAMELIST_GROUP,
|
|
PROCEDURE,
|
|
TYPE_DESC,
|
|
VARIABLE
|
|
};
|
|
|
|
/// Components of an unparsed unique name
|
|
struct DeconstructedName {
|
|
DeconstructedName(llvm::StringRef name) : name{name} {}
|
|
DeconstructedName(llvm::ArrayRef<std::string> modules,
|
|
llvm::ArrayRef<std::string> procs, std::int64_t blockId,
|
|
llvm::StringRef name, llvm::ArrayRef<std::int64_t> kinds)
|
|
: modules{modules}, procs{procs}, blockId{blockId}, name{name},
|
|
kinds{kinds} {}
|
|
|
|
llvm::SmallVector<std::string> modules;
|
|
llvm::SmallVector<std::string> procs;
|
|
std::int64_t blockId;
|
|
std::string name;
|
|
llvm::SmallVector<std::int64_t> kinds;
|
|
};
|
|
|
|
/// Unique a common block name
|
|
static std::string doCommonBlock(llvm::StringRef name);
|
|
|
|
/// Unique a (global) constant name
|
|
static std::string doConstant(llvm::ArrayRef<llvm::StringRef> modules,
|
|
llvm::ArrayRef<llvm::StringRef> procs,
|
|
std::int64_t block, llvm::StringRef name);
|
|
|
|
/// Unique a dispatch table name
|
|
static std::string doDispatchTable(llvm::ArrayRef<llvm::StringRef> modules,
|
|
llvm::ArrayRef<llvm::StringRef> procs,
|
|
std::int64_t block, llvm::StringRef name,
|
|
llvm::ArrayRef<std::int64_t> kinds);
|
|
|
|
/// Unique a compiler generated name without scope context.
|
|
static std::string doGenerated(llvm::StringRef name);
|
|
/// Unique a compiler generated name with scope context.
|
|
static std::string doGenerated(llvm::ArrayRef<llvm::StringRef> modules,
|
|
llvm::ArrayRef<llvm::StringRef> procs,
|
|
std::int64_t blockId, llvm::StringRef name);
|
|
|
|
/// Unique an intrinsic type descriptor
|
|
static std::string
|
|
doIntrinsicTypeDescriptor(llvm::ArrayRef<llvm::StringRef> modules,
|
|
llvm::ArrayRef<llvm::StringRef> procs,
|
|
std::int64_t block, IntrinsicType type,
|
|
std::int64_t kind);
|
|
|
|
/// Unique a procedure name
|
|
static std::string doProcedure(llvm::ArrayRef<llvm::StringRef> modules,
|
|
llvm::ArrayRef<llvm::StringRef> procs,
|
|
llvm::StringRef name);
|
|
|
|
/// Unique a derived type name
|
|
static std::string doType(llvm::ArrayRef<llvm::StringRef> modules,
|
|
llvm::ArrayRef<llvm::StringRef> procs,
|
|
std::int64_t block, llvm::StringRef name,
|
|
llvm::ArrayRef<std::int64_t> kinds);
|
|
|
|
/// Unique a (derived) type descriptor name
|
|
static std::string doTypeDescriptor(llvm::ArrayRef<llvm::StringRef> modules,
|
|
llvm::ArrayRef<llvm::StringRef> procs,
|
|
std::int64_t block, llvm::StringRef name,
|
|
llvm::ArrayRef<std::int64_t> kinds);
|
|
static std::string doTypeDescriptor(llvm::ArrayRef<std::string> modules,
|
|
llvm::ArrayRef<std::string> procs,
|
|
std::int64_t block, llvm::StringRef name,
|
|
llvm::ArrayRef<std::int64_t> kinds);
|
|
|
|
/// Unique a (global) variable name. A variable with save attribute
|
|
/// defined inside a subprogram also needs to be handled here
|
|
static std::string doVariable(llvm::ArrayRef<llvm::StringRef> modules,
|
|
llvm::ArrayRef<llvm::StringRef> procs,
|
|
std::int64_t block, llvm::StringRef name);
|
|
|
|
/// Unique a namelist group name
|
|
static std::string doNamelistGroup(llvm::ArrayRef<llvm::StringRef> modules,
|
|
llvm::ArrayRef<llvm::StringRef> procs,
|
|
llvm::StringRef name);
|
|
|
|
/// Entry point for the PROGRAM (called by the runtime)
|
|
/// Can be overridden with the `--main-entry-name=<name>` option.
|
|
static llvm::StringRef doProgramEntry();
|
|
|
|
/// Decompose `uniquedName` into the parse name, symbol type, and scope info
|
|
static std::pair<NameKind, DeconstructedName>
|
|
deconstruct(llvm::StringRef uniquedName);
|
|
|
|
/// Check if the name is an external facing name.
|
|
static bool isExternalFacingUniquedName(
|
|
const std::pair<NameKind, DeconstructedName> &deconstructResult);
|
|
|
|
/// Check whether the name should be re-mangle with external ABI convention.
|
|
static bool needExternalNameMangling(llvm::StringRef uniquedName);
|
|
|
|
/// Does \p uniquedName belong to module \p moduleName?
|
|
static bool belongsToModule(llvm::StringRef uniquedName,
|
|
llvm::StringRef moduleName);
|
|
|
|
/// True if \p uniquedName denotes module-scope data (variable, named
|
|
/// constant, or common block), as opposed to procedures, types, or other
|
|
/// symbols that may still carry a module prefix in the mangling. This
|
|
/// excludes symbols nested in a procedure according to the mangled prefix
|
|
/// (including \c SAVE locals in module procedures).
|
|
static bool isModuleScopeDataUniquedName(llvm::StringRef uniquedName);
|
|
|
|
/// Given a mangled derived type name, get the name of the related derived
|
|
/// type descriptor object. Returns an empty string if \p mangledTypeName is
|
|
/// not a valid mangled derived type name.
|
|
static std::string getTypeDescriptorName(llvm::StringRef mangledTypeName);
|
|
|
|
static std::string
|
|
getTypeDescriptorAssemblyName(llvm::StringRef mangledTypeName);
|
|
|
|
/// Given a mangled derived type name, get the name of the related binding
|
|
/// table object. Returns an empty string if \p mangledTypeName is not a valid
|
|
/// mangled derived type name.
|
|
static std::string
|
|
getTypeDescriptorBindingTableName(llvm::StringRef mangledTypeName);
|
|
|
|
/// Given a mangled derived type name and a component name, get the name of
|
|
/// the global object containing the component default initialization.
|
|
static std::string getComponentInitName(llvm::StringRef mangledTypeName,
|
|
llvm::StringRef componentName);
|
|
|
|
/// Remove markers that have been added when doing partial type
|
|
/// conversions. mlir::Type cannot be mutated in a pass, so new
|
|
/// fir::RecordType must be created when lowering member types.
|
|
/// Suffixes added to these new types are meaningless and are
|
|
/// dropped in the names passed to LLVM.
|
|
static llvm::StringRef
|
|
dropTypeConversionMarkers(llvm::StringRef mangledTypeName);
|
|
|
|
static std::string replaceSpecialSymbols(const std::string &name);
|
|
|
|
/// Returns true if the passed name denotes a special symbol (e.g. global
|
|
/// symbol generated for derived type description).
|
|
static bool isSpecialSymbol(llvm::StringRef name);
|
|
|
|
private:
|
|
static std::string intAsString(std::int64_t i);
|
|
static std::string doKind(std::int64_t kind);
|
|
static std::string doKinds(llvm::ArrayRef<std::int64_t> kinds);
|
|
static std::string toLower(llvm::StringRef name);
|
|
|
|
NameUniquer() = delete;
|
|
NameUniquer(const NameUniquer &) = delete;
|
|
NameUniquer(NameUniquer &&) = delete;
|
|
NameUniquer &operator=(const NameUniquer &) = delete;
|
|
};
|
|
|
|
} // namespace fir
|
|
|
|
#endif // FORTRAN_OPTIMIZER_SUPPORT_INTERNALNAMES_H
|