Coverage Report

Created: 2025-06-13 06:20

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