clang 20.0.0 (based on r547379) from build 12806354. Bug: http://b/379133546 Test: N/A Change-Id: I2eb8938af55d809de674be63cb30cf27e801862b Upstream-Commit: ad834e67b1105d15ef907f6255d4c96e8e733f57
693 lines
20 KiB
C++
693 lines
20 KiB
C++
//===- Action.h - Abstract compilation steps --------------------*- 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 LLVM_CLANG_DRIVER_ACTION_H
|
|
#define LLVM_CLANG_DRIVER_ACTION_H
|
|
|
|
#include "clang/Basic/LLVM.h"
|
|
#include "clang/Driver/Types.h"
|
|
#include "clang/Driver/Util.h"
|
|
#include "llvm/ADT/ArrayRef.h"
|
|
#include "llvm/ADT/STLExtras.h"
|
|
#include "llvm/ADT/SmallVector.h"
|
|
#include "llvm/ADT/StringRef.h"
|
|
#include "llvm/ADT/iterator_range.h"
|
|
#include <string>
|
|
|
|
namespace llvm {
|
|
namespace opt {
|
|
|
|
class Arg;
|
|
|
|
} // namespace opt
|
|
} // namespace llvm
|
|
|
|
namespace clang {
|
|
namespace driver {
|
|
|
|
class ToolChain;
|
|
|
|
/// Action - Represent an abstract compilation step to perform.
|
|
///
|
|
/// An action represents an edge in the compilation graph; typically
|
|
/// it is a job to transform an input using some tool.
|
|
///
|
|
/// The current driver is hard wired to expect actions which produce a
|
|
/// single primary output, at least in terms of controlling the
|
|
/// compilation. Actions can produce auxiliary files, but can only
|
|
/// produce a single output to feed into subsequent actions.
|
|
///
|
|
/// Actions are usually owned by a Compilation, which creates new
|
|
/// actions via MakeAction().
|
|
class Action {
|
|
public:
|
|
using size_type = ActionList::size_type;
|
|
using input_iterator = ActionList::iterator;
|
|
using input_const_iterator = ActionList::const_iterator;
|
|
using input_range = llvm::iterator_range<input_iterator>;
|
|
using input_const_range = llvm::iterator_range<input_const_iterator>;
|
|
|
|
enum ActionClass {
|
|
InputClass = 0,
|
|
BindArchClass,
|
|
OffloadClass,
|
|
PreprocessJobClass,
|
|
PrecompileJobClass,
|
|
ExtractAPIJobClass,
|
|
AnalyzeJobClass,
|
|
MigrateJobClass,
|
|
CompileJobClass,
|
|
BackendJobClass,
|
|
AssembleJobClass,
|
|
LinkJobClass,
|
|
IfsMergeJobClass,
|
|
LipoJobClass,
|
|
DsymutilJobClass,
|
|
VerifyDebugInfoJobClass,
|
|
VerifyPCHJobClass,
|
|
OffloadBundlingJobClass,
|
|
OffloadUnbundlingJobClass,
|
|
OffloadPackagerJobClass,
|
|
LinkerWrapperJobClass,
|
|
StaticLibJobClass,
|
|
BinaryAnalyzeJobClass,
|
|
|
|
JobClassFirst = PreprocessJobClass,
|
|
JobClassLast = BinaryAnalyzeJobClass
|
|
};
|
|
|
|
// The offloading kind determines if this action is binded to a particular
|
|
// programming model. Each entry reserves one bit. We also have a special kind
|
|
// to designate the host offloading tool chain.
|
|
enum OffloadKind {
|
|
OFK_None = 0x00,
|
|
|
|
// The host offloading tool chain.
|
|
OFK_Host = 0x01,
|
|
|
|
// The device offloading tool chains - one bit for each programming model.
|
|
OFK_Cuda = 0x02,
|
|
OFK_OpenMP = 0x04,
|
|
OFK_HIP = 0x08,
|
|
};
|
|
|
|
static const char *getClassName(ActionClass AC);
|
|
|
|
private:
|
|
ActionClass Kind;
|
|
|
|
/// The output type of this action.
|
|
types::ID Type;
|
|
|
|
ActionList Inputs;
|
|
|
|
/// Flag that is set to true if this action can be collapsed with others
|
|
/// actions that depend on it. This is true by default and set to false when
|
|
/// the action is used by two different tool chains, which is enabled by the
|
|
/// offloading support implementation.
|
|
bool CanBeCollapsedWithNextDependentAction = true;
|
|
|
|
protected:
|
|
///
|
|
/// Offload information.
|
|
///
|
|
|
|
/// The host offloading kind - a combination of kinds encoded in a mask.
|
|
/// Multiple programming models may be supported simultaneously by the same
|
|
/// host.
|
|
unsigned ActiveOffloadKindMask = 0u;
|
|
|
|
/// Offloading kind of the device.
|
|
OffloadKind OffloadingDeviceKind = OFK_None;
|
|
|
|
/// The Offloading architecture associated with this action.
|
|
const char *OffloadingArch = nullptr;
|
|
|
|
/// The Offloading toolchain associated with this device action.
|
|
const ToolChain *OffloadingToolChain = nullptr;
|
|
|
|
Action(ActionClass Kind, types::ID Type) : Action(Kind, ActionList(), Type) {}
|
|
Action(ActionClass Kind, Action *Input, types::ID Type)
|
|
: Action(Kind, ActionList({Input}), Type) {}
|
|
Action(ActionClass Kind, Action *Input)
|
|
: Action(Kind, ActionList({Input}), Input->getType()) {}
|
|
Action(ActionClass Kind, const ActionList &Inputs, types::ID Type)
|
|
: Kind(Kind), Type(Type), Inputs(Inputs) {}
|
|
|
|
public:
|
|
virtual ~Action();
|
|
|
|
const char *getClassName() const { return Action::getClassName(getKind()); }
|
|
|
|
ActionClass getKind() const { return Kind; }
|
|
types::ID getType() const { return Type; }
|
|
|
|
ActionList &getInputs() { return Inputs; }
|
|
const ActionList &getInputs() const { return Inputs; }
|
|
|
|
size_type size() const { return Inputs.size(); }
|
|
|
|
input_iterator input_begin() { return Inputs.begin(); }
|
|
input_iterator input_end() { return Inputs.end(); }
|
|
input_range inputs() { return input_range(input_begin(), input_end()); }
|
|
input_const_iterator input_begin() const { return Inputs.begin(); }
|
|
input_const_iterator input_end() const { return Inputs.end(); }
|
|
input_const_range inputs() const {
|
|
return input_const_range(input_begin(), input_end());
|
|
}
|
|
|
|
/// Mark this action as not legal to collapse.
|
|
void setCannotBeCollapsedWithNextDependentAction() {
|
|
CanBeCollapsedWithNextDependentAction = false;
|
|
}
|
|
|
|
/// Return true if this function can be collapsed with others.
|
|
bool isCollapsingWithNextDependentActionLegal() const {
|
|
return CanBeCollapsedWithNextDependentAction;
|
|
}
|
|
|
|
/// Return a string containing the offload kind of the action.
|
|
std::string getOffloadingKindPrefix() const;
|
|
|
|
/// Return a string that can be used as prefix in order to generate unique
|
|
/// files for each offloading kind. By default, no prefix is used for
|
|
/// non-device kinds, except if \a CreatePrefixForHost is set.
|
|
static std::string
|
|
GetOffloadingFileNamePrefix(OffloadKind Kind,
|
|
StringRef NormalizedTriple,
|
|
bool CreatePrefixForHost = false);
|
|
|
|
/// Return a string containing a offload kind name.
|
|
static StringRef GetOffloadKindName(OffloadKind Kind);
|
|
|
|
/// Set the device offload info of this action and propagate it to its
|
|
/// dependences.
|
|
void propagateDeviceOffloadInfo(OffloadKind OKind, const char *OArch,
|
|
const ToolChain *OToolChain);
|
|
|
|
/// Append the host offload info of this action and propagate it to its
|
|
/// dependences.
|
|
void propagateHostOffloadInfo(unsigned OKinds, const char *OArch);
|
|
|
|
void setHostOffloadInfo(unsigned OKinds, const char *OArch) {
|
|
ActiveOffloadKindMask |= OKinds;
|
|
OffloadingArch = OArch;
|
|
}
|
|
|
|
/// Set the offload info of this action to be the same as the provided action,
|
|
/// and propagate it to its dependences.
|
|
void propagateOffloadInfo(const Action *A);
|
|
|
|
unsigned getOffloadingHostActiveKinds() const {
|
|
return ActiveOffloadKindMask;
|
|
}
|
|
|
|
OffloadKind getOffloadingDeviceKind() const { return OffloadingDeviceKind; }
|
|
const char *getOffloadingArch() const { return OffloadingArch; }
|
|
const ToolChain *getOffloadingToolChain() const {
|
|
return OffloadingToolChain;
|
|
}
|
|
|
|
/// Check if this action have any offload kinds. Note that host offload kinds
|
|
/// are only set if the action is a dependence to a host offload action.
|
|
bool isHostOffloading(unsigned int OKind) const {
|
|
return ActiveOffloadKindMask & OKind;
|
|
}
|
|
bool isDeviceOffloading(OffloadKind OKind) const {
|
|
return OffloadingDeviceKind == OKind;
|
|
}
|
|
bool isOffloading(OffloadKind OKind) const {
|
|
return isHostOffloading(OKind) || isDeviceOffloading(OKind);
|
|
}
|
|
};
|
|
|
|
class InputAction : public Action {
|
|
const llvm::opt::Arg &Input;
|
|
std::string Id;
|
|
virtual void anchor();
|
|
|
|
public:
|
|
InputAction(const llvm::opt::Arg &Input, types::ID Type,
|
|
StringRef Id = StringRef());
|
|
|
|
const llvm::opt::Arg &getInputArg() const { return Input; }
|
|
|
|
void setId(StringRef _Id) { Id = _Id.str(); }
|
|
StringRef getId() const { return Id; }
|
|
|
|
static bool classof(const Action *A) {
|
|
return A->getKind() == InputClass;
|
|
}
|
|
};
|
|
|
|
class BindArchAction : public Action {
|
|
virtual void anchor();
|
|
|
|
/// The architecture to bind, or 0 if the default architecture
|
|
/// should be bound.
|
|
StringRef ArchName;
|
|
|
|
public:
|
|
BindArchAction(Action *Input, StringRef ArchName);
|
|
|
|
StringRef getArchName() const { return ArchName; }
|
|
|
|
static bool classof(const Action *A) {
|
|
return A->getKind() == BindArchClass;
|
|
}
|
|
};
|
|
|
|
/// An offload action combines host or/and device actions according to the
|
|
/// programming model implementation needs and propagates the offloading kind to
|
|
/// its dependences.
|
|
class OffloadAction final : public Action {
|
|
virtual void anchor();
|
|
|
|
public:
|
|
/// Type used to communicate device actions. It associates bound architecture,
|
|
/// toolchain, and offload kind to each action.
|
|
class DeviceDependences final {
|
|
public:
|
|
using ToolChainList = SmallVector<const ToolChain *, 3>;
|
|
using BoundArchList = SmallVector<const char *, 3>;
|
|
using OffloadKindList = SmallVector<OffloadKind, 3>;
|
|
|
|
private:
|
|
// Lists that keep the information for each dependency. All the lists are
|
|
// meant to be updated in sync. We are adopting separate lists instead of a
|
|
// list of structs, because that simplifies forwarding the actions list to
|
|
// initialize the inputs of the base Action class.
|
|
|
|
/// The dependence actions.
|
|
ActionList DeviceActions;
|
|
|
|
/// The offloading toolchains that should be used with the action.
|
|
ToolChainList DeviceToolChains;
|
|
|
|
/// The architectures that should be used with this action.
|
|
BoundArchList DeviceBoundArchs;
|
|
|
|
/// The offload kind of each dependence.
|
|
OffloadKindList DeviceOffloadKinds;
|
|
|
|
public:
|
|
/// Add an action along with the associated toolchain, bound arch, and
|
|
/// offload kind.
|
|
void add(Action &A, const ToolChain &TC, const char *BoundArch,
|
|
OffloadKind OKind);
|
|
|
|
/// Add an action along with the associated toolchain, bound arch, and
|
|
/// offload kinds.
|
|
void add(Action &A, const ToolChain &TC, const char *BoundArch,
|
|
unsigned OffloadKindMask);
|
|
|
|
/// Get each of the individual arrays.
|
|
const ActionList &getActions() const { return DeviceActions; }
|
|
const ToolChainList &getToolChains() const { return DeviceToolChains; }
|
|
const BoundArchList &getBoundArchs() const { return DeviceBoundArchs; }
|
|
const OffloadKindList &getOffloadKinds() const {
|
|
return DeviceOffloadKinds;
|
|
}
|
|
};
|
|
|
|
/// Type used to communicate host actions. It associates bound architecture,
|
|
/// toolchain, and offload kinds to the host action.
|
|
class HostDependence final {
|
|
/// The dependence action.
|
|
Action &HostAction;
|
|
|
|
/// The offloading toolchain that should be used with the action.
|
|
const ToolChain &HostToolChain;
|
|
|
|
/// The architectures that should be used with this action.
|
|
const char *HostBoundArch = nullptr;
|
|
|
|
/// The offload kind of each dependence.
|
|
unsigned HostOffloadKinds = 0u;
|
|
|
|
public:
|
|
HostDependence(Action &A, const ToolChain &TC, const char *BoundArch,
|
|
const unsigned OffloadKinds)
|
|
: HostAction(A), HostToolChain(TC), HostBoundArch(BoundArch),
|
|
HostOffloadKinds(OffloadKinds) {}
|
|
|
|
/// Constructor version that obtains the offload kinds from the device
|
|
/// dependencies.
|
|
HostDependence(Action &A, const ToolChain &TC, const char *BoundArch,
|
|
const DeviceDependences &DDeps);
|
|
Action *getAction() const { return &HostAction; }
|
|
const ToolChain *getToolChain() const { return &HostToolChain; }
|
|
const char *getBoundArch() const { return HostBoundArch; }
|
|
unsigned getOffloadKinds() const { return HostOffloadKinds; }
|
|
};
|
|
|
|
using OffloadActionWorkTy =
|
|
llvm::function_ref<void(Action *, const ToolChain *, const char *)>;
|
|
|
|
private:
|
|
/// The host offloading toolchain that should be used with the action.
|
|
const ToolChain *HostTC = nullptr;
|
|
|
|
/// The tool chains associated with the list of actions.
|
|
DeviceDependences::ToolChainList DevToolChains;
|
|
|
|
public:
|
|
OffloadAction(const HostDependence &HDep);
|
|
OffloadAction(const DeviceDependences &DDeps, types::ID Ty);
|
|
OffloadAction(const HostDependence &HDep, const DeviceDependences &DDeps);
|
|
|
|
/// Execute the work specified in \a Work on the host dependence.
|
|
void doOnHostDependence(const OffloadActionWorkTy &Work) const;
|
|
|
|
/// Execute the work specified in \a Work on each device dependence.
|
|
void doOnEachDeviceDependence(const OffloadActionWorkTy &Work) const;
|
|
|
|
/// Execute the work specified in \a Work on each dependence.
|
|
void doOnEachDependence(const OffloadActionWorkTy &Work) const;
|
|
|
|
/// Execute the work specified in \a Work on each host or device dependence if
|
|
/// \a IsHostDependenceto is true or false, respectively.
|
|
void doOnEachDependence(bool IsHostDependence,
|
|
const OffloadActionWorkTy &Work) const;
|
|
|
|
/// Return true if the action has a host dependence.
|
|
bool hasHostDependence() const;
|
|
|
|
/// Return the host dependence of this action. This function is only expected
|
|
/// to be called if the host dependence exists.
|
|
Action *getHostDependence() const;
|
|
|
|
/// Return true if the action has a single device dependence. If \a
|
|
/// DoNotConsiderHostActions is set, ignore the host dependence, if any, while
|
|
/// accounting for the number of dependences.
|
|
bool hasSingleDeviceDependence(bool DoNotConsiderHostActions = false) const;
|
|
|
|
/// Return the single device dependence of this action. This function is only
|
|
/// expected to be called if a single device dependence exists. If \a
|
|
/// DoNotConsiderHostActions is set, a host dependence is allowed.
|
|
Action *
|
|
getSingleDeviceDependence(bool DoNotConsiderHostActions = false) const;
|
|
|
|
static bool classof(const Action *A) { return A->getKind() == OffloadClass; }
|
|
};
|
|
|
|
class JobAction : public Action {
|
|
virtual void anchor();
|
|
|
|
protected:
|
|
JobAction(ActionClass Kind, Action *Input, types::ID Type);
|
|
JobAction(ActionClass Kind, const ActionList &Inputs, types::ID Type);
|
|
|
|
public:
|
|
static bool classof(const Action *A) {
|
|
return (A->getKind() >= JobClassFirst &&
|
|
A->getKind() <= JobClassLast);
|
|
}
|
|
};
|
|
|
|
class PreprocessJobAction : public JobAction {
|
|
void anchor() override;
|
|
|
|
public:
|
|
PreprocessJobAction(Action *Input, types::ID OutputType);
|
|
|
|
static bool classof(const Action *A) {
|
|
return A->getKind() == PreprocessJobClass;
|
|
}
|
|
};
|
|
|
|
class PrecompileJobAction : public JobAction {
|
|
void anchor() override;
|
|
|
|
protected:
|
|
PrecompileJobAction(ActionClass Kind, Action *Input, types::ID OutputType);
|
|
|
|
public:
|
|
PrecompileJobAction(Action *Input, types::ID OutputType);
|
|
|
|
static bool classof(const Action *A) {
|
|
return A->getKind() == PrecompileJobClass;
|
|
}
|
|
};
|
|
|
|
class ExtractAPIJobAction : public JobAction {
|
|
void anchor() override;
|
|
|
|
public:
|
|
ExtractAPIJobAction(Action *Input, types::ID OutputType);
|
|
|
|
static bool classof(const Action *A) {
|
|
return A->getKind() == ExtractAPIJobClass;
|
|
}
|
|
|
|
void addHeaderInput(Action *Input) { getInputs().push_back(Input); }
|
|
};
|
|
|
|
class AnalyzeJobAction : public JobAction {
|
|
void anchor() override;
|
|
|
|
public:
|
|
AnalyzeJobAction(Action *Input, types::ID OutputType);
|
|
|
|
static bool classof(const Action *A) {
|
|
return A->getKind() == AnalyzeJobClass;
|
|
}
|
|
};
|
|
|
|
class MigrateJobAction : public JobAction {
|
|
void anchor() override;
|
|
|
|
public:
|
|
MigrateJobAction(Action *Input, types::ID OutputType);
|
|
|
|
static bool classof(const Action *A) {
|
|
return A->getKind() == MigrateJobClass;
|
|
}
|
|
};
|
|
|
|
class CompileJobAction : public JobAction {
|
|
void anchor() override;
|
|
|
|
public:
|
|
CompileJobAction(Action *Input, types::ID OutputType);
|
|
|
|
static bool classof(const Action *A) {
|
|
return A->getKind() == CompileJobClass;
|
|
}
|
|
};
|
|
|
|
class BackendJobAction : public JobAction {
|
|
void anchor() override;
|
|
|
|
public:
|
|
BackendJobAction(Action *Input, types::ID OutputType);
|
|
|
|
static bool classof(const Action *A) {
|
|
return A->getKind() == BackendJobClass;
|
|
}
|
|
};
|
|
|
|
class AssembleJobAction : public JobAction {
|
|
void anchor() override;
|
|
|
|
public:
|
|
AssembleJobAction(Action *Input, types::ID OutputType);
|
|
|
|
static bool classof(const Action *A) {
|
|
return A->getKind() == AssembleJobClass;
|
|
}
|
|
};
|
|
|
|
class IfsMergeJobAction : public JobAction {
|
|
void anchor() override;
|
|
|
|
public:
|
|
IfsMergeJobAction(ActionList &Inputs, types::ID Type);
|
|
|
|
static bool classof(const Action *A) {
|
|
return A->getKind() == IfsMergeJobClass;
|
|
}
|
|
};
|
|
|
|
class LinkJobAction : public JobAction {
|
|
void anchor() override;
|
|
|
|
public:
|
|
LinkJobAction(ActionList &Inputs, types::ID Type);
|
|
|
|
static bool classof(const Action *A) {
|
|
return A->getKind() == LinkJobClass;
|
|
}
|
|
};
|
|
|
|
class LipoJobAction : public JobAction {
|
|
void anchor() override;
|
|
|
|
public:
|
|
LipoJobAction(ActionList &Inputs, types::ID Type);
|
|
|
|
static bool classof(const Action *A) {
|
|
return A->getKind() == LipoJobClass;
|
|
}
|
|
};
|
|
|
|
class DsymutilJobAction : public JobAction {
|
|
void anchor() override;
|
|
|
|
public:
|
|
DsymutilJobAction(ActionList &Inputs, types::ID Type);
|
|
|
|
static bool classof(const Action *A) {
|
|
return A->getKind() == DsymutilJobClass;
|
|
}
|
|
};
|
|
|
|
class VerifyJobAction : public JobAction {
|
|
void anchor() override;
|
|
|
|
public:
|
|
VerifyJobAction(ActionClass Kind, Action *Input, types::ID Type);
|
|
|
|
static bool classof(const Action *A) {
|
|
return A->getKind() == VerifyDebugInfoJobClass ||
|
|
A->getKind() == VerifyPCHJobClass;
|
|
}
|
|
};
|
|
|
|
class VerifyDebugInfoJobAction : public VerifyJobAction {
|
|
void anchor() override;
|
|
|
|
public:
|
|
VerifyDebugInfoJobAction(Action *Input, types::ID Type);
|
|
|
|
static bool classof(const Action *A) {
|
|
return A->getKind() == VerifyDebugInfoJobClass;
|
|
}
|
|
};
|
|
|
|
class VerifyPCHJobAction : public VerifyJobAction {
|
|
void anchor() override;
|
|
|
|
public:
|
|
VerifyPCHJobAction(Action *Input, types::ID Type);
|
|
|
|
static bool classof(const Action *A) {
|
|
return A->getKind() == VerifyPCHJobClass;
|
|
}
|
|
};
|
|
|
|
class OffloadBundlingJobAction : public JobAction {
|
|
void anchor() override;
|
|
|
|
public:
|
|
// Offloading bundling doesn't change the type of output.
|
|
OffloadBundlingJobAction(ActionList &Inputs);
|
|
|
|
static bool classof(const Action *A) {
|
|
return A->getKind() == OffloadBundlingJobClass;
|
|
}
|
|
};
|
|
|
|
class OffloadUnbundlingJobAction final : public JobAction {
|
|
void anchor() override;
|
|
|
|
public:
|
|
/// Type that provides information about the actions that depend on this
|
|
/// unbundling action.
|
|
struct DependentActionInfo final {
|
|
/// The tool chain of the dependent action.
|
|
const ToolChain *DependentToolChain = nullptr;
|
|
|
|
/// The bound architecture of the dependent action.
|
|
StringRef DependentBoundArch;
|
|
|
|
/// The offload kind of the dependent action.
|
|
const OffloadKind DependentOffloadKind = OFK_None;
|
|
|
|
DependentActionInfo(const ToolChain *DependentToolChain,
|
|
StringRef DependentBoundArch,
|
|
const OffloadKind DependentOffloadKind)
|
|
: DependentToolChain(DependentToolChain),
|
|
DependentBoundArch(DependentBoundArch),
|
|
DependentOffloadKind(DependentOffloadKind) {}
|
|
};
|
|
|
|
private:
|
|
/// Container that keeps information about each dependence of this unbundling
|
|
/// action.
|
|
SmallVector<DependentActionInfo, 6> DependentActionInfoArray;
|
|
|
|
public:
|
|
// Offloading unbundling doesn't change the type of output.
|
|
OffloadUnbundlingJobAction(Action *Input);
|
|
|
|
/// Register information about a dependent action.
|
|
void registerDependentActionInfo(const ToolChain *TC, StringRef BoundArch,
|
|
OffloadKind Kind) {
|
|
DependentActionInfoArray.push_back({TC, BoundArch, Kind});
|
|
}
|
|
|
|
/// Return the information about all depending actions.
|
|
ArrayRef<DependentActionInfo> getDependentActionsInfo() const {
|
|
return DependentActionInfoArray;
|
|
}
|
|
|
|
static bool classof(const Action *A) {
|
|
return A->getKind() == OffloadUnbundlingJobClass;
|
|
}
|
|
};
|
|
|
|
class OffloadPackagerJobAction : public JobAction {
|
|
void anchor() override;
|
|
|
|
public:
|
|
OffloadPackagerJobAction(ActionList &Inputs, types::ID Type);
|
|
|
|
static bool classof(const Action *A) {
|
|
return A->getKind() == OffloadPackagerJobClass;
|
|
}
|
|
};
|
|
|
|
class LinkerWrapperJobAction : public JobAction {
|
|
void anchor() override;
|
|
|
|
public:
|
|
LinkerWrapperJobAction(ActionList &Inputs, types::ID Type);
|
|
|
|
static bool classof(const Action *A) {
|
|
return A->getKind() == LinkerWrapperJobClass;
|
|
}
|
|
};
|
|
|
|
class StaticLibJobAction : public JobAction {
|
|
void anchor() override;
|
|
|
|
public:
|
|
StaticLibJobAction(ActionList &Inputs, types::ID Type);
|
|
|
|
static bool classof(const Action *A) {
|
|
return A->getKind() == StaticLibJobClass;
|
|
}
|
|
};
|
|
|
|
class BinaryAnalyzeJobAction : public JobAction {
|
|
void anchor() override;
|
|
|
|
public:
|
|
BinaryAnalyzeJobAction(Action *Input, types::ID Type);
|
|
|
|
static bool classof(const Action *A) {
|
|
return A->getKind() == BinaryAnalyzeJobClass;
|
|
}
|
|
};
|
|
|
|
} // namespace driver
|
|
} // namespace clang
|
|
|
|
#endif // LLVM_CLANG_DRIVER_ACTION_H
|