blob: 7fcad253a8d04618f3a9d5f3076747179d90952b [file] [log] [blame]
Jim Stichnothd97c7df2014-06-04 11:57:08 -07001//===- subzero/src/IceLiveness.h - Liveness analysis ------------*- C++ -*-===//
2//
3// The Subzero Code Generator
4//
5// This file is distributed under the University of Illinois Open Source
6// License. See LICENSE.TXT for details.
7//
8//===----------------------------------------------------------------------===//
Andrew Scull9612d322015-07-06 14:53:25 -07009///
10/// \file
11/// This file declares the Liveness and LivenessNode classes,
12/// which are used for liveness analysis. The node-specific
13/// information tracked for each Variable includes whether it is
14/// live on entry, whether it is live on exit, the instruction number
15/// that starts its live range, and the instruction number that ends
16/// its live range. At the Cfg level, the actual live intervals are
17/// recorded.
18///
Jim Stichnothd97c7df2014-06-04 11:57:08 -070019//===----------------------------------------------------------------------===//
20
21#ifndef SUBZERO_SRC_ICELIVENESS_H
22#define SUBZERO_SRC_ICELIVENESS_H
23
John Porto67f8de92015-06-25 10:14:17 -070024#include "IceCfgNode.h"
Jim Stichnothd97c7df2014-06-04 11:57:08 -070025#include "IceDefs.h"
26#include "IceTypes.h"
27
28namespace Ice {
29
Jim Stichnothd97c7df2014-06-04 11:57:08 -070030class Liveness {
Jim Stichnothc6ead202015-02-24 09:30:30 -080031 Liveness() = delete;
Jim Stichnoth5ce0abb2014-10-15 10:16:54 -070032 Liveness(const Liveness &) = delete;
33 Liveness &operator=(const Liveness &) = delete;
34
Jim Stichnoth7e571362015-01-09 11:43:26 -080035 class LivenessNode {
36 LivenessNode &operator=(const LivenessNode &) = delete;
37
38 public:
Jim Stichnotheafb56c2015-06-22 10:35:22 -070039 LivenessNode() = default;
Jim Stichnoth7e571362015-01-09 11:43:26 -080040 LivenessNode(const LivenessNode &) = default;
Andrew Scull9612d322015-07-06 14:53:25 -070041 /// NumLocals is the number of Variables local to this block.
Jim Stichnotheafb56c2015-06-22 10:35:22 -070042 SizeT NumLocals = 0;
Andrew Scull9612d322015-07-06 14:53:25 -070043 /// NumNonDeadPhis tracks the number of Phi instructions that
44 /// Inst::liveness() identified as tentatively live. If
45 /// NumNonDeadPhis changes from the last liveness pass, then liveness
46 /// has not yet converged.
Jim Stichnotheafb56c2015-06-22 10:35:22 -070047 SizeT NumNonDeadPhis = 0;
Jim Stichnoth7e571362015-01-09 11:43:26 -080048 // LiveToVarMap maps a liveness bitvector index to a Variable. This
49 // is generally just for printing/dumping. The index should be less
50 // than NumLocals + Liveness::NumGlobals.
51 std::vector<Variable *> LiveToVarMap;
52 // LiveIn and LiveOut track the in- and out-liveness of the global
53 // variables. The size of each vector is
54 // LivenessNode::NumGlobals.
55 LivenessBV LiveIn, LiveOut;
56 // LiveBegin and LiveEnd track the instruction numbers of the start
57 // and end of each variable's live range within this block. The
58 // index/key of each element is less than NumLocals +
59 // Liveness::NumGlobals.
60 LiveBeginEndMap LiveBegin, LiveEnd;
61 };
62
Jim Stichnothd97c7df2014-06-04 11:57:08 -070063public:
Jim Stichnotheafb56c2015-06-22 10:35:22 -070064 Liveness(Cfg *Func, LivenessMode Mode) : Func(Func), Mode(Mode) {}
Jim Stichnothd97c7df2014-06-04 11:57:08 -070065 void init();
Jim Stichnoth47752552014-10-13 17:15:08 -070066 Cfg *getFunc() const { return Func; }
67 LivenessMode getMode() const { return Mode; }
Jim Stichnothd97c7df2014-06-04 11:57:08 -070068 Variable *getVariable(SizeT LiveIndex, const CfgNode *Node) const;
Jim Stichnoth47752552014-10-13 17:15:08 -070069 SizeT getLiveIndex(SizeT VarIndex) const { return VarToLiveMap[VarIndex]; }
Jim Stichnothd97c7df2014-06-04 11:57:08 -070070 SizeT getNumGlobalVars() const { return NumGlobals; }
71 SizeT getNumVarsInNode(const CfgNode *Node) const {
72 return NumGlobals + Nodes[Node->getIndex()].NumLocals;
73 }
Jim Stichnoth336f6c42014-10-30 15:01:31 -070074 SizeT &getNumNonDeadPhis(const CfgNode *Node) {
75 return Nodes[Node->getIndex()].NumNonDeadPhis;
76 }
Jim Stichnoth47752552014-10-13 17:15:08 -070077 LivenessBV &getLiveIn(const CfgNode *Node) {
Jim Stichnoth336f6c42014-10-30 15:01:31 -070078 SizeT Index = Node->getIndex();
79 resize(Index);
80 return Nodes[Index].LiveIn;
Jim Stichnothd97c7df2014-06-04 11:57:08 -070081 }
Jim Stichnoth47752552014-10-13 17:15:08 -070082 LivenessBV &getLiveOut(const CfgNode *Node) {
Jim Stichnoth336f6c42014-10-30 15:01:31 -070083 SizeT Index = Node->getIndex();
84 resize(Index);
85 return Nodes[Index].LiveOut;
Jim Stichnothd97c7df2014-06-04 11:57:08 -070086 }
Jim Stichnoth47752552014-10-13 17:15:08 -070087 LiveBeginEndMap *getLiveBegin(const CfgNode *Node) {
Jim Stichnoth336f6c42014-10-30 15:01:31 -070088 SizeT Index = Node->getIndex();
89 resize(Index);
90 return &Nodes[Index].LiveBegin;
Jim Stichnothd97c7df2014-06-04 11:57:08 -070091 }
Jim Stichnoth47752552014-10-13 17:15:08 -070092 LiveBeginEndMap *getLiveEnd(const CfgNode *Node) {
Jim Stichnoth336f6c42014-10-30 15:01:31 -070093 SizeT Index = Node->getIndex();
94 resize(Index);
95 return &Nodes[Index].LiveEnd;
Jim Stichnothd97c7df2014-06-04 11:57:08 -070096 }
Jim Stichnothd97c7df2014-06-04 11:57:08 -070097
98private:
Andrew Scull9612d322015-07-06 14:53:25 -070099 /// Resize Nodes so that Nodes[Index] is valid.
Jim Stichnoth336f6c42014-10-30 15:01:31 -0700100 void resize(SizeT Index) {
101 if (Index >= Nodes.size())
102 Nodes.resize(Index + 1);
103 }
Jim Stichnothd97c7df2014-06-04 11:57:08 -0700104 Cfg *Func;
105 LivenessMode Mode;
Jim Stichnotheafb56c2015-06-22 10:35:22 -0700106 SizeT NumGlobals = 0;
Andrew Scull9612d322015-07-06 14:53:25 -0700107 /// Size of Nodes is Cfg::Nodes.size().
Jim Stichnothd97c7df2014-06-04 11:57:08 -0700108 std::vector<LivenessNode> Nodes;
Andrew Scull9612d322015-07-06 14:53:25 -0700109 /// VarToLiveMap maps a Variable's Variable::Number to its live index
110 /// within its basic block.
Jim Stichnothd97c7df2014-06-04 11:57:08 -0700111 std::vector<SizeT> VarToLiveMap;
Andrew Scull9612d322015-07-06 14:53:25 -0700112 /// LiveToVarMap is analogous to LivenessNode::LiveToVarMap, but for
113 /// non-local variables.
Jim Stichnothd97c7df2014-06-04 11:57:08 -0700114 std::vector<Variable *> LiveToVarMap;
Jim Stichnothd97c7df2014-06-04 11:57:08 -0700115};
116
117} // end of namespace Ice
118
119#endif // SUBZERO_SRC_ICELIVENESS_H