Commit 319e60eb authored by Yoni Fogel's avatar Yoni Fogel

Closes #1508 Write wrapper for [v]snprintf. Mimics linux version.

The windows wrapper will always null terminate.
It will return >= size if overflow, although it might return less than linux on overflow.
When overflowing by more than 1, it just indicates an overflow of 1.

git-svn-id: file:///svn/toku/tokudb@9714 c7de825b-a66e-492c-adef-691d508d4ae1
parent 6a9091ef
......@@ -51,11 +51,6 @@ long long int strtoll(const char *nptr, char **endptr, int base);
long int random(void);
void srandom(unsigned int seed);
//snprintf
//TODO: Put in its own file, or define a snprintf function based on _vsnprintf
//in its own file
#define snprintf(str, size, fmt, ...) _snprintf(str, size, fmt, __VA_ARGS__)
//strtoll has a different name in windows.
#define strtoll _strtoi64
#define strtoull _strtoui64
......@@ -73,6 +68,10 @@ char *realpath(const char *path, char *resolved_path);
int unsetenv(const char *name);
int setenv(const char *name, const char *value, int overwrite);
int vsnprintf(char *str, size_t size, const char *format, va_list ap);
int snprintf(char *str, size_t size, const char *format, ...);
#if defined(__cplusplus)
};
#endif
......
......@@ -12,7 +12,7 @@
void
check_snprintf(int i) {
char buf_before[8];
char target[8];
char target[5];
char buf_after[8];
memset(target, 0xFF, sizeof(target));
memset(buf_before, 0xFF, sizeof(buf_before));
......@@ -23,7 +23,8 @@ check_snprintf(int i) {
for (j = 0; j < i; j++) n *= 10;
int bytes = snprintf(target, sizeof target, "%"PRId64, n);
assert(bytes==i+1);
assert(bytes==i+1 ||
(i+1>=sizeof target && bytes>=sizeof target));
if (bytes>=sizeof target) {
//Overflow prevented by snprintf
assert(target[sizeof target - 1] == '\0');
......
......@@ -214,3 +214,27 @@ toku_os_is_absolute_name(const char* path) {
return (path[0] == '\\' ||
(isalpha(path[0]) && path[1]==':' && path[2]=='\\'));
}
int
vsnprintf(char *str, size_t size, const char *format, va_list ap) {
int r = _vsnprintf(str, size, format, ap);
if (str && size>0) {
str[size-1] = '\0'; //Always null terminate.
if (r<0 && errno==ERANGE);
r = strlen(str)+1; //Mimic linux return value.
//May be too small, but it does
//at least indicate overflow
}
}
return r;
}
int
snprintf(char *str, size_t size, const char *format, ...) {
va_list ap;
va_start(ap, format);
int r = vsnprintf(str, size, format, ap);
va_end(ap);
return r;
}
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment