Branch data Line data Source code
1 : : /* GLIB - Library of useful routines for C programming
2 : : * Copyright (C) 1995-1997 Peter Mattis, Spencer Kimball and Josh MacDonald
3 : : *
4 : : * SPDX-License-Identifier: LGPL-2.1-or-later
5 : : *
6 : : * This library is free software; you can redistribute it and/or
7 : : * modify it under the terms of the GNU Lesser General Public
8 : : * License as published by the Free Software Foundation; either
9 : : * version 2.1 of the License, or (at your option) any later version.
10 : : *
11 : : * This library is distributed in the hope that it will be useful,
12 : : * but WITHOUT ANY WARRANTY; without even the implied warranty of
13 : : * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
14 : : * Lesser General Public License for more details.
15 : : *
16 : : * You should have received a copy of the GNU Lesser General Public
17 : : * License along with this library; if not, see <http://www.gnu.org/licenses/>.
18 : : */
19 : :
20 : : /*
21 : : * Modified by the GLib Team and others 1997-2000. See the AUTHORS
22 : : * file for a list of people on the GLib Team. See the ChangeLog
23 : : * files for a list of changes. These files are distributed with
24 : : * GLib at ftp://ftp.gtk.org/pub/gtk/.
25 : : */
26 : :
27 : : /*
28 : : * MT safe
29 : : */
30 : :
31 : : #include "config.h"
32 : :
33 : : #include <stdarg.h>
34 : : #include <stdlib.h>
35 : : #include <stdio.h>
36 : : #include <string.h>
37 : : #include <ctype.h>
38 : :
39 : : #include "gstring.h"
40 : : #include "guriprivate.h"
41 : : #include "gprintf.h"
42 : : #include "gutilsprivate.h"
43 : :
44 : :
45 : : /**
46 : : * GString:
47 : : * @str: points to the character data. It may move as text is added.
48 : : * The @str field is null-terminated and so
49 : : * can be used as an ordinary C string.
50 : : * @len: contains the length of the string, not including the
51 : : * terminating nul byte.
52 : : * @allocated_len: the number of bytes that can be stored in the
53 : : * string before it needs to be reallocated. May be larger than @len.
54 : : *
55 : : * A `GString` is an object that handles the memory management of a C string.
56 : : *
57 : : * The emphasis of `GString` is on text, typically UTF-8. Crucially, the "str" member
58 : : * of a `GString` is guaranteed to have a trailing nul character, and it is therefore
59 : : * always safe to call functions such as `strchr()` or `strdup()` on it.
60 : : *
61 : : * However, a `GString` can also hold arbitrary binary data, because it has a "len" member,
62 : : * which includes any possible embedded nul characters in the data. Conceptually then,
63 : : * `GString` is like a `GByteArray` with the addition of many convenience methods for
64 : : * text, and a guaranteed nul terminator.
65 : : */
66 : :
67 : : static void
68 : 609905 : g_string_expand (GString *string,
69 : : gsize len)
70 : : {
71 : : /* Detect potential overflow */
72 : 609905 : if G_UNLIKELY ((G_MAXSIZE - string->len - 1) < len)
73 : 0 : g_error ("adding %" G_GSIZE_FORMAT " to string would overflow", len);
74 : :
75 : 609905 : string->allocated_len = g_nearest_pow (string->len + len + 1);
76 : : /* If the new size is bigger than G_MAXSIZE / 2, only allocate enough
77 : : * memory for this string and don't over-allocate.
78 : : */
79 : 609905 : if (string->allocated_len == 0)
80 : 0 : string->allocated_len = string->len + len + 1;
81 : :
82 : 609905 : string->str = g_realloc (string->str, string->allocated_len);
83 : 609905 : }
84 : :
85 : : static inline void
86 : 12597324 : g_string_maybe_expand (GString *string,
87 : : gsize len)
88 : : {
89 : 12597324 : if (G_UNLIKELY (string->len + len >= string->allocated_len))
90 : 100572 : g_string_expand (string, len);
91 : 12597324 : }
92 : :
93 : : /**
94 : : * g_string_sized_new: (constructor)
95 : : * @dfl_size: the default size of the space allocated to hold the string
96 : : *
97 : : * Creates a new #GString, with enough space for @dfl_size
98 : : * bytes. This is useful if you are going to add a lot of
99 : : * text to the string and don't want it to be reallocated
100 : : * too often.
101 : : *
102 : : * Returns: (transfer full): the new #GString
103 : : */
104 : : GString *
105 : 509333 : g_string_sized_new (gsize dfl_size)
106 : : {
107 : 509333 : GString *string = g_slice_new (GString);
108 : :
109 : 509333 : string->allocated_len = 0;
110 : 509333 : string->len = 0;
111 : 509333 : string->str = NULL;
112 : :
113 : 509333 : g_string_expand (string, MAX (dfl_size, 64));
114 : 509333 : string->str[0] = 0;
115 : :
116 : 509333 : return string;
117 : : }
118 : :
119 : : /**
120 : : * g_string_new: (constructor)
121 : : * @init: (nullable): the initial text to copy into the string, or %NULL to
122 : : * start with an empty string
123 : : *
124 : : * Creates a new #GString, initialized with the given string.
125 : : *
126 : : * Returns: (transfer full): the new #GString
127 : : */
128 : : GString *
129 : 362563 : g_string_new (const gchar *init)
130 : : {
131 : : GString *string;
132 : :
133 : 362563 : if (init == NULL || *init == '\0')
134 : 339180 : string = g_string_sized_new (2);
135 : : else
136 : : {
137 : : size_t len;
138 : :
139 : 23383 : len = strlen (init);
140 : 23383 : string = g_string_sized_new (len + 2);
141 : :
142 : 23383 : g_string_append_len (string, init, len);
143 : : }
144 : :
145 : 362563 : return string;
146 : : }
147 : :
148 : : /**
149 : : * g_string_new_take: (constructor)
150 : : * @init: (nullable) (transfer full): initial text used as the string.
151 : : * Ownership of the string is transferred to the #GString.
152 : : * Passing %NULL creates an empty string.
153 : : *
154 : : * Creates a new #GString, initialized with the given string.
155 : : *
156 : : * After this call, @init belongs to the #GString and may no longer be
157 : : * modified by the caller. The memory of @data has to be dynamically
158 : : * allocated and will eventually be freed with g_free().
159 : : *
160 : : * Returns: (transfer full): the new #GString
161 : : *
162 : : * Since: 2.78
163 : : */
164 : : GString *
165 : 2 : g_string_new_take (gchar *init)
166 : : {
167 : : GString *string;
168 : :
169 : 2 : if (init == NULL)
170 : : {
171 : 1 : return g_string_new (NULL);
172 : : }
173 : :
174 : 1 : string = g_slice_new (GString);
175 : :
176 : 1 : string->str = init;
177 : 1 : string->len = strlen (string->str);
178 : 1 : string->allocated_len = string->len + 1;
179 : :
180 : 1 : return string;
181 : : }
182 : :
183 : : /**
184 : : * g_string_new_len: (constructor)
185 : : * @init: initial contents of the string
186 : : * @len: length of @init to use
187 : : *
188 : : * Creates a new #GString with @len bytes of the @init buffer.
189 : : * Because a length is provided, @init need not be nul-terminated,
190 : : * and can contain embedded nul bytes.
191 : : *
192 : : * Since this function does not stop at nul bytes, it is the caller's
193 : : * responsibility to ensure that @init has at least @len addressable
194 : : * bytes.
195 : : *
196 : : * Returns: (transfer full): a new #GString
197 : : */
198 : : GString *
199 : 18087 : g_string_new_len (const gchar *init,
200 : : gssize len)
201 : : {
202 : : GString *string;
203 : :
204 : 18087 : if (len < 0)
205 : 148 : return g_string_new (init);
206 : : else
207 : : {
208 : 17939 : string = g_string_sized_new (len);
209 : :
210 : 17939 : if (init)
211 : : g_string_append_len (string, init, len);
212 : :
213 : 17939 : return string;
214 : : }
215 : : }
216 : :
217 : : /**
218 : : * g_string_free:
219 : : * @string: (transfer full): a #GString
220 : : * @free_segment: if %TRUE, the actual character data is freed as well
221 : : *
222 : : * Frees the memory allocated for the #GString.
223 : : * If @free_segment is %TRUE it also frees the character data. If
224 : : * it's %FALSE, the caller gains ownership of the buffer and must
225 : : * free it after use with g_free().
226 : : *
227 : : * Instead of passing %FALSE to this function, consider using
228 : : * g_string_free_and_steal().
229 : : *
230 : : * Returns: (nullable): the character data of @string
231 : : * (i.e. %NULL if @free_segment is %TRUE)
232 : : */
233 : : gchar *
234 : 508832 : (g_string_free) (GString *string,
235 : : gboolean free_segment)
236 : : {
237 : : gchar *segment;
238 : :
239 : 508832 : g_return_val_if_fail (string != NULL, NULL);
240 : :
241 : 508832 : if (free_segment)
242 : : {
243 : 210683 : g_free (string->str);
244 : 210683 : segment = NULL;
245 : : }
246 : : else
247 : 298149 : segment = string->str;
248 : :
249 : 508832 : g_slice_free (GString, string);
250 : :
251 : 508832 : return segment;
252 : : }
253 : :
254 : : /**
255 : : * g_string_free_and_steal:
256 : : * @string: (transfer full): a #GString
257 : : *
258 : : * Frees the memory allocated for the #GString.
259 : : *
260 : : * The caller gains ownership of the buffer and
261 : : * must free it after use with g_free().
262 : : *
263 : : * Returns: (transfer full): the character data of @string
264 : : *
265 : : * Since: 2.76
266 : : */
267 : : gchar *
268 : 298135 : g_string_free_and_steal (GString *string)
269 : : {
270 : 298135 : return (g_string_free) (string, FALSE);
271 : : }
272 : :
273 : : /**
274 : : * g_string_free_to_bytes:
275 : : * @string: (transfer full): a #GString
276 : : *
277 : : * Transfers ownership of the contents of @string to a newly allocated
278 : : * #GBytes. The #GString structure itself is deallocated, and it is
279 : : * therefore invalid to use @string after invoking this function.
280 : : *
281 : : * Note that while #GString ensures that its buffer always has a
282 : : * trailing nul character (not reflected in its "len"), the returned
283 : : * #GBytes does not include this extra nul; i.e. it has length exactly
284 : : * equal to the "len" member.
285 : : *
286 : : * Returns: (transfer full): A newly allocated #GBytes containing contents of @string; @string itself is freed
287 : : * Since: 2.34
288 : : */
289 : : GBytes*
290 : 1 : g_string_free_to_bytes (GString *string)
291 : : {
292 : : gsize len;
293 : : gchar *buf;
294 : :
295 : 1 : g_return_val_if_fail (string != NULL, NULL);
296 : :
297 : 1 : len = string->len;
298 : :
299 : 1 : buf = g_string_free (string, FALSE);
300 : :
301 : 1 : return g_bytes_new_take (buf, len);
302 : : }
303 : :
304 : : /**
305 : : * g_string_equal:
306 : : * @v: a #GString
307 : : * @v2: another #GString
308 : : *
309 : : * Compares two strings for equality, returning %TRUE if they are equal.
310 : : * For use with #GHashTable.
311 : : *
312 : : * Returns: %TRUE if the strings are the same length and contain the
313 : : * same bytes
314 : : */
315 : : gboolean
316 : 27 : g_string_equal (const GString *v,
317 : : const GString *v2)
318 : : {
319 : : gchar *p, *q;
320 : 27 : GString *string1 = (GString *) v;
321 : 27 : GString *string2 = (GString *) v2;
322 : 27 : gsize i = string1->len;
323 : :
324 : 27 : if (i != string2->len)
325 : 2 : return FALSE;
326 : :
327 : 25 : p = string1->str;
328 : 25 : q = string2->str;
329 : 172 : while (i)
330 : : {
331 : 148 : if (*p != *q)
332 : 1 : return FALSE;
333 : 147 : p++;
334 : 147 : q++;
335 : 147 : i--;
336 : : }
337 : 24 : return TRUE;
338 : : }
339 : :
340 : : /**
341 : : * g_string_hash:
342 : : * @str: a string to hash
343 : : *
344 : : * Creates a hash code for @str; for use with #GHashTable.
345 : : *
346 : : * Returns: hash code for @str
347 : : */
348 : : guint
349 : 40 : g_string_hash (const GString *str)
350 : : {
351 : 40 : const gchar *p = str->str;
352 : 40 : gsize n = str->len;
353 : 40 : guint h = 0;
354 : :
355 : : /* 31 bit hash function */
356 : 280 : while (n--)
357 : : {
358 : 240 : h = (h << 5) - h + *p;
359 : 240 : p++;
360 : : }
361 : :
362 : 40 : return h;
363 : : }
364 : :
365 : : /**
366 : : * g_string_assign:
367 : : * @string: the destination #GString. Its current contents
368 : : * are destroyed.
369 : : * @rval: the string to copy into @string
370 : : *
371 : : * Copies the bytes from a string into a #GString,
372 : : * destroying any previous contents. It is rather like
373 : : * the standard strcpy() function, except that you do not
374 : : * have to worry about having enough space to copy the string.
375 : : *
376 : : * Returns: (transfer none): @string
377 : : */
378 : : GString *
379 : 38 : g_string_assign (GString *string,
380 : : const gchar *rval)
381 : : {
382 : 38 : g_return_val_if_fail (string != NULL, NULL);
383 : 38 : g_return_val_if_fail (rval != NULL, string);
384 : :
385 : : /* Make sure assigning to itself doesn't corrupt the string. */
386 : 38 : if (string->str != rval)
387 : : {
388 : : /* Assigning from substring should be ok, since
389 : : * g_string_truncate() does not reallocate.
390 : : */
391 : : g_string_truncate (string, 0);
392 : : g_string_append (string, rval);
393 : : }
394 : :
395 : 38 : return string;
396 : : }
397 : :
398 : : /**
399 : : * g_string_truncate:
400 : : * @string: a #GString
401 : : * @len: the new size of @string
402 : : *
403 : : * Cuts off the end of the GString, leaving the first @len bytes.
404 : : *
405 : : * Returns: (transfer none): @string
406 : : */
407 : : GString *
408 : 9 : (g_string_truncate) (GString *string,
409 : : gsize len)
410 : : {
411 : 9 : g_return_val_if_fail (string != NULL, NULL);
412 : :
413 : 9 : string->len = MIN (len, string->len);
414 : 9 : string->str[string->len] = 0;
415 : :
416 : 9 : return string;
417 : : }
418 : :
419 : : /**
420 : : * g_string_set_size:
421 : : * @string: a #GString
422 : : * @len: the new length
423 : : *
424 : : * Sets the length of a #GString. If the length is less than
425 : : * the current length, the string will be truncated. If the
426 : : * length is greater than the current length, the contents
427 : : * of the newly added area are undefined. (However, as
428 : : * always, string->str[string->len] will be a nul byte.)
429 : : *
430 : : * Returns: (transfer none): @string
431 : : */
432 : : GString *
433 : 5243 : g_string_set_size (GString *string,
434 : : gsize len)
435 : : {
436 : 5243 : g_return_val_if_fail (string != NULL, NULL);
437 : :
438 : 5243 : if (len >= string->allocated_len)
439 : 0 : g_string_maybe_expand (string, len - string->len);
440 : :
441 : 5243 : string->len = len;
442 : 5243 : string->str[len] = 0;
443 : :
444 : 5243 : return string;
445 : : }
446 : :
447 : : /**
448 : : * g_string_insert_len:
449 : : * @string: a #GString
450 : : * @pos: position in @string where insertion should
451 : : * happen, or -1 for at the end
452 : : * @val: bytes to insert
453 : : * @len: number of bytes of @val to insert, or -1 for all of @val
454 : : *
455 : : * Inserts @len bytes of @val into @string at @pos.
456 : : *
457 : : * If @len is positive, @val may contain embedded nuls and need
458 : : * not be nul-terminated. It is the caller's responsibility to
459 : : * ensure that @val has at least @len addressable bytes.
460 : : *
461 : : * If @len is negative, @val must be nul-terminated and @len
462 : : * is considered to request the entire string length.
463 : : *
464 : : * If @pos is -1, bytes are inserted at the end of the string.
465 : : *
466 : : * Returns: (transfer none): @string
467 : : */
468 : : GString *
469 : 75014 : g_string_insert_len (GString *string,
470 : : gssize pos,
471 : : const gchar *val,
472 : : gssize len)
473 : : {
474 : : gsize len_unsigned, pos_unsigned;
475 : :
476 : 75014 : g_return_val_if_fail (string != NULL, NULL);
477 : 74978 : g_return_val_if_fail (len == 0 || val != NULL, string);
478 : :
479 : 74924 : if (len == 0)
480 : 9 : return string;
481 : :
482 : 74915 : if (len < 0)
483 : 7667 : len = strlen (val);
484 : 74915 : len_unsigned = len;
485 : :
486 : 74915 : if (pos < 0)
487 : 74833 : pos_unsigned = string->len;
488 : : else
489 : : {
490 : 82 : pos_unsigned = pos;
491 : 82 : g_return_val_if_fail (pos_unsigned <= string->len, string);
492 : : }
493 : :
494 : : /* Check whether val represents a substring of string.
495 : : * This test probably violates chapter and verse of the C standards,
496 : : * since ">=" and "<=" are only valid when val really is a substring.
497 : : * In practice, it will work on modern archs.
498 : : */
499 : 74915 : if (G_UNLIKELY (val >= string->str && val <= string->str + string->len))
500 : 1 : {
501 : 1 : gsize offset = val - string->str;
502 : 1 : gsize precount = 0;
503 : :
504 : 1 : g_string_maybe_expand (string, len_unsigned);
505 : 1 : val = string->str + offset;
506 : : /* At this point, val is valid again. */
507 : :
508 : : /* Open up space where we are going to insert. */
509 : 1 : if (pos_unsigned < string->len)
510 : 1 : memmove (string->str + pos_unsigned + len_unsigned,
511 : 1 : string->str + pos_unsigned, string->len - pos_unsigned);
512 : :
513 : : /* Move the source part before the gap, if any. */
514 : 1 : if (offset < pos_unsigned)
515 : : {
516 : 1 : precount = MIN (len_unsigned, pos_unsigned - offset);
517 : 1 : memcpy (string->str + pos_unsigned, val, precount);
518 : : }
519 : :
520 : : /* Move the source part after the gap, if any. */
521 : 1 : if (len_unsigned > precount)
522 : 1 : memcpy (string->str + pos_unsigned + precount,
523 : 1 : val + /* Already moved: */ precount +
524 : : /* Space opened up: */ len_unsigned,
525 : : len_unsigned - precount);
526 : : }
527 : : else
528 : : {
529 : 74914 : g_string_maybe_expand (string, len_unsigned);
530 : :
531 : : /* If we aren't appending at the end, move a hunk
532 : : * of the old string to the end, opening up space
533 : : */
534 : 74914 : if (pos_unsigned < string->len)
535 : 79 : memmove (string->str + pos_unsigned + len_unsigned,
536 : 79 : string->str + pos_unsigned, string->len - pos_unsigned);
537 : :
538 : : /* insert the new string */
539 : 74914 : if (len_unsigned == 1)
540 : 122 : string->str[pos_unsigned] = *val;
541 : : else
542 : 74792 : memcpy (string->str + pos_unsigned, val, len_unsigned);
543 : : }
544 : :
545 : 74915 : string->len += len_unsigned;
546 : :
547 : 74915 : string->str[string->len] = 0;
548 : :
549 : 74915 : return string;
550 : : }
551 : :
552 : : /**
553 : : * g_string_append_uri_escaped:
554 : : * @string: a #GString
555 : : * @unescaped: a string
556 : : * @reserved_chars_allowed: a string of reserved characters allowed
557 : : * to be used, or %NULL
558 : : * @allow_utf8: set %TRUE if the escaped string may include UTF8 characters
559 : : *
560 : : * Appends @unescaped to @string, escaping any characters that
561 : : * are reserved in URIs using URI-style escape sequences.
562 : : *
563 : : * Returns: (transfer none): @string
564 : : *
565 : : * Since: 2.16
566 : : */
567 : : GString *
568 : 2093 : g_string_append_uri_escaped (GString *string,
569 : : const gchar *unescaped,
570 : : const gchar *reserved_chars_allowed,
571 : : gboolean allow_utf8)
572 : : {
573 : 2093 : _uri_encoder (string, (const guchar *) unescaped, strlen (unescaped),
574 : : reserved_chars_allowed, allow_utf8);
575 : 2093 : return string;
576 : : }
577 : :
578 : : /**
579 : : * g_string_append:
580 : : * @string: a #GString
581 : : * @val: the string to append onto the end of @string
582 : : *
583 : : * Adds a string onto the end of a #GString, expanding
584 : : * it if necessary.
585 : : *
586 : : * Returns: (transfer none): @string
587 : : */
588 : : GString *
589 : 36 : (g_string_append) (GString *string,
590 : : const gchar *val)
591 : : {
592 : 36 : return g_string_insert_len (string, -1, val, -1);
593 : : }
594 : :
595 : : /**
596 : : * g_string_append_len:
597 : : * @string: a #GString
598 : : * @val: bytes to append
599 : : * @len: number of bytes of @val to use, or -1 for all of @val
600 : : *
601 : : * Appends @len bytes of @val to @string.
602 : : *
603 : : * If @len is positive, @val may contain embedded nuls and need
604 : : * not be nul-terminated. It is the caller's responsibility to
605 : : * ensure that @val has at least @len addressable bytes.
606 : : *
607 : : * If @len is negative, @val must be nul-terminated and @len
608 : : * is considered to request the entire string length. This
609 : : * makes g_string_append_len() equivalent to g_string_append().
610 : : *
611 : : * Returns: (transfer none): @string
612 : : */
613 : : GString *
614 : 99 : (g_string_append_len) (GString *string,
615 : : const gchar *val,
616 : : gssize len)
617 : : {
618 : 99 : return g_string_insert_len (string, -1, val, len);
619 : : }
620 : :
621 : : /**
622 : : * g_string_append_c:
623 : : * @string: a #GString
624 : : * @c: the byte to append onto the end of @string
625 : : *
626 : : * Adds a byte onto the end of a #GString, expanding
627 : : * it if necessary.
628 : : *
629 : : * Returns: (transfer none): @string
630 : : */
631 : : GString *
632 : 5008 : (g_string_append_c) (GString *string,
633 : : gchar c)
634 : : {
635 : 5008 : g_return_val_if_fail (string != NULL, NULL);
636 : :
637 : 5008 : return g_string_insert_c (string, -1, c);
638 : : }
639 : :
640 : : /**
641 : : * g_string_append_unichar:
642 : : * @string: a #GString
643 : : * @wc: a Unicode character
644 : : *
645 : : * Converts a Unicode character into UTF-8, and appends it
646 : : * to the string.
647 : : *
648 : : * Returns: (transfer none): @string
649 : : */
650 : : GString *
651 : 11015055 : g_string_append_unichar (GString *string,
652 : : gunichar wc)
653 : : {
654 : 11015055 : g_return_val_if_fail (string != NULL, NULL);
655 : :
656 : 11015055 : return g_string_insert_unichar (string, -1, wc);
657 : : }
658 : :
659 : : /**
660 : : * g_string_prepend:
661 : : * @string: a #GString
662 : : * @val: the string to prepend on the start of @string
663 : : *
664 : : * Adds a string on to the start of a #GString,
665 : : * expanding it if necessary.
666 : : *
667 : : * Returns: (transfer none): @string
668 : : */
669 : : GString *
670 : 73 : g_string_prepend (GString *string,
671 : : const gchar *val)
672 : : {
673 : 73 : return g_string_insert_len (string, 0, val, -1);
674 : : }
675 : :
676 : : /**
677 : : * g_string_prepend_len:
678 : : * @string: a #GString
679 : : * @val: bytes to prepend
680 : : * @len: number of bytes in @val to prepend, or -1 for all of @val
681 : : *
682 : : * Prepends @len bytes of @val to @string.
683 : : *
684 : : * If @len is positive, @val may contain embedded nuls and need
685 : : * not be nul-terminated. It is the caller's responsibility to
686 : : * ensure that @val has at least @len addressable bytes.
687 : : *
688 : : * If @len is negative, @val must be nul-terminated and @len
689 : : * is considered to request the entire string length. This
690 : : * makes g_string_prepend_len() equivalent to g_string_prepend().
691 : : *
692 : : * Returns: (transfer none): @string
693 : : */
694 : : GString *
695 : 2 : g_string_prepend_len (GString *string,
696 : : const gchar *val,
697 : : gssize len)
698 : : {
699 : 2 : return g_string_insert_len (string, 0, val, len);
700 : : }
701 : :
702 : : /**
703 : : * g_string_prepend_c:
704 : : * @string: a #GString
705 : : * @c: the byte to prepend on the start of the #GString
706 : : *
707 : : * Adds a byte onto the start of a #GString,
708 : : * expanding it if necessary.
709 : : *
710 : : * Returns: (transfer none): @string
711 : : */
712 : : GString *
713 : 10013 : g_string_prepend_c (GString *string,
714 : : gchar c)
715 : : {
716 : 10013 : g_return_val_if_fail (string != NULL, NULL);
717 : :
718 : 10013 : return g_string_insert_c (string, 0, c);
719 : : }
720 : :
721 : : /**
722 : : * g_string_prepend_unichar:
723 : : * @string: a #GString
724 : : * @wc: a Unicode character
725 : : *
726 : : * Converts a Unicode character into UTF-8, and prepends it
727 : : * to the string.
728 : : *
729 : : * Returns: (transfer none): @string
730 : : */
731 : : GString *
732 : 40 : g_string_prepend_unichar (GString *string,
733 : : gunichar wc)
734 : : {
735 : 40 : g_return_val_if_fail (string != NULL, NULL);
736 : :
737 : 40 : return g_string_insert_unichar (string, 0, wc);
738 : : }
739 : :
740 : : /**
741 : : * g_string_insert:
742 : : * @string: a #GString
743 : : * @pos: the position to insert the copy of the string
744 : : * @val: the string to insert
745 : : *
746 : : * Inserts a copy of a string into a #GString,
747 : : * expanding it if necessary.
748 : : *
749 : : * Returns: (transfer none): @string
750 : : */
751 : : GString *
752 : 4 : g_string_insert (GString *string,
753 : : gssize pos,
754 : : const gchar *val)
755 : : {
756 : 4 : return g_string_insert_len (string, pos, val, -1);
757 : : }
758 : :
759 : : /**
760 : : * g_string_insert_c:
761 : : * @string: a #GString
762 : : * @pos: the position to insert the byte
763 : : * @c: the byte to insert
764 : : *
765 : : * Inserts a byte into a #GString, expanding it if necessary.
766 : : *
767 : : * Returns: (transfer none): @string
768 : : */
769 : : GString *
770 : 17132 : g_string_insert_c (GString *string,
771 : : gssize pos,
772 : : gchar c)
773 : : {
774 : : gsize pos_unsigned;
775 : :
776 : 17132 : g_return_val_if_fail (string != NULL, NULL);
777 : :
778 : 17132 : g_string_maybe_expand (string, 1);
779 : :
780 : 17132 : if (pos < 0)
781 : 7119 : pos = string->len;
782 : : else
783 : 10013 : g_return_val_if_fail ((gsize) pos <= string->len, string);
784 : 17132 : pos_unsigned = pos;
785 : :
786 : : /* If not just an append, move the old stuff */
787 : 17132 : if (pos_unsigned < string->len)
788 : 10013 : memmove (string->str + pos_unsigned + 1,
789 : 10013 : string->str + pos_unsigned, string->len - pos_unsigned);
790 : :
791 : 17132 : string->str[pos_unsigned] = c;
792 : :
793 : 17132 : string->len += 1;
794 : :
795 : 17132 : string->str[string->len] = 0;
796 : :
797 : 17132 : return string;
798 : : }
799 : :
800 : : /**
801 : : * g_string_insert_unichar:
802 : : * @string: a #GString
803 : : * @pos: the position at which to insert character, or -1
804 : : * to append at the end of the string
805 : : * @wc: a Unicode character
806 : : *
807 : : * Converts a Unicode character into UTF-8, and insert it
808 : : * into the string at the given position.
809 : : *
810 : : * Returns: (transfer none): @string
811 : : */
812 : : GString *
813 : 11015105 : g_string_insert_unichar (GString *string,
814 : : gssize pos,
815 : : gunichar wc)
816 : : {
817 : : gint charlen, first, i;
818 : : gchar *dest;
819 : :
820 : 11015105 : g_return_val_if_fail (string != NULL, NULL);
821 : :
822 : : /* Code copied from g_unichar_to_utf() */
823 : 11015105 : if (wc < 0x80)
824 : : {
825 : 10833617 : first = 0;
826 : 10833617 : charlen = 1;
827 : : }
828 : 181488 : else if (wc < 0x800)
829 : : {
830 : 41053 : first = 0xc0;
831 : 41053 : charlen = 2;
832 : : }
833 : 140435 : else if (wc < 0x10000)
834 : : {
835 : 130446 : first = 0xe0;
836 : 130446 : charlen = 3;
837 : : }
838 : 9989 : else if (wc < 0x200000)
839 : : {
840 : 9989 : first = 0xf0;
841 : 9989 : charlen = 4;
842 : : }
843 : 0 : else if (wc < 0x4000000)
844 : : {
845 : 0 : first = 0xf8;
846 : 0 : charlen = 5;
847 : : }
848 : : else
849 : : {
850 : 0 : first = 0xfc;
851 : 0 : charlen = 6;
852 : : }
853 : : /* End of copied code */
854 : :
855 : 11015105 : g_string_maybe_expand (string, charlen);
856 : :
857 : 11015105 : if (pos < 0)
858 : 11015061 : pos = string->len;
859 : : else
860 : 44 : g_return_val_if_fail ((gsize) pos <= string->len, string);
861 : :
862 : : /* If not just an append, move the old stuff */
863 : 11015105 : if ((gsize) pos < string->len)
864 : 44 : memmove (string->str + pos + charlen, string->str + pos, string->len - pos);
865 : :
866 : 11015105 : dest = string->str + pos;
867 : : /* Code copied from g_unichar_to_utf() */
868 : 11347017 : for (i = charlen - 1; i > 0; --i)
869 : : {
870 : 331912 : dest[i] = (wc & 0x3f) | 0x80;
871 : 331912 : wc >>= 6;
872 : : }
873 : 11015105 : dest[0] = wc | first;
874 : : /* End of copied code */
875 : :
876 : 11015105 : string->len += charlen;
877 : :
878 : 11015105 : string->str[string->len] = 0;
879 : :
880 : 11015105 : return string;
881 : : }
882 : :
883 : : /**
884 : : * g_string_overwrite:
885 : : * @string: a #GString
886 : : * @pos: the position at which to start overwriting
887 : : * @val: the string that will overwrite the @string starting at @pos
888 : : *
889 : : * Overwrites part of a string, lengthening it if necessary.
890 : : *
891 : : * Returns: (transfer none): @string
892 : : *
893 : : * Since: 2.14
894 : : */
895 : : GString *
896 : 2 : g_string_overwrite (GString *string,
897 : : gsize pos,
898 : : const gchar *val)
899 : : {
900 : 2 : g_return_val_if_fail (val != NULL, string);
901 : 2 : return g_string_overwrite_len (string, pos, val, strlen (val));
902 : : }
903 : :
904 : : /**
905 : : * g_string_overwrite_len:
906 : : * @string: a #GString
907 : : * @pos: the position at which to start overwriting
908 : : * @val: the string that will overwrite the @string starting at @pos
909 : : * @len: the number of bytes to write from @val
910 : : *
911 : : * Overwrites part of a string, lengthening it if necessary.
912 : : * This function will work with embedded nuls.
913 : : *
914 : : * Returns: (transfer none): @string
915 : : *
916 : : * Since: 2.14
917 : : */
918 : : GString *
919 : 33687 : g_string_overwrite_len (GString *string,
920 : : gsize pos,
921 : : const gchar *val,
922 : : gssize len)
923 : : {
924 : : gsize end;
925 : :
926 : 33687 : g_return_val_if_fail (string != NULL, NULL);
927 : :
928 : 33687 : if (!len)
929 : 1 : return string;
930 : :
931 : 33686 : g_return_val_if_fail (val != NULL, string);
932 : 33686 : g_return_val_if_fail (pos <= string->len, string);
933 : :
934 : 33686 : if (len < 0)
935 : 1 : len = strlen (val);
936 : :
937 : 33686 : end = pos + len;
938 : :
939 : 33686 : if (end > string->len)
940 : 13 : g_string_maybe_expand (string, end - string->len);
941 : :
942 : 33686 : memcpy (string->str + pos, val, len);
943 : :
944 : 33686 : if (end > string->len)
945 : : {
946 : 13 : string->str[end] = '\0';
947 : 13 : string->len = end;
948 : : }
949 : :
950 : 33686 : return string;
951 : : }
952 : :
953 : : /**
954 : : * g_string_erase:
955 : : * @string: a #GString
956 : : * @pos: the position of the content to remove
957 : : * @len: the number of bytes to remove, or -1 to remove all
958 : : * following bytes
959 : : *
960 : : * Removes @len bytes from a #GString, starting at position @pos.
961 : : * The rest of the #GString is shifted down to fill the gap.
962 : : *
963 : : * Returns: (transfer none): @string
964 : : */
965 : : GString *
966 : 68291 : g_string_erase (GString *string,
967 : : gssize pos,
968 : : gssize len)
969 : : {
970 : : gsize len_unsigned, pos_unsigned;
971 : :
972 : 68291 : g_return_val_if_fail (string != NULL, NULL);
973 : 68291 : g_return_val_if_fail (pos >= 0, string);
974 : 68291 : pos_unsigned = pos;
975 : :
976 : 68291 : g_return_val_if_fail (pos_unsigned <= string->len, string);
977 : :
978 : 68291 : if (len < 0)
979 : 44366 : len_unsigned = string->len - pos_unsigned;
980 : : else
981 : : {
982 : 23925 : len_unsigned = len;
983 : 23925 : g_return_val_if_fail (pos_unsigned + len_unsigned <= string->len, string);
984 : :
985 : 23925 : if (pos_unsigned + len_unsigned < string->len)
986 : 20485 : memmove (string->str + pos_unsigned,
987 : 20485 : string->str + pos_unsigned + len_unsigned,
988 : 20485 : string->len - (pos_unsigned + len_unsigned));
989 : : }
990 : :
991 : 68291 : string->len -= len_unsigned;
992 : :
993 : 68291 : string->str[string->len] = 0;
994 : :
995 : 68291 : return string;
996 : : }
997 : :
998 : : /**
999 : : * g_string_replace:
1000 : : * @string: a #GString
1001 : : * @find: the string to find in @string
1002 : : * @replace: the string to insert in place of @find
1003 : : * @limit: the maximum instances of @find to replace with @replace, or `0` for
1004 : : * no limit
1005 : : *
1006 : : * Replaces the string @find with the string @replace in a #GString up to
1007 : : * @limit times. If the number of instances of @find in the #GString is
1008 : : * less than @limit, all instances are replaced. If @limit is `0`,
1009 : : * all instances of @find are replaced.
1010 : : *
1011 : : * If @find is the empty string, since versions 2.69.1 and 2.68.4 the
1012 : : * replacement will be inserted no more than once per possible position
1013 : : * (beginning of string, end of string and between characters). This did
1014 : : * not work correctly in earlier versions.
1015 : : *
1016 : : * Returns: the number of find and replace operations performed.
1017 : : *
1018 : : * Since: 2.68
1019 : : */
1020 : : guint
1021 : 39 : g_string_replace (GString *string,
1022 : : const gchar *find,
1023 : : const gchar *replace,
1024 : : guint limit)
1025 : : {
1026 : 39 : GString *new_string = NULL;
1027 : : gsize f_len, r_len, new_len;
1028 : : gchar *cur, *next, *first, *dst;
1029 : : guint n;
1030 : :
1031 : 39 : g_return_val_if_fail (string != NULL, 0);
1032 : 39 : g_return_val_if_fail (find != NULL, 0);
1033 : 39 : g_return_val_if_fail (replace != NULL, 0);
1034 : :
1035 : 39 : first = strstr (string->str, find);
1036 : :
1037 : 39 : if (first == NULL)
1038 : 17 : return 0;
1039 : :
1040 : 22 : new_len = string->len;
1041 : 22 : f_len = strlen (find);
1042 : 22 : r_len = strlen (replace);
1043 : :
1044 : : /* It removes a lot of branches and possibility for infinite loops if we
1045 : : * handle the case of an empty @find string separately. */
1046 : 22 : if (G_UNLIKELY (f_len == 0))
1047 : : {
1048 : 9 : if (limit == 0 || limit > string->len)
1049 : : {
1050 : 6 : if (string->len > G_MAXSIZE - 1)
1051 : 0 : g_error ("inserting in every position in string would overflow");
1052 : :
1053 : 6 : limit = string->len + 1;
1054 : : }
1055 : :
1056 : 9 : if (r_len > 0 &&
1057 : 8 : (limit > G_MAXSIZE / r_len ||
1058 : 8 : limit * r_len > G_MAXSIZE - string->len))
1059 : 0 : g_error ("inserting in every position in string would overflow");
1060 : :
1061 : 9 : new_len = string->len + limit * r_len;
1062 : 9 : new_string = g_string_sized_new (new_len);
1063 : 39 : for (size_t i = 0; i < limit; i++)
1064 : : {
1065 : 30 : g_string_append_len (new_string, replace, r_len);
1066 : 30 : if (i < string->len)
1067 : 24 : g_string_append_c (new_string, string->str[i]);
1068 : : }
1069 : 9 : if (limit < string->len)
1070 : 2 : g_string_append_len (new_string, string->str + limit, string->len - limit);
1071 : :
1072 : 9 : g_free (string->str);
1073 : 9 : string->allocated_len = new_string->allocated_len;
1074 : 9 : string->len = new_string->len;
1075 : 9 : string->str = g_string_free_and_steal (g_steal_pointer (&new_string));
1076 : :
1077 : 9 : return limit;
1078 : : }
1079 : :
1080 : : /* Potentially do two passes: the first to calculate the length of the new string,
1081 : : * new_len, if it’s going to be longer than the original string; and the second to
1082 : : * do the replacements. The first pass is skipped if the new string is going to be
1083 : : * no longer than the original.
1084 : : *
1085 : : * The second pass calls various g_string_insert_len() (and similar) methods
1086 : : * which would normally potentially reallocate string->str, and hence
1087 : : * invalidate the cur/next/first/dst pointers. Because we’ve pre-calculated
1088 : : * the new_len and do all the string manipulations on new_string, that
1089 : : * shouldn’t happen. This means we scan `string` while modifying
1090 : : * `new_string`. */
1091 : : do
1092 : : {
1093 : 19 : dst = first;
1094 : 19 : cur = first;
1095 : 19 : n = 0;
1096 : 64 : while ((next = strstr (cur, find)) != NULL)
1097 : : {
1098 : 46 : n++;
1099 : :
1100 : 46 : if (r_len <= f_len)
1101 : : {
1102 : 16 : memmove (dst, cur, next - cur);
1103 : 16 : dst += next - cur;
1104 : 16 : memcpy (dst, replace, r_len);
1105 : 16 : dst += r_len;
1106 : : }
1107 : : else
1108 : : {
1109 : 30 : if (new_string == NULL)
1110 : : {
1111 : 15 : new_len += r_len - f_len;
1112 : : }
1113 : : else
1114 : : {
1115 : 15 : g_string_append_len (new_string, cur, next - cur);
1116 : 15 : g_string_append_len (new_string, replace, r_len);
1117 : : }
1118 : : }
1119 : 46 : cur = next + f_len;
1120 : :
1121 : 46 : if (n == limit)
1122 : 1 : break;
1123 : : }
1124 : :
1125 : : /* Append the trailing characters from after the final instance of @find
1126 : : * in the input string. */
1127 : 19 : if (r_len <= f_len)
1128 : : {
1129 : : /* First pass skipped. */
1130 : 7 : gchar *end = string->str + string->len;
1131 : 7 : memmove (dst, cur, end - cur);
1132 : 7 : end = dst + (end - cur);
1133 : 7 : *end = 0;
1134 : 7 : string->len = end - string->str;
1135 : 7 : break;
1136 : : }
1137 : : else
1138 : : {
1139 : 12 : if (new_string == NULL)
1140 : : {
1141 : : /* First pass. */
1142 : 6 : new_string = g_string_sized_new (new_len);
1143 : 6 : g_string_append_len (new_string, string->str, first - string->str);
1144 : : }
1145 : : else
1146 : : {
1147 : : /* Second pass. */
1148 : 6 : g_string_append_len (new_string, cur, (string->str + string->len) - cur);
1149 : 6 : g_free (string->str);
1150 : 6 : string->allocated_len = new_string->allocated_len;
1151 : 6 : string->len = new_string->len;
1152 : 6 : string->str = g_string_free_and_steal (g_steal_pointer (&new_string));
1153 : 6 : break;
1154 : : }
1155 : : }
1156 : : }
1157 : : while (1);
1158 : :
1159 : 13 : return n;
1160 : : }
1161 : :
1162 : : /**
1163 : : * g_string_ascii_down:
1164 : : * @string: a GString
1165 : : *
1166 : : * Converts all uppercase ASCII letters to lowercase ASCII letters.
1167 : : *
1168 : : * Returns: (transfer none): passed-in @string pointer, with all the
1169 : : * uppercase characters converted to lowercase in place,
1170 : : * with semantics that exactly match g_ascii_tolower().
1171 : : */
1172 : : GString *
1173 : 1 : g_string_ascii_down (GString *string)
1174 : : {
1175 : : gchar *s;
1176 : : gint n;
1177 : :
1178 : 1 : g_return_val_if_fail (string != NULL, NULL);
1179 : :
1180 : 1 : n = string->len;
1181 : 1 : s = string->str;
1182 : :
1183 : 21 : while (n)
1184 : : {
1185 : 20 : *s = g_ascii_tolower (*s);
1186 : 20 : s++;
1187 : 20 : n--;
1188 : : }
1189 : :
1190 : 1 : return string;
1191 : : }
1192 : :
1193 : : /**
1194 : : * g_string_ascii_up:
1195 : : * @string: a GString
1196 : : *
1197 : : * Converts all lowercase ASCII letters to uppercase ASCII letters.
1198 : : *
1199 : : * Returns: (transfer none): passed-in @string pointer, with all the
1200 : : * lowercase characters converted to uppercase in place,
1201 : : * with semantics that exactly match g_ascii_toupper().
1202 : : */
1203 : : GString *
1204 : 1 : g_string_ascii_up (GString *string)
1205 : : {
1206 : : gchar *s;
1207 : : gint n;
1208 : :
1209 : 1 : g_return_val_if_fail (string != NULL, NULL);
1210 : :
1211 : 1 : n = string->len;
1212 : 1 : s = string->str;
1213 : :
1214 : 21 : while (n)
1215 : : {
1216 : 20 : *s = g_ascii_toupper (*s);
1217 : 20 : s++;
1218 : 20 : n--;
1219 : : }
1220 : :
1221 : 1 : return string;
1222 : : }
1223 : :
1224 : : /**
1225 : : * g_string_down:
1226 : : * @string: a #GString
1227 : : *
1228 : : * Converts a #GString to lowercase.
1229 : : *
1230 : : * Returns: (transfer none): the #GString
1231 : : *
1232 : : * Deprecated:2.2: This function uses the locale-specific
1233 : : * tolower() function, which is almost never the right thing.
1234 : : * Use g_string_ascii_down() or g_utf8_strdown() instead.
1235 : : */
1236 : : GString *
1237 : 1 : g_string_down (GString *string)
1238 : : {
1239 : : guchar *s;
1240 : : glong n;
1241 : :
1242 : 1 : g_return_val_if_fail (string != NULL, NULL);
1243 : :
1244 : 1 : n = string->len;
1245 : 1 : s = (guchar *) string->str;
1246 : :
1247 : 21 : while (n)
1248 : : {
1249 : 20 : if (isupper (*s))
1250 : 3 : *s = tolower (*s);
1251 : 20 : s++;
1252 : 20 : n--;
1253 : : }
1254 : :
1255 : 1 : return string;
1256 : : }
1257 : :
1258 : : /**
1259 : : * g_string_up:
1260 : : * @string: a #GString
1261 : : *
1262 : : * Converts a #GString to uppercase.
1263 : : *
1264 : : * Returns: (transfer none): @string
1265 : : *
1266 : : * Deprecated:2.2: This function uses the locale-specific
1267 : : * toupper() function, which is almost never the right thing.
1268 : : * Use g_string_ascii_up() or g_utf8_strup() instead.
1269 : : */
1270 : : GString *
1271 : 1 : g_string_up (GString *string)
1272 : : {
1273 : : guchar *s;
1274 : : glong n;
1275 : :
1276 : 1 : g_return_val_if_fail (string != NULL, NULL);
1277 : :
1278 : 1 : n = string->len;
1279 : 1 : s = (guchar *) string->str;
1280 : :
1281 : 21 : while (n)
1282 : : {
1283 : 20 : if (islower (*s))
1284 : 12 : *s = toupper (*s);
1285 : 20 : s++;
1286 : 20 : n--;
1287 : : }
1288 : :
1289 : 1 : return string;
1290 : : }
1291 : :
1292 : : /**
1293 : : * g_string_append_vprintf:
1294 : : * @string: a #GString
1295 : : * @format: (not nullable): the string format. See the printf() documentation
1296 : : * @args: the list of arguments to insert in the output
1297 : : *
1298 : : * Appends a formatted string onto the end of a #GString.
1299 : : * This function is similar to g_string_append_printf()
1300 : : * except that the arguments to the format string are passed
1301 : : * as a va_list.
1302 : : *
1303 : : * Since: 2.14
1304 : : */
1305 : : void
1306 : 1490160 : g_string_append_vprintf (GString *string,
1307 : : const gchar *format,
1308 : : va_list args)
1309 : : {
1310 : : gchar *buf;
1311 : : gint len;
1312 : :
1313 : 1490160 : g_return_if_fail (string != NULL);
1314 : 1490160 : g_return_if_fail (format != NULL);
1315 : :
1316 : 1490160 : len = g_vasprintf (&buf, format, args);
1317 : :
1318 : 1490160 : if (len >= 0)
1319 : : {
1320 : 1490159 : g_string_maybe_expand (string, len);
1321 : 1490159 : memcpy (string->str + string->len, buf, len + 1);
1322 : 1490159 : string->len += len;
1323 : 1490159 : g_free (buf);
1324 : : }
1325 : : else
1326 : : {
1327 : 1 : g_critical ("Failed to append to string: invalid format/args passed to g_vasprintf()");
1328 : : }
1329 : : }
1330 : :
1331 : : /**
1332 : : * g_string_vprintf:
1333 : : * @string: a #GString
1334 : : * @format: (not nullable): the string format. See the printf() documentation
1335 : : * @args: the parameters to insert into the format string
1336 : : *
1337 : : * Writes a formatted string into a #GString.
1338 : : * This function is similar to g_string_printf() except that
1339 : : * the arguments to the format string are passed as a va_list.
1340 : : *
1341 : : * Since: 2.14
1342 : : */
1343 : : void
1344 : 1 : g_string_vprintf (GString *string,
1345 : : const gchar *format,
1346 : : va_list args)
1347 : : {
1348 : : g_string_truncate (string, 0);
1349 : 1 : g_string_append_vprintf (string, format, args);
1350 : 1 : }
1351 : :
1352 : : /**
1353 : : * g_string_sprintf:
1354 : : * @string: a #GString
1355 : : * @format: the string format. See the sprintf() documentation
1356 : : * @...: the parameters to insert into the format string
1357 : : *
1358 : : * Writes a formatted string into a #GString.
1359 : : * This is similar to the standard sprintf() function,
1360 : : * except that the #GString buffer automatically expands
1361 : : * to contain the results. The previous contents of the
1362 : : * #GString are destroyed.
1363 : : *
1364 : : * Deprecated: This function has been renamed to g_string_printf().
1365 : : */
1366 : :
1367 : : /**
1368 : : * g_string_printf:
1369 : : * @string: a #GString
1370 : : * @format: the string format. See the printf() documentation
1371 : : * @...: the parameters to insert into the format string
1372 : : *
1373 : : * Writes a formatted string into a #GString.
1374 : : * This is similar to the standard sprintf() function,
1375 : : * except that the #GString buffer automatically expands
1376 : : * to contain the results. The previous contents of the
1377 : : * #GString are destroyed.
1378 : : */
1379 : : void
1380 : 58 : g_string_printf (GString *string,
1381 : : const gchar *format,
1382 : : ...)
1383 : : {
1384 : : va_list args;
1385 : :
1386 : : g_string_truncate (string, 0);
1387 : :
1388 : 58 : va_start (args, format);
1389 : 58 : g_string_append_vprintf (string, format, args);
1390 : 58 : va_end (args);
1391 : 58 : }
1392 : :
1393 : : /**
1394 : : * g_string_sprintfa:
1395 : : * @string: a #GString
1396 : : * @format: the string format. See the sprintf() documentation
1397 : : * @...: the parameters to insert into the format string
1398 : : *
1399 : : * Appends a formatted string onto the end of a #GString.
1400 : : * This function is similar to g_string_sprintf() except that
1401 : : * the text is appended to the #GString.
1402 : : *
1403 : : * Deprecated: This function has been renamed to g_string_append_printf()
1404 : : */
1405 : :
1406 : : /**
1407 : : * g_string_append_printf:
1408 : : * @string: a #GString
1409 : : * @format: the string format. See the printf() documentation
1410 : : * @...: the parameters to insert into the format string
1411 : : *
1412 : : * Appends a formatted string onto the end of a #GString.
1413 : : * This function is similar to g_string_printf() except
1414 : : * that the text is appended to the #GString.
1415 : : */
1416 : : void
1417 : 1489832 : g_string_append_printf (GString *string,
1418 : : const gchar *format,
1419 : : ...)
1420 : : {
1421 : : va_list args;
1422 : :
1423 : 1489832 : va_start (args, format);
1424 : 1489832 : g_string_append_vprintf (string, format, args);
1425 : 1489832 : va_end (args);
1426 : 1489832 : }
|