00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020
00021
00022
00023 #include <config.h>
00024
00025 #ifndef DOXYGEN_SHOULD_SKIP_THIS
00026
00027 #ifdef DBUS_BUILD_TESTS
00028 #include "dbus-message-factory.h"
00029 #include "dbus-message-private.h"
00030 #include "dbus-test.h"
00031 #include <stdio.h>
00032
00033 typedef enum
00034 {
00035 CHANGE_TYPE_ADJUST,
00036 CHANGE_TYPE_ABSOLUTE
00037 } ChangeType;
00038
00039 #define BYTE_ORDER_OFFSET 0
00040 #define TYPE_OFFSET 1
00041 #define BODY_LENGTH_OFFSET 4
00042 #define FIELDS_ARRAY_LENGTH_OFFSET 12
00043
00044 static void
00045 iter_recurse (DBusMessageDataIter *iter)
00046 {
00047 iter->depth += 1;
00048 _dbus_assert (iter->depth < _DBUS_MESSAGE_DATA_MAX_NESTING);
00049 _dbus_assert (iter->sequence_nos[iter->depth] >= 0);
00050 }
00051
00052 static int
00053 iter_get_sequence (DBusMessageDataIter *iter)
00054 {
00055 _dbus_assert (iter->sequence_nos[iter->depth] >= 0);
00056 return iter->sequence_nos[iter->depth];
00057 }
00058
00059 static void
00060 iter_set_sequence (DBusMessageDataIter *iter,
00061 int sequence)
00062 {
00063 _dbus_assert (sequence >= 0);
00064 iter->sequence_nos[iter->depth] = sequence;
00065 }
00066
00067 static void
00068 iter_unrecurse (DBusMessageDataIter *iter)
00069 {
00070 iter->depth -= 1;
00071 _dbus_assert (iter->depth >= 0);
00072 }
00073
00074 static void
00075 iter_next (DBusMessageDataIter *iter)
00076 {
00077 iter->sequence_nos[iter->depth] += 1;
00078 }
00079
00080 static dbus_bool_t
00081 iter_first_in_series (DBusMessageDataIter *iter)
00082 {
00083 int i;
00084
00085 i = iter->depth;
00086 while (i < _DBUS_MESSAGE_DATA_MAX_NESTING)
00087 {
00088 if (iter->sequence_nos[i] != 0)
00089 return FALSE;
00090 ++i;
00091 }
00092 return TRUE;
00093 }
00094
00095 typedef dbus_bool_t (* DBusInnerGeneratorFunc) (DBusMessageDataIter *iter,
00096 DBusMessage **message_p);
00097 typedef dbus_bool_t (* DBusMessageGeneratorFunc) (DBusMessageDataIter *iter,
00098 DBusString *data,
00099 DBusValidity *expected_validity);
00100
00101 static void
00102 set_reply_serial (DBusMessage *message)
00103 {
00104 if (message == NULL)
00105 _dbus_assert_not_reached ("oom");
00106 if (!dbus_message_set_reply_serial (message, 100))
00107 _dbus_assert_not_reached ("oom");
00108 }
00109
00110 static dbus_bool_t
00111 generate_trivial_inner (DBusMessageDataIter *iter,
00112 DBusMessage **message_p)
00113 {
00114 DBusMessage *message;
00115
00116 switch (iter_get_sequence (iter))
00117 {
00118 case 0:
00119 message = dbus_message_new_method_call ("org.freedesktop.TextEditor",
00120 "/foo/bar",
00121 "org.freedesktop.DocumentFactory",
00122 "Create");
00123 break;
00124 case 1:
00125 message = dbus_message_new (DBUS_MESSAGE_TYPE_METHOD_RETURN);
00126 set_reply_serial (message);
00127 break;
00128 case 2:
00129 message = dbus_message_new_signal ("/foo/bar",
00130 "org.freedesktop.DocumentFactory",
00131 "Created");
00132 break;
00133 case 3:
00134 message = dbus_message_new (DBUS_MESSAGE_TYPE_ERROR);
00135
00136 if (!dbus_message_set_error_name (message,
00137 "org.freedesktop.TestErrorName"))
00138 _dbus_assert_not_reached ("oom");
00139
00140 {
00141 DBusMessageIter iter;
00142 const char *v_STRING = "This is an error";
00143
00144 dbus_message_iter_init_append (message, &iter);
00145 if (!dbus_message_iter_append_basic (&iter,
00146 DBUS_TYPE_STRING,
00147 &v_STRING))
00148 _dbus_assert_not_reached ("oom");
00149 }
00150
00151 set_reply_serial (message);
00152 break;
00153 default:
00154 return FALSE;
00155 }
00156
00157 if (message == NULL)
00158 _dbus_assert_not_reached ("oom");
00159
00160 *message_p = message;
00161
00162 return TRUE;
00163 }
00164
00165 static dbus_bool_t
00166 generate_many_bodies_inner (DBusMessageDataIter *iter,
00167 DBusMessage **message_p)
00168 {
00169 DBusMessage *message;
00170 DBusString signature;
00171 DBusString body;
00172
00173
00174 message = dbus_message_new_method_call ("o.z.F",
00175 "/",
00176 "o.z.B",
00177 "Nah");
00178 if (message == NULL)
00179 _dbus_assert_not_reached ("oom");
00180
00181 set_reply_serial (message);
00182
00183 if (!_dbus_string_init (&signature) || !_dbus_string_init (&body))
00184 _dbus_assert_not_reached ("oom");
00185
00186 if (dbus_internal_do_not_use_generate_bodies (iter_get_sequence (iter),
00187 message->byte_order,
00188 &signature, &body))
00189 {
00190 const char *v_SIGNATURE;
00191
00192 v_SIGNATURE = _dbus_string_get_const_data (&signature);
00193 if (!_dbus_header_set_field_basic (&message->header,
00194 DBUS_HEADER_FIELD_SIGNATURE,
00195 DBUS_TYPE_SIGNATURE,
00196 &v_SIGNATURE))
00197 _dbus_assert_not_reached ("oom");
00198
00199 if (!_dbus_string_move (&body, 0, &message->body, 0))
00200 _dbus_assert_not_reached ("oom");
00201
00202 _dbus_marshal_set_uint32 (&message->header.data, BODY_LENGTH_OFFSET,
00203 _dbus_string_get_length (&message->body),
00204 message->byte_order);
00205
00206 *message_p = message;
00207 }
00208 else
00209 {
00210 dbus_message_unref (message);
00211 *message_p = NULL;
00212 }
00213
00214 _dbus_string_free (&signature);
00215 _dbus_string_free (&body);
00216
00217 return *message_p != NULL;
00218 }
00219
00220 static void
00221 generate_from_message (DBusString *data,
00222 DBusValidity *expected_validity,
00223 DBusMessage *message)
00224 {
00225 _dbus_message_set_serial (message, 1);
00226 _dbus_message_lock (message);
00227
00228 *expected_validity = DBUS_VALID;
00229
00230
00231 if (!_dbus_string_move (&message->header.data, 0,
00232 data, 0))
00233 _dbus_assert_not_reached ("oom");
00234
00235 if (!_dbus_string_copy (&message->body, 0,
00236 data, _dbus_string_get_length (data)))
00237 _dbus_assert_not_reached ("oom");
00238 }
00239
00240 static dbus_bool_t
00241 generate_outer (DBusMessageDataIter *iter,
00242 DBusString *data,
00243 DBusValidity *expected_validity,
00244 DBusInnerGeneratorFunc func)
00245 {
00246 DBusMessage *message;
00247
00248 message = NULL;
00249 if (!(*func)(iter, &message))
00250 return FALSE;
00251
00252 iter_next (iter);
00253
00254 _dbus_assert (message != NULL);
00255
00256 generate_from_message (data, expected_validity, message);
00257
00258 dbus_message_unref (message);
00259
00260 return TRUE;
00261 }
00262
00263 static dbus_bool_t
00264 generate_trivial (DBusMessageDataIter *iter,
00265 DBusString *data,
00266 DBusValidity *expected_validity)
00267 {
00268 return generate_outer (iter, data, expected_validity,
00269 generate_trivial_inner);
00270 }
00271
00272 static dbus_bool_t
00273 generate_many_bodies (DBusMessageDataIter *iter,
00274 DBusString *data,
00275 DBusValidity *expected_validity)
00276 {
00277 return generate_outer (iter, data, expected_validity,
00278 generate_many_bodies_inner);
00279 }
00280
00281 static DBusMessage*
00282 simple_method_call (void)
00283 {
00284 DBusMessage *message;
00285
00286 message = dbus_message_new_method_call ("o.b.Q",
00287 "/f/b",
00288 "o.b.Z",
00289 "Fro");
00290 if (message == NULL)
00291 _dbus_assert_not_reached ("oom");
00292 return message;
00293 }
00294
00295 static DBusMessage*
00296 simple_signal (void)
00297 {
00298 DBusMessage *message;
00299 message = dbus_message_new_signal ("/f/b",
00300 "o.b.Z",
00301 "Fro");
00302 if (message == NULL)
00303 _dbus_assert_not_reached ("oom");
00304 return message;
00305 }
00306
00307 static DBusMessage*
00308 simple_method_return (void)
00309 {
00310 DBusMessage *message;
00311 message = dbus_message_new (DBUS_MESSAGE_TYPE_METHOD_RETURN);
00312 if (message == NULL)
00313 _dbus_assert_not_reached ("oom");
00314
00315 set_reply_serial (message);
00316
00317 return message;
00318 }
00319
00320 static DBusMessage*
00321 simple_error (void)
00322 {
00323 DBusMessage *message;
00324 message = dbus_message_new (DBUS_MESSAGE_TYPE_ERROR);
00325 if (message == NULL)
00326 _dbus_assert_not_reached ("oom");
00327
00328 if (!dbus_message_set_error_name (message, "foo.bar"))
00329 _dbus_assert_not_reached ("oom");
00330
00331 set_reply_serial (message);
00332
00333 return message;
00334 }
00335
00336 static dbus_bool_t
00337 generate_special (DBusMessageDataIter *iter,
00338 DBusString *data,
00339 DBusValidity *expected_validity)
00340 {
00341 int item_seq;
00342 DBusMessage *message;
00343 int pos;
00344 dbus_int32_t v_INT32;
00345
00346 _dbus_assert (_dbus_string_get_length (data) == 0);
00347
00348 message = NULL;
00349 pos = -1;
00350 v_INT32 = 42;
00351 item_seq = iter_get_sequence (iter);
00352
00353 if (item_seq == 0)
00354 {
00355 message = simple_method_call ();
00356 if (!dbus_message_append_args (message,
00357 DBUS_TYPE_INT32, &v_INT32,
00358 DBUS_TYPE_INT32, &v_INT32,
00359 DBUS_TYPE_INT32, &v_INT32,
00360 DBUS_TYPE_INVALID))
00361 _dbus_assert_not_reached ("oom");
00362
00363 _dbus_header_get_field_raw (&message->header,
00364 DBUS_HEADER_FIELD_SIGNATURE,
00365 NULL, &pos);
00366 generate_from_message (data, expected_validity, message);
00367
00368
00369 _dbus_string_set_byte (data, pos + 1, '$');
00370
00371 *expected_validity = DBUS_INVALID_UNKNOWN_TYPECODE;
00372 }
00373 else if (item_seq == 1)
00374 {
00375 char long_sig[DBUS_MAXIMUM_TYPE_RECURSION_DEPTH+2];
00376 const char *v_STRING;
00377 int i;
00378
00379 message = simple_method_call ();
00380 if (!dbus_message_append_args (message,
00381 DBUS_TYPE_INT32, &v_INT32,
00382 DBUS_TYPE_INT32, &v_INT32,
00383 DBUS_TYPE_INT32, &v_INT32,
00384 DBUS_TYPE_INVALID))
00385 _dbus_assert_not_reached ("oom");
00386
00387 i = 0;
00388 while (i < (DBUS_MAXIMUM_TYPE_RECURSION_DEPTH + 1))
00389 {
00390 long_sig[i] = DBUS_TYPE_ARRAY;
00391 ++i;
00392 }
00393 long_sig[i] = DBUS_TYPE_INVALID;
00394
00395 v_STRING = long_sig;
00396 if (!_dbus_header_set_field_basic (&message->header,
00397 DBUS_HEADER_FIELD_SIGNATURE,
00398 DBUS_TYPE_SIGNATURE,
00399 &v_STRING))
00400 _dbus_assert_not_reached ("oom");
00401
00402 _dbus_header_get_field_raw (&message->header,
00403 DBUS_HEADER_FIELD_SIGNATURE,
00404 NULL, &pos);
00405 generate_from_message (data, expected_validity, message);
00406
00407 *expected_validity = DBUS_INVALID_EXCEEDED_MAXIMUM_ARRAY_RECURSION;
00408 }
00409 else if (item_seq == 2)
00410 {
00411 char long_sig[DBUS_MAXIMUM_TYPE_RECURSION_DEPTH*2+4];
00412 const char *v_STRING;
00413 int i;
00414
00415 message = simple_method_call ();
00416 if (!dbus_message_append_args (message,
00417 DBUS_TYPE_INT32, &v_INT32,
00418 DBUS_TYPE_INT32, &v_INT32,
00419 DBUS_TYPE_INT32, &v_INT32,
00420 DBUS_TYPE_INVALID))
00421 _dbus_assert_not_reached ("oom");
00422
00423 i = 0;
00424 while (i <= (DBUS_MAXIMUM_TYPE_RECURSION_DEPTH + 1))
00425 {
00426 long_sig[i] = DBUS_STRUCT_BEGIN_CHAR;
00427 ++i;
00428 }
00429
00430 long_sig[i] = DBUS_TYPE_INT32;
00431 ++i;
00432
00433 while (i < (DBUS_MAXIMUM_TYPE_RECURSION_DEPTH*2 + 3))
00434 {
00435 long_sig[i] = DBUS_STRUCT_END_CHAR;
00436 ++i;
00437 }
00438 long_sig[i] = DBUS_TYPE_INVALID;
00439
00440 v_STRING = long_sig;
00441 if (!_dbus_header_set_field_basic (&message->header,
00442 DBUS_HEADER_FIELD_SIGNATURE,
00443 DBUS_TYPE_SIGNATURE,
00444 &v_STRING))
00445 _dbus_assert_not_reached ("oom");
00446
00447 _dbus_header_get_field_raw (&message->header,
00448 DBUS_HEADER_FIELD_SIGNATURE,
00449 NULL, &pos);
00450 generate_from_message (data, expected_validity, message);
00451
00452 *expected_validity = DBUS_INVALID_EXCEEDED_MAXIMUM_STRUCT_RECURSION;
00453 }
00454 else if (item_seq == 3)
00455 {
00456 message = simple_method_call ();
00457 if (!dbus_message_append_args (message,
00458 DBUS_TYPE_INT32, &v_INT32,
00459 DBUS_TYPE_INT32, &v_INT32,
00460 DBUS_TYPE_INT32, &v_INT32,
00461 DBUS_TYPE_INVALID))
00462 _dbus_assert_not_reached ("oom");
00463
00464 _dbus_header_get_field_raw (&message->header,
00465 DBUS_HEADER_FIELD_SIGNATURE,
00466 NULL, &pos);
00467 generate_from_message (data, expected_validity, message);
00468
00469 _dbus_string_set_byte (data, pos + 1, DBUS_STRUCT_BEGIN_CHAR);
00470
00471 *expected_validity = DBUS_INVALID_STRUCT_STARTED_BUT_NOT_ENDED;
00472 }
00473 else if (item_seq == 4)
00474 {
00475 message = simple_method_call ();
00476 if (!dbus_message_append_args (message,
00477 DBUS_TYPE_INT32, &v_INT32,
00478 DBUS_TYPE_INT32, &v_INT32,
00479 DBUS_TYPE_INT32, &v_INT32,
00480 DBUS_TYPE_INVALID))
00481 _dbus_assert_not_reached ("oom");
00482
00483 _dbus_header_get_field_raw (&message->header,
00484 DBUS_HEADER_FIELD_SIGNATURE,
00485 NULL, &pos);
00486 generate_from_message (data, expected_validity, message);
00487
00488 _dbus_string_set_byte (data, pos + 1, DBUS_STRUCT_END_CHAR);
00489
00490 *expected_validity = DBUS_INVALID_STRUCT_ENDED_BUT_NOT_STARTED;
00491 }
00492 else if (item_seq == 5)
00493 {
00494 message = simple_method_call ();
00495 if (!dbus_message_append_args (message,
00496 DBUS_TYPE_INT32, &v_INT32,
00497 DBUS_TYPE_INT32, &v_INT32,
00498 DBUS_TYPE_INT32, &v_INT32,
00499 DBUS_TYPE_INVALID))
00500 _dbus_assert_not_reached ("oom");
00501
00502 _dbus_header_get_field_raw (&message->header,
00503 DBUS_HEADER_FIELD_SIGNATURE,
00504 NULL, &pos);
00505 generate_from_message (data, expected_validity, message);
00506
00507 _dbus_string_set_byte (data, pos + 1, DBUS_STRUCT_BEGIN_CHAR);
00508 _dbus_string_set_byte (data, pos + 2, DBUS_STRUCT_END_CHAR);
00509
00510 *expected_validity = DBUS_INVALID_STRUCT_HAS_NO_FIELDS;
00511 }
00512 else if (item_seq == 6)
00513 {
00514 message = simple_method_call ();
00515 generate_from_message (data, expected_validity, message);
00516
00517 _dbus_string_set_byte (data, TYPE_OFFSET, DBUS_MESSAGE_TYPE_INVALID);
00518
00519 *expected_validity = DBUS_INVALID_BAD_MESSAGE_TYPE;
00520 }
00521 else if (item_seq == 7)
00522 {
00523
00524 message = simple_method_call ();
00525 generate_from_message (data, expected_validity, message);
00526
00527 _dbus_string_set_byte (data, TYPE_OFFSET, 100);
00528
00529 *expected_validity = DBUS_VALID;
00530 }
00531 else if (item_seq == 8)
00532 {
00533 message = simple_method_call ();
00534 generate_from_message (data, expected_validity, message);
00535
00536 _dbus_marshal_set_uint32 (data, BODY_LENGTH_OFFSET,
00537 DBUS_MAXIMUM_MESSAGE_LENGTH / 2 + 4,
00538 message->byte_order);
00539 _dbus_marshal_set_uint32 (data, FIELDS_ARRAY_LENGTH_OFFSET,
00540 DBUS_MAXIMUM_MESSAGE_LENGTH / 2 + 4,
00541 message->byte_order);
00542 *expected_validity = DBUS_INVALID_MESSAGE_TOO_LONG;
00543 }
00544 else if (item_seq == 9)
00545 {
00546 const char *v_STRING = "not a valid bus name";
00547 message = simple_method_call ();
00548
00549 if (!_dbus_header_set_field_basic (&message->header,
00550 DBUS_HEADER_FIELD_SENDER,
00551 DBUS_TYPE_STRING, &v_STRING))
00552 _dbus_assert_not_reached ("oom");
00553
00554 generate_from_message (data, expected_validity, message);
00555
00556 *expected_validity = DBUS_INVALID_BAD_SENDER;
00557 }
00558 else if (item_seq == 10)
00559 {
00560 message = simple_method_call ();
00561
00562 if (!dbus_message_set_interface (message, DBUS_INTERFACE_LOCAL))
00563 _dbus_assert_not_reached ("oom");
00564
00565 generate_from_message (data, expected_validity, message);
00566
00567 *expected_validity = DBUS_INVALID_USES_LOCAL_INTERFACE;
00568 }
00569 else if (item_seq == 11)
00570 {
00571 message = simple_method_call ();
00572
00573 if (!dbus_message_set_path (message, DBUS_PATH_LOCAL))
00574 _dbus_assert_not_reached ("oom");
00575
00576 generate_from_message (data, expected_validity, message);
00577
00578 *expected_validity = DBUS_INVALID_USES_LOCAL_PATH;
00579 }
00580 else if (item_seq == 12)
00581 {
00582
00583 message = simple_method_call ();
00584
00585 if (!dbus_message_set_interface (message, NULL))
00586 _dbus_assert_not_reached ("oom");
00587
00588 generate_from_message (data, expected_validity, message);
00589
00590 *expected_validity = DBUS_VALID;
00591 }
00592 else if (item_seq == 13)
00593 {
00594
00595 message = simple_signal ();
00596
00597 if (!dbus_message_set_interface (message, NULL))
00598 _dbus_assert_not_reached ("oom");
00599
00600 generate_from_message (data, expected_validity, message);
00601
00602 *expected_validity = DBUS_INVALID_MISSING_INTERFACE;
00603 }
00604 else if (item_seq == 14)
00605 {
00606 message = simple_method_return ();
00607
00608 if (!_dbus_header_delete_field (&message->header, DBUS_HEADER_FIELD_REPLY_SERIAL))
00609 _dbus_assert_not_reached ("oom");
00610
00611 generate_from_message (data, expected_validity, message);
00612
00613 *expected_validity = DBUS_INVALID_MISSING_REPLY_SERIAL;
00614 }
00615 else if (item_seq == 15)
00616 {
00617 message = simple_error ();
00618
00619 if (!dbus_message_set_error_name (message, NULL))
00620 _dbus_assert_not_reached ("oom");
00621
00622 generate_from_message (data, expected_validity, message);
00623
00624 *expected_validity = DBUS_INVALID_MISSING_ERROR_NAME;
00625 }
00626 else if (item_seq == 16)
00627 {
00628 char long_sig[DBUS_MAXIMUM_TYPE_RECURSION_DEPTH*4+10];
00629 const char *v_STRING;
00630 int i;
00631 int n_begins;
00632
00633 message = simple_method_call ();
00634 if (!dbus_message_append_args (message,
00635 DBUS_TYPE_INT32, &v_INT32,
00636 DBUS_TYPE_INT32, &v_INT32,
00637 DBUS_TYPE_INT32, &v_INT32,
00638 DBUS_TYPE_INVALID))
00639 _dbus_assert_not_reached ("oom");
00640
00641 i = 0;
00642 while (i <= (DBUS_MAXIMUM_TYPE_RECURSION_DEPTH*3 + 3))
00643 {
00644 long_sig[i] = DBUS_TYPE_ARRAY;
00645 ++i;
00646 long_sig[i] = DBUS_DICT_ENTRY_BEGIN_CHAR;
00647 ++i;
00648 long_sig[i] = DBUS_TYPE_INT32;
00649 ++i;
00650 }
00651 n_begins = i / 3;
00652
00653 long_sig[i] = DBUS_TYPE_INT32;
00654 ++i;
00655
00656 while (n_begins > 0)
00657 {
00658 long_sig[i] = DBUS_DICT_ENTRY_END_CHAR;
00659 ++i;
00660 n_begins -= 1;
00661 }
00662 long_sig[i] = DBUS_TYPE_INVALID;
00663
00664 v_STRING = long_sig;
00665 if (!_dbus_header_set_field_basic (&message->header,
00666 DBUS_HEADER_FIELD_SIGNATURE,
00667 DBUS_TYPE_SIGNATURE,
00668 &v_STRING))
00669 _dbus_assert_not_reached ("oom");
00670
00671 _dbus_header_get_field_raw (&message->header,
00672 DBUS_HEADER_FIELD_SIGNATURE,
00673 NULL, &pos);
00674 generate_from_message (data, expected_validity, message);
00675
00676 *expected_validity = DBUS_INVALID_EXCEEDED_MAXIMUM_DICT_ENTRY_RECURSION;
00677 }
00678 else if (item_seq == 17)
00679 {
00680 message = simple_method_call ();
00681 if (!dbus_message_append_args (message,
00682 DBUS_TYPE_INT32, &v_INT32,
00683 DBUS_TYPE_INT32, &v_INT32,
00684 DBUS_TYPE_INT32, &v_INT32,
00685 DBUS_TYPE_INVALID))
00686 _dbus_assert_not_reached ("oom");
00687
00688 _dbus_header_get_field_raw (&message->header,
00689 DBUS_HEADER_FIELD_SIGNATURE,
00690 NULL, &pos);
00691 generate_from_message (data, expected_validity, message);
00692
00693 _dbus_string_set_byte (data, pos + 1, DBUS_TYPE_ARRAY);
00694 _dbus_string_set_byte (data, pos + 2, DBUS_DICT_ENTRY_BEGIN_CHAR);
00695
00696 *expected_validity = DBUS_INVALID_DICT_ENTRY_STARTED_BUT_NOT_ENDED;
00697 }
00698 else if (item_seq == 18)
00699 {
00700 message = simple_method_call ();
00701 if (!dbus_message_append_args (message,
00702 DBUS_TYPE_INT32, &v_INT32,
00703 DBUS_TYPE_INT32, &v_INT32,
00704 DBUS_TYPE_INT32, &v_INT32,
00705 DBUS_TYPE_INVALID))
00706 _dbus_assert_not_reached ("oom");
00707
00708 _dbus_header_get_field_raw (&message->header,
00709 DBUS_HEADER_FIELD_SIGNATURE,
00710 NULL, &pos);
00711 generate_from_message (data, expected_validity, message);
00712
00713 _dbus_string_set_byte (data, pos + 1, DBUS_DICT_ENTRY_END_CHAR);
00714
00715 *expected_validity = DBUS_INVALID_DICT_ENTRY_ENDED_BUT_NOT_STARTED;
00716 }
00717 else if (item_seq == 19)
00718 {
00719 message = simple_method_call ();
00720 if (!dbus_message_append_args (message,
00721 DBUS_TYPE_INT32, &v_INT32,
00722 DBUS_TYPE_INT32, &v_INT32,
00723 DBUS_TYPE_INT32, &v_INT32,
00724 DBUS_TYPE_INVALID))
00725 _dbus_assert_not_reached ("oom");
00726
00727 _dbus_header_get_field_raw (&message->header,
00728 DBUS_HEADER_FIELD_SIGNATURE,
00729 NULL, &pos);
00730 generate_from_message (data, expected_validity, message);
00731
00732 _dbus_string_set_byte (data, pos + 1, DBUS_TYPE_ARRAY);
00733 _dbus_string_set_byte (data, pos + 2, DBUS_DICT_ENTRY_BEGIN_CHAR);
00734 _dbus_string_set_byte (data, pos + 3, DBUS_DICT_ENTRY_END_CHAR);
00735
00736 *expected_validity = DBUS_INVALID_DICT_ENTRY_HAS_NO_FIELDS;
00737 }
00738 else
00739 {
00740 return FALSE;
00741 }
00742
00743 if (message)
00744 dbus_message_unref (message);
00745
00746 iter_next (iter);
00747 return TRUE;
00748 }
00749
00750 static dbus_bool_t
00751 generate_wrong_length (DBusMessageDataIter *iter,
00752 DBusString *data,
00753 DBusValidity *expected_validity)
00754 {
00755 int lengths[] = { -42, -17, -16, -15, -9, -8, -7, -6, -5, -4, -3, -2, -1,
00756 1, 2, 3, 4, 5, 6, 7, 8, 9, 15, 16, 30 };
00757 int adjust;
00758 int len_seq;
00759
00760 restart:
00761 len_seq = iter_get_sequence (iter);
00762 if (len_seq == _DBUS_N_ELEMENTS (lengths))
00763 return FALSE;
00764
00765 _dbus_assert (len_seq < _DBUS_N_ELEMENTS (lengths));
00766
00767 iter_recurse (iter);
00768 if (!generate_many_bodies (iter, data, expected_validity))
00769 {
00770 iter_set_sequence (iter, 0);
00771 iter_unrecurse (iter);
00772 iter_next (iter);
00773 goto restart;
00774 }
00775 iter_unrecurse (iter);
00776
00777 adjust = lengths[len_seq];
00778
00779 if (adjust < 0)
00780 {
00781 if ((_dbus_string_get_length (data) + adjust) < DBUS_MINIMUM_HEADER_SIZE)
00782 _dbus_string_set_length (data, DBUS_MINIMUM_HEADER_SIZE);
00783 else
00784 _dbus_string_shorten (data, - adjust);
00785 *expected_validity = DBUS_INVALID_FOR_UNKNOWN_REASON;
00786 }
00787 else
00788 {
00789 if (!_dbus_string_lengthen (data, adjust))
00790 _dbus_assert_not_reached ("oom");
00791 *expected_validity = DBUS_INVALID_TOO_MUCH_DATA;
00792 }
00793
00794
00795 {
00796 int old_body_len;
00797 int new_body_len;
00798 int byte_order;
00799
00800 _dbus_assert (_dbus_string_get_length (data) >= DBUS_MINIMUM_HEADER_SIZE);
00801
00802 byte_order = _dbus_string_get_byte (data, BYTE_ORDER_OFFSET);
00803 old_body_len = _dbus_marshal_read_uint32 (data,
00804 BODY_LENGTH_OFFSET,
00805 byte_order,
00806 NULL);
00807 _dbus_assert (old_body_len < _dbus_string_get_length (data));
00808 new_body_len = old_body_len + adjust;
00809 if (new_body_len < 0)
00810 {
00811 new_body_len = 0;
00812
00813 *expected_validity = DBUS_VALIDITY_UNKNOWN;
00814 }
00815
00816 _dbus_verbose ("changing body len from %u to %u by adjust %d\n",
00817 old_body_len, new_body_len, adjust);
00818
00819 _dbus_marshal_set_uint32 (data, BODY_LENGTH_OFFSET,
00820 new_body_len,
00821 byte_order);
00822 }
00823
00824 return TRUE;
00825 }
00826
00827 static dbus_bool_t
00828 generate_byte_changed (DBusMessageDataIter *iter,
00829 DBusString *data,
00830 DBusValidity *expected_validity)
00831 {
00832 int byte_seq;
00833 int v_BYTE;
00834
00835
00836
00837
00838
00839
00840 restart:
00841 if (!generate_many_bodies (iter, data, expected_validity))
00842 return FALSE;
00843
00844 iter_recurse (iter);
00845 byte_seq = iter_get_sequence (iter);
00846 iter_next (iter);
00847 iter_unrecurse (iter);
00848
00849 if (byte_seq == _dbus_string_get_length (data))
00850 {
00851 _dbus_string_set_length (data, 0);
00852
00853 iter_recurse (iter);
00854 iter_set_sequence (iter, 0);
00855 iter_unrecurse (iter);
00856 goto restart;
00857 }
00858 else
00859 {
00860
00861 iter_set_sequence (iter, iter_get_sequence (iter) - 1);
00862 }
00863
00864 _dbus_assert (byte_seq < _dbus_string_get_length (data));
00865 v_BYTE = _dbus_string_get_byte (data, byte_seq);
00866 v_BYTE += byte_seq;
00867 _dbus_string_set_byte (data, byte_seq, v_BYTE);
00868 *expected_validity = DBUS_VALIDITY_UNKNOWN;
00869
00870 return TRUE;
00871 }
00872
00873 static dbus_bool_t
00874 find_next_typecode (DBusMessageDataIter *iter,
00875 DBusString *data,
00876 DBusValidity *expected_validity)
00877 {
00878 int body_seq;
00879 int byte_seq;
00880 int base_depth;
00881
00882 base_depth = iter->depth;
00883
00884 restart:
00885 _dbus_assert (iter->depth == (base_depth + 0));
00886 _dbus_string_set_length (data, 0);
00887
00888 body_seq = iter_get_sequence (iter);
00889
00890 if (!generate_many_bodies (iter, data, expected_validity))
00891 return FALSE;
00892
00893 iter_set_sequence (iter, body_seq);
00894
00895 iter_recurse (iter);
00896 while (TRUE)
00897 {
00898 _dbus_assert (iter->depth == (base_depth + 1));
00899
00900 byte_seq = iter_get_sequence (iter);
00901
00902 _dbus_assert (byte_seq <= _dbus_string_get_length (data));
00903
00904 if (byte_seq == _dbus_string_get_length (data))
00905 {
00906
00907 iter_set_sequence (iter, 0);
00908 iter_unrecurse (iter);
00909 _dbus_assert (iter->depth == (base_depth + 0));
00910 iter_next (iter);
00911 goto restart;
00912 }
00913
00914 _dbus_assert (byte_seq < _dbus_string_get_length (data));
00915
00916 if (_dbus_type_is_valid (_dbus_string_get_byte (data, byte_seq)))
00917 break;
00918 else
00919 iter_next (iter);
00920 }
00921
00922 _dbus_assert (byte_seq == iter_get_sequence (iter));
00923 _dbus_assert (byte_seq < _dbus_string_get_length (data));
00924
00925 iter_unrecurse (iter);
00926
00927 _dbus_assert (iter->depth == (base_depth + 0));
00928
00929 return TRUE;
00930 }
00931
00932 static const int typecodes[] = {
00933 DBUS_TYPE_INVALID,
00934 DBUS_TYPE_BYTE,
00935 DBUS_TYPE_BOOLEAN,
00936 DBUS_TYPE_INT16,
00937 DBUS_TYPE_UINT16,
00938 DBUS_TYPE_INT32,
00939 DBUS_TYPE_UINT32,
00940 DBUS_TYPE_INT64,
00941 DBUS_TYPE_UINT64,
00942 DBUS_TYPE_DOUBLE,
00943 DBUS_TYPE_STRING,
00944 DBUS_TYPE_OBJECT_PATH,
00945 DBUS_TYPE_SIGNATURE,
00946 DBUS_TYPE_ARRAY,
00947 DBUS_TYPE_VARIANT,
00948 DBUS_STRUCT_BEGIN_CHAR,
00949 DBUS_STRUCT_END_CHAR,
00950 DBUS_DICT_ENTRY_BEGIN_CHAR,
00951 DBUS_DICT_ENTRY_END_CHAR,
00952 255
00953 };
00954
00955 static dbus_bool_t
00956 generate_typecode_changed (DBusMessageDataIter *iter,
00957 DBusString *data,
00958 DBusValidity *expected_validity)
00959 {
00960 int byte_seq;
00961 int typecode_seq;
00962 int base_depth;
00963
00964 base_depth = iter->depth;
00965
00966 restart:
00967 _dbus_assert (iter->depth == (base_depth + 0));
00968 _dbus_string_set_length (data, 0);
00969
00970 if (!find_next_typecode (iter, data, expected_validity))
00971 return FALSE;
00972
00973 iter_recurse (iter);
00974 byte_seq = iter_get_sequence (iter);
00975
00976 _dbus_assert (byte_seq < _dbus_string_get_length (data));
00977
00978 iter_recurse (iter);
00979 typecode_seq = iter_get_sequence (iter);
00980 iter_next (iter);
00981
00982 _dbus_assert (typecode_seq <= _DBUS_N_ELEMENTS (typecodes));
00983
00984 if (typecode_seq == _DBUS_N_ELEMENTS (typecodes))
00985 {
00986 _dbus_assert (iter->depth == (base_depth + 2));
00987 iter_set_sequence (iter, 0);
00988 iter_unrecurse (iter);
00989 _dbus_assert (iter->depth == (base_depth + 1));
00990 iter_next (iter);
00991 iter_unrecurse (iter);
00992 _dbus_assert (iter->depth == (base_depth + 0));
00993 goto restart;
00994 }
00995
00996 _dbus_assert (iter->depth == (base_depth + 2));
00997 iter_unrecurse (iter);
00998 _dbus_assert (iter->depth == (base_depth + 1));
00999 iter_unrecurse (iter);
01000 _dbus_assert (iter->depth == (base_depth + 0));
01001
01002 #if 0
01003 printf ("Changing byte %d in message %d to %c\n",
01004 byte_seq, iter_get_sequence (iter), typecodes[typecode_seq]);
01005 #endif
01006
01007 _dbus_string_set_byte (data, byte_seq, typecodes[typecode_seq]);
01008 *expected_validity = DBUS_VALIDITY_UNKNOWN;
01009 return TRUE;
01010 }
01011
01012 typedef struct
01013 {
01014 ChangeType type;
01015 dbus_uint32_t value;
01016 } UIntChange;
01017
01018 static const UIntChange uint32_changes[] = {
01019 { CHANGE_TYPE_ADJUST, (dbus_uint32_t) -1 },
01020 { CHANGE_TYPE_ADJUST, (dbus_uint32_t) -2 },
01021 { CHANGE_TYPE_ADJUST, (dbus_uint32_t) -3 },
01022 { CHANGE_TYPE_ADJUST, (dbus_uint32_t) 1 },
01023 { CHANGE_TYPE_ADJUST, (dbus_uint32_t) 2 },
01024 { CHANGE_TYPE_ADJUST, (dbus_uint32_t) 3 },
01025 { CHANGE_TYPE_ABSOLUTE, _DBUS_UINT32_MAX },
01026 { CHANGE_TYPE_ABSOLUTE, 0 },
01027 { CHANGE_TYPE_ABSOLUTE, 1 },
01028 { CHANGE_TYPE_ABSOLUTE, _DBUS_UINT32_MAX - 1 },
01029 { CHANGE_TYPE_ABSOLUTE, _DBUS_UINT32_MAX - 5 }
01030 };
01031
01032 static dbus_bool_t
01033 generate_uint32_changed (DBusMessageDataIter *iter,
01034 DBusString *data,
01035 DBusValidity *expected_validity)
01036 {
01037 int body_seq;
01038 int byte_seq;
01039 int change_seq;
01040 dbus_uint32_t v_UINT32;
01041 int byte_order;
01042 const UIntChange *change;
01043 int base_depth;
01044
01045
01046
01047
01048
01049 base_depth = iter->depth;
01050
01051 next_body:
01052 _dbus_assert (iter->depth == (base_depth + 0));
01053 _dbus_string_set_length (data, 0);
01054 body_seq = iter_get_sequence (iter);
01055
01056 if (!generate_many_bodies (iter, data, expected_validity))
01057 return FALSE;
01058
01059 _dbus_assert (iter->depth == (base_depth + 0));
01060
01061 iter_set_sequence (iter, body_seq);
01062 iter_recurse (iter);
01063 next_change:
01064 _dbus_assert (iter->depth == (base_depth + 1));
01065 change_seq = iter_get_sequence (iter);
01066
01067 if (change_seq == _DBUS_N_ELEMENTS (uint32_changes))
01068 {
01069
01070 iter_set_sequence (iter, 0);
01071 iter_unrecurse (iter);
01072 iter_next (iter);
01073 goto next_body;
01074 }
01075
01076 _dbus_assert (iter->depth == (base_depth + 1));
01077
01078 iter_recurse (iter);
01079 _dbus_assert (iter->depth == (base_depth + 2));
01080 byte_seq = iter_get_sequence (iter);
01081
01082 iter_next (iter);
01083 iter_next (iter);
01084 iter_next (iter);
01085 iter_next (iter);
01086 iter_unrecurse (iter);
01087
01088 _dbus_assert (_DBUS_ALIGN_VALUE (byte_seq, 4) == (unsigned) byte_seq);
01089 if (byte_seq >= (_dbus_string_get_length (data) - 4))
01090 {
01091
01092 _dbus_assert (iter->depth == (base_depth + 1));
01093 iter_recurse (iter);
01094 _dbus_assert (iter->depth == (base_depth + 2));
01095 iter_set_sequence (iter, 0);
01096 iter_unrecurse (iter);
01097 _dbus_assert (iter->depth == (base_depth + 1));
01098 iter_next (iter);
01099 goto next_change;
01100 }
01101
01102 _dbus_assert (byte_seq <= (_dbus_string_get_length (data) - 4));
01103
01104 byte_order = _dbus_string_get_byte (data, BYTE_ORDER_OFFSET);
01105
01106 v_UINT32 = _dbus_marshal_read_uint32 (data, byte_seq, byte_order, NULL);
01107
01108 change = &uint32_changes[change_seq];
01109
01110 if (change->type == CHANGE_TYPE_ADJUST)
01111 {
01112 v_UINT32 += (int) change->value;
01113 }
01114 else
01115 {
01116 v_UINT32 = change->value;
01117 }
01118
01119 #if 0
01120 printf ("body %d change %d pos %d ",
01121 body_seq, change_seq, byte_seq);
01122
01123 if (change->type == CHANGE_TYPE_ADJUST)
01124 printf ("adjust by %d", (int) change->value);
01125 else
01126 printf ("set to %u", change->value);
01127
01128 printf (" \t%u -> %u\n",
01129 _dbus_marshal_read_uint32 (data, byte_seq, byte_order, NULL),
01130 v_UINT32);
01131 #endif
01132
01133 _dbus_marshal_set_uint32 (data, byte_seq, v_UINT32, byte_order);
01134 *expected_validity = DBUS_VALIDITY_UNKNOWN;
01135
01136 _dbus_assert (iter->depth == (base_depth + 1));
01137 iter_unrecurse (iter);
01138 _dbus_assert (iter->depth == (base_depth + 0));
01139
01140 return TRUE;
01141 }
01142
01143 typedef struct
01144 {
01145 const char *name;
01146 DBusMessageGeneratorFunc func;
01147 } DBusMessageGenerator;
01148
01149 static const DBusMessageGenerator generators[] = {
01150 { "trivial example of each message type", generate_trivial },
01151 { "assorted arguments", generate_many_bodies },
01152 { "assorted special cases", generate_special },
01153 { "each uint32 modified", generate_uint32_changed },
01154 { "wrong body lengths", generate_wrong_length },
01155 { "each byte modified", generate_byte_changed },
01156 #if 0
01157
01158 { "change each typecode", generate_typecode_changed }
01159 #endif
01160 };
01161
01162 void
01163 _dbus_message_data_free (DBusMessageData *data)
01164 {
01165 _dbus_string_free (&data->data);
01166 }
01167
01168 void
01169 _dbus_message_data_iter_init (DBusMessageDataIter *iter)
01170 {
01171 int i;
01172
01173 iter->depth = 0;
01174 i = 0;
01175 while (i < _DBUS_MESSAGE_DATA_MAX_NESTING)
01176 {
01177 iter->sequence_nos[i] = 0;
01178 ++i;
01179 }
01180 iter->count = 0;
01181 }
01182
01183 dbus_bool_t
01184 _dbus_message_data_iter_get_and_next (DBusMessageDataIter *iter,
01185 DBusMessageData *data)
01186 {
01187 DBusMessageGeneratorFunc func;
01188 int generator;
01189
01190 restart:
01191 generator = iter_get_sequence (iter);
01192
01193 if (generator == _DBUS_N_ELEMENTS (generators))
01194 return FALSE;
01195
01196 iter_recurse (iter);
01197
01198 if (iter_first_in_series (iter))
01199 {
01200 printf (" testing message loading: %s ", generators[generator].name);
01201 fflush (stdout);
01202 }
01203
01204 func = generators[generator].func;
01205
01206 if (!_dbus_string_init (&data->data))
01207 _dbus_assert_not_reached ("oom");
01208
01209 if ((*func)(iter, &data->data, &data->expected_validity))
01210 ;
01211 else
01212 {
01213 iter_set_sequence (iter, 0);
01214 iter_unrecurse (iter);
01215 iter_next (iter);
01216 _dbus_string_free (&data->data);
01217 printf ("%d test loads cumulative\n", iter->count);
01218 goto restart;
01219 }
01220 iter_unrecurse (iter);
01221
01222 iter->count += 1;
01223 return TRUE;
01224 }
01225
01226 #endif
01227
01228 #endif