@@ -46,12 +46,13 @@ class StaticDataSplitter : public MachineFunctionPass {
46
46
const MachineBlockFrequencyInfo *MBFI = nullptr ;
47
47
const ProfileSummaryInfo *PSI = nullptr ;
48
48
49
- // Returns true iff any jump table is hot-cold categorized.
50
- bool splitJumpTables (MachineFunction &MF);
49
+ // Update LLVM statistics for a machine function without profiles.
50
+ void updateStatsWithoutProfiles (const MachineFunction &MF);
51
+ // Update LLVM statistics for a machine function with profiles.
52
+ void updateStatsWithProfiles (const MachineFunction &MF);
51
53
52
- // Same as above but works on functions with profile information.
53
- bool splitJumpTablesWithProfiles (const MachineFunction &MF,
54
- MachineJumpTableInfo &MJTI);
54
+ // Use profiles to partition static data.
55
+ bool partitionStaticDataWithProfiles (MachineFunction &MF);
55
56
56
57
public:
57
58
static char ID;
@@ -77,13 +78,25 @@ bool StaticDataSplitter::runOnMachineFunction(MachineFunction &MF) {
77
78
MBFI = &getAnalysis<MachineBlockFrequencyInfoWrapperPass>().getMBFI ();
78
79
PSI = &getAnalysis<ProfileSummaryInfoWrapperPass>().getPSI ();
79
80
80
- return splitJumpTables (MF);
81
+ const bool ProfileAvailable = PSI && PSI->hasProfileSummary () && MBFI &&
82
+ MF.getFunction ().hasProfileData ();
83
+
84
+ if (!ProfileAvailable) {
85
+ updateStatsWithoutProfiles (MF);
86
+ return false ;
87
+ }
88
+
89
+ bool Changed = partitionStaticDataWithProfiles (MF);
90
+
91
+ updateStatsWithProfiles (MF);
92
+ return Changed;
81
93
}
82
94
83
- bool StaticDataSplitter::splitJumpTablesWithProfiles (
84
- const MachineFunction &MF, MachineJumpTableInfo &MJTI) {
95
+ bool StaticDataSplitter::partitionStaticDataWithProfiles (MachineFunction &MF) {
85
96
int NumChangedJumpTables = 0 ;
86
97
98
+ MachineJumpTableInfo *MJTI = MF.getJumpTableInfo ();
99
+
87
100
// Jump table could be used by either terminating instructions or
88
101
// non-terminating ones, so we walk all instructions and use
89
102
// `MachineOperand::isJTI()` to identify jump table operands.
@@ -92,63 +105,55 @@ bool StaticDataSplitter::splitJumpTablesWithProfiles(
92
105
for (const auto &MBB : MF) {
93
106
for (const MachineInstr &I : MBB) {
94
107
for (const MachineOperand &Op : I.operands ()) {
95
- if (!Op.isJTI ())
96
- continue ;
97
- const int JTI = Op.getIndex ();
98
- // This is not a source block of jump table.
99
- if (JTI == -1 )
100
- continue ;
101
-
102
- auto Hotness = MachineFunctionDataHotness::Hot;
103
-
104
- // Hotness is based on source basic block hotness.
105
- // TODO: PSI APIs are about instruction hotness. Introduce API for data
106
- // access hotness.
107
- if (PSI->isColdBlock (&MBB, MBFI))
108
- Hotness = MachineFunctionDataHotness::Cold;
109
-
110
- if (MJTI.updateJumpTableEntryHotness (JTI, Hotness))
111
- ++NumChangedJumpTables;
108
+ if (Op.isJTI ()) {
109
+ assert (MJTI != nullptr && " Jump table info is not available." );
110
+ const int JTI = Op.getIndex ();
111
+ // This is not a source block of jump table.
112
+ if (JTI == -1 )
113
+ continue ;
114
+
115
+ auto Hotness = MachineFunctionDataHotness::Hot;
116
+
117
+ // Hotness is based on source basic block hotness.
118
+ // TODO: PSI APIs are about instruction hotness. Introduce API for
119
+ // data access hotness.
120
+ if (PSI->isColdBlock (&MBB, MBFI))
121
+ Hotness = MachineFunctionDataHotness::Cold;
122
+
123
+ if (MJTI->updateJumpTableEntryHotness (JTI, Hotness))
124
+ ++NumChangedJumpTables;
125
+ }
112
126
}
113
127
}
114
128
}
115
129
return NumChangedJumpTables > 0 ;
116
130
}
117
131
118
- bool StaticDataSplitter::splitJumpTables (MachineFunction &MF) {
119
- MachineJumpTableInfo *MJTI = MF.getJumpTableInfo ();
120
- if (!MJTI || MJTI->getJumpTables ().empty ())
121
- return false ;
132
+ void StaticDataSplitter::updateStatsWithProfiles (const MachineFunction &MF) {
133
+ if (!AreStatisticsEnabled ())
134
+ return ;
122
135
123
- const bool ProfileAvailable = PSI && PSI->hasProfileSummary () && MBFI &&
124
- MF.getFunction ().hasProfileData ();
125
- auto statOnExit = llvm::make_scope_exit ([&] {
126
- if (!AreStatisticsEnabled ())
127
- return ;
128
-
129
- if (!ProfileAvailable) {
130
- NumUnknownJumpTables += MJTI->getJumpTables ().size ();
131
- return ;
132
- }
133
-
134
- for (size_t JTI = 0 ; JTI < MJTI->getJumpTables ().size (); JTI++) {
135
- auto Hotness = MJTI->getJumpTables ()[JTI].Hotness ;
136
- if (Hotness == MachineFunctionDataHotness::Hot) {
136
+ if (const MachineJumpTableInfo *MJTI = MF.getJumpTableInfo ()) {
137
+ for (const auto &JumpTable : MJTI->getJumpTables ()) {
138
+ if (JumpTable.Hotness == MachineFunctionDataHotness::Hot) {
137
139
++NumHotJumpTables;
138
140
} else {
139
- assert (Hotness == MachineFunctionDataHotness::Cold &&
141
+ assert (JumpTable. Hotness == MachineFunctionDataHotness::Cold &&
140
142
" A jump table is either hot or cold when profile information is "
141
143
" available." );
142
144
++NumColdJumpTables;
143
145
}
144
146
}
145
- });
147
+ }
148
+ }
146
149
147
- // Place jump tables according to block hotness if function has profile data.
148
- if (ProfileAvailable )
149
- return splitJumpTablesWithProfiles (MF, *MJTI) ;
150
+ void StaticDataSplitter::updateStatsWithoutProfiles ( const MachineFunction &MF) {
151
+ if (! AreStatisticsEnabled () )
152
+ return ;
150
153
151
- return true ;
154
+ if (const MachineJumpTableInfo *MJTI = MF.getJumpTableInfo ()) {
155
+ NumUnknownJumpTables += MJTI->getJumpTables ().size ();
156
+ }
152
157
}
153
158
154
159
char StaticDataSplitter::ID = 0 ;
0 commit comments