diff --git a/ext/crlib b/ext/crlib index 26f9988..18ee233 160000 --- a/ext/crlib +++ b/ext/crlib @@ -1 +1 @@ -Subproject commit 26f99881d660fb86e7ef377cf2e6ee615be30cea +Subproject commit 18ee23308ed9142718b3b2d862dde8d5d34ad320 diff --git a/inc/product.h b/inc/product.h index 4ebeb66..3d0a457 100644 --- a/inc/product.h +++ b/inc/product.h @@ -29,7 +29,7 @@ public: public: StringRef name { "YaPB" }; - StringRef year { __DATE__ + 7 }; + StringRef year { &__DATE__[7] }; StringRef author { "YaPB Project" }; StringRef email { "yapb@jeefo.net" }; StringRef url { "https://yapb.ru/" }; diff --git a/inc/yapb.h b/inc/yapb.h index b36d185..1738a44 100644 --- a/inc/yapb.h +++ b/inc/yapb.h @@ -736,6 +736,7 @@ private: Array m_hostages; // pointer to used hostage entities Array m_routes; // pointer + Array m_goalHistory; // history of selected goals BinaryHeap m_routeQue; Path *m_path {}; // pointer to the current path node @@ -812,6 +813,7 @@ private: bool checkChatKeywords (String &reply); bool isReplyingToChat (); bool isReachableNode (int index); + bool isBannedNode (int index); bool updateLiftHandling (); bool updateLiftStates (); bool canRunHeavyWeight (); @@ -872,7 +874,7 @@ private: void selectWeaponById (int num); void completeTask (); - void executeTasks (); + void tasks (); void trackEnemies (); void choiceFreezetimeEntity (); @@ -1042,6 +1044,7 @@ public: void takeDamage (edict_t *inflictor, int damage, int armor, int bits); void showDebugOverlay (); void newRound (); + void resetPathSearchType (); void enteredBuyZone (int buyState); void pushMsgQueue (int message); void prepareChatMessage (StringRef message); diff --git a/meson.build b/meson.build index d69a34a..62a2f43 100644 --- a/meson.build +++ b/meson.build @@ -161,15 +161,11 @@ if linux or mac or (win32 and (gcc or clang)) '-msse2', '-mfpmath=sse', ] + else + ccflags += '-march=armv8-a+fp+simd' endif if clang and not mac - lld = find_program ('lld', required: false) - - if lld.found () == true - ldflags += '-fuse-ld=' + lld.full_path ().split ('/')[-1] - endif - ldflags += [ '-nostdlib++', '-Wunused-command-line-argument' diff --git a/src/botlib.cpp b/src/botlib.cpp index d5c3546..d5799dc 100644 --- a/src/botlib.cpp +++ b/src/botlib.cpp @@ -1246,17 +1246,7 @@ int Bot::pickBestWeapon (int *vec, int count, int moneySave) { bool needMoreRandomWeapon = (m_personality == Personality::Careful) || (rg.chance (25) && m_personality == Personality::Normal); if (needMoreRandomWeapon) { - auto pick = [] (const float factor) -> float { - union { - unsigned int u; - float f; - } cast {}; - cast.f = factor; - - return (static_cast ((cast.u >> 23) & 0xff) - 127) * 0.3010299956639812f; - }; - - float buyFactor = (m_moneyAmount - static_cast (moneySave)) / (16000.0f - static_cast (moneySave)) * 3.0f; + auto buyFactor = (m_moneyAmount - static_cast (moneySave)) / (16000.0f - static_cast (moneySave)) * 3.0f; if (buyFactor < 1.0f) { buyFactor = 1.0f; @@ -1266,7 +1256,7 @@ int Bot::pickBestWeapon (int *vec, int count, int moneySave) { for (int *begin = vec, *end = vec + count - 1; begin < end; ++begin, --end) { cr::swap (*end, *begin); } - return vec[static_cast (static_cast (count - 1) * pick (rg.get (1.0f, cr::powf (10.0f, buyFactor))) / buyFactor + 0.5f)]; + return vec[static_cast (static_cast (count - 1) * cr::log10 (rg.get (1.0f, cr::powf (10.0f, buyFactor))) / buyFactor + 0.5f)]; } int chance = 95; @@ -3242,13 +3232,13 @@ void Bot::normal_ () { ignoreCollision (); // did we already decide about a goal before? - auto destIndex = graph.exists (getTask ()->data) ? getTask ()->data : findBestGoal (); + auto currIndex = getTask ()->data; + auto destIndex = graph.exists (currIndex) && !isBannedNode (currIndex) ? currIndex : findBestGoal (); // check for existance (this is failover, for i.e. csdm, this should be not true with normal gameplay, only when spawned outside of waypointed area) if (!graph.exists (destIndex)) { destIndex = graph.getFarest (pev->origin, 512.0f); } - m_prevGoalIndex = destIndex; // remember index @@ -3258,7 +3248,7 @@ void Bot::normal_ () { // override with fast path if (game.mapIs (MapFlags::Demolition) && bots.isBombPlanted ()) { - pathSearchType = FindPath::Fast; + pathSearchType = rg.chance (60) ? FindPath::Fast : FindPath::Optimal; } // do pathfinding if it's not the current waypoint @@ -4640,7 +4630,7 @@ void Bot::pickupItem_ () { } } -void Bot::executeTasks () { +void Bot::tasks () { // this is core function that handle task execution auto func = getTask ()->func; @@ -4796,7 +4786,7 @@ void Bot::logic () { avoidGrenades (); // avoid flyings grenades m_isUsingGrenade = false; - executeTasks (); // execute current task + tasks (); // execute current task updateAimDir (); // choose aim direction updateLookAngles (); // and turn to chosen aim direction diff --git a/src/control.cpp b/src/control.cpp index 9c6d17d..1a33ebf 100644 --- a/src/control.cpp +++ b/src/control.cpp @@ -1565,7 +1565,7 @@ bool BotControl::executeCommands () { if (prefix != product.cmdPri && prefix != product.cmdSec) { return false; } - Client &client = util.getClient (game.indexOfPlayer (m_ent)); + auto &client = util.getClient (game.indexOfPlayer (m_ent)); // do not allow to execute stuff for non admins if (m_ent != game.getLocalEntity () && !(client.flags & ClientFlags::Admin)) { diff --git a/src/manager.cpp b/src/manager.cpp index d2ac79d..ae8b684 100644 --- a/src/manager.cpp +++ b/src/manager.cpp @@ -1217,20 +1217,7 @@ void Bot::newRound () { m_team = game.getTeam (ent ()); m_isVIP = false; - switch (m_personality) { - default: - case Personality::Normal: - m_pathType = rg.chance (50) ? FindPath::Optimal : FindPath::Safe; - break; - - case Personality::Rusher: - m_pathType = FindPath::Fast; - break; - - case Personality::Careful: - m_pathType = FindPath::Safe; - break; - } + resetPathSearchType (); // clear all states & tasks m_states = 0; @@ -1390,6 +1377,7 @@ void Bot::newRound () { msg = BotMsg::None; } m_msgQueue.clear (); + m_goalHistory.clear (); // clear last trace for (auto i = 0; i < TraceChannel::Num; ++i) { @@ -1410,6 +1398,23 @@ void Bot::newRound () { m_updateInterval = game.is (GameFlags::Legacy | GameFlags::Xash3D) ? 0.0f : (1.0f / cr::clamp (cv_think_fps.float_ (), 30.0f, 60.0f)); } +void Bot::resetPathSearchType () { + switch (m_personality) { + default: + case Personality::Normal: + m_pathType = rg.chance (50) ? FindPath::Optimal : FindPath::Safe; + break; + + case Personality::Rusher: + m_pathType = rg.chance (75) ? FindPath::Fast : FindPath::Optimal; + break; + + case Personality::Careful: + m_pathType = rg.chance (75) ? FindPath::Safe : FindPath::Optimal; + break; + } +} + void Bot::kill () { // this function kills a bot (not just using ClientKill, but like the CSBot does) // base code courtesy of Lazy (from bots-united forums!) diff --git a/src/navigate.cpp b/src/navigate.cpp index 64733f3..24ea9ad 100644 --- a/src/navigate.cpp +++ b/src/navigate.cpp @@ -12,6 +12,11 @@ ConVar cv_debug_heuristic_type ("yb_debug_heuristic_type", "0", "Selects the heu int Bot::findBestGoal () { + auto pushToHistroy = [&] (int32 goal) -> int32 { + m_goalHistory.push (goal); + return goal; + }; + // chooses a destination (goal) node for a bot if (!bots.isBombPlanted () && m_team == Team::Terrorist && game.mapIs (MapFlags::Demolition)) { int result = kInvalidNodeIndex; @@ -116,7 +121,7 @@ int Bot::findBestGoal () { else if (game.mapIs (MapFlags::Demolition) && m_team == Team::Terrorist && bots.getRoundStartTime () + 10.0f < game.time ()) { // send some terrorists to guard planted bomb if (!m_defendedBomb && bots.isBombPlanted () && getCurrentTaskId () != Task::EscapeFromBomb && getBombTimeleft () >= 15.0) { - return m_chosenGoalIndex = graph.getNearest (graph.getBombOrigin ()); + return pushToHistroy (m_chosenGoalIndex = graph.getNearest (graph.getBombOrigin ())); } } @@ -145,7 +150,7 @@ int Bot::findBestGoal () { if (goalDesire > tacticChoice) { tactic = 3; } - return findGoalPost (tactic, defensiveNodes, offensiveNodes); + return pushToHistroy (findGoalPost (tactic, defensiveNodes, offensiveNodes)); } int Bot::findGoalPost (int tactic, IntArray *defensive, IntArray *offsensive) { @@ -234,16 +239,16 @@ void Bot::postprocessGoals (const IntArray &goals, int result[]) { int searchCount = 0; for (int index = 0; index < 4; ++index) { - int rand = goals.random (); + auto goal = goals.random (); - if (searchCount <= 8 && (m_prevGoalIndex == rand || ((result[0] == rand || result[1] == rand || result[2] == rand || result[3] == rand) && goals.length () > 4)) && !isOccupiedNode (rand)) { + if (searchCount <= 8 && (isBannedNode (goal) || m_prevGoalIndex == goal || ((result[0] == goal || result[1] == goal || result[2] == goal || result[3] == goal) && goals.length () > 4)) && !isOccupiedNode (goal)) { if (index > 0) { index--; } ++searchCount; continue; } - result[index] = rand; + result[index] = goal; } } @@ -1562,7 +1567,7 @@ bool Bot::findBestNearestNode () { } // ignore non-reacheable nodes... - if (!isReachableNode (at)) { + if (!isReachableNode (at) || isBannedNode (at)) { continue; } @@ -1623,6 +1628,7 @@ bool Bot::findBestNearestNode () { if (selected == kInvalidNodeIndex) { selected = findNearestNode (); } + m_goalHistory.push (selected); changePointIndex (selected); return true; @@ -3104,3 +3110,12 @@ bool Bot::isReachableNode (int index) { } return false; } + +bool Bot::isBannedNode (int index) { + for (const auto &node : m_goalHistory) { + if (node == index) { + return true; + } + } + return false; +} diff --git a/vc/yapb.vcxproj b/vc/yapb.vcxproj index 648acb3..8a1299b 100644 --- a/vc/yapb.vcxproj +++ b/vc/yapb.vcxproj @@ -30,6 +30,7 @@ + @@ -89,7 +90,7 @@ DynamicLibrary - v143 + ClangCL false true false @@ -97,7 +98,7 @@ DynamicLibrary false - v143 + ClangCL false false @@ -155,7 +156,7 @@ yapb.h .\debug\inf\yapb.pch false - AssemblyAndSourceCode + NoListing .\debug\asm\ .\debug\obj\ .\debug\inf @@ -170,6 +171,7 @@ true false stdcpp14 + EditAndContinue NDEBUG;%(PreprocessorDefinitions) @@ -231,12 +233,12 @@ .\release\inf\ Level4 true - None + ProgramDatabase CompileAsCpp MultiFile true false - Fast + Precise Full AVXI AVXI @@ -266,7 +268,7 @@ .\release\yapb.dll true user32.dll;ws2_32.dll;%(DelayLoadDLLs) - false + true false Windows true diff --git a/vc/yapb.vcxproj.filters b/vc/yapb.vcxproj.filters index 03ecbd4..caf898c 100644 --- a/vc/yapb.vcxproj.filters +++ b/vc/yapb.vcxproj.filters @@ -150,6 +150,9 @@ inc\ext\crlib + + inc\ext\crlib +