25 * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE |
25 * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE |
26 * POSSIBILITY OF SUCH DAMAGE. |
26 * POSSIBILITY OF SUCH DAMAGE. |
27 */ |
27 */ |
28 |
28 |
29 #include "cx/string.h" |
29 #include "cx/string.h" |
|
30 #include "cx/utils.h" |
|
31 |
|
32 #include <string.h> |
|
33 #include <stdarg.h> |
|
34 #include <stdint.h> |
|
35 |
|
36 cxmutstr cx_mutstr(char *cstring) { |
|
37 return (cxmutstr) {cstring, strlen(cstring)}; |
|
38 } |
|
39 |
|
40 cxmutstr cx_mutstrn( |
|
41 char *cstring, |
|
42 size_t length |
|
43 ) { |
|
44 return (cxmutstr) {cstring, length}; |
|
45 } |
|
46 |
|
47 cxstring cx_str(const char *cstring) { |
|
48 return (cxstring) {cstring, strlen(cstring)}; |
|
49 } |
|
50 |
|
51 cxstring cx_strn( |
|
52 const char *cstring, |
|
53 size_t length |
|
54 ) { |
|
55 return (cxstring) {cstring, length}; |
|
56 } |
|
57 |
|
58 cxstring cx_strcast(cxmutstr str) { |
|
59 return (cxstring) {str.ptr, str.length}; |
|
60 } |
|
61 |
|
62 void cx_strfree(cxmutstr *str) { |
|
63 free(str->ptr); |
|
64 str->ptr = NULL; |
|
65 str->length = 0; |
|
66 } |
|
67 |
|
68 size_t cx_strlen( |
|
69 size_t count, |
|
70 ... |
|
71 ) { |
|
72 if (count == 0) return 0; |
|
73 |
|
74 va_list ap; |
|
75 va_start(ap, count); |
|
76 size_t size = 0; |
|
77 cx_for_n(i, count) { |
|
78 cxstring str = va_arg(ap, cxstring); |
|
79 size += str.length; |
|
80 } |
|
81 va_end(ap); |
|
82 |
|
83 return size; |
|
84 } |
|
85 |
|
86 cxmutstr cx_strcat_a( |
|
87 CxAllocator *alloc, |
|
88 size_t count, |
|
89 ... |
|
90 ) { |
|
91 cxstring *strings = calloc(count, sizeof(cxstring)); |
|
92 if (!strings) abort(); |
|
93 |
|
94 va_list ap; |
|
95 va_start(ap, count); |
|
96 |
|
97 // get all args and overall length |
|
98 size_t slen = 0; |
|
99 cx_for_n(i, count) { |
|
100 cxstring s = va_arg (ap, cxstring); |
|
101 strings[i] = s; |
|
102 slen += s.length; |
|
103 } |
|
104 |
|
105 // create new string |
|
106 cxmutstr result; |
|
107 result.ptr = cxMalloc(alloc, slen + 1); |
|
108 result.length = slen; |
|
109 if (result.ptr == NULL) abort(); |
|
110 |
|
111 // concatenate strings |
|
112 size_t pos = 0; |
|
113 cx_for_n(i, count) { |
|
114 cxstring s = strings[i]; |
|
115 memcpy(result.ptr + pos, s.ptr, s.length); |
|
116 pos += s.length; |
|
117 } |
|
118 |
|
119 // terminate string |
|
120 result.ptr[result.length] = '\0'; |
|
121 |
|
122 // free temporary array |
|
123 free(strings); |
|
124 |
|
125 return result; |
|
126 } |
|
127 |
|
128 |
|
129 |