mirror of
https://github.com/c64scene-ar/llvm-6502.git
synced 2025-07-22 23:24:59 +00:00
Generalize the PassConfig API and remove addFinalizeRegAlloc().
The target hooks are getting out of hand. What does it mean to run before or after regalloc anyway? Allowing either Pass* or AnalysisID pass identification should make it much easier for targets to use the substitutePass and insertPass APIs, and create less need for badly named target hooks. git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@179140 91177308-0d34-0410-b5e6-96231b3b80d8
This commit is contained in:
@@ -35,6 +35,46 @@ namespace llvm {
|
||||
|
||||
class PassConfigImpl;
|
||||
|
||||
/// Discriminated union of Pass ID types.
|
||||
///
|
||||
/// The PassConfig API prefers dealing with IDs because they are safer and more
|
||||
/// efficient. IDs decouple configuration from instantiation. This way, when a
|
||||
/// pass is overriden, it isn't unnecessarily instantiated. It is also unsafe to
|
||||
/// refer to a Pass pointer after adding it to a pass manager, which deletes
|
||||
/// redundant pass instances.
|
||||
///
|
||||
/// However, it is convient to directly instantiate target passes with
|
||||
/// non-default ctors. These often don't have a registered PassInfo. Rather than
|
||||
/// force all target passes to implement the pass registry boilerplate, allow
|
||||
/// the PassConfig API to handle either type.
|
||||
///
|
||||
/// AnalysisID is sadly char*, so PointerIntPair won't work.
|
||||
class IdentifyingPassPtr {
|
||||
void *P;
|
||||
bool IsInstance;
|
||||
public:
|
||||
IdentifyingPassPtr(): P(0), IsInstance(false) {}
|
||||
IdentifyingPassPtr(AnalysisID IDPtr): P((void*)IDPtr), IsInstance(false) {}
|
||||
IdentifyingPassPtr(Pass *InstancePtr)
|
||||
: P((void*)InstancePtr), IsInstance(true) {}
|
||||
|
||||
bool isValid() const { return P; }
|
||||
bool isInstance() const { return IsInstance; }
|
||||
|
||||
AnalysisID getID() const {
|
||||
assert(!IsInstance && "Not a Pass ID");
|
||||
return (AnalysisID)P;
|
||||
}
|
||||
Pass *getInstance() const {
|
||||
assert(IsInstance && "Not a Pass Instance");
|
||||
return (Pass *)P;
|
||||
}
|
||||
};
|
||||
|
||||
template <> struct isPodLike<IdentifyingPassPtr> {
|
||||
static const bool value = true;
|
||||
};
|
||||
|
||||
/// Target-Independent Code Generator Pass Configuration Options.
|
||||
///
|
||||
/// This is an ImmutablePass solely for the purpose of exposing CodeGen options
|
||||
@@ -117,20 +157,22 @@ public:
|
||||
/// Allow the target to override a specific pass without overriding the pass
|
||||
/// pipeline. When passes are added to the standard pipeline at the
|
||||
/// point where StandardID is expected, add TargetID in its place.
|
||||
void substitutePass(AnalysisID StandardID, AnalysisID TargetID);
|
||||
void substitutePass(AnalysisID StandardID, IdentifyingPassPtr TargetID);
|
||||
|
||||
/// Insert InsertedPassID pass after TargetPassID pass.
|
||||
void insertPass(AnalysisID TargetPassID, AnalysisID InsertedPassID);
|
||||
void insertPass(AnalysisID TargetPassID, IdentifyingPassPtr InsertedPassID);
|
||||
|
||||
/// Allow the target to enable a specific standard pass by default.
|
||||
void enablePass(AnalysisID PassID) { substitutePass(PassID, PassID); }
|
||||
|
||||
/// Allow the target to disable a specific standard pass by default.
|
||||
void disablePass(AnalysisID PassID) { substitutePass(PassID, 0); }
|
||||
void disablePass(AnalysisID PassID) {
|
||||
substitutePass(PassID, IdentifyingPassPtr());
|
||||
}
|
||||
|
||||
/// Return the pass substituted for StandardID by the target.
|
||||
/// If no substitution exists, return StandardID.
|
||||
AnalysisID getPassSubstitution(AnalysisID StandardID) const;
|
||||
IdentifyingPassPtr getPassSubstitution(AnalysisID StandardID) const;
|
||||
|
||||
/// Return true if the optimized regalloc pipeline is enabled.
|
||||
bool getOptimizeRegAlloc() const;
|
||||
@@ -222,17 +264,6 @@ protected:
|
||||
return false;
|
||||
}
|
||||
|
||||
/// addFinalizeRegAlloc - This method may be implemented by targets that want
|
||||
/// to run passes within the regalloc pipeline, immediately after the register
|
||||
/// allocation pass itself. These passes run as soon as virtual regisiters
|
||||
/// have been rewritten to physical registers but before and other postRA
|
||||
/// optimization happens. Targets that have marked instructions for bundling
|
||||
/// must have finalized those bundles by the time these passes have run,
|
||||
/// because subsequent passes are not guaranteed to be bundle-aware.
|
||||
virtual bool addFinalizeRegAlloc() {
|
||||
return false;
|
||||
}
|
||||
|
||||
/// addPostRegAlloc - This method may be implemented by targets that want to
|
||||
/// run passes after register allocation pass pipeline but before
|
||||
/// prolog-epilog insertion. This should return true if -print-machineinstrs
|
||||
|
Reference in New Issue
Block a user