1 /* -*- mode: C; c-file-style: "gnu" -*- */
2 /* dbus-marshal-recursive-util.c Would be in dbus-marshal-recursive.c, but only used in bus/tests
4 * Copyright (C) 2004, 2005 Red Hat, Inc.
6 * Licensed under the Academic Free License version 2.1
8 * This program is free software; you can redistribute it and/or modify
9 * it under the terms of the GNU General Public License as published by
10 * the Free Software Foundation; either version 2 of the License, or
11 * (at your option) any later version.
13 * This program is distributed in the hope that it will be useful,
14 * but WITHOUT ANY WARRANTY; without even the implied warranty of
15 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
16 * GNU General Public License for more details.
18 * You should have received a copy of the GNU General Public License
19 * along with this program; if not, write to the Free Software
20 * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
26 #ifdef DBUS_BUILD_TESTS
28 #include "dbus-marshal-recursive.h"
29 #include "dbus-marshal-basic.h"
30 #include "dbus-signature.h"
31 #include "dbus-internals.h"
35 basic_value_zero (DBusBasicValue *value)
38 #ifdef DBUS_HAVE_INT64
41 value->u64.first32 = 0;
42 value->u64.second32 = 0;
47 basic_value_equal (int type,
51 if (type == DBUS_TYPE_STRING ||
52 type == DBUS_TYPE_SIGNATURE ||
53 type == DBUS_TYPE_OBJECT_PATH)
55 return strcmp (lhs->str, rhs->str) == 0;
59 #ifdef DBUS_HAVE_INT64
60 return lhs->u64 == rhs->u64;
62 return lhs->u64.first32 == rhs->u64.first32 &&
63 lhs->u64.second32 == rhs->u64.second32;
69 equal_values_helper (DBusTypeReader *lhs,
75 lhs_type = _dbus_type_reader_get_current_type (lhs);
76 rhs_type = _dbus_type_reader_get_current_type (rhs);
78 if (lhs_type != rhs_type)
81 if (lhs_type == DBUS_TYPE_INVALID)
84 if (dbus_type_is_basic (lhs_type))
86 DBusBasicValue lhs_value;
87 DBusBasicValue rhs_value;
89 basic_value_zero (&lhs_value);
90 basic_value_zero (&rhs_value);
92 _dbus_type_reader_read_basic (lhs, &lhs_value);
93 _dbus_type_reader_read_basic (rhs, &rhs_value);
95 return basic_value_equal (lhs_type, &lhs_value, &rhs_value);
99 DBusTypeReader lhs_sub;
100 DBusTypeReader rhs_sub;
102 _dbus_type_reader_recurse (lhs, &lhs_sub);
103 _dbus_type_reader_recurse (rhs, &rhs_sub);
105 return equal_values_helper (&lhs_sub, &rhs_sub);
110 * See whether the two readers point to identical data blocks.
112 * @param lhs reader 1
113 * @param rhs reader 2
114 * @returns #TRUE if the data blocks have the same values
117 _dbus_type_reader_equal_values (const DBusTypeReader *lhs,
118 const DBusTypeReader *rhs)
120 DBusTypeReader copy_lhs = *lhs;
121 DBusTypeReader copy_rhs = *rhs;
123 return equal_values_helper (©_lhs, ©_rhs);
127 #include "dbus-test.h"
128 #include "dbus-list.h"
132 /* Whether to do the OOM stuff (only with other expensive tests) */
133 #define TEST_OOM_HANDLING 0
134 /* We do start offset 0 through 9, to get various alignment cases. Still this
135 * obviously makes the test suite run 10x as slow.
137 #define MAX_INITIAL_OFFSET 9
139 /* Largest iteration count to test copying, realignment,
140 * etc. with. i.e. we only test this stuff with some of the smaller
143 #define MAX_ITERATIONS_FOR_EXPENSIVE_TESTS 1000
149 DBusString signature;
159 #define N_FENCE_BYTES 5
160 #define FENCE_BYTES_STR "abcde"
161 #define INITIAL_PADDING_BYTE '\0'
164 data_block_init (DataBlock *block,
168 if (!_dbus_string_init (&block->signature))
171 if (!_dbus_string_init (&block->body))
173 _dbus_string_free (&block->signature);
177 if (!_dbus_string_insert_bytes (&block->signature, 0, initial_offset,
178 INITIAL_PADDING_BYTE) ||
179 !_dbus_string_insert_bytes (&block->body, 0, initial_offset,
180 INITIAL_PADDING_BYTE) ||
181 !_dbus_string_append (&block->signature, FENCE_BYTES_STR) ||
182 !_dbus_string_append (&block->body, FENCE_BYTES_STR))
184 _dbus_string_free (&block->signature);
185 _dbus_string_free (&block->body);
189 block->byte_order = byte_order;
190 block->initial_offset = initial_offset;
196 data_block_save (DataBlock *block,
197 DataBlockState *state)
199 state->saved_sig_len = _dbus_string_get_length (&block->signature) - N_FENCE_BYTES;
200 state->saved_body_len = _dbus_string_get_length (&block->body) - N_FENCE_BYTES;
204 data_block_restore (DataBlock *block,
205 DataBlockState *state)
207 _dbus_string_delete (&block->signature,
208 state->saved_sig_len,
209 _dbus_string_get_length (&block->signature) - state->saved_sig_len - N_FENCE_BYTES);
210 _dbus_string_delete (&block->body,
211 state->saved_body_len,
212 _dbus_string_get_length (&block->body) - state->saved_body_len - N_FENCE_BYTES);
216 data_block_verify (DataBlock *block)
218 if (!_dbus_string_ends_with_c_str (&block->signature,
223 offset = _dbus_string_get_length (&block->signature) - N_FENCE_BYTES - 8;
227 _dbus_verbose_bytes_of_string (&block->signature,
229 _dbus_string_get_length (&block->signature) - offset);
230 _dbus_assert_not_reached ("block did not verify: bad bytes at end of signature");
232 if (!_dbus_string_ends_with_c_str (&block->body,
237 offset = _dbus_string_get_length (&block->body) - N_FENCE_BYTES - 8;
241 _dbus_verbose_bytes_of_string (&block->body,
243 _dbus_string_get_length (&block->body) - offset);
244 _dbus_assert_not_reached ("block did not verify: bad bytes at end of body");
247 _dbus_assert (_dbus_string_validate_nul (&block->signature,
248 0, block->initial_offset));
249 _dbus_assert (_dbus_string_validate_nul (&block->body,
250 0, block->initial_offset));
254 data_block_free (DataBlock *block)
256 data_block_verify (block);
258 _dbus_string_free (&block->signature);
259 _dbus_string_free (&block->body);
263 data_block_reset (DataBlock *block)
265 data_block_verify (block);
267 _dbus_string_delete (&block->signature,
268 block->initial_offset,
269 _dbus_string_get_length (&block->signature) - N_FENCE_BYTES - block->initial_offset);
270 _dbus_string_delete (&block->body,
271 block->initial_offset,
272 _dbus_string_get_length (&block->body) - N_FENCE_BYTES - block->initial_offset);
274 data_block_verify (block);
278 data_block_init_reader_writer (DataBlock *block,
279 DBusTypeReader *reader,
280 DBusTypeWriter *writer)
283 _dbus_type_reader_init (reader,
286 block->initial_offset,
288 block->initial_offset);
291 _dbus_type_writer_init (writer,
294 _dbus_string_get_length (&block->signature) - N_FENCE_BYTES,
296 _dbus_string_get_length (&block->body) - N_FENCE_BYTES);
300 real_check_expected_type (DBusTypeReader *reader,
302 const char *funcname,
307 t = _dbus_type_reader_get_current_type (reader);
311 _dbus_warn ("Read type %s while expecting %s at %s line %d\n",
312 _dbus_type_to_string (t),
313 _dbus_type_to_string (expected),
316 _dbus_assert_not_reached ("read wrong type");
320 #define check_expected_type(reader, expected) real_check_expected_type (reader, expected, _DBUS_FUNCTION_NAME, __LINE__)
322 #define NEXT_EXPECTING_TRUE(reader) do { if (!_dbus_type_reader_next (reader)) \
324 _dbus_warn ("_dbus_type_reader_next() should have returned TRUE at %s %d\n", \
325 _DBUS_FUNCTION_NAME, __LINE__); \
326 _dbus_assert_not_reached ("test failed"); \
330 #define NEXT_EXPECTING_FALSE(reader) do { if (_dbus_type_reader_next (reader)) \
332 _dbus_warn ("_dbus_type_reader_next() should have returned FALSE at %s %d\n", \
333 _DBUS_FUNCTION_NAME, __LINE__); \
334 _dbus_assert_not_reached ("test failed"); \
336 check_expected_type (reader, DBUS_TYPE_INVALID); \
339 typedef struct TestTypeNode TestTypeNode;
340 typedef struct TestTypeNodeClass TestTypeNodeClass;
341 typedef struct TestTypeNodeContainer TestTypeNodeContainer;
342 typedef struct TestTypeNodeContainerClass TestTypeNodeContainerClass;
346 const TestTypeNodeClass *klass;
349 struct TestTypeNodeContainer
355 struct TestTypeNodeClass
361 int subclass_detail; /* a bad hack to avoid a bunch of subclass casting */
363 dbus_bool_t (* construct) (TestTypeNode *node);
364 void (* destroy) (TestTypeNode *node);
366 dbus_bool_t (* write_value) (TestTypeNode *node,
368 DBusTypeWriter *writer,
370 dbus_bool_t (* read_value) (TestTypeNode *node,
371 DBusTypeReader *reader,
373 dbus_bool_t (* set_value) (TestTypeNode *node,
374 DBusTypeReader *reader,
375 DBusTypeReader *realign_root,
377 dbus_bool_t (* build_signature) (TestTypeNode *node,
379 dbus_bool_t (* write_multi) (TestTypeNode *node,
381 DBusTypeWriter *writer,
384 dbus_bool_t (* read_multi) (TestTypeNode *node,
385 DBusTypeReader *reader,
390 struct TestTypeNodeContainerClass
392 TestTypeNodeClass base;
395 /* FIXME this could be chilled out substantially by unifying
396 * the basic types into basic_write_value/basic_read_value
397 * and by merging read_value and set_value into one function
398 * taking a flag argument.
400 static dbus_bool_t int16_write_value (TestTypeNode *node,
402 DBusTypeWriter *writer,
404 static dbus_bool_t int16_read_value (TestTypeNode *node,
405 DBusTypeReader *reader,
407 static dbus_bool_t int16_set_value (TestTypeNode *node,
408 DBusTypeReader *reader,
409 DBusTypeReader *realign_root,
411 static dbus_bool_t int16_write_multi (TestTypeNode *node,
413 DBusTypeWriter *writer,
416 static dbus_bool_t int16_read_multi (TestTypeNode *node,
417 DBusTypeReader *reader,
420 static dbus_bool_t int32_write_value (TestTypeNode *node,
422 DBusTypeWriter *writer,
424 static dbus_bool_t int32_read_value (TestTypeNode *node,
425 DBusTypeReader *reader,
427 static dbus_bool_t int32_set_value (TestTypeNode *node,
428 DBusTypeReader *reader,
429 DBusTypeReader *realign_root,
431 static dbus_bool_t int32_write_multi (TestTypeNode *node,
433 DBusTypeWriter *writer,
436 static dbus_bool_t int32_read_multi (TestTypeNode *node,
437 DBusTypeReader *reader,
440 static dbus_bool_t int64_write_value (TestTypeNode *node,
442 DBusTypeWriter *writer,
444 static dbus_bool_t int64_read_value (TestTypeNode *node,
445 DBusTypeReader *reader,
447 static dbus_bool_t int64_set_value (TestTypeNode *node,
448 DBusTypeReader *reader,
449 DBusTypeReader *realign_root,
451 static dbus_bool_t string_write_value (TestTypeNode *node,
453 DBusTypeWriter *writer,
455 static dbus_bool_t string_read_value (TestTypeNode *node,
456 DBusTypeReader *reader,
458 static dbus_bool_t string_set_value (TestTypeNode *node,
459 DBusTypeReader *reader,
460 DBusTypeReader *realign_root,
462 static dbus_bool_t bool_write_value (TestTypeNode *node,
464 DBusTypeWriter *writer,
466 static dbus_bool_t bool_read_value (TestTypeNode *node,
467 DBusTypeReader *reader,
469 static dbus_bool_t bool_set_value (TestTypeNode *node,
470 DBusTypeReader *reader,
471 DBusTypeReader *realign_root,
473 static dbus_bool_t byte_write_value (TestTypeNode *node,
475 DBusTypeWriter *writer,
477 static dbus_bool_t byte_read_value (TestTypeNode *node,
478 DBusTypeReader *reader,
480 static dbus_bool_t byte_set_value (TestTypeNode *node,
481 DBusTypeReader *reader,
482 DBusTypeReader *realign_root,
484 static dbus_bool_t double_write_value (TestTypeNode *node,
486 DBusTypeWriter *writer,
488 static dbus_bool_t double_read_value (TestTypeNode *node,
489 DBusTypeReader *reader,
491 static dbus_bool_t double_set_value (TestTypeNode *node,
492 DBusTypeReader *reader,
493 DBusTypeReader *realign_root,
495 static dbus_bool_t object_path_write_value (TestTypeNode *node,
497 DBusTypeWriter *writer,
499 static dbus_bool_t object_path_read_value (TestTypeNode *node,
500 DBusTypeReader *reader,
502 static dbus_bool_t object_path_set_value (TestTypeNode *node,
503 DBusTypeReader *reader,
504 DBusTypeReader *realign_root,
506 static dbus_bool_t signature_write_value (TestTypeNode *node,
508 DBusTypeWriter *writer,
510 static dbus_bool_t signature_read_value (TestTypeNode *node,
511 DBusTypeReader *reader,
513 static dbus_bool_t signature_set_value (TestTypeNode *node,
514 DBusTypeReader *reader,
515 DBusTypeReader *realign_root,
517 static dbus_bool_t struct_write_value (TestTypeNode *node,
519 DBusTypeWriter *writer,
521 static dbus_bool_t struct_read_value (TestTypeNode *node,
522 DBusTypeReader *reader,
524 static dbus_bool_t struct_set_value (TestTypeNode *node,
525 DBusTypeReader *reader,
526 DBusTypeReader *realign_root,
528 static dbus_bool_t struct_build_signature (TestTypeNode *node,
530 static dbus_bool_t dict_write_value (TestTypeNode *node,
532 DBusTypeWriter *writer,
534 static dbus_bool_t dict_read_value (TestTypeNode *node,
535 DBusTypeReader *reader,
537 static dbus_bool_t dict_set_value (TestTypeNode *node,
538 DBusTypeReader *reader,
539 DBusTypeReader *realign_root,
541 static dbus_bool_t dict_build_signature (TestTypeNode *node,
543 static dbus_bool_t array_write_value (TestTypeNode *node,
545 DBusTypeWriter *writer,
547 static dbus_bool_t array_read_value (TestTypeNode *node,
548 DBusTypeReader *reader,
550 static dbus_bool_t array_set_value (TestTypeNode *node,
551 DBusTypeReader *reader,
552 DBusTypeReader *realign_root,
554 static dbus_bool_t array_build_signature (TestTypeNode *node,
556 static dbus_bool_t variant_write_value (TestTypeNode *node,
558 DBusTypeWriter *writer,
560 static dbus_bool_t variant_read_value (TestTypeNode *node,
561 DBusTypeReader *reader,
563 static dbus_bool_t variant_set_value (TestTypeNode *node,
564 DBusTypeReader *reader,
565 DBusTypeReader *realign_root,
567 static void container_destroy (TestTypeNode *node);
571 static const TestTypeNodeClass int16_class = {
573 sizeof (TestTypeNode),
585 static const TestTypeNodeClass uint16_class = {
587 sizeof (TestTypeNode),
591 int16_write_value, /* recycle from int16 */
592 int16_read_value, /* recycle from int16 */
593 int16_set_value, /* recycle from int16 */
595 int16_write_multi, /* recycle from int16 */
596 int16_read_multi /* recycle from int16 */
599 static const TestTypeNodeClass int32_class = {
601 sizeof (TestTypeNode),
613 static const TestTypeNodeClass uint32_class = {
615 sizeof (TestTypeNode),
619 int32_write_value, /* recycle from int32 */
620 int32_read_value, /* recycle from int32 */
621 int32_set_value, /* recycle from int32 */
623 int32_write_multi, /* recycle from int32 */
624 int32_read_multi /* recycle from int32 */
627 static const TestTypeNodeClass int64_class = {
629 sizeof (TestTypeNode),
641 static const TestTypeNodeClass uint64_class = {
643 sizeof (TestTypeNode),
647 int64_write_value, /* recycle from int64 */
648 int64_read_value, /* recycle from int64 */
649 int64_set_value, /* recycle from int64 */
655 static const TestTypeNodeClass string_0_class = {
657 sizeof (TestTypeNode),
658 0, /* string length */
669 static const TestTypeNodeClass string_1_class = {
671 sizeof (TestTypeNode),
672 1, /* string length */
683 /* with nul, a len 3 string should fill 4 bytes and thus is "special" */
684 static const TestTypeNodeClass string_3_class = {
686 sizeof (TestTypeNode),
687 3, /* string length */
698 /* with nul, a len 8 string should fill 9 bytes and thus is "special" (far-fetched I suppose) */
699 static const TestTypeNodeClass string_8_class = {
701 sizeof (TestTypeNode),
702 8, /* string length */
713 static const TestTypeNodeClass bool_class = {
715 sizeof (TestTypeNode),
727 static const TestTypeNodeClass byte_class = {
729 sizeof (TestTypeNode),
741 static const TestTypeNodeClass double_class = {
743 sizeof (TestTypeNode),
755 static const TestTypeNodeClass object_path_class = {
756 DBUS_TYPE_OBJECT_PATH,
757 sizeof (TestTypeNode),
761 object_path_write_value,
762 object_path_read_value,
763 object_path_set_value,
769 static const TestTypeNodeClass signature_class = {
771 sizeof (TestTypeNode),
775 signature_write_value,
776 signature_read_value,
783 static const TestTypeNodeClass struct_1_class = {
785 sizeof (TestTypeNodeContainer),
786 1, /* number of times children appear as fields */
792 struct_build_signature,
797 static const TestTypeNodeClass struct_2_class = {
799 sizeof (TestTypeNodeContainer),
800 2, /* number of times children appear as fields */
806 struct_build_signature,
811 static const TestTypeNodeClass dict_1_class = {
812 DBUS_TYPE_ARRAY, /* this is correct, a dict is an array of dict entry */
813 sizeof (TestTypeNodeContainer),
814 1, /* number of entries */
820 dict_build_signature,
825 static dbus_bool_t arrays_write_fixed_in_blocks = FALSE;
827 static const TestTypeNodeClass array_0_class = {
829 sizeof (TestTypeNodeContainer),
830 0, /* number of array elements */
836 array_build_signature,
841 static const TestTypeNodeClass array_1_class = {
843 sizeof (TestTypeNodeContainer),
844 1, /* number of array elements */
850 array_build_signature,
855 static const TestTypeNodeClass array_2_class = {
857 sizeof (TestTypeNodeContainer),
858 2, /* number of array elements */
864 array_build_signature,
869 static const TestTypeNodeClass array_9_class = {
871 sizeof (TestTypeNodeContainer),
872 9, /* number of array elements */
878 array_build_signature,
883 static const TestTypeNodeClass variant_class = {
885 sizeof (TestTypeNodeContainer),
897 static const TestTypeNodeClass* const
915 #define N_BASICS (_DBUS_N_ELEMENTS (basic_nodes))
917 static const TestTypeNodeClass* const
918 container_nodes[] = {
925 &dict_1_class /* last since we want struct and array before it */
926 /* array_9_class is omitted on purpose, it's too slow;
927 * we only use it in one hardcoded test below
930 #define N_CONTAINERS (_DBUS_N_ELEMENTS (container_nodes))
933 node_new (const TestTypeNodeClass *klass)
937 node = dbus_malloc0 (klass->instance_size);
943 if (klass->construct)
945 if (!(* klass->construct) (node))
956 node_destroy (TestTypeNode *node)
958 if (node->klass->destroy)
959 (* node->klass->destroy) (node);
964 node_write_value (TestTypeNode *node,
966 DBusTypeWriter *writer,
971 retval = (* node->klass->write_value) (node, block, writer, seed);
974 /* Handy to see where things break, but too expensive to do all the time */
975 data_block_verify (block);
982 node_read_value (TestTypeNode *node,
983 DBusTypeReader *reader,
987 DBusTypeReader restored;
989 _dbus_type_reader_save_mark (reader, &mark);
991 if (!(* node->klass->read_value) (node, reader, seed))
994 _dbus_type_reader_init_from_mark (&restored,
1000 if (!(* node->klass->read_value) (node, &restored, seed))
1006 /* Warning: if this one fails due to OOM, it has side effects (can
1007 * modify only some of the sub-values). OK in a test suite, but we
1008 * never do this in real code.
1011 node_set_value (TestTypeNode *node,
1012 DBusTypeReader *reader,
1013 DBusTypeReader *realign_root,
1016 if (!(* node->klass->set_value) (node, reader, realign_root, seed))
1023 node_build_signature (TestTypeNode *node,
1026 if (node->klass->build_signature)
1027 return (* node->klass->build_signature) (node, str);
1029 return _dbus_string_append_byte (str, node->klass->typecode);
1033 node_append_child (TestTypeNode *node,
1034 TestTypeNode *child)
1036 TestTypeNodeContainer *container = (TestTypeNodeContainer*) node;
1038 _dbus_assert (node->klass->instance_size >= (int) sizeof (TestTypeNodeContainer));
1040 if (!_dbus_list_append (&container->children, child))
1041 _dbus_assert_not_reached ("no memory"); /* we never check the return value on node_append_child anyhow - it's run from outside the malloc-failure test code */
1047 node_write_multi (TestTypeNode *node,
1049 DBusTypeWriter *writer,
1055 _dbus_assert (node->klass->write_multi != NULL);
1056 retval = (* node->klass->write_multi) (node, block, writer, seed, n_copies);
1059 /* Handy to see where things break, but too expensive to do all the time */
1060 data_block_verify (block);
1067 node_read_multi (TestTypeNode *node,
1068 DBusTypeReader *reader,
1072 _dbus_assert (node->klass->read_multi != NULL);
1074 if (!(* node->klass->read_multi) (node, reader, seed, n_copies))
1080 static int n_iterations_completed_total = 0;
1081 static int n_iterations_completed_this_test = 0;
1082 static int n_iterations_expected_this_test = 0;
1086 const DBusString *signature;
1089 TestTypeNode **nodes;
1091 } NodeIterationData;
1094 run_test_copy (NodeIterationData *nid)
1099 DBusTypeReader reader;
1100 DBusTypeWriter writer;
1102 _dbus_verbose ("%s\n", _DBUS_FUNCTION_NAME);
1108 if (!data_block_init (&dest, src->byte_order, src->initial_offset))
1111 data_block_init_reader_writer (src, &reader, NULL);
1112 data_block_init_reader_writer (&dest, NULL, &writer);
1114 /* DBusTypeWriter assumes it's writing into an existing signature,
1115 * so doesn't add nul on its own. We have to do that.
1117 if (!_dbus_string_insert_byte (&dest.signature,
1118 dest.initial_offset, '\0'))
1121 if (!_dbus_type_writer_write_reader (&writer, &reader))
1124 /* Data blocks should now be identical */
1125 if (!_dbus_string_equal (&src->signature, &dest.signature))
1127 _dbus_verbose ("SOURCE\n");
1128 _dbus_verbose_bytes_of_string (&src->signature, 0,
1129 _dbus_string_get_length (&src->signature));
1130 _dbus_verbose ("DEST\n");
1131 _dbus_verbose_bytes_of_string (&dest.signature, 0,
1132 _dbus_string_get_length (&dest.signature));
1133 _dbus_assert_not_reached ("signatures did not match");
1136 if (!_dbus_string_equal (&src->body, &dest.body))
1138 _dbus_verbose ("SOURCE\n");
1139 _dbus_verbose_bytes_of_string (&src->body, 0,
1140 _dbus_string_get_length (&src->body));
1141 _dbus_verbose ("DEST\n");
1142 _dbus_verbose_bytes_of_string (&dest.body, 0,
1143 _dbus_string_get_length (&dest.body));
1144 _dbus_assert_not_reached ("bodies did not match");
1151 data_block_free (&dest);
1157 run_test_values_only_write (NodeIterationData *nid)
1159 DBusTypeReader reader;
1160 DBusTypeWriter writer;
1165 _dbus_verbose ("%s\n", _DBUS_FUNCTION_NAME);
1169 data_block_reset (nid->block);
1171 sig_len = _dbus_string_get_length (nid->signature);
1173 _dbus_type_writer_init_values_only (&writer,
1174 nid->block->byte_order,
1177 _dbus_string_get_length (&nid->block->body) - N_FENCE_BYTES);
1178 _dbus_type_reader_init (&reader,
1179 nid->block->byte_order,
1182 nid->block->initial_offset);
1185 while (i < nid->n_nodes)
1187 if (!node_write_value (nid->nodes[i], nid->block, &writer, i))
1193 /* if we wrote any typecodes then this would fail */
1194 _dbus_assert (sig_len == _dbus_string_get_length (nid->signature));
1196 /* But be sure we wrote out the values correctly */
1198 while (i < nid->n_nodes)
1200 if (!node_read_value (nid->nodes[i], &reader, i))
1203 if (i + 1 == nid->n_nodes)
1204 NEXT_EXPECTING_FALSE (&reader);
1206 NEXT_EXPECTING_TRUE (&reader);
1214 data_block_reset (nid->block);
1218 /* offset the seed for setting, so we set different numbers than
1219 * we originally wrote. Don't offset by a huge number since in
1220 * some cases it's value = possibilities[seed % n_possibilities]
1221 * and we don't want to wrap around. bool_from_seed
1222 * is just seed % 2 even.
1226 run_test_set_values (NodeIterationData *nid)
1228 DBusTypeReader reader;
1229 DBusTypeReader realign_root;
1233 _dbus_verbose ("%s\n", _DBUS_FUNCTION_NAME);
1237 data_block_init_reader_writer (nid->block,
1240 realign_root = reader;
1243 while (i < nid->n_nodes)
1245 if (!node_set_value (nid->nodes[i],
1246 &reader, &realign_root,
1250 if (i + 1 == nid->n_nodes)
1251 NEXT_EXPECTING_FALSE (&reader);
1253 NEXT_EXPECTING_TRUE (&reader);
1258 /* Check that the new values were set */
1260 reader = realign_root;
1263 while (i < nid->n_nodes)
1265 if (!node_read_value (nid->nodes[i], &reader,
1269 if (i + 1 == nid->n_nodes)
1270 NEXT_EXPECTING_FALSE (&reader);
1272 NEXT_EXPECTING_TRUE (&reader);
1284 run_test_delete_values (NodeIterationData *nid)
1286 DBusTypeReader reader;
1290 _dbus_verbose ("%s\n", _DBUS_FUNCTION_NAME);
1294 data_block_init_reader_writer (nid->block,
1297 while ((t = _dbus_type_reader_get_current_type (&reader)) != DBUS_TYPE_INVALID)
1299 /* Right now, deleting only works on array elements. We delete
1300 * all array elements, and then verify that there aren't any
1303 if (t == DBUS_TYPE_ARRAY)
1305 DBusTypeReader array;
1309 _dbus_type_reader_recurse (&reader, &array);
1311 while (_dbus_type_reader_get_current_type (&array) != DBUS_TYPE_INVALID)
1314 _dbus_type_reader_next (&array);
1317 /* reset to start of array */
1318 _dbus_type_reader_recurse (&reader, &array);
1319 _dbus_verbose ("recursing into deletion loop reader.value_pos = %d array.value_pos = %d array.u.start_pos = %d\n",
1320 reader.value_pos, array.value_pos, array.u.array.start_pos);
1321 while ((elem_type = _dbus_type_reader_get_current_type (&array)) != DBUS_TYPE_INVALID)
1323 /* We don't want to always delete from the same part of the array. */
1324 static int cycle = 0;
1327 _dbus_assert (n_elements > 0);
1330 if (elem == 3 || elem >= n_elements) /* end of array */
1331 elem = n_elements - 1;
1333 _dbus_verbose ("deleting array element %d of %d type %s cycle %d reader pos %d elem pos %d\n",
1334 elem, n_elements, _dbus_type_to_string (elem_type),
1335 cycle, reader.value_pos, array.value_pos);
1338 if (!_dbus_type_reader_next (&array))
1339 _dbus_assert_not_reached ("should have had another element\n");
1343 if (!_dbus_type_reader_delete (&array, &reader))
1349 _dbus_type_reader_recurse (&reader, &array);
1357 _dbus_type_reader_next (&reader);
1360 /* Check that there are no array elements left */
1361 data_block_init_reader_writer (nid->block,
1364 while ((t = _dbus_type_reader_get_current_type (&reader)) != DBUS_TYPE_INVALID)
1366 _dbus_type_reader_next (&reader);
1376 run_test_nodes_iteration (void *data)
1378 NodeIterationData *nid = data;
1379 DBusTypeReader reader;
1380 DBusTypeWriter writer;
1385 * 1. write the value
1386 * 2. strcmp-compare with the signature we built
1388 * 4. type-iterate the signature and the value and see if they are the same type-wise
1392 data_block_init_reader_writer (nid->block,
1395 /* DBusTypeWriter assumes it's writing into an existing signature,
1396 * so doesn't add nul on its own. We have to do that.
1398 if (!_dbus_string_insert_byte (&nid->block->signature,
1399 nid->type_offset, '\0'))
1403 while (i < nid->n_nodes)
1405 if (!node_write_value (nid->nodes[i], nid->block, &writer, i))
1411 if (!_dbus_string_equal_substring (nid->signature, 0, _dbus_string_get_length (nid->signature),
1412 &nid->block->signature, nid->type_offset))
1414 _dbus_warn ("Expected signature '%s' and got '%s' with initial offset %d\n",
1415 _dbus_string_get_const_data (nid->signature),
1416 _dbus_string_get_const_data_len (&nid->block->signature, nid->type_offset, 0),
1418 _dbus_assert_not_reached ("wrong signature");
1422 while (i < nid->n_nodes)
1424 if (!node_read_value (nid->nodes[i], &reader, i))
1427 if (i + 1 == nid->n_nodes)
1428 NEXT_EXPECTING_FALSE (&reader);
1430 NEXT_EXPECTING_TRUE (&reader);
1435 if (n_iterations_expected_this_test <= MAX_ITERATIONS_FOR_EXPENSIVE_TESTS)
1437 /* this set values test uses code from copy and
1438 * values_only_write so would ideally be last so you get a
1439 * simpler test case for problems with copying or values_only
1440 * writing; but it also needs an already-written DataBlock so it
1441 * has to go first. Comment it out if it breaks, and see if the
1442 * later tests also break - debug them first if so.
1444 if (!run_test_set_values (nid))
1447 if (!run_test_delete_values (nid))
1450 if (!run_test_copy (nid))
1453 if (!run_test_values_only_write (nid))
1457 /* FIXME type-iterate both signature and value and compare the resulting
1458 * tree to the node tree perhaps
1465 data_block_reset (nid->block);
1471 run_test_nodes_in_one_configuration (TestTypeNode **nodes,
1473 const DBusString *signature,
1478 NodeIterationData nid;
1480 if (!data_block_init (&block, byte_order, initial_offset))
1481 _dbus_assert_not_reached ("no memory");
1483 nid.signature = signature;
1485 nid.type_offset = initial_offset;
1487 nid.n_nodes = n_nodes;
1489 if (TEST_OOM_HANDLING &&
1490 n_iterations_expected_this_test <= MAX_ITERATIONS_FOR_EXPENSIVE_TESTS)
1492 _dbus_test_oom_handling ("running test node",
1493 run_test_nodes_iteration,
1498 if (!run_test_nodes_iteration (&nid))
1499 _dbus_assert_not_reached ("no memory");
1502 data_block_free (&block);
1506 run_test_nodes (TestTypeNode **nodes,
1510 DBusString signature;
1512 if (!_dbus_string_init (&signature))
1513 _dbus_assert_not_reached ("no memory");
1518 if (! node_build_signature (nodes[i], &signature))
1519 _dbus_assert_not_reached ("no memory");
1524 _dbus_verbose (">>> test nodes with signature '%s'\n",
1525 _dbus_string_get_const_data (&signature));
1528 while (i <= MAX_INITIAL_OFFSET)
1530 run_test_nodes_in_one_configuration (nodes, n_nodes, &signature,
1531 DBUS_LITTLE_ENDIAN, i);
1532 run_test_nodes_in_one_configuration (nodes, n_nodes, &signature,
1533 DBUS_BIG_ENDIAN, i);
1538 n_iterations_completed_this_test += 1;
1539 n_iterations_completed_total += 1;
1541 if (n_iterations_completed_this_test == n_iterations_expected_this_test)
1543 fprintf (stderr, " 100%% %d this test (%d cumulative)\n",
1544 n_iterations_completed_this_test,
1545 n_iterations_completed_total);
1547 /* this happens to turn out well with mod == 1 */
1548 else if ((n_iterations_completed_this_test %
1549 (int)(n_iterations_expected_this_test / 10.0)) == 1)
1551 fprintf (stderr, " %d%% ", (int) (n_iterations_completed_this_test / (double) n_iterations_expected_this_test * 100));
1554 _dbus_string_free (&signature);
1557 #define N_VALUES (N_BASICS * N_CONTAINERS + N_BASICS)
1559 static TestTypeNode*
1560 value_generator (int *ip)
1563 const TestTypeNodeClass *child_klass;
1564 const TestTypeNodeClass *container_klass;
1565 TestTypeNode *child;
1568 _dbus_assert (i <= N_VALUES);
1574 else if (i < N_BASICS)
1576 node = node_new (basic_nodes[i]);
1580 /* imagine an array:
1581 * container 0 of basic 0
1582 * container 0 of basic 1
1583 * container 0 of basic 2
1584 * container 1 of basic 0
1585 * container 1 of basic 1
1586 * container 1 of basic 2
1590 container_klass = container_nodes[i / N_BASICS];
1591 child_klass = basic_nodes[i % N_BASICS];
1593 node = node_new (container_klass);
1594 child = node_new (child_klass);
1596 node_append_child (node, child);
1599 *ip += 1; /* increment the generator */
1605 build_body (TestTypeNode **nodes,
1608 DBusString *signature,
1613 DBusTypeReader reader;
1614 DBusTypeWriter writer;
1619 if (! node_build_signature (nodes[i], signature))
1620 _dbus_assert_not_reached ("no memory");
1625 if (!data_block_init (&block, byte_order, 0))
1626 _dbus_assert_not_reached ("no memory");
1628 data_block_init_reader_writer (&block,
1631 /* DBusTypeWriter assumes it's writing into an existing signature,
1632 * so doesn't add nul on its own. We have to do that.
1634 if (!_dbus_string_insert_byte (&block.signature,
1636 _dbus_assert_not_reached ("no memory");
1641 if (!node_write_value (nodes[i], &block, &writer, i))
1642 _dbus_assert_not_reached ("no memory");
1647 if (!_dbus_string_copy_len (&block.body, 0,
1648 _dbus_string_get_length (&block.body) - N_FENCE_BYTES,
1650 _dbus_assert_not_reached ("oom");
1652 data_block_free (&block);
1656 dbus_internal_do_not_use_generate_bodies (int sequence,
1658 DBusString *signature,
1661 TestTypeNode *nodes[1];
1665 nodes[0] = value_generator (&sequence);
1667 if (nodes[0] == NULL)
1672 build_body (nodes, n_nodes, byte_order, signature, body);
1678 node_destroy (nodes[i]);
1686 make_and_run_values_inside_container (const TestTypeNodeClass *container_klass,
1690 TestTypeNode *container;
1691 TestTypeNode *child;
1694 root = node_new (container_klass);
1696 for (i = 1; i < n_nested; i++)
1698 child = node_new (container_klass);
1699 node_append_child (container, child);
1703 /* container should now be the most-nested container */
1706 while ((child = value_generator (&i)))
1708 node_append_child (container, child);
1710 run_test_nodes (&root, 1);
1712 _dbus_list_clear (&((TestTypeNodeContainer*)container)->children);
1713 node_destroy (child);
1716 node_destroy (root);
1720 start_next_test (const char *format,
1723 n_iterations_completed_this_test = 0;
1724 n_iterations_expected_this_test = expected;
1726 fprintf (stderr, ">>> >>> ");
1727 fprintf (stderr, format,
1728 n_iterations_expected_this_test);
1732 make_and_run_test_nodes (void)
1736 /* We try to do this in order of "complicatedness" so that test
1737 * failures tend to show up in the simplest test case that
1738 * demonstrates the failure. There are also some tests that run
1739 * more than once for this reason, first while going through simple
1740 * cases, second while going through a broader range of complex
1743 /* Each basic node. The basic nodes should include:
1745 * - each fixed-size type (in such a way that it has different values each time,
1746 * so we can tell if we mix two of them up)
1747 * - strings of various lengths
1751 /* Each container node. The container nodes should include:
1753 * struct with 1 and 2 copies of the contained item
1754 * array with 0, 1, 2 copies of the contained item
1757 /* Let a "value" be a basic node, or a container containing a single basic node.
1758 * Let n_values be the number of such values i.e. (n_container * n_basic + n_basic)
1759 * When iterating through all values to make combinations, do the basic types
1760 * first and the containers second.
1762 /* Each item is shown with its number of iterations to complete so
1763 * we can keep a handle on this unit test
1766 /* FIXME test just an empty body, no types at all */
1768 start_next_test ("Each value by itself %d iterations\n", N_VALUES);
1772 while ((node = value_generator (&i)))
1774 run_test_nodes (&node, 1);
1776 node_destroy (node);
1780 start_next_test ("Each value by itself with arrays as blocks %d iterations\n", N_VALUES);
1781 arrays_write_fixed_in_blocks = TRUE;
1785 while ((node = value_generator (&i)))
1787 run_test_nodes (&node, 1);
1789 node_destroy (node);
1792 arrays_write_fixed_in_blocks = FALSE;
1794 start_next_test ("All values in one big toplevel %d iteration\n", 1);
1796 TestTypeNode *nodes[N_VALUES];
1799 while ((nodes[i] = value_generator (&i)))
1802 run_test_nodes (nodes, N_VALUES);
1804 for (i = 0; i < N_VALUES; i++)
1805 node_destroy (nodes[i]);
1808 start_next_test ("Each value,value pair combination as toplevel, in both orders %d iterations\n",
1809 N_VALUES * N_VALUES);
1811 TestTypeNode *nodes[2];
1814 while ((nodes[0] = value_generator (&i)))
1817 while ((nodes[1] = value_generator (&j)))
1819 run_test_nodes (nodes, 2);
1821 node_destroy (nodes[1]);
1824 node_destroy (nodes[0]);
1828 start_next_test ("Each container containing each value %d iterations\n",
1829 N_CONTAINERS * N_VALUES);
1830 for (i = 0; i < N_CONTAINERS; i++)
1832 const TestTypeNodeClass *container_klass = container_nodes[i];
1834 make_and_run_values_inside_container (container_klass, 1);
1837 start_next_test ("Each container containing each value with arrays as blocks %d iterations\n",
1838 N_CONTAINERS * N_VALUES);
1839 arrays_write_fixed_in_blocks = TRUE;
1840 for (i = 0; i < N_CONTAINERS; i++)
1842 const TestTypeNodeClass *container_klass = container_nodes[i];
1844 make_and_run_values_inside_container (container_klass, 1);
1846 arrays_write_fixed_in_blocks = FALSE;
1848 start_next_test ("Each container of same container of each value %d iterations\n",
1849 N_CONTAINERS * N_VALUES);
1850 for (i = 0; i < N_CONTAINERS; i++)
1852 const TestTypeNodeClass *container_klass = container_nodes[i];
1854 make_and_run_values_inside_container (container_klass, 2);
1857 start_next_test ("Each container of same container of same container of each value %d iterations\n",
1858 N_CONTAINERS * N_VALUES);
1859 for (i = 0; i < N_CONTAINERS; i++)
1861 const TestTypeNodeClass *container_klass = container_nodes[i];
1863 make_and_run_values_inside_container (container_klass, 3);
1866 start_next_test ("Each value,value pair inside a struct %d iterations\n",
1867 N_VALUES * N_VALUES);
1869 TestTypeNode *val1, *val2;
1872 node = node_new (&struct_1_class);
1875 while ((val1 = value_generator (&i)))
1878 while ((val2 = value_generator (&j)))
1880 TestTypeNodeContainer *container = (TestTypeNodeContainer*) node;
1882 node_append_child (node, val1);
1883 node_append_child (node, val2);
1885 run_test_nodes (&node, 1);
1887 _dbus_list_clear (&container->children);
1888 node_destroy (val2);
1890 node_destroy (val1);
1892 node_destroy (node);
1895 start_next_test ("All values in one big struct %d iteration\n",
1899 TestTypeNode *child;
1901 node = node_new (&struct_1_class);
1904 while ((child = value_generator (&i)))
1905 node_append_child (node, child);
1907 run_test_nodes (&node, 1);
1909 node_destroy (node);
1912 start_next_test ("Each value in a large array %d iterations\n",
1918 node = node_new (&array_9_class);
1921 while ((val = value_generator (&i)))
1923 TestTypeNodeContainer *container = (TestTypeNodeContainer*) node;
1925 node_append_child (node, val);
1927 run_test_nodes (&node, 1);
1929 _dbus_list_clear (&container->children);
1933 node_destroy (node);
1936 start_next_test ("Each container of each container of each value %d iterations\n",
1937 N_CONTAINERS * N_CONTAINERS * N_VALUES);
1938 for (i = 0; i < N_CONTAINERS; i++)
1940 const TestTypeNodeClass *outer_container_klass = container_nodes[i];
1941 TestTypeNode *outer_container = node_new (outer_container_klass);
1943 for (j = 0; j < N_CONTAINERS; j++)
1945 TestTypeNode *child;
1946 const TestTypeNodeClass *inner_container_klass = container_nodes[j];
1947 TestTypeNode *inner_container = node_new (inner_container_klass);
1949 node_append_child (outer_container, inner_container);
1952 while ((child = value_generator (&m)))
1954 node_append_child (inner_container, child);
1956 run_test_nodes (&outer_container, 1);
1958 _dbus_list_clear (&((TestTypeNodeContainer*)inner_container)->children);
1959 node_destroy (child);
1961 _dbus_list_clear (&((TestTypeNodeContainer*)outer_container)->children);
1962 node_destroy (inner_container);
1964 node_destroy (outer_container);
1967 start_next_test ("Each container of each container of each container of each value %d iterations\n",
1968 N_CONTAINERS * N_CONTAINERS * N_CONTAINERS * N_VALUES);
1969 for (i = 0; i < N_CONTAINERS; i++)
1971 const TestTypeNodeClass *outer_container_klass = container_nodes[i];
1972 TestTypeNode *outer_container = node_new (outer_container_klass);
1974 for (j = 0; j < N_CONTAINERS; j++)
1976 const TestTypeNodeClass *inner_container_klass = container_nodes[j];
1977 TestTypeNode *inner_container = node_new (inner_container_klass);
1979 node_append_child (outer_container, inner_container);
1981 for (k = 0; k < N_CONTAINERS; k++)
1983 TestTypeNode *child;
1984 const TestTypeNodeClass *center_container_klass = container_nodes[k];
1985 TestTypeNode *center_container = node_new (center_container_klass);
1987 node_append_child (inner_container, center_container);
1990 while ((child = value_generator (&m)))
1992 node_append_child (center_container, child);
1994 run_test_nodes (&outer_container, 1);
1996 _dbus_list_clear (&((TestTypeNodeContainer*)center_container)->children);
1997 node_destroy (child);
1999 _dbus_list_clear (&((TestTypeNodeContainer*)inner_container)->children);
2000 node_destroy (center_container);
2002 _dbus_list_clear (&((TestTypeNodeContainer*)outer_container)->children);
2003 node_destroy (inner_container);
2005 node_destroy (outer_container);
2009 /* This one takes a really long time, so comment it out for now */
2010 start_next_test ("Each value,value,value triplet combination as toplevel, in all orders %d iterations\n",
2011 N_VALUES * N_VALUES * N_VALUES);
2013 TestTypeNode *nodes[3];
2016 while ((nodes[0] = value_generator (&i)))
2019 while ((nodes[1] = value_generator (&j)))
2022 while ((nodes[2] = value_generator (&k)))
2024 run_test_nodes (nodes, 3);
2026 node_destroy (nodes[2]);
2028 node_destroy (nodes[1]);
2030 node_destroy (nodes[0]);
2033 #endif /* #if 0 expensive test */
2035 fprintf (stderr, "%d total iterations of recursive marshaling tests\n",
2036 n_iterations_completed_total);
2037 fprintf (stderr, "each iteration ran at initial offsets 0 through %d in both big and little endian\n",
2038 MAX_INITIAL_OFFSET);
2039 fprintf (stderr, "out of memory handling %s tested\n",
2040 TEST_OOM_HANDLING ? "was" : "was not");
2044 _dbus_marshal_recursive_test (void)
2046 make_and_run_test_nodes ();
2054 * Implementations of each type node class
2059 #define MAX_MULTI_COUNT 5
2061 #define SAMPLE_INT16 1234
2062 #define SAMPLE_INT16_ALTERNATE 6785
2064 int16_from_seed (int seed)
2066 /* Generate an integer value that's predictable from seed. We could
2067 * just use seed itself, but that would only ever touch one byte of
2068 * the int so would miss some kinds of bug.
2072 v = 42; /* just to quiet compiler afaik */
2079 v = SAMPLE_INT16_ALTERNATE;
2085 v = _DBUS_INT16_MAX;
2093 v *= seed; /* wraps around eventually, which is fine */
2099 int16_write_value (TestTypeNode *node,
2101 DBusTypeWriter *writer,
2104 /* also used for uint16 */
2107 v = int16_from_seed (seed);
2109 return _dbus_type_writer_write_basic (writer,
2110 node->klass->typecode,
2115 int16_read_value (TestTypeNode *node,
2116 DBusTypeReader *reader,
2119 /* also used for uint16 */
2122 check_expected_type (reader, node->klass->typecode);
2124 _dbus_type_reader_read_basic (reader,
2125 (dbus_int16_t*) &v);
2127 _dbus_assert (v == int16_from_seed (seed));
2133 int16_set_value (TestTypeNode *node,
2134 DBusTypeReader *reader,
2135 DBusTypeReader *realign_root,
2138 /* also used for uint16 */
2141 v = int16_from_seed (seed);
2143 return _dbus_type_reader_set_basic (reader,
2149 int16_write_multi (TestTypeNode *node,
2151 DBusTypeWriter *writer,
2155 /* also used for uint16 */
2156 dbus_int16_t values[MAX_MULTI_COUNT];
2157 dbus_int16_t *v_ARRAY_INT16 = values;
2160 for (i = 0; i < count; ++i)
2161 values[i] = int16_from_seed (seed + i);
2163 return _dbus_type_writer_write_fixed_multi (writer,
2164 node->klass->typecode,
2165 &v_ARRAY_INT16, count);
2169 int16_read_multi (TestTypeNode *node,
2170 DBusTypeReader *reader,
2174 /* also used for uint16 */
2175 dbus_int16_t *values;
2179 check_expected_type (reader, node->klass->typecode);
2181 _dbus_type_reader_read_fixed_multi (reader,
2185 if (n_elements != count)
2186 _dbus_warn ("got %d elements expected %d\n", n_elements, count);
2187 _dbus_assert (n_elements == count);
2189 for (i = 0; i < count; i++)
2190 _dbus_assert (((dbus_int16_t)_dbus_unpack_uint16 (reader->byte_order,
2191 (const unsigned char*)values + (i * 2))) ==
2192 int16_from_seed (seed + i));
2198 #define SAMPLE_INT32 12345678
2199 #define SAMPLE_INT32_ALTERNATE 53781429
2201 int32_from_seed (int seed)
2203 /* Generate an integer value that's predictable from seed. We could
2204 * just use seed itself, but that would only ever touch one byte of
2205 * the int so would miss some kinds of bug.
2209 v = 42; /* just to quiet compiler afaik */
2216 v = SAMPLE_INT32_ALTERNATE;
2230 v *= seed; /* wraps around eventually, which is fine */
2236 int32_write_value (TestTypeNode *node,
2238 DBusTypeWriter *writer,
2241 /* also used for uint32 */
2244 v = int32_from_seed (seed);
2246 return _dbus_type_writer_write_basic (writer,
2247 node->klass->typecode,
2252 int32_read_value (TestTypeNode *node,
2253 DBusTypeReader *reader,
2256 /* also used for uint32 */
2259 check_expected_type (reader, node->klass->typecode);
2261 _dbus_type_reader_read_basic (reader,
2262 (dbus_int32_t*) &v);
2264 _dbus_assert (v == int32_from_seed (seed));
2270 int32_set_value (TestTypeNode *node,
2271 DBusTypeReader *reader,
2272 DBusTypeReader *realign_root,
2275 /* also used for uint32 */
2278 v = int32_from_seed (seed);
2280 return _dbus_type_reader_set_basic (reader,
2286 int32_write_multi (TestTypeNode *node,
2288 DBusTypeWriter *writer,
2292 /* also used for uint32 */
2293 dbus_int32_t values[MAX_MULTI_COUNT];
2294 dbus_int32_t *v_ARRAY_INT32 = values;
2297 for (i = 0; i < count; ++i)
2298 values[i] = int32_from_seed (seed + i);
2300 return _dbus_type_writer_write_fixed_multi (writer,
2301 node->klass->typecode,
2302 &v_ARRAY_INT32, count);
2306 int32_read_multi (TestTypeNode *node,
2307 DBusTypeReader *reader,
2311 /* also used for uint32 */
2312 dbus_int32_t *values;
2316 check_expected_type (reader, node->klass->typecode);
2318 _dbus_type_reader_read_fixed_multi (reader,
2322 if (n_elements != count)
2323 _dbus_warn ("got %d elements expected %d\n", n_elements, count);
2324 _dbus_assert (n_elements == count);
2326 for (i = 0; i < count; i++)
2327 _dbus_assert (((int)_dbus_unpack_uint32 (reader->byte_order,
2328 (const unsigned char*)values + (i * 4))) ==
2329 int32_from_seed (seed + i));
2334 #ifdef DBUS_HAVE_INT64
2336 int64_from_seed (int seed)
2341 v32 = int32_from_seed (seed);
2343 v = - (dbus_int32_t) ~ v32;
2344 v |= (((dbus_int64_t)v32) << 32);
2351 int64_write_value (TestTypeNode *node,
2353 DBusTypeWriter *writer,
2356 #ifdef DBUS_HAVE_INT64
2357 /* also used for uint64 */
2360 v = int64_from_seed (seed);
2362 return _dbus_type_writer_write_basic (writer,
2363 node->klass->typecode,
2371 int64_read_value (TestTypeNode *node,
2372 DBusTypeReader *reader,
2375 #ifdef DBUS_HAVE_INT64
2376 /* also used for uint64 */
2379 check_expected_type (reader, node->klass->typecode);
2381 _dbus_type_reader_read_basic (reader,
2382 (dbus_int64_t*) &v);
2384 _dbus_assert (v == int64_from_seed (seed));
2393 int64_set_value (TestTypeNode *node,
2394 DBusTypeReader *reader,
2395 DBusTypeReader *realign_root,
2398 #ifdef DBUS_HAVE_INT64
2399 /* also used for uint64 */
2402 v = int64_from_seed (seed);
2404 return _dbus_type_reader_set_basic (reader,
2412 #define MAX_SAMPLE_STRING_LEN 10
2414 string_from_seed (char *buf,
2421 _dbus_assert (len < MAX_SAMPLE_STRING_LEN);
2423 /* vary the length slightly, though we also have multiple string
2424 * value types for this, varying it here tests the set_value code
2438 v = (unsigned char) ('A' + seed);
2443 if (v < 'A' || v > 'z')
2456 string_write_value (TestTypeNode *node,
2458 DBusTypeWriter *writer,
2461 char buf[MAX_SAMPLE_STRING_LEN];
2462 const char *v_string = buf;
2464 string_from_seed (buf, node->klass->subclass_detail,
2467 return _dbus_type_writer_write_basic (writer,
2468 node->klass->typecode,
2473 string_read_value (TestTypeNode *node,
2474 DBusTypeReader *reader,
2478 char buf[MAX_SAMPLE_STRING_LEN];
2480 check_expected_type (reader, node->klass->typecode);
2482 _dbus_type_reader_read_basic (reader,
2483 (const char **) &v);
2485 string_from_seed (buf, node->klass->subclass_detail,
2488 if (strcmp (buf, v) != 0)
2490 _dbus_warn ("read string '%s' expected '%s'\n",
2492 _dbus_assert_not_reached ("test failed");
2499 string_set_value (TestTypeNode *node,
2500 DBusTypeReader *reader,
2501 DBusTypeReader *realign_root,
2504 char buf[MAX_SAMPLE_STRING_LEN];
2505 const char *v_string = buf;
2507 string_from_seed (buf, node->klass->subclass_detail,
2510 #if RECURSIVE_MARSHAL_WRITE_TRACE
2513 _dbus_type_reader_read_basic (reader, &old);
2514 _dbus_verbose ("SETTING new string '%s' len %d in place of '%s' len %d\n",
2515 v_string, strlen (v_string), old, strlen (old));
2519 return _dbus_type_reader_set_basic (reader,
2524 #define BOOL_FROM_SEED(seed) ((dbus_bool_t)((seed) % 2))
2527 bool_write_value (TestTypeNode *node,
2529 DBusTypeWriter *writer,
2534 v = BOOL_FROM_SEED (seed);
2536 return _dbus_type_writer_write_basic (writer,
2537 node->klass->typecode,
2542 bool_read_value (TestTypeNode *node,
2543 DBusTypeReader *reader,
2548 check_expected_type (reader, node->klass->typecode);
2550 _dbus_type_reader_read_basic (reader,
2551 (unsigned char*) &v);
2553 _dbus_assert (v == BOOL_FROM_SEED (seed));
2559 bool_set_value (TestTypeNode *node,
2560 DBusTypeReader *reader,
2561 DBusTypeReader *realign_root,
2566 v = BOOL_FROM_SEED (seed);
2568 return _dbus_type_reader_set_basic (reader,
2573 #define BYTE_FROM_SEED(seed) ((unsigned char) int32_from_seed (seed))
2576 byte_write_value (TestTypeNode *node,
2578 DBusTypeWriter *writer,
2583 v = BYTE_FROM_SEED (seed);
2585 return _dbus_type_writer_write_basic (writer,
2586 node->klass->typecode,
2591 byte_read_value (TestTypeNode *node,
2592 DBusTypeReader *reader,
2597 check_expected_type (reader, node->klass->typecode);
2599 _dbus_type_reader_read_basic (reader,
2600 (unsigned char*) &v);
2602 _dbus_assert (v == BYTE_FROM_SEED (seed));
2609 byte_set_value (TestTypeNode *node,
2610 DBusTypeReader *reader,
2611 DBusTypeReader *realign_root,
2616 v = BYTE_FROM_SEED (seed);
2618 return _dbus_type_reader_set_basic (reader,
2624 double_from_seed (int seed)
2626 return SAMPLE_INT32 * (double) seed + 0.3;
2630 double_write_value (TestTypeNode *node,
2632 DBusTypeWriter *writer,
2637 v = double_from_seed (seed);
2639 return _dbus_type_writer_write_basic (writer,
2640 node->klass->typecode,
2645 double_read_value (TestTypeNode *node,
2646 DBusTypeReader *reader,
2652 check_expected_type (reader, node->klass->typecode);
2654 _dbus_type_reader_read_basic (reader,
2657 expected = double_from_seed (seed);
2659 if (!_DBUS_DOUBLES_BITWISE_EQUAL (v, expected))
2661 #ifdef DBUS_HAVE_INT64
2662 _dbus_warn ("Expected double %g got %g\n bits = 0x%llx vs.\n bits = 0x%llx)\n",
2664 *(dbus_uint64_t*)(char*)&expected,
2665 *(dbus_uint64_t*)(char*)&v);
2667 _dbus_assert_not_reached ("test failed");
2674 double_set_value (TestTypeNode *node,
2675 DBusTypeReader *reader,
2676 DBusTypeReader *realign_root,
2681 v = double_from_seed (seed);
2683 return _dbus_type_reader_set_basic (reader,
2688 #define MAX_SAMPLE_OBJECT_PATH_LEN 10
2690 object_path_from_seed (char *buf,
2698 _dbus_assert (len < MAX_SAMPLE_OBJECT_PATH_LEN);
2700 v = (unsigned char) ('A' + seed);
2712 if (v < 'A' || v > 'z')
2728 object_path_write_value (TestTypeNode *node,
2730 DBusTypeWriter *writer,
2733 char buf[MAX_SAMPLE_OBJECT_PATH_LEN];
2734 const char *v_string = buf;
2736 object_path_from_seed (buf, seed);
2738 return _dbus_type_writer_write_basic (writer,
2739 node->klass->typecode,
2744 object_path_read_value (TestTypeNode *node,
2745 DBusTypeReader *reader,
2749 char buf[MAX_SAMPLE_OBJECT_PATH_LEN];
2751 check_expected_type (reader, node->klass->typecode);
2753 _dbus_type_reader_read_basic (reader,
2754 (const char **) &v);
2756 object_path_from_seed (buf, seed);
2758 if (strcmp (buf, v) != 0)
2760 _dbus_warn ("read object path '%s' expected '%s'\n",
2762 _dbus_assert_not_reached ("test failed");
2769 object_path_set_value (TestTypeNode *node,
2770 DBusTypeReader *reader,
2771 DBusTypeReader *realign_root,
2774 char buf[MAX_SAMPLE_OBJECT_PATH_LEN];
2775 const char *v_string = buf;
2777 object_path_from_seed (buf, seed);
2779 return _dbus_type_reader_set_basic (reader,
2784 #define MAX_SAMPLE_SIGNATURE_LEN 10
2786 signature_from_seed (char *buf,
2791 /* try to avoid ascending, descending, or alternating length to help find bugs */
2792 const char *sample_signatures[] = {
2801 s = sample_signatures[seed % _DBUS_N_ELEMENTS(sample_signatures)];
2803 for (i = 0; s[i]; i++)
2811 signature_write_value (TestTypeNode *node,
2813 DBusTypeWriter *writer,
2816 char buf[MAX_SAMPLE_SIGNATURE_LEN];
2817 const char *v_string = buf;
2819 signature_from_seed (buf, seed);
2821 return _dbus_type_writer_write_basic (writer,
2822 node->klass->typecode,
2827 signature_read_value (TestTypeNode *node,
2828 DBusTypeReader *reader,
2832 char buf[MAX_SAMPLE_SIGNATURE_LEN];
2834 check_expected_type (reader, node->klass->typecode);
2836 _dbus_type_reader_read_basic (reader,
2837 (const char **) &v);
2839 signature_from_seed (buf, seed);
2841 if (strcmp (buf, v) != 0)
2843 _dbus_warn ("read signature value '%s' expected '%s'\n",
2845 _dbus_assert_not_reached ("test failed");
2853 signature_set_value (TestTypeNode *node,
2854 DBusTypeReader *reader,
2855 DBusTypeReader *realign_root,
2858 char buf[MAX_SAMPLE_SIGNATURE_LEN];
2859 const char *v_string = buf;
2861 signature_from_seed (buf, seed);
2863 return _dbus_type_reader_set_basic (reader,
2869 struct_write_value (TestTypeNode *node,
2871 DBusTypeWriter *writer,
2874 TestTypeNodeContainer *container = (TestTypeNodeContainer*) node;
2875 DataBlockState saved;
2880 n_copies = node->klass->subclass_detail;
2882 _dbus_assert (container->children != NULL);
2884 data_block_save (block, &saved);
2886 if (!_dbus_type_writer_recurse (writer, DBUS_TYPE_STRUCT,
2892 while (i < n_copies)
2896 link = _dbus_list_get_first_link (&container->children);
2897 while (link != NULL)
2899 TestTypeNode *child = link->data;
2900 DBusList *next = _dbus_list_get_next_link (&container->children, link);
2902 if (!node_write_value (child, block, &sub, seed + i))
2904 data_block_restore (block, &saved);
2914 if (!_dbus_type_writer_unrecurse (writer, &sub))
2916 data_block_restore (block, &saved);
2924 struct_read_or_set_value (TestTypeNode *node,
2925 DBusTypeReader *reader,
2926 DBusTypeReader *realign_root,
2929 TestTypeNodeContainer *container = (TestTypeNodeContainer*) node;
2934 n_copies = node->klass->subclass_detail;
2936 check_expected_type (reader, DBUS_TYPE_STRUCT);
2938 _dbus_type_reader_recurse (reader, &sub);
2941 while (i < n_copies)
2945 link = _dbus_list_get_first_link (&container->children);
2946 while (link != NULL)
2948 TestTypeNode *child = link->data;
2949 DBusList *next = _dbus_list_get_next_link (&container->children, link);
2951 if (realign_root == NULL)
2953 if (!node_read_value (child, &sub, seed + i))
2958 if (!node_set_value (child, &sub, realign_root, seed + i))
2962 if (i == (n_copies - 1) && next == NULL)
2963 NEXT_EXPECTING_FALSE (&sub);
2965 NEXT_EXPECTING_TRUE (&sub);
2977 struct_read_value (TestTypeNode *node,
2978 DBusTypeReader *reader,
2981 return struct_read_or_set_value (node, reader, NULL, seed);
2985 struct_set_value (TestTypeNode *node,
2986 DBusTypeReader *reader,
2987 DBusTypeReader *realign_root,
2990 return struct_read_or_set_value (node, reader, realign_root, seed);
2994 struct_build_signature (TestTypeNode *node,
2997 TestTypeNodeContainer *container = (TestTypeNodeContainer*) node;
3002 n_copies = node->klass->subclass_detail;
3004 orig_len = _dbus_string_get_length (str);
3006 if (!_dbus_string_append_byte (str, DBUS_STRUCT_BEGIN_CHAR))
3010 while (i < n_copies)
3014 link = _dbus_list_get_first_link (&container->children);
3015 while (link != NULL)
3017 TestTypeNode *child = link->data;
3018 DBusList *next = _dbus_list_get_next_link (&container->children, link);
3020 if (!node_build_signature (child, str))
3029 if (!_dbus_string_append_byte (str, DBUS_STRUCT_END_CHAR))
3035 _dbus_string_set_length (str, orig_len);
3040 array_write_value (TestTypeNode *node,
3042 DBusTypeWriter *writer,
3045 TestTypeNodeContainer *container = (TestTypeNodeContainer*) node;
3046 DataBlockState saved;
3048 DBusString element_signature;
3052 TestTypeNode *child;
3054 n_copies = node->klass->subclass_detail;
3056 _dbus_assert (container->children != NULL);
3058 data_block_save (block, &saved);
3060 if (!_dbus_string_init (&element_signature))
3063 child = _dbus_list_get_first (&container->children);
3065 if (!node_build_signature (child,
3066 &element_signature))
3069 element_type = _dbus_first_type_in_signature (&element_signature, 0);
3071 if (!_dbus_type_writer_recurse (writer, DBUS_TYPE_ARRAY,
3072 &element_signature, 0,
3076 if (arrays_write_fixed_in_blocks &&
3077 dbus_type_is_fixed (element_type) &&
3078 child->klass->write_multi)
3080 if (!node_write_multi (child, block, &sub, seed, n_copies))
3086 while (i < n_copies)
3090 link = _dbus_list_get_first_link (&container->children);
3091 while (link != NULL)
3093 TestTypeNode *child = link->data;
3094 DBusList *next = _dbus_list_get_next_link (&container->children, link);
3096 if (!node_write_value (child, block, &sub, seed + i))
3106 if (!_dbus_type_writer_unrecurse (writer, &sub))
3109 _dbus_string_free (&element_signature);
3113 data_block_restore (block, &saved);
3114 _dbus_string_free (&element_signature);
3119 array_read_or_set_value (TestTypeNode *node,
3120 DBusTypeReader *reader,
3121 DBusTypeReader *realign_root,
3124 TestTypeNodeContainer *container = (TestTypeNodeContainer*) node;
3128 TestTypeNode *child;
3130 n_copies = node->klass->subclass_detail;
3132 check_expected_type (reader, DBUS_TYPE_ARRAY);
3134 child = _dbus_list_get_first (&container->children);
3138 _dbus_type_reader_recurse (reader, &sub);
3140 if (realign_root == NULL && arrays_write_fixed_in_blocks &&
3141 dbus_type_is_fixed (_dbus_type_reader_get_element_type (reader)) &&
3142 child->klass->read_multi)
3144 if (!node_read_multi (child, &sub, seed, n_copies))
3150 while (i < n_copies)
3154 link = _dbus_list_get_first_link (&container->children);
3155 while (link != NULL)
3157 TestTypeNode *child = link->data;
3158 DBusList *next = _dbus_list_get_next_link (&container->children, link);
3160 _dbus_assert (child->klass->typecode ==
3161 _dbus_type_reader_get_element_type (reader));
3163 if (realign_root == NULL)
3165 if (!node_read_value (child, &sub, seed + i))
3170 if (!node_set_value (child, &sub, realign_root, seed + i))
3174 if (i == (n_copies - 1) && next == NULL)
3175 NEXT_EXPECTING_FALSE (&sub);
3177 NEXT_EXPECTING_TRUE (&sub);
3191 array_read_value (TestTypeNode *node,
3192 DBusTypeReader *reader,
3195 return array_read_or_set_value (node, reader, NULL, seed);
3199 array_set_value (TestTypeNode *node,
3200 DBusTypeReader *reader,
3201 DBusTypeReader *realign_root,
3204 return array_read_or_set_value (node, reader, realign_root, seed);
3208 array_build_signature (TestTypeNode *node,
3211 TestTypeNodeContainer *container = (TestTypeNodeContainer*) node;
3214 orig_len = _dbus_string_get_length (str);
3216 if (!_dbus_string_append_byte (str, DBUS_TYPE_ARRAY))
3219 if (!node_build_signature (_dbus_list_get_first (&container->children),
3226 _dbus_string_set_length (str, orig_len);
3230 /* 10 is random just to add another seed that we use in the suite */
3231 #define VARIANT_SEED 10
3234 variant_write_value (TestTypeNode *node,
3236 DBusTypeWriter *writer,
3239 TestTypeNodeContainer *container = (TestTypeNodeContainer*) node;
3240 DataBlockState saved;
3242 DBusString content_signature;
3243 TestTypeNode *child;
3245 _dbus_assert (container->children != NULL);
3246 _dbus_assert (_dbus_list_length_is_one (&container->children));
3248 child = _dbus_list_get_first (&container->children);
3250 data_block_save (block, &saved);
3252 if (!_dbus_string_init (&content_signature))
3255 if (!node_build_signature (child,
3256 &content_signature))
3259 if (!_dbus_type_writer_recurse (writer, DBUS_TYPE_VARIANT,
3260 &content_signature, 0,
3264 if (!node_write_value (child, block, &sub, seed + VARIANT_SEED))
3267 if (!_dbus_type_writer_unrecurse (writer, &sub))
3270 _dbus_string_free (&content_signature);
3274 data_block_restore (block, &saved);
3275 _dbus_string_free (&content_signature);
3280 variant_read_or_set_value (TestTypeNode *node,
3281 DBusTypeReader *reader,
3282 DBusTypeReader *realign_root,
3285 TestTypeNodeContainer *container = (TestTypeNodeContainer*) node;
3287 TestTypeNode *child;
3289 _dbus_assert (container->children != NULL);
3290 _dbus_assert (_dbus_list_length_is_one (&container->children));
3292 child = _dbus_list_get_first (&container->children);
3294 check_expected_type (reader, DBUS_TYPE_VARIANT);
3296 _dbus_type_reader_recurse (reader, &sub);
3298 if (realign_root == NULL)
3300 if (!node_read_value (child, &sub, seed + VARIANT_SEED))
3305 if (!node_set_value (child, &sub, realign_root, seed + VARIANT_SEED))
3309 NEXT_EXPECTING_FALSE (&sub);
3315 variant_read_value (TestTypeNode *node,
3316 DBusTypeReader *reader,
3319 return variant_read_or_set_value (node, reader, NULL, seed);
3323 variant_set_value (TestTypeNode *node,
3324 DBusTypeReader *reader,
3325 DBusTypeReader *realign_root,
3328 return variant_read_or_set_value (node, reader, realign_root, seed);
3332 dict_write_value (TestTypeNode *node,
3334 DBusTypeWriter *writer,
3337 TestTypeNodeContainer *container = (TestTypeNodeContainer*) node;
3338 DataBlockState saved;
3340 DBusString entry_value_signature;
3341 DBusString dict_entry_signature;
3344 int entry_value_type;
3345 TestTypeNode *child;
3347 n_entries = node->klass->subclass_detail;
3349 _dbus_assert (container->children != NULL);
3351 data_block_save (block, &saved);
3353 if (!_dbus_string_init (&entry_value_signature))
3356 if (!_dbus_string_init (&dict_entry_signature))
3358 _dbus_string_free (&entry_value_signature);
3362 child = _dbus_list_get_first (&container->children);
3364 if (!node_build_signature (child,
3365 &entry_value_signature))
3368 if (!_dbus_string_append (&dict_entry_signature,
3369 DBUS_DICT_ENTRY_BEGIN_CHAR_AS_STRING
3370 DBUS_TYPE_INT32_AS_STRING))
3373 if (!_dbus_string_copy (&entry_value_signature, 0,
3374 &dict_entry_signature,
3375 _dbus_string_get_length (&dict_entry_signature)))
3378 if (!_dbus_string_append_byte (&dict_entry_signature,
3379 DBUS_DICT_ENTRY_END_CHAR))
3382 entry_value_type = _dbus_first_type_in_signature (&entry_value_signature, 0);
3384 if (!_dbus_type_writer_recurse (writer, DBUS_TYPE_ARRAY,
3385 &dict_entry_signature, 0,
3390 while (i < n_entries)
3392 DBusTypeWriter entry_sub;
3395 if (!_dbus_type_writer_recurse (&sub, DBUS_TYPE_DICT_ENTRY,
3400 key = int32_from_seed (seed + i);
3402 if (!_dbus_type_writer_write_basic (&entry_sub,
3407 if (!node_write_value (child, block, &entry_sub, seed + i))
3410 if (!_dbus_type_writer_unrecurse (&sub, &entry_sub))
3416 if (!_dbus_type_writer_unrecurse (writer, &sub))
3419 _dbus_string_free (&entry_value_signature);
3420 _dbus_string_free (&dict_entry_signature);
3424 data_block_restore (block, &saved);
3425 _dbus_string_free (&entry_value_signature);
3426 _dbus_string_free (&dict_entry_signature);
3431 dict_read_or_set_value (TestTypeNode *node,
3432 DBusTypeReader *reader,
3433 DBusTypeReader *realign_root,
3436 TestTypeNodeContainer *container = (TestTypeNodeContainer*) node;
3440 TestTypeNode *child;
3442 n_entries = node->klass->subclass_detail;
3444 check_expected_type (reader, DBUS_TYPE_ARRAY);
3446 child = _dbus_list_get_first (&container->children);
3450 _dbus_type_reader_recurse (reader, &sub);
3452 check_expected_type (&sub, DBUS_TYPE_DICT_ENTRY);
3455 while (i < n_entries)
3457 DBusTypeReader entry_sub;
3459 check_expected_type (&sub, DBUS_TYPE_DICT_ENTRY);
3461 _dbus_type_reader_recurse (&sub, &entry_sub);
3463 if (realign_root == NULL)
3467 check_expected_type (&entry_sub, DBUS_TYPE_INT32);
3469 _dbus_type_reader_read_basic (&entry_sub,
3470 (dbus_int32_t*) &v);
3472 _dbus_assert (v == int32_from_seed (seed + i));
3474 NEXT_EXPECTING_TRUE (&entry_sub);
3476 if (!node_read_value (child, &entry_sub, seed + i))
3479 NEXT_EXPECTING_FALSE (&entry_sub);
3485 v = int32_from_seed (seed + i);
3487 if (!_dbus_type_reader_set_basic (&entry_sub,
3492 NEXT_EXPECTING_TRUE (&entry_sub);
3494 if (!node_set_value (child, &entry_sub, realign_root, seed + i))
3497 NEXT_EXPECTING_FALSE (&entry_sub);
3500 if (i == (n_entries - 1))
3501 NEXT_EXPECTING_FALSE (&sub);
3503 NEXT_EXPECTING_TRUE (&sub);
3513 dict_read_value (TestTypeNode *node,
3514 DBusTypeReader *reader,
3517 return dict_read_or_set_value (node, reader, NULL, seed);
3521 dict_set_value (TestTypeNode *node,
3522 DBusTypeReader *reader,
3523 DBusTypeReader *realign_root,
3526 return dict_read_or_set_value (node, reader, realign_root, seed);
3530 dict_build_signature (TestTypeNode *node,
3533 TestTypeNodeContainer *container = (TestTypeNodeContainer*) node;
3536 orig_len = _dbus_string_get_length (str);
3538 if (!_dbus_string_append_byte (str, DBUS_TYPE_ARRAY))
3541 if (!_dbus_string_append (str, DBUS_DICT_ENTRY_BEGIN_CHAR_AS_STRING DBUS_TYPE_INT32_AS_STRING))
3544 if (!node_build_signature (_dbus_list_get_first (&container->children),
3548 if (!_dbus_string_append_byte (str, DBUS_DICT_ENTRY_END_CHAR))
3554 _dbus_string_set_length (str, orig_len);
3559 container_destroy (TestTypeNode *node)
3561 TestTypeNodeContainer *container = (TestTypeNodeContainer*) node;
3564 link = _dbus_list_get_first_link (&container->children);
3565 while (link != NULL)
3567 TestTypeNode *child = link->data;
3568 DBusList *next = _dbus_list_get_next_link (&container->children, link);
3570 node_destroy (child);
3572 _dbus_list_free_link (link);
3578 #endif /* DBUS_BUILD_TESTS */