]> git.ipfire.org Git - thirdparty/git.git/blame - compat/snprintf.c
Merge branch 'dz/connect-error-report' into maint
[thirdparty/git.git] / compat / snprintf.c
CommitLineData
c4582f93
MR
1#include "../git-compat-util.h"
2
f4626df5
JS
3/*
4 * The size parameter specifies the available space, i.e. includes
71064e3f
FL
5 * the trailing NUL byte; but Windows's vsnprintf uses the entire
6 * buffer and avoids the trailing NUL, should the buffer be exactly
7 * big enough for the result. Defining SNPRINTF_SIZE_CORR to 1 will
8 * therefore remove 1 byte from the reported buffer size, so we
9 * always have room for a trailing NUL byte.
f4626df5
JS
10 */
11#ifndef SNPRINTF_SIZE_CORR
71064e3f 12#if defined(WIN32) && (!defined(__GNUC__) || __GNUC__ < 4)
f90cf2b9
JS
13#define SNPRINTF_SIZE_CORR 1
14#else
f4626df5
JS
15#define SNPRINTF_SIZE_CORR 0
16#endif
f90cf2b9 17#endif
f4626df5 18
c4582f93
MR
19#undef vsnprintf
20int git_vsnprintf(char *str, size_t maxsize, const char *format, va_list ap)
21{
22 char *s;
f4626df5 23 int ret = -1;
c4582f93 24
f4626df5
JS
25 if (maxsize > 0) {
26 ret = vsnprintf(str, maxsize-SNPRINTF_SIZE_CORR, format, ap);
a81892dd
BC
27 if (ret == maxsize-1)
28 ret = -1;
f4626df5
JS
29 /* Windows does not NUL-terminate if result fills buffer */
30 str[maxsize-1] = 0;
31 }
c4582f93
MR
32 if (ret != -1)
33 return ret;
34
35 s = NULL;
36 if (maxsize < 128)
37 maxsize = 128;
38
39 while (ret == -1) {
40 maxsize *= 4;
41 str = realloc(s, maxsize);
42 if (! str)
43 break;
44 s = str;
f4626df5 45 ret = vsnprintf(str, maxsize-SNPRINTF_SIZE_CORR, format, ap);
a81892dd
BC
46 if (ret == maxsize-1)
47 ret = -1;
c4582f93
MR
48 }
49 free(s);
50 return ret;
51}
52
53int git_snprintf(char *str, size_t maxsize, const char *format, ...)
54{
55 va_list ap;
56 int ret;
57
58 va_start(ap, format);
59 ret = git_vsnprintf(str, maxsize, format, ap);
60 va_end(ap);
61
62 return ret;
63}
64