mirror of
https://gitea.wildfiregames.com/0ad/0ad.git
synced 2026-09-21 20:06:40 +00:00
Remove debug_printf filtering
The filter was rarely used. The implementation was overly complex and might have filtered out strings that should have been printed. Tags like "FILES|" have been removed. For the loader a macro `LOADER_LOG` has been introduced.
This commit is contained in:
+2
-91
@@ -1,4 +1,4 @@
|
||||
/* Copyright (C) 2025 Wildfire Games.
|
||||
/* Copyright (C) 2026 Wildfire Games.
|
||||
*
|
||||
* Permission is hereby granted, free of charge, to any person obtaining
|
||||
* a copy of this software and associated documentation files (the
|
||||
@@ -67,88 +67,6 @@ static const StatusDefinition debugStatusDefinitions[] = {
|
||||
};
|
||||
STATUS_ADD_DEFINITIONS(debugStatusDefinitions);
|
||||
|
||||
|
||||
// need to shoehorn printf-style variable params into
|
||||
// the OutputDebugString call.
|
||||
// - don't want to split into multiple calls - would add newlines to output.
|
||||
// - fixing Win32 _vsnprintf to return # characters that would be written,
|
||||
// as required by C99, looks difficult and unnecessary. if any other code
|
||||
// needs that, implement GNU vasprintf.
|
||||
// - fixed size buffers aren't nice, but much simpler than vasprintf-style
|
||||
// allocate+expand_until_it_fits. these calls are for quick debug output,
|
||||
// not loads of data, anyway.
|
||||
|
||||
// rationale: static data instead of std::set to allow setting at any time.
|
||||
// we store FNV hash of tag strings for fast comparison; collisions are
|
||||
// extremely unlikely and can only result in displaying more/less text.
|
||||
static const size_t MAX_TAGS = 20;
|
||||
static u32 tags[MAX_TAGS];
|
||||
static size_t num_tags;
|
||||
|
||||
void debug_filter_add(const char* tag)
|
||||
{
|
||||
const u32 hash = fnv_hash(tag, strlen(tag)*sizeof(tag[0]));
|
||||
|
||||
// make sure it isn't already in the list
|
||||
for(size_t i = 0; i < MAX_TAGS; i++)
|
||||
if(tags[i] == hash)
|
||||
return;
|
||||
|
||||
// too many already?
|
||||
if(num_tags == MAX_TAGS)
|
||||
{
|
||||
DEBUG_WARN_ERR(ERR::LOGIC); // increase MAX_TAGS
|
||||
return;
|
||||
}
|
||||
|
||||
tags[num_tags++] = hash;
|
||||
}
|
||||
|
||||
void debug_filter_remove(const char* tag)
|
||||
{
|
||||
const u32 hash = fnv_hash(tag, strlen(tag)*sizeof(tag[0]));
|
||||
|
||||
for(size_t i = 0; i < MAX_TAGS; i++)
|
||||
{
|
||||
if(tags[i] == hash) // found it
|
||||
{
|
||||
// replace with last element (avoid holes)
|
||||
tags[i] = tags[MAX_TAGS-1];
|
||||
num_tags--;
|
||||
|
||||
// can only happen once, so we're done.
|
||||
return;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
void debug_filter_clear()
|
||||
{
|
||||
std::fill(tags, tags+MAX_TAGS, 0);
|
||||
}
|
||||
|
||||
bool debug_filter_allows(const char* text)
|
||||
{
|
||||
size_t i;
|
||||
for(i = 0; ; i++)
|
||||
{
|
||||
// no | found => no tag => should always be displayed
|
||||
if(text[i] == ' ' || text[i] == '\0')
|
||||
return true;
|
||||
if(text[i] == '|' && i != 0)
|
||||
break;
|
||||
}
|
||||
|
||||
const u32 hash = fnv_hash(text, i*sizeof(text[0]));
|
||||
|
||||
// check if entry allowing this tag is found
|
||||
for(i = 0; i < MAX_TAGS; i++)
|
||||
if(tags[i] == hash)
|
||||
return true;
|
||||
|
||||
return false;
|
||||
}
|
||||
|
||||
#undef debug_printf // allowing #defining it out
|
||||
void debug_printf(const char* fmt, ...)
|
||||
{
|
||||
@@ -161,16 +79,9 @@ void debug_printf(const char* fmt, ...)
|
||||
debug_break(); // poor man's assert - avoid infinite loop because ENSURE also uses debug_printf
|
||||
va_end(ap);
|
||||
|
||||
debug_puts_filtered(buf);
|
||||
debug_puts(buf);
|
||||
}
|
||||
|
||||
void debug_puts_filtered(const char* text)
|
||||
{
|
||||
if(debug_filter_allows(text))
|
||||
debug_puts(text);
|
||||
}
|
||||
|
||||
|
||||
//-----------------------------------------------------------------------------
|
||||
|
||||
Status debug_WriteCrashlog(const wchar_t* text)
|
||||
|
||||
+3
-58
@@ -1,4 +1,4 @@
|
||||
/* Copyright (C) 2025 Wildfire Games.
|
||||
/* Copyright (C) 2026 Wildfire Games.
|
||||
*
|
||||
* Permission is hereby granted, free of charge, to any person obtaining
|
||||
* a copy of this software and associated documentation files (the
|
||||
@@ -63,8 +63,8 @@ extern void debug_break();
|
||||
//-----------------------------------------------------------------------------
|
||||
|
||||
/**
|
||||
* write a formatted string to the debug channel, subject to filtering
|
||||
* (see below). implemented via debug_puts - see performance note there.
|
||||
* write a formatted string to the debug channel. implemented via debug_puts -
|
||||
* see performance note there.
|
||||
*
|
||||
* @param fmt Format string and varargs; see printf.
|
||||
**/
|
||||
@@ -194,61 +194,6 @@ ErrorReaction debug_DisplayError(const wchar_t* description, size_t flags, void*
|
||||
// disallow continue for the error.
|
||||
#define DEBUG_DISPLAY_FATAL_ERROR(description) DEBUG_DISPLAY_ERROR_IMPL(description, DE_NO_CONTINUE)
|
||||
|
||||
|
||||
//
|
||||
// filtering
|
||||
//
|
||||
|
||||
/**
|
||||
* debug output is very useful, but "too much of a good thing can kill you".
|
||||
* we don't want to require different LOGn() macros that are enabled
|
||||
* depending on "debug level", because changing that entails lengthy
|
||||
* compiles and it's too coarse-grained. instead, we require all
|
||||
* strings to start with "tag_string|" (exact case and no quotes;
|
||||
* the alphanumeric-only \<tag_string\> identifies output type).
|
||||
* they are then subject to filtering: only if the tag has been
|
||||
* "added" via debug_filter_add is the appendant string displayed.
|
||||
*
|
||||
* this approach is easiest to implement and is fine because we control
|
||||
* all logging code. LIMODS falls from consideration since it's not
|
||||
* portable and too complex.
|
||||
*
|
||||
* notes:
|
||||
* - filter changes only affect subsequent debug_*printf calls;
|
||||
* output that didn't pass the filter is permanently discarded.
|
||||
* - strings not starting with a tag are always displayed.
|
||||
* - debug_filter_* can be called at any time and from the debugger,
|
||||
* but are not reentrant.
|
||||
*
|
||||
* in future, allow output with the given tag to proceed.
|
||||
* no effect if already added.
|
||||
**/
|
||||
void debug_filter_add(const char* tag);
|
||||
|
||||
/**
|
||||
* in future, discard output with the given tag.
|
||||
* no effect if not currently added.
|
||||
**/
|
||||
void debug_filter_remove(const char* tag);
|
||||
|
||||
/**
|
||||
* clear all filter state; equivalent to debug_filter_remove for
|
||||
* each tag that was debug_filter_add-ed.
|
||||
**/
|
||||
void debug_filter_clear();
|
||||
|
||||
/**
|
||||
* indicate if the given text would be printed.
|
||||
* useful for a series of debug_printfs - avoids needing to add a tag to
|
||||
* each of their format strings.
|
||||
**/
|
||||
bool debug_filter_allows(const char* text);
|
||||
|
||||
/**
|
||||
* call debug_puts if debug_filter_allows allows the string.
|
||||
**/
|
||||
void debug_puts_filtered(const char* text);
|
||||
|
||||
/**
|
||||
* write an error description and all logs into crashlog.txt
|
||||
* (in unicode format).
|
||||
|
||||
@@ -1,4 +1,4 @@
|
||||
/* Copyright (C) 2025 Wildfire Games.
|
||||
/* Copyright (C) 2026 Wildfire Games.
|
||||
*
|
||||
* Permission is hereby granted, free of charge, to any person obtaining
|
||||
* a copy of this software and associated documentation files (the
|
||||
@@ -800,7 +800,11 @@ static Status DetermineSymbolAddress(DWORD id, const SYMBOL_INFOW* sym, const Du
|
||||
|
||||
*pp = (const u8*)(uintptr_t)addr;
|
||||
|
||||
debug_printf("SYM| %s at %p flags=%X dk=%d sym->addr=%I64X fp=%I64x\n", utf8_from_wstring(sym->Name).c_str(), *pp, sym->Flags, dataKind, sym->Address, state.stackFrame->AddrFrame.Offset);
|
||||
#if 0
|
||||
debug_printf("Symbol: %s at %p flags=%X dk=%d sym->addr=%I64X fp=%I64x\n",
|
||||
utf8_from_wstring(sym->Name).c_str(), *pp, sym->Flags, dataKind, sym->Address,
|
||||
state.stackFrame->AddrFrame.Offset);
|
||||
#endif
|
||||
return INFO::OK;
|
||||
}
|
||||
|
||||
|
||||
@@ -667,9 +667,9 @@ void CConsole::SaveHistory()
|
||||
}
|
||||
|
||||
if (g_VFS->CreateFile(m_HistoryFile, {buffer.Data().get(), buffer.Size()}) == INFO::OK)
|
||||
ONCE(debug_printf("FILES| Console command history written to '%s'\n", m_HistoryFile.string8().c_str()));
|
||||
ONCE(debug_printf("Console command history written to '%s'\n", m_HistoryFile.string8().c_str()));
|
||||
else
|
||||
debug_printf("FILES| Failed to write console command history to '%s'\n", m_HistoryFile.string8().c_str());
|
||||
debug_printf("Failed to write console command history to '%s'\n", m_HistoryFile.string8().c_str());
|
||||
}
|
||||
|
||||
static bool isUnprintableChar(SDL_Keysym key)
|
||||
|
||||
@@ -1,4 +1,4 @@
|
||||
/* Copyright (C) 2025 Wildfire Games.
|
||||
/* Copyright (C) 2026 Wildfire Games.
|
||||
* This file is part of 0 A.D.
|
||||
*
|
||||
* 0 A.D. is free software: you can redistribute it and/or modify
|
||||
@@ -294,7 +294,7 @@ namespace
|
||||
std::ofstream OpenLogFile(const wchar_t* filePrefix, const char* logName)
|
||||
{
|
||||
OsPath path{psLogDir() / (filePrefix + g_UniqueLogPostfix + L".html")};
|
||||
debug_printf("FILES| %s written to '%s'\n", logName, path.string8().c_str());
|
||||
debug_printf("%s written to '%s'\n", logName, path.string8().c_str());
|
||||
return std::ofstream{OsString(path), std::ofstream::trunc};
|
||||
}
|
||||
}
|
||||
|
||||
@@ -462,8 +462,6 @@ void EarlyInit()
|
||||
Threading::SetMainThread();
|
||||
|
||||
debug_SetThreadName("main");
|
||||
// add all debug_printf "tags" that we are interested in:
|
||||
debug_filter_add("FILES");
|
||||
|
||||
timer_Init();
|
||||
|
||||
|
||||
@@ -316,7 +316,7 @@ void WriteSystemInfo(Renderer::Backend::IDevice* device, const utsname& un)
|
||||
fclose(f);
|
||||
f = 0;
|
||||
|
||||
debug_printf("FILES| Hardware details written to '%s'\n", pathname.string8().c_str());
|
||||
debug_printf("Hardware details written to '%s'\n", pathname.string8().c_str());
|
||||
}
|
||||
|
||||
} // anonymous namespace
|
||||
|
||||
+12
-3
@@ -1,4 +1,4 @@
|
||||
/* Copyright (C) 2025 Wildfire Games.
|
||||
/* Copyright (C) 2026 Wildfire Games.
|
||||
* This file is part of 0 A.D.
|
||||
*
|
||||
* 0 A.D. is free software: you can redistribute it and/or modify
|
||||
@@ -32,6 +32,12 @@
|
||||
#include <string>
|
||||
#include <utility>
|
||||
|
||||
#if 0
|
||||
#define LOADER_LOG(...) debug_printf(__VA_ARGS__)
|
||||
#else
|
||||
#define LOADER_LOG(...)
|
||||
#endif
|
||||
|
||||
namespace PS::Loader
|
||||
{
|
||||
namespace
|
||||
@@ -221,7 +227,9 @@ ProgressiveLoadResult ProgressiveLoad(double time_budget)
|
||||
// either finished entirely, or failed => remove from queue.
|
||||
if(!timed_out)
|
||||
{
|
||||
debug_printf("LOADER| completed %s in %g ms; estimate was %g ms\n", utf8_from_wstring(lr.description).c_str(), task_elapsed_time*1e3, estimated_duration*1e3);
|
||||
LOADER_LOG("Loader: completed %s in %g ms; estimate was %g ms\n",
|
||||
utf8_from_wstring(lr.description).c_str(), task_elapsed_time*1e3,
|
||||
estimated_duration*1e3);
|
||||
task_elapsed_time = 0.0;
|
||||
estimated_duration_tally += estimated_duration;
|
||||
load_requests.pop_front();
|
||||
@@ -284,7 +292,8 @@ done:
|
||||
if(!load_requests.empty())
|
||||
ret.nextDescription = load_requests.front().description;
|
||||
|
||||
debug_printf("LOADER| returning; desc=%s progress=%d\n", utf8_from_wstring(ret.nextDescription).c_str(), ret.progressPercent);
|
||||
LOADER_LOG("Loader: returning; desc=%s progress=%d\n",
|
||||
utf8_from_wstring(ret.nextDescription).c_str(), ret.progressPercent);
|
||||
|
||||
return ret;
|
||||
}
|
||||
|
||||
@@ -86,7 +86,7 @@ void CReplayLogger::StartGame(JS::MutableHandleValue attribs)
|
||||
Script::SetProperty(rq, attribs, "mods", mods);
|
||||
|
||||
m_Directory = createDateIndexSubdirectory(VisualReplay::GetDirectoryPath());
|
||||
debug_printf("FILES| Replay written to '%s'\n", m_Directory.string8().c_str());
|
||||
debug_printf("Replay written to '%s'\n", m_Directory.string8().c_str());
|
||||
|
||||
m_Stream = new std::ofstream(OsString(m_Directory / L"commands.txt"), std::ofstream::out | std::ofstream::trunc);
|
||||
*m_Stream << "start " << Script::StringifyJSON(rq, attribs, false) << "\n";
|
||||
@@ -137,10 +137,10 @@ void CReplayLogger::SaveMetadata(const CSimulation2& simulation)
|
||||
{
|
||||
stream << Script::StringifyJSON(rq, &metadata, false);
|
||||
stream.close();
|
||||
debug_printf("FILES| Replay metadata written to '%s'\n", fileName.string8().c_str());
|
||||
debug_printf("Replay metadata written to '%s'\n", fileName.string8().c_str());
|
||||
}
|
||||
else
|
||||
debug_printf("FILES| Failed to write replay metadata to '%s'\n", fileName.string8().c_str());
|
||||
debug_printf("Failed to write replay metadata to '%s'\n", fileName.string8().c_str());
|
||||
|
||||
}
|
||||
|
||||
|
||||
@@ -590,12 +590,12 @@ void CUserReporter::SubmitReport(const std::string& type, int version, const std
|
||||
std::ofstream stream(OsString(path), std::ofstream::trunc);
|
||||
if (stream)
|
||||
{
|
||||
debug_printf("FILES| UserReport written to '%s'\n", path.string8().c_str());
|
||||
debug_printf("UserReport written to '%s'\n", path.string8().c_str());
|
||||
stream << dataHumanReadable << std::endl;
|
||||
stream.close();
|
||||
}
|
||||
else
|
||||
debug_printf("FILES| Failed to write UserReport to '%s'\n", path.string8().c_str());
|
||||
debug_printf("Failed to write UserReport to '%s'\n", path.string8().c_str());
|
||||
}
|
||||
|
||||
// If not initialised, discard the report
|
||||
|
||||
@@ -279,10 +279,10 @@ void WriteJSONFile(const Script::Interface& scriptInterface, const std::wstring&
|
||||
{
|
||||
OsPath realPath;
|
||||
g_VFS->GetRealPath(path, realPath, false);
|
||||
debug_printf("FILES| JSON data written to '%s'\n", realPath.string8().c_str());
|
||||
debug_printf("JSON data written to '%s'\n", realPath.string8().c_str());
|
||||
}
|
||||
else
|
||||
debug_printf("FILES| Failed to write JSON data to '%s'\n", path.string8().c_str());
|
||||
debug_printf("Failed to write JSON data to '%s'\n", path.string8().c_str());
|
||||
}
|
||||
|
||||
bool DeleteCampaignSave(const CStrW& filePath)
|
||||
|
||||
Reference in New Issue
Block a user