LLVM 20.0.0git
|
#include "llvm/Transforms/IPO/WholeProgramDevirt.h"
#include "llvm/ADT/ArrayRef.h"
#include "llvm/ADT/DenseMap.h"
#include "llvm/ADT/DenseMapInfo.h"
#include "llvm/ADT/DenseSet.h"
#include "llvm/ADT/MapVector.h"
#include "llvm/ADT/SmallVector.h"
#include "llvm/ADT/Statistic.h"
#include "llvm/Analysis/AssumptionCache.h"
#include "llvm/Analysis/BasicAliasAnalysis.h"
#include "llvm/Analysis/OptimizationRemarkEmitter.h"
#include "llvm/Analysis/TypeMetadataUtils.h"
#include "llvm/Bitcode/BitcodeReader.h"
#include "llvm/Bitcode/BitcodeWriter.h"
#include "llvm/IR/Constants.h"
#include "llvm/IR/DataLayout.h"
#include "llvm/IR/DebugLoc.h"
#include "llvm/IR/DerivedTypes.h"
#include "llvm/IR/Dominators.h"
#include "llvm/IR/Function.h"
#include "llvm/IR/GlobalAlias.h"
#include "llvm/IR/GlobalVariable.h"
#include "llvm/IR/IRBuilder.h"
#include "llvm/IR/InstrTypes.h"
#include "llvm/IR/Instruction.h"
#include "llvm/IR/Instructions.h"
#include "llvm/IR/Intrinsics.h"
#include "llvm/IR/LLVMContext.h"
#include "llvm/IR/MDBuilder.h"
#include "llvm/IR/Metadata.h"
#include "llvm/IR/Module.h"
#include "llvm/IR/ModuleSummaryIndexYAML.h"
#include "llvm/Support/Casting.h"
#include "llvm/Support/CommandLine.h"
#include "llvm/Support/Errc.h"
#include "llvm/Support/Error.h"
#include "llvm/Support/FileSystem.h"
#include "llvm/Support/GlobPattern.h"
#include "llvm/TargetParser/Triple.h"
#include "llvm/Transforms/IPO.h"
#include "llvm/Transforms/IPO/FunctionAttrs.h"
#include "llvm/Transforms/Utils/BasicBlockUtils.h"
#include "llvm/Transforms/Utils/CallPromotionUtils.h"
#include "llvm/Transforms/Utils/Evaluator.h"
#include <algorithm>
#include <cstddef>
#include <map>
#include <set>
#include <string>
Go to the source code of this file.
Classes | |
struct | llvm::DenseMapInfo< VTableSlot > |
struct | llvm::DenseMapInfo< VTableSlotSummary > |
Namespaces | |
namespace | llvm |
This is an optimization pass for GlobalISel generic memory operations. | |
Macros | |
#define | DEBUG_TYPE "wholeprogramdevirt" |
Enumerations | |
enum | WPDCheckMode { None , Trap , Fallback } |
Mechanism to add runtime checking of devirtualization decisions, optionally trapping or falling back to indirect call on any that are not correct. More... | |
Functions | |
STATISTIC (NumDevirtTargets, "Number of whole program devirtualization targets") | |
STATISTIC (NumSingleImpl, "Number of single implementation devirtualizations") | |
STATISTIC (NumBranchFunnel, "Number of branch funnels") | |
STATISTIC (NumUniformRetVal, "Number of uniform return value optimizations") | |
STATISTIC (NumUniqueRetVal, "Number of unique return value optimizations") | |
STATISTIC (NumVirtConstProp1Bit, "Number of 1 bit virtual constant propagations") | |
STATISTIC (NumVirtConstProp, "Number of virtual constant propagations") | |
static bool | mustBeUnreachableFunction (ValueInfo TheFnVI) |
static bool | typeIDVisibleToRegularObj (StringRef TypeID, function_ref< bool(StringRef)> IsVisibleToRegularObj) |
static bool | skipUpdateDueToValidation (GlobalVariable &GV, function_ref< bool(StringRef)> IsVisibleToRegularObj) |
static Error | checkCombinedSummaryForTesting (ModuleSummaryIndex *Summary) |
static bool | AddCalls (VTableSlotInfo &SlotInfo, const ValueInfo &Callee) |
Variables | |
static cl::opt< PassSummaryAction > | ClSummaryAction ("wholeprogramdevirt-summary-action", cl::desc("What to do with the summary when running this pass"), cl::values(clEnumValN(PassSummaryAction::None, "none", "Do nothing"), clEnumValN(PassSummaryAction::Import, "import", "Import typeid resolutions from summary and globals"), clEnumValN(PassSummaryAction::Export, "export", "Export typeid resolutions to summary and globals")), cl::Hidden) |
static cl::opt< std::string > | ClReadSummary ("wholeprogramdevirt-read-summary", cl::desc("Read summary from given bitcode or YAML file before running pass"), cl::Hidden) |
static cl::opt< std::string > | ClWriteSummary ("wholeprogramdevirt-write-summary", cl::desc("Write summary to given bitcode or YAML file after running pass. " "Output file format is deduced from extension: *.bc means writing " "bitcode, otherwise YAML"), cl::Hidden) |
static cl::opt< unsigned > | ClThreshold ("wholeprogramdevirt-branch-funnel-threshold", cl::Hidden, cl::init(10), cl::desc("Maximum number of call targets per " "call site to enable branch funnels")) |
static cl::opt< bool > | PrintSummaryDevirt ("wholeprogramdevirt-print-index-based", cl::Hidden, cl::desc("Print index-based devirtualization messages")) |
static cl::opt< bool > | WholeProgramVisibility ("whole-program-visibility", cl::Hidden, cl::desc("Enable whole program visibility")) |
Provide a way to force enable whole program visibility in tests. | |
static cl::opt< bool > | DisableWholeProgramVisibility ("disable-whole-program-visibility", cl::Hidden, cl::desc("Disable whole program visibility (overrides enabling options)")) |
Provide a way to force disable whole program for debugging or workarounds, when enabled via the linker. | |
static cl::list< std::string > | SkipFunctionNames ("wholeprogramdevirt-skip", cl::desc("Prevent function(s) from being devirtualized"), cl::Hidden, cl::CommaSeparated) |
Provide way to prevent certain function from being devirtualized. | |
static cl::opt< bool > | WholeProgramDevirtKeepUnreachableFunction ("wholeprogramdevirt-keep-unreachable-function", cl::desc("Regard unreachable functions as possible devirtualize targets."), cl::Hidden, cl::init(true)) |
With Clang, a pure virtual class's deleting destructor is emitted as a llvm.trap intrinsic followed by an unreachable IR instruction. | |
static cl::opt< unsigned > | WholeProgramDevirtCutoff ("wholeprogramdevirt-cutoff", cl::desc("Max number of devirtualizations for devirt module pass"), cl::init(0)) |
If explicitly specified, the devirt module pass will stop transformation once the total number of devirtualizations reach the cutoff value. | |
static cl::opt< WPDCheckMode > | DevirtCheckMode ("wholeprogramdevirt-check", cl::Hidden, cl::desc("Type of checking for incorrect devirtualizations"), cl::values(clEnumValN(WPDCheckMode::None, "none", "No checking"), clEnumValN(WPDCheckMode::Trap, "trap", "Trap when incorrect"), clEnumValN(WPDCheckMode::Fallback, "fallback", "Fallback to indirect when incorrect"))) |
#define DEBUG_TYPE "wholeprogramdevirt" |
Definition at line 106 of file WholeProgramDevirt.cpp.
enum WPDCheckMode |
Mechanism to add runtime checking of devirtualization decisions, optionally trapping or falling back to indirect call on any that are not correct.
Trapping mode is useful for debugging undefined behavior leading to failures with WPD. Fallback mode is useful for ensuring safety when whole program visibility may be compromised.
Enumerator | |
---|---|
None | |
Trap | |
Fallback |
Definition at line 205 of file WholeProgramDevirt.cpp.
Definition at line 1290 of file WholeProgramDevirt.cpp.
References AddCalls(), CallSiteInfo, llvm::CalleeInfo::Hot, and P.
Referenced by AddCalls().
|
static |
Definition at line 988 of file WholeProgramDevirt.cpp.
References ClSummaryAction, llvm::createStringError(), llvm::ModuleSummaryIndex::getRegularLTOModuleName(), llvm::Import, and llvm::invalid_argument.
Definition at line 410 of file WholeProgramDevirt.cpp.
References llvm::ValueInfo::getSummaryList(), and WholeProgramDevirtKeepUnreachableFunction.
|
static |
Definition at line 844 of file WholeProgramDevirt.cpp.
References llvm::GlobalObject::getMetadata(), and typeIDVisibleToRegularObj().
Referenced by llvm::updateVCallVisibilityInModule().
STATISTIC | ( | NumBranchFunnel | , |
"Number of branch funnels" | |||
) |
STATISTIC | ( | NumDevirtTargets | , |
"Number of whole program devirtualization targets" | |||
) |
STATISTIC | ( | NumSingleImpl | , |
"Number of single implementation devirtualizations" | |||
) |
STATISTIC | ( | NumUniformRetVal | , |
"Number of uniform return value optimizations" | |||
) |
STATISTIC | ( | NumUniqueRetVal | , |
"Number of unique return value optimizations" | |||
) |
STATISTIC | ( | NumVirtConstProp | , |
"Number of virtual constant propagations" | |||
) |
STATISTIC | ( | NumVirtConstProp1Bit | , |
"Number of 1 bit virtual constant propagations" | |||
) |
|
static |
Definition at line 820 of file WholeProgramDevirt.cpp.
Referenced by llvm::getVisibleToRegularObjVtableGUIDs(), and skipUpdateDueToValidation().
|
static |
|
static |
|
static |
|
static |
|
static |
|
static |
Provide a way to force disable whole program for debugging or workarounds, when enabled via the linker.
Referenced by llvm::hasWholeProgramVisibility().
|
static |
|
static |
Provide way to prevent certain function from being devirtualized.
|
static |
If explicitly specified, the devirt module pass will stop transformation once the total number of devirtualizations reach the cutoff value.
Setting this option to 0 explicitly will do 0 devirtualization.
|
static |
With Clang, a pure virtual class's deleting destructor is emitted as a llvm.trap
intrinsic followed by an unreachable IR instruction.
In the context of whole program devirtualization, the deleting destructor of a pure virtual class won't be invoked by the source code so safe to skip as a devirtualize target.
However, not all unreachable functions are safe to skip. In some cases, the program intends to run such functions and terminate, for instance, a unit test may run a death test. A non-test program might (or allowed to) invoke such functions to report failures (whether/when it's a good practice or not is a different topic).
This option is enabled to keep an unreachable function as a possible devirtualize target to conservatively keep the program behavior.
TODO: Make a pure virtual class's deleting destructor precisely identifiable in Clang's codegen for more devirtualization in LLVM.
Referenced by mustBeUnreachableFunction().
|
static |
Provide a way to force enable whole program visibility in tests.
This is needed to support legacy tests that don't contain !vcall_visibility metadata (the mere presense of type tests previously implied hidden visibility).
Referenced by llvm::hasWholeProgramVisibility().