Branch data Line data Source code
1 : : /*
2 : : * Copyright © 2007, 2008 Ryan Lortie
3 : : * Copyright © 2010 Codethink Limited
4 : : *
5 : : * SPDX-License-Identifier: LGPL-2.1-or-later
6 : : *
7 : : * This library is free software; you can redistribute it and/or
8 : : * modify it under the terms of the GNU Lesser General Public
9 : : * License as published by the Free Software Foundation; either
10 : : * version 2.1 of the License, or (at your option) any later version.
11 : : *
12 : : * This library is distributed in the hope that it will be useful,
13 : : * but WITHOUT ANY WARRANTY; without even the implied warranty of
14 : : * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
15 : : * Lesser General Public License for more details.
16 : : *
17 : : * You should have received a copy of the GNU Lesser General Public
18 : : * License along with this library; if not, see <http://www.gnu.org/licenses/>.
19 : : *
20 : : * Author: Ryan Lortie <desrt@desrt.ca>
21 : : */
22 : :
23 : : /* Prologue {{{1 */
24 : :
25 : : #include "config.h"
26 : :
27 : : #include <glib/gvariant-serialiser.h>
28 : : #include "gvariant-internal.h"
29 : : #include <glib/gvariant-core.h>
30 : : #include <glib/gtestutils.h>
31 : : #include <glib/gstrfuncs.h>
32 : : #include <glib/gslice.h>
33 : : #include <glib/ghash.h>
34 : : #include <glib/gmem.h>
35 : :
36 : : #include <string.h>
37 : :
38 : : /**
39 : : * GVariant: (copy-func g_variant_ref_sink) (free-func g_variant_unref)
40 : : *
41 : : * `GVariant` is a variant datatype; it can contain one or more values
42 : : * along with information about the type of the values.
43 : : *
44 : : * A `GVariant` may contain simple types, like an integer, or a boolean value;
45 : : * or complex types, like an array of two strings, or a dictionary of key
46 : : * value pairs. A `GVariant` is also immutable: once it’s been created neither
47 : : * its type nor its content can be modified further.
48 : : *
49 : : * `GVariant` is useful whenever data needs to be serialized, for example when
50 : : * sending method parameters in D-Bus, or when saving settings using
51 : : * [`GSettings`](../gio/class.Settings.html).
52 : : *
53 : : * When creating a new `GVariant`, you pass the data you want to store in it
54 : : * along with a string representing the type of data you wish to pass to it.
55 : : *
56 : : * For instance, if you want to create a `GVariant` holding an integer value you
57 : : * can use:
58 : : *
59 : : * ```c
60 : : * GVariant *v = g_variant_new ("u", 40);
61 : : * ```
62 : : *
63 : : * The string `u` in the first argument tells `GVariant` that the data passed to
64 : : * the constructor (`40`) is going to be an unsigned integer.
65 : : *
66 : : * More advanced examples of `GVariant` in use can be found in documentation for
67 : : * [`GVariant` format strings](gvariant-format-strings.html#pointers).
68 : : *
69 : : * The range of possible values is determined by the type.
70 : : *
71 : : * The type system used by `GVariant` is [type@GLib.VariantType].
72 : : *
73 : : * `GVariant` instances always have a type and a value (which are given
74 : : * at construction time). The type and value of a `GVariant` instance
75 : : * can never change other than by the `GVariant` itself being
76 : : * destroyed. A `GVariant` cannot contain a pointer.
77 : : *
78 : : * `GVariant` is reference counted using [method@GLib.Variant.ref] and
79 : : * [method@GLib.Variant.unref]. `GVariant` also has floating reference counts —
80 : : * see [method@GLib.Variant.ref_sink].
81 : : *
82 : : * `GVariant` is completely threadsafe. A `GVariant` instance can be
83 : : * concurrently accessed in any way from any number of threads without
84 : : * problems.
85 : : *
86 : : * `GVariant` is heavily optimised for dealing with data in serialized
87 : : * form. It works particularly well with data located in memory-mapped
88 : : * files. It can perform nearly all deserialization operations in a
89 : : * small constant time, usually touching only a single memory page.
90 : : * Serialized `GVariant` data can also be sent over the network.
91 : : *
92 : : * `GVariant` is largely compatible with D-Bus. Almost all types of
93 : : * `GVariant` instances can be sent over D-Bus. See [type@GLib.VariantType] for
94 : : * exceptions. (However, `GVariant`’s serialization format is not the same
95 : : * as the serialization format of a D-Bus message body: use
96 : : * [GDBusMessage](../gio/class.DBusMessage.html), in the GIO library, for those.)
97 : : *
98 : : * For space-efficiency, the `GVariant` serialization format does not
99 : : * automatically include the variant’s length, type or endianness,
100 : : * which must either be implied from context (such as knowledge that a
101 : : * particular file format always contains a little-endian
102 : : * `G_VARIANT_TYPE_VARIANT` which occupies the whole length of the file)
103 : : * or supplied out-of-band (for instance, a length, type and/or endianness
104 : : * indicator could be placed at the beginning of a file, network message
105 : : * or network stream).
106 : : *
107 : : * A `GVariant`’s size is limited mainly by any lower level operating
108 : : * system constraints, such as the number of bits in `gsize`. For
109 : : * example, it is reasonable to have a 2GB file mapped into memory
110 : : * with [struct@GLib.MappedFile], and call [ctor@GLib.Variant.new_from_data] on
111 : : * it.
112 : : *
113 : : * For convenience to C programmers, `GVariant` features powerful
114 : : * varargs-based value construction and destruction. This feature is
115 : : * designed to be embedded in other libraries.
116 : : *
117 : : * There is a Python-inspired text language for describing `GVariant`
118 : : * values. `GVariant` includes a printer for this language and a parser
119 : : * with type inferencing.
120 : : *
121 : : * ## Memory Use
122 : : *
123 : : * `GVariant` tries to be quite efficient with respect to memory use.
124 : : * This section gives a rough idea of how much memory is used by the
125 : : * current implementation. The information here is subject to change
126 : : * in the future.
127 : : *
128 : : * The memory allocated by `GVariant` can be grouped into 4 broad
129 : : * purposes: memory for serialized data, memory for the type
130 : : * information cache, buffer management memory and memory for the
131 : : * `GVariant` structure itself.
132 : : *
133 : : * ## Serialized Data Memory
134 : : *
135 : : * This is the memory that is used for storing `GVariant` data in
136 : : * serialized form. This is what would be sent over the network or
137 : : * what would end up on disk, not counting any indicator of the
138 : : * endianness, or of the length or type of the top-level variant.
139 : : *
140 : : * The amount of memory required to store a boolean is 1 byte. 16,
141 : : * 32 and 64 bit integers and double precision floating point numbers
142 : : * use their ‘natural’ size. Strings (including object path and
143 : : * signature strings) are stored with a nul terminator, and as such
144 : : * use the length of the string plus 1 byte.
145 : : *
146 : : * ‘Maybe’ types use no space at all to represent the null value and
147 : : * use the same amount of space (sometimes plus one byte) as the
148 : : * equivalent non-maybe-typed value to represent the non-null case.
149 : : *
150 : : * Arrays use the amount of space required to store each of their
151 : : * members, concatenated. Additionally, if the items stored in an
152 : : * array are not of a fixed-size (ie: strings, other arrays, etc)
153 : : * then an additional framing offset is stored for each item. The
154 : : * size of this offset is either 1, 2 or 4 bytes depending on the
155 : : * overall size of the container. Additionally, extra padding bytes
156 : : * are added as required for alignment of child values.
157 : : *
158 : : * Tuples (including dictionary entries) use the amount of space
159 : : * required to store each of their members, concatenated, plus one
160 : : * framing offset (as per arrays) for each non-fixed-sized item in
161 : : * the tuple, except for the last one. Additionally, extra padding
162 : : * bytes are added as required for alignment of child values.
163 : : *
164 : : * Variants use the same amount of space as the item inside of the
165 : : * variant, plus 1 byte, plus the length of the type string for the
166 : : * item inside the variant.
167 : : *
168 : : * As an example, consider a dictionary mapping strings to variants.
169 : : * In the case that the dictionary is empty, 0 bytes are required for
170 : : * the serialization.
171 : : *
172 : : * If we add an item ‘width’ that maps to the int32 value of 500 then
173 : : * we will use 4 bytes to store the int32 (so 6 for the variant
174 : : * containing it) and 6 bytes for the string. The variant must be
175 : : * aligned to 8 after the 6 bytes of the string, so that’s 2 extra
176 : : * bytes. 6 (string) + 2 (padding) + 6 (variant) is 14 bytes used
177 : : * for the dictionary entry. An additional 1 byte is added to the
178 : : * array as a framing offset making a total of 15 bytes.
179 : : *
180 : : * If we add another entry, ‘title’ that maps to a nullable string
181 : : * that happens to have a value of null, then we use 0 bytes for the
182 : : * null value (and 3 bytes for the variant to contain it along with
183 : : * its type string) plus 6 bytes for the string. Again, we need 2
184 : : * padding bytes. That makes a total of 6 + 2 + 3 = 11 bytes.
185 : : *
186 : : * We now require extra padding between the two items in the array.
187 : : * After the 14 bytes of the first item, that’s 2 bytes required.
188 : : * We now require 2 framing offsets for an extra two
189 : : * bytes. 14 + 2 + 11 + 2 = 29 bytes to encode the entire two-item
190 : : * dictionary.
191 : : *
192 : : * ## Type Information Cache
193 : : *
194 : : * For each `GVariant` type that currently exists in the program a type
195 : : * information structure is kept in the type information cache. The
196 : : * type information structure is required for rapid deserialization.
197 : : *
198 : : * Continuing with the above example, if a `GVariant` exists with the
199 : : * type `a{sv}` then a type information struct will exist for
200 : : * `a{sv}`, `{sv}`, `s`, and `v`. Multiple uses of the same type
201 : : * will share the same type information. Additionally, all
202 : : * single-digit types are stored in read-only static memory and do
203 : : * not contribute to the writable memory footprint of a program using
204 : : * `GVariant`.
205 : : *
206 : : * Aside from the type information structures stored in read-only
207 : : * memory, there are two forms of type information. One is used for
208 : : * container types where there is a single element type: arrays and
209 : : * maybe types. The other is used for container types where there
210 : : * are multiple element types: tuples and dictionary entries.
211 : : *
212 : : * Array type info structures are `6 * sizeof (void *)`, plus the
213 : : * memory required to store the type string itself. This means that
214 : : * on 32-bit systems, the cache entry for `a{sv}` would require 30
215 : : * bytes of memory (plus allocation overhead).
216 : : *
217 : : * Tuple type info structures are `6 * sizeof (void *)`, plus `4 *
218 : : * sizeof (void *)` for each item in the tuple, plus the memory
219 : : * required to store the type string itself. A 2-item tuple, for
220 : : * example, would have a type information structure that consumed
221 : : * writable memory in the size of `14 * sizeof (void *)` (plus type
222 : : * string) This means that on 32-bit systems, the cache entry for
223 : : * `{sv}` would require 61 bytes of memory (plus allocation overhead).
224 : : *
225 : : * This means that in total, for our `a{sv}` example, 91 bytes of
226 : : * type information would be allocated.
227 : : *
228 : : * The type information cache, additionally, uses a [struct@GLib.HashTable] to
229 : : * store and look up the cached items and stores a pointer to this
230 : : * hash table in static storage. The hash table is freed when there
231 : : * are zero items in the type cache.
232 : : *
233 : : * Although these sizes may seem large it is important to remember
234 : : * that a program will probably only have a very small number of
235 : : * different types of values in it and that only one type information
236 : : * structure is required for many different values of the same type.
237 : : *
238 : : * ## Buffer Management Memory
239 : : *
240 : : * `GVariant` uses an internal buffer management structure to deal
241 : : * with the various different possible sources of serialized data
242 : : * that it uses. The buffer is responsible for ensuring that the
243 : : * correct call is made when the data is no longer in use by
244 : : * `GVariant`. This may involve a [func@GLib.free] or
245 : : * even [method@GLib.MappedFile.unref].
246 : : *
247 : : * One buffer management structure is used for each chunk of
248 : : * serialized data. The size of the buffer management structure
249 : : * is `4 * (void *)`. On 32-bit systems, that’s 16 bytes.
250 : : *
251 : : * ## GVariant structure
252 : : *
253 : : * The size of a `GVariant` structure is `6 * (void *)`. On 32-bit
254 : : * systems, that’s 24 bytes.
255 : : *
256 : : * `GVariant` structures only exist if they are explicitly created
257 : : * with API calls. For example, if a `GVariant` is constructed out of
258 : : * serialized data for the example given above (with the dictionary)
259 : : * then although there are 9 individual values that comprise the
260 : : * entire dictionary (two keys, two values, two variants containing
261 : : * the values, two dictionary entries, plus the dictionary itself),
262 : : * only 1 `GVariant` instance exists — the one referring to the
263 : : * dictionary.
264 : : *
265 : : * If calls are made to start accessing the other values then
266 : : * `GVariant` instances will exist for those values only for as long
267 : : * as they are in use (ie: until you call [method@GLib.Variant.unref]). The
268 : : * type information is shared. The serialized data and the buffer
269 : : * management structure for that serialized data is shared by the
270 : : * child.
271 : : *
272 : : * ## Summary
273 : : *
274 : : * To put the entire example together, for our dictionary mapping
275 : : * strings to variants (with two entries, as given above), we are
276 : : * using 91 bytes of memory for type information, 29 bytes of memory
277 : : * for the serialized data, 16 bytes for buffer management and 24
278 : : * bytes for the `GVariant` instance, or a total of 160 bytes, plus
279 : : * allocation overhead. If we were to use [method@GLib.Variant.get_child_value]
280 : : * to access the two dictionary entries, we would use an additional 48
281 : : * bytes. If we were to have other dictionaries of the same type, we
282 : : * would use more memory for the serialized data and buffer
283 : : * management for those dictionaries, but the type information would
284 : : * be shared.
285 : : *
286 : : * Since: 2.24
287 : : */
288 : :
289 : : /* definition of GVariant structure is in gvariant-core.c */
290 : :
291 : : /* this is a g_return_val_if_fail() for making
292 : : * sure a (GVariant *) has the required type.
293 : : */
294 : : #define TYPE_CHECK(value, TYPE, val) \
295 : : if G_UNLIKELY (!g_variant_is_of_type (value, TYPE)) { \
296 : : g_return_if_fail_warning (G_LOG_DOMAIN, G_STRFUNC, \
297 : : "g_variant_is_of_type (" #value \
298 : : ", " #TYPE ")"); \
299 : : return val; \
300 : : }
301 : :
302 : : /* Numeric Type Constructor/Getters {{{1 */
303 : : /* < private >
304 : : * g_variant_new_from_trusted:
305 : : * @type: the #GVariantType
306 : : * @data: the data to use
307 : : * @size: the size of @data
308 : : *
309 : : * Constructs a new trusted #GVariant instance from the provided data.
310 : : * This is used to implement g_variant_new_* for all the basic types.
311 : : *
312 : : * Note: @data must be backed by memory that is aligned appropriately for the
313 : : * @type being loaded. Otherwise this function will internally create a copy of
314 : : * the memory (since GLib 2.60) or (in older versions) fail and exit the
315 : : * process.
316 : : *
317 : : * Returns: a new floating #GVariant
318 : : */
319 : : static GVariant *
320 : 1936010 : g_variant_new_from_trusted (const GVariantType *type,
321 : : gconstpointer data,
322 : : gsize size)
323 : : {
324 : 1936010 : if (size <= G_VARIANT_MAX_PREALLOCATED)
325 : 1512566 : return g_variant_new_preallocated_trusted (type, data, size);
326 : : else
327 : 423444 : return g_variant_new_take_bytes (type, g_bytes_new (data, size), TRUE);
328 : : }
329 : :
330 : : /**
331 : : * g_variant_new_boolean:
332 : : * @value: a #gboolean value
333 : : *
334 : : * Creates a new boolean #GVariant instance -- either %TRUE or %FALSE.
335 : : *
336 : : * Returns: (transfer none): a floating reference to a new boolean #GVariant instance
337 : : *
338 : : * Since: 2.24
339 : : **/
340 : : GVariant *
341 : 3424 : g_variant_new_boolean (gboolean value)
342 : : {
343 : 3424 : guchar v = value;
344 : :
345 : 3424 : return g_variant_new_from_trusted (G_VARIANT_TYPE_BOOLEAN, &v, 1);
346 : : }
347 : :
348 : : /**
349 : : * g_variant_get_boolean:
350 : : * @value: a boolean #GVariant instance
351 : : *
352 : : * Returns the boolean value of @value.
353 : : *
354 : : * It is an error to call this function with a @value of any type
355 : : * other than %G_VARIANT_TYPE_BOOLEAN.
356 : : *
357 : : * Returns: %TRUE or %FALSE
358 : : *
359 : : * Since: 2.24
360 : : **/
361 : : gboolean
362 : 46945 : g_variant_get_boolean (GVariant *value)
363 : : {
364 : : const guchar *data;
365 : :
366 : 46945 : TYPE_CHECK (value, G_VARIANT_TYPE_BOOLEAN, FALSE);
367 : :
368 : 46945 : data = g_variant_get_data (value);
369 : :
370 : 46945 : return data != NULL ? *data != 0 : FALSE;
371 : : }
372 : :
373 : : /* the constructors and accessors for byte, int{16,32,64}, handles and
374 : : * doubles all look pretty much exactly the same, so we reduce
375 : : * copy/pasting here.
376 : : */
377 : : #define NUMERIC_TYPE(TYPE, type, ctype) \
378 : : GVariant *g_variant_new_##type (ctype value) { \
379 : : return g_variant_new_from_trusted (G_VARIANT_TYPE_##TYPE, \
380 : : &value, sizeof value); \
381 : : } \
382 : : ctype g_variant_get_##type (GVariant *value) { \
383 : : const ctype *data; \
384 : : TYPE_CHECK (value, G_VARIANT_TYPE_ ## TYPE, 0); \
385 : : data = g_variant_get_data (value); \
386 : : return data != NULL ? *data : 0; \
387 : : }
388 : :
389 : :
390 : : /**
391 : : * g_variant_new_byte:
392 : : * @value: a #guint8 value
393 : : *
394 : : * Creates a new byte #GVariant instance.
395 : : *
396 : : * Returns: (transfer none): a floating reference to a new byte #GVariant instance
397 : : *
398 : : * Since: 2.24
399 : : **/
400 : : /**
401 : : * g_variant_get_byte:
402 : : * @value: a byte #GVariant instance
403 : : *
404 : : * Returns the byte value of @value.
405 : : *
406 : : * It is an error to call this function with a @value of any type
407 : : * other than %G_VARIANT_TYPE_BYTE.
408 : : *
409 : : * Returns: a #guint8
410 : : *
411 : : * Since: 2.24
412 : : **/
413 : 419681 : NUMERIC_TYPE (BYTE, byte, guint8)
414 : :
415 : : /**
416 : : * g_variant_new_int16:
417 : : * @value: a #gint16 value
418 : : *
419 : : * Creates a new int16 #GVariant instance.
420 : : *
421 : : * Returns: (transfer none): a floating reference to a new int16 #GVariant instance
422 : : *
423 : : * Since: 2.24
424 : : **/
425 : : /**
426 : : * g_variant_get_int16:
427 : : * @value: an int16 #GVariant instance
428 : : *
429 : : * Returns the 16-bit signed integer value of @value.
430 : : *
431 : : * It is an error to call this function with a @value of any type
432 : : * other than %G_VARIANT_TYPE_INT16.
433 : : *
434 : : * Returns: a #gint16
435 : : *
436 : : * Since: 2.24
437 : : **/
438 : 119628 : NUMERIC_TYPE (INT16, int16, gint16)
439 : :
440 : : /**
441 : : * g_variant_new_uint16:
442 : : * @value: a #guint16 value
443 : : *
444 : : * Creates a new uint16 #GVariant instance.
445 : : *
446 : : * Returns: (transfer none): a floating reference to a new uint16 #GVariant instance
447 : : *
448 : : * Since: 2.24
449 : : **/
450 : : /**
451 : : * g_variant_get_uint16:
452 : : * @value: a uint16 #GVariant instance
453 : : *
454 : : * Returns the 16-bit unsigned integer value of @value.
455 : : *
456 : : * It is an error to call this function with a @value of any type
457 : : * other than %G_VARIANT_TYPE_UINT16.
458 : : *
459 : : * Returns: a #guint16
460 : : *
461 : : * Since: 2.24
462 : : **/
463 : 62005 : NUMERIC_TYPE (UINT16, uint16, guint16)
464 : :
465 : : /**
466 : : * g_variant_new_int32:
467 : : * @value: a #gint32 value
468 : : *
469 : : * Creates a new int32 #GVariant instance.
470 : : *
471 : : * Returns: (transfer none): a floating reference to a new int32 #GVariant instance
472 : : *
473 : : * Since: 2.24
474 : : **/
475 : : /**
476 : : * g_variant_get_int32:
477 : : * @value: an int32 #GVariant instance
478 : : *
479 : : * Returns the 32-bit signed integer value of @value.
480 : : *
481 : : * It is an error to call this function with a @value of any type
482 : : * other than %G_VARIANT_TYPE_INT32.
483 : : *
484 : : * Returns: a #gint32
485 : : *
486 : : * Since: 2.24
487 : : **/
488 : 137340 : NUMERIC_TYPE (INT32, int32, gint32)
489 : :
490 : : /**
491 : : * g_variant_new_uint32:
492 : : * @value: a #guint32 value
493 : : *
494 : : * Creates a new uint32 #GVariant instance.
495 : : *
496 : : * Returns: (transfer none): a floating reference to a new uint32 #GVariant instance
497 : : *
498 : : * Since: 2.24
499 : : **/
500 : : /**
501 : : * g_variant_get_uint32:
502 : : * @value: a uint32 #GVariant instance
503 : : *
504 : : * Returns the 32-bit unsigned integer value of @value.
505 : : *
506 : : * It is an error to call this function with a @value of any type
507 : : * other than %G_VARIANT_TYPE_UINT32.
508 : : *
509 : : * Returns: a #guint32
510 : : *
511 : : * Since: 2.24
512 : : **/
513 : 139423 : NUMERIC_TYPE (UINT32, uint32, guint32)
514 : :
515 : : /**
516 : : * g_variant_new_int64:
517 : : * @value: a #gint64 value
518 : : *
519 : : * Creates a new int64 #GVariant instance.
520 : : *
521 : : * Returns: (transfer none): a floating reference to a new int64 #GVariant instance
522 : : *
523 : : * Since: 2.24
524 : : **/
525 : : /**
526 : : * g_variant_get_int64:
527 : : * @value: an int64 #GVariant instance
528 : : *
529 : : * Returns the 64-bit signed integer value of @value.
530 : : *
531 : : * It is an error to call this function with a @value of any type
532 : : * other than %G_VARIANT_TYPE_INT64.
533 : : *
534 : : * Returns: a #gint64
535 : : *
536 : : * Since: 2.24
537 : : **/
538 : 122870 : NUMERIC_TYPE (INT64, int64, gint64)
539 : :
540 : : /**
541 : : * g_variant_new_uint64:
542 : : * @value: a #guint64 value
543 : : *
544 : : * Creates a new uint64 #GVariant instance.
545 : : *
546 : : * Returns: (transfer none): a floating reference to a new uint64 #GVariant instance
547 : : *
548 : : * Since: 2.24
549 : : **/
550 : : /**
551 : : * g_variant_get_uint64:
552 : : * @value: a uint64 #GVariant instance
553 : : *
554 : : * Returns the 64-bit unsigned integer value of @value.
555 : : *
556 : : * It is an error to call this function with a @value of any type
557 : : * other than %G_VARIANT_TYPE_UINT64.
558 : : *
559 : : * Returns: a #guint64
560 : : *
561 : : * Since: 2.24
562 : : **/
563 : 48740 : NUMERIC_TYPE (UINT64, uint64, guint64)
564 : :
565 : : /**
566 : : * g_variant_new_handle:
567 : : * @value: a #gint32 value
568 : : *
569 : : * Creates a new handle #GVariant instance.
570 : : *
571 : : * By convention, handles are indexes into an array of file descriptors
572 : : * that are sent alongside a D-Bus message. If you're not interacting
573 : : * with D-Bus, you probably don't need them.
574 : : *
575 : : * Returns: (transfer none): a floating reference to a new handle #GVariant instance
576 : : *
577 : : * Since: 2.24
578 : : **/
579 : : /**
580 : : * g_variant_get_handle:
581 : : * @value: a handle #GVariant instance
582 : : *
583 : : * Returns the 32-bit signed integer value of @value.
584 : : *
585 : : * It is an error to call this function with a @value of any type other
586 : : * than %G_VARIANT_TYPE_HANDLE.
587 : : *
588 : : * By convention, handles are indexes into an array of file descriptors
589 : : * that are sent alongside a D-Bus message. If you're not interacting
590 : : * with D-Bus, you probably don't need them.
591 : : *
592 : : * Returns: a #gint32
593 : : *
594 : : * Since: 2.24
595 : : **/
596 : 58012 : NUMERIC_TYPE (HANDLE, handle, gint32)
597 : :
598 : : /**
599 : : * g_variant_new_double:
600 : : * @value: a #gdouble floating point value
601 : : *
602 : : * Creates a new double #GVariant instance.
603 : : *
604 : : * Returns: (transfer none): a floating reference to a new double #GVariant instance
605 : : *
606 : : * Since: 2.24
607 : : **/
608 : : /**
609 : : * g_variant_get_double:
610 : : * @value: a double #GVariant instance
611 : : *
612 : : * Returns the double precision floating point value of @value.
613 : : *
614 : : * It is an error to call this function with a @value of any type
615 : : * other than %G_VARIANT_TYPE_DOUBLE.
616 : : *
617 : : * Returns: a #gdouble
618 : : *
619 : : * Since: 2.24
620 : : **/
621 : 132338 : NUMERIC_TYPE (DOUBLE, double, gdouble)
622 : :
623 : : /* Container type Constructor / Deconstructors {{{1 */
624 : : /**
625 : : * g_variant_new_maybe:
626 : : * @child_type: (nullable): the #GVariantType of the child, or %NULL
627 : : * @child: (nullable): the child value, or %NULL
628 : : *
629 : : * Depending on if @child is %NULL, either wraps @child inside of a
630 : : * maybe container or creates a Nothing instance for the given @type.
631 : : *
632 : : * At least one of @child_type and @child must be non-%NULL.
633 : : * If @child_type is non-%NULL then it must be a definite type.
634 : : * If they are both non-%NULL then @child_type must be the type
635 : : * of @child.
636 : : *
637 : : * If @child is a floating reference (see g_variant_ref_sink()), the new
638 : : * instance takes ownership of @child.
639 : : *
640 : : * Returns: (transfer none): a floating reference to a new #GVariant maybe instance
641 : : *
642 : : * Since: 2.24
643 : : **/
644 : : GVariant *
645 : 1589 : g_variant_new_maybe (const GVariantType *child_type,
646 : : GVariant *child)
647 : : {
648 : : GVariantType *maybe_type;
649 : : GVariant *value;
650 : :
651 : 1589 : g_return_val_if_fail (child_type == NULL || g_variant_type_is_definite
652 : : (child_type), 0);
653 : 1589 : g_return_val_if_fail (child_type != NULL || child != NULL, NULL);
654 : 1589 : g_return_val_if_fail (child_type == NULL || child == NULL ||
655 : : g_variant_is_of_type (child, child_type),
656 : : NULL);
657 : :
658 : 1589 : if (child_type == NULL)
659 : 305 : child_type = g_variant_get_type (child);
660 : :
661 : 1589 : maybe_type = g_variant_type_new_maybe (child_type);
662 : :
663 : 1589 : if (child != NULL)
664 : : {
665 : : GVariant **children;
666 : : gboolean trusted;
667 : :
668 : 511 : children = g_new (GVariant *, 1);
669 : 511 : children[0] = g_variant_ref_sink (child);
670 : 511 : trusted = g_variant_is_trusted (children[0]);
671 : :
672 : 511 : value = g_variant_new_from_children (maybe_type, children, 1, trusted);
673 : : }
674 : : else
675 : 1078 : value = g_variant_new_from_children (maybe_type, NULL, 0, TRUE);
676 : :
677 : 1589 : g_variant_type_free (maybe_type);
678 : :
679 : 1589 : return value;
680 : : }
681 : :
682 : : /**
683 : : * g_variant_get_maybe:
684 : : * @value: a maybe-typed value
685 : : *
686 : : * Given a maybe-typed #GVariant instance, extract its value. If the
687 : : * value is Nothing, then this function returns %NULL.
688 : : *
689 : : * Returns: (nullable) (transfer full): the contents of @value, or %NULL
690 : : *
691 : : * Since: 2.24
692 : : **/
693 : : GVariant *
694 : 1254 : g_variant_get_maybe (GVariant *value)
695 : : {
696 : 1254 : TYPE_CHECK (value, G_VARIANT_TYPE_MAYBE, NULL);
697 : :
698 : 1254 : if (g_variant_n_children (value))
699 : 598 : return g_variant_get_child_value (value, 0);
700 : :
701 : 656 : return NULL;
702 : : }
703 : :
704 : : /**
705 : : * g_variant_new_variant: (constructor)
706 : : * @value: a #GVariant instance
707 : : *
708 : : * Boxes @value. The result is a #GVariant instance representing a
709 : : * variant containing the original value.
710 : : *
711 : : * If @child is a floating reference (see g_variant_ref_sink()), the new
712 : : * instance takes ownership of @child.
713 : : *
714 : : * Returns: (transfer none): a floating reference to a new variant #GVariant instance
715 : : *
716 : : * Since: 2.24
717 : : **/
718 : : GVariant *
719 : 211520 : g_variant_new_variant (GVariant *value)
720 : : {
721 : 211520 : g_return_val_if_fail (value != NULL, NULL);
722 : :
723 : 211520 : g_variant_ref_sink (value);
724 : :
725 : 423040 : return g_variant_new_from_children (G_VARIANT_TYPE_VARIANT,
726 : 211520 : g_memdup2 (&value, sizeof value),
727 : : 1, g_variant_is_trusted (value));
728 : : }
729 : :
730 : : /**
731 : : * g_variant_get_variant:
732 : : * @value: a variant #GVariant instance
733 : : *
734 : : * Unboxes @value. The result is the #GVariant instance that was
735 : : * contained in @value.
736 : : *
737 : : * Returns: (transfer full): the item contained in the variant
738 : : *
739 : : * Since: 2.24
740 : : **/
741 : : GVariant *
742 : 173811 : g_variant_get_variant (GVariant *value)
743 : : {
744 : 173811 : TYPE_CHECK (value, G_VARIANT_TYPE_VARIANT, NULL);
745 : :
746 : 173811 : return g_variant_get_child_value (value, 0);
747 : : }
748 : :
749 : : /**
750 : : * g_variant_new_array:
751 : : * @child_type: (nullable): the element type of the new array
752 : : * @children: (nullable) (array length=n_children): an array of
753 : : * #GVariant pointers, the children
754 : : * @n_children: the length of @children
755 : : *
756 : : * Creates a new #GVariant array from @children.
757 : : *
758 : : * @child_type must be non-%NULL if @n_children is zero. Otherwise, the
759 : : * child type is determined by inspecting the first element of the
760 : : * @children array. If @child_type is non-%NULL then it must be a
761 : : * definite type.
762 : : *
763 : : * The items of the array are taken from the @children array. No entry
764 : : * in the @children array may be %NULL.
765 : : *
766 : : * All items in the array must have the same type, which must be the
767 : : * same as @child_type, if given.
768 : : *
769 : : * If the @children are floating references (see g_variant_ref_sink()), the
770 : : * new instance takes ownership of them as if via g_variant_ref_sink().
771 : : *
772 : : * Returns: (transfer none): a floating reference to a new #GVariant array
773 : : *
774 : : * Since: 2.24
775 : : **/
776 : : GVariant *
777 : 4182 : g_variant_new_array (const GVariantType *child_type,
778 : : GVariant * const *children,
779 : : gsize n_children)
780 : : {
781 : : GVariantType *array_type;
782 : : GVariant **my_children;
783 : : gboolean trusted;
784 : : GVariant *value;
785 : : gsize i;
786 : :
787 : 4182 : g_return_val_if_fail (n_children > 0 || child_type != NULL, NULL);
788 : 4182 : g_return_val_if_fail (n_children == 0 || children != NULL, NULL);
789 : 4182 : g_return_val_if_fail (child_type == NULL ||
790 : : g_variant_type_is_definite (child_type), NULL);
791 : :
792 : 4182 : my_children = g_new (GVariant *, n_children);
793 : 4182 : trusted = TRUE;
794 : :
795 : 4182 : if (child_type == NULL)
796 : 1941 : child_type = g_variant_get_type (children[0]);
797 : 4182 : array_type = g_variant_type_new_array (child_type);
798 : :
799 : 238190 : for (i = 0; i < n_children; i++)
800 : : {
801 : 234008 : gboolean is_of_child_type = g_variant_is_of_type (children[i], child_type);
802 : 234008 : if G_UNLIKELY (!is_of_child_type)
803 : : {
804 : 0 : while (i != 0)
805 : 0 : g_variant_unref (my_children[--i]);
806 : 0 : g_free (my_children);
807 : 0 : g_return_val_if_fail (is_of_child_type, NULL);
808 : : }
809 : 234008 : my_children[i] = g_variant_ref_sink (children[i]);
810 : 234008 : trusted &= g_variant_is_trusted (children[i]);
811 : : }
812 : :
813 : 4182 : value = g_variant_new_from_children (array_type, my_children,
814 : : n_children, trusted);
815 : 4182 : g_variant_type_free (array_type);
816 : :
817 : 4182 : return value;
818 : : }
819 : :
820 : : /*< private >
821 : : * g_variant_make_tuple_type:
822 : : * @children: (array length=n_children): an array of GVariant *
823 : : * @n_children: the length of @children
824 : : *
825 : : * Return the type of a tuple containing @children as its items.
826 : : **/
827 : : static GVariantType *
828 : 15388 : g_variant_make_tuple_type (GVariant * const *children,
829 : : gsize n_children)
830 : : {
831 : : const GVariantType **types;
832 : : GVariantType *type;
833 : : gsize i;
834 : :
835 : 15388 : types = g_new (const GVariantType *, n_children);
836 : :
837 : 55170 : for (i = 0; i < n_children; i++)
838 : 39782 : types[i] = g_variant_get_type (children[i]);
839 : :
840 : 15388 : type = g_variant_type_new_tuple (types, n_children);
841 : 15388 : g_free (types);
842 : :
843 : 15388 : return type;
844 : : }
845 : :
846 : : /**
847 : : * g_variant_new_tuple:
848 : : * @children: (array length=n_children): the items to make the tuple out of
849 : : * @n_children: the length of @children
850 : : *
851 : : * Creates a new tuple #GVariant out of the items in @children. The
852 : : * type is determined from the types of @children. No entry in the
853 : : * @children array may be %NULL.
854 : : *
855 : : * If @n_children is 0 then the unit tuple is constructed.
856 : : *
857 : : * If the @children are floating references (see g_variant_ref_sink()), the
858 : : * new instance takes ownership of them as if via g_variant_ref_sink().
859 : : *
860 : : * Returns: (transfer none): a floating reference to a new #GVariant tuple
861 : : *
862 : : * Since: 2.24
863 : : **/
864 : : GVariant *
865 : 4527 : g_variant_new_tuple (GVariant * const *children,
866 : : gsize n_children)
867 : : {
868 : : GVariantType *tuple_type;
869 : : GVariant **my_children;
870 : : gboolean trusted;
871 : : GVariant *value;
872 : : gsize i;
873 : :
874 : 4527 : g_return_val_if_fail (n_children == 0 || children != NULL, NULL);
875 : :
876 : 4527 : my_children = g_new (GVariant *, n_children);
877 : 4527 : trusted = TRUE;
878 : :
879 : 28874 : for (i = 0; i < n_children; i++)
880 : : {
881 : 24347 : my_children[i] = g_variant_ref_sink (children[i]);
882 : 24347 : trusted &= g_variant_is_trusted (children[i]);
883 : : }
884 : :
885 : 4527 : tuple_type = g_variant_make_tuple_type (children, n_children);
886 : 4527 : value = g_variant_new_from_children (tuple_type, my_children,
887 : : n_children, trusted);
888 : 4527 : g_variant_type_free (tuple_type);
889 : :
890 : 4527 : return value;
891 : : }
892 : :
893 : : /*< private >
894 : : * g_variant_make_dict_entry_type:
895 : : * @key: a #GVariant, the key
896 : : * @val: a #GVariant, the value
897 : : *
898 : : * Return the type of a dictionary entry containing @key and @val as its
899 : : * children.
900 : : **/
901 : : static GVariantType *
902 : 212674 : g_variant_make_dict_entry_type (GVariant *key,
903 : : GVariant *val)
904 : : {
905 : 212674 : return g_variant_type_new_dict_entry (g_variant_get_type (key),
906 : : g_variant_get_type (val));
907 : : }
908 : :
909 : : /**
910 : : * g_variant_new_dict_entry: (constructor)
911 : : * @key: a basic #GVariant, the key
912 : : * @value: a #GVariant, the value
913 : : *
914 : : * Creates a new dictionary entry #GVariant. @key and @value must be
915 : : * non-%NULL. @key must be a value of a basic type (ie: not a container).
916 : : *
917 : : * If the @key or @value are floating references (see g_variant_ref_sink()),
918 : : * the new instance takes ownership of them as if via g_variant_ref_sink().
919 : : *
920 : : * Returns: (transfer none): a floating reference to a new dictionary entry #GVariant
921 : : *
922 : : * Since: 2.24
923 : : **/
924 : : GVariant *
925 : 143663 : g_variant_new_dict_entry (GVariant *key,
926 : : GVariant *value)
927 : : {
928 : : GVariantType *dict_type;
929 : : GVariant **children;
930 : : gboolean trusted;
931 : :
932 : 143663 : g_return_val_if_fail (key != NULL && value != NULL, NULL);
933 : 143663 : g_return_val_if_fail (!g_variant_is_container (key), NULL);
934 : :
935 : 143663 : children = g_new (GVariant *, 2);
936 : 143663 : children[0] = g_variant_ref_sink (key);
937 : 143663 : children[1] = g_variant_ref_sink (value);
938 : 143663 : trusted = g_variant_is_trusted (key) && g_variant_is_trusted (value);
939 : :
940 : 143663 : dict_type = g_variant_make_dict_entry_type (key, value);
941 : 143663 : value = g_variant_new_from_children (dict_type, children, 2, trusted);
942 : 143663 : g_variant_type_free (dict_type);
943 : :
944 : 143663 : return value;
945 : : }
946 : :
947 : : /**
948 : : * g_variant_lookup: (skip)
949 : : * @dictionary: a dictionary #GVariant
950 : : * @key: the key to look up in the dictionary
951 : : * @format_string: a GVariant format string
952 : : * @...: the arguments to unpack the value into
953 : : *
954 : : * Looks up a value in a dictionary #GVariant.
955 : : *
956 : : * This function is a wrapper around g_variant_lookup_value() and
957 : : * g_variant_get(). In the case that %NULL would have been returned,
958 : : * this function returns %FALSE. Otherwise, it unpacks the returned
959 : : * value and returns %TRUE.
960 : : *
961 : : * @format_string determines the C types that are used for unpacking
962 : : * the values and also determines if the values are copied or borrowed,
963 : : * see the section on
964 : : * [`GVariant` format strings](gvariant-format-strings.html#pointers).
965 : : *
966 : : * This function is currently implemented with a linear scan. If you
967 : : * plan to do many lookups then #GVariantDict may be more efficient.
968 : : *
969 : : * Returns: %TRUE if a value was unpacked
970 : : *
971 : : * Since: 2.28
972 : : */
973 : : gboolean
974 : 34 : g_variant_lookup (GVariant *dictionary,
975 : : const gchar *key,
976 : : const gchar *format_string,
977 : : ...)
978 : : {
979 : : GVariantType *type;
980 : : GVariant *value;
981 : :
982 : : /* flatten */
983 : 34 : g_variant_get_data (dictionary);
984 : :
985 : 34 : type = g_variant_format_string_scan_type (format_string, NULL, NULL);
986 : 34 : value = g_variant_lookup_value (dictionary, key, type);
987 : 34 : g_variant_type_free (type);
988 : :
989 : 34 : if (value)
990 : : {
991 : : va_list ap;
992 : :
993 : 22 : va_start (ap, format_string);
994 : 22 : g_variant_get_va (value, format_string, NULL, &ap);
995 : 22 : g_variant_unref (value);
996 : 22 : va_end (ap);
997 : :
998 : 22 : return TRUE;
999 : : }
1000 : :
1001 : : else
1002 : 12 : return FALSE;
1003 : : }
1004 : :
1005 : : /**
1006 : : * g_variant_lookup_value:
1007 : : * @dictionary: a dictionary #GVariant
1008 : : * @key: the key to look up in the dictionary
1009 : : * @expected_type: (nullable): a #GVariantType, or %NULL
1010 : : *
1011 : : * Looks up a value in a dictionary #GVariant.
1012 : : *
1013 : : * This function works with dictionaries of the type a{s*} (and equally
1014 : : * well with type a{o*}, but we only further discuss the string case
1015 : : * for sake of clarity).
1016 : : *
1017 : : * In the event that @dictionary has the type a{sv}, the @expected_type
1018 : : * string specifies what type of value is expected to be inside of the
1019 : : * variant. If the value inside the variant has a different type then
1020 : : * %NULL is returned. In the event that @dictionary has a value type other
1021 : : * than v then @expected_type must directly match the value type and it is
1022 : : * used to unpack the value directly or an error occurs.
1023 : : *
1024 : : * In either case, if @key is not found in @dictionary, %NULL is returned.
1025 : : *
1026 : : * If the key is found and the value has the correct type, it is
1027 : : * returned. If @expected_type was specified then any non-%NULL return
1028 : : * value will have this type.
1029 : : *
1030 : : * This function is currently implemented with a linear scan. If you
1031 : : * plan to do many lookups then #GVariantDict may be more efficient.
1032 : : *
1033 : : * Returns: (transfer full): the value of the dictionary key, or %NULL
1034 : : *
1035 : : * Since: 2.28
1036 : : */
1037 : : GVariant *
1038 : 45 : g_variant_lookup_value (GVariant *dictionary,
1039 : : const gchar *key,
1040 : : const GVariantType *expected_type)
1041 : : {
1042 : : GVariantIter iter;
1043 : : GVariant *entry;
1044 : : GVariant *value;
1045 : :
1046 : 45 : g_return_val_if_fail (g_variant_is_of_type (dictionary,
1047 : : G_VARIANT_TYPE ("a{s*}")) ||
1048 : : g_variant_is_of_type (dictionary,
1049 : : G_VARIANT_TYPE ("a{o*}")),
1050 : : NULL);
1051 : :
1052 : 45 : g_variant_iter_init (&iter, dictionary);
1053 : :
1054 : 62 : while ((entry = g_variant_iter_next_value (&iter)))
1055 : : {
1056 : : GVariant *entry_key;
1057 : : gboolean matches;
1058 : :
1059 : 49 : entry_key = g_variant_get_child_value (entry, 0);
1060 : 49 : matches = strcmp (g_variant_get_string (entry_key, NULL), key) == 0;
1061 : 49 : g_variant_unref (entry_key);
1062 : :
1063 : 49 : if (matches)
1064 : 32 : break;
1065 : :
1066 : 17 : g_variant_unref (entry);
1067 : : }
1068 : :
1069 : 45 : if (entry == NULL)
1070 : 13 : return NULL;
1071 : :
1072 : 32 : value = g_variant_get_child_value (entry, 1);
1073 : 32 : g_variant_unref (entry);
1074 : :
1075 : 32 : if (g_variant_is_of_type (value, G_VARIANT_TYPE_VARIANT))
1076 : : {
1077 : : GVariant *tmp;
1078 : :
1079 : 30 : tmp = g_variant_get_variant (value);
1080 : 30 : g_variant_unref (value);
1081 : :
1082 : 30 : if (expected_type && !g_variant_is_of_type (tmp, expected_type))
1083 : : {
1084 : 2 : g_variant_unref (tmp);
1085 : 2 : tmp = NULL;
1086 : : }
1087 : :
1088 : 30 : value = tmp;
1089 : : }
1090 : :
1091 : 32 : g_return_val_if_fail (expected_type == NULL || value == NULL ||
1092 : : g_variant_is_of_type (value, expected_type), NULL);
1093 : :
1094 : 32 : return value;
1095 : : }
1096 : :
1097 : : /**
1098 : : * g_variant_get_fixed_array:
1099 : : * @value: a #GVariant array with fixed-sized elements
1100 : : * @n_elements: (out): a pointer to the location to store the number of items
1101 : : * @element_size: the size of each element
1102 : : *
1103 : : * Provides access to the serialized data for an array of fixed-sized
1104 : : * items.
1105 : : *
1106 : : * @value must be an array with fixed-sized elements. Numeric types are
1107 : : * fixed-size, as are tuples containing only other fixed-sized types.
1108 : : *
1109 : : * @element_size must be the size of a single element in the array,
1110 : : * as given by the section on
1111 : : * [serialized data memory](struct.Variant.html#serialized-data-memory).
1112 : : *
1113 : : * In particular, arrays of these fixed-sized types can be interpreted
1114 : : * as an array of the given C type, with @element_size set to the size
1115 : : * the appropriate type:
1116 : : * - %G_VARIANT_TYPE_INT16 (etc.): #gint16 (etc.)
1117 : : * - %G_VARIANT_TYPE_BOOLEAN: #guchar (not #gboolean!)
1118 : : * - %G_VARIANT_TYPE_BYTE: #guint8
1119 : : * - %G_VARIANT_TYPE_HANDLE: #guint32
1120 : : * - %G_VARIANT_TYPE_DOUBLE: #gdouble
1121 : : *
1122 : : * For example, if calling this function for an array of 32-bit integers,
1123 : : * you might say `sizeof(gint32)`. This value isn't used except for the purpose
1124 : : * of a double-check that the form of the serialized data matches the caller's
1125 : : * expectation.
1126 : : *
1127 : : * @n_elements, which must be non-%NULL, is set equal to the number of
1128 : : * items in the array.
1129 : : *
1130 : : * Returns: (array length=n_elements) (transfer none): a pointer to
1131 : : * the fixed array
1132 : : *
1133 : : * Since: 2.24
1134 : : **/
1135 : : gconstpointer
1136 : 28 : g_variant_get_fixed_array (GVariant *value,
1137 : : gsize *n_elements,
1138 : : gsize element_size)
1139 : : {
1140 : : GVariantTypeInfo *array_info;
1141 : : gsize array_element_size;
1142 : : gconstpointer data;
1143 : : gsize size;
1144 : :
1145 : 28 : TYPE_CHECK (value, G_VARIANT_TYPE_ARRAY, NULL);
1146 : :
1147 : 28 : g_return_val_if_fail (n_elements != NULL, NULL);
1148 : 28 : g_return_val_if_fail (element_size > 0, NULL);
1149 : :
1150 : 28 : array_info = g_variant_get_type_info (value);
1151 : 28 : g_variant_type_info_query_element (array_info, NULL, &array_element_size);
1152 : :
1153 : 28 : g_return_val_if_fail (array_element_size, NULL);
1154 : :
1155 : 28 : if G_UNLIKELY (array_element_size != element_size)
1156 : : {
1157 : 0 : if (array_element_size)
1158 : 0 : g_critical ("g_variant_get_fixed_array: assertion "
1159 : : "'g_variant_array_has_fixed_size (value, element_size)' "
1160 : : "failed: array size %"G_GSIZE_FORMAT" does not match "
1161 : : "given element_size %"G_GSIZE_FORMAT".",
1162 : : array_element_size, element_size);
1163 : : else
1164 : 0 : g_critical ("g_variant_get_fixed_array: assertion "
1165 : : "'g_variant_array_has_fixed_size (value, element_size)' "
1166 : : "failed: array does not have fixed size.");
1167 : : }
1168 : :
1169 : 28 : data = g_variant_get_data (value);
1170 : 28 : size = g_variant_get_size (value);
1171 : :
1172 : 28 : if (size % element_size)
1173 : 0 : *n_elements = 0;
1174 : : else
1175 : 28 : *n_elements = size / element_size;
1176 : :
1177 : 28 : if (*n_elements)
1178 : 28 : return data;
1179 : :
1180 : 0 : return NULL;
1181 : : }
1182 : :
1183 : : /**
1184 : : * g_variant_new_fixed_array:
1185 : : * @element_type: the #GVariantType of each element
1186 : : * @elements: a pointer to the fixed array of contiguous elements
1187 : : * @n_elements: the number of elements
1188 : : * @element_size: the size of each element
1189 : : *
1190 : : * Constructs a new array #GVariant instance, where the elements are
1191 : : * of @element_type type.
1192 : : *
1193 : : * @elements must be an array with fixed-sized elements. Numeric types are
1194 : : * fixed-size as are tuples containing only other fixed-sized types.
1195 : : *
1196 : : * @element_size must be the size of a single element in the array.
1197 : : * For example, if calling this function for an array of 32-bit integers,
1198 : : * you might say sizeof(gint32). This value isn't used except for the purpose
1199 : : * of a double-check that the form of the serialized data matches the caller's
1200 : : * expectation.
1201 : : *
1202 : : * @n_elements must be the length of the @elements array.
1203 : : *
1204 : : * Returns: (transfer none): a floating reference to a new array #GVariant instance
1205 : : *
1206 : : * Since: 2.32
1207 : : **/
1208 : : GVariant *
1209 : 756 : g_variant_new_fixed_array (const GVariantType *element_type,
1210 : : gconstpointer elements,
1211 : : gsize n_elements,
1212 : : gsize element_size)
1213 : : {
1214 : : GVariantType *array_type;
1215 : : gsize array_element_size;
1216 : : GVariantTypeInfo *array_info;
1217 : : GVariant *value;
1218 : : gpointer data;
1219 : :
1220 : 756 : g_return_val_if_fail (g_variant_type_is_definite (element_type), NULL);
1221 : 756 : g_return_val_if_fail (element_size > 0, NULL);
1222 : :
1223 : 756 : array_type = g_variant_type_new_array (element_type);
1224 : 756 : array_info = g_variant_type_info_get (array_type);
1225 : 756 : g_variant_type_info_query_element (array_info, NULL, &array_element_size);
1226 : 756 : if G_UNLIKELY (array_element_size != element_size)
1227 : : {
1228 : 0 : if (array_element_size)
1229 : 0 : g_critical ("g_variant_new_fixed_array: array size %" G_GSIZE_FORMAT
1230 : : " does not match given element_size %" G_GSIZE_FORMAT ".",
1231 : : array_element_size, element_size);
1232 : : else
1233 : 0 : g_critical ("g_variant_get_fixed_array: array does not have fixed size.");
1234 : 0 : return NULL;
1235 : : }
1236 : :
1237 : 756 : data = g_memdup2 (elements, n_elements * element_size);
1238 : 756 : value = g_variant_new_from_data (array_type, data,
1239 : : n_elements * element_size,
1240 : : FALSE, g_free, data);
1241 : :
1242 : 756 : g_variant_type_free (array_type);
1243 : 756 : g_variant_type_info_unref (array_info);
1244 : :
1245 : 756 : return value;
1246 : : }
1247 : :
1248 : : /* String type constructor/getters/validation {{{1 */
1249 : : /**
1250 : : * g_variant_new_string:
1251 : : * @string: a normal UTF-8 nul-terminated string
1252 : : *
1253 : : * Creates a string #GVariant with the contents of @string.
1254 : : *
1255 : : * @string must be valid UTF-8, and must not be %NULL. To encode
1256 : : * potentially-%NULL strings, use g_variant_new() with `ms` as the
1257 : : * [format string](gvariant-format-strings.html#maybe-types).
1258 : : *
1259 : : * Returns: (transfer none): a floating reference to a new string #GVariant instance
1260 : : *
1261 : : * Since: 2.24
1262 : : **/
1263 : : GVariant *
1264 : 899337 : g_variant_new_string (const gchar *string)
1265 : : {
1266 : 899337 : const char *endptr = NULL;
1267 : :
1268 : 899337 : g_return_val_if_fail (string != NULL, NULL);
1269 : :
1270 : 899337 : if G_LIKELY (g_utf8_validate (string, -1, &endptr))
1271 : 899337 : return g_variant_new_from_trusted (G_VARIANT_TYPE_STRING,
1272 : 899337 : string, endptr - string + 1);
1273 : :
1274 : 0 : g_critical ("g_variant_new_string(): requires valid UTF-8");
1275 : :
1276 : 0 : return NULL;
1277 : : }
1278 : :
1279 : : /**
1280 : : * g_variant_new_take_string: (skip)
1281 : : * @string: a normal UTF-8 nul-terminated string
1282 : : *
1283 : : * Creates a string #GVariant with the contents of @string.
1284 : : *
1285 : : * @string must be valid UTF-8, and must not be %NULL. To encode
1286 : : * potentially-%NULL strings, use this with g_variant_new_maybe().
1287 : : *
1288 : : * After this call, @string belongs to the #GVariant and may no longer be
1289 : : * modified by the caller. The memory of @data has to be dynamically
1290 : : * allocated and will eventually be freed with g_free().
1291 : : *
1292 : : * You must not modify or access @string in any other way after passing
1293 : : * it to this function. It is even possible that @string is immediately
1294 : : * freed.
1295 : : *
1296 : : * Returns: (transfer none): a floating reference to a new string
1297 : : * #GVariant instance
1298 : : *
1299 : : * Since: 2.38
1300 : : **/
1301 : : GVariant *
1302 : 7 : g_variant_new_take_string (gchar *string)
1303 : : {
1304 : 7 : const char *end = NULL;
1305 : :
1306 : 7 : g_return_val_if_fail (string != NULL, NULL);
1307 : :
1308 : 7 : if G_LIKELY (g_utf8_validate (string, -1, &end))
1309 : : {
1310 : 7 : GBytes *bytes = g_bytes_new_take (string, end - string + 1);
1311 : 7 : return g_variant_new_take_bytes (G_VARIANT_TYPE_STRING, g_steal_pointer (&bytes), TRUE);
1312 : : }
1313 : :
1314 : 0 : g_critical ("g_variant_new_take_string(): requires valid UTF-8");
1315 : :
1316 : 0 : return NULL;
1317 : : }
1318 : :
1319 : : /**
1320 : : * g_variant_new_printf: (skip)
1321 : : * @format_string: a printf-style format string
1322 : : * @...: arguments for @format_string
1323 : : *
1324 : : * Creates a string-type GVariant using printf formatting.
1325 : : *
1326 : : * This is similar to calling g_strdup_printf() and then
1327 : : * g_variant_new_string() but it saves a temporary variable and an
1328 : : * unnecessary copy.
1329 : : *
1330 : : * Returns: (transfer none): a floating reference to a new string
1331 : : * #GVariant instance
1332 : : *
1333 : : * Since: 2.38
1334 : : **/
1335 : : GVariant *
1336 : 1 : g_variant_new_printf (const gchar *format_string,
1337 : : ...)
1338 : : {
1339 : : GVariant *value;
1340 : : GBytes *bytes;
1341 : : gchar *string;
1342 : : va_list ap;
1343 : :
1344 : 1 : g_return_val_if_fail (format_string != NULL, NULL);
1345 : :
1346 : 1 : va_start (ap, format_string);
1347 : 1 : string = g_strdup_vprintf (format_string, ap);
1348 : 1 : va_end (ap);
1349 : :
1350 : 1 : bytes = g_bytes_new_take (string, strlen (string) + 1);
1351 : 1 : value = g_variant_new_take_bytes (G_VARIANT_TYPE_STRING, g_steal_pointer (&bytes), TRUE);
1352 : :
1353 : 1 : return value;
1354 : : }
1355 : :
1356 : : /**
1357 : : * g_variant_new_object_path:
1358 : : * @object_path: a normal C nul-terminated string
1359 : : *
1360 : : * Creates a D-Bus object path #GVariant with the contents of @object_path.
1361 : : * @object_path must be a valid D-Bus object path. Use
1362 : : * g_variant_is_object_path() if you're not sure.
1363 : : *
1364 : : * Returns: (transfer none): a floating reference to a new object path #GVariant instance
1365 : : *
1366 : : * Since: 2.24
1367 : : **/
1368 : : GVariant *
1369 : 42976 : g_variant_new_object_path (const gchar *object_path)
1370 : : {
1371 : 42976 : g_return_val_if_fail (g_variant_is_object_path (object_path), NULL);
1372 : :
1373 : 42976 : return g_variant_new_from_trusted (G_VARIANT_TYPE_OBJECT_PATH,
1374 : 42976 : object_path, strlen (object_path) + 1);
1375 : : }
1376 : :
1377 : : /**
1378 : : * g_variant_is_object_path:
1379 : : * @string: a normal C nul-terminated string
1380 : : *
1381 : : * Determines if a given string is a valid D-Bus object path. You
1382 : : * should ensure that a string is a valid D-Bus object path before
1383 : : * passing it to g_variant_new_object_path().
1384 : : *
1385 : : * A valid object path starts with `/` followed by zero or more
1386 : : * sequences of characters separated by `/` characters. Each sequence
1387 : : * must contain only the characters `[A-Z][a-z][0-9]_`. No sequence
1388 : : * (including the one following the final `/` character) may be empty.
1389 : : *
1390 : : * Returns: %TRUE if @string is a D-Bus object path
1391 : : *
1392 : : * Since: 2.24
1393 : : **/
1394 : : gboolean
1395 : 322174 : g_variant_is_object_path (const gchar *string)
1396 : : {
1397 : 322174 : g_return_val_if_fail (string != NULL, FALSE);
1398 : :
1399 : 322174 : return g_variant_serialiser_is_object_path (string, strlen (string) + 1);
1400 : : }
1401 : :
1402 : : /**
1403 : : * g_variant_new_signature:
1404 : : * @signature: a normal C nul-terminated string
1405 : : *
1406 : : * Creates a D-Bus type signature #GVariant with the contents of
1407 : : * @string. @string must be a valid D-Bus type signature. Use
1408 : : * g_variant_is_signature() if you're not sure.
1409 : : *
1410 : : * Returns: (transfer none): a floating reference to a new signature #GVariant instance
1411 : : *
1412 : : * Since: 2.24
1413 : : **/
1414 : : GVariant *
1415 : 603648 : g_variant_new_signature (const gchar *signature)
1416 : : {
1417 : 603648 : g_return_val_if_fail (g_variant_is_signature (signature), NULL);
1418 : :
1419 : 603648 : return g_variant_new_from_trusted (G_VARIANT_TYPE_SIGNATURE,
1420 : 603648 : signature, strlen (signature) + 1);
1421 : : }
1422 : :
1423 : : /**
1424 : : * g_variant_is_signature:
1425 : : * @string: a normal C nul-terminated string
1426 : : *
1427 : : * Determines if a given string is a valid D-Bus type signature. You
1428 : : * should ensure that a string is a valid D-Bus type signature before
1429 : : * passing it to g_variant_new_signature().
1430 : : *
1431 : : * D-Bus type signatures consist of zero or more definite #GVariantType
1432 : : * strings in sequence.
1433 : : *
1434 : : * Returns: %TRUE if @string is a D-Bus type signature
1435 : : *
1436 : : * Since: 2.24
1437 : : **/
1438 : : gboolean
1439 : 1187309 : g_variant_is_signature (const gchar *string)
1440 : : {
1441 : 1187309 : g_return_val_if_fail (string != NULL, FALSE);
1442 : :
1443 : 1187309 : return g_variant_serialiser_is_signature (string, strlen (string) + 1);
1444 : : }
1445 : :
1446 : : /**
1447 : : * g_variant_get_string:
1448 : : * @value: a string #GVariant instance
1449 : : * @length: (optional) (default 0) (out): a pointer to a #gsize,
1450 : : * to store the length
1451 : : *
1452 : : * Returns the string value of a #GVariant instance with a string
1453 : : * type. This includes the types %G_VARIANT_TYPE_STRING,
1454 : : * %G_VARIANT_TYPE_OBJECT_PATH and %G_VARIANT_TYPE_SIGNATURE.
1455 : : *
1456 : : * The string will always be UTF-8 encoded, will never be %NULL, and will never
1457 : : * contain nul bytes.
1458 : : *
1459 : : * If @length is non-%NULL then the length of the string (in bytes) is
1460 : : * returned there. For trusted values, this information is already
1461 : : * known. Untrusted values will be validated and, if valid, a strlen() will be
1462 : : * performed. If invalid, a default value will be returned — for
1463 : : * %G_VARIANT_TYPE_OBJECT_PATH, this is `"/"`, and for other types it is the
1464 : : * empty string.
1465 : : *
1466 : : * It is an error to call this function with a @value of any type
1467 : : * other than those three.
1468 : : *
1469 : : * The return value remains valid as long as @value exists.
1470 : : *
1471 : : * Returns: (transfer none): the constant string, UTF-8 encoded
1472 : : *
1473 : : * Since: 2.24
1474 : : **/
1475 : : const gchar *
1476 : 1306396 : g_variant_get_string (GVariant *value,
1477 : : gsize *length)
1478 : : {
1479 : : gconstpointer data;
1480 : : gsize size;
1481 : :
1482 : 1306396 : g_return_val_if_fail (value != NULL, NULL);
1483 : 1306396 : g_return_val_if_fail (
1484 : : g_variant_is_of_type (value, G_VARIANT_TYPE_STRING) ||
1485 : : g_variant_is_of_type (value, G_VARIANT_TYPE_OBJECT_PATH) ||
1486 : : g_variant_is_of_type (value, G_VARIANT_TYPE_SIGNATURE), NULL);
1487 : :
1488 : 1306396 : data = g_variant_get_data (value);
1489 : 1306396 : size = g_variant_get_size (value);
1490 : :
1491 : 1306396 : if (!g_variant_is_trusted (value))
1492 : : {
1493 : 11916 : switch (g_variant_classify (value))
1494 : : {
1495 : 3149 : case G_VARIANT_CLASS_STRING:
1496 : 3149 : if (g_variant_serialiser_is_string (data, size))
1497 : 2828 : break;
1498 : :
1499 : 321 : data = "";
1500 : 321 : size = 1;
1501 : 321 : break;
1502 : :
1503 : 6327 : case G_VARIANT_CLASS_OBJECT_PATH:
1504 : 6327 : if (g_variant_serialiser_is_object_path (data, size))
1505 : 6063 : break;
1506 : :
1507 : 264 : data = "/";
1508 : 264 : size = 2;
1509 : 264 : break;
1510 : :
1511 : 2440 : case G_VARIANT_CLASS_SIGNATURE:
1512 : 2440 : if (g_variant_serialiser_is_signature (data, size))
1513 : 2167 : break;
1514 : :
1515 : 273 : data = "";
1516 : 273 : size = 1;
1517 : 273 : break;
1518 : :
1519 : 0 : default:
1520 : : g_assert_not_reached ();
1521 : : }
1522 : : }
1523 : :
1524 : 1306396 : if (length)
1525 : 105612 : *length = size - 1;
1526 : :
1527 : 1306396 : return data;
1528 : : }
1529 : :
1530 : : /**
1531 : : * g_variant_dup_string:
1532 : : * @value: a string #GVariant instance
1533 : : * @length: (out): a pointer to a #gsize, to store the length
1534 : : *
1535 : : * Similar to g_variant_get_string() except that instead of returning
1536 : : * a constant string, the string is duplicated.
1537 : : *
1538 : : * The string will always be UTF-8 encoded.
1539 : : *
1540 : : * The return value must be freed using g_free().
1541 : : *
1542 : : * Returns: (transfer full): a newly allocated string, UTF-8 encoded
1543 : : *
1544 : : * Since: 2.24
1545 : : **/
1546 : : gchar *
1547 : 2264 : g_variant_dup_string (GVariant *value,
1548 : : gsize *length)
1549 : : {
1550 : 4528 : return g_strdup (g_variant_get_string (value, length));
1551 : : }
1552 : :
1553 : : /**
1554 : : * g_variant_new_strv:
1555 : : * @strv: (array length=length) (element-type utf8): an array of strings
1556 : : * @length: the length of @strv, or -1
1557 : : *
1558 : : * Constructs an array of strings #GVariant from the given array of
1559 : : * strings.
1560 : : *
1561 : : * If @length is -1 then @strv is %NULL-terminated.
1562 : : *
1563 : : * Returns: (transfer none): a new floating #GVariant instance
1564 : : *
1565 : : * Since: 2.24
1566 : : **/
1567 : : GVariant *
1568 : 92 : g_variant_new_strv (const gchar * const *strv,
1569 : : gssize length)
1570 : : {
1571 : : GVariant **strings;
1572 : : gsize i, length_unsigned;
1573 : :
1574 : 92 : g_return_val_if_fail (length == 0 || strv != NULL, NULL);
1575 : :
1576 : 92 : if (length < 0)
1577 : 87 : length = g_strv_length ((gchar **) strv);
1578 : 92 : length_unsigned = length;
1579 : :
1580 : 92 : strings = g_new (GVariant *, length_unsigned);
1581 : 219 : for (i = 0; i < length_unsigned; i++)
1582 : 127 : strings[i] = g_variant_ref_sink (g_variant_new_string (strv[i]));
1583 : :
1584 : 92 : return g_variant_new_from_children (G_VARIANT_TYPE_STRING_ARRAY,
1585 : : strings, length_unsigned, TRUE);
1586 : : }
1587 : :
1588 : : /**
1589 : : * g_variant_get_strv:
1590 : : * @value: an array of strings #GVariant
1591 : : * @length: (out) (optional): the length of the result, or %NULL
1592 : : *
1593 : : * Gets the contents of an array of strings #GVariant. This call
1594 : : * makes a shallow copy; the return result should be released with
1595 : : * g_free(), but the individual strings must not be modified.
1596 : : *
1597 : : * If @length is non-%NULL then the number of elements in the result
1598 : : * is stored there. In any case, the resulting array will be
1599 : : * %NULL-terminated.
1600 : : *
1601 : : * For an empty array, @length will be set to 0 and a pointer to a
1602 : : * %NULL pointer will be returned.
1603 : : *
1604 : : * Returns: (array length=length zero-terminated=1) (transfer container): an array of constant strings
1605 : : *
1606 : : * Since: 2.24
1607 : : **/
1608 : : const gchar **
1609 : 109 : g_variant_get_strv (GVariant *value,
1610 : : gsize *length)
1611 : : {
1612 : : const gchar **strv;
1613 : : gsize n;
1614 : : gsize i;
1615 : :
1616 : 109 : TYPE_CHECK (value, G_VARIANT_TYPE_STRING_ARRAY, NULL);
1617 : :
1618 : 109 : g_variant_get_data (value);
1619 : 109 : n = g_variant_n_children (value);
1620 : 109 : strv = g_new (const gchar *, n + 1);
1621 : :
1622 : 209 : for (i = 0; i < n; i++)
1623 : : {
1624 : : GVariant *string;
1625 : :
1626 : 100 : string = g_variant_get_child_value (value, i);
1627 : 100 : strv[i] = g_variant_get_string (string, NULL);
1628 : 100 : g_variant_unref (string);
1629 : : }
1630 : 109 : strv[i] = NULL;
1631 : :
1632 : 109 : if (length)
1633 : 9 : *length = n;
1634 : :
1635 : 109 : return strv;
1636 : : }
1637 : :
1638 : : /**
1639 : : * g_variant_dup_strv:
1640 : : * @value: an array of strings #GVariant
1641 : : * @length: (out) (optional): the length of the result, or %NULL
1642 : : *
1643 : : * Gets the contents of an array of strings #GVariant. This call
1644 : : * makes a deep copy; the return result should be released with
1645 : : * g_strfreev().
1646 : : *
1647 : : * If @length is non-%NULL then the number of elements in the result
1648 : : * is stored there. In any case, the resulting array will be
1649 : : * %NULL-terminated.
1650 : : *
1651 : : * For an empty array, @length will be set to 0 and a pointer to a
1652 : : * %NULL pointer will be returned.
1653 : : *
1654 : : * Returns: (array length=length zero-terminated=1) (transfer full): an array of strings
1655 : : *
1656 : : * Since: 2.24
1657 : : **/
1658 : : gchar **
1659 : 36 : g_variant_dup_strv (GVariant *value,
1660 : : gsize *length)
1661 : : {
1662 : : gchar **strv;
1663 : : gsize n;
1664 : : gsize i;
1665 : :
1666 : 36 : TYPE_CHECK (value, G_VARIANT_TYPE_STRING_ARRAY, NULL);
1667 : :
1668 : 36 : n = g_variant_n_children (value);
1669 : 36 : strv = g_new (gchar *, n + 1);
1670 : :
1671 : 102 : for (i = 0; i < n; i++)
1672 : : {
1673 : : GVariant *string;
1674 : :
1675 : 66 : string = g_variant_get_child_value (value, i);
1676 : 66 : strv[i] = g_variant_dup_string (string, NULL);
1677 : 66 : g_variant_unref (string);
1678 : : }
1679 : 36 : strv[i] = NULL;
1680 : :
1681 : 36 : if (length)
1682 : 0 : *length = n;
1683 : :
1684 : 36 : return strv;
1685 : : }
1686 : :
1687 : : /**
1688 : : * g_variant_new_objv:
1689 : : * @strv: (array length=length) (element-type utf8): an array of strings
1690 : : * @length: the length of @strv, or -1
1691 : : *
1692 : : * Constructs an array of object paths #GVariant from the given array of
1693 : : * strings.
1694 : : *
1695 : : * Each string must be a valid #GVariant object path; see
1696 : : * g_variant_is_object_path().
1697 : : *
1698 : : * If @length is -1 then @strv is %NULL-terminated.
1699 : : *
1700 : : * Returns: (transfer none): a new floating #GVariant instance
1701 : : *
1702 : : * Since: 2.30
1703 : : **/
1704 : : GVariant *
1705 : 56 : g_variant_new_objv (const gchar * const *strv,
1706 : : gssize length)
1707 : : {
1708 : : GVariant **strings;
1709 : : gsize i, length_unsigned;
1710 : :
1711 : 56 : g_return_val_if_fail (length == 0 || strv != NULL, NULL);
1712 : :
1713 : 56 : if (length < 0)
1714 : 56 : length = g_strv_length ((gchar **) strv);
1715 : 56 : length_unsigned = length;
1716 : :
1717 : 56 : strings = g_new (GVariant *, length_unsigned);
1718 : 84 : for (i = 0; i < length_unsigned; i++)
1719 : 28 : strings[i] = g_variant_ref_sink (g_variant_new_object_path (strv[i]));
1720 : :
1721 : 56 : return g_variant_new_from_children (G_VARIANT_TYPE_OBJECT_PATH_ARRAY,
1722 : : strings, length_unsigned, TRUE);
1723 : : }
1724 : :
1725 : : /**
1726 : : * g_variant_get_objv:
1727 : : * @value: an array of object paths #GVariant
1728 : : * @length: (out) (optional): the length of the result, or %NULL
1729 : : *
1730 : : * Gets the contents of an array of object paths #GVariant. This call
1731 : : * makes a shallow copy; the return result should be released with
1732 : : * g_free(), but the individual strings must not be modified.
1733 : : *
1734 : : * If @length is non-%NULL then the number of elements in the result
1735 : : * is stored there. In any case, the resulting array will be
1736 : : * %NULL-terminated.
1737 : : *
1738 : : * For an empty array, @length will be set to 0 and a pointer to a
1739 : : * %NULL pointer will be returned.
1740 : : *
1741 : : * Returns: (array length=length zero-terminated=1) (transfer container): an array of constant strings
1742 : : *
1743 : : * Since: 2.30
1744 : : **/
1745 : : const gchar **
1746 : 1 : g_variant_get_objv (GVariant *value,
1747 : : gsize *length)
1748 : : {
1749 : : const gchar **strv;
1750 : : gsize n;
1751 : : gsize i;
1752 : :
1753 : 1 : TYPE_CHECK (value, G_VARIANT_TYPE_OBJECT_PATH_ARRAY, NULL);
1754 : :
1755 : 1 : g_variant_get_data (value);
1756 : 1 : n = g_variant_n_children (value);
1757 : 1 : strv = g_new (const gchar *, n + 1);
1758 : :
1759 : 3 : for (i = 0; i < n; i++)
1760 : : {
1761 : : GVariant *string;
1762 : :
1763 : 2 : string = g_variant_get_child_value (value, i);
1764 : 2 : strv[i] = g_variant_get_string (string, NULL);
1765 : 2 : g_variant_unref (string);
1766 : : }
1767 : 1 : strv[i] = NULL;
1768 : :
1769 : 1 : if (length)
1770 : 0 : *length = n;
1771 : :
1772 : 1 : return strv;
1773 : : }
1774 : :
1775 : : /**
1776 : : * g_variant_dup_objv:
1777 : : * @value: an array of object paths #GVariant
1778 : : * @length: (out) (optional): the length of the result, or %NULL
1779 : : *
1780 : : * Gets the contents of an array of object paths #GVariant. This call
1781 : : * makes a deep copy; the return result should be released with
1782 : : * g_strfreev().
1783 : : *
1784 : : * If @length is non-%NULL then the number of elements in the result
1785 : : * is stored there. In any case, the resulting array will be
1786 : : * %NULL-terminated.
1787 : : *
1788 : : * For an empty array, @length will be set to 0 and a pointer to a
1789 : : * %NULL pointer will be returned.
1790 : : *
1791 : : * Returns: (array length=length zero-terminated=1) (transfer full): an array of strings
1792 : : *
1793 : : * Since: 2.30
1794 : : **/
1795 : : gchar **
1796 : 16 : g_variant_dup_objv (GVariant *value,
1797 : : gsize *length)
1798 : : {
1799 : : gchar **strv;
1800 : : gsize n;
1801 : : gsize i;
1802 : :
1803 : 16 : TYPE_CHECK (value, G_VARIANT_TYPE_OBJECT_PATH_ARRAY, NULL);
1804 : :
1805 : 16 : n = g_variant_n_children (value);
1806 : 16 : strv = g_new (gchar *, n + 1);
1807 : :
1808 : 36 : for (i = 0; i < n; i++)
1809 : : {
1810 : : GVariant *string;
1811 : :
1812 : 20 : string = g_variant_get_child_value (value, i);
1813 : 20 : strv[i] = g_variant_dup_string (string, NULL);
1814 : 20 : g_variant_unref (string);
1815 : : }
1816 : 16 : strv[i] = NULL;
1817 : :
1818 : 16 : if (length)
1819 : 0 : *length = n;
1820 : :
1821 : 16 : return strv;
1822 : : }
1823 : :
1824 : :
1825 : : /**
1826 : : * g_variant_new_bytestring:
1827 : : * @string: (array zero-terminated=1) (element-type guint8): a normal
1828 : : * nul-terminated string in no particular encoding
1829 : : *
1830 : : * Creates an array-of-bytes #GVariant with the contents of @string.
1831 : : * This function is just like g_variant_new_string() except that the
1832 : : * string need not be valid UTF-8.
1833 : : *
1834 : : * The nul terminator character at the end of the string is stored in
1835 : : * the array.
1836 : : *
1837 : : * Returns: (transfer none): a floating reference to a new bytestring #GVariant instance
1838 : : *
1839 : : * Since: 2.26
1840 : : **/
1841 : : GVariant *
1842 : 179 : g_variant_new_bytestring (const gchar *string)
1843 : : {
1844 : 179 : g_return_val_if_fail (string != NULL, NULL);
1845 : :
1846 : 179 : return g_variant_new_from_trusted (G_VARIANT_TYPE_BYTESTRING,
1847 : 179 : string, strlen (string) + 1);
1848 : : }
1849 : :
1850 : : /**
1851 : : * g_variant_get_bytestring:
1852 : : * @value: an array-of-bytes #GVariant instance
1853 : : *
1854 : : * Returns the string value of a #GVariant instance with an
1855 : : * array-of-bytes type. The string has no particular encoding.
1856 : : *
1857 : : * If the array does not end with a nul terminator character, the empty
1858 : : * string is returned. For this reason, you can always trust that a
1859 : : * non-%NULL nul-terminated string will be returned by this function.
1860 : : *
1861 : : * If the array contains a nul terminator character somewhere other than
1862 : : * the last byte then the returned string is the string, up to the first
1863 : : * such nul character.
1864 : : *
1865 : : * g_variant_get_fixed_array() should be used instead if the array contains
1866 : : * arbitrary data that could not be nul-terminated or could contain nul bytes.
1867 : : *
1868 : : * It is an error to call this function with a @value that is not an
1869 : : * array of bytes.
1870 : : *
1871 : : * The return value remains valid as long as @value exists.
1872 : : *
1873 : : * Returns: (transfer none) (array zero-terminated=1) (element-type guint8):
1874 : : * the constant string
1875 : : *
1876 : : * Since: 2.26
1877 : : **/
1878 : : const gchar *
1879 : 112 : g_variant_get_bytestring (GVariant *value)
1880 : : {
1881 : : const gchar *string;
1882 : : gsize size;
1883 : :
1884 : 112 : TYPE_CHECK (value, G_VARIANT_TYPE_BYTESTRING, NULL);
1885 : :
1886 : : /* Won't be NULL since this is an array type */
1887 : 112 : string = g_variant_get_data (value);
1888 : 112 : size = g_variant_get_size (value);
1889 : :
1890 : 112 : if (size && string[size - 1] == '\0')
1891 : 110 : return string;
1892 : : else
1893 : 2 : return "";
1894 : : }
1895 : :
1896 : : /**
1897 : : * g_variant_dup_bytestring:
1898 : : * @value: an array-of-bytes #GVariant instance
1899 : : * @length: (out) (optional) (default NULL): a pointer to a #gsize, to store
1900 : : * the length (not including the nul terminator)
1901 : : *
1902 : : * Similar to g_variant_get_bytestring() except that instead of
1903 : : * returning a constant string, the string is duplicated.
1904 : : *
1905 : : * The return value must be freed using g_free().
1906 : : *
1907 : : * Returns: (transfer full) (array zero-terminated=1 length=length) (element-type guint8):
1908 : : * a newly allocated string
1909 : : *
1910 : : * Since: 2.26
1911 : : **/
1912 : : gchar *
1913 : 60 : g_variant_dup_bytestring (GVariant *value,
1914 : : gsize *length)
1915 : : {
1916 : 60 : const gchar *original = g_variant_get_bytestring (value);
1917 : : gsize size;
1918 : :
1919 : : /* don't crash in case get_bytestring() had an assert failure */
1920 : 60 : if (original == NULL)
1921 : 0 : return NULL;
1922 : :
1923 : 60 : size = strlen (original);
1924 : :
1925 : 60 : if (length)
1926 : 0 : *length = size;
1927 : :
1928 : 60 : return g_memdup2 (original, size + 1);
1929 : : }
1930 : :
1931 : : /**
1932 : : * g_variant_new_bytestring_array:
1933 : : * @strv: (array length=length): an array of strings
1934 : : * @length: the length of @strv, or -1
1935 : : *
1936 : : * Constructs an array of bytestring #GVariant from the given array of
1937 : : * strings.
1938 : : *
1939 : : * If @length is -1 then @strv is %NULL-terminated.
1940 : : *
1941 : : * Returns: (transfer none): a new floating #GVariant instance
1942 : : *
1943 : : * Since: 2.26
1944 : : **/
1945 : : GVariant *
1946 : 44 : g_variant_new_bytestring_array (const gchar * const *strv,
1947 : : gssize length)
1948 : : {
1949 : : GVariant **strings;
1950 : : gsize i, length_unsigned;
1951 : :
1952 : 44 : g_return_val_if_fail (length == 0 || strv != NULL, NULL);
1953 : :
1954 : 44 : if (length < 0)
1955 : 44 : length = g_strv_length ((gchar **) strv);
1956 : 44 : length_unsigned = length;
1957 : :
1958 : 44 : strings = g_new (GVariant *, length_unsigned);
1959 : 92 : for (i = 0; i < length_unsigned; i++)
1960 : 48 : strings[i] = g_variant_ref_sink (g_variant_new_bytestring (strv[i]));
1961 : :
1962 : 44 : return g_variant_new_from_children (G_VARIANT_TYPE_BYTESTRING_ARRAY,
1963 : : strings, length_unsigned, TRUE);
1964 : : }
1965 : :
1966 : : /**
1967 : : * g_variant_get_bytestring_array:
1968 : : * @value: an array of array of bytes #GVariant ('aay')
1969 : : * @length: (out) (optional): the length of the result, or %NULL
1970 : : *
1971 : : * Gets the contents of an array of array of bytes #GVariant. This call
1972 : : * makes a shallow copy; the return result should be released with
1973 : : * g_free(), but the individual strings must not be modified.
1974 : : *
1975 : : * If @length is non-%NULL then the number of elements in the result is
1976 : : * stored there. In any case, the resulting array will be
1977 : : * %NULL-terminated.
1978 : : *
1979 : : * For an empty array, @length will be set to 0 and a pointer to a
1980 : : * %NULL pointer will be returned.
1981 : : *
1982 : : * Returns: (array length=length) (transfer container): an array of constant strings
1983 : : *
1984 : : * Since: 2.26
1985 : : **/
1986 : : const gchar **
1987 : 6 : g_variant_get_bytestring_array (GVariant *value,
1988 : : gsize *length)
1989 : : {
1990 : : const gchar **strv;
1991 : : gsize n;
1992 : : gsize i;
1993 : :
1994 : 6 : TYPE_CHECK (value, G_VARIANT_TYPE_BYTESTRING_ARRAY, NULL);
1995 : :
1996 : 6 : g_variant_get_data (value);
1997 : 6 : n = g_variant_n_children (value);
1998 : 6 : strv = g_new (const gchar *, n + 1);
1999 : :
2000 : 24 : for (i = 0; i < n; i++)
2001 : : {
2002 : : GVariant *string;
2003 : :
2004 : 18 : string = g_variant_get_child_value (value, i);
2005 : 18 : strv[i] = g_variant_get_bytestring (string);
2006 : 18 : g_variant_unref (string);
2007 : : }
2008 : 6 : strv[i] = NULL;
2009 : :
2010 : 6 : if (length)
2011 : 0 : *length = n;
2012 : :
2013 : 6 : return strv;
2014 : : }
2015 : :
2016 : : /**
2017 : : * g_variant_dup_bytestring_array:
2018 : : * @value: an array of array of bytes #GVariant ('aay')
2019 : : * @length: (out) (optional): the length of the result, or %NULL
2020 : : *
2021 : : * Gets the contents of an array of array of bytes #GVariant. This call
2022 : : * makes a deep copy; the return result should be released with
2023 : : * g_strfreev().
2024 : : *
2025 : : * If @length is non-%NULL then the number of elements in the result is
2026 : : * stored there. In any case, the resulting array will be
2027 : : * %NULL-terminated.
2028 : : *
2029 : : * For an empty array, @length will be set to 0 and a pointer to a
2030 : : * %NULL pointer will be returned.
2031 : : *
2032 : : * Returns: (array length=length) (transfer full): an array of strings
2033 : : *
2034 : : * Since: 2.26
2035 : : **/
2036 : : gchar **
2037 : 18 : g_variant_dup_bytestring_array (GVariant *value,
2038 : : gsize *length)
2039 : : {
2040 : : gchar **strv;
2041 : : gsize n;
2042 : : gsize i;
2043 : :
2044 : 18 : TYPE_CHECK (value, G_VARIANT_TYPE_BYTESTRING_ARRAY, NULL);
2045 : :
2046 : 18 : g_variant_get_data (value);
2047 : 18 : n = g_variant_n_children (value);
2048 : 18 : strv = g_new (gchar *, n + 1);
2049 : :
2050 : 64 : for (i = 0; i < n; i++)
2051 : : {
2052 : : GVariant *string;
2053 : :
2054 : 46 : string = g_variant_get_child_value (value, i);
2055 : 46 : strv[i] = g_variant_dup_bytestring (string, NULL);
2056 : 46 : g_variant_unref (string);
2057 : : }
2058 : 18 : strv[i] = NULL;
2059 : :
2060 : 18 : if (length)
2061 : 1 : *length = n;
2062 : :
2063 : 18 : return strv;
2064 : : }
2065 : :
2066 : : /* Type checking and querying {{{1 */
2067 : : /**
2068 : : * g_variant_get_type:
2069 : : * @value: a #GVariant
2070 : : *
2071 : : * Determines the type of @value.
2072 : : *
2073 : : * The return value is valid for the lifetime of @value and must not
2074 : : * be freed.
2075 : : *
2076 : : * Returns: a #GVariantType
2077 : : *
2078 : : * Since: 2.24
2079 : : **/
2080 : : const GVariantType *
2081 : 8651692 : g_variant_get_type (GVariant *value)
2082 : : {
2083 : : GVariantTypeInfo *type_info;
2084 : :
2085 : 8651692 : g_return_val_if_fail (value != NULL, NULL);
2086 : :
2087 : 8651692 : type_info = g_variant_get_type_info (value);
2088 : :
2089 : 8651692 : return (GVariantType *) g_variant_type_info_get_type_string (type_info);
2090 : : }
2091 : :
2092 : : /**
2093 : : * g_variant_get_type_string:
2094 : : * @value: a #GVariant
2095 : : *
2096 : : * Returns the type string of @value. Unlike the result of calling
2097 : : * g_variant_type_peek_string(), this string is nul-terminated. This
2098 : : * string belongs to #GVariant and must not be freed.
2099 : : *
2100 : : * Returns: the type string for the type of @value
2101 : : *
2102 : : * Since: 2.24
2103 : : **/
2104 : : const gchar *
2105 : 1747048 : g_variant_get_type_string (GVariant *value)
2106 : : {
2107 : : GVariantTypeInfo *type_info;
2108 : :
2109 : 1747048 : g_return_val_if_fail (value != NULL, NULL);
2110 : :
2111 : 1747048 : type_info = g_variant_get_type_info (value);
2112 : :
2113 : 1747048 : return g_variant_type_info_get_type_string (type_info);
2114 : : }
2115 : :
2116 : : /**
2117 : : * g_variant_is_of_type:
2118 : : * @value: a #GVariant instance
2119 : : * @type: a #GVariantType
2120 : : *
2121 : : * Checks if a value has a type matching the provided type.
2122 : : *
2123 : : * Returns: %TRUE if the type of @value matches @type
2124 : : *
2125 : : * Since: 2.24
2126 : : **/
2127 : : gboolean
2128 : 6973053 : g_variant_is_of_type (GVariant *value,
2129 : : const GVariantType *type)
2130 : : {
2131 : 6973053 : return g_variant_type_is_subtype_of (g_variant_get_type (value), type);
2132 : : }
2133 : :
2134 : : /**
2135 : : * g_variant_is_container:
2136 : : * @value: a #GVariant instance
2137 : : *
2138 : : * Checks if @value is a container.
2139 : : *
2140 : : * Returns: %TRUE if @value is a container
2141 : : *
2142 : : * Since: 2.24
2143 : : */
2144 : : gboolean
2145 : 164633 : g_variant_is_container (GVariant *value)
2146 : : {
2147 : 164633 : return g_variant_type_is_container (g_variant_get_type (value));
2148 : : }
2149 : :
2150 : :
2151 : : /**
2152 : : * g_variant_classify:
2153 : : * @value: a #GVariant
2154 : : *
2155 : : * Classifies @value according to its top-level type.
2156 : : *
2157 : : * Returns: the #GVariantClass of @value
2158 : : *
2159 : : * Since: 2.24
2160 : : **/
2161 : : /**
2162 : : * GVariantClass:
2163 : : * @G_VARIANT_CLASS_BOOLEAN: The #GVariant is a boolean.
2164 : : * @G_VARIANT_CLASS_BYTE: The #GVariant is a byte.
2165 : : * @G_VARIANT_CLASS_INT16: The #GVariant is a signed 16 bit integer.
2166 : : * @G_VARIANT_CLASS_UINT16: The #GVariant is an unsigned 16 bit integer.
2167 : : * @G_VARIANT_CLASS_INT32: The #GVariant is a signed 32 bit integer.
2168 : : * @G_VARIANT_CLASS_UINT32: The #GVariant is an unsigned 32 bit integer.
2169 : : * @G_VARIANT_CLASS_INT64: The #GVariant is a signed 64 bit integer.
2170 : : * @G_VARIANT_CLASS_UINT64: The #GVariant is an unsigned 64 bit integer.
2171 : : * @G_VARIANT_CLASS_HANDLE: The #GVariant is a file handle index.
2172 : : * @G_VARIANT_CLASS_DOUBLE: The #GVariant is a double precision floating
2173 : : * point value.
2174 : : * @G_VARIANT_CLASS_STRING: The #GVariant is a normal string.
2175 : : * @G_VARIANT_CLASS_OBJECT_PATH: The #GVariant is a D-Bus object path
2176 : : * string.
2177 : : * @G_VARIANT_CLASS_SIGNATURE: The #GVariant is a D-Bus signature string.
2178 : : * @G_VARIANT_CLASS_VARIANT: The #GVariant is a variant.
2179 : : * @G_VARIANT_CLASS_MAYBE: The #GVariant is a maybe-typed value.
2180 : : * @G_VARIANT_CLASS_ARRAY: The #GVariant is an array.
2181 : : * @G_VARIANT_CLASS_TUPLE: The #GVariant is a tuple.
2182 : : * @G_VARIANT_CLASS_DICT_ENTRY: The #GVariant is a dictionary entry.
2183 : : *
2184 : : * The range of possible top-level types of #GVariant instances.
2185 : : *
2186 : : * Since: 2.24
2187 : : **/
2188 : : GVariantClass
2189 : 24329 : g_variant_classify (GVariant *value)
2190 : : {
2191 : 24329 : g_return_val_if_fail (value != NULL, 0);
2192 : :
2193 : 24329 : return *g_variant_get_type_string (value);
2194 : : }
2195 : :
2196 : : /* Pretty printer {{{1 */
2197 : : /* This function is not introspectable because if @string is NULL,
2198 : : @returns is (transfer full), otherwise it is (transfer none), which
2199 : : is not supported by GObjectIntrospection */
2200 : : /**
2201 : : * g_variant_print_string: (skip)
2202 : : * @value: a #GVariant
2203 : : * @string: (nullable) (default NULL): a #GString, or %NULL
2204 : : * @type_annotate: %TRUE if type information should be included in
2205 : : * the output
2206 : : *
2207 : : * Behaves as g_variant_print(), but operates on a #GString.
2208 : : *
2209 : : * If @string is non-%NULL then it is appended to and returned. Else,
2210 : : * a new empty #GString is allocated and it is returned.
2211 : : *
2212 : : * Returns: a #GString containing the string
2213 : : *
2214 : : * Since: 2.24
2215 : : **/
2216 : : GString *
2217 : 1630287 : g_variant_print_string (GVariant *value,
2218 : : GString *string,
2219 : : gboolean type_annotate)
2220 : : {
2221 : 1630287 : const gchar *value_type_string = g_variant_get_type_string (value);
2222 : :
2223 : 1630287 : if G_UNLIKELY (string == NULL)
2224 : 1605 : string = g_string_new (NULL);
2225 : :
2226 : 1630287 : switch (value_type_string[0])
2227 : : {
2228 : 40773 : case G_VARIANT_CLASS_MAYBE:
2229 : 40773 : if (type_annotate)
2230 : 635 : g_string_append_printf (string, "@%s ", value_type_string);
2231 : :
2232 : 40773 : if (g_variant_n_children (value))
2233 : : {
2234 : : const GVariantType *base_type;
2235 : : guint i, depth;
2236 : 19433 : GVariant *element = NULL;
2237 : :
2238 : : /* Nested maybes:
2239 : : *
2240 : : * Consider the case of the type "mmi". In this case we could
2241 : : * write "just just 4", but "4" alone is totally unambiguous,
2242 : : * so we try to drop "just" where possible.
2243 : : *
2244 : : * We have to be careful not to always drop "just", though,
2245 : : * since "nothing" needs to be distinguishable from "just
2246 : : * nothing". The case where we need to ensure we keep the
2247 : : * "just" is actually exactly the case where we have a nested
2248 : : * Nothing.
2249 : : *
2250 : : * Search for the nested Nothing, to save a lot of recursion if there
2251 : : * are multiple levels of maybes.
2252 : : */
2253 : 19433 : for (depth = 0, base_type = g_variant_get_type (value);
2254 : 39115 : g_variant_type_is_maybe (base_type);
2255 : 19682 : depth++, base_type = g_variant_type_element (base_type));
2256 : :
2257 : 19433 : element = g_variant_ref (value);
2258 : 39113 : for (i = 0; i < depth && element != NULL; i++)
2259 : : {
2260 : 19680 : GVariant *new_element = g_variant_n_children (element) ? g_variant_get_child_value (element, 0) : NULL;
2261 : 19680 : g_variant_unref (element);
2262 : 19680 : element = g_steal_pointer (&new_element);
2263 : : }
2264 : :
2265 : 19433 : if (element == NULL)
2266 : : {
2267 : : /* One of the maybes was Nothing, so print out the right number of
2268 : : * justs. */
2269 : 266 : for (; i > 1; i--)
2270 : 266 : g_string_append (string, "just ");
2271 : 266 : g_string_append (string, "nothing");
2272 : : }
2273 : : else
2274 : : {
2275 : : /* There are no Nothings, so print out the child with no prefixes. */
2276 : 19300 : g_variant_print_string (element, string, FALSE);
2277 : : }
2278 : :
2279 : 19433 : g_clear_pointer (&element, g_variant_unref);
2280 : : }
2281 : : else
2282 : 42680 : g_string_append (string, "nothing");
2283 : :
2284 : 40773 : break;
2285 : :
2286 : 39398 : case G_VARIANT_CLASS_ARRAY:
2287 : : /* it's an array so the first character of the type string is 'a'
2288 : : *
2289 : : * if the first two characters are 'ay' then it's a bytestring.
2290 : : * under certain conditions we print those as strings.
2291 : : */
2292 : 39398 : if (value_type_string[1] == 'y')
2293 : : {
2294 : : const gchar *str;
2295 : : gsize size;
2296 : : gsize i;
2297 : :
2298 : : /* first determine if it is a byte string.
2299 : : * that's when there's a single nul character: at the end.
2300 : : */
2301 : 179 : str = g_variant_get_data (value);
2302 : 179 : size = g_variant_get_size (value);
2303 : :
2304 : 7641 : for (i = 0; i < size; i++)
2305 : 7505 : if (str[i] == '\0')
2306 : 43 : break;
2307 : :
2308 : : /* first nul byte is the last byte -> it's a byte string. */
2309 : 179 : if (i == size - 1)
2310 : : {
2311 : 17 : gchar *escaped = g_strescape (str, NULL);
2312 : :
2313 : : /* use double quotes only if a ' is in the string */
2314 : 17 : if (strchr (str, '\''))
2315 : 0 : g_string_append_printf (string, "b\"%s\"", escaped);
2316 : : else
2317 : 17 : g_string_append_printf (string, "b'%s'", escaped);
2318 : :
2319 : 17 : g_free (escaped);
2320 : 17 : break;
2321 : : }
2322 : :
2323 : : else
2324 : : {
2325 : : /* fall through and handle normally... */
2326 : : }
2327 : : }
2328 : :
2329 : : /*
2330 : : * if the first two characters are 'a{' then it's an array of
2331 : : * dictionary entries (ie: a dictionary) so we print that
2332 : : * differently.
2333 : : */
2334 : 39381 : if (value_type_string[1] == '{')
2335 : : /* dictionary */
2336 : : {
2337 : 769 : const gchar *comma = "";
2338 : : gsize n, i;
2339 : :
2340 : 769 : if ((n = g_variant_n_children (value)) == 0)
2341 : : {
2342 : 17 : if (type_annotate)
2343 : 4 : g_string_append_printf (string, "@%s ", value_type_string);
2344 : 17 : g_string_append (string, "{}");
2345 : 17 : break;
2346 : : }
2347 : :
2348 : : g_string_append_c (string, '{');
2349 : 45625 : for (i = 0; i < n; i++)
2350 : : {
2351 : : GVariant *entry, *key, *val;
2352 : :
2353 : : g_string_append (string, comma);
2354 : 44873 : comma = ", ";
2355 : :
2356 : 44873 : entry = g_variant_get_child_value (value, i);
2357 : 44873 : key = g_variant_get_child_value (entry, 0);
2358 : 44873 : val = g_variant_get_child_value (entry, 1);
2359 : 44873 : g_variant_unref (entry);
2360 : :
2361 : 44873 : g_variant_print_string (key, string, type_annotate);
2362 : 44873 : g_variant_unref (key);
2363 : 44873 : g_string_append (string, ": ");
2364 : 44873 : g_variant_print_string (val, string, type_annotate);
2365 : 44873 : g_variant_unref (val);
2366 : 44873 : type_annotate = FALSE;
2367 : : }
2368 : : g_string_append_c (string, '}');
2369 : : }
2370 : : else
2371 : : /* normal (non-dictionary) array */
2372 : : {
2373 : 38612 : const gchar *comma = "";
2374 : : gsize n, i;
2375 : :
2376 : 38612 : if ((n = g_variant_n_children (value)) == 0)
2377 : : {
2378 : 20020 : if (type_annotate)
2379 : 92 : g_string_append_printf (string, "@%s ", value_type_string);
2380 : 20020 : g_string_append (string, "[]");
2381 : 20020 : break;
2382 : : }
2383 : :
2384 : : g_string_append_c (string, '[');
2385 : 1245792 : for (i = 0; i < n; i++)
2386 : : {
2387 : : GVariant *element;
2388 : :
2389 : : g_string_append (string, comma);
2390 : 1227200 : comma = ", ";
2391 : :
2392 : 1227200 : element = g_variant_get_child_value (value, i);
2393 : :
2394 : 1227200 : g_variant_print_string (element, string, type_annotate);
2395 : 1227200 : g_variant_unref (element);
2396 : 1227200 : type_annotate = FALSE;
2397 : : }
2398 : : g_string_append_c (string, ']');
2399 : : }
2400 : :
2401 : 19344 : break;
2402 : :
2403 : 57402 : case G_VARIANT_CLASS_TUPLE:
2404 : : {
2405 : : gsize n, i;
2406 : :
2407 : 57402 : n = g_variant_n_children (value);
2408 : :
2409 : : g_string_append_c (string, '(');
2410 : 308553 : for (i = 0; i < n; i++)
2411 : : {
2412 : : GVariant *element;
2413 : :
2414 : 251151 : element = g_variant_get_child_value (value, i);
2415 : 251151 : g_variant_print_string (element, string, type_annotate);
2416 : 251151 : g_string_append (string, ", ");
2417 : 251151 : g_variant_unref (element);
2418 : : }
2419 : :
2420 : : /* for >1 item: remove final ", "
2421 : : * for 1 item: remove final " ", but leave the ","
2422 : : * for 0 items: there is only "(", so remove nothing
2423 : : */
2424 : 57402 : g_string_truncate (string, string->len - (n > 0) - (n > 1));
2425 : : g_string_append_c (string, ')');
2426 : : }
2427 : 57402 : break;
2428 : :
2429 : 3444 : case G_VARIANT_CLASS_DICT_ENTRY:
2430 : : {
2431 : : GVariant *element;
2432 : :
2433 : : g_string_append_c (string, '{');
2434 : :
2435 : 3444 : element = g_variant_get_child_value (value, 0);
2436 : 3444 : g_variant_print_string (element, string, type_annotate);
2437 : 3444 : g_variant_unref (element);
2438 : :
2439 : 3444 : g_string_append (string, ", ");
2440 : :
2441 : 3444 : element = g_variant_get_child_value (value, 1);
2442 : 3444 : g_variant_print_string (element, string, type_annotate);
2443 : 3444 : g_variant_unref (element);
2444 : :
2445 : : g_string_append_c (string, '}');
2446 : : }
2447 : 3444 : break;
2448 : :
2449 : 34365 : case G_VARIANT_CLASS_VARIANT:
2450 : : {
2451 : 34365 : GVariant *child = g_variant_get_variant (value);
2452 : :
2453 : : /* Always annotate types in nested variants, because they are
2454 : : * (by nature) of variable type.
2455 : : */
2456 : : g_string_append_c (string, '<');
2457 : 34365 : g_variant_print_string (child, string, TRUE);
2458 : : g_string_append_c (string, '>');
2459 : :
2460 : 34365 : g_variant_unref (child);
2461 : : }
2462 : 34365 : break;
2463 : :
2464 : 44506 : case G_VARIANT_CLASS_BOOLEAN:
2465 : 44506 : if (g_variant_get_boolean (value))
2466 : 44286 : g_string_append (string, "true");
2467 : : else
2468 : 44726 : g_string_append (string, "false");
2469 : 44506 : break;
2470 : :
2471 : 29636 : case G_VARIANT_CLASS_STRING:
2472 : : {
2473 : 29636 : const gchar *str = g_variant_get_string (value, NULL);
2474 : 29636 : gunichar quote = strchr (str, '\'') ? '"' : '\'';
2475 : :
2476 : 29636 : g_string_append_c (string, quote);
2477 : :
2478 : 3018109 : while (*str)
2479 : : {
2480 : 2988473 : gunichar c = g_utf8_get_char (str);
2481 : :
2482 : 2988473 : if (c == quote || c == '\\')
2483 : : g_string_append_c (string, '\\');
2484 : :
2485 : 2988473 : if (g_unichar_isprint (c))
2486 : 2988398 : g_string_append_unichar (string, c);
2487 : :
2488 : : else
2489 : : {
2490 : : g_string_append_c (string, '\\');
2491 : 75 : if (c < 0x10000)
2492 : 74 : switch (c)
2493 : : {
2494 : 3 : case '\a':
2495 : : g_string_append_c (string, 'a');
2496 : 3 : break;
2497 : :
2498 : 3 : case '\b':
2499 : : g_string_append_c (string, 'b');
2500 : 3 : break;
2501 : :
2502 : 3 : case '\f':
2503 : : g_string_append_c (string, 'f');
2504 : 3 : break;
2505 : :
2506 : 4 : case '\n':
2507 : : g_string_append_c (string, 'n');
2508 : 4 : break;
2509 : :
2510 : 3 : case '\r':
2511 : : g_string_append_c (string, 'r');
2512 : 3 : break;
2513 : :
2514 : 4 : case '\t':
2515 : : g_string_append_c (string, 't');
2516 : 4 : break;
2517 : :
2518 : 3 : case '\v':
2519 : : g_string_append_c (string, 'v');
2520 : 3 : break;
2521 : :
2522 : 51 : default:
2523 : 51 : g_string_append_printf (string, "u%04x", c);
2524 : 51 : break;
2525 : : }
2526 : : else
2527 : 1 : g_string_append_printf (string, "U%08x", c);
2528 : : }
2529 : :
2530 : 2988473 : str = g_utf8_next_char (str);
2531 : : }
2532 : :
2533 : 29636 : g_string_append_c (string, quote);
2534 : : }
2535 : 29636 : break;
2536 : :
2537 : 13860 : case G_VARIANT_CLASS_BYTE:
2538 : 13860 : if (type_annotate)
2539 : 2508 : g_string_append (string, "byte ");
2540 : 13860 : g_string_append_printf (string, "0x%02x",
2541 : 13860 : g_variant_get_byte (value));
2542 : 13860 : break;
2543 : :
2544 : 91674 : case G_VARIANT_CLASS_INT16:
2545 : 91674 : if (type_annotate)
2546 : 2532 : g_string_append (string, "int16 ");
2547 : 91674 : g_string_append_printf (string, "%"G_GINT16_FORMAT,
2548 : 91674 : g_variant_get_int16 (value));
2549 : 91674 : break;
2550 : :
2551 : 54566 : case G_VARIANT_CLASS_UINT16:
2552 : 54566 : if (type_annotate)
2553 : 2332 : g_string_append (string, "uint16 ");
2554 : 54566 : g_string_append_printf (string, "%"G_GUINT16_FORMAT,
2555 : 54566 : g_variant_get_uint16 (value));
2556 : 54566 : break;
2557 : :
2558 : 104981 : case G_VARIANT_CLASS_INT32:
2559 : : /* Never annotate this type because it is the default for numbers
2560 : : * (and this is a *pretty* printer)
2561 : : */
2562 : 104981 : g_string_append_printf (string, "%"G_GINT32_FORMAT,
2563 : : g_variant_get_int32 (value));
2564 : 104981 : break;
2565 : :
2566 : 31945 : case G_VARIANT_CLASS_HANDLE:
2567 : 31945 : if (type_annotate)
2568 : 2558 : g_string_append (string, "handle ");
2569 : 31945 : g_string_append_printf (string, "%"G_GINT32_FORMAT,
2570 : : g_variant_get_handle (value));
2571 : 31945 : break;
2572 : :
2573 : 52205 : case G_VARIANT_CLASS_UINT32:
2574 : 52205 : if (type_annotate)
2575 : 2592 : g_string_append (string, "uint32 ");
2576 : 52205 : g_string_append_printf (string, "%"G_GUINT32_FORMAT,
2577 : : g_variant_get_uint32 (value));
2578 : 52205 : break;
2579 : :
2580 : 93339 : case G_VARIANT_CLASS_INT64:
2581 : 93339 : if (type_annotate)
2582 : 2700 : g_string_append (string, "int64 ");
2583 : 93339 : g_string_append_printf (string, "%"G_GINT64_FORMAT,
2584 : : g_variant_get_int64 (value));
2585 : 93339 : break;
2586 : :
2587 : 35332 : case G_VARIANT_CLASS_UINT64:
2588 : 35332 : if (type_annotate)
2589 : 2540 : g_string_append (string, "uint64 ");
2590 : 35332 : g_string_append_printf (string, "%"G_GUINT64_FORMAT,
2591 : : g_variant_get_uint64 (value));
2592 : 35332 : break;
2593 : :
2594 : 105285 : case G_VARIANT_CLASS_DOUBLE:
2595 : : {
2596 : : gchar buffer[100];
2597 : : gint i;
2598 : :
2599 : 105285 : g_ascii_dtostr (buffer, sizeof buffer, g_variant_get_double (value));
2600 : :
2601 : 227492 : for (i = 0; buffer[i]; i++)
2602 : 227284 : if (buffer[i] == '.' || buffer[i] == 'e' ||
2603 : 122222 : buffer[i] == 'n' || buffer[i] == 'N')
2604 : : break;
2605 : :
2606 : : /* if there is no '.' or 'e' in the float then add one */
2607 : 105285 : if (buffer[i] == '\0')
2608 : : {
2609 : 208 : buffer[i++] = '.';
2610 : 208 : buffer[i++] = '0';
2611 : 208 : buffer[i++] = '\0';
2612 : : }
2613 : :
2614 : : g_string_append (string, buffer);
2615 : : }
2616 : 105285 : break;
2617 : :
2618 : 35235 : case G_VARIANT_CLASS_OBJECT_PATH:
2619 : 35235 : if (type_annotate)
2620 : 2656 : g_string_append (string, "objectpath ");
2621 : 35235 : g_string_append_printf (string, "\'%s\'",
2622 : : g_variant_get_string (value, NULL));
2623 : 35235 : break;
2624 : :
2625 : 762341 : case G_VARIANT_CLASS_SIGNATURE:
2626 : 762341 : if (type_annotate)
2627 : 2282 : g_string_append (string, "signature ");
2628 : 762341 : g_string_append_printf (string, "\'%s\'",
2629 : : g_variant_get_string (value, NULL));
2630 : 762341 : break;
2631 : :
2632 : 0 : default:
2633 : : g_assert_not_reached ();
2634 : : }
2635 : :
2636 : 1630287 : return string;
2637 : : }
2638 : :
2639 : : /**
2640 : : * g_variant_print:
2641 : : * @value: a #GVariant
2642 : : * @type_annotate: %TRUE if type information should be included in
2643 : : * the output
2644 : : *
2645 : : * Pretty-prints @value in the format understood by g_variant_parse().
2646 : : *
2647 : : * The format is described [here](gvariant-text-format.html).
2648 : : *
2649 : : * If @type_annotate is %TRUE, then type information is included in
2650 : : * the output.
2651 : : *
2652 : : * Returns: (transfer full): a newly-allocated string holding the result.
2653 : : *
2654 : : * Since: 2.24
2655 : : */
2656 : : gchar *
2657 : 1605 : g_variant_print (GVariant *value,
2658 : : gboolean type_annotate)
2659 : : {
2660 : 1605 : return g_string_free (g_variant_print_string (value, NULL, type_annotate),
2661 : : FALSE);
2662 : : }
2663 : :
2664 : : /* Hash, Equal, Compare {{{1 */
2665 : : /**
2666 : : * g_variant_hash:
2667 : : * @value: (type GVariant): a basic #GVariant value as a #gconstpointer
2668 : : *
2669 : : * Generates a hash value for a #GVariant instance.
2670 : : *
2671 : : * The output of this function is guaranteed to be the same for a given
2672 : : * value only per-process. It may change between different processor
2673 : : * architectures or even different versions of GLib. Do not use this
2674 : : * function as a basis for building protocols or file formats.
2675 : : *
2676 : : * The type of @value is #gconstpointer only to allow use of this
2677 : : * function with #GHashTable. @value must be a #GVariant.
2678 : : *
2679 : : * Returns: a hash value corresponding to @value
2680 : : *
2681 : : * Since: 2.24
2682 : : **/
2683 : : guint
2684 : 8192 : g_variant_hash (gconstpointer value_)
2685 : : {
2686 : 8192 : GVariant *value = (GVariant *) value_;
2687 : :
2688 : 8192 : switch (g_variant_classify (value))
2689 : : {
2690 : 2256 : case G_VARIANT_CLASS_STRING:
2691 : : case G_VARIANT_CLASS_OBJECT_PATH:
2692 : : case G_VARIANT_CLASS_SIGNATURE:
2693 : 2256 : return g_str_hash (g_variant_get_string (value, NULL));
2694 : :
2695 : 4 : case G_VARIANT_CLASS_BOOLEAN:
2696 : : /* this is a very odd thing to hash... */
2697 : 4 : return g_variant_get_boolean (value);
2698 : :
2699 : 386 : case G_VARIANT_CLASS_BYTE:
2700 : 386 : return g_variant_get_byte (value);
2701 : :
2702 : 1414 : case G_VARIANT_CLASS_INT16:
2703 : : case G_VARIANT_CLASS_UINT16:
2704 : : {
2705 : : const guint16 *ptr;
2706 : :
2707 : 1414 : ptr = g_variant_get_data (value);
2708 : :
2709 : 1414 : if (ptr)
2710 : 1414 : return *ptr;
2711 : : else
2712 : 0 : return 0;
2713 : : }
2714 : :
2715 : 2090 : case G_VARIANT_CLASS_INT32:
2716 : : case G_VARIANT_CLASS_UINT32:
2717 : : case G_VARIANT_CLASS_HANDLE:
2718 : : {
2719 : : const guint *ptr;
2720 : :
2721 : 2090 : ptr = g_variant_get_data (value);
2722 : :
2723 : 2090 : if (ptr)
2724 : 2090 : return *ptr;
2725 : : else
2726 : 0 : return 0;
2727 : : }
2728 : :
2729 : 2042 : case G_VARIANT_CLASS_INT64:
2730 : : case G_VARIANT_CLASS_UINT64:
2731 : : case G_VARIANT_CLASS_DOUBLE:
2732 : : /* need a separate case for these guys because otherwise
2733 : : * performance could be quite bad on big endian systems
2734 : : */
2735 : : {
2736 : : const guint *ptr;
2737 : :
2738 : 2042 : ptr = g_variant_get_data (value);
2739 : :
2740 : 2042 : if (ptr)
2741 : 2042 : return ptr[0] + ptr[1];
2742 : : else
2743 : 0 : return 0;
2744 : : }
2745 : :
2746 : 0 : default:
2747 : 0 : g_return_val_if_fail (!g_variant_is_container (value), 0);
2748 : : g_assert_not_reached ();
2749 : : }
2750 : : }
2751 : :
2752 : : /**
2753 : : * g_variant_equal:
2754 : : * @one: (type GVariant): a #GVariant instance
2755 : : * @two: (type GVariant): a #GVariant instance
2756 : : *
2757 : : * Checks if @one and @two have the same type and value.
2758 : : *
2759 : : * The types of @one and @two are #gconstpointer only to allow use of
2760 : : * this function with #GHashTable. They must each be a #GVariant.
2761 : : *
2762 : : * Returns: %TRUE if @one and @two are equal
2763 : : *
2764 : : * Since: 2.24
2765 : : **/
2766 : : gboolean
2767 : 9374897 : g_variant_equal (gconstpointer one,
2768 : : gconstpointer two)
2769 : : {
2770 : : gboolean equal;
2771 : :
2772 : 9374897 : g_return_val_if_fail (one != NULL && two != NULL, FALSE);
2773 : :
2774 : 18749794 : if (g_variant_get_type_info ((GVariant *) one) !=
2775 : 9374897 : g_variant_get_type_info ((GVariant *) two))
2776 : 7844002 : return FALSE;
2777 : :
2778 : : /* if both values are trusted to be in their canonical serialized form
2779 : : * then a simple memcmp() of their serialized data will answer the
2780 : : * question.
2781 : : *
2782 : : * if not, then this might generate a false negative (since it is
2783 : : * possible for two different byte sequences to represent the same
2784 : : * value). for now we solve this by pretty-printing both values and
2785 : : * comparing the result.
2786 : : */
2787 : 3061581 : if (g_variant_is_trusted ((GVariant *) one) &&
2788 : 1530686 : g_variant_is_trusted ((GVariant *) two))
2789 : 1319752 : {
2790 : : gconstpointer data_one, data_two;
2791 : : gsize size_one, size_two;
2792 : :
2793 : 1530487 : size_one = g_variant_get_size ((GVariant *) one);
2794 : 1530487 : size_two = g_variant_get_size ((GVariant *) two);
2795 : :
2796 : 1530487 : if (size_one != size_two)
2797 : 210735 : return FALSE;
2798 : :
2799 : 1319752 : data_one = g_variant_get_data ((GVariant *) one);
2800 : 1319752 : data_two = g_variant_get_data ((GVariant *) two);
2801 : :
2802 : 1319752 : if (size_one)
2803 : 1319744 : equal = memcmp (data_one, data_two, size_one) == 0;
2804 : : else
2805 : 8 : equal = TRUE;
2806 : : }
2807 : : else
2808 : : {
2809 : : gchar *strone, *strtwo;
2810 : :
2811 : 408 : strone = g_variant_print ((GVariant *) one, FALSE);
2812 : 408 : strtwo = g_variant_print ((GVariant *) two, FALSE);
2813 : 408 : equal = strcmp (strone, strtwo) == 0;
2814 : 408 : g_free (strone);
2815 : 408 : g_free (strtwo);
2816 : : }
2817 : :
2818 : 1320160 : return equal;
2819 : : }
2820 : :
2821 : : /**
2822 : : * g_variant_compare:
2823 : : * @one: (type GVariant): a basic-typed #GVariant instance
2824 : : * @two: (type GVariant): a #GVariant instance of the same type
2825 : : *
2826 : : * Compares @one and @two.
2827 : : *
2828 : : * The types of @one and @two are #gconstpointer only to allow use of
2829 : : * this function with #GTree, #GPtrArray, etc. They must each be a
2830 : : * #GVariant.
2831 : : *
2832 : : * Comparison is only defined for basic types (ie: booleans, numbers,
2833 : : * strings). For booleans, %FALSE is less than %TRUE. Numbers are
2834 : : * ordered in the usual way. Strings are in ASCII lexographical order.
2835 : : *
2836 : : * It is a programmer error to attempt to compare container values or
2837 : : * two values that have types that are not exactly equal. For example,
2838 : : * you cannot compare a 32-bit signed integer with a 32-bit unsigned
2839 : : * integer. Also note that this function is not particularly
2840 : : * well-behaved when it comes to comparison of doubles; in particular,
2841 : : * the handling of incomparable values (ie: NaN) is undefined.
2842 : : *
2843 : : * If you only require an equality comparison, g_variant_equal() is more
2844 : : * general.
2845 : : *
2846 : : * Returns: negative value if a < b;
2847 : : * zero if a = b;
2848 : : * positive value if a > b.
2849 : : *
2850 : : * Since: 2.26
2851 : : **/
2852 : : gint
2853 : 124 : g_variant_compare (gconstpointer one,
2854 : : gconstpointer two)
2855 : : {
2856 : 124 : GVariant *a = (GVariant *) one;
2857 : 124 : GVariant *b = (GVariant *) two;
2858 : :
2859 : 124 : g_return_val_if_fail (g_variant_classify (a) == g_variant_classify (b), 0);
2860 : :
2861 : 124 : switch (g_variant_classify (a))
2862 : : {
2863 : 1 : case G_VARIANT_CLASS_BOOLEAN:
2864 : 2 : return g_variant_get_boolean (a) -
2865 : 1 : g_variant_get_boolean (b);
2866 : :
2867 : 7 : case G_VARIANT_CLASS_BYTE:
2868 : 7 : return ((gint) g_variant_get_byte (a)) -
2869 : 7 : ((gint) g_variant_get_byte (b));
2870 : :
2871 : 7 : case G_VARIANT_CLASS_INT16:
2872 : 7 : return ((gint) g_variant_get_int16 (a)) -
2873 : 7 : ((gint) g_variant_get_int16 (b));
2874 : :
2875 : 7 : case G_VARIANT_CLASS_UINT16:
2876 : 7 : return ((gint) g_variant_get_uint16 (a)) -
2877 : 7 : ((gint) g_variant_get_uint16 (b));
2878 : :
2879 : 59 : case G_VARIANT_CLASS_INT32:
2880 : : {
2881 : 59 : gint32 a_val = g_variant_get_int32 (a);
2882 : 59 : gint32 b_val = g_variant_get_int32 (b);
2883 : :
2884 : 59 : return (a_val == b_val) ? 0 : (a_val > b_val) ? 1 : -1;
2885 : : }
2886 : :
2887 : 19 : case G_VARIANT_CLASS_UINT32:
2888 : : {
2889 : 19 : guint32 a_val = g_variant_get_uint32 (a);
2890 : 19 : guint32 b_val = g_variant_get_uint32 (b);
2891 : :
2892 : 19 : return (a_val == b_val) ? 0 : (a_val > b_val) ? 1 : -1;
2893 : : }
2894 : :
2895 : 7 : case G_VARIANT_CLASS_INT64:
2896 : : {
2897 : 7 : gint64 a_val = g_variant_get_int64 (a);
2898 : 7 : gint64 b_val = g_variant_get_int64 (b);
2899 : :
2900 : 7 : return (a_val == b_val) ? 0 : (a_val > b_val) ? 1 : -1;
2901 : : }
2902 : :
2903 : 7 : case G_VARIANT_CLASS_UINT64:
2904 : : {
2905 : 7 : guint64 a_val = g_variant_get_uint64 (a);
2906 : 7 : guint64 b_val = g_variant_get_uint64 (b);
2907 : :
2908 : 7 : return (a_val == b_val) ? 0 : (a_val > b_val) ? 1 : -1;
2909 : : }
2910 : :
2911 : 7 : case G_VARIANT_CLASS_DOUBLE:
2912 : : {
2913 : 7 : gdouble a_val = g_variant_get_double (a);
2914 : 7 : gdouble b_val = g_variant_get_double (b);
2915 : :
2916 : 7 : return (a_val == b_val) ? 0 : (a_val > b_val) ? 1 : -1;
2917 : : }
2918 : :
2919 : 3 : case G_VARIANT_CLASS_STRING:
2920 : : case G_VARIANT_CLASS_OBJECT_PATH:
2921 : : case G_VARIANT_CLASS_SIGNATURE:
2922 : 3 : return strcmp (g_variant_get_string (a, NULL),
2923 : 3 : g_variant_get_string (b, NULL));
2924 : :
2925 : 0 : default:
2926 : 0 : g_return_val_if_fail (!g_variant_is_container (a), 0);
2927 : : g_assert_not_reached ();
2928 : : }
2929 : : }
2930 : :
2931 : : /* GVariantIter {{{1 */
2932 : : /**
2933 : : * GVariantIter: (skip)
2934 : : *
2935 : : * #GVariantIter is an opaque data structure and can only be accessed
2936 : : * using the following functions.
2937 : : **/
2938 : : struct stack_iter
2939 : : {
2940 : : GVariant *value;
2941 : : gssize n, i;
2942 : :
2943 : : const gchar *loop_format;
2944 : :
2945 : : gsize padding[3];
2946 : : gsize magic;
2947 : : };
2948 : :
2949 : : G_STATIC_ASSERT (sizeof (struct stack_iter) <= sizeof (GVariantIter));
2950 : :
2951 : : struct heap_iter
2952 : : {
2953 : : struct stack_iter iter;
2954 : :
2955 : : GVariant *value_ref;
2956 : : gsize magic;
2957 : : };
2958 : :
2959 : : G_STATIC_ASSERT (sizeof (struct heap_iter) <= sizeof (GVariantIter));
2960 : :
2961 : : #define GVSI(i) ((struct stack_iter *) (i))
2962 : : #define GVHI(i) ((struct heap_iter *) (i))
2963 : : #define GVSI_MAGIC ((gsize) 3579507750u)
2964 : : #define GVHI_MAGIC ((gsize) 1450270775u)
2965 : : #define is_valid_iter(i) (i != NULL && \
2966 : : GVSI(i)->magic == GVSI_MAGIC)
2967 : : #define is_valid_heap_iter(i) (is_valid_iter(i) && \
2968 : : GVHI(i)->magic == GVHI_MAGIC)
2969 : :
2970 : : /**
2971 : : * g_variant_iter_new:
2972 : : * @value: a container #GVariant
2973 : : *
2974 : : * Creates a heap-allocated #GVariantIter for iterating over the items
2975 : : * in @value.
2976 : : *
2977 : : * Use g_variant_iter_free() to free the return value when you no longer
2978 : : * need it.
2979 : : *
2980 : : * A reference is taken to @value and will be released only when
2981 : : * g_variant_iter_free() is called.
2982 : : *
2983 : : * Returns: (transfer full): a new heap-allocated #GVariantIter
2984 : : *
2985 : : * Since: 2.24
2986 : : **/
2987 : : GVariantIter *
2988 : 3284 : g_variant_iter_new (GVariant *value)
2989 : : {
2990 : : GVariantIter *iter;
2991 : :
2992 : 3284 : iter = (GVariantIter *) g_slice_new (struct heap_iter);
2993 : 3284 : GVHI(iter)->value_ref = g_variant_ref (value);
2994 : 3284 : GVHI(iter)->magic = GVHI_MAGIC;
2995 : :
2996 : 3284 : g_variant_iter_init (iter, value);
2997 : :
2998 : 3284 : return iter;
2999 : : }
3000 : :
3001 : : /**
3002 : : * g_variant_iter_init: (skip)
3003 : : * @iter: a pointer to a #GVariantIter
3004 : : * @value: a container #GVariant
3005 : : *
3006 : : * Initialises (without allocating) a #GVariantIter. @iter may be
3007 : : * completely uninitialised prior to this call; its old value is
3008 : : * ignored.
3009 : : *
3010 : : * The iterator remains valid for as long as @value exists, and need not
3011 : : * be freed in any way.
3012 : : *
3013 : : * Returns: the number of items in @value
3014 : : *
3015 : : * Since: 2.24
3016 : : **/
3017 : : gsize
3018 : 133192 : g_variant_iter_init (GVariantIter *iter,
3019 : : GVariant *value)
3020 : : {
3021 : 133192 : GVSI(iter)->magic = GVSI_MAGIC;
3022 : 133192 : GVSI(iter)->value = value;
3023 : 133192 : GVSI(iter)->n = g_variant_n_children (value);
3024 : 133192 : GVSI(iter)->i = -1;
3025 : 133192 : GVSI(iter)->loop_format = NULL;
3026 : :
3027 : 133192 : return GVSI(iter)->n;
3028 : : }
3029 : :
3030 : : /**
3031 : : * g_variant_iter_copy:
3032 : : * @iter: a #GVariantIter
3033 : : *
3034 : : * Creates a new heap-allocated #GVariantIter to iterate over the
3035 : : * container that was being iterated over by @iter. Iteration begins on
3036 : : * the new iterator from the current position of the old iterator but
3037 : : * the two copies are independent past that point.
3038 : : *
3039 : : * Use g_variant_iter_free() to free the return value when you no longer
3040 : : * need it.
3041 : : *
3042 : : * A reference is taken to the container that @iter is iterating over
3043 : : * and will be related only when g_variant_iter_free() is called.
3044 : : *
3045 : : * Returns: (transfer full): a new heap-allocated #GVariantIter
3046 : : *
3047 : : * Since: 2.24
3048 : : **/
3049 : : GVariantIter *
3050 : 1 : g_variant_iter_copy (GVariantIter *iter)
3051 : : {
3052 : : GVariantIter *copy;
3053 : :
3054 : 1 : g_return_val_if_fail (is_valid_iter (iter), 0);
3055 : :
3056 : 1 : copy = g_variant_iter_new (GVSI(iter)->value);
3057 : 1 : GVSI(copy)->i = GVSI(iter)->i;
3058 : :
3059 : 1 : return copy;
3060 : : }
3061 : :
3062 : : /**
3063 : : * g_variant_iter_n_children:
3064 : : * @iter: a #GVariantIter
3065 : : *
3066 : : * Queries the number of child items in the container that we are
3067 : : * iterating over. This is the total number of items -- not the number
3068 : : * of items remaining.
3069 : : *
3070 : : * This function might be useful for preallocation of arrays.
3071 : : *
3072 : : * Returns: the number of children in the container
3073 : : *
3074 : : * Since: 2.24
3075 : : **/
3076 : : gsize
3077 : 2270 : g_variant_iter_n_children (GVariantIter *iter)
3078 : : {
3079 : 2270 : g_return_val_if_fail (is_valid_iter (iter), 0);
3080 : :
3081 : 2270 : return GVSI(iter)->n;
3082 : : }
3083 : :
3084 : : /**
3085 : : * g_variant_iter_free:
3086 : : * @iter: (transfer full): a heap-allocated #GVariantIter
3087 : : *
3088 : : * Frees a heap-allocated #GVariantIter. Only call this function on
3089 : : * iterators that were returned by g_variant_iter_new() or
3090 : : * g_variant_iter_copy().
3091 : : *
3092 : : * Since: 2.24
3093 : : **/
3094 : : void
3095 : 3284 : g_variant_iter_free (GVariantIter *iter)
3096 : : {
3097 : 3284 : g_return_if_fail (is_valid_heap_iter (iter));
3098 : :
3099 : 3284 : g_variant_unref (GVHI(iter)->value_ref);
3100 : 3284 : GVHI(iter)->magic = 0;
3101 : :
3102 : 3284 : g_slice_free (struct heap_iter, GVHI(iter));
3103 : : }
3104 : :
3105 : : /**
3106 : : * g_variant_iter_next_value:
3107 : : * @iter: a #GVariantIter
3108 : : *
3109 : : * Gets the next item in the container. If no more items remain then
3110 : : * %NULL is returned.
3111 : : *
3112 : : * Use g_variant_unref() to drop your reference on the return value when
3113 : : * you no longer need it.
3114 : : *
3115 : : * Here is an example for iterating with g_variant_iter_next_value():
3116 : : * |[<!-- language="C" -->
3117 : : * // recursively iterate a container
3118 : : * void
3119 : : * iterate_container_recursive (GVariant *container)
3120 : : * {
3121 : : * GVariantIter iter;
3122 : : * GVariant *child;
3123 : : *
3124 : : * g_variant_iter_init (&iter, container);
3125 : : * while ((child = g_variant_iter_next_value (&iter)))
3126 : : * {
3127 : : * g_print ("type '%s'\n", g_variant_get_type_string (child));
3128 : : *
3129 : : * if (g_variant_is_container (child))
3130 : : * iterate_container_recursive (child);
3131 : : *
3132 : : * g_variant_unref (child);
3133 : : * }
3134 : : * }
3135 : : * ]|
3136 : : *
3137 : : * Returns: (nullable) (transfer full): a #GVariant, or %NULL
3138 : : *
3139 : : * Since: 2.24
3140 : : **/
3141 : : GVariant *
3142 : 523923 : g_variant_iter_next_value (GVariantIter *iter)
3143 : : {
3144 : 523923 : g_return_val_if_fail (is_valid_iter (iter), FALSE);
3145 : :
3146 : 523923 : if G_UNLIKELY (GVSI(iter)->i >= GVSI(iter)->n)
3147 : : {
3148 : 1 : g_critical ("g_variant_iter_next_value: must not be called again "
3149 : : "after NULL has already been returned.");
3150 : 1 : return NULL;
3151 : : }
3152 : :
3153 : 523922 : GVSI(iter)->i++;
3154 : :
3155 : 523922 : if (GVSI(iter)->i < GVSI(iter)->n)
3156 : 390787 : return g_variant_get_child_value (GVSI(iter)->value, GVSI(iter)->i);
3157 : :
3158 : 133135 : return NULL;
3159 : : }
3160 : :
3161 : : /* GVariantBuilder {{{1 */
3162 : : /**
3163 : : * GVariantBuilder:
3164 : : *
3165 : : * A utility type for constructing container-type #GVariant instances.
3166 : : *
3167 : : * This is an opaque structure and may only be accessed using the
3168 : : * following functions.
3169 : : *
3170 : : * #GVariantBuilder is not threadsafe in any way. Do not attempt to
3171 : : * access it from more than one thread.
3172 : : **/
3173 : :
3174 : : struct stack_builder
3175 : : {
3176 : : GVariantBuilder *parent;
3177 : : GVariantType *type;
3178 : :
3179 : : /* type constraint explicitly specified by 'type'.
3180 : : * for tuple types, this moves along as we add more items.
3181 : : */
3182 : : const GVariantType *expected_type;
3183 : :
3184 : : /* type constraint implied by previous array item.
3185 : : */
3186 : : const GVariantType *prev_item_type;
3187 : :
3188 : : /* constraints on the number of children. max = -1 for unlimited. */
3189 : : gsize min_items;
3190 : : gsize max_items;
3191 : :
3192 : : /* dynamically-growing pointer array */
3193 : : GVariant **children;
3194 : : gsize allocated_children;
3195 : : gsize offset;
3196 : :
3197 : : /* set to '1' if all items in the container will have the same type
3198 : : * (ie: maybe, array, variant) '0' if not (ie: tuple, dict entry)
3199 : : */
3200 : : guint uniform_item_types : 1;
3201 : :
3202 : : /* set to '1' initially and changed to '0' if an untrusted value is
3203 : : * added
3204 : : */
3205 : : guint trusted : 1;
3206 : :
3207 : : /* If @type was copied when constructing the builder */
3208 : : guint type_owned : 1;
3209 : :
3210 : : gsize magic;
3211 : : };
3212 : :
3213 : : G_STATIC_ASSERT (sizeof (struct stack_builder) <= sizeof (GVariantBuilder));
3214 : :
3215 : : struct heap_builder
3216 : : {
3217 : : GVariantBuilder builder;
3218 : : gsize magic;
3219 : :
3220 : : gint ref_count;
3221 : : };
3222 : :
3223 : : #define GVSB(b) ((struct stack_builder *) (b))
3224 : : #define GVHB(b) ((struct heap_builder *) (b))
3225 : : #define GVSB_MAGIC ((gsize) 1033660112u)
3226 : : #define GVSB_MAGIC_PARTIAL ((gsize) 2942751021u)
3227 : : #define GVHB_MAGIC ((gsize) 3087242682u)
3228 : : #define is_valid_builder(b) (GVSB(b)->magic == GVSB_MAGIC)
3229 : : #define is_valid_heap_builder(b) (GVHB(b)->magic == GVHB_MAGIC)
3230 : :
3231 : : /* Just to make sure that by adding a union to GVariantBuilder, we
3232 : : * didn't accidentally change ABI. */
3233 : : G_STATIC_ASSERT (sizeof (GVariantBuilder) == sizeof (guintptr[16]));
3234 : :
3235 : : static gboolean
3236 : 1378189 : ensure_valid_builder (GVariantBuilder *builder)
3237 : : {
3238 : 1378189 : if (builder == NULL)
3239 : 0 : return FALSE;
3240 : 1378189 : else if (is_valid_builder (builder))
3241 : 1378185 : return TRUE;
3242 : 4 : if (builder->u.s.partial_magic == GVSB_MAGIC_PARTIAL)
3243 : : {
3244 : : static GVariantBuilder cleared_builder;
3245 : :
3246 : : /* Make sure that only first two fields were set and the rest is
3247 : : * zeroed to avoid messing up the builder that had parent
3248 : : * address equal to GVSB_MAGIC_PARTIAL. */
3249 : 4 : if (memcmp (cleared_builder.u.s.y, builder->u.s.y, sizeof cleared_builder.u.s.y))
3250 : 0 : return FALSE;
3251 : :
3252 : 4 : g_variant_builder_init_static (builder, builder->u.s.type);
3253 : : }
3254 : 4 : return is_valid_builder (builder);
3255 : : }
3256 : :
3257 : : /* return_if_invalid_builder (b) is like
3258 : : * g_return_if_fail (ensure_valid_builder (b)), except that
3259 : : * the side effects of ensure_valid_builder are evaluated
3260 : : * regardless of whether G_DISABLE_CHECKS is defined or not. */
3261 : : #define return_if_invalid_builder(b) G_STMT_START { \
3262 : : gboolean valid_builder G_GNUC_UNUSED = ensure_valid_builder (b); \
3263 : : g_return_if_fail (valid_builder); \
3264 : : } G_STMT_END
3265 : :
3266 : : /* return_val_if_invalid_builder (b, val) is like
3267 : : * g_return_val_if_fail (ensure_valid_builder (b), val), except that
3268 : : * the side effects of ensure_valid_builder are evaluated
3269 : : * regardless of whether G_DISABLE_CHECKS is defined or not. */
3270 : : #define return_val_if_invalid_builder(b, val) G_STMT_START { \
3271 : : gboolean valid_builder G_GNUC_UNUSED = ensure_valid_builder (b); \
3272 : : g_return_val_if_fail (valid_builder, val); \
3273 : : } G_STMT_END
3274 : :
3275 : : /**
3276 : : * g_variant_builder_new:
3277 : : * @type: a container type
3278 : : *
3279 : : * Allocates and initialises a new #GVariantBuilder.
3280 : : *
3281 : : * You should call g_variant_builder_unref() on the return value when it
3282 : : * is no longer needed. The memory will not be automatically freed by
3283 : : * any other call.
3284 : : *
3285 : : * In most cases it is easier to place a #GVariantBuilder directly on
3286 : : * the stack of the calling function and initialise it with
3287 : : * g_variant_builder_init_static().
3288 : : *
3289 : : * Returns: (transfer full): a #GVariantBuilder
3290 : : *
3291 : : * Since: 2.24
3292 : : **/
3293 : : GVariantBuilder *
3294 : 6 : g_variant_builder_new (const GVariantType *type)
3295 : : {
3296 : : GVariantBuilder *builder;
3297 : :
3298 : 6 : builder = (GVariantBuilder *) g_slice_new (struct heap_builder);
3299 : 6 : g_variant_builder_init (builder, type);
3300 : 6 : GVHB(builder)->magic = GVHB_MAGIC;
3301 : 6 : GVHB(builder)->ref_count = 1;
3302 : :
3303 : 6 : return builder;
3304 : : }
3305 : :
3306 : : /**
3307 : : * g_variant_builder_unref:
3308 : : * @builder: (transfer full): a #GVariantBuilder allocated by g_variant_builder_new()
3309 : : *
3310 : : * Decreases the reference count on @builder.
3311 : : *
3312 : : * In the event that there are no more references, releases all memory
3313 : : * associated with the #GVariantBuilder.
3314 : : *
3315 : : * Don't call this on stack-allocated #GVariantBuilder instances or bad
3316 : : * things will happen.
3317 : : *
3318 : : * Since: 2.24
3319 : : **/
3320 : : void
3321 : 8 : g_variant_builder_unref (GVariantBuilder *builder)
3322 : : {
3323 : 8 : g_return_if_fail (is_valid_heap_builder (builder));
3324 : :
3325 : 8 : if (--GVHB(builder)->ref_count)
3326 : 2 : return;
3327 : :
3328 : 6 : g_variant_builder_clear (builder);
3329 : 6 : GVHB(builder)->magic = 0;
3330 : :
3331 : 6 : g_slice_free (struct heap_builder, GVHB(builder));
3332 : : }
3333 : :
3334 : : /**
3335 : : * g_variant_builder_ref:
3336 : : * @builder: a #GVariantBuilder allocated by g_variant_builder_new()
3337 : : *
3338 : : * Increases the reference count on @builder.
3339 : : *
3340 : : * Don't call this on stack-allocated #GVariantBuilder instances or bad
3341 : : * things will happen.
3342 : : *
3343 : : * Returns: (transfer full): a new reference to @builder
3344 : : *
3345 : : * Since: 2.24
3346 : : **/
3347 : : GVariantBuilder *
3348 : 2 : g_variant_builder_ref (GVariantBuilder *builder)
3349 : : {
3350 : 2 : g_return_val_if_fail (is_valid_heap_builder (builder), NULL);
3351 : :
3352 : 2 : GVHB(builder)->ref_count++;
3353 : :
3354 : 2 : return builder;
3355 : : }
3356 : :
3357 : : /**
3358 : : * g_variant_builder_clear: (skip)
3359 : : * @builder: a #GVariantBuilder
3360 : : *
3361 : : * Releases all memory associated with a #GVariantBuilder without
3362 : : * freeing the #GVariantBuilder structure itself.
3363 : : *
3364 : : * It typically only makes sense to do this on a stack-allocated
3365 : : * #GVariantBuilder if you want to abort building the value part-way
3366 : : * through. This function need not be called if you call
3367 : : * g_variant_builder_end() and it also doesn't need to be called on
3368 : : * builders allocated with g_variant_builder_new() (see
3369 : : * g_variant_builder_unref() for that).
3370 : : *
3371 : : * This function leaves the #GVariantBuilder structure set to all-zeros.
3372 : : * It is valid to call this function on either an initialised
3373 : : * #GVariantBuilder or one that is set to all-zeros but it is not valid
3374 : : * to call this function on uninitialised memory.
3375 : : *
3376 : : * Since: 2.24
3377 : : **/
3378 : : void
3379 : 187378 : g_variant_builder_clear (GVariantBuilder *builder)
3380 : : {
3381 : : gsize i;
3382 : :
3383 : 187378 : if (GVSB(builder)->magic == 0)
3384 : : /* all-zeros or partial case */
3385 : 4 : return;
3386 : :
3387 : 187374 : return_if_invalid_builder (builder);
3388 : :
3389 : 187374 : if (GVSB(builder)->type_owned)
3390 : 11929 : g_variant_type_free (GVSB(builder)->type);
3391 : :
3392 : 187719 : for (i = 0; i < GVSB(builder)->offset; i++)
3393 : 345 : g_variant_unref (GVSB(builder)->children[i]);
3394 : :
3395 : 187374 : g_free (GVSB(builder)->children);
3396 : :
3397 : 187374 : if (GVSB(builder)->parent)
3398 : : {
3399 : 9 : g_variant_builder_clear (GVSB(builder)->parent);
3400 : 9 : g_slice_free (GVariantBuilder, GVSB(builder)->parent);
3401 : : }
3402 : :
3403 : 187374 : memset (builder, 0, sizeof (GVariantBuilder));
3404 : : }
3405 : :
3406 : : static void
3407 : 187374 : _g_variant_builder_init (GVariantBuilder *builder,
3408 : : const GVariantType *type,
3409 : : gboolean type_owned)
3410 : : {
3411 : 187374 : g_return_if_fail (type != NULL);
3412 : 187374 : g_return_if_fail (g_variant_type_is_container (type));
3413 : :
3414 : 187374 : memset (builder, 0, sizeof (GVariantBuilder));
3415 : :
3416 : 187374 : GVSB(builder)->type = (GVariantType *)type;
3417 : 187374 : GVSB(builder)->magic = GVSB_MAGIC;
3418 : 187374 : GVSB(builder)->trusted = TRUE;
3419 : 187374 : GVSB(builder)->type_owned = type_owned;
3420 : :
3421 : 187374 : switch (*(const gchar *) type)
3422 : : {
3423 : 603 : case G_VARIANT_CLASS_VARIANT:
3424 : 603 : GVSB(builder)->uniform_item_types = TRUE;
3425 : 603 : GVSB(builder)->allocated_children = 1;
3426 : 603 : GVSB(builder)->expected_type = NULL;
3427 : 603 : GVSB(builder)->min_items = 1;
3428 : 603 : GVSB(builder)->max_items = 1;
3429 : 603 : break;
3430 : :
3431 : 58426 : case G_VARIANT_CLASS_ARRAY:
3432 : 58426 : GVSB(builder)->uniform_item_types = TRUE;
3433 : 58426 : GVSB(builder)->allocated_children = 8;
3434 : 58426 : GVSB(builder)->expected_type =
3435 : 58426 : g_variant_type_element (GVSB(builder)->type);
3436 : 58426 : GVSB(builder)->min_items = 0;
3437 : 58426 : GVSB(builder)->max_items = -1;
3438 : 58426 : break;
3439 : :
3440 : 660 : case G_VARIANT_CLASS_MAYBE:
3441 : 660 : GVSB(builder)->uniform_item_types = TRUE;
3442 : 660 : GVSB(builder)->allocated_children = 1;
3443 : 660 : GVSB(builder)->expected_type =
3444 : 660 : g_variant_type_element (GVSB(builder)->type);
3445 : 660 : GVSB(builder)->min_items = 0;
3446 : 660 : GVSB(builder)->max_items = 1;
3447 : 660 : break;
3448 : :
3449 : 78532 : case G_VARIANT_CLASS_DICT_ENTRY:
3450 : 78532 : GVSB(builder)->uniform_item_types = FALSE;
3451 : 78532 : GVSB(builder)->allocated_children = 2;
3452 : 78532 : GVSB(builder)->expected_type =
3453 : 78532 : g_variant_type_key (GVSB(builder)->type);
3454 : 78532 : GVSB(builder)->min_items = 2;
3455 : 78532 : GVSB(builder)->max_items = 2;
3456 : 78532 : break;
3457 : :
3458 : 10861 : case 'r': /* G_VARIANT_TYPE_TUPLE was given */
3459 : 10861 : GVSB(builder)->uniform_item_types = FALSE;
3460 : 10861 : GVSB(builder)->allocated_children = 8;
3461 : 10861 : GVSB(builder)->expected_type = NULL;
3462 : 10861 : GVSB(builder)->min_items = 0;
3463 : 10861 : GVSB(builder)->max_items = -1;
3464 : 10861 : break;
3465 : :
3466 : 38292 : case G_VARIANT_CLASS_TUPLE: /* a definite tuple type was given */
3467 : 38292 : GVSB(builder)->allocated_children = g_variant_type_n_items (type);
3468 : 38292 : GVSB(builder)->expected_type =
3469 : 38292 : g_variant_type_first (GVSB(builder)->type);
3470 : 38292 : GVSB(builder)->min_items = GVSB(builder)->allocated_children;
3471 : 38292 : GVSB(builder)->max_items = GVSB(builder)->allocated_children;
3472 : 38292 : GVSB(builder)->uniform_item_types = FALSE;
3473 : 38292 : break;
3474 : :
3475 : 0 : default:
3476 : : g_assert_not_reached ();
3477 : : }
3478 : :
3479 : : #if G_ANALYZER_ANALYZING
3480 : : /* Static analysers can’t couple the code in g_variant_builder_init() to the
3481 : : * code in g_variant_builder_end() by GVariantType, so end up assuming that
3482 : : * @offset and @children mismatch and that uninitialised memory is accessed
3483 : : * from @children. At runtime, this is caught by the preconditions at the top
3484 : : * of g_variant_builder_end(). Help the analyser by zero-initialising the
3485 : : * memory to avoid a false positive. */
3486 : : GVSB(builder)->children = g_new0 (GVariant *,
3487 : : GVSB(builder)->allocated_children);
3488 : : #else
3489 : 187374 : GVSB(builder)->children = g_new (GVariant *,
3490 : : GVSB(builder)->allocated_children);
3491 : : #endif
3492 : : }
3493 : :
3494 : : /**
3495 : : * g_variant_builder_init: (skip)
3496 : : * @builder: a #GVariantBuilder
3497 : : * @type: a container type
3498 : : *
3499 : : * Initialises a #GVariantBuilder structure.
3500 : : *
3501 : : * @type must be non-%NULL. It specifies the type of container to
3502 : : * construct. It can be an indefinite type such as
3503 : : * %G_VARIANT_TYPE_ARRAY or a definite type such as "as" or "(ii)".
3504 : : * Maybe, array, tuple, dictionary entry and variant-typed values may be
3505 : : * constructed.
3506 : : *
3507 : : * If using a static type such as one of the `G_VARIANT_TYPE_*` constants
3508 : : * or a `G_VARIANT_TYPE ("(ii)")` macro, it is more performant to use
3509 : : * g_variant_builder_init_static() rather than g_variant_builder_init().
3510 : : *
3511 : : * After the builder is initialised, values are added using
3512 : : * g_variant_builder_add_value() or g_variant_builder_add().
3513 : : *
3514 : : * After all the child values are added, g_variant_builder_end() frees
3515 : : * the memory associated with the builder and returns the #GVariant that
3516 : : * was created.
3517 : : *
3518 : : * This function completely ignores the previous contents of @builder.
3519 : : * On one hand this means that it is valid to pass in completely
3520 : : * uninitialised memory. On the other hand, this means that if you are
3521 : : * initialising over top of an existing #GVariantBuilder you need to
3522 : : * first call g_variant_builder_clear() in order to avoid leaking
3523 : : * memory.
3524 : : *
3525 : : * You must not call g_variant_builder_ref() or
3526 : : * g_variant_builder_unref() on a #GVariantBuilder that was initialised
3527 : : * with this function. If you ever pass a reference to a
3528 : : * #GVariantBuilder outside of the control of your own code then you
3529 : : * should assume that the person receiving that reference may try to use
3530 : : * reference counting; you should use g_variant_builder_new() instead of
3531 : : * this function.
3532 : : *
3533 : : * Since: 2.24
3534 : : **/
3535 : : void
3536 : 11929 : g_variant_builder_init (GVariantBuilder *builder,
3537 : : const GVariantType *type)
3538 : : {
3539 : 11929 : _g_variant_builder_init (builder, g_variant_type_copy (type), TRUE);
3540 : 11929 : }
3541 : :
3542 : : /**
3543 : : * g_variant_builder_init_static: (skip)
3544 : : * @builder: a #GVariantBuilder
3545 : : * @type: a container type
3546 : : *
3547 : : * Initialises a #GVariantBuilder structure.
3548 : : *
3549 : : * This function works exactly like g_variant_builder_init() but does
3550 : : * not make a copy of @type. Therefore, @type must remain valid for the
3551 : : * lifetime of @builder. This is always true of type constants like
3552 : : * `G_VARIANT_TYPE_*` or `G_VARIANT_TYPE ("(ii)")`.
3553 : : *
3554 : : * Since: 2.84
3555 : : **/
3556 : : void
3557 : 175445 : g_variant_builder_init_static (GVariantBuilder *builder,
3558 : : const GVariantType *type)
3559 : : {
3560 : 175445 : _g_variant_builder_init (builder, type, FALSE);
3561 : 175445 : }
3562 : :
3563 : : static void
3564 : 980067 : g_variant_builder_make_room (struct stack_builder *builder)
3565 : : {
3566 : 980067 : if (builder->offset == builder->allocated_children)
3567 : : {
3568 : 21920 : builder->allocated_children *= 2;
3569 : 21920 : builder->children = g_renew (GVariant *, builder->children,
3570 : : builder->allocated_children);
3571 : : }
3572 : 980067 : }
3573 : :
3574 : : /**
3575 : : * g_variant_builder_add_value:
3576 : : * @builder: a #GVariantBuilder
3577 : : * @value: a #GVariant
3578 : : *
3579 : : * Adds @value to @builder.
3580 : : *
3581 : : * It is an error to call this function in any way that would create an
3582 : : * inconsistent value to be constructed. Some examples of this are
3583 : : * putting different types of items into an array, putting the wrong
3584 : : * types or number of items in a tuple, putting more than one value into
3585 : : * a variant, etc.
3586 : : *
3587 : : * If @value is a floating reference (see g_variant_ref_sink()),
3588 : : * the @builder instance takes ownership of @value.
3589 : : *
3590 : : * Since: 2.24
3591 : : **/
3592 : : void
3593 : 980067 : g_variant_builder_add_value (GVariantBuilder *builder,
3594 : : GVariant *value)
3595 : : {
3596 : 980067 : return_if_invalid_builder (builder);
3597 : 980067 : g_return_if_fail (GVSB(builder)->offset < GVSB(builder)->max_items);
3598 : 980067 : g_return_if_fail (!GVSB(builder)->expected_type ||
3599 : : g_variant_is_of_type (value,
3600 : : GVSB(builder)->expected_type));
3601 : 980067 : g_return_if_fail (!GVSB(builder)->prev_item_type ||
3602 : : g_variant_is_of_type (value,
3603 : : GVSB(builder)->prev_item_type));
3604 : :
3605 : 980067 : GVSB(builder)->trusted &= g_variant_is_trusted (value);
3606 : :
3607 : 980067 : if (!GVSB(builder)->uniform_item_types)
3608 : : {
3609 : : /* advance our expected type pointers */
3610 : 267486 : if (GVSB(builder)->expected_type)
3611 : 252051 : GVSB(builder)->expected_type =
3612 : 252051 : g_variant_type_next (GVSB(builder)->expected_type);
3613 : :
3614 : 267486 : if (GVSB(builder)->prev_item_type)
3615 : 20309 : GVSB(builder)->prev_item_type =
3616 : 20309 : g_variant_type_next (GVSB(builder)->prev_item_type);
3617 : : }
3618 : : else
3619 : 712581 : GVSB(builder)->prev_item_type = g_variant_get_type (value);
3620 : :
3621 : 980067 : g_variant_builder_make_room (GVSB(builder));
3622 : :
3623 : 980067 : GVSB(builder)->children[GVSB(builder)->offset++] =
3624 : 980067 : g_variant_ref_sink (value);
3625 : : }
3626 : :
3627 : : /**
3628 : : * g_variant_builder_open:
3629 : : * @builder: a #GVariantBuilder
3630 : : * @type: the #GVariantType of the container
3631 : : *
3632 : : * Opens a subcontainer inside the given @builder. When done adding
3633 : : * items to the subcontainer, g_variant_builder_close() must be called. @type
3634 : : * is the type of the container: so to build a tuple of several values, @type
3635 : : * must include the tuple itself.
3636 : : *
3637 : : * It is an error to call this function in any way that would cause an
3638 : : * inconsistent value to be constructed (ie: adding too many values or
3639 : : * a value of an incorrect type).
3640 : : *
3641 : : * Example of building a nested variant:
3642 : : * |[<!-- language="C" -->
3643 : : * GVariantBuilder builder;
3644 : : * guint32 some_number = get_number ();
3645 : : * g_autoptr (GHashTable) some_dict = get_dict ();
3646 : : * GHashTableIter iter;
3647 : : * const gchar *key;
3648 : : * const GVariant *value;
3649 : : * g_autoptr (GVariant) output = NULL;
3650 : : *
3651 : : * g_variant_builder_init (&builder, G_VARIANT_TYPE ("(ua{sv})"));
3652 : : * g_variant_builder_add (&builder, "u", some_number);
3653 : : * g_variant_builder_open (&builder, G_VARIANT_TYPE ("a{sv}"));
3654 : : *
3655 : : * g_hash_table_iter_init (&iter, some_dict);
3656 : : * while (g_hash_table_iter_next (&iter, (gpointer *) &key, (gpointer *) &value))
3657 : : * {
3658 : : * g_variant_builder_open (&builder, G_VARIANT_TYPE ("{sv}"));
3659 : : * g_variant_builder_add (&builder, "s", key);
3660 : : * g_variant_builder_add (&builder, "v", value);
3661 : : * g_variant_builder_close (&builder);
3662 : : * }
3663 : : *
3664 : : * g_variant_builder_close (&builder);
3665 : : *
3666 : : * output = g_variant_builder_end (&builder);
3667 : : * ]|
3668 : : *
3669 : : * Since: 2.24
3670 : : **/
3671 : : void
3672 : 11786 : g_variant_builder_open (GVariantBuilder *builder,
3673 : : const GVariantType *type)
3674 : : {
3675 : : GVariantBuilder *parent;
3676 : :
3677 : 11786 : return_if_invalid_builder (builder);
3678 : 11786 : g_return_if_fail (GVSB(builder)->offset < GVSB(builder)->max_items);
3679 : 11786 : g_return_if_fail (!GVSB(builder)->expected_type ||
3680 : : g_variant_type_is_subtype_of (type,
3681 : : GVSB(builder)->expected_type));
3682 : 11786 : g_return_if_fail (!GVSB(builder)->prev_item_type ||
3683 : : g_variant_type_is_subtype_of (GVSB(builder)->prev_item_type,
3684 : : type));
3685 : :
3686 : 11786 : parent = g_slice_dup (GVariantBuilder, builder);
3687 : 11786 : g_variant_builder_init (builder, type);
3688 : 11786 : GVSB(builder)->parent = parent;
3689 : :
3690 : : /* push the prev_item_type down into the subcontainer */
3691 : 11786 : if (GVSB(parent)->prev_item_type)
3692 : : {
3693 : 9936 : if (!GVSB(builder)->uniform_item_types)
3694 : : /* tuples and dict entries */
3695 : 9148 : GVSB(builder)->prev_item_type =
3696 : 9148 : g_variant_type_first (GVSB(parent)->prev_item_type);
3697 : :
3698 : 788 : else if (!g_variant_type_is_variant (GVSB(builder)->type))
3699 : : /* maybes and arrays */
3700 : 550 : GVSB(builder)->prev_item_type =
3701 : 550 : g_variant_type_element (GVSB(parent)->prev_item_type);
3702 : : }
3703 : : }
3704 : :
3705 : : /**
3706 : : * g_variant_builder_close:
3707 : : * @builder: a #GVariantBuilder
3708 : : *
3709 : : * Closes the subcontainer inside the given @builder that was opened by
3710 : : * the most recent call to g_variant_builder_open().
3711 : : *
3712 : : * It is an error to call this function in any way that would create an
3713 : : * inconsistent value to be constructed (ie: too few values added to the
3714 : : * subcontainer).
3715 : : *
3716 : : * Since: 2.24
3717 : : **/
3718 : : void
3719 : 11777 : g_variant_builder_close (GVariantBuilder *builder)
3720 : : {
3721 : : GVariantBuilder *parent;
3722 : :
3723 : 11777 : return_if_invalid_builder (builder);
3724 : 11777 : g_return_if_fail (GVSB(builder)->parent != NULL);
3725 : :
3726 : 11777 : parent = GVSB(builder)->parent;
3727 : 11777 : GVSB(builder)->parent = NULL;
3728 : :
3729 : 11777 : g_variant_builder_add_value (parent, g_variant_builder_end (builder));
3730 : 11777 : *builder = *parent;
3731 : :
3732 : 11777 : g_slice_free (GVariantBuilder, parent);
3733 : : }
3734 : :
3735 : : /*< private >
3736 : : * g_variant_make_maybe_type:
3737 : : * @element: a #GVariant
3738 : : *
3739 : : * Return the type of a maybe containing @element.
3740 : : */
3741 : : static GVariantType *
3742 : 39 : g_variant_make_maybe_type (GVariant *element)
3743 : : {
3744 : 39 : return g_variant_type_new_maybe (g_variant_get_type (element));
3745 : : }
3746 : :
3747 : : /*< private >
3748 : : * g_variant_make_array_type:
3749 : : * @element: a #GVariant
3750 : : *
3751 : : * Return the type of an array containing @element.
3752 : : */
3753 : : static GVariantType *
3754 : 476 : g_variant_make_array_type (GVariant *element)
3755 : : {
3756 : 476 : return g_variant_type_new_array (g_variant_get_type (element));
3757 : : }
3758 : :
3759 : : /**
3760 : : * g_variant_builder_end:
3761 : : * @builder: a #GVariantBuilder
3762 : : *
3763 : : * Ends the builder process and returns the constructed value.
3764 : : *
3765 : : * It is not permissible to use @builder in any way after this call
3766 : : * except for reference counting operations (in the case of a
3767 : : * heap-allocated #GVariantBuilder) or by reinitialising it with
3768 : : * g_variant_builder_init() (in the case of stack-allocated). This
3769 : : * means that for the stack-allocated builders there is no need to
3770 : : * call g_variant_builder_clear() after the call to
3771 : : * g_variant_builder_end().
3772 : : *
3773 : : * It is an error to call this function in any way that would create an
3774 : : * inconsistent value to be constructed (ie: insufficient number of
3775 : : * items added to a container with a specific number of children
3776 : : * required). It is also an error to call this function if the builder
3777 : : * was created with an indefinite array or maybe type and no children
3778 : : * have been added; in this case it is impossible to infer the type of
3779 : : * the empty array.
3780 : : *
3781 : : * Returns: (transfer none): a new, floating, #GVariant
3782 : : *
3783 : : * Since: 2.24
3784 : : **/
3785 : : GVariant *
3786 : 187185 : g_variant_builder_end (GVariantBuilder *builder)
3787 : : {
3788 : : const GVariantType *type;
3789 : 187185 : GVariantType *new_type = NULL;
3790 : : GVariant *value;
3791 : : GVariant **children;
3792 : :
3793 : 187185 : return_val_if_invalid_builder (builder, NULL);
3794 : 187185 : g_return_val_if_fail (GVSB(builder)->offset >= GVSB(builder)->min_items,
3795 : : NULL);
3796 : 187185 : g_return_val_if_fail (!GVSB(builder)->uniform_item_types ||
3797 : : GVSB(builder)->prev_item_type != NULL ||
3798 : : g_variant_type_is_definite (GVSB(builder)->type),
3799 : : NULL);
3800 : :
3801 : 187185 : if (g_variant_type_is_definite (GVSB(builder)->type))
3802 : 106798 : type = GVSB(builder)->type;
3803 : :
3804 : 80387 : else if (g_variant_type_is_maybe (GVSB(builder)->type))
3805 : 39 : type = new_type = g_variant_make_maybe_type (GVSB(builder)->children[0]);
3806 : :
3807 : 80348 : else if (g_variant_type_is_array (GVSB(builder)->type))
3808 : 476 : type = new_type = g_variant_make_array_type (GVSB(builder)->children[0]);
3809 : :
3810 : 79872 : else if (g_variant_type_is_tuple (GVSB(builder)->type))
3811 : 10861 : type = new_type = g_variant_make_tuple_type (GVSB(builder)->children,
3812 : : GVSB(builder)->offset);
3813 : :
3814 : 69011 : else if (g_variant_type_is_dict_entry (GVSB(builder)->type))
3815 : 69011 : type = new_type = g_variant_make_dict_entry_type (GVSB(builder)->children[0],
3816 : 69011 : GVSB(builder)->children[1]);
3817 : : else
3818 : : g_assert_not_reached ();
3819 : :
3820 : 187185 : children = GVSB(builder)->children;
3821 : :
3822 : : /* shrink allocation to release extra space to allocator */
3823 : 187185 : if G_UNLIKELY (GVSB(builder)->offset < GVSB(builder)->allocated_children)
3824 : 69339 : children = g_renew (GVariant *, children, GVSB(builder)->offset);
3825 : :
3826 : 187185 : value = g_variant_new_from_children (type,
3827 : : children,
3828 : : GVSB(builder)->offset,
3829 : 187185 : GVSB(builder)->trusted);
3830 : 187185 : GVSB(builder)->children = NULL;
3831 : 187185 : GVSB(builder)->offset = 0;
3832 : :
3833 : 187185 : g_variant_builder_clear (builder);
3834 : :
3835 : 187185 : if (new_type != NULL)
3836 : 80387 : g_variant_type_free (new_type);
3837 : :
3838 : 187185 : return value;
3839 : : }
3840 : :
3841 : : /* GVariantDict {{{1 */
3842 : :
3843 : : /**
3844 : : * GVariantDict:
3845 : : *
3846 : : * #GVariantDict is a mutable interface to #GVariant dictionaries.
3847 : : *
3848 : : * It can be used for doing a sequence of dictionary lookups in an
3849 : : * efficient way on an existing #GVariant dictionary or it can be used
3850 : : * to construct new dictionaries with a hashtable-like interface. It
3851 : : * can also be used for taking existing dictionaries and modifying them
3852 : : * in order to create new ones.
3853 : : *
3854 : : * #GVariantDict can only be used with %G_VARIANT_TYPE_VARDICT
3855 : : * dictionaries.
3856 : : *
3857 : : * It is possible to use #GVariantDict allocated on the stack or on the
3858 : : * heap. When using a stack-allocated #GVariantDict, you begin with a
3859 : : * call to g_variant_dict_init() and free the resources with a call to
3860 : : * g_variant_dict_clear().
3861 : : *
3862 : : * Heap-allocated #GVariantDict follows normal refcounting rules: you
3863 : : * allocate it with g_variant_dict_new() and use g_variant_dict_ref()
3864 : : * and g_variant_dict_unref().
3865 : : *
3866 : : * g_variant_dict_end() is used to convert the #GVariantDict back into a
3867 : : * dictionary-type #GVariant. When used with stack-allocated instances,
3868 : : * this also implicitly frees all associated memory, but for
3869 : : * heap-allocated instances, you must still call g_variant_dict_unref()
3870 : : * afterwards.
3871 : : *
3872 : : * You will typically want to use a heap-allocated #GVariantDict when
3873 : : * you expose it as part of an API. For most other uses, the
3874 : : * stack-allocated form will be more convenient.
3875 : : *
3876 : : * Consider the following two examples that do the same thing in each
3877 : : * style: take an existing dictionary and look up the "count" uint32
3878 : : * key, adding 1 to it if it is found, or returning an error if the
3879 : : * key is not found. Each returns the new dictionary as a floating
3880 : : * #GVariant.
3881 : : *
3882 : : * ## Using a stack-allocated GVariantDict
3883 : : *
3884 : : * |[<!-- language="C" -->
3885 : : * GVariant *
3886 : : * add_to_count (GVariant *orig,
3887 : : * GError **error)
3888 : : * {
3889 : : * GVariantDict dict;
3890 : : * guint32 count;
3891 : : *
3892 : : * g_variant_dict_init (&dict, orig);
3893 : : * if (!g_variant_dict_lookup (&dict, "count", "u", &count))
3894 : : * {
3895 : : * g_set_error (...);
3896 : : * g_variant_dict_clear (&dict);
3897 : : * return NULL;
3898 : : * }
3899 : : *
3900 : : * g_variant_dict_insert (&dict, "count", "u", count + 1);
3901 : : *
3902 : : * return g_variant_dict_end (&dict);
3903 : : * }
3904 : : * ]|
3905 : : *
3906 : : * ## Using heap-allocated GVariantDict
3907 : : *
3908 : : * |[<!-- language="C" -->
3909 : : * GVariant *
3910 : : * add_to_count (GVariant *orig,
3911 : : * GError **error)
3912 : : * {
3913 : : * GVariantDict *dict;
3914 : : * GVariant *result;
3915 : : * guint32 count;
3916 : : *
3917 : : * dict = g_variant_dict_new (orig);
3918 : : *
3919 : : * if (g_variant_dict_lookup (dict, "count", "u", &count))
3920 : : * {
3921 : : * g_variant_dict_insert (dict, "count", "u", count + 1);
3922 : : * result = g_variant_dict_end (dict);
3923 : : * }
3924 : : * else
3925 : : * {
3926 : : * g_set_error (...);
3927 : : * result = NULL;
3928 : : * }
3929 : : *
3930 : : * g_variant_dict_unref (dict);
3931 : : *
3932 : : * return result;
3933 : : * }
3934 : : * ]|
3935 : : *
3936 : : * Since: 2.40
3937 : : **/
3938 : : struct stack_dict
3939 : : {
3940 : : GHashTable *values;
3941 : : gsize magic;
3942 : : };
3943 : :
3944 : : G_STATIC_ASSERT (sizeof (struct stack_dict) <= sizeof (GVariantDict));
3945 : :
3946 : : struct heap_dict
3947 : : {
3948 : : struct stack_dict dict;
3949 : : gint ref_count;
3950 : : gsize magic;
3951 : : };
3952 : :
3953 : : #define GVSD(d) ((struct stack_dict *) (d))
3954 : : #define GVHD(d) ((struct heap_dict *) (d))
3955 : : #define GVSD_MAGIC ((gsize) 2579507750u)
3956 : : #define GVSD_MAGIC_PARTIAL ((gsize) 3488698669u)
3957 : : #define GVHD_MAGIC ((gsize) 2450270775u)
3958 : : #define is_valid_dict(d) (GVSD(d)->magic == GVSD_MAGIC)
3959 : : #define is_valid_heap_dict(d) (GVHD(d)->magic == GVHD_MAGIC)
3960 : :
3961 : : /* Just to make sure that by adding a union to GVariantDict, we didn't
3962 : : * accidentally change ABI. */
3963 : : G_STATIC_ASSERT (sizeof (GVariantDict) == sizeof (guintptr[16]));
3964 : :
3965 : : static gboolean
3966 : 95 : ensure_valid_dict (GVariantDict *dict)
3967 : : {
3968 : 95 : if (dict == NULL)
3969 : 0 : return FALSE;
3970 : 95 : else if (is_valid_dict (dict))
3971 : 94 : return TRUE;
3972 : 1 : if (dict->u.s.partial_magic == GVSD_MAGIC_PARTIAL)
3973 : : {
3974 : : static GVariantDict cleared_dict;
3975 : :
3976 : : /* Make sure that only first two fields were set and the rest is
3977 : : * zeroed to avoid messing up the builder that had parent
3978 : : * address equal to GVSB_MAGIC_PARTIAL. */
3979 : 1 : if (memcmp (cleared_dict.u.s.y, dict->u.s.y, sizeof cleared_dict.u.s.y))
3980 : 0 : return FALSE;
3981 : :
3982 : 1 : g_variant_dict_init (dict, dict->u.s.asv);
3983 : : }
3984 : 1 : return is_valid_dict (dict);
3985 : : }
3986 : :
3987 : : /* return_if_invalid_dict (d) is like
3988 : : * g_return_if_fail (ensure_valid_dict (d)), except that
3989 : : * the side effects of ensure_valid_dict are evaluated
3990 : : * regardless of whether G_DISABLE_CHECKS is defined or not. */
3991 : : #define return_if_invalid_dict(d) G_STMT_START { \
3992 : : gboolean valid_dict G_GNUC_UNUSED = ensure_valid_dict (d); \
3993 : : g_return_if_fail (valid_dict); \
3994 : : } G_STMT_END
3995 : :
3996 : : /* return_val_if_invalid_dict (d, val) is like
3997 : : * g_return_val_if_fail (ensure_valid_dict (d), val), except that
3998 : : * the side effects of ensure_valid_dict are evaluated
3999 : : * regardless of whether G_DISABLE_CHECKS is defined or not. */
4000 : : #define return_val_if_invalid_dict(d, val) G_STMT_START { \
4001 : : gboolean valid_dict G_GNUC_UNUSED = ensure_valid_dict (d); \
4002 : : g_return_val_if_fail (valid_dict, val); \
4003 : : } G_STMT_END
4004 : :
4005 : : /**
4006 : : * g_variant_dict_new:
4007 : : * @from_asv: (nullable): the #GVariant with which to initialise the
4008 : : * dictionary
4009 : : *
4010 : : * Allocates and initialises a new #GVariantDict.
4011 : : *
4012 : : * You should call g_variant_dict_unref() on the return value when it
4013 : : * is no longer needed. The memory will not be automatically freed by
4014 : : * any other call.
4015 : : *
4016 : : * In some cases it may be easier to place a #GVariantDict directly on
4017 : : * the stack of the calling function and initialise it with
4018 : : * g_variant_dict_init(). This is particularly useful when you are
4019 : : * using #GVariantDict to construct a #GVariant.
4020 : : *
4021 : : * Returns: (transfer full): a #GVariantDict
4022 : : *
4023 : : * Since: 2.40
4024 : : **/
4025 : : GVariantDict *
4026 : 44 : g_variant_dict_new (GVariant *from_asv)
4027 : : {
4028 : : GVariantDict *dict;
4029 : :
4030 : : /* We actually want to treat the allocation as a `struct heap_dict`, but the
4031 : : * compiler will warn if it’s not at least as big as `struct GVariantDict`. */
4032 : : G_STATIC_ASSERT (sizeof (GVariantDict) >= sizeof (struct heap_dict));
4033 : :
4034 : 44 : dict = g_malloc (sizeof (GVariantDict));
4035 : 44 : g_variant_dict_init (dict, from_asv);
4036 : 44 : GVHD(dict)->magic = GVHD_MAGIC;
4037 : 44 : GVHD(dict)->ref_count = 1;
4038 : :
4039 : 44 : return dict;
4040 : : }
4041 : :
4042 : : /**
4043 : : * g_variant_dict_init: (skip)
4044 : : * @dict: a #GVariantDict
4045 : : * @from_asv: (nullable): the initial value for @dict
4046 : : *
4047 : : * Initialises a #GVariantDict structure.
4048 : : *
4049 : : * If @from_asv is given, it is used to initialise the dictionary.
4050 : : *
4051 : : * This function completely ignores the previous contents of @dict. On
4052 : : * one hand this means that it is valid to pass in completely
4053 : : * uninitialised memory. On the other hand, this means that if you are
4054 : : * initialising over top of an existing #GVariantDict you need to first
4055 : : * call g_variant_dict_clear() in order to avoid leaking memory.
4056 : : *
4057 : : * You must not call g_variant_dict_ref() or g_variant_dict_unref() on a
4058 : : * #GVariantDict that was initialised with this function. If you ever
4059 : : * pass a reference to a #GVariantDict outside of the control of your
4060 : : * own code then you should assume that the person receiving that
4061 : : * reference may try to use reference counting; you should use
4062 : : * g_variant_dict_new() instead of this function.
4063 : : *
4064 : : * Since: 2.40
4065 : : **/
4066 : : void
4067 : 58 : g_variant_dict_init (GVariantDict *dict,
4068 : : GVariant *from_asv)
4069 : : {
4070 : : GVariantIter iter;
4071 : : gchar *key;
4072 : : GVariant *value;
4073 : :
4074 : 58 : GVSD(dict)->values = g_hash_table_new_full (g_str_hash, g_str_equal, g_free, (GDestroyNotify) g_variant_unref);
4075 : 58 : GVSD(dict)->magic = GVSD_MAGIC;
4076 : :
4077 : 58 : if (from_asv)
4078 : : {
4079 : 17 : g_variant_iter_init (&iter, from_asv);
4080 : 37 : while (g_variant_iter_next (&iter, "{sv}", &key, &value))
4081 : 20 : g_hash_table_insert (GVSD(dict)->values, key, value);
4082 : : }
4083 : 58 : }
4084 : :
4085 : : /**
4086 : : * g_variant_dict_lookup:
4087 : : * @dict: a #GVariantDict
4088 : : * @key: the key to look up in the dictionary
4089 : : * @format_string: a GVariant format string
4090 : : * @...: the arguments to unpack the value into
4091 : : *
4092 : : * Looks up a value in a #GVariantDict.
4093 : : *
4094 : : * This function is a wrapper around g_variant_dict_lookup_value() and
4095 : : * g_variant_get(). In the case that %NULL would have been returned,
4096 : : * this function returns %FALSE and does not modify the values of the arguments
4097 : : * passed in to @.... Otherwise, it unpacks the returned
4098 : : * value and returns %TRUE.
4099 : : *
4100 : : * @format_string determines the C types that are used for unpacking the
4101 : : * values and also determines if the values are copied or borrowed, see the
4102 : : * section on [`GVariant` format strings](gvariant-format-strings.html#pointers).
4103 : : *
4104 : : * Returns: %TRUE if a value was unpacked
4105 : : *
4106 : : * Since: 2.40
4107 : : **/
4108 : : gboolean
4109 : 16 : g_variant_dict_lookup (GVariantDict *dict,
4110 : : const gchar *key,
4111 : : const gchar *format_string,
4112 : : ...)
4113 : : {
4114 : : GVariant *value;
4115 : : va_list ap;
4116 : :
4117 : 16 : return_val_if_invalid_dict (dict, FALSE);
4118 : 16 : g_return_val_if_fail (key != NULL, FALSE);
4119 : 16 : g_return_val_if_fail (format_string != NULL, FALSE);
4120 : :
4121 : 16 : value = g_hash_table_lookup (GVSD(dict)->values, key);
4122 : :
4123 : 16 : if (value == NULL || !g_variant_check_format_string (value, format_string, FALSE))
4124 : 3 : return FALSE;
4125 : :
4126 : 13 : va_start (ap, format_string);
4127 : 13 : g_variant_get_va (value, format_string, NULL, &ap);
4128 : 13 : va_end (ap);
4129 : :
4130 : 13 : return TRUE;
4131 : : }
4132 : :
4133 : : /**
4134 : : * g_variant_dict_lookup_value:
4135 : : * @dict: a #GVariantDict
4136 : : * @key: the key to look up in the dictionary
4137 : : * @expected_type: (nullable): a #GVariantType, or %NULL
4138 : : *
4139 : : * Looks up a value in a #GVariantDict.
4140 : : *
4141 : : * If @key is not found in @dictionary, %NULL is returned.
4142 : : *
4143 : : * The @expected_type string specifies what type of value is expected.
4144 : : * If the value associated with @key has a different type then %NULL is
4145 : : * returned.
4146 : : *
4147 : : * If the key is found and the value has the correct type, it is
4148 : : * returned. If @expected_type was specified then any non-%NULL return
4149 : : * value will have this type.
4150 : : *
4151 : : * Returns: (transfer full) (nullable): the value of the dictionary key, or %NULL
4152 : : *
4153 : : * Since: 2.40
4154 : : **/
4155 : : GVariant *
4156 : 0 : g_variant_dict_lookup_value (GVariantDict *dict,
4157 : : const gchar *key,
4158 : : const GVariantType *expected_type)
4159 : : {
4160 : : GVariant *result;
4161 : :
4162 : 0 : return_val_if_invalid_dict (dict, NULL);
4163 : 0 : g_return_val_if_fail (key != NULL, NULL);
4164 : :
4165 : 0 : result = g_hash_table_lookup (GVSD(dict)->values, key);
4166 : :
4167 : 0 : if (result && (!expected_type || g_variant_is_of_type (result, expected_type)))
4168 : 0 : return g_variant_ref (result);
4169 : :
4170 : 0 : return NULL;
4171 : : }
4172 : :
4173 : : /**
4174 : : * g_variant_dict_contains:
4175 : : * @dict: a #GVariantDict
4176 : : * @key: the key to look up in the dictionary
4177 : : *
4178 : : * Checks if @key exists in @dict.
4179 : : *
4180 : : * Returns: %TRUE if @key is in @dict
4181 : : *
4182 : : * Since: 2.40
4183 : : **/
4184 : : gboolean
4185 : 9 : g_variant_dict_contains (GVariantDict *dict,
4186 : : const gchar *key)
4187 : : {
4188 : 9 : return_val_if_invalid_dict (dict, FALSE);
4189 : 9 : g_return_val_if_fail (key != NULL, FALSE);
4190 : :
4191 : 9 : return g_hash_table_contains (GVSD(dict)->values, key);
4192 : : }
4193 : :
4194 : : /**
4195 : : * g_variant_dict_insert:
4196 : : * @dict: a #GVariantDict
4197 : : * @key: the key to insert a value for
4198 : : * @format_string: a #GVariant varargs format string
4199 : : * @...: arguments, as per @format_string
4200 : : *
4201 : : * Inserts a value into a #GVariantDict.
4202 : : *
4203 : : * This call is a convenience wrapper that is exactly equivalent to
4204 : : * calling g_variant_new() followed by g_variant_dict_insert_value().
4205 : : *
4206 : : * Since: 2.40
4207 : : **/
4208 : : void
4209 : 0 : g_variant_dict_insert (GVariantDict *dict,
4210 : : const gchar *key,
4211 : : const gchar *format_string,
4212 : : ...)
4213 : : {
4214 : : va_list ap;
4215 : :
4216 : 0 : return_if_invalid_dict (dict);
4217 : 0 : g_return_if_fail (key != NULL);
4218 : 0 : g_return_if_fail (format_string != NULL);
4219 : :
4220 : 0 : va_start (ap, format_string);
4221 : 0 : g_variant_dict_insert_value (dict, key, g_variant_new_va (format_string, NULL, &ap));
4222 : 0 : va_end (ap);
4223 : : }
4224 : :
4225 : : /**
4226 : : * g_variant_dict_insert_value:
4227 : : * @dict: a #GVariantDict
4228 : : * @key: the key to insert a value for
4229 : : * @value: the value to insert
4230 : : *
4231 : : * Inserts (or replaces) a key in a #GVariantDict.
4232 : : *
4233 : : * @value is consumed if it is floating.
4234 : : *
4235 : : * Since: 2.40
4236 : : **/
4237 : : void
4238 : 5 : g_variant_dict_insert_value (GVariantDict *dict,
4239 : : const gchar *key,
4240 : : GVariant *value)
4241 : : {
4242 : 5 : return_if_invalid_dict (dict);
4243 : 5 : g_return_if_fail (key != NULL);
4244 : 5 : g_return_if_fail (value != NULL);
4245 : :
4246 : 10 : g_hash_table_insert (GVSD(dict)->values, g_strdup (key), g_variant_ref_sink (value));
4247 : : }
4248 : :
4249 : : /**
4250 : : * g_variant_dict_remove:
4251 : : * @dict: a #GVariantDict
4252 : : * @key: the key to remove
4253 : : *
4254 : : * Removes a key and its associated value from a #GVariantDict.
4255 : : *
4256 : : * Returns: %TRUE if the key was found and removed
4257 : : *
4258 : : * Since: 2.40
4259 : : **/
4260 : : gboolean
4261 : 0 : g_variant_dict_remove (GVariantDict *dict,
4262 : : const gchar *key)
4263 : : {
4264 : 0 : return_val_if_invalid_dict (dict, FALSE);
4265 : 0 : g_return_val_if_fail (key != NULL, FALSE);
4266 : :
4267 : 0 : return g_hash_table_remove (GVSD(dict)->values, key);
4268 : : }
4269 : :
4270 : : /**
4271 : : * g_variant_dict_clear:
4272 : : * @dict: a #GVariantDict
4273 : : *
4274 : : * Releases all memory associated with a #GVariantDict without freeing
4275 : : * the #GVariantDict structure itself.
4276 : : *
4277 : : * It typically only makes sense to do this on a stack-allocated
4278 : : * #GVariantDict if you want to abort building the value part-way
4279 : : * through. This function need not be called if you call
4280 : : * g_variant_dict_end() and it also doesn't need to be called on dicts
4281 : : * allocated with g_variant_dict_new (see g_variant_dict_unref() for
4282 : : * that).
4283 : : *
4284 : : * It is valid to call this function on either an initialised
4285 : : * #GVariantDict or one that was previously cleared by an earlier call
4286 : : * to g_variant_dict_clear() but it is not valid to call this function
4287 : : * on uninitialised memory.
4288 : : *
4289 : : * Since: 2.40
4290 : : **/
4291 : : void
4292 : 64 : g_variant_dict_clear (GVariantDict *dict)
4293 : : {
4294 : 64 : if (GVSD(dict)->magic == 0)
4295 : : /* all-zeros case */
4296 : 6 : return;
4297 : :
4298 : 58 : return_if_invalid_dict (dict);
4299 : :
4300 : 58 : g_hash_table_unref (GVSD(dict)->values);
4301 : 58 : GVSD(dict)->values = NULL;
4302 : :
4303 : 58 : GVSD(dict)->magic = 0;
4304 : : }
4305 : :
4306 : : /**
4307 : : * g_variant_dict_end:
4308 : : * @dict: a #GVariantDict
4309 : : *
4310 : : * Returns the current value of @dict as a #GVariant of type
4311 : : * %G_VARIANT_TYPE_VARDICT, clearing it in the process.
4312 : : *
4313 : : * It is not permissible to use @dict in any way after this call except
4314 : : * for reference counting operations (in the case of a heap-allocated
4315 : : * #GVariantDict) or by reinitialising it with g_variant_dict_init() (in
4316 : : * the case of stack-allocated).
4317 : : *
4318 : : * Returns: (transfer none): a new, floating, #GVariant
4319 : : *
4320 : : * Since: 2.40
4321 : : **/
4322 : : GVariant *
4323 : 7 : g_variant_dict_end (GVariantDict *dict)
4324 : : {
4325 : : GVariantBuilder builder;
4326 : : GHashTableIter iter;
4327 : : gpointer key, value;
4328 : :
4329 : 7 : return_val_if_invalid_dict (dict, NULL);
4330 : :
4331 : 7 : g_variant_builder_init_static (&builder, G_VARIANT_TYPE_VARDICT);
4332 : :
4333 : 7 : g_hash_table_iter_init (&iter, GVSD(dict)->values);
4334 : 12 : while (g_hash_table_iter_next (&iter, &key, &value))
4335 : 5 : g_variant_builder_add (&builder, "{sv}", (const gchar *) key, (GVariant *) value);
4336 : :
4337 : 7 : g_variant_dict_clear (dict);
4338 : :
4339 : 7 : return g_variant_builder_end (&builder);
4340 : : }
4341 : :
4342 : : /**
4343 : : * g_variant_dict_ref:
4344 : : * @dict: a heap-allocated #GVariantDict
4345 : : *
4346 : : * Increases the reference count on @dict.
4347 : : *
4348 : : * Don't call this on stack-allocated #GVariantDict instances or bad
4349 : : * things will happen.
4350 : : *
4351 : : * Returns: (transfer full): a new reference to @dict
4352 : : *
4353 : : * Since: 2.40
4354 : : **/
4355 : : GVariantDict *
4356 : 40 : g_variant_dict_ref (GVariantDict *dict)
4357 : : {
4358 : 40 : g_return_val_if_fail (is_valid_heap_dict (dict), NULL);
4359 : :
4360 : 40 : GVHD(dict)->ref_count++;
4361 : :
4362 : 40 : return dict;
4363 : : }
4364 : :
4365 : : /**
4366 : : * g_variant_dict_unref:
4367 : : * @dict: (transfer full): a heap-allocated #GVariantDict
4368 : : *
4369 : : * Decreases the reference count on @dict.
4370 : : *
4371 : : * In the event that there are no more references, releases all memory
4372 : : * associated with the #GVariantDict.
4373 : : *
4374 : : * Don't call this on stack-allocated #GVariantDict instances or bad
4375 : : * things will happen.
4376 : : *
4377 : : * Since: 2.40
4378 : : **/
4379 : : void
4380 : 84 : g_variant_dict_unref (GVariantDict *dict)
4381 : : {
4382 : 84 : g_return_if_fail (is_valid_heap_dict (dict));
4383 : :
4384 : 84 : if (--GVHD(dict)->ref_count == 0)
4385 : : {
4386 : 44 : g_variant_dict_clear (dict);
4387 : 44 : g_free_sized (dict, sizeof (GVariantDict));
4388 : : }
4389 : : }
4390 : :
4391 : :
4392 : : /* Format strings {{{1 */
4393 : : /*< private >
4394 : : * g_variant_format_string_scan:
4395 : : * @string: a string that may be prefixed with a format string
4396 : : * @limit: (nullable) (default NULL): a pointer to the end of @string,
4397 : : * or %NULL
4398 : : * @endptr: (nullable) (default NULL): location to store the end pointer,
4399 : : * or %NULL
4400 : : *
4401 : : * Checks the string pointed to by @string for starting with a properly
4402 : : * formed #GVariant varargs format string. If no valid format string is
4403 : : * found then %FALSE is returned.
4404 : : *
4405 : : * If @string does start with a valid format string then %TRUE is
4406 : : * returned. If @endptr is non-%NULL then it is updated to point to the
4407 : : * first character after the format string.
4408 : : *
4409 : : * If @limit is non-%NULL then @limit (and any character after it) will
4410 : : * not be accessed and the effect is otherwise equivalent to if the
4411 : : * character at @limit were nul.
4412 : : *
4413 : : * See the section on [GVariant format strings](gvariant-format-strings.html).
4414 : : *
4415 : : * Returns: %TRUE if there was a valid format string
4416 : : *
4417 : : * Since: 2.24
4418 : : */
4419 : : gboolean
4420 : 960005 : g_variant_format_string_scan (const gchar *string,
4421 : : const gchar *limit,
4422 : : const gchar **endptr)
4423 : : {
4424 : : #define next_char() (string == limit ? '\0' : *(string++))
4425 : : #define peek_char() (string == limit ? '\0' : *string)
4426 : : char c;
4427 : :
4428 : 960005 : switch (next_char())
4429 : : {
4430 : 402049 : case 'b': case 'y': case 'n': case 'q': case 'i': case 'u':
4431 : : case 'x': case 't': case 'h': case 'd': case 's': case 'o':
4432 : : case 'g': case 'v': case '*': case '?': case 'r':
4433 : 402049 : break;
4434 : :
4435 : 351 : case 'm':
4436 : 351 : return g_variant_format_string_scan (string, limit, endptr);
4437 : :
4438 : 5730 : case 'a':
4439 : : case '@':
4440 : 5730 : return g_variant_type_string_scan (string, limit, endptr);
4441 : :
4442 : 75906 : case '(':
4443 : 246756 : while (peek_char() != ')')
4444 : 170854 : if (!g_variant_format_string_scan (string, limit, &string))
4445 : 4 : return FALSE;
4446 : :
4447 : 75902 : next_char(); /* consume ')' */
4448 : 75902 : break;
4449 : :
4450 : 342133 : case '{':
4451 : 342133 : c = next_char();
4452 : :
4453 : 342133 : if (c == '&')
4454 : : {
4455 : 2549 : c = next_char ();
4456 : :
4457 : 2549 : if (c != 's' && c != 'o' && c != 'g')
4458 : 2 : return FALSE;
4459 : : }
4460 : : else
4461 : : {
4462 : 339584 : if (c == '@')
4463 : 4 : c = next_char ();
4464 : :
4465 : : /* ISO/IEC 9899:1999 (C99) §7.21.5.2:
4466 : : * The terminating null character is considered to be
4467 : : * part of the string.
4468 : : */
4469 : 339584 : if (c != '\0' && strchr ("bynqiuxthdsog?", c) == NULL)
4470 : 4 : return FALSE;
4471 : : }
4472 : :
4473 : 342127 : if (!g_variant_format_string_scan (string, limit, &string))
4474 : 2 : return FALSE;
4475 : :
4476 : 342125 : if (next_char() != '}')
4477 : 1 : return FALSE;
4478 : :
4479 : 342124 : break;
4480 : :
4481 : 398 : case '^':
4482 : 398 : if ((c = next_char()) == 'a')
4483 : : {
4484 : 389 : if ((c = next_char()) == '&')
4485 : : {
4486 : 202 : if ((c = next_char()) == 'a')
4487 : : {
4488 : 11 : if ((c = next_char()) == 'y')
4489 : 11 : break; /* '^a&ay' */
4490 : : }
4491 : :
4492 : 191 : else if (c == 's' || c == 'o')
4493 : : break; /* '^a&s', '^a&o' */
4494 : : }
4495 : :
4496 : 187 : else if (c == 'a')
4497 : : {
4498 : 38 : if ((c = next_char()) == 'y')
4499 : 38 : break; /* '^aay' */
4500 : : }
4501 : :
4502 : 149 : else if (c == 's' || c == 'o')
4503 : : break; /* '^as', '^ao' */
4504 : :
4505 : 61 : else if (c == 'y')
4506 : 60 : break; /* '^ay' */
4507 : : }
4508 : 9 : else if (c == '&')
4509 : : {
4510 : 8 : if ((c = next_char()) == 'a')
4511 : : {
4512 : 8 : if ((c = next_char()) == 'y')
4513 : 8 : break; /* '^&ay' */
4514 : : }
4515 : : }
4516 : :
4517 : 3 : return FALSE;
4518 : :
4519 : 133432 : case '&':
4520 : 133432 : c = next_char();
4521 : :
4522 : 133432 : if (c != 's' && c != 'o' && c != 'g')
4523 : 1 : return FALSE;
4524 : :
4525 : 133431 : break;
4526 : :
4527 : 6 : default:
4528 : 6 : return FALSE;
4529 : : }
4530 : :
4531 : 953901 : if (endptr != NULL)
4532 : 953901 : *endptr = string;
4533 : :
4534 : : #undef next_char
4535 : : #undef peek_char
4536 : :
4537 : 953901 : return TRUE;
4538 : : }
4539 : :
4540 : : /**
4541 : : * g_variant_check_format_string:
4542 : : * @value: a #GVariant
4543 : : * @format_string: a valid #GVariant format string
4544 : : * @copy_only: %TRUE to ensure the format string makes deep copies
4545 : : *
4546 : : * Checks if calling g_variant_get() with @format_string on @value would
4547 : : * be valid from a type-compatibility standpoint. @format_string is
4548 : : * assumed to be a valid format string (from a syntactic standpoint).
4549 : : *
4550 : : * If @copy_only is %TRUE then this function additionally checks that it
4551 : : * would be safe to call g_variant_unref() on @value immediately after
4552 : : * the call to g_variant_get() without invalidating the result. This is
4553 : : * only possible if deep copies are made (ie: there are no pointers to
4554 : : * the data inside of the soon-to-be-freed #GVariant instance). If this
4555 : : * check fails then a g_critical() is printed and %FALSE is returned.
4556 : : *
4557 : : * This function is meant to be used by functions that wish to provide
4558 : : * varargs accessors to #GVariant values of uncertain values (eg:
4559 : : * g_variant_lookup() or g_menu_model_get_item_attribute()).
4560 : : *
4561 : : * Returns: %TRUE if @format_string is safe to use
4562 : : *
4563 : : * Since: 2.34
4564 : : */
4565 : : gboolean
4566 : 37 : g_variant_check_format_string (GVariant *value,
4567 : : const gchar *format_string,
4568 : : gboolean copy_only)
4569 : : {
4570 : 37 : const gchar *original_format = format_string;
4571 : : const gchar *type_string;
4572 : :
4573 : : /* Interesting factoid: assuming a format string is valid, it can be
4574 : : * converted to a type string by removing all '@' '&' and '^'
4575 : : * characters.
4576 : : *
4577 : : * Instead of doing that, we can just skip those characters when
4578 : : * comparing it to the type string of @value.
4579 : : *
4580 : : * For the copy-only case we can just drop the '&' from the list of
4581 : : * characters to skip over. A '&' will never appear in a type string
4582 : : * so we know that it won't be possible to return %TRUE if it is in a
4583 : : * format string.
4584 : : */
4585 : 37 : type_string = g_variant_get_type_string (value);
4586 : :
4587 : 146 : while (*type_string || *format_string)
4588 : : {
4589 : 117 : gchar format = *format_string++;
4590 : :
4591 : 117 : switch (format)
4592 : : {
4593 : 16 : case '&':
4594 : 16 : if G_UNLIKELY (copy_only)
4595 : : {
4596 : : /* for the love of all that is good, please don't mark this string for translation... */
4597 : 4 : g_critical ("g_variant_check_format_string() is being called by a function with a GVariant varargs "
4598 : : "interface to validate the passed format string for type safety. The passed format "
4599 : : "(%s) contains a '&' character which would result in a pointer being returned to the "
4600 : : "data inside of a GVariant instance that may no longer exist by the time the function "
4601 : : "returns. Modify your code to use a format string without '&'.", original_format);
4602 : 4 : return FALSE;
4603 : : }
4604 : :
4605 : : G_GNUC_FALLTHROUGH;
4606 : : case '^':
4607 : : case '@':
4608 : : /* ignore these 2 (or 3) */
4609 : 20 : continue;
4610 : :
4611 : 2 : case '?':
4612 : : /* attempt to consume one of 'bynqiuxthdsog' */
4613 : : {
4614 : 2 : char s = *type_string++;
4615 : :
4616 : 2 : if (s == '\0' || strchr ("bynqiuxthdsog", s) == NULL)
4617 : 0 : return FALSE;
4618 : : }
4619 : 2 : continue;
4620 : :
4621 : 1 : case 'r':
4622 : : /* ensure it's a tuple */
4623 : 1 : if (*type_string != '(')
4624 : 0 : return FALSE;
4625 : :
4626 : : G_GNUC_FALLTHROUGH;
4627 : : case '*':
4628 : : /* consume a full type string for the '*' or 'r' */
4629 : 7 : if (!g_variant_type_string_scan (type_string, NULL, &type_string))
4630 : 0 : return FALSE;
4631 : :
4632 : 7 : continue;
4633 : :
4634 : 84 : default:
4635 : : /* attempt to consume exactly one character equal to the format */
4636 : 84 : if (format != *type_string++)
4637 : 4 : return FALSE;
4638 : : }
4639 : : }
4640 : :
4641 : 29 : return TRUE;
4642 : : }
4643 : :
4644 : : /*< private >
4645 : : * g_variant_format_string_scan_type:
4646 : : * @string: a string that may be prefixed with a format string
4647 : : * @limit: (nullable) (default NULL): a pointer to the end of @string,
4648 : : * or %NULL
4649 : : * @endptr: (nullable) (default NULL): location to store the end pointer,
4650 : : * or %NULL
4651 : : *
4652 : : * If @string starts with a valid format string then this function will
4653 : : * return the type that the format string corresponds to. Otherwise
4654 : : * this function returns %NULL.
4655 : : *
4656 : : * Use g_variant_type_free() to free the return value when you no longer
4657 : : * need it.
4658 : : *
4659 : : * This function is otherwise exactly like
4660 : : * g_variant_format_string_scan().
4661 : : *
4662 : : * Returns: (nullable): a #GVariantType if there was a valid format string
4663 : : *
4664 : : * Since: 2.24
4665 : : */
4666 : : GVariantType *
4667 : 329517 : g_variant_format_string_scan_type (const gchar *string,
4668 : : const gchar *limit,
4669 : : const gchar **endptr)
4670 : : {
4671 : : const gchar *my_end;
4672 : : gsize i;
4673 : : gchar *new;
4674 : :
4675 : 329517 : if (endptr == NULL)
4676 : 99 : endptr = &my_end;
4677 : :
4678 : 329517 : if (!g_variant_format_string_scan (string, limit, endptr))
4679 : 3 : return NULL;
4680 : :
4681 : 329514 : new = g_malloc (*endptr - string + 1);
4682 : 329514 : i = 0;
4683 : 1814001 : while (string != *endptr)
4684 : : {
4685 : 1484487 : if (*string != '@' && *string != '&' && *string != '^')
4686 : 1366382 : new[i++] = *string;
4687 : 1484487 : string++;
4688 : : }
4689 : 329514 : new[i++] = '\0';
4690 : :
4691 : 329514 : g_assert (g_variant_type_string_is_valid (new));
4692 : :
4693 : 329514 : return (GVariantType *) new;
4694 : : }
4695 : :
4696 : : static gboolean
4697 : 423211 : valid_format_string (const gchar *format_string,
4698 : : gboolean single,
4699 : : GVariant *value)
4700 : : {
4701 : : const gchar *endptr;
4702 : : GVariantType *type;
4703 : :
4704 : : /* An extremely common use-case is checking the format string without
4705 : : * caring about the value specifically. Provide a fast-path for this to
4706 : : * avoid the malloc/free overhead.
4707 : : */
4708 : 423211 : if G_LIKELY (value == NULL &&
4709 : : g_variant_format_string_scan (format_string, NULL, &endptr) &&
4710 : : (single || *endptr == '\0'))
4711 : 93797 : return TRUE;
4712 : :
4713 : 329414 : type = g_variant_format_string_scan_type (format_string, NULL, &endptr);
4714 : :
4715 : 329414 : if G_UNLIKELY (type == NULL || (single && *endptr != '\0'))
4716 : : {
4717 : 2 : if (single)
4718 : 1 : g_critical ("'%s' is not a valid GVariant format string",
4719 : : format_string);
4720 : : else
4721 : 1 : g_critical ("'%s' does not have a valid GVariant format "
4722 : : "string as a prefix", format_string);
4723 : :
4724 : 2 : if (type != NULL)
4725 : 0 : g_variant_type_free (type);
4726 : :
4727 : 2 : return FALSE;
4728 : : }
4729 : :
4730 : 329412 : if G_UNLIKELY (value && !g_variant_is_of_type (value, type))
4731 : : {
4732 : : gchar *fragment;
4733 : : gchar *typestr;
4734 : :
4735 : 2 : fragment = g_strndup (format_string, endptr - format_string);
4736 : 2 : typestr = g_variant_type_dup_string (type);
4737 : :
4738 : 2 : g_critical ("the GVariant format string '%s' has a type of "
4739 : : "'%s' but the given value has a type of '%s'",
4740 : : fragment, typestr, g_variant_get_type_string (value));
4741 : :
4742 : 2 : g_variant_type_free (type);
4743 : 2 : g_free (fragment);
4744 : 2 : g_free (typestr);
4745 : :
4746 : 2 : return FALSE;
4747 : : }
4748 : :
4749 : 329410 : g_variant_type_free (type);
4750 : :
4751 : 329410 : return TRUE;
4752 : : }
4753 : :
4754 : : /* Variable Arguments {{{1 */
4755 : : /* We consider 2 main classes of format strings:
4756 : : *
4757 : : * - recursive format strings
4758 : : * these are ones that result in recursion and the collection of
4759 : : * possibly more than one argument. Maybe types, tuples,
4760 : : * dictionary entries.
4761 : : *
4762 : : * - leaf format string
4763 : : * these result in the collection of a single argument.
4764 : : *
4765 : : * Leaf format strings are further subdivided into two categories:
4766 : : *
4767 : : * - single non-null pointer ("nnp")
4768 : : * these either collect or return a single non-null pointer.
4769 : : *
4770 : : * - other
4771 : : * these collect or return something else (bool, number, etc).
4772 : : *
4773 : : * Based on the above, the varargs handling code is split into 4 main parts:
4774 : : *
4775 : : * - nnp handling code
4776 : : * - leaf handling code (which may invoke nnp code)
4777 : : * - generic handling code (may be recursive, may invoke leaf code)
4778 : : * - user-facing API (which invokes the generic code)
4779 : : *
4780 : : * Each section implements some of the following functions:
4781 : : *
4782 : : * - skip:
4783 : : * collect the arguments for the format string as if
4784 : : * g_variant_new() had been called, but do nothing with them. used
4785 : : * for skipping over arguments when constructing a Nothing maybe
4786 : : * type.
4787 : : *
4788 : : * - new:
4789 : : * create a GVariant *
4790 : : *
4791 : : * - get:
4792 : : * unpack a GVariant *
4793 : : *
4794 : : * - free (nnp only):
4795 : : * free a previously allocated item
4796 : : */
4797 : :
4798 : : static gboolean
4799 : 761748 : g_variant_format_string_is_leaf (const gchar *str)
4800 : : {
4801 : 761748 : return str[0] != 'm' && str[0] != '(' && str[0] != '{';
4802 : : }
4803 : :
4804 : : static gboolean
4805 : 495310 : g_variant_format_string_is_nnp (const gchar *str)
4806 : : {
4807 : 494172 : return str[0] == 'a' || str[0] == 's' || str[0] == 'o' || str[0] == 'g' ||
4808 : 479160 : str[0] == '^' || str[0] == '@' || str[0] == '*' || str[0] == '?' ||
4809 : 989482 : str[0] == 'r' || str[0] == 'v' || str[0] == '&';
4810 : : }
4811 : :
4812 : : /* Single non-null pointer ("nnp") {{{2 */
4813 : : static void
4814 : 6563 : g_variant_valist_free_nnp (const gchar *str,
4815 : : gpointer ptr)
4816 : : {
4817 : 6563 : switch (*str)
4818 : : {
4819 : 3 : case 'a':
4820 : 3 : g_variant_iter_free (ptr);
4821 : 3 : break;
4822 : :
4823 : 18 : case '^':
4824 : 18 : if (g_str_has_suffix (str, "y"))
4825 : : {
4826 : 12 : if (str[2] != 'a') /* '^a&ay', '^ay' */
4827 : 6 : g_free (ptr);
4828 : 6 : else if (str[1] == 'a') /* '^aay' */
4829 : 3 : g_strfreev (ptr);
4830 : 12 : break; /* '^&ay' */
4831 : : }
4832 : 6 : else if (str[2] != '&') /* '^as', '^ao' */
4833 : 3 : g_strfreev (ptr);
4834 : : else /* '^a&s', '^a&o' */
4835 : 3 : g_free (ptr);
4836 : 6 : break;
4837 : :
4838 : 124 : case 's':
4839 : : case 'o':
4840 : : case 'g':
4841 : 124 : g_free (ptr);
4842 : 124 : break;
4843 : :
4844 : 4389 : case '@':
4845 : : case '*':
4846 : : case '?':
4847 : : case 'v':
4848 : 4389 : g_variant_unref (ptr);
4849 : 4389 : break;
4850 : :
4851 : 2029 : case '&':
4852 : 2029 : break;
4853 : :
4854 : 0 : default:
4855 : : g_assert_not_reached ();
4856 : : }
4857 : 6563 : }
4858 : :
4859 : : static gchar
4860 : 221 : g_variant_scan_convenience (const gchar **str,
4861 : : gboolean *constant,
4862 : : guint *arrays)
4863 : : {
4864 : 221 : *constant = FALSE;
4865 : 221 : *arrays = 0;
4866 : :
4867 : : for (;;)
4868 : 363 : {
4869 : 584 : char c = *(*str)++;
4870 : :
4871 : 584 : if (c == '&')
4872 : 111 : *constant = TRUE;
4873 : :
4874 : 473 : else if (c == 'a')
4875 : 252 : (*arrays)++;
4876 : :
4877 : : else
4878 : 221 : return c;
4879 : : }
4880 : : }
4881 : :
4882 : : static GVariant *
4883 : 82453 : g_variant_valist_new_nnp (const gchar **str,
4884 : : gpointer ptr)
4885 : : {
4886 : 82453 : if (**str == '&')
4887 : 8 : (*str)++;
4888 : :
4889 : 82453 : switch (*(*str)++)
4890 : : {
4891 : 380 : case 'a':
4892 : 380 : if (ptr != NULL)
4893 : : {
4894 : : const GVariantType *type;
4895 : : GVariant *value;
4896 : :
4897 : 321 : value = g_variant_builder_end (ptr);
4898 : 321 : type = g_variant_get_type (value);
4899 : :
4900 : 321 : if G_UNLIKELY (!g_variant_type_is_array (type))
4901 : 0 : g_error ("g_variant_new: expected array GVariantBuilder but "
4902 : : "the built value has type '%s'",
4903 : : g_variant_get_type_string (value));
4904 : :
4905 : 321 : type = g_variant_type_element (type);
4906 : :
4907 : 321 : if G_UNLIKELY (!g_variant_type_is_subtype_of (type, (GVariantType *) *str))
4908 : : {
4909 : 0 : gchar *type_string = g_variant_type_dup_string ((GVariantType *) *str);
4910 : 0 : g_error ("g_variant_new: expected GVariantBuilder array element "
4911 : : "type '%s' but the built value has element type '%s'",
4912 : : type_string, g_variant_get_type_string (value) + 1);
4913 : : g_free (type_string);
4914 : : }
4915 : :
4916 : 321 : g_variant_type_string_scan (*str, NULL, str);
4917 : :
4918 : 321 : return value;
4919 : : }
4920 : : else
4921 : :
4922 : : /* special case: NULL pointer for empty array */
4923 : : {
4924 : 59 : const GVariantType *type = (GVariantType *) *str;
4925 : :
4926 : 59 : g_variant_type_string_scan (*str, NULL, str);
4927 : :
4928 : 59 : if G_UNLIKELY (!g_variant_type_is_definite (type))
4929 : 0 : g_error ("g_variant_new: NULL pointer given with indefinite "
4930 : : "array type; unable to determine which type of empty "
4931 : : "array to construct.");
4932 : :
4933 : 59 : return g_variant_new_array (type, NULL, 0);
4934 : : }
4935 : :
4936 : 12728 : case 's':
4937 : : {
4938 : : GVariant *value;
4939 : :
4940 : 12728 : value = g_variant_new_string (ptr);
4941 : :
4942 : 12728 : if (value == NULL)
4943 : 0 : value = g_variant_new_string ("[Invalid UTF-8]");
4944 : :
4945 : 12728 : return value;
4946 : : }
4947 : :
4948 : 107 : case 'o':
4949 : 107 : return g_variant_new_object_path (ptr);
4950 : :
4951 : 22 : case 'g':
4952 : 22 : return g_variant_new_signature (ptr);
4953 : :
4954 : 81 : case '^':
4955 : : {
4956 : : gboolean constant;
4957 : : guint arrays;
4958 : : gchar type;
4959 : :
4960 : 81 : type = g_variant_scan_convenience (str, &constant, &arrays);
4961 : :
4962 : 81 : if (type == 's')
4963 : 30 : return g_variant_new_strv (ptr, -1);
4964 : :
4965 : 51 : if (type == 'o')
4966 : 8 : return g_variant_new_objv (ptr, -1);
4967 : :
4968 : 43 : if (arrays > 1)
4969 : 16 : return g_variant_new_bytestring_array (ptr, -1);
4970 : :
4971 : 27 : return g_variant_new_bytestring (ptr);
4972 : : }
4973 : :
4974 : 198 : case '@':
4975 : 198 : if G_UNLIKELY (!g_variant_is_of_type (ptr, (GVariantType *) *str))
4976 : : {
4977 : 0 : gchar *type_string = g_variant_type_dup_string ((GVariantType *) *str);
4978 : 0 : g_error ("g_variant_new: expected GVariant of type '%s' but "
4979 : : "received value has type '%s'",
4980 : : type_string, g_variant_get_type_string (ptr));
4981 : : g_free (type_string);
4982 : : }
4983 : :
4984 : 198 : g_variant_type_string_scan (*str, NULL, str);
4985 : :
4986 : 198 : return ptr;
4987 : :
4988 : 7 : case '*':
4989 : 7 : return ptr;
4990 : :
4991 : 1 : case '?':
4992 : 1 : if G_UNLIKELY (!g_variant_type_is_basic (g_variant_get_type (ptr)))
4993 : 0 : g_error ("g_variant_new: format string '?' expects basic-typed "
4994 : : "GVariant, but received value has type '%s'",
4995 : : g_variant_get_type_string (ptr));
4996 : :
4997 : 1 : return ptr;
4998 : :
4999 : 1 : case 'r':
5000 : 1 : if G_UNLIKELY (!g_variant_type_is_tuple (g_variant_get_type (ptr)))
5001 : 0 : g_error ("g_variant_new: format string 'r' expects tuple-typed "
5002 : : "GVariant, but received value has type '%s'",
5003 : : g_variant_get_type_string (ptr));
5004 : :
5005 : 1 : return ptr;
5006 : :
5007 : 68928 : case 'v':
5008 : 68928 : return g_variant_new_variant (ptr);
5009 : :
5010 : 0 : default:
5011 : : g_assert_not_reached ();
5012 : : }
5013 : : }
5014 : :
5015 : : static gpointer
5016 : 185378 : g_variant_valist_get_nnp (const gchar **str,
5017 : : GVariant *value)
5018 : : {
5019 : 185378 : switch (*(*str)++)
5020 : : {
5021 : 754 : case 'a':
5022 : 754 : g_variant_type_string_scan (*str, NULL, str);
5023 : 754 : return g_variant_iter_new (value);
5024 : :
5025 : 41261 : case '&':
5026 : 41261 : (*str)++;
5027 : 41261 : return (gchar *) g_variant_get_string (value, NULL);
5028 : :
5029 : 2157 : case 's':
5030 : : case 'o':
5031 : : case 'g':
5032 : 2157 : return g_variant_dup_string (value, NULL);
5033 : :
5034 : 140 : case '^':
5035 : : {
5036 : : gboolean constant;
5037 : : guint arrays;
5038 : : gchar type;
5039 : :
5040 : 140 : type = g_variant_scan_convenience (str, &constant, &arrays);
5041 : :
5042 : 140 : if (type == 's')
5043 : : {
5044 : 102 : if (constant)
5045 : 94 : return g_variant_get_strv (value, NULL);
5046 : : else
5047 : 8 : return g_variant_dup_strv (value, NULL);
5048 : : }
5049 : :
5050 : 38 : else if (type == 'o')
5051 : : {
5052 : 5 : if (constant)
5053 : 1 : return g_variant_get_objv (value, NULL);
5054 : : else
5055 : 4 : return g_variant_dup_objv (value, NULL);
5056 : : }
5057 : :
5058 : 33 : else if (arrays > 1)
5059 : : {
5060 : 15 : if (constant)
5061 : 6 : return g_variant_get_bytestring_array (value, NULL);
5062 : : else
5063 : 9 : return g_variant_dup_bytestring_array (value, NULL);
5064 : : }
5065 : :
5066 : : else
5067 : : {
5068 : 18 : if (constant)
5069 : 5 : return (gchar *) g_variant_get_bytestring (value);
5070 : : else
5071 : 13 : return g_variant_dup_bytestring (value, NULL);
5072 : : }
5073 : : }
5074 : :
5075 : 2668 : case '@':
5076 : 2668 : g_variant_type_string_scan (*str, NULL, str);
5077 : : G_GNUC_FALLTHROUGH;
5078 : :
5079 : 2844 : case '*':
5080 : : case '?':
5081 : : case 'r':
5082 : 2844 : return g_variant_ref (value);
5083 : :
5084 : 138222 : case 'v':
5085 : 138222 : return g_variant_get_variant (value);
5086 : :
5087 : 0 : default:
5088 : : g_assert_not_reached ();
5089 : : }
5090 : : }
5091 : :
5092 : : /* Leaves {{{2 */
5093 : : static void
5094 : 64 : g_variant_valist_skip_leaf (const gchar **str,
5095 : : va_list *app)
5096 : : {
5097 : 64 : if (g_variant_format_string_is_nnp (*str))
5098 : : {
5099 : 1 : g_variant_format_string_scan (*str, NULL, str);
5100 : 1 : va_arg (*app, gpointer);
5101 : 1 : return;
5102 : : }
5103 : :
5104 : 63 : switch (*(*str)++)
5105 : : {
5106 : 60 : case 'b':
5107 : : case 'y':
5108 : : case 'n':
5109 : : case 'q':
5110 : : case 'i':
5111 : : case 'u':
5112 : : case 'h':
5113 : 60 : va_arg (*app, int);
5114 : 60 : return;
5115 : :
5116 : 2 : case 'x':
5117 : : case 't':
5118 : 2 : va_arg (*app, guint64);
5119 : 2 : return;
5120 : :
5121 : 1 : case 'd':
5122 : 1 : va_arg (*app, gdouble);
5123 : 1 : return;
5124 : :
5125 : 0 : default:
5126 : : g_assert_not_reached ();
5127 : : }
5128 : : }
5129 : :
5130 : : static GVariant *
5131 : 155376 : g_variant_valist_new_leaf (const gchar **str,
5132 : : va_list *app)
5133 : : {
5134 : 155376 : if (g_variant_format_string_is_nnp (*str))
5135 : 82451 : return g_variant_valist_new_nnp (str, va_arg (*app, gpointer));
5136 : :
5137 : 72925 : switch (*(*str)++)
5138 : : {
5139 : 47 : case 'b':
5140 : 47 : return g_variant_new_boolean (va_arg (*app, gboolean));
5141 : :
5142 : 65450 : case 'y':
5143 : 65450 : return g_variant_new_byte (va_arg (*app, guint));
5144 : :
5145 : 13 : case 'n':
5146 : 13 : return g_variant_new_int16 (va_arg (*app, gint));
5147 : :
5148 : 17 : case 'q':
5149 : 17 : return g_variant_new_uint16 (va_arg (*app, guint));
5150 : :
5151 : 206 : case 'i':
5152 : 206 : return g_variant_new_int32 (va_arg (*app, gint));
5153 : :
5154 : 6722 : case 'u':
5155 : 6722 : return g_variant_new_uint32 (va_arg (*app, guint));
5156 : :
5157 : 425 : case 'x':
5158 : 425 : return g_variant_new_int64 (va_arg (*app, gint64));
5159 : :
5160 : 13 : case 't':
5161 : 13 : return g_variant_new_uint64 (va_arg (*app, guint64));
5162 : :
5163 : 11 : case 'h':
5164 : 11 : return g_variant_new_handle (va_arg (*app, gint));
5165 : :
5166 : 21 : case 'd':
5167 : 21 : return g_variant_new_double (va_arg (*app, gdouble));
5168 : :
5169 : 0 : default:
5170 : : g_assert_not_reached ();
5171 : : }
5172 : : }
5173 : :
5174 : : /* The code below assumes this */
5175 : : G_STATIC_ASSERT (sizeof (gboolean) == sizeof (guint32));
5176 : : G_STATIC_ASSERT (sizeof (gdouble) == sizeof (guint64));
5177 : :
5178 : : static void
5179 : 358127 : g_variant_valist_get_leaf (const gchar **str,
5180 : : GVariant *value,
5181 : : gboolean free,
5182 : : va_list *app)
5183 : : {
5184 : 358127 : gpointer ptr = va_arg (*app, gpointer);
5185 : :
5186 : 358127 : if (ptr == NULL)
5187 : : {
5188 : 18681 : g_variant_format_string_scan (*str, NULL, str);
5189 : 18681 : return;
5190 : : }
5191 : :
5192 : 339446 : if (g_variant_format_string_is_nnp (*str))
5193 : : {
5194 : 190025 : gpointer *nnp = (gpointer *) ptr;
5195 : :
5196 : 190025 : if (free && *nnp != NULL)
5197 : 6563 : g_variant_valist_free_nnp (*str, *nnp);
5198 : :
5199 : 190025 : *nnp = NULL;
5200 : :
5201 : 190025 : if (value != NULL)
5202 : 185378 : *nnp = g_variant_valist_get_nnp (str, value);
5203 : : else
5204 : 4647 : g_variant_format_string_scan (*str, NULL, str);
5205 : :
5206 : 190025 : return;
5207 : : }
5208 : :
5209 : 149421 : if (value != NULL)
5210 : : {
5211 : 147433 : switch (*(*str)++)
5212 : : {
5213 : 24 : case 'b':
5214 : 24 : *(gboolean *) ptr = g_variant_get_boolean (value);
5215 : 24 : return;
5216 : :
5217 : 135116 : case 'y':
5218 : 135116 : *(guint8 *) ptr = g_variant_get_byte (value);
5219 : 135116 : return;
5220 : :
5221 : 9 : case 'n':
5222 : 9 : *(gint16 *) ptr = g_variant_get_int16 (value);
5223 : 9 : return;
5224 : :
5225 : 8 : case 'q':
5226 : 8 : *(guint16 *) ptr = g_variant_get_uint16 (value);
5227 : 8 : return;
5228 : :
5229 : 221 : case 'i':
5230 : 221 : *(gint32 *) ptr = g_variant_get_int32 (value);
5231 : 221 : return;
5232 : :
5233 : 12007 : case 'u':
5234 : 12007 : *(guint32 *) ptr = g_variant_get_uint32 (value);
5235 : 12007 : return;
5236 : :
5237 : 27 : case 'x':
5238 : 27 : *(gint64 *) ptr = g_variant_get_int64 (value);
5239 : 27 : return;
5240 : :
5241 : 8 : case 't':
5242 : 8 : *(guint64 *) ptr = g_variant_get_uint64 (value);
5243 : 8 : return;
5244 : :
5245 : 5 : case 'h':
5246 : 5 : *(gint32 *) ptr = g_variant_get_handle (value);
5247 : 5 : return;
5248 : :
5249 : 8 : case 'd':
5250 : 8 : *(gdouble *) ptr = g_variant_get_double (value);
5251 : 8 : return;
5252 : : }
5253 : : }
5254 : : else
5255 : : {
5256 : 1988 : switch (*(*str)++)
5257 : : {
5258 : 2 : case 'y':
5259 : 2 : *(guint8 *) ptr = 0;
5260 : 2 : return;
5261 : :
5262 : 4 : case 'n':
5263 : : case 'q':
5264 : 4 : *(guint16 *) ptr = 0;
5265 : 4 : return;
5266 : :
5267 : 1976 : case 'i':
5268 : : case 'u':
5269 : : case 'h':
5270 : : case 'b':
5271 : 1976 : *(guint32 *) ptr = 0;
5272 : 1976 : return;
5273 : :
5274 : 6 : case 'x':
5275 : : case 't':
5276 : : case 'd':
5277 : 6 : *(guint64 *) ptr = 0;
5278 : 6 : return;
5279 : : }
5280 : : }
5281 : :
5282 : : g_assert_not_reached ();
5283 : : }
5284 : :
5285 : : /* Generic (recursive) {{{2 */
5286 : : static void
5287 : 66 : g_variant_valist_skip (const gchar **str,
5288 : : va_list *app)
5289 : : {
5290 : 66 : if (g_variant_format_string_is_leaf (*str))
5291 : 64 : g_variant_valist_skip_leaf (str, app);
5292 : :
5293 : 2 : else if (**str == 'm') /* maybe */
5294 : : {
5295 : 1 : (*str)++;
5296 : :
5297 : 1 : if (!g_variant_format_string_is_nnp (*str))
5298 : 1 : va_arg (*app, gboolean);
5299 : :
5300 : 1 : g_variant_valist_skip (str, app);
5301 : : }
5302 : : else /* tuple, dictionary entry */
5303 : : {
5304 : 1 : g_assert (**str == '(' || **str == '{');
5305 : 1 : (*str)++;
5306 : 2 : while (**str != ')' && **str != '}')
5307 : 1 : g_variant_valist_skip (str, app);
5308 : 1 : (*str)++;
5309 : : }
5310 : 66 : }
5311 : :
5312 : : static GVariant *
5313 : 234828 : g_variant_valist_new (const gchar **str,
5314 : : va_list *app)
5315 : : {
5316 : 234828 : if (g_variant_format_string_is_leaf (*str))
5317 : 155376 : return g_variant_valist_new_leaf (str, app);
5318 : :
5319 : 79452 : if (**str == 'm') /* maybe */
5320 : : {
5321 : 133 : GVariantType *type = NULL;
5322 : 133 : GVariant *value = NULL;
5323 : :
5324 : 133 : (*str)++;
5325 : :
5326 : 133 : if (g_variant_format_string_is_nnp (*str))
5327 : : {
5328 : 5 : gpointer nnp = va_arg (*app, gpointer);
5329 : :
5330 : 5 : if (nnp != NULL)
5331 : 2 : value = g_variant_valist_new_nnp (str, nnp);
5332 : : else
5333 : 3 : type = g_variant_format_string_scan_type (*str, NULL, str);
5334 : : }
5335 : : else
5336 : : {
5337 : 128 : gboolean just = va_arg (*app, gboolean);
5338 : :
5339 : 128 : if (just)
5340 : 64 : value = g_variant_valist_new (str, app);
5341 : : else
5342 : : {
5343 : 64 : type = g_variant_format_string_scan_type (*str, NULL, NULL);
5344 : 64 : g_variant_valist_skip (str, app);
5345 : : }
5346 : : }
5347 : :
5348 : 133 : value = g_variant_new_maybe (type, value);
5349 : :
5350 : 133 : if (type != NULL)
5351 : 67 : g_variant_type_free (type);
5352 : :
5353 : 133 : return value;
5354 : : }
5355 : : else /* tuple, dictionary entry */
5356 : : {
5357 : : GVariantBuilder b;
5358 : :
5359 : 79319 : if (**str == '(')
5360 : 10409 : g_variant_builder_init_static (&b, G_VARIANT_TYPE_TUPLE);
5361 : : else
5362 : : {
5363 : 68910 : g_assert (**str == '{');
5364 : 68910 : g_variant_builder_init_static (&b, G_VARIANT_TYPE_DICT_ENTRY);
5365 : : }
5366 : :
5367 : 79319 : (*str)++; /* '(' */
5368 : 231770 : while (**str != ')' && **str != '}')
5369 : 152451 : g_variant_builder_add_value (&b, g_variant_valist_new (str, app));
5370 : 79319 : (*str)++; /* ')' */
5371 : :
5372 : 79319 : return g_variant_builder_end (&b);
5373 : : }
5374 : : }
5375 : :
5376 : : static void
5377 : 526854 : g_variant_valist_get (const gchar **str,
5378 : : GVariant *value,
5379 : : gboolean free,
5380 : : va_list *app)
5381 : : {
5382 : 526854 : if (g_variant_format_string_is_leaf (*str))
5383 : 358127 : g_variant_valist_get_leaf (str, value, free, app);
5384 : :
5385 : 168727 : else if (**str == 'm')
5386 : : {
5387 : 290 : (*str)++;
5388 : :
5389 : 290 : if (value != NULL)
5390 : 288 : value = g_variant_get_maybe (value);
5391 : :
5392 : 290 : if (!g_variant_format_string_is_nnp (*str))
5393 : : {
5394 : 282 : gboolean *ptr = va_arg (*app, gboolean *);
5395 : :
5396 : 282 : if (ptr != NULL)
5397 : 141 : *ptr = value != NULL;
5398 : : }
5399 : :
5400 : 290 : g_variant_valist_get (str, value, free, app);
5401 : :
5402 : 290 : if (value != NULL)
5403 : 144 : g_variant_unref (value);
5404 : : }
5405 : :
5406 : : else /* tuple, dictionary entry */
5407 : : {
5408 : 168437 : gint index = 0;
5409 : :
5410 : 168437 : g_assert (**str == '(' || **str == '{');
5411 : :
5412 : 168437 : (*str)++;
5413 : 523035 : while (**str != ')' && **str != '}')
5414 : : {
5415 : 354598 : if (value != NULL)
5416 : : {
5417 : 348763 : GVariant *child = g_variant_get_child_value (value, index++);
5418 : 348763 : g_variant_valist_get (str, child, free, app);
5419 : 348763 : g_variant_unref (child);
5420 : : }
5421 : : else
5422 : 5835 : g_variant_valist_get (str, NULL, free, app);
5423 : : }
5424 : 168437 : (*str)++;
5425 : : }
5426 : 526854 : }
5427 : :
5428 : : /* User-facing API {{{2 */
5429 : : /**
5430 : : * g_variant_new: (skip)
5431 : : * @format_string: a #GVariant format string
5432 : : * @...: arguments, as per @format_string
5433 : : *
5434 : : * Creates a new #GVariant instance.
5435 : : *
5436 : : * Think of this function as an analogue to g_strdup_printf().
5437 : : *
5438 : : * The type of the created instance and the arguments that are expected
5439 : : * by this function are determined by @format_string. See the section on
5440 : : * [GVariant format strings](gvariant-format-strings.html). Please note that
5441 : : * the syntax of the format string is very likely to be extended in the
5442 : : * future.
5443 : : *
5444 : : * The first character of the format string must not be '*' '?' '@' or
5445 : : * 'r'; in essence, a new #GVariant must always be constructed by this
5446 : : * function (and not merely passed through it unmodified).
5447 : : *
5448 : : * Note that the arguments must be of the correct width for their types
5449 : : * specified in @format_string. This can be achieved by casting them. See
5450 : : * the [GVariant varargs documentation](gvariant-format-strings.html#varargs).
5451 : : *
5452 : : * |[<!-- language="C" -->
5453 : : * MyFlags some_flags = FLAG_ONE | FLAG_TWO;
5454 : : * const gchar *some_strings[] = { "a", "b", "c", NULL };
5455 : : * GVariant *new_variant;
5456 : : *
5457 : : * new_variant = g_variant_new ("(t^as)",
5458 : : * // This cast is required.
5459 : : * (guint64) some_flags,
5460 : : * some_strings);
5461 : : * ]|
5462 : : *
5463 : : * Returns: a new floating #GVariant instance
5464 : : *
5465 : : * Since: 2.24
5466 : : **/
5467 : : GVariant *
5468 : 10410 : g_variant_new (const gchar *format_string,
5469 : : ...)
5470 : : {
5471 : : GVariant *value;
5472 : : va_list ap;
5473 : :
5474 : 10410 : g_return_val_if_fail (valid_format_string (format_string, TRUE, NULL) &&
5475 : : format_string[0] != '?' && format_string[0] != '@' &&
5476 : : format_string[0] != '*' && format_string[0] != 'r',
5477 : : NULL);
5478 : :
5479 : 10409 : va_start (ap, format_string);
5480 : 10409 : value = g_variant_new_va (format_string, NULL, &ap);
5481 : 10409 : va_end (ap);
5482 : :
5483 : 10409 : return value;
5484 : : }
5485 : :
5486 : : /**
5487 : : * g_variant_new_va: (skip)
5488 : : * @format_string: a string that is prefixed with a format string
5489 : : * @endptr: (nullable) (default NULL): location to store the end pointer,
5490 : : * or %NULL
5491 : : * @app: a pointer to a #va_list
5492 : : *
5493 : : * This function is intended to be used by libraries based on
5494 : : * #GVariant that want to provide g_variant_new()-like functionality
5495 : : * to their users.
5496 : : *
5497 : : * The API is more general than g_variant_new() to allow a wider range
5498 : : * of possible uses.
5499 : : *
5500 : : * @format_string must still point to a valid format string, but it only
5501 : : * needs to be nul-terminated if @endptr is %NULL. If @endptr is
5502 : : * non-%NULL then it is updated to point to the first character past the
5503 : : * end of the format string.
5504 : : *
5505 : : * @app is a pointer to a #va_list. The arguments, according to
5506 : : * @format_string, are collected from this #va_list and the list is left
5507 : : * pointing to the argument following the last.
5508 : : *
5509 : : * Note that the arguments in @app must be of the correct width for their
5510 : : * types specified in @format_string when collected into the #va_list.
5511 : : * See the [GVariant varargs documentation](gvariant-format-strings.html#varargs).
5512 : : *
5513 : : * These two generalisations allow mixing of multiple calls to
5514 : : * g_variant_new_va() and g_variant_get_va() within a single actual
5515 : : * varargs call by the user.
5516 : : *
5517 : : * The return value will be floating if it was a newly created GVariant
5518 : : * instance (for example, if the format string was "(ii)"). In the case
5519 : : * that the format_string was '*', '?', 'r', or a format starting with
5520 : : * '@' then the collected #GVariant pointer will be returned unmodified,
5521 : : * without adding any additional references.
5522 : : *
5523 : : * In order to behave correctly in all cases it is necessary for the
5524 : : * calling function to g_variant_ref_sink() the return result before
5525 : : * returning control to the user that originally provided the pointer.
5526 : : * At this point, the caller will have their own full reference to the
5527 : : * result. This can also be done by adding the result to a container,
5528 : : * or by passing it to another g_variant_new() call.
5529 : : *
5530 : : * Returns: a new, usually floating, #GVariant
5531 : : *
5532 : : * Since: 2.24
5533 : : **/
5534 : : GVariant *
5535 : 82314 : g_variant_new_va (const gchar *format_string,
5536 : : const gchar **endptr,
5537 : : va_list *app)
5538 : : {
5539 : : GVariant *value;
5540 : :
5541 : 82314 : g_return_val_if_fail (valid_format_string (format_string, !endptr, NULL),
5542 : : NULL);
5543 : 82313 : g_return_val_if_fail (app != NULL, NULL);
5544 : :
5545 : 82313 : value = g_variant_valist_new (&format_string, app);
5546 : :
5547 : 82313 : if (endptr != NULL)
5548 : 485 : *endptr = format_string;
5549 : :
5550 : 82313 : return value;
5551 : : }
5552 : :
5553 : : /**
5554 : : * g_variant_get: (skip)
5555 : : * @value: a #GVariant instance
5556 : : * @format_string: a #GVariant format string
5557 : : * @...: arguments, as per @format_string
5558 : : *
5559 : : * Deconstructs a #GVariant instance.
5560 : : *
5561 : : * Think of this function as an analogue to scanf().
5562 : : *
5563 : : * The arguments that are expected by this function are entirely
5564 : : * determined by @format_string. @format_string also restricts the
5565 : : * permissible types of @value. It is an error to give a value with
5566 : : * an incompatible type. See the section on
5567 : : * [GVariant format strings](gvariant-format-strings.html).
5568 : : * Please note that the syntax of the format string is very likely to be
5569 : : * extended in the future.
5570 : : *
5571 : : * @format_string determines the C types that are used for unpacking
5572 : : * the values and also determines if the values are copied or borrowed,
5573 : : * see the section on
5574 : : * [`GVariant` format strings](gvariant-format-strings.html#pointers).
5575 : : *
5576 : : * Since: 2.24
5577 : : **/
5578 : : void
5579 : 162077 : g_variant_get (GVariant *value,
5580 : : const gchar *format_string,
5581 : : ...)
5582 : : {
5583 : : va_list ap;
5584 : :
5585 : 162078 : g_return_if_fail (value != NULL);
5586 : 162077 : g_return_if_fail (valid_format_string (format_string, TRUE, value));
5587 : :
5588 : : /* if any direct-pointer-access formats are in use, flatten first */
5589 : 162076 : if (strchr (format_string, '&'))
5590 : 20073 : g_variant_get_data (value);
5591 : :
5592 : 162076 : va_start (ap, format_string);
5593 : 162076 : g_variant_get_va (value, format_string, NULL, &ap);
5594 : 162076 : va_end (ap);
5595 : : }
5596 : :
5597 : : /**
5598 : : * g_variant_get_va: (skip)
5599 : : * @value: a #GVariant
5600 : : * @format_string: a string that is prefixed with a format string
5601 : : * @endptr: (nullable) (default NULL): location to store the end pointer,
5602 : : * or %NULL
5603 : : * @app: a pointer to a #va_list
5604 : : *
5605 : : * This function is intended to be used by libraries based on #GVariant
5606 : : * that want to provide g_variant_get()-like functionality to their
5607 : : * users.
5608 : : *
5609 : : * The API is more general than g_variant_get() to allow a wider range
5610 : : * of possible uses.
5611 : : *
5612 : : * @format_string must still point to a valid format string, but it only
5613 : : * need to be nul-terminated if @endptr is %NULL. If @endptr is
5614 : : * non-%NULL then it is updated to point to the first character past the
5615 : : * end of the format string.
5616 : : *
5617 : : * @app is a pointer to a #va_list. The arguments, according to
5618 : : * @format_string, are collected from this #va_list and the list is left
5619 : : * pointing to the argument following the last.
5620 : : *
5621 : : * These two generalisations allow mixing of multiple calls to
5622 : : * g_variant_new_va() and g_variant_get_va() within a single actual
5623 : : * varargs call by the user.
5624 : : *
5625 : : * @format_string determines the C types that are used for unpacking
5626 : : * the values and also determines if the values are copied or borrowed,
5627 : : * see the section on
5628 : : * [`GVariant` format strings](gvariant-format-strings.html#pointers).
5629 : : *
5630 : : * Since: 2.24
5631 : : **/
5632 : : void
5633 : 162352 : g_variant_get_va (GVariant *value,
5634 : : const gchar *format_string,
5635 : : const gchar **endptr,
5636 : : va_list *app)
5637 : : {
5638 : 162352 : g_return_if_fail (valid_format_string (format_string, !endptr, value));
5639 : 162351 : g_return_if_fail (value != NULL);
5640 : 162351 : g_return_if_fail (app != NULL);
5641 : :
5642 : : /* if any direct-pointer-access formats are in use, flatten first */
5643 : 162351 : if (strchr (format_string, '&'))
5644 : 20177 : g_variant_get_data (value);
5645 : :
5646 : 162351 : g_variant_valist_get (&format_string, value, FALSE, app);
5647 : :
5648 : 162351 : if (endptr != NULL)
5649 : 1 : *endptr = format_string;
5650 : : }
5651 : :
5652 : : /* Varargs-enabled Utility Functions {{{1 */
5653 : :
5654 : : /**
5655 : : * g_variant_builder_add: (skip)
5656 : : * @builder: a #GVariantBuilder
5657 : : * @format_string: a #GVariant varargs format string
5658 : : * @...: arguments, as per @format_string
5659 : : *
5660 : : * Adds to a #GVariantBuilder.
5661 : : *
5662 : : * This call is a convenience wrapper that is exactly equivalent to
5663 : : * calling g_variant_new() followed by g_variant_builder_add_value().
5664 : : *
5665 : : * Note that the arguments must be of the correct width for their types
5666 : : * specified in @format_string. This can be achieved by casting them. See
5667 : : * the [GVariant varargs documentation](gvariant-format-strings.html#varargs).
5668 : : *
5669 : : * This function might be used as follows:
5670 : : *
5671 : : * |[<!-- language="C" -->
5672 : : * GVariant *
5673 : : * make_pointless_dictionary (void)
5674 : : * {
5675 : : * GVariantBuilder builder;
5676 : : * int i;
5677 : : *
5678 : : * g_variant_builder_init_static (&builder, G_VARIANT_TYPE_ARRAY);
5679 : : * for (i = 0; i < 16; i++)
5680 : : * {
5681 : : * gchar buf[3];
5682 : : *
5683 : : * sprintf (buf, "%d", i);
5684 : : * g_variant_builder_add (&builder, "{is}", i, buf);
5685 : : * }
5686 : : *
5687 : : * return g_variant_builder_end (&builder);
5688 : : * }
5689 : : * ]|
5690 : : *
5691 : : * Since: 2.24
5692 : : */
5693 : : void
5694 : 71327 : g_variant_builder_add (GVariantBuilder *builder,
5695 : : const gchar *format_string,
5696 : : ...)
5697 : : {
5698 : : GVariant *variant;
5699 : : va_list ap;
5700 : :
5701 : 71327 : va_start (ap, format_string);
5702 : 71327 : variant = g_variant_new_va (format_string, NULL, &ap);
5703 : 71327 : va_end (ap);
5704 : :
5705 : 71327 : g_variant_builder_add_value (builder, variant);
5706 : 71327 : }
5707 : :
5708 : : /**
5709 : : * g_variant_get_child: (skip)
5710 : : * @value: a container #GVariant
5711 : : * @index_: the index of the child to deconstruct
5712 : : * @format_string: a #GVariant format string
5713 : : * @...: arguments, as per @format_string
5714 : : *
5715 : : * Reads a child item out of a container #GVariant instance and
5716 : : * deconstructs it according to @format_string. This call is
5717 : : * essentially a combination of g_variant_get_child_value() and
5718 : : * g_variant_get().
5719 : : *
5720 : : * @format_string determines the C types that are used for unpacking
5721 : : * the values and also determines if the values are copied or borrowed,
5722 : : * see the section on
5723 : : * [`GVariant` format strings](gvariant-format-strings.html#pointers).
5724 : : *
5725 : : * Since: 2.24
5726 : : **/
5727 : : void
5728 : 165 : g_variant_get_child (GVariant *value,
5729 : : gsize index_,
5730 : : const gchar *format_string,
5731 : : ...)
5732 : : {
5733 : : GVariant *child;
5734 : : va_list ap;
5735 : :
5736 : : /* if any direct-pointer-access formats are in use, flatten first */
5737 : 165 : if (strchr (format_string, '&'))
5738 : 76 : g_variant_get_data (value);
5739 : :
5740 : 165 : child = g_variant_get_child_value (value, index_);
5741 : 165 : g_return_if_fail (valid_format_string (format_string, TRUE, child));
5742 : :
5743 : 165 : va_start (ap, format_string);
5744 : 165 : g_variant_get_va (child, format_string, NULL, &ap);
5745 : 165 : va_end (ap);
5746 : :
5747 : 165 : g_variant_unref (child);
5748 : : }
5749 : :
5750 : : /**
5751 : : * g_variant_iter_next: (skip)
5752 : : * @iter: a #GVariantIter
5753 : : * @format_string: a GVariant format string
5754 : : * @...: the arguments to unpack the value into
5755 : : *
5756 : : * Gets the next item in the container and unpacks it into the variable
5757 : : * argument list according to @format_string, returning %TRUE.
5758 : : *
5759 : : * If no more items remain then %FALSE is returned.
5760 : : *
5761 : : * All of the pointers given on the variable arguments list of this
5762 : : * function are assumed to point at uninitialised memory. It is the
5763 : : * responsibility of the caller to free all of the values returned by
5764 : : * the unpacking process.
5765 : : *
5766 : : * Here is an example for memory management with g_variant_iter_next():
5767 : : * |[<!-- language="C" -->
5768 : : * // Iterates a dictionary of type 'a{sv}'
5769 : : * void
5770 : : * iterate_dictionary (GVariant *dictionary)
5771 : : * {
5772 : : * GVariantIter iter;
5773 : : * GVariant *value;
5774 : : * gchar *key;
5775 : : *
5776 : : * g_variant_iter_init (&iter, dictionary);
5777 : : * while (g_variant_iter_next (&iter, "{sv}", &key, &value))
5778 : : * {
5779 : : * g_print ("Item '%s' has type '%s'\n", key,
5780 : : * g_variant_get_type_string (value));
5781 : : *
5782 : : * // must free data for ourselves
5783 : : * g_variant_unref (value);
5784 : : * g_free (key);
5785 : : * }
5786 : : * }
5787 : : * ]|
5788 : : *
5789 : : * For a solution that is likely to be more convenient to C programmers
5790 : : * when dealing with loops, see g_variant_iter_loop().
5791 : : *
5792 : : * @format_string determines the C types that are used for unpacking
5793 : : * the values and also determines if the values are copied or borrowed.
5794 : : *
5795 : : * See the section on
5796 : : * [`GVariant` format strings](gvariant-format-strings.html#pointers).
5797 : : *
5798 : : * Returns: %TRUE if a value was unpacked, or %FALSE if there as no value
5799 : : *
5800 : : * Since: 2.24
5801 : : **/
5802 : : gboolean
5803 : 2942 : g_variant_iter_next (GVariantIter *iter,
5804 : : const gchar *format_string,
5805 : : ...)
5806 : : {
5807 : : GVariant *value;
5808 : :
5809 : 2942 : value = g_variant_iter_next_value (iter);
5810 : :
5811 : 2942 : g_return_val_if_fail (valid_format_string (format_string, TRUE, value),
5812 : : FALSE);
5813 : :
5814 : 2942 : if (value != NULL)
5815 : : {
5816 : : va_list ap;
5817 : :
5818 : 1924 : va_start (ap, format_string);
5819 : 1924 : g_variant_valist_get (&format_string, value, FALSE, &ap);
5820 : 1924 : va_end (ap);
5821 : :
5822 : 1924 : g_variant_unref (value);
5823 : : }
5824 : :
5825 : 2942 : return value != NULL;
5826 : : }
5827 : :
5828 : : /**
5829 : : * g_variant_iter_loop: (skip)
5830 : : * @iter: a #GVariantIter
5831 : : * @format_string: a GVariant format string
5832 : : * @...: the arguments to unpack the value into
5833 : : *
5834 : : * Gets the next item in the container and unpacks it into the variable
5835 : : * argument list according to @format_string, returning %TRUE.
5836 : : *
5837 : : * If no more items remain then %FALSE is returned.
5838 : : *
5839 : : * On the first call to this function, the pointers appearing on the
5840 : : * variable argument list are assumed to point at uninitialised memory.
5841 : : * On the second and later calls, it is assumed that the same pointers
5842 : : * will be given and that they will point to the memory as set by the
5843 : : * previous call to this function. This allows the previous values to
5844 : : * be freed, as appropriate.
5845 : : *
5846 : : * This function is intended to be used with a while loop as
5847 : : * demonstrated in the following example. This function can only be
5848 : : * used when iterating over an array. It is only valid to call this
5849 : : * function with a string constant for the format string and the same
5850 : : * string constant must be used each time. Mixing calls to this
5851 : : * function and g_variant_iter_next() or g_variant_iter_next_value() on
5852 : : * the same iterator causes undefined behavior.
5853 : : *
5854 : : * If you break out of a such a while loop using g_variant_iter_loop() then
5855 : : * you must free or unreference all the unpacked values as you would with
5856 : : * g_variant_get(). Failure to do so will cause a memory leak.
5857 : : *
5858 : : * Here is an example for memory management with g_variant_iter_loop():
5859 : : * |[<!-- language="C" -->
5860 : : * // Iterates a dictionary of type 'a{sv}'
5861 : : * void
5862 : : * iterate_dictionary (GVariant *dictionary)
5863 : : * {
5864 : : * GVariantIter iter;
5865 : : * GVariant *value;
5866 : : * gchar *key;
5867 : : *
5868 : : * g_variant_iter_init (&iter, dictionary);
5869 : : * while (g_variant_iter_loop (&iter, "{sv}", &key, &value))
5870 : : * {
5871 : : * g_print ("Item '%s' has type '%s'\n", key,
5872 : : * g_variant_get_type_string (value));
5873 : : *
5874 : : * // no need to free 'key' and 'value' here
5875 : : * // unless breaking out of this loop
5876 : : * }
5877 : : * }
5878 : : * ]|
5879 : : *
5880 : : * For most cases you should use g_variant_iter_next().
5881 : : *
5882 : : * This function is really only useful when unpacking into #GVariant or
5883 : : * #GVariantIter in order to allow you to skip the call to
5884 : : * g_variant_unref() or g_variant_iter_free().
5885 : : *
5886 : : * For example, if you are only looping over simple integer and string
5887 : : * types, g_variant_iter_next() is definitely preferred. For string
5888 : : * types, use the '&' prefix to avoid allocating any memory at all (and
5889 : : * thereby avoiding the need to free anything as well).
5890 : : *
5891 : : * @format_string determines the C types that are used for unpacking
5892 : : * the values and also determines if the values are copied or borrowed.
5893 : : *
5894 : : * See the section on
5895 : : * [`GVariant` format strings](gvariant-format-strings.html#pointers).
5896 : : *
5897 : : * Returns: %TRUE if a value was unpacked, or %FALSE if there was no
5898 : : * value
5899 : : *
5900 : : * Since: 2.24
5901 : : **/
5902 : : gboolean
5903 : 7691 : g_variant_iter_loop (GVariantIter *iter,
5904 : : const gchar *format_string,
5905 : : ...)
5906 : : {
5907 : 7691 : gboolean first_time = GVSI(iter)->loop_format == NULL;
5908 : : GVariant *value;
5909 : : va_list ap;
5910 : :
5911 : 7691 : g_return_val_if_fail (first_time ||
5912 : : format_string == GVSI(iter)->loop_format,
5913 : : FALSE);
5914 : :
5915 : 7691 : if (first_time)
5916 : : {
5917 : 2951 : TYPE_CHECK (GVSI(iter)->value, G_VARIANT_TYPE_ARRAY, FALSE);
5918 : 2951 : GVSI(iter)->loop_format = format_string;
5919 : :
5920 : 2951 : if (strchr (format_string, '&'))
5921 : 1701 : g_variant_get_data (GVSI(iter)->value);
5922 : : }
5923 : :
5924 : 7691 : value = g_variant_iter_next_value (iter);
5925 : :
5926 : 7691 : g_return_val_if_fail (!first_time ||
5927 : : valid_format_string (format_string, TRUE, value),
5928 : : FALSE);
5929 : :
5930 : 7691 : va_start (ap, format_string);
5931 : 7691 : g_variant_valist_get (&format_string, value, !first_time, &ap);
5932 : 7691 : va_end (ap);
5933 : :
5934 : 7691 : if (value != NULL)
5935 : 4740 : g_variant_unref (value);
5936 : :
5937 : 7691 : return value != NULL;
5938 : : }
5939 : :
5940 : : /* Serialized data {{{1 */
5941 : : static GVariant *
5942 : 3579 : g_variant_deep_copy (GVariant *value,
5943 : : gboolean byteswap)
5944 : : {
5945 : 3579 : switch (g_variant_classify (value))
5946 : : {
5947 : 984 : case G_VARIANT_CLASS_MAYBE:
5948 : : case G_VARIANT_CLASS_TUPLE:
5949 : : case G_VARIANT_CLASS_DICT_ENTRY:
5950 : : case G_VARIANT_CLASS_VARIANT:
5951 : : {
5952 : : GVariantBuilder builder;
5953 : : gsize i, n_children;
5954 : :
5955 : 984 : g_variant_builder_init_static (&builder, g_variant_get_type (value));
5956 : :
5957 : 3885 : for (i = 0, n_children = g_variant_n_children (value); i < n_children; i++)
5958 : : {
5959 : 2901 : GVariant *child = g_variant_get_child_value (value, i);
5960 : 2901 : g_variant_builder_add_value (&builder, g_variant_deep_copy (child, byteswap));
5961 : 2901 : g_variant_unref (child);
5962 : : }
5963 : :
5964 : 984 : return g_variant_builder_end (&builder);
5965 : : }
5966 : :
5967 : 448 : case G_VARIANT_CLASS_ARRAY:
5968 : : {
5969 : : GVariantBuilder builder;
5970 : : gsize i, n_children;
5971 : 448 : GVariant *first_invalid_child_deep_copy = NULL;
5972 : :
5973 : : /* Arrays are in theory treated the same as maybes, tuples, dict entries
5974 : : * and variants, and could be another case in the above block of code.
5975 : : *
5976 : : * However, they have the property that when dealing with non-normal
5977 : : * data (which is the only time g_variant_deep_copy() is currently
5978 : : * called) in a variable-sized array, the code above can easily end up
5979 : : * creating many default child values in order to return an array which
5980 : : * is of the right length and type, but without containing non-normal
5981 : : * data. This can happen if the offset table for the array is malformed.
5982 : : *
5983 : : * In this case, the code above would end up allocating the same default
5984 : : * value for each one of the child indexes beyond the first malformed
5985 : : * entry in the offset table. This can end up being a lot of identical
5986 : : * allocations of default values, particularly if the non-normal array
5987 : : * is crafted maliciously.
5988 : : *
5989 : : * Avoid that problem by returning a new reference to the same default
5990 : : * value for every child after the first invalid one. This results in
5991 : : * returning an equivalent array, in normal form and trusted — but with
5992 : : * significantly fewer memory allocations.
5993 : : *
5994 : : * See https://gitlab.gnome.org/GNOME/glib/-/issues/2540 */
5995 : :
5996 : 448 : g_variant_builder_init_static (&builder, g_variant_get_type (value));
5997 : :
5998 : 45748 : for (i = 0, n_children = g_variant_n_children (value); i < n_children; i++)
5999 : : {
6000 : : /* Try maybe_get_child_value() first; if it returns NULL, this child
6001 : : * is non-normal. get_child_value() would have constructed and
6002 : : * returned a default value in that case. */
6003 : 45300 : GVariant *child = g_variant_maybe_get_child_value (value, i);
6004 : :
6005 : 45300 : if (child != NULL)
6006 : : {
6007 : : /* Non-normal children may not always be contiguous, as they may
6008 : : * be non-normal for reasons other than invalid offset table
6009 : : * entries. As they are all the same type, they will all have
6010 : : * the same default value though, so keep that around. */
6011 : 387 : g_variant_builder_add_value (&builder, g_variant_deep_copy (child, byteswap));
6012 : : }
6013 : 44913 : else if (child == NULL && first_invalid_child_deep_copy != NULL)
6014 : : {
6015 : 44889 : g_variant_builder_add_value (&builder, first_invalid_child_deep_copy);
6016 : : }
6017 : 24 : else if (child == NULL)
6018 : : {
6019 : 24 : child = g_variant_get_child_value (value, i);
6020 : 24 : first_invalid_child_deep_copy = g_variant_ref_sink (g_variant_deep_copy (child, byteswap));
6021 : 24 : g_variant_builder_add_value (&builder, first_invalid_child_deep_copy);
6022 : : }
6023 : :
6024 : 45300 : g_clear_pointer (&child, g_variant_unref);
6025 : : }
6026 : :
6027 : 448 : g_clear_pointer (&first_invalid_child_deep_copy, g_variant_unref);
6028 : :
6029 : 448 : return g_variant_builder_end (&builder);
6030 : : }
6031 : :
6032 : 490 : case G_VARIANT_CLASS_BOOLEAN:
6033 : 490 : return g_variant_new_boolean (g_variant_get_boolean (value));
6034 : :
6035 : 128 : case G_VARIANT_CLASS_BYTE:
6036 : 128 : return g_variant_new_byte (g_variant_get_byte (value));
6037 : :
6038 : 123 : case G_VARIANT_CLASS_INT16:
6039 : 123 : if (byteswap)
6040 : 123 : return g_variant_new_int16 (GUINT16_SWAP_LE_BE (g_variant_get_int16 (value)));
6041 : : else
6042 : 0 : return g_variant_new_int16 (g_variant_get_int16 (value));
6043 : :
6044 : 126 : case G_VARIANT_CLASS_UINT16:
6045 : 126 : if (byteswap)
6046 : 126 : return g_variant_new_uint16 (GUINT16_SWAP_LE_BE (g_variant_get_uint16 (value)));
6047 : : else
6048 : 0 : return g_variant_new_uint16 (g_variant_get_uint16 (value));
6049 : :
6050 : 169 : case G_VARIANT_CLASS_INT32:
6051 : 169 : if (byteswap)
6052 : 122 : return g_variant_new_int32 (GUINT32_SWAP_LE_BE (g_variant_get_int32 (value)));
6053 : : else
6054 : 47 : return g_variant_new_int32 (g_variant_get_int32 (value));
6055 : :
6056 : 114 : case G_VARIANT_CLASS_UINT32:
6057 : 114 : if (byteswap)
6058 : 114 : return g_variant_new_uint32 (GUINT32_SWAP_LE_BE (g_variant_get_uint32 (value)));
6059 : : else
6060 : 0 : return g_variant_new_uint32 (g_variant_get_uint32 (value));
6061 : :
6062 : 135 : case G_VARIANT_CLASS_INT64:
6063 : 135 : if (byteswap)
6064 : 135 : return g_variant_new_int64 (GUINT64_SWAP_LE_BE (g_variant_get_int64 (value)));
6065 : : else
6066 : 0 : return g_variant_new_int64 (g_variant_get_int64 (value));
6067 : :
6068 : 122 : case G_VARIANT_CLASS_UINT64:
6069 : 122 : if (byteswap)
6070 : 122 : return g_variant_new_uint64 (GUINT64_SWAP_LE_BE (g_variant_get_uint64 (value)));
6071 : : else
6072 : 0 : return g_variant_new_uint64 (g_variant_get_uint64 (value));
6073 : :
6074 : 118 : case G_VARIANT_CLASS_HANDLE:
6075 : 118 : if (byteswap)
6076 : 117 : return g_variant_new_handle (GUINT32_SWAP_LE_BE (g_variant_get_handle (value)));
6077 : : else
6078 : 1 : return g_variant_new_handle (g_variant_get_handle (value));
6079 : :
6080 : 154 : case G_VARIANT_CLASS_DOUBLE:
6081 : 154 : if (byteswap)
6082 : : {
6083 : : /* We have to convert the double to a uint64 here using a union,
6084 : : * because a cast will round it numerically. */
6085 : : union
6086 : : {
6087 : : guint64 u64;
6088 : : gdouble dbl;
6089 : : } u1, u2;
6090 : 133 : u1.dbl = g_variant_get_double (value);
6091 : 133 : u2.u64 = GUINT64_SWAP_LE_BE (u1.u64);
6092 : 133 : return g_variant_new_double (u2.dbl);
6093 : : }
6094 : : else
6095 : 21 : return g_variant_new_double (g_variant_get_double (value));
6096 : :
6097 : 178 : case G_VARIANT_CLASS_STRING:
6098 : 178 : return g_variant_new_string (g_variant_get_string (value, NULL));
6099 : :
6100 : 143 : case G_VARIANT_CLASS_OBJECT_PATH:
6101 : 143 : return g_variant_new_object_path (g_variant_get_string (value, NULL));
6102 : :
6103 : 147 : case G_VARIANT_CLASS_SIGNATURE:
6104 : 147 : return g_variant_new_signature (g_variant_get_string (value, NULL));
6105 : : }
6106 : :
6107 : : g_assert_not_reached ();
6108 : : }
6109 : :
6110 : : /**
6111 : : * g_variant_get_normal_form:
6112 : : * @value: a #GVariant
6113 : : *
6114 : : * Gets a #GVariant instance that has the same value as @value and is
6115 : : * trusted to be in normal form.
6116 : : *
6117 : : * If @value is already trusted to be in normal form then a new
6118 : : * reference to @value is returned.
6119 : : *
6120 : : * If @value is not already trusted, then it is scanned to check if it
6121 : : * is in normal form. If it is found to be in normal form then it is
6122 : : * marked as trusted and a new reference to it is returned.
6123 : : *
6124 : : * If @value is found not to be in normal form then a new trusted
6125 : : * #GVariant is created with the same value as @value. The non-normal parts of
6126 : : * @value will be replaced with default values which are guaranteed to be in
6127 : : * normal form.
6128 : : *
6129 : : * It makes sense to call this function if you've received #GVariant
6130 : : * data from untrusted sources and you want to ensure your serialized
6131 : : * output is definitely in normal form.
6132 : : *
6133 : : * If @value is already in normal form, a new reference will be returned
6134 : : * (which will be floating if @value is floating). If it is not in normal form,
6135 : : * the newly created #GVariant will be returned with a single non-floating
6136 : : * reference. Typically, g_variant_take_ref() should be called on the return
6137 : : * value from this function to guarantee ownership of a single non-floating
6138 : : * reference to it.
6139 : : *
6140 : : * Returns: (transfer full): a trusted #GVariant
6141 : : *
6142 : : * Since: 2.24
6143 : : **/
6144 : : GVariant *
6145 : 310 : g_variant_get_normal_form (GVariant *value)
6146 : : {
6147 : : GVariant *trusted;
6148 : :
6149 : 310 : if (g_variant_is_normal_form (value))
6150 : 207 : return g_variant_ref (value);
6151 : :
6152 : 103 : trusted = g_variant_deep_copy (value, FALSE);
6153 : 103 : g_assert (g_variant_is_trusted (trusted));
6154 : :
6155 : 103 : return g_variant_ref_sink (trusted);
6156 : : }
6157 : :
6158 : : /**
6159 : : * g_variant_byteswap:
6160 : : * @value: a #GVariant
6161 : : *
6162 : : * Performs a byteswapping operation on the contents of @value. The
6163 : : * result is that all multi-byte numeric data contained in @value is
6164 : : * byteswapped. That includes 16, 32, and 64bit signed and unsigned
6165 : : * integers as well as file handles and double precision floating point
6166 : : * values.
6167 : : *
6168 : : * This function is an identity mapping on any value that does not
6169 : : * contain multi-byte numeric data. That include strings, booleans,
6170 : : * bytes and containers containing only these things (recursively).
6171 : : *
6172 : : * While this function can safely handle untrusted, non-normal data, it is
6173 : : * recommended to check whether the input is in normal form beforehand, using
6174 : : * g_variant_is_normal_form(), and to reject non-normal inputs if your
6175 : : * application can be strict about what inputs it rejects.
6176 : : *
6177 : : * The returned value is always in normal form and is marked as trusted.
6178 : : * A full, not floating, reference is returned.
6179 : : *
6180 : : * Returns: (transfer full): the byteswapped form of @value
6181 : : *
6182 : : * Since: 2.24
6183 : : **/
6184 : : GVariant *
6185 : 412 : g_variant_byteswap (GVariant *value)
6186 : : {
6187 : : GVariantTypeInfo *type_info;
6188 : : guint alignment;
6189 : : GVariant *new;
6190 : :
6191 : 412 : type_info = g_variant_get_type_info (value);
6192 : :
6193 : 412 : g_variant_type_info_query (type_info, &alignment, NULL);
6194 : :
6195 : 412 : if (alignment && g_variant_is_normal_form (value))
6196 : 175 : {
6197 : : /* (potentially) contains multi-byte numeric data, but is also already in
6198 : : * normal form so we can use a faster byteswapping codepath on the
6199 : : * serialised data */
6200 : 175 : GVariantSerialised serialised = { 0, };
6201 : : GBytes *bytes;
6202 : :
6203 : 175 : serialised.type_info = g_variant_get_type_info (value);
6204 : 175 : serialised.size = g_variant_get_size (value);
6205 : 175 : serialised.data = g_malloc (serialised.size);
6206 : 175 : serialised.depth = g_variant_get_depth (value);
6207 : 175 : serialised.ordered_offsets_up_to = G_MAXSIZE; /* operating on the normal form */
6208 : 175 : serialised.checked_offsets_up_to = G_MAXSIZE;
6209 : 175 : g_variant_store (value, serialised.data);
6210 : :
6211 : 175 : g_variant_serialised_byteswap (serialised);
6212 : :
6213 : 175 : bytes = g_bytes_new_take (serialised.data, serialised.size);
6214 : 175 : new = g_variant_ref_sink (g_variant_new_take_bytes (g_variant_get_type (value), g_steal_pointer (&bytes), TRUE));
6215 : : }
6216 : 237 : else if (alignment)
6217 : : /* (potentially) contains multi-byte numeric data */
6218 : 164 : new = g_variant_ref_sink (g_variant_deep_copy (value, TRUE));
6219 : : else
6220 : : /* contains no multi-byte data */
6221 : 73 : new = g_variant_get_normal_form (value);
6222 : :
6223 : 412 : g_assert (g_variant_is_trusted (new));
6224 : :
6225 : 412 : return g_steal_pointer (&new);
6226 : : }
6227 : :
6228 : : /**
6229 : : * g_variant_new_from_data:
6230 : : * @type: a definite #GVariantType
6231 : : * @data: (array length=size) (element-type guint8): the serialized data
6232 : : * @size: the size of @data
6233 : : * @trusted: %TRUE if @data is definitely in normal form
6234 : : * @notify: (scope async): function to call when @data is no longer needed
6235 : : * @user_data: data for @notify
6236 : : *
6237 : : * Creates a new #GVariant instance from serialized data.
6238 : : *
6239 : : * @type is the type of #GVariant instance that will be constructed.
6240 : : * The interpretation of @data depends on knowing the type.
6241 : : *
6242 : : * @data is not modified by this function and must remain valid with an
6243 : : * unchanging value until such a time as @notify is called with
6244 : : * @user_data. If the contents of @data change before that time then
6245 : : * the result is undefined.
6246 : : *
6247 : : * If @data is trusted to be serialized data in normal form then
6248 : : * @trusted should be %TRUE. This applies to serialized data created
6249 : : * within this process or read from a trusted location on the disk (such
6250 : : * as a file installed in /usr/lib alongside your application). You
6251 : : * should set trusted to %FALSE if @data is read from the network, a
6252 : : * file in the user's home directory, etc.
6253 : : *
6254 : : * If @data was not stored in this machine's native endianness, any multi-byte
6255 : : * numeric values in the returned variant will also be in non-native
6256 : : * endianness. g_variant_byteswap() can be used to recover the original values.
6257 : : *
6258 : : * @notify will be called with @user_data when @data is no longer
6259 : : * needed. The exact time of this call is unspecified and might even be
6260 : : * before this function returns.
6261 : : *
6262 : : * Note: @data must be backed by memory that is aligned appropriately for the
6263 : : * @type being loaded. Otherwise this function will internally create a copy of
6264 : : * the memory (since GLib 2.60) or (in older versions) fail and exit the
6265 : : * process.
6266 : : *
6267 : : * Returns: (transfer none): a new floating #GVariant of type @type
6268 : : *
6269 : : * Since: 2.24
6270 : : **/
6271 : : GVariant *
6272 : 1527 : g_variant_new_from_data (const GVariantType *type,
6273 : : gconstpointer data,
6274 : : gsize size,
6275 : : gboolean trusted,
6276 : : GDestroyNotify notify,
6277 : : gpointer user_data)
6278 : : {
6279 : : GBytes *bytes;
6280 : :
6281 : 1527 : g_return_val_if_fail (g_variant_type_is_definite (type), NULL);
6282 : 1527 : g_return_val_if_fail (data != NULL || size == 0, NULL);
6283 : :
6284 : 1527 : if (notify)
6285 : 779 : bytes = g_bytes_new_with_free_func (data, size, notify, user_data);
6286 : : else
6287 : 748 : bytes = g_bytes_new_static (data, size);
6288 : :
6289 : 1527 : return g_variant_new_take_bytes (type, g_steal_pointer (&bytes), trusted);
6290 : : }
6291 : :
6292 : : /* Epilogue {{{1 */
6293 : : /* vim:set foldmethod=marker: */
|