class BlockNamer; class CodeGenerator; class HBasicBlock; class HConstant; class HCurrentMethod; class HDoubleConstant; class HFloatConstant; class HInstruction; class HLongConstant; class HIntConstant; class HInvoke; class HNullConstant; class VariableSizedHandleScope;
// An iterator to only blocks that are still actually in the graph (when // blocks are removed they are replaced with 'nullptr' in GetBlocks to // simplify block-id assignment and avoid memmoves in the block-list).
IterationRange<FilterNull<ArenaVector<HBasicBlock*>::const_iterator>> GetActiveBlocks() const { return FilterOutNull(MakeIterationRange(GetBlocks()));
}
// Analyze all natural loops in this graph. Returns a code specifying that it // was successful or the reason for failure. The method will fail if a loop // is a throw-catch loop, i.e. the header is a catch block.
GraphAnalysisResult AnalyzeLoops() const;
// Iterate over blocks to compute try block membership. Needs reverse post // order and loop information. void ComputeTryBlockInformation();
// Inline this graph in `outer_graph`, replacing the given `invoke` instruction. // Returns the instruction to replace the invoke expression or null if the // invoke is for a void method. Note that the caller is responsible for replacing // and removing the invoke instruction.
HInstruction* InlineInto(HGraph* outer_graph, HInvoke* invoke);
// Update the loop and try membership of `block`, which was spawned from `reference`. // In case `reference` is a back edge, `replace_if_back_edge` notifies whether `block` // should be the new back edge. // `has_more_specific_try_catch_info` will be set to true when inlining a try catch. void UpdateLoopAndTryInformationOfNewBlock(HBasicBlock* block,
HBasicBlock* reference, bool replace_if_back_edge, bool has_more_specific_try_catch_info = false);
// Need to add a couple of blocks to test if the loop body is entered and // put deoptimization instructions, etc. void TransformLoopHeaderForBCE(HBasicBlock* header);
// Adds a new loop directly after the loop with the given header and exit. // Returns the new preheader.
HBasicBlock* TransformLoopForVectorization(HBasicBlock* header,
HBasicBlock* body,
HBasicBlock* exit);
// Removes `block` from the graph. Assumes `block` has been disconnected from // other blocks and has no instructions or phis. void DeleteDeadEmptyBlock(HBasicBlock* block);
// Splits the edge between `block` and `successor` while preserving the // indices in the predecessor/successor lists. If there are multiple edges // between the blocks, the lowest indices are used. // Returns the new block which is empty and has the same dex pc as `successor`.
HBasicBlock* SplitEdge(HBasicBlock* block, HBasicBlock* successor);
// Transform a loop into a format with a single preheader. // // Each phi in the header should be split: original one in the header should only hold // inputs reachable from the back edges and a single input from the preheader. The newly created // phi in the preheader should collate the inputs from the original multiple incoming blocks. // // Loops in the graph typically have a single preheader, so this method is used to "repair" loops // that no longer have this property. void TransformLoopToSinglePreheaderFormat(HBasicBlock* header);
// Is the code known to be robust against eliminating dead references // and the effects of early finalization? bool IsDeadReferenceSafe() const { return dead_reference_safe_; }
// Returns a constant of the given type and value. If it does not exist // already, it is created and inserted into the graph. This method is only for // integral types.
HConstant* GetConstant(DataType::Type type, int64_t value);
// TODO: This is problematic for the consistency of reference type propagation // because it can be created anytime after the pass and thus it will be left // with an invalid type.
HNullConstant* GetNullConstant();
// In case of OSR we intend to use SuspendChecks as an entry point to the // function; for debuggable graphs we might deoptimize to interpreter from // SuspendChecks. In these cases we should always generate code for them. bool SuspendChecksAreAllowedToNoOp() const { return !IsDebuggable() && !IsCompilingOsr();
}
// Cache a float constant into the graph. This method should only be // called by the SsaBuilder when creating "equivalent" instructions. void CacheFloatConstant(HFloatConstant* constant);
// See CacheFloatConstant comment. void CacheDoubleConstant(HDoubleConstant* constant);
// List of blocks in insertion order.
ArenaVector<HBasicBlock*> blocks_;
// List of blocks to perform a reverse post order tree traversal.
ArenaVector<HBasicBlock*> reverse_post_order_;
// List of blocks to perform a linear order tree traversal. Unlike the reverse // post order, this order is not incrementally kept up-to-date.
ArenaVector<HBasicBlock*> linear_order_;
// The number of virtual registers in this method. Contains the parameters.
uint16_t number_of_vregs_;
// The number of virtual registers used by parameters of this method.
uint16_t number_of_in_vregs_;
// Number of vreg size slots that the temporaries use (used in baseline compiler).
size_t temporaries_vreg_slots_;
// Flag whether there are bounds checks in the graph. We can skip // BCE if it's false. bool has_bounds_checks_;
// Flag whether there are try/catch blocks in the graph. We will skip // try/catch-related passes if it's false. bool has_try_catch_;
// Flag whether there are any HMonitorOperation in the graph. If yes this will mandate // DexRegisterMap to be present to allow deadlock analysis for non-debuggable code. bool has_monitor_operations_;
// Flags whether SIMD (traditional or predicated) instructions appear in the graph. // If either is true, the code generators may have to be more careful spilling the wider // contents of SIMD registers. bool has_traditional_simd_; bool has_predicated_simd_;
// Flag whether there are any loops in the graph. We can skip loop // optimization if it's false. bool has_loops_;
// Flag whether there are any irreducible loops in the graph. bool has_irreducible_loops_;
// Flag whether there are any direct calls to native code registered // for @CriticalNative methods. bool has_direct_critical_native_call_;
// Flag whether the graph contains invokes that always throw. bool has_always_throwing_invokes_;
// Is the code known to be robust against eliminating dead references // and the effects of early finalization? If false, dead reference variables // are kept if they might be visible to the garbage collector. // Currently this means that the class was declared to be dead-reference-safe, // the method accesses no reachability-sensitive fields or data, and the same // is true for any methods that were inlined into the current one. bool dead_reference_safe_;
// Indicates whether the graph should be compiled in a way that // ensures full debuggability. If false, we can apply more // aggressive optimizations that may limit the level of debugging. constbool debuggable_;
// Whether the graph should be compiled with extra hooks to attach dynamic // instrumentation. constbool dynamic_instrumentation_;
// The current id to assign to a newly added instruction. See HInstruction.id_.
int32_t current_instruction_id_;
// The dex file from which the method is from. const DexFile& dex_file_;
// The method index in the dex file. const uint32_t method_idx_;
// If inlined, this encodes how the callee is being invoked. const InvokeType invoke_type_;
// Whether the graph has been transformed to SSA form. Only used // in debug mode to ensure we are not using properties only valid // for non-SSA form (like the number of temporaries). bool in_ssa_form_;
// Number of CHA guards in the graph. Used to short-circuit the // CHA guard optimization pass when there is no CHA guard left.
uint32_t number_of_cha_guards_;
// The ArtMethod this graph is for. Note that for AOT, it may be null, // for example for methods whose declaring class could not be resolved // (such as when the superclass could not be found).
ArtMethod* art_method_;
// The `ProfilingInfo` associated with the method being compiled.
ProfilingInfo* profiling_info_;
// How we are compiling the graph: either optimized, osr, or baseline. // For osr, we will make all loops seen as irreducible and emit special // stack maps to mark compiled code entries which the interpreter can // directly jump to. const CompilationKind compilation_kind_;
// Whether after compiling baseline it is still useful re-optimizing this // method. bool useful_optimizing_;
// List of methods that are assumed to have single implementation.
ArenaSet<ArtMethod*> cha_single_implementation_list_;
friendclass HControlFlowSimplifier; // For direct modification of `reverse_post_order_`. friendclass HInliner; // For the reverse post order. friendclass SsaBuilder; // For caching constants. friendclass SsaLivenessAnalysis; // For the linear order.
ART_FRIEND_TEST(GraphTest, IfSuccessorSimpleJoinBlock1);
DISALLOW_COPY_AND_ASSIGN(HGraph);
};
} // namespace art
#endif// ART_COMPILER_OPTIMIZING_GRAPH_H_
Messung V0.5 in Prozent
¤ Dauer der Verarbeitung: 0.13 Sekunden
(vorverarbeitet am 2026-06-29)
¤
Die Informationen auf dieser Webseite wurden
nach bestem Wissen sorgfältig zusammengestellt. Es wird jedoch weder Vollständigkeit, noch Richtigkeit,
noch Qualität der bereit gestellten Informationen zugesichert.
Bemerkung:
Die farbliche Syntaxdarstellung und die Messung sind noch experimentell.