improve dead code analysis #45
@@ -6,6 +6,8 @@
|
||||
#include "../CFGraph.h"
|
||||
#include "../IR.h"
|
||||
|
||||
enum class DATA_FLOW_UPD_STATUS { NO_CHANGE = 0, PROPAGATED, GENERATED };
|
||||
|
||||
template <class DataType>
|
||||
class DataFlowAnalysisNode {
|
||||
static const int CNT_NOTINIT = 0;
|
||||
@@ -13,7 +15,6 @@ class DataFlowAnalysisNode {
|
||||
int in_cnt = CNT_NOTINIT, out_cnt = CNT_NOTINIT;
|
||||
|
||||
std::set<int> rollback;
|
||||
std::set<int> ignore_rollback;
|
||||
|
||||
std::set<DataFlowAnalysisNode<DataType>*> prev_blocks;
|
||||
|
||||
@@ -30,7 +31,7 @@ public:
|
||||
virtual bool addOut(const DataType& data) = 0;
|
||||
|
||||
virtual bool updateState() { return false; }
|
||||
virtual bool forwardData(const DataType& data) = 0;
|
||||
virtual DATA_FLOW_UPD_STATUS forwardData(const DataType& data) = 0;
|
||||
|
||||
bool newerThan(const DataFlowAnalysisNode<DataType>* block) const { return out_cnt > block->in_cnt; }
|
||||
|
||||
@@ -42,7 +43,6 @@ public:
|
||||
static int getStartCounter() { return CNT_NOTINIT; }
|
||||
|
||||
std::set<int>& getRollback() { return rollback; }
|
||||
std::set<int>& getIgnoreRollback() { return ignore_rollback; }
|
||||
|
||||
std::set<DataFlowAnalysisNode<DataType>*>& getPrevBlocks() { return prev_blocks; }
|
||||
|
||||
|
||||
@@ -19,7 +19,6 @@ template <class DataType>
|
||||
DataFlowAnalysisNode<DataType>::DataFlowAnalysisNode()
|
||||
{
|
||||
getRollback() = {};
|
||||
getIgnoreRollback() = {};
|
||||
prev_blocks = {};
|
||||
}
|
||||
|
||||
@@ -33,18 +32,21 @@ void DataFlowAnalysisNode<DataType>::doStep()
|
||||
{
|
||||
if (in_cnt < next->out_cnt)
|
||||
{
|
||||
if (next->out_cnt > in_max_cnt)
|
||||
in_max_cnt = next->out_cnt;
|
||||
|
||||
const auto& byOut = next->getOut();
|
||||
bool inserted = addIn( byOut);
|
||||
|
||||
if (inserted)
|
||||
{
|
||||
if (next->out_cnt > in_max_cnt)
|
||||
in_max_cnt = next->out_cnt;
|
||||
|
||||
inserted = forwardData(byOut);
|
||||
auto status = forwardData(byOut);
|
||||
inserted = status != DATA_FLOW_UPD_STATUS::NO_CHANGE;
|
||||
|
||||
if (inserted && next->out_cnt > out_max_cnt)
|
||||
out_max_cnt = next->out_cnt;
|
||||
|
||||
uniq_change |= status == DATA_FLOW_UPD_STATUS::GENERATED;
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -81,12 +83,10 @@ void DataFlowAnalysis<NodeType>::analyze()
|
||||
const auto& jumps = curr_bb->getRollback();
|
||||
if (jumps.size() != 0)
|
||||
{
|
||||
auto& ignored_jumps = curr_bb->getIgnoreRollback();
|
||||
|
||||
bool jump = false;
|
||||
for (const auto& jump_to : jumps)
|
||||
{
|
||||
if (ignored_jumps.insert(jump_to).second && curr_bb->newerThan(nodes[jump_to]))
|
||||
if (curr_bb->newerThan(nodes[jump_to]))
|
||||
{
|
||||
jump = true;
|
||||
curr = jump_to;
|
||||
@@ -94,9 +94,7 @@ void DataFlowAnalysis<NodeType>::analyze()
|
||||
}
|
||||
}
|
||||
|
||||
if (!jump)
|
||||
curr_bb->getIgnoreRollback().clear();
|
||||
else
|
||||
if (jump)
|
||||
continue;
|
||||
}
|
||||
|
||||
|
||||
@@ -107,23 +107,21 @@ namespace SAPFOR
|
||||
|
||||
removed |= (current_set.erase(to_remove) != 0);
|
||||
|
||||
if (!removed)
|
||||
auto it = live_inout.find(to_remove);
|
||||
|
||||
if (it != live_inout.end())
|
||||
{
|
||||
auto it = live_inout.find(to_remove);
|
||||
|
||||
if (it != live_inout.end())
|
||||
auto& dest = opposite_set[to_remove];
|
||||
for (SAPFOR::BasicBlock* bb : it->second)
|
||||
{
|
||||
auto& dest = opposite_set[to_remove];
|
||||
for (SAPFOR::BasicBlock* bb : it->second)
|
||||
{
|
||||
auto find_bb_from_dest = std::lower_bound(dest.begin(), dest.end(), bb);
|
||||
auto find_bb_from_dest = std::lower_bound(dest.begin(), dest.end(), bb);
|
||||
|
||||
if (find_bb_from_dest == dest.end() || *find_bb_from_dest != bb)
|
||||
dest.insert(find_bb_from_dest, bb);
|
||||
}
|
||||
|
||||
removed = true;
|
||||
if (find_bb_from_dest == dest.end() || *find_bb_from_dest != bb)
|
||||
dest.insert(find_bb_from_dest, bb);
|
||||
}
|
||||
|
||||
live_inout.erase(to_remove);
|
||||
removed = true;
|
||||
}
|
||||
|
||||
return removed;
|
||||
@@ -253,7 +251,7 @@ public:
|
||||
return getBlock()->addLiveIn(data);
|
||||
}
|
||||
|
||||
bool forwardData(const map<SAPFOR::Argument*, vector<SAPFOR::BasicBlock*>>& data)
|
||||
DATA_FLOW_UPD_STATUS forwardData(const map<SAPFOR::Argument*, vector<SAPFOR::BasicBlock*>>& data)
|
||||
{
|
||||
bool inserted = false;
|
||||
|
||||
@@ -261,7 +259,7 @@ public:
|
||||
if (live.find(byArg.first) == live.end() && dead.find(byArg.first) == dead.end())
|
||||
inserted |= getBlock()->addLiveIn({ byArg });
|
||||
|
||||
return inserted;
|
||||
return inserted ? DATA_FLOW_UPD_STATUS::PROPAGATED : DATA_FLOW_UPD_STATUS::NO_CHANGE;
|
||||
}
|
||||
|
||||
LiveVarAnalysisNode(SAPFOR::BasicBlock* block, vector<SAPFOR::Argument*>& formal_parameters,
|
||||
@@ -740,7 +738,7 @@ void runLiveVariableAnalysis(const map<FuncInfo*, vector<SAPFOR::BasicBlock*>>&
|
||||
if (exit->addIn(converted))
|
||||
{
|
||||
exit->setInCnt(max_cnt);
|
||||
if (exit->forwardData(converted))
|
||||
if (exit->forwardData(converted) != DATA_FLOW_UPD_STATUS::NO_CHANGE)
|
||||
exit->setOutCnt(max_cnt);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -235,6 +235,15 @@ public:
|
||||
if (!useful_block)
|
||||
updated |= updateNextNotEmpty();
|
||||
|
||||
if (!useful_block)
|
||||
{
|
||||
if (next_notempty_in != next_notempty_out)
|
||||
{
|
||||
updated = true;
|
||||
next_notempty_out = next_notempty_in;
|
||||
}
|
||||
}
|
||||
|
||||
updated |= updateJumpStatus();
|
||||
|
||||
if(updated)
|
||||
@@ -243,9 +252,10 @@ public:
|
||||
return updated;
|
||||
}
|
||||
|
||||
bool forwardData(const map<SAPFOR::Argument*, vector<SAPFOR::BasicBlock*>>& data)
|
||||
DATA_FLOW_UPD_STATUS forwardData(const map<SAPFOR::Argument*, vector<SAPFOR::BasicBlock*>>& data)
|
||||
{
|
||||
bool inserted = false;
|
||||
bool inserted_prop = false, inserted_gen = false;
|
||||
|
||||
SAPFOR::BasicBlock* bb = getBlock();
|
||||
|
||||
set<SAPFOR::Argument*> use, def;
|
||||
@@ -271,7 +281,7 @@ public:
|
||||
if (data_it == data.end())
|
||||
printInternalError(convertFileName(__FILE__).c_str(), __LINE__);
|
||||
|
||||
inserted |= bb->addLiveIn({ *data_it });
|
||||
inserted_prop |= bb->addLiveIn({ *data_it });
|
||||
}
|
||||
else
|
||||
{
|
||||
@@ -285,7 +295,7 @@ public:
|
||||
bb->removeLiveIn(arg);
|
||||
}
|
||||
if(!skip)
|
||||
inserted |= bb->addLiveIn({ { arg, { bb } } });
|
||||
inserted_gen |= bb->addLiveIn({ { arg, { bb } } });
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -298,23 +308,19 @@ public:
|
||||
{
|
||||
useful_block = true;
|
||||
|
||||
inserted = true;
|
||||
inserted_gen = true;
|
||||
next_notempty_out = { this };
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
if (!useful_block)
|
||||
{
|
||||
if (next_notempty_in != next_notempty_out)
|
||||
{
|
||||
inserted = true;
|
||||
next_notempty_out = next_notempty_in;
|
||||
}
|
||||
}
|
||||
if(inserted_gen)
|
||||
return DATA_FLOW_UPD_STATUS::GENERATED;
|
||||
else if(inserted_prop)
|
||||
return DATA_FLOW_UPD_STATUS::PROPAGATED;
|
||||
|
||||
return inserted;
|
||||
return DATA_FLOW_UPD_STATUS::NO_CHANGE;
|
||||
}
|
||||
|
||||
DeadCodeAnalysisNode(SAPFOR::BasicBlock* block,
|
||||
|
||||
Reference in New Issue
Block a user