Forced branches to be first to be scheduled.

git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@18195 91177308-0d34-0410-b5e6-96231b3b80d8
This commit is contained in:
Tanya Lattner
2004-11-24 01:49:10 +00:00
parent 8599d385a2
commit a6ec8f5548
2 changed files with 105 additions and 71 deletions

View File

@@ -23,7 +23,9 @@ bool MSSchedule::insert(MSchedGraphNode *node, int cycle) {
//First, check if the cycle has a spot free to start //First, check if the cycle has a spot free to start
if(schedule.find(cycle) != schedule.end()) { if(schedule.find(cycle) != schedule.end()) {
//Check if we have a free issue slot at this cycle
if (schedule[cycle].size() < numIssue) { if (schedule[cycle].size() < numIssue) {
//Now check if all the resources in their respective cycles are available
if(resourcesFree(node, cycle)) { if(resourcesFree(node, cycle)) {
schedule[cycle].push_back(node); schedule[cycle].push_back(node);
DEBUG(std::cerr << "Found spot in map, and there is an issue slot\n"); DEBUG(std::cerr << "Found spot in map, and there is an issue slot\n");
@@ -44,45 +46,43 @@ bool MSSchedule::insert(MSchedGraphNode *node, int cycle) {
DEBUG(std::cerr << "All issue slots taken\n"); DEBUG(std::cerr << "All issue slots taken\n");
return true; return true;
} }
bool MSSchedule::resourcesFree(MSchedGraphNode *node, int cycle) { bool MSSchedule::resourcesFree(MSchedGraphNode *node, int cycle) {
//Get Resource usage for this instruction //Get Resource usage for this instruction
const TargetSchedInfo *msi = node->getParent()->getTarget()->getSchedInfo(); const TargetSchedInfo *msi = node->getParent()->getTarget()->getSchedInfo();
int currentCycle = cycle; int currentCycle = cycle;
bool success = true; bool success = true;
//map for easy backtracking, resource num at a certain cycle //Get resource usage for this instruction
//std::map<int, int> backtrackMap; InstrRUsage rUsage = msi->getInstrRUsage(node->getInst()->getOpcode());
std::vector<std::vector<resourceId_t> > resources = rUsage.resourcesByCycle;
//Get resource usage for this instruction
InstrRUsage rUsage = msi->getInstrRUsage(node->getInst()->getOpcode()); //Loop over resources in each cycle and increments their usage count
std::vector<std::vector<resourceId_t> > resources = rUsage.resourcesByCycle; for(unsigned i=0; i < resources.size(); ++i) {
for(unsigned j=0; j < resources[i].size(); ++j) {
//Loop over resources in each cycle and increments their usage count
for(unsigned i=0; i < resources.size(); ++i) { //Get Resource to check its availability
for(unsigned j=0; j < resources[i].size(); ++j) { int resourceNum = resources[i][j];
int resourceNum = resources[i][j];
DEBUG(std::cerr << "Attempting to schedule Resource Num: " << resourceNum << " in cycle: " << currentCycle << "\n");
DEBUG(std::cerr << "Attempting to schedule Resource Num: " << resourceNum << " in cycle: " << currentCycle << "\n");
//Check if this resource is available for this cycle //Check if this resource is available for this cycle
std::map<int, std::map<int,int> >::iterator resourcesForCycle = resourceNumPerCycle.find(currentCycle); std::map<int, std::map<int,int> >::iterator resourcesForCycle = resourceNumPerCycle.find(currentCycle);
//First check map of resources for this cycle //First check if map exists for this cycle
if(resourcesForCycle != resourceNumPerCycle.end()) { if(resourcesForCycle != resourceNumPerCycle.end()) {
//A map exists for this cycle, so lets check for the resource //A map exists for this cycle, so lets check for the resource
std::map<int, int>::iterator resourceUse = resourcesForCycle->second.find(resourceNum); std::map<int, int>::iterator resourceUse = resourcesForCycle->second.find(resourceNum);
if(resourceUse != resourcesForCycle->second.end()) { if(resourceUse != resourcesForCycle->second.end()) {
//Check if there are enough of this resource and if so, increase count and move on //Check if there are enough of this resource and if so, increase count and move on
if(resourceUse->second < CPUResource::getCPUResource(resourceNum)->maxNumUsers) { if(resourceUse->second < CPUResource::getCPUResource(resourceNum)->maxNumUsers)
++resourceUse->second; ++resourceUse->second;
//Document that we increased the usage count for this resource at this cycle
}
else { else {
DEBUG(std::cerr << "No resource num " << resourceNum << " available for cycle " << currentCycle << "\n");
success = false; success = false;
} }
} }
@@ -96,50 +96,51 @@ bool MSSchedule::resourcesFree(MSchedGraphNode *node, int cycle) {
std::map<int, int> resourceMap; std::map<int, int> resourceMap;
resourceMap[resourceNum] = 1; resourceMap[resourceNum] = 1;
resourceNumPerCycle[currentCycle] = resourceMap; resourceNumPerCycle[currentCycle] = resourceMap;
} }
if(!success) if(!success)
break; break;
} }
if(!success) if(!success)
break; break;
//Increase cycle
currentCycle++;
}
if(!success) {
int oldCycle = cycle;
DEBUG(std::cerr << "Backtrack\n");
//Get resource usage for this instruction
InstrRUsage rUsage = msi->getInstrRUsage(node->getInst()->getOpcode());
std::vector<std::vector<resourceId_t> > resources = rUsage.resourcesByCycle;
//Loop over resources in each cycle and increments their usage count //Increase cycle
for(unsigned i=0; i < resources.size(); ++i) { currentCycle++;
if(oldCycle < currentCycle) { }
//Check if this resource is available for this cycle if(!success) {
std::map<int, std::map<int,int> >::iterator resourcesForCycle = resourceNumPerCycle.find(oldCycle); int oldCycle = cycle;
if(resourcesForCycle != resourceNumPerCycle.end()) { DEBUG(std::cerr << "Backtrack\n");
for(unsigned j=0; j < resources[i].size(); ++j) { //Get resource usage for this instruction
int resourceNum = resources[i][j]; InstrRUsage rUsage = msi->getInstrRUsage(node->getInst()->getOpcode());
//remove from map std::vector<std::vector<resourceId_t> > resources = rUsage.resourcesByCycle;
std::map<int, int>::iterator resourceUse = resourcesForCycle->second.find(resourceNum);
//assert if not in the map.. since it should be! //Loop over resources in each cycle and increments their usage count
//assert(resourceUse != resourcesForCycle.end() && "Resource should be in map!"); for(unsigned i=0; i < resources.size(); ++i) {
--resourceUse->second; if(oldCycle < currentCycle) {
}
//Check if this resource is available for this cycle
std::map<int, std::map<int,int> >::iterator resourcesForCycle = resourceNumPerCycle.find(oldCycle);
if(resourcesForCycle != resourceNumPerCycle.end()) {
for(unsigned j=0; j < resources[i].size(); ++j) {
int resourceNum = resources[i][j];
//remove from map
std::map<int, int>::iterator resourceUse = resourcesForCycle->second.find(resourceNum);
//assert if not in the map.. since it should be!
//assert(resourceUse != resourcesForCycle.end() && "Resource should be in map!");
--resourceUse->second;
} }
} }
else
break;
oldCycle++;
} }
return false; else
break;
oldCycle++;
} }
return false;
}
return true; return true;
} }

View File

@@ -748,7 +748,11 @@ void ModuloSchedulingPass::findAllReccurrences(MSchedGraphNode *node,
void ModuloSchedulingPass::computePartialOrder() { void ModuloSchedulingPass::computePartialOrder() {
//Only push BA branches onto the final node order, we put other branches after it
//FIXME: Should we really be pushing branches on it a specific order instead of relying
//on BA being there?
std::vector<MSchedGraphNode*> otherBranch;
//Loop over all recurrences and add to our partial order //Loop over all recurrences and add to our partial order
//be sure to remove nodes that are already in the partial order in //be sure to remove nodes that are already in the partial order in
@@ -772,8 +776,15 @@ void ModuloSchedulingPass::computePartialOrder() {
found = true; found = true;
} }
if(!found) { if(!found) {
new_recurrence.insert(*N); if((*N)->isBranch()) {
if((*N)->getInst()->getOpcode() == V9::BA)
FinalNodeOrder.push_back(*N);
else
otherBranch.push_back(*N);
}
else
new_recurrence.insert(*N);
}
if(partialOrder.size() == 0) if(partialOrder.size() == 0)
//For each predecessors, add it to this recurrence ONLY if it is not already in it //For each predecessors, add it to this recurrence ONLY if it is not already in it
for(MSchedGraphNode::pred_iterator P = (*N)->pred_begin(), for(MSchedGraphNode::pred_iterator P = (*N)->pred_begin(),
@@ -791,15 +802,21 @@ void ModuloSchedulingPass::computePartialOrder() {
} }
if(!predFound) if(!predFound)
if(!new_recurrence.count(*P)) if(!new_recurrence.count(*P)) {
new_recurrence.insert(*P); if((*P)->isBranch()) {
if((*P)->getInst()->getOpcode() == V9::BA)
FinalNodeOrder.push_back(*P);
else
otherBranch.push_back(*P);
}
else
new_recurrence.insert(*P);
}
} }
} }
}
} }
if(new_recurrence.size() > 0) if(new_recurrence.size() > 0)
partialOrder.push_back(new_recurrence); partialOrder.push_back(new_recurrence);
} }
@@ -814,8 +831,17 @@ void ModuloSchedulingPass::computePartialOrder() {
if(PO->count(I->first)) if(PO->count(I->first))
found = true; found = true;
} }
if(!found) if(!found) {
lastNodes.insert(I->first); if(I->first->isBranch()) {
if(std::find(FinalNodeOrder.begin(), FinalNodeOrder.end(), I->first) == FinalNodeOrder.end())
if((I->first)->getInst()->getOpcode() == V9::BA)
FinalNodeOrder.push_back(I->first);
else
otherBranch.push_back(I->first);
}
else
lastNodes.insert(I->first);
}
} }
//Break up remaining nodes that are not in the partial order //Break up remaining nodes that are not in the partial order
@@ -829,15 +855,22 @@ void ModuloSchedulingPass::computePartialOrder() {
//if(lastNodes.size() > 0) //if(lastNodes.size() > 0)
//partialOrder.push_back(lastNodes); //partialOrder.push_back(lastNodes);
//Clean up branches by putting them in final order
for(std::vector<MSchedGraphNode*>::iterator I = otherBranch.begin(), E = otherBranch.end(); I != E; ++I)
FinalNodeOrder.push_back(*I);
} }
void ModuloSchedulingPass::connectedComponentSet(MSchedGraphNode *node, std::set<MSchedGraphNode*> &ccSet, std::set<MSchedGraphNode*> &lastNodes) { void ModuloSchedulingPass::connectedComponentSet(MSchedGraphNode *node, std::set<MSchedGraphNode*> &ccSet, std::set<MSchedGraphNode*> &lastNodes) {
//Add to final set //Add to final set
if( !ccSet.count(node) && lastNodes.count(node)) { if( !ccSet.count(node) && lastNodes.count(node)) {
lastNodes.erase(node); lastNodes.erase(node);
ccSet.insert(node); if(node->isBranch())
FinalNodeOrder.push_back(node);
else
ccSet.insert(node);
} }
else else
return; return;
@@ -904,7 +937,7 @@ void ModuloSchedulingPass::orderNodes() {
//Set default order //Set default order
int order = BOTTOM_UP; int order = BOTTOM_UP;
//Loop over all the sets and place them in the final node order //Loop over all the sets and place them in the final node order
for(std::vector<std::set<MSchedGraphNode*> >::iterator CurrentSet = partialOrder.begin(), E= partialOrder.end(); CurrentSet != E; ++CurrentSet) { for(std::vector<std::set<MSchedGraphNode*> >::iterator CurrentSet = partialOrder.begin(), E= partialOrder.end(); CurrentSet != E; ++CurrentSet) {
@@ -1120,7 +1153,7 @@ void ModuloSchedulingPass::computeSchedule() {
int capII = 30; int capII = 30;
while(!success) { while(!success) {
//Loop over the final node order and process each node //Loop over the final node order and process each node
for(std::vector<MSchedGraphNode*>::iterator I = FinalNodeOrder.begin(), for(std::vector<MSchedGraphNode*>::iterator I = FinalNodeOrder.begin(),
E = FinalNodeOrder.end(); I != E; ++I) { E = FinalNodeOrder.end(); I != E; ++I) {
@@ -1170,8 +1203,8 @@ void ModuloSchedulingPass::computeSchedule() {
LateStart = II-1; LateStart = II-1;
} }
else { else {
EarlyStart = II-1; EarlyStart = II-2;
LateStart = II-1; LateStart = 0;
assert( (EarlyStart >= 0) && (LateStart >=0) && "EarlyStart and LateStart must be greater then 0"); assert( (EarlyStart >= 0) && (LateStart >=0) && "EarlyStart and LateStart must be greater then 0");
} }
hasPred = 1; hasPred = 1;