summaryrefslogtreecommitdiffstats
path: root/gl/snprintf.c
diff options
context:
space:
mode:
Diffstat (limited to 'gl/snprintf.c')
-rw-r--r--gl/snprintf.c41
1 files changed, 8 insertions, 33 deletions
diff --git a/gl/snprintf.c b/gl/snprintf.c
index c1b93562..edeee083 100644
--- a/gl/snprintf.c
+++ b/gl/snprintf.c
@@ -1,6 +1,5 @@
1/* Formatted output to strings. 1/* Formatted output to strings.
2 Copyright (C) 2004, 2006-2024 Free Software Foundation, Inc. 2 Copyright (C) 2004, 2006-2025 Free Software Foundation, Inc.
3 Written by Simon Josefsson and Paul Eggert.
4 3
5 This file is free software: you can redistribute it and/or modify 4 This file is free software: you can redistribute it and/or modify
6 it under the terms of the GNU Lesser General Public License as 5 it under the terms of the GNU Lesser General Public License as
@@ -23,49 +22,25 @@
23#include <errno.h> 22#include <errno.h>
24#include <limits.h> 23#include <limits.h>
25#include <stdarg.h> 24#include <stdarg.h>
26#include <stdlib.h> 25#include <stdint.h>
27#include <string.h>
28 26
29#include "vasnprintf.h"
30
31/* Print formatted output to string STR. Similar to sprintf, but
32 additional length SIZE limit how much is written into STR. Returns
33 string length of formatted string (which may be larger than SIZE).
34 STR may be NULL, in which case nothing will be written. On error,
35 return a negative value. */
36int 27int
37snprintf (char *str, size_t size, const char *format, ...) 28snprintf (char *str, size_t size, const char *format, ...)
38{ 29{
39 char *output;
40 size_t len;
41 size_t lenbuf = size;
42 va_list args; 30 va_list args;
31 ptrdiff_t ret;
43 32
44 va_start (args, format); 33 va_start (args, format);
45 output = vasnprintf (str, &lenbuf, format, args); 34 ret = vsnzprintf (str, size, format, args);
46 len = lenbuf;
47 va_end (args); 35 va_end (args);
48 36
49 if (!output) 37#if PTRDIFF_MAX > INT_MAX
50 return -1; 38 if (ret > INT_MAX)
51
52 if (output != str)
53 {
54 if (size)
55 {
56 size_t pruned_len = (len < size ? len : size - 1);
57 memcpy (str, output, pruned_len);
58 str[pruned_len] = '\0';
59 }
60
61 free (output);
62 }
63
64 if (INT_MAX < len)
65 { 39 {
66 errno = EOVERFLOW; 40 errno = EOVERFLOW;
67 return -1; 41 return -1;
68 } 42 }
43#endif
69 44
70 return len; 45 return ret;
71} 46}