Modify directory hierarchy 97/312197/2
authorHwankyu Jhun <h.jhun@samsung.com>
Wed, 5 Jun 2024 04:47:11 +0000 (13:47 +0900)
committerHwankyu Jhun <h.jhun@samsung.com>
Wed, 5 Jun 2024 04:48:52 +0000 (13:48 +0900)
Source directories are moved to src.

- src/bundle
- src/parcel
- src/tizen-database
- src/tizen-shared-queue

Change-Id: I3b0dd75dd1d18d5e6611d08e90754df3b393e9d5
Signed-off-by: Hwankyu Jhun <h.jhun@samsung.com>
78 files changed:
CMakeLists.txt
bundle.pc.in [deleted file]
cmake/Modules/ApplyPkgConfig.cmake [new file with mode: 0644]
include/SLP_bundle_PG.h [deleted file]
include/bundle.h [deleted file]
include/bundle_cpp.h [deleted file]
include/bundle_internal.h [deleted file]
packaging/bundle.spec
parcel/CMakeLists.txt [deleted file]
parcel/api/parcel.h [deleted file]
parcel/common.hh [deleted file]
parcel/log_private.hh [deleted file]
parcel/parcel.cc [deleted file]
parcel/parcel.hh [deleted file]
parcel/parcel.pc.in [deleted file]
parcel/parcel_implementation.hh [deleted file]
parcel/parcelable.hh [deleted file]
parcel/stub.cc [deleted file]
src/CMakeLists.txt [new file with mode: 0644]
src/bundle-internal.cc [deleted file]
src/bundle-internal.h [deleted file]
src/bundle/CMakeLists.txt [new file with mode: 0644]
src/bundle/bundle-internal.cc [new file with mode: 0644]
src/bundle/bundle-internal.h [new file with mode: 0644]
src/bundle/bundle.pc.in [new file with mode: 0644]
src/bundle/bundle_cpp.cc [new file with mode: 0644]
src/bundle/bundle_cpp_implementation.h [new file with mode: 0644]
src/bundle/exception-internal.h [new file with mode: 0644]
src/bundle/export-api-internal.h [new file with mode: 0644]
src/bundle/include/SLP_bundle_PG.h [new file with mode: 0644]
src/bundle/include/bundle.h [new file with mode: 0644]
src/bundle/include/bundle_cpp.h [new file with mode: 0644]
src/bundle/include/bundle_internal.h [new file with mode: 0644]
src/bundle/json-internal.cc [new file with mode: 0644]
src/bundle/json-internal.h [new file with mode: 0644]
src/bundle/key-info-internal.cc [new file with mode: 0644]
src/bundle/key-info-internal.h [new file with mode: 0644]
src/bundle/log-private.h [new file with mode: 0644]
src/bundle/stub.cc [new file with mode: 0644]
src/bundle_cpp.cc [deleted file]
src/bundle_cpp_implementation.h [deleted file]
src/exception-internal.h [deleted file]
src/export-api-internal.h [deleted file]
src/json-internal.cc [deleted file]
src/json-internal.h [deleted file]
src/key-info-internal.cc [deleted file]
src/key-info-internal.h [deleted file]
src/log-private.h [deleted file]
src/parcel/CMakeLists.txt [new file with mode: 0644]
src/parcel/api/parcel.h [new file with mode: 0644]
src/parcel/common.hh [new file with mode: 0644]
src/parcel/log_private.hh [new file with mode: 0644]
src/parcel/parcel.cc [new file with mode: 0644]
src/parcel/parcel.hh [new file with mode: 0644]
src/parcel/parcel.pc.in [new file with mode: 0644]
src/parcel/parcel_implementation.hh [new file with mode: 0644]
src/parcel/parcelable.hh [new file with mode: 0644]
src/parcel/stub.cc [new file with mode: 0644]
src/stub.cc [deleted file]
src/tizen-database/CMakeLists.txt [new file with mode: 0644]
src/tizen-database/README.md [new file with mode: 0644]
src/tizen-database/database.hpp [new file with mode: 0644]
src/tizen-database/tizen-database.pc.in [new file with mode: 0644]
src/tizen-shared-queue/CMakeLists.txt [new file with mode: 0644]
src/tizen-shared-queue/shared-queue.hpp [new file with mode: 0644]
src/tizen-shared-queue/tizen-shared-queue.pc.in [new file with mode: 0644]
tests/CMakeLists.txt
tests/bundle_unittests/CMakeLists.txt
tests/parcel_unittests/CMakeLists.txt
tests/tizen-database_unittests/CMakeLists.txt
tests/tizen-shared-queue_unittests/CMakeLists.txt
tizen-database/CMakeLists.txt [deleted file]
tizen-database/README.md [deleted file]
tizen-database/database.hpp [deleted file]
tizen-database/tizen-database.pc.in [deleted file]
tizen-shared-queue/CMakeLists.txt [deleted file]
tizen-shared-queue/shared-queue.hpp [deleted file]
tizen-shared-queue/tizen-shared-queue.pc.in [deleted file]

index b22b34afa722f6a07e9f1d9625c571f8bc43e15d..aaea2db51e61c903702f30868627aa0eb959921c 100644 (file)
@@ -1,79 +1,63 @@
-CMAKE_MINIMUM_REQUIRED(VERSION 2.8)
-PROJECT(bundle C CXX)
-IF("${VERSION}" STREQUAL "")
-       MESSAGE(FATAL_ERROR "VERSION is not defined")
-ENDIF()
-STRING(REGEX MATCH "^[0-9]+" VERSION_MAJOR ${VERSION})
-IF("${VERSION_MAJOR}" STREQUAL "")
-       MESSAGE(FATAL_ERROR "can't get VERSION_MAJOR")
-ENDIF()
+CMAKE_MINIMUM_REQUIRED(VERSION 3.2)
 
-INCLUDE(FindPkgConfig)
-PKG_CHECK_MODULES(pkgs REQUIRED
-       glib-2.0 dlog capi-base-common json-glib-1.0
-)
-
-FOREACH(flag ${pkgs_CFLAGS})
-       SET(EXTRA_CFLAGS "${EXTRA_CFLAGS} ${flag}")
-ENDFOREACH(flag)
-SET(EXTRA_CFLAGS "${EXTRA_CFLAGS} -fvisibility=hidden -flto -Wall -Werror -Winline -Wno-noexcept-type")
-
-SET(CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} ${EXTRA_CFLAGS} -std=c++17")
-SET(CMAKE_CXX_FLAGS_DEBUG "-O0 -g")
-SET(CMAKE_CXX_FLAGS_RELEASE "-O2")
-
-INCLUDE_DIRECTORIES(${CMAKE_CURRENT_SOURCE_DIR}/include)
-INCLUDE_DIRECTORIES(${CMAKE_CURRENT_SOURCE_DIR}/src)
-INCLUDE_DIRECTORIES(${CMAKE_CURRENT_SOURCE_DIR}/)
+PROJECT(bundle)
 
-AUX_SOURCE_DIRECTORY(src SOURCES)
-
-ADD_LIBRARY (${PROJECT_NAME} SHARED ${SOURCES})
+SET(PREFIX ${CMAKE_INSTALL_PREFIX})
+SET(VERSION ${FULLVER})
 
-SET_TARGET_PROPERTIES(bundle PROPERTIES SOVERSION ${VERSION_MAJOR})
-SET_TARGET_PROPERTIES(bundle PROPERTIES VERSION "${VERSION}")
+SET(CMAKE_C_FLAGS "${CMAKE_C_FLAGS} -Wall")
+SET(CMAKE_C_FLAGS "${CMAKE_C_FLAGS} -Werror")
+SET(CMAKE_C_FLAGS "${CMAKE_C_FLAGS} -Wl,-zdefs")
+SET(CMAKE_C_FLAGS "${CMAKE_C_FLAGS} -Winline")
+SET(CMAKE_C_FLAGS "${CMAKE_C_FLAGS} -Wno-noexcept-type")
+SET(CMAKE_C_FLAGS "${CMAKE_C_FLAGS} -fvisibility=hidden")
+SET(CMAKE_C_FLAGS "${CMAKE_C_FLAGS} -flto")
 
-SET_TARGET_PROPERTIES(${PROJECT_NAME} PROPERTIES COMPILE_FLAGS "${EXTRA_CFLAGS} -fPIE")
-SET_TARGET_PROPERTIES(${PROJECT_NAME} PROPERTIES LINK_FLAGS "-pie")
-TARGET_LINK_LIBRARIES(${PROJECT_NAME} ${pkgs_LDFLAGS})
+SET(CMAKE_C_FLAGS_DEBUG "-O0 -g")
+SET(CMAKE_C_FLAGS_RELEASE "-O2")
 
-### Make pkgconfig file
-SET(PREFIX ${CMAKE_INSTALL_PREFIX})
-CONFIGURE_FILE(${CMAKE_SOURCE_DIR}/bundle.pc.in ${CMAKE_BINARY_DIR}/bundle.pc @ONLY)
+SET(CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} ${EXTRA_C_FLAGS} -std=c++17")
+SET(CMAKE_CXX_FLAGS_DEBUG "-O0 -g")
+SET(CMAKE_CXX_FLAGS_RELEASE "-O2")
 
-### Install
-INSTALL(TARGETS bundle DESTINATION ${LIB_INSTALL_DIR})
-INSTALL(DIRECTORY ${CMAKE_SOURCE_DIR}/include/ DESTINATION include/)
-INSTALL(FILES ${CMAKE_BINARY_DIR}/bundle.pc DESTINATION ${LIB_INSTALL_DIR}/pkgconfig/)
+SET(CMAKE_MODULE_PATH ${CMAKE_MODULE_PATH}
+  "${CMAKE_CURRENT_SOURCE_DIR}/cmake/Modules/")
 
-ADD_SUBDIRECTORY(parcel)
-ADD_DEPENDENCIES(parcel bundle)
+SET(TARGET_BUNDLE "bundle")
+SET(TARGET_PARCEL "parcel")
+SET(TARGET_TIZEN_DATABASE "tizen-database")
+SET(TARGET_TIZEN_SHARED_QUEUE "tizen-shared-queue")
+SET(TARGET_BUNDLE_UNITTESTS "bundle_unittests")
+SET(TARGET_PARCEL_UNITTESTS "parcel_unittests")
+SET(TARGET_TIZEN_DATABASE_UNITTESTS "tizen-database_unittests")
+SET(TARGET_TIZEN_SHARED_QUEUE_UNITTESTS "tizen-shared-queue_unittests")
 
-ADD_SUBDIRECTORY(tizen-database)
-ADD_SUBDIRECTORY(tizen-shared-queue)
+INCLUDE(FindPkgConfig)
+INCLUDE(ApplyPkgConfig)
 
-IF(NOT DEFINED MINIMUM_BUILD)
-ENABLE_TESTING()
-SET(BUNDLE_UNITTESTS bundle_unittests)
-ADD_TEST(NAME ${BUNDLE_UNITTESTS} COMMAND ${BUNDLE_UNITTESTS}
-        WORKING_DIRECTORY ${CMAKE_SOURCE_DIR}/tests/bundle_unittests)
+PKG_CHECK_MODULES(CAPI_BASE_COMMON_DEPS REQUIRED capi-base-common)
+PKG_CHECK_MODULES(DLOG_DEPS REQUIRED dlog)
+PKG_CHECK_MODULES(GLIB_DEPS REQUIRED glib-2.0)
+PKG_CHECK_MODULES(GMOCK_DEPS REQUIRED gmock)
+PKG_CHECK_MODULES(JSON_GLIB_DEPS REQUIRED json-glib-1.0)
+PKG_CHECK_MODULES(SQLITE3_DEPS REQUIRED sqlite3)
 
+ADD_SUBDIRECTORY(src)
 ADD_SUBDIRECTORY(tests)
-ADD_DEPENDENCIES(bundle_unittests bundle)
 
-SET(PARCEL_UNITTESTS parcel_unittests)
-ADD_TEST(NAME ${PARCEL_UNITTESTS} COMMAND ${PARCEL_UNITTESTS}
-        WORKING_DIRECTORY ${CMAKE_SOURCE_DIR}/tests/parcel_unittests)
+ENABLE_TESTING()
+ADD_TEST(NAME ${TARGET_BUNDLE_UNITTESTS}
+  COMMAND ${TARGET_BUNDLE_UNITTESTS}
+  WORKING_DIRECTORY ${CMAKE_SOURCE_DIR}/tests/bundle_unittests)
 
-ADD_DEPENDENCIES(parcel_unittests parcel)
+ADD_TEST(NAME ${TARGET_PARCEL_UNITTESTS}
+  COMMAND ${TARGET_PARCEL_UNITTESTS}
+  WORKING_DIRECTORY ${CMAKE_SOURCE_DIR}/tests/parcel_unittests)
 
-SET(TIZEN_DATABASE_UNITTESTS tizen-database_unittests)
-ADD_TEST(NAME ${TIZEN_DATABASE_UNITTESTS} COMMAND ${TIZEN_DATABASE_UNITTESTS}
-        WORKING_DIRECTORY ${CMAKE_SOURCE_DIR}/tests/tizen-database_unittests)
+ADD_TEST(NAME ${TARGET_TIZEN_DATABASE_UNITTESTS} 
+  COMMAND ${TARGET_TIZEN_DATABASE_UNITTESTS}
+  WORKING_DIRECTORY ${CMAKE_SOURCE_DIR}/tests/tizen-database_unittests)
 
-SET(TIZEN_SHARED_QUEUE_UNITTESTS tizen-shared-queue_unittests)
-ADD_TEST(NAME ${TIZEN_SHARED_QUEUE_UNITTESTS}
-  COMMAND ${TIZEN_SHARED_QUEUE_UNITTESTS}
+ADD_TEST(NAME ${TARGET_TIZEN_SHARED_QUEUE_UNITTESTS}
+  COMMAND ${TARGET_TIZEN_SHARED_QUEUE_UNITTESTS}
   WORKING_DIRECTORY ${CMAKE_SOURCE_DIR}/tests/tizen-shared-queue_unittests)
-
-ENDIF(NOT DEFINED MINIMUM_BUILD)
diff --git a/bundle.pc.in b/bundle.pc.in
deleted file mode 100644 (file)
index c05c076..0000000
+++ /dev/null
@@ -1,14 +0,0 @@
-# Package Information for pkg-config
-
-prefix=@PREFIX@
-exec_prefix=${prefix}
-libdir=@LIB_INSTALL_DIR@
-includedir=${prefix}/include
-
-Name: bundle
-Description: Simple string key/val dictionary library
-Version: @VERSION@
-Requires: capi-base-common
-Libs: -L${libdir} -lbundle
-Cflags: -I${includedir}
-cppflags: -I${includedir}
diff --git a/cmake/Modules/ApplyPkgConfig.cmake b/cmake/Modules/ApplyPkgConfig.cmake
new file mode 100644 (file)
index 0000000..b71e5a6
--- /dev/null
@@ -0,0 +1,35 @@
+# Copyright (c) 2024 Samsung Electronics Co., Ltd All Rights Reserved
+# Use of this source code is governed by a BSD-style license that can be
+# found in the LICENSE file.
+
+#
+# This function applies external (out of source tree) dependencies
+# to given target. Arguments are:
+#   TARGET - valid cmake target
+#   PRIVACY - dependency can be inherited by dependent targets or not:
+#     PUBLIC - this should be used by default, cause compile/link flags passing
+#     PRIVATE - do not passes any settings to dependent targets,
+#               may be usefull for static libraries from the inside of the project
+# Argument ARGV2 and following are supposed to be names of checked pkg config
+# packages. This function will use variables created by check_pkg_modules().
+#  - ${DEP_NAME}_LIBRARIES
+#  - ${DEP_NAME}_INCLUDE_DIRS
+#  - ${DEP_NAME}_CFLAGS
+#
+FUNCTION(APPLY_PKG_CONFIG TARGET PRIVACY)
+  MATH(EXPR DEST_INDEX "${ARGC}-1")
+  FOREACH(I RANGE 2 ${DEST_INDEX})
+    IF(NOT ${ARGV${I}}_FOUND)
+      MESSAGE(FATAL_ERROR "Not found dependency - ${ARGV${I}}_FOUND")
+    ENDIF(NOT ${ARGV${I}}_FOUND)
+    TARGET_LINK_LIBRARIES(${TARGET} ${PRIVACY} "${${ARGV${I}}_LIBRARIES}")
+    TARGET_INCLUDE_DIRECTORIES(${TARGET} ${PRIVACY} SYSTEM "${${ARGV${I}}_INCLUDE_DIRS}")
+    STRING(REPLACE ";" " " CFLAGS_STR "${${ARGV${I}}_CFLAGS}")
+    SET(CFLAGS_LIST ${CFLAGS_STR})
+    SEPARATE_ARGUMENTS(CFLAGS_LIST)
+    FOREACH(OPTION ${CFLAGS_LIST})
+      TARGET_COMPILE_OPTIONS(${TARGET} ${PRIVACY} ${OPTION})
+    ENDFOREACH(OPTION)
+    SET_TARGET_PROPERTIES(${TARGET} PROPERTIES SKIP_BUILD_RPATH true)
+  ENDFOREACH(I RANGE 2 ${DEST_INDEX})
+ENDFUNCTION(APPLY_PKG_CONFIG TARGET PRIVACY)
diff --git a/include/SLP_bundle_PG.h b/include/SLP_bundle_PG.h
deleted file mode 100644 (file)
index 2420441..0000000
+++ /dev/null
@@ -1,156 +0,0 @@
-/*
- * Copyright (c) 2000 - 2020 Samsung Electronics Co., Ltd. All rights reserved.
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-/**
- *
- * @ingroup SLP_PG
- * @defgroup bundle_PG Bundle
- * @brief A simple string-based dictionary ADT.
- * @{
-
-<h1 class="pg">Introduction</h1>
-
-<p> Bundle is a string based Dictionary ADT. A dictionary is an ordered or unordered list of key element pairs, where keys are used to locate elements in the list. </p><br/>
-
-<p> ADT (Abstract data type) An Abstract Data type is defined as a mathematical model of the data objects that make up a data type as well
-as the functions that operate on these objects.</p>
-
-<h1 class="pg">Features</h1>
-<ul>
-       <li> Bundle provides string based Dictionary ADT to
-               map/store key-value pairs. Eg. Clock </li>
-       <li> Bundle  provides Application Data Exchange (ADE):
-               <ul>
-                       <li> Transfer application argument between caller and callee by creating a bundle and storing key-value pairs in it. </li>
-                       <li> This bundle object can be passed between applications by encoding and decoding the bundle objects. </li>
-               </ul> </li>
-
-</ul>
-
-<h1 class="pg">Properties</h1>
-<ul>
-       <li>Only string type is allowed for key and value.</li>
-       <li>Each key and value is duplicated into the bundle object.</li>
-       <li>Unlimited number of key/value pairs. (Memory limit is still to be considered)</li>
-       <li>No key overlap : You cannot assign new values with existing key.</li>
-</ul>
-
-<h1 class="pg">Bundle Logical View diagram</h1>
-\image html SLP_bundle_PG_images_logical_view.png "Picture 1. Logical view"
-
-
-<h1 class="pg">Functional architecture diagram</h1>
-\image html SLP_bundle_PG_image01.png "Picture 2. Functional architecture"
-
-<p> Bundle requests are received by the Bundle interface. It passes the requests to bundle manager. Bundle Manager checks the type of the request and handles it accordingly. If string key-value needs to be handled in the request it interacts with String manager to provide the required functionality. If the request is based on array of string key-value pair then, Bundle manager interacts with Array manager to provide the required functionality.</p>
-
-<h1 class="pg"> Bundle encode decode life cycle </h1>
-\image html SLP_bundle_PG_images_encode_decode.png "Picture 2. Encode decode life cycle"
-
-<h1 class="pg"> Bundle export import life cycle </h1>
-\image html SLP_bundle_PG_images_export_import.png "Picture 2. Export import life cycle"
-
-<h1 class="pg">API list and description</h1>
-<ul>
-       <li>bundle_create() : Create a bundle object.</li>
-       <li>bundle_free() : Free a bundle object.</li>
-       <li>bundle_add() : Add a key/value pair into the bundle object.</li>
-       <li>bundle_del() : Delete a key/value pair by given key from the bundle object.</li>
-       <li>bundle_get_val() : Get a value by key.</li>
-       <li>bundle_get_count() : Get number of key/value pairs in the bundle object.</li>
-       <li>bundle_dup() : Duplicate give bundle object</li>
-       <li>bundle_iterate() : Run iterator function for each key/value pair in the bundle object.</li>
-       <li>bundle_encode() : Encode bundle object into a byte code.</li>
-       <li>bundle_decode() : Decode byt code into a bundle object.</li>
-       <li></li>
-</ul>
-
-<h1 class="pg">Programming Guide</h1>
-<p> bundle library is very easy to use, and the sample code below would enough to understand how to use bundle. </p><br>
-<p>Detailed API instructions are in API reference in doxygen document.</p>
-<h2 class="pg">Note</h2>
-<ul>
-       <li>Only string type(char *) keys/values are allowed.</li>
-       <li>A bundle object must be freed certainly by bundle_free(). </li>
-       <li>Values retrived by bundle_get_val() cannot be modified.<br> If you want to modify value string, duplicate it.</li>
-</ul>
-<h2 class="pg"> Header file </h2>
-<p> header file name: <strong> bundle.h </strong></p>
-<h2 class="pg">Code</h2>
-@code
-#include <stdio.h>
-#include <bundle.h>
-
-// This is a sample iterator callback function
-void print_bundle_item(const char *key, const char *val, void *data);
-
-// Sample code
-int
-main(int argc, char **argv)
-{
-       char *str;
-       int count;
-
-       bundle *b, *b_dup;
-
-       // Create a new bundle object
-       b = bundle_new();
-
-       // Add a string with key "a"
-       bundle_add(b, "a", "123abc");
-
-       // Add another string with key "b"
-       bundle_add("b", "456def");
-
-       // str = "123abc"
-       // You cannot modify string!
-       str = bundle_get_val(b, "a");
-
-       // Run iterator function with each items
-       bundle_iterate(b, print_bundle_item, NULL);
-
-       // count = 2
-       count = bundle_get_count(b);
-
-       // Delete an item with key "a"
-       bundle_del(b, "a");
-
-       // count = 1
-       count = bundle_get_count(b);
-
-       // If "a" key is requested, NULL is returned
-       // str = NULL, errno = ENOKEY
-       str = bundle_get_val(b, "a");
-
-       // Duplicate bundle object
-       b_dup = bundle_dup(b);
-
-       // Free bundle objects
-       bundle_free(b);
-       bundle_free(b_dup);
-
-       return 0;
-}
-
-void
-print_bundle_item(const char *key, const char *val, void *data)
-{
-       printf("%s -> %s\n", key, val);
-}
-@endcode
-
- * @}
- */
diff --git a/include/bundle.h b/include/bundle.h
deleted file mode 100644 (file)
index 00a18c0..0000000
+++ /dev/null
@@ -1,700 +0,0 @@
-/*
- * Copyright (c) 2000 - 2020 Samsung Electronics Co., Ltd. All rights reserved.
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#ifndef __BUNDLE_H__
-#define __BUNDLE_H__
-
-/**
- * @file bundle.h
- * @brief This file declares API of the bundle library.
- */
-
-/**
- * @addtogroup CORE_LIB_BUNDLE_MODULE
- * @{
- */
-
-#include <errno.h>
-#include <stddef.h>
-#include <tizen_error.h>
-
-#ifdef __cplusplus
-extern "C" {
-# endif
-
-/**
- * @brief Enumeration for error codes of Bundle.
- * @since_tizen 2.3
- */
-typedef enum {
-       BUNDLE_ERROR_NONE = TIZEN_ERROR_NONE, /**< Successful */
-       BUNDLE_ERROR_OUT_OF_MEMORY = TIZEN_ERROR_OUT_OF_MEMORY, /**< Out of memory */
-       BUNDLE_ERROR_INVALID_PARAMETER = TIZEN_ERROR_INVALID_PARAMETER, /**< Invalid parameter */
-       BUNDLE_ERROR_KEY_NOT_AVAILABLE = TIZEN_ERROR_KEY_NOT_AVAILABLE, /**< Required key not available */
-       BUNDLE_ERROR_KEY_EXISTS = TIZEN_ERROR_BUNDLE | 0x01, /**< Key exists */
-       BUNDLE_ERROR_ARRAY_INDEX_OUT_OF_BOUNDS = TIZEN_ERROR_BUNDLE | 0x02 /**< The index is out of bounds of the array */
-} bundle_error_e;
-
-
-/**
- * @brief The bundle handle.
- * @since_tizen 2.3
- */
-typedef struct _bundle_t bundle;
-
-
-/**
- * @brief The encoded data type.
- * @since_tizen 2.3
- * @see bundle_encode()
- * @see bundle_decode()
- */
-typedef unsigned char bundle_raw;
-
-
-/**
- * @brief Enumeration for key-value pair types.
- * @since_tizen 2.3
- */
-enum bundle_type_property {
-       BUNDLE_TYPE_ARRAY = 0x0100, /**< Array type */
-       BUNDLE_TYPE_PRIMITIVE = 0x0200, /**< Primitive type */
-       BUNDLE_TYPE_MEASURABLE = 0x0400 /**< Measurable type */
-};
-
-
-/**
- * @brief Enumeration for bundle types.
- * @since_tizen 2.3
- */
-enum bundle_type {
-       BUNDLE_TYPE_NONE = -1, /**< None */
-       BUNDLE_TYPE_ANY = 0, /**< Any type */
-       BUNDLE_TYPE_STR = 1 | BUNDLE_TYPE_MEASURABLE, /**< String type (Default) */
-       BUNDLE_TYPE_STR_ARRAY = BUNDLE_TYPE_STR | BUNDLE_TYPE_ARRAY | BUNDLE_TYPE_MEASURABLE, /**< String array type */
-       BUNDLE_TYPE_BYTE = 2, /**< Byte type */
-       BUNDLE_TYPE_BYTE_ARRAY = BUNDLE_TYPE_BYTE | BUNDLE_TYPE_ARRAY /**< Byte array type */
-};
-
-
-/**
- * @brief The key-value pair handle.
- * @since_tizen 2.3
- * @see bundle_iterator_t
- */
-typedef struct keyval_t bundle_keyval_t;
-
-
-/**
- * @brief Called for every key-value pair.
- * @since_tizen 2.3
- * @param[in] key The key of key-value pair
- * @param[in] type The type of bundle
- * @param[in] kv The handle of key-value pair
- * @param[in] user_data The user data
- * @see bundle_foreach()
- */
-typedef void (*bundle_iterator_t) (const char *key, const int type, const bundle_keyval_t *kv, void *user_data);
-
-
-/**
- * @brief Creates a bundle object.
- * @since_tizen 2.3
- * @remarks The specific error code can be obtained using the get_last_result() method. Error codes are described in Exception section.
- * @return The bundle object,
- *         @c NULL - Failure
- * @exception #BUNDLE_ERROR_NONE Success
- * @exception #BUNDLE_ERROR_OUT_OF_MEMORY Out of memory
- * @see bundle_free()
- *
- * @code
- #include <bundle.h>
- bundle *b = bundle_create(); // Create a new bundle object
- bundle_free(b); // Free the bundle
- * @endcode
- */
-bundle *bundle_create(void);
-
-
-/**
- * @brief Frees the given bundle object with key-value pairs in it.
- * @since_tizen 2.3
- * @param[in] b The bundle object to be freed
- * @return The operation result
- * @retval #BUNDLE_ERROR_NONE Success
- * @retval #BUNDLE_ERROR_INVALID_PARAMETER Invalid parameter
- * @pre @a b must be a valid bundle object.
- * @see bundle_create()
- *
- * @code
- #include <bundle.h>
- bundle *b = bundle_create(); // Create a new bundle object
- bundle_free(b); // Free the bundle
- * @endcode
- */
-int bundle_free(bundle *b);
-
-
-/**
- * @brief Adds a strings array type key-value pair into a given bundle.
- * @since_tizen 2.3
- * @param[in] b The bundle object
- * @param[in] key The key
- * @param[in] str_array The string type value; if @c NULL, an empty array is created; you can change an item with
- * @param[in] len The length of the array
- * @return The operation result
- * @retval #BUNDLE_ERROR_NONE Success
- * @retval #BUNDLE_ERROR_INVALID_PARAMETER Invalid parameter
- * @retval #BUNDLE_ERROR_KEY_EXISTS Key already exists
- * @retval #BUNDLE_ERROR_OUT_OF_MEMORY Out of memory
- * @pre @a b must be a valid bundle object.
- * @see bundle_get_str_array()
- *
- * @code
- #include <bundle.h>
- char *sa = {"aaa", "bbb", "ccc"}; // String array of length 3
- bundle *b = bundle_create();
- bundle_add_str_array(b, "foo", sa, 3); // Add a key-value pair
- bundle_free(b);
- * @endcode
- */
-int bundle_add_str_array(bundle *b, const char *key, const char **str_array, const int len);
-
-
-/**
- * @brief Deletes a key-value object with the given key.
- * @since_tizen 2.3
- * @param[in] b The bundle object
- * @param[in] key The given key
- * @return The operation result
- * @retval #BUNDLE_ERROR_NONE Success
- * @retval #BUNDLE_ERROR_INVALID_PARAMETER Invalid parameter
- * @retval #BUNDLE_ERROR_KEY_NOT_AVAILABLE Key not available
- * @pre @a b must be a valid bundle object.
- *
- * @code
- #include <bundle.h>
- bundle *b = bundle_create(); // Create a new bundle object
- bundle_add_str(b, "foo_key", "bar_val"); // Add a key-value pair
- bundle_del(b, "foo_key"); // Delete "foo_key" from b
-
- bundle_free(b);
- * @endcode
- */
-int bundle_del(bundle *b, const char *key);
-
-
-/**
- * @brief Gets a string array from a given key.
- * @since_tizen 2.3
- * @remarks You MUST NOT free or modify the returned string. \n
- *          The specific error code can be obtained using the get_last_result() method. Error codes are described in Exception section.
- * @param[in] b The bundle object
- * @param[in] key The key
- * @param[out] len The array length
- * @return The pointer to the array of strings,
- *         @c NULL - Key not found
- * @exception #BUNDLE_ERROR_NONE Success
- * @exception #BUNDLE_ERROR_INVALID_PARAMETER Invalid parameter
- * @exception #BUNDLE_ERROR_KEY_NOT_AVAILABLE Key not available
- * @pre @a b must be a valid bundle object.
- * @see bundle_add_str_array()
- *
- * @code
- #include <bundle.h>
- bundle *b = bundle_create();
- char *sa = {"aaa", "bbb", "ccc"}; // String array of length 3
- bundle_add_str_array(b, "foo", sa, 3); // Add a key-value pair
-
- char **str_array = NULL;
- int len_str_array = 0;
-
- str_array=bundle_get_str_array(b, "foo", &len_str_array);
- // str_array = {"aaa", "bbb", "ccc"}, and len_str_array = 3
-
- bundle_free(b);
- * @endcode
- */
-const char **bundle_get_str_array(bundle *b, const char *key, int *len);
-
-
-/**
- * @brief Gets the number of bundle items.
- * @since_tizen 2.3
- * @param[in] b The bundle object
- * @return The number of bundle items
- * @pre @a b must be a valid bundle object.
- *
- * @code
- #include <bundle.h>
- bundle *b = bundle_create(); // Create a new bundle object
- bundle_add_str(b, "key1", "val1"); // Add a key-value pair
- int count = bundle_get_count(b); // count = 1
- bundle_add_str(b, "key2", "val2"); // Add another key-value pair
- count = bundle_get_count(b); // count = 2
-
- bundle_free(b);
- * @endcode
- */
-int bundle_get_count(bundle *b);
-
-
-/**
- * @brief Gets the type of the value with a given key.
- * @since_tizen 2.3
- * @remarks The specific error code can be obtained using the get_last_result() method. Error codes are described in Exception section.
- * @param[in] b A bundle
- * @param[in] key A key in the bundle
- * @return The type of a key in @a b
- * @exception #BUNDLE_ERROR_NONE Success
- * @exception #BUNDLE_ERROR_INVALID_PARAMETER Invalid parameter
- * @exception #BUNDLE_ERROR_KEY_NOT_AVAILABLE Key not available
- * @pre @a b must be a valid bundle object.
- * @see bundle_type
- */
-int bundle_get_type(bundle *b, const char *key);
-
-
-/**
- * @brief Duplicates a given bundle object.
- * @since_tizen 2.4
- * @remarks The specific error code can be obtained using the get_last_result() method. Error codes are described in Exception section.
- *          The returned value should be released using bundle_free().
- * @param[in] b_from The bundle object to be duplicated
- * @return The new bundle object,
- *         @c NULL - Failure
- * @exception #BUNDLE_ERROR_NONE Success
- * @exception #BUNDLE_ERROR_INVALID_PARAMETER Invalid parameter
- * @pre @a b_from must be a valid bundle object.
- *
- * @code
- #include <bundle.h>
- bundle *b = bundle_create(); // Create a new bundle object
- bundle_add_str(b, "foo_key", "bar_val"); // Add a key-value pair
- bundle *b_dup = bundle_dup(b); // Duplicate b
-
- bundle_free(b);
- bundle_free(b_dup);
- * @endcode
- */
-bundle *bundle_dup(bundle *b_from);
-
-
-/**
- * @brief Iterates a callback function for each key-value pair in a given bundle.
- * @details Supports all types of values.
- * @since_tizen 2.3
- * @remarks The specific error code can be obtained using the get_last_result() method. Error codes are described in Exception section. \n
- *          This function supports all types.
- * @param[in] b The bundle object
- * @param[in] iter The iteration callback function
- * @param[in] user_data The data for the callback function
- * @exception #BUNDLE_ERROR_NONE Success
- * @exception #BUNDLE_ERROR_INVALID_PARAMETER Invalid parameter
- * @pre @a b must be a valid bundle object.
- * @see bundle_keyval_get_type()
- * @see bundle_keyval_type_is_array()
- * @see bundle_keyval_get_basic_val()
- * @see bundle_keyval_get_array_val()
- *
- * @code
- #include <stdio.h>
- #include <bundle.h>
- void
- sample_cb(const char *key, const int type, const bundle_keyval_t *kv, void *user_data)
- {
-     void *basic_val = NULL;
-     size_t basic_size = 0;
-     void **array_val = NULL;
-     int array_len = 0;
-     size_t *array_elem_size = NULL;
-
-     printf("Key:%s, Type:%d\n", key, type);
-     if (bundle_keyval_type_is_array(kv)) {
-         bundle_keyval_get_array_val(kv, &array_val, &array_len, &array_elem_size);
-         // Do something
-     }
-     else {
-         bundle_keyval_get_basic_val(kv, &basic_val, &basic_size);
-         // Do something
-     }
- }
-
- int main(void)
- {
-     bundle *b = bundle_create(); // Create a new bundle object
-     bundle_add_str(b, "k1", "v1"); // Add a key-value pair
-     bundle_add_byte(b, "k2", "v2", 3); // Add a key-value pair
-     char *s_arr[] = {"abc", "bcd", "cde"};
-     bundle_add_str_array(b, "k3", s_arr, 3); // Add a key-value pair
-     bundle_foreach(b, sample_cb, NULL); // Iterate sample_cb() for each key/value
-
-     return 0;
- }
- * @endcode
- */
-void bundle_foreach(bundle *b, bundle_iterator_t iter, void *user_data);
-
-
-/**
- * @brief Gets the type of a key-value pair.
- * @since_tizen 2.3
- * @remarks The specific error code can be obtained using the get_last_result() method. Error codes are described in Exception section.
- * @param[in] kv A bundle_keyval_t object
- * @return The type of @a kv,
- *         @c -1 - Failure
- * @exception #BUNDLE_ERROR_NONE Success
- * @exception #BUNDLE_ERROR_INVALID_PARAMETER Invalid parameter
- * @pre @a kv must be a valid bundle_keyval_t object.
- * @see bundle_foreach()
- */
-int bundle_keyval_get_type(bundle_keyval_t *kv);
-
-
-/**
- * @brief Determines whether the type of a key-value pair is an array.
- * @since_tizen 2.3
- * @remarks The specific error code can be obtained using the get_last_result() method. Error codes are described in Exception section.
- * @param[in] kv A bundle_keyval_t object
- * @return The operation result
- *         @c 1 - @a kv is an array
- *         @c 0 - @a kv is not an array
- * @exception #BUNDLE_ERROR_NONE Success
- * @exception #BUNDLE_ERROR_INVALID_PARAMETER Invalid parameter
- * @pre @a kv must be a valid bundle_keyval_t object.
- * @see bundle_foreach()
- */
-int bundle_keyval_type_is_array(bundle_keyval_t *kv);
-
-
-/**
- * @brief Gets the value and size of the value from a key-value pair of basic type.
- * @since_tizen 2.3
- * @remarks You must not free @a val.
- * @param[in] kv A bundle_keyval_t object
- * @param[out] val The value
- * @param[out] size The size of @a val
- * @return The operation result
- * @retval #BUNDLE_ERROR_NONE Success
- * @retval #BUNDLE_ERROR_INVALID_PARAMETER Invalid parameter
- * @pre @a kv must be a valid bundle_keyval_t object.
- * @post @a val and @a size are set.
- * @see bundle_foreach()
- */
-int bundle_keyval_get_basic_val(bundle_keyval_t *kv, void **val, size_t *size);
-
-
-/**
- * @brief Gets the value array, length of the array, and size of each array item.
- * @since_tizen 2.3
- * @remarks The @a array_val should not be released.
- *          The @a array_element_size should not be released.
- * @param[in] kv A bundle_keyval_t object
- * @param[out] array_val The array pointer of values
- * @param[out] array_len The length of @a array_val
- * @param[out] array_element_size The array of size of each array element
- * @return The operation result
- * @retval #BUNDLE_ERROR_NONE Success
- * @retval #BUNDLE_ERROR_INVALID_PARAMETER Invalid parameter
- * @pre @a kv must be a valid bundle_keyval_t object.
- * @post @a array_val, @a array_len, @a array_element_size are set.
- * @code
- #include <stdio.h>
- #include <bundle.h>
- void
- sample_cb(const char *key, const int type, const bundle_keyval_t *kv, void *user_data)
- {
-     void **array_val = NULL;
-     unsigned int array_len = 0;
-     size_t *array_elem_size = NULL;
-     unsigned int i;
-
-     printf("Key: %s, Type: %d\n", key, type);
-     if (bundle_keyval_type_is_array(kv)) {
-         bundle_keyval_get_array_val(kv, &array_val, &array_len, &array_elem_size);
-         for (i = 0; i < array_len; ++i) {
-             printf("Value[%u]: %s\n", i, (const char *)array_val[i]);
-         }
-     }
- }
-
- int main(void)
- {
-     bundle *b = bundle_create();
-     const char *s_arr[] = {"abc", "bcd", "cde"};
-     bundle_add_str_array(b, "k3", s_arr, 3); // Add a key-value pair
-     bundle_foreach(b, sample_cb, NULL);
-     bundle_free(b);
-     return 0;
- }
- * @endcode
- * @see bundle_foreach()
- */
-int bundle_keyval_get_array_val(bundle_keyval_t *kv, void ***array_val, unsigned int *array_len, size_t **array_element_size);
-
-
-/**
- * @brief Encodes a bundle to the bundle_raw format (uses base64 format).
- * @since_tizen 2.3
- * @remarks The @a r should be released using free().
- * @param[in] b The bundle object
- * @param[out] r The returned bundle_raw data(byte data)
- *               @a r MUST BE FREED by free(r)
- * @param[out] len The size of @a r (in bytes)
- * @return The size of the raw data
- * @retval #BUNDLE_ERROR_NONE Success
- * @retval #BUNDLE_ERROR_INVALID_PARAMETER Invalid parameter
- * @pre @a b must be a valid bundle object.
- *
- * @code
- #include <bundle.h>
- bundle *b = bundle_create(); // Create a new bundle object
- bundle_add_str(b, "foo_key", "bar_val"); // Add a key-value pair
- bundle_raw *r;
- int len;
- bundle_encode(b, &r, &len); // Encode b
- bundle_free(b);
- free(r);
- * @endcode
- */
-int bundle_encode(bundle *b, bundle_raw **r, int *len);
-
-
-/**
- * @brief Deserializes bundle_raw and gets the bundle object.
- * @since_tizen 2.3
- * @remarks The specific error code can be obtained using the get_last_result() method. Error codes are described in Exception section.
- *          The returned value should be released using bundle_free().
- * @param[in] r The bundle_raw data to be converted to bundle object
- * @param[in] len The size of @a r
- * @return The bundle object,
- *         @c NULL - Failure
- * @exception #BUNDLE_ERROR_NONE Success
- * @exception #BUNDLE_ERROR_INVALID_PARAMETER Invalid parameter
- * @pre @a r must be a valid bundle object.
- *
- * @code
- #include <bundle.h>
- bundle *b = bundle_create(); // Create a new bundle object
- bundle_add_str(b, "foo_key", "bar_val"); // Add a key-value pair
-
- bundle_raw *encoded_b;
- int len;
- bundle_encode(b, &encoded_b, &len); // Encode b
-
- bundle *b_dup;
- b_dup = bundle_decode(encoded_b, len); // Decoded bundle object
-
- bundle_free(b);
- free(encoded_b);
- bundle_free(b_dup);
- * @endcode
- */
-bundle *bundle_decode(const bundle_raw *r, const int len);
-
-
-/**
- * @brief Adds a string type key-value pair into a bundle.
- * @since_tizen 2.3
- * @param[in] b The bundle object
- * @param[in] key The key
- * @param[in] str The string type value
- * @return The operation result
- * @retval #BUNDLE_ERROR_NONE Success
- * @retval #BUNDLE_ERROR_INVALID_PARAMETER Invalid parameter
- * @retval #BUNDLE_ERROR_KEY_EXISTS Key already exists
- * @retval #BUNDLE_ERROR_OUT_OF_MEMORY Out of memory
- * @pre @a b must be a valid bundle object.
- * @see bundle_get_str()
- * @code
- #include <bundle.h>
- bundle *b = bundle_create(); // Create a new bundle object
- bundle_add_str(b, "foo", "bar"); // Add a key-value pair
-
- bundle_free(b);
- * @endcode
- */
-int bundle_add_str(bundle *b, const char *key, const char *str);
-
-
-/**
- * @brief Adds a byte sequence type key-value pair into a bundle.
- * @details The bundle will contain a copy of the added byte sequence.
- * @since_tizen 2.3
- * @param[in] b The bundle object
- * @param[in] key The key
- * @param[in] bytes The byte sequence
- * @param[in] size The byte sequence size in bytes
- * @return The operation result
- * @retval #BUNDLE_ERROR_NONE Success
- * @retval #BUNDLE_ERROR_INVALID_PARAMETER Invalid parameter
- * @retval #BUNDLE_ERROR_KEY_EXISTS Key already exists
- * @retval #BUNDLE_ERROR_OUT_OF_MEMORY Out of memory
- * @pre @a b must be a valid bundle object.
- * @see bundle_get_byte()
- *
- * @code
- #include <bundle.h>
- bundle *b = bundle_create(); // Create a new bundle object
- bundle_add_byte(b, "foo", "bar\0", 4); // Add a key-value pair
-
- int number = 12345;
- bundle_add_byte(b, "number", &number, sizeof(int));
-
- bundle_free(b);
- * @endcode
- */
-int bundle_add_byte(bundle *b, const char *key, const void *bytes, const size_t size);
-
-
-/**
- * @brief Gets the string value with the given key.
- * @since_tizen 2.3
- * @remarks You must not free str.
- * @param[in] b The bundle object
- * @param[in] key The key
- * @param[out] str The returned value
- * @return The operation result
- * @retval #BUNDLE_ERROR_NONE Success
- * @retval #BUNDLE_ERROR_INVALID_PARAMETER Invalid parameter
- * @retval #BUNDLE_ERROR_KEY_NOT_AVAILABLE Key not available
- * @pre @a b must be a valid bundle object.
- * @see bundle_add_str()
- *
- * @code
- #include <bundle.h>
- bundle *b = bundle_create(); // Create a new bundle object
- bundle_add_str(b, "foo_key", "bar_val"); // Add a key-value pair
-
- char *v = NULL;
- bundle_get_str(b, "foo_key", &v); // v = "bar_val"
-
- bundle_free(b); // After freeing b, v becomes a dangling pointer
- v = NULL;
- * @endcode
- */
-int bundle_get_str(bundle *b, const char *key, char **str);
-
-
-/**
- * @brief Gets the byte sequence with the given key.
- * @since_tizen 2.3
- * @remarks You must not free @a bytes.
- * @param[in] b The bundle object
- * @param[in] key The key
- * @param[out] bytes The byte sequence
- * @param[out] size The byte sequence size in bytes
- * @return The operation result
- * @retval #BUNDLE_ERROR_NONE Success
- * @retval #BUNDLE_ERROR_INVALID_PARAMETER Invalid parameter
- * @retval #BUNDLE_ERROR_KEY_NOT_AVAILABLE Key not available
- * @pre @a b must be a valid bundle object.
- * @see bundle_add_byte()
- *
- * @code
- #include <bundle.h>
- bundle *b = bundle_create(); // Create a new bundle object
- bundle_add_byte(b, "foo", "bar\0", 4); // Add a string to the bundle
- int number = 12345;
- bundle_add_byte(b, "number", (const void**)&number, sizeof(int)); // Add an integer to the bundle
-
- unsigned char *v = NULL;
- size_t v_size;
- bundle_get_byte(b, "foo", (void**)&v, &v_size); // v = "bar\0"
- int *n = NULL;
- size_t n_size;
- bundle_get_byte(b, "number", (void**)&n, &n_size); // number = 12345
-
- bundle_free(b); // After freeing b, v and n become a dangling pointer
- * @endcode
- */
-int bundle_get_byte(bundle *b, const char *key, void **bytes, size_t *size);
-
-/**
- * @brief Adds an 'array of byte sequences' type key-value pair into a bundle.
- * @since_tizen 5.5
- * @remarks To set the value of the byte array element, you should use bundle_set_byte_array_element().
- *          This function is only for creating a buffer of the byte array.
- *
- * @param[in]   b                       The bundle object
- * @param[in]   key                     The key
- * @param[in]   len                     The length of the array to be created
- * @return      @c 0 on success,
- *              otherwise a negative error value
- * @retval #BUNDLE_ERROR_NONE Successful
- * @retval #BUNDLE_ERROR_INVALID_PARAMETER Invalid parameter
- * @retval #BUNDLE_ERROR_KEY_EXISTS Key already exists
- * @retval #BUNDLE_ERROR_OUT_OF_MEMORY Out of memory
- *
- * @see bundle_get_byte_array()
- * @see bundle_set_byte_array_element()
- */
-int bundle_add_byte_array(bundle *b, const char *key, const unsigned int len);
-
-/**
- * @brief Sets an element of an array of byte sequences.
- * @details The array will contain its own copy of the added value.
- * @since_tizen 5.5
- *
- * @param[in]   b                       The bundle object
- * @param[in]   key                     The key
- * @param[in]   idx                     The index of the array element to be changed
- * @param[in]   bytes                   The byte sequence
- * @param[in]   size                    The byte sequence size in bytes
- * @return      @c 0 on success,
- *              otherwise a negative error value
- * @retval #BUNDLE_ERROR_NONE Successful
- * @retval #BUNDLE_ERROR_INVALID_PARAMETER Invalid parameter
- * @retval #BUNDLE_ERROR_KEY_NOT_AVAILABLE Key not available
- * @retval #BUNDLE_ERROR_OUT_OF_MEMORY Out of memory
- * @retval #BUNDLE_ERROR_ARRAY_INDEX_OUT_OF_BOUNDS The index is out of bounds of the array
- *
- * @see bundle_add_byte_array()
- * @see bundle_get_byte_array()
- */
-int bundle_set_byte_array_element(bundle *b, const char *key, const unsigned int idx, const void *bytes, const size_t size);
-
-/**
- * @brief Gets the array of byte sequences with the given key.
- * @since_tizen 5.5
- * @remarks You should not release @a byte_array, @a len and @a array_element_size.
- *          @a byte_array, @a len and @a array_element_size will be released when the bundle containing them is released with bundle_free().
- *
- * @param[in]   b                       The bundle object
- * @param[in]   key                     The key
- * @param[out]  byte_array              The array pointer of the byte value
- * @param[out]  len                     The array length
- * @param[out]  array_element_size      An array of sizes of each @a byte_array element
- * @return      @c 0 on success,
- *              otherwise a negative error value
- * @retval #BUNDLE_ERROR_NONE Successful
- * @retval #BUNDLE_ERROR_INVALID_PARAMETER Invalid parameter
- * @retval #BUNDLE_ERROR_KEY_NOT_AVAILABLE Key not available
- *
- * @see bundle_add_byte_array()
- * @see bundle_set_byte_array_element()
-*/
-int bundle_get_byte_array(bundle *b, const char *key, void ***byte_array, unsigned int *len, unsigned int **array_element_size);
-
-#ifdef __cplusplus
-}
-#endif
-
-/**
- * @}
- */
-
-#endif /* __BUNDLE_H__ */
diff --git a/include/bundle_cpp.h b/include/bundle_cpp.h
deleted file mode 100644 (file)
index 997da06..0000000
+++ /dev/null
@@ -1,348 +0,0 @@
-/*
- * Copyright (c) 2019 - 2020 Samsung Electronics Co., Ltd.
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#ifndef BUNDLE_CPP_H_
-#define BUNDLE_CPP_H_
-
-/**
- * @file bundle_cpp.h
- * @brief This file declares API of the bundle C++ library.
- */
-
-/**
- * @addtogroup CORE_LIB_BUNDLE_CPP_MODULE
- * @{
- */
-
-#include <bundle.h>
-
-#include <cstdio>
-#include <initializer_list>
-#include <memory>
-#include <string>
-#include <utility>
-#include <vector>
-
-#ifndef EXPORT_API
-#define EXPORT_API __attribute__((visibility("default")))
-#endif
-
-namespace tizen_base {
-
-/**
- * @brief The class for bundle APIs.
- * @since_tizen 5.5
- */
-class EXPORT_API Bundle final {
- public:
-  /**
-   * @brief The type for raw bundle.
-   * @since_tizen 5.5
-   */
-  using BundleRaw =
-      std::pair<std::unique_ptr<bundle_raw, decltype(std::free)*>, int>;
-
-  /**
-   * @brief The class for information of keys.
-   * @since_tizen 5.5
-   */
-  class KeyInfo final {
-   public:
-    /**
-     * @brief Constructor.
-     * @since_tizen 5.5
-     * @param[in] handle The handle for type bundle_keyval_t
-     * @param[in] name The key string
-     * @param[in] own True if this object owns the handle
-     */
-    KeyInfo(const bundle_keyval_t* handle,  std::string name, bool own = false);
-
-    /**
-     * @brief Destructor.
-     * @since_tizen 5.5
-     */
-    ~KeyInfo();
-
-    /**
-     * @brief Copy-constructor.
-     * @since_tizen 5.5
-     * @param[in] b The object to copy
-    */
-    KeyInfo(const KeyInfo& b);
-
-    /**
-     * @brief Assignment.
-     * @since_tizen 5.5
-     * @param[in] b The object to copy
-     */
-    KeyInfo& operator = (const KeyInfo& b);
-
-    /**
-     * @brief Move-constructor.
-     * @since_tizen 5.5
-     * @param[in] b The object to move
-    */
-    KeyInfo(KeyInfo&& b) noexcept;
-
-    /**
-     * @brief Assignment.
-     * @since_tizen 5.5
-     * @param[in] b The object to move
-     */
-    KeyInfo& operator = (KeyInfo&& b) noexcept;
-
-    /**
-     * @brief Gets the type of a key-value pair.
-     * @since_tizen 5.5
-     * @return The type
-     */
-    bundle_type GetType() const;
-
-    /**
-     * @brief Determines whether the type of a key-value pair is an array.
-     * @since_tizen 5.5
-     * @return True when it is an array
-     */
-    bool IsArray() const;
-
-    /**
-     * @brief Gets the key string.
-     * @since_tizen 5.5
-     * @return The key string
-     */
-    const std::string& GetName() const;
-
-   private:
-    class Impl;
-    std::unique_ptr<Impl> impl_;
-  };
-
-  /**
-   * @brief Constructor.
-   * @since_tizen 5.5
-   */
-  Bundle();
-
-  /**
-   * @brief Constructor.
-   * @since_tizen 6.5
-   * @param[in] key_values The list of key-value pair
-   */
-  Bundle(std::initializer_list<
-      std::pair<std::string, std::string>> key_values);
-
-  /**
-   * @brief Constructor.
-   * @since_tizen 5.5
-   * @param[in] raw The object for BundleRaw
-   * @param[in] base64 @c true, @a raw is the encoded raw data using base64-encoding
-   */
-  explicit Bundle(BundleRaw raw, bool base64 = true);
-
-  /**
-   * @brief Constructor.
-   * @since_tizen 5.5
-   * @param[in] raw The string object for raw bundle
-   */
-  explicit Bundle(const std::string& raw);
-
-  /**
-   * @brief Constructor.
-   * @since_tizen 5.5
-   * @param[in] b The handle for bundle
-   * @param[in] copy True if this object wants to copy it from the handle
-   * @param[in] own True if this object owns the handle
-   */
-  explicit Bundle(bundle* b, bool copy = true, bool own = true);
-
-  /**
-   * @brief Destructor.
-   * @since_tizen 5.5
-   */
-  ~Bundle();
-
-  /**
-   * @brief Copy-constructor.
-   * @since_tizen 5.5
-   * @param[in] b The object to copy
-   */
-  Bundle(const Bundle& b);
-
-  /**
-   * @brief Assignment.
-   * @since_tizen 5.5
-   * @param[in] b The object to copy
-   */
-  Bundle& operator = (const Bundle& b);
-
-  /**
-   * @brief Move-constructor.
-   * @since_tizen 5.5
-   * @param[in] b The object to move
-   */
-  Bundle(Bundle&& b) noexcept;
-
-  /**
-   * @brief Assignment.
-   * @since_tizen 5.5
-   * @param[in] b The object to move
-   */
-  Bundle& operator = (Bundle&& b) noexcept;
-
-  /**
-   * @brief Check the bundle is empty or not.
-   * @since_tizen 6.0
-   * @return true if the bundle is empty
-   */
-  bool IsEmpty() const noexcept;
-
-  /**
-   * @brief Gets keys in bundle object.
-   * @since_tizen 5.5
-   * @return A string array of object KeyInfo
-  */
-  std::vector<KeyInfo> GetKeys();
-
-  /**
-   * @brief Adds a string type key-value pair into a bundle.
-   * @since_tizen 5.5
-   * @param[in] key The string key
-   * @param[in] val The string value
-   * @return The operation result
-   * @retval BUNDLE_ERROR_NONE Success
-   * @retval BUNDLE_ERROR_INVALID_PARAMETER Invalid parameter
-   * @retval BUNDLE_ERROR_KEY_EXISTS Key already exists
-   * @retval BUNDLE_ERROR_OUT_OF_MEMORY Out of memory
-  */
-  int Add(const std::string& key, const std::string& val);
-
-  /**
-   * @brief Adds a string type key-value pair into a bundle.
-   * @since_tizen 5.5
-   * @param[in] key The string key
-   * @param[in] val The array of strings
-   * @return The operation result
-   * @retval BUNDLE_ERROR_NONE Success
-   * @retval BUNDLE_ERROR_INVALID_PARAMETER Invalid parameter
-   * @retval BUNDLE_ERROR_KEY_EXISTS Key already exists
-   * @retval BUNDLE_ERROR_OUT_OF_MEMORY Out of memory
-  */
-  int Add(const std::string& key, const std::vector<std::string>& val);
-
-  /**
-   * @brief Adds a string type key-value pair into a bundle.
-   * @since_tizen 5.5
-   * @param[in] key The string key
-   * @param[in] val The array of bytes
-   * @return The operation result
-   * @retval BUNDLE_ERROR_NONE Success
-   * @retval BUNDLE_ERROR_INVALID_PARAMETER Invalid parameter
-   * @retval BUNDLE_ERROR_KEY_EXISTS Key already exists
-   * @retval BUNDLE_ERROR_OUT_OF_MEMORY Out of memory
-  */
-  int Add(const std::string& key, const std::vector<unsigned char>& val);
-
-  /**
-   * @brief Deletes a key-value object with the given key.
-   * @since_tizen 5.5
-   * @param[in] key The string key
-   * @return The operation result
-   * @retval BUNDLE_ERROR_NONE Success
-   * @retval BUNDLE_ERROR_INVALID_PARAMETER Invalid parameter
-   * @retval BUNDLE_ERROR_KEY_NOT_AVAILABLE Key not available
-  */
-  int Delete(const std::string& key);
-
-  /**
-   * @brief Gets a string from the key.
-   * @since_tizen 5.5
-   * @param[in] key The string key
-   * @return The string
-  */
-  std::string GetString(const std::string& key) const;
-
-  /**
-   * @brief Gets strings from the key.
-   * @since_tizen 5.5
-   * @param[in] key The string key
-   * @return The array of strings
-  */
-  std::vector<std::string> GetStringArray(const std::string& key) const;
-
-  /**
-   * @brief Gets bytes from the key.
-   * @since_tizen 5.5
-   * @param[in] key The string key
-   * @return Bytes
-  */
-  std::vector<unsigned char> GetByte(const std::string& key) const;
-
-  /**
-   * @brief Converts this object to BundleRaw type.
-   * @since_tizen 5.5
-   * @param[in] base64 @c true, the BundleRaw will be encoded using base64-encoding.
-   * @return The object of BundleRaw
-  */
-  BundleRaw ToRaw(bool base64 = true);
-
-  /**
-   * @brief Gets the count of keys.
-   * @since_tizen 5.5
-   * @return The count
-  */
-  int GetCount() const;
-
-  /**
-   * @brief Gets the data type from the key.
-   * @since_tizen 5.5
-   * @param[in] key The string key
-   * @return The data type
-  */
-  bundle_type GetType(const std::string& key) const;
-
-  /**
-   * @brief Gets the handle for bundle APIs.
-   * @since_tizen 5.5
-   * @return The handle for bundle
-  */
-  bundle* GetHandle() const;
-
-  /**
-   * @brief Moves this object into the bundle handle.
-   * @since_tizen 5.5
-   * @return The handle for bundle
-  */
-  bundle* Detach();
-
-  /**
-   * @brief Exports bundle to an argument vector.
-   * @since_tizen 6.5
-   * @return The argument vector
-   */
-  std::vector<std::string> Export() const;
-
- private:
-  class Impl;
-  std::unique_ptr<Impl> impl_;
-};
-
-}  // namespace tizen_base
-
-/**
- * @}
- */
-
-#endif  // BUNDLE_CPP_H_
diff --git a/include/bundle_internal.h b/include/bundle_internal.h
deleted file mode 100644 (file)
index b489adb..0000000
+++ /dev/null
@@ -1,448 +0,0 @@
-/*
- * Copyright (c) 2000 - 2020 Samsung Electronics Co., Ltd. All rights reserved.
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#ifndef __BUNDLE_INTERNAL_H__
-#define __BUNDLE_INTERNAL_H__
-
-/**
- * @file bundle_internal.h
- * @brief    This file declares has API of the bundle library
- */
-
-/**
- * @addtogroup CORE_LIB_BUNDLE_MODULE
- * @{
- */
-
-#include <bundle.h>
-
-#ifdef __cplusplus
-extern "C" {
-# endif
-
-/**
- * @brief Called for every key-value pair.
- * @since_tizen 2.3
- * @remarks This type is obsolete. You must not use this type any more.
- * @see bundle_iterate()
- */
-typedef void (*bundle_iterate_cb_t) (const char *key, const char *val, void *data);
-
-/**
- * @brief Adds a string type key-value pair into a given bundle.
- * @since_tizen 2.3
- * @param[in] b The bundle object
- * @param[in] key The key
- * @param[in] val The value
- * @return The operation result
- * @retval #BUNDLE_ERROR_NONE Success
- * @retval #BUNDLE_ERROR_INVALID_PARAMETER Invalid parameter
- * @retval #BUNDLE_ERROR_KEY_EXISTS Key already exists
- * @retval #BUNDLE_ERROR_OUT_OF_MEMORY Out of memory
- * @pre @a b must be a valid bundle object.
- * @see bundle_add_str()
- @code
- #include <bundle_internal.h>
- bundle *b = bundle_create(); // Create new bundle object
- bundle_add(b, "foo_key", "bar_val"); // add a key-val pair
-
- bundle_free(b);
- @endcode
- */
-int bundle_add(bundle *b, const char *key, const char *val);
-
-/**
- * @brief Gets a value with a given key.
- * @since_tizen 2.3
- * @remarks You MUST NOT free or modify the returned string!
- * @remarks The specific error code can be obtained using the get_last_result() method. Error codes are described in Exception section.
- * @param[in] b The bundle object
- * @param[in] key The key
- * @return The pointer for the value string
- * @retval @c NULL - Key not found
- * @exception #BUNDLE_ERROR_NONE Success
- * @exception #BUNDLE_ERROR_INVALID_PARAMETER Invalid parameter
- * @exception #BUNDLE_ERROR_KEY_NOT_AVAILABLE Key not available
- * @pre @a b must be a valid bundle object.
- * @see bundle_get_str()
- @code
- #include <bundle_internal.h>
- bundle *b = bundle_create(); // Create new bundle object
- bundle_add_str(b, "foo", "bar"); //add a key-val pair
- char *val = bundle_get_val(b, "foo_key");     // val = "bar_val"
-
- bundle_free(b);       // After freeing b, val becomes a dangling pointer.
- val = NULL;
- @endcode
- */
-const char *bundle_get_val(bundle *b, const char *key);
-
-/**
- * @brief Iterates a callback function for each key-value pairs in a given bundle.
- * @details (NOTE: Only BUNDLE_TYPE_STR type values come!)
- * @since_tizen 2.3
- * @remarks The specific error code can be obtained using the get_last_result() method. Error codes are described in Exception section.
- * @remarks This function is obsolete and does not give values whose types are not BUNDLE_TYPE_STR.
- * @param[in] b The bundle object
- * @param[in] callback The iteration callback function
- * @param[in] cb_data The data for callback function
- * @exception #BUNDLE_ERROR_NONE Success
- * @exception #BUNDLE_ERROR_INVALID_PARAMETER Invalid parameter
- * @pre @a b must be a valid bundle object.
- @code
- #include <stdio.h>
- #include <bundle_internal.h>
- void sample_cb(const char *k, const char *v, void *data) {
-   printf("%s -> %s\n", k, v);
- }
-
- int main(void) {
-        bundle *b = bundle_create(); // Create new bundle object
-        bundle_add_str(b, "k1", "v1"); // add a key-val pair
-        bundle_add_str(b, "k2", "v2"); // add a key-val pair
-        bundle_add_str(b, "k3", "v3"); // add a key-val pair
-        bundle_iterate(b, sample_cb, NULL); // iterate sample_cb() for each key/val
-        return 0;
- }
- @endcode
- */
-void bundle_iterate(bundle *b, bundle_iterate_cb_t callback, void *cb_data);
-
-/**
- * @brief Determines whether the type of a key-value pair is measurable.
- * @since_tizen 2.3
- * @remarks The specific error code can be obtained using the get_last_result() method. Error codes are described in Exception section.
- * @param[in] kv A bundle_keyval_t object
- * @return The operation result
- * @retval @c 1 - @a kv is an measurable
- * @retval @c 0 - @a kv is not an measurable
- * @exception #BUNDLE_ERROR_NONE Success
- * @exception #BUNDLE_ERROR_INVALID_PARAMETER Invalid parameter
- * @pre @a kv must be a valid bundle_keyval_t object.
- * @see bundle_foreach()
- */
-int bundle_keyval_type_is_measurable(bundle_keyval_t *kv);
-
-/**
- * @brief Duplicates key-value pair.
- * @since_tizen 5.5
- * @param[in] kv A bundle_keyval_t object
- * @return The bundle object
- * @retval @c NULL - Failure
- * @pre @a kv must be a valid bundle_keyval_t object.
- */
-bundle_keyval_t *bundle_keyval_dup(const bundle_keyval_t *kv);
-
-/**
- * @brief Frees the encoded rawdata.
- * @since_tizen 2.3
- * @param[in] r The rawdata
- * @return The operation result
- * @retval #BUNDLE_ERROR_NONE Success
- * @retval #BUNDLE_ERROR_INVALID_PARAMETER Invalid parameter
- * @pre @a r is a valid rawdata generated by bundle_encode().
- * @see bundle_encode()
- */
-int bundle_free_encoded_rawdata(bundle_raw **r);
-
-/**
- * @brief Encodes a bundle to the bundle_raw format.
- * @since_tizen 2.3
- * @param[in] b The bundle object
- * @param[out] r The returned bundle_raw data(byte data)
- *               @a r MUST BE FREED by free(r)
- * @param[out] len The size of @a r (in bytes)
- * @return The size of the raw data
- * @retval #BUNDLE_ERROR_NONE Success
- * @retval #BUNDLE_ERROR_INVALID_PARAMETER Invalid parameter
- * @retval #BUNDLE_ERROR_OUT_OF_MEMORY Out of memory
- * @pre @a b must be a valid bundle object.
- @code
- #include <bundle_internal.h>
- bundle *b = bundle_create(); // Create new bundle object
- bundle_add_str(b, "foo_key", "bar_val"); // add a key-val pair
- bundle_raw *r;
- int len;
- bundle_encode_raw(b, &r, &len);       // encode b
-
- bundle_free(b);
- @endcode
- */
-int bundle_encode_raw(bundle *b, bundle_raw **r, int *len);
-
-/**
- * @brief Deserializes bundle_raw and gets a bundle object.
- * @since_tizen 2.3
- * @remarks The specific error code can be obtained using the get_last_result() method. Error codes are described in Exception section.
- * @param[in] r The bundle_raw data to be converted to a bundle object
- * @param[in] len The size of @a r
- * @return The bundle object
- * @retval @c NULL - Failure
- * @exception #BUNDLE_ERROR_NONE Success
- * @exception #BUNDLE_ERROR_INVALID_PARAMETER Invalid parameter
- * @pre @a r must be a valid bundle object.
- @code
- #include <bundle_internal.h>
- bundle *b = bundle_create(); // Create new bundle object
- bundle_add_str(b, "foo_key", "bar_val"); // add a key-val pair
-
- bundle_raw *encoded_b;
- int len;
- bundle_encode(b, &encoded_b, &len);   // encode b
-
- bundle *b_dup;
- b_dup = bundle_decode_raw(encoded_b, len);    // decoded bundle object
-
- bundle_free(b);
- free(encoded_b);
- bundle_free(b_dup);
- @endcode
- */
-bundle *bundle_decode_raw(const bundle_raw *r, const int len);
-
-/**
- * @brief Exports bundle to @a argv.
- * @since_tizen 2.3
- * @remarks The specific error code can be obtained using the get_last_result() method. Error codes are described in Exception section.
- * @param[in] b The bundle object
- * @param[out] argv The pointer of the string array; \n
- *                  This array has NULL values for the first and last item; \n
- *                  First NULL is for argv[0], and last NULL is a terminator for execv() \n
- * @return The number of item in @a argv. This value is equal to the actual count of argv - 1. (Last NULL terminator is not counted.)
- * @retval @c -1 - Failure
- * @exception #BUNDLE_ERROR_NONE Success
- * @exception #BUNDLE_ERROR_INVALID_PARAMETER Invalid parameter
- * @exception #BUNDLE_ERROR_OUT_OF_MEMORY Out of memory
- * @pre @a b is a valid bundle object.
- * @post @a argv is a pointer of newly allocated memory. It must be freed.
- * @see bundle_import_from_argv()
- @code
- #include <bundle_internal.h>
- bundle *b = bundle_create(); // Create new bundle object
- bundle_add_str(b, "foo_key", "bar_val"); // add a key-val pair
-
- int argc = 0;
- char **argv = NULL;
- argc = bundle_export_to_argv(b, &argv);       // export to argv
- if(0 > argc) error("export failure");
-
- int i;
- for(i=0; i < argc; i++) {
-   printf("%s\n", argv[i]);            // print argv
- }
- bundle_free_exported_argv(argc, argv);        // argv must be freed after being used.
-
- bundle_free(b);
- @endcode
- */
-int bundle_export_to_argv(bundle *b, char ***argv);
-
-/**
- * @brief Frees the exported @a argv.
- * @since_tizen 2.3
- * @remarks You must not use this API when you use global @a argv.
- * @param[in] argc The number of args, which is the return value of bundle_export_to_argv()
- * @param[in] argv The array from bundle_export_to_argv()
- * @return The operation result
- * @retval #BUNDLE_ERROR_NONE Success
- * @retval #BUNDLE_ERROR_INVALID_PARAMETER Invalid parameter
- * @pre @a argv is a valid string array generated from bundle_export_to_argv().
- * @see bundle_export_to_argv()
- @code
- bundle *b = bundle_create();
- bundle_add_str(b, "foo", "bar");
-
- int argc = 0;
- char **argv = NULL;
- argc = bundle_export_to_argv(b, &argv);
- if(0 > argc) error("export failure");
-
- // Use argv...
-
- bundle_free_exported_argv(argc, argv);
- argv = NULL;
-
- bundle_free(b);
- @endcode
- */
-int bundle_free_exported_argv(int argc, char ***argv);
-
-/**
- * @brief Imports a bundle from @a argv.
- * @since_tizen 2.3
- * @remarks The specific error code can be obtained using the get_last_result() method. Error codes are described in Exception section.
- * @param[in] argc The argument count
- * @param[in] argv The argument vector
- * @return The new bundle object
- * @retval @c NULL - Failure
- * @exception #BUNDLE_ERROR_NONE Success
- * @exception #BUNDLE_ERROR_INVALID_PARAMETER Invalid parameter
- * @exception #BUNDLE_ERROR_OUT_OF_MEMORY Out of memory
- * @pre @a argv is a valid string array, which is created by bundle_export_to_argv().
- * @post The returned bundle @a b must be freed.
- * @see bundle_export_to_argv()
- @code
- #include <bundle_internal.h>
-
- int main(int argc, char **argv) {
-   bundle *b = bundle_import_from_argv(argc, argv); // import from argc+argv
-   char *val = bundle_get_val(b, "foo_key");   // value for "foo_key"
-   // ......
-   bundle_free(b);     // After freeing b, val becomes a dangling pointer.
-   val = NULL;
- }
- @endcode
- */
-bundle *bundle_import_from_argv(int argc, char **argv);
-
-/**
- * @brief Sets a value of string array elements.
- * @since_tizen 2.3
- * @param[in] b The bundle object
- * @param[in] key The key
- * @param[in] idx The index of the array element to be changed
- * @param[in] val The string type value; if @c NULL, an empty array is created; you can change an item with
- * @return The operation result
- * @retval #BUNDLE_ERROR_NONE Success
- * @retval #BUNDLE_ERROR_INVALID_PARAMETER Invalid parameter
- * @pre @a b must be a valid bundle object.
- * @see bundle_add_str_array()
- * @see bundle_get_str_array()
- @code
- #include <bundle_internal.h>
- bundle *b = bundle_create();
- bundle_add_str_array(b, "foo", NULL, 3); // add a key-val pair
- bundle_set_str_array_element(b, "foo", 0, "aaa");
- bundle_set_str_array_element(b, "foo", 1, "bbb");
- bundle_set_str_array_element(b, "foo", 2, "ccc");
-
- char **str_array = NULL;
- int len_str_array = 0;
-
- str_array=bundle_get_str_array(b, "foo", &len_str_array);
- // str_array = { "aaa", "bbb", "ccc" }, and len_str_array = 3
-
- bundle_free(b);
- @endcode
- */
-int bundle_set_str_array_element(bundle *b, const char *key, const unsigned int idx, const char *val);
-
-/**
- * @brief Creates a JSON data from bundle.
- * @since_tizen 3.0
- * @remarks This function only supports the string type and the string array type.
- * @param[in] b The bundle object
- * @param[out] json The new created json data
- * @return The operation result
- * @retval #BUNDLE_ERROR_NONE Success
- * @retval #BUNDLE_ERROR_INVALID_PARAMETER Invalid parameter
- * @retval #BUNDLE_ERROR_OUT_OF_MEMORY Out of memory
- * @pre @a b must be a valid bundle object.
- @code
- #include <bundle_internal.h>
- bundle *b = bundle_create();
- char *json;
- int ret;
-
- bundle_add_str(b, "foo", "bar");
- ret = bundle_to_json(b, &json);
- if (ret != BUNDLE_ERROR_NONE) {
- bundle_free(b);
- return;
- }
- // json = "{"foo":"bar"}"
- bundle_free(b);
- free(json);
- @endcode
- */
-int bundle_to_json(bundle *b, char **json);
-
-/**
- * @breif Creates a bundle object from json.
- * @since_tizen 3.0
- * @remarks This function only supports the string type and the string array type.
- * @param[in] json The json data
- * @param[out] b The bundle object
- * @return The operation result
- * @retval #BUNDLE_ERROR_NONE Success
- * @retval #BUNDLE_ERROR_INVALID_PARAMETER Invalid parameter
- * @retval #BUNDLE_ERROR_OUT_OF_MEMORY Out of memory
- @code
- #include <bundle_internal.h>
- bundle *b;
- char *json = "{"foo":"bar"}";
- int ret;
-
- ret =  bundle_from_json(json, &b);
- if (ret != BUNDLE_ERROR_NONE)
- return;
- bundle_free(b);
- @endcode
- */
-int bundle_from_json(const char *json, bundle **b);
-
-/**
- * @breif Compares the bundle 1, 2.
- * @since_tizen 3.0
- * @param[in] b1 The bundle object
- * @param[in] b2 The bundle object
- * @return The operation result
- * @retval @c 0 It is identical
- * @retval @c -1 Invalid parameter
- * @retval @c 1 It is not identical
- */
-int bundle_compare(bundle *b1, bundle *b2);
-
-/**
- * @brief Initializes a byte array type key-value pair into a bundle.
- * @details To set the value of the byte array element, you should use bundle_set_byte_array_element().
- *          This function is only for creating a buffer of the byte array.
- * @since_tizen 5.5
- * @param[in] b The bundle object
- * @param[in] key The key
- * @param[in] len The length of the array to be created
- * @return @c 0 on success,
- *         otherwise a negative error value
- * @retval #BUNDLE_ERROR_NONE Successful
- * @retval #BUNDLE_ERROR_INVALID_PARAMETER Invalid parameter
- * @retval #BUNDLE_ERROR_KEY_EXISTS Key already exists
- * @retval #BUNDLE_ERROR_OUT_OF_MEMORY Out of memory
- *
- * @see bundle_set_byte_array_element()
- */
-int bundle_init_byte_array(bundle *b, const char *key, const unsigned int len);
-
-/**
- * @brief Frees the given key-value pair.
- * @since_tizen 6.0
- * @param[in] kv The key-value pair
- * @return @c 0 on success,
- *         otherwise a negative error value
- * @retval #BUNDLE_ERROR_NONE Successful
- * @retval #BUNDLE_ERROR_INVALID_PARAMETER Invalid parameter
- */
-int bundle_keyval_free(bundle_keyval_t *kv);
-
-#ifdef __cplusplus
-}
-#endif
-
-/**
- * @}
- * @}
- */
-
-#endif /* __BUNDLE__INTERNAL_H__ */
index 5d23df936501143d85119c260cadef6fe9d0f6e9..91a5653888b10ef473fe9d76547de5838e04a4b5 100644 (file)
@@ -134,10 +134,12 @@ export FFLAGS+=" -fprofile-arcs -ftest-coverage"
 export LDFLAGS+=" -lgcov"
 %endif
 
-%cmake -DVERSION=%{version} .
+MAJORVER=`echo %{version} | awk 'BEGIN {FS="."}{print $1}'`
+%cmake . -DFULLVER=%{version} -DMAJORVER=${MAJORVER}
 %__make %{?_smp_mflags}
 
 %check
+export LD_LIBRARY_PATH="../../src/bundle:../../src/parcel"
 ctest --verbose %{?_smp_mflags}
 %if 0%{?gcov:1}
 lcov -c --ignore-errors mismatch,graph,unused --no-external -b . -d . -o %{name}.info
diff --git a/parcel/CMakeLists.txt b/parcel/CMakeLists.txt
deleted file mode 100644 (file)
index 2e72f73..0000000
+++ /dev/null
@@ -1,50 +0,0 @@
-CMAKE_MINIMUM_REQUIRED(VERSION 2.8)
-PROJECT(parcel C CXX)
-
-INCLUDE(FindPkgConfig)
-PKG_CHECK_MODULES(pkgs REQUIRED dlog capi-base-common glib-2.0)
-
-FOREACH(flag ${pkgs_CFLAGS})
-       SET(EXTRA_CFLAGS "${EXTRA_CFLAGS} ${flag}")
-ENDFOREACH(flag)
-SET(EXTRA_CFLAGS "${EXTRA_CFLAGS} -fvisibility=hidden -flto -Wall -Werror -Winline")
-
-SET(CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} ${EXTRA_CFLAGS} -std=c++17")
-SET(CMAKE_CXX_FLAGS_DEBUG "-O0 -g")
-SET(CMAKE_CXX_FLAGS_RELEASE "-O2")
-
-INCLUDE_DIRECTORIES(${CMAKE_CURRENT_SOURCE_DIR}/../)
-INCLUDE_DIRECTORIES(${CMAKE_CURRENT_SOURCE_DIR}/)
-INCLUDE_DIRECTORIES(${CMAKE_CURRENT_SOURCE_DIR}/api)
-
-AUX_SOURCE_DIRECTORY(${CMAKE_SOURCE_DIR}/parcel PARCEL_SRCS)
-
-ADD_LIBRARY (${PROJECT_NAME} SHARED ${PARCEL_SRCS})
-
-SET_TARGET_PROPERTIES(parcel PROPERTIES SOVERSION ${VERSION_MAJOR})
-SET_TARGET_PROPERTIES(parcel PROPERTIES VERSION "${VERSION}")
-
-SET_TARGET_PROPERTIES(${PROJECT_NAME} PROPERTIES COMPILE_FLAGS "${EXTRA_CFLAGS} -fPIE")
-SET_TARGET_PROPERTIES(${PROJECT_NAME} PROPERTIES LINK_FLAGS "-pie")
-
-### Make pkgconfig file
-SET(PREFIX ${CMAKE_INSTALL_PREFIX})
-CONFIGURE_FILE(${CMAKE_CURRENT_SOURCE_DIR}/parcel.pc.in
-  ${CMAKE_BINARY_DIR}/parcel.pc @ONLY)
-
-### Install
-INSTALL(TARGETS parcel DESTINATION ${LIB_INSTALL_DIR})
-INSTALL(FILES ${CMAKE_BINARY_DIR}/parcel.pc DESTINATION ${LIB_INSTALL_DIR}/pkgconfig/)
-
-SET(HEADER_PARCEL
-  common.hh
-  parcel.hh
-  parcelable.hh
-)
-
-FOREACH(hfile ${HEADER_PARCEL})
-  INSTALL(FILES ${CMAKE_CURRENT_SOURCE_DIR}/${hfile} DESTINATION include/parcel)
-ENDFOREACH(hfile)
-
-INSTALL(FILES ${CMAKE_CURRENT_SOURCE_DIR}/api/parcel.h
-  DESTINATION include/parcel)
diff --git a/parcel/api/parcel.h b/parcel/api/parcel.h
deleted file mode 100644 (file)
index 10dbaba..0000000
+++ /dev/null
@@ -1,566 +0,0 @@
-/*
- * Copyright (c) 2020 Samsung Electronics Co., Ltd. All rights reserved.
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#ifndef __PARCEL_H__
-#define __PARCEL_H__
-
-#include <stdint.h>
-#include <stddef.h>
-#include <tizen.h>
-
-/**
- * @addtogroup CORE_LIB_PARCEL_MODULE
- * @{
- */
-
-#ifdef __cplusplus
-extern "C" {
-#endif
-
-/**
- * @brief The parcel handle.
- * @since_tizen 6.5
- */
-typedef void *parcel_h;
-
-/**
- * @brief The interface for converting data to/from a parcel.
- * @since_tizen 6.5
- */
-typedef struct {
-       void (*to)(parcel_h parcel, void *data);
-       void (*from)(parcel_h parcel, void *data);
-} parcelable_t;
-
-/**
- * @brief Enumeration for error codes for a parcel.
- * @since_tizen 6.5
- */
-typedef enum {
-       PARCEL_ERROR_NONE = TIZEN_ERROR_NONE, /**< Successful */
-       PARCEL_ERROR_ILLEGAL_BYTE_SEQ = TIZEN_ERROR_ILLEGAL_BYTE_SEQ, /**< Illegal byte sequence */
-       PARCEL_ERROR_INVALID_PARAMETER = TIZEN_ERROR_INVALID_PARAMETER, /**< Invalid parameter */
-       PARCEL_ERROR_NO_DATA = TIZEN_ERROR_NO_DATA, /**< No data available */
-       PARCEL_ERROR_OUT_OF_MEMORY = TIZEN_ERROR_OUT_OF_MEMORY, /**< Out of memory */
-} parcel_error_e;
-
-/**
- * @brief Creates a parcel handle.
- * @since_tizen 6.5
- * @remarks You MUST release @a parcel using parcel_destroy().
- * @param[out] parcel The parcel handle that is newly created
- * @return @c 0 on success,
- *         otherwise a negative error value
- * @retval #PARCEL_ERROR_NONE Successful
- * @retval #PARCEL_ERROR_INVALID_PARAMETER Invalid parameter
- * @retval #PARCEL_ERROR_OUT_OF_MEMORY Out of memory
- * @see parcel_destroy()
- */
-int parcel_create(parcel_h *parcel);
-
-/**
- * @brief Destroys a parcel handle.
- * @since_tizen 6.5
- * @param[in] parcel The parcel handle
- * @return @c 0 on success,
- *         otherwise a negative error value
- * @retval #PARCEL_ERROR_NONE Successful
- * @retval #PARCEL_ERROR_INVALID_PARAMETER
- * @see parcel_create()
- */
-int parcel_destroy(parcel_h parcel);
-
-/**
- * @brief Creates and returns a copy of the given parcel handle.
- * @since_tizen 6.5
- * @remarks A newly created parcel should be destroyed by calling the parcel_destroy() if it is no longer needed.
- * @param[in] parcel The parcel handle
- * @param[out] If successful, a newly created parcel handle will be returned
- * @return @c 0 on success,
- *         otherwise a negative error value
- * @retval #PARCEL_ERROR_NONE Successful
- * @retval #PARCEL_ERROR_INVALID_PARAMETER Invalid parameter
- * @see parcel_destroy()
- */
-int parcel_clone(parcel_h parcel, parcel_h *clone);
-
-/**
- * @brief Writes bytes to the parcel handle.
- * @since_tizen 6.5
- * @param[in] parcel The parcel handle
- * @param[in] buf The array buffer to write
- * @param[in] size The size of bytes to write
- * @return @c 0 on success,
- *         otherwise a negative error value
- * @retval #PARCEL_ERROR_NONE Successful
- * @retval #PARCEL_ERROR_INVALID_PARAMETER Invalid parameter
- * @see parcel_burst_read()
- */
-int parcel_burst_write(parcel_h parcel, const void *buf, uint32_t size);
-
-/**
- * @brief Reads bytes from the parcel handle.
- * @since_tizen 6.5
- * @param[in] parcel The parcel handle
- * @param[out] buf The array buffer to read
- * @param[in] size The size of bytes to read
- * @return @c 0 on success,
- *         otherwise a negative error value
- * @retval #PARCEL_ERROR_NONE Successful
- * @retval #PARCEL_ERROR_INVALID_PARAMETER Invalid parameter
- * @retval #PARCEL_ERROR_NO_DATA No data available
- * @retval #PARCEL_ERROR_ILLEGAL_BYTE_SEQ Illegal byte sequence
- * @see parcel_burst_write()
- */
-int parcel_burst_read(parcel_h parcel, void *buf, uint32_t size);
-
-/**
- * @brief Writes a boolean value into the parcel handle.
- * @since_tizen 6.5
- * @param[in] parcel The parcel handle
- * @param[in] val The boolean value
- * @return @c 0 on success,
- *         otherwise a negative error value
- * @retval #PARCEL_ERROR_NONE Successful
- * @retval #PARCEL_ERROR_INVALID_PARAMETER Invalid parameter
- * @see parcel_read_bool()
- */
-int parcel_write_bool(parcel_h parcel, bool val);
-
-/**
- * @brief Writes a byte value into the parcel handle.
- * @since_tizen 6.5
- * @param[in] parcel The parcel handle
- * @param[in] val The byte value
- * @return @c 0 on success,
- *         otherwise a negative error value
- * @retval #PARCEL_ERROR_NONE Successful
- * @retval #PARCEL_ERROR_INVALID_PARAMETER Invalid parameter
- * @see parcel_read_uint8()
- */
-int parcel_write_byte(parcel_h parcel, char val);
-
-/**
- * @brief Writes an unsigned short value into the parcel handle.
- * @since_tizen 6.5
- * @param[in] parcel The parcel handle
- * @param[in] val The unsigned short value
- * @return @c 0 on success,
- *         otherwise a negative error value
- * @retval #PARCEL_ERROR_NONE Successful
- * @retval #PARCEL_ERROR_INVALID_PARAMETER Invalid parameter
- * @see parcel_read_uint16()
- */
-int parcel_write_uint16(parcel_h parcel, uint16_t val);
-
-/**
- * @brief Writes an unsigned integer value into the parcel handle.
- * @since_tizen 6.5
- * @param[in] parcel The parcel handle
- * @param[in] val The unsigned integer value
- * @return @c 0 on success,
- *         otherwise a negative error value
- * @retval #PARCEL_ERROR_NONE Successful
- * @retval #PARCEL_ERROR_INVALID_PARAMETER Invalid parameter
- * @see parcel_read_uint32()
- */
-int parcel_write_uint32(parcel_h parcel, uint32_t val);
-
-/**
- * @brief Writes an unsigned long long integer value into the parcel handle.
- * @since_tizen 6.5
- * @param[in] parcel The parcel handle
- * @param[in] val The unsigned long long interger value
- * @return @c 0 on success,
- *         otherwise a negative error value
- * @retval #PARCEL_ERROR_NONE Successful
- * @retval #PARCEL_ERROR_INVALID_PARAMETER Invalid parameter
- * @see parcel_read_uint64()
- */
-int parcel_write_uint64(parcel_h parcel, uint64_t val);
-
-/**
- * @brief Writes a signed short value into the parcel handle.
- * @since_tizen 6.5
- * @param[in] parcel The parcel handle
- * @param[in] val The signed short value
- * @return @c 0 on success,
- *         otherwise a negative error value
- * @retval #PARCEL_ERROR_NONE Successful
- * @retval #PARCEL_ERROR_INVALID_PARAMETER Invalid parameter
- * @see parcel_read_int16()
- */
-int parcel_write_int16(parcel_h parcel, int16_t val);
-
-/**
- * @brief Writes a signed integer value into the parcel handle.
- * @since_tizen 6.5
- * @param[in] parcel The parcel handle
- * @param[in] val The signed integer value
- * @return @c 0 on success,
- *         otherwise a negative error value
- * @retval #PARCEL_ERROR_NONE Successful
- * @retval #PARCEL_ERROR_INVALID_PARAMETER Invalid parameter
- * @see parcel_read_int32()
- */
-int parcel_write_int32(parcel_h parcel, int32_t val);
-
-/**
- * @brief Writes a signed long long integer value into the parcel handle.
- * @since_tizen 6.5
- * @param[in] parcel The parcel handle
- * @param[in] val The signedi long long integer value
- * @return @c 0 on success,
- *         otherwise a negative error value
- * @retval #PARCEL_ERROR_NONE Successful
- * @retval #PARCEL_ERROR_INVALID_PARAMETER Invalid parameter
- * @see parcel_read_int64()
- */
-int parcel_write_int64(parcel_h parcel, int64_t val);
-
-/**
- * @brief Writes a floating point value into the parcel handle.
- * @since_tizen 6.5
- * @param[in] parcel The parcel handle
- * @param[in] val The floating point value
- * @return @c 0 on success,
- *         otherwise a negative error value
- * @retval #PARCEL_ERROR_NONE Successful
- * @retval #PARCLE_ERROR_INVALID_PARAMETER Invalid parameter
- * @see parcel_read_float()
- */
-int parcel_write_float(parcel_h parcel, float val);
-
-/**
- * @brief Writes a double precision floating point value into the parcel handle.
- * @since_tizen 6.5
- * @param[in] parcel The parcel handle
- * @param[in] val The double precision floating point value
- * @return @c 0 on success,
- *         otherwise a negative error value
- * @retval #PARCEL_ERROR_NONE Successful
- * @retval #PARCLE_ERROR_INVALID_PARAMETER Invalid parameter
- * @see parcel_read_double()
- */
-int parcel_write_double(parcel_h parcel, double val);
-
-/**
- * @brief Writes a string data into the parcel handle.
- * @since_tizen 6.5
- * @param[in] parcel The parcel handle
- * @param[in] str The string data
- * @return @c 0 on success,
- *         otherwise a negative error value
- * @retval #PARCEL_ERROR_NONE Successful
- * @retval #PARCEL_ERROR_INVALID_PARAMETER Invalid parameter
- * @see parcel_read_string()
- */
-int parcel_write_string(parcel_h parcel, const char *str);
-
-/**
- * @brief Reads a boolean value from the parcel handle.
- * @since_tizen 6.5
- * @param[in] parcel The parcel handle
- * @param[out] val The boolean value
- * @return @c 0 on success,
- *         otherwise a negative error value
- * @retval #PARCEL_ERROR_NONE Successful
- * @retval #PARCEL_ERROR_INVALID_PARAMETER Invalid parameter
- * @retval #PARCEL_ERROR_NO_DATA No data available
- * @retval #PARCEL_ERROR_ILLEGAL_BYTE_SEQ Illegal byte sequence
- * @see parcel_write_bool()
- */
-int parcel_read_bool(parcel_h parcel, bool *val);
-
-/**
- * @brief Reads a byte value from the parcel handle.
- * @since_tizen 6.5
- * @param[in] parcel The parcel handle
- * @param[out] val The byte value
- * @return @c 0 on success,
- *         otherwise a negative error value
- * @retval #PARCEL_ERROR_NONE Successful
- * @retval #PARCEL_ERROR_INVALID_PARAMETER Invalid parameter
- * @retval #PARCEL_ERROR_NO_DATA No data available
- * @retval #PARCEL_ERROR_ILLEGAL_BYTE_SEQ Illegal byte sequence
- * @see parcel_write_uint8()
- */
-int parcel_read_byte(parcel_h parcel, char *val);
-
-/**
- * @brief Reads an unsigned short value from the parcel handle.
- * @since_tizen 6.5
- * @param[in] parcel The parcel handle
- * @param[out] val The unsigned short value
- * @return @c 0 on success,
- *         otherwise a negative error value
- * @retval #PARCEL_ERROR_NONE Successful
- * @retval #PARCEL_ERROR_INVALID_PARAMETER Invalid parameter
- * @retval #PARCEL_ERROR_NO_DATA No data available
- * @retval #PARCEL_ERROR_ILLEGAL_BYTE_SEQ Illegal byte sequence
- * @see parcel_write_uint16()
- */
-int parcel_read_uint16(parcel_h parcel, uint16_t *val);
-
-/**
- * @brief Reads an unsigned integer value from the parcel handle.
- * @since_tizen 6.5
- * @param[in] parcel The parcel handle
- * @param[out] val The unsigned integer value
- * @return @c 0 on success,
- *         otherwise a negative error value
- * @retval #PARCEL_ERROR_NONE Successful
- * @retval #PARCEL_ERROR_INVALID_PARAMETER Invalid parameter
- * @retval #PARCEL_ERROR_NO_DATA No data available
- * @retval #PARCEL_ERROR_ILLEGAL_BYTE_SEQ Illegal byte sequence
- * @see parcel_write_uint32()
- */
-int parcel_read_uint32(parcel_h parcel, uint32_t *val);
-
-/**
- * @brief Reads an unsigned long long integer value from the parcel handle.
- * @since_tizen 6.5
- * @param[in] parcel The parcel handle
- * @param[out] val The unsigned long long integer value
- * @return @c 0 on success,
- *         otherwise a negative error value
- * @retval #PARCEL_ERROR_NONE Successful
- * @retval #PARCEL_ERROR_INVALID_PARAMETER Invalid parameter
- * @retval #PARCEL_ERROR_NO_DATA No data available
- * @retval #PARCEL_ERROR_ILLEGAL_BYTE_SEQ Illegal byte sequence
- * @see parcel_write_uint64()
- */
-int parcel_read_uint64(parcel_h parcel, uint64_t *val);
-
-/**
- * @brief Reads a signed short value from the parcel handle.
- * @since_tizen 6.5
- * @param[in] parcel The parcel handle
- * @param[out] val The signed short value
- * @return @c 0 on success,
- *         otherwise a negative error value
- * @retval #PARCEL_ERROR_NONE Successful
- * @retval #PARCEL_ERROR_INVALID_PARAMETER Invalid parameter
- * @retval #PARCEL_ERROR_NO_DATA No data available
- * @retval #PARCEL_ERROR_ILLEGAL_BYTE_SEQ Illegal byte sequence
- * @see parcel_write_int16()
- */
-int parcel_read_int16(parcel_h parcel, int16_t *val);
-
-/**
- * @brief Reads a signed integer value from the parcel handle.
- * @since_tizen 6.5
- * @param[in] parcel The parcel handle
- * @param[out] val The signed integer value
- * @return @c 0 on success,
- *         otherwise a negative error value
- * @retval #PARCEL_ERROR_NONE Successful
- * @retval #PARCEL_ERROR_INVALID_PARAMETER Invalid parameter
- * @retval #PARCEL_ERROR_NO_DATA No data available
- * @retval #PARCEL_ERROR_ILLEGAL_BYTE_SEQ Illegal byte sequence
- * @see parcel_write_int32()
- */
-int parcel_read_int32(parcel_h parcel, int32_t *val);
-
-/**
- * @brief Reads a signed long long integer value from the parcel handle.
- * @since_tizen 6.5
- * @param[in] parcel The parcel handle
- * @param[out] val The signed long long integer value
- * @return @c 0 on success,
- *         otherwise a negative error value
- * @retval #PARCEL_ERROR_NONE Successful
- * @retval #PARCEL_ERROR_INVALID_PARAMETER Invalid parameter
- * @retval #PARCEL_ERROR_NO_DATA No data available
- * @retval #PARCEL_ERROR_ILLEGAL_BYTE_SEQ Illegal byte sequence
- * @see parcel_write_int64()
- */
-int parcel_read_int64(parcel_h parcel, int64_t *val);
-
-/**
- * @brief Reads a floating point value from the parcel handle.
- * @since_tizen 6.5
- * @param[in] parcel The parcel handle
- * @param[out] val The floating point value
- * @return @c 0 on success,
- *         otherwise a negative error value
- * @retval #PARCEL_ERROR_NONE Successful
- * @retval #PARCEL_ERROR_INVALID_PARAMETER Invalid parameter
- * @retval #PARCEL_ERROR_NO_DATA No data available
- * @retval #PARCEL_ERROR_ILLEGAL_BYTE_SEQ Illegal byte sequence
- * @see parcel_write_uint8()
- */
-int parcel_read_float(parcel_h parcel, float *val);
-
-/**
- * @brief Reads a double precision floating point value from the parcel handle.
- * @since_tizen 6.5
- * @param[in] parcel The parcel handle
- * @param[out] val The double precision floating point value
- * @return @c 0 on success,
- *         otherwise a negative error value
- * @retval #PARCEL_ERROR_NONE Successful
- * @retval #PARCEL_ERROR_INVALID_PARAMETER Invalid parameter
- * @retval #PARCEL_ERROR_NO_DATA No data available
- * @retval #PARCEL_ERROR_ILLEGAL_BYTE_SEQ Illegal byte sequence
- * @see parcel_write_uint8()
- */
-int parcel_read_double(parcel_h parcel, double *val);
-
-/**
- * @brief Reads a string data from the parcel handle.
- * @since_tizen 6.5
- * @param[in] parcel The parcel handle
- * @param[out] str The string data
- * @return @c 0 on success,
- *         otherwise a negative error value
- * @retval #PARCEL_ERROR_NONE Successful
- * @retval #PARCEL_ERROR_INVALID_PARAMETER Invalid parameter
- * @retval #PARCEL_ERROR_NO_DATA No data available
- * @retval #PARCEL_ERROR_ILLEGAL_BYTE_SEQ Illegal byte sequence
- * @retval #PARCEL_ERROR_OUT_OF_MEMORY Out of memory
- * @see parcel_write_uint8()
- */
-int parcel_read_string(parcel_h parcel, char **str);
-
-/**
- * @brief Resets the reader pointer of the parcel handle to the start.
- * @since_tizen 6.5
- * @param[in] parcel The parcel handle
- * @return @c 0 on success,
- *         otherwise a negative error value
- * @retval #PARCEL_ERROR_NONE Successful
- * @retval #PARCEL_ERROR_INVALID_PARAMETER Invalid parameter
- */
-int parcel_reset_reader(parcel_h parcel);
-
-/**
- * @brief Clears the data of the parcel handle.
- * @since_tizen 6.5
- * @param[in] parcel The parcel handle
- * @return @c 0 on success,
- *         otherwise a negative error value
- * @retval #PARCEL_ERROR_NONE Successful
- * @retval #PARCEL_ERROR_INVALID_PARAMETER Invalid parameter
- */
-int parcel_clear(parcel_h parcel);
-
-/**
- * @brief Resets the data of the parcel handle.
- * @since_tizen 6.5
- * @param[in] parcel The parcel handle
- * @param[in] buf The array buffer to write
- * @param[in] size The size of bytes to write
- * @return @c 0 on success,
- *         otherwise a negative error value
- * @retval #PARCEL_ERROR_NONE Successful
- * @retval #PARCEL_ERROR_INVALID_PARAMETER Invalid parameter
- */
-int parcel_reset(parcel_h parcel, const void *buf, uint32_t size);
-
-/**
- * @brief Writes the data using @a parcelable to the parcel handle.
- * @since_tizen 6.5
- * @param[in] parcel The parcel handle
- * @param[in] parcelable The interface to write the data into the parcel handle
- * @param[in] data The user data which writes into the parcel handle
- * @return @c 0 on success,
- *         otherwise a negative error value
- * @retval #PARCEL_ERROR_NONE Successful
- * @retval #PARCEL_ERROR_INVALID_PARAMETER Invalid parameter
- * @see parcel_read()
- */
-int parcel_write(parcel_h parcel, parcelable_t *parcelable, void *data);
-
-/**
- * @brief Reads the data using @a parcelable from the parcel handle.
- * @since_tizen 6.5
- * @param[in] parcel The parcel handle
- * @param[in] parcelable The interface to read the data from the parcel handle
- * @param[in] data The user data which reads from the parcel handle
- * @return @c 0 on success,
- *         otherwise a negative error value
- * @retval #PARCEL_ERROR_NONE Successful
- * @retval #PARCEL_ERROR_INVALID_PARAMETER Invalid parameter
- * @see parcel_write()
- */
-int parcel_read(parcel_h parcel, parcelable_t *parcelable, void *data);
-
-/**
- * @brief Gets the raw data of the parcel handle.
- * @since_tizen 6.5
- * @remarks You MUST NOT release @a raw using free(). It's managed by platform.
- * @param[in] parcel The parcel handle
- * @param[out] raw The raw data
- * @param[out] size The size of the raw data
- * @return @c 0 on success,
- *         otherwise a negative error value
- * @retval #PARCEL_ERROR_NONE Successful
- * @retval #PARCEL_ERROR_INVALID_PARAMETER Invalid parameter
- */
-int parcel_get_raw(parcel_h parcel, void **raw, uint32_t *size);
-
-/**
- * @brief Sets byte order of the parcel handle.
- * @since_tizen 6.5
- * @remarks The platform byte order is little-endian.
- *          The network byte order is defined to always be big-endian.
- *          If you want to change byte order of the raw data of the parcel handle,
- *          you set byte order of the parcel handle using the function.
- * @param[in] parcel The parcel handle
- * @param[in] big_endian @ true, if byte order of the parcel is big-endian
- * @return @c 0 on success,
- *         otherwise a negative error value
- * @retval #PARCEL_ERROR_NONE Successful
- * @retval #PARCEL_ERROR_INVALID_PARAMETER Invalid parameter
- */
-int parcel_set_byte_order(parcel_h parcle, bool big_endian);
-
-/**
- * @brief Gets the size of the data capacity of the parcel handle.
- * @since_tizen 7.0
- * @param[in] parcel The parcel handle
- * @param[out] size The size of the data capacity
- * @return @c 0 on success,
- *         otherwise a negative error value
- * @retval #PARCEL_ERROR_NONE Successful
- * @retval #PARCEL_ERROR_INVALID_PARAMETER Invalid parameter
- */
-int parcel_get_data_capacity(parcel_h parcel, size_t *size);
-
-/**
- * @brief Sets the size of the data capacity of the parcel handle.
- * @since_tizen 7.0
- * @remarks The raw data will be reallocated using the given size.
- * @param[in] parcel The parcel handle
- * @param[in] size The size of the data capacity
- * @return @c 0 on success,
- *         otherwise a negative error value
- * @retval #PARCEL_ERROR_NONE Successful
- * @retval #PARCEL_ERROR_INVALID_PARAMETER Invalid parameter
- * @retval #PARCEL_ERROR_OUT_OF_MEMORY
- */
-int parcel_set_data_capacity(parcel_h parcel, size_t size);
-
-#ifdef __cplusplus
-}
-#endif
-
-/**
- * @}
- */
-
-#endif /* __PARCEL_H__ */
diff --git a/parcel/common.hh b/parcel/common.hh
deleted file mode 100644 (file)
index 91f3535..0000000
+++ /dev/null
@@ -1,23 +0,0 @@
-/*
- * Copyright (c) 2020 Samsung Electronics Co., Ltd. All rights reserved.
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#ifndef PARCEL_COMMON_HH_
-#define PARCEL_COMMON_HH_
-
-#undef EXPORT
-#define EXPORT __attribute__((visibility("default")))
-
-#endif  // PARCEL_COMMON_HH_
diff --git a/parcel/log_private.hh b/parcel/log_private.hh
deleted file mode 100644 (file)
index a005add..0000000
+++ /dev/null
@@ -1,37 +0,0 @@
-/*
- * Copyright (c) 2020 Samsung Electronics Co., Ltd. All rights reserved.
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#ifndef PARCEL_LOG_PRIVATE_HH_
-#define PARCEL_LOG_PRIVATE_HH_
-
-#include <dlog.h>
-
-#undef LOG_TAG
-#define LOG_TAG "PARCEL"
-
-#undef _E
-#define _E LOGE
-
-#undef _W
-#define _W LOGW
-
-#undef _I
-#define _I LOGI
-
-#undef _D
-#define _D LOGD
-
-#endif  // PARCEL_LOG_PRIVATE_HH_
diff --git a/parcel/parcel.cc b/parcel/parcel.cc
deleted file mode 100644 (file)
index 1f266c0..0000000
+++ /dev/null
@@ -1,542 +0,0 @@
-/*
- * Copyright (c) 2020 Samsung Electronics Co., Ltd. All rights reserved.
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#include <glib.h>
-
-#include <exception>
-#include <mutex>
-
-#include "parcel/common.hh"
-#include "parcel/log_private.hh"
-#include "parcel/parcel.hh"
-#include "parcel/parcel_implementation.hh"
-#include "parcel/parcelable.hh"
-
-namespace tizen_base {
-namespace {
-
-constexpr const size_t kDataCapacity = 1024;
-
-}  // namespace
-
-Parcel::Impl::Impl(Parcel* parent, size_t data_capacity, uint8_t* data)
-    : parent_(parent), data_capacity_(data_capacity), data_(data) {
-  if (data_ != nullptr)
-    data_size_ = data_capacity_;
-  else
-    data_ = static_cast<uint8_t*>(malloc(data_capacity_));
-}
-
-Parcel::Impl::~Impl() {
-  free(data_);
-}
-
-void Parcel::Impl::Write(const void* buf, uint32_t size) {
-  if (data_size_ + size > data_capacity_) {
-    size_t new_size = (data_capacity_ + size) * 3 / 2;
-    uint8_t* data = static_cast<uint8_t*>(realloc(data_, new_size));
-    if (data == nullptr)
-      throw std::bad_alloc();
-
-    data_ = data;
-    data_capacity_ = new_size;
-  }
-
-  memcpy(data_ + data_size_, buf, size);
-  data_size_ += size;
-}
-
-int Parcel::Impl::Read(void* buf, uint32_t size) {
-  if (data_size_ == 0)
-    return TIZEN_ERROR_NO_DATA;
-
-  if (reader_ + size > data_size_)
-    return TIZEN_ERROR_ILLEGAL_BYTE_SEQ;
-
-  memcpy(buf, data_ + reader_, size);
-  reader_ += size;
-  set_last_result(TIZEN_ERROR_NONE);
-  return TIZEN_ERROR_NONE;
-}
-
-void Parcel::Impl::ResetReader() {
-  reader_ = 0;
-}
-
-void Parcel::Impl::Clear() {
-  data_size_ = 0;
-  reader_ = 0;
-}
-
-void Parcel::Impl::Reset(const void* buf, uint32_t size) {
-  Clear();
-  Write(buf, size);
-}
-
-bool Parcel::Impl::IsEmpty() {
-  return data_size_ == 0;
-}
-
-void Parcel::Impl::WriteSize(uint32_t size) {
-  if (IsBigEndian())
-    size = GUINT32_TO_BE(size);
-
-  Write<uint32_t>(size);
-}
-
-template <typename T>
-void Parcel::Impl::Write(T d) {
-  if (data_size_ + sizeof(T) > data_capacity_) {
-    size_t new_size = (data_capacity_ + sizeof(T)) * 3 / 2;
-    uint8_t* data = static_cast<uint8_t*>(realloc(data_, new_size));
-    if (data == nullptr)
-      throw std::bad_alloc();
-
-    data_ = data;
-    data_capacity_ = new_size;
-  }
-
-  auto* p = reinterpret_cast<uint8_t*>(&d);
-  memcpy(data_ + data_size_, p, sizeof(T));
-  data_size_ += sizeof(T);
-}
-
-int Parcel::Impl::ReadSize(uint32_t* size) {
-  if (data_size_ == 0)
-    return TIZEN_ERROR_NO_DATA;
-
-  int ret = Read<uint32_t>(size);
-  if (ret != TIZEN_ERROR_NONE)
-    return ret;
-
-  if (IsBigEndian())
-    *size = GUINT32_FROM_BE(*size);
-
-  return TIZEN_ERROR_NONE;
-}
-
-template <typename T>
-int Parcel::Impl::Read(T* d) {
-  uint32_t size = static_cast<uint32_t>(sizeof(T));
-  if (reader_ + size > data_size_)
-    return TIZEN_ERROR_ILLEGAL_BYTE_SEQ;
-
-  auto* p = reinterpret_cast<uint8_t*>(d);
-  memcpy(p, data_ + reader_, size);
-  reader_ += size;
-  return TIZEN_ERROR_NONE;
-}
-
-void Parcel::Impl::SetByteOrder(bool big_endian) {
-  big_endian_ = big_endian;
-}
-
-bool Parcel::Impl::IsBigEndian() const {
-  return big_endian_;
-}
-
-uint8_t* Parcel::Impl::GetData() const {
-  return data_;
-}
-
-size_t Parcel::Impl::GetDataSize() const {
-  return data_size_;
-}
-
-size_t Parcel::Impl::GetDataCapacity() const {
-  return data_capacity_;
-}
-
-void Parcel::Impl::SetDataCapacity(size_t size) {
-  uint8_t* data = static_cast<uint8_t*>(realloc(data_, size));
-  if (data == nullptr)
-    throw std::bad_alloc();
-
-  data_ = data;
-  data_capacity_ = size;
-}
-
-uint8_t* Parcel::Impl::Detach(size_t* size) {
-  uint8_t* data = data_;
-  *size = data_size_;
-  data_ = nullptr;
-  data_capacity_ = 0;
-  data_size_ = 0;
-  reader_= 0;
-  return data;
-}
-
-uint32_t Parcel::Impl::GetReader() const {
-  return reader_;
-}
-
-std::vector<uint8_t> Parcel::Impl::ToRaw() {
-  return std::vector<uint8_t>(data_, data_ + data_size_);
-}
-
-Parcel::Parcel()
-    : impl_(new Impl(this, kDataCapacity, nullptr)) {
-  if (impl_->data_ == nullptr)
-    throw std::bad_alloc();
-}
-
-Parcel::Parcel(const void* buf, uint32_t size, bool copy)
-    : impl_(new Impl(this, size,
-          copy ? nullptr : static_cast<uint8_t*>(const_cast<void*>(buf)))) {
-  if (impl_->data_ == nullptr)
-    throw std::bad_alloc();
-
-  if (copy)
-    impl_->Write(buf, size);
-}
-
-Parcel::~Parcel() {};
-
-Parcel::Parcel(const Parcel& p)
-  : impl_(new Impl(this, kDataCapacity)) {
-  impl_->big_endian_ = p.impl_->big_endian_;
-  impl_->data_capacity_ = p.impl_->data_capacity_;
-  impl_->data_size_ = p.impl_->data_size_;
-
-  uint8_t* data = static_cast<uint8_t*>(
-      realloc(impl_->data_, impl_->data_capacity_));
-  if (data == nullptr)
-    throw std::bad_alloc();
-
-  impl_->data_ = data;
-  memcpy(impl_->data_, p.impl_->data_, impl_->data_size_);
-
-  impl_->reader_ = p.impl_->reader_;
-}
-
-Parcel& Parcel::operator = (const Parcel& p) {
-  if (this != &p) {
-    impl_->big_endian_ = p.impl_->big_endian_;
-    impl_->data_capacity_ = p.impl_->data_capacity_;
-    impl_->data_size_ = p.impl_->data_size_;
-
-    uint8_t* data = static_cast<uint8_t*>(
-        realloc(impl_->data_, impl_->data_capacity_));
-    if (data == nullptr)
-      throw std::bad_alloc();
-
-    impl_->data_ = data;
-    memcpy(impl_->data_, p.impl_->data_, impl_->data_size_);
-
-    impl_->reader_ = p.impl_->reader_;
-  }
-  return *this;
-}
-
-Parcel::Parcel(Parcel&& p) noexcept
-    : impl_(new Impl(this, kDataCapacity)) {
-  impl_->big_endian_ = p.impl_->big_endian_;
-
-  impl_->data_size_ = p.impl_->data_size_;
-  p.impl_->data_size_ = 0;
-
-  uint8_t* data = impl_->data_;
-  size_t data_capacity = impl_->data_capacity_;
-
-  impl_->data_ = p.impl_->data_;
-  impl_->data_capacity_ = p.impl_->data_capacity_;
-
-  p.impl_->data_ = data;
-  p.impl_->data_capacity_ = data_capacity;
-
-  impl_->reader_ = p.impl_->reader_;
-  p.impl_->reader_ = 0;
-}
-
-Parcel& Parcel::operator = (Parcel&& p) noexcept {
-  if (this != &p) {
-    impl_->big_endian_ = p.impl_->big_endian_;
-
-    impl_->data_size_ = p.impl_->data_size_;
-    p.impl_->data_size_ = 0;
-
-    uint8_t* data = impl_->data_;
-    size_t data_capacity = impl_->data_capacity_;
-
-    impl_->data_ = p.impl_->data_;
-    impl_->data_capacity_ = p.impl_->data_capacity_;
-
-    p.impl_->data_ = data;
-    p.impl_->data_capacity_ = data_capacity;
-
-    impl_->reader_ = p.impl_->reader_;
-    p.impl_->reader_ = 0;
-  }
-  return *this;
-}
-
-bool Parcel::IsEmpty() const noexcept {
-  return impl_->IsEmpty();
-}
-
-void Parcel::Write(const void* buf, uint32_t size) {
-  impl_->Write(buf, size);
-}
-
-int Parcel::Read(void* buf, uint32_t size) {
-  return impl_->Read(buf, size);
-}
-
-void Parcel::WriteBool(bool val) {
-  impl_->Write<bool>(val);
-}
-
-void Parcel::WriteByte(char val) {
-  impl_->Write<char>(val);
-}
-
-void Parcel::WriteUInt16(uint16_t val) {
-  if (impl_->IsBigEndian())
-    val = GUINT16_TO_BE(val);
-
-  impl_->Write<uint16_t>(val);
-}
-
-void Parcel::WriteUInt32(uint32_t val) {
-  if (impl_->IsBigEndian())
-    val = GUINT32_TO_BE(val);
-
-  impl_->Write<uint32_t>(val);
-}
-
-void Parcel::WriteUInt64(uint64_t val) {
-  if (impl_->IsBigEndian())
-    val = GUINT64_TO_BE(val);
-
-  impl_->Write<uint64_t>(val);
-}
-
-void Parcel::WriteInt16(int16_t val) {
-  if (impl_->IsBigEndian())
-    val = GINT16_TO_BE(val);
-
-  impl_->Write<int16_t>(val);
-}
-
-void Parcel::WriteInt32(int32_t val) {
-  if (impl_->IsBigEndian())
-    val = GINT32_TO_BE(val);
-
-  impl_->Write<int32_t>(val);
-}
-
-void Parcel::WriteInt64(int64_t val) {
-  if (impl_->IsBigEndian())
-    val = GINT64_TO_BE(val);
-
-  impl_->Write<int64_t>(val);
-}
-
-void Parcel::WriteFloat(float val) {
-  if (impl_->IsBigEndian())
-    val = static_cast<float>(GINT32_TO_BE(val));
-
-  impl_->Write<float>(val);
-}
-
-void Parcel::WriteDouble(double val) {
-  if (impl_->IsBigEndian())
-    val = static_cast<double>(GINT64_TO_BE(val));
-
-  impl_->Write<double>(val);
-}
-
-void Parcel::WriteString(const std::string& str) {
-  impl_->WriteSize(str.length() + 1);
-  impl_->Write(str.c_str(), str.length() + 1);
-}
-
-void Parcel::WriteCString(const char* str) {
-  impl_->WriteSize(strlen(str) + 1);
-  impl_->Write(str, strlen(str) + 1);
-}
-
-int Parcel::ReadBool(bool* val) {
-  return impl_->Read<bool>(val);
-}
-
-int Parcel::ReadByte(char* val) {
-  return impl_->Read<char>(val);
-}
-
-int Parcel::ReadUInt16(uint16_t* val) {
-  int ret = impl_->Read<uint16_t>(val);
-  if (impl_->IsBigEndian())
-    *val = GUINT16_FROM_BE(*val);
-
-  return ret;
-}
-
-int Parcel::ReadUInt32(uint32_t* val) {
-  int ret = impl_->Read<uint32_t>(val);
-  if (impl_->IsBigEndian())
-    *val = GUINT32_FROM_BE(*val);
-
-  return ret;
-}
-
-int Parcel::ReadUInt64(uint64_t* val) {
-  int ret = impl_->Read<uint64_t>(val);
-  if (impl_->IsBigEndian())
-    *val = GUINT64_FROM_BE(*val);
-
-  return ret;
-}
-
-int Parcel::ReadInt16(int16_t* val) {
-  int ret = impl_->Read<int16_t>(val);
-  if (impl_->IsBigEndian())
-    *val = GINT16_FROM_BE(*val);
-
-  return ret;
-}
-
-int Parcel::ReadInt32(int32_t* val) {
-  int ret = impl_->Read<int32_t>(val);
-  if (impl_->IsBigEndian())
-    *val = GINT32_FROM_BE(*val);
-
-  return ret;
-}
-
-int Parcel::ReadInt64(int64_t* val) {
-  int ret = impl_->Read<int64_t>(val);
-  if (impl_->IsBigEndian())
-    *val = GINT64_FROM_BE(*val);
-
-  return ret;
-}
-
-int Parcel::ReadFloat(float* val) {
-  int ret = impl_->Read<float>(val);
-  if (impl_->IsBigEndian())
-    *val = static_cast<float>(GINT32_FROM_BE(*val));
-
-  return ret;
-}
-
-int Parcel::ReadDouble(double* val) {
-  int ret = impl_->Read<double>(val);
-  if (impl_->IsBigEndian())
-    *val = static_cast<double>(GINT64_FROM_BE(*val));
-
-  return ret;
-}
-
-std::string Parcel::ReadString() {
-  uint32_t len = 0;
-  int ret = impl_->ReadSize(&len);
-  if (ret != TIZEN_ERROR_NONE) {
-    set_last_result(ret);
-    return {};
-  }
-
-  char* str = new (std::nothrow) char[len];
-  if (str == nullptr) {
-    set_last_result(TIZEN_ERROR_OUT_OF_MEMORY);
-    return {};
-  }
-
-  auto ptr = std::unique_ptr<char[]>(str);
-  ret = impl_->Read(str, len);
-  if (ret != TIZEN_ERROR_NONE) {
-    set_last_result(ret);
-    return {};
-  }
-
-  set_last_result(TIZEN_ERROR_NONE);
-  return std::string(str);
-}
-
-int Parcel::ReadCString(char** str) {
-  uint32_t len = 0;
-  int ret = impl_->ReadSize(&len);
-  if (ret != TIZEN_ERROR_NONE)
-    return ret;
-
-  char* val = static_cast<char*>(calloc(len, sizeof(char)));
-  if (val == nullptr)
-    return TIZEN_ERROR_OUT_OF_MEMORY;
-
-  ret = impl_->Read(val, len);
-  if (ret != TIZEN_ERROR_NONE) {
-    free(val);
-    return ret;
-  }
-
-  *str = val;
-  return TIZEN_ERROR_NONE;
-}
-
-void Parcel::ResetReader() {
-  impl_->ResetReader();
-}
-
-void Parcel::Clear() {
-  impl_->Clear();
-}
-
-void Parcel::Reset(const void* buf, uint32_t size) {
-  impl_->Reset(buf, size);
-}
-
-void Parcel::WriteParcelable(const Parcelable& parcelable) {
-  parcelable.WriteToParcel(this);
-}
-
-int Parcel::ReadParcelable(Parcelable* parcelable) {
-  parcelable->ReadFromParcel(this);
-  return TIZEN_ERROR_NONE;
-}
-
-void Parcel::SetByteOrder(bool big_endian) {
-  impl_->SetByteOrder(big_endian);
-}
-
-uint8_t* Parcel::GetData() const {
-  return impl_->GetData();
-}
-
-size_t Parcel::GetDataSize() const {
-  return impl_->GetDataSize();
-}
-
-size_t Parcel::GetDataCapacity() const {
-  return impl_->GetDataCapacity();
-}
-
-void Parcel::SetDataCapacity(size_t size) {
-  impl_->SetDataCapacity(size);
-}
-
-uint8_t* Parcel::Detach(size_t* size) {
-  return impl_->Detach(size);
-}
-
-uint32_t Parcel::GetReader() const {
-  return impl_->GetReader();
-}
-
-std::vector<uint8_t> Parcel::ToRaw() {
-  return impl_->ToRaw();
-}
-
-}  // namespace tizen_base
diff --git a/parcel/parcel.hh b/parcel/parcel.hh
deleted file mode 100644 (file)
index 7d94d00..0000000
+++ /dev/null
@@ -1,435 +0,0 @@
-/*
- * Copyright (c) 2020 Samsung Electronics Co., Ltd. All rights reserved.
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#ifndef PARCEL_PARCEL_HH_
-#define PARCEL_PARCEL_HH_
-
-/**
- * @addtogroup CORE_LIB_PARCEL_MODULE
- * @{
- */
-
-#include <tizen.h>
-
-#include <memory>
-#include <string>
-#include <vector>
-
-#include "parcel/common.hh"
-#include "parcel/parcelable.hh"
-
-namespace tizen_base {
-
-/**
- * @brief The class for Parcel API.
- * @since_tizen 6.5
- */
-class EXPORT Parcel final {
- public:
-  /**
-   * @brief Enumeration for parcel error.
-   * @since_tizen 6.5
-   */
-  enum Error {
-    None = TIZEN_ERROR_NONE, /**< Successful */
-    IllegalByteSeq = TIZEN_ERROR_ILLEGAL_BYTE_SEQ, /**< Illegal byte sequence */
-    InvalidParameter = TIZEN_ERROR_INVALID_PARAMETER, /**< Invalid parameter */
-    NoData = TIZEN_ERROR_NO_DATA, /**< No data available */
-    OutOfMemory = TIZEN_ERROR_OUT_OF_MEMORY, /**< Out of memory */
-  };
-
-  /**
-   * @brief Constructor.
-   * @since_tizen 6.5
-   */
-  Parcel();
-
-  /**
-   * @brief Constructor
-   * @since_tizen 6.5
-   * @param[in] buf The bytes to write
-   * @param[in] size the size of bytes to write
-   * @param[in] copy If @c is true, this object copies bytes.
-   *                 If @c is false, this object takes ownership of @buf.
-   */
-  Parcel(const void* buf, uint32_t size, bool copy = true);
-
-  /**
-   * @brief Destructor
-   * @since_tizen 6.5
-   */
-  ~Parcel();
-
-  /**
-   * @brief Copy-constructor.
-   * @since_tizen 6.5
-   * @param[in] p The object to copy
-   */
-  Parcel(const Parcel& p);
-
-  /**
-   * @brief Assignment.
-   * @since_tizen 6.5
-   * @param[in] b The object to copy
-   */
-  Parcel& operator = (const Parcel& p);
-
-  /**
-   * @brief Move-constructor.
-   * @since_tizen 6.5
-   * @param[in] p The object to move
-   */
-  Parcel(Parcel&& p) noexcept;
-
-  /**
-   * @brief Assignment.
-   * @since_tizen 6.5
-   * @param[in] p The object to move
-   */
-  Parcel& operator = (Parcel&& p) noexcept;
-
-  /**
-   * @brief Checks the parcel is empty or not.
-   * @since_tizen 6.5
-   * @return true if the parcel is empty
-   */
-  bool IsEmpty() const noexcept;
-
-  /**
-   * @brief Writes bytes into the parcel.
-   * @since_tizen 6.5
-   * @param[in] buf The bytes to write
-   * @param[in] size The size of bytes to write
-   */
-  void Write(const void* buf, uint32_t size);
-
-  /**
-   * @brief Reads bytes from the parcel.
-   * @since_tizen 6.5
-   * @param[out] buf The bytes to read
-   * @param[in] size The size of bytes to read
-   * @return @c 0 on success,
-   *         otherwise a negative error value
-   */
-  int Read(void* buf, uint32_t size);
-
-  /**
-   * @brief Writes a boolean value into the parcel.
-   * @since_tizen 6.5
-   * @param[in] val The boolean value
-   */
-  void WriteBool(bool val);
-
-  /**
-   * @brief Writes a byte value into the parcel.
-   * @since_tizen 6.5
-   * @param[in] val The unsigned byte value
-   */
-  void WriteByte(char byte);
-
-  /**
-   * @brief Writes an unsigned short value into the parcel.
-   * @since_tizen 6.5
-   * @param[in] val The unsigned short value
-   */
-  void WriteUInt16(uint16_t val);
-
-  /**
-   * @brief Writes an unsigned integer value into the parcel.
-   * @since_tizen 6.5
-   * @param[in] val The unsigned integer value
-   */
-  void WriteUInt32(uint32_t val);
-
-  /**
-   * @brief Writes an unsigned long long integer into the parcel.
-   * @since_tizen 6.5
-   * @param[in] val The unsigned long long integer value
-   */
-  void WriteUInt64(uint64_t val);
-
-  /**
-   * @brief Writes a signed short value into the parcel.
-   * @since_tizen 6.5
-   * @param[in] val The signed short value
-   */
-  void WriteInt16(int16_t val);
-
-  /**
-   * @brief Writes a signed integer value into the parcel.
-   * @since_tizen 6.5
-   * @param[in] val The signed integer value
-   */
-  void WriteInt32(int32_t val);
-
-  /**
-   * @brief Writes a signed long long integer value into the parcel.
-   * @since_tizen 6.5
-   * @param[in] val The signed long long integer value
-   */
-  void WriteInt64(int64_t val);
-
-  /**
-   * @brief Writes a floating point value into the parcel.
-   * @since_tizen 6.5
-   * @param[in] val The floating point value
-   */
-  void WriteFloat(float val);
-
-  /**
-   * @brief Writes a double precision floating point value into the parcel.
-   * @since_tizen 6.5
-   * @param[in] val The double precision floating point value
-   */
-  void WriteDouble(double val);
-
-  /**
-   * @brief Writes a string data into the parcel.
-   * @since_tizen 6.5
-   * @param[in] str The string data
-   */
-  void WriteString(const std::string& str);
-
-  /**
-   * @brief Writes a string data into the parcel.
-   * @since_tizen 6.5
-   * @param[in] str The string data
-   */
-  void WriteCString(const char* str);
-
-  /**
-   * @brief Reads a boolean value from the parcel.
-   * @since_tizen 6.5
-   * @param[out] val The boolean value
-   * @return @c 0 on success,
-   *         otherwise a negative error value
-   */
-  int ReadBool(bool* val);
-
-  /**
-   * @brief Reads a byte value from the parcel.
-   * @since_tizen 6.5
-   * @param[out] val The unsigned byte value
-   * @return @c 0 on success,
-   *         otherwise a negative error value
-   */
-  int ReadByte(char* val);
-
-  /**
-   * @breif Reads an unsigned short value from the parcel.
-   * @since_tizen 6.5
-   * @param[out] val The unsigned short value
-   * @return @c 0 on success,
-   *         otherwise a negative error value
-   */
-  int ReadUInt16(uint16_t* val);
-
-  /**
-   * @brief Reads an unsigned integer value from the parcel.
-   * @since_tizen 6.5
-   * @param[out] val The unsigned integer value
-   * @return @c 0 on success,
-   *         otherwise a negative error value
-   */
-  int ReadUInt32(uint32_t* val);
-
-  /**
-   * @brief Reads an unsigned long long integer value from the parcel.
-   * @since_tizen 6.5
-   * @param[out] val The unsigned long long integer value
-   * @return @c 0 on success,
-   *         otherwise a negative error value
-   */
-  int ReadUInt64(uint64_t* val);
-
-  /**
-   * @brief Reads a signed byte value from the parcel.
-   * @since_tizen 6.5
-   * @param[out] val The signed byte value
-   * @return @c 0 on success,
-   *         otherwise a negative error value
-   */
-  int ReadInt8(int8_t* val);
-
-  /**
-   * @brief Reads a signed short value from the parcel.
-   * @since_tizen 6.5
-   * @param[out] val The signed short value
-   * @return @c 0 on success,
-   *         otherwise a negative error value
-   */
-  int ReadInt16(int16_t* val);
-
-  /**
-   * @brief Reads a signed integer value from the parcel.
-   * @since_tizen 6.5
-   * @param[out] val The signed integer value
-   * @return @c 0 on success,
-   *         otherwise a negative error value
-   */
-  int ReadInt32(int32_t* val);
-
-  /**
-   * @brief Reads a signed long long integer value from the parcel.
-   * @since_tizen 6.5
-   * @param[out] val The signed long long integer value
-   * @return @c 0 on success,
-   *         otherwise a negative error value
-   */
-  int ReadInt64(int64_t* val);
-
-  /**
-   * @brief Reads a floating point value from the parcel.
-   * @since_tizen 6.5
-   * @param[out] val The floating point value
-   * @return @c 0 on success,
-   *         otherwise a negative error value
-   */
-  int ReadFloat(float* val);
-
-  /**
-   * @brief Reads a double precision floating point value from the parcel.
-   * @since_tizen 6.5
-   * @param[out] val The double precision floating point value
-   * @return @c 0 on success,
-   *         otherwise a negative error value
-   */
-  int ReadDouble(double* val);
-
-  /**
-   * @brief Reads a string data from the parcel.
-   * @since_tizen 6.5
-   * @return The string data
-   * @remarks Before using the returned value, you should check the result using get_last_result().
-   * @see get_last_result()
-   */
-  std::string ReadString();
-
-  /**
-   * @brief Reads a string data from the parcel.
-   * @since_tizen 6.5
-   * @remarks You should release @a str using free().
-   * @param[out] str The string data
-   * @return @c 0 on success,
-   *         otherwise a negative error value
-   */
-  int ReadCString(char** str);
-
-  /**
-   * @brief Resets the reader pointer of the parcel to the start.
-   * @since_tizen 6.5
-   */
-  void ResetReader();
-
-  /**
-   * @brief Clears the data of the parcel.
-   * @since_tizen 6.5
-   */
-  void Clear();
-
-  /**
-   * @brief Resets the parcel.
-   * @since_tizen 6.5
-   * @param[in] buf The bytes to write
-   * @param[in] size The size of bytes to write
-   */
-  void Reset(const void* buf, uint32_t size);
-
-  /**
-   * @brief Writes the data using @a parcelable into the parcel.
-   * @since_tizen 6.5
-   * @param[in] parcelable The interface to write the data into the parcel
-   */
-  void WriteParcelable(const Parcelable& parcelable);
-
-  /**
-   * @brief Reads the data using @a parcelable from the parcel.
-   * @since_tizen 6.5
-   * @param[out] parcelable The interface to get data from the parcel
-   * @return @c 0 on success,
-   *         otherwise a negative error value
-   */
-  int ReadParcelable(Parcelable* parcelable);
-
-  /**
-   * @brief Sets byte order of the parcel.
-   * @since_tizen 6.5
-   * @param[in] big_endian @c true, if byte order of the parcel is big-endian
-   */
-  void SetByteOrder(bool big_endian);
-
-  /**
-   * @brief Gets the raw data of the parcel.
-   * @since_tizen 7.0
-   * @return The raw data
-   */
-  uint8_t* GetData() const;
-
-  /**
-   * @breif Gets the size of the raw data of the parcel.
-   * @since_tizen 7.0
-   * @return The size of the raw data
-   */
-  size_t GetDataSize() const;
-
-  /**
-   * @brief Gets the size of the data capacity of the parcel.
-   * @since_tizen 7.0
-   * @return The size of the data capacity
-   */
-  size_t GetDataCapacity() const;
-
-  /**
-   * @breif Sets the size of the data capacity of the parcel.
-   * @since_tizen 7.0
-   * @param[in] size The size of the data capcity
-   */
-  void SetDataCapacity(size_t size);
-
-  /**
-   * @brief Detaches the raw data from the parcel.
-   * @since_tizen 7.0
-   * @param[out] size The size of the raw data
-   * @return The raw data
-   */
-  uint8_t* Detach(size_t* size);
-
-  /**
-   * @brief Gets the position of the reader of the parcel.
-   * @since_tizen 7.0
-   * @return The position of the reader
-   */
-  uint32_t GetReader() const;
-
-  /**
-   * @brief Converts the raw data of the parcel to the vector.
-   * @since_tizen 7.0
-   * @return The vector of the raw data
-   */
-  std::vector<uint8_t> ToRaw();
-
- private:
-  class Impl;
-  std::unique_ptr<Impl> impl_;
-};
-
-}  // naemspace tizen_base
-
-/**
- * @}
- */
-
-#endif  // PARCEL_PARCEL_HH_
diff --git a/parcel/parcel.pc.in b/parcel/parcel.pc.in
deleted file mode 100644 (file)
index 0238b17..0000000
+++ /dev/null
@@ -1,14 +0,0 @@
-# Package Information for pkg-config
-
-prefix=@PREFIX@
-exec_prefix=${prefix}
-libdir=@LIB_INSTALL_DIR@
-includedir=${prefix}/include
-
-Name: parcel
-Description: Parcel library
-Version: @VERSION@
-Requires: capi-base-common
-Libs: -L${libdir} -lparcel
-Cflags: -I${includedir} -I${includedir}/parcel
-cppflags: -I${includedir} -I${includedir}/parcel
diff --git a/parcel/parcel_implementation.hh b/parcel/parcel_implementation.hh
deleted file mode 100644 (file)
index d9a9c7d..0000000
+++ /dev/null
@@ -1,71 +0,0 @@
-/*
- * Copyright (c) 2020 Samsung Electronics Co., Ltd. All rights reserved.
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#ifndef PARCEL_PARCEL_IMPLEMENTATION_HH_
-#define PARCEL_PARCEL_IMPLEMENTATION_HH_
-
-#include <string>
-#include <vector>
-
-#include "parcel/parcel.hh"
-#include "parcel/parcelable.hh"
-
-namespace tizen_base {
-
-class Parcel::Impl {
- public:
-  virtual ~Impl();
-
-  void Write(const void* buf, uint32_t size);
-  int Read(void* buf, uint32_t size);
-  void ResetReader();
-  void Clear();
-  void Reset(const void* buf, uint32_t size);
-  bool IsEmpty();
-  void WriteSize(uint32_t size);
-  int ReadSize(uint32_t* size);
-
-  template <typename T>
-  void Write(T d);
-  template <typename T>
-  int Read(T* d);
-
-  void SetByteOrder(bool big_endian);
-  bool IsBigEndian() const;
-  uint8_t* GetData() const;
-  size_t GetDataSize() const;
-  size_t GetDataCapacity() const;
-  void SetDataCapacity(size_t size);
-  uint8_t* Detach(size_t* size);
-  uint32_t GetReader() const;
-  std::vector<uint8_t> ToRaw();
-
- private:
-  friend class Parcel;
-  explicit Impl(Parcel* parent, size_t data_capacity, uint8_t* data = nullptr);
-
- private:
-  Parcel* parent_;
-  size_t data_capacity_;
-  bool big_endian_ = false;
-  size_t data_size_ = 0;
-  uint8_t* data_ = nullptr;
-  uint32_t reader_ = 0;
-};
-
-}  // naemspace tizen_base
-
-#endif  // PARCEL_PARCEL_IMPLEMENTATION_HH_
diff --git a/parcel/parcelable.hh b/parcel/parcelable.hh
deleted file mode 100644 (file)
index 6dc9471..0000000
+++ /dev/null
@@ -1,76 +0,0 @@
-/*
- * Copyright (c) 2020 Samsung Electronics Co., Ltd. All rights reserved.
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#ifndef PARCEL_PARCELABLE_HH_
-#define PARCEL_PARCELABLE_HH_
-
-/**
- * @addtogroup CORE_LIB_PARCEL_MODULE
- * @{
- */
-
-#include "parcel/common.hh"
-
-namespace tizen_base {
-
-class Parcel;
-
-/**
- * @brief The Parcelable interface.
- * @since_tizen 6.5
- */
-class EXPORT Parcelable {
- public:
-  /**
-   * @brief Constructor.
-   * @since_tizen 6.5
-   */
-  Parcelable() = default;
-
-  /**
-   * @brief Copy constructor.
-   * @since_tizen 6.5
-   */
-  Parcelable(const Parcelable&) = default;
-
-  /**
-   * @brief Destructor.
-   * @since_tizen 6.5
-   */
-  virtual ~Parcelable() = default;
-
-  /**
-   * @brief Writes the data into the parcel.
-   * @since_tizen 6.5
-   * @param[in] parcel The parcel object
-   */
-  virtual void WriteToParcel(Parcel* parcel) const = 0;
-
-  /**
-   * @brief Reads the data from the parcel.
-   * @since_tizen 6.5
-   * @param[in] parcel The parcel object
-   */
-  virtual void ReadFromParcel(Parcel* parcel) = 0;
-};
-
-}  // naemspace tizen_base
-
-/**
- * @}
- */
-
-#endif  // PARCEL_PARCELABLE_HH_
diff --git a/parcel/stub.cc b/parcel/stub.cc
deleted file mode 100644 (file)
index 245e3ac..0000000
+++ /dev/null
@@ -1,437 +0,0 @@
-/*
- * Copyright (c) 2020 Samsung Electronics Co., Ltd. All rights reserved.
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#include "parcel/api/parcel.h"
-
-#include <exception>
-
-#include "parcel/common.hh"
-#include "parcel/log_private.hh"
-#include "parcel/parcel.hh"
-#include "parcel/parcelable.hh"
-
-using namespace tizen_base;
-
-extern "C" EXPORT int parcel_create(parcel_h *parcel) {
-  if (parcel == nullptr) {
-    _E("Invalid parameter");
-    return PARCEL_ERROR_INVALID_PARAMETER;
-  }
-
-  auto* h = new (std::nothrow) Parcel();
-  if (h == nullptr) {
-    _E("Out of memory");
-    return PARCEL_ERROR_OUT_OF_MEMORY;
-  }
-
-  *parcel = static_cast<parcel_h>(h);
-  return PARCEL_ERROR_NONE;
-}
-
-extern "C" EXPORT int parcel_destroy(parcel_h parcel) {
-  if (parcel == nullptr) {
-    _E("Invalid parameter");
-    return PARCEL_ERROR_INVALID_PARAMETER;
-  }
-
-  auto* h = static_cast<Parcel*>(parcel);
-  delete h;
-  return PARCEL_ERROR_NONE;
-}
-
-extern "C" EXPORT int parcel_clone(parcel_h parcel, parcel_h* clone) {
-  if (parcel == nullptr || clone == nullptr) {
-    _E("Invalid parameter");
-    return PARCEL_ERROR_INVALID_PARAMETER;
-  }
-
-  auto* h = static_cast<Parcel*>(parcel);
-  auto* c = new (std::nothrow) Parcel(*h);
-  if (c == nullptr) {
-    _E("Out of memory");
-    return PARCEL_ERROR_OUT_OF_MEMORY;
-  }
-
-  *clone = static_cast<parcel_h>(c);
-  return PARCEL_ERROR_NONE;
-}
-
-extern "C" EXPORT int parcel_burst_write(parcel_h parcel, const void *buf,
-    uint32_t size) {
-  if (parcel == nullptr || buf == nullptr || size == 0) {
-    _E("Invalid parameter");
-    return PARCEL_ERROR_INVALID_PARAMETER;
-  }
-
-  auto* h = static_cast<Parcel*>(parcel);
-  h->Write(buf, size);
-  return PARCEL_ERROR_NONE;
-}
-
-extern "C" EXPORT int parcel_burst_read(parcel_h parcel, void *buf,
-    uint32_t size) {
-  if (parcel == nullptr || buf == nullptr || size == 0) {
-    _E("Invalid parameter");
-    return PARCEL_ERROR_INVALID_PARAMETER;
-  }
-
-  auto* h = static_cast<Parcel*>(parcel);
-  h->Read(buf, size);
-  return PARCEL_ERROR_NONE;
-}
-
-extern "C" EXPORT int parcel_write_bool(parcel_h parcel, bool val) {
-  if (parcel == nullptr) {
-    _E("Invalid parameter");
-    return PARCEL_ERROR_INVALID_PARAMETER;
-  }
-
-  auto* h = static_cast<Parcel*>(parcel);
-  h->WriteBool(val);
-  return PARCEL_ERROR_NONE;
-}
-
-extern "C" EXPORT int parcel_write_byte(parcel_h parcel, char val) {
-  if (parcel == nullptr) {
-    _E("Invalid parameter");
-    return PARCEL_ERROR_INVALID_PARAMETER;
-  }
-
-  auto* h = static_cast<Parcel*>(parcel);
-  h->WriteByte(val);
-  return PARCEL_ERROR_NONE;
-}
-
-extern "C" EXPORT int parcel_write_uint16(parcel_h parcel, uint16_t val) {
-  if (parcel == nullptr) {
-    _E("Invalid parameter");
-    return PARCEL_ERROR_INVALID_PARAMETER;
-  }
-
-  auto* h = static_cast<Parcel*>(parcel);
-  h->WriteUInt16(val);
-  return PARCEL_ERROR_NONE;
-}
-
-extern "C" EXPORT int parcel_write_uint32(parcel_h parcel, uint32_t val) {
-  if (parcel == nullptr) {
-    _E("Invalid parameter");
-    return PARCEL_ERROR_INVALID_PARAMETER;
-  }
-
-  auto* h = static_cast<Parcel*>(parcel);
-  h->WriteUInt32(val);
-  return PARCEL_ERROR_NONE;
-}
-
-extern "C" EXPORT int parcel_write_uint64(parcel_h parcel, uint64_t val) {
-  if (parcel == nullptr) {
-    _E("Invalid parameter");
-    return PARCEL_ERROR_INVALID_PARAMETER;
-  }
-
-  auto* h = static_cast<Parcel*>(parcel);
-  h->WriteUInt64(val);
-  return PARCEL_ERROR_NONE;
-}
-
-extern "C" EXPORT int parcel_write_int16(parcel_h parcel, int16_t val) {
-  if (parcel == nullptr) {
-    _E("Invalid parameter");
-    return PARCEL_ERROR_INVALID_PARAMETER;
-  }
-
-  auto* h = static_cast<Parcel*>(parcel);
-  h->WriteInt16(val);
-  return PARCEL_ERROR_NONE;
-}
-
-extern "C" EXPORT int parcel_write_int32(parcel_h parcel, int32_t val) {
-  if (parcel == nullptr) {
-    _E("Invalid parameter");
-    return PARCEL_ERROR_INVALID_PARAMETER;
-  }
-
-  auto* h = static_cast<Parcel*>(parcel);
-  h->WriteInt32(val);
-  return PARCEL_ERROR_NONE;
-}
-
-extern "C" EXPORT int parcel_write_int64(parcel_h parcel, int64_t val) {
-  if (parcel == nullptr) {
-    _E("Invalid parameter");
-    return PARCEL_ERROR_INVALID_PARAMETER;
-  }
-
-  auto* h = static_cast<Parcel*>(parcel);
-  h->WriteInt64(val);
-  return PARCEL_ERROR_NONE;
-}
-
-extern "C" EXPORT int parcel_write_float(parcel_h parcel, float val) {
-  if (parcel == nullptr) {
-    _E("Invalid parameter");
-    return PARCEL_ERROR_INVALID_PARAMETER;
-  }
-
-  auto* h = static_cast<Parcel*>(parcel);
-  h->WriteFloat(val);
-  return PARCEL_ERROR_NONE;
-}
-
-extern "C" EXPORT int parcel_write_double(parcel_h parcel, double val) {
-  if (parcel == nullptr) {
-    _E("Invalid parameter");
-    return PARCEL_ERROR_INVALID_PARAMETER;
-  }
-
-  auto* h = static_cast<Parcel*>(parcel);
-  h->WriteDouble(val);
-  return PARCEL_ERROR_NONE;
-}
-
-extern "C" EXPORT int parcel_write_string(parcel_h parcel, const char* str) {
-  if (parcel == nullptr || str == nullptr) {
-    _E("Invalid parameter");
-    return PARCEL_ERROR_INVALID_PARAMETER;
-  }
-
-  auto* h = static_cast<Parcel*>(parcel);
-  h->WriteCString(str);
-  return PARCEL_ERROR_NONE;
-}
-
-extern "C" EXPORT int parcel_read_bool(parcel_h parcel, bool* val) {
-  if (parcel == nullptr || val == nullptr) {
-    _E("Invalid parameter");
-    return PARCEL_ERROR_INVALID_PARAMETER;
-  }
-
-  auto* h = static_cast<Parcel*>(parcel);
-  return h->ReadBool(val);
-}
-
-extern "C" EXPORT int parcel_read_byte(parcel_h parcel, char* val) {
-  if (parcel == nullptr || val == nullptr) {
-    _E("Invalid parameter");
-    return PARCEL_ERROR_INVALID_PARAMETER;
-  }
-
-  auto* h = static_cast<Parcel*>(parcel);
-  return h->ReadByte(val);
-}
-
-extern "C" EXPORT int parcel_read_uint16(parcel_h parcel, uint16_t* val) {
-  if (parcel == nullptr || val == nullptr) {
-    _E("Invalid parameter");
-    return PARCEL_ERROR_INVALID_PARAMETER;
-  }
-
-  auto* h = static_cast<Parcel*>(parcel);
-  return h->ReadUInt16(val);
-}
-
-extern "C" EXPORT int parcel_read_uint32(parcel_h parcel, uint32_t* val) {
-  if (parcel == nullptr || val == nullptr) {
-    _E("Invalid parameter");
-    return PARCEL_ERROR_INVALID_PARAMETER;
-  }
-
-  auto* h = static_cast<Parcel*>(parcel);
-  return h->ReadUInt32(val);
-}
-
-extern "C" EXPORT int parcel_read_uint64(parcel_h parcel, uint64_t* val) {
-  if (parcel == nullptr || val == nullptr) {
-    _E("Invalid parameter");
-    return PARCEL_ERROR_INVALID_PARAMETER;
-  }
-
-  auto* h = static_cast<Parcel*>(parcel);
-  return h->ReadUInt64(val);
-}
-
-extern "C" EXPORT int parcel_read_int16(parcel_h parcel, int16_t* val) {
-  if (parcel == nullptr || val == nullptr) {
-    _E("Invalid parameter");
-    return PARCEL_ERROR_INVALID_PARAMETER;
-  }
-
-  auto* h = static_cast<Parcel*>(parcel);
-  return h->ReadInt16(val);
-}
-
-extern "C" EXPORT int parcel_read_int32(parcel_h parcel, int32_t* val) {
-  if (parcel == nullptr || val == nullptr) {
-    _E("Invalid parameter");
-    return PARCEL_ERROR_INVALID_PARAMETER;
-  }
-
-  auto* h = static_cast<Parcel*>(parcel);
-  return h->ReadInt32(val);
-}
-
-extern "C" EXPORT int parcel_read_int64(parcel_h parcel, int64_t* val) {
-  if (parcel == nullptr || val == nullptr) {
-    _E("Invalid parameter");
-    return PARCEL_ERROR_INVALID_PARAMETER;
-  }
-
-  auto* h = static_cast<Parcel*>(parcel);
-  return h->ReadInt64(val);
-}
-
-extern "C" EXPORT int parcel_read_float(parcel_h parcel, float* val) {
-  if (parcel == nullptr || val == nullptr) {
-    _E("Invalid parameter");
-    return PARCEL_ERROR_INVALID_PARAMETER;
-  }
-
-  auto* h = static_cast<Parcel*>(parcel);
-  return h->ReadFloat(val);
-}
-
-extern "C" EXPORT int parcel_read_double(parcel_h parcel, double* val) {
-  if (parcel == nullptr || val == nullptr) {
-    _E("Invalid parameter");
-    return PARCEL_ERROR_INVALID_PARAMETER;
-  }
-
-  auto* h = static_cast<Parcel*>(parcel);
-  return h->ReadDouble(val);
-}
-
-extern "C" EXPORT int parcel_read_string(parcel_h parcel, char** str) {
-  if (parcel == nullptr || str == nullptr) {
-    _E("Invalid parameter");
-    return PARCEL_ERROR_INVALID_PARAMETER;
-  }
-
-  auto* h = static_cast<Parcel*>(parcel);
-  return h->ReadCString(str);
-}
-
-extern "C" EXPORT int parcel_reset_reader(parcel_h parcel) {
-  if (parcel == nullptr) {
-    _E("Invalid parameter");
-    return PARCEL_ERROR_INVALID_PARAMETER;
-  }
-
-  auto* h = static_cast<Parcel*>(parcel);
-  h->ResetReader();
-  return PARCEL_ERROR_NONE;
-}
-
-extern "C" EXPORT int parcel_clear(parcel_h parcel) {
-  if (parcel == nullptr) {
-    _E("Invalid parameter");
-    return PARCEL_ERROR_INVALID_PARAMETER;
-  }
-
-  auto* h = static_cast<Parcel*>(parcel);
-  h->Clear();
-  return PARCEL_ERROR_NONE;
-}
-
-extern "C" EXPORT int parcel_reset(parcel_h parcel, const void* buf,
-    uint32_t size) {
-  if (parcel == nullptr || buf == nullptr || size == 0) {
-    _E("Invalid parameter");
-    return PARCEL_ERROR_INVALID_PARAMETER;
-  }
-
-  auto* h = static_cast<Parcel*>(parcel);
-  h->Reset(buf, size);
-  return PARCEL_ERROR_NONE;
-}
-
-extern "C" EXPORT int parcel_write(parcel_h parcel, parcelable_t* parcelable,
-    void* data) {
-  if (parcel == nullptr || parcelable == nullptr || parcelable->to == nullptr) {
-    _E("Invalid parameter");
-    return PARCEL_ERROR_INVALID_PARAMETER;
-  }
-
-  parcelable->to(parcel, data);
-  return PARCEL_ERROR_NONE;
-}
-
-extern "C" EXPORT int parcel_read(parcel_h parcel, parcelable_t* parcelable,
-    void* data) {
-  if (parcel == nullptr || parcelable == nullptr ||
-      parcelable->from == nullptr) {
-    _E("Invalid parameter");
-    return PARCEL_ERROR_INVALID_PARAMETER;
-  }
-
-  parcelable->from(parcel, data);
-  return PARCEL_ERROR_NONE;
-}
-
-extern "C" EXPORT int parcel_get_raw(parcel_h parcel, void** raw,
-    uint32_t* size) {
-  if (parcel == nullptr || raw == nullptr || size == nullptr) {
-    _E("Invalid parameter");
-    return PARCEL_ERROR_INVALID_PARAMETER;
-  }
-
-  auto* h = static_cast<Parcel*>(parcel);
-  *raw = reinterpret_cast<void*>(h->GetData());
-  *size = static_cast<uint32_t>(h->GetDataSize() & UINT32_MAX);
-  return PARCEL_ERROR_NONE;
-}
-
-extern "C" EXPORT int parcel_set_byte_order(parcel_h parcel,
-    bool big_endian) {
-  if (parcel == nullptr) {
-    _E("Invalid parameter");
-    return PARCEL_ERROR_INVALID_PARAMETER;
-  }
-
-  auto* h = static_cast<Parcel*>(parcel);
-  h->SetByteOrder(big_endian);
-  return PARCEL_ERROR_NONE;
-}
-
-extern "C" EXPORT int parcel_get_data_capacity(parcel_h parcel,
-    size_t* size) {
-  if (parcel == nullptr || size == nullptr) {
-    _E("Invalid parameter");
-    return PARCEL_ERROR_INVALID_PARAMETER;
-  }
-
-  auto* h = static_cast<Parcel*>(parcel);
-  *size = h->GetDataCapacity();
-  return PARCEL_ERROR_NONE;
-}
-
-extern "C" EXPORT int parcel_set_data_capacity(parcel_h parcel,
-    size_t size) {
-  if (parcel == nullptr || size == 0) {
-    _E("Invalid parameter");
-    return PARCEL_ERROR_INVALID_PARAMETER;
-  }
-
-  auto* h = static_cast<Parcel*>(parcel);
-  try {
-    h->SetDataCapacity(size);
-  } catch (const std::bad_alloc& e) {
-    _E("Exception occurs. error(%s)", e.what());
-    return PARCEL_ERROR_OUT_OF_MEMORY;
-  }
-
-  return PARCEL_ERROR_NONE;
-}
diff --git a/src/CMakeLists.txt b/src/CMakeLists.txt
new file mode 100644 (file)
index 0000000..9373d86
--- /dev/null
@@ -0,0 +1,4 @@
+ADD_SUBDIRECTORY(bundle)
+ADD_SUBDIRECTORY(parcel)
+ADD_SUBDIRECTORY(tizen-database)
+ADD_SUBDIRECTORY(tizen-shared-queue)
diff --git a/src/bundle-internal.cc b/src/bundle-internal.cc
deleted file mode 100644 (file)
index 68ccd8e..0000000
+++ /dev/null
@@ -1,366 +0,0 @@
-/*
- * Copyright (c) 2020 Samsung Electronics Co., Ltd. All rights reserved.
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#include "bundle-internal.h"
-
-#include <errno.h>
-#include <glib.h>
-
-#include <algorithm>
-#include <cstring>
-#include <memory>
-#include <utility>
-
-#include "include/bundle.h"
-
-#include "exception-internal.h"
-
-namespace tizen_base {
-namespace internal {
-
-static const int CHECKSUM_LENGTH = 32;
-
-Bundle::Bundle(unsigned char* raw, int size, bool base64) {
-  if (size < 0)
-    THROW(BUNDLE_ERROR_INVALID_PARAMETER);
-
-  int ret;
-  if (base64)
-    ret = Decode(raw, static_cast<size_t>(size));
-  else
-    ret = DecodeRaw(raw, static_cast<size_t>(size));
-  if (ret != BUNDLE_ERROR_NONE)
-    THROW(ret);
-}
-
-Bundle::Bundle(int argc, char** argv) {
-  int ret = Import(argc, argv);
-  if (ret != BUNDLE_ERROR_NONE)
-    THROW(ret);
-}
-
-Bundle::Bundle(const Bundle& b) {
-  for (const auto& [key, val] : b.map_) {
-    const KeyInfo& info = *val;
-    auto new_val = std::make_shared<KeyInfo>(info);
-    map_[key] = new_val;
-    list_.push_back(std::move(new_val));
-  }
-}
-
-Bundle& Bundle::operator = (const Bundle& b) {
-  if (this != &b) {
-    map_.clear();
-    list_.clear();
-    for (const auto& [key, val] : b.map_) {
-      const KeyInfo& info = *val;
-      auto new_val = std::make_shared<KeyInfo>(info);
-      map_[key] = new_val;
-      list_.push_back(std::move(new_val));
-    }
-  }
-  return *this;
-}
-
-Bundle::Bundle(Bundle&& b) noexcept {
-  map_ = std::move(b.map_);
-  list_ = std::move(b.list_);
-}
-
-Bundle& Bundle::operator = (Bundle&& b) noexcept {
-  if (this != &b) {
-    map_ = std::move(b.map_);
-    list_ = std::move(b.list_);
-  }
-  return *this;
-}
-
-bool Bundle::operator == (const Bundle& b) {
-  if (this == &b)
-    return true;
-
-  if (map_.size() != b.map_.size())
-    return false;
-
-  for (const auto& kv : map_) {
-    auto& lhs = kv.second;
-    auto iter = b.map_.find(lhs->GetKey());
-    if (iter == b.map_.end())
-      return false;
-
-    auto& rhs = iter->second;
-    if (!(*lhs == *rhs))
-      return false;
-  }
-
-  return true;
-}
-
-void Bundle::Remove(const std::string& key) {
-  auto iter = map_.find(key);
-  if (iter == map_.end())
-    THROW(BUNDLE_ERROR_KEY_NOT_AVAILABLE);
-
-  list_.remove(iter->second);
-  map_.erase(iter);
-}
-
-void Bundle::Add(std::shared_ptr<KeyInfo> key_info) {
-  auto iter = map_.find(key_info->GetKey());
-  if (iter != map_.end())
-    THROW(BUNDLE_ERROR_KEY_EXISTS);
-
-  map_[key_info->GetKey()] = key_info;
-  list_.push_back(std::move(key_info));
-}
-
-void Bundle::Set(const std::string& key, int index,
-    std::vector<unsigned char> value) {
-  auto iter = map_.find(key);
-  if (iter == map_.end())
-    THROW(BUNDLE_ERROR_KEY_NOT_AVAILABLE);
-
-  int ret = iter->second->SetValue(index, value);
-  if (ret != BUNDLE_ERROR_NONE)
-    THROW(ret);
-}
-
-std::shared_ptr<KeyInfo>& Bundle::Get(const std::string& key) {
-  auto iter = map_.find(key.c_str());
-  if (iter == map_.end())
-    THROW(BUNDLE_ERROR_KEY_NOT_AVAILABLE);
-
-  return iter->second;
-}
-
-int Bundle::GetSize() {
-  return map_.size();
-}
-
-int Bundle::GetType(const std::string& key) {
-  auto iter = map_.find(key);
-  if (iter == map_.end())
-    THROW(BUNDLE_ERROR_KEY_NOT_AVAILABLE);
-
-  return iter->second->GetType();
-}
-
-unsigned char* Bundle::Encode() {
-  int size = 0;
-  unsigned char* raw;
-  try {
-    raw = EncodeRaw(&size);
-  } catch (const Exception& e) {
-    THROW(e.GetErrorCode());
-  }
-
-  std::unique_ptr<unsigned char, decltype(std::free)*> raw_ptr(raw, std::free);
-  char* encoded_data = reinterpret_cast<char*>(
-      g_base64_encode(reinterpret_cast<guchar*>(raw),
-        static_cast<gsize>(size)));
-  if (encoded_data == nullptr)
-    THROW(BUNDLE_ERROR_OUT_OF_MEMORY);
-
-  return reinterpret_cast<unsigned char*>(encoded_data);
-}
-
-int Bundle::Decode(unsigned char* raw, size_t size) {
-  unsigned char* d_str = new (std::nothrow) unsigned char[(size / 4) * 3 + 3];
-  if (d_str == nullptr)
-    return BUNDLE_ERROR_OUT_OF_MEMORY;
-
-  std::unique_ptr<unsigned char[]> d_ptr(d_str);
-  gint state = 0;
-  guint save = 0;
-  size_t d_len_raw = static_cast<size_t>(g_base64_decode_step(
-      reinterpret_cast<char*>(raw), size, d_str, &state, &save));
-  if (d_len_raw < CHECKSUM_LENGTH)
-    return BUNDLE_ERROR_OUT_OF_MEMORY;
-
-  return DecodeRaw(d_str, d_len_raw);
-}
-
-unsigned char* Bundle::EncodeRaw(int* size) {
-  std::vector<unsigned char> bytes;
-  for (const auto& key_info : list_) {
-    auto encoded_bytes = key_info->Encode();
-    bytes.insert(bytes.end(),
-        std::make_move_iterator(encoded_bytes.begin()),
-        std::make_move_iterator(encoded_bytes.end()));
-  }
-
-  gchar* checksum = g_compute_checksum_for_string(
-      G_CHECKSUM_MD5, reinterpret_cast<gchar*>(&bytes[0]),
-      static_cast<gssize>(bytes.size()));
-  if (checksum == nullptr)
-    THROW(BUNDLE_ERROR_OUT_OF_MEMORY);
-
-  std::unique_ptr<gchar, decltype(g_free)*> ptr(checksum, g_free);
-  unsigned char* p = reinterpret_cast<unsigned char*>(checksum);
-  bytes.insert(bytes.begin(), p, p + CHECKSUM_LENGTH);
-
-  unsigned char* raw = static_cast<unsigned char*>(malloc(bytes.size()));
-  if (raw == nullptr)
-    THROW(BUNDLE_ERROR_OUT_OF_MEMORY);
-
-  std::copy(std::make_move_iterator(bytes.begin()),
-      std::make_move_iterator(bytes.end()), raw);
-  *size = static_cast<int>(bytes.size());
-  return raw;
-}
-
-int Bundle::DecodeRaw(unsigned char* raw, size_t size) {
-  char* extract_checksum = new (std::nothrow) char[CHECKSUM_LENGTH + 1];
-  if (extract_checksum == nullptr)
-    return BUNDLE_ERROR_OUT_OF_MEMORY;
-
-  std::unique_ptr<char[]> extract_ptr(extract_checksum);
-  unsigned char* d_str = raw;
-  size_t d_len_raw = size;
-  strncpy(extract_checksum, reinterpret_cast<char*>(d_str), CHECKSUM_LENGTH);
-  extract_checksum[CHECKSUM_LENGTH] = '\0';
-
-  gchar* compute_checksum = g_compute_checksum_for_string(G_CHECKSUM_MD5,
-      reinterpret_cast<gchar*>(d_str + CHECKSUM_LENGTH),
-      d_len_raw - CHECKSUM_LENGTH);
-  if (compute_checksum == nullptr)
-    return BUNDLE_ERROR_OUT_OF_MEMORY;
-
-  std::unique_ptr<gchar, decltype(g_free)*> compute_ptr(compute_checksum,
-      g_free);
-  if (strcmp(extract_checksum, static_cast<char*>(compute_checksum)) != 0)
-    return BUNDLE_ERROR_INVALID_PARAMETER;
-
-  unsigned char* d_r = d_str + CHECKSUM_LENGTH;
-  size_t d_len = d_len_raw - CHECKSUM_LENGTH;
-
-  unsigned int reader = 0;
-  std::vector<unsigned char> bytes(d_r, d_r + d_len);
-
-  while (reader < bytes.size()) {
-    std::size_t total_size = -1;
-    unsigned char* p = reinterpret_cast<unsigned char*>(&total_size);
-    std::copy(&bytes[reader], &bytes[reader] + sizeof(total_size), p);
-
-    std::vector<unsigned char> encoded_bytes(
-        &bytes[reader], &bytes[reader] + total_size);
-    reader += total_size;
-
-    try {
-      auto key_info = std::make_shared<KeyInfo>(std::move(encoded_bytes));
-      auto iter = map_.find(key_info->GetKey());
-      if (iter != map_.end())
-        continue;
-
-      map_[key_info->GetKey()] = key_info;
-      list_.push_back(std::move(key_info));
-    } catch (const Exception& e) {
-      return e.GetErrorCode();
-    } catch (const std::bad_alloc& ba) {
-      return BUNDLE_ERROR_OUT_OF_MEMORY;
-    }
-  }
-
-  return BUNDLE_ERROR_NONE;
-}
-
-const std::unordered_map<std::string, std::shared_ptr<KeyInfo>>&
-Bundle::GetMap() const {
-  return map_;
-}
-
-std::vector<std::string> Bundle::Export() {
-  std::vector<std::string> argv(2);
-  for (const auto& key_info : list_) {
-    argv.push_back(key_info->GetKey());
-
-    auto encoded_bytes = key_info->Encode();
-    auto* p = reinterpret_cast<unsigned char*>(&encoded_bytes[0]);
-    auto* base64_bytes = g_base64_encode(p, encoded_bytes.size());
-    if (base64_bytes == nullptr)
-      THROW(BUNDLE_ERROR_OUT_OF_MEMORY);
-
-    std::unique_ptr<gchar, decltype(g_free)*> base64_bytes_ptr(base64_bytes,
-        g_free);
-    argv.push_back(base64_bytes);
-  }
-
-  return argv;
-}
-
-int Bundle::Import(int argc, char** argv) {
-  if (argc < 2)
-    return BUNDLE_ERROR_NONE;
-
-  if (!argv[1] || std::strcmp(argv[1], TAG_IMPORT_EXPORT_CHECK)) {
-    for (int idx = 1; idx + 1 < argc; idx += 2) {
-      auto* p = reinterpret_cast<unsigned char*>(argv[idx +1]);
-      auto len = strlen(argv[idx + 1]) + 1;
-      std::vector<unsigned char> value(p, p + len);
-
-      try {
-        auto key_info = std::make_shared<KeyInfo>(Type::String, argv[idx],
-            std::move(value));
-        auto iter = map_.find(key_info->GetKey());
-        if (iter != map_.end())
-          continue;
-
-        map_[key_info->GetKey()] = key_info;
-        list_.push_back(std::move(key_info));
-      } catch (const Exception& e) {
-        return e.GetErrorCode();
-      } catch (const std::bad_alloc& ba) {
-        return BUNDLE_ERROR_OUT_OF_MEMORY;
-      }
-    }
-
-    return BUNDLE_ERROR_NONE;
-  }
-
-  for (int idx = 2; idx + 1 < argc; idx += 2) {
-    gsize out_len = 0;
-    auto* bytes = g_base64_decode(argv[idx + 1], &out_len);
-    if (bytes == nullptr)
-      return BUNDLE_ERROR_OUT_OF_MEMORY;
-
-    std::unique_ptr<guchar, decltype(g_free)*> bytes_ptr(bytes, g_free);
-
-    if (out_len < sizeof(std::size_t))
-      continue;
-
-    auto* p = reinterpret_cast<unsigned char*>(bytes);
-    std::vector<unsigned char> decoded_bytes(p, p + (out_len + 1));
-
-    try {
-      auto key_info = std::make_shared<KeyInfo>(std::move(decoded_bytes));
-      auto iter = map_.find(key_info->GetKey());
-      if (iter != map_.end())
-        continue;
-
-      map_[key_info->GetKey()] = key_info;
-      list_.push_back(std::move(key_info));
-    } catch (const Exception& e) {
-      return e.GetErrorCode();
-    } catch (const std::bad_alloc& ba) {
-      return BUNDLE_ERROR_OUT_OF_MEMORY;
-    }
-  }
-
-  return BUNDLE_ERROR_NONE;
-}
-
-}  // namespace internal
-}  // namespace tizen_base
diff --git a/src/bundle-internal.h b/src/bundle-internal.h
deleted file mode 100644 (file)
index f8d0fb1..0000000
+++ /dev/null
@@ -1,90 +0,0 @@
-/*
- * Copyright (c) 2020 Samsung Electronics Co., Ltd. All rights reserved.
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#ifndef BUNDLE_INTERNAL_H_
-#define BUNDLE_INTERNAL_H_
-
-#include <list>
-#include <memory>
-#include <string>
-#include <unordered_map>
-#include <vector>
-
-#include "include/bundle.h"
-
-#include "key-info-internal.h"
-
-namespace tizen_base {
-namespace internal {
-
-static const char TAG_IMPORT_EXPORT_CHECK[] = "`zaybxcwdveuftgsh`";
-
-class Bundle {
- public:
-  enum Property {
-    Array = BUNDLE_TYPE_ARRAY,
-    Primitive = BUNDLE_TYPE_PRIMITIVE,
-    Measurable = BUNDLE_TYPE_MEASURABLE,
-  };
-
-  enum Type {
-    None = BUNDLE_TYPE_NONE,
-    Any = BUNDLE_TYPE_ANY,
-    String = BUNDLE_TYPE_STR,
-    StringArray = BUNDLE_TYPE_STR_ARRAY,
-    Byte = BUNDLE_TYPE_BYTE,
-    ByteArray = BUNDLE_TYPE_BYTE_ARRAY,
-  };
-
-  Bundle() = default;
-  Bundle(unsigned char* raw, int size, bool base64 = true);
-  Bundle(int argc, char** argv);
-  virtual ~Bundle() = default;
-
-  Bundle(const Bundle& b);
-  Bundle& operator = (const Bundle& b);
-  Bundle(Bundle&& b) noexcept;
-  Bundle& operator = (Bundle&& b) noexcept;
-
-  bool operator == (const Bundle& b);
-
-  void Remove(const std::string& key);
-  void Add(std::shared_ptr<KeyInfo> key_info);
-  void Set(const std::string& key, int index, std::vector<unsigned char> value);
-
-  std::shared_ptr<KeyInfo>& Get(const std::string& key);
-  int GetSize();
-  int GetType(const std::string& key);
-
-  unsigned char* Encode();
-  unsigned char* EncodeRaw(int* size);
-  int DecodeRaw(unsigned char* raw, size_t size);
-  const std::unordered_map<std::string, std::shared_ptr<KeyInfo>>& GetMap() const;
-  std::vector<std::string> Export();
-
- private:
-  int Decode(unsigned char* raw, size_t size);
-  int Import(int argc, char** argv);
-
- private:
-  std::unordered_map<std::string, std::shared_ptr<KeyInfo>> map_;
-  std::list<std::shared_ptr<KeyInfo>> list_;
-};
-
-}  // namespace internal
-}  // namespace tizen_base
-
-#endif  // BUNDLE_INTERNAL_H_
diff --git a/src/bundle/CMakeLists.txt b/src/bundle/CMakeLists.txt
new file mode 100644 (file)
index 0000000..7938a11
--- /dev/null
@@ -0,0 +1,28 @@
+AUX_SOURCE_DIRECTORY(${CMAKE_CURRENT_SOURCE_DIR} BUNDLE_SRCS)
+
+ADD_LIBRARY(${TARGET_BUNDLE} SHARED ${BUNDLE_SRCS})
+
+SET_TARGET_PROPERTIES(${TARGET_BUNDLE} PROPERTIES SOVERSION ${MAJORVER})
+SET_TARGET_PROPERTIES(${TARGET_BUNDLE} PROPERTIES VERSION ${FULLVER})
+
+TARGET_INCLUDE_DIRECTORIES(${TARGET_BUNDLE} PUBLIC
+  ${CMAKE_CURRENT_SOURCE_DIR}
+  ${CMAKE_CURRENT_SOURCE_DIR}/include
+  ${CMAKE_CURRENT_SOURCE_DIR}/../)
+
+APPLY_PKG_CONFIG(${TARGET_BUNDLE} PUBLIC
+  CAPI_BASE_COMMON_DEPS
+  DLOG_DEPS
+  GLIB_DEPS
+  JSON_GLIB_DEPS)
+
+SET(PREFIX ${CMAKE_INSTALL_PREFIX})
+SET(VERSION ${FULLVER})
+
+CONFIGURE_FILE(${CMAKE_CURRENT_SOURCE_DIR}/bundle.pc.in
+  ${CMAKE_CURRENT_SOURCE_DIR}/bundle.pc @ONLY)
+
+INSTALL(TARGETS ${TARGET_BUNDLE} DESTINATION ${LIB_INSTALL_DIR})
+INSTALL(DIRECTORY ${CMAKE_CURRENT_SOURCE_DIR}/include/ DESTINATION include/)
+INSTALL(FILES ${CMAKE_CURRENT_SOURCE_DIR}/bundle.pc DESTINATION
+  ${LIB_INSTALL_DIR}/pkgconfig/)
diff --git a/src/bundle/bundle-internal.cc b/src/bundle/bundle-internal.cc
new file mode 100644 (file)
index 0000000..68ccd8e
--- /dev/null
@@ -0,0 +1,366 @@
+/*
+ * Copyright (c) 2020 Samsung Electronics Co., Ltd. All rights reserved.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#include "bundle-internal.h"
+
+#include <errno.h>
+#include <glib.h>
+
+#include <algorithm>
+#include <cstring>
+#include <memory>
+#include <utility>
+
+#include "include/bundle.h"
+
+#include "exception-internal.h"
+
+namespace tizen_base {
+namespace internal {
+
+static const int CHECKSUM_LENGTH = 32;
+
+Bundle::Bundle(unsigned char* raw, int size, bool base64) {
+  if (size < 0)
+    THROW(BUNDLE_ERROR_INVALID_PARAMETER);
+
+  int ret;
+  if (base64)
+    ret = Decode(raw, static_cast<size_t>(size));
+  else
+    ret = DecodeRaw(raw, static_cast<size_t>(size));
+  if (ret != BUNDLE_ERROR_NONE)
+    THROW(ret);
+}
+
+Bundle::Bundle(int argc, char** argv) {
+  int ret = Import(argc, argv);
+  if (ret != BUNDLE_ERROR_NONE)
+    THROW(ret);
+}
+
+Bundle::Bundle(const Bundle& b) {
+  for (const auto& [key, val] : b.map_) {
+    const KeyInfo& info = *val;
+    auto new_val = std::make_shared<KeyInfo>(info);
+    map_[key] = new_val;
+    list_.push_back(std::move(new_val));
+  }
+}
+
+Bundle& Bundle::operator = (const Bundle& b) {
+  if (this != &b) {
+    map_.clear();
+    list_.clear();
+    for (const auto& [key, val] : b.map_) {
+      const KeyInfo& info = *val;
+      auto new_val = std::make_shared<KeyInfo>(info);
+      map_[key] = new_val;
+      list_.push_back(std::move(new_val));
+    }
+  }
+  return *this;
+}
+
+Bundle::Bundle(Bundle&& b) noexcept {
+  map_ = std::move(b.map_);
+  list_ = std::move(b.list_);
+}
+
+Bundle& Bundle::operator = (Bundle&& b) noexcept {
+  if (this != &b) {
+    map_ = std::move(b.map_);
+    list_ = std::move(b.list_);
+  }
+  return *this;
+}
+
+bool Bundle::operator == (const Bundle& b) {
+  if (this == &b)
+    return true;
+
+  if (map_.size() != b.map_.size())
+    return false;
+
+  for (const auto& kv : map_) {
+    auto& lhs = kv.second;
+    auto iter = b.map_.find(lhs->GetKey());
+    if (iter == b.map_.end())
+      return false;
+
+    auto& rhs = iter->second;
+    if (!(*lhs == *rhs))
+      return false;
+  }
+
+  return true;
+}
+
+void Bundle::Remove(const std::string& key) {
+  auto iter = map_.find(key);
+  if (iter == map_.end())
+    THROW(BUNDLE_ERROR_KEY_NOT_AVAILABLE);
+
+  list_.remove(iter->second);
+  map_.erase(iter);
+}
+
+void Bundle::Add(std::shared_ptr<KeyInfo> key_info) {
+  auto iter = map_.find(key_info->GetKey());
+  if (iter != map_.end())
+    THROW(BUNDLE_ERROR_KEY_EXISTS);
+
+  map_[key_info->GetKey()] = key_info;
+  list_.push_back(std::move(key_info));
+}
+
+void Bundle::Set(const std::string& key, int index,
+    std::vector<unsigned char> value) {
+  auto iter = map_.find(key);
+  if (iter == map_.end())
+    THROW(BUNDLE_ERROR_KEY_NOT_AVAILABLE);
+
+  int ret = iter->second->SetValue(index, value);
+  if (ret != BUNDLE_ERROR_NONE)
+    THROW(ret);
+}
+
+std::shared_ptr<KeyInfo>& Bundle::Get(const std::string& key) {
+  auto iter = map_.find(key.c_str());
+  if (iter == map_.end())
+    THROW(BUNDLE_ERROR_KEY_NOT_AVAILABLE);
+
+  return iter->second;
+}
+
+int Bundle::GetSize() {
+  return map_.size();
+}
+
+int Bundle::GetType(const std::string& key) {
+  auto iter = map_.find(key);
+  if (iter == map_.end())
+    THROW(BUNDLE_ERROR_KEY_NOT_AVAILABLE);
+
+  return iter->second->GetType();
+}
+
+unsigned char* Bundle::Encode() {
+  int size = 0;
+  unsigned char* raw;
+  try {
+    raw = EncodeRaw(&size);
+  } catch (const Exception& e) {
+    THROW(e.GetErrorCode());
+  }
+
+  std::unique_ptr<unsigned char, decltype(std::free)*> raw_ptr(raw, std::free);
+  char* encoded_data = reinterpret_cast<char*>(
+      g_base64_encode(reinterpret_cast<guchar*>(raw),
+        static_cast<gsize>(size)));
+  if (encoded_data == nullptr)
+    THROW(BUNDLE_ERROR_OUT_OF_MEMORY);
+
+  return reinterpret_cast<unsigned char*>(encoded_data);
+}
+
+int Bundle::Decode(unsigned char* raw, size_t size) {
+  unsigned char* d_str = new (std::nothrow) unsigned char[(size / 4) * 3 + 3];
+  if (d_str == nullptr)
+    return BUNDLE_ERROR_OUT_OF_MEMORY;
+
+  std::unique_ptr<unsigned char[]> d_ptr(d_str);
+  gint state = 0;
+  guint save = 0;
+  size_t d_len_raw = static_cast<size_t>(g_base64_decode_step(
+      reinterpret_cast<char*>(raw), size, d_str, &state, &save));
+  if (d_len_raw < CHECKSUM_LENGTH)
+    return BUNDLE_ERROR_OUT_OF_MEMORY;
+
+  return DecodeRaw(d_str, d_len_raw);
+}
+
+unsigned char* Bundle::EncodeRaw(int* size) {
+  std::vector<unsigned char> bytes;
+  for (const auto& key_info : list_) {
+    auto encoded_bytes = key_info->Encode();
+    bytes.insert(bytes.end(),
+        std::make_move_iterator(encoded_bytes.begin()),
+        std::make_move_iterator(encoded_bytes.end()));
+  }
+
+  gchar* checksum = g_compute_checksum_for_string(
+      G_CHECKSUM_MD5, reinterpret_cast<gchar*>(&bytes[0]),
+      static_cast<gssize>(bytes.size()));
+  if (checksum == nullptr)
+    THROW(BUNDLE_ERROR_OUT_OF_MEMORY);
+
+  std::unique_ptr<gchar, decltype(g_free)*> ptr(checksum, g_free);
+  unsigned char* p = reinterpret_cast<unsigned char*>(checksum);
+  bytes.insert(bytes.begin(), p, p + CHECKSUM_LENGTH);
+
+  unsigned char* raw = static_cast<unsigned char*>(malloc(bytes.size()));
+  if (raw == nullptr)
+    THROW(BUNDLE_ERROR_OUT_OF_MEMORY);
+
+  std::copy(std::make_move_iterator(bytes.begin()),
+      std::make_move_iterator(bytes.end()), raw);
+  *size = static_cast<int>(bytes.size());
+  return raw;
+}
+
+int Bundle::DecodeRaw(unsigned char* raw, size_t size) {
+  char* extract_checksum = new (std::nothrow) char[CHECKSUM_LENGTH + 1];
+  if (extract_checksum == nullptr)
+    return BUNDLE_ERROR_OUT_OF_MEMORY;
+
+  std::unique_ptr<char[]> extract_ptr(extract_checksum);
+  unsigned char* d_str = raw;
+  size_t d_len_raw = size;
+  strncpy(extract_checksum, reinterpret_cast<char*>(d_str), CHECKSUM_LENGTH);
+  extract_checksum[CHECKSUM_LENGTH] = '\0';
+
+  gchar* compute_checksum = g_compute_checksum_for_string(G_CHECKSUM_MD5,
+      reinterpret_cast<gchar*>(d_str + CHECKSUM_LENGTH),
+      d_len_raw - CHECKSUM_LENGTH);
+  if (compute_checksum == nullptr)
+    return BUNDLE_ERROR_OUT_OF_MEMORY;
+
+  std::unique_ptr<gchar, decltype(g_free)*> compute_ptr(compute_checksum,
+      g_free);
+  if (strcmp(extract_checksum, static_cast<char*>(compute_checksum)) != 0)
+    return BUNDLE_ERROR_INVALID_PARAMETER;
+
+  unsigned char* d_r = d_str + CHECKSUM_LENGTH;
+  size_t d_len = d_len_raw - CHECKSUM_LENGTH;
+
+  unsigned int reader = 0;
+  std::vector<unsigned char> bytes(d_r, d_r + d_len);
+
+  while (reader < bytes.size()) {
+    std::size_t total_size = -1;
+    unsigned char* p = reinterpret_cast<unsigned char*>(&total_size);
+    std::copy(&bytes[reader], &bytes[reader] + sizeof(total_size), p);
+
+    std::vector<unsigned char> encoded_bytes(
+        &bytes[reader], &bytes[reader] + total_size);
+    reader += total_size;
+
+    try {
+      auto key_info = std::make_shared<KeyInfo>(std::move(encoded_bytes));
+      auto iter = map_.find(key_info->GetKey());
+      if (iter != map_.end())
+        continue;
+
+      map_[key_info->GetKey()] = key_info;
+      list_.push_back(std::move(key_info));
+    } catch (const Exception& e) {
+      return e.GetErrorCode();
+    } catch (const std::bad_alloc& ba) {
+      return BUNDLE_ERROR_OUT_OF_MEMORY;
+    }
+  }
+
+  return BUNDLE_ERROR_NONE;
+}
+
+const std::unordered_map<std::string, std::shared_ptr<KeyInfo>>&
+Bundle::GetMap() const {
+  return map_;
+}
+
+std::vector<std::string> Bundle::Export() {
+  std::vector<std::string> argv(2);
+  for (const auto& key_info : list_) {
+    argv.push_back(key_info->GetKey());
+
+    auto encoded_bytes = key_info->Encode();
+    auto* p = reinterpret_cast<unsigned char*>(&encoded_bytes[0]);
+    auto* base64_bytes = g_base64_encode(p, encoded_bytes.size());
+    if (base64_bytes == nullptr)
+      THROW(BUNDLE_ERROR_OUT_OF_MEMORY);
+
+    std::unique_ptr<gchar, decltype(g_free)*> base64_bytes_ptr(base64_bytes,
+        g_free);
+    argv.push_back(base64_bytes);
+  }
+
+  return argv;
+}
+
+int Bundle::Import(int argc, char** argv) {
+  if (argc < 2)
+    return BUNDLE_ERROR_NONE;
+
+  if (!argv[1] || std::strcmp(argv[1], TAG_IMPORT_EXPORT_CHECK)) {
+    for (int idx = 1; idx + 1 < argc; idx += 2) {
+      auto* p = reinterpret_cast<unsigned char*>(argv[idx +1]);
+      auto len = strlen(argv[idx + 1]) + 1;
+      std::vector<unsigned char> value(p, p + len);
+
+      try {
+        auto key_info = std::make_shared<KeyInfo>(Type::String, argv[idx],
+            std::move(value));
+        auto iter = map_.find(key_info->GetKey());
+        if (iter != map_.end())
+          continue;
+
+        map_[key_info->GetKey()] = key_info;
+        list_.push_back(std::move(key_info));
+      } catch (const Exception& e) {
+        return e.GetErrorCode();
+      } catch (const std::bad_alloc& ba) {
+        return BUNDLE_ERROR_OUT_OF_MEMORY;
+      }
+    }
+
+    return BUNDLE_ERROR_NONE;
+  }
+
+  for (int idx = 2; idx + 1 < argc; idx += 2) {
+    gsize out_len = 0;
+    auto* bytes = g_base64_decode(argv[idx + 1], &out_len);
+    if (bytes == nullptr)
+      return BUNDLE_ERROR_OUT_OF_MEMORY;
+
+    std::unique_ptr<guchar, decltype(g_free)*> bytes_ptr(bytes, g_free);
+
+    if (out_len < sizeof(std::size_t))
+      continue;
+
+    auto* p = reinterpret_cast<unsigned char*>(bytes);
+    std::vector<unsigned char> decoded_bytes(p, p + (out_len + 1));
+
+    try {
+      auto key_info = std::make_shared<KeyInfo>(std::move(decoded_bytes));
+      auto iter = map_.find(key_info->GetKey());
+      if (iter != map_.end())
+        continue;
+
+      map_[key_info->GetKey()] = key_info;
+      list_.push_back(std::move(key_info));
+    } catch (const Exception& e) {
+      return e.GetErrorCode();
+    } catch (const std::bad_alloc& ba) {
+      return BUNDLE_ERROR_OUT_OF_MEMORY;
+    }
+  }
+
+  return BUNDLE_ERROR_NONE;
+}
+
+}  // namespace internal
+}  // namespace tizen_base
diff --git a/src/bundle/bundle-internal.h b/src/bundle/bundle-internal.h
new file mode 100644 (file)
index 0000000..f8d0fb1
--- /dev/null
@@ -0,0 +1,90 @@
+/*
+ * Copyright (c) 2020 Samsung Electronics Co., Ltd. All rights reserved.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#ifndef BUNDLE_INTERNAL_H_
+#define BUNDLE_INTERNAL_H_
+
+#include <list>
+#include <memory>
+#include <string>
+#include <unordered_map>
+#include <vector>
+
+#include "include/bundle.h"
+
+#include "key-info-internal.h"
+
+namespace tizen_base {
+namespace internal {
+
+static const char TAG_IMPORT_EXPORT_CHECK[] = "`zaybxcwdveuftgsh`";
+
+class Bundle {
+ public:
+  enum Property {
+    Array = BUNDLE_TYPE_ARRAY,
+    Primitive = BUNDLE_TYPE_PRIMITIVE,
+    Measurable = BUNDLE_TYPE_MEASURABLE,
+  };
+
+  enum Type {
+    None = BUNDLE_TYPE_NONE,
+    Any = BUNDLE_TYPE_ANY,
+    String = BUNDLE_TYPE_STR,
+    StringArray = BUNDLE_TYPE_STR_ARRAY,
+    Byte = BUNDLE_TYPE_BYTE,
+    ByteArray = BUNDLE_TYPE_BYTE_ARRAY,
+  };
+
+  Bundle() = default;
+  Bundle(unsigned char* raw, int size, bool base64 = true);
+  Bundle(int argc, char** argv);
+  virtual ~Bundle() = default;
+
+  Bundle(const Bundle& b);
+  Bundle& operator = (const Bundle& b);
+  Bundle(Bundle&& b) noexcept;
+  Bundle& operator = (Bundle&& b) noexcept;
+
+  bool operator == (const Bundle& b);
+
+  void Remove(const std::string& key);
+  void Add(std::shared_ptr<KeyInfo> key_info);
+  void Set(const std::string& key, int index, std::vector<unsigned char> value);
+
+  std::shared_ptr<KeyInfo>& Get(const std::string& key);
+  int GetSize();
+  int GetType(const std::string& key);
+
+  unsigned char* Encode();
+  unsigned char* EncodeRaw(int* size);
+  int DecodeRaw(unsigned char* raw, size_t size);
+  const std::unordered_map<std::string, std::shared_ptr<KeyInfo>>& GetMap() const;
+  std::vector<std::string> Export();
+
+ private:
+  int Decode(unsigned char* raw, size_t size);
+  int Import(int argc, char** argv);
+
+ private:
+  std::unordered_map<std::string, std::shared_ptr<KeyInfo>> map_;
+  std::list<std::shared_ptr<KeyInfo>> list_;
+};
+
+}  // namespace internal
+}  // namespace tizen_base
+
+#endif  // BUNDLE_INTERNAL_H_
diff --git a/src/bundle/bundle.pc.in b/src/bundle/bundle.pc.in
new file mode 100644 (file)
index 0000000..c05c076
--- /dev/null
@@ -0,0 +1,14 @@
+# Package Information for pkg-config
+
+prefix=@PREFIX@
+exec_prefix=${prefix}
+libdir=@LIB_INSTALL_DIR@
+includedir=${prefix}/include
+
+Name: bundle
+Description: Simple string key/val dictionary library
+Version: @VERSION@
+Requires: capi-base-common
+Libs: -L${libdir} -lbundle
+Cflags: -I${includedir}
+cppflags: -I${includedir}
diff --git a/src/bundle/bundle_cpp.cc b/src/bundle/bundle_cpp.cc
new file mode 100644 (file)
index 0000000..c45f405
--- /dev/null
@@ -0,0 +1,350 @@
+/*
+ * Copyright (c) 2019 - 2020 Samsung Electronics Co., Ltd.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#include <memory>
+#include <stdexcept>
+
+#include "bundle_cpp.h"
+#include "bundle_cpp_implementation.h"
+#include "bundle_internal.h"
+#include "log-private.h"
+
+namespace tizen_base {
+Bundle::Impl::Impl(Bundle* parent, bool copy, bool own)
+  : copy_(copy), own_(own), parent_(parent) {
+}
+
+Bundle::Impl::Impl(Bundle* parent) : parent_(parent) {
+}
+
+Bundle::Impl::~Impl() = default;
+
+Bundle::Bundle()
+  : impl_(new Impl(this)) {
+  impl_->handle_ = bundle_create();
+  if (impl_->handle_ == nullptr)
+    throw std::bad_alloc();
+}
+
+Bundle::Bundle(std::initializer_list<
+    std::pair<std::string, std::string>> key_values)
+  : impl_(new Impl(this)) {
+  impl_->handle_ = bundle_create();
+  if (impl_->handle_ == nullptr)
+    throw std::bad_alloc();
+  for (auto& i : key_values)
+    Add(i.first, i.second);
+}
+
+Bundle::Bundle(BundleRaw raw, bool base64)
+  : impl_(new Impl(this)) {
+  if (base64)
+    impl_->handle_ = bundle_decode(raw.first.get(), raw.second);
+  else
+    impl_->handle_ = bundle_decode_raw(raw.first.get(), raw.second);
+  if (impl_->handle_ == nullptr)
+    throw std::bad_alloc();
+}
+
+Bundle::Bundle(const std::string& raw)
+  : impl_(new Impl(this)) {
+  impl_->handle_ = bundle_decode(reinterpret_cast<const bundle_raw*>(
+      raw.c_str()), raw.length());
+  if (impl_->handle_ == nullptr)
+    throw std::bad_alloc();
+}
+
+Bundle::Bundle(bundle* b, bool copy, bool own)
+  : impl_(new Impl(this, copy, own)) {
+  if (b == nullptr)
+    throw std::invalid_argument("b cannot be null");
+
+  if (!impl_->copy_) {
+    impl_->handle_ = b;
+  } else {
+    impl_->handle_ = bundle_dup(b);
+    if (impl_->handle_ == nullptr)
+      throw std::bad_alloc();
+  }
+}
+
+Bundle::~Bundle() {
+  if (impl_ && impl_->handle_ && (impl_->own_ || impl_->copy_))
+    bundle_free(impl_->handle_);
+}
+
+Bundle::Bundle(const Bundle& b)
+  : impl_(new Impl(this)) {
+  impl_->handle_ = bundle_dup(b.impl_->handle_);
+  if (impl_->handle_ == nullptr)
+    throw std::bad_alloc();
+}
+
+Bundle::KeyInfo::KeyInfo(const bundle_keyval_t* handle, std::string name,
+                         bool own)
+  : impl_(new Impl(this, handle, std::move(name), own)) {
+}
+
+Bundle::KeyInfo::~KeyInfo() {
+  if (impl_ && impl_->handle_ && impl_->own_)
+    bundle_keyval_free(const_cast<bundle_keyval_t*>(impl_->handle_));
+}
+
+Bundle::KeyInfo::Impl::~Impl() = default;
+
+Bundle::KeyInfo::Impl::Impl(Bundle::KeyInfo* parent,
+                            const bundle_keyval_t* handle,
+                            std::string name,
+                            bool own)
+  : handle_(handle), name_(name), parent_(parent), own_(own) {
+}
+
+Bundle::KeyInfo::Impl::Impl(Bundle::KeyInfo* parent) : parent_(parent) {
+}
+
+Bundle::KeyInfo::KeyInfo(const KeyInfo& k)
+    : impl_(new Impl(this)) {
+  impl_->handle_ = bundle_keyval_dup(k.impl_->handle_);
+  impl_->name_ = k.impl_->name_;
+  impl_->own_ = true;
+  if (impl_->handle_ == nullptr)
+    throw std::bad_alloc();
+}
+
+Bundle::KeyInfo& Bundle::KeyInfo::operator = (const Bundle::KeyInfo& k) {
+  if (this != &k) {
+    if (impl_->handle_ && impl_->own_)
+      bundle_keyval_free(const_cast<bundle_keyval_t*>(impl_->handle_));
+
+    impl_->handle_ = bundle_keyval_dup(k.impl_->handle_);
+    impl_->name_ = k.impl_->name_;
+    if (impl_->handle_ == nullptr)
+      throw std::bad_alloc();
+
+    impl_->own_ = true;
+  }
+  return *this;
+}
+
+Bundle::KeyInfo::KeyInfo(Bundle::KeyInfo&& k) noexcept {
+  impl_ = std::move(k.impl_);
+  impl_->parent_ = this;
+}
+
+Bundle::KeyInfo& Bundle::KeyInfo::operator = (Bundle::KeyInfo&& k) noexcept {
+  if (this != &k) {
+    if (impl_->handle_ && impl_->own_)
+      bundle_keyval_free(const_cast<bundle_keyval_t*>(impl_->handle_));
+
+    impl_->handle_ = k.impl_->handle_;
+    impl_->name_ = k.impl_->name_;
+    impl_->own_ = k.impl_->own_;
+    k.impl_->handle_ = nullptr;
+    k.impl_->name_ = "";
+    k.impl_->own_ = false;
+  }
+  return *this;
+}
+
+bundle_type Bundle::KeyInfo::GetType() const {
+  return static_cast<bundle_type>(
+      bundle_keyval_get_type(const_cast<bundle_keyval_t*>(impl_->handle_)));
+}
+
+bool Bundle::KeyInfo::IsArray() const {
+  return bundle_keyval_type_is_array(const_cast<bundle_keyval_t*>(
+      impl_->handle_));
+}
+
+const std::string& Bundle::KeyInfo::GetName() const {
+  return impl_->name_;
+}
+
+Bundle& Bundle::operator = (const Bundle& b) {
+  if (this != &b) {
+    if (impl_->handle_ && (impl_->own_ || impl_->copy_))
+      bundle_free(impl_->handle_);
+
+    impl_->handle_ = bundle_dup(b.impl_->handle_);
+    if (impl_->handle_ == nullptr)
+      throw std::bad_alloc();
+
+    impl_->own_ = true;
+    impl_->copy_ = true;
+  }
+  return *this;
+}
+
+Bundle::Bundle(Bundle&& b) noexcept {
+  impl_ = std::move(b.impl_);
+  impl_->parent_ = this;
+  b.impl_.reset(new Impl(&b));
+  b.impl_->handle_ = bundle_create();
+}
+
+Bundle& Bundle::operator = (Bundle&& b) noexcept {
+  if (this != &b) {
+    if (impl_->handle_ && (impl_->own_ || impl_->copy_))
+      bundle_free(impl_->handle_);
+
+    impl_->handle_ = b.impl_->handle_;
+    b.impl_->handle_ = nullptr;
+    impl_->own_ = b.impl_->own_;
+    b.impl_->own_ = false;
+    impl_->copy_ = b.impl_->copy_;
+    b.impl_->copy_ = false;
+  }
+  return *this;
+}
+
+bool Bundle::IsEmpty() const noexcept {
+  return (bundle_get_count(impl_->handle_) == 0) ? true : false;
+}
+
+std::vector<Bundle::KeyInfo> Bundle::GetKeys() {
+  std::vector<Bundle::KeyInfo> v;
+
+  bundle_foreach(impl_->handle_, [](const char *key, const int type,
+      const bundle_keyval_t *kv, void *user_data) {
+        auto* v = static_cast<std::vector<KeyInfo>*>(user_data);
+        v->emplace_back(kv, key, false);
+      }, &v);
+
+  return v;
+}
+
+int Bundle::Add(const std::string& key, const std::string& val) {
+  int ret = bundle_add_str(impl_->handle_, key.c_str(), val.c_str());
+  if (ret != BUNDLE_ERROR_NONE)
+    LOGE("Add fail key(%s), val(%s), ret(%d)", key.c_str(), val.c_str(), ret);
+  return ret;
+}
+
+int Bundle::Add(const std::string& key, const std::vector<std::string>& val) {
+  std::vector<const char*> v;
+  for (auto& i : val) {
+    v.push_back(i.c_str());
+  }
+
+  int ret = bundle_add_str_array(
+    impl_->handle_, key.c_str(), v.data(), v.size());
+  if (ret != BUNDLE_ERROR_NONE)
+    LOGE("Add fail key(%s), ret(%d)", key.c_str(), ret);
+
+  return ret;
+}
+
+int Bundle::Add(const std::string& key, const std::vector<unsigned char>& val) {
+  int ret = bundle_add_byte(impl_->handle_, key.c_str(), val.data(), val.size());
+  if (ret != BUNDLE_ERROR_NONE)
+    LOGE("Add fail key(%s), ret(%d)", key.c_str(), ret);
+  return ret;
+}
+
+int Bundle::Delete(const std::string& key) {
+  return bundle_del(impl_->handle_, key.c_str());
+}
+
+std::string Bundle::GetString(const std::string& key) const {
+  char* str = nullptr;
+  bundle_get_str(impl_->handle_, key.c_str(), &str);
+
+  if (!str)
+    return "";
+
+  return std::string(str);
+}
+
+std::vector<std::string> Bundle::GetStringArray(const std::string& key) const {
+  std::vector<std::string> v;
+
+  const char** str_array = nullptr;
+  int len = 0;
+
+  str_array = bundle_get_str_array(impl_->handle_, key.c_str(), &len);
+
+  for (int i = 0; i < len; i++) {
+    v.emplace_back(str_array[i]);
+  }
+
+  return v;
+}
+
+std::vector<unsigned char> Bundle::GetByte(const std::string& key) const {
+  size_t size;
+  unsigned char* bytes = nullptr;
+  int ret = bundle_get_byte(impl_->handle_, key.c_str(),
+      reinterpret_cast<void**>(&bytes), &size);
+  if (ret != BUNDLE_ERROR_NONE) {
+    LOGE("bundle_get_byte() is failed");
+    return {};
+  }
+
+  return std::vector<unsigned char>(bytes, bytes + size);
+}
+
+Bundle::BundleRaw Bundle::ToRaw(bool base64) {
+  bundle_raw* raw = nullptr;
+  int len = 0;
+  int ret;
+  if (base64)
+    ret = bundle_encode(impl_->handle_, &raw, &len);
+  else
+    ret = bundle_encode_raw(impl_->handle_, &raw, &len);
+  if (raw == nullptr) {
+    LOGE("Fail to encode data (%d)", ret);
+    throw std::bad_alloc();
+  }
+
+  return BundleRaw(
+      std::unique_ptr<bundle_raw, decltype(std::free)*>(raw, std::free), len);
+}
+
+int Bundle::GetCount() const {
+  return bundle_get_count(impl_->handle_);
+}
+
+bundle_type Bundle::GetType(const std::string& key) const {
+  return static_cast<bundle_type>(bundle_get_type(impl_->handle_, key.c_str()));
+}
+
+bundle* Bundle::GetHandle() const {
+  return impl_->handle_;
+}
+
+bundle* Bundle::Detach() {
+  auto* h = impl_->handle_;
+  impl_->handle_ = nullptr;
+  return h;
+}
+
+std::vector<std::string> Bundle::Export() const {
+  char** argv = nullptr;
+  int argc = bundle_export_to_argv(impl_->handle_, &argv);
+  if (argc < 0) {
+    LOGE("bundle_export_to_argv() is failed");
+    return {};
+  }
+
+  std::vector<std::string> args(1);
+  for (int i = 1; i < argc; ++i)
+    args.push_back(argv[i]);
+
+  bundle_free_exported_argv(argc, &argv);
+  return args;
+}
+
+}  // namespace tizen_base
diff --git a/src/bundle/bundle_cpp_implementation.h b/src/bundle/bundle_cpp_implementation.h
new file mode 100644 (file)
index 0000000..bf7c38c
--- /dev/null
@@ -0,0 +1,66 @@
+/*
+ * Copyright (c) 2019 - 2020 Samsung Electronics Co., Ltd.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#ifndef BUNDLE_CPP_IMPLEMENTATION_H_
+#define BUNDLE_CPP_IMPLEMENTATION_H_
+
+#include <string>
+#include <memory>
+#include <list>
+
+#include "include/bundle_cpp.h"
+
+namespace tizen_base {
+
+class Bundle::KeyInfo::Impl {
+ public:
+  virtual ~Impl();
+
+ private:
+  Impl(Bundle::KeyInfo* parent, const bundle_keyval_t* handle,
+       std::string name, bool own);
+  explicit Impl(Bundle::KeyInfo* parent);
+
+ private:
+  friend class Bundle::KeyInfo;
+
+ private:
+  const bundle_keyval_t* handle_ = nullptr;
+  std::string name_;
+  Bundle::KeyInfo* parent_;
+  bool own_ = false;
+};
+
+class Bundle::Impl {
+ public:
+  virtual ~Impl();
+
+ private:
+  explicit Impl(Bundle* parent);
+  Impl(Bundle* parent, bool copy, bool own);
+
+ private:
+  friend class Bundle;
+
+  bundle* handle_ = nullptr;
+  bool copy_ = true;
+  bool own_ = true;
+  Bundle* parent_ = nullptr;
+};
+
+}  // namespace tizen_base
+
+#endif  // BUNDLE_CPP_IMPLEMENTATION_H_
diff --git a/src/bundle/exception-internal.h b/src/bundle/exception-internal.h
new file mode 100644 (file)
index 0000000..4ce8690
--- /dev/null
@@ -0,0 +1,57 @@
+/*
+ * Copyright (c) 2020 Samsung Electronics Co., Ltd.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#ifndef EXCEPTION_INTERNAL_H_
+#define EXCEPTION_INTERNAL_H_
+
+#include <string>
+#include <exception>
+
+#include "log-private.h"
+
+#define THROW(error_code) throw Exception(error_code)
+
+namespace tizen_base {
+namespace internal {
+
+class Exception : public std::exception {
+ public:
+  explicit Exception(int error_code, std::string file = __FILE__,
+      int line = __LINE__ ) {
+    error_code_ = error_code;
+    message_ = file.substr(file.find_last_of("/") + 1) + ":"
+        + std::to_string(line) + " code:" + std::to_string(error_code_);
+  }
+
+  virtual ~Exception() {}
+
+  virtual const char *what(void) const noexcept {
+    return message_.c_str();
+  }
+
+  int GetErrorCode() const {
+    return error_code_;
+  }
+
+ private:
+  int error_code_;
+  std::string message_;
+};
+
+}  // namespace internal
+}  // namespace tizen_base
+
+#endif  // EXCEPTION_INTERNAL_H_
diff --git a/src/bundle/export-api-internal.h b/src/bundle/export-api-internal.h
new file mode 100644 (file)
index 0000000..cd0299d
--- /dev/null
@@ -0,0 +1,24 @@
+/*
+ * Copyright (c) 2020 Samsung Electronics Co., Ltd All Rights Reserved
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#ifndef EXPORT_API_INTERNAL_H_
+#define EXPORT_API_INTERNAL_H_
+
+#ifndef EXPORT_API
+#define EXPORT_API __attribute__((visibility("default")))
+#endif
+
+#endif  // EXPORT_API_INTERNAL_H_
diff --git a/src/bundle/include/SLP_bundle_PG.h b/src/bundle/include/SLP_bundle_PG.h
new file mode 100644 (file)
index 0000000..2420441
--- /dev/null
@@ -0,0 +1,156 @@
+/*
+ * Copyright (c) 2000 - 2020 Samsung Electronics Co., Ltd. All rights reserved.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+/**
+ *
+ * @ingroup SLP_PG
+ * @defgroup bundle_PG Bundle
+ * @brief A simple string-based dictionary ADT.
+ * @{
+
+<h1 class="pg">Introduction</h1>
+
+<p> Bundle is a string based Dictionary ADT. A dictionary is an ordered or unordered list of key element pairs, where keys are used to locate elements in the list. </p><br/>
+
+<p> ADT (Abstract data type) An Abstract Data type is defined as a mathematical model of the data objects that make up a data type as well
+as the functions that operate on these objects.</p>
+
+<h1 class="pg">Features</h1>
+<ul>
+       <li> Bundle provides string based Dictionary ADT to
+               map/store key-value pairs. Eg. Clock </li>
+       <li> Bundle  provides Application Data Exchange (ADE):
+               <ul>
+                       <li> Transfer application argument between caller and callee by creating a bundle and storing key-value pairs in it. </li>
+                       <li> This bundle object can be passed between applications by encoding and decoding the bundle objects. </li>
+               </ul> </li>
+
+</ul>
+
+<h1 class="pg">Properties</h1>
+<ul>
+       <li>Only string type is allowed for key and value.</li>
+       <li>Each key and value is duplicated into the bundle object.</li>
+       <li>Unlimited number of key/value pairs. (Memory limit is still to be considered)</li>
+       <li>No key overlap : You cannot assign new values with existing key.</li>
+</ul>
+
+<h1 class="pg">Bundle Logical View diagram</h1>
+\image html SLP_bundle_PG_images_logical_view.png "Picture 1. Logical view"
+
+
+<h1 class="pg">Functional architecture diagram</h1>
+\image html SLP_bundle_PG_image01.png "Picture 2. Functional architecture"
+
+<p> Bundle requests are received by the Bundle interface. It passes the requests to bundle manager. Bundle Manager checks the type of the request and handles it accordingly. If string key-value needs to be handled in the request it interacts with String manager to provide the required functionality. If the request is based on array of string key-value pair then, Bundle manager interacts with Array manager to provide the required functionality.</p>
+
+<h1 class="pg"> Bundle encode decode life cycle </h1>
+\image html SLP_bundle_PG_images_encode_decode.png "Picture 2. Encode decode life cycle"
+
+<h1 class="pg"> Bundle export import life cycle </h1>
+\image html SLP_bundle_PG_images_export_import.png "Picture 2. Export import life cycle"
+
+<h1 class="pg">API list and description</h1>
+<ul>
+       <li>bundle_create() : Create a bundle object.</li>
+       <li>bundle_free() : Free a bundle object.</li>
+       <li>bundle_add() : Add a key/value pair into the bundle object.</li>
+       <li>bundle_del() : Delete a key/value pair by given key from the bundle object.</li>
+       <li>bundle_get_val() : Get a value by key.</li>
+       <li>bundle_get_count() : Get number of key/value pairs in the bundle object.</li>
+       <li>bundle_dup() : Duplicate give bundle object</li>
+       <li>bundle_iterate() : Run iterator function for each key/value pair in the bundle object.</li>
+       <li>bundle_encode() : Encode bundle object into a byte code.</li>
+       <li>bundle_decode() : Decode byt code into a bundle object.</li>
+       <li></li>
+</ul>
+
+<h1 class="pg">Programming Guide</h1>
+<p> bundle library is very easy to use, and the sample code below would enough to understand how to use bundle. </p><br>
+<p>Detailed API instructions are in API reference in doxygen document.</p>
+<h2 class="pg">Note</h2>
+<ul>
+       <li>Only string type(char *) keys/values are allowed.</li>
+       <li>A bundle object must be freed certainly by bundle_free(). </li>
+       <li>Values retrived by bundle_get_val() cannot be modified.<br> If you want to modify value string, duplicate it.</li>
+</ul>
+<h2 class="pg"> Header file </h2>
+<p> header file name: <strong> bundle.h </strong></p>
+<h2 class="pg">Code</h2>
+@code
+#include <stdio.h>
+#include <bundle.h>
+
+// This is a sample iterator callback function
+void print_bundle_item(const char *key, const char *val, void *data);
+
+// Sample code
+int
+main(int argc, char **argv)
+{
+       char *str;
+       int count;
+
+       bundle *b, *b_dup;
+
+       // Create a new bundle object
+       b = bundle_new();
+
+       // Add a string with key "a"
+       bundle_add(b, "a", "123abc");
+
+       // Add another string with key "b"
+       bundle_add("b", "456def");
+
+       // str = "123abc"
+       // You cannot modify string!
+       str = bundle_get_val(b, "a");
+
+       // Run iterator function with each items
+       bundle_iterate(b, print_bundle_item, NULL);
+
+       // count = 2
+       count = bundle_get_count(b);
+
+       // Delete an item with key "a"
+       bundle_del(b, "a");
+
+       // count = 1
+       count = bundle_get_count(b);
+
+       // If "a" key is requested, NULL is returned
+       // str = NULL, errno = ENOKEY
+       str = bundle_get_val(b, "a");
+
+       // Duplicate bundle object
+       b_dup = bundle_dup(b);
+
+       // Free bundle objects
+       bundle_free(b);
+       bundle_free(b_dup);
+
+       return 0;
+}
+
+void
+print_bundle_item(const char *key, const char *val, void *data)
+{
+       printf("%s -> %s\n", key, val);
+}
+@endcode
+
+ * @}
+ */
diff --git a/src/bundle/include/bundle.h b/src/bundle/include/bundle.h
new file mode 100644 (file)
index 0000000..00a18c0
--- /dev/null
@@ -0,0 +1,700 @@
+/*
+ * Copyright (c) 2000 - 2020 Samsung Electronics Co., Ltd. All rights reserved.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#ifndef __BUNDLE_H__
+#define __BUNDLE_H__
+
+/**
+ * @file bundle.h
+ * @brief This file declares API of the bundle library.
+ */
+
+/**
+ * @addtogroup CORE_LIB_BUNDLE_MODULE
+ * @{
+ */
+
+#include <errno.h>
+#include <stddef.h>
+#include <tizen_error.h>
+
+#ifdef __cplusplus
+extern "C" {
+# endif
+
+/**
+ * @brief Enumeration for error codes of Bundle.
+ * @since_tizen 2.3
+ */
+typedef enum {
+       BUNDLE_ERROR_NONE = TIZEN_ERROR_NONE, /**< Successful */
+       BUNDLE_ERROR_OUT_OF_MEMORY = TIZEN_ERROR_OUT_OF_MEMORY, /**< Out of memory */
+       BUNDLE_ERROR_INVALID_PARAMETER = TIZEN_ERROR_INVALID_PARAMETER, /**< Invalid parameter */
+       BUNDLE_ERROR_KEY_NOT_AVAILABLE = TIZEN_ERROR_KEY_NOT_AVAILABLE, /**< Required key not available */
+       BUNDLE_ERROR_KEY_EXISTS = TIZEN_ERROR_BUNDLE | 0x01, /**< Key exists */
+       BUNDLE_ERROR_ARRAY_INDEX_OUT_OF_BOUNDS = TIZEN_ERROR_BUNDLE | 0x02 /**< The index is out of bounds of the array */
+} bundle_error_e;
+
+
+/**
+ * @brief The bundle handle.
+ * @since_tizen 2.3
+ */
+typedef struct _bundle_t bundle;
+
+
+/**
+ * @brief The encoded data type.
+ * @since_tizen 2.3
+ * @see bundle_encode()
+ * @see bundle_decode()
+ */
+typedef unsigned char bundle_raw;
+
+
+/**
+ * @brief Enumeration for key-value pair types.
+ * @since_tizen 2.3
+ */
+enum bundle_type_property {
+       BUNDLE_TYPE_ARRAY = 0x0100, /**< Array type */
+       BUNDLE_TYPE_PRIMITIVE = 0x0200, /**< Primitive type */
+       BUNDLE_TYPE_MEASURABLE = 0x0400 /**< Measurable type */
+};
+
+
+/**
+ * @brief Enumeration for bundle types.
+ * @since_tizen 2.3
+ */
+enum bundle_type {
+       BUNDLE_TYPE_NONE = -1, /**< None */
+       BUNDLE_TYPE_ANY = 0, /**< Any type */
+       BUNDLE_TYPE_STR = 1 | BUNDLE_TYPE_MEASURABLE, /**< String type (Default) */
+       BUNDLE_TYPE_STR_ARRAY = BUNDLE_TYPE_STR | BUNDLE_TYPE_ARRAY | BUNDLE_TYPE_MEASURABLE, /**< String array type */
+       BUNDLE_TYPE_BYTE = 2, /**< Byte type */
+       BUNDLE_TYPE_BYTE_ARRAY = BUNDLE_TYPE_BYTE | BUNDLE_TYPE_ARRAY /**< Byte array type */
+};
+
+
+/**
+ * @brief The key-value pair handle.
+ * @since_tizen 2.3
+ * @see bundle_iterator_t
+ */
+typedef struct keyval_t bundle_keyval_t;
+
+
+/**
+ * @brief Called for every key-value pair.
+ * @since_tizen 2.3
+ * @param[in] key The key of key-value pair
+ * @param[in] type The type of bundle
+ * @param[in] kv The handle of key-value pair
+ * @param[in] user_data The user data
+ * @see bundle_foreach()
+ */
+typedef void (*bundle_iterator_t) (const char *key, const int type, const bundle_keyval_t *kv, void *user_data);
+
+
+/**
+ * @brief Creates a bundle object.
+ * @since_tizen 2.3
+ * @remarks The specific error code can be obtained using the get_last_result() method. Error codes are described in Exception section.
+ * @return The bundle object,
+ *         @c NULL - Failure
+ * @exception #BUNDLE_ERROR_NONE Success
+ * @exception #BUNDLE_ERROR_OUT_OF_MEMORY Out of memory
+ * @see bundle_free()
+ *
+ * @code
+ #include <bundle.h>
+ bundle *b = bundle_create(); // Create a new bundle object
+ bundle_free(b); // Free the bundle
+ * @endcode
+ */
+bundle *bundle_create(void);
+
+
+/**
+ * @brief Frees the given bundle object with key-value pairs in it.
+ * @since_tizen 2.3
+ * @param[in] b The bundle object to be freed
+ * @return The operation result
+ * @retval #BUNDLE_ERROR_NONE Success
+ * @retval #BUNDLE_ERROR_INVALID_PARAMETER Invalid parameter
+ * @pre @a b must be a valid bundle object.
+ * @see bundle_create()
+ *
+ * @code
+ #include <bundle.h>
+ bundle *b = bundle_create(); // Create a new bundle object
+ bundle_free(b); // Free the bundle
+ * @endcode
+ */
+int bundle_free(bundle *b);
+
+
+/**
+ * @brief Adds a strings array type key-value pair into a given bundle.
+ * @since_tizen 2.3
+ * @param[in] b The bundle object
+ * @param[in] key The key
+ * @param[in] str_array The string type value; if @c NULL, an empty array is created; you can change an item with
+ * @param[in] len The length of the array
+ * @return The operation result
+ * @retval #BUNDLE_ERROR_NONE Success
+ * @retval #BUNDLE_ERROR_INVALID_PARAMETER Invalid parameter
+ * @retval #BUNDLE_ERROR_KEY_EXISTS Key already exists
+ * @retval #BUNDLE_ERROR_OUT_OF_MEMORY Out of memory
+ * @pre @a b must be a valid bundle object.
+ * @see bundle_get_str_array()
+ *
+ * @code
+ #include <bundle.h>
+ char *sa = {"aaa", "bbb", "ccc"}; // String array of length 3
+ bundle *b = bundle_create();
+ bundle_add_str_array(b, "foo", sa, 3); // Add a key-value pair
+ bundle_free(b);
+ * @endcode
+ */
+int bundle_add_str_array(bundle *b, const char *key, const char **str_array, const int len);
+
+
+/**
+ * @brief Deletes a key-value object with the given key.
+ * @since_tizen 2.3
+ * @param[in] b The bundle object
+ * @param[in] key The given key
+ * @return The operation result
+ * @retval #BUNDLE_ERROR_NONE Success
+ * @retval #BUNDLE_ERROR_INVALID_PARAMETER Invalid parameter
+ * @retval #BUNDLE_ERROR_KEY_NOT_AVAILABLE Key not available
+ * @pre @a b must be a valid bundle object.
+ *
+ * @code
+ #include <bundle.h>
+ bundle *b = bundle_create(); // Create a new bundle object
+ bundle_add_str(b, "foo_key", "bar_val"); // Add a key-value pair
+ bundle_del(b, "foo_key"); // Delete "foo_key" from b
+
+ bundle_free(b);
+ * @endcode
+ */
+int bundle_del(bundle *b, const char *key);
+
+
+/**
+ * @brief Gets a string array from a given key.
+ * @since_tizen 2.3
+ * @remarks You MUST NOT free or modify the returned string. \n
+ *          The specific error code can be obtained using the get_last_result() method. Error codes are described in Exception section.
+ * @param[in] b The bundle object
+ * @param[in] key The key
+ * @param[out] len The array length
+ * @return The pointer to the array of strings,
+ *         @c NULL - Key not found
+ * @exception #BUNDLE_ERROR_NONE Success
+ * @exception #BUNDLE_ERROR_INVALID_PARAMETER Invalid parameter
+ * @exception #BUNDLE_ERROR_KEY_NOT_AVAILABLE Key not available
+ * @pre @a b must be a valid bundle object.
+ * @see bundle_add_str_array()
+ *
+ * @code
+ #include <bundle.h>
+ bundle *b = bundle_create();
+ char *sa = {"aaa", "bbb", "ccc"}; // String array of length 3
+ bundle_add_str_array(b, "foo", sa, 3); // Add a key-value pair
+
+ char **str_array = NULL;
+ int len_str_array = 0;
+
+ str_array=bundle_get_str_array(b, "foo", &len_str_array);
+ // str_array = {"aaa", "bbb", "ccc"}, and len_str_array = 3
+
+ bundle_free(b);
+ * @endcode
+ */
+const char **bundle_get_str_array(bundle *b, const char *key, int *len);
+
+
+/**
+ * @brief Gets the number of bundle items.
+ * @since_tizen 2.3
+ * @param[in] b The bundle object
+ * @return The number of bundle items
+ * @pre @a b must be a valid bundle object.
+ *
+ * @code
+ #include <bundle.h>
+ bundle *b = bundle_create(); // Create a new bundle object
+ bundle_add_str(b, "key1", "val1"); // Add a key-value pair
+ int count = bundle_get_count(b); // count = 1
+ bundle_add_str(b, "key2", "val2"); // Add another key-value pair
+ count = bundle_get_count(b); // count = 2
+
+ bundle_free(b);
+ * @endcode
+ */
+int bundle_get_count(bundle *b);
+
+
+/**
+ * @brief Gets the type of the value with a given key.
+ * @since_tizen 2.3
+ * @remarks The specific error code can be obtained using the get_last_result() method. Error codes are described in Exception section.
+ * @param[in] b A bundle
+ * @param[in] key A key in the bundle
+ * @return The type of a key in @a b
+ * @exception #BUNDLE_ERROR_NONE Success
+ * @exception #BUNDLE_ERROR_INVALID_PARAMETER Invalid parameter
+ * @exception #BUNDLE_ERROR_KEY_NOT_AVAILABLE Key not available
+ * @pre @a b must be a valid bundle object.
+ * @see bundle_type
+ */
+int bundle_get_type(bundle *b, const char *key);
+
+
+/**
+ * @brief Duplicates a given bundle object.
+ * @since_tizen 2.4
+ * @remarks The specific error code can be obtained using the get_last_result() method. Error codes are described in Exception section.
+ *          The returned value should be released using bundle_free().
+ * @param[in] b_from The bundle object to be duplicated
+ * @return The new bundle object,
+ *         @c NULL - Failure
+ * @exception #BUNDLE_ERROR_NONE Success
+ * @exception #BUNDLE_ERROR_INVALID_PARAMETER Invalid parameter
+ * @pre @a b_from must be a valid bundle object.
+ *
+ * @code
+ #include <bundle.h>
+ bundle *b = bundle_create(); // Create a new bundle object
+ bundle_add_str(b, "foo_key", "bar_val"); // Add a key-value pair
+ bundle *b_dup = bundle_dup(b); // Duplicate b
+
+ bundle_free(b);
+ bundle_free(b_dup);
+ * @endcode
+ */
+bundle *bundle_dup(bundle *b_from);
+
+
+/**
+ * @brief Iterates a callback function for each key-value pair in a given bundle.
+ * @details Supports all types of values.
+ * @since_tizen 2.3
+ * @remarks The specific error code can be obtained using the get_last_result() method. Error codes are described in Exception section. \n
+ *          This function supports all types.
+ * @param[in] b The bundle object
+ * @param[in] iter The iteration callback function
+ * @param[in] user_data The data for the callback function
+ * @exception #BUNDLE_ERROR_NONE Success
+ * @exception #BUNDLE_ERROR_INVALID_PARAMETER Invalid parameter
+ * @pre @a b must be a valid bundle object.
+ * @see bundle_keyval_get_type()
+ * @see bundle_keyval_type_is_array()
+ * @see bundle_keyval_get_basic_val()
+ * @see bundle_keyval_get_array_val()
+ *
+ * @code
+ #include <stdio.h>
+ #include <bundle.h>
+ void
+ sample_cb(const char *key, const int type, const bundle_keyval_t *kv, void *user_data)
+ {
+     void *basic_val = NULL;
+     size_t basic_size = 0;
+     void **array_val = NULL;
+     int array_len = 0;
+     size_t *array_elem_size = NULL;
+
+     printf("Key:%s, Type:%d\n", key, type);
+     if (bundle_keyval_type_is_array(kv)) {
+         bundle_keyval_get_array_val(kv, &array_val, &array_len, &array_elem_size);
+         // Do something
+     }
+     else {
+         bundle_keyval_get_basic_val(kv, &basic_val, &basic_size);
+         // Do something
+     }
+ }
+
+ int main(void)
+ {
+     bundle *b = bundle_create(); // Create a new bundle object
+     bundle_add_str(b, "k1", "v1"); // Add a key-value pair
+     bundle_add_byte(b, "k2", "v2", 3); // Add a key-value pair
+     char *s_arr[] = {"abc", "bcd", "cde"};
+     bundle_add_str_array(b, "k3", s_arr, 3); // Add a key-value pair
+     bundle_foreach(b, sample_cb, NULL); // Iterate sample_cb() for each key/value
+
+     return 0;
+ }
+ * @endcode
+ */
+void bundle_foreach(bundle *b, bundle_iterator_t iter, void *user_data);
+
+
+/**
+ * @brief Gets the type of a key-value pair.
+ * @since_tizen 2.3
+ * @remarks The specific error code can be obtained using the get_last_result() method. Error codes are described in Exception section.
+ * @param[in] kv A bundle_keyval_t object
+ * @return The type of @a kv,
+ *         @c -1 - Failure
+ * @exception #BUNDLE_ERROR_NONE Success
+ * @exception #BUNDLE_ERROR_INVALID_PARAMETER Invalid parameter
+ * @pre @a kv must be a valid bundle_keyval_t object.
+ * @see bundle_foreach()
+ */
+int bundle_keyval_get_type(bundle_keyval_t *kv);
+
+
+/**
+ * @brief Determines whether the type of a key-value pair is an array.
+ * @since_tizen 2.3
+ * @remarks The specific error code can be obtained using the get_last_result() method. Error codes are described in Exception section.
+ * @param[in] kv A bundle_keyval_t object
+ * @return The operation result
+ *         @c 1 - @a kv is an array
+ *         @c 0 - @a kv is not an array
+ * @exception #BUNDLE_ERROR_NONE Success
+ * @exception #BUNDLE_ERROR_INVALID_PARAMETER Invalid parameter
+ * @pre @a kv must be a valid bundle_keyval_t object.
+ * @see bundle_foreach()
+ */
+int bundle_keyval_type_is_array(bundle_keyval_t *kv);
+
+
+/**
+ * @brief Gets the value and size of the value from a key-value pair of basic type.
+ * @since_tizen 2.3
+ * @remarks You must not free @a val.
+ * @param[in] kv A bundle_keyval_t object
+ * @param[out] val The value
+ * @param[out] size The size of @a val
+ * @return The operation result
+ * @retval #BUNDLE_ERROR_NONE Success
+ * @retval #BUNDLE_ERROR_INVALID_PARAMETER Invalid parameter
+ * @pre @a kv must be a valid bundle_keyval_t object.
+ * @post @a val and @a size are set.
+ * @see bundle_foreach()
+ */
+int bundle_keyval_get_basic_val(bundle_keyval_t *kv, void **val, size_t *size);
+
+
+/**
+ * @brief Gets the value array, length of the array, and size of each array item.
+ * @since_tizen 2.3
+ * @remarks The @a array_val should not be released.
+ *          The @a array_element_size should not be released.
+ * @param[in] kv A bundle_keyval_t object
+ * @param[out] array_val The array pointer of values
+ * @param[out] array_len The length of @a array_val
+ * @param[out] array_element_size The array of size of each array element
+ * @return The operation result
+ * @retval #BUNDLE_ERROR_NONE Success
+ * @retval #BUNDLE_ERROR_INVALID_PARAMETER Invalid parameter
+ * @pre @a kv must be a valid bundle_keyval_t object.
+ * @post @a array_val, @a array_len, @a array_element_size are set.
+ * @code
+ #include <stdio.h>
+ #include <bundle.h>
+ void
+ sample_cb(const char *key, const int type, const bundle_keyval_t *kv, void *user_data)
+ {
+     void **array_val = NULL;
+     unsigned int array_len = 0;
+     size_t *array_elem_size = NULL;
+     unsigned int i;
+
+     printf("Key: %s, Type: %d\n", key, type);
+     if (bundle_keyval_type_is_array(kv)) {
+         bundle_keyval_get_array_val(kv, &array_val, &array_len, &array_elem_size);
+         for (i = 0; i < array_len; ++i) {
+             printf("Value[%u]: %s\n", i, (const char *)array_val[i]);
+         }
+     }
+ }
+
+ int main(void)
+ {
+     bundle *b = bundle_create();
+     const char *s_arr[] = {"abc", "bcd", "cde"};
+     bundle_add_str_array(b, "k3", s_arr, 3); // Add a key-value pair
+     bundle_foreach(b, sample_cb, NULL);
+     bundle_free(b);
+     return 0;
+ }
+ * @endcode
+ * @see bundle_foreach()
+ */
+int bundle_keyval_get_array_val(bundle_keyval_t *kv, void ***array_val, unsigned int *array_len, size_t **array_element_size);
+
+
+/**
+ * @brief Encodes a bundle to the bundle_raw format (uses base64 format).
+ * @since_tizen 2.3
+ * @remarks The @a r should be released using free().
+ * @param[in] b The bundle object
+ * @param[out] r The returned bundle_raw data(byte data)
+ *               @a r MUST BE FREED by free(r)
+ * @param[out] len The size of @a r (in bytes)
+ * @return The size of the raw data
+ * @retval #BUNDLE_ERROR_NONE Success
+ * @retval #BUNDLE_ERROR_INVALID_PARAMETER Invalid parameter
+ * @pre @a b must be a valid bundle object.
+ *
+ * @code
+ #include <bundle.h>
+ bundle *b = bundle_create(); // Create a new bundle object
+ bundle_add_str(b, "foo_key", "bar_val"); // Add a key-value pair
+ bundle_raw *r;
+ int len;
+ bundle_encode(b, &r, &len); // Encode b
+ bundle_free(b);
+ free(r);
+ * @endcode
+ */
+int bundle_encode(bundle *b, bundle_raw **r, int *len);
+
+
+/**
+ * @brief Deserializes bundle_raw and gets the bundle object.
+ * @since_tizen 2.3
+ * @remarks The specific error code can be obtained using the get_last_result() method. Error codes are described in Exception section.
+ *          The returned value should be released using bundle_free().
+ * @param[in] r The bundle_raw data to be converted to bundle object
+ * @param[in] len The size of @a r
+ * @return The bundle object,
+ *         @c NULL - Failure
+ * @exception #BUNDLE_ERROR_NONE Success
+ * @exception #BUNDLE_ERROR_INVALID_PARAMETER Invalid parameter
+ * @pre @a r must be a valid bundle object.
+ *
+ * @code
+ #include <bundle.h>
+ bundle *b = bundle_create(); // Create a new bundle object
+ bundle_add_str(b, "foo_key", "bar_val"); // Add a key-value pair
+
+ bundle_raw *encoded_b;
+ int len;
+ bundle_encode(b, &encoded_b, &len); // Encode b
+
+ bundle *b_dup;
+ b_dup = bundle_decode(encoded_b, len); // Decoded bundle object
+
+ bundle_free(b);
+ free(encoded_b);
+ bundle_free(b_dup);
+ * @endcode
+ */
+bundle *bundle_decode(const bundle_raw *r, const int len);
+
+
+/**
+ * @brief Adds a string type key-value pair into a bundle.
+ * @since_tizen 2.3
+ * @param[in] b The bundle object
+ * @param[in] key The key
+ * @param[in] str The string type value
+ * @return The operation result
+ * @retval #BUNDLE_ERROR_NONE Success
+ * @retval #BUNDLE_ERROR_INVALID_PARAMETER Invalid parameter
+ * @retval #BUNDLE_ERROR_KEY_EXISTS Key already exists
+ * @retval #BUNDLE_ERROR_OUT_OF_MEMORY Out of memory
+ * @pre @a b must be a valid bundle object.
+ * @see bundle_get_str()
+ * @code
+ #include <bundle.h>
+ bundle *b = bundle_create(); // Create a new bundle object
+ bundle_add_str(b, "foo", "bar"); // Add a key-value pair
+
+ bundle_free(b);
+ * @endcode
+ */
+int bundle_add_str(bundle *b, const char *key, const char *str);
+
+
+/**
+ * @brief Adds a byte sequence type key-value pair into a bundle.
+ * @details The bundle will contain a copy of the added byte sequence.
+ * @since_tizen 2.3
+ * @param[in] b The bundle object
+ * @param[in] key The key
+ * @param[in] bytes The byte sequence
+ * @param[in] size The byte sequence size in bytes
+ * @return The operation result
+ * @retval #BUNDLE_ERROR_NONE Success
+ * @retval #BUNDLE_ERROR_INVALID_PARAMETER Invalid parameter
+ * @retval #BUNDLE_ERROR_KEY_EXISTS Key already exists
+ * @retval #BUNDLE_ERROR_OUT_OF_MEMORY Out of memory
+ * @pre @a b must be a valid bundle object.
+ * @see bundle_get_byte()
+ *
+ * @code
+ #include <bundle.h>
+ bundle *b = bundle_create(); // Create a new bundle object
+ bundle_add_byte(b, "foo", "bar\0", 4); // Add a key-value pair
+
+ int number = 12345;
+ bundle_add_byte(b, "number", &number, sizeof(int));
+
+ bundle_free(b);
+ * @endcode
+ */
+int bundle_add_byte(bundle *b, const char *key, const void *bytes, const size_t size);
+
+
+/**
+ * @brief Gets the string value with the given key.
+ * @since_tizen 2.3
+ * @remarks You must not free str.
+ * @param[in] b The bundle object
+ * @param[in] key The key
+ * @param[out] str The returned value
+ * @return The operation result
+ * @retval #BUNDLE_ERROR_NONE Success
+ * @retval #BUNDLE_ERROR_INVALID_PARAMETER Invalid parameter
+ * @retval #BUNDLE_ERROR_KEY_NOT_AVAILABLE Key not available
+ * @pre @a b must be a valid bundle object.
+ * @see bundle_add_str()
+ *
+ * @code
+ #include <bundle.h>
+ bundle *b = bundle_create(); // Create a new bundle object
+ bundle_add_str(b, "foo_key", "bar_val"); // Add a key-value pair
+
+ char *v = NULL;
+ bundle_get_str(b, "foo_key", &v); // v = "bar_val"
+
+ bundle_free(b); // After freeing b, v becomes a dangling pointer
+ v = NULL;
+ * @endcode
+ */
+int bundle_get_str(bundle *b, const char *key, char **str);
+
+
+/**
+ * @brief Gets the byte sequence with the given key.
+ * @since_tizen 2.3
+ * @remarks You must not free @a bytes.
+ * @param[in] b The bundle object
+ * @param[in] key The key
+ * @param[out] bytes The byte sequence
+ * @param[out] size The byte sequence size in bytes
+ * @return The operation result
+ * @retval #BUNDLE_ERROR_NONE Success
+ * @retval #BUNDLE_ERROR_INVALID_PARAMETER Invalid parameter
+ * @retval #BUNDLE_ERROR_KEY_NOT_AVAILABLE Key not available
+ * @pre @a b must be a valid bundle object.
+ * @see bundle_add_byte()
+ *
+ * @code
+ #include <bundle.h>
+ bundle *b = bundle_create(); // Create a new bundle object
+ bundle_add_byte(b, "foo", "bar\0", 4); // Add a string to the bundle
+ int number = 12345;
+ bundle_add_byte(b, "number", (const void**)&number, sizeof(int)); // Add an integer to the bundle
+
+ unsigned char *v = NULL;
+ size_t v_size;
+ bundle_get_byte(b, "foo", (void**)&v, &v_size); // v = "bar\0"
+ int *n = NULL;
+ size_t n_size;
+ bundle_get_byte(b, "number", (void**)&n, &n_size); // number = 12345
+
+ bundle_free(b); // After freeing b, v and n become a dangling pointer
+ * @endcode
+ */
+int bundle_get_byte(bundle *b, const char *key, void **bytes, size_t *size);
+
+/**
+ * @brief Adds an 'array of byte sequences' type key-value pair into a bundle.
+ * @since_tizen 5.5
+ * @remarks To set the value of the byte array element, you should use bundle_set_byte_array_element().
+ *          This function is only for creating a buffer of the byte array.
+ *
+ * @param[in]   b                       The bundle object
+ * @param[in]   key                     The key
+ * @param[in]   len                     The length of the array to be created
+ * @return      @c 0 on success,
+ *              otherwise a negative error value
+ * @retval #BUNDLE_ERROR_NONE Successful
+ * @retval #BUNDLE_ERROR_INVALID_PARAMETER Invalid parameter
+ * @retval #BUNDLE_ERROR_KEY_EXISTS Key already exists
+ * @retval #BUNDLE_ERROR_OUT_OF_MEMORY Out of memory
+ *
+ * @see bundle_get_byte_array()
+ * @see bundle_set_byte_array_element()
+ */
+int bundle_add_byte_array(bundle *b, const char *key, const unsigned int len);
+
+/**
+ * @brief Sets an element of an array of byte sequences.
+ * @details The array will contain its own copy of the added value.
+ * @since_tizen 5.5
+ *
+ * @param[in]   b                       The bundle object
+ * @param[in]   key                     The key
+ * @param[in]   idx                     The index of the array element to be changed
+ * @param[in]   bytes                   The byte sequence
+ * @param[in]   size                    The byte sequence size in bytes
+ * @return      @c 0 on success,
+ *              otherwise a negative error value
+ * @retval #BUNDLE_ERROR_NONE Successful
+ * @retval #BUNDLE_ERROR_INVALID_PARAMETER Invalid parameter
+ * @retval #BUNDLE_ERROR_KEY_NOT_AVAILABLE Key not available
+ * @retval #BUNDLE_ERROR_OUT_OF_MEMORY Out of memory
+ * @retval #BUNDLE_ERROR_ARRAY_INDEX_OUT_OF_BOUNDS The index is out of bounds of the array
+ *
+ * @see bundle_add_byte_array()
+ * @see bundle_get_byte_array()
+ */
+int bundle_set_byte_array_element(bundle *b, const char *key, const unsigned int idx, const void *bytes, const size_t size);
+
+/**
+ * @brief Gets the array of byte sequences with the given key.
+ * @since_tizen 5.5
+ * @remarks You should not release @a byte_array, @a len and @a array_element_size.
+ *          @a byte_array, @a len and @a array_element_size will be released when the bundle containing them is released with bundle_free().
+ *
+ * @param[in]   b                       The bundle object
+ * @param[in]   key                     The key
+ * @param[out]  byte_array              The array pointer of the byte value
+ * @param[out]  len                     The array length
+ * @param[out]  array_element_size      An array of sizes of each @a byte_array element
+ * @return      @c 0 on success,
+ *              otherwise a negative error value
+ * @retval #BUNDLE_ERROR_NONE Successful
+ * @retval #BUNDLE_ERROR_INVALID_PARAMETER Invalid parameter
+ * @retval #BUNDLE_ERROR_KEY_NOT_AVAILABLE Key not available
+ *
+ * @see bundle_add_byte_array()
+ * @see bundle_set_byte_array_element()
+*/
+int bundle_get_byte_array(bundle *b, const char *key, void ***byte_array, unsigned int *len, unsigned int **array_element_size);
+
+#ifdef __cplusplus
+}
+#endif
+
+/**
+ * @}
+ */
+
+#endif /* __BUNDLE_H__ */
diff --git a/src/bundle/include/bundle_cpp.h b/src/bundle/include/bundle_cpp.h
new file mode 100644 (file)
index 0000000..997da06
--- /dev/null
@@ -0,0 +1,348 @@
+/*
+ * Copyright (c) 2019 - 2020 Samsung Electronics Co., Ltd.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#ifndef BUNDLE_CPP_H_
+#define BUNDLE_CPP_H_
+
+/**
+ * @file bundle_cpp.h
+ * @brief This file declares API of the bundle C++ library.
+ */
+
+/**
+ * @addtogroup CORE_LIB_BUNDLE_CPP_MODULE
+ * @{
+ */
+
+#include <bundle.h>
+
+#include <cstdio>
+#include <initializer_list>
+#include <memory>
+#include <string>
+#include <utility>
+#include <vector>
+
+#ifndef EXPORT_API
+#define EXPORT_API __attribute__((visibility("default")))
+#endif
+
+namespace tizen_base {
+
+/**
+ * @brief The class for bundle APIs.
+ * @since_tizen 5.5
+ */
+class EXPORT_API Bundle final {
+ public:
+  /**
+   * @brief The type for raw bundle.
+   * @since_tizen 5.5
+   */
+  using BundleRaw =
+      std::pair<std::unique_ptr<bundle_raw, decltype(std::free)*>, int>;
+
+  /**
+   * @brief The class for information of keys.
+   * @since_tizen 5.5
+   */
+  class KeyInfo final {
+   public:
+    /**
+     * @brief Constructor.
+     * @since_tizen 5.5
+     * @param[in] handle The handle for type bundle_keyval_t
+     * @param[in] name The key string
+     * @param[in] own True if this object owns the handle
+     */
+    KeyInfo(const bundle_keyval_t* handle,  std::string name, bool own = false);
+
+    /**
+     * @brief Destructor.
+     * @since_tizen 5.5
+     */
+    ~KeyInfo();
+
+    /**
+     * @brief Copy-constructor.
+     * @since_tizen 5.5
+     * @param[in] b The object to copy
+    */
+    KeyInfo(const KeyInfo& b);
+
+    /**
+     * @brief Assignment.
+     * @since_tizen 5.5
+     * @param[in] b The object to copy
+     */
+    KeyInfo& operator = (const KeyInfo& b);
+
+    /**
+     * @brief Move-constructor.
+     * @since_tizen 5.5
+     * @param[in] b The object to move
+    */
+    KeyInfo(KeyInfo&& b) noexcept;
+
+    /**
+     * @brief Assignment.
+     * @since_tizen 5.5
+     * @param[in] b The object to move
+     */
+    KeyInfo& operator = (KeyInfo&& b) noexcept;
+
+    /**
+     * @brief Gets the type of a key-value pair.
+     * @since_tizen 5.5
+     * @return The type
+     */
+    bundle_type GetType() const;
+
+    /**
+     * @brief Determines whether the type of a key-value pair is an array.
+     * @since_tizen 5.5
+     * @return True when it is an array
+     */
+    bool IsArray() const;
+
+    /**
+     * @brief Gets the key string.
+     * @since_tizen 5.5
+     * @return The key string
+     */
+    const std::string& GetName() const;
+
+   private:
+    class Impl;
+    std::unique_ptr<Impl> impl_;
+  };
+
+  /**
+   * @brief Constructor.
+   * @since_tizen 5.5
+   */
+  Bundle();
+
+  /**
+   * @brief Constructor.
+   * @since_tizen 6.5
+   * @param[in] key_values The list of key-value pair
+   */
+  Bundle(std::initializer_list<
+      std::pair<std::string, std::string>> key_values);
+
+  /**
+   * @brief Constructor.
+   * @since_tizen 5.5
+   * @param[in] raw The object for BundleRaw
+   * @param[in] base64 @c true, @a raw is the encoded raw data using base64-encoding
+   */
+  explicit Bundle(BundleRaw raw, bool base64 = true);
+
+  /**
+   * @brief Constructor.
+   * @since_tizen 5.5
+   * @param[in] raw The string object for raw bundle
+   */
+  explicit Bundle(const std::string& raw);
+
+  /**
+   * @brief Constructor.
+   * @since_tizen 5.5
+   * @param[in] b The handle for bundle
+   * @param[in] copy True if this object wants to copy it from the handle
+   * @param[in] own True if this object owns the handle
+   */
+  explicit Bundle(bundle* b, bool copy = true, bool own = true);
+
+  /**
+   * @brief Destructor.
+   * @since_tizen 5.5
+   */
+  ~Bundle();
+
+  /**
+   * @brief Copy-constructor.
+   * @since_tizen 5.5
+   * @param[in] b The object to copy
+   */
+  Bundle(const Bundle& b);
+
+  /**
+   * @brief Assignment.
+   * @since_tizen 5.5
+   * @param[in] b The object to copy
+   */
+  Bundle& operator = (const Bundle& b);
+
+  /**
+   * @brief Move-constructor.
+   * @since_tizen 5.5
+   * @param[in] b The object to move
+   */
+  Bundle(Bundle&& b) noexcept;
+
+  /**
+   * @brief Assignment.
+   * @since_tizen 5.5
+   * @param[in] b The object to move
+   */
+  Bundle& operator = (Bundle&& b) noexcept;
+
+  /**
+   * @brief Check the bundle is empty or not.
+   * @since_tizen 6.0
+   * @return true if the bundle is empty
+   */
+  bool IsEmpty() const noexcept;
+
+  /**
+   * @brief Gets keys in bundle object.
+   * @since_tizen 5.5
+   * @return A string array of object KeyInfo
+  */
+  std::vector<KeyInfo> GetKeys();
+
+  /**
+   * @brief Adds a string type key-value pair into a bundle.
+   * @since_tizen 5.5
+   * @param[in] key The string key
+   * @param[in] val The string value
+   * @return The operation result
+   * @retval BUNDLE_ERROR_NONE Success
+   * @retval BUNDLE_ERROR_INVALID_PARAMETER Invalid parameter
+   * @retval BUNDLE_ERROR_KEY_EXISTS Key already exists
+   * @retval BUNDLE_ERROR_OUT_OF_MEMORY Out of memory
+  */
+  int Add(const std::string& key, const std::string& val);
+
+  /**
+   * @brief Adds a string type key-value pair into a bundle.
+   * @since_tizen 5.5
+   * @param[in] key The string key
+   * @param[in] val The array of strings
+   * @return The operation result
+   * @retval BUNDLE_ERROR_NONE Success
+   * @retval BUNDLE_ERROR_INVALID_PARAMETER Invalid parameter
+   * @retval BUNDLE_ERROR_KEY_EXISTS Key already exists
+   * @retval BUNDLE_ERROR_OUT_OF_MEMORY Out of memory
+  */
+  int Add(const std::string& key, const std::vector<std::string>& val);
+
+  /**
+   * @brief Adds a string type key-value pair into a bundle.
+   * @since_tizen 5.5
+   * @param[in] key The string key
+   * @param[in] val The array of bytes
+   * @return The operation result
+   * @retval BUNDLE_ERROR_NONE Success
+   * @retval BUNDLE_ERROR_INVALID_PARAMETER Invalid parameter
+   * @retval BUNDLE_ERROR_KEY_EXISTS Key already exists
+   * @retval BUNDLE_ERROR_OUT_OF_MEMORY Out of memory
+  */
+  int Add(const std::string& key, const std::vector<unsigned char>& val);
+
+  /**
+   * @brief Deletes a key-value object with the given key.
+   * @since_tizen 5.5
+   * @param[in] key The string key
+   * @return The operation result
+   * @retval BUNDLE_ERROR_NONE Success
+   * @retval BUNDLE_ERROR_INVALID_PARAMETER Invalid parameter
+   * @retval BUNDLE_ERROR_KEY_NOT_AVAILABLE Key not available
+  */
+  int Delete(const std::string& key);
+
+  /**
+   * @brief Gets a string from the key.
+   * @since_tizen 5.5
+   * @param[in] key The string key
+   * @return The string
+  */
+  std::string GetString(const std::string& key) const;
+
+  /**
+   * @brief Gets strings from the key.
+   * @since_tizen 5.5
+   * @param[in] key The string key
+   * @return The array of strings
+  */
+  std::vector<std::string> GetStringArray(const std::string& key) const;
+
+  /**
+   * @brief Gets bytes from the key.
+   * @since_tizen 5.5
+   * @param[in] key The string key
+   * @return Bytes
+  */
+  std::vector<unsigned char> GetByte(const std::string& key) const;
+
+  /**
+   * @brief Converts this object to BundleRaw type.
+   * @since_tizen 5.5
+   * @param[in] base64 @c true, the BundleRaw will be encoded using base64-encoding.
+   * @return The object of BundleRaw
+  */
+  BundleRaw ToRaw(bool base64 = true);
+
+  /**
+   * @brief Gets the count of keys.
+   * @since_tizen 5.5
+   * @return The count
+  */
+  int GetCount() const;
+
+  /**
+   * @brief Gets the data type from the key.
+   * @since_tizen 5.5
+   * @param[in] key The string key
+   * @return The data type
+  */
+  bundle_type GetType(const std::string& key) const;
+
+  /**
+   * @brief Gets the handle for bundle APIs.
+   * @since_tizen 5.5
+   * @return The handle for bundle
+  */
+  bundle* GetHandle() const;
+
+  /**
+   * @brief Moves this object into the bundle handle.
+   * @since_tizen 5.5
+   * @return The handle for bundle
+  */
+  bundle* Detach();
+
+  /**
+   * @brief Exports bundle to an argument vector.
+   * @since_tizen 6.5
+   * @return The argument vector
+   */
+  std::vector<std::string> Export() const;
+
+ private:
+  class Impl;
+  std::unique_ptr<Impl> impl_;
+};
+
+}  // namespace tizen_base
+
+/**
+ * @}
+ */
+
+#endif  // BUNDLE_CPP_H_
diff --git a/src/bundle/include/bundle_internal.h b/src/bundle/include/bundle_internal.h
new file mode 100644 (file)
index 0000000..b489adb
--- /dev/null
@@ -0,0 +1,448 @@
+/*
+ * Copyright (c) 2000 - 2020 Samsung Electronics Co., Ltd. All rights reserved.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#ifndef __BUNDLE_INTERNAL_H__
+#define __BUNDLE_INTERNAL_H__
+
+/**
+ * @file bundle_internal.h
+ * @brief    This file declares has API of the bundle library
+ */
+
+/**
+ * @addtogroup CORE_LIB_BUNDLE_MODULE
+ * @{
+ */
+
+#include <bundle.h>
+
+#ifdef __cplusplus
+extern "C" {
+# endif
+
+/**
+ * @brief Called for every key-value pair.
+ * @since_tizen 2.3
+ * @remarks This type is obsolete. You must not use this type any more.
+ * @see bundle_iterate()
+ */
+typedef void (*bundle_iterate_cb_t) (const char *key, const char *val, void *data);
+
+/**
+ * @brief Adds a string type key-value pair into a given bundle.
+ * @since_tizen 2.3
+ * @param[in] b The bundle object
+ * @param[in] key The key
+ * @param[in] val The value
+ * @return The operation result
+ * @retval #BUNDLE_ERROR_NONE Success
+ * @retval #BUNDLE_ERROR_INVALID_PARAMETER Invalid parameter
+ * @retval #BUNDLE_ERROR_KEY_EXISTS Key already exists
+ * @retval #BUNDLE_ERROR_OUT_OF_MEMORY Out of memory
+ * @pre @a b must be a valid bundle object.
+ * @see bundle_add_str()
+ @code
+ #include <bundle_internal.h>
+ bundle *b = bundle_create(); // Create new bundle object
+ bundle_add(b, "foo_key", "bar_val"); // add a key-val pair
+
+ bundle_free(b);
+ @endcode
+ */
+int bundle_add(bundle *b, const char *key, const char *val);
+
+/**
+ * @brief Gets a value with a given key.
+ * @since_tizen 2.3
+ * @remarks You MUST NOT free or modify the returned string!
+ * @remarks The specific error code can be obtained using the get_last_result() method. Error codes are described in Exception section.
+ * @param[in] b The bundle object
+ * @param[in] key The key
+ * @return The pointer for the value string
+ * @retval @c NULL - Key not found
+ * @exception #BUNDLE_ERROR_NONE Success
+ * @exception #BUNDLE_ERROR_INVALID_PARAMETER Invalid parameter
+ * @exception #BUNDLE_ERROR_KEY_NOT_AVAILABLE Key not available
+ * @pre @a b must be a valid bundle object.
+ * @see bundle_get_str()
+ @code
+ #include <bundle_internal.h>
+ bundle *b = bundle_create(); // Create new bundle object
+ bundle_add_str(b, "foo", "bar"); //add a key-val pair
+ char *val = bundle_get_val(b, "foo_key");     // val = "bar_val"
+
+ bundle_free(b);       // After freeing b, val becomes a dangling pointer.
+ val = NULL;
+ @endcode
+ */
+const char *bundle_get_val(bundle *b, const char *key);
+
+/**
+ * @brief Iterates a callback function for each key-value pairs in a given bundle.
+ * @details (NOTE: Only BUNDLE_TYPE_STR type values come!)
+ * @since_tizen 2.3
+ * @remarks The specific error code can be obtained using the get_last_result() method. Error codes are described in Exception section.
+ * @remarks This function is obsolete and does not give values whose types are not BUNDLE_TYPE_STR.
+ * @param[in] b The bundle object
+ * @param[in] callback The iteration callback function
+ * @param[in] cb_data The data for callback function
+ * @exception #BUNDLE_ERROR_NONE Success
+ * @exception #BUNDLE_ERROR_INVALID_PARAMETER Invalid parameter
+ * @pre @a b must be a valid bundle object.
+ @code
+ #include <stdio.h>
+ #include <bundle_internal.h>
+ void sample_cb(const char *k, const char *v, void *data) {
+   printf("%s -> %s\n", k, v);
+ }
+
+ int main(void) {
+        bundle *b = bundle_create(); // Create new bundle object
+        bundle_add_str(b, "k1", "v1"); // add a key-val pair
+        bundle_add_str(b, "k2", "v2"); // add a key-val pair
+        bundle_add_str(b, "k3", "v3"); // add a key-val pair
+        bundle_iterate(b, sample_cb, NULL); // iterate sample_cb() for each key/val
+        return 0;
+ }
+ @endcode
+ */
+void bundle_iterate(bundle *b, bundle_iterate_cb_t callback, void *cb_data);
+
+/**
+ * @brief Determines whether the type of a key-value pair is measurable.
+ * @since_tizen 2.3
+ * @remarks The specific error code can be obtained using the get_last_result() method. Error codes are described in Exception section.
+ * @param[in] kv A bundle_keyval_t object
+ * @return The operation result
+ * @retval @c 1 - @a kv is an measurable
+ * @retval @c 0 - @a kv is not an measurable
+ * @exception #BUNDLE_ERROR_NONE Success
+ * @exception #BUNDLE_ERROR_INVALID_PARAMETER Invalid parameter
+ * @pre @a kv must be a valid bundle_keyval_t object.
+ * @see bundle_foreach()
+ */
+int bundle_keyval_type_is_measurable(bundle_keyval_t *kv);
+
+/**
+ * @brief Duplicates key-value pair.
+ * @since_tizen 5.5
+ * @param[in] kv A bundle_keyval_t object
+ * @return The bundle object
+ * @retval @c NULL - Failure
+ * @pre @a kv must be a valid bundle_keyval_t object.
+ */
+bundle_keyval_t *bundle_keyval_dup(const bundle_keyval_t *kv);
+
+/**
+ * @brief Frees the encoded rawdata.
+ * @since_tizen 2.3
+ * @param[in] r The rawdata
+ * @return The operation result
+ * @retval #BUNDLE_ERROR_NONE Success
+ * @retval #BUNDLE_ERROR_INVALID_PARAMETER Invalid parameter
+ * @pre @a r is a valid rawdata generated by bundle_encode().
+ * @see bundle_encode()
+ */
+int bundle_free_encoded_rawdata(bundle_raw **r);
+
+/**
+ * @brief Encodes a bundle to the bundle_raw format.
+ * @since_tizen 2.3
+ * @param[in] b The bundle object
+ * @param[out] r The returned bundle_raw data(byte data)
+ *               @a r MUST BE FREED by free(r)
+ * @param[out] len The size of @a r (in bytes)
+ * @return The size of the raw data
+ * @retval #BUNDLE_ERROR_NONE Success
+ * @retval #BUNDLE_ERROR_INVALID_PARAMETER Invalid parameter
+ * @retval #BUNDLE_ERROR_OUT_OF_MEMORY Out of memory
+ * @pre @a b must be a valid bundle object.
+ @code
+ #include <bundle_internal.h>
+ bundle *b = bundle_create(); // Create new bundle object
+ bundle_add_str(b, "foo_key", "bar_val"); // add a key-val pair
+ bundle_raw *r;
+ int len;
+ bundle_encode_raw(b, &r, &len);       // encode b
+
+ bundle_free(b);
+ @endcode
+ */
+int bundle_encode_raw(bundle *b, bundle_raw **r, int *len);
+
+/**
+ * @brief Deserializes bundle_raw and gets a bundle object.
+ * @since_tizen 2.3
+ * @remarks The specific error code can be obtained using the get_last_result() method. Error codes are described in Exception section.
+ * @param[in] r The bundle_raw data to be converted to a bundle object
+ * @param[in] len The size of @a r
+ * @return The bundle object
+ * @retval @c NULL - Failure
+ * @exception #BUNDLE_ERROR_NONE Success
+ * @exception #BUNDLE_ERROR_INVALID_PARAMETER Invalid parameter
+ * @pre @a r must be a valid bundle object.
+ @code
+ #include <bundle_internal.h>
+ bundle *b = bundle_create(); // Create new bundle object
+ bundle_add_str(b, "foo_key", "bar_val"); // add a key-val pair
+
+ bundle_raw *encoded_b;
+ int len;
+ bundle_encode(b, &encoded_b, &len);   // encode b
+
+ bundle *b_dup;
+ b_dup = bundle_decode_raw(encoded_b, len);    // decoded bundle object
+
+ bundle_free(b);
+ free(encoded_b);
+ bundle_free(b_dup);
+ @endcode
+ */
+bundle *bundle_decode_raw(const bundle_raw *r, const int len);
+
+/**
+ * @brief Exports bundle to @a argv.
+ * @since_tizen 2.3
+ * @remarks The specific error code can be obtained using the get_last_result() method. Error codes are described in Exception section.
+ * @param[in] b The bundle object
+ * @param[out] argv The pointer of the string array; \n
+ *                  This array has NULL values for the first and last item; \n
+ *                  First NULL is for argv[0], and last NULL is a terminator for execv() \n
+ * @return The number of item in @a argv. This value is equal to the actual count of argv - 1. (Last NULL terminator is not counted.)
+ * @retval @c -1 - Failure
+ * @exception #BUNDLE_ERROR_NONE Success
+ * @exception #BUNDLE_ERROR_INVALID_PARAMETER Invalid parameter
+ * @exception #BUNDLE_ERROR_OUT_OF_MEMORY Out of memory
+ * @pre @a b is a valid bundle object.
+ * @post @a argv is a pointer of newly allocated memory. It must be freed.
+ * @see bundle_import_from_argv()
+ @code
+ #include <bundle_internal.h>
+ bundle *b = bundle_create(); // Create new bundle object
+ bundle_add_str(b, "foo_key", "bar_val"); // add a key-val pair
+
+ int argc = 0;
+ char **argv = NULL;
+ argc = bundle_export_to_argv(b, &argv);       // export to argv
+ if(0 > argc) error("export failure");
+
+ int i;
+ for(i=0; i < argc; i++) {
+   printf("%s\n", argv[i]);            // print argv
+ }
+ bundle_free_exported_argv(argc, argv);        // argv must be freed after being used.
+
+ bundle_free(b);
+ @endcode
+ */
+int bundle_export_to_argv(bundle *b, char ***argv);
+
+/**
+ * @brief Frees the exported @a argv.
+ * @since_tizen 2.3
+ * @remarks You must not use this API when you use global @a argv.
+ * @param[in] argc The number of args, which is the return value of bundle_export_to_argv()
+ * @param[in] argv The array from bundle_export_to_argv()
+ * @return The operation result
+ * @retval #BUNDLE_ERROR_NONE Success
+ * @retval #BUNDLE_ERROR_INVALID_PARAMETER Invalid parameter
+ * @pre @a argv is a valid string array generated from bundle_export_to_argv().
+ * @see bundle_export_to_argv()
+ @code
+ bundle *b = bundle_create();
+ bundle_add_str(b, "foo", "bar");
+
+ int argc = 0;
+ char **argv = NULL;
+ argc = bundle_export_to_argv(b, &argv);
+ if(0 > argc) error("export failure");
+
+ // Use argv...
+
+ bundle_free_exported_argv(argc, argv);
+ argv = NULL;
+
+ bundle_free(b);
+ @endcode
+ */
+int bundle_free_exported_argv(int argc, char ***argv);
+
+/**
+ * @brief Imports a bundle from @a argv.
+ * @since_tizen 2.3
+ * @remarks The specific error code can be obtained using the get_last_result() method. Error codes are described in Exception section.
+ * @param[in] argc The argument count
+ * @param[in] argv The argument vector
+ * @return The new bundle object
+ * @retval @c NULL - Failure
+ * @exception #BUNDLE_ERROR_NONE Success
+ * @exception #BUNDLE_ERROR_INVALID_PARAMETER Invalid parameter
+ * @exception #BUNDLE_ERROR_OUT_OF_MEMORY Out of memory
+ * @pre @a argv is a valid string array, which is created by bundle_export_to_argv().
+ * @post The returned bundle @a b must be freed.
+ * @see bundle_export_to_argv()
+ @code
+ #include <bundle_internal.h>
+
+ int main(int argc, char **argv) {
+   bundle *b = bundle_import_from_argv(argc, argv); // import from argc+argv
+   char *val = bundle_get_val(b, "foo_key");   // value for "foo_key"
+   // ......
+   bundle_free(b);     // After freeing b, val becomes a dangling pointer.
+   val = NULL;
+ }
+ @endcode
+ */
+bundle *bundle_import_from_argv(int argc, char **argv);
+
+/**
+ * @brief Sets a value of string array elements.
+ * @since_tizen 2.3
+ * @param[in] b The bundle object
+ * @param[in] key The key
+ * @param[in] idx The index of the array element to be changed
+ * @param[in] val The string type value; if @c NULL, an empty array is created; you can change an item with
+ * @return The operation result
+ * @retval #BUNDLE_ERROR_NONE Success
+ * @retval #BUNDLE_ERROR_INVALID_PARAMETER Invalid parameter
+ * @pre @a b must be a valid bundle object.
+ * @see bundle_add_str_array()
+ * @see bundle_get_str_array()
+ @code
+ #include <bundle_internal.h>
+ bundle *b = bundle_create();
+ bundle_add_str_array(b, "foo", NULL, 3); // add a key-val pair
+ bundle_set_str_array_element(b, "foo", 0, "aaa");
+ bundle_set_str_array_element(b, "foo", 1, "bbb");
+ bundle_set_str_array_element(b, "foo", 2, "ccc");
+
+ char **str_array = NULL;
+ int len_str_array = 0;
+
+ str_array=bundle_get_str_array(b, "foo", &len_str_array);
+ // str_array = { "aaa", "bbb", "ccc" }, and len_str_array = 3
+
+ bundle_free(b);
+ @endcode
+ */
+int bundle_set_str_array_element(bundle *b, const char *key, const unsigned int idx, const char *val);
+
+/**
+ * @brief Creates a JSON data from bundle.
+ * @since_tizen 3.0
+ * @remarks This function only supports the string type and the string array type.
+ * @param[in] b The bundle object
+ * @param[out] json The new created json data
+ * @return The operation result
+ * @retval #BUNDLE_ERROR_NONE Success
+ * @retval #BUNDLE_ERROR_INVALID_PARAMETER Invalid parameter
+ * @retval #BUNDLE_ERROR_OUT_OF_MEMORY Out of memory
+ * @pre @a b must be a valid bundle object.
+ @code
+ #include <bundle_internal.h>
+ bundle *b = bundle_create();
+ char *json;
+ int ret;
+
+ bundle_add_str(b, "foo", "bar");
+ ret = bundle_to_json(b, &json);
+ if (ret != BUNDLE_ERROR_NONE) {
+ bundle_free(b);
+ return;
+ }
+ // json = "{"foo":"bar"}"
+ bundle_free(b);
+ free(json);
+ @endcode
+ */
+int bundle_to_json(bundle *b, char **json);
+
+/**
+ * @breif Creates a bundle object from json.
+ * @since_tizen 3.0
+ * @remarks This function only supports the string type and the string array type.
+ * @param[in] json The json data
+ * @param[out] b The bundle object
+ * @return The operation result
+ * @retval #BUNDLE_ERROR_NONE Success
+ * @retval #BUNDLE_ERROR_INVALID_PARAMETER Invalid parameter
+ * @retval #BUNDLE_ERROR_OUT_OF_MEMORY Out of memory
+ @code
+ #include <bundle_internal.h>
+ bundle *b;
+ char *json = "{"foo":"bar"}";
+ int ret;
+
+ ret =  bundle_from_json(json, &b);
+ if (ret != BUNDLE_ERROR_NONE)
+ return;
+ bundle_free(b);
+ @endcode
+ */
+int bundle_from_json(const char *json, bundle **b);
+
+/**
+ * @breif Compares the bundle 1, 2.
+ * @since_tizen 3.0
+ * @param[in] b1 The bundle object
+ * @param[in] b2 The bundle object
+ * @return The operation result
+ * @retval @c 0 It is identical
+ * @retval @c -1 Invalid parameter
+ * @retval @c 1 It is not identical
+ */
+int bundle_compare(bundle *b1, bundle *b2);
+
+/**
+ * @brief Initializes a byte array type key-value pair into a bundle.
+ * @details To set the value of the byte array element, you should use bundle_set_byte_array_element().
+ *          This function is only for creating a buffer of the byte array.
+ * @since_tizen 5.5
+ * @param[in] b The bundle object
+ * @param[in] key The key
+ * @param[in] len The length of the array to be created
+ * @return @c 0 on success,
+ *         otherwise a negative error value
+ * @retval #BUNDLE_ERROR_NONE Successful
+ * @retval #BUNDLE_ERROR_INVALID_PARAMETER Invalid parameter
+ * @retval #BUNDLE_ERROR_KEY_EXISTS Key already exists
+ * @retval #BUNDLE_ERROR_OUT_OF_MEMORY Out of memory
+ *
+ * @see bundle_set_byte_array_element()
+ */
+int bundle_init_byte_array(bundle *b, const char *key, const unsigned int len);
+
+/**
+ * @brief Frees the given key-value pair.
+ * @since_tizen 6.0
+ * @param[in] kv The key-value pair
+ * @return @c 0 on success,
+ *         otherwise a negative error value
+ * @retval #BUNDLE_ERROR_NONE Successful
+ * @retval #BUNDLE_ERROR_INVALID_PARAMETER Invalid parameter
+ */
+int bundle_keyval_free(bundle_keyval_t *kv);
+
+#ifdef __cplusplus
+}
+#endif
+
+/**
+ * @}
+ * @}
+ */
+
+#endif /* __BUNDLE__INTERNAL_H__ */
diff --git a/src/bundle/json-internal.cc b/src/bundle/json-internal.cc
new file mode 100644 (file)
index 0000000..882af4c
--- /dev/null
@@ -0,0 +1,183 @@
+/*
+ * Copyright (c) 2020 Samsung Electronics Co., Ltd. All rights reserved.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#include "exception-internal.h"
+#include "json-internal.h"
+
+namespace tizen_base {
+namespace internal {
+
+Json::Json(std::string json) : json_(std::move(json)) {
+}
+
+Json::Json(Bundle* b) : b_(b) {
+}
+
+Bundle* Json::ToBundle() {
+  if (json_.empty())
+    return nullptr;
+
+  JsonParser* parser = json_parser_new();
+  if (parser == nullptr)
+    THROW(BUNDLE_ERROR_OUT_OF_MEMORY);
+
+  std::unique_ptr<JsonParser, decltype(g_object_unref)*> parser_ptr(parser,
+      g_object_unref);
+
+  GError* error = nullptr;
+  json_parser_load_from_data(parser, json_.c_str(), json_.length(), &error);
+  if (error) {
+    g_error_free(error);
+    THROW(BUNDLE_ERROR_INVALID_PARAMETER);
+  }
+
+  JsonNode* root = json_parser_get_root(parser);
+  if (root == nullptr)
+    THROW(BUNDLE_ERROR_INVALID_PARAMETER);
+
+  JsonObject* root_obj = json_node_get_object(root);
+  if (root_obj == nullptr)
+    THROW(BUNDLE_ERROR_INVALID_PARAMETER);
+
+  Bundle* b = new (std::nothrow) Bundle();
+  if (b == nullptr)
+    THROW(BUNDLE_ERROR_OUT_OF_MEMORY);
+
+  json_object_foreach_member(root_obj, OnJsonObjectMember, b);
+
+  return b;
+}
+
+std::string Json::ToString() {
+  if (b_ == nullptr)
+    THROW(BUNDLE_ERROR_INVALID_PARAMETER);
+
+  JsonObject* object = json_object_new();
+  if (object == nullptr)
+    THROW(BUNDLE_ERROR_OUT_OF_MEMORY);
+
+  std::unique_ptr<JsonObject, decltype(json_object_unref)*> object_ptr(object,
+      json_object_unref);
+
+  for (const auto& kv : b_->GetMap()) {
+    auto& key_info = kv.second;
+    if (key_info->GetType() == Bundle::Type::StringArray) {
+      JsonArray* json_arr = json_array_new();
+      if (json_arr == nullptr)
+        THROW(BUNDLE_ERROR_OUT_OF_MEMORY);
+
+      for (const auto& v : key_info->GetValues()) {
+        json_array_add_string_element(json_arr,
+            const_cast<const char*>(reinterpret_cast<char*>(v.get())));
+      }
+
+      json_object_set_array_member(object, key_info->GetKey().c_str(),
+          json_arr);
+    } else {
+      json_object_set_string_member(object, key_info->GetKey().c_str(),
+          const_cast<const char*>(
+            reinterpret_cast<char*>(
+              key_info->GetValues()[0].get())));
+    }
+  }
+
+  JsonNode* node = json_node_new(JSON_NODE_OBJECT);
+  if (node == nullptr)
+    THROW(BUNDLE_ERROR_OUT_OF_MEMORY);
+
+  std::unique_ptr<JsonNode, decltype(json_node_free)*> node_ptr(node,
+      json_node_free);
+
+  json_node_set_object(node, object);
+
+  JsonGenerator* generator = json_generator_new();
+  if (generator == nullptr)
+    THROW(BUNDLE_ERROR_OUT_OF_MEMORY);
+
+  std::unique_ptr<JsonGenerator, decltype(g_object_unref)*> generator_ptr(
+      generator, g_object_unref);
+
+  json_generator_set_root(generator, node);
+  gsize length = 0;
+  gchar* json = json_generator_to_data(generator, &length);
+  if (json == nullptr)
+    THROW(BUNDLE_ERROR_OUT_OF_MEMORY);
+
+  std::unique_ptr<gchar, decltype(g_free)*> json_auto(json, g_free);
+  json_ = json;
+  return json_;
+}
+
+void Json::OnJsonObjectMember(JsonObject* object, const char* key,
+  JsonNode* node, gpointer user_data) {
+  auto* b = static_cast<Bundle*>(user_data);
+  KeyInfo* key_info;
+  JsonNodeType node_type = JSON_NODE_TYPE(node);
+  if (node_type == JSON_NODE_ARRAY) {
+    JsonArray* json_arr = json_node_get_array(node);
+    if (json_arr == nullptr)
+      return;
+
+    std::vector<std::vector<unsigned char>> values;
+    guint len = json_array_get_length(json_arr);
+    for (guint i = 0; i < len; ++i) {
+      auto* val = json_array_get_string_element(json_arr, i);
+      if (val == nullptr)
+        val = "";
+
+      auto* p = reinterpret_cast<unsigned char*>(const_cast<char*>(val));
+      std::vector<unsigned char> value(p, p + (strlen(val) + 1));
+      values.push_back(std::move(value));
+    }
+
+    try {
+      key_info = new KeyInfo(Bundle::Type::StringArray, key, std::move(values));
+    } catch (const Exception& e) {
+      _E("Error(%d)", e.GetErrorCode());
+      return;
+    } catch (const std::bad_alloc& ba) {
+      _E("bad alloc exception");
+      return;
+    }
+  } else {
+    auto* val = json_node_get_string(node);
+    if (val == nullptr)
+      val = "";
+
+    auto* p = reinterpret_cast<unsigned char*>(const_cast<char*>(val));
+    std::vector<unsigned char> value(p, p + (strlen(val) + 1));
+
+    try {
+      key_info = new KeyInfo(Bundle::Type::String, key, std::move(value));
+    } catch (const Exception& e) {
+      _E("Error(%d)", e.GetErrorCode());
+      return;
+    } catch (const std::bad_alloc& ba) {
+      _E("bad alloc exception");
+      return;
+    }
+  }
+
+  try {
+    b->Add(std::shared_ptr<KeyInfo>(key_info));
+  } catch (const Exception& e) {
+    _W("Add() is failed. error(%d)", e.GetErrorCode());
+    return;
+  }
+}
+
+}  // namespace internal
+}  // namespace tizen_base
diff --git a/src/bundle/json-internal.h b/src/bundle/json-internal.h
new file mode 100644 (file)
index 0000000..a1f175a
--- /dev/null
@@ -0,0 +1,52 @@
+/*
+ * Copyright (c) 2020 Samsung Electronics Co., Ltd. All rights reserved.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#ifndef JSON_INTERNAL_H_
+#define JSON_INTERNAL_H_
+
+#include <glib.h>
+#include <json-glib/json-glib.h>
+
+#include <memory>
+#include <string>
+
+#include "bundle-internal.h"
+
+namespace tizen_base {
+namespace internal {
+
+class Json {
+ public:
+  explicit Json(std::string json);
+  explicit Json(Bundle* b);
+  virtual ~Json() = default;
+
+  Bundle* ToBundle();
+  std::string ToString();
+
+ private:
+  static void OnJsonObjectMember(JsonObject* object, const char* key,
+      JsonNode* node, gpointer user_data);
+
+ private:
+  Bundle* b_ = nullptr;
+  std::string json_;
+};
+
+}  // namespace internal
+}  // namespace tizen_base
+
+#endif  // JSON_INTERNAL_H_
diff --git a/src/bundle/key-info-internal.cc b/src/bundle/key-info-internal.cc
new file mode 100644 (file)
index 0000000..e5d0b03
--- /dev/null
@@ -0,0 +1,400 @@
+/*
+ * Copyright (c) 2020 Samsung Electronics Co., Ltd. All rights reserved.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#include <algorithm>
+#include <cstring>
+#include <utility>
+
+#include "include/bundle.h"
+
+#include "exception-internal.h"
+#include "key-info-internal.h"
+
+namespace tizen_base {
+namespace internal {
+
+KeyInfo::KeyInfo(int type, std::string key, std::vector<unsigned char> value)
+    : type_(type), key_(std::move(key)) {
+  int ret = SetValue(value);
+  if (ret != BUNDLE_ERROR_NONE)
+    THROW(ret);
+}
+
+KeyInfo::KeyInfo(int type, std::string key,
+    std::vector<std::vector<unsigned char>> values)
+    : type_(type), key_(std::move(key)) {
+  int ret = SetValues(values);
+  if (ret != BUNDLE_ERROR_NONE)
+    THROW(ret);
+}
+
+KeyInfo::KeyInfo(std::vector<unsigned char> encoded_bytes) {
+  int ret = Decode(encoded_bytes);
+  if (ret != BUNDLE_ERROR_NONE)
+    THROW(ret);
+}
+
+KeyInfo::KeyInfo(const KeyInfo& key_info) {
+  values_.reserve(key_info.values_.size());
+  try {
+    for (unsigned int i = 0; i < key_info.values_.size(); ++i) {
+      auto new_value =
+          std::make_unique<unsigned char[]>(key_info.values_size_[i]);
+      std::copy(key_info.values_[i].get(),
+          key_info.values_[i].get() + key_info.values_size_[i],
+          new_value.get());
+      values_.push_back(std::move(new_value));
+    }
+  } catch (const std::bad_alloc& e) {
+    THROW(BUNDLE_ERROR_OUT_OF_MEMORY);
+  }
+
+  type_ = key_info.type_;
+  key_ = key_info.key_;
+  values_size_ = key_info.values_size_;
+  uvalues_size_ = key_info.uvalues_size_;
+}
+
+KeyInfo& KeyInfo::operator=(const KeyInfo& key_info) {
+  if (this != &key_info) {
+    decltype(values_) new_values;
+    try {
+      for (unsigned int i = 0; i < key_info.values_.size(); ++i) {
+        auto new_value =
+            std::make_unique<unsigned char[]>(key_info.values_size_[i]);
+        std::copy(key_info.values_[i].get(),
+            key_info.values_[i].get() + key_info.values_size_[i],
+            new_value.get());
+        new_values.push_back(std::move(new_value));
+      }
+    } catch (const std::bad_alloc& e) {
+      THROW(BUNDLE_ERROR_OUT_OF_MEMORY);
+    }
+
+    type_ = key_info.type_;
+    key_ = key_info.key_;
+    values_size_ = key_info.values_size_;
+    uvalues_size_ = key_info.uvalues_size_;
+    values_ = std::move(new_values);
+  }
+
+  return *this;
+}
+
+KeyInfo::KeyInfo(KeyInfo&& key_info) noexcept {
+  type_ = key_info.type_;
+  key_info.type_ = 0;
+  key_ = std::move(key_info.key_);
+  values_ = std::move(key_info.values_);
+  values_size_ = std::move(key_info.values_size_);
+  uvalues_size_ = std::move(key_info.uvalues_size_);
+}
+
+KeyInfo& KeyInfo::operator=(KeyInfo&& key_info) noexcept {
+  if (this != &key_info) {
+    type_ = key_info.type_;
+    key_info.type_ = 0;
+    key_ = std::move(key_info.key_);
+    values_ = std::move(key_info.values_);
+    values_size_ = std::move(key_info.values_size_);
+    uvalues_size_ = std::move(key_info.uvalues_size_);
+  }
+  return *this;
+}
+
+bool KeyInfo::operator==(const KeyInfo& key_info) {
+  if (this == &key_info)
+    return true;
+
+  if (type_ != key_info.type_)
+    return false;
+
+  if (key_ != key_info.key_)
+    return false;
+
+  if (values_.size() != key_info.values_.size())
+    return false;
+
+  for (unsigned int i = 0; i < values_.size(); ++i) {
+    if (values_size_[i] != key_info.values_size_[i])
+      return false;
+
+    int ret = std::memcmp(values_[i].get(), key_info.values_[i].get(),
+        values_size_[i]);
+    if (ret != 0)
+      return false;
+  }
+
+  return true;
+}
+
+int KeyInfo::GetType() const {
+  return type_;
+}
+
+bool KeyInfo::IsArray() const {
+  if (type_ & BUNDLE_TYPE_ARRAY)
+    return true;
+
+  return false;
+}
+
+const std::string& KeyInfo::GetKey() {
+  return key_;
+}
+
+const std::vector<std::unique_ptr<unsigned char[]>>& KeyInfo::GetValues() {
+  return values_;
+}
+
+const std::vector<std::size_t>& KeyInfo::GetValuesSize() {
+  return values_size_;
+}
+
+const std::vector<unsigned int>& KeyInfo::GetUValuesSize() {
+  return uvalues_size_;
+}
+
+int KeyInfo::SetValue(const std::vector<unsigned char>& value) {
+  try {
+    auto new_value = std::make_unique<unsigned char[]>(value.size());
+    std::copy(value.begin(), value.end(), new_value.get());
+    values_.emplace_back(std::move(new_value));
+  } catch (const std::bad_alloc& e) {
+    return BUNDLE_ERROR_OUT_OF_MEMORY;
+  }
+
+  values_size_.push_back(value.size());
+  uvalues_size_.push_back(static_cast<unsigned int>(value.size()));
+  return BUNDLE_ERROR_NONE;
+}
+
+int KeyInfo::SetValues(const std::vector<std::vector<unsigned char>>& values) {
+  try {
+    for (unsigned int i = 0; i < values.size(); ++i) {
+      auto new_value = std::make_unique<unsigned char[]>(values[i].size());
+      std::copy(values[i].begin(), values[i].end(), new_value.get());
+      values_.push_back(std::move(new_value));
+      values_size_.push_back(values[i].size());
+      uvalues_size_.push_back(values[i].size());
+    }
+  } catch (const std::bad_alloc& e) {
+    return BUNDLE_ERROR_OUT_OF_MEMORY;
+  }
+
+  return BUNDLE_ERROR_NONE;
+}
+
+std::vector<unsigned char> KeyInfo::Encode() {
+  std::size_t encoded_size = GetEncodedSize();
+  if (encoded_size == 0)
+    return {};
+
+  std::vector<unsigned char> bytes;
+
+  // total size
+  unsigned char* p = reinterpret_cast<unsigned char*>(&encoded_size);
+  bytes.insert(bytes.end(), p, p + sizeof(encoded_size));
+
+  // type
+  p = reinterpret_cast<unsigned char*>(&type_);
+  bytes.insert(bytes.end(), p, p + sizeof(type_));
+
+  // key size
+  std::size_t key_length = key_.length() + 1;
+  p = reinterpret_cast<unsigned char*>(&key_length);
+  bytes.insert(bytes.end(), p, p + sizeof(key_length));
+
+  // key
+  bytes.insert(bytes.end(), key_.begin(), key_.end() + 1);
+
+  if (type_ & BUNDLE_TYPE_ARRAY) {
+    // values size
+    std::size_t values_size = values_.size();
+    p = reinterpret_cast<unsigned char*>(&values_size);
+    bytes.insert(bytes.end(), p, p + sizeof(values_size));
+  }
+
+  // values
+  for (unsigned int i = 0; i < values_.size(); i++) {
+    std::size_t value_size = values_size_[i];
+    p = reinterpret_cast<unsigned char*>(&value_size);
+    bytes.insert(bytes.end(), p, p + sizeof(value_size));
+
+    bytes.insert(bytes.end(), values_[i].get(), values_[i].get() + value_size);
+  }
+
+  return bytes;
+}
+
+std::size_t KeyInfo::GetEncodedSize() {
+  // total size
+  std::size_t encoded_size = sizeof(std::size_t);
+
+  // type
+  encoded_size += sizeof(int);
+
+  // key size
+  encoded_size += sizeof(std::size_t);
+
+  // key
+  if ((encoded_size + key_.length() + 1) < encoded_size)
+    return 0;
+
+  encoded_size += key_.length() + 1;
+
+  if (type_ & BUNDLE_TYPE_ARRAY) {
+    // values size
+    if ((encoded_size + sizeof(std::size_t)) < encoded_size)
+      return 0;
+
+    encoded_size += sizeof(std::size_t);
+  }
+
+  // values
+  std::size_t values_size = 0;
+  for (unsigned int i = 0; i < values_.size(); ++i) {
+    // value size
+    if ((values_size + sizeof(std::size_t)) < values_size)
+      return 0;
+
+    values_size += sizeof(std::size_t);
+
+    // value
+    if ((values_size + values_size_[i]) < values_size)
+      return 0;
+
+    values_size += values_size_[i];
+  }
+
+  if ((encoded_size + values_size) < encoded_size)
+    return 0;
+
+  encoded_size += values_size;
+
+  return encoded_size;
+}
+
+int KeyInfo::Decode(const std::vector<unsigned char>& bytes) {
+  unsigned int reader = 0;
+
+  // total size
+  std::size_t total_size = 0;
+  if ((reader + sizeof(total_size)) > bytes.size())
+    return BUNDLE_ERROR_INVALID_PARAMETER;
+
+  unsigned char* p = reinterpret_cast<unsigned char*>(&total_size);
+  std::copy(&bytes[reader], &bytes[reader] + sizeof(total_size), p);
+  reader += sizeof(total_size);
+
+  // type
+  if ((reader + sizeof(type_)) > bytes.size())
+    return BUNDLE_ERROR_INVALID_PARAMETER;
+
+  p = reinterpret_cast<unsigned char*>(&type_);
+  std::copy(&bytes[reader], &bytes[reader] + sizeof(type_), p);
+  reader += sizeof(type_);
+
+  // key size
+  std::size_t key_size = 0;
+
+  if ((reader + sizeof(key_size)) > bytes.size())
+    return BUNDLE_ERROR_INVALID_PARAMETER;
+
+  p = reinterpret_cast<unsigned char*>(&key_size);
+  std::copy(&bytes[reader], &bytes[reader] + sizeof(key_size), p);
+  reader += sizeof(key_size);
+
+  if ((reader + key_size) > bytes.size())
+    return BUNDLE_ERROR_INVALID_PARAMETER;
+
+  // key
+  std::vector<unsigned char> key(&bytes[reader], &bytes[reader] + key_size);
+  p = reinterpret_cast<unsigned char*>(&key[0]);
+  key_ = std::string(reinterpret_cast<char*>(p));
+  reader += key_size;
+
+  std::size_t values_size = 0;
+  if (type_ & BUNDLE_TYPE_ARRAY) {
+    // values size
+    if ((reader + sizeof(values_size)) > bytes.size())
+      return BUNDLE_ERROR_INVALID_PARAMETER;
+
+    p = reinterpret_cast<unsigned char*>(&values_size);
+    std::copy(&bytes[reader], &bytes[reader] + sizeof(values_size), p);
+    reader += sizeof(values_size);
+  } else {
+    values_size = 1;
+  }
+
+  // values
+  for (std::size_t i = 0; i < values_size; ++i) {
+    // value_size
+    std::size_t value_size = 0;
+    if ((reader + sizeof(value_size)) > bytes.size())
+      return BUNDLE_ERROR_INVALID_PARAMETER;
+
+    p = reinterpret_cast<unsigned char*>(&value_size);
+    std::copy(&bytes[reader], &bytes[reader] + sizeof(value_size), p);
+    reader += sizeof(value_size);
+
+    // value
+    if ((reader + value_size) > bytes.size())
+      return BUNDLE_ERROR_INVALID_PARAMETER;
+
+    try {
+      auto new_value = std::make_unique<unsigned char[]>(value_size);
+      std::copy(&bytes[reader], &bytes[reader] + value_size, new_value.get());
+      reader += value_size;
+      values_.push_back(std::move(new_value));
+    } catch (const std::bad_alloc& e) {
+      return BUNDLE_ERROR_OUT_OF_MEMORY;
+    }
+    values_size_.push_back(value_size);
+    uvalues_size_.push_back(static_cast<unsigned int>(value_size));
+  }
+
+  return BUNDLE_ERROR_NONE;
+}
+
+int KeyInfo::SetValue(int index, const std::vector<unsigned char>& value) {
+  if (index > GetSize() || index < 0)
+    return BUNDLE_ERROR_ARRAY_INDEX_OUT_OF_BOUNDS;
+
+  if (!IsArray())
+    return BUNDLE_ERROR_INVALID_PARAMETER;
+
+  try {
+    auto new_value = std::make_unique<unsigned char[]>(value.size());
+    if (value.size() != 0)
+      std::copy(value.begin(), value.end(), new_value.get());
+
+    values_[index] = std::move(new_value);
+  } catch (const std::bad_alloc& e) {
+    return BUNDLE_ERROR_OUT_OF_MEMORY;
+  }
+
+  values_size_[index] = value.size();
+  uvalues_size_[index] = static_cast<unsigned int>(value.size());
+  return BUNDLE_ERROR_NONE;
+}
+
+int KeyInfo::GetSize() const {
+  return values_.size();
+}
+
+}  // namespace internal
+}  // namespace tizen_base
diff --git a/src/bundle/key-info-internal.h b/src/bundle/key-info-internal.h
new file mode 100644 (file)
index 0000000..b26ba5b
--- /dev/null
@@ -0,0 +1,72 @@
+/*
+ * Copyright (c) 2020 Samsung Electronics Co., Ltd. All rights reserved.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#ifndef KEY_INFO_INTERNAL_H_
+#define KEY_INFO_INTERNAL_H_
+
+#include <string>
+#include <vector>
+#include <memory>
+
+namespace tizen_base {
+namespace internal {
+
+class KeyInfo {
+ public:
+  KeyInfo(int type, std::string key,
+          std::vector<unsigned char> value);
+  KeyInfo(int type, std::string key,
+          std::vector<std::vector<unsigned char>> values);
+  explicit KeyInfo(std::vector<unsigned char> encoded_bytes);
+  virtual ~KeyInfo() = default;
+
+  KeyInfo(const KeyInfo& key_info);
+  KeyInfo& operator = (const KeyInfo& key_info);
+  KeyInfo(KeyInfo&& key_info) noexcept;
+  KeyInfo& operator = (KeyInfo&& key_info) noexcept;
+
+  bool operator == (const KeyInfo& key_info);
+
+  int GetType() const;
+  bool IsArray() const;
+  const std::string& GetKey();
+  const std::vector<std::unique_ptr<unsigned char[]>>& GetValues();
+  const std::vector<std::size_t>& GetValuesSize();
+  const std::vector<unsigned int>& GetUValuesSize();
+  std::vector<unsigned char> Encode();
+
+  int SetValue(int index, const std::vector<unsigned char>& value);
+  int GetSize() const;
+
+ private:
+  std::size_t GetEncodedSize();
+  int SetValuesSize();
+  int SetValue(const std::vector<unsigned char>& value);
+  int SetValues(const std::vector<std::vector<unsigned char>>& values);
+  int Decode(const std::vector<unsigned char>& bytes);
+
+ private:
+  int type_;
+  std::string key_;
+  std::vector<std::unique_ptr<unsigned char[]>> values_;
+  std::vector<std::size_t> values_size_;
+  std::vector<unsigned int> uvalues_size_;
+};
+
+}  // namespace internal
+}  // namespace tizen_base
+
+#endif  // KEY_INFO_INTERNAL_H_
diff --git a/src/bundle/log-private.h b/src/bundle/log-private.h
new file mode 100644 (file)
index 0000000..29e99da
--- /dev/null
@@ -0,0 +1,37 @@
+/*
+ * Copyright (c) 2020 Samsung Electronics Co., Ltd All Rights Reserved
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#ifndef LOG_PRIVATE_H_
+#define LOG_PRIVATE_H_
+
+#include <dlog.h>
+
+#undef LOG_TAG
+#define LOG_TAG "BUNDLE"
+
+#undef _E
+#define _E LOGE
+
+#undef _W
+#define _W LOGW
+
+#undef _I
+#define _I LOGI
+
+#undef _D
+#define _D LOGD
+
+#endif  // LOG_PRIVATE_H_
diff --git a/src/bundle/stub.cc b/src/bundle/stub.cc
new file mode 100644 (file)
index 0000000..7d8b84f
--- /dev/null
@@ -0,0 +1,775 @@
+/*
+ * Copyright (c) 2020 Samsung Electronics Co., Ltd. All rights reserved.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#include <tizen.h>
+#include <glib.h>
+
+#include <stdexcept>
+
+#include "include/bundle.h"
+#include "include/bundle_internal.h"
+
+#include "bundle-internal.h"
+#include "exception-internal.h"
+#include "export-api-internal.h"
+#include "json-internal.h"
+
+using namespace tizen_base::internal;
+
+extern "C" EXPORT_API bundle* bundle_create(void) {
+  auto* h = new (std::nothrow) Bundle();
+  if (h == nullptr) {
+    set_last_result(BUNDLE_ERROR_OUT_OF_MEMORY);
+    return nullptr;
+  }
+
+  set_last_result(BUNDLE_ERROR_NONE);
+  return reinterpret_cast<bundle*>(h);
+}
+
+extern "C" EXPORT_API int bundle_free(bundle* b) {
+  if (b == nullptr)
+    return BUNDLE_ERROR_INVALID_PARAMETER;
+
+  auto* h = reinterpret_cast<Bundle*>(b);
+  delete h;
+  return BUNDLE_ERROR_NONE;
+}
+
+extern "C" EXPORT_API int bundle_add_str(bundle* b,
+    const char* key, const char* str) {
+  if (b == nullptr || key == nullptr || strlen(key) == 0 || str == nullptr)
+    return BUNDLE_ERROR_INVALID_PARAMETER;
+
+  auto* h = reinterpret_cast<Bundle*>(b);
+  std::vector<unsigned char> value(str, str + (strlen(str) + 1));
+
+  KeyInfo* key_info;
+  try {
+    key_info = new KeyInfo(BUNDLE_TYPE_STR, key, std::move(value));
+  } catch (const Exception& e) {
+    return e.GetErrorCode();
+  } catch (const std::bad_alloc& ba) {
+    return BUNDLE_ERROR_OUT_OF_MEMORY;
+  }
+
+  try {
+    h->Add(std::shared_ptr<KeyInfo>(key_info));
+  } catch (const Exception& e) {
+    return e.GetErrorCode();
+  }
+
+  return BUNDLE_ERROR_NONE;
+}
+
+extern "C" EXPORT_API int bundle_get_str(bundle* b,
+    const char* key, char** str) {
+  if (b == nullptr || key == nullptr)
+    return BUNDLE_ERROR_INVALID_PARAMETER;
+
+  auto* h = reinterpret_cast<Bundle*>(b);
+  std::shared_ptr<KeyInfo> key_info;
+  try {
+    key_info = h->Get(key);
+  } catch (const Exception& e) {
+    return e.GetErrorCode();
+  }
+
+  if (key_info->GetType() != BUNDLE_TYPE_STR)
+    return BUNDLE_ERROR_INVALID_PARAMETER;
+
+  if (str) {
+    auto& values = key_info->GetValues();
+    auto& value = const_cast<std::unique_ptr<unsigned char[]>&>(values[0]);
+    *str = reinterpret_cast<char*>(&value[0]);
+  }
+
+  return BUNDLE_ERROR_NONE;
+}
+
+extern "C" EXPORT_API int bundle_add(bundle* b, const char* key,
+    const char* val) {
+  return bundle_add_str(b, key, val);
+}
+
+extern "C" EXPORT_API int bundle_del(bundle* b, const char* key) {
+  if (b == nullptr || key == nullptr || strlen(key) == 0)
+    return BUNDLE_ERROR_INVALID_PARAMETER;
+
+  auto* h = reinterpret_cast<Bundle*>(b);
+  try {
+    h->Remove(key);
+  } catch (const Exception& e) {
+    return e.GetErrorCode();
+  }
+
+  return BUNDLE_ERROR_NONE;
+}
+
+extern "C" EXPORT_API const char* bundle_get_val(bundle* b, const char* key) {
+  char* val = nullptr;
+  int ret = bundle_get_str(b, key, &val);
+  set_last_result(ret);
+  return val;
+}
+
+extern "C" EXPORT_API int bundle_get_count(bundle* b) {
+  if (b == nullptr)
+    return 0;
+
+  auto* h = reinterpret_cast<Bundle*>(b);
+  set_last_result(BUNDLE_ERROR_NONE);
+  return h->GetSize();
+}
+
+extern "C" EXPORT_API void bundle_iterate(bundle* b,
+    bundle_iterate_cb_t callback, void* user_data) {
+  if (b == nullptr || callback == nullptr) {
+    set_last_result(BUNDLE_ERROR_INVALID_PARAMETER);
+    return;
+  }
+
+  auto* h = reinterpret_cast<Bundle*>(b);
+  for (const auto& [key, key_info] : h->GetMap()) {
+    auto& values = key_info->GetValues();
+    auto& value = const_cast<std::unique_ptr<unsigned char[]>&>(values[0]);
+    auto* val = reinterpret_cast<char*>(&value[0]);
+    callback(key_info->GetKey().c_str(), val, user_data);
+  }
+
+  set_last_result(BUNDLE_ERROR_NONE);
+}
+
+extern "C" EXPORT_API void bundle_foreach(bundle* b,
+    bundle_iterator_t callback, void* user_data) {
+  if (b == nullptr || callback == nullptr) {
+    set_last_result(BUNDLE_ERROR_INVALID_PARAMETER);
+    return;
+  }
+
+  auto* h = reinterpret_cast<Bundle*>(b);
+  auto it = h->GetMap().begin();
+  while (it != h->GetMap().end()) {
+    auto& key_info = it->second;
+    ++it;
+    callback(key_info->GetKey().c_str(), key_info->GetType(),
+             reinterpret_cast<bundle_keyval_t*>(key_info.get()), user_data);
+  }
+
+  set_last_result(BUNDLE_ERROR_NONE);
+}
+
+extern "C" EXPORT_API int bundle_keyval_get_type(bundle_keyval_t* kv) {
+  if (kv == nullptr) {
+    set_last_result(BUNDLE_ERROR_INVALID_PARAMETER);
+    return -1;
+  }
+
+  auto* key_info = reinterpret_cast<KeyInfo*>(kv);
+  set_last_result(BUNDLE_ERROR_NONE);
+  return key_info->GetType();
+}
+
+extern "C" EXPORT_API int bundle_keyval_type_is_array(bundle_keyval_t* kv) {
+  int type = bundle_keyval_get_type(kv);
+  if (type == -1)
+    return -1;
+
+  set_last_result(BUNDLE_ERROR_NONE);
+  if (type & BUNDLE_TYPE_ARRAY)
+    return 1;
+
+  return 0;
+}
+
+extern "C" EXPORT_API int bundle_keyval_type_is_measurable(
+    bundle_keyval_t* kv) {
+  int type = bundle_keyval_get_type(kv);
+  if (type == -1)
+    return -1;
+
+  set_last_result(BUNDLE_ERROR_NONE);
+  if (type & BUNDLE_TYPE_MEASURABLE)
+    return 1;
+
+  return 0;
+}
+
+extern "C" EXPORT_API int bundle_keyval_get_basic_val(bundle_keyval_t* kv,
+    void** val, size_t* size) {
+  if (kv == nullptr)
+    return BUNDLE_ERROR_INVALID_PARAMETER;
+
+  auto* key_info = reinterpret_cast<KeyInfo*>(kv);
+  if (key_info->IsArray())
+    return BUNDLE_ERROR_INVALID_PARAMETER;
+
+  if (val) {
+    auto& values = key_info->GetValues();
+    auto& value = const_cast<std::unique_ptr<unsigned char[]>&>(values[0]);
+    *val = reinterpret_cast<void*>(&value[0]);
+  }
+
+  if (size) {
+    auto& values_size = key_info->GetValuesSize();
+    *size = reinterpret_cast<size_t>(values_size[0]);
+  }
+
+  return BUNDLE_ERROR_NONE;
+}
+
+extern "C" EXPORT_API int bundle_keyval_get_array_val(bundle_keyval_t* kv,
+    void*** array_val, unsigned int* array_len, size_t** array_item_size) {
+  if (kv == nullptr)
+    return BUNDLE_ERROR_INVALID_PARAMETER;
+
+  auto* key_info = reinterpret_cast<KeyInfo*>(kv);
+  if (!key_info->IsArray())
+    return BUNDLE_ERROR_INVALID_PARAMETER;
+
+  auto& values = const_cast<std::vector<std::unique_ptr<unsigned char[]>>&>(
+      key_info->GetValues());
+
+  if (array_val)
+    *array_val = reinterpret_cast<void**>(&values[0]);
+
+  if (array_len)
+    *array_len = static_cast<unsigned int>(values.size());
+
+  if (array_item_size) {
+    auto& values_size = const_cast<std::vector<std::size_t>&>(
+      key_info->GetValuesSize());
+    *array_item_size = reinterpret_cast<size_t*>(&values_size[0]);
+  }
+
+  return BUNDLE_ERROR_NONE;
+}
+
+extern "C" EXPORT_API bundle_keyval_t* bundle_keyval_dup(
+    const bundle_keyval_t* kv) {
+  if (kv == nullptr) {
+    set_last_result(BUNDLE_ERROR_INVALID_PARAMETER);
+    return nullptr;
+  }
+
+  auto* keyval = const_cast<bundle_keyval_t*>(kv);
+  auto* key_info = reinterpret_cast<KeyInfo*>(keyval);
+
+  KeyInfo* k;
+  try {
+    k = new KeyInfo(*key_info);
+  } catch (const Exception& e) {
+    set_last_result(e.GetErrorCode());
+    return nullptr;
+  } catch (const std::bad_alloc& ba) {
+    set_last_result(BUNDLE_ERROR_OUT_OF_MEMORY);
+    return nullptr;
+  }
+
+  set_last_result(BUNDLE_ERROR_NONE);
+  return reinterpret_cast<bundle_keyval_t*>(k);
+}
+
+extern "C" EXPORT_API int bundle_keyval_free(bundle_keyval_t* kv) {
+  if (kv == nullptr)
+    return BUNDLE_ERROR_INVALID_PARAMETER;
+
+  auto* key_info = reinterpret_cast<KeyInfo*>(kv);
+  delete key_info;
+  return BUNDLE_ERROR_NONE;
+}
+
+extern "C" EXPORT_API bundle* bundle_dup(bundle* b_from) {
+  if (b_from == nullptr) {
+    set_last_result(BUNDLE_ERROR_INVALID_PARAMETER);
+    return nullptr;
+  }
+
+  Bundle* b;
+  try {
+    auto* h = reinterpret_cast<Bundle*>(b_from);
+    b = new Bundle(*h);
+  } catch (const Exception& e) {
+    set_last_result(e.GetErrorCode());
+    return nullptr;
+  } catch (const std::bad_alloc& e) {
+    set_last_result(BUNDLE_ERROR_OUT_OF_MEMORY);
+    return nullptr;
+  }
+
+  set_last_result(BUNDLE_ERROR_NONE);
+  return reinterpret_cast<bundle*>(b);
+}
+
+extern "C" EXPORT_API int bundle_encode(bundle *b, bundle_raw** raw, int* len) {
+  if (b == nullptr || raw == nullptr || len == nullptr)
+    return BUNDLE_ERROR_INVALID_PARAMETER;
+
+  auto* h = reinterpret_cast<Bundle*>(b);
+  try {
+    *raw = reinterpret_cast<bundle_raw*>(h->Encode());
+  } catch (const Exception& e) {
+    *raw = nullptr;
+    return e.GetErrorCode();
+  }
+
+  *len = strlen(reinterpret_cast<char*>(*raw));
+  return BUNDLE_ERROR_NONE;
+}
+
+extern "C" EXPORT_API int bundle_free_encoded_rawdata(bundle_raw **r) {
+  if (r == nullptr || *r == nullptr)
+    return BUNDLE_ERROR_INVALID_PARAMETER;
+
+  free(*r);
+  *r = nullptr;
+  return BUNDLE_ERROR_NONE;
+}
+
+extern "C" EXPORT_API bundle* bundle_decode(const bundle_raw* r,
+    const int data_size) {
+  if (r == nullptr) {
+    set_last_result(BUNDLE_ERROR_INVALID_PARAMETER);
+    return nullptr;
+  }
+
+  Bundle* b = nullptr;
+  try {
+    auto* raw = const_cast<bundle_raw*>(r);
+    b = new Bundle(static_cast<unsigned char*>(raw), data_size);
+  } catch (const Exception& e) {
+    set_last_result(e.GetErrorCode());
+    return nullptr;
+  } catch (const std::bad_alloc& ba) {
+    set_last_result(BUNDLE_ERROR_OUT_OF_MEMORY);
+    return nullptr;
+  }
+
+  set_last_result(BUNDLE_ERROR_NONE);
+  return reinterpret_cast<bundle*>(b);
+}
+
+extern "C" EXPORT_API int bundle_encode_raw(bundle* b, bundle_raw** r,
+    int* len) {
+  if (b == nullptr || r == nullptr || len == nullptr)
+    return BUNDLE_ERROR_INVALID_PARAMETER;
+
+  auto* h = reinterpret_cast<Bundle*>(b);
+  try {
+    *r = reinterpret_cast<bundle_raw*>(h->EncodeRaw(len));
+  } catch (const Exception& e) {
+    return e.GetErrorCode();
+  }
+  return BUNDLE_ERROR_NONE;
+}
+
+extern "C" EXPORT_API bundle* bundle_decode_raw(const bundle_raw* r,
+    const int data_size) {
+  if (r == nullptr) {
+    set_last_result(BUNDLE_ERROR_INVALID_PARAMETER);
+    return nullptr;
+  }
+
+  Bundle* b = nullptr;
+  try {
+    auto* raw = const_cast<bundle_raw*>(r);
+    b = new Bundle(static_cast<unsigned char*>(raw), data_size, false);
+  } catch (const Exception& e) {
+    set_last_result(e.GetErrorCode());
+    return nullptr;
+  } catch (const std::bad_alloc& ba) {
+    set_last_result(BUNDLE_ERROR_OUT_OF_MEMORY);
+    return nullptr;
+  }
+
+  set_last_result(BUNDLE_ERROR_NONE);
+  return reinterpret_cast<bundle*>(b);
+}
+
+extern "C" EXPORT_API int bundle_get_type(bundle* b, const char* key) {
+  if (b == nullptr || key == nullptr) {
+    set_last_result(BUNDLE_ERROR_INVALID_PARAMETER);
+    return BUNDLE_TYPE_NONE;
+  }
+
+  auto* h = reinterpret_cast<Bundle*>(b);
+  std::shared_ptr<KeyInfo> key_info;
+  try {
+    key_info = h->Get(key);
+  } catch (const Exception& e) {
+    set_last_result(e.GetErrorCode());
+    return BUNDLE_TYPE_NONE;
+  }
+
+  set_last_result(BUNDLE_ERROR_NONE);
+  return key_info->GetType();
+}
+
+extern "C" EXPORT_API int bundle_add_str_array(bundle* b, const char* key,
+    const char** str_array, const int len) {
+  if (b == nullptr || key == nullptr || strlen(key) == 0)
+    return BUNDLE_ERROR_INVALID_PARAMETER;
+
+  auto* h = reinterpret_cast<Bundle*>(b);
+  std::vector<std::vector<unsigned char>> values(len);
+  if (str_array) {
+    for (int i = 0; i < len; ++i) {
+      std::vector<unsigned char> value(str_array[i],
+          str_array[i] + (strlen(str_array[i]) + 1));
+      values[i] = std::move(value);
+    }
+  }
+
+  try {
+    auto key_info = std::make_shared<KeyInfo>(
+        (BUNDLE_TYPE_STR_ARRAY | BUNDLE_TYPE_ARRAY), key, values);
+    h->Add(std::move(key_info));
+  } catch (const Exception& e) {
+    return e.GetErrorCode();
+  } catch (const std::bad_alloc& ba) {
+    return BUNDLE_ERROR_OUT_OF_MEMORY;
+  }
+
+  return BUNDLE_ERROR_NONE;
+}
+
+extern "C" EXPORT_API const char** bundle_get_str_array(bundle* b,
+    const char* key, int* len) {
+  if (b == nullptr || key == nullptr) {
+    set_last_result(BUNDLE_ERROR_INVALID_PARAMETER);
+    return nullptr;
+  }
+
+  auto* h = reinterpret_cast<Bundle*>(b);
+  std::shared_ptr<KeyInfo> key_info;
+  try {
+    key_info = h->Get(key);
+  } catch (const Exception& e) {
+    set_last_result(e.GetErrorCode());
+    return nullptr;
+  }
+
+  if (key_info->GetType() != BUNDLE_TYPE_STR_ARRAY) {
+    set_last_result(BUNDLE_ERROR_INVALID_PARAMETER);
+    return nullptr;
+  }
+
+  set_last_result(BUNDLE_ERROR_NONE);
+
+  auto& raw_values = const_cast<std::vector<std::unique_ptr<unsigned char[]>>&>(
+      key_info->GetValues());
+
+  if (len)
+    *len = static_cast<int>(raw_values.size());
+
+  if (raw_values.size() == 0)
+    return nullptr;
+
+  auto** values = reinterpret_cast<unsigned char**>(&raw_values[0]);
+  return const_cast<const char**>(reinterpret_cast<char**>(values));
+}
+
+extern "C" EXPORT_API int bundle_add_byte(bundle* b, const char* key,
+    const void* bytes, const size_t size) {
+  if (b == nullptr || key == nullptr || strlen(key) == 0)
+    return BUNDLE_ERROR_INVALID_PARAMETER;
+
+  auto* h = reinterpret_cast<Bundle*>(b);
+  auto* p = reinterpret_cast<const unsigned char*>(bytes);
+  std::vector<unsigned char> value;
+  if (bytes)
+    value.insert(value.end(), p, p + size);
+
+  KeyInfo* key_info;
+  try {
+    key_info = new KeyInfo(BUNDLE_TYPE_BYTE, key, std::move(value));
+  } catch (const Exception& e) {
+    return e.GetErrorCode();
+  } catch (const std::bad_alloc& ba) {
+    return BUNDLE_ERROR_OUT_OF_MEMORY;
+  }
+
+  try {
+    h->Add(std::shared_ptr<KeyInfo>(key_info));
+  } catch (const Exception& e) {
+    return e.GetErrorCode();
+  }
+
+  return BUNDLE_ERROR_NONE;
+}
+
+extern "C" EXPORT_API int bundle_get_byte(bundle* b, const char* key,
+    void** bytes, size_t* size) {
+  if (b == nullptr || key == nullptr)
+    return BUNDLE_ERROR_INVALID_PARAMETER;
+
+  auto* h = reinterpret_cast<Bundle*>(b);
+  std::shared_ptr<KeyInfo> key_info;
+  try {
+    key_info = h->Get(key);
+  } catch (const Exception& e) {
+    return e.GetErrorCode();
+  }
+
+  if (key_info->GetType() != BUNDLE_TYPE_BYTE)
+    return BUNDLE_ERROR_INVALID_PARAMETER;
+
+  if (bytes) {
+    auto& values = const_cast<std::vector<std::unique_ptr<unsigned char[]>>&>(
+        key_info->GetValues());
+    if (values.size() == 0) {
+      *bytes = nullptr;
+    } else {
+      auto& value = values[0];
+      *bytes = reinterpret_cast<void*>(&value[0]);
+    }
+  }
+
+  if (size) {
+    auto& values_size = key_info->GetValuesSize();
+    *size = reinterpret_cast<size_t>(values_size[0]);
+  }
+
+  return BUNDLE_ERROR_NONE;
+}
+
+extern "C" EXPORT_API int bundle_export_to_argv(bundle* b, char*** argv) {
+  if (b == nullptr || argv == nullptr) {
+    set_last_result(BUNDLE_ERROR_INVALID_PARAMETER);
+    return -1;
+  }
+
+  auto* h = reinterpret_cast<Bundle*>(b);
+  std::vector<std::string> exported_vt;
+  try {
+    exported_vt = h->Export();
+  } catch (const Exception& e) {
+    set_last_result(e.GetErrorCode());
+    return -1;
+  }
+
+  int argc = exported_vt.size();
+  auto** exported_argv = reinterpret_cast<char**>(
+      calloc(argc + 1, sizeof(char*)));
+  if (exported_argv == nullptr) {
+    set_last_result(BUNDLE_ERROR_OUT_OF_MEMORY);
+    return -1;
+  }
+
+  exported_argv[1] = const_cast<char*>(TAG_IMPORT_EXPORT_CHECK);
+  for (unsigned int idx = 2; idx < exported_vt.size(); idx += 2) {
+    exported_argv[idx] = strdup(exported_vt[idx].c_str());
+    if (exported_argv[idx] == nullptr) {
+      set_last_result(BUNDLE_ERROR_OUT_OF_MEMORY);
+      bundle_free_exported_argv(idx + 1, &exported_argv);
+      return -1;
+    }
+
+    exported_argv[idx + 1] = strdup(exported_vt[idx + 1].c_str());
+    if (exported_argv[idx + 1] == nullptr) {
+      set_last_result(BUNDLE_ERROR_OUT_OF_MEMORY);
+      bundle_free_exported_argv(idx + 2, &exported_argv);
+      return -1;
+    }
+  }
+
+  *argv = exported_argv;
+  set_last_result(BUNDLE_ERROR_NONE);
+  return argc;
+}
+
+extern "C" EXPORT_API int bundle_free_exported_argv(int argc, char*** argv) {
+  if (argc < 2 || !argv || !*argv)
+    return BUNDLE_ERROR_INVALID_PARAMETER;
+
+  for (int i = 2; i < argc; i++)
+    std::free((*argv)[i]);
+
+  std::free(*argv);
+  *argv = nullptr;
+
+  return BUNDLE_ERROR_NONE;
+}
+
+extern "C" EXPORT_API bundle* bundle_import_from_argv(int argc, char** argv) {
+  if (argv == nullptr) {
+    set_last_result(BUNDLE_ERROR_INVALID_PARAMETER);
+    return nullptr;
+  }
+
+  Bundle* b = nullptr;
+  try {
+    b = new (std::nothrow) Bundle(argc, argv);
+  } catch (const Exception& e) {
+    set_last_result(e.GetErrorCode());
+    return nullptr;
+  }
+
+  set_last_result(BUNDLE_ERROR_NONE);
+  return reinterpret_cast<bundle*>(b);
+}
+
+extern "C" EXPORT_API int bundle_compare(bundle* b1, bundle* b2) {
+  if (b1 == nullptr || b2 == nullptr)
+    return -1;
+
+  auto* h1 = reinterpret_cast<Bundle*>(b1);
+  auto* h2 = reinterpret_cast<Bundle*>(b2);
+  if (*h1 == *h2)
+    return 0;
+
+  return 1;
+}
+
+extern "C" EXPORT_API int bundle_set_str_array_element(bundle* b,
+    const char* key, const unsigned int idx, const char* val) {
+  if (b == nullptr || key == nullptr || val == nullptr)
+    return BUNDLE_ERROR_INVALID_PARAMETER;
+
+  auto len = strlen(val) + 1;
+  auto* p = reinterpret_cast<unsigned char*>(const_cast<char*>(val));
+  std::vector<unsigned char> value(p, p + len);
+
+  auto* h = reinterpret_cast<Bundle*>(b);
+  try {
+    h->Set(key, idx, std::move(value));
+  } catch (const Exception& e) {
+    return e.GetErrorCode();
+  }
+
+  return BUNDLE_ERROR_NONE;
+}
+
+extern "C" EXPORT_API int bundle_add_byte_array(bundle* b,
+    const char* key, const unsigned int len) {
+  return bundle_init_byte_array(b, key, len);
+}
+
+extern "C" EXPORT_API int bundle_init_byte_array(bundle* b,
+    const char* key, const unsigned int len) {
+  if (b == nullptr || key == nullptr || strlen(key) == 0)
+    return BUNDLE_ERROR_INVALID_PARAMETER;
+
+  auto* h = reinterpret_cast<Bundle*>(b);
+
+  KeyInfo* key_info;
+  try {
+    std::vector<std::vector<unsigned char>> values(len);
+    key_info = new KeyInfo(Bundle::Type::ByteArray, key, std::move(values));
+  } catch (const Exception& e) {
+    return e.GetErrorCode();
+  } catch (const std::bad_alloc& ba) {
+    return BUNDLE_ERROR_OUT_OF_MEMORY;
+  } catch (const std::length_error&) {
+    return BUNDLE_ERROR_OUT_OF_MEMORY;
+  }
+
+  try {
+    h->Add(std::shared_ptr<KeyInfo>(key_info));
+  } catch (const Exception& e) {
+    return e.GetErrorCode();
+  }
+
+  return BUNDLE_ERROR_NONE;
+}
+
+extern "C" EXPORT_API int bundle_get_byte_array(bundle* b,
+    const char* key, void*** bytes_array, unsigned int* len,
+    unsigned int** array_element_size) {
+  if (b == nullptr || key == nullptr)
+    return BUNDLE_ERROR_INVALID_PARAMETER;
+
+  auto* h = reinterpret_cast<Bundle*>(b);
+  std::shared_ptr<KeyInfo> key_info;
+  try {
+    key_info = h->Get(key);
+  } catch (const Exception& e) {
+    return e.GetErrorCode();
+  }
+
+  if (key_info->GetType() != BUNDLE_TYPE_BYTE_ARRAY)
+    return BUNDLE_ERROR_INVALID_PARAMETER;
+
+  auto& raw_values = const_cast<std::vector<std::unique_ptr<unsigned char[]>>&>(
+      key_info->GetValues());
+
+  if (bytes_array) {
+    auto** values = reinterpret_cast<unsigned char**>(&raw_values[0]);
+    *bytes_array = reinterpret_cast<void**>(values);
+  }
+
+  if (len)
+    *len = static_cast<unsigned int>(raw_values.size());
+
+  if (array_element_size) {
+    auto& raw_values_size = const_cast<std::vector<unsigned int>&>(
+        key_info->GetUValuesSize());
+    *array_element_size = reinterpret_cast<unsigned int*>(&raw_values_size[0]);
+  }
+
+  return BUNDLE_ERROR_NONE;
+}
+
+extern "C" EXPORT_API int bundle_set_byte_array_element(bundle* b,
+    const char* key, const unsigned int idx,
+    const void* bytes, const size_t size) {
+  if (b == nullptr || key == nullptr || size <= 0)
+    return BUNDLE_ERROR_INVALID_PARAMETER;
+
+  std::vector<unsigned char> value;
+  if (bytes) {
+    auto* p = reinterpret_cast<unsigned char*>(const_cast<void*>(bytes));
+    value.insert(value.end(), p, p + size);
+  }
+
+  auto* h = reinterpret_cast<Bundle*>(b);
+  try {
+    h->Set(key, idx, std::move(value));
+  } catch (const Exception& e) {
+    return e.GetErrorCode();
+  }
+
+  return BUNDLE_ERROR_NONE;
+}
+
+extern "C" EXPORT_API int bundle_to_json(bundle* b, char** json) {
+  if (b == nullptr || json == nullptr)
+    return BUNDLE_ERROR_INVALID_PARAMETER;
+
+  auto* h = reinterpret_cast<Bundle*>(b);
+  Json js(h);
+  try {
+    *json = strdup(js.ToString().c_str());
+  } catch (const Exception& e) {
+    return e.GetErrorCode();
+  }
+
+  return BUNDLE_ERROR_NONE;
+}
+
+extern "C" EXPORT_API int bundle_from_json(const char* json, bundle** b) {
+  if (json == nullptr || b == nullptr)
+    return BUNDLE_ERROR_INVALID_PARAMETER;
+
+  Json js(json);
+  try {
+    *b = reinterpret_cast<bundle*>(js.ToBundle());
+  } catch (const Exception& e) {
+    return e.GetErrorCode();
+  }
+
+  return BUNDLE_ERROR_NONE;
+}
diff --git a/src/bundle_cpp.cc b/src/bundle_cpp.cc
deleted file mode 100644 (file)
index c45f405..0000000
+++ /dev/null
@@ -1,350 +0,0 @@
-/*
- * Copyright (c) 2019 - 2020 Samsung Electronics Co., Ltd.
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#include <memory>
-#include <stdexcept>
-
-#include "bundle_cpp.h"
-#include "bundle_cpp_implementation.h"
-#include "bundle_internal.h"
-#include "log-private.h"
-
-namespace tizen_base {
-Bundle::Impl::Impl(Bundle* parent, bool copy, bool own)
-  : copy_(copy), own_(own), parent_(parent) {
-}
-
-Bundle::Impl::Impl(Bundle* parent) : parent_(parent) {
-}
-
-Bundle::Impl::~Impl() = default;
-
-Bundle::Bundle()
-  : impl_(new Impl(this)) {
-  impl_->handle_ = bundle_create();
-  if (impl_->handle_ == nullptr)
-    throw std::bad_alloc();
-}
-
-Bundle::Bundle(std::initializer_list<
-    std::pair<std::string, std::string>> key_values)
-  : impl_(new Impl(this)) {
-  impl_->handle_ = bundle_create();
-  if (impl_->handle_ == nullptr)
-    throw std::bad_alloc();
-  for (auto& i : key_values)
-    Add(i.first, i.second);
-}
-
-Bundle::Bundle(BundleRaw raw, bool base64)
-  : impl_(new Impl(this)) {
-  if (base64)
-    impl_->handle_ = bundle_decode(raw.first.get(), raw.second);
-  else
-    impl_->handle_ = bundle_decode_raw(raw.first.get(), raw.second);
-  if (impl_->handle_ == nullptr)
-    throw std::bad_alloc();
-}
-
-Bundle::Bundle(const std::string& raw)
-  : impl_(new Impl(this)) {
-  impl_->handle_ = bundle_decode(reinterpret_cast<const bundle_raw*>(
-      raw.c_str()), raw.length());
-  if (impl_->handle_ == nullptr)
-    throw std::bad_alloc();
-}
-
-Bundle::Bundle(bundle* b, bool copy, bool own)
-  : impl_(new Impl(this, copy, own)) {
-  if (b == nullptr)
-    throw std::invalid_argument("b cannot be null");
-
-  if (!impl_->copy_) {
-    impl_->handle_ = b;
-  } else {
-    impl_->handle_ = bundle_dup(b);
-    if (impl_->handle_ == nullptr)
-      throw std::bad_alloc();
-  }
-}
-
-Bundle::~Bundle() {
-  if (impl_ && impl_->handle_ && (impl_->own_ || impl_->copy_))
-    bundle_free(impl_->handle_);
-}
-
-Bundle::Bundle(const Bundle& b)
-  : impl_(new Impl(this)) {
-  impl_->handle_ = bundle_dup(b.impl_->handle_);
-  if (impl_->handle_ == nullptr)
-    throw std::bad_alloc();
-}
-
-Bundle::KeyInfo::KeyInfo(const bundle_keyval_t* handle, std::string name,
-                         bool own)
-  : impl_(new Impl(this, handle, std::move(name), own)) {
-}
-
-Bundle::KeyInfo::~KeyInfo() {
-  if (impl_ && impl_->handle_ && impl_->own_)
-    bundle_keyval_free(const_cast<bundle_keyval_t*>(impl_->handle_));
-}
-
-Bundle::KeyInfo::Impl::~Impl() = default;
-
-Bundle::KeyInfo::Impl::Impl(Bundle::KeyInfo* parent,
-                            const bundle_keyval_t* handle,
-                            std::string name,
-                            bool own)
-  : handle_(handle), name_(name), parent_(parent), own_(own) {
-}
-
-Bundle::KeyInfo::Impl::Impl(Bundle::KeyInfo* parent) : parent_(parent) {
-}
-
-Bundle::KeyInfo::KeyInfo(const KeyInfo& k)
-    : impl_(new Impl(this)) {
-  impl_->handle_ = bundle_keyval_dup(k.impl_->handle_);
-  impl_->name_ = k.impl_->name_;
-  impl_->own_ = true;
-  if (impl_->handle_ == nullptr)
-    throw std::bad_alloc();
-}
-
-Bundle::KeyInfo& Bundle::KeyInfo::operator = (const Bundle::KeyInfo& k) {
-  if (this != &k) {
-    if (impl_->handle_ && impl_->own_)
-      bundle_keyval_free(const_cast<bundle_keyval_t*>(impl_->handle_));
-
-    impl_->handle_ = bundle_keyval_dup(k.impl_->handle_);
-    impl_->name_ = k.impl_->name_;
-    if (impl_->handle_ == nullptr)
-      throw std::bad_alloc();
-
-    impl_->own_ = true;
-  }
-  return *this;
-}
-
-Bundle::KeyInfo::KeyInfo(Bundle::KeyInfo&& k) noexcept {
-  impl_ = std::move(k.impl_);
-  impl_->parent_ = this;
-}
-
-Bundle::KeyInfo& Bundle::KeyInfo::operator = (Bundle::KeyInfo&& k) noexcept {
-  if (this != &k) {
-    if (impl_->handle_ && impl_->own_)
-      bundle_keyval_free(const_cast<bundle_keyval_t*>(impl_->handle_));
-
-    impl_->handle_ = k.impl_->handle_;
-    impl_->name_ = k.impl_->name_;
-    impl_->own_ = k.impl_->own_;
-    k.impl_->handle_ = nullptr;
-    k.impl_->name_ = "";
-    k.impl_->own_ = false;
-  }
-  return *this;
-}
-
-bundle_type Bundle::KeyInfo::GetType() const {
-  return static_cast<bundle_type>(
-      bundle_keyval_get_type(const_cast<bundle_keyval_t*>(impl_->handle_)));
-}
-
-bool Bundle::KeyInfo::IsArray() const {
-  return bundle_keyval_type_is_array(const_cast<bundle_keyval_t*>(
-      impl_->handle_));
-}
-
-const std::string& Bundle::KeyInfo::GetName() const {
-  return impl_->name_;
-}
-
-Bundle& Bundle::operator = (const Bundle& b) {
-  if (this != &b) {
-    if (impl_->handle_ && (impl_->own_ || impl_->copy_))
-      bundle_free(impl_->handle_);
-
-    impl_->handle_ = bundle_dup(b.impl_->handle_);
-    if (impl_->handle_ == nullptr)
-      throw std::bad_alloc();
-
-    impl_->own_ = true;
-    impl_->copy_ = true;
-  }
-  return *this;
-}
-
-Bundle::Bundle(Bundle&& b) noexcept {
-  impl_ = std::move(b.impl_);
-  impl_->parent_ = this;
-  b.impl_.reset(new Impl(&b));
-  b.impl_->handle_ = bundle_create();
-}
-
-Bundle& Bundle::operator = (Bundle&& b) noexcept {
-  if (this != &b) {
-    if (impl_->handle_ && (impl_->own_ || impl_->copy_))
-      bundle_free(impl_->handle_);
-
-    impl_->handle_ = b.impl_->handle_;
-    b.impl_->handle_ = nullptr;
-    impl_->own_ = b.impl_->own_;
-    b.impl_->own_ = false;
-    impl_->copy_ = b.impl_->copy_;
-    b.impl_->copy_ = false;
-  }
-  return *this;
-}
-
-bool Bundle::IsEmpty() const noexcept {
-  return (bundle_get_count(impl_->handle_) == 0) ? true : false;
-}
-
-std::vector<Bundle::KeyInfo> Bundle::GetKeys() {
-  std::vector<Bundle::KeyInfo> v;
-
-  bundle_foreach(impl_->handle_, [](const char *key, const int type,
-      const bundle_keyval_t *kv, void *user_data) {
-        auto* v = static_cast<std::vector<KeyInfo>*>(user_data);
-        v->emplace_back(kv, key, false);
-      }, &v);
-
-  return v;
-}
-
-int Bundle::Add(const std::string& key, const std::string& val) {
-  int ret = bundle_add_str(impl_->handle_, key.c_str(), val.c_str());
-  if (ret != BUNDLE_ERROR_NONE)
-    LOGE("Add fail key(%s), val(%s), ret(%d)", key.c_str(), val.c_str(), ret);
-  return ret;
-}
-
-int Bundle::Add(const std::string& key, const std::vector<std::string>& val) {
-  std::vector<const char*> v;
-  for (auto& i : val) {
-    v.push_back(i.c_str());
-  }
-
-  int ret = bundle_add_str_array(
-    impl_->handle_, key.c_str(), v.data(), v.size());
-  if (ret != BUNDLE_ERROR_NONE)
-    LOGE("Add fail key(%s), ret(%d)", key.c_str(), ret);
-
-  return ret;
-}
-
-int Bundle::Add(const std::string& key, const std::vector<unsigned char>& val) {
-  int ret = bundle_add_byte(impl_->handle_, key.c_str(), val.data(), val.size());
-  if (ret != BUNDLE_ERROR_NONE)
-    LOGE("Add fail key(%s), ret(%d)", key.c_str(), ret);
-  return ret;
-}
-
-int Bundle::Delete(const std::string& key) {
-  return bundle_del(impl_->handle_, key.c_str());
-}
-
-std::string Bundle::GetString(const std::string& key) const {
-  char* str = nullptr;
-  bundle_get_str(impl_->handle_, key.c_str(), &str);
-
-  if (!str)
-    return "";
-
-  return std::string(str);
-}
-
-std::vector<std::string> Bundle::GetStringArray(const std::string& key) const {
-  std::vector<std::string> v;
-
-  const char** str_array = nullptr;
-  int len = 0;
-
-  str_array = bundle_get_str_array(impl_->handle_, key.c_str(), &len);
-
-  for (int i = 0; i < len; i++) {
-    v.emplace_back(str_array[i]);
-  }
-
-  return v;
-}
-
-std::vector<unsigned char> Bundle::GetByte(const std::string& key) const {
-  size_t size;
-  unsigned char* bytes = nullptr;
-  int ret = bundle_get_byte(impl_->handle_, key.c_str(),
-      reinterpret_cast<void**>(&bytes), &size);
-  if (ret != BUNDLE_ERROR_NONE) {
-    LOGE("bundle_get_byte() is failed");
-    return {};
-  }
-
-  return std::vector<unsigned char>(bytes, bytes + size);
-}
-
-Bundle::BundleRaw Bundle::ToRaw(bool base64) {
-  bundle_raw* raw = nullptr;
-  int len = 0;
-  int ret;
-  if (base64)
-    ret = bundle_encode(impl_->handle_, &raw, &len);
-  else
-    ret = bundle_encode_raw(impl_->handle_, &raw, &len);
-  if (raw == nullptr) {
-    LOGE("Fail to encode data (%d)", ret);
-    throw std::bad_alloc();
-  }
-
-  return BundleRaw(
-      std::unique_ptr<bundle_raw, decltype(std::free)*>(raw, std::free), len);
-}
-
-int Bundle::GetCount() const {
-  return bundle_get_count(impl_->handle_);
-}
-
-bundle_type Bundle::GetType(const std::string& key) const {
-  return static_cast<bundle_type>(bundle_get_type(impl_->handle_, key.c_str()));
-}
-
-bundle* Bundle::GetHandle() const {
-  return impl_->handle_;
-}
-
-bundle* Bundle::Detach() {
-  auto* h = impl_->handle_;
-  impl_->handle_ = nullptr;
-  return h;
-}
-
-std::vector<std::string> Bundle::Export() const {
-  char** argv = nullptr;
-  int argc = bundle_export_to_argv(impl_->handle_, &argv);
-  if (argc < 0) {
-    LOGE("bundle_export_to_argv() is failed");
-    return {};
-  }
-
-  std::vector<std::string> args(1);
-  for (int i = 1; i < argc; ++i)
-    args.push_back(argv[i]);
-
-  bundle_free_exported_argv(argc, &argv);
-  return args;
-}
-
-}  // namespace tizen_base
diff --git a/src/bundle_cpp_implementation.h b/src/bundle_cpp_implementation.h
deleted file mode 100644 (file)
index bf7c38c..0000000
+++ /dev/null
@@ -1,66 +0,0 @@
-/*
- * Copyright (c) 2019 - 2020 Samsung Electronics Co., Ltd.
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#ifndef BUNDLE_CPP_IMPLEMENTATION_H_
-#define BUNDLE_CPP_IMPLEMENTATION_H_
-
-#include <string>
-#include <memory>
-#include <list>
-
-#include "include/bundle_cpp.h"
-
-namespace tizen_base {
-
-class Bundle::KeyInfo::Impl {
- public:
-  virtual ~Impl();
-
- private:
-  Impl(Bundle::KeyInfo* parent, const bundle_keyval_t* handle,
-       std::string name, bool own);
-  explicit Impl(Bundle::KeyInfo* parent);
-
- private:
-  friend class Bundle::KeyInfo;
-
- private:
-  const bundle_keyval_t* handle_ = nullptr;
-  std::string name_;
-  Bundle::KeyInfo* parent_;
-  bool own_ = false;
-};
-
-class Bundle::Impl {
- public:
-  virtual ~Impl();
-
- private:
-  explicit Impl(Bundle* parent);
-  Impl(Bundle* parent, bool copy, bool own);
-
- private:
-  friend class Bundle;
-
-  bundle* handle_ = nullptr;
-  bool copy_ = true;
-  bool own_ = true;
-  Bundle* parent_ = nullptr;
-};
-
-}  // namespace tizen_base
-
-#endif  // BUNDLE_CPP_IMPLEMENTATION_H_
diff --git a/src/exception-internal.h b/src/exception-internal.h
deleted file mode 100644 (file)
index 4ce8690..0000000
+++ /dev/null
@@ -1,57 +0,0 @@
-/*
- * Copyright (c) 2020 Samsung Electronics Co., Ltd.
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#ifndef EXCEPTION_INTERNAL_H_
-#define EXCEPTION_INTERNAL_H_
-
-#include <string>
-#include <exception>
-
-#include "log-private.h"
-
-#define THROW(error_code) throw Exception(error_code)
-
-namespace tizen_base {
-namespace internal {
-
-class Exception : public std::exception {
- public:
-  explicit Exception(int error_code, std::string file = __FILE__,
-      int line = __LINE__ ) {
-    error_code_ = error_code;
-    message_ = file.substr(file.find_last_of("/") + 1) + ":"
-        + std::to_string(line) + " code:" + std::to_string(error_code_);
-  }
-
-  virtual ~Exception() {}
-
-  virtual const char *what(void) const noexcept {
-    return message_.c_str();
-  }
-
-  int GetErrorCode() const {
-    return error_code_;
-  }
-
- private:
-  int error_code_;
-  std::string message_;
-};
-
-}  // namespace internal
-}  // namespace tizen_base
-
-#endif  // EXCEPTION_INTERNAL_H_
diff --git a/src/export-api-internal.h b/src/export-api-internal.h
deleted file mode 100644 (file)
index cd0299d..0000000
+++ /dev/null
@@ -1,24 +0,0 @@
-/*
- * Copyright (c) 2020 Samsung Electronics Co., Ltd All Rights Reserved
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#ifndef EXPORT_API_INTERNAL_H_
-#define EXPORT_API_INTERNAL_H_
-
-#ifndef EXPORT_API
-#define EXPORT_API __attribute__((visibility("default")))
-#endif
-
-#endif  // EXPORT_API_INTERNAL_H_
diff --git a/src/json-internal.cc b/src/json-internal.cc
deleted file mode 100644 (file)
index 882af4c..0000000
+++ /dev/null
@@ -1,183 +0,0 @@
-/*
- * Copyright (c) 2020 Samsung Electronics Co., Ltd. All rights reserved.
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#include "exception-internal.h"
-#include "json-internal.h"
-
-namespace tizen_base {
-namespace internal {
-
-Json::Json(std::string json) : json_(std::move(json)) {
-}
-
-Json::Json(Bundle* b) : b_(b) {
-}
-
-Bundle* Json::ToBundle() {
-  if (json_.empty())
-    return nullptr;
-
-  JsonParser* parser = json_parser_new();
-  if (parser == nullptr)
-    THROW(BUNDLE_ERROR_OUT_OF_MEMORY);
-
-  std::unique_ptr<JsonParser, decltype(g_object_unref)*> parser_ptr(parser,
-      g_object_unref);
-
-  GError* error = nullptr;
-  json_parser_load_from_data(parser, json_.c_str(), json_.length(), &error);
-  if (error) {
-    g_error_free(error);
-    THROW(BUNDLE_ERROR_INVALID_PARAMETER);
-  }
-
-  JsonNode* root = json_parser_get_root(parser);
-  if (root == nullptr)
-    THROW(BUNDLE_ERROR_INVALID_PARAMETER);
-
-  JsonObject* root_obj = json_node_get_object(root);
-  if (root_obj == nullptr)
-    THROW(BUNDLE_ERROR_INVALID_PARAMETER);
-
-  Bundle* b = new (std::nothrow) Bundle();
-  if (b == nullptr)
-    THROW(BUNDLE_ERROR_OUT_OF_MEMORY);
-
-  json_object_foreach_member(root_obj, OnJsonObjectMember, b);
-
-  return b;
-}
-
-std::string Json::ToString() {
-  if (b_ == nullptr)
-    THROW(BUNDLE_ERROR_INVALID_PARAMETER);
-
-  JsonObject* object = json_object_new();
-  if (object == nullptr)
-    THROW(BUNDLE_ERROR_OUT_OF_MEMORY);
-
-  std::unique_ptr<JsonObject, decltype(json_object_unref)*> object_ptr(object,
-      json_object_unref);
-
-  for (const auto& kv : b_->GetMap()) {
-    auto& key_info = kv.second;
-    if (key_info->GetType() == Bundle::Type::StringArray) {
-      JsonArray* json_arr = json_array_new();
-      if (json_arr == nullptr)
-        THROW(BUNDLE_ERROR_OUT_OF_MEMORY);
-
-      for (const auto& v : key_info->GetValues()) {
-        json_array_add_string_element(json_arr,
-            const_cast<const char*>(reinterpret_cast<char*>(v.get())));
-      }
-
-      json_object_set_array_member(object, key_info->GetKey().c_str(),
-          json_arr);
-    } else {
-      json_object_set_string_member(object, key_info->GetKey().c_str(),
-          const_cast<const char*>(
-            reinterpret_cast<char*>(
-              key_info->GetValues()[0].get())));
-    }
-  }
-
-  JsonNode* node = json_node_new(JSON_NODE_OBJECT);
-  if (node == nullptr)
-    THROW(BUNDLE_ERROR_OUT_OF_MEMORY);
-
-  std::unique_ptr<JsonNode, decltype(json_node_free)*> node_ptr(node,
-      json_node_free);
-
-  json_node_set_object(node, object);
-
-  JsonGenerator* generator = json_generator_new();
-  if (generator == nullptr)
-    THROW(BUNDLE_ERROR_OUT_OF_MEMORY);
-
-  std::unique_ptr<JsonGenerator, decltype(g_object_unref)*> generator_ptr(
-      generator, g_object_unref);
-
-  json_generator_set_root(generator, node);
-  gsize length = 0;
-  gchar* json = json_generator_to_data(generator, &length);
-  if (json == nullptr)
-    THROW(BUNDLE_ERROR_OUT_OF_MEMORY);
-
-  std::unique_ptr<gchar, decltype(g_free)*> json_auto(json, g_free);
-  json_ = json;
-  return json_;
-}
-
-void Json::OnJsonObjectMember(JsonObject* object, const char* key,
-  JsonNode* node, gpointer user_data) {
-  auto* b = static_cast<Bundle*>(user_data);
-  KeyInfo* key_info;
-  JsonNodeType node_type = JSON_NODE_TYPE(node);
-  if (node_type == JSON_NODE_ARRAY) {
-    JsonArray* json_arr = json_node_get_array(node);
-    if (json_arr == nullptr)
-      return;
-
-    std::vector<std::vector<unsigned char>> values;
-    guint len = json_array_get_length(json_arr);
-    for (guint i = 0; i < len; ++i) {
-      auto* val = json_array_get_string_element(json_arr, i);
-      if (val == nullptr)
-        val = "";
-
-      auto* p = reinterpret_cast<unsigned char*>(const_cast<char*>(val));
-      std::vector<unsigned char> value(p, p + (strlen(val) + 1));
-      values.push_back(std::move(value));
-    }
-
-    try {
-      key_info = new KeyInfo(Bundle::Type::StringArray, key, std::move(values));
-    } catch (const Exception& e) {
-      _E("Error(%d)", e.GetErrorCode());
-      return;
-    } catch (const std::bad_alloc& ba) {
-      _E("bad alloc exception");
-      return;
-    }
-  } else {
-    auto* val = json_node_get_string(node);
-    if (val == nullptr)
-      val = "";
-
-    auto* p = reinterpret_cast<unsigned char*>(const_cast<char*>(val));
-    std::vector<unsigned char> value(p, p + (strlen(val) + 1));
-
-    try {
-      key_info = new KeyInfo(Bundle::Type::String, key, std::move(value));
-    } catch (const Exception& e) {
-      _E("Error(%d)", e.GetErrorCode());
-      return;
-    } catch (const std::bad_alloc& ba) {
-      _E("bad alloc exception");
-      return;
-    }
-  }
-
-  try {
-    b->Add(std::shared_ptr<KeyInfo>(key_info));
-  } catch (const Exception& e) {
-    _W("Add() is failed. error(%d)", e.GetErrorCode());
-    return;
-  }
-}
-
-}  // namespace internal
-}  // namespace tizen_base
diff --git a/src/json-internal.h b/src/json-internal.h
deleted file mode 100644 (file)
index a1f175a..0000000
+++ /dev/null
@@ -1,52 +0,0 @@
-/*
- * Copyright (c) 2020 Samsung Electronics Co., Ltd. All rights reserved.
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#ifndef JSON_INTERNAL_H_
-#define JSON_INTERNAL_H_
-
-#include <glib.h>
-#include <json-glib/json-glib.h>
-
-#include <memory>
-#include <string>
-
-#include "bundle-internal.h"
-
-namespace tizen_base {
-namespace internal {
-
-class Json {
- public:
-  explicit Json(std::string json);
-  explicit Json(Bundle* b);
-  virtual ~Json() = default;
-
-  Bundle* ToBundle();
-  std::string ToString();
-
- private:
-  static void OnJsonObjectMember(JsonObject* object, const char* key,
-      JsonNode* node, gpointer user_data);
-
- private:
-  Bundle* b_ = nullptr;
-  std::string json_;
-};
-
-}  // namespace internal
-}  // namespace tizen_base
-
-#endif  // JSON_INTERNAL_H_
diff --git a/src/key-info-internal.cc b/src/key-info-internal.cc
deleted file mode 100644 (file)
index e5d0b03..0000000
+++ /dev/null
@@ -1,400 +0,0 @@
-/*
- * Copyright (c) 2020 Samsung Electronics Co., Ltd. All rights reserved.
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#include <algorithm>
-#include <cstring>
-#include <utility>
-
-#include "include/bundle.h"
-
-#include "exception-internal.h"
-#include "key-info-internal.h"
-
-namespace tizen_base {
-namespace internal {
-
-KeyInfo::KeyInfo(int type, std::string key, std::vector<unsigned char> value)
-    : type_(type), key_(std::move(key)) {
-  int ret = SetValue(value);
-  if (ret != BUNDLE_ERROR_NONE)
-    THROW(ret);
-}
-
-KeyInfo::KeyInfo(int type, std::string key,
-    std::vector<std::vector<unsigned char>> values)
-    : type_(type), key_(std::move(key)) {
-  int ret = SetValues(values);
-  if (ret != BUNDLE_ERROR_NONE)
-    THROW(ret);
-}
-
-KeyInfo::KeyInfo(std::vector<unsigned char> encoded_bytes) {
-  int ret = Decode(encoded_bytes);
-  if (ret != BUNDLE_ERROR_NONE)
-    THROW(ret);
-}
-
-KeyInfo::KeyInfo(const KeyInfo& key_info) {
-  values_.reserve(key_info.values_.size());
-  try {
-    for (unsigned int i = 0; i < key_info.values_.size(); ++i) {
-      auto new_value =
-          std::make_unique<unsigned char[]>(key_info.values_size_[i]);
-      std::copy(key_info.values_[i].get(),
-          key_info.values_[i].get() + key_info.values_size_[i],
-          new_value.get());
-      values_.push_back(std::move(new_value));
-    }
-  } catch (const std::bad_alloc& e) {
-    THROW(BUNDLE_ERROR_OUT_OF_MEMORY);
-  }
-
-  type_ = key_info.type_;
-  key_ = key_info.key_;
-  values_size_ = key_info.values_size_;
-  uvalues_size_ = key_info.uvalues_size_;
-}
-
-KeyInfo& KeyInfo::operator=(const KeyInfo& key_info) {
-  if (this != &key_info) {
-    decltype(values_) new_values;
-    try {
-      for (unsigned int i = 0; i < key_info.values_.size(); ++i) {
-        auto new_value =
-            std::make_unique<unsigned char[]>(key_info.values_size_[i]);
-        std::copy(key_info.values_[i].get(),
-            key_info.values_[i].get() + key_info.values_size_[i],
-            new_value.get());
-        new_values.push_back(std::move(new_value));
-      }
-    } catch (const std::bad_alloc& e) {
-      THROW(BUNDLE_ERROR_OUT_OF_MEMORY);
-    }
-
-    type_ = key_info.type_;
-    key_ = key_info.key_;
-    values_size_ = key_info.values_size_;
-    uvalues_size_ = key_info.uvalues_size_;
-    values_ = std::move(new_values);
-  }
-
-  return *this;
-}
-
-KeyInfo::KeyInfo(KeyInfo&& key_info) noexcept {
-  type_ = key_info.type_;
-  key_info.type_ = 0;
-  key_ = std::move(key_info.key_);
-  values_ = std::move(key_info.values_);
-  values_size_ = std::move(key_info.values_size_);
-  uvalues_size_ = std::move(key_info.uvalues_size_);
-}
-
-KeyInfo& KeyInfo::operator=(KeyInfo&& key_info) noexcept {
-  if (this != &key_info) {
-    type_ = key_info.type_;
-    key_info.type_ = 0;
-    key_ = std::move(key_info.key_);
-    values_ = std::move(key_info.values_);
-    values_size_ = std::move(key_info.values_size_);
-    uvalues_size_ = std::move(key_info.uvalues_size_);
-  }
-  return *this;
-}
-
-bool KeyInfo::operator==(const KeyInfo& key_info) {
-  if (this == &key_info)
-    return true;
-
-  if (type_ != key_info.type_)
-    return false;
-
-  if (key_ != key_info.key_)
-    return false;
-
-  if (values_.size() != key_info.values_.size())
-    return false;
-
-  for (unsigned int i = 0; i < values_.size(); ++i) {
-    if (values_size_[i] != key_info.values_size_[i])
-      return false;
-
-    int ret = std::memcmp(values_[i].get(), key_info.values_[i].get(),
-        values_size_[i]);
-    if (ret != 0)
-      return false;
-  }
-
-  return true;
-}
-
-int KeyInfo::GetType() const {
-  return type_;
-}
-
-bool KeyInfo::IsArray() const {
-  if (type_ & BUNDLE_TYPE_ARRAY)
-    return true;
-
-  return false;
-}
-
-const std::string& KeyInfo::GetKey() {
-  return key_;
-}
-
-const std::vector<std::unique_ptr<unsigned char[]>>& KeyInfo::GetValues() {
-  return values_;
-}
-
-const std::vector<std::size_t>& KeyInfo::GetValuesSize() {
-  return values_size_;
-}
-
-const std::vector<unsigned int>& KeyInfo::GetUValuesSize() {
-  return uvalues_size_;
-}
-
-int KeyInfo::SetValue(const std::vector<unsigned char>& value) {
-  try {
-    auto new_value = std::make_unique<unsigned char[]>(value.size());
-    std::copy(value.begin(), value.end(), new_value.get());
-    values_.emplace_back(std::move(new_value));
-  } catch (const std::bad_alloc& e) {
-    return BUNDLE_ERROR_OUT_OF_MEMORY;
-  }
-
-  values_size_.push_back(value.size());
-  uvalues_size_.push_back(static_cast<unsigned int>(value.size()));
-  return BUNDLE_ERROR_NONE;
-}
-
-int KeyInfo::SetValues(const std::vector<std::vector<unsigned char>>& values) {
-  try {
-    for (unsigned int i = 0; i < values.size(); ++i) {
-      auto new_value = std::make_unique<unsigned char[]>(values[i].size());
-      std::copy(values[i].begin(), values[i].end(), new_value.get());
-      values_.push_back(std::move(new_value));
-      values_size_.push_back(values[i].size());
-      uvalues_size_.push_back(values[i].size());
-    }
-  } catch (const std::bad_alloc& e) {
-    return BUNDLE_ERROR_OUT_OF_MEMORY;
-  }
-
-  return BUNDLE_ERROR_NONE;
-}
-
-std::vector<unsigned char> KeyInfo::Encode() {
-  std::size_t encoded_size = GetEncodedSize();
-  if (encoded_size == 0)
-    return {};
-
-  std::vector<unsigned char> bytes;
-
-  // total size
-  unsigned char* p = reinterpret_cast<unsigned char*>(&encoded_size);
-  bytes.insert(bytes.end(), p, p + sizeof(encoded_size));
-
-  // type
-  p = reinterpret_cast<unsigned char*>(&type_);
-  bytes.insert(bytes.end(), p, p + sizeof(type_));
-
-  // key size
-  std::size_t key_length = key_.length() + 1;
-  p = reinterpret_cast<unsigned char*>(&key_length);
-  bytes.insert(bytes.end(), p, p + sizeof(key_length));
-
-  // key
-  bytes.insert(bytes.end(), key_.begin(), key_.end() + 1);
-
-  if (type_ & BUNDLE_TYPE_ARRAY) {
-    // values size
-    std::size_t values_size = values_.size();
-    p = reinterpret_cast<unsigned char*>(&values_size);
-    bytes.insert(bytes.end(), p, p + sizeof(values_size));
-  }
-
-  // values
-  for (unsigned int i = 0; i < values_.size(); i++) {
-    std::size_t value_size = values_size_[i];
-    p = reinterpret_cast<unsigned char*>(&value_size);
-    bytes.insert(bytes.end(), p, p + sizeof(value_size));
-
-    bytes.insert(bytes.end(), values_[i].get(), values_[i].get() + value_size);
-  }
-
-  return bytes;
-}
-
-std::size_t KeyInfo::GetEncodedSize() {
-  // total size
-  std::size_t encoded_size = sizeof(std::size_t);
-
-  // type
-  encoded_size += sizeof(int);
-
-  // key size
-  encoded_size += sizeof(std::size_t);
-
-  // key
-  if ((encoded_size + key_.length() + 1) < encoded_size)
-    return 0;
-
-  encoded_size += key_.length() + 1;
-
-  if (type_ & BUNDLE_TYPE_ARRAY) {
-    // values size
-    if ((encoded_size + sizeof(std::size_t)) < encoded_size)
-      return 0;
-
-    encoded_size += sizeof(std::size_t);
-  }
-
-  // values
-  std::size_t values_size = 0;
-  for (unsigned int i = 0; i < values_.size(); ++i) {
-    // value size
-    if ((values_size + sizeof(std::size_t)) < values_size)
-      return 0;
-
-    values_size += sizeof(std::size_t);
-
-    // value
-    if ((values_size + values_size_[i]) < values_size)
-      return 0;
-
-    values_size += values_size_[i];
-  }
-
-  if ((encoded_size + values_size) < encoded_size)
-    return 0;
-
-  encoded_size += values_size;
-
-  return encoded_size;
-}
-
-int KeyInfo::Decode(const std::vector<unsigned char>& bytes) {
-  unsigned int reader = 0;
-
-  // total size
-  std::size_t total_size = 0;
-  if ((reader + sizeof(total_size)) > bytes.size())
-    return BUNDLE_ERROR_INVALID_PARAMETER;
-
-  unsigned char* p = reinterpret_cast<unsigned char*>(&total_size);
-  std::copy(&bytes[reader], &bytes[reader] + sizeof(total_size), p);
-  reader += sizeof(total_size);
-
-  // type
-  if ((reader + sizeof(type_)) > bytes.size())
-    return BUNDLE_ERROR_INVALID_PARAMETER;
-
-  p = reinterpret_cast<unsigned char*>(&type_);
-  std::copy(&bytes[reader], &bytes[reader] + sizeof(type_), p);
-  reader += sizeof(type_);
-
-  // key size
-  std::size_t key_size = 0;
-
-  if ((reader + sizeof(key_size)) > bytes.size())
-    return BUNDLE_ERROR_INVALID_PARAMETER;
-
-  p = reinterpret_cast<unsigned char*>(&key_size);
-  std::copy(&bytes[reader], &bytes[reader] + sizeof(key_size), p);
-  reader += sizeof(key_size);
-
-  if ((reader + key_size) > bytes.size())
-    return BUNDLE_ERROR_INVALID_PARAMETER;
-
-  // key
-  std::vector<unsigned char> key(&bytes[reader], &bytes[reader] + key_size);
-  p = reinterpret_cast<unsigned char*>(&key[0]);
-  key_ = std::string(reinterpret_cast<char*>(p));
-  reader += key_size;
-
-  std::size_t values_size = 0;
-  if (type_ & BUNDLE_TYPE_ARRAY) {
-    // values size
-    if ((reader + sizeof(values_size)) > bytes.size())
-      return BUNDLE_ERROR_INVALID_PARAMETER;
-
-    p = reinterpret_cast<unsigned char*>(&values_size);
-    std::copy(&bytes[reader], &bytes[reader] + sizeof(values_size), p);
-    reader += sizeof(values_size);
-  } else {
-    values_size = 1;
-  }
-
-  // values
-  for (std::size_t i = 0; i < values_size; ++i) {
-    // value_size
-    std::size_t value_size = 0;
-    if ((reader + sizeof(value_size)) > bytes.size())
-      return BUNDLE_ERROR_INVALID_PARAMETER;
-
-    p = reinterpret_cast<unsigned char*>(&value_size);
-    std::copy(&bytes[reader], &bytes[reader] + sizeof(value_size), p);
-    reader += sizeof(value_size);
-
-    // value
-    if ((reader + value_size) > bytes.size())
-      return BUNDLE_ERROR_INVALID_PARAMETER;
-
-    try {
-      auto new_value = std::make_unique<unsigned char[]>(value_size);
-      std::copy(&bytes[reader], &bytes[reader] + value_size, new_value.get());
-      reader += value_size;
-      values_.push_back(std::move(new_value));
-    } catch (const std::bad_alloc& e) {
-      return BUNDLE_ERROR_OUT_OF_MEMORY;
-    }
-    values_size_.push_back(value_size);
-    uvalues_size_.push_back(static_cast<unsigned int>(value_size));
-  }
-
-  return BUNDLE_ERROR_NONE;
-}
-
-int KeyInfo::SetValue(int index, const std::vector<unsigned char>& value) {
-  if (index > GetSize() || index < 0)
-    return BUNDLE_ERROR_ARRAY_INDEX_OUT_OF_BOUNDS;
-
-  if (!IsArray())
-    return BUNDLE_ERROR_INVALID_PARAMETER;
-
-  try {
-    auto new_value = std::make_unique<unsigned char[]>(value.size());
-    if (value.size() != 0)
-      std::copy(value.begin(), value.end(), new_value.get());
-
-    values_[index] = std::move(new_value);
-  } catch (const std::bad_alloc& e) {
-    return BUNDLE_ERROR_OUT_OF_MEMORY;
-  }
-
-  values_size_[index] = value.size();
-  uvalues_size_[index] = static_cast<unsigned int>(value.size());
-  return BUNDLE_ERROR_NONE;
-}
-
-int KeyInfo::GetSize() const {
-  return values_.size();
-}
-
-}  // namespace internal
-}  // namespace tizen_base
diff --git a/src/key-info-internal.h b/src/key-info-internal.h
deleted file mode 100644 (file)
index b26ba5b..0000000
+++ /dev/null
@@ -1,72 +0,0 @@
-/*
- * Copyright (c) 2020 Samsung Electronics Co., Ltd. All rights reserved.
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#ifndef KEY_INFO_INTERNAL_H_
-#define KEY_INFO_INTERNAL_H_
-
-#include <string>
-#include <vector>
-#include <memory>
-
-namespace tizen_base {
-namespace internal {
-
-class KeyInfo {
- public:
-  KeyInfo(int type, std::string key,
-          std::vector<unsigned char> value);
-  KeyInfo(int type, std::string key,
-          std::vector<std::vector<unsigned char>> values);
-  explicit KeyInfo(std::vector<unsigned char> encoded_bytes);
-  virtual ~KeyInfo() = default;
-
-  KeyInfo(const KeyInfo& key_info);
-  KeyInfo& operator = (const KeyInfo& key_info);
-  KeyInfo(KeyInfo&& key_info) noexcept;
-  KeyInfo& operator = (KeyInfo&& key_info) noexcept;
-
-  bool operator == (const KeyInfo& key_info);
-
-  int GetType() const;
-  bool IsArray() const;
-  const std::string& GetKey();
-  const std::vector<std::unique_ptr<unsigned char[]>>& GetValues();
-  const std::vector<std::size_t>& GetValuesSize();
-  const std::vector<unsigned int>& GetUValuesSize();
-  std::vector<unsigned char> Encode();
-
-  int SetValue(int index, const std::vector<unsigned char>& value);
-  int GetSize() const;
-
- private:
-  std::size_t GetEncodedSize();
-  int SetValuesSize();
-  int SetValue(const std::vector<unsigned char>& value);
-  int SetValues(const std::vector<std::vector<unsigned char>>& values);
-  int Decode(const std::vector<unsigned char>& bytes);
-
- private:
-  int type_;
-  std::string key_;
-  std::vector<std::unique_ptr<unsigned char[]>> values_;
-  std::vector<std::size_t> values_size_;
-  std::vector<unsigned int> uvalues_size_;
-};
-
-}  // namespace internal
-}  // namespace tizen_base
-
-#endif  // KEY_INFO_INTERNAL_H_
diff --git a/src/log-private.h b/src/log-private.h
deleted file mode 100644 (file)
index 29e99da..0000000
+++ /dev/null
@@ -1,37 +0,0 @@
-/*
- * Copyright (c) 2020 Samsung Electronics Co., Ltd All Rights Reserved
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#ifndef LOG_PRIVATE_H_
-#define LOG_PRIVATE_H_
-
-#include <dlog.h>
-
-#undef LOG_TAG
-#define LOG_TAG "BUNDLE"
-
-#undef _E
-#define _E LOGE
-
-#undef _W
-#define _W LOGW
-
-#undef _I
-#define _I LOGI
-
-#undef _D
-#define _D LOGD
-
-#endif  // LOG_PRIVATE_H_
diff --git a/src/parcel/CMakeLists.txt b/src/parcel/CMakeLists.txt
new file mode 100644 (file)
index 0000000..b042a16
--- /dev/null
@@ -0,0 +1,38 @@
+AUX_SOURCE_DIRECTORY(${CMAKE_CURRENT_SOURCE_DIR} PARCEL_SRCS)
+
+ADD_LIBRARY(${TARGET_PARCEL} SHARED ${PARCEL_SRCS})
+
+TARGET_INCLUDE_DIRECTORIES(${TARGET_PARCEL} PUBLIC
+  ${CMAKE_CURRENT_SOURCE_DIR}
+  ${CMAKE_CURRENT_SOURCE_DIR}/api
+  ${CMAKE_CURRENT_SOURCE_DIR}/../)
+
+SET_TARGET_PROPERTIES(${TARGET_PARCEL} PROPERTIES SOVERSION ${MAJORVER})
+SET_TARGET_PROPERTIES(${TARGET_PARCEL} PROPERTIES VERSION ${FULLVER})
+
+APPLY_PKG_CONFIG(${TARGET_PARCEL} PUBLIC
+  CAPI_BASE_COMMON_DEPS
+  DLOG_DEPS
+  GLIB_DEPS
+)
+
+TARGET_LINK_LIBRARIES(${TARGET_PARCEL} PUBLIC ${TARGET_BUNDLE})
+
+CONFIGURE_FILE(${CMAKE_CURRENT_SOURCE_DIR}/parcel.pc.in
+  ${CMAKE_CURRENT_SOURCE_DIR}/parcel.pc @ONLY)
+
+INSTALL(TARGETS ${TARGET_PARCEL} DESTINATION ${LIB_INSTALL_DIR})
+INSTALL(FILES ${CMAKE_CURRENT_SOURCE_DIR}/parcel.pc
+  DESTINATION ${LIB_INSTALL_DIR}/pkgconfig/)
+
+INSTALL(DIRECTORY ${CMAKE_CURRENT_SOURCE_DIR}
+  DESTINATION include/parcel/
+  FILES_MATCHING
+  PATTERN "*.hh"
+  PATTERN "*_private.hh" EXCLUDE
+  PATTERN "*_implementation.hh" EXCLUDE)
+
+  INSTALL(DIRECTORY ${CMAKE_CURRENT_SOURCE_DIR}/api
+  DESTINATION include/parcel/
+  FILES_MATCHING
+  PATTERN "*.h")
diff --git a/src/parcel/api/parcel.h b/src/parcel/api/parcel.h
new file mode 100644 (file)
index 0000000..10dbaba
--- /dev/null
@@ -0,0 +1,566 @@
+/*
+ * Copyright (c) 2020 Samsung Electronics Co., Ltd. All rights reserved.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#ifndef __PARCEL_H__
+#define __PARCEL_H__
+
+#include <stdint.h>
+#include <stddef.h>
+#include <tizen.h>
+
+/**
+ * @addtogroup CORE_LIB_PARCEL_MODULE
+ * @{
+ */
+
+#ifdef __cplusplus
+extern "C" {
+#endif
+
+/**
+ * @brief The parcel handle.
+ * @since_tizen 6.5
+ */
+typedef void *parcel_h;
+
+/**
+ * @brief The interface for converting data to/from a parcel.
+ * @since_tizen 6.5
+ */
+typedef struct {
+       void (*to)(parcel_h parcel, void *data);
+       void (*from)(parcel_h parcel, void *data);
+} parcelable_t;
+
+/**
+ * @brief Enumeration for error codes for a parcel.
+ * @since_tizen 6.5
+ */
+typedef enum {
+       PARCEL_ERROR_NONE = TIZEN_ERROR_NONE, /**< Successful */
+       PARCEL_ERROR_ILLEGAL_BYTE_SEQ = TIZEN_ERROR_ILLEGAL_BYTE_SEQ, /**< Illegal byte sequence */
+       PARCEL_ERROR_INVALID_PARAMETER = TIZEN_ERROR_INVALID_PARAMETER, /**< Invalid parameter */
+       PARCEL_ERROR_NO_DATA = TIZEN_ERROR_NO_DATA, /**< No data available */
+       PARCEL_ERROR_OUT_OF_MEMORY = TIZEN_ERROR_OUT_OF_MEMORY, /**< Out of memory */
+} parcel_error_e;
+
+/**
+ * @brief Creates a parcel handle.
+ * @since_tizen 6.5
+ * @remarks You MUST release @a parcel using parcel_destroy().
+ * @param[out] parcel The parcel handle that is newly created
+ * @return @c 0 on success,
+ *         otherwise a negative error value
+ * @retval #PARCEL_ERROR_NONE Successful
+ * @retval #PARCEL_ERROR_INVALID_PARAMETER Invalid parameter
+ * @retval #PARCEL_ERROR_OUT_OF_MEMORY Out of memory
+ * @see parcel_destroy()
+ */
+int parcel_create(parcel_h *parcel);
+
+/**
+ * @brief Destroys a parcel handle.
+ * @since_tizen 6.5
+ * @param[in] parcel The parcel handle
+ * @return @c 0 on success,
+ *         otherwise a negative error value
+ * @retval #PARCEL_ERROR_NONE Successful
+ * @retval #PARCEL_ERROR_INVALID_PARAMETER
+ * @see parcel_create()
+ */
+int parcel_destroy(parcel_h parcel);
+
+/**
+ * @brief Creates and returns a copy of the given parcel handle.
+ * @since_tizen 6.5
+ * @remarks A newly created parcel should be destroyed by calling the parcel_destroy() if it is no longer needed.
+ * @param[in] parcel The parcel handle
+ * @param[out] If successful, a newly created parcel handle will be returned
+ * @return @c 0 on success,
+ *         otherwise a negative error value
+ * @retval #PARCEL_ERROR_NONE Successful
+ * @retval #PARCEL_ERROR_INVALID_PARAMETER Invalid parameter
+ * @see parcel_destroy()
+ */
+int parcel_clone(parcel_h parcel, parcel_h *clone);
+
+/**
+ * @brief Writes bytes to the parcel handle.
+ * @since_tizen 6.5
+ * @param[in] parcel The parcel handle
+ * @param[in] buf The array buffer to write
+ * @param[in] size The size of bytes to write
+ * @return @c 0 on success,
+ *         otherwise a negative error value
+ * @retval #PARCEL_ERROR_NONE Successful
+ * @retval #PARCEL_ERROR_INVALID_PARAMETER Invalid parameter
+ * @see parcel_burst_read()
+ */
+int parcel_burst_write(parcel_h parcel, const void *buf, uint32_t size);
+
+/**
+ * @brief Reads bytes from the parcel handle.
+ * @since_tizen 6.5
+ * @param[in] parcel The parcel handle
+ * @param[out] buf The array buffer to read
+ * @param[in] size The size of bytes to read
+ * @return @c 0 on success,
+ *         otherwise a negative error value
+ * @retval #PARCEL_ERROR_NONE Successful
+ * @retval #PARCEL_ERROR_INVALID_PARAMETER Invalid parameter
+ * @retval #PARCEL_ERROR_NO_DATA No data available
+ * @retval #PARCEL_ERROR_ILLEGAL_BYTE_SEQ Illegal byte sequence
+ * @see parcel_burst_write()
+ */
+int parcel_burst_read(parcel_h parcel, void *buf, uint32_t size);
+
+/**
+ * @brief Writes a boolean value into the parcel handle.
+ * @since_tizen 6.5
+ * @param[in] parcel The parcel handle
+ * @param[in] val The boolean value
+ * @return @c 0 on success,
+ *         otherwise a negative error value
+ * @retval #PARCEL_ERROR_NONE Successful
+ * @retval #PARCEL_ERROR_INVALID_PARAMETER Invalid parameter
+ * @see parcel_read_bool()
+ */
+int parcel_write_bool(parcel_h parcel, bool val);
+
+/**
+ * @brief Writes a byte value into the parcel handle.
+ * @since_tizen 6.5
+ * @param[in] parcel The parcel handle
+ * @param[in] val The byte value
+ * @return @c 0 on success,
+ *         otherwise a negative error value
+ * @retval #PARCEL_ERROR_NONE Successful
+ * @retval #PARCEL_ERROR_INVALID_PARAMETER Invalid parameter
+ * @see parcel_read_uint8()
+ */
+int parcel_write_byte(parcel_h parcel, char val);
+
+/**
+ * @brief Writes an unsigned short value into the parcel handle.
+ * @since_tizen 6.5
+ * @param[in] parcel The parcel handle
+ * @param[in] val The unsigned short value
+ * @return @c 0 on success,
+ *         otherwise a negative error value
+ * @retval #PARCEL_ERROR_NONE Successful
+ * @retval #PARCEL_ERROR_INVALID_PARAMETER Invalid parameter
+ * @see parcel_read_uint16()
+ */
+int parcel_write_uint16(parcel_h parcel, uint16_t val);
+
+/**
+ * @brief Writes an unsigned integer value into the parcel handle.
+ * @since_tizen 6.5
+ * @param[in] parcel The parcel handle
+ * @param[in] val The unsigned integer value
+ * @return @c 0 on success,
+ *         otherwise a negative error value
+ * @retval #PARCEL_ERROR_NONE Successful
+ * @retval #PARCEL_ERROR_INVALID_PARAMETER Invalid parameter
+ * @see parcel_read_uint32()
+ */
+int parcel_write_uint32(parcel_h parcel, uint32_t val);
+
+/**
+ * @brief Writes an unsigned long long integer value into the parcel handle.
+ * @since_tizen 6.5
+ * @param[in] parcel The parcel handle
+ * @param[in] val The unsigned long long interger value
+ * @return @c 0 on success,
+ *         otherwise a negative error value
+ * @retval #PARCEL_ERROR_NONE Successful
+ * @retval #PARCEL_ERROR_INVALID_PARAMETER Invalid parameter
+ * @see parcel_read_uint64()
+ */
+int parcel_write_uint64(parcel_h parcel, uint64_t val);
+
+/**
+ * @brief Writes a signed short value into the parcel handle.
+ * @since_tizen 6.5
+ * @param[in] parcel The parcel handle
+ * @param[in] val The signed short value
+ * @return @c 0 on success,
+ *         otherwise a negative error value
+ * @retval #PARCEL_ERROR_NONE Successful
+ * @retval #PARCEL_ERROR_INVALID_PARAMETER Invalid parameter
+ * @see parcel_read_int16()
+ */
+int parcel_write_int16(parcel_h parcel, int16_t val);
+
+/**
+ * @brief Writes a signed integer value into the parcel handle.
+ * @since_tizen 6.5
+ * @param[in] parcel The parcel handle
+ * @param[in] val The signed integer value
+ * @return @c 0 on success,
+ *         otherwise a negative error value
+ * @retval #PARCEL_ERROR_NONE Successful
+ * @retval #PARCEL_ERROR_INVALID_PARAMETER Invalid parameter
+ * @see parcel_read_int32()
+ */
+int parcel_write_int32(parcel_h parcel, int32_t val);
+
+/**
+ * @brief Writes a signed long long integer value into the parcel handle.
+ * @since_tizen 6.5
+ * @param[in] parcel The parcel handle
+ * @param[in] val The signedi long long integer value
+ * @return @c 0 on success,
+ *         otherwise a negative error value
+ * @retval #PARCEL_ERROR_NONE Successful
+ * @retval #PARCEL_ERROR_INVALID_PARAMETER Invalid parameter
+ * @see parcel_read_int64()
+ */
+int parcel_write_int64(parcel_h parcel, int64_t val);
+
+/**
+ * @brief Writes a floating point value into the parcel handle.
+ * @since_tizen 6.5
+ * @param[in] parcel The parcel handle
+ * @param[in] val The floating point value
+ * @return @c 0 on success,
+ *         otherwise a negative error value
+ * @retval #PARCEL_ERROR_NONE Successful
+ * @retval #PARCLE_ERROR_INVALID_PARAMETER Invalid parameter
+ * @see parcel_read_float()
+ */
+int parcel_write_float(parcel_h parcel, float val);
+
+/**
+ * @brief Writes a double precision floating point value into the parcel handle.
+ * @since_tizen 6.5
+ * @param[in] parcel The parcel handle
+ * @param[in] val The double precision floating point value
+ * @return @c 0 on success,
+ *         otherwise a negative error value
+ * @retval #PARCEL_ERROR_NONE Successful
+ * @retval #PARCLE_ERROR_INVALID_PARAMETER Invalid parameter
+ * @see parcel_read_double()
+ */
+int parcel_write_double(parcel_h parcel, double val);
+
+/**
+ * @brief Writes a string data into the parcel handle.
+ * @since_tizen 6.5
+ * @param[in] parcel The parcel handle
+ * @param[in] str The string data
+ * @return @c 0 on success,
+ *         otherwise a negative error value
+ * @retval #PARCEL_ERROR_NONE Successful
+ * @retval #PARCEL_ERROR_INVALID_PARAMETER Invalid parameter
+ * @see parcel_read_string()
+ */
+int parcel_write_string(parcel_h parcel, const char *str);
+
+/**
+ * @brief Reads a boolean value from the parcel handle.
+ * @since_tizen 6.5
+ * @param[in] parcel The parcel handle
+ * @param[out] val The boolean value
+ * @return @c 0 on success,
+ *         otherwise a negative error value
+ * @retval #PARCEL_ERROR_NONE Successful
+ * @retval #PARCEL_ERROR_INVALID_PARAMETER Invalid parameter
+ * @retval #PARCEL_ERROR_NO_DATA No data available
+ * @retval #PARCEL_ERROR_ILLEGAL_BYTE_SEQ Illegal byte sequence
+ * @see parcel_write_bool()
+ */
+int parcel_read_bool(parcel_h parcel, bool *val);
+
+/**
+ * @brief Reads a byte value from the parcel handle.
+ * @since_tizen 6.5
+ * @param[in] parcel The parcel handle
+ * @param[out] val The byte value
+ * @return @c 0 on success,
+ *         otherwise a negative error value
+ * @retval #PARCEL_ERROR_NONE Successful
+ * @retval #PARCEL_ERROR_INVALID_PARAMETER Invalid parameter
+ * @retval #PARCEL_ERROR_NO_DATA No data available
+ * @retval #PARCEL_ERROR_ILLEGAL_BYTE_SEQ Illegal byte sequence
+ * @see parcel_write_uint8()
+ */
+int parcel_read_byte(parcel_h parcel, char *val);
+
+/**
+ * @brief Reads an unsigned short value from the parcel handle.
+ * @since_tizen 6.5
+ * @param[in] parcel The parcel handle
+ * @param[out] val The unsigned short value
+ * @return @c 0 on success,
+ *         otherwise a negative error value
+ * @retval #PARCEL_ERROR_NONE Successful
+ * @retval #PARCEL_ERROR_INVALID_PARAMETER Invalid parameter
+ * @retval #PARCEL_ERROR_NO_DATA No data available
+ * @retval #PARCEL_ERROR_ILLEGAL_BYTE_SEQ Illegal byte sequence
+ * @see parcel_write_uint16()
+ */
+int parcel_read_uint16(parcel_h parcel, uint16_t *val);
+
+/**
+ * @brief Reads an unsigned integer value from the parcel handle.
+ * @since_tizen 6.5
+ * @param[in] parcel The parcel handle
+ * @param[out] val The unsigned integer value
+ * @return @c 0 on success,
+ *         otherwise a negative error value
+ * @retval #PARCEL_ERROR_NONE Successful
+ * @retval #PARCEL_ERROR_INVALID_PARAMETER Invalid parameter
+ * @retval #PARCEL_ERROR_NO_DATA No data available
+ * @retval #PARCEL_ERROR_ILLEGAL_BYTE_SEQ Illegal byte sequence
+ * @see parcel_write_uint32()
+ */
+int parcel_read_uint32(parcel_h parcel, uint32_t *val);
+
+/**
+ * @brief Reads an unsigned long long integer value from the parcel handle.
+ * @since_tizen 6.5
+ * @param[in] parcel The parcel handle
+ * @param[out] val The unsigned long long integer value
+ * @return @c 0 on success,
+ *         otherwise a negative error value
+ * @retval #PARCEL_ERROR_NONE Successful
+ * @retval #PARCEL_ERROR_INVALID_PARAMETER Invalid parameter
+ * @retval #PARCEL_ERROR_NO_DATA No data available
+ * @retval #PARCEL_ERROR_ILLEGAL_BYTE_SEQ Illegal byte sequence
+ * @see parcel_write_uint64()
+ */
+int parcel_read_uint64(parcel_h parcel, uint64_t *val);
+
+/**
+ * @brief Reads a signed short value from the parcel handle.
+ * @since_tizen 6.5
+ * @param[in] parcel The parcel handle
+ * @param[out] val The signed short value
+ * @return @c 0 on success,
+ *         otherwise a negative error value
+ * @retval #PARCEL_ERROR_NONE Successful
+ * @retval #PARCEL_ERROR_INVALID_PARAMETER Invalid parameter
+ * @retval #PARCEL_ERROR_NO_DATA No data available
+ * @retval #PARCEL_ERROR_ILLEGAL_BYTE_SEQ Illegal byte sequence
+ * @see parcel_write_int16()
+ */
+int parcel_read_int16(parcel_h parcel, int16_t *val);
+
+/**
+ * @brief Reads a signed integer value from the parcel handle.
+ * @since_tizen 6.5
+ * @param[in] parcel The parcel handle
+ * @param[out] val The signed integer value
+ * @return @c 0 on success,
+ *         otherwise a negative error value
+ * @retval #PARCEL_ERROR_NONE Successful
+ * @retval #PARCEL_ERROR_INVALID_PARAMETER Invalid parameter
+ * @retval #PARCEL_ERROR_NO_DATA No data available
+ * @retval #PARCEL_ERROR_ILLEGAL_BYTE_SEQ Illegal byte sequence
+ * @see parcel_write_int32()
+ */
+int parcel_read_int32(parcel_h parcel, int32_t *val);
+
+/**
+ * @brief Reads a signed long long integer value from the parcel handle.
+ * @since_tizen 6.5
+ * @param[in] parcel The parcel handle
+ * @param[out] val The signed long long integer value
+ * @return @c 0 on success,
+ *         otherwise a negative error value
+ * @retval #PARCEL_ERROR_NONE Successful
+ * @retval #PARCEL_ERROR_INVALID_PARAMETER Invalid parameter
+ * @retval #PARCEL_ERROR_NO_DATA No data available
+ * @retval #PARCEL_ERROR_ILLEGAL_BYTE_SEQ Illegal byte sequence
+ * @see parcel_write_int64()
+ */
+int parcel_read_int64(parcel_h parcel, int64_t *val);
+
+/**
+ * @brief Reads a floating point value from the parcel handle.
+ * @since_tizen 6.5
+ * @param[in] parcel The parcel handle
+ * @param[out] val The floating point value
+ * @return @c 0 on success,
+ *         otherwise a negative error value
+ * @retval #PARCEL_ERROR_NONE Successful
+ * @retval #PARCEL_ERROR_INVALID_PARAMETER Invalid parameter
+ * @retval #PARCEL_ERROR_NO_DATA No data available
+ * @retval #PARCEL_ERROR_ILLEGAL_BYTE_SEQ Illegal byte sequence
+ * @see parcel_write_uint8()
+ */
+int parcel_read_float(parcel_h parcel, float *val);
+
+/**
+ * @brief Reads a double precision floating point value from the parcel handle.
+ * @since_tizen 6.5
+ * @param[in] parcel The parcel handle
+ * @param[out] val The double precision floating point value
+ * @return @c 0 on success,
+ *         otherwise a negative error value
+ * @retval #PARCEL_ERROR_NONE Successful
+ * @retval #PARCEL_ERROR_INVALID_PARAMETER Invalid parameter
+ * @retval #PARCEL_ERROR_NO_DATA No data available
+ * @retval #PARCEL_ERROR_ILLEGAL_BYTE_SEQ Illegal byte sequence
+ * @see parcel_write_uint8()
+ */
+int parcel_read_double(parcel_h parcel, double *val);
+
+/**
+ * @brief Reads a string data from the parcel handle.
+ * @since_tizen 6.5
+ * @param[in] parcel The parcel handle
+ * @param[out] str The string data
+ * @return @c 0 on success,
+ *         otherwise a negative error value
+ * @retval #PARCEL_ERROR_NONE Successful
+ * @retval #PARCEL_ERROR_INVALID_PARAMETER Invalid parameter
+ * @retval #PARCEL_ERROR_NO_DATA No data available
+ * @retval #PARCEL_ERROR_ILLEGAL_BYTE_SEQ Illegal byte sequence
+ * @retval #PARCEL_ERROR_OUT_OF_MEMORY Out of memory
+ * @see parcel_write_uint8()
+ */
+int parcel_read_string(parcel_h parcel, char **str);
+
+/**
+ * @brief Resets the reader pointer of the parcel handle to the start.
+ * @since_tizen 6.5
+ * @param[in] parcel The parcel handle
+ * @return @c 0 on success,
+ *         otherwise a negative error value
+ * @retval #PARCEL_ERROR_NONE Successful
+ * @retval #PARCEL_ERROR_INVALID_PARAMETER Invalid parameter
+ */
+int parcel_reset_reader(parcel_h parcel);
+
+/**
+ * @brief Clears the data of the parcel handle.
+ * @since_tizen 6.5
+ * @param[in] parcel The parcel handle
+ * @return @c 0 on success,
+ *         otherwise a negative error value
+ * @retval #PARCEL_ERROR_NONE Successful
+ * @retval #PARCEL_ERROR_INVALID_PARAMETER Invalid parameter
+ */
+int parcel_clear(parcel_h parcel);
+
+/**
+ * @brief Resets the data of the parcel handle.
+ * @since_tizen 6.5
+ * @param[in] parcel The parcel handle
+ * @param[in] buf The array buffer to write
+ * @param[in] size The size of bytes to write
+ * @return @c 0 on success,
+ *         otherwise a negative error value
+ * @retval #PARCEL_ERROR_NONE Successful
+ * @retval #PARCEL_ERROR_INVALID_PARAMETER Invalid parameter
+ */
+int parcel_reset(parcel_h parcel, const void *buf, uint32_t size);
+
+/**
+ * @brief Writes the data using @a parcelable to the parcel handle.
+ * @since_tizen 6.5
+ * @param[in] parcel The parcel handle
+ * @param[in] parcelable The interface to write the data into the parcel handle
+ * @param[in] data The user data which writes into the parcel handle
+ * @return @c 0 on success,
+ *         otherwise a negative error value
+ * @retval #PARCEL_ERROR_NONE Successful
+ * @retval #PARCEL_ERROR_INVALID_PARAMETER Invalid parameter
+ * @see parcel_read()
+ */
+int parcel_write(parcel_h parcel, parcelable_t *parcelable, void *data);
+
+/**
+ * @brief Reads the data using @a parcelable from the parcel handle.
+ * @since_tizen 6.5
+ * @param[in] parcel The parcel handle
+ * @param[in] parcelable The interface to read the data from the parcel handle
+ * @param[in] data The user data which reads from the parcel handle
+ * @return @c 0 on success,
+ *         otherwise a negative error value
+ * @retval #PARCEL_ERROR_NONE Successful
+ * @retval #PARCEL_ERROR_INVALID_PARAMETER Invalid parameter
+ * @see parcel_write()
+ */
+int parcel_read(parcel_h parcel, parcelable_t *parcelable, void *data);
+
+/**
+ * @brief Gets the raw data of the parcel handle.
+ * @since_tizen 6.5
+ * @remarks You MUST NOT release @a raw using free(). It's managed by platform.
+ * @param[in] parcel The parcel handle
+ * @param[out] raw The raw data
+ * @param[out] size The size of the raw data
+ * @return @c 0 on success,
+ *         otherwise a negative error value
+ * @retval #PARCEL_ERROR_NONE Successful
+ * @retval #PARCEL_ERROR_INVALID_PARAMETER Invalid parameter
+ */
+int parcel_get_raw(parcel_h parcel, void **raw, uint32_t *size);
+
+/**
+ * @brief Sets byte order of the parcel handle.
+ * @since_tizen 6.5
+ * @remarks The platform byte order is little-endian.
+ *          The network byte order is defined to always be big-endian.
+ *          If you want to change byte order of the raw data of the parcel handle,
+ *          you set byte order of the parcel handle using the function.
+ * @param[in] parcel The parcel handle
+ * @param[in] big_endian @ true, if byte order of the parcel is big-endian
+ * @return @c 0 on success,
+ *         otherwise a negative error value
+ * @retval #PARCEL_ERROR_NONE Successful
+ * @retval #PARCEL_ERROR_INVALID_PARAMETER Invalid parameter
+ */
+int parcel_set_byte_order(parcel_h parcle, bool big_endian);
+
+/**
+ * @brief Gets the size of the data capacity of the parcel handle.
+ * @since_tizen 7.0
+ * @param[in] parcel The parcel handle
+ * @param[out] size The size of the data capacity
+ * @return @c 0 on success,
+ *         otherwise a negative error value
+ * @retval #PARCEL_ERROR_NONE Successful
+ * @retval #PARCEL_ERROR_INVALID_PARAMETER Invalid parameter
+ */
+int parcel_get_data_capacity(parcel_h parcel, size_t *size);
+
+/**
+ * @brief Sets the size of the data capacity of the parcel handle.
+ * @since_tizen 7.0
+ * @remarks The raw data will be reallocated using the given size.
+ * @param[in] parcel The parcel handle
+ * @param[in] size The size of the data capacity
+ * @return @c 0 on success,
+ *         otherwise a negative error value
+ * @retval #PARCEL_ERROR_NONE Successful
+ * @retval #PARCEL_ERROR_INVALID_PARAMETER Invalid parameter
+ * @retval #PARCEL_ERROR_OUT_OF_MEMORY
+ */
+int parcel_set_data_capacity(parcel_h parcel, size_t size);
+
+#ifdef __cplusplus
+}
+#endif
+
+/**
+ * @}
+ */
+
+#endif /* __PARCEL_H__ */
diff --git a/src/parcel/common.hh b/src/parcel/common.hh
new file mode 100644 (file)
index 0000000..91f3535
--- /dev/null
@@ -0,0 +1,23 @@
+/*
+ * Copyright (c) 2020 Samsung Electronics Co., Ltd. All rights reserved.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#ifndef PARCEL_COMMON_HH_
+#define PARCEL_COMMON_HH_
+
+#undef EXPORT
+#define EXPORT __attribute__((visibility("default")))
+
+#endif  // PARCEL_COMMON_HH_
diff --git a/src/parcel/log_private.hh b/src/parcel/log_private.hh
new file mode 100644 (file)
index 0000000..a005add
--- /dev/null
@@ -0,0 +1,37 @@
+/*
+ * Copyright (c) 2020 Samsung Electronics Co., Ltd. All rights reserved.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#ifndef PARCEL_LOG_PRIVATE_HH_
+#define PARCEL_LOG_PRIVATE_HH_
+
+#include <dlog.h>
+
+#undef LOG_TAG
+#define LOG_TAG "PARCEL"
+
+#undef _E
+#define _E LOGE
+
+#undef _W
+#define _W LOGW
+
+#undef _I
+#define _I LOGI
+
+#undef _D
+#define _D LOGD
+
+#endif  // PARCEL_LOG_PRIVATE_HH_
diff --git a/src/parcel/parcel.cc b/src/parcel/parcel.cc
new file mode 100644 (file)
index 0000000..1f266c0
--- /dev/null
@@ -0,0 +1,542 @@
+/*
+ * Copyright (c) 2020 Samsung Electronics Co., Ltd. All rights reserved.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#include <glib.h>
+
+#include <exception>
+#include <mutex>
+
+#include "parcel/common.hh"
+#include "parcel/log_private.hh"
+#include "parcel/parcel.hh"
+#include "parcel/parcel_implementation.hh"
+#include "parcel/parcelable.hh"
+
+namespace tizen_base {
+namespace {
+
+constexpr const size_t kDataCapacity = 1024;
+
+}  // namespace
+
+Parcel::Impl::Impl(Parcel* parent, size_t data_capacity, uint8_t* data)
+    : parent_(parent), data_capacity_(data_capacity), data_(data) {
+  if (data_ != nullptr)
+    data_size_ = data_capacity_;
+  else
+    data_ = static_cast<uint8_t*>(malloc(data_capacity_));
+}
+
+Parcel::Impl::~Impl() {
+  free(data_);
+}
+
+void Parcel::Impl::Write(const void* buf, uint32_t size) {
+  if (data_size_ + size > data_capacity_) {
+    size_t new_size = (data_capacity_ + size) * 3 / 2;
+    uint8_t* data = static_cast<uint8_t*>(realloc(data_, new_size));
+    if (data == nullptr)
+      throw std::bad_alloc();
+
+    data_ = data;
+    data_capacity_ = new_size;
+  }
+
+  memcpy(data_ + data_size_, buf, size);
+  data_size_ += size;
+}
+
+int Parcel::Impl::Read(void* buf, uint32_t size) {
+  if (data_size_ == 0)
+    return TIZEN_ERROR_NO_DATA;
+
+  if (reader_ + size > data_size_)
+    return TIZEN_ERROR_ILLEGAL_BYTE_SEQ;
+
+  memcpy(buf, data_ + reader_, size);
+  reader_ += size;
+  set_last_result(TIZEN_ERROR_NONE);
+  return TIZEN_ERROR_NONE;
+}
+
+void Parcel::Impl::ResetReader() {
+  reader_ = 0;
+}
+
+void Parcel::Impl::Clear() {
+  data_size_ = 0;
+  reader_ = 0;
+}
+
+void Parcel::Impl::Reset(const void* buf, uint32_t size) {
+  Clear();
+  Write(buf, size);
+}
+
+bool Parcel::Impl::IsEmpty() {
+  return data_size_ == 0;
+}
+
+void Parcel::Impl::WriteSize(uint32_t size) {
+  if (IsBigEndian())
+    size = GUINT32_TO_BE(size);
+
+  Write<uint32_t>(size);
+}
+
+template <typename T>
+void Parcel::Impl::Write(T d) {
+  if (data_size_ + sizeof(T) > data_capacity_) {
+    size_t new_size = (data_capacity_ + sizeof(T)) * 3 / 2;
+    uint8_t* data = static_cast<uint8_t*>(realloc(data_, new_size));
+    if (data == nullptr)
+      throw std::bad_alloc();
+
+    data_ = data;
+    data_capacity_ = new_size;
+  }
+
+  auto* p = reinterpret_cast<uint8_t*>(&d);
+  memcpy(data_ + data_size_, p, sizeof(T));
+  data_size_ += sizeof(T);
+}
+
+int Parcel::Impl::ReadSize(uint32_t* size) {
+  if (data_size_ == 0)
+    return TIZEN_ERROR_NO_DATA;
+
+  int ret = Read<uint32_t>(size);
+  if (ret != TIZEN_ERROR_NONE)
+    return ret;
+
+  if (IsBigEndian())
+    *size = GUINT32_FROM_BE(*size);
+
+  return TIZEN_ERROR_NONE;
+}
+
+template <typename T>
+int Parcel::Impl::Read(T* d) {
+  uint32_t size = static_cast<uint32_t>(sizeof(T));
+  if (reader_ + size > data_size_)
+    return TIZEN_ERROR_ILLEGAL_BYTE_SEQ;
+
+  auto* p = reinterpret_cast<uint8_t*>(d);
+  memcpy(p, data_ + reader_, size);
+  reader_ += size;
+  return TIZEN_ERROR_NONE;
+}
+
+void Parcel::Impl::SetByteOrder(bool big_endian) {
+  big_endian_ = big_endian;
+}
+
+bool Parcel::Impl::IsBigEndian() const {
+  return big_endian_;
+}
+
+uint8_t* Parcel::Impl::GetData() const {
+  return data_;
+}
+
+size_t Parcel::Impl::GetDataSize() const {
+  return data_size_;
+}
+
+size_t Parcel::Impl::GetDataCapacity() const {
+  return data_capacity_;
+}
+
+void Parcel::Impl::SetDataCapacity(size_t size) {
+  uint8_t* data = static_cast<uint8_t*>(realloc(data_, size));
+  if (data == nullptr)
+    throw std::bad_alloc();
+
+  data_ = data;
+  data_capacity_ = size;
+}
+
+uint8_t* Parcel::Impl::Detach(size_t* size) {
+  uint8_t* data = data_;
+  *size = data_size_;
+  data_ = nullptr;
+  data_capacity_ = 0;
+  data_size_ = 0;
+  reader_= 0;
+  return data;
+}
+
+uint32_t Parcel::Impl::GetReader() const {
+  return reader_;
+}
+
+std::vector<uint8_t> Parcel::Impl::ToRaw() {
+  return std::vector<uint8_t>(data_, data_ + data_size_);
+}
+
+Parcel::Parcel()
+    : impl_(new Impl(this, kDataCapacity, nullptr)) {
+  if (impl_->data_ == nullptr)
+    throw std::bad_alloc();
+}
+
+Parcel::Parcel(const void* buf, uint32_t size, bool copy)
+    : impl_(new Impl(this, size,
+          copy ? nullptr : static_cast<uint8_t*>(const_cast<void*>(buf)))) {
+  if (impl_->data_ == nullptr)
+    throw std::bad_alloc();
+
+  if (copy)
+    impl_->Write(buf, size);
+}
+
+Parcel::~Parcel() {};
+
+Parcel::Parcel(const Parcel& p)
+  : impl_(new Impl(this, kDataCapacity)) {
+  impl_->big_endian_ = p.impl_->big_endian_;
+  impl_->data_capacity_ = p.impl_->data_capacity_;
+  impl_->data_size_ = p.impl_->data_size_;
+
+  uint8_t* data = static_cast<uint8_t*>(
+      realloc(impl_->data_, impl_->data_capacity_));
+  if (data == nullptr)
+    throw std::bad_alloc();
+
+  impl_->data_ = data;
+  memcpy(impl_->data_, p.impl_->data_, impl_->data_size_);
+
+  impl_->reader_ = p.impl_->reader_;
+}
+
+Parcel& Parcel::operator = (const Parcel& p) {
+  if (this != &p) {
+    impl_->big_endian_ = p.impl_->big_endian_;
+    impl_->data_capacity_ = p.impl_->data_capacity_;
+    impl_->data_size_ = p.impl_->data_size_;
+
+    uint8_t* data = static_cast<uint8_t*>(
+        realloc(impl_->data_, impl_->data_capacity_));
+    if (data == nullptr)
+      throw std::bad_alloc();
+
+    impl_->data_ = data;
+    memcpy(impl_->data_, p.impl_->data_, impl_->data_size_);
+
+    impl_->reader_ = p.impl_->reader_;
+  }
+  return *this;
+}
+
+Parcel::Parcel(Parcel&& p) noexcept
+    : impl_(new Impl(this, kDataCapacity)) {
+  impl_->big_endian_ = p.impl_->big_endian_;
+
+  impl_->data_size_ = p.impl_->data_size_;
+  p.impl_->data_size_ = 0;
+
+  uint8_t* data = impl_->data_;
+  size_t data_capacity = impl_->data_capacity_;
+
+  impl_->data_ = p.impl_->data_;
+  impl_->data_capacity_ = p.impl_->data_capacity_;
+
+  p.impl_->data_ = data;
+  p.impl_->data_capacity_ = data_capacity;
+
+  impl_->reader_ = p.impl_->reader_;
+  p.impl_->reader_ = 0;
+}
+
+Parcel& Parcel::operator = (Parcel&& p) noexcept {
+  if (this != &p) {
+    impl_->big_endian_ = p.impl_->big_endian_;
+
+    impl_->data_size_ = p.impl_->data_size_;
+    p.impl_->data_size_ = 0;
+
+    uint8_t* data = impl_->data_;
+    size_t data_capacity = impl_->data_capacity_;
+
+    impl_->data_ = p.impl_->data_;
+    impl_->data_capacity_ = p.impl_->data_capacity_;
+
+    p.impl_->data_ = data;
+    p.impl_->data_capacity_ = data_capacity;
+
+    impl_->reader_ = p.impl_->reader_;
+    p.impl_->reader_ = 0;
+  }
+  return *this;
+}
+
+bool Parcel::IsEmpty() const noexcept {
+  return impl_->IsEmpty();
+}
+
+void Parcel::Write(const void* buf, uint32_t size) {
+  impl_->Write(buf, size);
+}
+
+int Parcel::Read(void* buf, uint32_t size) {
+  return impl_->Read(buf, size);
+}
+
+void Parcel::WriteBool(bool val) {
+  impl_->Write<bool>(val);
+}
+
+void Parcel::WriteByte(char val) {
+  impl_->Write<char>(val);
+}
+
+void Parcel::WriteUInt16(uint16_t val) {
+  if (impl_->IsBigEndian())
+    val = GUINT16_TO_BE(val);
+
+  impl_->Write<uint16_t>(val);
+}
+
+void Parcel::WriteUInt32(uint32_t val) {
+  if (impl_->IsBigEndian())
+    val = GUINT32_TO_BE(val);
+
+  impl_->Write<uint32_t>(val);
+}
+
+void Parcel::WriteUInt64(uint64_t val) {
+  if (impl_->IsBigEndian())
+    val = GUINT64_TO_BE(val);
+
+  impl_->Write<uint64_t>(val);
+}
+
+void Parcel::WriteInt16(int16_t val) {
+  if (impl_->IsBigEndian())
+    val = GINT16_TO_BE(val);
+
+  impl_->Write<int16_t>(val);
+}
+
+void Parcel::WriteInt32(int32_t val) {
+  if (impl_->IsBigEndian())
+    val = GINT32_TO_BE(val);
+
+  impl_->Write<int32_t>(val);
+}
+
+void Parcel::WriteInt64(int64_t val) {
+  if (impl_->IsBigEndian())
+    val = GINT64_TO_BE(val);
+
+  impl_->Write<int64_t>(val);
+}
+
+void Parcel::WriteFloat(float val) {
+  if (impl_->IsBigEndian())
+    val = static_cast<float>(GINT32_TO_BE(val));
+
+  impl_->Write<float>(val);
+}
+
+void Parcel::WriteDouble(double val) {
+  if (impl_->IsBigEndian())
+    val = static_cast<double>(GINT64_TO_BE(val));
+
+  impl_->Write<double>(val);
+}
+
+void Parcel::WriteString(const std::string& str) {
+  impl_->WriteSize(str.length() + 1);
+  impl_->Write(str.c_str(), str.length() + 1);
+}
+
+void Parcel::WriteCString(const char* str) {
+  impl_->WriteSize(strlen(str) + 1);
+  impl_->Write(str, strlen(str) + 1);
+}
+
+int Parcel::ReadBool(bool* val) {
+  return impl_->Read<bool>(val);
+}
+
+int Parcel::ReadByte(char* val) {
+  return impl_->Read<char>(val);
+}
+
+int Parcel::ReadUInt16(uint16_t* val) {
+  int ret = impl_->Read<uint16_t>(val);
+  if (impl_->IsBigEndian())
+    *val = GUINT16_FROM_BE(*val);
+
+  return ret;
+}
+
+int Parcel::ReadUInt32(uint32_t* val) {
+  int ret = impl_->Read<uint32_t>(val);
+  if (impl_->IsBigEndian())
+    *val = GUINT32_FROM_BE(*val);
+
+  return ret;
+}
+
+int Parcel::ReadUInt64(uint64_t* val) {
+  int ret = impl_->Read<uint64_t>(val);
+  if (impl_->IsBigEndian())
+    *val = GUINT64_FROM_BE(*val);
+
+  return ret;
+}
+
+int Parcel::ReadInt16(int16_t* val) {
+  int ret = impl_->Read<int16_t>(val);
+  if (impl_->IsBigEndian())
+    *val = GINT16_FROM_BE(*val);
+
+  return ret;
+}
+
+int Parcel::ReadInt32(int32_t* val) {
+  int ret = impl_->Read<int32_t>(val);
+  if (impl_->IsBigEndian())
+    *val = GINT32_FROM_BE(*val);
+
+  return ret;
+}
+
+int Parcel::ReadInt64(int64_t* val) {
+  int ret = impl_->Read<int64_t>(val);
+  if (impl_->IsBigEndian())
+    *val = GINT64_FROM_BE(*val);
+
+  return ret;
+}
+
+int Parcel::ReadFloat(float* val) {
+  int ret = impl_->Read<float>(val);
+  if (impl_->IsBigEndian())
+    *val = static_cast<float>(GINT32_FROM_BE(*val));
+
+  return ret;
+}
+
+int Parcel::ReadDouble(double* val) {
+  int ret = impl_->Read<double>(val);
+  if (impl_->IsBigEndian())
+    *val = static_cast<double>(GINT64_FROM_BE(*val));
+
+  return ret;
+}
+
+std::string Parcel::ReadString() {
+  uint32_t len = 0;
+  int ret = impl_->ReadSize(&len);
+  if (ret != TIZEN_ERROR_NONE) {
+    set_last_result(ret);
+    return {};
+  }
+
+  char* str = new (std::nothrow) char[len];
+  if (str == nullptr) {
+    set_last_result(TIZEN_ERROR_OUT_OF_MEMORY);
+    return {};
+  }
+
+  auto ptr = std::unique_ptr<char[]>(str);
+  ret = impl_->Read(str, len);
+  if (ret != TIZEN_ERROR_NONE) {
+    set_last_result(ret);
+    return {};
+  }
+
+  set_last_result(TIZEN_ERROR_NONE);
+  return std::string(str);
+}
+
+int Parcel::ReadCString(char** str) {
+  uint32_t len = 0;
+  int ret = impl_->ReadSize(&len);
+  if (ret != TIZEN_ERROR_NONE)
+    return ret;
+
+  char* val = static_cast<char*>(calloc(len, sizeof(char)));
+  if (val == nullptr)
+    return TIZEN_ERROR_OUT_OF_MEMORY;
+
+  ret = impl_->Read(val, len);
+  if (ret != TIZEN_ERROR_NONE) {
+    free(val);
+    return ret;
+  }
+
+  *str = val;
+  return TIZEN_ERROR_NONE;
+}
+
+void Parcel::ResetReader() {
+  impl_->ResetReader();
+}
+
+void Parcel::Clear() {
+  impl_->Clear();
+}
+
+void Parcel::Reset(const void* buf, uint32_t size) {
+  impl_->Reset(buf, size);
+}
+
+void Parcel::WriteParcelable(const Parcelable& parcelable) {
+  parcelable.WriteToParcel(this);
+}
+
+int Parcel::ReadParcelable(Parcelable* parcelable) {
+  parcelable->ReadFromParcel(this);
+  return TIZEN_ERROR_NONE;
+}
+
+void Parcel::SetByteOrder(bool big_endian) {
+  impl_->SetByteOrder(big_endian);
+}
+
+uint8_t* Parcel::GetData() const {
+  return impl_->GetData();
+}
+
+size_t Parcel::GetDataSize() const {
+  return impl_->GetDataSize();
+}
+
+size_t Parcel::GetDataCapacity() const {
+  return impl_->GetDataCapacity();
+}
+
+void Parcel::SetDataCapacity(size_t size) {
+  impl_->SetDataCapacity(size);
+}
+
+uint8_t* Parcel::Detach(size_t* size) {
+  return impl_->Detach(size);
+}
+
+uint32_t Parcel::GetReader() const {
+  return impl_->GetReader();
+}
+
+std::vector<uint8_t> Parcel::ToRaw() {
+  return impl_->ToRaw();
+}
+
+}  // namespace tizen_base
diff --git a/src/parcel/parcel.hh b/src/parcel/parcel.hh
new file mode 100644 (file)
index 0000000..7d94d00
--- /dev/null
@@ -0,0 +1,435 @@
+/*
+ * Copyright (c) 2020 Samsung Electronics Co., Ltd. All rights reserved.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#ifndef PARCEL_PARCEL_HH_
+#define PARCEL_PARCEL_HH_
+
+/**
+ * @addtogroup CORE_LIB_PARCEL_MODULE
+ * @{
+ */
+
+#include <tizen.h>
+
+#include <memory>
+#include <string>
+#include <vector>
+
+#include "parcel/common.hh"
+#include "parcel/parcelable.hh"
+
+namespace tizen_base {
+
+/**
+ * @brief The class for Parcel API.
+ * @since_tizen 6.5
+ */
+class EXPORT Parcel final {
+ public:
+  /**
+   * @brief Enumeration for parcel error.
+   * @since_tizen 6.5
+   */
+  enum Error {
+    None = TIZEN_ERROR_NONE, /**< Successful */
+    IllegalByteSeq = TIZEN_ERROR_ILLEGAL_BYTE_SEQ, /**< Illegal byte sequence */
+    InvalidParameter = TIZEN_ERROR_INVALID_PARAMETER, /**< Invalid parameter */
+    NoData = TIZEN_ERROR_NO_DATA, /**< No data available */
+    OutOfMemory = TIZEN_ERROR_OUT_OF_MEMORY, /**< Out of memory */
+  };
+
+  /**
+   * @brief Constructor.
+   * @since_tizen 6.5
+   */
+  Parcel();
+
+  /**
+   * @brief Constructor
+   * @since_tizen 6.5
+   * @param[in] buf The bytes to write
+   * @param[in] size the size of bytes to write
+   * @param[in] copy If @c is true, this object copies bytes.
+   *                 If @c is false, this object takes ownership of @buf.
+   */
+  Parcel(const void* buf, uint32_t size, bool copy = true);
+
+  /**
+   * @brief Destructor
+   * @since_tizen 6.5
+   */
+  ~Parcel();
+
+  /**
+   * @brief Copy-constructor.
+   * @since_tizen 6.5
+   * @param[in] p The object to copy
+   */
+  Parcel(const Parcel& p);
+
+  /**
+   * @brief Assignment.
+   * @since_tizen 6.5
+   * @param[in] b The object to copy
+   */
+  Parcel& operator = (const Parcel& p);
+
+  /**
+   * @brief Move-constructor.
+   * @since_tizen 6.5
+   * @param[in] p The object to move
+   */
+  Parcel(Parcel&& p) noexcept;
+
+  /**
+   * @brief Assignment.
+   * @since_tizen 6.5
+   * @param[in] p The object to move
+   */
+  Parcel& operator = (Parcel&& p) noexcept;
+
+  /**
+   * @brief Checks the parcel is empty or not.
+   * @since_tizen 6.5
+   * @return true if the parcel is empty
+   */
+  bool IsEmpty() const noexcept;
+
+  /**
+   * @brief Writes bytes into the parcel.
+   * @since_tizen 6.5
+   * @param[in] buf The bytes to write
+   * @param[in] size The size of bytes to write
+   */
+  void Write(const void* buf, uint32_t size);
+
+  /**
+   * @brief Reads bytes from the parcel.
+   * @since_tizen 6.5
+   * @param[out] buf The bytes to read
+   * @param[in] size The size of bytes to read
+   * @return @c 0 on success,
+   *         otherwise a negative error value
+   */
+  int Read(void* buf, uint32_t size);
+
+  /**
+   * @brief Writes a boolean value into the parcel.
+   * @since_tizen 6.5
+   * @param[in] val The boolean value
+   */
+  void WriteBool(bool val);
+
+  /**
+   * @brief Writes a byte value into the parcel.
+   * @since_tizen 6.5
+   * @param[in] val The unsigned byte value
+   */
+  void WriteByte(char byte);
+
+  /**
+   * @brief Writes an unsigned short value into the parcel.
+   * @since_tizen 6.5
+   * @param[in] val The unsigned short value
+   */
+  void WriteUInt16(uint16_t val);
+
+  /**
+   * @brief Writes an unsigned integer value into the parcel.
+   * @since_tizen 6.5
+   * @param[in] val The unsigned integer value
+   */
+  void WriteUInt32(uint32_t val);
+
+  /**
+   * @brief Writes an unsigned long long integer into the parcel.
+   * @since_tizen 6.5
+   * @param[in] val The unsigned long long integer value
+   */
+  void WriteUInt64(uint64_t val);
+
+  /**
+   * @brief Writes a signed short value into the parcel.
+   * @since_tizen 6.5
+   * @param[in] val The signed short value
+   */
+  void WriteInt16(int16_t val);
+
+  /**
+   * @brief Writes a signed integer value into the parcel.
+   * @since_tizen 6.5
+   * @param[in] val The signed integer value
+   */
+  void WriteInt32(int32_t val);
+
+  /**
+   * @brief Writes a signed long long integer value into the parcel.
+   * @since_tizen 6.5
+   * @param[in] val The signed long long integer value
+   */
+  void WriteInt64(int64_t val);
+
+  /**
+   * @brief Writes a floating point value into the parcel.
+   * @since_tizen 6.5
+   * @param[in] val The floating point value
+   */
+  void WriteFloat(float val);
+
+  /**
+   * @brief Writes a double precision floating point value into the parcel.
+   * @since_tizen 6.5
+   * @param[in] val The double precision floating point value
+   */
+  void WriteDouble(double val);
+
+  /**
+   * @brief Writes a string data into the parcel.
+   * @since_tizen 6.5
+   * @param[in] str The string data
+   */
+  void WriteString(const std::string& str);
+
+  /**
+   * @brief Writes a string data into the parcel.
+   * @since_tizen 6.5
+   * @param[in] str The string data
+   */
+  void WriteCString(const char* str);
+
+  /**
+   * @brief Reads a boolean value from the parcel.
+   * @since_tizen 6.5
+   * @param[out] val The boolean value
+   * @return @c 0 on success,
+   *         otherwise a negative error value
+   */
+  int ReadBool(bool* val);
+
+  /**
+   * @brief Reads a byte value from the parcel.
+   * @since_tizen 6.5
+   * @param[out] val The unsigned byte value
+   * @return @c 0 on success,
+   *         otherwise a negative error value
+   */
+  int ReadByte(char* val);
+
+  /**
+   * @breif Reads an unsigned short value from the parcel.
+   * @since_tizen 6.5
+   * @param[out] val The unsigned short value
+   * @return @c 0 on success,
+   *         otherwise a negative error value
+   */
+  int ReadUInt16(uint16_t* val);
+
+  /**
+   * @brief Reads an unsigned integer value from the parcel.
+   * @since_tizen 6.5
+   * @param[out] val The unsigned integer value
+   * @return @c 0 on success,
+   *         otherwise a negative error value
+   */
+  int ReadUInt32(uint32_t* val);
+
+  /**
+   * @brief Reads an unsigned long long integer value from the parcel.
+   * @since_tizen 6.5
+   * @param[out] val The unsigned long long integer value
+   * @return @c 0 on success,
+   *         otherwise a negative error value
+   */
+  int ReadUInt64(uint64_t* val);
+
+  /**
+   * @brief Reads a signed byte value from the parcel.
+   * @since_tizen 6.5
+   * @param[out] val The signed byte value
+   * @return @c 0 on success,
+   *         otherwise a negative error value
+   */
+  int ReadInt8(int8_t* val);
+
+  /**
+   * @brief Reads a signed short value from the parcel.
+   * @since_tizen 6.5
+   * @param[out] val The signed short value
+   * @return @c 0 on success,
+   *         otherwise a negative error value
+   */
+  int ReadInt16(int16_t* val);
+
+  /**
+   * @brief Reads a signed integer value from the parcel.
+   * @since_tizen 6.5
+   * @param[out] val The signed integer value
+   * @return @c 0 on success,
+   *         otherwise a negative error value
+   */
+  int ReadInt32(int32_t* val);
+
+  /**
+   * @brief Reads a signed long long integer value from the parcel.
+   * @since_tizen 6.5
+   * @param[out] val The signed long long integer value
+   * @return @c 0 on success,
+   *         otherwise a negative error value
+   */
+  int ReadInt64(int64_t* val);
+
+  /**
+   * @brief Reads a floating point value from the parcel.
+   * @since_tizen 6.5
+   * @param[out] val The floating point value
+   * @return @c 0 on success,
+   *         otherwise a negative error value
+   */
+  int ReadFloat(float* val);
+
+  /**
+   * @brief Reads a double precision floating point value from the parcel.
+   * @since_tizen 6.5
+   * @param[out] val The double precision floating point value
+   * @return @c 0 on success,
+   *         otherwise a negative error value
+   */
+  int ReadDouble(double* val);
+
+  /**
+   * @brief Reads a string data from the parcel.
+   * @since_tizen 6.5
+   * @return The string data
+   * @remarks Before using the returned value, you should check the result using get_last_result().
+   * @see get_last_result()
+   */
+  std::string ReadString();
+
+  /**
+   * @brief Reads a string data from the parcel.
+   * @since_tizen 6.5
+   * @remarks You should release @a str using free().
+   * @param[out] str The string data
+   * @return @c 0 on success,
+   *         otherwise a negative error value
+   */
+  int ReadCString(char** str);
+
+  /**
+   * @brief Resets the reader pointer of the parcel to the start.
+   * @since_tizen 6.5
+   */
+  void ResetReader();
+
+  /**
+   * @brief Clears the data of the parcel.
+   * @since_tizen 6.5
+   */
+  void Clear();
+
+  /**
+   * @brief Resets the parcel.
+   * @since_tizen 6.5
+   * @param[in] buf The bytes to write
+   * @param[in] size The size of bytes to write
+   */
+  void Reset(const void* buf, uint32_t size);
+
+  /**
+   * @brief Writes the data using @a parcelable into the parcel.
+   * @since_tizen 6.5
+   * @param[in] parcelable The interface to write the data into the parcel
+   */
+  void WriteParcelable(const Parcelable& parcelable);
+
+  /**
+   * @brief Reads the data using @a parcelable from the parcel.
+   * @since_tizen 6.5
+   * @param[out] parcelable The interface to get data from the parcel
+   * @return @c 0 on success,
+   *         otherwise a negative error value
+   */
+  int ReadParcelable(Parcelable* parcelable);
+
+  /**
+   * @brief Sets byte order of the parcel.
+   * @since_tizen 6.5
+   * @param[in] big_endian @c true, if byte order of the parcel is big-endian
+   */
+  void SetByteOrder(bool big_endian);
+
+  /**
+   * @brief Gets the raw data of the parcel.
+   * @since_tizen 7.0
+   * @return The raw data
+   */
+  uint8_t* GetData() const;
+
+  /**
+   * @breif Gets the size of the raw data of the parcel.
+   * @since_tizen 7.0
+   * @return The size of the raw data
+   */
+  size_t GetDataSize() const;
+
+  /**
+   * @brief Gets the size of the data capacity of the parcel.
+   * @since_tizen 7.0
+   * @return The size of the data capacity
+   */
+  size_t GetDataCapacity() const;
+
+  /**
+   * @breif Sets the size of the data capacity of the parcel.
+   * @since_tizen 7.0
+   * @param[in] size The size of the data capcity
+   */
+  void SetDataCapacity(size_t size);
+
+  /**
+   * @brief Detaches the raw data from the parcel.
+   * @since_tizen 7.0
+   * @param[out] size The size of the raw data
+   * @return The raw data
+   */
+  uint8_t* Detach(size_t* size);
+
+  /**
+   * @brief Gets the position of the reader of the parcel.
+   * @since_tizen 7.0
+   * @return The position of the reader
+   */
+  uint32_t GetReader() const;
+
+  /**
+   * @brief Converts the raw data of the parcel to the vector.
+   * @since_tizen 7.0
+   * @return The vector of the raw data
+   */
+  std::vector<uint8_t> ToRaw();
+
+ private:
+  class Impl;
+  std::unique_ptr<Impl> impl_;
+};
+
+}  // naemspace tizen_base
+
+/**
+ * @}
+ */
+
+#endif  // PARCEL_PARCEL_HH_
diff --git a/src/parcel/parcel.pc.in b/src/parcel/parcel.pc.in
new file mode 100644 (file)
index 0000000..0238b17
--- /dev/null
@@ -0,0 +1,14 @@
+# Package Information for pkg-config
+
+prefix=@PREFIX@
+exec_prefix=${prefix}
+libdir=@LIB_INSTALL_DIR@
+includedir=${prefix}/include
+
+Name: parcel
+Description: Parcel library
+Version: @VERSION@
+Requires: capi-base-common
+Libs: -L${libdir} -lparcel
+Cflags: -I${includedir} -I${includedir}/parcel
+cppflags: -I${includedir} -I${includedir}/parcel
diff --git a/src/parcel/parcel_implementation.hh b/src/parcel/parcel_implementation.hh
new file mode 100644 (file)
index 0000000..d9a9c7d
--- /dev/null
@@ -0,0 +1,71 @@
+/*
+ * Copyright (c) 2020 Samsung Electronics Co., Ltd. All rights reserved.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#ifndef PARCEL_PARCEL_IMPLEMENTATION_HH_
+#define PARCEL_PARCEL_IMPLEMENTATION_HH_
+
+#include <string>
+#include <vector>
+
+#include "parcel/parcel.hh"
+#include "parcel/parcelable.hh"
+
+namespace tizen_base {
+
+class Parcel::Impl {
+ public:
+  virtual ~Impl();
+
+  void Write(const void* buf, uint32_t size);
+  int Read(void* buf, uint32_t size);
+  void ResetReader();
+  void Clear();
+  void Reset(const void* buf, uint32_t size);
+  bool IsEmpty();
+  void WriteSize(uint32_t size);
+  int ReadSize(uint32_t* size);
+
+  template <typename T>
+  void Write(T d);
+  template <typename T>
+  int Read(T* d);
+
+  void SetByteOrder(bool big_endian);
+  bool IsBigEndian() const;
+  uint8_t* GetData() const;
+  size_t GetDataSize() const;
+  size_t GetDataCapacity() const;
+  void SetDataCapacity(size_t size);
+  uint8_t* Detach(size_t* size);
+  uint32_t GetReader() const;
+  std::vector<uint8_t> ToRaw();
+
+ private:
+  friend class Parcel;
+  explicit Impl(Parcel* parent, size_t data_capacity, uint8_t* data = nullptr);
+
+ private:
+  Parcel* parent_;
+  size_t data_capacity_;
+  bool big_endian_ = false;
+  size_t data_size_ = 0;
+  uint8_t* data_ = nullptr;
+  uint32_t reader_ = 0;
+};
+
+}  // naemspace tizen_base
+
+#endif  // PARCEL_PARCEL_IMPLEMENTATION_HH_
diff --git a/src/parcel/parcelable.hh b/src/parcel/parcelable.hh
new file mode 100644 (file)
index 0000000..6dc9471
--- /dev/null
@@ -0,0 +1,76 @@
+/*
+ * Copyright (c) 2020 Samsung Electronics Co., Ltd. All rights reserved.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#ifndef PARCEL_PARCELABLE_HH_
+#define PARCEL_PARCELABLE_HH_
+
+/**
+ * @addtogroup CORE_LIB_PARCEL_MODULE
+ * @{
+ */
+
+#include "parcel/common.hh"
+
+namespace tizen_base {
+
+class Parcel;
+
+/**
+ * @brief The Parcelable interface.
+ * @since_tizen 6.5
+ */
+class EXPORT Parcelable {
+ public:
+  /**
+   * @brief Constructor.
+   * @since_tizen 6.5
+   */
+  Parcelable() = default;
+
+  /**
+   * @brief Copy constructor.
+   * @since_tizen 6.5
+   */
+  Parcelable(const Parcelable&) = default;
+
+  /**
+   * @brief Destructor.
+   * @since_tizen 6.5
+   */
+  virtual ~Parcelable() = default;
+
+  /**
+   * @brief Writes the data into the parcel.
+   * @since_tizen 6.5
+   * @param[in] parcel The parcel object
+   */
+  virtual void WriteToParcel(Parcel* parcel) const = 0;
+
+  /**
+   * @brief Reads the data from the parcel.
+   * @since_tizen 6.5
+   * @param[in] parcel The parcel object
+   */
+  virtual void ReadFromParcel(Parcel* parcel) = 0;
+};
+
+}  // naemspace tizen_base
+
+/**
+ * @}
+ */
+
+#endif  // PARCEL_PARCELABLE_HH_
diff --git a/src/parcel/stub.cc b/src/parcel/stub.cc
new file mode 100644 (file)
index 0000000..245e3ac
--- /dev/null
@@ -0,0 +1,437 @@
+/*
+ * Copyright (c) 2020 Samsung Electronics Co., Ltd. All rights reserved.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#include "parcel/api/parcel.h"
+
+#include <exception>
+
+#include "parcel/common.hh"
+#include "parcel/log_private.hh"
+#include "parcel/parcel.hh"
+#include "parcel/parcelable.hh"
+
+using namespace tizen_base;
+
+extern "C" EXPORT int parcel_create(parcel_h *parcel) {
+  if (parcel == nullptr) {
+    _E("Invalid parameter");
+    return PARCEL_ERROR_INVALID_PARAMETER;
+  }
+
+  auto* h = new (std::nothrow) Parcel();
+  if (h == nullptr) {
+    _E("Out of memory");
+    return PARCEL_ERROR_OUT_OF_MEMORY;
+  }
+
+  *parcel = static_cast<parcel_h>(h);
+  return PARCEL_ERROR_NONE;
+}
+
+extern "C" EXPORT int parcel_destroy(parcel_h parcel) {
+  if (parcel == nullptr) {
+    _E("Invalid parameter");
+    return PARCEL_ERROR_INVALID_PARAMETER;
+  }
+
+  auto* h = static_cast<Parcel*>(parcel);
+  delete h;
+  return PARCEL_ERROR_NONE;
+}
+
+extern "C" EXPORT int parcel_clone(parcel_h parcel, parcel_h* clone) {
+  if (parcel == nullptr || clone == nullptr) {
+    _E("Invalid parameter");
+    return PARCEL_ERROR_INVALID_PARAMETER;
+  }
+
+  auto* h = static_cast<Parcel*>(parcel);
+  auto* c = new (std::nothrow) Parcel(*h);
+  if (c == nullptr) {
+    _E("Out of memory");
+    return PARCEL_ERROR_OUT_OF_MEMORY;
+  }
+
+  *clone = static_cast<parcel_h>(c);
+  return PARCEL_ERROR_NONE;
+}
+
+extern "C" EXPORT int parcel_burst_write(parcel_h parcel, const void *buf,
+    uint32_t size) {
+  if (parcel == nullptr || buf == nullptr || size == 0) {
+    _E("Invalid parameter");
+    return PARCEL_ERROR_INVALID_PARAMETER;
+  }
+
+  auto* h = static_cast<Parcel*>(parcel);
+  h->Write(buf, size);
+  return PARCEL_ERROR_NONE;
+}
+
+extern "C" EXPORT int parcel_burst_read(parcel_h parcel, void *buf,
+    uint32_t size) {
+  if (parcel == nullptr || buf == nullptr || size == 0) {
+    _E("Invalid parameter");
+    return PARCEL_ERROR_INVALID_PARAMETER;
+  }
+
+  auto* h = static_cast<Parcel*>(parcel);
+  h->Read(buf, size);
+  return PARCEL_ERROR_NONE;
+}
+
+extern "C" EXPORT int parcel_write_bool(parcel_h parcel, bool val) {
+  if (parcel == nullptr) {
+    _E("Invalid parameter");
+    return PARCEL_ERROR_INVALID_PARAMETER;
+  }
+
+  auto* h = static_cast<Parcel*>(parcel);
+  h->WriteBool(val);
+  return PARCEL_ERROR_NONE;
+}
+
+extern "C" EXPORT int parcel_write_byte(parcel_h parcel, char val) {
+  if (parcel == nullptr) {
+    _E("Invalid parameter");
+    return PARCEL_ERROR_INVALID_PARAMETER;
+  }
+
+  auto* h = static_cast<Parcel*>(parcel);
+  h->WriteByte(val);
+  return PARCEL_ERROR_NONE;
+}
+
+extern "C" EXPORT int parcel_write_uint16(parcel_h parcel, uint16_t val) {
+  if (parcel == nullptr) {
+    _E("Invalid parameter");
+    return PARCEL_ERROR_INVALID_PARAMETER;
+  }
+
+  auto* h = static_cast<Parcel*>(parcel);
+  h->WriteUInt16(val);
+  return PARCEL_ERROR_NONE;
+}
+
+extern "C" EXPORT int parcel_write_uint32(parcel_h parcel, uint32_t val) {
+  if (parcel == nullptr) {
+    _E("Invalid parameter");
+    return PARCEL_ERROR_INVALID_PARAMETER;
+  }
+
+  auto* h = static_cast<Parcel*>(parcel);
+  h->WriteUInt32(val);
+  return PARCEL_ERROR_NONE;
+}
+
+extern "C" EXPORT int parcel_write_uint64(parcel_h parcel, uint64_t val) {
+  if (parcel == nullptr) {
+    _E("Invalid parameter");
+    return PARCEL_ERROR_INVALID_PARAMETER;
+  }
+
+  auto* h = static_cast<Parcel*>(parcel);
+  h->WriteUInt64(val);
+  return PARCEL_ERROR_NONE;
+}
+
+extern "C" EXPORT int parcel_write_int16(parcel_h parcel, int16_t val) {
+  if (parcel == nullptr) {
+    _E("Invalid parameter");
+    return PARCEL_ERROR_INVALID_PARAMETER;
+  }
+
+  auto* h = static_cast<Parcel*>(parcel);
+  h->WriteInt16(val);
+  return PARCEL_ERROR_NONE;
+}
+
+extern "C" EXPORT int parcel_write_int32(parcel_h parcel, int32_t val) {
+  if (parcel == nullptr) {
+    _E("Invalid parameter");
+    return PARCEL_ERROR_INVALID_PARAMETER;
+  }
+
+  auto* h = static_cast<Parcel*>(parcel);
+  h->WriteInt32(val);
+  return PARCEL_ERROR_NONE;
+}
+
+extern "C" EXPORT int parcel_write_int64(parcel_h parcel, int64_t val) {
+  if (parcel == nullptr) {
+    _E("Invalid parameter");
+    return PARCEL_ERROR_INVALID_PARAMETER;
+  }
+
+  auto* h = static_cast<Parcel*>(parcel);
+  h->WriteInt64(val);
+  return PARCEL_ERROR_NONE;
+}
+
+extern "C" EXPORT int parcel_write_float(parcel_h parcel, float val) {
+  if (parcel == nullptr) {
+    _E("Invalid parameter");
+    return PARCEL_ERROR_INVALID_PARAMETER;
+  }
+
+  auto* h = static_cast<Parcel*>(parcel);
+  h->WriteFloat(val);
+  return PARCEL_ERROR_NONE;
+}
+
+extern "C" EXPORT int parcel_write_double(parcel_h parcel, double val) {
+  if (parcel == nullptr) {
+    _E("Invalid parameter");
+    return PARCEL_ERROR_INVALID_PARAMETER;
+  }
+
+  auto* h = static_cast<Parcel*>(parcel);
+  h->WriteDouble(val);
+  return PARCEL_ERROR_NONE;
+}
+
+extern "C" EXPORT int parcel_write_string(parcel_h parcel, const char* str) {
+  if (parcel == nullptr || str == nullptr) {
+    _E("Invalid parameter");
+    return PARCEL_ERROR_INVALID_PARAMETER;
+  }
+
+  auto* h = static_cast<Parcel*>(parcel);
+  h->WriteCString(str);
+  return PARCEL_ERROR_NONE;
+}
+
+extern "C" EXPORT int parcel_read_bool(parcel_h parcel, bool* val) {
+  if (parcel == nullptr || val == nullptr) {
+    _E("Invalid parameter");
+    return PARCEL_ERROR_INVALID_PARAMETER;
+  }
+
+  auto* h = static_cast<Parcel*>(parcel);
+  return h->ReadBool(val);
+}
+
+extern "C" EXPORT int parcel_read_byte(parcel_h parcel, char* val) {
+  if (parcel == nullptr || val == nullptr) {
+    _E("Invalid parameter");
+    return PARCEL_ERROR_INVALID_PARAMETER;
+  }
+
+  auto* h = static_cast<Parcel*>(parcel);
+  return h->ReadByte(val);
+}
+
+extern "C" EXPORT int parcel_read_uint16(parcel_h parcel, uint16_t* val) {
+  if (parcel == nullptr || val == nullptr) {
+    _E("Invalid parameter");
+    return PARCEL_ERROR_INVALID_PARAMETER;
+  }
+
+  auto* h = static_cast<Parcel*>(parcel);
+  return h->ReadUInt16(val);
+}
+
+extern "C" EXPORT int parcel_read_uint32(parcel_h parcel, uint32_t* val) {
+  if (parcel == nullptr || val == nullptr) {
+    _E("Invalid parameter");
+    return PARCEL_ERROR_INVALID_PARAMETER;
+  }
+
+  auto* h = static_cast<Parcel*>(parcel);
+  return h->ReadUInt32(val);
+}
+
+extern "C" EXPORT int parcel_read_uint64(parcel_h parcel, uint64_t* val) {
+  if (parcel == nullptr || val == nullptr) {
+    _E("Invalid parameter");
+    return PARCEL_ERROR_INVALID_PARAMETER;
+  }
+
+  auto* h = static_cast<Parcel*>(parcel);
+  return h->ReadUInt64(val);
+}
+
+extern "C" EXPORT int parcel_read_int16(parcel_h parcel, int16_t* val) {
+  if (parcel == nullptr || val == nullptr) {
+    _E("Invalid parameter");
+    return PARCEL_ERROR_INVALID_PARAMETER;
+  }
+
+  auto* h = static_cast<Parcel*>(parcel);
+  return h->ReadInt16(val);
+}
+
+extern "C" EXPORT int parcel_read_int32(parcel_h parcel, int32_t* val) {
+  if (parcel == nullptr || val == nullptr) {
+    _E("Invalid parameter");
+    return PARCEL_ERROR_INVALID_PARAMETER;
+  }
+
+  auto* h = static_cast<Parcel*>(parcel);
+  return h->ReadInt32(val);
+}
+
+extern "C" EXPORT int parcel_read_int64(parcel_h parcel, int64_t* val) {
+  if (parcel == nullptr || val == nullptr) {
+    _E("Invalid parameter");
+    return PARCEL_ERROR_INVALID_PARAMETER;
+  }
+
+  auto* h = static_cast<Parcel*>(parcel);
+  return h->ReadInt64(val);
+}
+
+extern "C" EXPORT int parcel_read_float(parcel_h parcel, float* val) {
+  if (parcel == nullptr || val == nullptr) {
+    _E("Invalid parameter");
+    return PARCEL_ERROR_INVALID_PARAMETER;
+  }
+
+  auto* h = static_cast<Parcel*>(parcel);
+  return h->ReadFloat(val);
+}
+
+extern "C" EXPORT int parcel_read_double(parcel_h parcel, double* val) {
+  if (parcel == nullptr || val == nullptr) {
+    _E("Invalid parameter");
+    return PARCEL_ERROR_INVALID_PARAMETER;
+  }
+
+  auto* h = static_cast<Parcel*>(parcel);
+  return h->ReadDouble(val);
+}
+
+extern "C" EXPORT int parcel_read_string(parcel_h parcel, char** str) {
+  if (parcel == nullptr || str == nullptr) {
+    _E("Invalid parameter");
+    return PARCEL_ERROR_INVALID_PARAMETER;
+  }
+
+  auto* h = static_cast<Parcel*>(parcel);
+  return h->ReadCString(str);
+}
+
+extern "C" EXPORT int parcel_reset_reader(parcel_h parcel) {
+  if (parcel == nullptr) {
+    _E("Invalid parameter");
+    return PARCEL_ERROR_INVALID_PARAMETER;
+  }
+
+  auto* h = static_cast<Parcel*>(parcel);
+  h->ResetReader();
+  return PARCEL_ERROR_NONE;
+}
+
+extern "C" EXPORT int parcel_clear(parcel_h parcel) {
+  if (parcel == nullptr) {
+    _E("Invalid parameter");
+    return PARCEL_ERROR_INVALID_PARAMETER;
+  }
+
+  auto* h = static_cast<Parcel*>(parcel);
+  h->Clear();
+  return PARCEL_ERROR_NONE;
+}
+
+extern "C" EXPORT int parcel_reset(parcel_h parcel, const void* buf,
+    uint32_t size) {
+  if (parcel == nullptr || buf == nullptr || size == 0) {
+    _E("Invalid parameter");
+    return PARCEL_ERROR_INVALID_PARAMETER;
+  }
+
+  auto* h = static_cast<Parcel*>(parcel);
+  h->Reset(buf, size);
+  return PARCEL_ERROR_NONE;
+}
+
+extern "C" EXPORT int parcel_write(parcel_h parcel, parcelable_t* parcelable,
+    void* data) {
+  if (parcel == nullptr || parcelable == nullptr || parcelable->to == nullptr) {
+    _E("Invalid parameter");
+    return PARCEL_ERROR_INVALID_PARAMETER;
+  }
+
+  parcelable->to(parcel, data);
+  return PARCEL_ERROR_NONE;
+}
+
+extern "C" EXPORT int parcel_read(parcel_h parcel, parcelable_t* parcelable,
+    void* data) {
+  if (parcel == nullptr || parcelable == nullptr ||
+      parcelable->from == nullptr) {
+    _E("Invalid parameter");
+    return PARCEL_ERROR_INVALID_PARAMETER;
+  }
+
+  parcelable->from(parcel, data);
+  return PARCEL_ERROR_NONE;
+}
+
+extern "C" EXPORT int parcel_get_raw(parcel_h parcel, void** raw,
+    uint32_t* size) {
+  if (parcel == nullptr || raw == nullptr || size == nullptr) {
+    _E("Invalid parameter");
+    return PARCEL_ERROR_INVALID_PARAMETER;
+  }
+
+  auto* h = static_cast<Parcel*>(parcel);
+  *raw = reinterpret_cast<void*>(h->GetData());
+  *size = static_cast<uint32_t>(h->GetDataSize() & UINT32_MAX);
+  return PARCEL_ERROR_NONE;
+}
+
+extern "C" EXPORT int parcel_set_byte_order(parcel_h parcel,
+    bool big_endian) {
+  if (parcel == nullptr) {
+    _E("Invalid parameter");
+    return PARCEL_ERROR_INVALID_PARAMETER;
+  }
+
+  auto* h = static_cast<Parcel*>(parcel);
+  h->SetByteOrder(big_endian);
+  return PARCEL_ERROR_NONE;
+}
+
+extern "C" EXPORT int parcel_get_data_capacity(parcel_h parcel,
+    size_t* size) {
+  if (parcel == nullptr || size == nullptr) {
+    _E("Invalid parameter");
+    return PARCEL_ERROR_INVALID_PARAMETER;
+  }
+
+  auto* h = static_cast<Parcel*>(parcel);
+  *size = h->GetDataCapacity();
+  return PARCEL_ERROR_NONE;
+}
+
+extern "C" EXPORT int parcel_set_data_capacity(parcel_h parcel,
+    size_t size) {
+  if (parcel == nullptr || size == 0) {
+    _E("Invalid parameter");
+    return PARCEL_ERROR_INVALID_PARAMETER;
+  }
+
+  auto* h = static_cast<Parcel*>(parcel);
+  try {
+    h->SetDataCapacity(size);
+  } catch (const std::bad_alloc& e) {
+    _E("Exception occurs. error(%s)", e.what());
+    return PARCEL_ERROR_OUT_OF_MEMORY;
+  }
+
+  return PARCEL_ERROR_NONE;
+}
diff --git a/src/stub.cc b/src/stub.cc
deleted file mode 100644 (file)
index 7d8b84f..0000000
+++ /dev/null
@@ -1,775 +0,0 @@
-/*
- * Copyright (c) 2020 Samsung Electronics Co., Ltd. All rights reserved.
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#include <tizen.h>
-#include <glib.h>
-
-#include <stdexcept>
-
-#include "include/bundle.h"
-#include "include/bundle_internal.h"
-
-#include "bundle-internal.h"
-#include "exception-internal.h"
-#include "export-api-internal.h"
-#include "json-internal.h"
-
-using namespace tizen_base::internal;
-
-extern "C" EXPORT_API bundle* bundle_create(void) {
-  auto* h = new (std::nothrow) Bundle();
-  if (h == nullptr) {
-    set_last_result(BUNDLE_ERROR_OUT_OF_MEMORY);
-    return nullptr;
-  }
-
-  set_last_result(BUNDLE_ERROR_NONE);
-  return reinterpret_cast<bundle*>(h);
-}
-
-extern "C" EXPORT_API int bundle_free(bundle* b) {
-  if (b == nullptr)
-    return BUNDLE_ERROR_INVALID_PARAMETER;
-
-  auto* h = reinterpret_cast<Bundle*>(b);
-  delete h;
-  return BUNDLE_ERROR_NONE;
-}
-
-extern "C" EXPORT_API int bundle_add_str(bundle* b,
-    const char* key, const char* str) {
-  if (b == nullptr || key == nullptr || strlen(key) == 0 || str == nullptr)
-    return BUNDLE_ERROR_INVALID_PARAMETER;
-
-  auto* h = reinterpret_cast<Bundle*>(b);
-  std::vector<unsigned char> value(str, str + (strlen(str) + 1));
-
-  KeyInfo* key_info;
-  try {
-    key_info = new KeyInfo(BUNDLE_TYPE_STR, key, std::move(value));
-  } catch (const Exception& e) {
-    return e.GetErrorCode();
-  } catch (const std::bad_alloc& ba) {
-    return BUNDLE_ERROR_OUT_OF_MEMORY;
-  }
-
-  try {
-    h->Add(std::shared_ptr<KeyInfo>(key_info));
-  } catch (const Exception& e) {
-    return e.GetErrorCode();
-  }
-
-  return BUNDLE_ERROR_NONE;
-}
-
-extern "C" EXPORT_API int bundle_get_str(bundle* b,
-    const char* key, char** str) {
-  if (b == nullptr || key == nullptr)
-    return BUNDLE_ERROR_INVALID_PARAMETER;
-
-  auto* h = reinterpret_cast<Bundle*>(b);
-  std::shared_ptr<KeyInfo> key_info;
-  try {
-    key_info = h->Get(key);
-  } catch (const Exception& e) {
-    return e.GetErrorCode();
-  }
-
-  if (key_info->GetType() != BUNDLE_TYPE_STR)
-    return BUNDLE_ERROR_INVALID_PARAMETER;
-
-  if (str) {
-    auto& values = key_info->GetValues();
-    auto& value = const_cast<std::unique_ptr<unsigned char[]>&>(values[0]);
-    *str = reinterpret_cast<char*>(&value[0]);
-  }
-
-  return BUNDLE_ERROR_NONE;
-}
-
-extern "C" EXPORT_API int bundle_add(bundle* b, const char* key,
-    const char* val) {
-  return bundle_add_str(b, key, val);
-}
-
-extern "C" EXPORT_API int bundle_del(bundle* b, const char* key) {
-  if (b == nullptr || key == nullptr || strlen(key) == 0)
-    return BUNDLE_ERROR_INVALID_PARAMETER;
-
-  auto* h = reinterpret_cast<Bundle*>(b);
-  try {
-    h->Remove(key);
-  } catch (const Exception& e) {
-    return e.GetErrorCode();
-  }
-
-  return BUNDLE_ERROR_NONE;
-}
-
-extern "C" EXPORT_API const char* bundle_get_val(bundle* b, const char* key) {
-  char* val = nullptr;
-  int ret = bundle_get_str(b, key, &val);
-  set_last_result(ret);
-  return val;
-}
-
-extern "C" EXPORT_API int bundle_get_count(bundle* b) {
-  if (b == nullptr)
-    return 0;
-
-  auto* h = reinterpret_cast<Bundle*>(b);
-  set_last_result(BUNDLE_ERROR_NONE);
-  return h->GetSize();
-}
-
-extern "C" EXPORT_API void bundle_iterate(bundle* b,
-    bundle_iterate_cb_t callback, void* user_data) {
-  if (b == nullptr || callback == nullptr) {
-    set_last_result(BUNDLE_ERROR_INVALID_PARAMETER);
-    return;
-  }
-
-  auto* h = reinterpret_cast<Bundle*>(b);
-  for (const auto& [key, key_info] : h->GetMap()) {
-    auto& values = key_info->GetValues();
-    auto& value = const_cast<std::unique_ptr<unsigned char[]>&>(values[0]);
-    auto* val = reinterpret_cast<char*>(&value[0]);
-    callback(key_info->GetKey().c_str(), val, user_data);
-  }
-
-  set_last_result(BUNDLE_ERROR_NONE);
-}
-
-extern "C" EXPORT_API void bundle_foreach(bundle* b,
-    bundle_iterator_t callback, void* user_data) {
-  if (b == nullptr || callback == nullptr) {
-    set_last_result(BUNDLE_ERROR_INVALID_PARAMETER);
-    return;
-  }
-
-  auto* h = reinterpret_cast<Bundle*>(b);
-  auto it = h->GetMap().begin();
-  while (it != h->GetMap().end()) {
-    auto& key_info = it->second;
-    ++it;
-    callback(key_info->GetKey().c_str(), key_info->GetType(),
-             reinterpret_cast<bundle_keyval_t*>(key_info.get()), user_data);
-  }
-
-  set_last_result(BUNDLE_ERROR_NONE);
-}
-
-extern "C" EXPORT_API int bundle_keyval_get_type(bundle_keyval_t* kv) {
-  if (kv == nullptr) {
-    set_last_result(BUNDLE_ERROR_INVALID_PARAMETER);
-    return -1;
-  }
-
-  auto* key_info = reinterpret_cast<KeyInfo*>(kv);
-  set_last_result(BUNDLE_ERROR_NONE);
-  return key_info->GetType();
-}
-
-extern "C" EXPORT_API int bundle_keyval_type_is_array(bundle_keyval_t* kv) {
-  int type = bundle_keyval_get_type(kv);
-  if (type == -1)
-    return -1;
-
-  set_last_result(BUNDLE_ERROR_NONE);
-  if (type & BUNDLE_TYPE_ARRAY)
-    return 1;
-
-  return 0;
-}
-
-extern "C" EXPORT_API int bundle_keyval_type_is_measurable(
-    bundle_keyval_t* kv) {
-  int type = bundle_keyval_get_type(kv);
-  if (type == -1)
-    return -1;
-
-  set_last_result(BUNDLE_ERROR_NONE);
-  if (type & BUNDLE_TYPE_MEASURABLE)
-    return 1;
-
-  return 0;
-}
-
-extern "C" EXPORT_API int bundle_keyval_get_basic_val(bundle_keyval_t* kv,
-    void** val, size_t* size) {
-  if (kv == nullptr)
-    return BUNDLE_ERROR_INVALID_PARAMETER;
-
-  auto* key_info = reinterpret_cast<KeyInfo*>(kv);
-  if (key_info->IsArray())
-    return BUNDLE_ERROR_INVALID_PARAMETER;
-
-  if (val) {
-    auto& values = key_info->GetValues();
-    auto& value = const_cast<std::unique_ptr<unsigned char[]>&>(values[0]);
-    *val = reinterpret_cast<void*>(&value[0]);
-  }
-
-  if (size) {
-    auto& values_size = key_info->GetValuesSize();
-    *size = reinterpret_cast<size_t>(values_size[0]);
-  }
-
-  return BUNDLE_ERROR_NONE;
-}
-
-extern "C" EXPORT_API int bundle_keyval_get_array_val(bundle_keyval_t* kv,
-    void*** array_val, unsigned int* array_len, size_t** array_item_size) {
-  if (kv == nullptr)
-    return BUNDLE_ERROR_INVALID_PARAMETER;
-
-  auto* key_info = reinterpret_cast<KeyInfo*>(kv);
-  if (!key_info->IsArray())
-    return BUNDLE_ERROR_INVALID_PARAMETER;
-
-  auto& values = const_cast<std::vector<std::unique_ptr<unsigned char[]>>&>(
-      key_info->GetValues());
-
-  if (array_val)
-    *array_val = reinterpret_cast<void**>(&values[0]);
-
-  if (array_len)
-    *array_len = static_cast<unsigned int>(values.size());
-
-  if (array_item_size) {
-    auto& values_size = const_cast<std::vector<std::size_t>&>(
-      key_info->GetValuesSize());
-    *array_item_size = reinterpret_cast<size_t*>(&values_size[0]);
-  }
-
-  return BUNDLE_ERROR_NONE;
-}
-
-extern "C" EXPORT_API bundle_keyval_t* bundle_keyval_dup(
-    const bundle_keyval_t* kv) {
-  if (kv == nullptr) {
-    set_last_result(BUNDLE_ERROR_INVALID_PARAMETER);
-    return nullptr;
-  }
-
-  auto* keyval = const_cast<bundle_keyval_t*>(kv);
-  auto* key_info = reinterpret_cast<KeyInfo*>(keyval);
-
-  KeyInfo* k;
-  try {
-    k = new KeyInfo(*key_info);
-  } catch (const Exception& e) {
-    set_last_result(e.GetErrorCode());
-    return nullptr;
-  } catch (const std::bad_alloc& ba) {
-    set_last_result(BUNDLE_ERROR_OUT_OF_MEMORY);
-    return nullptr;
-  }
-
-  set_last_result(BUNDLE_ERROR_NONE);
-  return reinterpret_cast<bundle_keyval_t*>(k);
-}
-
-extern "C" EXPORT_API int bundle_keyval_free(bundle_keyval_t* kv) {
-  if (kv == nullptr)
-    return BUNDLE_ERROR_INVALID_PARAMETER;
-
-  auto* key_info = reinterpret_cast<KeyInfo*>(kv);
-  delete key_info;
-  return BUNDLE_ERROR_NONE;
-}
-
-extern "C" EXPORT_API bundle* bundle_dup(bundle* b_from) {
-  if (b_from == nullptr) {
-    set_last_result(BUNDLE_ERROR_INVALID_PARAMETER);
-    return nullptr;
-  }
-
-  Bundle* b;
-  try {
-    auto* h = reinterpret_cast<Bundle*>(b_from);
-    b = new Bundle(*h);
-  } catch (const Exception& e) {
-    set_last_result(e.GetErrorCode());
-    return nullptr;
-  } catch (const std::bad_alloc& e) {
-    set_last_result(BUNDLE_ERROR_OUT_OF_MEMORY);
-    return nullptr;
-  }
-
-  set_last_result(BUNDLE_ERROR_NONE);
-  return reinterpret_cast<bundle*>(b);
-}
-
-extern "C" EXPORT_API int bundle_encode(bundle *b, bundle_raw** raw, int* len) {
-  if (b == nullptr || raw == nullptr || len == nullptr)
-    return BUNDLE_ERROR_INVALID_PARAMETER;
-
-  auto* h = reinterpret_cast<Bundle*>(b);
-  try {
-    *raw = reinterpret_cast<bundle_raw*>(h->Encode());
-  } catch (const Exception& e) {
-    *raw = nullptr;
-    return e.GetErrorCode();
-  }
-
-  *len = strlen(reinterpret_cast<char*>(*raw));
-  return BUNDLE_ERROR_NONE;
-}
-
-extern "C" EXPORT_API int bundle_free_encoded_rawdata(bundle_raw **r) {
-  if (r == nullptr || *r == nullptr)
-    return BUNDLE_ERROR_INVALID_PARAMETER;
-
-  free(*r);
-  *r = nullptr;
-  return BUNDLE_ERROR_NONE;
-}
-
-extern "C" EXPORT_API bundle* bundle_decode(const bundle_raw* r,
-    const int data_size) {
-  if (r == nullptr) {
-    set_last_result(BUNDLE_ERROR_INVALID_PARAMETER);
-    return nullptr;
-  }
-
-  Bundle* b = nullptr;
-  try {
-    auto* raw = const_cast<bundle_raw*>(r);
-    b = new Bundle(static_cast<unsigned char*>(raw), data_size);
-  } catch (const Exception& e) {
-    set_last_result(e.GetErrorCode());
-    return nullptr;
-  } catch (const std::bad_alloc& ba) {
-    set_last_result(BUNDLE_ERROR_OUT_OF_MEMORY);
-    return nullptr;
-  }
-
-  set_last_result(BUNDLE_ERROR_NONE);
-  return reinterpret_cast<bundle*>(b);
-}
-
-extern "C" EXPORT_API int bundle_encode_raw(bundle* b, bundle_raw** r,
-    int* len) {
-  if (b == nullptr || r == nullptr || len == nullptr)
-    return BUNDLE_ERROR_INVALID_PARAMETER;
-
-  auto* h = reinterpret_cast<Bundle*>(b);
-  try {
-    *r = reinterpret_cast<bundle_raw*>(h->EncodeRaw(len));
-  } catch (const Exception& e) {
-    return e.GetErrorCode();
-  }
-  return BUNDLE_ERROR_NONE;
-}
-
-extern "C" EXPORT_API bundle* bundle_decode_raw(const bundle_raw* r,
-    const int data_size) {
-  if (r == nullptr) {
-    set_last_result(BUNDLE_ERROR_INVALID_PARAMETER);
-    return nullptr;
-  }
-
-  Bundle* b = nullptr;
-  try {
-    auto* raw = const_cast<bundle_raw*>(r);
-    b = new Bundle(static_cast<unsigned char*>(raw), data_size, false);
-  } catch (const Exception& e) {
-    set_last_result(e.GetErrorCode());
-    return nullptr;
-  } catch (const std::bad_alloc& ba) {
-    set_last_result(BUNDLE_ERROR_OUT_OF_MEMORY);
-    return nullptr;
-  }
-
-  set_last_result(BUNDLE_ERROR_NONE);
-  return reinterpret_cast<bundle*>(b);
-}
-
-extern "C" EXPORT_API int bundle_get_type(bundle* b, const char* key) {
-  if (b == nullptr || key == nullptr) {
-    set_last_result(BUNDLE_ERROR_INVALID_PARAMETER);
-    return BUNDLE_TYPE_NONE;
-  }
-
-  auto* h = reinterpret_cast<Bundle*>(b);
-  std::shared_ptr<KeyInfo> key_info;
-  try {
-    key_info = h->Get(key);
-  } catch (const Exception& e) {
-    set_last_result(e.GetErrorCode());
-    return BUNDLE_TYPE_NONE;
-  }
-
-  set_last_result(BUNDLE_ERROR_NONE);
-  return key_info->GetType();
-}
-
-extern "C" EXPORT_API int bundle_add_str_array(bundle* b, const char* key,
-    const char** str_array, const int len) {
-  if (b == nullptr || key == nullptr || strlen(key) == 0)
-    return BUNDLE_ERROR_INVALID_PARAMETER;
-
-  auto* h = reinterpret_cast<Bundle*>(b);
-  std::vector<std::vector<unsigned char>> values(len);
-  if (str_array) {
-    for (int i = 0; i < len; ++i) {
-      std::vector<unsigned char> value(str_array[i],
-          str_array[i] + (strlen(str_array[i]) + 1));
-      values[i] = std::move(value);
-    }
-  }
-
-  try {
-    auto key_info = std::make_shared<KeyInfo>(
-        (BUNDLE_TYPE_STR_ARRAY | BUNDLE_TYPE_ARRAY), key, values);
-    h->Add(std::move(key_info));
-  } catch (const Exception& e) {
-    return e.GetErrorCode();
-  } catch (const std::bad_alloc& ba) {
-    return BUNDLE_ERROR_OUT_OF_MEMORY;
-  }
-
-  return BUNDLE_ERROR_NONE;
-}
-
-extern "C" EXPORT_API const char** bundle_get_str_array(bundle* b,
-    const char* key, int* len) {
-  if (b == nullptr || key == nullptr) {
-    set_last_result(BUNDLE_ERROR_INVALID_PARAMETER);
-    return nullptr;
-  }
-
-  auto* h = reinterpret_cast<Bundle*>(b);
-  std::shared_ptr<KeyInfo> key_info;
-  try {
-    key_info = h->Get(key);
-  } catch (const Exception& e) {
-    set_last_result(e.GetErrorCode());
-    return nullptr;
-  }
-
-  if (key_info->GetType() != BUNDLE_TYPE_STR_ARRAY) {
-    set_last_result(BUNDLE_ERROR_INVALID_PARAMETER);
-    return nullptr;
-  }
-
-  set_last_result(BUNDLE_ERROR_NONE);
-
-  auto& raw_values = const_cast<std::vector<std::unique_ptr<unsigned char[]>>&>(
-      key_info->GetValues());
-
-  if (len)
-    *len = static_cast<int>(raw_values.size());
-
-  if (raw_values.size() == 0)
-    return nullptr;
-
-  auto** values = reinterpret_cast<unsigned char**>(&raw_values[0]);
-  return const_cast<const char**>(reinterpret_cast<char**>(values));
-}
-
-extern "C" EXPORT_API int bundle_add_byte(bundle* b, const char* key,
-    const void* bytes, const size_t size) {
-  if (b == nullptr || key == nullptr || strlen(key) == 0)
-    return BUNDLE_ERROR_INVALID_PARAMETER;
-
-  auto* h = reinterpret_cast<Bundle*>(b);
-  auto* p = reinterpret_cast<const unsigned char*>(bytes);
-  std::vector<unsigned char> value;
-  if (bytes)
-    value.insert(value.end(), p, p + size);
-
-  KeyInfo* key_info;
-  try {
-    key_info = new KeyInfo(BUNDLE_TYPE_BYTE, key, std::move(value));
-  } catch (const Exception& e) {
-    return e.GetErrorCode();
-  } catch (const std::bad_alloc& ba) {
-    return BUNDLE_ERROR_OUT_OF_MEMORY;
-  }
-
-  try {
-    h->Add(std::shared_ptr<KeyInfo>(key_info));
-  } catch (const Exception& e) {
-    return e.GetErrorCode();
-  }
-
-  return BUNDLE_ERROR_NONE;
-}
-
-extern "C" EXPORT_API int bundle_get_byte(bundle* b, const char* key,
-    void** bytes, size_t* size) {
-  if (b == nullptr || key == nullptr)
-    return BUNDLE_ERROR_INVALID_PARAMETER;
-
-  auto* h = reinterpret_cast<Bundle*>(b);
-  std::shared_ptr<KeyInfo> key_info;
-  try {
-    key_info = h->Get(key);
-  } catch (const Exception& e) {
-    return e.GetErrorCode();
-  }
-
-  if (key_info->GetType() != BUNDLE_TYPE_BYTE)
-    return BUNDLE_ERROR_INVALID_PARAMETER;
-
-  if (bytes) {
-    auto& values = const_cast<std::vector<std::unique_ptr<unsigned char[]>>&>(
-        key_info->GetValues());
-    if (values.size() == 0) {
-      *bytes = nullptr;
-    } else {
-      auto& value = values[0];
-      *bytes = reinterpret_cast<void*>(&value[0]);
-    }
-  }
-
-  if (size) {
-    auto& values_size = key_info->GetValuesSize();
-    *size = reinterpret_cast<size_t>(values_size[0]);
-  }
-
-  return BUNDLE_ERROR_NONE;
-}
-
-extern "C" EXPORT_API int bundle_export_to_argv(bundle* b, char*** argv) {
-  if (b == nullptr || argv == nullptr) {
-    set_last_result(BUNDLE_ERROR_INVALID_PARAMETER);
-    return -1;
-  }
-
-  auto* h = reinterpret_cast<Bundle*>(b);
-  std::vector<std::string> exported_vt;
-  try {
-    exported_vt = h->Export();
-  } catch (const Exception& e) {
-    set_last_result(e.GetErrorCode());
-    return -1;
-  }
-
-  int argc = exported_vt.size();
-  auto** exported_argv = reinterpret_cast<char**>(
-      calloc(argc + 1, sizeof(char*)));
-  if (exported_argv == nullptr) {
-    set_last_result(BUNDLE_ERROR_OUT_OF_MEMORY);
-    return -1;
-  }
-
-  exported_argv[1] = const_cast<char*>(TAG_IMPORT_EXPORT_CHECK);
-  for (unsigned int idx = 2; idx < exported_vt.size(); idx += 2) {
-    exported_argv[idx] = strdup(exported_vt[idx].c_str());
-    if (exported_argv[idx] == nullptr) {
-      set_last_result(BUNDLE_ERROR_OUT_OF_MEMORY);
-      bundle_free_exported_argv(idx + 1, &exported_argv);
-      return -1;
-    }
-
-    exported_argv[idx + 1] = strdup(exported_vt[idx + 1].c_str());
-    if (exported_argv[idx + 1] == nullptr) {
-      set_last_result(BUNDLE_ERROR_OUT_OF_MEMORY);
-      bundle_free_exported_argv(idx + 2, &exported_argv);
-      return -1;
-    }
-  }
-
-  *argv = exported_argv;
-  set_last_result(BUNDLE_ERROR_NONE);
-  return argc;
-}
-
-extern "C" EXPORT_API int bundle_free_exported_argv(int argc, char*** argv) {
-  if (argc < 2 || !argv || !*argv)
-    return BUNDLE_ERROR_INVALID_PARAMETER;
-
-  for (int i = 2; i < argc; i++)
-    std::free((*argv)[i]);
-
-  std::free(*argv);
-  *argv = nullptr;
-
-  return BUNDLE_ERROR_NONE;
-}
-
-extern "C" EXPORT_API bundle* bundle_import_from_argv(int argc, char** argv) {
-  if (argv == nullptr) {
-    set_last_result(BUNDLE_ERROR_INVALID_PARAMETER);
-    return nullptr;
-  }
-
-  Bundle* b = nullptr;
-  try {
-    b = new (std::nothrow) Bundle(argc, argv);
-  } catch (const Exception& e) {
-    set_last_result(e.GetErrorCode());
-    return nullptr;
-  }
-
-  set_last_result(BUNDLE_ERROR_NONE);
-  return reinterpret_cast<bundle*>(b);
-}
-
-extern "C" EXPORT_API int bundle_compare(bundle* b1, bundle* b2) {
-  if (b1 == nullptr || b2 == nullptr)
-    return -1;
-
-  auto* h1 = reinterpret_cast<Bundle*>(b1);
-  auto* h2 = reinterpret_cast<Bundle*>(b2);
-  if (*h1 == *h2)
-    return 0;
-
-  return 1;
-}
-
-extern "C" EXPORT_API int bundle_set_str_array_element(bundle* b,
-    const char* key, const unsigned int idx, const char* val) {
-  if (b == nullptr || key == nullptr || val == nullptr)
-    return BUNDLE_ERROR_INVALID_PARAMETER;
-
-  auto len = strlen(val) + 1;
-  auto* p = reinterpret_cast<unsigned char*>(const_cast<char*>(val));
-  std::vector<unsigned char> value(p, p + len);
-
-  auto* h = reinterpret_cast<Bundle*>(b);
-  try {
-    h->Set(key, idx, std::move(value));
-  } catch (const Exception& e) {
-    return e.GetErrorCode();
-  }
-
-  return BUNDLE_ERROR_NONE;
-}
-
-extern "C" EXPORT_API int bundle_add_byte_array(bundle* b,
-    const char* key, const unsigned int len) {
-  return bundle_init_byte_array(b, key, len);
-}
-
-extern "C" EXPORT_API int bundle_init_byte_array(bundle* b,
-    const char* key, const unsigned int len) {
-  if (b == nullptr || key == nullptr || strlen(key) == 0)
-    return BUNDLE_ERROR_INVALID_PARAMETER;
-
-  auto* h = reinterpret_cast<Bundle*>(b);
-
-  KeyInfo* key_info;
-  try {
-    std::vector<std::vector<unsigned char>> values(len);
-    key_info = new KeyInfo(Bundle::Type::ByteArray, key, std::move(values));
-  } catch (const Exception& e) {
-    return e.GetErrorCode();
-  } catch (const std::bad_alloc& ba) {
-    return BUNDLE_ERROR_OUT_OF_MEMORY;
-  } catch (const std::length_error&) {
-    return BUNDLE_ERROR_OUT_OF_MEMORY;
-  }
-
-  try {
-    h->Add(std::shared_ptr<KeyInfo>(key_info));
-  } catch (const Exception& e) {
-    return e.GetErrorCode();
-  }
-
-  return BUNDLE_ERROR_NONE;
-}
-
-extern "C" EXPORT_API int bundle_get_byte_array(bundle* b,
-    const char* key, void*** bytes_array, unsigned int* len,
-    unsigned int** array_element_size) {
-  if (b == nullptr || key == nullptr)
-    return BUNDLE_ERROR_INVALID_PARAMETER;
-
-  auto* h = reinterpret_cast<Bundle*>(b);
-  std::shared_ptr<KeyInfo> key_info;
-  try {
-    key_info = h->Get(key);
-  } catch (const Exception& e) {
-    return e.GetErrorCode();
-  }
-
-  if (key_info->GetType() != BUNDLE_TYPE_BYTE_ARRAY)
-    return BUNDLE_ERROR_INVALID_PARAMETER;
-
-  auto& raw_values = const_cast<std::vector<std::unique_ptr<unsigned char[]>>&>(
-      key_info->GetValues());
-
-  if (bytes_array) {
-    auto** values = reinterpret_cast<unsigned char**>(&raw_values[0]);
-    *bytes_array = reinterpret_cast<void**>(values);
-  }
-
-  if (len)
-    *len = static_cast<unsigned int>(raw_values.size());
-
-  if (array_element_size) {
-    auto& raw_values_size = const_cast<std::vector<unsigned int>&>(
-        key_info->GetUValuesSize());
-    *array_element_size = reinterpret_cast<unsigned int*>(&raw_values_size[0]);
-  }
-
-  return BUNDLE_ERROR_NONE;
-}
-
-extern "C" EXPORT_API int bundle_set_byte_array_element(bundle* b,
-    const char* key, const unsigned int idx,
-    const void* bytes, const size_t size) {
-  if (b == nullptr || key == nullptr || size <= 0)
-    return BUNDLE_ERROR_INVALID_PARAMETER;
-
-  std::vector<unsigned char> value;
-  if (bytes) {
-    auto* p = reinterpret_cast<unsigned char*>(const_cast<void*>(bytes));
-    value.insert(value.end(), p, p + size);
-  }
-
-  auto* h = reinterpret_cast<Bundle*>(b);
-  try {
-    h->Set(key, idx, std::move(value));
-  } catch (const Exception& e) {
-    return e.GetErrorCode();
-  }
-
-  return BUNDLE_ERROR_NONE;
-}
-
-extern "C" EXPORT_API int bundle_to_json(bundle* b, char** json) {
-  if (b == nullptr || json == nullptr)
-    return BUNDLE_ERROR_INVALID_PARAMETER;
-
-  auto* h = reinterpret_cast<Bundle*>(b);
-  Json js(h);
-  try {
-    *json = strdup(js.ToString().c_str());
-  } catch (const Exception& e) {
-    return e.GetErrorCode();
-  }
-
-  return BUNDLE_ERROR_NONE;
-}
-
-extern "C" EXPORT_API int bundle_from_json(const char* json, bundle** b) {
-  if (json == nullptr || b == nullptr)
-    return BUNDLE_ERROR_INVALID_PARAMETER;
-
-  Json js(json);
-  try {
-    *b = reinterpret_cast<bundle*>(js.ToBundle());
-  } catch (const Exception& e) {
-    return e.GetErrorCode();
-  }
-
-  return BUNDLE_ERROR_NONE;
-}
diff --git a/src/tizen-database/CMakeLists.txt b/src/tizen-database/CMakeLists.txt
new file mode 100644 (file)
index 0000000..fe66efd
--- /dev/null
@@ -0,0 +1,7 @@
+CONFIGURE_FILE(${CMAKE_CURRENT_SOURCE_DIR}/tizen-database.pc.in
+  ${CMAKE_BINARY_DIR}/tizen-database.pc @ONLY)
+
+INSTALL(FILES ${CMAKE_BINARY_DIR}/tizen-database.pc
+  DESTINATION ${LIB_INSTALL_DIR}/pkgconfig/)
+INSTALL(FILES ${CMAKE_CURRENT_SOURCE_DIR}/database.hpp
+  DESTINATION include/tizen-database)
diff --git a/src/tizen-database/README.md b/src/tizen-database/README.md
new file mode 100644 (file)
index 0000000..00b5e94
--- /dev/null
@@ -0,0 +1,217 @@
+# TizenDatabase
+Wrapper class for sqlite3
+
+## Source
+See database.hpp
+
+## Require
+sqlite3, C++17
+
+## How to use?
+Add 'BuildRequires: pkgconfig(tizen-database)' in your .spec file.
+
+## Cookbook
+
+### Auto close
+- It was implemented by RAII idiom. Database is automatically closed when it exits the scope.
+```cpp
+void test() {
+  tizen_base::Database db("test.db", SQLITE_OPEN_READWRITE);
+  ...
+}
+```
+
+### Binding
+- Bind() method supports various data type such as std::string, int, double and std::vector<unsigned char>.
+
+```cpp
+  tizen_base::Database db("test.db", SQLITE_OPEN_READWRITE);
+  auto q = tizen_base::Database::Sql(
+      "INSERT INTO TestTable(name, num, val, data) VALUES (?, ?, ?, ?);")
+      .Bind("gogo")
+      .Bind(1234)
+      .Bind(9.216)
+      .Bind( std::vector<unsigned char> {'9', '2', '1', '6' } );
+```
+
+- Bind() method also supports named tag using ':'.
+```cpp
+  tizen_base::Database db("test.db", SQLITE_OPEN_READWRITE);
+  auto q = tizen_base::Database::Sql("INSERT INTO TestTable(name, num, val, data) VALUES (:name, :num, :val, :data);")
+      .Bind(":name", "gogo")
+      .Bind(":num", 1234)
+      .Bind(":val", 9.216)
+      .Bind(":data", std::vector<unsigned char> {'9', '2', '1', '6' });
+```
+
+### Null-type binding
+- Null-type binding is supported using 'std::nullopt'.
+
+```cpp
+  tizen_base::Database db("test.db", SQLITE_OPEN_READWRITE);
+  auto q = tizen_base::Database::Sql(
+      "INSERT INTO TestTable(name, num, val, data) VALUES (?, ?, ?, ?);")
+      .Bind(std::nullopt)
+      .Bind(1234)
+      .Bind(9.216)
+      .Bind(std::nullopt);
+```
+- To get nullable object, you can use 'std::optional<>'.
+```cpp
+  for (const auto& i : r) {
+    std::optional<std::string> name = i.Get(0);
+    double val = static_cast<double>(i.Get(2));
+    std::optional<std::vector<unsigned char>> data = i.Get(3);
+    ...
+  }
+```
+
+### Structured binding declaration
+```cpp
+  auto [name, num, val, data] = i.Get<_, _, _, _>();
+```
+- Structured binding declaration can be used to unpack the record.
+
+```cpp
+  for (const auto& i : db.Exec({ "SELECT name, num, val, data FROM TestTable;" })) {
+    auto [name, num, val, data] = i.Get<_, _, _, _>();
+    std::cout << static_cast<std::string>(name) << std::endl;
+  }
+```
+
+### Range-based for loop
+- class 'Result' is iterable.
+
+```cpp
+  tizen_base::Database::Result r =
+      db.Exec({ "SELECT name, num, val, data FROM TestTable;" });
+  for (const auto& i : r) {
+    ...
+  }
+```
+
+### 'bool' type and 'int' type conversion operator
+- 'bool' type operator is supported to check errors.
+- 'int' type operator is supported to get error number.
+```cpp
+  auto r = db.Exec(q);
+  if (!r) {
+    std::cout << "error code:" << static_cast<int>(r) << std::endl;
+  }
+```
+
+### 'const char*' type conversion operator
+- 'const char*' type operator is supported to get error string
+```cpp
+  auto r = db.Exec(q);
+  if (!r) {
+    std::cout << "error message:" << static_cast<const char*>(r) << std::endl;
+  }
+```
+
+### Extract values from query results
+- There are many conversion operators to get the value.
+```cpp
+  for (const auto& i : db.Exec({ "SELECT name, num, val, data FROM TestTable;" })) {
+    auto name = static_cast<std::string>(i.Get(0));
+    auto num = static_cast<int>(i.Get(1));
+    auto val = static_cast<double>(i.Get(2));
+    auto data = static_cast<std::vector<unsigned char>>(i.Get(3));
+  }
+```
+
+### ToList(), ToVector() methods
+- Once you provide function operator in your classes, you can call the methods.
+- The class or struct should be movable.
+```cpp
+  struct MyRec {
+    std::string Id;
+    int Val;
+
+    // It should be implemented to map data set
+    void operator () (const tizen_base::Database::Result::Record& rec) {
+      Id = static_cast<std::string>(rec.Get(0));
+      Val = static_cast<int>(rec.Get(1));
+    }
+  };
+
+  auto /*std::vector<MyRec>*/ table =
+      db.Exec({ "SELECT id, val FROM TestTable;" }).ToVector<MyRec>();
+```
+
+### Transaction guard
+```cpp
+void test() {
+  tizen_base::Database db("test.db", SQLITE_OPEN_READWRITE);
+  auto guard = db.CreateTransactionGuard();
+
+  auto r = db.Exec({ "INSERT INTO MyTable(name, id) VALUES('gogo', 1);" });
+  if (!r)
+    return; // Rollback
+
+  auto r2 = db.Exec({ "INSERT INTO MyTable(name, id) VALUES('gugu', 2);" });
+  if (!r2)
+    return; // Rollback
+
+  guard.Commit();
+}
+```
+
+### Busy handler
+```cpp
+void test() {
+  tizen_base::Database db("test.db", SQLITE_OPEN_READWRITE, [&](int count) {
+    // Busy handler
+    usleep(BUSY_WAITING_USEC);
+    if (count < 10)
+      return true;
+
+    return false;
+  });
+  ...
+}
+```
+
+### Samples
+```cpp
+void test() {
+  tizen_base::Database db("test.db", SQLITE_OPEN_READWRITE);
+  for (const auto& i : db.Exec({ "SELECT name, num, val, data FROM TestTable;" })) {
+    auto [name, num, val, data] = i.Get<_, _, _, _>();
+    std::cout << static_cast<std::string>(name) << std::endl;
+  }
+}
+```
+
+```cpp
+void test() {
+  tizen_base::Database db("test.db", SQLITE_OPEN_READWRITE);
+  auto q = tizen_base::Database::Sql("INSERT INTO TestTable(name, num, val, data) VALUES (?, ?, ?, ?);")
+      .Bind("gogo")
+      .Bind(1234)
+      .Bind(9.216)
+      .Bind( std::vector<unsigned char> {'9', '2', '1', '6' } );
+  auto r = db.Exec(q);
+  if (!r) {
+    std::cout << "insert failed:" << r << std::endl;
+    std::cout << "error code:" << static_cast<int>(r) << std::endl;
+  }
+}
+```
+
+```cpp
+void test() {
+  tizen_base::Database db("test.db", SQLITE_OPEN_READWRITE);
+  auto q = tizen_base::Database::Sql(
+      "INSERT INTO TestTable(name, num, val, data) VALUES (:name, :num, :val, :data);")
+      .Bind(":name", "gogo")
+      .Bind(":num", 1234)
+      .Bind(":val", 9.216)
+      .Bind(":data", std::vector<unsigned char> {'9', '2', '1', '6' });
+  auto r = db.Exec(q);
+  if (!r) {
+    std::cout << "insert failed:" << r << std::endl;
+    std::cout << "error code:" << static_cast<int>(r) << std::endl;
+  }
+}
+```
diff --git a/src/tizen-database/database.hpp b/src/tizen-database/database.hpp
new file mode 100644 (file)
index 0000000..c5f1f72
--- /dev/null
@@ -0,0 +1,881 @@
+/*
+ * Copyright (c) 2022 Samsung Electronics Co., Ltd. All rights reserved.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#ifndef TIZEN_DATABASE_DATABASE_HPP_
+#define TIZEN_DATABASE_DATABASE_HPP_
+
+#include <sqlite3.h>
+
+#include <functional>
+#include <list>
+#include <map>
+#include <memory>
+#include <optional>
+#include <stdexcept>
+#include <string>
+#include <tuple>
+#include <utility>
+#include <variant>
+#include <vector>
+
+namespace tizen_base {
+
+template<std::size_t N>
+struct num {
+  static const constexpr auto value = N;
+};
+
+template <class F, std::size_t... Is>
+void for_(F func, std::index_sequence<Is...>) {
+  (func(num<Is>{}), ...);
+}
+
+template <std::size_t N, typename F>
+void for_(F func) {
+  for_(func, std::make_index_sequence<N>());
+}
+
+using DbType = std::optional<std::variant<int64_t, double, std::string,
+    std::vector<unsigned char>>>;
+
+class DbException : public std::runtime_error {
+ public:
+  explicit DbException(const std::string& msg, int code = SQLITE_ERROR)
+      : std::runtime_error(msg), code_(code) {
+  }
+
+  DbException(const std::string& msg, int code, const std::string& file,
+      int line) : std::runtime_error(msg), code_(code) {
+    msg_ = msg + " at " + file + ":" + std::to_string(line);
+  }
+
+  int code() const {
+    return code_;
+  }
+
+  const char* msg() const {
+    if (msg_.empty())
+      return what();
+    return msg_.c_str();
+  }
+
+ private:
+  int code_;
+  std::string msg_;
+};
+
+class AutoDbType {
+ public:
+  AutoDbType() = default;
+  explicit AutoDbType(DbType db_type, int real_type)
+      : db_type_(db_type), real_type_(real_type) {}
+
+  int GetType() const {
+    return real_type_;
+  }
+
+  explicit operator int () {
+    if (!db_type_)
+      throw DbException("invalid type conversion from nullopt to int");
+    if (real_type_ != SQLITE_INTEGER)
+      throw DbException("invalid type conversion to int");
+
+    return std::get<int64_t>(*db_type_);
+  }
+
+  explicit operator int64_t () {
+    if (!db_type_)
+      throw DbException("invalid type conversion from nullopt to int64_t");
+    if (real_type_ != SQLITE_INTEGER)
+      throw DbException("invalid type conversion to int64_t");
+
+    return std::get<int64_t>(*db_type_);
+  }
+
+  explicit operator std::string () {
+    if (!db_type_) {
+      throw DbException(
+          "invalid type conversion from nullopt to string");
+    }
+
+    if (real_type_ != SQLITE_TEXT)
+      throw DbException("invalid type conversion to string");
+
+    return std::get<std::string>(*db_type_);
+  }
+
+  explicit operator double () {
+    if (!db_type_) {
+      throw DbException(
+          "invalid type conversion from nullopt to double");
+    }
+
+    if (real_type_ != SQLITE_FLOAT)
+      throw DbException("invalid type conversion to double");
+
+    return std::get<double>(*db_type_);
+  }
+
+  explicit operator std::vector<unsigned char> () {
+    if (!db_type_) {
+      throw DbException(
+          "invalid type conversion from nullopt to std::vector<unsigned char>");
+    }
+
+    if (real_type_ != SQLITE_BLOB)
+      throw DbException("invalid type conversion to std::vector<unsigned char>");
+
+    return std::get<std::vector<unsigned char>>(*db_type_);
+  }
+
+  operator std::optional<int> () {
+    if (!db_type_)
+      return std::nullopt;
+    if (real_type_ != SQLITE_INTEGER)
+      throw DbException("invalid type conversion to int");
+
+    return std::get<int64_t>(*db_type_);
+  }
+
+  operator std::optional<int64_t> () {
+    if (!db_type_)
+      return std::nullopt;
+    if (real_type_ != SQLITE_INTEGER)
+      throw DbException("invalid type conversion to int64_t");
+
+    return std::get<int64_t>(*db_type_);
+  }
+
+  operator std::optional<std::string> () {
+    if (!db_type_)
+      return std::nullopt;
+    if (real_type_ != SQLITE_TEXT)
+      throw DbException("invalid type conversion to string");
+
+    return std::get<std::string>(*db_type_);
+  }
+
+  operator std::optional<double> () {
+    if (!db_type_)
+      return std::nullopt;
+    if (real_type_ != SQLITE_FLOAT)
+      throw DbException("invalid type conversion to double");
+
+    return std::get<double>(*db_type_);
+  }
+
+  operator std::optional<std::vector<unsigned char>> () {
+    if (!db_type_)
+      return std::nullopt;
+    if (real_type_ != SQLITE_BLOB)
+      throw DbException("invalid type conversion to std::vector<unsigned char>");
+
+    return std::get<std::vector<unsigned char>>(*db_type_);
+  }
+
+ private:
+  DbType db_type_;
+  int real_type_ = SQLITE_NULL;
+};
+
+using _ = AutoDbType;
+
+class Database {
+ public:
+  class TransactionGuard {
+   public:
+    TransactionGuard(const TransactionGuard&) = delete;
+    TransactionGuard& operator = (const TransactionGuard&) = delete;
+
+    TransactionGuard(TransactionGuard&& t) noexcept {
+      db_ = std::move(t.db_);
+    }
+
+    TransactionGuard& operator = (TransactionGuard&& t) noexcept {
+      if (this != &t) {
+        if (!db_.expired())
+          sqlite3_exec(db_.lock().get(), "ROLLBACK", nullptr, nullptr, nullptr);
+        db_ = std::move(t.db_);
+      }
+
+      return *this;
+    }
+
+    explicit TransactionGuard(const std::shared_ptr<sqlite3>& db)
+        : db_(db) {
+      int r = sqlite3_exec(db_.lock().get(), "BEGIN DEFERRED",
+          nullptr, nullptr, nullptr);
+      if (r != SQLITE_OK) {
+        throw DbException("begin transaction failed", r);
+      }
+    }
+
+    ~TransactionGuard() {
+      if (!db_.expired())
+        sqlite3_exec(db_.lock().get(), "ROLLBACK", nullptr, nullptr, nullptr);
+    }
+
+    int Commit() {
+      if (db_.expired())
+        return SQLITE_OK;
+
+      auto db = db_.lock();
+      int ret = sqlite3_exec(db.get(), "COMMIT", nullptr, nullptr, nullptr);
+      if (ret != SQLITE_OK) {
+        sqlite3_exec(db.get(), "ROLLBACK", nullptr, nullptr, nullptr);
+      }
+
+      return ret;
+    }
+
+   private:
+    std::weak_ptr<sqlite3> db_;
+  };
+
+  class Sql {
+   public:
+    Sql(std::string query) : query_(std::move(query)) {}
+
+    Sql& Bind(const char* val) {
+      if (val == nullptr) {
+        bindings_.push_back(DbType(std::nullopt));
+      } else {
+        std::string str = val;
+        if (empty_string_as_null_ && str.empty())
+          bindings_.push_back(DbType(std::nullopt));
+        else
+          bindings_.push_back(DbType(std::move(str)));
+      }
+      return *this;
+    }
+
+    Sql& Bind(std::string val) {
+      if (empty_string_as_null_ && val.empty())
+        bindings_.push_back(DbType(std::nullopt));
+      else
+        bindings_.push_back(DbType(std::move(val)));
+      return *this;
+    }
+
+    Sql& Bind(int val) {
+      bindings_.push_back(DbType(static_cast<int64_t>(val)));
+      return *this;
+    }
+
+    Sql& Bind(int64_t val) {
+      bindings_.push_back(DbType(val));
+      return *this;
+    }
+
+    Sql& Bind(double val) {
+      bindings_.push_back(DbType(val));
+      return *this;
+    }
+
+    Sql& Bind(std::vector<unsigned char> val) {
+      if (empty_vector_as_null_ && val.empty())
+        bindings_.push_back(DbType(std::nullopt));
+      else
+        bindings_.push_back(DbType(std::move(val)));
+      return *this;
+    }
+
+    Sql& Bind(const std::nullopt_t val) {
+      bindings_.push_back(DbType(val));
+      return *this;
+    }
+
+    Sql& Bind(int pos, const char* val) {
+      if (val == nullptr) {
+        binding_map_[pos] = DbType(std::nullopt);
+      } else {
+        std::string str = val;
+        if (empty_string_as_null_ && str.empty())
+          binding_map_[pos] = DbType(std::nullopt);
+        else
+          binding_map_[pos] = DbType(std::move(str));
+      }
+      return *this;
+    }
+
+    Sql& Bind(int pos, std::string val) {
+      if (empty_string_as_null_ && val.empty())
+        binding_map_[pos] = DbType(std::nullopt);
+      else
+        binding_map_[pos] = DbType(std::move(val));
+      return *this;
+    }
+
+    Sql& Bind(int pos, int val) {
+      binding_map_[pos] = DbType(static_cast<int64_t>(val));
+      return *this;
+    }
+
+    Sql& Bind(int pos, int64_t val) {
+      binding_map_[pos] = DbType(val);
+      return *this;
+    }
+
+    Sql& Bind(int pos, double val) {
+      binding_map_[pos] = DbType(val);
+      return *this;
+    }
+
+    Sql& Bind(int pos, std::vector<unsigned char> val) {
+      if (empty_vector_as_null_ && val.empty())
+        binding_map_[pos] = DbType(std::nullopt);
+      else
+        binding_map_[pos] = DbType(std::move(val));
+      return *this;
+    }
+
+    Sql& Bind(int pos, const std::nullopt_t& val) {
+      binding_map_[pos] = DbType(val);
+      return *this;
+    }
+
+    Sql& Bind(std::string name, const char* val) {
+      if (val == nullptr) {
+        binding_name_map_[std::move(name)] = DbType(std::nullopt);
+      } else {
+        std::string str = val;
+        if (empty_string_as_null_ && str.empty())
+          binding_name_map_[std::move(name)] = DbType(std::nullopt);
+        else
+          binding_name_map_[std::move(name)] = DbType(std::move(str));
+      }
+      return *this;
+    }
+
+    Sql& Bind(std::string name, std::string val) {
+      if (empty_string_as_null_ && val.empty())
+        binding_name_map_[std::move(name)] = DbType(std::nullopt);
+      else
+        binding_name_map_[std::move(name)] = DbType(std::move(val));
+      return *this;
+    }
+
+    Sql& Bind(std::string name, int val) {
+      binding_name_map_[std::move(name)] = DbType(static_cast<int64_t>(val));
+      return *this;
+    }
+
+    Sql& Bind(std::string name, int64_t val) {
+      binding_name_map_[std::move(name)] = DbType(val);
+      return *this;
+    }
+
+    Sql& Bind(std::string name, double val) {
+      binding_name_map_[std::move(name)] = DbType(val);
+      return *this;
+    }
+
+    Sql& Bind(std::string name, std::vector<unsigned char> val) {
+      if (empty_vector_as_null_ && val.empty())
+        binding_name_map_[std::move(name)] = DbType(std::nullopt);
+      else
+        binding_name_map_[std::move(name)] = DbType(std::move(val));
+      return *this;
+    }
+
+    Sql& Bind(std::string name, const std::nullopt_t& val) {
+      binding_name_map_[std::move(name)] = DbType(val);
+      return *this;
+    }
+
+    const std::vector<DbType>& GetBindings() const {
+      return bindings_;
+    }
+
+    const std::map<int, DbType>& GetBindingMap() const {
+      return binding_map_;
+    }
+
+    const std::map<std::string, DbType>& GetBindingNameMap() const {
+      return binding_name_map_;
+    }
+
+    const std::string& GetQuery() const {
+      return query_;
+    }
+
+    Sql& SetEmptyStringAsNull(bool as_null) {
+      empty_string_as_null_ = as_null;
+      return *this;
+    }
+
+    Sql& SetEmptyVectorAsNull(bool as_null) {
+      empty_vector_as_null_ = as_null;
+      return *this;
+    }
+
+    Sql& Reset() {
+      bindings_.clear();
+      binding_map_.clear();
+      binding_name_map_.clear();
+      empty_string_as_null_ = false;
+      empty_vector_as_null_ = false;
+      return *this;
+    }
+
+   private:
+    std::string query_;
+    std::vector<DbType> bindings_;
+    std::map<int, DbType> binding_map_;
+    std::map<std::string, DbType> binding_name_map_;
+    bool empty_string_as_null_ = false;
+    bool empty_vector_as_null_ = false;
+  };
+
+  class Result {
+   public:
+    Result() = default;
+    ~Result() {
+      if (stmt_)
+        sqlite3_finalize(stmt_);
+    }
+
+    Result(const Result&) = delete;
+    Result& operator = (const Result&) = delete;
+
+    Result(Result&& r) noexcept {
+      stmt_ = r.stmt_;
+      r.stmt_ = nullptr;
+      query_ = std::move(r.query_);
+      is_done_ = r.is_done_;
+    }
+
+    Result& operator = (Result&& r) noexcept {
+      if (this != &r) {
+        if (stmt_)
+          sqlite3_finalize(stmt_);
+        stmt_ = r.stmt_;
+        r.stmt_ = nullptr;
+        query_ = std::move(r.query_);
+        is_done_ = r.is_done_;
+      }
+
+      return *this;
+    }
+
+    class Record {
+     public:
+      explicit Record(const sqlite3_stmt* stmt) : stmt_(stmt) {}
+
+      std::optional<std::string> GetString(int pos) const {
+        sqlite3_stmt* stmt = const_cast<sqlite3_stmt*>(stmt_);
+        const char* text = reinterpret_cast<const char*>(
+            sqlite3_column_text(stmt, pos));
+        if (!text)
+          return std::nullopt;
+
+        return text;
+      }
+
+      AutoDbType Get(int pos) const {
+        sqlite3_stmt* stmt = const_cast<sqlite3_stmt*>(stmt_);
+        int type = sqlite3_column_type(stmt, pos);
+
+        DbType dbt;
+        if (type == SQLITE_TEXT) {
+          dbt = DbType(reinterpret_cast<const char*>(
+              sqlite3_column_text(stmt, pos)));
+        } else if (type == SQLITE_INTEGER) {
+          dbt = DbType(static_cast<int64_t>(sqlite3_column_int64(stmt, pos)));
+        } else if (type == SQLITE_FLOAT) {
+          dbt = DbType(sqlite3_column_double(stmt, pos));
+        } else if (type == SQLITE_BLOB) {
+          const unsigned char* val = reinterpret_cast<const unsigned char*>(
+              sqlite3_column_blob(stmt, pos));
+          int len = sqlite3_column_bytes(stmt, pos);
+
+          if (!val || len < 0) {
+            throw DbException("invalid blob");;
+          } else {
+            dbt = DbType(std::vector<unsigned char>(val, val + len));
+          }
+        } else if (type == SQLITE_NULL) {
+          dbt = DbType(std::nullopt);
+        } else {
+          throw DbException("invalid column type", type);
+        }
+
+        return AutoDbType(dbt, type);
+      }
+
+      template <typename ...Types>
+      auto Get() const {
+        std::tuple<Types...> t;
+        int pos = 0;
+        for_<std::tuple_size_v<std::tuple<Types...>>>([&] (auto i) {
+          std::get<i.value>(t) = Get(pos++);
+        });
+
+        return t;
+      }
+
+     private:
+      const sqlite3_stmt* stmt_;
+    };
+
+    class Iterator {
+     public:
+      explicit Iterator(sqlite3_stmt* stmt) : stmt_(stmt) {}
+
+      Record operator*() { return Record(stmt_); }
+
+      bool operator != (const Iterator& rhs) const {
+        return stmt_ != rhs.stmt_;
+      }
+
+      void operator ++() {
+        int r = sqlite3_step(stmt_);
+        if (r != SQLITE_ROW)
+          stmt_ = nullptr;
+      }
+
+     private:
+      sqlite3_stmt* stmt_ = nullptr;
+    };
+
+    Iterator begin() const {
+      if (is_done_)
+        return Iterator(nullptr);
+      return Iterator(stmt_);
+    }
+
+    Iterator end() const {
+      return Iterator(nullptr);
+    }
+
+    operator bool() const {
+      if (stmt_ == nullptr)
+        return false;
+      return true;
+    }
+
+    explicit operator int() const {
+      auto db = db_.lock();
+      if (db == nullptr)
+        return SQLITE_ERROR;
+      return sqlite3_errcode(db.get());
+    }
+
+    explicit operator const char*() const {
+      auto db = db_.lock();
+      if (db == nullptr)
+        return "";
+      return sqlite3_errmsg(db.get());
+    }
+
+    template <class T>
+    std::vector<T> ToVector() {
+      if (stmt_ == nullptr)
+        return {};
+
+      std::vector<T> vec;
+      for (const auto& rec : *this) {
+        T t;
+        t(rec);
+        vec.push_back(std::move(t));
+      }
+
+      return vec;
+    }
+
+    template <class T>
+    std::list<T> ToList() {
+      if (stmt_ == nullptr)
+        return {};
+
+      std::list<T> l;
+      for (const auto& rec : *this) {
+        T t;
+        t(rec);
+        l.push_back(std::move(t));
+      }
+
+      return l;
+    }
+
+    template <class T>
+    std::optional<T> GetFirst() {
+      if (stmt_ == nullptr)
+        return std::nullopt;
+      for (const auto& rec : *this) {
+        T t;
+        t(rec);
+        return t;
+      }
+
+      return std::nullopt;
+    }
+
+    std::optional<Record> GetFirstRecord() {
+      if (stmt_ == nullptr)
+        return std::nullopt;
+      for (const auto& rec : *this) {
+        return rec;
+      }
+
+      return std::nullopt;
+    }
+
+    sqlite3_stmt* GetRaw() const {
+      return stmt_;
+    }
+
+    const std::string& GetQuery() const {
+      return query_;
+    }
+
+    void SetDone(bool is_done) {
+      is_done_ = is_done;
+    }
+
+    size_t GetColumnCount() const {
+      return sqlite3_column_count(stmt_);
+    }
+
+   private:
+    friend class Database;
+    Result(sqlite3_stmt* stmt, const std::shared_ptr<sqlite3>& db, std::string query, bool is_done)
+        : stmt_(stmt), db_(db), query_(std::move(query)), is_done_(is_done) {}
+
+    sqlite3_stmt* stmt_ = nullptr;
+    std::weak_ptr<sqlite3> db_;
+    std::string query_;
+    bool is_done_ = false;
+  };
+
+  Database(std::string db_path, int flags) {
+    sqlite3* raw_db = nullptr;
+    int r = sqlite3_open_v2(db_path.c_str(), &raw_db, flags, nullptr);
+    if (r != SQLITE_OK)
+      throw DbException("open failed", r);
+
+    db_.reset(raw_db, sqlite3_close_v2);
+  }
+
+  Database(std::string db_path, int flags,
+      std::function<bool(int)> busy_handler) {
+    sqlite3* raw_db = nullptr;
+    int r = sqlite3_open_v2(db_path.c_str(), &raw_db, flags, nullptr);
+    if (r != SQLITE_OK)
+      throw DbException("sqlite3_open_v2() failed", r);
+
+    db_.reset(raw_db, sqlite3_close_v2);
+    busy_handler_ = std::move(busy_handler);
+    r = sqlite3_busy_handler(db_.get(), [](void* data, int count) {
+      Database* pDb = static_cast<Database*>(data);
+      if (pDb->busy_handler_ && pDb->busy_handler_(count))
+        return 1;
+      return 0;
+    }, this);
+
+    if (r != SQLITE_OK)
+      throw DbException("sqlite3_busy_handler() failed", r);
+  }
+
+  ~Database() = default;
+  Database() = default;
+  Database(const Database&) = delete;
+  Database& operator = (const Database&) = delete;
+
+  Database(Database&& db) noexcept {
+    db_ = std::move(db.db_);
+    busy_handler_ = std::move(db.busy_handler_);
+    db.db_ = nullptr;
+    db.busy_handler_ = nullptr;
+
+    sqlite3_busy_handler(db_.get(), [](void* data, int count) {
+      Database* pDb = static_cast<Database*>(data);
+      if (pDb->busy_handler_ && pDb->busy_handler_(count))
+        return 1;
+      return 0;
+    }, this);
+  }
+
+  explicit operator bool() const {
+    if (db_ == nullptr)
+      return false;
+    return true;
+  }
+
+  Database& operator = (Database&& db) noexcept {
+    if (this != &db) {
+      db_ = std::move(db.db_);
+      busy_handler_ = std::move(db.busy_handler_);
+      db.db_ = nullptr;
+      db.busy_handler_ = nullptr;
+      sqlite3_busy_handler(db_.get(), [](void* data, int count) {
+        Database* pDb = static_cast<Database*>(data);
+        if (pDb->busy_handler_ && pDb->busy_handler_(count))
+          return 1;
+        return 0;
+      }, this);
+    }
+
+    return *this;
+  }
+
+  TransactionGuard CreateTransactionGuard() const {
+    return TransactionGuard(db_);
+  }
+
+  Result Prepare(const Sql& sql) const {
+    if (!db_)
+      throw DbException("Not opened");
+
+    sqlite3_stmt* stmt = nullptr;
+    int r = sqlite3_prepare_v2(db_.get(), sql.GetQuery().c_str(),
+        -1, &stmt, nullptr);
+    if (r != SQLITE_OK)
+      return { nullptr, db_, "", true };
+    return { stmt, db_, sql.GetQuery(), false };
+  }
+
+  Result Exec(const Sql& sql) const {
+    if (!db_)
+      throw DbException("Not opened");
+
+    sqlite3_stmt* stmt = nullptr;
+    int r = sqlite3_prepare_v2(db_.get(), sql.GetQuery().c_str(),
+        -1, &stmt, nullptr);
+    if (r != SQLITE_OK) {
+      return { nullptr, db_, "", true };
+    }
+
+    std::unique_ptr<sqlite3_stmt, decltype(sqlite3_finalize)*> stmt_auto(stmt,
+        sqlite3_finalize);
+    int pos = 1;
+    for (const auto& i : sql.GetBindings()) {
+      Bind(pos++, i, stmt);
+    }
+
+    for (const auto& i : sql.GetBindingMap()) {
+      Bind(i.first, i.second, stmt);
+    }
+
+    for (const auto& i : sql.GetBindingNameMap()) {
+      int pos = sqlite3_bind_parameter_index(stmt, i.first.c_str());
+      if (pos == 0)
+        throw DbException("Invalid binding");
+      Bind(pos, i.second, stmt);
+    }
+
+    r = sqlite3_step(stmt);
+    if (r != SQLITE_ROW && r != SQLITE_DONE) {
+      return { nullptr, db_, "", true };
+    }
+
+    return { stmt_auto.release(), db_, sql.GetQuery(),
+        r == SQLITE_DONE ? true : false };
+  }
+
+  bool Exec(const Sql& sql, Result& previous_stmt) const {
+    if (sql.GetQuery() != previous_stmt.GetQuery())
+      throw DbException("Query is different");
+
+    sqlite3_stmt* stmt = previous_stmt.GetRaw();
+    if (!stmt)
+      return false;
+
+    int r = sqlite3_reset(stmt);
+    if (r != SQLITE_ROW && r != SQLITE_DONE && r != SQLITE_OK)
+      return false;
+
+    int pos = 1;
+    for (const auto& i : sql.GetBindings()) {
+      Bind(pos++, i, stmt);
+    }
+
+    for (const auto& i : sql.GetBindingMap()) {
+      Bind(i.first, i.second, stmt);
+    }
+
+    for (const auto& i : sql.GetBindingNameMap()) {
+      int pos = sqlite3_bind_parameter_index(stmt, i.first.c_str());
+      if (pos == 0)
+        throw DbException("Invalid binding");
+      Bind(pos, i.second, stmt);
+    }
+
+    r = sqlite3_step(stmt);
+    if (r != SQLITE_ROW && r != SQLITE_DONE)
+      return false;
+
+    previous_stmt.SetDone(r == SQLITE_DONE ? true : false);
+    return true;
+  }
+
+  void OneStepExec(const Sql& sql) const {
+    char* errmsg = nullptr;
+    int ret = sqlite3_exec(db_.get(), sql.GetQuery().c_str(), nullptr, nullptr,
+        &errmsg);
+    if (ret != SQLITE_OK) {
+      std::unique_ptr<char, decltype(sqlite3_free)*> errmsg_auto(
+          errmsg, sqlite3_free);
+      throw DbException(errmsg);
+    }
+  }
+
+  sqlite3* GetRaw() const {
+    if (!db_)
+      throw DbException("Not opened");
+    return db_.get();
+  }
+
+ private:
+  void Bind(int pos, const DbType& type, sqlite3_stmt* stmt) const {
+    int r;
+    if (!type) {
+      r = sqlite3_bind_null(stmt, pos);
+      if (r != SQLITE_OK) {
+        throw DbException("Invalid binding", r);
+      }
+
+      return;
+    }
+
+    if (const std::string* pstr = std::get_if<std::string>(&(*type))) {
+      r = sqlite3_bind_text(stmt, pos, (*pstr).c_str(), -1,
+          SQLITE_TRANSIENT);
+    } else if (const int64_t* pint = std::get_if<int64_t>(&(*type))) {
+      r = sqlite3_bind_int64(stmt, pos, (*pint));
+    } else if (const double* pdouble = std::get_if<double>(&(*type))) {
+      r = sqlite3_bind_double(stmt, pos, (*pdouble));
+    } else if (const std::vector<unsigned char>* pvector =
+        std::get_if<std::vector<unsigned char>>(&(*type))) {
+      r = sqlite3_bind_blob(stmt, pos, (*pvector).data(),
+          (*pvector).size(), nullptr);
+    } else {
+      r = -1;
+    }
+
+    if (r != SQLITE_OK) {
+      throw DbException("Invalid binding");
+    }
+  }
+
+ private:
+  std::shared_ptr<sqlite3> db_ = nullptr;
+  std::function<bool(int)> busy_handler_;
+};
+
+}  // namespace tizen_base
+
+#endif  // TIZEN_DATABASE_DATABASE_HPP_
diff --git a/src/tizen-database/tizen-database.pc.in b/src/tizen-database/tizen-database.pc.in
new file mode 100644 (file)
index 0000000..82ee192
--- /dev/null
@@ -0,0 +1,11 @@
+# Wrapper class for sqlite3
+
+prefix=@PREFIX@
+includedir=${prefix}/include
+
+Name: tizen-database
+Description: Wrapper class for sqlite3
+Version: @VERSION@
+Requires: sqlite3
+Cflags: -I${includedir} -I${includedir}/tizen-database
+cppflags: -I${includedir} -I${includedir}/tizen-database
diff --git a/src/tizen-shared-queue/CMakeLists.txt b/src/tizen-shared-queue/CMakeLists.txt
new file mode 100644 (file)
index 0000000..5a033e5
--- /dev/null
@@ -0,0 +1,7 @@
+CONFIGURE_FILE(${CMAKE_CURRENT_SOURCE_DIR}/tizen-shared-queue.pc.in
+  ${CMAKE_BINARY_DIR}/tizen-shared-queue.pc @ONLY)
+
+INSTALL(FILES ${CMAKE_BINARY_DIR}/tizen-shared-queue.pc
+  DESTINATION ${LIB_INSTALL_DIR}/pkgconfig/)
+INSTALL(FILES ${CMAKE_CURRENT_SOURCE_DIR}/shared-queue.hpp
+  DESTINATION include/tizen-shared-queue)
diff --git a/src/tizen-shared-queue/shared-queue.hpp b/src/tizen-shared-queue/shared-queue.hpp
new file mode 100644 (file)
index 0000000..f73552d
--- /dev/null
@@ -0,0 +1,96 @@
+/*
+ * Copyright (c) 2023 Samsung Electronics Co., Ltd All Rights Reserved
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#ifndef TIZEN_SHARED_QUEUE_SHARED_QUEUE_HPP_
+#define TIZEN_SHARED_QUEUE_SHARED_QUEUE_HPP_
+
+#include <condition_variable>
+#include <memory>
+#include <mutex>
+#include <queue>
+#include <thread>
+#include <utility>
+
+namespace tizen_base {
+
+template <class T>
+class SharedQueue {
+ public:
+  SharedQueue() = default;
+  virtual ~SharedQueue() = default;
+
+  void Push(T item) {
+    std::lock_guard<std::mutex> lock(mutex_);
+    queue_.push(item);
+    cond_var_.notify_one();
+  }
+
+  bool TryAndPop(T& item) {
+    std::lock_guard<std::mutex> lock(mutex_);
+    if (queue_.empty())
+      return false;
+
+    item = queue_.front();
+    queue_.pop();
+    return true;
+  }
+
+  T WaitAndPop() {
+    std::unique_lock<std::mutex> lock(mutex_);
+    while (queue_.empty())
+      cond_var_.wait(lock);
+
+    auto item = std::move(queue_.front());
+    queue_.pop();
+    return item;
+  }
+
+  bool WaitAndPopFor(T& item, int timeout) {
+    std::unique_lock<std::mutex> lock(mutex_);
+    if (!queue_.empty()) {
+      item = queue_.front();
+      queue_.pop();
+      return true;
+    }
+
+    std::chrono::milliseconds duration(timeout);
+    if (cond_var_.wait_for(lock, duration) == std::cv_status::timeout)
+      return false;
+
+    item = queue_.front();
+    queue_.pop();
+    return true;
+  }
+
+  bool IsEmpty() const {
+    std::lock_guard<std::mutex> lock(mutex_);
+    return queue_.empty();
+  }
+
+  unsigned int Size() const {
+    std::lock_guard<std::mutex> lock(mutex_);
+    return queue_.size();
+  }
+
+ private:
+  std::queue<T> queue_;
+  mutable std::mutex mutex_;
+  std::condition_variable cond_var_;
+};
+
+}  // namespace tizen_base
+
+#endif  // TIZEN_SHARED_QUEUE_SHARED_QUEUE_HPP_
diff --git a/src/tizen-shared-queue/tizen-shared-queue.pc.in b/src/tizen-shared-queue/tizen-shared-queue.pc.in
new file mode 100644 (file)
index 0000000..22969ce
--- /dev/null
@@ -0,0 +1,11 @@
+# Wrapper class for sqlite3
+
+prefix=@PREFIX@
+includedir=${prefix}/include
+
+Name: tizen-shared-queue
+Description: shared queue class for active object pattern
+Version: @VERSION@
+Requires:
+Cflags: -I${includedir} -I${includedir}/tizen-shared-queue
+cppflags: -I${includedir} -I${includedir}/tizen-shared-queue
index bb5abb25fcc1a5aff2e9436e08ce464df260164c..30e9d3ef12c74d13e1848400f0353d91900d8866 100644 (file)
@@ -2,3 +2,6 @@ ADD_SUBDIRECTORY(bundle_unittests)
 ADD_SUBDIRECTORY(parcel_unittests)
 ADD_SUBDIRECTORY(tizen-database_unittests)
 ADD_SUBDIRECTORY(tizen-shared-queue_unittests)
+
+ADD_DEPENDENCIES(${TARGET_BUNDLE_UNITTESTS} ${TARGET_BUNDLE})
+ADD_DEPENDENCIES(${TARGET_PARCEL_UNITTESTS} ${TARGET_PARCEL})
index 7ee51e9b97bc1855fa82a0bba240eebc5cbfd4ad..d057490f543a0e50cb5297597cbae1cff79b8d14 100644 (file)
@@ -1,39 +1,20 @@
-CMAKE_MINIMUM_REQUIRED(VERSION 2.8)
-PROJECT(bundle_unittests C CXX)
+AUX_SOURCE_DIRECTORY(${CMAKE_CURRENT_SOURCE_DIR}/src BUNDLE_UNITTESTS_SRCS)
 
-INCLUDE(FindPkgConfig)
-PKG_CHECK_MODULES(bundle_unittests REQUIRED
-    dlog
-    gmock
-    glib-2.0
-    json-glib-1.0
-    capi-base-common
-)
-
-FOREACH(flag ${bundle_unittests_CFLAGS})
-    SET(EXTRA_CFLAGS "${EXTRA_CFLAGS} ${flag}")
-ENDFOREACH(flag)
-SET(EXTRA_CFLAGS "${EXTRA_CFLAGS} -fvisibility=hidden -Wall -Werror -Winline")
-
-SET(CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} ${EXTRA_CFLAGS} -std=c++17")
-SET(CMAKE_CXX_FLAGS_DEBUG "-O0 -g")
-SET(CMAKE_CXX_FLAGS_RELEASE "-O2")
+ADD_EXECUTABLE(${TARGET_BUNDLE_UNITTESTS} ${BUNDLE_UNITTESTS_SRCS})
 
-INCLUDE_DIRECTORIES(${CMAKE_CURRENT_SOURCE_DIR}/../)
-INCLUDE_DIRECTORIES(${CMAKE_CURRENT_SOURCE_DIR}/../../)
-INCLUDE_DIRECTORIES(${CMAKE_CURRENT_SOURCE_DIR}/../../src)
-INCLUDE_DIRECTORIES(${CMAKE_CURRENT_SOURCE_DIR}/../../include)
-INCLUDE_DIRECTORIES(${CMAKE_CURRENT_SOURCE_DIR}/../../bundle)
-
-AUX_SOURCE_DIRECTORY(${CMAKE_CURRENT_SOURCE_DIR}/src UNITTESTS_SOURCES)
-AUX_SOURCE_DIRECTORY(${CMAKE_CURRENT_SOURCE_DIR}/../../src BUNDLE_SOURCES)
+TARGET_INCLUDE_DIRECTORIES(${TARGET_BUNDLE_UNITTESTS} PUBLIC
+  ${CMAKE_CURRENT_SOURCE_DIR}
+  ${CMAKE_CURRENT_SOURCE_DIR}/../
+  ${CMAKE_CURRENT_SOURCE_DIR}/../../
+  ${CMAKE_CURRENT_SOURCE_DIR}/../../bundle/include
+)
 
-ADD_EXECUTABLE(${PROJECT_NAME}
-    ${BUNDLE_SOURCES}
-    ${UNITTESTS_SOURCES}
+APPLY_PKG_CONFIG(${TARGET_BUNDLE_UNITTESTS} PUBLIC
+  GMOCK_DEPS
+  DLOG_DEPS
+  GLIB_DEPS
 )
 
-SET_TARGET_PROPERTIES(${PROJECT_NAME} PROPERTIES COMPILE_FLAGS "${EXTRA_CFLAGS}")
-TARGET_LINK_LIBRARIES(${PROJECT_NAME} ${bundle_unittests_LDFLAGS})
+TARGET_LINK_LIBRARIES(${TARGET_BUNDLE_UNITTESTS} PRIVATE ${TARGET_BUNDLE})
 
-INSTALL(TARGETS ${PROJECT_NAME} DESTINATION /usr/bin/)
+INSTALL(TARGETS ${TARGET_BUNDLE_UNITTESTS} DESTINATION bin)
index b2df484cb02ad97d5895c289fd7702dd05f83782..69486d086661097ed40e52c25c955f956daabf7d 100644 (file)
@@ -1,42 +1,20 @@
-CMAKE_MINIMUM_REQUIRED(VERSION 2.8)
-PROJECT(parcel_unittests C CXX)
+AUX_SOURCE_DIRECTORY(${CMAKE_CURRENT_SOURCE_DIR} PARCEL_UNITTESTS_SRCS)
 
-INCLUDE(FindPkgConfig)
-PKG_CHECK_MODULES(parcel_unittests REQUIRED
-    capi-base-common
-    dlog
-    glib-2.0
-    gmock
-    json-glib-1.0
-)
-
-FOREACH(flag ${parcel_unittests_CFLAGS})
-    SET(EXTRA_CFLAGS "${EXTRA_CFLAGS} ${flag}")
-ENDFOREACH(flag)
-SET(EXTRA_CFLAGS "${EXTRA_CFLAGS} -fvisibility=hidden -Wall -Werror -Winline")
-
-SET(CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} ${EXTRA_CFLAGS} -std=c++17")
-SET(CMAKE_CXX_FLAGS_DEBUG "-O0 -g")
-SET(CMAKE_CXX_FLAGS_RELEASE "-O2")
+ADD_EXECUTABLE(${TARGET_PARCEL_UNITTESTS} ${PARCEL_UNITTESTS_SRCS})
 
-INCLUDE_DIRECTORIES(${CMAKE_CURRENT_SOURCE_DIR}/../)
-INCLUDE_DIRECTORIES(${CMAKE_CURRENT_SOURCE_DIR}/../../)
-INCLUDE_DIRECTORIES(${CMAKE_CURRENT_SOURCE_DIR}/../../src)
-INCLUDE_DIRECTORIES(${CMAKE_CURRENT_SOURCE_DIR}/../../include)
-INCLUDE_DIRECTORIES(${CMAKE_CURRENT_SOURCE_DIR}/../../parcel)
-INCLUDE_DIRECTORIES(${CMAKE_CURRENT_SOURCE_DIR}/../../parcel/api)
-
-AUX_SOURCE_DIRECTORY(${CMAKE_CURRENT_SOURCE_DIR}/ UNITTESTS_SOURCES)
-AUX_SOURCE_DIRECTORY(${CMAKE_CURRENT_SOURCE_DIR}/../../src BUNDLE_SOURCES)
-AUX_SOURCE_DIRECTORY(${CMAKE_CURRENT_SOURCE_DIR}/../../parcel PARCEL_SOURCES)
+TARGET_INCLUDE_DIRECTORIES(${TARGET_PARCEL_UNITTESTS} PUBLIC
+  ${CMAKE_CURRENT_SOURCE_DIR}
+  ${CMAKE_CURRENT_SOURCE_DIR}/../
+  ${CMAKE_CURRENT_SOURCE_DIR}/../../
+  ${CMAKE_CURRENT_SOURCE_DIR}/../../src
+  ${CMAKE_CURRENT_SOURCE_DIR}/../../src/parcel
+  ${CMAKE_CURRENT_SOURCE_DIR}/../../src/parcel/api
+)
 
-ADD_EXECUTABLE(${PROJECT_NAME}
-  ${BUNDLE_SOURCES}
-  ${PARCEL_SOURCES}
-  ${UNITTESTS_SOURCES}
+APPLY_PKG_CONFIG(${TARGET_PARCEL_UNITTESTS} PUBLIC
+  GMOCK_DEPS
 )
 
-SET_TARGET_PROPERTIES(${PROJECT_NAME} PROPERTIES COMPILE_FLAGS "${EXTRA_CFLAGS}")
-TARGET_LINK_LIBRARIES(${PROJECT_NAME} ${parcel_unittests_LDFLAGS})
+TARGET_LINK_LIBRARIES(${TARGET_PARCEL_UNITTESTS} PRIVATE ${TARGET_PARCEL})
 
-INSTALL(TARGETS ${PROJECT_NAME} DESTINATION /usr/bin/)
+INSTALL(TARGETS ${TARGET_PARCEL_UNITTESTS} DESTINATION bin)
index a7a36fd7758250d1c38c2e011e50ee955e10709a..0e7d5f73d4e6c77128323eb27d5422c687226eaa 100644 (file)
@@ -1,29 +1,22 @@
-CMAKE_MINIMUM_REQUIRED(VERSION 2.8)
-PROJECT(tizen-database_unittests CXX)
+AUX_SOURCE_DIRECTORY(${CMAKE_CURRENT_SOURCE_DIR}/src TIZEN_DATABASE_UNITTESTS_SRCS)
 
-INCLUDE(FindPkgConfig)
-PKG_CHECK_MODULES(tizen-database_unittests REQUIRED
-    gmock
-    sqlite3
-)
-
-SET(EXTRA_CFLAGS "")
-FOREACH(flag ${database_unittests_CFLAGS})
-    SET(EXTRA_CFLAGS "${EXTRA_CFLAGS} ${flag}")
-ENDFOREACH(flag)
-SET(EXTRA_CFLAGS "${EXTRA_CFLAGS} -fvisibility=hidden -Wall -Werror")
-
-SET(CMAKE_CXX_FLAGS "${EXTRA_CFLAGS} -std=c++17")
-SET(CMAKE_CXX_FLAGS_DEBUG "-O0 -g")
-SET(CMAKE_CXX_FLAGS_RELEASE "-O2")
+ADD_EXECUTABLE(${TARGET_TIZEN_DATABASE_UNITTESTS}
+  ${TIZEN_DATABASE_UNITTESTS_SRCS})
 
-INCLUDE_DIRECTORIES(${CMAKE_CURRENT_SOURCE_DIR}/../../)
-AUX_SOURCE_DIRECTORY(${CMAKE_CURRENT_SOURCE_DIR}/src UNITTESTS_SOURCES)
+TARGET_INCLUDE_DIRECTORIES(${TARGET_TIZEN_DATABASE_UNITTESTS} PUBLIC
+  ${CMAKE_CURRENT_SOURCE_DIR}
+  ${CMAKE_CURRENT_SOURCE_DIR}/../
+  ${CMAKE_CURRENT_SOURCE_DIR}/../../
+  ${CMAKE_CURRENT_SOURCE_DIR}/../../src
+  ${CMAKE_CURRENT_SOURCE_DIR}/../../src/tizen-database
+)
 
-ADD_EXECUTABLE(${PROJECT_NAME}
-    ${UNITTESTS_SOURCES}
+APPLY_PKG_CONFIG(${TARGET_TIZEN_DATABASE_UNITTESTS} PUBLIC
+  GMOCK_DEPS
+  SQLITE3_DEPS
 )
 
-SET_TARGET_PROPERTIES(${PROJECT_NAME} PROPERTIES COMPILE_FLAGS "${EXTRA_CFLAGS}")
-TARGET_LINK_LIBRARIES(${PROJECT_NAME} ${tizen-database_unittests_LDFLAGS})
-INSTALL(TARGETS ${PROJECT_NAME} DESTINATION /usr/bin/)
\ No newline at end of file
+#TARGET_LINK_LIBRARIES(${TARGET_TIZEN_DATABASE_UNITTESTS} PRIVATE
+#  ${TARGET_TIZEN_DATABASE})
+
+INSTALL(TARGETS ${TARGET_TIZEN_DATABASE_UNITTESTS} DESTINATION bin)
index 3a17063bc2258ea9d53e83e933139122bea11aac..377566b1f019328983ec3a213cef4caac2cf8801 100644 (file)
@@ -1,25 +1,22 @@
-CMAKE_MINIMUM_REQUIRED(VERSION 2.8)
-PROJECT(tizen-shared-queue_unittests CXX)
+AUX_SOURCE_DIRECTORY(${CMAKE_CURRENT_SOURCE_DIR}
+  TIZEN_SHARED_QUEUE_UNITTESTS_SRCS)
 
-INCLUDE(FindPkgConfig)
-PKG_CHECK_MODULES(tizen-shared-queue_unittests REQUIRED gmock)
+ADD_EXECUTABLE(${TARGET_TIZEN_SHARED_QUEUE_UNITTESTS}
+  ${TIZEN_SHARED_QUEUE_UNITTESTS_SRCS})
 
-SET(EXTRA_CFLAGS "")
-FOREACH(flag ${tizen-shared-queue_unittests_CFLAGS})
-    SET(EXTRA_CFLAGS "${EXTRA_CFLAGS} ${flag}")
-ENDFOREACH(flag)
-SET(EXTRA_CFLAGS "${EXTRA_CFLAGS} -fvisibility=hidden -Wall -Werror")
+TARGET_INCLUDE_DIRECTORIES(${TARGET_TIZEN_SHARED_QUEUE_UNITTESTS} PUBLIC
+  ${CMAKE_CURRENT_SOURCE_DIR}
+  ${CMAKE_CURRENT_SOURCE_DIR}/../
+  ${CMAKE_CURRENT_SOURCE_DIR}/../../
+  ${CMAKE_CURRENT_SOURCE_DIR}/../../src
+  ${CMAKE_CURRENT_SOURCE_DIR}/../../src/tizen-shared-queue
+)
 
-SET(CMAKE_CXX_FLAGS "${EXTRA_CFLAGS} -std=c++17")
-SET(CMAKE_CXX_FLAGS_DEBUG "-O0 -g")
-SET(CMAKE_CXX_FLAGS_RELEASE "-O2")
+APPLY_PKG_CONFIG(${TARGET_TIZEN_SHARED_QUEUE_UNITTESTS} PUBLIC
+  GMOCK_DEPS
+)
 
-INCLUDE_DIRECTORIES(${CMAKE_CURRENT_SOURCE_DIR}/../../)
-AUX_SOURCE_DIRECTORY(${CMAKE_CURRENT_SOURCE_DIR} UNITTESTS_SOURCES)
+#TARGET_LINK_LIBRARIES(${TARGET_TIZEN_SHARED_QUEUE_UNITTESTS}
+#  PRIVATE ${TARGET_TIZEN_SHARED_QUEUE})
 
-ADD_EXECUTABLE(${PROJECT_NAME} ${UNITTESTS_SOURCES})
-
-SET_TARGET_PROPERTIES(${PROJECT_NAME} PROPERTIES COMPILE_FLAGS
-  "${EXTRA_CFLAGS}")
-TARGET_LINK_LIBRARIES(${PROJECT_NAME} ${tizen-shared-queue_unittests_LDFLAGS})
-INSTALL(TARGETS ${PROJECT_NAME} DESTINATION /usr/bin/)
+INSTALL(TARGETS ${TARGET_TIZEN_SHARED_QUEUE_UNITTESTS} DESTINATION bin)
diff --git a/tizen-database/CMakeLists.txt b/tizen-database/CMakeLists.txt
deleted file mode 100644 (file)
index 9062594..0000000
+++ /dev/null
@@ -1,9 +0,0 @@
-### Make pkgconfig file
-SET(PREFIX ${CMAKE_INSTALL_PREFIX})
-CONFIGURE_FILE(${CMAKE_CURRENT_SOURCE_DIR}/tizen-database.pc.in
-  ${CMAKE_BINARY_DIR}/tizen-database.pc @ONLY)
-
-### Install
-INSTALL(FILES ${CMAKE_BINARY_DIR}/tizen-database.pc DESTINATION ${LIB_INSTALL_DIR}/pkgconfig/)
-INSTALL(FILES ${CMAKE_CURRENT_SOURCE_DIR}/database.hpp
-  DESTINATION include/tizen-database)
diff --git a/tizen-database/README.md b/tizen-database/README.md
deleted file mode 100644 (file)
index 00b5e94..0000000
+++ /dev/null
@@ -1,217 +0,0 @@
-# TizenDatabase
-Wrapper class for sqlite3
-
-## Source
-See database.hpp
-
-## Require
-sqlite3, C++17
-
-## How to use?
-Add 'BuildRequires: pkgconfig(tizen-database)' in your .spec file.
-
-## Cookbook
-
-### Auto close
-- It was implemented by RAII idiom. Database is automatically closed when it exits the scope.
-```cpp
-void test() {
-  tizen_base::Database db("test.db", SQLITE_OPEN_READWRITE);
-  ...
-}
-```
-
-### Binding
-- Bind() method supports various data type such as std::string, int, double and std::vector<unsigned char>.
-
-```cpp
-  tizen_base::Database db("test.db", SQLITE_OPEN_READWRITE);
-  auto q = tizen_base::Database::Sql(
-      "INSERT INTO TestTable(name, num, val, data) VALUES (?, ?, ?, ?);")
-      .Bind("gogo")
-      .Bind(1234)
-      .Bind(9.216)
-      .Bind( std::vector<unsigned char> {'9', '2', '1', '6' } );
-```
-
-- Bind() method also supports named tag using ':'.
-```cpp
-  tizen_base::Database db("test.db", SQLITE_OPEN_READWRITE);
-  auto q = tizen_base::Database::Sql("INSERT INTO TestTable(name, num, val, data) VALUES (:name, :num, :val, :data);")
-      .Bind(":name", "gogo")
-      .Bind(":num", 1234)
-      .Bind(":val", 9.216)
-      .Bind(":data", std::vector<unsigned char> {'9', '2', '1', '6' });
-```
-
-### Null-type binding
-- Null-type binding is supported using 'std::nullopt'.
-
-```cpp
-  tizen_base::Database db("test.db", SQLITE_OPEN_READWRITE);
-  auto q = tizen_base::Database::Sql(
-      "INSERT INTO TestTable(name, num, val, data) VALUES (?, ?, ?, ?);")
-      .Bind(std::nullopt)
-      .Bind(1234)
-      .Bind(9.216)
-      .Bind(std::nullopt);
-```
-- To get nullable object, you can use 'std::optional<>'.
-```cpp
-  for (const auto& i : r) {
-    std::optional<std::string> name = i.Get(0);
-    double val = static_cast<double>(i.Get(2));
-    std::optional<std::vector<unsigned char>> data = i.Get(3);
-    ...
-  }
-```
-
-### Structured binding declaration
-```cpp
-  auto [name, num, val, data] = i.Get<_, _, _, _>();
-```
-- Structured binding declaration can be used to unpack the record.
-
-```cpp
-  for (const auto& i : db.Exec({ "SELECT name, num, val, data FROM TestTable;" })) {
-    auto [name, num, val, data] = i.Get<_, _, _, _>();
-    std::cout << static_cast<std::string>(name) << std::endl;
-  }
-```
-
-### Range-based for loop
-- class 'Result' is iterable.
-
-```cpp
-  tizen_base::Database::Result r =
-      db.Exec({ "SELECT name, num, val, data FROM TestTable;" });
-  for (const auto& i : r) {
-    ...
-  }
-```
-
-### 'bool' type and 'int' type conversion operator
-- 'bool' type operator is supported to check errors.
-- 'int' type operator is supported to get error number.
-```cpp
-  auto r = db.Exec(q);
-  if (!r) {
-    std::cout << "error code:" << static_cast<int>(r) << std::endl;
-  }
-```
-
-### 'const char*' type conversion operator
-- 'const char*' type operator is supported to get error string
-```cpp
-  auto r = db.Exec(q);
-  if (!r) {
-    std::cout << "error message:" << static_cast<const char*>(r) << std::endl;
-  }
-```
-
-### Extract values from query results
-- There are many conversion operators to get the value.
-```cpp
-  for (const auto& i : db.Exec({ "SELECT name, num, val, data FROM TestTable;" })) {
-    auto name = static_cast<std::string>(i.Get(0));
-    auto num = static_cast<int>(i.Get(1));
-    auto val = static_cast<double>(i.Get(2));
-    auto data = static_cast<std::vector<unsigned char>>(i.Get(3));
-  }
-```
-
-### ToList(), ToVector() methods
-- Once you provide function operator in your classes, you can call the methods.
-- The class or struct should be movable.
-```cpp
-  struct MyRec {
-    std::string Id;
-    int Val;
-
-    // It should be implemented to map data set
-    void operator () (const tizen_base::Database::Result::Record& rec) {
-      Id = static_cast<std::string>(rec.Get(0));
-      Val = static_cast<int>(rec.Get(1));
-    }
-  };
-
-  auto /*std::vector<MyRec>*/ table =
-      db.Exec({ "SELECT id, val FROM TestTable;" }).ToVector<MyRec>();
-```
-
-### Transaction guard
-```cpp
-void test() {
-  tizen_base::Database db("test.db", SQLITE_OPEN_READWRITE);
-  auto guard = db.CreateTransactionGuard();
-
-  auto r = db.Exec({ "INSERT INTO MyTable(name, id) VALUES('gogo', 1);" });
-  if (!r)
-    return; // Rollback
-
-  auto r2 = db.Exec({ "INSERT INTO MyTable(name, id) VALUES('gugu', 2);" });
-  if (!r2)
-    return; // Rollback
-
-  guard.Commit();
-}
-```
-
-### Busy handler
-```cpp
-void test() {
-  tizen_base::Database db("test.db", SQLITE_OPEN_READWRITE, [&](int count) {
-    // Busy handler
-    usleep(BUSY_WAITING_USEC);
-    if (count < 10)
-      return true;
-
-    return false;
-  });
-  ...
-}
-```
-
-### Samples
-```cpp
-void test() {
-  tizen_base::Database db("test.db", SQLITE_OPEN_READWRITE);
-  for (const auto& i : db.Exec({ "SELECT name, num, val, data FROM TestTable;" })) {
-    auto [name, num, val, data] = i.Get<_, _, _, _>();
-    std::cout << static_cast<std::string>(name) << std::endl;
-  }
-}
-```
-
-```cpp
-void test() {
-  tizen_base::Database db("test.db", SQLITE_OPEN_READWRITE);
-  auto q = tizen_base::Database::Sql("INSERT INTO TestTable(name, num, val, data) VALUES (?, ?, ?, ?);")
-      .Bind("gogo")
-      .Bind(1234)
-      .Bind(9.216)
-      .Bind( std::vector<unsigned char> {'9', '2', '1', '6' } );
-  auto r = db.Exec(q);
-  if (!r) {
-    std::cout << "insert failed:" << r << std::endl;
-    std::cout << "error code:" << static_cast<int>(r) << std::endl;
-  }
-}
-```
-
-```cpp
-void test() {
-  tizen_base::Database db("test.db", SQLITE_OPEN_READWRITE);
-  auto q = tizen_base::Database::Sql(
-      "INSERT INTO TestTable(name, num, val, data) VALUES (:name, :num, :val, :data);")
-      .Bind(":name", "gogo")
-      .Bind(":num", 1234)
-      .Bind(":val", 9.216)
-      .Bind(":data", std::vector<unsigned char> {'9', '2', '1', '6' });
-  auto r = db.Exec(q);
-  if (!r) {
-    std::cout << "insert failed:" << r << std::endl;
-    std::cout << "error code:" << static_cast<int>(r) << std::endl;
-  }
-}
-```
diff --git a/tizen-database/database.hpp b/tizen-database/database.hpp
deleted file mode 100644 (file)
index c5f1f72..0000000
+++ /dev/null
@@ -1,881 +0,0 @@
-/*
- * Copyright (c) 2022 Samsung Electronics Co., Ltd. All rights reserved.
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#ifndef TIZEN_DATABASE_DATABASE_HPP_
-#define TIZEN_DATABASE_DATABASE_HPP_
-
-#include <sqlite3.h>
-
-#include <functional>
-#include <list>
-#include <map>
-#include <memory>
-#include <optional>
-#include <stdexcept>
-#include <string>
-#include <tuple>
-#include <utility>
-#include <variant>
-#include <vector>
-
-namespace tizen_base {
-
-template<std::size_t N>
-struct num {
-  static const constexpr auto value = N;
-};
-
-template <class F, std::size_t... Is>
-void for_(F func, std::index_sequence<Is...>) {
-  (func(num<Is>{}), ...);
-}
-
-template <std::size_t N, typename F>
-void for_(F func) {
-  for_(func, std::make_index_sequence<N>());
-}
-
-using DbType = std::optional<std::variant<int64_t, double, std::string,
-    std::vector<unsigned char>>>;
-
-class DbException : public std::runtime_error {
- public:
-  explicit DbException(const std::string& msg, int code = SQLITE_ERROR)
-      : std::runtime_error(msg), code_(code) {
-  }
-
-  DbException(const std::string& msg, int code, const std::string& file,
-      int line) : std::runtime_error(msg), code_(code) {
-    msg_ = msg + " at " + file + ":" + std::to_string(line);
-  }
-
-  int code() const {
-    return code_;
-  }
-
-  const char* msg() const {
-    if (msg_.empty())
-      return what();
-    return msg_.c_str();
-  }
-
- private:
-  int code_;
-  std::string msg_;
-};
-
-class AutoDbType {
- public:
-  AutoDbType() = default;
-  explicit AutoDbType(DbType db_type, int real_type)
-      : db_type_(db_type), real_type_(real_type) {}
-
-  int GetType() const {
-    return real_type_;
-  }
-
-  explicit operator int () {
-    if (!db_type_)
-      throw DbException("invalid type conversion from nullopt to int");
-    if (real_type_ != SQLITE_INTEGER)
-      throw DbException("invalid type conversion to int");
-
-    return std::get<int64_t>(*db_type_);
-  }
-
-  explicit operator int64_t () {
-    if (!db_type_)
-      throw DbException("invalid type conversion from nullopt to int64_t");
-    if (real_type_ != SQLITE_INTEGER)
-      throw DbException("invalid type conversion to int64_t");
-
-    return std::get<int64_t>(*db_type_);
-  }
-
-  explicit operator std::string () {
-    if (!db_type_) {
-      throw DbException(
-          "invalid type conversion from nullopt to string");
-    }
-
-    if (real_type_ != SQLITE_TEXT)
-      throw DbException("invalid type conversion to string");
-
-    return std::get<std::string>(*db_type_);
-  }
-
-  explicit operator double () {
-    if (!db_type_) {
-      throw DbException(
-          "invalid type conversion from nullopt to double");
-    }
-
-    if (real_type_ != SQLITE_FLOAT)
-      throw DbException("invalid type conversion to double");
-
-    return std::get<double>(*db_type_);
-  }
-
-  explicit operator std::vector<unsigned char> () {
-    if (!db_type_) {
-      throw DbException(
-          "invalid type conversion from nullopt to std::vector<unsigned char>");
-    }
-
-    if (real_type_ != SQLITE_BLOB)
-      throw DbException("invalid type conversion to std::vector<unsigned char>");
-
-    return std::get<std::vector<unsigned char>>(*db_type_);
-  }
-
-  operator std::optional<int> () {
-    if (!db_type_)
-      return std::nullopt;
-    if (real_type_ != SQLITE_INTEGER)
-      throw DbException("invalid type conversion to int");
-
-    return std::get<int64_t>(*db_type_);
-  }
-
-  operator std::optional<int64_t> () {
-    if (!db_type_)
-      return std::nullopt;
-    if (real_type_ != SQLITE_INTEGER)
-      throw DbException("invalid type conversion to int64_t");
-
-    return std::get<int64_t>(*db_type_);
-  }
-
-  operator std::optional<std::string> () {
-    if (!db_type_)
-      return std::nullopt;
-    if (real_type_ != SQLITE_TEXT)
-      throw DbException("invalid type conversion to string");
-
-    return std::get<std::string>(*db_type_);
-  }
-
-  operator std::optional<double> () {
-    if (!db_type_)
-      return std::nullopt;
-    if (real_type_ != SQLITE_FLOAT)
-      throw DbException("invalid type conversion to double");
-
-    return std::get<double>(*db_type_);
-  }
-
-  operator std::optional<std::vector<unsigned char>> () {
-    if (!db_type_)
-      return std::nullopt;
-    if (real_type_ != SQLITE_BLOB)
-      throw DbException("invalid type conversion to std::vector<unsigned char>");
-
-    return std::get<std::vector<unsigned char>>(*db_type_);
-  }
-
- private:
-  DbType db_type_;
-  int real_type_ = SQLITE_NULL;
-};
-
-using _ = AutoDbType;
-
-class Database {
- public:
-  class TransactionGuard {
-   public:
-    TransactionGuard(const TransactionGuard&) = delete;
-    TransactionGuard& operator = (const TransactionGuard&) = delete;
-
-    TransactionGuard(TransactionGuard&& t) noexcept {
-      db_ = std::move(t.db_);
-    }
-
-    TransactionGuard& operator = (TransactionGuard&& t) noexcept {
-      if (this != &t) {
-        if (!db_.expired())
-          sqlite3_exec(db_.lock().get(), "ROLLBACK", nullptr, nullptr, nullptr);
-        db_ = std::move(t.db_);
-      }
-
-      return *this;
-    }
-
-    explicit TransactionGuard(const std::shared_ptr<sqlite3>& db)
-        : db_(db) {
-      int r = sqlite3_exec(db_.lock().get(), "BEGIN DEFERRED",
-          nullptr, nullptr, nullptr);
-      if (r != SQLITE_OK) {
-        throw DbException("begin transaction failed", r);
-      }
-    }
-
-    ~TransactionGuard() {
-      if (!db_.expired())
-        sqlite3_exec(db_.lock().get(), "ROLLBACK", nullptr, nullptr, nullptr);
-    }
-
-    int Commit() {
-      if (db_.expired())
-        return SQLITE_OK;
-
-      auto db = db_.lock();
-      int ret = sqlite3_exec(db.get(), "COMMIT", nullptr, nullptr, nullptr);
-      if (ret != SQLITE_OK) {
-        sqlite3_exec(db.get(), "ROLLBACK", nullptr, nullptr, nullptr);
-      }
-
-      return ret;
-    }
-
-   private:
-    std::weak_ptr<sqlite3> db_;
-  };
-
-  class Sql {
-   public:
-    Sql(std::string query) : query_(std::move(query)) {}
-
-    Sql& Bind(const char* val) {
-      if (val == nullptr) {
-        bindings_.push_back(DbType(std::nullopt));
-      } else {
-        std::string str = val;
-        if (empty_string_as_null_ && str.empty())
-          bindings_.push_back(DbType(std::nullopt));
-        else
-          bindings_.push_back(DbType(std::move(str)));
-      }
-      return *this;
-    }
-
-    Sql& Bind(std::string val) {
-      if (empty_string_as_null_ && val.empty())
-        bindings_.push_back(DbType(std::nullopt));
-      else
-        bindings_.push_back(DbType(std::move(val)));
-      return *this;
-    }
-
-    Sql& Bind(int val) {
-      bindings_.push_back(DbType(static_cast<int64_t>(val)));
-      return *this;
-    }
-
-    Sql& Bind(int64_t val) {
-      bindings_.push_back(DbType(val));
-      return *this;
-    }
-
-    Sql& Bind(double val) {
-      bindings_.push_back(DbType(val));
-      return *this;
-    }
-
-    Sql& Bind(std::vector<unsigned char> val) {
-      if (empty_vector_as_null_ && val.empty())
-        bindings_.push_back(DbType(std::nullopt));
-      else
-        bindings_.push_back(DbType(std::move(val)));
-      return *this;
-    }
-
-    Sql& Bind(const std::nullopt_t val) {
-      bindings_.push_back(DbType(val));
-      return *this;
-    }
-
-    Sql& Bind(int pos, const char* val) {
-      if (val == nullptr) {
-        binding_map_[pos] = DbType(std::nullopt);
-      } else {
-        std::string str = val;
-        if (empty_string_as_null_ && str.empty())
-          binding_map_[pos] = DbType(std::nullopt);
-        else
-          binding_map_[pos] = DbType(std::move(str));
-      }
-      return *this;
-    }
-
-    Sql& Bind(int pos, std::string val) {
-      if (empty_string_as_null_ && val.empty())
-        binding_map_[pos] = DbType(std::nullopt);
-      else
-        binding_map_[pos] = DbType(std::move(val));
-      return *this;
-    }
-
-    Sql& Bind(int pos, int val) {
-      binding_map_[pos] = DbType(static_cast<int64_t>(val));
-      return *this;
-    }
-
-    Sql& Bind(int pos, int64_t val) {
-      binding_map_[pos] = DbType(val);
-      return *this;
-    }
-
-    Sql& Bind(int pos, double val) {
-      binding_map_[pos] = DbType(val);
-      return *this;
-    }
-
-    Sql& Bind(int pos, std::vector<unsigned char> val) {
-      if (empty_vector_as_null_ && val.empty())
-        binding_map_[pos] = DbType(std::nullopt);
-      else
-        binding_map_[pos] = DbType(std::move(val));
-      return *this;
-    }
-
-    Sql& Bind(int pos, const std::nullopt_t& val) {
-      binding_map_[pos] = DbType(val);
-      return *this;
-    }
-
-    Sql& Bind(std::string name, const char* val) {
-      if (val == nullptr) {
-        binding_name_map_[std::move(name)] = DbType(std::nullopt);
-      } else {
-        std::string str = val;
-        if (empty_string_as_null_ && str.empty())
-          binding_name_map_[std::move(name)] = DbType(std::nullopt);
-        else
-          binding_name_map_[std::move(name)] = DbType(std::move(str));
-      }
-      return *this;
-    }
-
-    Sql& Bind(std::string name, std::string val) {
-      if (empty_string_as_null_ && val.empty())
-        binding_name_map_[std::move(name)] = DbType(std::nullopt);
-      else
-        binding_name_map_[std::move(name)] = DbType(std::move(val));
-      return *this;
-    }
-
-    Sql& Bind(std::string name, int val) {
-      binding_name_map_[std::move(name)] = DbType(static_cast<int64_t>(val));
-      return *this;
-    }
-
-    Sql& Bind(std::string name, int64_t val) {
-      binding_name_map_[std::move(name)] = DbType(val);
-      return *this;
-    }
-
-    Sql& Bind(std::string name, double val) {
-      binding_name_map_[std::move(name)] = DbType(val);
-      return *this;
-    }
-
-    Sql& Bind(std::string name, std::vector<unsigned char> val) {
-      if (empty_vector_as_null_ && val.empty())
-        binding_name_map_[std::move(name)] = DbType(std::nullopt);
-      else
-        binding_name_map_[std::move(name)] = DbType(std::move(val));
-      return *this;
-    }
-
-    Sql& Bind(std::string name, const std::nullopt_t& val) {
-      binding_name_map_[std::move(name)] = DbType(val);
-      return *this;
-    }
-
-    const std::vector<DbType>& GetBindings() const {
-      return bindings_;
-    }
-
-    const std::map<int, DbType>& GetBindingMap() const {
-      return binding_map_;
-    }
-
-    const std::map<std::string, DbType>& GetBindingNameMap() const {
-      return binding_name_map_;
-    }
-
-    const std::string& GetQuery() const {
-      return query_;
-    }
-
-    Sql& SetEmptyStringAsNull(bool as_null) {
-      empty_string_as_null_ = as_null;
-      return *this;
-    }
-
-    Sql& SetEmptyVectorAsNull(bool as_null) {
-      empty_vector_as_null_ = as_null;
-      return *this;
-    }
-
-    Sql& Reset() {
-      bindings_.clear();
-      binding_map_.clear();
-      binding_name_map_.clear();
-      empty_string_as_null_ = false;
-      empty_vector_as_null_ = false;
-      return *this;
-    }
-
-   private:
-    std::string query_;
-    std::vector<DbType> bindings_;
-    std::map<int, DbType> binding_map_;
-    std::map<std::string, DbType> binding_name_map_;
-    bool empty_string_as_null_ = false;
-    bool empty_vector_as_null_ = false;
-  };
-
-  class Result {
-   public:
-    Result() = default;
-    ~Result() {
-      if (stmt_)
-        sqlite3_finalize(stmt_);
-    }
-
-    Result(const Result&) = delete;
-    Result& operator = (const Result&) = delete;
-
-    Result(Result&& r) noexcept {
-      stmt_ = r.stmt_;
-      r.stmt_ = nullptr;
-      query_ = std::move(r.query_);
-      is_done_ = r.is_done_;
-    }
-
-    Result& operator = (Result&& r) noexcept {
-      if (this != &r) {
-        if (stmt_)
-          sqlite3_finalize(stmt_);
-        stmt_ = r.stmt_;
-        r.stmt_ = nullptr;
-        query_ = std::move(r.query_);
-        is_done_ = r.is_done_;
-      }
-
-      return *this;
-    }
-
-    class Record {
-     public:
-      explicit Record(const sqlite3_stmt* stmt) : stmt_(stmt) {}
-
-      std::optional<std::string> GetString(int pos) const {
-        sqlite3_stmt* stmt = const_cast<sqlite3_stmt*>(stmt_);
-        const char* text = reinterpret_cast<const char*>(
-            sqlite3_column_text(stmt, pos));
-        if (!text)
-          return std::nullopt;
-
-        return text;
-      }
-
-      AutoDbType Get(int pos) const {
-        sqlite3_stmt* stmt = const_cast<sqlite3_stmt*>(stmt_);
-        int type = sqlite3_column_type(stmt, pos);
-
-        DbType dbt;
-        if (type == SQLITE_TEXT) {
-          dbt = DbType(reinterpret_cast<const char*>(
-              sqlite3_column_text(stmt, pos)));
-        } else if (type == SQLITE_INTEGER) {
-          dbt = DbType(static_cast<int64_t>(sqlite3_column_int64(stmt, pos)));
-        } else if (type == SQLITE_FLOAT) {
-          dbt = DbType(sqlite3_column_double(stmt, pos));
-        } else if (type == SQLITE_BLOB) {
-          const unsigned char* val = reinterpret_cast<const unsigned char*>(
-              sqlite3_column_blob(stmt, pos));
-          int len = sqlite3_column_bytes(stmt, pos);
-
-          if (!val || len < 0) {
-            throw DbException("invalid blob");;
-          } else {
-            dbt = DbType(std::vector<unsigned char>(val, val + len));
-          }
-        } else if (type == SQLITE_NULL) {
-          dbt = DbType(std::nullopt);
-        } else {
-          throw DbException("invalid column type", type);
-        }
-
-        return AutoDbType(dbt, type);
-      }
-
-      template <typename ...Types>
-      auto Get() const {
-        std::tuple<Types...> t;
-        int pos = 0;
-        for_<std::tuple_size_v<std::tuple<Types...>>>([&] (auto i) {
-          std::get<i.value>(t) = Get(pos++);
-        });
-
-        return t;
-      }
-
-     private:
-      const sqlite3_stmt* stmt_;
-    };
-
-    class Iterator {
-     public:
-      explicit Iterator(sqlite3_stmt* stmt) : stmt_(stmt) {}
-
-      Record operator*() { return Record(stmt_); }
-
-      bool operator != (const Iterator& rhs) const {
-        return stmt_ != rhs.stmt_;
-      }
-
-      void operator ++() {
-        int r = sqlite3_step(stmt_);
-        if (r != SQLITE_ROW)
-          stmt_ = nullptr;
-      }
-
-     private:
-      sqlite3_stmt* stmt_ = nullptr;
-    };
-
-    Iterator begin() const {
-      if (is_done_)
-        return Iterator(nullptr);
-      return Iterator(stmt_);
-    }
-
-    Iterator end() const {
-      return Iterator(nullptr);
-    }
-
-    operator bool() const {
-      if (stmt_ == nullptr)
-        return false;
-      return true;
-    }
-
-    explicit operator int() const {
-      auto db = db_.lock();
-      if (db == nullptr)
-        return SQLITE_ERROR;
-      return sqlite3_errcode(db.get());
-    }
-
-    explicit operator const char*() const {
-      auto db = db_.lock();
-      if (db == nullptr)
-        return "";
-      return sqlite3_errmsg(db.get());
-    }
-
-    template <class T>
-    std::vector<T> ToVector() {
-      if (stmt_ == nullptr)
-        return {};
-
-      std::vector<T> vec;
-      for (const auto& rec : *this) {
-        T t;
-        t(rec);
-        vec.push_back(std::move(t));
-      }
-
-      return vec;
-    }
-
-    template <class T>
-    std::list<T> ToList() {
-      if (stmt_ == nullptr)
-        return {};
-
-      std::list<T> l;
-      for (const auto& rec : *this) {
-        T t;
-        t(rec);
-        l.push_back(std::move(t));
-      }
-
-      return l;
-    }
-
-    template <class T>
-    std::optional<T> GetFirst() {
-      if (stmt_ == nullptr)
-        return std::nullopt;
-      for (const auto& rec : *this) {
-        T t;
-        t(rec);
-        return t;
-      }
-
-      return std::nullopt;
-    }
-
-    std::optional<Record> GetFirstRecord() {
-      if (stmt_ == nullptr)
-        return std::nullopt;
-      for (const auto& rec : *this) {
-        return rec;
-      }
-
-      return std::nullopt;
-    }
-
-    sqlite3_stmt* GetRaw() const {
-      return stmt_;
-    }
-
-    const std::string& GetQuery() const {
-      return query_;
-    }
-
-    void SetDone(bool is_done) {
-      is_done_ = is_done;
-    }
-
-    size_t GetColumnCount() const {
-      return sqlite3_column_count(stmt_);
-    }
-
-   private:
-    friend class Database;
-    Result(sqlite3_stmt* stmt, const std::shared_ptr<sqlite3>& db, std::string query, bool is_done)
-        : stmt_(stmt), db_(db), query_(std::move(query)), is_done_(is_done) {}
-
-    sqlite3_stmt* stmt_ = nullptr;
-    std::weak_ptr<sqlite3> db_;
-    std::string query_;
-    bool is_done_ = false;
-  };
-
-  Database(std::string db_path, int flags) {
-    sqlite3* raw_db = nullptr;
-    int r = sqlite3_open_v2(db_path.c_str(), &raw_db, flags, nullptr);
-    if (r != SQLITE_OK)
-      throw DbException("open failed", r);
-
-    db_.reset(raw_db, sqlite3_close_v2);
-  }
-
-  Database(std::string db_path, int flags,
-      std::function<bool(int)> busy_handler) {
-    sqlite3* raw_db = nullptr;
-    int r = sqlite3_open_v2(db_path.c_str(), &raw_db, flags, nullptr);
-    if (r != SQLITE_OK)
-      throw DbException("sqlite3_open_v2() failed", r);
-
-    db_.reset(raw_db, sqlite3_close_v2);
-    busy_handler_ = std::move(busy_handler);
-    r = sqlite3_busy_handler(db_.get(), [](void* data, int count) {
-      Database* pDb = static_cast<Database*>(data);
-      if (pDb->busy_handler_ && pDb->busy_handler_(count))
-        return 1;
-      return 0;
-    }, this);
-
-    if (r != SQLITE_OK)
-      throw DbException("sqlite3_busy_handler() failed", r);
-  }
-
-  ~Database() = default;
-  Database() = default;
-  Database(const Database&) = delete;
-  Database& operator = (const Database&) = delete;
-
-  Database(Database&& db) noexcept {
-    db_ = std::move(db.db_);
-    busy_handler_ = std::move(db.busy_handler_);
-    db.db_ = nullptr;
-    db.busy_handler_ = nullptr;
-
-    sqlite3_busy_handler(db_.get(), [](void* data, int count) {
-      Database* pDb = static_cast<Database*>(data);
-      if (pDb->busy_handler_ && pDb->busy_handler_(count))
-        return 1;
-      return 0;
-    }, this);
-  }
-
-  explicit operator bool() const {
-    if (db_ == nullptr)
-      return false;
-    return true;
-  }
-
-  Database& operator = (Database&& db) noexcept {
-    if (this != &db) {
-      db_ = std::move(db.db_);
-      busy_handler_ = std::move(db.busy_handler_);
-      db.db_ = nullptr;
-      db.busy_handler_ = nullptr;
-      sqlite3_busy_handler(db_.get(), [](void* data, int count) {
-        Database* pDb = static_cast<Database*>(data);
-        if (pDb->busy_handler_ && pDb->busy_handler_(count))
-          return 1;
-        return 0;
-      }, this);
-    }
-
-    return *this;
-  }
-
-  TransactionGuard CreateTransactionGuard() const {
-    return TransactionGuard(db_);
-  }
-
-  Result Prepare(const Sql& sql) const {
-    if (!db_)
-      throw DbException("Not opened");
-
-    sqlite3_stmt* stmt = nullptr;
-    int r = sqlite3_prepare_v2(db_.get(), sql.GetQuery().c_str(),
-        -1, &stmt, nullptr);
-    if (r != SQLITE_OK)
-      return { nullptr, db_, "", true };
-    return { stmt, db_, sql.GetQuery(), false };
-  }
-
-  Result Exec(const Sql& sql) const {
-    if (!db_)
-      throw DbException("Not opened");
-
-    sqlite3_stmt* stmt = nullptr;
-    int r = sqlite3_prepare_v2(db_.get(), sql.GetQuery().c_str(),
-        -1, &stmt, nullptr);
-    if (r != SQLITE_OK) {
-      return { nullptr, db_, "", true };
-    }
-
-    std::unique_ptr<sqlite3_stmt, decltype(sqlite3_finalize)*> stmt_auto(stmt,
-        sqlite3_finalize);
-    int pos = 1;
-    for (const auto& i : sql.GetBindings()) {
-      Bind(pos++, i, stmt);
-    }
-
-    for (const auto& i : sql.GetBindingMap()) {
-      Bind(i.first, i.second, stmt);
-    }
-
-    for (const auto& i : sql.GetBindingNameMap()) {
-      int pos = sqlite3_bind_parameter_index(stmt, i.first.c_str());
-      if (pos == 0)
-        throw DbException("Invalid binding");
-      Bind(pos, i.second, stmt);
-    }
-
-    r = sqlite3_step(stmt);
-    if (r != SQLITE_ROW && r != SQLITE_DONE) {
-      return { nullptr, db_, "", true };
-    }
-
-    return { stmt_auto.release(), db_, sql.GetQuery(),
-        r == SQLITE_DONE ? true : false };
-  }
-
-  bool Exec(const Sql& sql, Result& previous_stmt) const {
-    if (sql.GetQuery() != previous_stmt.GetQuery())
-      throw DbException("Query is different");
-
-    sqlite3_stmt* stmt = previous_stmt.GetRaw();
-    if (!stmt)
-      return false;
-
-    int r = sqlite3_reset(stmt);
-    if (r != SQLITE_ROW && r != SQLITE_DONE && r != SQLITE_OK)
-      return false;
-
-    int pos = 1;
-    for (const auto& i : sql.GetBindings()) {
-      Bind(pos++, i, stmt);
-    }
-
-    for (const auto& i : sql.GetBindingMap()) {
-      Bind(i.first, i.second, stmt);
-    }
-
-    for (const auto& i : sql.GetBindingNameMap()) {
-      int pos = sqlite3_bind_parameter_index(stmt, i.first.c_str());
-      if (pos == 0)
-        throw DbException("Invalid binding");
-      Bind(pos, i.second, stmt);
-    }
-
-    r = sqlite3_step(stmt);
-    if (r != SQLITE_ROW && r != SQLITE_DONE)
-      return false;
-
-    previous_stmt.SetDone(r == SQLITE_DONE ? true : false);
-    return true;
-  }
-
-  void OneStepExec(const Sql& sql) const {
-    char* errmsg = nullptr;
-    int ret = sqlite3_exec(db_.get(), sql.GetQuery().c_str(), nullptr, nullptr,
-        &errmsg);
-    if (ret != SQLITE_OK) {
-      std::unique_ptr<char, decltype(sqlite3_free)*> errmsg_auto(
-          errmsg, sqlite3_free);
-      throw DbException(errmsg);
-    }
-  }
-
-  sqlite3* GetRaw() const {
-    if (!db_)
-      throw DbException("Not opened");
-    return db_.get();
-  }
-
- private:
-  void Bind(int pos, const DbType& type, sqlite3_stmt* stmt) const {
-    int r;
-    if (!type) {
-      r = sqlite3_bind_null(stmt, pos);
-      if (r != SQLITE_OK) {
-        throw DbException("Invalid binding", r);
-      }
-
-      return;
-    }
-
-    if (const std::string* pstr = std::get_if<std::string>(&(*type))) {
-      r = sqlite3_bind_text(stmt, pos, (*pstr).c_str(), -1,
-          SQLITE_TRANSIENT);
-    } else if (const int64_t* pint = std::get_if<int64_t>(&(*type))) {
-      r = sqlite3_bind_int64(stmt, pos, (*pint));
-    } else if (const double* pdouble = std::get_if<double>(&(*type))) {
-      r = sqlite3_bind_double(stmt, pos, (*pdouble));
-    } else if (const std::vector<unsigned char>* pvector =
-        std::get_if<std::vector<unsigned char>>(&(*type))) {
-      r = sqlite3_bind_blob(stmt, pos, (*pvector).data(),
-          (*pvector).size(), nullptr);
-    } else {
-      r = -1;
-    }
-
-    if (r != SQLITE_OK) {
-      throw DbException("Invalid binding");
-    }
-  }
-
- private:
-  std::shared_ptr<sqlite3> db_ = nullptr;
-  std::function<bool(int)> busy_handler_;
-};
-
-}  // namespace tizen_base
-
-#endif  // TIZEN_DATABASE_DATABASE_HPP_
diff --git a/tizen-database/tizen-database.pc.in b/tizen-database/tizen-database.pc.in
deleted file mode 100644 (file)
index 82ee192..0000000
+++ /dev/null
@@ -1,11 +0,0 @@
-# Wrapper class for sqlite3
-
-prefix=@PREFIX@
-includedir=${prefix}/include
-
-Name: tizen-database
-Description: Wrapper class for sqlite3
-Version: @VERSION@
-Requires: sqlite3
-Cflags: -I${includedir} -I${includedir}/tizen-database
-cppflags: -I${includedir} -I${includedir}/tizen-database
diff --git a/tizen-shared-queue/CMakeLists.txt b/tizen-shared-queue/CMakeLists.txt
deleted file mode 100644 (file)
index 8ffe1c8..0000000
+++ /dev/null
@@ -1,10 +0,0 @@
-### Make pkgconfig file
-SET(PREFIX ${CMAKE_INSTALL_PREFIX})
-CONFIGURE_FILE(${CMAKE_CURRENT_SOURCE_DIR}/tizen-shared-queue.pc.in
-  ${CMAKE_BINARY_DIR}/tizen-shared-queue.pc @ONLY)
-
-### Install
-INSTALL(FILES ${CMAKE_BINARY_DIR}/tizen-shared-queue.pc
-  DESTINATION ${LIB_INSTALL_DIR}/pkgconfig/)
-INSTALL(FILES ${CMAKE_CURRENT_SOURCE_DIR}/shared-queue.hpp
-  DESTINATION include/tizen-shared-queue)
diff --git a/tizen-shared-queue/shared-queue.hpp b/tizen-shared-queue/shared-queue.hpp
deleted file mode 100644 (file)
index f73552d..0000000
+++ /dev/null
@@ -1,96 +0,0 @@
-/*
- * Copyright (c) 2023 Samsung Electronics Co., Ltd All Rights Reserved
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- *     http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#ifndef TIZEN_SHARED_QUEUE_SHARED_QUEUE_HPP_
-#define TIZEN_SHARED_QUEUE_SHARED_QUEUE_HPP_
-
-#include <condition_variable>
-#include <memory>
-#include <mutex>
-#include <queue>
-#include <thread>
-#include <utility>
-
-namespace tizen_base {
-
-template <class T>
-class SharedQueue {
- public:
-  SharedQueue() = default;
-  virtual ~SharedQueue() = default;
-
-  void Push(T item) {
-    std::lock_guard<std::mutex> lock(mutex_);
-    queue_.push(item);
-    cond_var_.notify_one();
-  }
-
-  bool TryAndPop(T& item) {
-    std::lock_guard<std::mutex> lock(mutex_);
-    if (queue_.empty())
-      return false;
-
-    item = queue_.front();
-    queue_.pop();
-    return true;
-  }
-
-  T WaitAndPop() {
-    std::unique_lock<std::mutex> lock(mutex_);
-    while (queue_.empty())
-      cond_var_.wait(lock);
-
-    auto item = std::move(queue_.front());
-    queue_.pop();
-    return item;
-  }
-
-  bool WaitAndPopFor(T& item, int timeout) {
-    std::unique_lock<std::mutex> lock(mutex_);
-    if (!queue_.empty()) {
-      item = queue_.front();
-      queue_.pop();
-      return true;
-    }
-
-    std::chrono::milliseconds duration(timeout);
-    if (cond_var_.wait_for(lock, duration) == std::cv_status::timeout)
-      return false;
-
-    item = queue_.front();
-    queue_.pop();
-    return true;
-  }
-
-  bool IsEmpty() const {
-    std::lock_guard<std::mutex> lock(mutex_);
-    return queue_.empty();
-  }
-
-  unsigned int Size() const {
-    std::lock_guard<std::mutex> lock(mutex_);
-    return queue_.size();
-  }
-
- private:
-  std::queue<T> queue_;
-  mutable std::mutex mutex_;
-  std::condition_variable cond_var_;
-};
-
-}  // namespace tizen_base
-
-#endif  // TIZEN_SHARED_QUEUE_SHARED_QUEUE_HPP_
diff --git a/tizen-shared-queue/tizen-shared-queue.pc.in b/tizen-shared-queue/tizen-shared-queue.pc.in
deleted file mode 100644 (file)
index 22969ce..0000000
+++ /dev/null
@@ -1,11 +0,0 @@
-# Wrapper class for sqlite3
-
-prefix=@PREFIX@
-includedir=${prefix}/include
-
-Name: tizen-shared-queue
-Description: shared queue class for active object pattern
-Version: @VERSION@
-Requires:
-Cflags: -I${includedir} -I${includedir}/tizen-shared-queue
-cppflags: -I${includedir} -I${includedir}/tizen-shared-queue