12345678910111213141516171819202122232425262728293031323334353637383940414243444546474849505152535455565758596061626364656667686970 |
- #include "../git-compat-util.h"
- /*
- * The size parameter specifies the available space, i.e. includes
- * the trailing NUL byte; but Windows's vsnprintf uses the entire
- * buffer and avoids the trailing NUL, should the buffer be exactly
- * big enough for the result. Defining SNPRINTF_SIZE_CORR to 1 will
- * therefore remove 1 byte from the reported buffer size, so we
- * always have room for a trailing NUL byte.
- */
- #ifndef SNPRINTF_SIZE_CORR
- #if defined(WIN32) && (!defined(__GNUC__) || __GNUC__ < 4) && (!defined(_MSC_VER) || _MSC_VER < 1900)
- #define SNPRINTF_SIZE_CORR 1
- #else
- #define SNPRINTF_SIZE_CORR 0
- #endif
- #endif
- #undef vsnprintf
- int git_vsnprintf(char *str, size_t maxsize, const char *format, va_list ap)
- {
- va_list cp;
- char *s;
- int ret = -1;
- if (maxsize > 0) {
- va_copy(cp, ap);
- ret = vsnprintf(str, maxsize-SNPRINTF_SIZE_CORR, format, cp);
- va_end(cp);
- if (ret == maxsize-1)
- ret = -1;
- /* Windows does not NUL-terminate if result fills buffer */
- str[maxsize-1] = 0;
- }
- if (ret != -1)
- return ret;
- s = NULL;
- if (maxsize < 128)
- maxsize = 128;
- while (ret == -1) {
- maxsize *= 4;
- str = realloc(s, maxsize);
- if (! str)
- break;
- s = str;
- va_copy(cp, ap);
- ret = vsnprintf(str, maxsize-SNPRINTF_SIZE_CORR, format, cp);
- va_end(cp);
- if (ret == maxsize-1)
- ret = -1;
- }
- free(s);
- return ret;
- }
- int git_snprintf(char *str, size_t maxsize, const char *format, ...)
- {
- va_list ap;
- int ret;
- va_start(ap, format);
- ret = git_vsnprintf(str, maxsize, format, ap);
- va_end(ap);
- return ret;
- }
|