1 /* GLIB - Library of useful routines for C programming
2 * Copyright (C) 1995-1997 Peter Mattis, Spencer Kimball and Josh MacDonald
4 * This library is free software; you can redistribute it and/or
5 * modify it under the terms of the GNU Library General Public
6 * License as published by the Free Software Foundation; either
7 * version 2 of the License, or (at your option) any later version.
9 * This library is distributed in the hope that it will be useful,
10 * but WITHOUT ANY WARRANTY; without even the implied warranty of
11 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
12 * Library General Public License for more details.
14 * You should have received a copy of the GNU Library General Public
15 * License along with this library; if not, write to the
16 * Free Software Foundation, Inc., 59 Temple Place - Suite 330,
17 * Boston, MA 02111-1307, USA.
21 * Modified by the GLib Team and others 1997-1999. 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/.
45 typedef struct _GRealStringChunk GRealStringChunk;
46 typedef struct _GRealString GRealString;
48 struct _GRealStringChunk
50 GHashTable *const_table;
64 G_LOCK_DEFINE_STATIC (string_mem_chunk);
65 static GMemChunk *string_mem_chunk = NULL;
71 g_str_equal (gconstpointer v1,
74 const gchar *string1 = v1;
75 const gchar *string2 = v2;
77 return strcmp (string1, string2) == 0;
80 /* 31 bit hash function */
82 g_str_hash (gconstpointer key)
88 for (p += 1; *p != '\0'; p++)
89 h = (h << 5) - h + *p;
99 g_string_chunk_new (gint default_size)
101 GRealStringChunk *new_chunk = g_new (GRealStringChunk, 1);
104 while (size < default_size)
107 new_chunk->const_table = NULL;
108 new_chunk->storage_list = NULL;
109 new_chunk->storage_next = size;
110 new_chunk->default_size = size;
111 new_chunk->this_size = size;
113 return (GStringChunk*) new_chunk;
117 g_string_chunk_free (GStringChunk *fchunk)
119 GRealStringChunk *chunk = (GRealStringChunk*) fchunk;
122 g_return_if_fail (chunk != NULL);
124 if (chunk->storage_list)
126 for (tmp_list = chunk->storage_list; tmp_list; tmp_list = tmp_list->next)
127 g_free (tmp_list->data);
129 g_slist_free (chunk->storage_list);
132 if (chunk->const_table)
133 g_hash_table_destroy (chunk->const_table);
139 g_string_chunk_insert (GStringChunk *fchunk,
142 GRealStringChunk *chunk = (GRealStringChunk*) fchunk;
143 gint len = strlen (string);
146 g_return_val_if_fail (chunk != NULL, NULL);
148 if ((chunk->storage_next + len + 1) > chunk->this_size)
150 gint new_size = chunk->default_size;
152 while (new_size < len+1)
155 chunk->storage_list = g_slist_prepend (chunk->storage_list,
156 g_new (char, new_size));
158 chunk->this_size = new_size;
159 chunk->storage_next = 0;
162 pos = ((char *) chunk->storage_list->data) + chunk->storage_next;
164 strcpy (pos, string);
166 chunk->storage_next += len + 1;
172 g_string_chunk_insert_const (GStringChunk *fchunk,
175 GRealStringChunk *chunk = (GRealStringChunk*) fchunk;
178 g_return_val_if_fail (chunk != NULL, NULL);
180 if (!chunk->const_table)
181 chunk->const_table = g_hash_table_new (g_str_hash, g_str_equal);
183 lookup = (char*) g_hash_table_lookup (chunk->const_table, (gchar *)string);
187 lookup = g_string_chunk_insert (fchunk, string);
188 g_hash_table_insert (chunk->const_table, lookup, lookup);
197 nearest_power (gint num)
208 g_string_maybe_expand (GRealString* string, gint len)
210 if (string->len + len >= string->alloc)
212 string->alloc = nearest_power (string->len + len + 1);
213 string->str = g_realloc (string->str, string->alloc);
218 g_string_sized_new (guint dfl_size)
222 G_LOCK (string_mem_chunk);
223 if (!string_mem_chunk)
224 string_mem_chunk = g_mem_chunk_new ("string mem chunk",
225 sizeof (GRealString),
226 1024, G_ALLOC_AND_FREE);
228 string = g_chunk_new (GRealString, string_mem_chunk);
229 G_UNLOCK (string_mem_chunk);
235 g_string_maybe_expand (string, MAX (dfl_size, 2));
238 return (GString*) string;
242 g_string_new (const gchar *init)
246 string = g_string_sized_new (2);
249 g_string_append (string, init);
255 g_string_free (GString *string,
256 gboolean free_segment)
258 g_return_if_fail (string != NULL);
261 g_free (string->str);
263 G_LOCK (string_mem_chunk);
264 g_mem_chunk_free (string_mem_chunk, string);
265 G_UNLOCK (string_mem_chunk);
269 g_string_equal (const GString *v,
273 GRealString *string1 = (GRealString *) v;
274 GRealString *string2 = (GRealString *) v2;
275 gint i = string1->len;
277 if (i != string2->len)
293 /* 31 bit hash function */
295 g_string_hash (const GString *str)
297 const gchar *p = str->str;
303 h = (h << 5) - h + *p;
311 g_string_assign (GString *string,
314 g_return_val_if_fail (string != NULL, NULL);
315 g_return_val_if_fail (rval != NULL, string);
317 g_string_truncate (string, 0);
318 g_string_append (string, rval);
324 g_string_truncate (GString *fstring,
327 GRealString *string = (GRealString *) fstring;
329 g_return_val_if_fail (string != NULL, NULL);
331 string->len = MIN (len, string->len);
333 string->str[string->len] = 0;
339 g_string_insert_len (GString *fstring,
344 GRealString *string = (GRealString *) fstring;
346 g_return_val_if_fail (string != NULL, NULL);
347 g_return_val_if_fail (val != NULL, fstring);
348 g_return_val_if_fail (pos <= string->len, fstring);
356 g_string_maybe_expand (string, len);
358 /* If we aren't appending at the end, move a hunk
359 * of the old string to the end, opening up space
361 if (pos < string->len)
362 g_memmove (string->str + pos + len, string->str + pos, string->len - pos);
364 /* insert the new string */
365 g_memmove (string->str + pos, val, len);
369 string->str[string->len] = 0;
375 g_string_append (GString *fstring,
378 g_return_val_if_fail (fstring != NULL, NULL);
379 g_return_val_if_fail (val != NULL, fstring);
381 return g_string_insert_len (fstring, -1, val, -1);
385 g_string_append_len (GString *string,
389 g_return_val_if_fail (string != NULL, NULL);
390 g_return_val_if_fail (val != NULL, string);
392 return g_string_insert_len (string, -1, val, len);
396 g_string_append_c (GString *fstring,
399 g_return_val_if_fail (fstring != NULL, NULL);
401 return g_string_insert_c (fstring, -1, c);
405 g_string_prepend (GString *fstring,
408 g_return_val_if_fail (fstring != NULL, NULL);
409 g_return_val_if_fail (val != NULL, fstring);
411 return g_string_insert_len (fstring, 0, val, -1);
415 g_string_prepend_len (GString *string,
419 g_return_val_if_fail (string != NULL, NULL);
420 g_return_val_if_fail (val != NULL, string);
422 return g_string_insert_len (string, 0, val, len);
426 g_string_prepend_c (GString *fstring,
429 g_return_val_if_fail (fstring != NULL, NULL);
431 return g_string_insert_c (fstring, 0, c);
435 g_string_insert (GString *fstring,
439 g_return_val_if_fail (fstring != NULL, NULL);
440 g_return_val_if_fail (val != NULL, fstring);
441 g_return_val_if_fail (pos <= fstring->len, fstring);
443 return g_string_insert_len (fstring, pos, val, -1);
447 g_string_insert_c (GString *fstring,
451 GRealString *string = (GRealString *) fstring;
453 g_return_val_if_fail (string != NULL, NULL);
454 g_return_val_if_fail (pos <= string->len, fstring);
456 g_string_maybe_expand (string, 1);
461 /* If not just an append, move the old stuff */
462 if (pos < string->len)
463 g_memmove (string->str + pos + 1, string->str + pos, string->len - pos);
465 string->str[pos] = c;
469 string->str[string->len] = 0;
475 g_string_erase (GString *fstring,
479 GRealString *string = (GRealString*)fstring;
481 g_return_val_if_fail (string != NULL, NULL);
482 g_return_val_if_fail (len >= 0, fstring);
483 g_return_val_if_fail (pos >= 0, fstring);
484 g_return_val_if_fail (pos <= string->len, fstring);
485 g_return_val_if_fail (pos + len <= string->len, fstring);
487 if (pos + len < string->len)
488 g_memmove (string->str + pos, string->str + pos + len, string->len - (pos + len));
492 string->str[string->len] = 0;
498 g_string_down (GString *fstring)
500 GRealString *string = (GRealString *) fstring;
502 gint n = string->len;
504 g_return_val_if_fail (string != NULL, NULL);
519 g_string_up (GString *fstring)
521 GRealString *string = (GRealString *) fstring;
523 gint n = string->len;
525 g_return_val_if_fail (string != NULL, NULL);
540 g_string_sprintfa_int (GString *string,
546 buffer = g_strdup_vprintf (fmt, args);
547 g_string_append (string, buffer);
552 g_string_sprintf (GString *string,
558 g_string_truncate (string, 0);
560 va_start (args, fmt);
561 g_string_sprintfa_int (string, fmt, args);
566 g_string_sprintfa (GString *string,
572 va_start (args, fmt);
573 g_string_sprintfa_int (string, fmt, args);