xref: /trueos/lib/libxpc/xpc_array.c (revision 9003378ef8b6bfee936280a62e5be6bd2617a859)
1 /*
2  * Copyright 2014-2015 iXsystems, Inc.
3  * All rights reserved
4  *
5  * Redistribution and use in source and binary forms, with or without
6  * modification, are permitted providing that the following conditions
7  * are met:
8  * 1. Redistributions of source code must retain the above copyright
9  *    notice, this list of conditions and the following disclaimer.
10  * 2. Redistributions in binary form must reproduce the above copyright
11  *    notice, this list of conditions and the following disclaimer in the
12  *    documentation and/or other materials provided with the distribution.
13  *
14  * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR
15  * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
16  * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
17  * ARE DISCLAIMED.  IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY
18  * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
19  * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
20  * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
21  * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT,
22  * STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING
23  * IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
24  * POSSIBILITY OF SUCH DAMAGE.
25  *
26  */
27 
28 #include <sys/types.h>
29 #include <mach/mach.h>
30 #include <xpc/launchd.h>
31 #include "xpc_internal.h"
32 
33 xpc_object_t
xpc_array_create(const xpc_object_t * objects,size_t count)34 xpc_array_create(const xpc_object_t *objects, size_t count)
35 {
36 	struct xpc_object *xo;
37 	size_t i;
38 	xpc_u val;
39 
40 	xo = _xpc_prim_create(_XPC_TYPE_ARRAY, val, 0);
41 
42 	for (i = 0; i < count; i++)
43 		xpc_array_append_value(xo, objects[i]);
44 
45 	return (xo);
46 }
47 
48 void
xpc_array_set_value(xpc_object_t xarray,size_t index,xpc_object_t value)49 xpc_array_set_value(xpc_object_t xarray, size_t index, xpc_object_t value)
50 {
51 	struct xpc_object *xo, *xotmp, *xotmp2;
52 	struct xpc_array_head *arr;
53 	size_t i;
54 
55 	xo = xarray;
56 	arr = &xo->xo_array;
57 	i = 0;
58 
59 	if (index == XPC_ARRAY_APPEND)
60 		return xpc_array_append_value(xarray, value);
61 
62 	if (index >= (size_t)xo->xo_size)
63 		return;
64 
65 	TAILQ_FOREACH_SAFE(xotmp, arr, xo_link, xotmp2) {
66 		if (i++ == index) {
67 			TAILQ_INSERT_AFTER(arr, (struct xpc_object *)value,
68 			    xotmp, xo_link);
69 			TAILQ_REMOVE(arr, xotmp, xo_link);
70 			xpc_retain(value);
71 			free(xotmp);
72 			break;
73 		}
74 	}
75 }
76 
77 void
xpc_array_append_value(xpc_object_t xarray,xpc_object_t value)78 xpc_array_append_value(xpc_object_t xarray, xpc_object_t value)
79 {
80 	struct xpc_object *xo;
81 	struct xpc_array_head *arr;
82 
83 	xo = xarray;
84 	arr = &xo->xo_array;
85 
86 	TAILQ_INSERT_TAIL(arr, (struct xpc_object *)value, xo_link);
87 	xpc_retain(value);
88 }
89 
90 
91 xpc_object_t
xpc_array_get_value(xpc_object_t xarray,size_t index)92 xpc_array_get_value(xpc_object_t xarray, size_t index)
93 {
94 	struct xpc_object *xo, *xotmp;
95 	struct xpc_array_head *arr;
96 	size_t i;
97 
98 	xo = xarray;
99 	arr = &xo->xo_array;
100 	i = 0;
101 
102 	if (index > xo->xo_size)
103 		return (NULL);
104 
105 	TAILQ_FOREACH(xotmp, arr, xo_link) {
106 		if (i++ == index)
107 			return (xotmp);
108 	}
109 
110 	return (NULL);
111 }
112 
113 size_t
xpc_array_get_count(xpc_object_t xarray)114 xpc_array_get_count(xpc_object_t xarray)
115 {
116 	struct xpc_object *xo;
117 
118 	xo = xarray;
119 	return (xo->xo_size);
120 }
121 
122 void
xpc_array_set_bool(xpc_object_t xarray,size_t index,bool value)123 xpc_array_set_bool(xpc_object_t xarray, size_t index, bool value)
124 {
125 	struct xpc_object *xo, *xotmp;
126 
127 	xo = xarray;
128 	xotmp = xpc_bool_create(value);
129 	return (xpc_array_set_value(xarray, index, xotmp));
130 }
131 
132 
133 void
xpc_array_set_int64(xpc_object_t xarray,size_t index,int64_t value)134 xpc_array_set_int64(xpc_object_t xarray, size_t index, int64_t value)
135 {
136 	struct xpc_object *xo, *xotmp;
137 
138 	xo = xarray;
139 	xotmp = xpc_int64_create(value);
140 	return (xpc_array_set_value(xarray, index, xotmp));
141 }
142 
143 void
xpc_array_set_uint64(xpc_object_t xarray,size_t index,uint64_t value)144 xpc_array_set_uint64(xpc_object_t xarray, size_t index, uint64_t value)
145 {
146 	struct xpc_object *xo, *xotmp;
147 
148 	xo = xarray;
149 	xotmp = xpc_uint64_create(value);
150 	return (xpc_array_set_value(xarray, index, xotmp));
151 }
152 
153 void
xpc_array_set_double(xpc_object_t xarray,size_t index,double value)154 xpc_array_set_double(xpc_object_t xarray, size_t index, double value)
155 {
156 	struct xpc_object *xo, *xotmp;
157 
158 	xo = xarray;
159 	xotmp = xpc_double_create(value);
160 	return (xpc_array_set_value(xarray, index, xotmp));
161 }
162 
163 void
xpc_array_set_date(xpc_object_t xarray,size_t index,int64_t value)164 xpc_array_set_date(xpc_object_t xarray, size_t index, int64_t value)
165 {
166 	struct xpc_object *xo, *xotmp;
167 
168 	xo = xarray;
169 	xotmp = xpc_date_create(value);
170 	return (xpc_array_set_value(xarray, index, xotmp));
171 }
172 
173 void
xpc_array_set_data(xpc_object_t xarray,size_t index,const void * data,size_t length)174 xpc_array_set_data(xpc_object_t xarray, size_t index, const void *data,
175     size_t length)
176 {
177 	struct xpc_object *xo, *xotmp;
178 
179 	xo = xarray;
180 	xotmp = xpc_data_create(data, length);
181 	return (xpc_array_set_value(xarray, index, xotmp));
182 }
183 
184 void
xpc_array_set_string(xpc_object_t xarray,size_t index,const char * string)185 xpc_array_set_string(xpc_object_t xarray, size_t index, const char *string)
186 {
187 	struct xpc_object *xo, *xotmp;
188 
189 	xo = xarray;
190 	xotmp = xpc_string_create(string);
191 	return (xpc_array_set_value(xarray, index, xotmp));
192 }
193 
194 void
xpc_array_set_uuid(xpc_object_t xarray,size_t index,const uuid_t value)195 xpc_array_set_uuid(xpc_object_t xarray, size_t index, const uuid_t value)
196 {
197 	struct xpc_object *xo, *xotmp;
198 
199 	xo = xarray;
200 	xotmp = xpc_uuid_create(value);
201 	return (xpc_array_set_value(xarray, index, xotmp));
202 }
203 
204 void
xpc_array_set_fd(xpc_object_t xarray,size_t index,int value)205 xpc_array_set_fd(xpc_object_t xarray, size_t index, int value)
206 {
207 	struct xpc_object *xo, *xotmp;
208 
209 	xo = xarray;
210 	//xotmp = xpc_fd_create(value);
211 	return (xpc_array_set_value(xarray, index, xotmp));
212 }
213 
214 void
xpc_array_set_connection(xpc_object_t xarray,size_t index,xpc_connection_t value)215 xpc_array_set_connection(xpc_object_t xarray, size_t index,
216     xpc_connection_t value)
217 {
218 
219 }
220 
221 bool
xpc_array_get_bool(xpc_object_t xarray,size_t index)222 xpc_array_get_bool(xpc_object_t xarray, size_t index)
223 {
224 	struct xpc_object *xotmp;
225 
226 	xotmp = xpc_array_get_value(xarray, index);
227 	return (xpc_bool_get_value(xotmp));
228 }
229 
230 int64_t
xpc_array_get_int64(xpc_object_t xarray,size_t index)231 xpc_array_get_int64(xpc_object_t xarray, size_t index)
232 {
233 	struct xpc_object *xotmp;
234 
235 	xotmp = xpc_array_get_value(xarray, index);
236 	return (xpc_int64_get_value(xotmp));
237 }
238 
239 uint64_t
xpc_array_get_uint64(xpc_object_t xarray,size_t index)240 xpc_array_get_uint64(xpc_object_t xarray, size_t index)
241 {
242 	struct xpc_object *xotmp;
243 
244 	xotmp = xpc_array_get_value(xarray, index);
245 	return (xpc_uint64_get_value(xotmp));
246 }
247 
248 double
xpc_array_get_double(xpc_object_t xarray,size_t index)249 xpc_array_get_double(xpc_object_t xarray, size_t index)
250 {
251 	struct xpc_object *xotmp;
252 
253 	xotmp = xpc_array_get_value(xarray, index);
254 	return (xpc_double_get_value(xotmp));
255 }
256 
257 int64_t
xpc_array_get_date(xpc_object_t xarray,size_t index)258 xpc_array_get_date(xpc_object_t xarray, size_t index)
259 {
260 	struct xpc_object *xotmp;
261 
262 	xotmp = xpc_array_get_value(xarray, index);
263 	return (xpc_date_get_value(xotmp));
264 }
265 
266 const void *
xpc_array_get_data(xpc_object_t xarray,size_t index,size_t * length)267 xpc_array_get_data(xpc_object_t xarray, size_t index, size_t *length)
268 {
269 	struct xpc_object *xotmp;
270 
271 	xotmp = xpc_array_get_value(xarray, index);
272 	*length = xpc_data_get_length(xotmp);
273 	return (xpc_data_get_bytes_ptr(xotmp));
274 }
275 
276 const uint8_t *
xpc_array_get_uuid(xpc_object_t xarray,size_t index)277 xpc_array_get_uuid(xpc_object_t xarray, size_t index)
278 {
279 	struct xpc_object *xotmp;
280 
281 	xotmp = xpc_array_get_value(xarray, index);
282 	return (xpc_uuid_get_bytes(xotmp));
283 }
284 
285 const char *
xpc_array_get_string(xpc_object_t xarray,size_t index)286 xpc_array_get_string(xpc_object_t xarray, size_t index)
287 {
288 	struct xpc_object *xotmp;
289 
290 	xotmp = xpc_array_get_value(xarray, index);
291 	return (xpc_string_get_string_ptr(xotmp));
292 }
293 
294 int
xpc_array_dup_fd(xpc_object_t array,size_t index)295 xpc_array_dup_fd(xpc_object_t array, size_t index)
296 {
297 	/* XXX */
298 	return (-1);
299 }
300 
301 xpc_connection_t
xpc_array_get_connection(xpc_object_t array,size_t index)302 xpc_array_get_connection(xpc_object_t array, size_t index)
303 {
304 	/* XXX */
305 	return (NULL);
306 }
307 
308 bool
xpc_array_apply(xpc_object_t xarray,xpc_array_applier_t applier)309 xpc_array_apply(xpc_object_t xarray, xpc_array_applier_t applier)
310 {
311 	struct xpc_object *xo, *xotmp;
312 	struct xpc_array_head *arr;
313 	size_t i;
314 
315 	i = 0;
316 	xo = xarray;
317 	arr = &xo->xo_array;
318 
319 	TAILQ_FOREACH(xotmp, arr, xo_link) {
320 		if (!applier(i++, xotmp))
321 			return (false);
322 	}
323 
324 	return (true);
325 }
326