graph: do not show any warnings on analyzed maps (ref #726)

ctr: revert cvars to it's config value instead of hardcoded values (resolves #722)
This commit is contained in:
jeefo 2025-08-14 19:35:26 +03:00
commit 784ad5e303
No known key found for this signature in database
GPG key ID: D696786B81B667C8
8 changed files with 77 additions and 41 deletions

View file

@ -9,6 +9,12 @@
; NOTE: All changes to this file takes effect only on server restart.
;
;
; Specifies the hostname the bot will attempt to connect to for checking network
; availability and enabling graph download/upload features.
;
CheckConnectivityHost = yapb.jeefo.net
;
; Custom name for C4 model, for servers that replacing C4 model with it's own.
; By default it's "c4.mdl" (the models/ path is omitted), so if you need to use

View file

@ -247,6 +247,8 @@ public:
// load the cs binary in non metamod mode
bool loadCSBinary ();
void constructCSBinaryName (StringArray &libs);
// do post-load stuff
bool postload ();

View file

@ -89,7 +89,7 @@ public:
int32_t storageToBotFile (int32_t options);
// remove all bot related files from disk
void unlinkFromDisk (bool onlyTrainingData);
void unlinkFromDisk (bool onlyTrainingData, bool silenceMessages);
public:
// loading the graph may attempt to recurse loading, with converting or download, reset retry counter

View file

@ -46,6 +46,19 @@ void BotConfig::loadMainConfig (bool isFirstLoad) {
return false;
};
auto storeVarValue = [] (cvar_t *c, StringRef value) {
auto &cvars = game.getCvars ();
for (auto &var : cvars) {
if (var.name == c->name) {
var.init = value;
engfuncs.pfnCvar_DirectSet (c, value.chars ());
break;
}
}
};
String line {};
MemFile file {};
@ -77,16 +90,16 @@ void BotConfig::loadMainConfig (bool isFirstLoad) {
// preserve quota number if it's zero
if (cv_quota.name () == cvar->name && cv_quota.as <int> () <= 0) {
engfuncs.pfnCvar_DirectSet (cvar, value);
storeVarValue (cvar, value);
continue;
}
ctrl.msg ("Bot CVAR '%s' differs from the stored in the config (%s/%s). Ignoring.", cvar->name, cvar->string, value);
// ensure cvar will have old value
engfuncs.pfnCvar_DirectSet (cvar, cvar->string);
storeVarValue (cvar, cvar->string);
}
else {
engfuncs.pfnCvar_DirectSet (cvar, value);
storeVarValue (cvar, value);
}
}
else {
@ -108,12 +121,17 @@ void BotConfig::loadMainConfig (bool isFirstLoad) {
// preload custom config
conf.loadCustomConfig ();
// startup the sockets on windows and check if our host is available
if (isFirstLoad) {
http.startup (conf.fetchCustom ("CheckConnectivityHost"), "Bot is unable to check network availability. Networking features are disabled.");
}
// bind the correct menu key for bot menu...
if (!game.isDedicated ()) {
auto val = cv_bind_menu_key.as <StringRef> ();
if (!val.empty ()) {
game.serverCommand ("bind \"%s\" \"yb menu\"", val);
game.serverCommand ("bind \"%s\" \"%s menu\"", val, product.cmdPri);
}
}
static const bool disableLogWrite = conf.fetchCustom ("DisableLogFile").startsWith ("yes");
@ -698,10 +716,10 @@ void BotConfig::loadCustomConfig () {
{ "ZMDelayCvar", "zp_delay" },
{ "ZMInfectedTeam", "T" },
{ "EnableFakeBotFeatures", "no" },
{ "DisableLogFile", "no" }
{ "DisableLogFile", "no" },
{ "CheckConnectivityHost", "yapb.jeefo.net" }
};
};
setDefaults ();
// has errors ?

View file

@ -636,7 +636,7 @@ int BotControl::cmdNodeErase () {
// prevent accidents when graph are deleted unintentionally
if (arg <StringRef> (iamsure) == "iamsure") {
bstor.unlinkFromDisk (false);
bstor.unlinkFromDisk (false, false);
}
else {
msg ("Please, append \"iamsure\" as parameter to get graph erased from the disk.");
@ -647,7 +647,7 @@ int BotControl::cmdNodeErase () {
int BotControl::cmdNodeEraseTraining () {
enum args { graph_cmd = 1, cmd };
bstor.unlinkFromDisk (true);
bstor.unlinkFromDisk (true, false);
return BotCommandResult::Handled;
}

View file

@ -658,7 +658,7 @@ void ConVar::revert () {
for (const auto &var : cvars) {
if (var.name == ptr->name) {
set (var.initial);
set (var.init.chars ());
break;
}
}
@ -789,41 +789,38 @@ void Game::registerCvars (bool gameVars) {
}
}
bool Game::loadCSBinary () {
StringRef modname = getRunningModName ();
if (modname.empty ()) {
return false;
}
Array <String> libs {};
// construct library suffix
String libSuffix {};
void Game::constructCSBinaryName (StringArray &libs) {
String libSuffix {}; // construct library suffix
if (plat.android) {
libSuffix += "_android";
} else if (plat.psvita) {
}
else if (plat.psvita) {
libSuffix += "_psvita";
}
if (plat.x64) {
if (plat.arm) {
libSuffix += "_arm64";
} else if (plat.ppc) {
}
else if (plat.ppc) {
libSuffix += "_ppc64le";
} else {
}
else {
libSuffix += "_amd64";
}
} else {
}
else {
if (plat.arm) {
// don't want to put whole build.h logic from xash3d, just set whatever is supported by the YaPB
if (plat.android) {
libSuffix += "_armv7l";
} else {
}
else {
libSuffix += "_armv7hf";
}
} else if (!plat.nix && !plat.win && !plat.macos) {
}
else if (!plat.nix && !plat.win && !plat.macos) {
libSuffix += "_i386";
}
}
@ -837,10 +834,21 @@ bool Game::loadCSBinary () {
else
libs.insert (0, { "mp", "cs" });
for (auto &lib: libs) {
for (auto &lib : libs) {
lib += libSuffix;
}
}
}
bool Game::loadCSBinary () {
StringRef modname = getRunningModName ();
if (modname.empty ()) {
return false;
}
StringArray libs {};
constructCSBinaryName (libs);
auto libCheck = [&] (StringRef mod, StringRef dll) {
// try to load gamedll
@ -971,9 +979,6 @@ bool Game::postload () {
// set out user agent for http stuff
http.setUserAgent (strings.format ("%s/%s", product.name, product.version));
// startup the sockets on windows and check if our host is available (hardcoded, yup)
http.startup ("yapb.jeefo.net", "Bot is unable to check network availability. Networking features are disabled.");
// set the app name
plat.setAppName (product.name.chars ());

View file

@ -1829,7 +1829,7 @@ bool BotGraph::loadGraphData () {
}
// notify user about graph problems
if (planner.isPathsCheckFailed ()) {
if (planner.isPathsCheckFailed () && !graph.isAnalyzed ()) {
ctrl.msg ("Warning: Graph data has failed sanity check.");
ctrl.msg ("Warning: Bots will use only shortest-path algo for path finding.");
ctrl.msg ("Warning: This may significantly affect bots behavior on this map.");
@ -2523,6 +2523,8 @@ bool BotGraph::checkNodes (bool teleportPlayer, bool onlyPaths) {
if (test.index != kInvalidNodeIndex) {
if (!exists (test.index)) {
if (showErrors) {
teleport (path);
msg ("Node %d path index %d out of range.", path.number, test.index);
}
teleport (path);
@ -2531,17 +2533,17 @@ bool BotGraph::checkNodes (bool teleportPlayer, bool onlyPaths) {
}
else if (test.index == path.number) {
if (showErrors) {
teleport (path);
msg ("Node %d path index %d points to itself.", path.number, test.index);
}
teleport (path);
return false;
}
}
}
}
if (game.mapIs (MapFlags::HostageRescue)) {
if (!onlyPaths && game.mapIs (MapFlags::HostageRescue)) {
if (rescuePoints == 0) {
msg ("You didn't set a rescue point.");
return false;
@ -2648,10 +2650,10 @@ bool BotGraph::checkNodes (bool teleportPlayer, bool onlyPaths) {
for (const auto &path : m_paths) {
if (!visited[path.number]) {
if (showErrors) {
teleport (path);
msg ("Path broken from node %d to node 0.", path.number);
}
teleport (path);
return false;
}
}

View file

@ -95,7 +95,7 @@ template <typename U> bool BotStorage::load (SmallArray <U> &data, ExtenHeader *
// erase the current graph just in case
auto unlinkIfGraph = [&] () {
if (isGraph) {
unlinkFromDisk (false);
unlinkFromDisk (false, true);
}
};
@ -406,7 +406,7 @@ int32_t BotStorage::storageToBotFile (int32_t options) {
return BotFile::Graph;
}
void BotStorage::unlinkFromDisk (bool onlyTrainingData) {
void BotStorage::unlinkFromDisk (bool onlyTrainingData, bool silenceMessages) {
// this function removes graph file from the hard disk
StringArray unlinkable {};
@ -423,9 +423,12 @@ void BotStorage::unlinkFromDisk (bool onlyTrainingData) {
for (const auto &item : unlinkable) {
if (plat.fileExists (item.chars ())) {
plat.removeFile (item.chars ());
ctrl.msg ("File %s, has been deleted from the hard disk", item);
if (!silenceMessages) {
ctrl.msg ("File %s, has been deleted from the hard disk", item);
}
}
else {
else if (!silenceMessages) {
logger.error ("Unable to open %s", item);
}
}