xref: /aosp_15_r20/external/kmod/shared/strbuf.c (revision cc4ad7da8cefe208cb129ac2aa9a357c7c72deb2)
1*cc4ad7daSAndroid Build Coastguard Worker /*
2*cc4ad7daSAndroid Build Coastguard Worker  * libkmod - interface to kernel module operations
3*cc4ad7daSAndroid Build Coastguard Worker  *
4*cc4ad7daSAndroid Build Coastguard Worker  * Copyright (C) 2011-2013  ProFUSION embedded systems
5*cc4ad7daSAndroid Build Coastguard Worker  * Copyright (C) 2014  Intel Corporation. All rights reserved.
6*cc4ad7daSAndroid Build Coastguard Worker  *
7*cc4ad7daSAndroid Build Coastguard Worker  * This library is free software; you can redistribute it and/or
8*cc4ad7daSAndroid Build Coastguard Worker  * modify it under the terms of the GNU Lesser General Public
9*cc4ad7daSAndroid Build Coastguard Worker  * License as published by the Free Software Foundation; either
10*cc4ad7daSAndroid Build Coastguard Worker  * version 2.1 of the License, or (at your option) any later version.
11*cc4ad7daSAndroid Build Coastguard Worker  *
12*cc4ad7daSAndroid Build Coastguard Worker  * This library is distributed in the hope that it will be useful,
13*cc4ad7daSAndroid Build Coastguard Worker  * but WITHOUT ANY WARRANTY; without even the implied warranty of
14*cc4ad7daSAndroid Build Coastguard Worker  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
15*cc4ad7daSAndroid Build Coastguard Worker  * Lesser General Public License for more details.
16*cc4ad7daSAndroid Build Coastguard Worker  *
17*cc4ad7daSAndroid Build Coastguard Worker  * You should have received a copy of the GNU Lesser General Public
18*cc4ad7daSAndroid Build Coastguard Worker  * License along with this library; if not, see <http://www.gnu.org/licenses/>.
19*cc4ad7daSAndroid Build Coastguard Worker  */
20*cc4ad7daSAndroid Build Coastguard Worker 
21*cc4ad7daSAndroid Build Coastguard Worker #include <assert.h>
22*cc4ad7daSAndroid Build Coastguard Worker #include <stdbool.h>
23*cc4ad7daSAndroid Build Coastguard Worker #include <stdlib.h>
24*cc4ad7daSAndroid Build Coastguard Worker #include <string.h>
25*cc4ad7daSAndroid Build Coastguard Worker 
26*cc4ad7daSAndroid Build Coastguard Worker #include "util.h"
27*cc4ad7daSAndroid Build Coastguard Worker #include "strbuf.h"
28*cc4ad7daSAndroid Build Coastguard Worker 
29*cc4ad7daSAndroid Build Coastguard Worker #define BUF_STEP 128
30*cc4ad7daSAndroid Build Coastguard Worker 
buf_grow(struct strbuf * buf,size_t newsize)31*cc4ad7daSAndroid Build Coastguard Worker static bool buf_grow(struct strbuf *buf, size_t newsize)
32*cc4ad7daSAndroid Build Coastguard Worker {
33*cc4ad7daSAndroid Build Coastguard Worker 	void *tmp;
34*cc4ad7daSAndroid Build Coastguard Worker 	size_t sz;
35*cc4ad7daSAndroid Build Coastguard Worker 
36*cc4ad7daSAndroid Build Coastguard Worker 	if (newsize <= buf->size)
37*cc4ad7daSAndroid Build Coastguard Worker 		return true;
38*cc4ad7daSAndroid Build Coastguard Worker 
39*cc4ad7daSAndroid Build Coastguard Worker 	if (newsize % BUF_STEP == 0)
40*cc4ad7daSAndroid Build Coastguard Worker 		sz = newsize;
41*cc4ad7daSAndroid Build Coastguard Worker 	else
42*cc4ad7daSAndroid Build Coastguard Worker 		sz = ((newsize / BUF_STEP) + 1) * BUF_STEP;
43*cc4ad7daSAndroid Build Coastguard Worker 
44*cc4ad7daSAndroid Build Coastguard Worker 	tmp = realloc(buf->bytes, sz);
45*cc4ad7daSAndroid Build Coastguard Worker 	if (sz > 0 && tmp == NULL)
46*cc4ad7daSAndroid Build Coastguard Worker 		return false;
47*cc4ad7daSAndroid Build Coastguard Worker 	buf->bytes = tmp;
48*cc4ad7daSAndroid Build Coastguard Worker 	buf->size = sz;
49*cc4ad7daSAndroid Build Coastguard Worker 	return true;
50*cc4ad7daSAndroid Build Coastguard Worker }
51*cc4ad7daSAndroid Build Coastguard Worker 
strbuf_init(struct strbuf * buf)52*cc4ad7daSAndroid Build Coastguard Worker void strbuf_init(struct strbuf *buf)
53*cc4ad7daSAndroid Build Coastguard Worker {
54*cc4ad7daSAndroid Build Coastguard Worker 	buf->bytes = NULL;
55*cc4ad7daSAndroid Build Coastguard Worker 	buf->size = 0;
56*cc4ad7daSAndroid Build Coastguard Worker 	buf->used = 0;
57*cc4ad7daSAndroid Build Coastguard Worker }
58*cc4ad7daSAndroid Build Coastguard Worker 
strbuf_release(struct strbuf * buf)59*cc4ad7daSAndroid Build Coastguard Worker void strbuf_release(struct strbuf *buf)
60*cc4ad7daSAndroid Build Coastguard Worker {
61*cc4ad7daSAndroid Build Coastguard Worker 	free(buf->bytes);
62*cc4ad7daSAndroid Build Coastguard Worker }
63*cc4ad7daSAndroid Build Coastguard Worker 
strbuf_steal(struct strbuf * buf)64*cc4ad7daSAndroid Build Coastguard Worker char *strbuf_steal(struct strbuf *buf)
65*cc4ad7daSAndroid Build Coastguard Worker {
66*cc4ad7daSAndroid Build Coastguard Worker 	char *bytes;
67*cc4ad7daSAndroid Build Coastguard Worker 
68*cc4ad7daSAndroid Build Coastguard Worker 	bytes = realloc(buf->bytes, buf->used + 1);
69*cc4ad7daSAndroid Build Coastguard Worker 	if (!bytes) {
70*cc4ad7daSAndroid Build Coastguard Worker 		free(buf->bytes);
71*cc4ad7daSAndroid Build Coastguard Worker 		return NULL;
72*cc4ad7daSAndroid Build Coastguard Worker 	}
73*cc4ad7daSAndroid Build Coastguard Worker 	bytes[buf->used] = '\0';
74*cc4ad7daSAndroid Build Coastguard Worker 	return bytes;
75*cc4ad7daSAndroid Build Coastguard Worker }
76*cc4ad7daSAndroid Build Coastguard Worker 
strbuf_str(struct strbuf * buf)77*cc4ad7daSAndroid Build Coastguard Worker const char *strbuf_str(struct strbuf *buf)
78*cc4ad7daSAndroid Build Coastguard Worker {
79*cc4ad7daSAndroid Build Coastguard Worker 	if (!buf_grow(buf, buf->used + 1))
80*cc4ad7daSAndroid Build Coastguard Worker 		return NULL;
81*cc4ad7daSAndroid Build Coastguard Worker 	buf->bytes[buf->used] = '\0';
82*cc4ad7daSAndroid Build Coastguard Worker 	return buf->bytes;
83*cc4ad7daSAndroid Build Coastguard Worker }
84*cc4ad7daSAndroid Build Coastguard Worker 
strbuf_pushchar(struct strbuf * buf,char ch)85*cc4ad7daSAndroid Build Coastguard Worker bool strbuf_pushchar(struct strbuf *buf, char ch)
86*cc4ad7daSAndroid Build Coastguard Worker {
87*cc4ad7daSAndroid Build Coastguard Worker 	if (!buf_grow(buf, buf->used + 1))
88*cc4ad7daSAndroid Build Coastguard Worker 		return false;
89*cc4ad7daSAndroid Build Coastguard Worker 	buf->bytes[buf->used] = ch;
90*cc4ad7daSAndroid Build Coastguard Worker 	buf->used++;
91*cc4ad7daSAndroid Build Coastguard Worker 	return true;
92*cc4ad7daSAndroid Build Coastguard Worker }
93*cc4ad7daSAndroid Build Coastguard Worker 
strbuf_pushchars(struct strbuf * buf,const char * str)94*cc4ad7daSAndroid Build Coastguard Worker unsigned strbuf_pushchars(struct strbuf *buf, const char *str)
95*cc4ad7daSAndroid Build Coastguard Worker {
96*cc4ad7daSAndroid Build Coastguard Worker 	unsigned int len;
97*cc4ad7daSAndroid Build Coastguard Worker 
98*cc4ad7daSAndroid Build Coastguard Worker 	assert(str != NULL);
99*cc4ad7daSAndroid Build Coastguard Worker 	assert(buf != NULL);
100*cc4ad7daSAndroid Build Coastguard Worker 
101*cc4ad7daSAndroid Build Coastguard Worker 	len = strlen(str);
102*cc4ad7daSAndroid Build Coastguard Worker 
103*cc4ad7daSAndroid Build Coastguard Worker 	if (!buf_grow(buf, buf->used + len))
104*cc4ad7daSAndroid Build Coastguard Worker 		return 0;
105*cc4ad7daSAndroid Build Coastguard Worker 
106*cc4ad7daSAndroid Build Coastguard Worker 	memcpy(buf->bytes + buf->used, str, len);
107*cc4ad7daSAndroid Build Coastguard Worker 	buf->used += len;
108*cc4ad7daSAndroid Build Coastguard Worker 
109*cc4ad7daSAndroid Build Coastguard Worker 	return len;
110*cc4ad7daSAndroid Build Coastguard Worker }
111*cc4ad7daSAndroid Build Coastguard Worker 
strbuf_popchar(struct strbuf * buf)112*cc4ad7daSAndroid Build Coastguard Worker void strbuf_popchar(struct strbuf *buf)
113*cc4ad7daSAndroid Build Coastguard Worker {
114*cc4ad7daSAndroid Build Coastguard Worker 	assert(buf->used > 0);
115*cc4ad7daSAndroid Build Coastguard Worker 	buf->used--;
116*cc4ad7daSAndroid Build Coastguard Worker }
117*cc4ad7daSAndroid Build Coastguard Worker 
strbuf_popchars(struct strbuf * buf,unsigned n)118*cc4ad7daSAndroid Build Coastguard Worker void strbuf_popchars(struct strbuf *buf, unsigned n)
119*cc4ad7daSAndroid Build Coastguard Worker {
120*cc4ad7daSAndroid Build Coastguard Worker 	assert(buf->used >= n);
121*cc4ad7daSAndroid Build Coastguard Worker 	buf->used -= n;
122*cc4ad7daSAndroid Build Coastguard Worker }
123*cc4ad7daSAndroid Build Coastguard Worker 
strbuf_clear(struct strbuf * buf)124*cc4ad7daSAndroid Build Coastguard Worker void strbuf_clear(struct strbuf *buf)
125*cc4ad7daSAndroid Build Coastguard Worker {
126*cc4ad7daSAndroid Build Coastguard Worker 	buf->used = 0;
127*cc4ad7daSAndroid Build Coastguard Worker }
128*cc4ad7daSAndroid Build Coastguard Worker 
129