Mercurial > malikania
comparison extern/jansson/src/strbuffer.c @ 0:8991989c4708
Initial import
author | David Demelier <markand@malikania.fr> |
---|---|
date | Tue, 22 Mar 2016 18:26:05 +0100 |
parents | |
children |
comparison
equal
deleted
inserted
replaced
-1:000000000000 | 0:8991989c4708 |
---|---|
1 /* | |
2 * Copyright (c) 2009-2014 Petri Lehtinen <petri@digip.org> | |
3 * | |
4 * Jansson is free software; you can redistribute it and/or modify | |
5 * it under the terms of the MIT license. See LICENSE for details. | |
6 */ | |
7 | |
8 #ifndef _GNU_SOURCE | |
9 #define _GNU_SOURCE | |
10 #endif | |
11 | |
12 #include <stdlib.h> | |
13 #include <string.h> | |
14 #include "jansson_private.h" | |
15 #include "strbuffer.h" | |
16 | |
17 #define STRBUFFER_MIN_SIZE 16 | |
18 #define STRBUFFER_FACTOR 2 | |
19 #define STRBUFFER_SIZE_MAX ((size_t)-1) | |
20 | |
21 int strbuffer_init(strbuffer_t *strbuff) | |
22 { | |
23 strbuff->size = STRBUFFER_MIN_SIZE; | |
24 strbuff->length = 0; | |
25 | |
26 strbuff->value = jsonp_malloc(strbuff->size); | |
27 if(!strbuff->value) | |
28 return -1; | |
29 | |
30 /* initialize to empty */ | |
31 strbuff->value[0] = '\0'; | |
32 return 0; | |
33 } | |
34 | |
35 void strbuffer_close(strbuffer_t *strbuff) | |
36 { | |
37 if(strbuff->value) | |
38 jsonp_free(strbuff->value); | |
39 | |
40 strbuff->size = 0; | |
41 strbuff->length = 0; | |
42 strbuff->value = NULL; | |
43 } | |
44 | |
45 void strbuffer_clear(strbuffer_t *strbuff) | |
46 { | |
47 strbuff->length = 0; | |
48 strbuff->value[0] = '\0'; | |
49 } | |
50 | |
51 const char *strbuffer_value(const strbuffer_t *strbuff) | |
52 { | |
53 return strbuff->value; | |
54 } | |
55 | |
56 char *strbuffer_steal_value(strbuffer_t *strbuff) | |
57 { | |
58 char *result = strbuff->value; | |
59 strbuff->value = NULL; | |
60 return result; | |
61 } | |
62 | |
63 int strbuffer_append(strbuffer_t *strbuff, const char *string) | |
64 { | |
65 return strbuffer_append_bytes(strbuff, string, strlen(string)); | |
66 } | |
67 | |
68 int strbuffer_append_byte(strbuffer_t *strbuff, char byte) | |
69 { | |
70 return strbuffer_append_bytes(strbuff, &byte, 1); | |
71 } | |
72 | |
73 int strbuffer_append_bytes(strbuffer_t *strbuff, const char *data, size_t size) | |
74 { | |
75 if(size >= strbuff->size - strbuff->length) | |
76 { | |
77 size_t new_size; | |
78 char *new_value; | |
79 | |
80 /* avoid integer overflow */ | |
81 if (strbuff->size > STRBUFFER_SIZE_MAX / STRBUFFER_FACTOR | |
82 || size > STRBUFFER_SIZE_MAX - 1 | |
83 || strbuff->length > STRBUFFER_SIZE_MAX - 1 - size) | |
84 return -1; | |
85 | |
86 new_size = max(strbuff->size * STRBUFFER_FACTOR, | |
87 strbuff->length + size + 1); | |
88 | |
89 new_value = jsonp_malloc(new_size); | |
90 if(!new_value) | |
91 return -1; | |
92 | |
93 memcpy(new_value, strbuff->value, strbuff->length); | |
94 | |
95 jsonp_free(strbuff->value); | |
96 strbuff->value = new_value; | |
97 strbuff->size = new_size; | |
98 } | |
99 | |
100 memcpy(strbuff->value + strbuff->length, data, size); | |
101 strbuff->length += size; | |
102 strbuff->value[strbuff->length] = '\0'; | |
103 | |
104 return 0; | |
105 } | |
106 | |
107 char strbuffer_pop(strbuffer_t *strbuff) | |
108 { | |
109 if(strbuff->length > 0) { | |
110 char c = strbuff->value[--strbuff->length]; | |
111 strbuff->value[strbuff->length] = '\0'; | |
112 return c; | |
113 } | |
114 else | |
115 return '\0'; | |
116 } |