00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020
00021
00022
00023
00024 #include <config.h>
00025
00026 #include "dbus-signature.h"
00027 #include "dbus-marshal-recursive.h"
00028 #include "dbus-marshal-basic.h"
00029 #include "dbus-internals.h"
00030 #include "dbus-test.h"
00031
00035 typedef struct
00036 {
00037 const char *pos;
00038 unsigned int finished : 1;
00039 unsigned int in_array : 1;
00040 } DBusSignatureRealIter;
00041
00043 #define TYPE_IS_CONTAINER(typecode) \
00044 ((typecode) == DBUS_TYPE_STRUCT || \
00045 (typecode) == DBUS_TYPE_DICT_ENTRY || \
00046 (typecode) == DBUS_TYPE_VARIANT || \
00047 (typecode) == DBUS_TYPE_ARRAY)
00048
00049
00066 void
00067 dbus_signature_iter_init (DBusSignatureIter *iter,
00068 const char *signature)
00069 {
00070 DBusSignatureRealIter *real_iter = (DBusSignatureRealIter *) iter;
00071
00072 real_iter->pos = signature;
00073 real_iter->finished = FALSE;
00074 real_iter->in_array = FALSE;
00075 }
00076
00091 int
00092 dbus_signature_iter_get_current_type (const DBusSignatureIter *iter)
00093 {
00094 DBusSignatureRealIter *real_iter = (DBusSignatureRealIter *) iter;
00095
00096 return _dbus_first_type_in_signature_c_str (real_iter->pos, 0);
00097 }
00098
00111 char *
00112 dbus_signature_iter_get_signature (const DBusSignatureIter *iter)
00113 {
00114 DBusSignatureRealIter *real_iter = (DBusSignatureRealIter *) iter;
00115 DBusString str;
00116 char *ret;
00117 int pos;
00118
00119 if (!_dbus_string_init (&str))
00120 return NULL;
00121
00122 pos = 0;
00123 _dbus_type_signature_next (real_iter->pos, &pos);
00124
00125 if (!_dbus_string_append_len (&str, real_iter->pos, pos))
00126 return NULL;
00127 if (!_dbus_string_steal_data (&str, &ret))
00128 ret = NULL;
00129 _dbus_string_free (&str);
00130
00131 return ret;
00132 }
00133
00145 int
00146 dbus_signature_iter_get_element_type (const DBusSignatureIter *iter)
00147 {
00148 DBusSignatureRealIter *real_iter = (DBusSignatureRealIter *) iter;
00149
00150 _dbus_return_val_if_fail (dbus_signature_iter_get_current_type (iter) == DBUS_TYPE_ARRAY, DBUS_TYPE_INVALID);
00151
00152 return _dbus_first_type_in_signature_c_str (real_iter->pos, 1);
00153 }
00154
00163 dbus_bool_t
00164 dbus_signature_iter_next (DBusSignatureIter *iter)
00165 {
00166 DBusSignatureRealIter *real_iter = (DBusSignatureRealIter *) iter;
00167
00168 if (real_iter->finished)
00169 return FALSE;
00170 else
00171 {
00172 int pos;
00173
00174 if (real_iter->in_array)
00175 {
00176 real_iter->finished = TRUE;
00177 return FALSE;
00178 }
00179
00180 pos = 0;
00181 _dbus_type_signature_next (real_iter->pos, &pos);
00182 real_iter->pos += pos;
00183
00184 if (*real_iter->pos == DBUS_STRUCT_END_CHAR
00185 || *real_iter->pos == DBUS_DICT_ENTRY_END_CHAR)
00186 {
00187 real_iter->finished = TRUE;
00188 return FALSE;
00189 }
00190
00191 return *real_iter->pos != DBUS_TYPE_INVALID;
00192 }
00193 }
00194
00206 void
00207 dbus_signature_iter_recurse (const DBusSignatureIter *iter,
00208 DBusSignatureIter *subiter)
00209 {
00210 DBusSignatureRealIter *real_iter = (DBusSignatureRealIter *) iter;
00211 DBusSignatureRealIter *real_sub_iter = (DBusSignatureRealIter *) subiter;
00212
00213 _dbus_return_if_fail (dbus_type_is_container (dbus_signature_iter_get_current_type (iter)));
00214
00215 *real_sub_iter = *real_iter;
00216 real_sub_iter->in_array = FALSE;
00217 real_sub_iter->pos++;
00218
00219 if (dbus_signature_iter_get_current_type (iter) == DBUS_TYPE_ARRAY)
00220 real_sub_iter->in_array = TRUE;
00221 }
00222
00232 dbus_bool_t
00233 dbus_signature_validate (const char *signature,
00234 DBusError *error)
00235
00236 {
00237 DBusString str;
00238 DBusValidity reason;
00239
00240 _dbus_string_init_const (&str, signature);
00241 reason = _dbus_validate_signature_with_reason (&str, 0, _dbus_string_get_length (&str));
00242
00243 if (reason == DBUS_VALID)
00244 return TRUE;
00245 else
00246 {
00247 dbus_set_error (error, DBUS_ERROR_INVALID_SIGNATURE, _dbus_validity_to_error_message (reason));
00248 return FALSE;
00249 }
00250 }
00251
00263 dbus_bool_t
00264 dbus_signature_validate_single (const char *signature,
00265 DBusError *error)
00266 {
00267 DBusSignatureIter iter;
00268
00269 if (!dbus_signature_validate (signature, error))
00270 return FALSE;
00271
00272 dbus_signature_iter_init (&iter, signature);
00273 if (dbus_signature_iter_get_current_type (&iter) == DBUS_TYPE_INVALID)
00274 goto lose;
00275 if (!dbus_signature_iter_next (&iter))
00276 return TRUE;
00277 lose:
00278 dbus_set_error (error, DBUS_ERROR_INVALID_SIGNATURE, "Exactly one complete type required in signature");
00279 return FALSE;
00280 }
00281
00292 dbus_bool_t
00293 dbus_type_is_container (int typecode)
00294 {
00295
00296 _dbus_return_val_if_fail (_dbus_type_is_valid (typecode) || typecode == DBUS_TYPE_INVALID,
00297 FALSE);
00298 return TYPE_IS_CONTAINER (typecode);
00299 }
00300
00315 dbus_bool_t
00316 dbus_type_is_basic (int typecode)
00317 {
00318
00319 _dbus_return_val_if_fail (_dbus_type_is_valid (typecode) || typecode == DBUS_TYPE_INVALID,
00320 FALSE);
00321
00322
00323 return !(typecode == DBUS_TYPE_INVALID || TYPE_IS_CONTAINER (typecode));
00324 }
00325
00345 dbus_bool_t
00346 dbus_type_is_fixed (int typecode)
00347 {
00348
00349 _dbus_return_val_if_fail (_dbus_type_is_valid (typecode) || typecode == DBUS_TYPE_INVALID,
00350 FALSE);
00351
00352 switch (typecode)
00353 {
00354 case DBUS_TYPE_BYTE:
00355 case DBUS_TYPE_BOOLEAN:
00356 case DBUS_TYPE_INT16:
00357 case DBUS_TYPE_UINT16:
00358 case DBUS_TYPE_INT32:
00359 case DBUS_TYPE_UINT32:
00360 case DBUS_TYPE_INT64:
00361 case DBUS_TYPE_UINT64:
00362 case DBUS_TYPE_DOUBLE:
00363 case DBUS_TYPE_UNIX_FD:
00364 return TRUE;
00365 default:
00366 return FALSE;
00367 }
00368 }
00369
00371
00372 #ifdef DBUS_BUILD_TESTS
00373
00380 dbus_bool_t
00381 _dbus_signature_test (void)
00382 {
00383 DBusSignatureIter iter;
00384 DBusSignatureIter subiter;
00385 DBusSignatureIter subsubiter;
00386 DBusSignatureIter subsubsubiter;
00387 const char *sig;
00388 dbus_bool_t boolres;
00389
00390 _dbus_assert (sizeof (DBusSignatureIter) >= sizeof (DBusSignatureRealIter));
00391
00392 sig = "";
00393 _dbus_assert (dbus_signature_validate (sig, NULL));
00394 _dbus_assert (!dbus_signature_validate_single (sig, NULL));
00395 dbus_signature_iter_init (&iter, sig);
00396 _dbus_assert (dbus_signature_iter_get_current_type (&iter) == DBUS_TYPE_INVALID);
00397
00398 sig = DBUS_TYPE_STRING_AS_STRING;
00399 _dbus_assert (dbus_signature_validate (sig, NULL));
00400 _dbus_assert (dbus_signature_validate_single (sig, NULL));
00401 dbus_signature_iter_init (&iter, sig);
00402 _dbus_assert (dbus_signature_iter_get_current_type (&iter) == DBUS_TYPE_STRING);
00403
00404 sig = DBUS_TYPE_STRING_AS_STRING DBUS_TYPE_BYTE_AS_STRING;
00405 _dbus_assert (dbus_signature_validate (sig, NULL));
00406 dbus_signature_iter_init (&iter, sig);
00407 _dbus_assert (dbus_signature_iter_get_current_type (&iter) == DBUS_TYPE_STRING);
00408 boolres = dbus_signature_iter_next (&iter);
00409 _dbus_assert (boolres);
00410 _dbus_assert (dbus_signature_iter_get_current_type (&iter) == DBUS_TYPE_BYTE);
00411
00412 sig = DBUS_TYPE_UINT16_AS_STRING
00413 DBUS_STRUCT_BEGIN_CHAR_AS_STRING
00414 DBUS_TYPE_STRING_AS_STRING
00415 DBUS_TYPE_UINT32_AS_STRING
00416 DBUS_TYPE_VARIANT_AS_STRING
00417 DBUS_TYPE_DOUBLE_AS_STRING
00418 DBUS_STRUCT_END_CHAR_AS_STRING;
00419 _dbus_assert (dbus_signature_validate (sig, NULL));
00420 dbus_signature_iter_init (&iter, sig);
00421 _dbus_assert (dbus_signature_iter_get_current_type (&iter) == DBUS_TYPE_UINT16);
00422 boolres = dbus_signature_iter_next (&iter);
00423 _dbus_assert (boolres);
00424 _dbus_assert (dbus_signature_iter_get_current_type (&iter) == DBUS_TYPE_STRUCT);
00425 dbus_signature_iter_recurse (&iter, &subiter);
00426 _dbus_assert (dbus_signature_iter_get_current_type (&subiter) == DBUS_TYPE_STRING);
00427 boolres = dbus_signature_iter_next (&subiter);
00428 _dbus_assert (boolres);
00429 _dbus_assert (dbus_signature_iter_get_current_type (&subiter) == DBUS_TYPE_UINT32);
00430 boolres = dbus_signature_iter_next (&subiter);
00431 _dbus_assert (boolres);
00432 _dbus_assert (dbus_signature_iter_get_current_type (&subiter) == DBUS_TYPE_VARIANT);
00433 boolres = dbus_signature_iter_next (&subiter);
00434 _dbus_assert (boolres);
00435 _dbus_assert (dbus_signature_iter_get_current_type (&subiter) == DBUS_TYPE_DOUBLE);
00436
00437 sig = DBUS_TYPE_UINT16_AS_STRING
00438 DBUS_STRUCT_BEGIN_CHAR_AS_STRING
00439 DBUS_TYPE_UINT32_AS_STRING
00440 DBUS_TYPE_BYTE_AS_STRING
00441 DBUS_TYPE_ARRAY_AS_STRING
00442 DBUS_TYPE_ARRAY_AS_STRING
00443 DBUS_TYPE_DOUBLE_AS_STRING
00444 DBUS_STRUCT_BEGIN_CHAR_AS_STRING
00445 DBUS_TYPE_BYTE_AS_STRING
00446 DBUS_STRUCT_END_CHAR_AS_STRING
00447 DBUS_STRUCT_END_CHAR_AS_STRING;
00448 _dbus_assert (dbus_signature_validate (sig, NULL));
00449 dbus_signature_iter_init (&iter, sig);
00450 _dbus_assert (dbus_signature_iter_get_current_type (&iter) == DBUS_TYPE_UINT16);
00451 boolres = dbus_signature_iter_next (&iter);
00452 _dbus_assert (boolres);
00453 _dbus_assert (dbus_signature_iter_get_current_type (&iter) == DBUS_TYPE_STRUCT);
00454 dbus_signature_iter_recurse (&iter, &subiter);
00455 _dbus_assert (dbus_signature_iter_get_current_type (&subiter) == DBUS_TYPE_UINT32);
00456 boolres = dbus_signature_iter_next (&subiter);
00457 _dbus_assert (boolres);
00458 _dbus_assert (dbus_signature_iter_get_current_type (&subiter) == DBUS_TYPE_BYTE);
00459 boolres = dbus_signature_iter_next (&subiter);
00460 _dbus_assert (boolres);
00461 _dbus_assert (dbus_signature_iter_get_current_type (&subiter) == DBUS_TYPE_ARRAY);
00462 _dbus_assert (dbus_signature_iter_get_element_type (&subiter) == DBUS_TYPE_ARRAY);
00463
00464 dbus_signature_iter_recurse (&subiter, &subsubiter);
00465 _dbus_assert (dbus_signature_iter_get_current_type (&subsubiter) == DBUS_TYPE_ARRAY);
00466 _dbus_assert (dbus_signature_iter_get_element_type (&subsubiter) == DBUS_TYPE_DOUBLE);
00467
00468 dbus_signature_iter_recurse (&subsubiter, &subsubsubiter);
00469 _dbus_assert (dbus_signature_iter_get_current_type (&subsubsubiter) == DBUS_TYPE_DOUBLE);
00470 boolres = dbus_signature_iter_next (&subiter);
00471 _dbus_assert (boolres);
00472 _dbus_assert (dbus_signature_iter_get_current_type (&subiter) == DBUS_TYPE_STRUCT);
00473 dbus_signature_iter_recurse (&subiter, &subsubiter);
00474 _dbus_assert (dbus_signature_iter_get_current_type (&subsubiter) == DBUS_TYPE_BYTE);
00475
00476 sig = DBUS_TYPE_ARRAY_AS_STRING
00477 DBUS_DICT_ENTRY_BEGIN_CHAR_AS_STRING
00478 DBUS_TYPE_INT16_AS_STRING
00479 DBUS_TYPE_STRING_AS_STRING
00480 DBUS_DICT_ENTRY_END_CHAR_AS_STRING
00481 DBUS_TYPE_VARIANT_AS_STRING;
00482 _dbus_assert (dbus_signature_validate (sig, NULL));
00483 _dbus_assert (!dbus_signature_validate_single (sig, NULL));
00484 dbus_signature_iter_init (&iter, sig);
00485 _dbus_assert (dbus_signature_iter_get_current_type (&iter) == DBUS_TYPE_ARRAY);
00486 _dbus_assert (dbus_signature_iter_get_element_type (&iter) == DBUS_TYPE_DICT_ENTRY);
00487
00488 dbus_signature_iter_recurse (&iter, &subiter);
00489 dbus_signature_iter_recurse (&subiter, &subsubiter);
00490 _dbus_assert (dbus_signature_iter_get_current_type (&subsubiter) == DBUS_TYPE_INT16);
00491 boolres = dbus_signature_iter_next (&subsubiter);
00492 _dbus_assert (boolres);
00493 _dbus_assert (dbus_signature_iter_get_current_type (&subsubiter) == DBUS_TYPE_STRING);
00494 boolres = dbus_signature_iter_next (&subsubiter);
00495 _dbus_assert (!boolres);
00496
00497 boolres = dbus_signature_iter_next (&iter);
00498 _dbus_assert (boolres);
00499 _dbus_assert (dbus_signature_iter_get_current_type (&iter) == DBUS_TYPE_VARIANT);
00500 boolres = dbus_signature_iter_next (&iter);
00501 _dbus_assert (!boolres);
00502
00503 sig = DBUS_TYPE_DICT_ENTRY_AS_STRING;
00504 _dbus_assert (!dbus_signature_validate (sig, NULL));
00505
00506 sig = DBUS_TYPE_ARRAY_AS_STRING;
00507 _dbus_assert (!dbus_signature_validate (sig, NULL));
00508
00509 sig = DBUS_TYPE_UINT32_AS_STRING
00510 DBUS_TYPE_ARRAY_AS_STRING;
00511 _dbus_assert (!dbus_signature_validate (sig, NULL));
00512
00513 sig = DBUS_TYPE_ARRAY_AS_STRING
00514 DBUS_TYPE_DICT_ENTRY_AS_STRING;
00515 _dbus_assert (!dbus_signature_validate (sig, NULL));
00516
00517 sig = DBUS_DICT_ENTRY_BEGIN_CHAR_AS_STRING;
00518 _dbus_assert (!dbus_signature_validate (sig, NULL));
00519
00520 sig = DBUS_DICT_ENTRY_END_CHAR_AS_STRING;
00521 _dbus_assert (!dbus_signature_validate (sig, NULL));
00522
00523 sig = DBUS_DICT_ENTRY_BEGIN_CHAR_AS_STRING
00524 DBUS_TYPE_INT32_AS_STRING;
00525 _dbus_assert (!dbus_signature_validate (sig, NULL));
00526
00527 sig = DBUS_DICT_ENTRY_BEGIN_CHAR_AS_STRING
00528 DBUS_TYPE_INT32_AS_STRING
00529 DBUS_TYPE_STRING_AS_STRING;
00530 _dbus_assert (!dbus_signature_validate (sig, NULL));
00531
00532 sig = DBUS_STRUCT_END_CHAR_AS_STRING
00533 DBUS_STRUCT_BEGIN_CHAR_AS_STRING;
00534 _dbus_assert (!dbus_signature_validate (sig, NULL));
00535
00536 sig = DBUS_STRUCT_BEGIN_CHAR_AS_STRING
00537 DBUS_TYPE_BOOLEAN_AS_STRING;
00538 _dbus_assert (!dbus_signature_validate (sig, NULL));
00539 return TRUE;
00540 #if 0
00541 oom:
00542 _dbus_assert_not_reached ("out of memory");
00543 return FALSE;
00544 #endif
00545 }
00546
00547 #endif
00548