Get rid of snprintf (except one) with fixed buffers, shorten code

- Use strprintf or vstrprintf instead of snprintf
This commit is contained in:
Wladimir J. van der Laan 2012-05-14 19:53:02 +02:00
parent a6f18e4686
commit 29b79e4c0e
2 changed files with 37 additions and 81 deletions

View File

@ -180,8 +180,6 @@ int GetRandInt(int nMax)
inline int OutputDebugStringF(const char* pszFormat, ...)
{
int ret = 0;
@ -228,68 +226,30 @@ inline int OutputDebugStringF(const char* pszFormat, ...)
{
static CCriticalSection cs_OutputDebugStringF;
// accumulate a line at a time
// accumulate and output a line at a time
{
LOCK(cs_OutputDebugStringF);
static char pszBuffer[50000];
static char* pend;
if (pend == NULL)
pend = pszBuffer;
static std::string buffer;
va_list arg_ptr;
va_start(arg_ptr, pszFormat);
int limit = END(pszBuffer) - pend - 2;
int ret = _vsnprintf(pend, limit, pszFormat, arg_ptr);
buffer += vstrprintf(pszFormat, arg_ptr);
va_end(arg_ptr);
if (ret < 0 || ret >= limit)
int line_start = 0, line_end;
while((line_end = buffer.find('\n', line_start)) != -1)
{
pend = END(pszBuffer) - 2;
*pend++ = '\n';
OutputDebugStringA(buffer.substr(line_start, line_end - line_start).c_str());
line_start = line_end + 1;
}
else
pend += ret;
*pend = '\0';
char* p1 = pszBuffer;
char* p2;
while ((p2 = strchr(p1, '\n')))
{
p2++;
char c = *p2;
*p2 = '\0';
OutputDebugStringA(p1);
*p2 = c;
p1 = p2;
}
if (p1 != pszBuffer)
memmove(pszBuffer, p1, pend - p1 + 1);
pend -= (p1 - pszBuffer);
buffer.erase(0, line_start);
}
}
#endif
return ret;
}
// Safer snprintf
// - prints up to limit-1 characters
// - output string is always null terminated even if limit reached
// - return value is the number of characters actually printed
int my_snprintf(char* buffer, size_t limit, const char* format, ...)
{
if (limit == 0)
return 0;
va_list arg_ptr;
va_start(arg_ptr, format);
int ret = _vsnprintf(buffer, limit, format, arg_ptr);
va_end(arg_ptr);
if (ret < 0 || ret >= (int)limit)
{
ret = limit - 1;
buffer[limit-1] = 0;
}
return ret;
}
string real_strprintf(const std::string &format, int dummy, ...)
string vstrprintf(const std::string &format, va_list ap)
{
char buffer[50000];
char* p = buffer;
@ -298,7 +258,7 @@ string real_strprintf(const std::string &format, int dummy, ...)
loop
{
va_list arg_ptr;
va_start(arg_ptr, dummy);
va_copy(arg_ptr, ap);
ret = _vsnprintf(p, limit, format.c_str(), arg_ptr);
va_end(arg_ptr);
if (ret >= 0 && ret < limit)
@ -316,19 +276,22 @@ string real_strprintf(const std::string &format, int dummy, ...)
return str;
}
string real_strprintf(const std::string &format, int dummy, ...)
{
va_list arg_ptr;
va_start(arg_ptr, dummy);
string str = vstrprintf(format, arg_ptr);
va_end(arg_ptr);
return str;
}
bool error(const char *format, ...)
{
char buffer[50000];
int limit = sizeof(buffer);
va_list arg_ptr;
va_start(arg_ptr, format);
int ret = _vsnprintf(buffer, limit, format, arg_ptr);
std::string str = vstrprintf(format, arg_ptr);
va_end(arg_ptr);
if (ret < 0 || ret >= limit)
{
buffer[limit - 1] = 0;
}
printf("ERROR: %s\n", buffer);
printf("ERROR: %s\n", str.c_str());
return false;
}
@ -756,7 +719,7 @@ bool WildcardMatch(const string& str, const string& mask)
void FormatException(char* pszMessage, std::exception* pex, const char* pszThread)
static std::string FormatException(std::exception* pex, const char* pszThread)
{
#ifdef WIN32
char pszModule[MAX_PATH] = "";
@ -765,37 +728,34 @@ void FormatException(char* pszMessage, std::exception* pex, const char* pszThrea
const char* pszModule = "bitcoin";
#endif
if (pex)
snprintf(pszMessage, 1000,
return strprintf(
"EXCEPTION: %s \n%s \n%s in %s \n", typeid(*pex).name(), pex->what(), pszModule, pszThread);
else
snprintf(pszMessage, 1000,
return strprintf(
"UNKNOWN EXCEPTION \n%s in %s \n", pszModule, pszThread);
}
void LogException(std::exception* pex, const char* pszThread)
{
char pszMessage[10000];
FormatException(pszMessage, pex, pszThread);
printf("\n%s", pszMessage);
std::string message = FormatException(pex, pszThread);
printf("\n%s", message.c_str());
}
void PrintException(std::exception* pex, const char* pszThread)
{
char pszMessage[10000];
FormatException(pszMessage, pex, pszThread);
printf("\n\n************************\n%s\n", pszMessage);
fprintf(stderr, "\n\n************************\n%s\n", pszMessage);
strMiscWarning = pszMessage;
std::string message = FormatException(pex, pszThread);
printf("\n\n************************\n%s\n", message.c_str());
fprintf(stderr, "\n\n************************\n%s\n", message.c_str());
strMiscWarning = message;
throw;
}
void PrintExceptionContinue(std::exception* pex, const char* pszThread)
{
char pszMessage[10000];
FormatException(pszMessage, pex, pszThread);
printf("\n\n************************\n%s\n", pszMessage);
fprintf(stderr, "\n\n************************\n%s\n", pszMessage);
strMiscWarning = pszMessage;
std::string message = FormatException(pex, pszThread);
printf("\n\n************************\n%s\n", message.c_str());
fprintf(stderr, "\n\n************************\n%s\n", message.c_str());
strMiscWarning = message;
}
boost::filesystem::path GetDefaultDataDir()

View File

@ -43,11 +43,6 @@ static const int64 CENT = 1000000;
#define ARRAYLEN(array) (sizeof(array)/sizeof((array)[0]))
#define printf OutputDebugStringF
#ifdef snprintf
#undef snprintf
#endif
#define snprintf my_snprintf
#ifndef PRI64d
#if defined(_MSC_VER) || defined(__MSVCRT__)
#define PRI64d "I64d"
@ -133,6 +128,7 @@ int my_snprintf(char* buffer, size_t limit, const char* format, ...);
*/
std::string real_strprintf(const std::string &format, int dummy, ...);
#define strprintf(format, ...) real_strprintf(format, 0, __VA_ARGS__)
std::string vstrprintf(const std::string &format, va_list ap);
bool error(const char *format, ...);
void LogException(std::exception* pex, const char* pszThread);