2 * Copyright (c) 2020 Samsung Electronics Co., Ltd. All rights reserved.
4 * Licensed under the Apache License, Version 2.0 (the "License");
5 * you may not use this file except in compliance with the License.
6 * You may obtain a copy of the License at
8 * http://www.apache.org/licenses/LICENSE-2.0
10 * Unless required by applicable law or agreed to in writing, software
11 * distributed under the License is distributed on an "AS IS" BASIS,
12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13 * See the License for the specific language governing permissions and
14 * limitations under the License.
20 #include "include/bundle.h"
21 #include "include/bundle_internal.h"
23 #include "bundle-internal.h"
24 #include "exception-internal.h"
25 #include "export-api-internal.h"
26 #include "json-internal.h"
28 using namespace tizen_base::internal;
30 extern "C" EXPORT_API bundle* bundle_create(void) {
31 auto* h = new (std::nothrow) Bundle();
33 set_last_result(BUNDLE_ERROR_OUT_OF_MEMORY);
37 set_last_result(BUNDLE_ERROR_NONE);
38 return reinterpret_cast<bundle*>(h);
41 extern "C" EXPORT_API int bundle_free(bundle* b) {
43 return BUNDLE_ERROR_INVALID_PARAMETER;
45 auto* h = reinterpret_cast<Bundle*>(b);
47 return BUNDLE_ERROR_NONE;
50 extern "C" EXPORT_API int bundle_add_str(bundle* b,
51 const char* key, const char* str) {
52 if (b == nullptr || key == nullptr || strlen(key) == 0 || str == nullptr)
53 return BUNDLE_ERROR_INVALID_PARAMETER;
55 auto* h = reinterpret_cast<Bundle*>(b);
56 std::vector<unsigned char> value(str, str + (strlen(str) + 1));
60 key_info = new KeyInfo(BUNDLE_TYPE_STR, key, std::move(value));
61 } catch (const Exception& e) {
62 return e.GetErrorCode();
63 } catch (const std::bad_alloc& ba) {
64 return BUNDLE_ERROR_OUT_OF_MEMORY;
68 h->Add(std::shared_ptr<KeyInfo>(key_info));
69 } catch (const Exception& e) {
70 return e.GetErrorCode();
73 return BUNDLE_ERROR_NONE;
76 extern "C" EXPORT_API int bundle_get_str(bundle* b,
77 const char* key, char** str) {
78 if (b == nullptr || key == nullptr)
79 return BUNDLE_ERROR_INVALID_PARAMETER;
81 auto* h = reinterpret_cast<Bundle*>(b);
82 std::shared_ptr<KeyInfo> key_info;
84 key_info = h->Get(key);
85 } catch (const Exception& e) {
86 return e.GetErrorCode();
89 if (key_info->GetType() != BUNDLE_TYPE_STR)
90 return BUNDLE_ERROR_INVALID_PARAMETER;
93 auto& values = key_info->GetValues();
94 auto& value = const_cast<std::unique_ptr<unsigned char[]>&>(values[0]);
95 *str = reinterpret_cast<char*>(&value[0]);
98 return BUNDLE_ERROR_NONE;
101 extern "C" EXPORT_API int bundle_add(bundle* b, const char* key,
103 return bundle_add_str(b, key, val);
106 extern "C" EXPORT_API int bundle_del(bundle* b, const char* key) {
107 if (b == nullptr || key == nullptr || strlen(key) == 0)
108 return BUNDLE_ERROR_INVALID_PARAMETER;
110 auto* h = reinterpret_cast<Bundle*>(b);
113 } catch (const Exception& e) {
114 return e.GetErrorCode();
117 return BUNDLE_ERROR_NONE;
120 extern "C" EXPORT_API const char* bundle_get_val(bundle* b, const char* key) {
122 int ret = bundle_get_str(b, key, &val);
123 set_last_result(ret);
127 extern "C" EXPORT_API int bundle_get_count(bundle* b) {
131 auto* h = reinterpret_cast<Bundle*>(b);
132 set_last_result(BUNDLE_ERROR_NONE);
136 extern "C" EXPORT_API void bundle_iterate(bundle* b,
137 bundle_iterate_cb_t callback, void* user_data) {
138 if (b == nullptr || callback == nullptr) {
139 set_last_result(BUNDLE_ERROR_INVALID_PARAMETER);
143 auto* h = reinterpret_cast<Bundle*>(b);
144 for (const auto& kv : h->GetMap()) {
145 auto& key_info = kv.second;
146 auto& values = key_info->GetValues();
147 auto& value = const_cast<std::unique_ptr<unsigned char[]>&>(values[0]);
148 auto* val = reinterpret_cast<char*>(&value[0]);
149 callback(key_info->GetKey().c_str(), val, user_data);
152 set_last_result(BUNDLE_ERROR_NONE);
155 extern "C" EXPORT_API void bundle_foreach(bundle* b,
156 bundle_iterator_t callback, void* user_data) {
157 if (b == nullptr || callback == nullptr) {
158 set_last_result(BUNDLE_ERROR_INVALID_PARAMETER);
162 auto* h = reinterpret_cast<Bundle*>(b);
163 auto it = h->GetMap().begin();
164 while (it != h->GetMap().end()) {
165 auto& key_info = it->second;
167 callback(key_info->GetKey().c_str(), key_info->GetType(),
168 reinterpret_cast<bundle_keyval_t*>(key_info.get()), user_data);
171 set_last_result(BUNDLE_ERROR_NONE);
174 extern "C" EXPORT_API int bundle_keyval_get_type(bundle_keyval_t* kv) {
176 set_last_result(BUNDLE_ERROR_INVALID_PARAMETER);
180 auto* key_info = reinterpret_cast<KeyInfo*>(kv);
181 set_last_result(BUNDLE_ERROR_NONE);
182 return key_info->GetType();
185 extern "C" EXPORT_API int bundle_keyval_type_is_array(bundle_keyval_t* kv) {
186 int type = bundle_keyval_get_type(kv);
190 set_last_result(BUNDLE_ERROR_NONE);
191 if (type & BUNDLE_TYPE_ARRAY)
197 extern "C" EXPORT_API int bundle_keyval_type_is_measurable(
198 bundle_keyval_t* kv) {
199 int type = bundle_keyval_get_type(kv);
203 set_last_result(BUNDLE_ERROR_NONE);
204 if (type & BUNDLE_TYPE_MEASURABLE)
210 extern "C" EXPORT_API int bundle_keyval_get_basic_val(bundle_keyval_t* kv,
211 void** val, size_t* size) {
213 return BUNDLE_ERROR_INVALID_PARAMETER;
215 auto* key_info = reinterpret_cast<KeyInfo*>(kv);
216 if (key_info->IsArray())
217 return BUNDLE_ERROR_INVALID_PARAMETER;
220 auto& values = key_info->GetValues();
221 auto& value = const_cast<std::unique_ptr<unsigned char[]>&>(values[0]);
222 *val = reinterpret_cast<void*>(&value[0]);
226 auto& values_size = key_info->GetValuesSize();
227 *size = reinterpret_cast<size_t>(values_size[0]);
230 return BUNDLE_ERROR_NONE;
233 extern "C" EXPORT_API int bundle_keyval_get_array_val(bundle_keyval_t* kv,
234 void*** array_val, unsigned int* array_len, size_t** array_item_size) {
236 return BUNDLE_ERROR_INVALID_PARAMETER;
238 auto* key_info = reinterpret_cast<KeyInfo*>(kv);
239 if (!key_info->IsArray())
240 return BUNDLE_ERROR_INVALID_PARAMETER;
242 auto& values = const_cast<std::vector<std::unique_ptr<unsigned char[]>>&>(
243 key_info->GetValues());
246 *array_val = reinterpret_cast<void**>(&values[0]);
249 *array_len = static_cast<unsigned int>(values.size());
251 if (array_item_size) {
252 auto& values_size = const_cast<std::vector<std::size_t>&>(
253 key_info->GetValuesSize());
254 *array_item_size = reinterpret_cast<size_t*>(&values_size[0]);
257 return BUNDLE_ERROR_NONE;
260 extern "C" EXPORT_API bundle_keyval_t* bundle_keyval_dup(
261 const bundle_keyval_t* kv) {
263 set_last_result(BUNDLE_ERROR_INVALID_PARAMETER);
267 auto* keyval = const_cast<bundle_keyval_t*>(kv);
268 auto* key_info = reinterpret_cast<KeyInfo*>(keyval);
272 k = new KeyInfo(*key_info);
273 } catch (const Exception& e) {
274 set_last_result(e.GetErrorCode());
276 } catch (const std::bad_alloc& ba) {
277 set_last_result(BUNDLE_ERROR_OUT_OF_MEMORY);
281 set_last_result(BUNDLE_ERROR_NONE);
282 return reinterpret_cast<bundle_keyval_t*>(k);
285 extern "C" EXPORT_API int bundle_keyval_free(bundle_keyval_t* kv) {
287 return BUNDLE_ERROR_INVALID_PARAMETER;
289 auto* key_info = reinterpret_cast<KeyInfo*>(kv);
291 return BUNDLE_ERROR_NONE;
294 extern "C" EXPORT_API bundle* bundle_dup(bundle* b_from) {
295 if (b_from == nullptr) {
296 set_last_result(BUNDLE_ERROR_INVALID_PARAMETER);
300 auto* h = reinterpret_cast<Bundle*>(b_from);
301 auto* b = new (std::nothrow) Bundle(*h);
303 set_last_result(BUNDLE_ERROR_OUT_OF_MEMORY);
307 set_last_result(BUNDLE_ERROR_NONE);
308 return reinterpret_cast<bundle*>(b);
311 extern "C" EXPORT_API int bundle_encode(bundle *b, bundle_raw** raw, int* len) {
312 if (b == nullptr || raw == nullptr || len == nullptr)
313 return BUNDLE_ERROR_INVALID_PARAMETER;
315 auto* h = reinterpret_cast<Bundle*>(b);
316 *raw = reinterpret_cast<bundle_raw*>(h->Encode());
317 *len = strlen(reinterpret_cast<char*>(*raw));
318 return BUNDLE_ERROR_NONE;
321 extern "C" EXPORT_API int bundle_free_encoded_rawdata(bundle_raw **r) {
322 if (r == nullptr || *r == nullptr)
323 return BUNDLE_ERROR_INVALID_PARAMETER;
327 return BUNDLE_ERROR_NONE;
330 extern "C" EXPORT_API bundle* bundle_decode(const bundle_raw* r,
331 const int data_size) {
333 set_last_result(BUNDLE_ERROR_INVALID_PARAMETER);
339 auto* raw = const_cast<bundle_raw*>(r);
340 b = new Bundle(static_cast<unsigned char*>(raw), data_size);
341 } catch (const Exception& e) {
342 set_last_result(e.GetErrorCode());
344 } catch (const std::bad_alloc& ba) {
345 set_last_result(BUNDLE_ERROR_OUT_OF_MEMORY);
349 set_last_result(BUNDLE_ERROR_NONE);
350 return reinterpret_cast<bundle*>(b);
353 extern "C" EXPORT_API int bundle_encode_raw(bundle* b, bundle_raw** r,
355 if (b == nullptr || r == nullptr || len == nullptr)
356 return BUNDLE_ERROR_INVALID_PARAMETER;
358 auto* h = reinterpret_cast<Bundle*>(b);
360 *r = reinterpret_cast<bundle_raw*>(h->EncodeRaw(len));
361 } catch (const Exception& e) {
362 return e.GetErrorCode();
364 return BUNDLE_ERROR_NONE;
367 extern "C" EXPORT_API bundle* bundle_decode_raw(const bundle_raw* r,
368 const int data_size) {
370 set_last_result(BUNDLE_ERROR_INVALID_PARAMETER);
376 auto* raw = const_cast<bundle_raw*>(r);
377 b = new Bundle(static_cast<unsigned char*>(raw), data_size, false);
378 } catch (const Exception& e) {
379 set_last_result(e.GetErrorCode());
381 } catch (const std::bad_alloc& ba) {
382 set_last_result(BUNDLE_ERROR_OUT_OF_MEMORY);
386 set_last_result(BUNDLE_ERROR_NONE);
387 return reinterpret_cast<bundle*>(b);
390 extern "C" EXPORT_API int bundle_get_type(bundle* b, const char* key) {
391 if (b == nullptr || key == nullptr) {
392 set_last_result(BUNDLE_ERROR_INVALID_PARAMETER);
393 return BUNDLE_TYPE_NONE;
396 auto* h = reinterpret_cast<Bundle*>(b);
397 std::shared_ptr<KeyInfo> key_info;
399 key_info = h->Get(key);
400 } catch (const Exception& e) {
401 set_last_result(e.GetErrorCode());
402 return BUNDLE_TYPE_NONE;
405 set_last_result(BUNDLE_ERROR_NONE);
406 return key_info->GetType();
409 extern "C" EXPORT_API int bundle_add_str_array(bundle* b, const char* key,
410 const char** str_array, const int len) {
411 if (b == nullptr || key == nullptr || strlen(key) == 0)
412 return BUNDLE_ERROR_INVALID_PARAMETER;
414 auto* h = reinterpret_cast<Bundle*>(b);
415 std::vector<std::vector<unsigned char>> values(len);
417 for (int i = 0; i < len; ++i) {
418 std::vector<unsigned char> value(str_array[i],
419 str_array[i] + (strlen(str_array[i]) + 1));
420 values[i] = std::move(value);
426 key_info = new KeyInfo((BUNDLE_TYPE_STR_ARRAY | BUNDLE_TYPE_ARRAY),
428 } catch (const Exception& e) {
429 return e.GetErrorCode();
433 h->Add(std::shared_ptr<KeyInfo>(key_info));
434 } catch (const Exception& e) {
435 return e.GetErrorCode();
438 return BUNDLE_ERROR_NONE;
441 extern "C" EXPORT_API const char** bundle_get_str_array(bundle* b,
442 const char* key, int* len) {
443 if (b == nullptr || key == nullptr) {
444 set_last_result(BUNDLE_ERROR_INVALID_PARAMETER);
448 auto* h = reinterpret_cast<Bundle*>(b);
449 std::shared_ptr<KeyInfo> key_info;
451 key_info = h->Get(key);
452 } catch (const Exception& e) {
453 set_last_result(e.GetErrorCode());
457 if (key_info->GetType() != BUNDLE_TYPE_STR_ARRAY) {
458 set_last_result(BUNDLE_ERROR_INVALID_PARAMETER);
462 set_last_result(BUNDLE_ERROR_NONE);
464 auto& raw_values = const_cast<std::vector<std::unique_ptr<unsigned char[]>>&>(
465 key_info->GetValues());
468 *len = static_cast<int>(raw_values.size());
470 if (raw_values.size() == 0)
473 auto** values = reinterpret_cast<unsigned char**>(&raw_values[0]);
474 return const_cast<const char**>(reinterpret_cast<char**>(values));
477 extern "C" EXPORT_API int bundle_add_byte(bundle* b, const char* key,
478 const void* bytes, const size_t size) {
479 if (b == nullptr || key == nullptr || strlen(key) == 0)
480 return BUNDLE_ERROR_INVALID_PARAMETER;
482 auto* h = reinterpret_cast<Bundle*>(b);
483 auto* p = reinterpret_cast<const unsigned char*>(bytes);
484 std::vector<unsigned char> value;
486 value.insert(value.end(), p, p + size);
490 key_info = new KeyInfo(BUNDLE_TYPE_BYTE, key, std::move(value));
491 } catch (const Exception& e) {
492 return e.GetErrorCode();
493 } catch (const std::bad_alloc& ba) {
494 return BUNDLE_ERROR_OUT_OF_MEMORY;
498 h->Add(std::shared_ptr<KeyInfo>(key_info));
499 } catch (const Exception& e) {
500 return e.GetErrorCode();
503 return BUNDLE_ERROR_NONE;
506 extern "C" EXPORT_API int bundle_get_byte(bundle* b, const char* key,
507 void** bytes, size_t* size) {
508 if (b == nullptr || key == nullptr)
509 return BUNDLE_ERROR_INVALID_PARAMETER;
511 auto* h = reinterpret_cast<Bundle*>(b);
512 std::shared_ptr<KeyInfo> key_info;
514 key_info = h->Get(key);
515 } catch (const Exception& e) {
516 return e.GetErrorCode();
519 if (key_info->GetType() != BUNDLE_TYPE_BYTE)
520 return BUNDLE_ERROR_INVALID_PARAMETER;
523 auto& values = const_cast<std::vector<std::unique_ptr<unsigned char[]>>&>(
524 key_info->GetValues());
525 if (values.size() == 0) {
528 auto& value = values[0];
529 *bytes = reinterpret_cast<void*>(&value[0]);
534 auto& values_size = key_info->GetValuesSize();
535 *size = reinterpret_cast<size_t>(values_size[0]);
538 return BUNDLE_ERROR_NONE;
541 extern "C" EXPORT_API int bundle_export_to_argv(bundle* b, char*** argv) {
542 if (b == nullptr || argv == nullptr) {
543 set_last_result(BUNDLE_ERROR_INVALID_PARAMETER);
547 auto* h = reinterpret_cast<Bundle*>(b);
548 std::vector<std::string> exported_vt;
550 exported_vt = h->Export();
551 } catch (const Exception& e) {
552 set_last_result(e.GetErrorCode());
556 int argc = exported_vt.size();
557 auto** exported_argv = reinterpret_cast<char**>(
558 calloc(argc + 1, sizeof(char*)));
559 if (exported_argv == nullptr) {
560 set_last_result(BUNDLE_ERROR_OUT_OF_MEMORY);
564 exported_argv[1] = const_cast<char*>(TAG_IMPORT_EXPORT_CHECK);
565 for (unsigned int idx = 2; idx < exported_vt.size(); idx += 2) {
566 exported_argv[idx] = strdup(exported_vt[idx].c_str());
567 if (exported_argv[idx] == nullptr) {
568 set_last_result(BUNDLE_ERROR_OUT_OF_MEMORY);
569 bundle_free_exported_argv(idx + 1, &exported_argv);
573 exported_argv[idx + 1] = strdup(exported_vt[idx + 1].c_str());
574 if (exported_argv[idx + 1] == nullptr) {
575 set_last_result(BUNDLE_ERROR_OUT_OF_MEMORY);
576 bundle_free_exported_argv(idx + 2, &exported_argv);
581 *argv = exported_argv;
582 set_last_result(BUNDLE_ERROR_NONE);
586 extern "C" EXPORT_API int bundle_free_exported_argv(int argc, char*** argv) {
587 if (argc < 2 || !argv || !*argv)
588 return BUNDLE_ERROR_INVALID_PARAMETER;
590 for (int i = 2; i < argc; i++)
591 std::free((*argv)[i]);
596 return BUNDLE_ERROR_NONE;
599 extern "C" EXPORT_API bundle* bundle_import_from_argv(int argc, char** argv) {
600 if (argv == nullptr) {
601 set_last_result(BUNDLE_ERROR_INVALID_PARAMETER);
607 b = new (std::nothrow) Bundle(argc, argv);
608 } catch (const Exception& e) {
609 set_last_result(e.GetErrorCode());
613 set_last_result(BUNDLE_ERROR_NONE);
614 return reinterpret_cast<bundle*>(b);
617 extern "C" EXPORT_API int bundle_compare(bundle* b1, bundle* b2) {
618 if (b1 == nullptr || b2 == nullptr)
621 auto* h1 = reinterpret_cast<Bundle*>(b1);
622 auto* h2 = reinterpret_cast<Bundle*>(b2);
629 extern "C" EXPORT_API int bundle_set_str_array_element(bundle* b,
630 const char* key, const unsigned int idx, const char* val) {
631 if (b == nullptr || key == nullptr || val == nullptr)
632 return BUNDLE_ERROR_INVALID_PARAMETER;
634 auto len = strlen(val) + 1;
635 auto* p = reinterpret_cast<unsigned char*>(const_cast<char*>(val));
636 std::vector<unsigned char> value(p, p + len);
638 auto* h = reinterpret_cast<Bundle*>(b);
640 h->Set(key, idx, std::move(value));
641 } catch (const Exception& e) {
642 return e.GetErrorCode();
645 return BUNDLE_ERROR_NONE;
648 extern "C" EXPORT_API int bundle_add_byte_array(bundle* b,
649 const char* key, const unsigned int len) {
650 return bundle_init_byte_array(b, key, len);
653 extern "C" EXPORT_API int bundle_init_byte_array(bundle* b,
654 const char* key, const unsigned int len) {
655 if (b == nullptr || key == nullptr || strlen(key) == 0)
656 return BUNDLE_ERROR_INVALID_PARAMETER;
658 auto* h = reinterpret_cast<Bundle*>(b);
662 std::vector<std::vector<unsigned char>> values(len);
663 key_info = new KeyInfo(Bundle::Type::ByteArray, key, std::move(values));
664 } catch (const Exception& e) {
665 return e.GetErrorCode();
666 } catch (const std::bad_alloc& ba) {
667 return BUNDLE_ERROR_OUT_OF_MEMORY;
668 } catch (const std::length_error&) {
669 return BUNDLE_ERROR_OUT_OF_MEMORY;
673 h->Add(std::shared_ptr<KeyInfo>(key_info));
674 } catch (const Exception& e) {
675 return e.GetErrorCode();
678 return BUNDLE_ERROR_NONE;
681 extern "C" EXPORT_API int bundle_get_byte_array(bundle* b,
682 const char* key, void*** bytes_array, unsigned int* len,
683 unsigned int** array_element_size) {
684 if (b == nullptr || key == nullptr)
685 return BUNDLE_ERROR_INVALID_PARAMETER;
687 auto* h = reinterpret_cast<Bundle*>(b);
688 std::shared_ptr<KeyInfo> key_info;
690 key_info = h->Get(key);
691 } catch (const Exception& e) {
692 return e.GetErrorCode();
695 if (key_info->GetType() != BUNDLE_TYPE_BYTE_ARRAY)
696 return BUNDLE_ERROR_INVALID_PARAMETER;
698 auto& raw_values = const_cast<std::vector<std::unique_ptr<unsigned char[]>>&>(
699 key_info->GetValues());
702 auto** values = reinterpret_cast<unsigned char**>(&raw_values[0]);
703 *bytes_array = reinterpret_cast<void**>(values);
707 *len = static_cast<unsigned int>(raw_values.size());
709 if (array_element_size) {
710 auto& raw_values_size = const_cast<std::vector<unsigned int>&>(
711 key_info->GetUValuesSize());
712 *array_element_size = reinterpret_cast<unsigned int*>(&raw_values_size[0]);
715 return BUNDLE_ERROR_NONE;
718 extern "C" EXPORT_API int bundle_set_byte_array_element(bundle* b,
719 const char* key, const unsigned int idx,
720 const void* bytes, const size_t size) {
721 if (b == nullptr || key == nullptr || size <= 0)
722 return BUNDLE_ERROR_INVALID_PARAMETER;
724 std::vector<unsigned char> value;
726 auto* p = reinterpret_cast<unsigned char*>(const_cast<void*>(bytes));
727 value.insert(value.end(), p, p + size);
730 auto* h = reinterpret_cast<Bundle*>(b);
732 h->Set(key, idx, std::move(value));
733 } catch (const Exception& e) {
734 return e.GetErrorCode();
737 return BUNDLE_ERROR_NONE;
740 extern "C" EXPORT_API int bundle_to_json(bundle* b, char** json) {
741 if (b == nullptr || json == nullptr)
742 return BUNDLE_ERROR_INVALID_PARAMETER;
744 auto* h = reinterpret_cast<Bundle*>(b);
747 *json = strdup(js.ToString().c_str());
748 } catch (const Exception& e) {
749 return e.GetErrorCode();
752 return BUNDLE_ERROR_NONE;
755 extern "C" EXPORT_API int bundle_from_json(const char* json, bundle** b) {
756 if (json == nullptr || b == nullptr)
757 return BUNDLE_ERROR_INVALID_PARAMETER;
761 *b = reinterpret_cast<bundle*>(js.ToBundle());
762 } catch (const Exception& e) {
763 return e.GetErrorCode();
766 return BUNDLE_ERROR_NONE;