attempt to fix performance issue with pathfinder and mutexes

This commit is contained in:
Mark Vejvoda 2013-11-10 07:25:52 +00:00
parent 597feb452f
commit 2d4cf315f6
2 changed files with 15 additions and 43 deletions

View File

@ -50,7 +50,7 @@ PathFinder::PathFinder() {
map=NULL; map=NULL;
} }
int PathFinder::getPathFindExtendRefreshNodeCount(FactionState &faction, bool mutexLock) { int PathFinder::getPathFindExtendRefreshNodeCount(FactionState &faction) {
int refreshNodeCount = faction.random.randRange(PathFinder::pathFindExtendRefreshNodeCountMin,PathFinder::pathFindExtendRefreshNodeCountMax); int refreshNodeCount = faction.random.randRange(PathFinder::pathFindExtendRefreshNodeCountMin,PathFinder::pathFindExtendRefreshNodeCountMax);
return refreshNodeCount; return refreshNodeCount;
} }
@ -132,6 +132,11 @@ TravelState PathFinder::findPath(Unit *unit, const Vec2i &finalPos, bool *wasStu
string codeLocation = "1"; string codeLocation = "1";
try { try {
int factionIndex = unit->getFactionIndex();
FactionState &faction = factions.getFactionState(factionIndex);
static string mutexOwnerId = string(__FILE__) + string("_") + intToStr(__LINE__);
MutexSafeWrapper safeMutexPrecache(faction.getMutexPreCache(),mutexOwnerId);
if(map == NULL) { if(map == NULL) {
throw megaglest_runtime_error("map == NULL"); throw megaglest_runtime_error("map == NULL");
} }
@ -436,17 +441,12 @@ TravelState PathFinder::findPath(Unit *unit, const Vec2i &finalPos, bool *wasStu
} }
else { else {
codeLocation = "38"; codeLocation = "38";
int factionIndex = unit->getFactionIndex();
static string mutexOwnerId = string(__FILE__) + string("_") + intToStr(__LINE__);
FactionState &faction = factions.getFactionState(factionIndex);
MutexSafeWrapper safeMutexPreCache(faction.getMutexPreCache(),mutexOwnerId);
if(faction.precachedPath[unit->getId()].size() <= 0) { if(faction.precachedPath[unit->getId()].size() <= 0) {
throw megaglest_runtime_error("factions[unit->getFactionIndex()].precachedPath[unit->getId()].size() <= 0!"); throw megaglest_runtime_error("factions[unit->getFactionIndex()].precachedPath[unit->getId()].size() <= 0!");
} }
pos = faction.precachedPath[unit->getId()][0]; pos = faction.precachedPath[unit->getId()][0];
safeMutexPreCache.ReleaseLock();
codeLocation = "39"; codeLocation = "39";
} }
@ -537,6 +537,9 @@ TravelState PathFinder::aStar(Unit *unit, const Vec2i &targetPos, bool inBailout
string codeLocation = "1"; string codeLocation = "1";
try { try {
int unitFactionIndex = unit->getFactionIndex();
int factionIndex = unit->getFactionIndex();
FactionState &faction = factions.getFactionState(factionIndex);
if(SystemFlags::getSystemSettingType(SystemFlags::debugWorldSynch).enabled == true && frameIndex >= 0) { if(SystemFlags::getSystemSettingType(SystemFlags::debugWorldSynch).enabled == true && frameIndex >= 0) {
char szBuf[8096]=""; char szBuf[8096]="";
@ -568,10 +571,6 @@ TravelState PathFinder::aStar(Unit *unit, const Vec2i &targetPos, bool inBailout
codeLocation = "4"; codeLocation = "4";
UnitPathInterface *path= unit->getPath(); UnitPathInterface *path= unit->getPath();
int unitFactionIndex = unit->getFactionIndex();
int factionIndex = unit->getFactionIndex();
FactionState &faction = factions.getFactionState(factionIndex);
faction.nodePoolCount= 0; faction.nodePoolCount= 0;
faction.openNodesList.clear(); faction.openNodesList.clear();
@ -583,11 +582,7 @@ TravelState PathFinder::aStar(Unit *unit, const Vec2i &targetPos, bool inBailout
if(frameIndex < 0) { if(frameIndex < 0) {
codeLocation = "6"; codeLocation = "6";
static string mutexOwnerId = string(__FILE__) + string("_") + intToStr(__LINE__);
MutexSafeWrapper safeMutexPrecache(faction.getMutexPreCache(),mutexOwnerId);
bool foundPrecacheTravelState = (faction.precachedTravelState.find(unit->getId()) != faction.precachedTravelState.end()); bool foundPrecacheTravelState = (faction.precachedTravelState.find(unit->getId()) != faction.precachedTravelState.end());
safeMutexPrecache.ReleaseLock(true);
if(foundPrecacheTravelState == true) { if(foundPrecacheTravelState == true) {
codeLocation = "7"; codeLocation = "7";
@ -597,26 +592,19 @@ TravelState PathFinder::aStar(Unit *unit, const Vec2i &targetPos, bool inBailout
// unit->logSynchData(extractFileFromDirectoryPath(__FILE__).c_str(),__LINE__,szBuf); // unit->logSynchData(extractFileFromDirectoryPath(__FILE__).c_str(),__LINE__,szBuf);
// } // }
safeMutexPrecache.Lock();
bool foundPrecacheTravelStateIsMoving = (faction.precachedTravelState[unit->getId()] == tsMoving); bool foundPrecacheTravelStateIsMoving = (faction.precachedTravelState[unit->getId()] == tsMoving);
safeMutexPrecache.ReleaseLock(true);
if(foundPrecacheTravelStateIsMoving == true) { if(foundPrecacheTravelStateIsMoving == true) {
codeLocation = "8"; codeLocation = "8";
bool canMoveToCells = true; bool canMoveToCells = true;
Vec2i lastPos = unit->getPos(); Vec2i lastPos = unit->getPos();
safeMutexPrecache.Lock();
int unitPrecachePathSize = (int)faction.precachedPath[unit->getId()].size(); int unitPrecachePathSize = (int)faction.precachedPath[unit->getId()].size();
safeMutexPrecache.ReleaseLock(true);
for(int i=0; i < unitPrecachePathSize; i++) { for(int i=0; i < unitPrecachePathSize; i++) {
codeLocation = "9"; codeLocation = "9";
safeMutexPrecache.Lock();
Vec2i nodePos = faction.precachedPath[unit->getId()][i]; Vec2i nodePos = faction.precachedPath[unit->getId()][i];
safeMutexPrecache.ReleaseLock(true);
if(map->isInside(nodePos) == false || map->isInsideSurface(map->toSurfCoords(nodePos)) == false) { if(map->isInside(nodePos) == false || map->isInsideSurface(map->toSurfCoords(nodePos)) == false) {
throw megaglest_runtime_error("Pathfinder invalid node path position = " + nodePos.getString() + " i = " + intToStr(i)); throw megaglest_runtime_error("Pathfinder invalid node path position = " + nodePos.getString() + " i = " + intToStr(i));
@ -624,7 +612,7 @@ TravelState PathFinder::aStar(Unit *unit, const Vec2i &targetPos, bool inBailout
if(i < unit->getPathFindRefreshCellCount() || if(i < unit->getPathFindRefreshCellCount() ||
(unitPrecachePathSize >= pathFindExtendRefreshForNodeCount && (unitPrecachePathSize >= pathFindExtendRefreshForNodeCount &&
i < getPathFindExtendRefreshNodeCount(faction,false))) { i < getPathFindExtendRefreshNodeCount(faction))) {
codeLocation = "10"; codeLocation = "10";
if(canUnitMoveSoon(unit, lastPos, nodePos) == false) { if(canUnitMoveSoon(unit, lastPos, nodePos) == false) {
@ -644,16 +632,12 @@ TravelState PathFinder::aStar(Unit *unit, const Vec2i &targetPos, bool inBailout
path->clear(); path->clear();
UnitPathBasic *basicPathFinder = dynamic_cast<UnitPathBasic *>(path); UnitPathBasic *basicPathFinder = dynamic_cast<UnitPathBasic *>(path);
safeMutexPrecache.Lock();
int unitPrecachePathSize = (int)faction.precachedPath[unit->getId()].size(); int unitPrecachePathSize = (int)faction.precachedPath[unit->getId()].size();
safeMutexPrecache.ReleaseLock(true);
for(int i=0; i < unitPrecachePathSize; i++) { for(int i=0; i < unitPrecachePathSize; i++) {
codeLocation = "13"; codeLocation = "13";
safeMutexPrecache.Lock();
Vec2i nodePos = faction.precachedPath[unit->getId()][i]; Vec2i nodePos = faction.precachedPath[unit->getId()][i];
safeMutexPrecache.ReleaseLock(true);
if(map->isInside(nodePos) == false || map->isInsideSurface(map->toSurfCoords(nodePos)) == false) { if(map->isInside(nodePos) == false || map->isInsideSurface(map->toSurfCoords(nodePos)) == false) {
throw megaglest_runtime_error("Pathfinder invalid node path position = " + nodePos.getString() + " i = " + intToStr(i)); throw megaglest_runtime_error("Pathfinder invalid node path position = " + nodePos.getString() + " i = " + intToStr(i));
@ -662,7 +646,7 @@ TravelState PathFinder::aStar(Unit *unit, const Vec2i &targetPos, bool inBailout
//if(i < pathFindRefresh || //if(i < pathFindRefresh ||
if(i < unit->getPathFindRefreshCellCount() || if(i < unit->getPathFindRefreshCellCount() ||
(unitPrecachePathSize >= pathFindExtendRefreshForNodeCount && (unitPrecachePathSize >= pathFindExtendRefreshForNodeCount &&
i < getPathFindExtendRefreshNodeCount(faction,false))) { i < getPathFindExtendRefreshNodeCount(faction))) {
codeLocation = "14"; codeLocation = "14";
path->add(nodePos); path->add(nodePos);
} }
@ -677,7 +661,6 @@ TravelState PathFinder::aStar(Unit *unit, const Vec2i &targetPos, bool inBailout
// } // }
codeLocation = "17"; codeLocation = "17";
safeMutexPrecache.Lock();
return faction.precachedTravelState[unit->getId()]; return faction.precachedTravelState[unit->getId()];
} }
else { else {
@ -688,9 +671,7 @@ TravelState PathFinder::aStar(Unit *unit, const Vec2i &targetPos, bool inBailout
else { else {
codeLocation = "19"; codeLocation = "19";
safeMutexPrecache.Lock();
bool foundPrecacheTravelStateIsBlocked = (faction.precachedTravelState[unit->getId()] == tsBlocked); bool foundPrecacheTravelStateIsBlocked = (faction.precachedTravelState[unit->getId()] == tsBlocked);
safeMutexPrecache.ReleaseLock(true);
if(foundPrecacheTravelStateIsBlocked == true) { if(foundPrecacheTravelStateIsBlocked == true) {
codeLocation = "20"; codeLocation = "20";
@ -704,7 +685,6 @@ TravelState PathFinder::aStar(Unit *unit, const Vec2i &targetPos, bool inBailout
// } // }
codeLocation = "21"; codeLocation = "21";
safeMutexPrecache.Lock();
return faction.precachedTravelState[unit->getId()]; return faction.precachedTravelState[unit->getId()];
} }
} }
@ -997,10 +977,6 @@ TravelState PathFinder::aStar(Unit *unit, const Vec2i &targetPos, bool inBailout
currNode= firstNode; currNode= firstNode;
static string mutexOwnerId = string(__FILE__) + string("_") + intToStr(__LINE__);
MutexSafeWrapper safeMutexPreCache(faction.getMutexPreCache(),mutexOwnerId);
safeMutexPreCache.ReleaseLock(true);
for(int i=0; currNode->next != NULL; currNode= currNode->next, i++) { for(int i=0; currNode->next != NULL; currNode= currNode->next, i++) {
codeLocation = "55"; codeLocation = "55";
Vec2i nodePos = currNode->next->pos; Vec2i nodePos = currNode->next->pos;
@ -1013,15 +989,13 @@ TravelState PathFinder::aStar(Unit *unit, const Vec2i &targetPos, bool inBailout
if(frameIndex >= 0) { if(frameIndex >= 0) {
codeLocation = "56"; codeLocation = "56";
safeMutexPreCache.Lock();
faction.precachedPath[unit->getId()].push_back(nodePos); faction.precachedPath[unit->getId()].push_back(nodePos);
safeMutexPreCache.ReleaseLock(true);
} }
else { else {
codeLocation = "57"; codeLocation = "57";
if(i < unit->getPathFindRefreshCellCount() || if(i < unit->getPathFindRefreshCellCount() ||
(whileLoopCount >= pathFindExtendRefreshForNodeCount && (whileLoopCount >= pathFindExtendRefreshForNodeCount &&
i < getPathFindExtendRefreshNodeCount(faction,true))) { i < getPathFindExtendRefreshNodeCount(faction))) {
codeLocation = "58"; codeLocation = "58";
path->add(nodePos); path->add(nodePos);
} }
@ -1071,10 +1045,7 @@ TravelState PathFinder::aStar(Unit *unit, const Vec2i &targetPos, bool inBailout
if(frameIndex >= 0) { if(frameIndex >= 0) {
codeLocation = "61"; codeLocation = "61";
static string mutexOwnerId = string(__FILE__) + string("_") + intToStr(__LINE__);
FactionState &faction = factions.getFactionState(factionIndex); FactionState &faction = factions.getFactionState(factionIndex);
MutexSafeWrapper safeMutexPrecache(faction.getMutexPreCache(),mutexOwnerId);
faction.precachedTravelState[unit->getId()] = ts; faction.precachedTravelState[unit->getId()] = ts;
} }
else { else {

View File

@ -209,7 +209,8 @@ public:
private: private:
void init(); void init();
TravelState aStar(Unit *unit, const Vec2i &finalPos, bool inBailout, int frameIndex, int maxNodeCount=-1,uint32 *searched_node_count=NULL); TravelState aStar(Unit *unit, const Vec2i &finalPos, bool inBailout,
int frameIndex, int maxNodeCount=-1,uint32 *searched_node_count=NULL);
inline static Node *newNode(FactionState &faction, int maxNodeCount) { inline static Node *newNode(FactionState &faction, int maxNodeCount) {
if( faction.nodePoolCount < faction.nodePool.size() && if( faction.nodePoolCount < faction.nodePool.size() &&
faction.nodePoolCount < maxNodeCount) { faction.nodePoolCount < maxNodeCount) {
@ -283,7 +284,7 @@ private:
void processNearestFreePos(const Vec2i &finalPos, int i, int j, int size, void processNearestFreePos(const Vec2i &finalPos, int i, int j, int size,
Field field, int teamIndex,Vec2i unitPos, Vec2i &nearestPos, float &nearestDist); Field field, int teamIndex,Vec2i unitPos, Vec2i &nearestPos, float &nearestDist);
int getPathFindExtendRefreshNodeCount(FactionState &faction, bool mutexLock); int getPathFindExtendRefreshNodeCount(FactionState &faction);
inline bool canUnitMoveSoon(const Unit *unit, const Vec2i &pos1, const Vec2i &pos2) { inline bool canUnitMoveSoon(const Unit *unit, const Vec2i &pos1, const Vec2i &pos2) {
bool result = map->aproxCanMoveSoon(unit, pos1, pos2); bool result = map->aproxCanMoveSoon(unit, pos1, pos2);