diff options
author | Jinkun Jang <jinkun.jang@samsung.com> | 2013-03-13 01:46:48 +0900 |
---|---|---|
committer | Jinkun Jang <jinkun.jang@samsung.com> | 2013-03-13 01:46:48 +0900 |
commit | 9945e57e45c70b16b7e2ddd6c0a62f2d03397f02 (patch) | |
tree | c392bc1776c72ac47e5e4270a81c2446410c188f | |
parent | 7c1dbd27a3ca235a892ffdb9ee07e67b74e90409 (diff) | |
download | bundle-9945e57e45c70b16b7e2ddd6c0a62f2d03397f02.tar.gz bundle-9945e57e45c70b16b7e2ddd6c0a62f2d03397f02.tar.bz2 bundle-9945e57e45c70b16b7e2ddd6c0a62f2d03397f02.zip |
Tizen 2.1 base
53 files changed, 6576 insertions, 0 deletions
@@ -0,0 +1,4 @@ +Youmin Ha <youmin.ha@samsung.com> +Jayoun Lee <airjany@samsung.com> +Sewook Park <sewook7.park@samsung.com> +Jaeho Lee <jaeho81.lee@samsung.com> diff --git a/CMakeLists.txt b/CMakeLists.txt new file mode 100644 index 0000000..9a298eb --- /dev/null +++ b/CMakeLists.txt @@ -0,0 +1,55 @@ +CMAKE_MINIMUM_REQUIRED(VERSION 2.6) +PROJECT(bundle C) + +### Get VERSION from debian/changelog +file(STRINGS debian/changelog version_line LIMIT_COUNT 1 REGEX "(.*)") +string(REGEX REPLACE ".*\\(\([0-9]+:\)*\([0-9a-zA-Z.]*\).*\\).*" "\\2" VERSION ${version_line}) # Get version +string(REGEX REPLACE "^\([0-9]+\)\\..*" "\\1" VERSION_MAJOR ${VERSION}) # Get major version +message(STATUS "Version from debian/changelog: ${VERSION}, Major version: ${VERSION_MAJOR}") + +### Required packages +INCLUDE(FindPkgConfig) +pkg_check_modules(pkgs REQUIRED glib-2.0 dlog) +FOREACH(flag ${pkgs_CFLAGS}) + SET(EXTRA_CFLAGS "${EXTRA_CFLAGS} ${flag}") +ENDFOREACH(flag) + +set(CMAKE_C_FLAGS "${CMAKE_C_FLAGS} ${EXTRA_CFLAGS}") + +### Local include directories +include_directories(${CMAKE_SOURCE_DIR}/include ${CMAKE_SOURCE_DIR}/src) + +### Build +add_library(bundle SHARED + src/bundle.c + src/keyval_type.c + src/keyval.c + src/keyval_array.c + ) +set_target_properties(bundle PROPERTIES SOVERSION ${VERSION_MAJOR}) +set_target_properties(bundle PROPERTIES VERSION ${VERSION}) +target_link_libraries(bundle ${pkgs_LDFLAGS}) + + +### Make pkgconfig file +SET(PREFIX ${CMAKE_INSTALL_PREFIX}) +CONFIGURE_FILE(${CMAKE_SOURCE_DIR}/bundle.pc.in ${CMAKE_BINARY_DIR}/bundle.pc @ONLY) + + +### Install +install(TARGETS bundle + DESTINATION lib + ) +install(FILES + ${CMAKE_SOURCE_DIR}/include/bundle.h + ${CMAKE_SOURCE_DIR}/include/SLP_bundle_PG.h + DESTINATION include/ + ) +install(FILES ${CMAKE_BINARY_DIR}/bundle.pc + DESTINATION lib/pkgconfig/ + ) + + +### Test +add_subdirectory(test) + @@ -0,0 +1,204 @@ +Copyright (c) 2000 - 2011 Samsung Electronics Co., Ltd. All rights reserved. + + Apache License + Version 2.0, January 2004 + http://www.apache.org/licenses/ + + TERMS AND CONDITIONS FOR USE, REPRODUCTION, AND DISTRIBUTION + + 1. Definitions. + + "License" shall mean the terms and conditions for use, reproduction, + and distribution as defined by Sections 1 through 9 of this document. + + "Licensor" shall mean the copyright owner or entity authorized by + the copyright owner that is granting the License. + + "Legal Entity" shall mean the union of the acting entity and all + other entities that control, are controlled by, or are under common + control with that entity. For the purposes of this definition, + "control" means (i) the power, direct or indirect, to cause the + direction or management of such entity, whether by contract or + otherwise, or (ii) ownership of fifty percent (50%) or more of the + outstanding shares, or (iii) beneficial ownership of such entity. + + "You" (or "Your") shall mean an individual or Legal Entity + exercising permissions granted by this License. + + "Source" form shall mean the preferred form for making modifications, + including but not limited to software source code, documentation + source, and configuration files. + + "Object" form shall mean any form resulting from mechanical + transformation or translation of a Source form, including but + not limited to compiled object code, generated documentation, + and conversions to other media types. + + "Work" shall mean the work of authorship, whether in Source or + Object form, made available under the License, as indicated by a + copyright notice that is included in or attached to the work + (an example is provided in the Appendix below). + + "Derivative Works" shall mean any work, whether in Source or Object + form, that is based on (or derived from) the Work and for which the + editorial revisions, annotations, elaborations, or other modifications + represent, as a whole, an original work of authorship. For the purposes + of this License, Derivative Works shall not include works that remain + separable from, or merely link (or bind by name) to the interfaces of, + the Work and Derivative Works thereof. + + "Contribution" shall mean any work of authorship, including + the original version of the Work and any modifications or additions + to that Work or Derivative Works thereof, that is intentionally + submitted to Licensor for inclusion in the Work by the copyright owner + or by an individual or Legal Entity authorized to submit on behalf of + the copyright owner. For the purposes of this definition, "submitted" + means any form of electronic, verbal, or written communication sent + to the Licensor or its representatives, including but not limited to + communication on electronic mailing lists, source code control systems, + and issue tracking systems that are managed by, or on behalf of, the + Licensor for the purpose of discussing and improving the Work, but + excluding communication that is conspicuously marked or otherwise + designated in writing by the copyright owner as "Not a Contribution." + + "Contributor" shall mean Licensor and any individual or Legal Entity + on behalf of whom a Contribution has been received by Licensor and + subsequently incorporated within the Work. + + 2. Grant of Copyright License. Subject to the terms and conditions of + this License, each Contributor hereby grants to You a perpetual, + worldwide, non-exclusive, no-charge, royalty-free, irrevocable + copyright license to reproduce, prepare Derivative Works of, + publicly display, publicly perform, sublicense, and distribute the + Work and such Derivative Works in Source or Object form. + + 3. Grant of Patent License. Subject to the terms and conditions of + this License, each Contributor hereby grants to You a perpetual, + worldwide, non-exclusive, no-charge, royalty-free, irrevocable + (except as stated in this section) patent license to make, have made, + use, offer to sell, sell, import, and otherwise transfer the Work, + where such license applies only to those patent claims licensable + by such Contributor that are necessarily infringed by their + Contribution(s) alone or by combination of their Contribution(s) + with the Work to which such Contribution(s) was submitted. If You + institute patent litigation against any entity (including a + cross-claim or counterclaim in a lawsuit) alleging that the Work + or a Contribution incorporated within the Work constitutes direct + or contributory patent infringement, then any patent licenses + granted to You under this License for that Work shall terminate + as of the date such litigation is filed. + + 4. Redistribution. You may reproduce and distribute copies of the + Work or Derivative Works thereof in any medium, with or without + modifications, and in Source or Object form, provided that You + meet the following conditions: + + (a) You must give any other recipients of the Work or + Derivative Works a copy of this License; and + + (b) You must cause any modified files to carry prominent notices + stating that You changed the files; and + + (c) You must retain, in the Source form of any Derivative Works + that You distribute, all copyright, patent, trademark, and + attribution notices from the Source form of the Work, + excluding those notices that do not pertain to any part of + the Derivative Works; and + + (d) If the Work includes a "NOTICE" text file as part of its + distribution, then any Derivative Works that You distribute must + include a readable copy of the attribution notices contained + within such NOTICE file, excluding those notices that do not + pertain to any part of the Derivative Works, in at least one + of the following places: within a NOTICE text file distributed + as part of the Derivative Works; within the Source form or + documentation, if provided along with the Derivative Works; or, + within a display generated by the Derivative Works, if and + wherever such third-party notices normally appear. The contents + of the NOTICE file are for informational purposes only and + do not modify the License. You may add Your own attribution + notices within Derivative Works that You distribute, alongside + or as an addendum to the NOTICE text from the Work, provided + that such additional attribution notices cannot be construed + as modifying the License. + + You may add Your own copyright statement to Your modifications and + may provide additional or different license terms and conditions + for use, reproduction, or distribution of Your modifications, or + for any such Derivative Works as a whole, provided Your use, + reproduction, and distribution of the Work otherwise complies with + the conditions stated in this License. + + 5. Submission of Contributions. Unless You explicitly state otherwise, + any Contribution intentionally submitted for inclusion in the Work + by You to the Licensor shall be under the terms and conditions of + this License, without any additional terms or conditions. + Notwithstanding the above, nothing herein shall supersede or modify + the terms of any separate license agreement you may have executed + with Licensor regarding such Contributions. + + 6. Trademarks. This License does not grant permission to use the trade + names, trademarks, service marks, or product names of the Licensor, + except as required for reasonable and customary use in describing the + origin of the Work and reproducing the content of the NOTICE file. + + 7. Disclaimer of Warranty. Unless required by applicable law or + agreed to in writing, Licensor provides the Work (and each + Contributor provides its Contributions) on an "AS IS" BASIS, + WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or + implied, including, without limitation, any warranties or conditions + of TITLE, NON-INFRINGEMENT, MERCHANTABILITY, or FITNESS FOR A + PARTICULAR PURPOSE. You are solely responsible for determining the + appropriateness of using or redistributing the Work and assume any + risks associated with Your exercise of permissions under this License. + + 8. Limitation of Liability. In no event and under no legal theory, + whether in tort (including negligence), contract, or otherwise, + unless required by applicable law (such as deliberate and grossly + negligent acts) or agreed to in writing, shall any Contributor be + liable to You for damages, including any direct, indirect, special, + incidental, or consequential damages of any character arising as a + result of this License or out of the use or inability to use the + Work (including but not limited to damages for loss of goodwill, + work stoppage, computer failure or malfunction, or any and all + other commercial damages or losses), even if such Contributor + has been advised of the possibility of such damages. + + 9. Accepting Warranty or Additional Liability. While redistributing + the Work or Derivative Works thereof, You may choose to offer, + and charge a fee for, acceptance of support, warranty, indemnity, + or other liability obligations and/or rights consistent with this + License. However, in accepting such obligations, You may act only + on Your own behalf and on Your sole responsibility, not on behalf + of any other Contributor, and only if You agree to indemnify, + defend, and hold each Contributor harmless for any liability + incurred by, or claims asserted against, such Contributor by reason + of your accepting any such warranty or additional liability. + + END OF TERMS AND CONDITIONS + + APPENDIX: How to apply the Apache License to your work. + + To apply the Apache License to your work, attach the following + boilerplate notice, with the fields enclosed by brackets "[]" + replaced with your own identifying information. (Don't include + the brackets!) The text should be enclosed in the appropriate + comment syntax for the file format. We also recommend that a + file or class name and description of purpose be included on the + same "printed page" as the copyright notice for easier + identification within third-party archives. + + Copyright [yyyy] [name of copyright owner] + + 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. + @@ -0,0 +1,4 @@ +bundle : A simple string-based key-val dictionary + +By Youmin Ha + diff --git a/TC/build.sh b/TC/build.sh new file mode 100755 index 0000000..98ebeff --- /dev/null +++ b/TC/build.sh @@ -0,0 +1,20 @@ +#!/bin/sh + +export TET_INSTALL_PATH=/scratchbox/tetware # local tetware path +export TET_TARGET_PATH=$TET_INSTALL_PATH/tetware-target +export PATH=$TET_TARGET_PATH/bin:$PATH +export LD_LIBRARY_PATH=$TET_TARGET_PATH/lib/tet3:$LD_LIBRARY_PATH +export TET_ROOT=$TET_TARGET_PATH + +export TET_SUITE_ROOT=`pwd` +FILE_NAME_EXTENSION=`date +%s` + +RESULT_DIR=results +HTML_RESULT=$RESULT_DIR/build-tar-result-$FILE_NAME_EXTENSION.html +JOURNAL_RESULT=$RESULT_DIR/build-tar-result-$FILE_NAME_EXTENSION.journal + +mkdir -p $RESULT_DIR + +tcc -c -p ./ +tcc -b -j $JOURNAL_RESULT -p ./ +grw -c 3 -f chtml -o $HTML_RESULT $JOURNAL_RESULT diff --git a/TC/execute.sh b/TC/execute.sh new file mode 100755 index 0000000..2d9df79 --- /dev/null +++ b/TC/execute.sh @@ -0,0 +1,20 @@ +#!/bin/sh +#export TET_INSTALL_PATH=/mnt/nfs/tetware +export TET_INSTALL_PATH=/scratchbox/tetware +export TET_TARGET_PATH=$TET_INSTALL_PATH/tetware-target +export PATH=$TET_TARGET_PATH/bin:$PATH +export LD_LIBRARY_PATH=$TET_TARGET_PATH/lib/tet3:$LD_LIBRARY_PATH + +export TET_ROOT=$TET_TARGET_PATH + +export TET_SUITE_ROOT=`pwd` +FILE_NAME_EXTENSION=`date +%s` + +RESULT_DIR=results +HTML_RESULT=$RESULT_DIR/exec-tar-result-$FILE_NAME_EXTENSION.html +JOURNAL_RESULT=$RESULT_DIR/exec-tar-result-$FILE_NAME_EXTENSION.journal + +mkdir -p $RESULT_DIR + +tcc -e -j $JOURNAL_RESULT -p ./ +grw -c 3 -f chtml -o $HTML_RESULT $JOURNAL_RESULT diff --git a/TC/tet_code b/TC/tet_code new file mode 100755 index 0000000..a2cf6c1 --- /dev/null +++ b/TC/tet_code @@ -0,0 +1,12 @@ +# TET reserved codes +0 "PASS" +1 "FAIL" +2 "UNRESOLVED" +3 "NOTINUSE" +4 "UNSUPPORTED" +5 "UNTESTED" +6 "UNINITIATED" +7 "NORESULT" + +# Test suite additional codes +33 "INSPECT" diff --git a/TC/tet_scen b/TC/tet_scen new file mode 100755 index 0000000..43cbc9b --- /dev/null +++ b/TC/tet_scen @@ -0,0 +1,7 @@ +all + ^TEST +##### Scenarios for TEST ##### + +# Test scenario +TEST + :include:/unit/tslist diff --git a/TC/tetbuild.cfg b/TC/tetbuild.cfg new file mode 100755 index 0000000..6192c78 --- /dev/null +++ b/TC/tetbuild.cfg @@ -0,0 +1,3 @@ +TET_OUTPUT_CAPTURE=False +TET_BUILD_TOOL=make +TET_PASS_TC_NAME=True diff --git a/TC/tetclean.cfg b/TC/tetclean.cfg new file mode 100755 index 0000000..c66eda4 --- /dev/null +++ b/TC/tetclean.cfg @@ -0,0 +1,2 @@ +TET_OUTPUT_CAPTURE=False +TET_CLEAN_TOOL=make clean diff --git a/TC/tetexec.cfg b/TC/tetexec.cfg new file mode 100755 index 0000000..0d9d39a --- /dev/null +++ b/TC/tetexec.cfg @@ -0,0 +1 @@ +TET_OUTPUT_CAPTURE=False diff --git a/TC/unit/Makefile b/TC/unit/Makefile new file mode 100644 index 0000000..2d8e954 --- /dev/null +++ b/TC/unit/Makefile @@ -0,0 +1,22 @@ +CC ?= gcc + +TARGETS = utc_ApplicationFW_bundle_create_func utc_ApplicationFW_bundle_free_func utc_ApplicationFW_bundle_add_func utc_ApplicationFW_bundle_del_func utc_ApplicationFW_bundle_get_val_func utc_ApplicationFW_bundle_get_count_func utc_ApplicationFW_bundle_dup_func utc_ApplicationFW_bundle_iterate_func utc_ApplicationFW_bundle_encode_func utc_ApplicationFW_bundle_decode_func + +PKGS = bundle + +LDFLAGS = `pkg-config --libs $(PKGS)` +LDFLAGS += $(TET_ROOT)/lib/tet3/tcm_s.o +LDFLAGS += -L$(TET_ROOT)/lib/tet3 -ltcm_s +LDFLAGS += -L$(TET_ROOT)/lib/tet3 -lapi_s + +CFLAGS = -I. `pkg-config --cflags $(PKGS)` +CFLAGS += -I$(TET_ROOT)/inc/tet3 +CFLAGS += -Wall + +all: $(TARGETS) + +$(TARGETS): %: %.c + $(CC) -o $@ $< $(CFLAGS) $(LDFLAGS) + +clean: + rm -f $(TARGETS) diff --git a/TC/unit/tc_gen.sh b/TC/unit/tc_gen.sh new file mode 100755 index 0000000..54f482d --- /dev/null +++ b/TC/unit/tc_gen.sh @@ -0,0 +1,28 @@ +#!/bin/sh + +TMPSTR=$0 +SCRIPT=${TMPSTR##*/} + +if [ $# -lt 2 ]; then + echo "Usage) $SCRIPT module_name api_name" + exit 1 +fi + +MODULE=$1 +API=$2 +TEMPLATE=utc_MODULE_API_func.c.in +TESTCASE=utc_${MODULE}_${API}_func + +sed -e ' + s^@API@^'"$API"'^g + s^@MODULE@^'"$MODULE"'^g + ' $TEMPLATE > $TESTCASE.c + +if [ ! -e "$TESTCASE.c" ]; then + echo "Failed" + exit 1 +fi +echo "Testcase file is $TESTCASE.c" +echo "Done" +echo "please put \"$TESTCASE\" as Target in Makefile" +echo "please put \"/unit/$TESTCASE\" in tslist" diff --git a/TC/unit/tslist b/TC/unit/tslist new file mode 100644 index 0000000..3217a8f --- /dev/null +++ b/TC/unit/tslist @@ -0,0 +1,10 @@ +/unit/utc_ApplicationFW_bundle_create_func +/unit/utc_ApplicationFW_bundle_free_func +/unit/utc_ApplicationFW_bundle_add_func +/unit/utc_ApplicationFW_bundle_del_func +/unit/utc_ApplicationFW_bundle_get_val_func +/unit/utc_ApplicationFW_bundle_get_count_func +/unit/utc_ApplicationFW_bundle_dup_func +/unit/utc_ApplicationFW_bundle_iterate_func +/unit/utc_ApplicationFW_bundle_encode_func +/unit/utc_ApplicationFW_bundle_decode_func diff --git a/TC/unit/utc_ApplicationFW_bundle_add_func.c b/TC/unit/utc_ApplicationFW_bundle_add_func.c new file mode 100644 index 0000000..936d863 --- /dev/null +++ b/TC/unit/utc_ApplicationFW_bundle_add_func.c @@ -0,0 +1,116 @@ +/* + * bundle + * + * Copyright (c) 2000 - 2011 Samsung Electronics Co., Ltd. All rights reserved. + * + * Contact: Jayoun Lee <airjany@samsung.com>, Sewook Park <sewook7.park@samsung.com>, + * Jaeho Lee <jaeho81.lee@samsung.com> + * + * 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 <tet_api.h> +#include "bundle.h" + +static void startup(void); +static void cleanup(void); + +void (*tet_startup)(void) = startup; +void (*tet_cleanup)(void) = cleanup; + +static void utc_ApplicationFW_bundle_add_func_01(void); +static void utc_ApplicationFW_bundle_add_func_02(void); + +enum { + POSITIVE_TC_IDX = 0x01, + NEGATIVE_TC_IDX, +}; + +struct tet_testlist tet_testlist[] = { + { utc_ApplicationFW_bundle_add_func_01, POSITIVE_TC_IDX }, + { utc_ApplicationFW_bundle_add_func_02, NEGATIVE_TC_IDX }, + { NULL, 0 } +}; + +static void startup(void) +{ +} + +static void cleanup(void) +{ +} + +/** + * @brief Positive test case of bundle_add() + */ +static void utc_ApplicationFW_bundle_add_func_01(void) +{ + int r = 0; + + bundle *b = bundle_create(); + if(!b) { + tet_result(TET_UNINITIATED); + return; + } + + r = bundle_add(b, "a", "abc"); + + if (r) { + tet_infoline("bundle_add() failed in positive test case"); + tet_result(TET_FAIL); + return; + } + + bundle_free(b); + tet_result(TET_PASS); +} + +/** + * @brief Negative test case of ug_init bundle_add() + */ +static void utc_ApplicationFW_bundle_add_func_02(void) +{ + int r = 0; + + bundle *b = bundle_create(); + if(!b) { + tet_result(TET_UNINITIATED); + return; + } + + + bundle_add(b, "abc", "def"); + r = bundle_add(b, "abc", "aaa"); + if (0 == r) { + tet_infoline("bundle_add() failed in negative test case\nduplicated key is not detected"); + tet_result(TET_FAIL); + return; + } + + r = bundle_add(b, NULL, "aaa"); + if (0 == r) { + tet_infoline("bundle_add() failed in negative test case\nNULL key is not detected"); + tet_result(TET_FAIL); + return; + } + + r = bundle_add(b, "def", NULL); + if (0 == r) { + tet_infoline("bundle_add() failed in negative test case\nNULL val is not detected"); + tet_result(TET_FAIL); + return; + } + + bundle_free(b); + tet_result(TET_PASS); +} diff --git a/TC/unit/utc_ApplicationFW_bundle_create_func.c b/TC/unit/utc_ApplicationFW_bundle_create_func.c new file mode 100644 index 0000000..137ab37 --- /dev/null +++ b/TC/unit/utc_ApplicationFW_bundle_create_func.c @@ -0,0 +1,93 @@ +/* + * bundle + * + * Copyright (c) 2000 - 2011 Samsung Electronics Co., Ltd. All rights reserved. + * + * Contact: Jayoun Lee <airjany@samsung.com>, Sewook Park <sewook7.park@samsung.com>, + * Jaeho Lee <jaeho81.lee@samsung.com> + * + * 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 <tet_api.h> +#include "bundle.h" + + +static void startup(void); +static void cleanup(void); + +void (*tet_startup)(void) = startup; +void (*tet_cleanup)(void) = cleanup; + +static void utc_ApplicationFW_bundle_create_func_01(void); +static void utc_ApplicationFW_bundle_create_func_02(void); + +enum { + POSITIVE_TC_IDX = 0x01, + NEGATIVE_TC_IDX, +}; + +struct tet_testlist tet_testlist[] = { + { utc_ApplicationFW_bundle_create_func_01, POSITIVE_TC_IDX }, + { utc_ApplicationFW_bundle_create_func_02, NEGATIVE_TC_IDX }, + { NULL, 0 } +}; + +static void startup(void) +{ +} + +static void cleanup(void) +{ +} + +/** + * @brief Positive test case of bundle_create() + */ +static void utc_ApplicationFW_bundle_create_func_01(void) +{ + bundle *b = NULL; + + b = bundle_create(); + +/* + r = bundle_create(...); +*/ + if (NULL == b) { + tet_infoline("bundle_create() failed in positive test case"); + tet_result(TET_FAIL); + return; + } + + if(b) bundle_free(b); + + tet_result(TET_PASS); +} + +/** + * @brief Negative test case of ug_init bundle_create() + */ +static void utc_ApplicationFW_bundle_create_func_02(void) +{ + int r = 0; + +/* + * No argument is required +*/ + if (r) { + tet_infoline("bundle_create() failed in negative test case"); + tet_result(TET_FAIL); + return; + } + tet_result(TET_PASS); +} diff --git a/TC/unit/utc_ApplicationFW_bundle_decode_func.c b/TC/unit/utc_ApplicationFW_bundle_decode_func.c new file mode 100644 index 0000000..e84fec5 --- /dev/null +++ b/TC/unit/utc_ApplicationFW_bundle_decode_func.c @@ -0,0 +1,111 @@ +/* + * bundle + * + * Copyright (c) 2000 - 2011 Samsung Electronics Co., Ltd. All rights reserved. + * + * Contact: Jayoun Lee <airjany@samsung.com>, Sewook Park <sewook7.park@samsung.com>, + * Jaeho Lee <jaeho81.lee@samsung.com> + * + * 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 <tet_api.h> +#include "bundle.h" +#include <string.h> +#include <stdlib.h> + +static void startup(void); +static void cleanup(void); + +void (*tet_startup)(void) = startup; +void (*tet_cleanup)(void) = cleanup; + +static void utc_ApplicationFW_bundle_decode_func_01(void); +static void utc_ApplicationFW_bundle_decode_func_02(void); + +enum { + POSITIVE_TC_IDX = 0x01, + NEGATIVE_TC_IDX, +}; + +struct tet_testlist tet_testlist[] = { + { utc_ApplicationFW_bundle_decode_func_01, POSITIVE_TC_IDX }, + { utc_ApplicationFW_bundle_decode_func_02, NEGATIVE_TC_IDX }, + { NULL, 0 } +}; + +static void startup(void) +{ +} + +static void cleanup(void) +{ +} + +/** + * @brief Positive test case of bundle_decode() + */ +static void utc_ApplicationFW_bundle_decode_func_01(void) +{ + int r = 0; + int len; + bundle_raw *raw = NULL; + + bundle *b = bundle_create(); + if(!b) { + tet_result(TET_UNINITIATED); + return; + } + if(bundle_add(b, "a", "123")) { + tet_result(TET_UNINITIATED); + goto cleanup; + } + + r = bundle_encode(b, &raw, &len); + if(NULL == raw) { + tet_result(TET_UNINITIATED); + goto cleanup; + } + + bundle *b_dec = bundle_decode(raw, len); + if(NULL == b_dec) { + tet_result(TET_FAIL); + goto cleanup; + } + if(0 != strcmp("123", bundle_get_val(b, "a"))) { + tet_result(TET_FAIL); + goto cleanup; + } + + tet_result(TET_PASS); + +cleanup: + if(b) bundle_free(b); + if(raw) free(raw); + return; +} + +/** + * @brief Negative test case of ug_init bundle_decode() + */ +static void utc_ApplicationFW_bundle_decode_func_02(void) +{ + if(NULL != bundle_decode(NULL, 1)) { + tet_result(TET_FAIL); + goto cleanup; + } + + tet_result(TET_PASS); +cleanup: + return; +} diff --git a/TC/unit/utc_ApplicationFW_bundle_del_func.c b/TC/unit/utc_ApplicationFW_bundle_del_func.c new file mode 100644 index 0000000..847a9fb --- /dev/null +++ b/TC/unit/utc_ApplicationFW_bundle_del_func.c @@ -0,0 +1,133 @@ +/* + * bundle + * + * Copyright (c) 2000 - 2011 Samsung Electronics Co., Ltd. All rights reserved. + * + * Contact: Jayoun Lee <airjany@samsung.com>, Sewook Park <sewook7.park@samsung.com>, + * Jaeho Lee <jaeho81.lee@samsung.com> + * + * 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 <tet_api.h> +#include "bundle.h" + +static void startup(void); +static void cleanup(void); + +void (*tet_startup)(void) = startup; +void (*tet_cleanup)(void) = cleanup; + +static void utc_ApplicationFW_bundle_del_func_01(void); +static void utc_ApplicationFW_bundle_del_func_02(void); + +enum { + POSITIVE_TC_IDX = 0x01, + NEGATIVE_TC_IDX, +}; + +struct tet_testlist tet_testlist[] = { + { utc_ApplicationFW_bundle_del_func_01, POSITIVE_TC_IDX }, + { utc_ApplicationFW_bundle_del_func_02, NEGATIVE_TC_IDX }, + { NULL, 0 } +}; + +static void startup(void) +{ +} + +static void cleanup(void) +{ +} + +/** + * @brief Positive test case of bundle_del() + */ +static void utc_ApplicationFW_bundle_del_func_01(void) +{ + int r = 0; + + bundle *b = bundle_create(); + if(!b) { + tet_result(TET_UNINITIATED); + return; + } + if(bundle_add(b, "a", "123")) { + tet_result(TET_UNINITIATED); + goto cleanup; + } + + r = bundle_del(b, "a"); + if (r) { + tet_infoline("bundle_del() failed in positive test case"); + tet_result(TET_FAIL); + goto cleanup; + } + tet_result(TET_PASS); + +cleanup: + if(b) bundle_free(b); + return; +} + +/** + * @brief Negative test case of ug_init bundle_del() + */ +static void utc_ApplicationFW_bundle_del_func_02(void) +{ + int r = 0; + + bundle *b = bundle_create(); + if(!b) { + tet_result(TET_UNINITIATED); + return; + } + if(bundle_add(b, "a", "123")) { + tet_result(TET_UNINITIATED); + goto cleanup; + } + + r = bundle_del(b, "a"); + if (r) { + tet_infoline("bundle_del() failed in negative test case"); + tet_result(TET_FAIL); + goto cleanup; + } + + r = bundle_del(b, "a"); + if(!r) { + tet_infoline("bundle_del() failed in negative test case"); + tet_result(TET_FAIL); + goto cleanup; + } + + r = bundle_del(b, NULL); + if(!r) { + tet_infoline("bundle_del() failed in negative test case"); + tet_result(TET_FAIL); + goto cleanup; + } + + r = bundle_del(NULL, "a"); + if(!r) { + tet_infoline("bundle_del() failed in negative test case"); + tet_result(TET_FAIL); + goto cleanup; + } + + tet_result(TET_PASS); + +cleanup: + if(b) bundle_free(b); + return; +} diff --git a/TC/unit/utc_ApplicationFW_bundle_dup_func.c b/TC/unit/utc_ApplicationFW_bundle_dup_func.c new file mode 100644 index 0000000..34ba8ac --- /dev/null +++ b/TC/unit/utc_ApplicationFW_bundle_dup_func.c @@ -0,0 +1,100 @@ +/* + * bundle + * + * Copyright (c) 2000 - 2011 Samsung Electronics Co., Ltd. All rights reserved. + * + * Contact: Jayoun Lee <airjany@samsung.com>, Sewook Park <sewook7.park@samsung.com>, + * Jaeho Lee <jaeho81.lee@samsung.com> + * + * 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 <tet_api.h> +#include "bundle.h" + +static void startup(void); +static void cleanup(void); + +void (*tet_startup)(void) = startup; +void (*tet_cleanup)(void) = cleanup; + +static void utc_ApplicationFW_bundle_dup_func_01(void); +static void utc_ApplicationFW_bundle_dup_func_02(void); + +enum { + POSITIVE_TC_IDX = 0x01, + NEGATIVE_TC_IDX, +}; + +struct tet_testlist tet_testlist[] = { + { utc_ApplicationFW_bundle_dup_func_01, POSITIVE_TC_IDX }, + { utc_ApplicationFW_bundle_dup_func_02, NEGATIVE_TC_IDX }, + { NULL, 0 } +}; + +static void startup(void) +{ +} + +static void cleanup(void) +{ +} + +/** + * @brief Positive test case of bundle_dup() + */ +static void utc_ApplicationFW_bundle_dup_func_01(void) +{ + bundle *b = NULL; + bundle *b_dup = NULL; + + b = bundle_create(); + + bundle_add(b, "aa", "bb"); + b_dup = bundle_dup(b); + + if(0 != strcmp(bundle_get_val(b, "aa"), bundle_get_val(b_dup, "aa"))) { + tet_infoline("bundle_dup() failed in positive test case"); + tet_result(TET_FAIL); + goto cleanup; + } + + tet_result(TET_PASS); + +cleanup: + if(b) bundle_free(b); + if(b_dup) bundle_free(b_dup); + return; +} + +/** + * @brief Negative test case of ug_init bundle_dup() + */ +static void utc_ApplicationFW_bundle_dup_func_02(void) +{ + bundle *b = NULL; + + b = bundle_dup(NULL); + + if(NULL != b) { + tet_infoline("bundle_dup() failed in negative test case"); + tet_result(TET_FAIL); + goto cleanup; + } + + tet_result(TET_PASS); + +cleanup: + if(b) bundle_free(b); + return; +} diff --git a/TC/unit/utc_ApplicationFW_bundle_encode_func.c b/TC/unit/utc_ApplicationFW_bundle_encode_func.c new file mode 100644 index 0000000..026cb0e --- /dev/null +++ b/TC/unit/utc_ApplicationFW_bundle_encode_func.c @@ -0,0 +1,104 @@ +/* + * bundle + * + * Copyright (c) 2000 - 2011 Samsung Electronics Co., Ltd. All rights reserved. + * + * Contact: Jayoun Lee <airjany@samsung.com>, Sewook Park <sewook7.park@samsung.com>, + * Jaeho Lee <jaeho81.lee@samsung.com> + * + * 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 <tet_api.h> +#include <stdlib.h> +#include "bundle.h" + +static void startup(void); +static void cleanup(void); + +void (*tet_startup)(void) = startup; +void (*tet_cleanup)(void) = cleanup; + +static void utc_ApplicationFW_bundle_encode_func_01(void); +static void utc_ApplicationFW_bundle_encode_func_02(void); + +enum { + POSITIVE_TC_IDX = 0x01, + NEGATIVE_TC_IDX, +}; + +struct tet_testlist tet_testlist[] = { + { utc_ApplicationFW_bundle_encode_func_01, POSITIVE_TC_IDX }, + { utc_ApplicationFW_bundle_encode_func_02, NEGATIVE_TC_IDX }, + { NULL, 0 } +}; + +static void startup(void) +{ +} + +static void cleanup(void) +{ +} + +/** + * @brief Positive test case of bundle_encode() + */ +static void utc_ApplicationFW_bundle_encode_func_01(void) +{ + int r, len; + bundle_raw *raw = NULL; + + bundle *b = bundle_create(); + if(!b) { + tet_result(TET_UNINITIATED); + return; + } + if(bundle_add(b, "a", "123")) { + tet_result(TET_UNINITIATED); + goto cleanup; + } + + r = bundle_encode(b, &raw, &len); + if(NULL == raw) { + tet_result(TET_FAIL); + goto cleanup; + } + if(len <= 0) { + tet_result(TET_FAIL); + goto cleanup; + } + + tet_result(TET_PASS); + +cleanup: + if(b) bundle_free(b); + if(raw) free(raw); + return; +} + +/** + * @brief Negative test case of ug_init bundle_encode() + */ +static void utc_ApplicationFW_bundle_encode_func_02(void) +{ + int r = 0; + + r = bundle_encode(NULL, NULL, NULL); + if (!r) { + tet_infoline("bundle_encode() failed in negative test case"); + tet_result(TET_FAIL); + return; + } + tet_result(TET_PASS); +} diff --git a/TC/unit/utc_ApplicationFW_bundle_free_func.c b/TC/unit/utc_ApplicationFW_bundle_free_func.c new file mode 100644 index 0000000..0bd59d7 --- /dev/null +++ b/TC/unit/utc_ApplicationFW_bundle_free_func.c @@ -0,0 +1,87 @@ +/* + * bundle + * + * Copyright (c) 2000 - 2011 Samsung Electronics Co., Ltd. All rights reserved. + * + * Contact: Jayoun Lee <airjany@samsung.com>, Sewook Park <sewook7.park@samsung.com>, + * Jaeho Lee <jaeho81.lee@samsung.com> + * + * 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 <tet_api.h> +#include "bundle.h" + +static void startup(void); +static void cleanup(void); + +void (*tet_startup)(void) = startup; +void (*tet_cleanup)(void) = cleanup; + +static void utc_ApplicationFW_bundle_free_func_01(void); +static void utc_ApplicationFW_bundle_free_func_02(void); + +enum { + POSITIVE_TC_IDX = 0x01, + NEGATIVE_TC_IDX, +}; + +struct tet_testlist tet_testlist[] = { + { utc_ApplicationFW_bundle_free_func_01, POSITIVE_TC_IDX }, + { utc_ApplicationFW_bundle_free_func_02, NEGATIVE_TC_IDX }, + { NULL, 0 } +}; + +static void startup(void) +{ +} + +static void cleanup(void) +{ +} + +/** + * @brief Positive test case of bundle_free() + */ +static void utc_ApplicationFW_bundle_free_func_01(void) +{ + int r; + + bundle *b; + b = bundle_create(); + r = bundle_free(b); + + if (r) { + tet_infoline("bundle_free() failed in positive test case"); + tet_result(TET_FAIL); + return; + } + tet_result(TET_PASS); +} + +/** + * @brief Negative test case of ug_init bundle_free() + */ +static void utc_ApplicationFW_bundle_free_func_02(void) +{ + int r = 0; + + r = bundle_free(NULL); + + if (0 == r) { + tet_infoline("bundle_free() failed in negative test case"); + tet_result(TET_FAIL); + return; + } + tet_result(TET_PASS); +} diff --git a/TC/unit/utc_ApplicationFW_bundle_get_count_func.c b/TC/unit/utc_ApplicationFW_bundle_get_count_func.c new file mode 100644 index 0000000..d7502cc --- /dev/null +++ b/TC/unit/utc_ApplicationFW_bundle_get_count_func.c @@ -0,0 +1,98 @@ +/* + * bundle + * + * Copyright (c) 2000 - 2011 Samsung Electronics Co., Ltd. All rights reserved. + * + * Contact: Jayoun Lee <airjany@samsung.com>, Sewook Park <sewook7.park@samsung.com>, + * Jaeho Lee <jaeho81.lee@samsung.com> + * + * 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 <tet_api.h> +#include "bundle.h" + +static void startup(void); +static void cleanup(void); + +void (*tet_startup)(void) = startup; +void (*tet_cleanup)(void) = cleanup; + +static void utc_ApplicationFW_bundle_get_count_func_01(void); +static void utc_ApplicationFW_bundle_get_count_func_02(void); + +enum { + POSITIVE_TC_IDX = 0x01, + NEGATIVE_TC_IDX, +}; + +struct tet_testlist tet_testlist[] = { + { utc_ApplicationFW_bundle_get_count_func_01, POSITIVE_TC_IDX }, + { utc_ApplicationFW_bundle_get_count_func_02, NEGATIVE_TC_IDX }, + { NULL, 0 } +}; + +static void startup(void) +{ +} + +static void cleanup(void) +{ +} + +/** + * @brief Positive test case of bundle_get_count() + */ +static void utc_ApplicationFW_bundle_get_count_func_01(void) +{ + int r; + bundle *b = bundle_create(); + if(!b) { + tet_result(TET_UNINITIATED); + return; + } + if(bundle_add(b, "a", "123")) { + tet_result(TET_UNINITIATED); + goto cleanup; + } + r = bundle_get_count(b); + if(1 != r) { + tet_infoline("bundle_get_count() failed in positive test case"); + tet_result(TET_FAIL); + goto cleanup; + } + + tet_result(TET_PASS); + +cleanup: + if(b) bundle_free(b); + return; +} + +/** + * @brief Negative test case of ug_init bundle_get_count() + */ +static void utc_ApplicationFW_bundle_get_count_func_02(void) +{ + int r; + r = bundle_get_count(NULL); + if(0 != r) { + tet_infoline("bundle_get_count() failed in negative test case"); + tet_result(TET_FAIL); + goto cleanup; + } + tet_result(TET_PASS); + +cleanup: + return; +} diff --git a/TC/unit/utc_ApplicationFW_bundle_get_val_func.c b/TC/unit/utc_ApplicationFW_bundle_get_val_func.c new file mode 100644 index 0000000..78d9e08 --- /dev/null +++ b/TC/unit/utc_ApplicationFW_bundle_get_val_func.c @@ -0,0 +1,116 @@ +/* + * bundle + * + * Copyright (c) 2000 - 2011 Samsung Electronics Co., Ltd. All rights reserved. + * + * Contact: Jayoun Lee <airjany@samsung.com>, Sewook Park <sewook7.park@samsung.com>, + * Jaeho Lee <jaeho81.lee@samsung.com> + * + * 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 <tet_api.h> +#include "bundle.h" +#include <string.h> + +static void startup(void); +static void cleanup(void); + +void (*tet_startup)(void) = startup; +void (*tet_cleanup)(void) = cleanup; + +static void utc_ApplicationFW_bundle_get_val_func_01(void); +static void utc_ApplicationFW_bundle_get_val_func_02(void); + +enum { + POSITIVE_TC_IDX = 0x01, + NEGATIVE_TC_IDX, +}; + +struct tet_testlist tet_testlist[] = { + { utc_ApplicationFW_bundle_get_val_func_01, POSITIVE_TC_IDX }, + { utc_ApplicationFW_bundle_get_val_func_02, NEGATIVE_TC_IDX }, + { NULL, 0 } +}; + +static void startup(void) +{ +} + +static void cleanup(void) +{ +} + +/** + * @brief Positive test case of bundle_get_val() + */ +static void utc_ApplicationFW_bundle_get_val_func_01(void) +{ + char *ret; + bundle *b = bundle_create(); + if(!b) { + tet_result(TET_UNINITIATED); + return; + } + if(bundle_add(b, "a", "123")) { + tet_result(TET_UNINITIATED); + goto cleanup; + } + ret = bundle_get_val(b, "a"); + if(0 != strcmp("123", ret)) { + tet_infoline("bundle_get_val() failed in positive test case"); + tet_result(TET_FAIL); + goto cleanup; + } + tet_result(TET_PASS); + +cleanup: + if(b) bundle_free(b); + return; +} + +/** + * @brief Negative test case of ug_init bundle_get_val() + */ +static void utc_ApplicationFW_bundle_get_val_func_02(void) +{ + + char *ret; + bundle *b = bundle_create(); + if(!b) { + tet_result(TET_UNINITIATED); + return; + } + if(bundle_add(b, "a", "123")) { + tet_result(TET_UNINITIATED); + goto cleanup; + } + ret = bundle_get_val(NULL, "a"); + if(NULL != ret) { + tet_infoline("bundle_get_val() failed in negative test case"); + tet_result(TET_FAIL); + goto cleanup; + } + ret = bundle_get_val(b, NULL); + if(NULL != ret) { + tet_infoline("bundle_get_val() failed in negative test case"); + tet_result(TET_FAIL); + goto cleanup; + } + + tet_result(TET_PASS); + +cleanup: + if(b) bundle_free(b); + return; +} diff --git a/TC/unit/utc_ApplicationFW_bundle_iterate_func.c b/TC/unit/utc_ApplicationFW_bundle_iterate_func.c new file mode 100644 index 0000000..a773b0d --- /dev/null +++ b/TC/unit/utc_ApplicationFW_bundle_iterate_func.c @@ -0,0 +1,109 @@ +/* + * bundle + * + * Copyright (c) 2000 - 2011 Samsung Electronics Co., Ltd. All rights reserved. + * + * Contact: Jayoun Lee <airjany@samsung.com>, Sewook Park <sewook7.park@samsung.com>, + * Jaeho Lee <jaeho81.lee@samsung.com> + * + * 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 <tet_api.h> +#include "bundle.h" +#include <string.h> + +static void startup(void); +static void cleanup(void); + +void (*tet_startup)(void) = startup; +void (*tet_cleanup)(void) = cleanup; + +static void utc_ApplicationFW_bundle_iterate_func_01(void); +static void utc_ApplicationFW_bundle_iterate_func_02(void); + +enum { + POSITIVE_TC_IDX = 0x01, + NEGATIVE_TC_IDX, +}; + +struct tet_testlist tet_testlist[] = { + { utc_ApplicationFW_bundle_iterate_func_01, POSITIVE_TC_IDX }, + { utc_ApplicationFW_bundle_iterate_func_02, NEGATIVE_TC_IDX }, + { NULL, 0 } +}; + +static void startup(void) +{ +} + +static void cleanup(void) +{ +} + +static char *cb_val = NULL; + +static void +cb_test(const char *k, const char *v, void *data) +{ + cb_val = v; +} + +/** + * @brief Positive test case of bundle_iterate() + */ +static void utc_ApplicationFW_bundle_iterate_func_01(void) +{ + int r = 0; + + bundle *b = bundle_create(); + if(!b) { + tet_result(TET_UNINITIATED); + return; + } + if(bundle_add(b, "a", "123")) { + tet_result(TET_UNINITIATED); + goto cleanup; + } + + bundle_iterate(b, cb_test, NULL); + if (0 != strcmp(bundle_get_val(b, "a"), cb_val)) { + tet_infoline("bundle_iterate() failed in positive test case"); + tet_result(TET_FAIL); + goto cleanup; + } + + tet_result(TET_PASS); + +cleanup: + if(b) bundle_free(b); + return; +} + +/** + * @brief Negative test case of ug_init bundle_iterate() + */ +static void utc_ApplicationFW_bundle_iterate_func_02(void) +{ + int r = 0; + +/* + r = bundle_iterate(...); +*/ + if (r) { + tet_infoline("bundle_iterate() failed in negative test case"); + tet_result(TET_FAIL); + return; + } + tet_result(TET_PASS); +} diff --git a/TC/unit/utc_MODULE_API_func.c.in b/TC/unit/utc_MODULE_API_func.c.in new file mode 100644 index 0000000..383a897 --- /dev/null +++ b/TC/unit/utc_MODULE_API_func.c.in @@ -0,0 +1,65 @@ +#include <tet_api.h> + +static void startup(void); +static void cleanup(void); + +void (*tet_startup)(void) = startup; +void (*tet_cleanup)(void) = cleanup; + +static void utc_@MODULE@_@API@_func_01(void); +static void utc_@MODULE@_@API@_func_02(void); + +enum { + POSITIVE_TC_IDX = 0x01, + NEGATIVE_TC_IDX, +}; + +struct tet_testlist tet_testlist[] = { + { utc_@MODULE@_@API@_func_01, POSITIVE_TC_IDX }, + { utc_@MODULE@_@API@_func_02, NEGATIVE_TC_IDX }, + { NULL, 0 } +}; + +static void startup(void) +{ +} + +static void cleanup(void) +{ +} + +/** + * @brief Positive test case of @API@() + */ +static void utc_@MODULE@_@API@_func_01(void) +{ + int r = 0; + +/* + r = @API@(...); +*/ + if (r) { + tet_infoline("@API@() failed in positive test case"); + tet_result(TET_FAIL); + return; + } + tet_result(TET_PASS); +} + +/** + * @brief Negative test case of ug_init @API@() + */ +static void utc_@MODULE@_@API@_func_02(void) +{ + int r = 0; + +/* + r = @API@(...); +*/ + if (r) { + tet_infoline("@API@() failed in negative test case"); + tet_result(TET_FAIL); + return; + } + tet_result(TET_PASS); +} diff --git a/bundle.manifest b/bundle.manifest new file mode 100644 index 0000000..97e8c31 --- /dev/null +++ b/bundle.manifest @@ -0,0 +1,5 @@ +<manifest> + <request> + <domain name="_"/> + </request> +</manifest> diff --git a/bundle.pc.in b/bundle.pc.in new file mode 100644 index 0000000..aa9cb10 --- /dev/null +++ b/bundle.pc.in @@ -0,0 +1,12 @@ +# Package Information for pkg-config + +prefix=/usr +exec_prefix=${prefix} +libdir=${prefix}/lib +includedir=${prefix}/include + +Name: bundle +Description: Simple string key/val dictionary library +Version: @VERSION@ +Libs: -L${libdir} -lbundle +Cflags: -I${includedir} diff --git a/debian/changelog b/debian/changelog new file mode 100644 index 0000000..40dcfae --- /dev/null +++ b/debian/changelog @@ -0,0 +1,239 @@ +bundle (0.1.22) unstable; urgency=low + + * Checksum added to encode/decode to enhance stability and svace defects fixed. + * Git: 165.213.180.234:slp/pkgs/b/bundle + * Tag: bundle_0.1.22 + + -- Jaeho Lee <jaeho81.lee@samsung.com> Fri, 17 Feb 2012 16:45:12 +0900 + +bundle (0.1.21) unstable; urgency=low + + * Updated changelog + * Git: 165.213.180.234:slp/pkgs/b/bundle + * Tag: bundle_0.1.21 + + -- Sewook Park <sewook7.park@samsung.com> Mon, 05 Dec 2011 15:58:05 +0900 + +bundle (0.1.20) unstable; urgency=low + + * Changed Boilerplate as per the guideline + * Git: 165.213.180.234:slp/pkgs/b/bundle + * Tag: bundle_0.1.20 + + -- Jaeho Lee <jaeho81.lee@samsung.com> Mon, 07 Nov 2011 09:57:20 +0900 + +bundle (0.1.19) unstable; urgency=low + + * Support array + * Git: 165.213.180.234:slp/pkgs/b/bundle + * Tag: bundle_0.1.19 + + -- Jaeho Lee <jaeho81.lee@samsung.com> Thu, 06 Oct 2011 14:53:57 +0900 + +bundle (0.1.18) unstable; urgency=low + + * Modify TC Makefile + * Git: 165.213.180.234:slp/pkgs/b/bundle + * Tag: bundle_0.1.18 + + -- Jaeho Lee <jaeho81.lee@samsung.com> Tue, 16 Aug 2011 14:53:16 +0900 + +bundle (0.1.17) unstable; urgency=low + + * Fix Apply code cleanup + * Git: 165.213.180.234:slp/pkgs/b/bundle + * Tag: bundle_0.1.17 + + -- Sewook Park <sewook7.park@samsung.com> Tue, 02 Aug 2011 19:11:59 +0900 + +bundle (0.1.16) unstable; urgency=low + + * Fix Boilerplate module name + * Git: 165.213.180.234:slp/pkgs/b/bundle + * Tag: bundle_0.1.16 + + -- Sewook Park <sewook7.park@samsung.com> Sat, 16 Jul 2011 13:33:11 +0900 + +bundle (0.1.15) unstable; urgency=low + + * Apply Boilerplate + * Git: 165.213.180.234:slp/pkgs/b/bundle + * Tag: bundle_0.1.15 + + -- Sewook Park <sewook7.park@samsung.com> Wed, 13 Jul 2011 17:36:38 +0900 + +bundle (0.1.14) unstable; urgency=low + + * Rollback to bundle_0.1.12 + * Git: 165.213.180.234:slp/pkgs/b/bundle + * Tag: bundle_0.1.14 + + -- Sewook Park <sewook7.park@samsung.com> Thu, 07 Jul 2011 15:25:40 +0900 + +bundle (0.1.13) unstable; urgency=low + + * Check ENOMEM when adding a value in a bundle + * Git: 165.213.180.234:slp/pkgs/b/bundle + * Tag: bundle_0.1.13 + + -- Youmin Ha <youmin.ha@samsung.com> Thu, 21 Apr 2011 10:52:49 +0900 + +bundle (0.1.12) unstable; urgency=low + + * Add bundle_export_to_argv(), bundle_import_from-argv() + * Git: 165.213.180.234:slp/pkgs/b/bundle + * Tag: bundle_0.1.12 + + -- Youmin Ha <youmin.ha@samsung.com> Mon, 28 Feb 2011 09:33:57 +0900 + +bundle (0.1.11-3) unstable; urgency=low + + * reupload + * Git: 165.213.180.234:slp/pkgs/b/bundle + * Tag: bundle_0.1.11-3 + + -- Youmin Ha <youmin.ha@samsung.com> Wed, 19 Jan 2011 11:13:57 +0900 + +bundle (0.1.11-2) unstable; urgency=low + + * fix git path + * Git: 165.213.180.234:slp/pkgs/b/bundle + * Tag: bundle_0.1.11-2 + + -- Youmin Ha <youmin.ha@samsung.com> Wed, 19 Jan 2011 10:38:28 +0900 + +bundle (0.1.11-1) unstable; urgency=low + + * add {0, NULL} as last item to the tclist + * Git: 165.213.180.234:/git/slp/pkgs/bundle + * Tag: bundle_0.1.11-1 + + -- Youmin Ha <youmin.ha@samsung.com> Wed, 19 Jan 2011 08:36:04 +0900 + +bundle (0.1.11) unstable; urgency=low + + * remove garbages from src pkg + * Git: 165.213.180.234:/git/slp/pkgs/bundle + * Tag: bundle_0.1.11 + + -- Youmin Ha <youmin.ha@samsung.com> Wed, 24 Nov 2010 17:48:57 +0900 + +bundle (0.1.10-1) unstable; urgency=low + + * Add doxygen + * Git: 165.213.180.234:/git/slp/pkgs/bundle + * Tag: bundle_0.1.10-1 + + -- Youmin Ha <youmin.ha@samsung.com> Fri, 05 Nov 2010 14:13:58 +0900 + +bundle (0.1.10) unstable; urgency=low + + * Add doxygen + * Git: 165.213.180.234:/git/slp/pkgs/bundle + * Tag: bundle_0.1.10 + + -- Youmin Ha <youmin.ha@samsung.com> Tue, 02 Nov 2010 16:57:33 +0900 + +bundle (0.1.9) unstable; urgency=low + + * Apply SOVERSION + VERSION automatically + * Git: 165.213.180.234:/git/slp/pkgs/bundle + * Tag: bundle_0.1.9 + + -- Youmin Ha <youmin.ha@samsung.com> Wed, 20 Oct 2010 19:24:28 +0900 + +bundle (0.1.8-3) unstable; urgency=low + + * Fix doxygen + * Git: 165.213.180.234:/git/slp/pkgs/bundle + * Tag: bundle_0.1.8-3 + + -- Youmin Ha <youmin.ha@samsung.com> Mon, 18 Oct 2010 19:58:08 +0900 + +bundle (0.1.8-2) unstable; urgency=low + + * Fix doxygen + * Git: 165.213.180.234:/git/slp/pkgs/bundle + * Tag: bundle_0.1.8-2 + + -- Youmin Ha <youmin.ha@samsung.com> Mon, 18 Oct 2010 11:05:06 +0900 + +bundle (0.1.8-1) unstable; urgency=low + + * Add libglib2.0-dev to build-dep + * Git: 165.213.180.234:/git/slp/pkgs/bundle + * Tag: bundle_0.1.8-1 + + -- Youmin Ha <youmin.ha@samsung.com> Sat, 18 Sep 2010 17:16:52 +0900 + +bundle (0.1.8) unstable; urgency=low + + * Use base64 encoding/decoding with bundle_encode(), bundle_decode() + * Git: 165.213.180.234:/git/slp/pkgs/bundle + * Tag: bundle_0.1.8 + + -- Youmin Ha <youmin.ha@samsung.com> Sat, 18 Sep 2010 16:47:29 +0900 + +bundle (0.1.7) unstable; urgency=low + + * add TC + * Git: 165.213.180.234:/git/slp/pkgs/bundle + * Tag: bundle_0.1.7 + + -- Youmin Ha <youmin.ha@samsung.com> Wed, 08 Sep 2010 17:22:15 +0900 + +bundle (0.1.6) unstable; urgency=low + + * Include PG into dev package + * Git: 165.213.180.234:/git/slp/pkgs/bundle + * Tag: bundle_0.1.6 + + -- Youmin Ha <youmin.ha@samsung.com> Fri, 27 Aug 2010 15:26:31 +0900 + +bundle (0.1.5) unstable; urgency=low + + * add programming guide into doxygen + * Git: 165.213.180.234:/git/slp/pkgs/bundle + * Tag: bundle_0.1.5 + + -- Youmin Ha <youmin.ha@samsung.com> Tue, 24 Aug 2010 19:04:10 +0900 + +bundle (0.1.4) unstable; urgency=low + + * add bundle_dup() function + * Git: 165.213.180.234:/git/slp/pkgs/bundle + * Tag: bundle_0.1.4 + + -- Youmin Ha <youmin.ha@samsung.com> Tue, 27 Jul 2010 14:04:52 +0900 + +bundle (0.1.3) unstable; urgency=low + + * add bundle_del() function, and many tests for wrong uses + * Git: 165.213.180.234:/git/slp/pkgs/bundle + * Tag: bundle_0.1.3 + + -- Youmin Ha <youmin.ha@samsung.com> Fri, 23 Jul 2010 11:21:32 +0900 + +bundle (0.1.2) unstable; urgency=low + + * Create libbundle.so.0 and its symlink libbundle.so + * Git: 165.213.180.234:/git/slp/pkgs/bundle + * Tag: bundle_0.1.2 + + -- Youmin Ha <youmin.ha@samsung.com> Thu, 22 Jul 2010 11:22:13 +0900 + +bundle (0.1.1) unstable; urgency=low + + * Fix CMakeList.txt : add @ONLY option to the command generating pc file + * Git: 165.213.180.234:/git/slp/pkgs/bundle + * Tag: bundle_0.1.1 + + -- Youmin Ha <youmin.ha@samsung.com> Thu, 22 Jul 2010 09:49:54 +0900 + +bundle (0.1.0) unstable; urgency=low + + * Initial release. + * Git: 165.213.180.234:/git/slp/pkgs/bundle + * Tag: bundle_0.1.0 + + -- Youmin Ha <youmin.ha@samsung.com> Wed, 21 Jul 2010 17:04:19 +0900 diff --git a/debian/compat b/debian/compat new file mode 100644 index 0000000..7ed6ff8 --- /dev/null +++ b/debian/compat @@ -0,0 +1 @@ +5 diff --git a/debian/control b/debian/control new file mode 100755 index 0000000..9db2a05 --- /dev/null +++ b/debian/control @@ -0,0 +1,24 @@ +Source: bundle +Section: devel +Priority: extra +Maintainer: Garima <garima.s@samsung.com>, Jayoun Lee <airjany@samsung.com>, Sewook Park <sewook7.park@samsung.com>, Jaeho Lee <jaeho81.lee@samsung.com> +Build-Depends: debhelper (>= 4.0.0), libglib2.0-dev, dlog-dev +Standards-Version: 0.1.0 + +Package: libbundle-0 +Architecture: any +Depends: ${shlibs:Depends}, ${misc:Depends} +Description: Simple string key-val dictionary ADT + +Package: libbundle-dev +Architecture: any +Depends: libbundle-0 (= ${Source-Version}) +Description: Dev package for libbundle-0 +XB-Generate-Docs: yes + +Package: libbundle-dbg +Section: debug +Architecture: any +Depends: ${shlibs:Depends}, ${misc:Depends}, libbundle-0 (= ${Source-Version}) +Description: Debug symbols for libbundle-0 + diff --git a/debian/libbundle-0.install.in b/debian/libbundle-0.install.in new file mode 100644 index 0000000..bf766f0 --- /dev/null +++ b/debian/libbundle-0.install.in @@ -0,0 +1 @@ +@PREFIX@/lib/*.so* diff --git a/debian/libbundle-dev.install.in b/debian/libbundle-dev.install.in new file mode 100644 index 0000000..0f2a4da --- /dev/null +++ b/debian/libbundle-dev.install.in @@ -0,0 +1,2 @@ +@PREFIX@/include/* +@PREFIX@/lib/pkgconfig/*.pc diff --git a/debian/rules b/debian/rules new file mode 100755 index 0000000..a868b66 --- /dev/null +++ b/debian/rules @@ -0,0 +1,126 @@ +#!/usr/bin/make -f +# -*- makefile -*- +# Sample debian/rules that uses debhelper. +# This file was originally written by Joey Hess and Craig Small. +# As a special exception, when this file is copied by dh-make into a +# dh-make output file, you may use that output file without restriction. +# This special exception was added by Craig Small in version 0.37 of dh-make. + +# Uncomment this to turn on verbose mode. +#export DH_VERBOSE=1 + + +# These are used for cross-compiling and for saving the configure script +# from having to guess our platform (since we know it already) +DEB_BUILD_GNU_TYPE ?= $(shell dpkg-architecture -qDEB_BUILD_GNU_TYPE) +DEB_HOST_GNU_TYPE ?= $(shell dpkg-architecture -qDEB_HOST_GNU_TYPE) +DEB_HOST_ARCH ?= $(shell dpkg-architecture -qDEB_HOST_ARCH) +DEB_HOST_ARCH_OS ?= $(shell dpkg-architecture -qDEB_HOST_GNU_OS) + +CFLAGS ?= -Wall -g +LDFLAGS ?= +PREFIX ?= /usr +DATADIR ?= /opt + +ifneq (,$(findstring noopt,$(DEB_BUILD_OPTIONS))) + CFLAGS += -O0 +else + CFLAGS += -O2 +endif + +# architecture is not arm +ifneq (, $(findstring arm, $(DEB_HOST_ARCH))) + # do something here +else + # do something here for arm +endif + +CFLAGS += -fvisibility=hidden -fPIC +LDFLAGS += -Wl,--rpath=$(PREFIX)/lib -Wl,--as-needed + +CMAKE_TMP_DIR = $(CURDIR)/cmake_tmp + +config.status: + +configure: configure-stamp + +configure-stamp: + dh_testdir + mkdir -p $(CMAKE_TMP_DIR); + export LD_LIBRARY_PATH=$(LD_LIBRARY_PATH):$(CMAKE_TMP_DIR) && cd $(CMAKE_TMP_DIR); CFLAGS="$(CFLAGS)" CXXFLAGS="$(CXXFLAGS)" LDFLAGS="$(LDFLAGS)" cmake .. -DCMAKE_INSTALL_PREFIX=$(PREFIX) + touch configure-stamp + +build: build-stamp + +build-stamp: configure-stamp + dh_testdir + # Add here commands to compile the package. + cd $(CMAKE_TMP_DIR) && $(MAKE) all + + for f in `find $(CURDIR)/debian/ -name "*.in"`; do \ + cat $$f > $${f%.in}; \ + sed -i -e "s#@PREFIX@#$(PREFIX)#g" $${f%.in}; \ + sed -i -e "s#@DATADIR@#$(DATADIR)#g" $${f%.in}; \ + done + + touch $@ + +clean: + dh_testdir + dh_testroot + rm -f *-stamp + + rm -rf $(CMAKE_TMP_DIR) + + for f in `find $(CURDIR)/debian/ -name "*.in"`; do \ + rm -f $${f%.in}; \ + done + + dh_clean + +install: build + dh_testdir + dh_testroot + dh_clean -k + dh_installdirs + + # Add here commands to install the package into debian/ncurses. + cd $(CMAKE_TMP_DIR) && $(MAKE) DESTDIR=$(CURDIR)/debian/tmp install + +# Build architecture-independent files here. +binary-indep: build install +# We have nothing to do by default. + +# Build architecture-dependent files here. +binary-arch: build install + dh_testdir + dh_testroot + dh_installchangelogs + dh_installdocs + dh_installexamples + dh_install --list-missing --sourcedir=debian/tmp +# dh_installmenu +# dh_installdebconf +# dh_installlogrotate +# dh_installemacsen +# dh_installpam +# dh_installmime +# dh_python +# dh_installinit +# dh_installcron +# dh_installinfo + dh_installman + dh_link + dh_strip --dbg-package=libbundle-dbg + dh_compress + dh_fixperms +# dh_perl + dh_makeshlibs + dh_installdeb + dh_shlibdeps + dh_gencontrol + dh_md5sums + dh_builddeb + +binary: binary-indep binary-arch +.PHONY: build clean binary-indep binary-arch binary install diff --git a/image/SLP_bundle_PG_image01.png b/image/SLP_bundle_PG_image01.png Binary files differnew file mode 100755 index 0000000..3dd18de --- /dev/null +++ b/image/SLP_bundle_PG_image01.png diff --git a/image/SLP_bundle_PG_images_encode_decode.png b/image/SLP_bundle_PG_images_encode_decode.png Binary files differnew file mode 100644 index 0000000..96cc725 --- /dev/null +++ b/image/SLP_bundle_PG_images_encode_decode.png diff --git a/image/SLP_bundle_PG_images_export_import.png b/image/SLP_bundle_PG_images_export_import.png Binary files differnew file mode 100644 index 0000000..fd7202f --- /dev/null +++ b/image/SLP_bundle_PG_images_export_import.png diff --git a/image/SLP_bundle_PG_images_logical_view.png b/image/SLP_bundle_PG_images_logical_view.png Binary files differnew file mode 100644 index 0000000..b2bbaf7 --- /dev/null +++ b/image/SLP_bundle_PG_images_logical_view.png diff --git a/include/SLP_bundle_PG.h b/include/SLP_bundle_PG.h new file mode 100755 index 0000000..65993de --- /dev/null +++ b/include/SLP_bundle_PG.h @@ -0,0 +1,163 @@ +/* + * bundle + * + * Copyright (c) 2000 - 2011 Samsung Electronics Co., Ltd. All rights reserved. + * + * Contact: Jayoun Lee <airjany@samsung.com>, Sewook Park <sewook7.park@samsung.com>, + * Jaeho Lee <jaeho81.lee@samsung.com> + * + * 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 new file mode 100755 index 0000000..d12cd06 --- /dev/null +++ b/include/bundle.h @@ -0,0 +1,912 @@ +/* + * bundle + * + * Copyright (c) 2000 - 2011 Samsung Electronics Co., Ltd. All rights reserved. + * + * Contact: Jayoun Lee <airjany@samsung.com>, Sewook Park <sewook7.park@samsung.com>, + * Jaeho Lee <jaeho81.lee@samsung.com> + * + * 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 + * @version 0.1 + * @brief This file declares API of bundle library + */ + +/** + * @addtogroup APPLICATION_FRAMEWORK + * @{ + * + * @defgroup bundle + * @version 0.1 + * + * @section Header to use them: + * @code + * #include <bundle.h> + * @endcode + * + * @addtogroup bundle + * @{ + */ + +#include <errno.h> +#include <stddef.h> + +#ifdef __cplusplus +extern "C" { +# endif + +#define API __attribute__((visibility("default"))) +#define likely(x) __builtin_expect(x,1) +#define unlikely(x) __builtin_expect(x,0) + +/** + * bundle is an opaque type pointing a bundle object + */ +typedef struct _bundle_t bundle; + +/** + * bundle_raw is an encoded data type + * @see bundle_encode() + * @see bundle_decode() + */ +typedef unsigned char bundle_raw; + + +/** + * Each bundle keyval have a type. + */ +enum bundle_type_property { + BUNDLE_TYPE_ARRAY = 0x0100, + BUNDLE_TYPE_PRIMITIVE = 0x0200, + BUNDLE_TYPE_MEASURABLE = 0x0400 +}; + +enum bundle_type { + BUNDLE_TYPE_NONE = -1, + BUNDLE_TYPE_ANY = 0, + BUNDLE_TYPE_STR = 1 | BUNDLE_TYPE_MEASURABLE, /* Default */ + BUNDLE_TYPE_STR_ARRAY = BUNDLE_TYPE_STR | BUNDLE_TYPE_ARRAY | BUNDLE_TYPE_MEASURABLE, + BUNDLE_TYPE_BYTE = 2, + BUNDLE_TYPE_BYTE_ARRAY = BUNDLE_TYPE_BYTE | BUNDLE_TYPE_ARRAY +}; + +/** + * A keyval object in a bundle. + * @see bundle_iterator_t + */ +typedef struct keyval_t bundle_keyval_t; + + +/** + * bundle_iterator is a new iterator function type for bundle_foreach() + * @see bundle_foreach() + */ +typedef void (*bundle_iterator_t) ( + const char *key, + const int type, + const bundle_keyval_t *kv, + void *user_data +); + + +/** + * bundle_iterate_cb_t is an iterator function type for bundle_iterate() + * @see bundle_iterate() + * @remark This type is obsolete. Do not use this type any more. + */ +typedef void (*bundle_iterate_cb_t) (const char *key, const char *val, void *data); + + +/** + * @brief Create a bundle object. + * @pre None + * @post None + * @see bundle_free() + * @return bundle object + * @retval NULL on failure creating an object + * @remark When NULL is returned, errno is set to one of the following values; \n + * ENOMEM : No memory to create an object + * + @code + #include <bundle.h> + bundle *b = bundle_create(); // Create new bundle object + bundle_free(b); // free bundle + @endcode + */ +API bundle* bundle_create(void); + +/** + * @brief Free given bundle object with key/values in it + * @pre b must be a valid bundle object. + * @post None + * @see bundle_create() + * @param[in] b bundle object to be freed + * @return Operation result; + * @retval 0 success + * @retval -1 failure + * @remark None + @code + #include <bundle.h> + bundle *b = bundle_create(); // Create new bundle object + bundle_free(b); // free bundle + @endcode + */ +API int bundle_free(bundle *b); +/** + * @brief Add a string array type key-value pair into bundle. + * @pre b must be a valid bundle object. + * @post None + * @see bundle_get_str_array() + * @see bundle_set_str_array_element() + * @param[in] b bundle object + * @param[in] key key + * @param[in] str_array string type value. If NULL, empty array is created. You can change an item with + * @param[in] len Length of array. + * @return Operation result + * @retval 0 success + * @retval -1 failure + * + * @remark When -1 is returned, errno is set to one of the following values; \n + EKEYREJECTED : key is rejected (NULL or sth) \n + EPERM : key is already exist, not permitted to overwrite value \n + EINVAL : b or val is not valid (NULL or sth) \n + @code + #include <bundle.h> + char *sa = { "aaa", "bbb", "ccc" }; // A string array of length 3 + bundle *b = bundle_create(); + bundle_add_str_array(b, "foo", sa, 3); // add a key-val pair + bundle_free(b); + @endcode + */ +API int bundle_add_str_array(bundle *b, const char *key, const char **str_array, const int len); +/** + * @brief Add a string type key-value pair into bundle. + * @pre b must be a valid bundle object. + * @post None + * @see bundle_add_str() + * @param[in] b bundle object + * @param[in] key key + * @param[in] val value + * @return Operation result + * @retval 0 success + * @retval -1 failure + * + * @remark When -1 is returned, errno is set to one of the following values; \n + EKEYREJECTED : key is rejected (NULL or sth) \n + EPERM : key is already exist, not permitted to overwrite value \n + EINVAL : b or val is not valid (NULL or sth) \n + @code + #include <bundle.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 + */ +API int bundle_add(bundle *b, const char *key, const char *val); + +/** + * @brief Delete val with given key + * @pre b must be a valid bundle object. + * @post None + * @see None + * @param[in] b bundle object + * @param[in] key given key + * @return Operation result + * @retval 0 Success + * @retval -1 Failure + * + * @remark When -1 is returned, errno is set to one of the following values; \n + EINVAL : b is invalid (NULL or sth) \n + ENOKEY : No key exist \n + EKEYREJECTED : key is invalid (NULL or sth) \n + @code + #include <bundle.h> + bundle *b = bundle_create(); // Create new bundle object + bundle_add(b, "foo_key", "bar_val"); // add a key-val pair + bundle_del(b, "foo_key"); // del "foo_key" from b + + bundle_free(b); + @endcode + */ +API int bundle_del(bundle *b, const char* key); +/** + * @brief Get string array value from key + * @pre b must be a valid bundle object. + * @post None + * @see bundle_add_str_array() + * @see bundle_set_str_array_element() + * @param[in] b bundle object + * @param[in] key key + * @param[out] len array length + * @return Pointer to array of string + * @retval NULL If key is not found, returns NULL. + * @remark DO NOT free or modify returned string! + When NULL is returned, errno is set to one of the following values; \n + EINVAL : b is invalid \n + ENOKEY : No key exists \n + EKEYREJECTED : invalid key (NULL or sth) \n + @code + #include <bundle.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 + */ + +API const char** bundle_get_str_array(bundle *b, const char *key,int *len); +/** + * @brief Get value from key + * @pre b must be a valid bundle object. + * @post None + * @see bundle_get_str() + * @param[in] b bundle object + * @param[in] key key + * @return Pointer for value string + * @retval NULL If key is not found, returns NULL. + * @remark DO NOT free or modify returned string! + When NULL is returned, errno is set to one of the following values; \n + EINVAL : b is invalid \n + ENOKEY : No key exists \n + EKEYREJECTED : invalid key (NULL or sth) \n + @code + #include <bundle.h> + bundle *b = bundle_create(); // Create new bundle object + bundle_add(b, "foo_key", "bar_val"); // 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 + */ +API const char* bundle_get_val(bundle *b, const char *key); + +/** + * @brief Get the number of bundle items + * @pre b must be a valid bundle object. + * @post None + * @see None + * @param[in] b bundle object + * @return Number of bundle items + * @remark None + @code + #include <bundle.h> + bundle *b = bundle_create(); // Create new bundle object + bundle_add(b, "key1", "val1"); // add a key-val pair + int count = bundle_get_count(b); // count=1 + bundle_add(b, "key2", "val2"); // add another key-val pair + count = bundle_get_count(b); // count=2 + + bundle_free(b); + @endcode + */ +API int bundle_get_count(bundle *b); + + +/** + * @brief Get a type of a value with certain key + * @pre b must be a valid bundle object + * @post None + * @see bundle_type_t + * @param[in] b A bundle + * @param[in] key A key in bundle + * @return Type of a key in b + * @remark + @code + @endcode + */ +API int bundle_get_type(bundle *b, const char *key); + + +/** + * @brief Duplicate given bundle object + * @pre b must be a valid bundle object. + * @post None + * @see None + * @param[in] b_from bundle object to be duplicated + * @return New bundle object + * @retval NULL Failure + * @remark None + @code + #include <bundle.h> + bundle *b = bundle_create(); // Create new bundle object + bundle_add(b, "foo_key", "bar_val"); // add a key-val pair + bundle *b_dup = bundle_dup(b); // duplicate b + + bundle_free(b); + bundle_free(b_dup); + @endcode + */ +API bundle * bundle_dup(bundle *b_from); + +/** + * @brief iterate callback function with each key/val pairs in bundle. (NOTE: Only BUNDLE_TYPE_STR type values come!) + * @pre b must be a valid bundle object. + * @post None + * @see None + * @param[in] b bundle object + * @param[in] callback iteration callback function + * @param[in] data data for callback function + * @remark This function is obsolete, and does not give values whose types are not BUNDLE_TYPE_STR. + @code + @include <stdio.h> + #include <bundle.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(b, "k1", "v1"); // add a key-val pair + bundle_add(b, "k2", "v2"); // add a key-val pair + bundle_add(b, "k3", "v3"); // add a key-val pair + bundle_iterate(b, sample_cb, NULL); // iterate sample_cb for each key/val + return 0; + } + @endcode + */ +API void bundle_iterate(bundle *b, bundle_iterate_cb_t callback, void *cb_data); + + +/** + * @brief iterate callback function with each key/val pairs in bundle. (Supports all types of value) + * @pre b must be a valid bundle object. + * @post None + * @see bundle_keyval_get_type bundle_keyval_type_is_array bundle_keyval_get_basic_val bundle_keyval_get_array_val + * @param[in] b bundle object + * @param[in] iter iteration callback function + * @param[in] user_data data for callback function + * @remark This function supports all types. + @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, &size); + // Do something... + } + } + + int main(void) { + bundle *b = bundle_create(); // Create new bundle object + bundle_add_str(b, "k1", "v1"); // add a key-val pair + bundle_add_byte(b, "k2", "v2", 3); // add a key-val pair + char *s_arr[] = {"abc", "bcd", "cde"}; + bundle_add_str_array(b, "k3", s_arr, 3); // add a key-val pair + bundle_iterate(b, sample_cb, NULL); // iterate sample_cb for each key/val + return 0; + } + @endcode + */ +API void bundle_foreach(bundle *b, bundle_iterator_t iter, void *user_data); + + +/** + * @brief Get type for a bundle_keyval_t object. + * @pre kv must be a valid bundle_keyval_t object. + * @post None + * @see bundle_foreach + * @param[in] kv A bundle_keyval_t object + * @return Type of kv + * @retval -1 Operation failure. errno is set. + * @remark + */ +API int bundle_keyval_get_type(bundle_keyval_t *kv); + + +/** + * @brief Determine if kv is array type or not. + * @pre kv must be a valid bundle_keyval_t object. + * @post None + * @see bundle_foreach + * @param[in] kv A bundle_keyval_t object + * @return Operation result + * @retval 1 kv is an array. + * @retval 0 kv is not an array. + * @remark + */ +API int bundle_keyval_type_is_array(bundle_keyval_t *kv); + + +/** + * @brief Get value and size of the value from kv of basic type. + * @pre kv must be a valid bundle_keyval_t object. + * @post val, size are set. + * @see bundle_foreach + * @param[in] kv A bundle_keyval_t object + * @param[out] val Value + * @param[out] size Size of val + * @return Operation result + * @retval 0 Success + * @remark Do not free val. + */ +API int bundle_keyval_get_basic_val(bundle_keyval_t *kv, void **val, size_t *size); + + +/** + * @brief Get value array, length of array, and size of each array item + * @pre kv must be a valid bundle_keyval_t object. + * @post array_val, array_len, array_item_size are set. + * @see bundle_foreach + * @param[in] kv A bundle_keyval_t object + * @param[out] array_val Array pointer of values + * @param[out] array_len Length of array_val + * @param[out] array_element_size Array of size of each array element + * @return Operation result + * @retval 0 Success + * @retval 0 Failure + * @remark + */ +API int bundle_keyval_get_array_val(bundle_keyval_t *kv, void ***array_val, unsigned int *array_len, size_t **array_element_size); + + +/** + * @brief Encode bundle to bundle_raw format (uses base64 format) + * @pre b must be a valid bundle object. + * @post None + * @see None + * @param[in] b bundle object + * @param[out] r returned bundle_raw data(byte data) + * r MUST BE FREED by free(r). + * @param[out] len size of r (in bytes) + * @return size of raw data + * @retval 0 Success + * @retval -1 Failure + * @remark None + @code + #include <bundle.h> + bundle *b = bundle_create(); // Create new bundle object + bundle_add(b, "foo_key", "bar_val"); // add a key-val pair + bundle_raw *r; + int len; + bundle_encode(b, &r, &len); // encode b + + bundle_free_encoded_rawdata(r); + bundle_free(b); + @endcode + */ +API int bundle_encode(bundle *b, bundle_raw **r, int *len); + +/** + * @brief Free encoded rawdata from memory + * @pre r is a valid rawdata generated by bundle_encode(). + * @post None + * @see bundle_encode + * @param[in] r is a rawdata + * @return Operation result + * @retval 0 Success + * @retval -1 Failure + * @reamark None + */ +API int bundle_free_encoded_rawdata(bundle_raw **r); + +/** + * @brief deserialize bundle_raw, and get bundle object + * @pre b must be a valid bundle object. + * @post None + * @see None + * @param[in] r bundle_raw data to be converted to bundle object + * @param[in] len size of r + * @return bundle object + * @retval NULL Failure + * @remark None + @code + #include <bundle.h> + bundle *b = bundle_create(); // Create new bundle object + bundle_add(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(encoded_b, len); // decoded bundle object + + bundle_free(b); + free(encoded_b); + bundle_free(b_dup); + @endcode + */ +API bundle * bundle_decode(const bundle_raw *r, const int len); + + +/** + * @brief Export bundle to argv + * @pre b is a valid bundle object. + * @post argv is a pointer of newly allocated memory. It must be freed. + * Each item of argv points the string in the bundle object b. If b is freed, argv will have garbage pointers. DO NOT FREE b BEFORE ACCESSING argv!! + * @see bundle_import_from_argv + * @param[in] b bundle object + * @param[out] argv Pointer of string array. + * This array has NULL values for first and last item. + * First NULL is for argv[0], and last NULL is a terminator for execv(). + * @return Number of item in argv. This value is equal to actual count of argv - 1. (Last NULL terminator is not counted.) + * @retval -1 Function failure. Check errno to get the reason. + * @remark None + @code + #include <bundle.h> + bundle *b = bundle_create(); // Create new bundle object + bundle_add(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 + */ +API int bundle_export_to_argv(bundle *b, char ***argv); + +/** + * @brief Free exported argv + * @pre argv is a valid string array generated from bundle_export_to_argv(). + * @post None + * @see bundle_export_to_argv + * @param[in] argc number of args, which is the return value of bundle_export_to_argv(). + * @param[in] argv array from bundle_export_to_argv(). + * @return Operation result. + * @retval 0 on success + * @retval -1 on failure + * @remark You must not use this API when you use global 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_export_argv(argc, argv); + argv = NULL; + + bundle_free(b); + @endcode + */ +API int bundle_free_exported_argv(int argc, char ***argv); + +/** + * @brief import a bundle from argv + * @pre argv is a valid string array, which is created by bundle_export_to_argv(). + * @post Returned bundle b must be freed. + * @see bundle_export_to_argv + * @param[in] argc argument count + * @param[in] argv argument vector + * @return New bundle object + * @retval NULL Function failure + * @remark None + @code + #include <bundle.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 + */ +API bundle * bundle_import_from_argv(int argc, char **argv); + +#if 0 +/** + * @brief Add a string type key-value pair into bundle. + * @pre b must be a valid bundle object. + * @post None + * @see bundle_get_str() + * @param[in] b bundle object + * @param[in] key key + * @param[in] str string type value + * @return Operation result + * @retval 0 success + * @retval -1 failure + * + * @remark When -1 is returned, errno is set to one of the following values; \n + EKEYREJECTED : key is rejected (NULL or sth) \n + EPERM : key is already exist, not permitted to overwrite value \n + EINVAL : b or val is not valid (NULL or sth) \n + @code + #include <bundle.h> + bundle *b = bundle_create(); // Create new bundle object + bundle_add_str(b, "foo", "bar"); // add a key-val pair + + bundle_free(b); + @endcode + */ +API int bundle_add_str(bundle *b, const char *key, const char *str); + +/** + * @brief Set a value of string array element + * @pre b must be a valid bundle object. + * @post None + * @see bundle_add_str_array() + * @see bundle_get_str_array() + * @param[in] b bundle object + * @param[in] key key + * @param[in] idx index of array element to be changed + * @param[in] val string type value. If NULL, empty array is created. You can change an item with + * @return Operation result + * @retval 0 success + * @retval -1 failure + * + * @remark When -1 is returned, errno is set to one of the following values; \n + EKEYREJECTED : key is rejected (NULL or sth) \n + EPERM : key is already exist, not permitted to overwrite value \n + EINVAL : b or val is not valid (NULL or sth) \n + @code + #include <bundle.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 + */ +API int bundle_set_str_array_element(bundle *b, const char *key, const unsigned int idx, const char *val); + +/** + * @brief Add a byte type key-value pair into bundle. + * @pre b must be a valid bundle object. + * @post None + * @see bundle_get_byte() + * @param[in] b bundle object + * @param[in] key key + * @param[in] byte string type value + * @param[in] size size of byte + * @return Operation result + * @retval 0 success + * @retval -1 failure + * + * @remark When -1 is returned, errno is set to one of the following values; \n + EKEYREJECTED : key is rejected (NULL or sth) \n + EPERM : key is already exist, not permitted to overwrite value \n + EINVAL : b or val is not valid (NULL or sth) \n + @code + #include <bundle.h> + bundle *b = bundle_create(); // Create new bundle object + bundle_add_byte(b, "foo", "bar\0", 4); // add a key-val pair + + bundle_free(b); + @endcode + */ + +API int bundle_add_byte(bundle *b, const char *key, const void *byte, const size_t size); + +/** + * @brief Add a byte array type key-value pair into bundle. + * @pre b must be a valid bundle object. + * @post None + * @see bundle_get_str_array() + * @see bundle_set_byte_array_element() + * @param[in] b bundle object + * @param[in] key key + * @param[in] byte_array Not used. + * @param[in] len Length of array to be created + * @return Operation result + * @retval 0 success + * @retval -1 failure + * + * @remark When -1 is returned, errno is set to one of the following values; \n + EKEYREJECTED : key is rejected (NULL or sth) \n + EPERM : key is already exist, not permitted to overwrite value \n + EINVAL : b or val is not valid (NULL or sth) \n + @code + #include <bundle.h> + bundle *b = bundle_create(); + bundle_add_byte_array(b, "foo", NULL, 3); // add a byte-array with length 3 + + bundle_set_byte_array_element(b, "foo", 0, "aaa\0", 4); array[0] = "aaa\0" + bundle_set_byte_array_element(b, "foo", 1, "bbb\0", 4); array[1] = "bbb\0" + bundle_set_byte_array_element(b, "foo", 2, "ccc\0", 4); array[2] = "ccc\0" + + bundle_free(b); + @endcode + */ +API int bundle_add_byte_array(bundle *b, const char *key, void **byte_array, const unsigned int len); + +/** + * @brief Set a value of byte array element + * @pre b must be a valid bundle object. + * @post None + * @see bundle_add_str_array() + * @see bundle_get_str_array() + * @param[in] b bundle object + * @param[in] key key + * @param[in] idx index of array element to be changed + * @param[in] val string type value. If NULL, empty array is created. You can change an item with + * @param[in] size Size of value in byte + * @return Operation result + * @retval 0 success + * @retval -1 failure + * + * @remark When -1 is returned, errno is set to one of the following values; \n + EKEYREJECTED : key is rejected (NULL or sth) \n + EPERM : key is already exist, not permitted to overwrite value \n + EINVAL : b or val is not valid (NULL or sth) \n + @code + #include <bundle.h> + bundle *b = bundle_create(); + bundle_add_byte_array(b, "foo", NULL, 3); // add a key-val pair + bundle_set_byte_array_element(b, "foo", 0, "aaa\0", 4); + bundle_set_byte_array_element(b, "foo", 1, "bbb\0", 4); + bundle_set_byte_array_element(b, "foo", 2, "ccc\0", 4); + + unsigned char **byte_array = NULL; + int len_byte_array = 0; + + byte_array=bundle_get_str_array(b, "foo", &len_byte_array); + // byte_array = { "aaa\0", "bbb\0", "ccc\0" }, and len_byte_array = 3 + + bundle_free(b); + @endcode + */ +API int bundle_set_byte_array_element(bundle *b, const char *key, const unsigned int idx, const void *val, const size_t size); + +/** + * @brief Get string value from key + * @pre b must be a valid bundle object. + * @post None + * @see bundle_add_str() + * @param[in] b bundle object + * @param[in] key key + * @param[out] str returned value + * @return Operation result + * @retval 0 on success + * @retval -1 on failure + * @remark Do not free str! + When -1 is returned, errno is set to one of the following values; \n + EINVAL : b is invalid \n + ENOKEY : No key exists \n + EKEYREJECTED : invalid key (NULL or sth) \n + @code + #include <bundle.h> + bundle *b = bundle_create(); // Create new bundle object + bundle_add_str(b, "foo_key", "bar_val"); // add a key-val 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 + */ +API int bundle_get_str(bundle *b, const char *key, char **str); + +/** + * @brief Get byte value from key + * @pre b must be a valid bundle object. + * @post None + * @see bundle_add_byte() + * @param[in] b bundle object + * @param[in] key key + * @param[out] byte returned value + * @param[out] size Size of byte + * @return Operation result + * @retval 0 on success + * @retval -1 on failure + * @remark Do not free str! + When -1 is returned, errno is set to one of the following values; \n + EINVAL : b is invalid \n + ENOKEY : No key exists \n + EKEYREJECTED : invalid key (NULL or sth) \n + @code + #include <bundle.h> + bundle *b = bundle_create(); // Create new bundle object + bundle_add_byte(b, "foo", "bar\0", 4); // add a key-val pair + + unsigned char *v = NULL; + bundle_get_str(b, "foo", &v); // v = "bar\0" + + bundle_free(b); // After freeing b, v becomes a dangling pointer. + @endcode + */ +API int bundle_get_byte(bundle *b, const char *key, void **byte, size_t *size); + +/** + * @brief Get byte array value from key + * @pre b must be a valid bundle object. + * @post None + * @see bundle_add_str_array() + * @see bundle_set_str_array_element() + * @param[in] b bundle object + * @param[in] key key + * @param[out] byte_array returned value + * @param[out] len array length + * @param[out] array_element_size an array of sizes of each byte_array element + * @return Operation result + * @retval 0 on success + * @retval -1 on failure + * @remark Do not free str! + When -1 is returned, errno is set to one of the following values; \n + EINVAL : b is invalid \n + ENOKEY : No key exists \n + EKEYREJECTED : invalid key (NULL or sth) \n + @code + #include <bundle.h> + bundle *b = bundle_create(); + bundle_add_byte_array(b, "foo", NULL, 3); + bundle_set_byte_array_element(b, "foo", 0, "aaa\0", 4); + bundle_set_byte_array_element(b, "foo", 1, "bbb\0", 4); + bundle_set_byte_array_element(b, "foo", 2, "ccc\0", 4); + + char **byte_array = NULL; + int len_byte_array = 0; + size_t *size_byte_array = NULL; + + byte_array = bundle_get_str_array(b, "foo", &len_byte_array, &size_byte_array); + // byte_array = { "aaa\0", "bbb\0", "ccc\0" }, len_byte_array = 3, and size_byte_array = { 4, 4, 4 } + + bundle_free(b); + @endcode + */ +API int bundle_get_byte_array(bundle *b, const char *key, void ***byte_array, unsigned int *len, unsigned int **array_element_size); +#endif + + +#ifdef __cplusplus +} +#endif + +/** + * @} + * @} + */ + +#endif /* __BUNDLE_H__ */ diff --git a/include/bundle_log.h b/include/bundle_log.h new file mode 100755 index 0000000..192c283 --- /dev/null +++ b/include/bundle_log.h @@ -0,0 +1,42 @@ +/* + * bundle + * + * Copyright (c) 2000 - 2011 Samsung Electronics Co., Ltd. All rights reserved. + * + * Contact: Jayoun Lee <airjany@samsung.com>, Sewook Park <sewook7.park@samsung.com>, + * Jaeho Lee <jaeho81.lee@samsung.com> + * + * 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 <dlog/dlog.h> +#ifdef LOG_TAG +#undef LOG_TAG +#endif + +#define LOG_TAG "BUNDLE" + +#ifdef _DEBUG_MODE_ +#define BUNDLE_LOG_PRINT(FMT, ARG...) do { printf("%5d", getpid()); printf + ("%s() : "FMT"\n", __FUNCTION__, ##ARG); } while (false) +#define BUNDLE_EXCEPTION_PRINT(FMT, ARG...) do { printf("%5d", getpid()); + printf("%s() : "FMT"\n", __FUNCTION__, ##ARG); } while (false) +#define BUNDLE_ASSERT_PRINT(FMT, ARG...) do { printf("%5d", getpid()); printf + ("%s() : "FMT"\n", __FUNCTION__, ##ARG); } while (false) +#else +#define BUNDLE_LOG_PRINT(FMT, ARG...) SLOGD(FMT, ##ARG); +#define BUNDLE_EXCEPTION_PRINT(FMT, ARG...) SLOGW(FMT, ##ARG); +#define BUNDLE_ASSERT_PRINT(FMT, ARG...) SLOGE(FMT, ##ARG); +#endif diff --git a/include/keyval.h b/include/keyval.h new file mode 100755 index 0000000..ce1e7f8 --- /dev/null +++ b/include/keyval.h @@ -0,0 +1,80 @@ +/* + * bundle + * + * Copyright (c) 2000 - 2011 Samsung Electronics Co., Ltd. All rights reserved. + * + * Contact: Jayoun Lee <airjany@samsung.com>, Sewook Park <sewook7.park@samsung.com>, + * Jaeho Lee <jaeho81.lee@samsung.com> + * + * 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 __KEYVAL_H__ +#define __KEYVAL_H__ + +/** + * keyval.h + * + * keyval object + */ + +#include <stddef.h> + +// ADT: object +typedef struct keyval_t keyval_t; + +// Object methods +typedef struct keyval_method_collection_t keyval_method_collection_t; + +typedef void (*keyval_method_free_t)(keyval_t *kv, int do_free_object); +typedef int (*keyval_method_compare_t) (keyval_t *kv1, keyval_t *kv2); +typedef size_t (*keyval_method_get_encoded_size_t)(keyval_t *kv); +typedef size_t (*keyval_method_encode_t)(keyval_t *, unsigned char **byte, size_t *byte_len); +typedef size_t (*keyval_method_decode_t)(unsigned char *byte, keyval_t **kv); + + +struct keyval_method_collection_t +{ + keyval_method_free_t free; + keyval_method_compare_t compare; + keyval_method_get_encoded_size_t get_encoded_size; + keyval_method_encode_t encode; + keyval_method_decode_t decode; +}; + +struct keyval_t +{ + int type; + char *key; // To be freed. + void *val; // To be freed. + size_t size; // Size of a single value. + struct keyval_t *next; + + keyval_method_collection_t *method; + +}; + + +keyval_t * keyval_new(keyval_t *kv, const char *key, const int type, const void *val, const size_t size); +void keyval_free(keyval_t *kv, int do_free_object); +int keyval_compare(keyval_t *kv1, keyval_t *kv2); +size_t keyval_get_encoded_size(keyval_t *kv); +size_t keyval_encode(keyval_t *kv, unsigned char **byte, size_t *byte_len); +size_t keyval_decode(unsigned char *byte, keyval_t **kv); +int keyval_get_data(keyval_t *kv, int *type, void **val, size_t *size); +int keyval_get_type_from_encoded_byte(unsigned char *byte); + +#endif /* __KEYVAL_H__ */ + diff --git a/include/keyval_array.h b/include/keyval_array.h new file mode 100755 index 0000000..afdf52c --- /dev/null +++ b/include/keyval_array.h @@ -0,0 +1,52 @@ +/* + * bundle + * + * Copyright (c) 2000 - 2011 Samsung Electronics Co., Ltd. All rights reserved. + * + * Contact: Jayoun Lee <airjany@samsung.com>, Sewook Park <sewook7.park@samsung.com>, + * Jaeho Lee <jaeho81.lee@samsung.com> + * + * 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. + * + */ + + +/** + * keyval_array.h + * + * keyval_array object + */ + +#include "keyval.h" + + +typedef struct keyval_array_t +{ + struct keyval_t kv; // Inherits keyval_t + + unsigned int len; // length of array_val + size_t *array_element_size; // Array of size of each element + void **array_val; // Array + +} keyval_array_t; + + +keyval_array_t *keyval_array_new(keyval_array_t *kva, const char *key, const int type, const void **array_val, const unsigned int len); +void keyval_array_free(keyval_array_t *kva, int do_free_object); +int keyval_array_compare(keyval_array_t *kva1, keyval_array_t *kva2); +size_t keyval_array_get_encoded_size(keyval_array_t *kva); +size_t keyval_array_encode(keyval_array_t *kva, void **byte, size_t *byte_len); +size_t keyval_array_decode(void *byte, keyval_array_t **kva); +int keyval_array_copy_array(keyval_array_t *kva, void **array_val, unsigned int array_len, size_t (*measure_val_len)(void * val)); +int keyval_array_get_data(keyval_array_t *kva, int *type,void ***array_val, unsigned int *len, size_t **array_element_size); +int keyval_array_set_element(keyval_array_t *kva, int idx, void *val, size_t size); diff --git a/include/keyval_type.h b/include/keyval_type.h new file mode 100755 index 0000000..9561c5a --- /dev/null +++ b/include/keyval_type.h @@ -0,0 +1,50 @@ +/* + * bundle + * + * Copyright (c) 2000 - 2011 Samsung Electronics Co., Ltd. All rights reserved. + * + * Contact: Jayoun Lee <airjany@samsung.com>, Sewook Park <sewook7.park@samsung.com>, + * Jaeho Lee <jaeho81.lee@samsung.com> + * + * 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 __KEYVAL_TYPE_H__ +#define __KEYVAL_TYPE_H__ + +/** + * keyval_type.h + * + * Definitions & short funcs for keyval type + */ + +#include "bundle.h" +#include <stddef.h> +#include <string.h> + +// measure_size function type +typedef size_t (*keyval_type_measure_size_func_t) (void *val); + +void _type_init_measure_size_func(void); +int keyval_type_is_array(int type); +int keyval_type_is_measurable(int type); +keyval_type_measure_size_func_t keyval_type_get_measure_size_func(int type); + + +/* Measure functions for each type */ +size_t keyval_type_measure_size_str(void *val); +void keyval_type_init(void); + +#endif /* __KEYVAL_TYPE_H__ */ diff --git a/packaging/bundle.spec b/packaging/bundle.spec new file mode 100644 index 0000000..d4a91fe --- /dev/null +++ b/packaging/bundle.spec @@ -0,0 +1,67 @@ + +Name: bundle +Summary: String key-val dictionary ADT +Version: 0.1.27 +Release: 1 +Group: System/Libraries +License: Apache License, Version 2.0 +Source0: bundle-%{version}.tar.gz +Requires(post): /sbin/ldconfig +Requires(postun): /sbin/ldconfig +BuildRequires: cmake +BuildRequires: pkgconfig(glib-2.0) +BuildRequires: pkgconfig(dlog) + + +%description +Simple string key-val dictionary ADT + + + +%package devel +Summary: String key-val dictionary ADT (devel) +Group: Development/Libraries +Requires: %{name} = %{version}-%{release} + +%description devel +Simple string key-val dictionary ADT (devel) + + +%prep +%setup -q -n %{name}-%{version} + + +%build +cmake . -DCMAKE_INSTALL_PREFIX=%{_prefix} + + +make %{?jobs:-j%jobs} + +%install +rm -rf %{buildroot} +%make_install + + + + +%post -p /sbin/ldconfig + +%postun -p /sbin/ldconfig + + + + + +%files +%manifest bundle.manifest +%defattr(-,root,root,-) +%{_libdir}/libbundle.so.* + + +%files devel +%defattr(-,root,root,-) +%{_includedir}/bundle.h +%{_includedir}/SLP_bundle_PG.h +%{_libdir}/pkgconfig/bundle.pc +%{_libdir}/libbundle.so + diff --git a/src/bundle.c b/src/bundle.c new file mode 100755 index 0000000..ce45976 --- /dev/null +++ b/src/bundle.c @@ -0,0 +1,819 @@ +/* + * bundle + * + * Copyright (c) 2000 - 2011 Samsung Electronics Co., Ltd. All rights reserved. + * + * Contact: Jayoun Lee <airjany@samsung.com>, Sewook Park <sewook7.park@samsung.com>, + * Jaeho Lee <jaeho81.lee@samsung.com> + * + * 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. + * + */ + + + +/** + * bundle.c + */ + +#include "bundle.h" +#include "keyval.h" +#include "keyval_array.h" +#include "keyval_type.h" +#include "bundle_log.h" +#include <glib.h> + +#include <stdlib.h> /* calloc, free */ +#include <string.h> /* strdup */ +#include <errno.h> + +#define CHECKSUM_LENGTH 32 +#define TAG_IMPORT_EXPORT_CHECK "`zaybxcwdveuftgsh`" +/* ADT */ +struct _bundle_t +{ + keyval_t *kv_head; +}; + + +/** + * Find a kv from bundle + */ +static keyval_t * +_bundle_find_kv(bundle *b, const char *key) +{ + keyval_t *kv; + + if(NULL == b) { errno = EINVAL; return NULL; } + if(NULL == key) { errno = EKEYREJECTED; return NULL; } + + kv = b->kv_head; + while (kv != NULL) { + if(0 == strcmp(key, kv->key)) return kv; + kv = kv->next; + } + /* Not found */ + errno = ENOKEY; + return NULL; +} + +/** + * Append kv into bundle + */ +static int +_bundle_append_kv(bundle *b, keyval_t *new_kv) +{ + keyval_t *kv; + + if (NULL == b->kv_head) b->kv_head = new_kv; + else { + kv = b->kv_head; + while (NULL != kv->next) kv = kv->next; + kv->next = new_kv; + } + return 0; +} + +static int +_bundle_add_kv(bundle *b, const char *key, const void *val, const size_t size, const int type, const unsigned int len) +{ + /* basic value check */ + if(NULL == b) { errno = EINVAL; return -1; } + if(NULL == key) { errno = EKEYREJECTED; return -1; } + if(0 == strlen(key)) { errno = EKEYREJECTED; return -1; } + + keyval_t *kv = _bundle_find_kv(b, key); + if(kv) { /* Key already exists */ + errno = EPERM; + return -1; + } + errno = 0; + + keyval_t *new_kv = NULL; + if(keyval_type_is_array(type)) { + // array type + keyval_array_t *kva = keyval_array_new(NULL, key, type, (const void **) val, len); + new_kv = (keyval_t *)kva; + } + else { + // normal type + new_kv = keyval_new(NULL, key, type, val, size); + } + if(!new_kv) { + // NOTE: errno is already set. (ENOMEM, ...) + return -1; + } + + _bundle_append_kv(b, new_kv); + + return 0; + +} + +static int +_bundle_get_val(bundle *b, const char *key, const int type, void **val, size_t *size, unsigned int *len, size_t **array_element_size) +{ + keyval_t *kv = _bundle_find_kv(b, key); + if(!kv) { /* Key doesn't exist */ + /* NOTE: errno is already set. */ + return -1; + } + if(BUNDLE_TYPE_ANY != type && type != kv->type) { + errno = ENOTSUP; + return -1; + } + + if(keyval_type_is_array(type)) { + keyval_array_t *kva = (keyval_array_t *)kv; + keyval_array_get_data(kva, NULL, (void ***)val, len, array_element_size); + } + else { + keyval_get_data(kv, NULL, val, size); + } + + return 0; +} + +/** global initialization + * Run only once. + */ +static void +_bundle_global_init(void) +{ + static int _is_done = 0; + if(_is_done) return; + + // Run init functions + keyval_type_init(); + + _is_done = 1; + return; +} + + +/* APIs */ +bundle * +bundle_create(void) +{ + bundle *b = NULL; + + _bundle_global_init(); + + b = calloc(1, sizeof(bundle)); /* fill mem with NULL */ + if(NULL == b) { + BUNDLE_EXCEPTION_PRINT("Unable to allocate memory for bundle\n"); + errno = ENOMEM; + goto EXCEPTION; + } + + return b; + +EXCEPTION: + return NULL; +} + +int +bundle_free(bundle *b) +{ + keyval_t *kv, *tmp_kv; + + if(NULL == b) { + BUNDLE_EXCEPTION_PRINT("Bundle is already freed\n"); + errno = EINVAL; + return -1; + } + + /* Free keyval list */ + kv = b->kv_head; + while(kv != NULL) { + tmp_kv = kv; + kv = kv->next; + tmp_kv->method->free(tmp_kv, 1); + } + + /* free bundle */ + free(b); + + return 0; +} +// str type +int +bundle_add_str(bundle *b, const char *key, const char *str) +{ + if(!str) { errno = EINVAL; return -1; } + return _bundle_add_kv(b, key, str, strlen(str)+1, BUNDLE_TYPE_STR, 1); +} + +int +bundle_get_str(bundle *b, const char *key, char **str) +{ + return _bundle_get_val(b, key, BUNDLE_TYPE_STR, (void **) str, NULL, NULL, NULL); +} + +int +bundle_add(bundle *b, const char *key, const char *val) +{ + return bundle_add_str(b, key, val); +} + +int +bundle_del(bundle *b, const char *key) +{ + keyval_t *kv = NULL, *prev_kv = NULL; + + /* basic value check */ + if(NULL == b) { errno = EINVAL; return -1; } + if(NULL == key) { errno = EKEYREJECTED; return -1; } + if(0 == strlen(key)) { errno = EKEYREJECTED; return -1; } + + kv = b->kv_head; + while (kv != NULL) { + if(0 == strcmp(key, kv->key)) break; + prev_kv = kv; + kv = kv->next; + } + if (NULL == kv) { errno = ENOKEY; return -1; } + else { + if(NULL != prev_kv) { + prev_kv->next = kv->next; + } + if(kv == b->kv_head) b->kv_head = kv->next; + kv->method->free(kv, 1); + } + return 0; + +} + +const char * +bundle_get_val(bundle *b, const char *key) +{ + char *val = NULL; + int r = 0; + + r = bundle_get_str(b, key, &val); + return val; + +} + +/** + * @brief used by bundle_get_count() API, to count number of items in a bundle + */ +static void +_bundle_get_count_iter(const char *k, const int type, const bundle_keyval_t *kv, void *user_data) +{ + int *count = (int *)user_data; + *count += 1; +} + +int +bundle_get_count (bundle *b) +{ + int count = 0; + if (NULL == b) return count; + bundle_foreach(b, _bundle_get_count_iter, &count); + return count; +} + +void +bundle_iterate(bundle *b, bundle_iterate_cb_t callback, void *data) +{ + keyval_t *kv = b->kv_head; + if(callback) { + while(NULL != kv) { + callback(kv->key, kv->val, data); + kv = kv->next; + } + } +} + +void +bundle_foreach(bundle *b, bundle_iterator_t iter, void *user_data) +{ + if(NULL==b) + { + return; /*TC_FIX if b=NULL- error handling */ + } + keyval_t *kv = b->kv_head; + if(iter) { + while(NULL != kv) { + iter(kv->key, kv->type, kv, user_data); + kv = kv->next; + } + } +} + +/* keyval functions */ +int +bundle_keyval_get_type(bundle_keyval_t *kv) +{ + return kv->type; +} + +int +bundle_keyval_type_is_array(bundle_keyval_t *kv) +{ + return keyval_type_is_array(kv->type); +} + +int +bundle_keyval_get_basic_val(bundle_keyval_t *kv, void **val, size_t *size) +{ + return keyval_get_data(kv, NULL, val, size); +} + +int +bundle_keyval_get_array_val(bundle_keyval_t *kv, void ***array_val, unsigned int *array_len, size_t **array_item_size) +{ + return keyval_array_get_data((keyval_array_t *)kv, NULL, array_val, array_len, array_item_size); +} + + +/*static void +_iter_do_bundle_dup(const char *key, const void *val, const int type, const size_t size, const unsigned int len, void *user_data) +{ + //int r; + bundle *b_to = (bundle *)user_data; + + _bundle_add_kv(b_to, key, val, size, type, len); + +} +*/ +bundle * +bundle_dup(bundle *b_from) +{ + bundle *b_to = NULL; + int i; + + if(NULL == b_from) { errno = EINVAL; return NULL; } + b_to = bundle_create(); + if(NULL == b_to) return NULL; + + keyval_t *kv_from = b_from->kv_head; + keyval_t *kv_to = NULL; + while(kv_from != NULL) { + if(keyval_type_is_array(kv_from->type)) { + keyval_array_t *kva_from = (keyval_array_t *)kv_from; + kv_to = (keyval_t *) keyval_array_new(NULL, kv_from->key, kv_from->type, NULL, kva_from->len); + if(!kv_to) goto ERR_CLEANUP; + for(i=0; i < kva_from->len; i++) { + if(((keyval_array_t *)kv_from)->array_val[i]) { + keyval_array_set_element((keyval_array_t*)kv_to, i, ((keyval_array_t *)kv_from)->array_val[i], ((keyval_array_t *)kv_from)->array_element_size[i]); + } + } + _bundle_append_kv(b_to, kv_to); + } + else { + if(_bundle_add_kv(b_to, kv_from->key, kv_from->val, kv_from->size, kv_from->type, 0)) goto ERR_CLEANUP; + } + + kv_from = kv_from->next; + } + return b_to; + +ERR_CLEANUP: + bundle_free(b_to); + return NULL; +} + + +int +bundle_encode(bundle *b, bundle_raw **r, int *len) +{ + keyval_t *kv; + unsigned char *m; + unsigned char *p_m; + unsigned char *byte; + size_t byte_len; + gchar *chksum_val; + + if(NULL == b) { + errno = EINVAL; + return -1; + } + + /* calculate memory size */ + size_t msize = 0; // Sum of required size + + kv = b->kv_head; + while(kv != NULL) { + msize += kv->method->get_encoded_size(kv); + kv = kv->next; + } + m = calloc(msize+CHECKSUM_LENGTH, sizeof(unsigned char)); + if(unlikely(NULL == m )) { errno = ENOMEM; return -1; } + + p_m = m+CHECKSUM_LENGTH; /* temporary pointer */ + + kv = b->kv_head; + while(kv != NULL) { + byte = NULL; + byte_len = 0; + + kv->method->encode(kv, &byte, &byte_len); + memcpy(p_m, byte, byte_len); + + p_m += byte_len; + kv = kv->next; + + free(byte); + } + + /*compute checksum from the data*/ + chksum_val = g_compute_checksum_for_string(G_CHECKSUM_MD5,m+CHECKSUM_LENGTH,msize); + /*prefix checksum to the data */ + memcpy(m,chksum_val,CHECKSUM_LENGTH); + if ( NULL != r ) { + /*base64 encode for whole string checksum and data*/ + *r =(unsigned char*)g_base64_encode(m,msize+CHECKSUM_LENGTH); + if ( NULL != len ) *len = strlen((char*)*r); + } + free(m); + g_free(chksum_val);/*free checksum string */ + + return 0; +} + +int +bundle_free_encoded_rawdata(bundle_raw **r) +{ + if(!*r) return -1; /*TC_FIX - double free sigabrt handling */ + + free(*r); + *r=NULL; + return 0; +} + +bundle * +bundle_decode(const bundle_raw *r, const int data_size) +{ + bundle *b; + bundle_raw *p_r; + unsigned char *d_str; + unsigned int d_len_raw; + unsigned char *d_r; + unsigned int d_len; + char *extract_cksum; + gchar* compute_cksum; + + if(NULL == r) { + errno = EINVAL; + return NULL; + } + + extract_cksum = calloc(CHECKSUM_LENGTH+1, sizeof(char)); + if(unlikely(NULL== extract_cksum)) + { + errno = ENOMEM; + return NULL; + } + + /* base 64 decode of input string*/ + d_str = g_base64_decode((char*)r, &d_len_raw); + /*extract checksum from the received string */ + strncpy(extract_cksum,d_str,CHECKSUM_LENGTH); + /* compute checksum for the data */ + compute_cksum = g_compute_checksum_for_string(G_CHECKSUM_MD5,d_str+CHECKSUM_LENGTH,d_len_raw-CHECKSUM_LENGTH); + /*compare checksum values- extracted from the received string and computed from the data */ + if(strcmp(extract_cksum,compute_cksum)!=0) + { + free(extract_cksum); + g_free(compute_cksum); + return NULL; + } + d_r = d_str+CHECKSUM_LENGTH; + d_len= d_len_raw-CHECKSUM_LENGTH; + + /* re-construct bundle */ + b = bundle_create(); + + p_r = (bundle_raw *)d_r; + + size_t bytes_read; + keyval_t *kv; + + while(p_r < d_r + d_len - 1) { + kv = NULL; // To get a new kv + + // Find type, and use decode function according to type + int type = keyval_get_type_from_encoded_byte(p_r); + + if(keyval_type_is_array(type)) { + bytes_read = keyval_array_decode(p_r, (keyval_array_t **) &kv); + } + else { + bytes_read = keyval_decode(p_r, &kv); + } + + if(kv) _bundle_append_kv(b, kv); + else { break; } + p_r += bytes_read; + } + + free(extract_cksum); + g_free(compute_cksum); + free(d_str); + + return b; +} + +struct _argv_idx { + int argc; + char **argv; + int idx; +}; + + +void +_iter_export_to_argv(const char *key, const int type, const keyval_t *kv, void *user_data) +{ + struct _argv_idx *vi = (struct _argv_idx *)user_data; + + vi->argv[vi->idx] = (char *)key; + + unsigned char *byte = NULL, *encoded_byte = NULL; + size_t byte_len = 0; + + if(0 == kv->method->encode((struct keyval_t *)kv, &byte, &byte_len)) { + // TODO: encode FAILED! + BUNDLE_EXCEPTION_PRINT("bundle: FAILED to encode keyval: %s\n", key); + return; + } + // bas64 encode + + encoded_byte =(unsigned char *) g_base64_encode(byte, byte_len); + if(NULL == encoded_byte) { + BUNDLE_EXCEPTION_PRINT("bundle: failed to encode byte\n"); + return; + } + + vi->argv[vi->idx + 1] =(char*)encoded_byte; + (vi->idx) += 2; + + free(byte); +} + +int +bundle_export_to_argv(bundle *b, char ***argv) +{ + int argc, item_count; + + item_count = bundle_get_count(b); + argc = 2 * item_count + 2; /* 2 more count for argv[0] and arv[1] = encoded */ + *argv = calloc(argc + 1, sizeof(char *)); + if(!*argv) return -1; + + struct _argv_idx vi; + vi.argc = argc; + vi.argv = *argv; + vi.idx = 2; /* start from index 2*/ + vi.argv[1]=TAG_IMPORT_EXPORT_CHECK; /* set argv[1] as encoded*/ + /*BUNDLE_LOG_PRINT("\nargument 1 is %s",vi.argv[1]);*/ + + bundle_foreach(b, _iter_export_to_argv, &vi); + + return argc; +} + +int bundle_free_exported_argv(int argc, char ***argv) +{ + if(!*argv) return -1; /*TC_FIX : fix for double free- sigabrt */ + + int i; + for(i=1; i < argc; i+=2) { + free((*argv)[i+1]); + } + + free(*argv); + *argv= NULL; + return 0; +} + + bundle * +bundle_import_from_argv(int argc, char **argv) +{ + if(!argv) return NULL; /* TC_FIX error handling for argv =NULL*/ + + bundle *b = bundle_create(); + if(!b) return NULL; + + + /* + int i; + for(i=0; i<argc; i++) { + BUNDLE_LOG_PRINT("[bundle-dbg] argv[%d]='%s'\n", i, argv[i]); + } + */ + + if(!argv[1]||strcmp(argv[1],TAG_IMPORT_EXPORT_CHECK)) + { + /*BUNDLE_LOG_PRINT("\nit is not encoded");*/ + int idx; + for (idx = 1; idx < argc; idx = idx + 2) { /*start idx from one as argv[1] is user given argument*/ + bundle_add(b, argv[idx], argv[idx + 1]); + } + return b; + } + /*BUNDLE_LOG_PRINT("\nit is encoded");*/ + int idx, type; + keyval_t *kv = NULL; + keyval_array_t *kva = NULL; + unsigned char *byte = NULL; + char *encoded_byte; + unsigned int byte_size; + for(idx = 2; idx < argc; idx = idx+2) { // start idx from 2 as argv[1] is encoded + kv = NULL; + kva = NULL; + + encoded_byte = argv[idx+1]; + + // base64_decode + byte = g_base64_decode(encoded_byte, &byte_size); + if(NULL == byte) { + if(b) bundle_free(b); + return NULL; + } + + type = keyval_get_type_from_encoded_byte(byte); + if(keyval_type_is_array(type)) { + if(0 == keyval_array_decode(byte, &kva)) { + // TODO: error! + BUNDLE_EXCEPTION_PRINT("Unable to Decode array\n"); + } + kv = (keyval_t *)kva; + } + else { + if(0 == keyval_decode(byte, &kv)) { + // TODO: error! + BUNDLE_EXCEPTION_PRINT("Unable to Decode\n"); + } + } + _bundle_append_kv(b, kv); + + free(byte); + byte = NULL; + } + return b; +} + + + int +bundle_get_type(bundle *b, const char *key) +{ + keyval_t *kv = _bundle_find_kv(b, key); + if(kv) return kv->type; + else { + errno = ENOKEY; + return BUNDLE_TYPE_NONE; + } +} + +// array functions +/** Get length of an array + */ + unsigned int +bundle_get_array_len(bundle *b, const char *key) +{ + return 0; +} + +/** Get size of an item in byte, of given pointer + */ + size_t +bundle_get_array_val_size(bundle *b, const char *key, const void *val_ptr) +{ + return 0; +} +/*static int + bundle_set_array_val(bundle *b, const char *key, const int type, const unsigned int idx, const void *val, const size_t size) + { +//void **array = NULL; + +keyval_t *kv = _bundle_find_kv(b, key); +if(NULL == kv) return -1; + +if(type != kv->type) { +errno = EINVAL; +return -1; +} + +if(! keyval_type_is_array(kv->type)) { // TODO: Is this needed? +errno = EINVAL; +return -1; +} + +keyval_array_t *kva = (keyval_array_t *)kv; + +if(! keyval_array_is_idx_valid(kva, idx)) { +errno = EINVAL; +return -1; +} + +if(!kva->array_val) { // NULL value test (TODO: is this needed?) +errno = ENOMEM; +return -1; +} + +return keyval_array_set_element(kva, idx, val, size); +}*/ + + + int +bundle_add_str_array(bundle *b, const char *key, const char **str_array, const int len) +{ + return _bundle_add_kv(b, key, str_array, 0, BUNDLE_TYPE_STR_ARRAY, len); +} + + + int +bundle_get_val_array(bundle *b, const char *key, char ***str_array, int *len) +{ + return _bundle_get_val(b, key, BUNDLE_TYPE_STR_ARRAY, (void **) str_array, NULL,(unsigned int *)len, NULL); +} + +const char ** bundle_get_str_array(bundle *b, const char *key,int *len) +{ + const char **arr_val = NULL; + int r = 0; + + r = bundle_get_val_array(b,key,(char***)&arr_val,len); + return arr_val; + +} + + + int +bundle_compare(bundle *b1, bundle *b2) +{ + if(!b1 || !b2) return -1; + + keyval_t *kv1, *kv2; + //keyval_array_t *kva1, *kva2; + //char *key; + + if(bundle_get_count(b1) != bundle_get_count(b2)) return 1; + for(kv1 = b1->kv_head; kv1 != NULL; kv1 = kv1->next) { + kv2 = _bundle_find_kv(b2, kv1->key); + if(!kv2) return 1; + if(kv1->method->compare(kv1, kv2)) return 1; + } + return 0; +} + + + +#if 0 + int +bundle_set_str_array_element(bundle *b, const char *key, const unsigned int idx, const char *val) +{ + if(!val) { + errno = EINVAL; + return -1; + } + return bundle_set_array_val(b, key, BUNDLE_TYPE_STR_ARRAY, idx, val, strlen(val)+1); +} + + +// byte type + int +bundle_add_byte(bundle *b, const char *key, const void *byte, const size_t size) +{ + return _bundle_add_kv(b, key, byte, size, BUNDLE_TYPE_BYTE, 1); +} + + int +bundle_get_byte(bundle *b, const char *key, void **byte, size_t *size) +{ + return _bundle_get_val(b, key, BUNDLE_TYPE_BYTE, (void **) byte, size, NULL, NULL); +} + + int +bundle_add_byte_array(bundle *b, const char *key, void **byte_array, const unsigned int len) +{ + return _bundle_add_kv(b, key, byte_array, 0, BUNDLE_TYPE_BYTE_ARRAY, len); +} + + int +bundle_get_byte_array(bundle *b, const char *key, void ***byte_array, unsigned int *len, unsigned int **array_element_size) +{ + return _bundle_get_val(b, key, BUNDLE_TYPE_BYTE_ARRAY, (void **)byte_array, NULL, len, array_element_size); +} + + + int +bundle_set_byte_array_element(bundle *b, const char *key, const unsigned int idx, const void *val, const size_t size) +{ + return bundle_set_array_val(b, key, BUNDLE_TYPE_BYTE_ARRAY, idx, val, size); +} + +#endif + diff --git a/src/keyval.c b/src/keyval.c new file mode 100755 index 0000000..5397f90 --- /dev/null +++ b/src/keyval.c @@ -0,0 +1,248 @@ +/* + * bundle + * + * Copyright (c) 2000 - 2011 Samsung Electronics Co., Ltd. All rights reserved. + * + * Contact: Jayoun Lee <airjany@samsung.com>, Sewook Park <sewook7.park@samsung.com>, + * Jaeho Lee <jaeho81.lee@samsung.com> + * + * 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. + * + */ + + +/** + * keyval.c + * Implementation of keyval object + */ + +#include "keyval_type.h" +#include "keyval.h" +#include "bundle_log.h" +#include <stdlib.h> +#include <errno.h> +extern int errno; + +static keyval_method_collection_t method = { + keyval_free, + keyval_compare, + keyval_get_encoded_size, + keyval_encode, + keyval_decode +}; + +keyval_t * +keyval_new(keyval_t *kv, const char *key, const int type, const void *val, const size_t size) +{ + int must_free_obj; + must_free_obj = kv ? 0 : 1; + + if(!kv) { + kv = calloc(1, sizeof(keyval_t)); + if(!kv) { + //errno = ENOMEM; // set by calloc + return NULL; + } + } + + // key + if(kv->key) { + keyval_free(kv, must_free_obj); + return NULL; + } + kv->key = strdup(key); + if(!kv->key) { + //errno = ENOMEM; // set by strdup + keyval_free(kv, must_free_obj); + return NULL; + } + + // elementa of primitive types + kv->type = type; + kv->size = size; + + if(size) { + kv->val = calloc(1, size); // allocate memory unconditionally ! + if(!kv->val) { + errno = ENOMEM; + keyval_free(kv, 1); + return NULL; + } + if(val) { + memcpy(kv->val, val, size); + } + } + + // Set methods + kv->method = &method; + + return kv; +} + +void +keyval_free(keyval_t *kv, int do_free_object) +{ + //int i; + + if(NULL == kv) return; + + if(kv->key) { + free(kv->key); + kv->key = NULL; + } + + if(NULL != kv->val) { + free(kv->val); + kv->val = NULL; + } + + if(do_free_object) free(kv); + + return; +} + +int +keyval_get_data(keyval_t *kv, int *type, void **val, size_t *size) +{ + if(!kv) return -EINVAL; + if(keyval_type_is_array(kv->type)) return -EINVAL; + + if(type) *type = kv->type; + if(val) *val = kv->val; + if(size) *size = kv->size; + + return 0; +} + +int +keyval_compare(keyval_t *kv1, keyval_t *kv2) +{ + if(!kv1 || !kv2) return -1; + + if(0 != strcmp(kv1->key, kv2->key)) return 1; + if(kv1->type != kv2->type) return 1; + if(kv1->size != kv2->size) return 1; + + if(kv1->val == NULL && kv2->val == NULL) return 0; + if(kv1->val == NULL || kv2->val == NULL) return 1; + if(0 != memcmp(kv1->val, kv2->val, kv1->size)) return 1; + + return 0; +} + +size_t +keyval_get_encoded_size(keyval_t *kv) +{ + if(!kv) return 0; + + size_t encoded_size + = sizeof(size_t) // total size + + sizeof(int) // type + + sizeof(size_t) // key size + + strlen(kv->key) + 1 // key (+ null byte) + + sizeof(size_t) // size + + kv->size; // val + + return encoded_size; +} + +/** + * encode a keyval to byte + * + * @pre kv must be valid. + * @post byte must be freed. + * @param[in] kv + * @param[out] byte + * @param[out] byte_len + * @return byte_len + */ +size_t +keyval_encode(keyval_t *kv, unsigned char **byte, size_t *byte_len) +{ + /* + * type + * key size + * key + * val size + * val + */ + + static const size_t sz_type = sizeof(int); + static const size_t sz_keysize = sizeof(size_t); + size_t sz_key = strlen(kv->key) + 1; + static const size_t sz_size = sizeof(size_t); + size_t sz_val = kv->size; + + *byte_len = keyval_get_encoded_size(kv); + + *byte = calloc(1, *byte_len); + if(!*byte) return 0; + + unsigned char *p = *byte; + + memcpy(p, byte_len, sizeof(size_t)); p += sizeof(size_t); + memcpy(p, &(kv->type), sz_type); p += sz_type; + memcpy(p, &sz_key, sz_keysize); p += sz_keysize; + memcpy(p, kv->key, sz_key); p += sz_key; + memcpy(p, &(kv->size), sz_size); p += sz_size; + memcpy(p, kv->val, sz_val); p += sz_val; + + return *byte_len; +} + +/** + * decode a byte stream to a keyval + * + * @param[in] byte byte stream. + * @param[in|out] kv keyval. + * If kv is NULL, new keyval_t object comes. + * If kv is not NULL, given kv is used. (No new kv is created.) + * @return Number of bytes read from byte. + */ +size_t +keyval_decode(unsigned char *byte, keyval_t **kv) +{ + static const size_t sz_byte_len = sizeof(size_t); + static const size_t sz_type = sizeof(int); + static const size_t sz_keysize = sizeof(size_t); + static const size_t sz_size = sizeof(size_t); + + unsigned char *p = byte; + + size_t byte_len = *((size_t *)p); p += sz_byte_len; + int type = *((int *)p); p += sz_type; + size_t keysize = *((size_t *)p); p += sz_keysize; + char *key = (char *)p; p += keysize; + size_t size = *((size_t *)p); p += sz_size; + void *val = (void *)p; p += size; + + if(kv) *kv = keyval_new(*kv, key, type, val, size); // If *kv != NULL, use given kv + + return byte_len; +} + + +int +keyval_get_type_from_encoded_byte(unsigned char *byte) +{ + // skip total size (== sizeof(size_t)) + static const size_t sz_byte_len = sizeof(size_t); + + unsigned char *p=byte; + p += sz_byte_len; + int type = *((int *)p); + return type; + + //return (int )*(byte + sizeof(size_t)); +} + diff --git a/src/keyval_array.c b/src/keyval_array.c new file mode 100755 index 0000000..af2aa12 --- /dev/null +++ b/src/keyval_array.c @@ -0,0 +1,337 @@ +/* + * bundle + * + * Copyright (c) 2000 - 2011 Samsung Electronics Co., Ltd. All rights reserved. + * + * Contact: Jayoun Lee <airjany@samsung.com>, Sewook Park <sewook7.park@samsung.com>, + * Jaeho Lee <jaeho81.lee@samsung.com> + * + * 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. + * + */ + + +/** + * keyval_array.c + * Implementation of keyval_array object + */ + +#include "keyval_array.h" +#include "keyval.h" +#include "keyval_type.h" +#include "bundle.h" +#include "bundle_log.h" + +#include <stdlib.h> +#include <string.h> +#include <errno.h> + + +static keyval_method_collection_t method = { + (keyval_method_free_t) keyval_array_free, + (keyval_method_compare_t) keyval_array_compare, + (keyval_method_get_encoded_size_t) keyval_array_get_encoded_size, + (keyval_method_encode_t) keyval_array_encode, + (keyval_method_decode_t) keyval_array_decode +}; + +keyval_array_t * +keyval_array_new(keyval_array_t *kva, const char *key, const int type, const void **array_val, const unsigned int len) +{ + int must_free_obj; + must_free_obj = kva ? 0 : 1; + + if(!kva) { + kva = calloc(1, sizeof(keyval_array_t)); + if(unlikely(NULL==kva)) { + errno = ENOMEM; + return NULL; + } + } + + // keyval setting + keyval_t *kv = keyval_new((keyval_t *)kva, key, type, NULL, 0); + if(unlikely(NULL==kv)) + { + errno = ENOMEM; + return NULL; + } + + kv->type = kv->type | BUNDLE_TYPE_ARRAY; + + kva->len = len; + + // Set array value, if exist + if(kva->array_val) { + errno=EINVAL; + if(must_free_obj) keyval_array_free(kva, 1); + return NULL; + } + kva->array_val = calloc(len, sizeof(void *)); + if(!(kva->array_val)) { + errno = ENOMEM; + keyval_array_free(kva, 1); + return NULL; + } + // array_element_size + kva->array_element_size = calloc(len, sizeof(size_t)); + if(!(kva->array_element_size)) { + errno = ENOMEM; + keyval_array_free(kva, 1); + return NULL; + } + // If avaliable, copy array val + if(array_val + && keyval_type_is_measurable(type) + && keyval_type_get_measure_size_func(type)) { + // array_val have original data array. copy it! + + if(keyval_array_copy_array((keyval_array_t*)kv, + (void**)array_val, + len, + keyval_type_get_measure_size_func(type)) + ) { + keyval_array_free(kva, 1); + return NULL; + } + } + + // Set methods + kv->method = &method; + + return kva; +} + +void +keyval_array_free(keyval_array_t *kva, int do_free_object) +{ + if(!kva) return; + + // free keyval_array elements + free(kva->array_element_size); + int i; + for(i=0; i<kva->len; i++) { + if(kva->array_val[i]) free(kva->array_val[i]); + } + free(kva->array_val); + + // free parent + keyval_free((keyval_t *)kva, 0); + + // free object + if(do_free_object) free(kva); +} + +int +keyval_array_compare(keyval_array_t *kva1, keyval_array_t *kva2) +{ + keyval_t *kv1, *kv2; + if(!kva1 || !kva2) return -1; + + kv1 = (keyval_t *)kva1; + kv2 = (keyval_t *)kva2; + + if(0 != strcmp(kv1->key, kv2->key)) return 1; + if(kv1->type != kv2->type) return 1; + if(kva1->len != kva2->len) return 1; + int i; + for(i=0; i<kva1->len; i++) { + if(kva1->array_val[i] == NULL && kva2->array_val[i] == NULL) continue; + if(kva1->array_val[i] == NULL || kva2->array_val[i] == NULL) return 1; + if(0 != memcmp(kva1->array_val[i], kva2->array_val[i], kva1->array_element_size[i])) return 1; + } + + return 0; +} + +int +keyval_array_copy_array(keyval_array_t *kva, void **array_val, unsigned int array_len, size_t (*measure_val_len)(void * val)) +{ + keyval_t *kv = (keyval_t *)kva; + + // Get measure_size function of the value type + keyval_type_measure_size_func_t measure_size = keyval_type_get_measure_size_func(kv->type); + if(!measure_size) return -1; + + // Copy each array item + int i; + for(i=0; i < array_len; i++) { + kva->array_val[i] = malloc(measure_size(array_val[i])); + if(!(kva->array_val[i])) { + errno = ENOMEM; + goto cleanup_exit; + } + memcpy(kva->array_val[i], array_val[i], measure_size(array_val[i])); + kva->array_element_size[i] = measure_size(array_val[i]); + } + return 0; + +cleanup_exit: + for(i=0; i<array_len; i++) { + if(kva->array_val[i]) { + free(kva->array_val[i]); + kva->array_val[i] = NULL; + } + } + return -1; +} + +int +keyval_array_is_idx_valid(keyval_array_t *kva, int idx) +{ + //keyval_t *kv = (keyval_t *)kva; + if(kva && kva->len > idx && 0 <= idx) return 1; + return 0; +} + +int +keyval_array_set_element(keyval_array_t *kva, int idx, void *val, size_t size) +{ + if(kva->array_val[idx]) { // An element is already exist in the idx! + if(!val) { // val==NULL means 'Free this element!' + free(kva->array_val[idx]); + kva->array_val[idx] = NULL; + kva->array_element_size[idx] = 0; + } + else { + // Error case! + errno = EINVAL; + return -1; + } + } + else { + // Normal case. Copy value into the array. + kva->array_val[idx] = malloc(size); + if(!(kva->array_val[idx])) { + errno = ENOMEM; + return -1; + } + if(val) { + memcpy(kva->array_val[idx], val, size); // val + kva->array_element_size[idx] = size; // size + } + } + + return 0; +} + +int +keyval_array_get_data(keyval_array_t *kva, int *type, + void ***array_val, unsigned int *len, size_t **array_element_size) +{ + if(!kva) return -EINVAL; + keyval_t *kv = (keyval_t *)kva; + if(!keyval_type_is_array(kv->type)) return -EINVAL; + + // Return values + if(type) *type = kv->type; + if(array_val) *array_val = kva->array_val; + if(len) *len = kva->len; + if(array_element_size) *array_element_size = kva->array_element_size; + + return 0; +} + +size_t +keyval_array_get_encoded_size(keyval_array_t *kva) +{ + size_t sum_array_element_size = 0; + int i; + for(i=0; i < kva->len; i++) { + sum_array_element_size += kva->array_element_size[i]; + } + size_t encoded_size + = sizeof(size_t) // total size + + sizeof(int) // type + + sizeof(size_t) // keysize + + strlen(((keyval_t *)kva)->key) + 1 // key (+ null byte) + + sizeof(int) // len + + kva->len * sizeof(size_t) // array_element_size + + sum_array_element_size; + + return encoded_size; +} + +size_t +keyval_array_encode(keyval_array_t *kva, void **byte, size_t *byte_len) +{ + keyval_t *kv = (keyval_t *)kva; + int i; + + // Calculate memory size for kva + static const size_t sz_type = sizeof(int); + static const size_t sz_keysize = sizeof(size_t); + size_t sz_key = strlen(kv->key) + 1; + static const unsigned int sz_len = sizeof(int); + size_t sz_array_element_size = kva->len * sizeof(size_t); + size_t sz_array_val = 0; + for(i=0; i < kva->len; i++) { + sz_array_val += kva->array_element_size[i]; + } + + // Allocate memory + *byte_len = keyval_array_get_encoded_size(kva); + *byte = calloc(1, *byte_len); + if(!*byte) return 0; + + // Copy data + unsigned char *p = *byte; + + memcpy(p, byte_len, sizeof(size_t)); p += sizeof(size_t); + memcpy(p, &(kv->type), sz_type); p += sz_type; + memcpy(p, &sz_key, sz_keysize); p += sz_keysize; + memcpy(p, kv->key, sz_key); p += sz_key; + memcpy(p, &(kva->len), sz_len); p += sz_len; + memcpy(p, kva->array_element_size, sz_array_element_size); p += sz_array_element_size; + for(i=0; i < kva->len; i++) { + memcpy(p, kva->array_val[i], kva->array_element_size[i]); + p += kva->array_element_size[i]; + } + + return *byte_len; +} + +size_t +keyval_array_decode(void *byte, keyval_array_t **kva) +{ + static const size_t sz_byte_len = sizeof(size_t); + static const size_t sz_type = sizeof(int); + static const size_t sz_keysize = sizeof(size_t); + static const int sz_len = sizeof(unsigned int); + + unsigned char *p = byte; + + // Get data + size_t byte_len = *((size_t *)p); p += sz_byte_len; + int type = *((int *)p); p += sz_type; + size_t keysize = *((size_t *)p); p += sz_keysize; + char *key = (char *)p; p += keysize; + unsigned int len = *((unsigned int *)p); p += sz_len; + size_t *array_element_size = (size_t *) p; p += sizeof(size_t) * len; + void *array_val = (void *)p; + + *kva = keyval_array_new(NULL, key, type, NULL, len); + int i; + size_t elem_size = 0; + for(i=0; i < len; i++) { + elem_size += i ? array_element_size[i-1] : 0; + if(keyval_array_set_element(*kva, i, (void *)(array_val+elem_size), array_element_size[i])) { + keyval_array_free(*kva, 1); + *kva = NULL; + return 0; + } + } + + return byte_len; +} + diff --git a/src/keyval_type.c b/src/keyval_type.c new file mode 100755 index 0000000..38db370 --- /dev/null +++ b/src/keyval_type.c @@ -0,0 +1,74 @@ +/* + * bundle + * + * Copyright (c) 2000 - 2011 Samsung Electronics Co., Ltd. All rights reserved. + * + * Contact: Jayoun Lee <airjany@samsung.com>, Sewook Park <sewook7.park@samsung.com>, + * Jaeho Lee <jaeho81.lee@samsung.com> + * + * 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 "keyval_type.h" +#include "bundle_log.h" +#include <stddef.h> + +void +keyval_type_init(void) +{ + static int is_done; + is_done = 0; + if(is_done) return; + + // Still do nothing + + is_done = 1; +} + +int +keyval_type_is_array(int type) +{ + if(type & BUNDLE_TYPE_ARRAY) return 1; + return 0; +} + +int +keyval_type_is_measurable(int type) +{ + if(type & BUNDLE_TYPE_MEASURABLE) return 1; + return 0; +} + +keyval_type_measure_size_func_t +keyval_type_get_measure_size_func(int type) +{ + switch(type) { + case BUNDLE_TYPE_STR: + case BUNDLE_TYPE_STR_ARRAY: + return keyval_type_measure_size_str; + break; + default: + return NULL; + } + return NULL; +} + +size_t +keyval_type_measure_size_str(void *val) +{ + if(!val) return 0; + return strlen((char *)val) + 1; +} + @@ -0,0 +1,11 @@ +#!/bin/bash + +cd `dirname $0` + +rm -rf cmake_tmp +mkdir cmake_tmp +cd cmake_tmp + +LD_LIBRARY_PATH=$LD_LIBRARY_PATH:`pwd` +CFLAGS="-g $CFLAGS" LDFLAGS="-Wl,--as-needed -Wl,--hash-style=both" cmake .. -DCMAKE_INSTALL_PREFIX=/usr && make test && echo "Test OK. No error." + diff --git a/test/CMakeLists.txt b/test/CMakeLists.txt new file mode 100755 index 0000000..9126b44 --- /dev/null +++ b/test/CMakeLists.txt @@ -0,0 +1,11 @@ +add_executable(test_bundle EXCLUDE_FROM_ALL + test_bundle.c + ) +target_link_libraries(test_bundle bundle) + +add_custom_target(test + COMMAND LD_LIBRARY_PATH=${CMAKE_BINARY_DIR} ./test_bundle + DEPENDS test_bundle + WORKING_DIRECTORY "${CMAKE_CURRENT_BINARY_DIR}" + COMMENT "Run 'make test'" + ) diff --git a/test/Makefile b/test/Makefile new file mode 100755 index 0000000..f461477 --- /dev/null +++ b/test/Makefile @@ -0,0 +1,10 @@ +#Steps to build the TC_bundle.c +#1.build the bundle code +#2.make +#3. TC_bundle binary file would be created. +export PKG_CONFIG_PATH=../debian/libbundle-dev/usr/lib/pkgconfig/ + +all: + sbs -e gcc -Wall -o TC_bundle TC_bundle.c `pkg-config --libs bundle` +clean: + rm -rf *.exe diff --git a/test/TC_bundle.c b/test/TC_bundle.c new file mode 100755 index 0000000..03e0c26 --- /dev/null +++ b/test/TC_bundle.c @@ -0,0 +1,1478 @@ +/* + * Copyright (c) 2011 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 <stdio.h> +#include <stdlib.h> +#include <unistd.h> +#include <malloc.h> +#include <string.h> +#include <assert.h> +#include <errno.h> +#include <bundle.h> +#include <sys/wait.h> +#include <sys/types.h> +#define SUCCESS 1 +#define FAIL 0 +int ret_bundle_foreach=FAIL; +int ret_bundle_foreach_invalid=FAIL; +int ret_bundle_keyval_typeget=FAIL; +int ret_bundle_exp_imp_p=FAIL; +int ret_bundle_en_dec_p=FAIL; +int ret_exp_imp_cases=FAIL; +int ret_bundle_exp_invalid=FAIL; +int ret_bundle_imp_invalid=FAIL; +int ret_bundle_add=FAIL; +int ret_bundle_get_val=FAIL; +int ret_bundle_dup=FAIL; +int ret_bundle_encode=FAIL; +int ret_bundle_decode=FAIL; +int ret_bundle_free_encoded=FAIL; +int ret_bundle_get_type=FAIL; +int ret_tc_free_exp_argv=FAIL; +int ret_keyval_is_array=FAIL; +int ret_keyval_get_basicval=FAIL; +int ret_bundle_del=FAIL; +int ret_keyval_get_arrval=FAIL; +int ret_bundle_get_str_arr=FAIL; +int ret_bundle_add_str_arr=FAIL; + +void iterate_bundleforeach(const char *key,const int type, bundle_keyval_t *kv, void *data) +{ + switch(type) + { + case BUNDLE_TYPE_STR: + { + //printf("\n CASE: BUNDLE_TYPE_STR "); + char *basic_val=NULL; + size_t size; + bundle_keyval_get_basic_val(kv,(void *)&basic_val,&size); + //printf("Key: %s ---- Val: %s\n",key,basic_val); + break; + } + case BUNDLE_TYPE_STR_ARRAY: + { + //printf("\n CASE: BUNDLE_TYPE_STR_ARRAY: "); + void **arr=NULL; + size_t *array_ele_size=NULL; + unsigned int ele_nos=0; + int i=0; + bundle_keyval_get_array_val(kv,&arr,&ele_nos,&array_ele_size); + //printf("Total Elements: %d\n",ele_nos); + //printf("Key: %s \n",key); + for(i=0;i<ele_nos;i++) + { + //printf("element is %s\n",(char *)*(arr+i)); + } + break; + } + case BUNDLE_TYPE_BYTE: + { + //printf("\n CASE: BUNDLE_TYPE_BYTE "); + char *basic_val=NULL; + size_t size; + bundle_keyval_get_basic_val(kv,(void *)&basic_val,&size); + //printf("Key: %s ---- Val: %s\n",key,basic_val); + break; + } + case BUNDLE_TYPE_BYTE_ARRAY: + { + //printf("\n CASE:BUNDLE_TYPE_BYTE_ARRAY "); + void **arr=NULL; + size_t *array_ele_size=NULL; + unsigned int ele_nos=0; + int i=0; + bundle_keyval_get_array_val(kv,&arr,&ele_nos,&array_ele_size); + //printf("Total Elements: %d\n",ele_nos); + //printf("Key: %s \n",key); + for (i=0;i<ele_nos;i++) + { + //printf("element is %s\n",(char *)*(arr+i)); + } + break; + } + default: + { + //printf("\n no match found"); + //printf("Key: %s is of type %d\n",key, type); + break; + } + + } + + return; +} + +void iterate_bundleforeach_withdata(const char *key,const int type, bundle_keyval_t *kv, void *data) +{ + //printf("\n data received is %d",(int)data); +} + +int TC_bundle_foreach() +{ + //printf("\n ====================================================================\n"); + + //printf("\nTESTCASE: TC_bundle_foreach"); + bundle *b=NULL; + char **array=NULL; + char buf[10]={0,}; + int no_of_ele=10; + int i=0; + int data_pass = 35; + + b=bundle_create(); + assert(NULL != b); +/*add elements */ + assert(0 == bundle_add(b, "k1", "val1")); + assert(0 == bundle_add(b, "k2", "val2")); + +/*bundle_for each with passed data */ + bundle_foreach(b,(void *)iterate_bundleforeach_withdata,(void*)data_pass); + + array=(char **)malloc(no_of_ele*sizeof(char *)); + for (i=0;i<no_of_ele;i++) + { + sprintf(buf,"arr_val%d",i); + *(array+i)=(char *)malloc(sizeof(char *)*strlen(buf)); + strcpy(*(array+i),buf); + } + assert(0==bundle_add_str_array(b,"k3", (const char **)array, no_of_ele)); + + + + bundle_foreach(b,(void *)iterate_bundleforeach,NULL); + + assert(0==bundle_free(b)); + return SUCCESS; +} + +int TC_bundle_foreach_invalid() +{ + //printf("\n ====================================================================\n"); + + //printf("\nTESTCASE: TC_bundle_foreach_invalid"); + bundle *b=NULL; + + bundle_foreach(b,(void *)iterate_bundleforeach,NULL); //FIXED:segmentation fault- put check for b=null + b=bundle_create(); + assert(NULL != b); + + assert(0 == bundle_add(b, "k1", "val1")); + assert(0 == bundle_add(b, "k2", "val2")); + return SUCCESS; +} +void iterate_bundle_keyvalgettype(const char *key,const int type, bundle_keyval_t *kv, void *data) +{ + + assert(type == bundle_keyval_get_type(kv)); + return; +} +int TC_bundle_keyval_get_type() +{ + //printf("\n====================================================================\n"); + + //printf("\nTESTCASE: TC_bundle_keyval_get_type"); + bundle *b=NULL; + char **array=NULL; + char buf[10]={0,}; + int no_of_ele=10; + int i=0; + + b=bundle_create(); + assert(NULL != b); + + assert(0 == bundle_add(b, "k1", "val1")); + assert(0 == bundle_add(b, "k2", "val2")); + + array=(char **)malloc(no_of_ele*sizeof(char *)); + for (i=0;i<no_of_ele;i++) + { + sprintf(buf,"arr_val%d",i); + *(array+i)=(char *)malloc(sizeof(char *)*strlen(buf)); + strcpy(*(array+i),buf); + } + assert(0==bundle_add_str_array(b,"k3", (const char **)array, no_of_ele)); + + + bundle_foreach(b,(void *)iterate_bundle_keyvalgettype,NULL); + return SUCCESS; +} + +int TC_bundle_export_import_print() +{ + + //printf("\n ====================================================================\n"); + //printf("\nTESTCASE: TC_bundle_export_import_print "); + bundle *b=NULL; + bundle *b_new=NULL; + char **array=NULL; + char buf[10]={0,}; + int no_of_ele=10; + int i=0; + + int argc1=0; + char **argv1=NULL; + + b=bundle_create(); + assert(NULL != b); + + assert(0 == bundle_add(b, "k1", "val1")); + assert(0 == bundle_add(b, "k2", "val2")); + + array=(char **)malloc(no_of_ele*sizeof(char *)); + for (i=0;i<no_of_ele;i++) + { + sprintf(buf,"arr_val%d",i); + *(array+i)=(char *)malloc(sizeof(char *)*strlen(buf)); + strcpy(*(array+i),buf); + } + assert(0==bundle_add_str_array(b,"k3", (const char **)array, no_of_ele)); + + + //printf("\noriginal bundle"); + bundle_foreach(b,(void *)iterate_bundleforeach,NULL); + + argc1=bundle_export_to_argv(b,&argv1); + assert(0<argc1); + b_new=bundle_import_from_argv(argc1,argv1); + assert(NULL != b_new); + + //printf("\nimported bundle"); + bundle_foreach(b_new,(void *)iterate_bundleforeach,NULL); + + + assert(0==bundle_free(b)); + assert(0==bundle_free(b_new)); + return SUCCESS; +} + +int TC_bundle_dup_print() +{ + + //printf("\n ====================================================================\n"); + //printf("\nTESTCASE: TC_bundle_dup_print"); + bundle *b=NULL; + char **array=NULL; + char buf[10]={0,}; + int no_of_ele=10; + int i=0; + bundle *dup_b=NULL; + + b=bundle_create(); + assert(NULL != b); + + assert(0 == bundle_add(b, "k1", "val1")); + assert(0 == bundle_add(b, "k2", "val2")); + + array=(char **)malloc(no_of_ele*sizeof(char *)); + for (i=0;i<no_of_ele;i++) + { + sprintf(buf,"arr_val%d",i); + *(array+i)=(char *)malloc(sizeof(char *)*strlen(buf)); + strcpy(*(array+i),buf); + } + assert(0==bundle_add_str_array(b,"k3", (const char **)array, no_of_ele)); + + + //printf("\noriginal bundle "); + bundle_foreach(b,(void *)iterate_bundleforeach,NULL); + + dup_b = bundle_dup(b); + assert(NULL != dup_b); + //printf("\n duplicated bundle "); + bundle_foreach(dup_b,(void *)iterate_bundleforeach,NULL); + + + assert(0==bundle_free(b)); + assert(0==bundle_free(dup_b)); + return SUCCESS; +} +int TC_bundle_encode_decode_print() +{ + + //printf("\n ====================================================================\n"); + //printf("\nTESTCASE: TC_bundle_encode_decode_print"); + bundle *b=NULL; + char **array=NULL; + char buf[10]={0,}; + int no_of_ele=10; + int i=0; + int len=-1; + bundle_raw *bundle_data; + bundle *dec_b=NULL; + + b=bundle_create(); + assert(NULL != b); + + assert(0 == bundle_add(b, "k1", "val1")); + assert(0 == bundle_add(b, "k2", "val2")); + + array=(char **)malloc(no_of_ele*sizeof(char *)); + for (i=0;i<no_of_ele;i++) + { + sprintf(buf,"arr_val%d",i); + *(array+i)=(char *)malloc(sizeof(char *)*strlen(buf)); + strcpy(*(array+i),buf); + } + assert(0==bundle_add_str_array(b,"k3", (const char **)array, no_of_ele)); + + + //printf("\noriginal bundle "); + bundle_foreach(b,(void *)iterate_bundleforeach,NULL); + + assert(0==bundle_encode(b,&bundle_data,&len)); + dec_b=bundle_decode(bundle_data,len); + assert(NULL != dec_b); + + //printf("\n decoded bundle "); + bundle_foreach(dec_b,(void *)iterate_bundleforeach,NULL); + + assert(0==bundle_free(b)); + assert(0==bundle_free(dec_b)); + return SUCCESS; +} + +int TC_bundle_export_to_argv_invalid() +{ + //printf("\n ====================================================================\n"); + //printf("\nTESTCASE: TC_bundle_export_to_argv_invalid "); + bundle *b_null=NULL; + int argc1=0; + char **argv1=NULL; + +/*CASE1:INVALID b= null,FIXED : segmentation fault in(put check for bundle=null) bundle_foreach (b=0x0, iter=0x4001322c <_iter_export_to_argv>, user_data=0xbead0a24)*/ + argc1=bundle_export_to_argv(b_null,&argv1); + return SUCCESS; + +} +int TC_bundle_import_from_argv_invalid() +{ + //printf("\n ====================================================================\n"); + //printf("\nTESTCASE: TC_bundle_import_from_argv_invalid "); + bundle *b_new=NULL; + int argc1=0; + char **argv1=NULL; + + +/* INVALID: passing invalid arguments -not exported/encoded */ +/*CASE1: argc1=0 */ + argc1=0; + argv1 = calloc(argc1+1,sizeof(char*)); + b_new=bundle_import_from_argv(argc1,argv1); + assert(NULL != b_new); + assert(0 == bundle_get_count(b_new)); + bundle_foreach(b_new,(void *)iterate_bundleforeach,NULL); + assert(0==bundle_free(b_new)); + +/*CASE2: argv1 =NULL--FIXED : segmentation fault-put check in code*/ + argc1=2; + argv1=NULL; + b_new=bundle_import_from_argv(argc1,argv1); + //printf("\n cannot form bundle"); + assert(NULL == b_new); +/*CASE3: argc1=4 /argv1!=NULL but all arguments value= null */ + argc1=4; +// argv1=calloc(1,sizeof(char*)); //sigsegv - atleast no of elements= arc1 should be allocated memory properly. + argv1=calloc(5,sizeof(char*)); + b_new=bundle_import_from_argv(argc1,argv1); + assert(NULL != b_new); + assert(0 == bundle_get_count(b_new)); + assert(0==bundle_free(b_new)); +/*CASE5: passing even no of arguments-[max=4] 6 arguments passed-no of bundle elements must be 2.*/ + argc1=4; + argv1=NULL; + argv1=calloc(5,sizeof(char*)); + argv1[0]="prog_name"; + argv1[1]="k2"; + argv1[2]="v2"; + argv1[3]="k3"; + argv1[4]="v3"; + argv1[5]="k4";//add extra- should not get added to bundle + argv1[6]="v4";//add extra- should not get added to bundle + b_new=bundle_import_from_argv(argc1,argv1); + assert(NULL != b_new); + //printf("\n no of elements in imported bundle is%d", bundle_get_count(b_new)); + assert(2 == bundle_get_count(b_new)); + bundle_foreach(b_new,(void *)iterate_bundleforeach,NULL); + assert(0==bundle_free(b_new)); +/*CASE6: passing odd no of arguments- [max=4]3 arguments passed-no of bundle elements will be 1.*/ + argc1=4; + argv1= NULL; + argv1=calloc(5,sizeof(char*)); + argv1[0]="prog_name"; + argv1[1]="k4"; + argv1[2]="v4"; + argv1[3]="k5"; + b_new=bundle_import_from_argv(argc1,argv1); + assert(NULL != b_new); + //printf("\n no of elements in imported bundle is%d", bundle_get_count(b_new)); + //bundle_foreach(b_new,(void *)iterate_bundleforeach,NULL); + assert(1 == bundle_get_count(b_new)); + assert(0==bundle_free(b_new)); + return SUCCESS; +} +int TC_bundle_export_import_cases() +{ + //printf("\n ====================================================================\n"); + //printf("\nTESTCASE: TC_bundle_export_import_cases "); + bundle *b=NULL; + bundle *b_new=NULL; + int argc1=0; + char **argv1=NULL; + + b=bundle_create(); + assert(NULL != b); + + +/*CASE1:bundle created succesfully- no keyval pair added ||return value of bundle_export_to_argv() >=2 in success and -1 in failure. */ + argc1=bundle_export_to_argv(b,&argv1); + //printf("\nargc is %d",argc1); + assert(argc1>0); + + b_new=bundle_import_from_argv(argc1,argv1); + assert(NULL != b_new); + assert(0 == bundle_get_count(b_new)); + /*reset values*/ + assert(0==bundle_free(b_new)); + argc1=0; + argv1=NULL; + +/*CASE2: adding elements to bundle and then export-import*/ + assert(0 == bundle_add(b, "k1", "val1")); + assert(0 == bundle_add(b, "k2", "val2")); + assert(0 == bundle_add(b, "k3", "val3")); + + argc1=bundle_export_to_argv(b,&argv1); + //printf("\nargc is %d",argc1); + assert(argc1>0); + assert(argc1==8); /*argc1 = 2*no of bundle elements +2 = actual count of argv [last null terminator not counted in argc1]*/ + assert(argv1!=NULL); + assert(argv1[0]==NULL); + assert(argv1[argc1]==NULL);/*last element must be NULL */ + + b_new=bundle_import_from_argv(argc1,argv1); + assert(NULL != b_new); + assert(3 == bundle_get_count(b_new)); + assert(0== strcmp(bundle_get_val(b_new,"k1"),bundle_get_val(b,"k1"))); + assert(0== strcmp(bundle_get_val(b_new,"k2"),bundle_get_val(b,"k2"))); + assert(0== strcmp(bundle_get_val(b_new,"k3"),bundle_get_val(b,"k3"))); + bundle_foreach(b_new,(void *)iterate_bundleforeach,NULL); + + + assert(0==bundle_free(b_new)); + assert(0==bundle_free(b)); + return SUCCESS; + +} +int TC_bundle_add() +{ + //printf("\n ====================================================================\n"); + //printf("\n TESTCASE : TC_bundle_add"); + bundle *b=NULL; + b=bundle_create(); + assert(NULL != b); + + bundle *b2=NULL; + + assert(0 == bundle_add(b, "key1", "val1")); + assert(0 == bundle_add(b, "key2", "val2")); +/*duplicate key */ + assert(0 != bundle_add(b, "key1", "val123")); + //printf("\n 1 %s",strerror(errno)); + assert(EPERM == errno ); +/*Null key */ + assert(0 != bundle_add(b, NULL, "val123")); + //printf("\n 2 %s",strerror(errno)); + assert(EKEYREJECTED == errno ); +/*Empty(string) key */ + assert(0 != bundle_add(b,"","val123")); + //printf("\n 2-empty key %s",strerror(errno)); + assert(EKEYREJECTED == errno ); +/*Null value */ + assert(0 != bundle_add(b, "key3", NULL)); + //printf("\n 3 %s",strerror(errno)); + assert(EINVAL == errno ); +/*Null bundle */ + assert(0 != bundle_add(NULL,"key4", "val123")); + //printf("\n 4 %s",strerror(errno)); + assert(EINVAL == errno ); +/*Null bundle/value - duplicate key */ + assert(0 != bundle_add(NULL,"key4", NULL)); + //printf("\n 5 %s",strerror(errno)); + assert(EINVAL == errno ); +/*Null value - duplicate key */ + assert(0 != bundle_add(b,"key4", NULL)); + //printf("\n 6 %s",strerror(errno)); + assert(EINVAL == errno ); +/*get value for given key */ + assert(0==strcmp("val1",bundle_get_val(b,"key1"))); + assert(0==strcmp("val2",bundle_get_val(b,"key2"))); +/*get count*/ + assert(2==bundle_get_count(b)); +/* add one more key-val */ + assert(0 == bundle_add(b, "k3", "v3")); +/*get count again - should be incremented*/ + assert(3 == bundle_get_count(b)); +/*add same key-val to different bundle- b2 */ + + b2=bundle_create(); + assert(NULL != b2); + assert(0 == bundle_add(b2, "key1", "val1")); + assert(0 == bundle_add(b2, "key2", "v2")); + assert(0==strcmp("v2",bundle_get_val(b2,"key2"))); + assert(2==bundle_get_count(b2)); +/*Empty(string) value- allowed */ + assert(0 == bundle_add(b2,"key3","")); +/*Bundle_add without prior bundle_create */ + bundle *b3=NULL; + assert(0 != bundle_add(b3, "k1", "v1")); + assert(EINVAL == errno ); + return SUCCESS; +} +int TC_bundle_get_val() +{ + //printf("\n ====================================================================\n"); + //printf("\n TEST CASE :TC_bundle_get_val"); + bundle *b=NULL; + bundle *b1=NULL; + b=bundle_create(); + assert(NULL != b); + assert(0 == bundle_add(b, "key1", "val1")); + assert(0 == bundle_add(b, "key2", "val2")); + + assert(0==strcmp("val1",bundle_get_val(b,"key1"))); + assert(0==strcmp("val2",bundle_get_val(b,"key2"))); +/*wrong key passed as input */ + assert(NULL==bundle_get_val(b,"key4")); + assert(ENOKEY == errno ); +/*bundle = NULL */ + assert(NULL==bundle_get_val(NULL,"key4")); + assert(EINVAL == errno ); +/*bundle = not created */ + assert(NULL==bundle_get_val(b1,"key4")); + assert(EINVAL == errno ); +/*key = NULL, bundle = proper */ + assert(NULL==bundle_get_val(b,NULL)); + assert(EKEYREJECTED == errno ); +/*pass string instead of bundle -sigsegv */ +// assert(NULL==bundle_get_val("bundle","key1")); +// assert(EINVAL == errno ); + + assert(0==bundle_free(b)); + return SUCCESS; + +} +#if 0 +int TC_bundle_add_byte() +{ +/*pass str="aa" instead of byte="aa\0"*/ + //printf("\n ====================================================================\n"); + //printf("\n TESTCASE: TC_bundle_add_byte"); + bundle *b=NULL; + bundle *b1=NULL; + b=bundle_create(); + assert(NULL != b); +/*valid cases */ + char *data_1byte ="bbbbb"; + char *data_2byte ="aaaa"; + assert(0 == bundle_add_byte(b, "k4", (void *)data_1byte, strlen(data_1byte)+1)); + assert(0==bundle_add_byte(b, "k5", (void *)data_2byte, strlen(data_2byte)+1)); +/*duplicate value */ + assert(0==bundle_add_byte(b, "k7", (void *)data_2byte, strlen(data_2byte)+1)); +/*value and size NULL */ + assert(0==bundle_add_byte(b, "k8",NULL,NULL)); +/*value = NULL, size not NULL */ + assert(0==bundle_add_byte(b, "k9",NULL,9)); + +/*invalid cases */ +/*bundle = NULL */ + assert(0!=bundle_add_byte(b1, "k5", (void *)data_2byte,(size_t)strlen(data_2byte)+1)); + assert(EINVAL == errno ); +/*duplicate key */ + assert(0!=bundle_add_byte(b, "k5","abcd",4)); + assert(EPERM == errno); +/*empty key */ + assert(0!=bundle_add_byte(b,"","lion",4)); + assert(EKEYREJECTED == errno ); + assert(0==bundle_free(b)); + return SUCCESS; +} +#endif +////// +int TC_bundle_add_str_array() +{ + //printf("\n ====================================================================\n"); + //printf("\n TESTCASE :TC_bundle_add_str_array"); + const char *arr[]={"v1","v2","v3","v4"}; + bundle *b=NULL; + bundle *b1=NULL; + b=bundle_create(); + assert(NULL != b); + + assert(0==bundle_add_str_array(b,"k1",&arr,4)); + + +/*bundle= NULL - fail */ + assert(0!=bundle_add_str_array(b1,"key1",NULL,6)); + assert(EINVAL == errno ); +/*duplicate key - fail */ + assert(0!=bundle_add_str_array(b,"k1",NULL,6)); + assert(EPERM == errno ); +/*empty key - fail */ + assert(0!=bundle_add_str_array(b,"",NULL,6)); + assert(EKEYREJECTED == errno ); +/*No of elements = NULL - success */ + assert(0==bundle_add_str_array(b,"k3",NULL,NULL)); +/*add new array with a different key and 6 elements -success */ + assert(0==bundle_add_str_array(b,"k4",NULL,6)); + + assert(0==bundle_free(b)); + return SUCCESS; +} +/////// +#if 0 +int TC_bundle_add_byte_array() +{ + //printf("\n ====================================================================\n"); + //printf("\n TESTCASE :TC_bundle_add_byte_array"); + bundle *b=NULL; + bundle *b1=NULL; + b=bundle_create(); + assert(NULL != b); +/* cases */ + assert(0==bundle_add_byte_array(b,"k1",NULL,4)); + assert(0==bundle_set_byte_array_element(b,"k1",0,"ccc\0",4)); + assert(0==bundle_set_byte_array_element(b,"k1",1,"dd\0",3)); + assert(0==bundle_set_byte_array_element(b,"k1",2,"eee\0",4)); +/*try to add second array element again- over writing not allowed-fail */ + assert(0!=bundle_set_byte_array_element(b,"k1",1,"new\0",4)); + assert(EINVAL == errno ); +/*add fifth element - fail */ + assert(0!=bundle_set_byte_array_element(b,"k1",4,"gggg\0",5)); + assert(EINVAL == errno ); +/*bundle= NULL - fail */ + assert(0!=bundle_add_byte_array(b1,"key1",NULL,6)); + assert(EINVAL == errno ); +/*duplicate key - fail */ + assert(0!=bundle_add_byte_array(b,"k1",NULL,6)); + assert(EPERM == errno ); +/*empty key - fail */ + assert(0!=bundle_add_byte_array(b,"",NULL,6)); + assert(EKEYREJECTED == errno ); +/*No of elements = NULL - success */ + assert(0==bundle_add_byte_array(b,"k3",NULL,NULL)); +/*add new array with a different key and 6 elements -success */ + assert(0==bundle_add_byte_array(b,"k2",NULL,6)); +/* add fifth element- 1st/2nd/3rd/4th not yet added. */ + assert(0==bundle_set_byte_array_element(b,"k2",4,"ccc\0",4)); +/* bundle = NULL */ + assert(0!=bundle_set_byte_array_element(b1,"k2",0,"ccc\0",4)); + assert(EINVAL == errno ); +/* key = NULL */ + assert(0!=bundle_set_byte_array_element(b,NULL,1,"gggg\0",5)); + assert(EKEYREJECTED == errno ); +/* pass string instead of byte in value */ + assert(0==bundle_set_byte_array_element(b,"k2",3,"hello",6)); + assert(0==bundle_set_byte_array_element(b,"k2",5,"world",6));/*note size = size of string+ 1 (for \0) -- if \0 not added then juck characters appear while encode- decode */ + +// bundle_foreach(b,(void *)iterate_bundleforeach,NULL); + assert(0==bundle_free(b)); + return SUCCESS; + +} +int TC_bundle_get_byte() +{ + //printf("\n ====================================================================\n"); + //printf("\nTESTCASE :TC_bundle_get_byte"); + bundle *b=NULL; + const char *arr[]={"v1","v2","v3"}; + size_t len= -1; + void* ret_byte; + b=bundle_create(); + assert(NULL != b); + /* add elements */ + assert(0 == bundle_add_byte(b, "k1","aa\0",3)); + assert(0 == bundle_add_byte(b, "k2","bb\0",3)); + + assert(0 == bundle_add(b, "key1", "val1")); + assert(0==bundle_add_str_array(b,"key2",arr,3)); + assert(0==bundle_add_byte_array(b,"key3",NULL,4)); + assert(0==bundle_set_byte_array_element(b,"key3",0,"ccc\0",4)); +/*valid tests */ + assert(0==bundle_get_byte(b,"k1",&ret_byte,&len)); + assert(0==strcmp("aa",ret_byte)); + assert(3==len); + assert(0==bundle_get_byte(b,"k2",&ret_byte,&len)); + assert(0==strcmp("bb",ret_byte)); + assert(3==len); + assert(0==bundle_get_byte(b,"k2",NULL,&len)); + assert(3==len); + assert(0==bundle_get_byte(b,"k2",NULL,NULL)); +/*invalid tests */ + /* bundle= NULL */ + assert(0!=bundle_get_byte(NULL,"k1",&ret_byte,&len)); + assert(EINVAL == errno ); + /*key = empty */ + assert(0!=bundle_get_byte(b,"",&ret_byte,&len)); + assert(ENOKEY == errno ); + /*key does not exist */ + assert(0!=bundle_get_byte(b,"k3",&ret_byte,&len)); + assert(ENOKEY == errno ); + /*key = NULL */ + assert(0!=bundle_get_byte(b,NULL,&ret_byte,&len)); + assert(EKEYREJECTED == errno ); + /*pass the key for str type bundle-operation not supported */ + assert(0!=bundle_get_byte(b,"key1",&ret_byte,&len)); + assert(ENOTSUP == errno ); + /*pass the key for array type bundle */ + assert(0!=bundle_get_byte(b,"key2",&ret_byte,&len)); + assert(ENOTSUP == errno ); + assert(0!=bundle_get_byte(b,"key3",&ret_byte,&len)); + assert(ENOTSUP == errno ); + + assert(0==bundle_free(b)); + return SUCCESS; +} +#endif +/*API prototype changed */ +#if 0 +int TC_bundle_get_str_array() +{ + //printf("\n ====================================================================\n"); + //printf("\n TESTCASE :TC_bundle_get_str_array"); + bundle *b=NULL; + const char *arr[]={"v1","v2","v3"}; + char **str_arr=NULL; + int len = -1; + b=bundle_create(); + assert(NULL != b); +/* add elements */ + assert(0 == bundle_add(b, "k1", "val1")); + assert(0==bundle_add_str_array(b,"k2",arr,3)); + assert(0 == bundle_add_byte(b, "k3","hello\0",6)); + assert(0==bundle_add_byte_array(b,"k4",NULL,4)); + assert(0==bundle_set_byte_array_element(b,"k4",0,"ccc\0",4)); +/* valid case test */ + assert(0==bundle_get_str_array(b,"k2",&str_arr,&len)); + assert(0==strcmp("v1",str_arr[0])); + assert(0==strcmp("v2",str_arr[1])); + assert(3==len); + assert(3== (strlen(str_arr[0])+1)); + assert(3== (strlen(str_arr[1])+1)); + + assert(0==bundle_get_str_array(b,"k2",NULL,&len)); + assert(3==len); + assert(0==bundle_get_str_array(b,"k2",NULL,NULL)); +/* invalid cases test */ + /*bundle= null */ + assert(0!=bundle_get_str_array(NULL,"k2",&str_arr,&len)); + assert(EINVAL == errno ); + /*key = empty */ + assert(0!=bundle_get_str_array(b,"",&str_arr,&len)); + assert(ENOKEY == errno ); + /*invalid key */ + assert(0!=bundle_get_str_array(b,"key1",&str_arr,&len)); + assert(ENOKEY == errno ); + /*key = NULL */ + assert(0!=bundle_get_str_array(b,NULL,&str_arr,&len)); + assert(EKEYREJECTED == errno ); + /*key for invalid type of element */ + assert(0!=bundle_get_str_array(b,"k1",&str_arr,&len)); + assert(ENOTSUP == errno ); + assert(0!=bundle_get_str_array(b,"k3",&str_arr,&len)); + assert(ENOTSUP == errno ); + assert(0!=bundle_get_str_array(b,"k4",&str_arr,&len)); + assert(ENOTSUP == errno ); + + assert(0==bundle_free(b)); + return SUCCESS; +} +#endif +#if 1 +int TC_bundle_get_str_array() +{ + //printf("\n ====================================================================\n"); + //printf("\n TESTCASE :TC_bundle_get_str_array"); + bundle *b=NULL; + const char *arr[]={"v1","v2","v3"}; + const char **str_arr=NULL; + const char **str_arr1=NULL; + const char **str_arr2=NULL; + int len = -1; + b=bundle_create(); + assert(NULL != b); +/* add elements */ + assert(0 == bundle_add(b, "k1", "val1")); + assert(0==bundle_add_str_array(b,"k2",arr,3)); +/* valid case test */ + str_arr=bundle_get_str_array(b,"k2",&len); + /*printf("\nreturned array ele 1 is %s",str_arr[0]); + printf("\nreturned array ele 2 is %s",str_arr[1]); + printf("\nreturned array ele 3 is %s",str_arr[2]);*/ + assert(3==len); + //assert(0==strcmp("v1",str_arr[0])); + str_arr1=bundle_get_str_array(b,"k2",&len); + assert(3==len); + str_arr2=bundle_get_str_array(b,"k2",NULL); +/* invalid cases test */ + /*bundle= null */ + assert(NULL ==bundle_get_str_array(NULL,"k2",&len)); + assert(EINVAL == errno ); + /*key = empty */ + assert(NULL==bundle_get_str_array(b,"",&len)); + assert(ENOKEY == errno ); + /*invalid key */ + assert(NULL==bundle_get_str_array(b,"key1",&len)); + assert(ENOKEY == errno ); + /*key = NULL */ + assert(NULL==bundle_get_str_array(b,NULL,&len)); + assert(EKEYREJECTED == errno ); + /*key for invalid type of element */ + assert(NULL==bundle_get_str_array(b,"k1",&len)); + assert(ENOTSUP == errno ); + assert(0==bundle_free(b)); + return SUCCESS; +} +#endif +#if 0 +int TC_bundle_get_byte_array() +{ + //printf("\n ====================================================================\n"); + //printf("\nTESTCASE :TC_bundle_get_byte_array"); + bundle *b=NULL; + const char *arr[]={"v1","v2","v3"}; + void **byte_arr=NULL; + unsigned int len = -1; + unsigned int *ele_size= NULL; + b=bundle_create(); + assert(NULL != b); +/* add elements */ + assert(0 == bundle_add(b, "k1", "val1")); + assert(0==bundle_add_str_array(b,"k2",arr,3)); + assert(0 == bundle_add_byte(b, "k3","hello\0",6)); + assert(0==bundle_add_byte_array(b,"k4",NULL,4)); + assert(0==bundle_set_byte_array_element(b,"k4",0,"ccc\0",4)); + assert(0==bundle_set_byte_array_element(b,"k4",1,"dddd\0",5)); +/* valid case test */ + assert(0==bundle_get_byte_array(b,"k4",&byte_arr,&len,&ele_size)); + assert(0==strcmp("ccc",byte_arr[0])); + assert(0==strcmp("dddd",byte_arr[1])); + assert(4==len); + assert(4== (strlen(byte_arr[0])+1)); + assert(5== (strlen(byte_arr[1])+1)); + + assert(0==bundle_get_byte_array(b,"k4",NULL,&len,&ele_size)); + assert(4==len); + assert(0==bundle_get_byte_array(b,"k4",NULL,NULL,&ele_size)); +/* invalid cases test */ + /*bundle= null */ + assert(0!=bundle_get_byte_array(NULL,"k4",&byte_arr,&len,&ele_size)); + assert(EINVAL == errno ); + /*key = empty */ + assert(0!=bundle_get_byte_array(b,"",&byte_arr,&len,&ele_size)); + assert(ENOKEY == errno ); + /*invalid key */ + assert(0!=bundle_get_byte_array(b,"key1",&byte_arr,&len,&ele_size)); + assert(ENOKEY == errno ); + /*key = NULL */ + assert(0!=bundle_get_byte_array(b,NULL,&byte_arr,&len,&ele_size)); + assert(EKEYREJECTED == errno ); + /*key for invalid type of element */ + assert(0!=bundle_get_byte_array(b,"k1",&byte_arr,&len,&ele_size)); + assert(ENOTSUP == errno ); + assert(0!=bundle_get_byte_array(b,"k2",&byte_arr,&len,&ele_size)); + assert(ENOTSUP == errno ); + assert(0!=bundle_get_byte_array(b,"k3",&byte_arr,&len,&ele_size)); + assert(ENOTSUP == errno ); + + assert(0==bundle_free(b)); + return SUCCESS; +} +#endif +int TC_bundle_get_type() +{ + //printf("\n ====================================================================\n"); + //printf("\nTESTCASE: TC_bundle_get_type"); + char **array=NULL; + char buf[10]={0,}; + int no_of_ele=10; + int i=0; + bundle *b=NULL; + b=bundle_create(); + assert(NULL != b); + + /* add elements */ + assert(0 == bundle_add(b, "k1", "val1")); + array=(char **)malloc(no_of_ele*sizeof(char *)); + for (i=0;i<no_of_ele;i++) + { + sprintf(buf,"arr_val%d",i); + *(array+i)=(char *)malloc(sizeof(char *)*strlen(buf)); + strcpy(*(array+i),buf); + } + assert(0==bundle_add_str_array(b,"k2", (const char **)array, no_of_ele)); + + /*valid case test for bundle_get_type */ + assert(BUNDLE_TYPE_STR==bundle_get_type(b,"k1")); + assert(BUNDLE_TYPE_STR_ARRAY==bundle_get_type(b,"k2")); + + /* in valid cases test */ + assert(BUNDLE_TYPE_NONE==bundle_get_type(b,"k5")); + assert(ENOKEY == errno); + assert(BUNDLE_TYPE_NONE==bundle_get_type(b,NULL)); + assert(ENOKEY == errno); + assert(BUNDLE_TYPE_NONE==bundle_get_type(b,"")); + assert(ENOKEY == errno); + assert(0==bundle_free(b)); + return SUCCESS; +} +void iterate_is_keyval_type_array(const char *key,const int type, bundle_keyval_t *kv, void *data) +{ + + if(0==strcmp(key,"k1")) + assert(0 == bundle_keyval_type_is_array(kv)); + else if(0==strcmp(key,"k2")) + assert(1 == bundle_keyval_type_is_array(kv)); + else if(0==strcmp(key,"k3")) + assert(0 == bundle_keyval_type_is_array(kv)); + else if(0==strcmp(key,"k4")) + assert(1 == bundle_keyval_type_is_array(kv)); + return; +} +int TC_bundle_keyval_type_is_array() +{ + //printf("\n ====================================================================\n"); + //printf("\nTESTCASE : TC_bundle_keyval_type_is_array"); + bundle *b=NULL; + const char *arr[]={"v1","v2","v3"}; + b=bundle_create(); + assert(NULL != b); + assert(0 == bundle_add(b, "k1", "val1")); + assert(0==bundle_add_str_array(b,"k2",arr,3)); + + bundle_foreach(b,(void *)iterate_is_keyval_type_array,NULL); + return SUCCESS; + +} +void iterate_keyval_get_basicval(const char *key,const int type, bundle_keyval_t *kv, void *data) +{ + void **val=NULL; + size_t len =-1; + if(0==strcmp(key,"k1")) + assert(0 == bundle_keyval_get_basic_val(kv,val,&len)); + else if(0==strcmp(key,"k2")) + assert(0!= bundle_keyval_get_basic_val(kv,val,&len)); + else if(0==strcmp(key,"k3")) + assert(0 == bundle_keyval_get_basic_val(kv,val,&len)); + else if(0==strcmp(key,"k4")) + assert(0!= bundle_keyval_get_basic_val(kv,val,&len)); + return; +} +int TC_bundle_keyval_get_basic_val() +{ + //printf("\n ====================================================================\n"); + //printf("\nTESTCASE:TC_bundle_keyval_get_basic_val"); + const char *arr[]={"v1","v2","v3"}; + bundle *b=NULL; + b=bundle_create(); + assert(NULL != b); + + assert(0 == bundle_add(b, "k1", "val1")); + assert(0==bundle_add_str_array(b,"k2",arr,3)); + + bundle_foreach(b,(void *)iterate_keyval_get_basicval,NULL); + return SUCCESS; +} + +void iterate_is_keyval_get_arrayval(const char *key,const int type, bundle_keyval_t *kv, void *data) +{ + void ***array_val=NULL; + unsigned int *array_len =NULL; + size_t **ele_size=NULL; + if(0==strcmp(key,"k1")) + assert(0 != bundle_keyval_get_array_val(kv,array_val,array_len,ele_size)); + else if(0==strcmp(key,"k2")) + assert(0 == bundle_keyval_get_array_val(kv,array_val,array_len,ele_size)); + else if(0==strcmp(key,"k3")) + assert(0 != bundle_keyval_get_array_val(kv,array_val,array_len,ele_size)); + else if(0==strcmp(key,"k4")) + assert(0 == bundle_keyval_get_array_val(kv,array_val,array_len,ele_size)); + return; +} +int TC_bundle_keyval_get_array_val() +{ + //printf("\n ====================================================================\n"); + //printf("\nTESTCASE :TC_bundle_keyval_get_array_val"); + const char *arr[]={"v1","v2","v3"}; + bundle *b=NULL; + b=bundle_create(); + assert(NULL != b); + + assert(0 == bundle_add(b, "k1", "val1")); + assert(0==bundle_add_str_array(b,"k2",arr,3)); + + bundle_foreach(b,(void *)iterate_is_keyval_get_arrayval,NULL); + return SUCCESS; +} + +int TC_bundle_encode() +{ + //printf("\n ====================================================================\n"); + //printf("\nTESTCASE: TC_bundle_encode"); + bundle *b=NULL; + bundle_raw *bundle_data; + int len = -1; +/*bundle not created-encode - b= NULL*/ + assert(0!=bundle_encode(b,&bundle_data,&len)); +/*bundle created- no element added -encode */ + b=bundle_create(); + assert(NULL != b); + assert(0==bundle_encode(b,&bundle_data,&len)); +/*2 elements added - encode */ + assert(0 == bundle_add(b, "k1", "val1")); + assert(0 == bundle_add(b, "k2", "val2")); + + assert(0==bundle_encode(b,&bundle_data,&len)); + assert(0==bundle_free(b)); + return SUCCESS; +} +int TC_bundle_decode() +{ + //printf("\n ====================================================================\n"); + //printf("\nTESTCASE: TC_bundle_decode"); + bundle *b=NULL; + bundle_raw *bundle_data=NULL; + bundle *dec_b=NULL; + int len = -1; +/*invalid bundle_data and len values- not encoded */ + dec_b=bundle_decode(bundle_data,len); + assert(NULL == dec_b); + assert(EINVAL == errno); +/*invalid bundle_data and len values- not encoded-any random string passed -FIXED */ + dec_b=bundle_decode("not_encodeddata",len); + assert(NULL == dec_b); +// assert(EINVAL == errno); +/*encode- decode but incorrect value for length */ + b=bundle_create(); + assert(NULL != b); + assert(0 == bundle_add(b, "k1", "val1")); + assert(0 == bundle_add(b, "k2", "val2")); + assert(0==bundle_encode(b,&bundle_data,&len)); + dec_b=bundle_decode(bundle_data,9); + assert(NULL != dec_b); + bundle_foreach(dec_b,(void *)iterate_bundleforeach,NULL); + assert(0==bundle_free(b)); + assert(0==bundle_free(dec_b)); + return SUCCESS; +} +#if 0 +void TC_bundle_free_encoded_raw_data() +{ + printf("\n ====================================================================\n"); + printf("\n TESTCASE: TC_bundle_free_encoded_raw_data"); + bundle_raw *bundle_data=NULL; + bundle_raw *bundle_data_null=NULL; + int len =-1; + bundle *b=NULL; + b=bundle_create(); + assert(NULL != b); + assert(0 == bundle_add(b, "k1", "val1")); + assert(0 == bundle_add(b, "k2", "val2")); +/* valid case */ + assert(0==bundle_encode(b,&bundle_data,&len)); + assert(0==bundle_free_encoded_rawdata(bundle_data)); +/* FIXED -sigabrt trying to free twice */ +if(0!=bundle_free_encoded_rawdata(bundle_data)) + printf("\nalready freed"); + assert(0!=bundle_free_encoded_rawdata(bundle_data)); + assert(0!=bundle_free_encoded_rawdata(bundle_data)); +/*trying to free bundle_data= NULL */ + assert(0!=bundle_free_encoded_rawdata(bundle_data_null)); + + assert(0==bundle_free(b)); +} +#endif +int TC_bundle_free_encoded_raw_data() +{ + //printf("\n ====================================================================\n"); + //printf("\n TESTCASE: TC_bundle_free_encoded_raw_data"); + bundle_raw *bundle_data=NULL; + bundle_raw *bundle_data_null=NULL; + int len =-1; + bundle *b=NULL; + b=bundle_create(); + assert(NULL != b); + assert(0 == bundle_add(b, "k1", "val1")); + assert(0 == bundle_add(b, "k2", "val2")); +/* valid case */ + assert(0==bundle_encode(b,&bundle_data,&len)); + assert(0==bundle_free_encoded_rawdata(&bundle_data)); +/* FIXED -sigabrt trying to free twice */ +if(0!=bundle_free_encoded_rawdata(&bundle_data)) + //printf("\nalready freed"); + assert(0!=bundle_free_encoded_rawdata(&bundle_data)); + assert(0!=bundle_free_encoded_rawdata(&bundle_data)); +/*trying to free bundle_data= NULL */ + assert(0!=bundle_free_encoded_rawdata(&bundle_data_null)); + + assert(0==bundle_free(b)); + return SUCCESS; +} +int TC_bundle_free_exported_argv() +{ + //printf("\n ====================================================================\n"); + //printf("\n TESTCASE :TC_bundle_free_exported_argv"); + int argc1=0; + char **argv1=NULL; + int argc2=0; + char **argv2=NULL; + bundle *b=NULL; + b=bundle_create(); + assert(NULL != b); + + assert(0 == bundle_add(b, "k1", "val1")); + assert(0 == bundle_add(b, "k2", "val2")); + argc1=bundle_export_to_argv(b,&argv1); + assert(0<argc1); +/*valid args */ + assert(0 ==bundle_free_exported_argv(argc1,&argv1)); +/*invalid args- argc =0,argv = NULL */ + assert(0 !=bundle_free_exported_argv(argc2,&argv2)); +/*invalid args- argc =8 , argv= NULL */ + assert(0 !=bundle_free_exported_argv(8,&argv2)); +/* FIXED double free -sigabrt */ + assert(0 !=bundle_free_exported_argv(argc1,&argv1)); + return SUCCESS; +} + +#if 0 +void TC_bundle_free_exported_argv() +{ + printf("\n ====================================================================\n"); + printf("\n TESTCASE :TC_bundle_free_exported_argv"); + int argc1=0; + char **argv1=NULL; + int argc2=0; + char **argv2=NULL; + bundle *b=NULL; + b=bundle_create(); + assert(NULL != b); + + assert(0 == bundle_add(b, "k1", "val1")); + assert(0 == bundle_add(b, "k2", "val2")); + argc1=bundle_export_to_argv(b,&argv1); + assert(0<argc1); +/*valid args */ + assert(0 ==bundle_free_exported_argv(argc1,argv1)); +/*invalid args- argc =0,argv = NULL */ + assert(0 !=bundle_free_exported_argv(argc2,argv2)); +/*invalid args- argc =8 , argv= NULL */ + assert(0 !=bundle_free_exported_argv(8,argv2)); +/* FIXED double free -sigabrt */ +// assert(0 !=bundle_free_exported_argv(argc1,argv1)); +} +#endif +int TC_bundle_del() +{ + //printf("\n ====================================================================\n"); + //printf("\n TESTCASE :TC_bundle_del"); + const char *arr[]={"v1","v2","v3"}; + bundle *b=NULL; + b=bundle_create(); + assert(NULL != b); +/* add elements */ + assert(0 == bundle_add(b, "k1", "val1")); + assert(0==bundle_add_str_array(b,"k2",arr,3)); + assert(2 == bundle_get_count(b)); +/*valid case tests */ + assert(0 == bundle_del(b, "k1")); + assert(NULL == bundle_get_val(b, "k1")); + assert(ENOKEY == errno); + assert(1 == bundle_get_count(b)); + + assert(0 == bundle_del(b, "k2")); + assert(0 == bundle_get_count(b)); +/*invalid case tests */ + /*bundle = NULL */ + assert(0 != bundle_del(NULL, "key")); + assert(EINVAL == errno); + /*key =NULL */ + + assert(0 != bundle_del(b, NULL)); + assert(EKEYREJECTED == errno); + /*key = empty */ + assert(0 != bundle_del(b, "")); + assert(EKEYREJECTED == errno); + /*key does not exist- invalid key */ + assert(0 != bundle_del(b, "key")); + assert(ENOKEY == errno); + /* invalid key-again pass the same key */ + assert(0 != bundle_del(b, "k1")); + assert(ENOKEY == errno); + + assert(0 == bundle_get_count(b)); + assert(0==bundle_free(b)); + return SUCCESS; +} + +int +main(int argc, char **argv) +{ + /*print the results */ + printf("\n************************************************************************\n"); + printf("\n Test Suite Report \n"); + printf("\n Output : 1 = Success , On failure the respective test case aborts and prints the assert log \n"); + printf("\n************************************************************************\n"); + printf("TC ID\t\tRESULT\n"); + + pid_t tc_bundle_foreach = fork(); + if (tc_bundle_foreach == 0) + { + ret_bundle_foreach = TC_bundle_foreach(); + printf("TC_bundle_foreach\t%d\n",ret_bundle_foreach); + exit(1); + } + waitpid(tc_bundle_foreach,NULL,WNOHANG); + + + pid_t tc_bundle_foreach_invalid = fork(); + if (tc_bundle_foreach_invalid == 0) + { + ret_bundle_foreach_invalid =TC_bundle_foreach_invalid(); + printf("TC_bundle_foreach_invalid\t%d\n",ret_bundle_foreach_invalid); + exit(1); + } + waitpid(tc_bundle_foreach,NULL,WNOHANG); + + pid_t tc_bundle_keyval_gettype = fork(); + if ( tc_bundle_keyval_gettype == 0) + { + ret_bundle_keyval_typeget = TC_bundle_keyval_get_type(); + printf("TC_bundle_keyval_get_type\t%d\n",ret_bundle_keyval_typeget ); + exit(1); + } + waitpid(tc_bundle_keyval_gettype ,NULL,WNOHANG); + + pid_t tc_bundle_export_import_print = fork(); + if ( tc_bundle_export_import_print == 0) + { + ret_bundle_exp_imp_p = TC_bundle_export_import_print(); + printf("TC_bundle_export_import_print\t%d\n",ret_bundle_exp_imp_p); + exit(1); + } + waitpid(tc_bundle_export_import_print ,NULL,WNOHANG); + + pid_t tc_bundle_encode_decode_print = fork(); + if ( tc_bundle_encode_decode_print == 0) + { + ret_bundle_en_dec_p = TC_bundle_encode_decode_print(); + printf("TC_bundle_encode_decode_print\t%d\n",ret_bundle_en_dec_p); + exit(1); + } + waitpid(tc_bundle_encode_decode_print ,NULL,WNOHANG); + + pid_t tc_bundle_exp_imp_case = fork(); + if ( tc_bundle_exp_imp_case == 0) + { + ret_exp_imp_cases = TC_bundle_export_import_cases(); + printf("TC_bundle_export_import_cases\t%d\n",ret_exp_imp_cases); + exit(1); + } + waitpid(tc_bundle_exp_imp_case ,NULL,WNOHANG); + + pid_t tc_bundle_exp_invalid = fork(); + if ( tc_bundle_exp_invalid == 0) + { + ret_bundle_exp_invalid = TC_bundle_export_to_argv_invalid(); + printf("TC_bundle_export_to_argv_invalid\t%d\n",ret_bundle_exp_invalid); + exit(1); + } + waitpid(tc_bundle_exp_invalid ,NULL,WNOHANG); + + pid_t tc_bundle_imp_invalid = fork(); + if ( tc_bundle_imp_invalid == 0) + { + ret_bundle_imp_invalid = TC_bundle_import_from_argv_invalid(); + printf("TC_bundle_import_from_argv_invalid\t%d\n",ret_bundle_imp_invalid ); + exit(1); + } + waitpid(tc_bundle_imp_invalid ,NULL,WNOHANG); + + pid_t tc_bundle_add = fork(); + if ( tc_bundle_add == 0) + { + ret_bundle_add = TC_bundle_add(); + printf("TC_bundle_add\t%d\n",ret_bundle_add); + exit(1); + } + waitpid(tc_bundle_add ,NULL,WNOHANG); + + pid_t tc_bundle_get_val = fork(); + if ( tc_bundle_get_val == 0) + { + ret_bundle_get_val = TC_bundle_get_val(); + printf("TC_bundle_get_val\t%d\n",ret_bundle_get_val); + exit(1); + } + waitpid( tc_bundle_get_val ,NULL,WNOHANG); + + pid_t tc_bundle_dup = fork(); + if ( tc_bundle_dup == 0) + { + ret_bundle_dup = TC_bundle_dup_print(); + printf("TC_bundle_dup_print\t%d\n",ret_bundle_dup ); + exit(1); + } + waitpid( tc_bundle_dup ,NULL,WNOHANG); + + pid_t tc_bundle_encode = fork(); + if ( tc_bundle_encode == 0) + { + ret_bundle_encode = TC_bundle_encode(); + printf("TC_bundle_encode\t%d\n",ret_bundle_encode ); + exit(1); + } + waitpid( tc_bundle_encode ,NULL,WNOHANG); + + pid_t tc_bundle_decode = fork(); + if ( tc_bundle_decode == 0) + { + ret_bundle_decode = TC_bundle_decode(); + printf("TC_bundle_decode\t%d\n",ret_bundle_decode ); + exit(1); + } + waitpid( tc_bundle_decode ,NULL,WNOHANG); + + pid_t tc_bundle_free_encoded = fork(); + if ( tc_bundle_free_encoded == 0) + { + ret_bundle_free_encoded = TC_bundle_free_encoded_raw_data(); + printf("TC_bundle_free_encoded_raw_data\t%d\n",ret_bundle_free_encoded ); + exit(1); + } + waitpid( tc_bundle_free_encoded ,NULL,WNOHANG); +#if 0 + pid_t tc_bundle_add_byte = fork(); + if ( tc_bundle_add_byte == 0) + { + ret_bundle_add_byte = TC_bundle_add_byte(); + printf("TC_bundle_add_byte\t%d\n",ret_bundle_add_byte ); + exit(1); + } + waitpid(tc_bundle_add_byte ,NULL,WNOHANG); + + pid_t tc_bundle_add_byte_arr = fork(); + if ( tc_bundle_add_byte_arr == 0) + { + ret_bundle_add_byte_arr = TC_bundle_add_byte_array(); + printf("TC_bundle_add_byte_array\t%d\n",ret_bundle_add_byte_arr ); + exit(1); + } + waitpid(tc_bundle_add_byte_arr ,NULL,WNOHANG); +#endif + pid_t tc_bundle_get_type = fork(); + if ( tc_bundle_get_type == 0) + { + ret_bundle_get_type = TC_bundle_get_type(); + printf("TC_bundle_get_type\t%d\n",ret_bundle_get_type ); + exit(1); + } + waitpid( tc_bundle_get_type ,NULL,WNOHANG); + + pid_t tc_keyval_is_array = fork(); + if ( tc_keyval_is_array == 0) + { + ret_keyval_is_array = TC_bundle_keyval_type_is_array(); + printf("TC_bundle_keyval_type_is_array\t%d\n",ret_keyval_is_array ); + exit(1); + exit(1); + } + waitpid( tc_keyval_is_array ,NULL,WNOHANG); + + pid_t tc_keyval_get_basicval = fork(); + if ( tc_keyval_get_basicval == 0) + { + ret_keyval_get_basicval = TC_bundle_keyval_get_basic_val(); + printf("TC_bundle_keyval_get_basic_val\t%d\n",ret_keyval_get_basicval ); + exit(1); + } + waitpid( tc_keyval_get_basicval ,NULL,WNOHANG); +#if 0 + pid_t tc_bundle_get_byte = fork(); + if ( tc_bundle_get_byte == 0) + { + ret_bundle_get_byte = TC_bundle_get_byte(); + printf("TC_bundle_get_byte\t%d\n",ret_bundle_get_byte ); + exit(1); + } + waitpid( tc_bundle_get_byte ,NULL,WNOHANG); + + pid_t tc_bundle_get_byte_arr = fork(); + if ( tc_bundle_get_byte_arr == 0) + { + ret_bundle_get_byte_arr = TC_bundle_get_byte_array(); + printf("TC_bundle_get_byte_array\t%d\n",ret_bundle_get_byte_arr ); + exit(1); + } + waitpid( tc_bundle_get_byte_arr ,NULL,WNOHANG); +#endif + pid_t tc_free_exp_argv = fork(); + if ( tc_free_exp_argv == 0) + { + ret_tc_free_exp_argv = TC_bundle_free_exported_argv(); + printf("TC_bundle_free_exported_argv\t%d\n",ret_tc_free_exp_argv ); + exit(1); + } + waitpid( tc_free_exp_argv ,NULL,WNOHANG); + + pid_t tc_bundle_del = fork(); + if ( tc_bundle_del == 0) + { + ret_bundle_del = TC_bundle_del(); + printf("TC_bundle_del\t%d\n",ret_bundle_del ); + exit(1); + } + waitpid( tc_bundle_del ,NULL,WNOHANG); + + pid_t tc_keyval_get_arrval = fork(); + if ( tc_keyval_get_arrval == 0) + { + ret_keyval_get_arrval = TC_bundle_keyval_get_array_val(); + printf("TC_bundle_keyval_get_array_val\t%d\n",ret_keyval_get_arrval ); + exit(1); + } + waitpid( tc_keyval_get_arrval ,NULL,WNOHANG); + + pid_t tc_bundle_get_str_arr = fork(); + if ( tc_bundle_get_str_arr == 0) + { + ret_bundle_get_str_arr = TC_bundle_get_str_array(); + printf("TC_bundle_get_str_array\t%d\n",ret_bundle_get_str_arr ); + exit(1); + } + waitpid( tc_bundle_get_str_arr ,NULL,WNOHANG); + + pid_t tc_bundle_add_str_arr = fork(); + if ( tc_bundle_add_str_arr == 0) + { + ret_bundle_add_str_arr = TC_bundle_add_str_array(); + printf("TC_bundle_add_str_array\t%d\n",ret_bundle_add_str_arr ); + exit(1); + } + waitpid( tc_bundle_add_str_arr ,NULL,WNOHANG); + + return 0; +} diff --git a/test/test_bundle.c b/test/test_bundle.c new file mode 100755 index 0000000..7fa5f71 --- /dev/null +++ b/test/test_bundle.c @@ -0,0 +1,288 @@ +/* + * Copyright (c) 2011 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 <assert.h> +#include <stdlib.h> +#include <stdio.h> +#include <errno.h> +#include "bundle.h" + +void test_bundle_create(void) +{ + bundle *b; + + b = bundle_create(); + assert(NULL != b); + + bundle_free(b); +} + +void test_bundle_add_get(void) +{ + bundle *b = NULL; + + /* new bundle */ + b = bundle_create(); + assert(0 == bundle_add(b, "key1", "val1")); + assert(0 == bundle_add(b, "key2", "val2")); + + assert(0 == strcmp("val2", bundle_get_val(b, "key2"))); + assert(2 == bundle_get_count(b)); + + /* key duplication check + * If key is already exist, raise error code, and ignore new val. + * old value is preserved. + */ + assert(0 != bundle_add(b, "key1", "val123")); + assert(EPERM == errno); + /* still has "val1" for "key1" */ + assert(0 == strcmp("val1", bundle_get_val(b, "key1"))); + /* still count is 2 */ + assert(2 == bundle_get_count(b)); + + /* 3rd val */ + bundle_add(b, "key3", "val3"); + assert(3 == bundle_get_count(b)); /* now 3 */ + + bundle_free(b); +} + +void test_bundle_add_invalid(void) +{ + bundle *b; + + assert(0 != bundle_add(NULL, "a", "b")); + assert(EINVAL == errno); + + b = bundle_create(); + assert(-1 == bundle_add(b, NULL, "val1")); + assert(EKEYREJECTED == errno); + + assert(0 != bundle_add(b, "key1", NULL)); + assert(EINVAL == errno); + + assert(0 != bundle_add(b, "", "aaa")); + assert(EKEYREJECTED == errno); + + bundle_free(b); +} + +void test_bundle_get_invalid(void) +{ + bundle *b; + + assert(NULL == bundle_get_val(NULL, "key1")); + assert(EINVAL == errno); + + b = bundle_create(); + + assert(NULL == bundle_get_val(b, "key4")); + assert(ENOKEY == errno); + + assert(NULL == bundle_get_val(NULL, "aaa")); + assert(EINVAL == errno); + + assert(NULL == bundle_get_val(b, NULL)); + assert(EKEYREJECTED == errno); + + bundle_free(b); +} + +void iter_f(const char *key, const char *val, void *data) +{ + char *keys[] = { "1", "2", "3" }; + char *vals[] = { "a", "b", "c" }; + int i; + + for (i = 0; i < 3; i++) { + if (0 == strcmp(key, keys[i])) { + assert(0 == strcmp(val, vals[i])); + break; + } + } +} + +void test_bundle_del(void) +{ + bundle *b; + + assert(0 != bundle_del(NULL, "key")); + assert(EINVAL == errno); + + b = bundle_create(); + + assert(0 != bundle_del(b, NULL)); + assert(EKEYREJECTED == errno); + + assert(0 != bundle_del(b, "")); + assert(EKEYREJECTED == errno); + + assert(0 != bundle_del(b, "key")); + assert(ENOKEY == errno); + + assert(0 == bundle_get_count(b)); + + bundle_add(b, "k1", "v1"); + const char *v = bundle_get_val(b, "k1"); + assert(NULL != v && 0 == strcmp("v1", v)); + + assert(1 == bundle_get_count(b)); + + assert(0 == bundle_del(b, "k1")); + assert(NULL == bundle_get_val(b, "k1")); + assert(ENOKEY == errno); + + assert(0 == bundle_get_count(b)); + + bundle_free(b); +} + +void test_bundle_iterate(void) +{ + bundle *b; + + b = bundle_create(); + + bundle_add(b, "1", "a"); + bundle_add(b, "2", "b"); + bundle_add(b, "3", "c"); + + bundle_iterate(b, iter_f, NULL); + + bundle_free(b); +} + +void test_bundle_encode_decode(void) +{ + bundle *b1, *b2; + bundle_raw *r; + int size_r; + + b1 = bundle_create(); + bundle_add(b1, "k1", "v1"); + bundle_add(b1, "k2", "v2"); + bundle_encode(b1, &r, &size_r); + + /* show serialized data */ + /* + char *c = r; + for(; c < r+size_r; c++) { + printf("%c", *c); + if ('\0' == *c) printf("\n"); + } + */ + + b2 = bundle_decode(r, size_r); + + assert(0 == strcmp(bundle_get_val(b1, "k1"), bundle_get_val(b2, "k1"))); + assert(0 == strcmp(bundle_get_val(b1, "k2"), bundle_get_val(b2, "k2"))); + + bundle_free(b1); + bundle_free(b2); + free(r); +} + +void test_bundle_2byte_chars(void) +{ + bundle *b; + char *k1 = "?넝리언루aaabb?ㅏ?ss처푸?"; + char *v1 = "?ㅂ짜ccc?언sss루퍼?; + char *k2 = "ljvvn?챂?ㅇ?징?풐;?sdfxa?ㅣ?ㅁ?; + char *v2 = "axs?ㅇ?퍼?놔미ㅇ"; + + b = bundle_create(); + + bundle_add(b, k1, v1); + assert(0 == strcmp(v1, bundle_get_val(b, k1))); + bundle_add(b, k2, v2); + assert(0 == strcmp(v2, bundle_get_val(b, k2))); + + bundle_free(b); +} + +static void _dup_check_cb(const char *k, const char *v, void *data) +{ + bundle *b = (bundle *) data; + + assert(0 == strcmp(bundle_get_val(b, k), v)); +} + +void test_bundle_dup(void) +{ + bundle *b1, *b2; + b1 = bundle_create(); + bundle_add(b1, "k1", "v1"); + bundle_add(b1, "k2", "v2"); + + b2 = bundle_dup(b1); + + assert(NULL != b2); + bundle_iterate(b2, _dup_check_cb, b1); + assert(bundle_get_count(b1) == bundle_get_count(b2)); + + bundle_free(b1); + bundle_free(b2); +} + +void test_bundle_convert_argv(void) +{ + + bundle *b1, *b2; + + b1 = bundle_create(); + bundle_add(b1, "k1", "v1"); + bundle_add(b1, "k2", "v2"); + + /* export test */ + int argc = 0; + char **argv = NULL; + argc = bundle_export_to_argv(b1, &argv); + assert(5 == argc); + assert(NULL != argv); + assert(NULL == argv[0]); + assert(0 == strcmp("k1", argv[1]) && 0 == strcmp("v1", argv[2])); + assert(0 == strcmp("k2", argv[3]) && 0 == strcmp("v2", argv[4])); + assert(NULL == argv[5]); /* Last item must be NULL */ + + /* import test */ + b2 = bundle_import_from_argv(argc, argv); + assert(NULL != b2); + assert(2 == bundle_get_count(b2)); + assert(0 == strcmp("v1", bundle_get_val(b2, "k1"))); + assert(0 == strcmp("v2", bundle_get_val(b2, "k2"))); + + free(argv); + bundle_free(b1); + bundle_free(b2); +} + +int main(int argc, char **argv) +{ + test_bundle_create(); + test_bundle_add_get(); + test_bundle_add_invalid(); + test_bundle_get_invalid(); + test_bundle_del(); + test_bundle_iterate(); + test_bundle_encode_decode(); + test_bundle_2byte_chars(); + test_bundle_dup(); + test_bundle_convert_argv(); + + return 0; +} + |