SET(INC_DIR include)
INCLUDE_DIRECTORIES(${INC_DIR})
-SET(dependents "dlog libmedia-service media-thumbnail libmedia-utils capi-base-common vconf cynara-client cynara-creds-socket cynara-session")
+SET(dependents "dlog libmedia-service media-thumbnail libmedia-utils capi-base-common capi-system-info vconf cynara-client cynara-creds-socket cynara-session")
SET(pc_dependents "dlog capi-base-common")
INCLUDE(FindPkgConfig)
*
*/
+/**
+ * @defgroup CAPI_CONTENT_MEDIA_FACE_DETECTION_MODULE Face Detection
+ * @brief The Face Detection API provides functions to detect face information about stored image files.
+ *
+ * @ingroup CAPI_CONTENT_MEDIA_INFO_MODULE
+ *
+ * @section CAPI_CONTENT_MEDIA_FACE_DETECTION_MODULE_HEADER Required Header
+ * \#include <media_content.h>
+ *
+ * @section CAPI_CONTENT_MEDIA_FACE_DETECTION_MODULE_FEATURE Related Features
+ * This API is related with the following feature: \n
+ * - %http://tizen.org/feature/vision.face_recognition
+ * It is recommended to create applications with regard to features, to increase reliability. \n
+ *
+ * You can check if a device supports the related features for this API by using @ref CAPI_SYSTEM_SYSTEM_INFO_MODULE, thereby controlling the procedure of your application. \n
+ *
+ * To ensure your application is only running on a device with specific features, please define the features in your manifest file using the manifest editor in the SDK. \n
+ *
+ * More details on featuring your application can be found from <a href="https://developer.tizen.org/development/getting-started/native-application/understanding-tizen-programming/application-filtering"><b>Feature Element</b>.</a>
+ *
+ * @section CAPI_CONTENT_MEDIA_FACE_DETECTION_MODULE_OVERVIEW Overview
+ * The Face Detection API provides functions to detect face information associated with image files. \n
+ * Face information detected by mediavision API. To detect faces, you should use media_info_start_face_detection() API. \n
+ *
+ * API allows to:
+ * - start and cancel face detection with image files
+ *
+ *<p>
+ * To obtain the media handle (#media_info_h), call the #media_info_create() function.\n
+ * To start face detection, call the #media_info_start_face_detection() function.\n
+ * To cancel face detection after it's been started, call the #media_info_cancel_face_detection() function.\n
+ *
+ */
/**
* @defgroup CAPI_CONTENT_MEDIA_BOOKMARK_MODULE Media Bookmark
MEDIA_CONTENT_ERROR_DB_BUSY = MEDIA_CONTENT_ERROR_CLASS | 0x02, /**< DB operation BUSY */
MEDIA_CONTENT_ERROR_NETWORK = MEDIA_CONTENT_ERROR_CLASS | 0x03, /**< Network Fail */
MEDIA_CONTENT_ERROR_UNSUPPORTED_CONTENT = MEDIA_CONTENT_ERROR_CLASS | 0x04, /**< Unsupported Content */
+ MEDIA_CONTENT_ERROR_NOT_SUPPORTED = TIZEN_ERROR_NOT_SUPPORTED, /**< Not supported */
} media_content_error_e;
/**
*/
typedef void (*media_thumbnail_completed_cb)(media_content_error_e error, const char *path, void *user_data);
+/**
+ * @ingroup CAPI_CONTENT_MEDIA_FACE_DETECTION_MODULE
+ * @brief Called when face detection on the image is completed.
+ *
+ * @details The following error codes can be delivered. \n
+ * #MEDIA_CONTENT_ERROR_NONE, \n
+ * #MEDIA_CONTENT_ERROR_OUT_OF_MEMORY, \n
+ * #MEDIA_CONTENT_ERROR_INVALID_OPERATION, \n
+ * #MEDIA_CONTENT_ERROR_DB_FAILED, \n
+ * #MEDIA_CONTENT_ERROR_DB_BUSY, \n
+ * #MEDIA_CONTENT_ERROR_UNSUPPORTED_CONTENT
+ *
+ * @since_tizen 3.0
+ *
+ * @remarks The callback is called in a separate thread(not in the main loop).
+ *
+ * @param[in] error The error code
+ * @param[in] face_count The number of all detected faces
+ * @param[in] user_data The user data passed from the foreach function
+ *
+ * @pre media_info_start_face_detection()
+ *
+ * @see media_info_start_face_detection()
+ */
+typedef void (*media_face_detection_completed_cb)(media_content_error_e error, const int face_count, void *user_data);
+
/**
* @ingroup CAPI_CONTENT_MEDIA_FOLDER_MODULE
* @privlevel public
* @privilege %http://tizen.org/privilege/content.write
*
- * @remarks If you want to destory media handle before callback invoked, you must cancel thumbnail request by using media_info_cancel_thumbnail() \n
+ * @remarks If you want to destroy media handle before callback invoked, you must cancel thumbnail request by using media_info_cancel_thumbnail() \n
* Since 3.0, if creation of a thumbnail is failed, empty string will be passed through media_thumbnail_completed_cb().
* Items in external storage except MMC not supported.
*
int media_info_cancel_thumbnail(media_info_h media);
/**
+ * @ingroup CAPI_CONTENT_MEDIA_FACE_DETECTION_MODULE
+ * @brief Starts face detection for the given image, asynchronously.
+ * @details This function detects faces for given image item and calls the given callback function when the detection is completed. \n
+ * The given callback function is called when the detection is completed. \n
+ * To obtain the detected faces, call the media_info_foreach_face_from_db() function.
+ *
+ * @since_tizen 3.0
+ *
+ * @privlevel public
+ * @privilege %http://tizen.org/privilege/content.write \n
+ * %http://tizen.org/privilege/mediastorage
+ *
+ * @remarks If you want to destroy the media handle before callback invoked, you must cancel the face detection request by using media_info_cancel_face_detection(). \n
+ * If face detection fails, the @a face_count argument in media_face_detection_completed_cb() will be set to 0.
+ * Media items in external storage are not supported, with the exception of MMC items.
+ *
+ * @param[in] media The media info handle
+ * @param[in] callback The callback function to be invoked when detection is completed
+ * @param[in] user_data The user data to be passed to the callback function
+ *
+ * @return @c 0 on success,
+ * otherwise a negative error value
+ *
+ * @retval #MEDIA_CONTENT_ERROR_NONE Successful
+ * @retval #MEDIA_CONTENT_ERROR_INVALID_PARAMETER Invalid parameter
+ * @retval #MEDIA_CONTENT_ERROR_OUT_OF_MEMORY Out of memory
+ * @retval #MEDIA_CONTENT_ERROR_INVALID_OPERATION Invalid operation
+ * @retval #MEDIA_CONTENT_ERROR_DB_FAILED DB Operation failed
+ * @retval #MEDIA_CONTENT_ERROR_DB_BUSY DB Operation busy
+ * @retval #MEDIA_CONTENT_ERROR_NETWORK Network fail
+ * @retval #MEDIA_CONTENT_ERROR_PERMISSION_DENIED Permission denied
+ * @retval #MEDIA_CONTENT_ERROR_NOT_SUPPORTED Not supported
+ *
+ * @pre This function requires opened connection to content service by media_content_connect().
+ *
+ * @see media_content_connect()
+ * @see media_info_cancel_face_detection()
+ */
+int media_info_start_face_detection(media_info_h media, media_face_detection_completed_cb callback, void *user_data);
+
+/**
+ * @ingroup CAPI_CONTENT_MEDIA_FACE_DETECTION_MODULE
+ * @brief Cancels face detection of image for the given media.
+ * @details This function cancels face detection for given media item. \n
+ * If you cancel face detection request before callback is invoked, the callback registered by media_info_start_face_detection() API will not be invoked.
+ *
+ * @since_tizen 3.0
+ *
+ * @privlevel public
+ * @privilege %http://tizen.org/privilege/content.write
+ *
+ * @remarks If face detection is already done when you request the cancellation, this API return MEDIA_CONTENT_ERROR_INVALID_OPERATION
+ *
+ * @param[in] media The media info handle
+ *
+ * @return @c 0 on success,
+ * otherwise a negative error value
+ *
+ * @retval #MEDIA_CONTENT_ERROR_NONE Successful
+ * @retval #MEDIA_CONTENT_ERROR_INVALID_PARAMETER Invalid parameter
+ * @retval #MEDIA_CONTENT_ERROR_PERMISSION_DENIED Permission denied
+ * @retval #MEDIA_CONTENT_ERROR_INVALID_OPERATION Invalid operation
+ *
+ * @pre This function requires opened connection to content service by media_content_connect().
+ *
+ * @see media_content_connect()
+ * @see media_info_start_face_detection()
+ */
+int media_info_cancel_face_detection(media_info_h media);
+
+/**
* @brief Creates the media info handle.
* @details If the information about the file that is already known, you can use this API to generate empty handler.
* And you can add the information to the generated handler using media_info_set_XXX() API.
char *storage_uuid;
int sync_status;
unsigned int request_id;
+ unsigned int face_request_id;
int is_360;
image_meta_s *image_meta;
video_meta_s *video_meta;
} media_thumbnail_cb_s;
typedef struct {
+ media_info_s *handle;
+ void *user_data;
+ media_face_detection_completed_cb face_completed_cb;
+} media_face_cb_s;
+
+typedef struct {
media_insert_completed_cb insert_completed_cb;
char *insert_list_path;
void *user_data;
#define SELECT_MEDIA_COUNT_FROM_MEDIA_BY_ID "SELECT COUNT(*) FROM "DB_TABLE_MEDIA_VIEW" WHERE media_uuid='%q' AND validity=1"
#define SELECT_FACE_COUNT_BY_MEDIA_ID "SELECT COUNT(*) FROM "FACE_MEDIA_JOIN" AND fa.media_uuid='%s'"
#define SELECT_FACE_LIST_BY_MEDIA_ID "SELECT fa.face_uuid, fa.media_uuid, fa.face_rect_x, fa.face_rect_y, fa.face_rect_w, fa.face_rect_h, fa.orientation, fa.face_tag FROM "FACE_MEDIA_JOIN" AND fa.media_uuid='%s'"
+#define SELECT_FACE_PATH_FROM_MEDIA "SELECT path FROM "DB_TABLE_MEDIA_VIEW" media_uuid='%s'"
#define DEFAULT_MEDIA_STORAGE_ID "media"
Name: capi-content-media-content
Summary: A Media content library in Tizen Native API
-Version: 0.2.79
+Version: 0.2.80
Release: 0
Group: Multimedia/API
License: Apache-2.0
BuildRequires: cmake
BuildRequires: pkgconfig(dlog)
BuildRequires: pkgconfig(capi-base-common)
+BuildRequires: pkgconfig(capi-system-info)
BuildRequires: pkgconfig(libmedia-service)
BuildRequires: pkgconfig(media-thumbnail)
BuildRequires: pkgconfig(libmedia-utils)
%{_libdir}/libcapi-content-media-content.so.*
#License
%{_datadir}/license/%{name}
+%{_bindir}/*
%files devel
%manifest %{name}.manifest
#include <media_info.h>
#include <media-thumbnail.h>
+#include <media-util-dcm.h>
#include <media_info_private.h>
#include <media_util_private.h>
+#include <system_info.h>
static void __media_info_insert_completed_cb(media_request_result_s *result, void *user_data);
static void __media_info_thumbnail_completed_cb(int error, const char *path, void *user_data);
+static void __media_info_face_completed_cb(int error, const int face_count, void *user_data);
static bool __media_info_delete_batch_cb(media_info_h media, void *user_data);
static int __media_info_insert_batch(media_batch_insert_e insert_type, const char **path_array, unsigned int array_length, media_insert_completed_cb completed_cb, void *user_data);
return;
}
+static bool __media_info_isFaceRecognition_feature_supported()
+{
+ bool isFaceRecognitionSupported = false;
+
+ const int nRetVal = system_info_get_platform_bool("http://tizen.org/feature/vision.face_recognition", &isFaceRecognitionSupported);
+
+ if (nRetVal != SYSTEM_INFO_ERROR_NONE) {
+ media_content_debug("SYSTEM_INFO_ERROR: vision.face_recognition [%d]", nRetVal);
+ return false;
+ }
+
+ return isFaceRecognitionSupported;
+}
+
+static void __media_info_face_completed_cb(int error, const int face_count, void *user_data)
+{
+ int error_value = MEDIA_CONTENT_ERROR_NONE;
+
+ media_face_cb_s *_face_cb = (media_face_cb_s *)user_data;
+
+ if (_face_cb != NULL) {
+ media_content_debug("error [%d], face_count [%d]", error, face_count);
+ error_value = _content_error_capi(MEDIA_THUMBNAIL_TYPE, error);
+ if (_face_cb->face_completed_cb)
+ _face_cb->face_completed_cb(error_value, face_count, _face_cb->user_data);
+ }
+
+ SAFE_FREE(_face_cb);
+
+ return;
+}
+
static bool __media_info_delete_batch_cb(media_info_h media, void *user_data)
{
int err = MEDIA_CONTENT_ERROR_NONE;
_dst->played_position = _src->played_position;
_dst->sync_status = _src->sync_status;
_dst->request_id = _src->request_id;
+ _dst->face_request_id = _src->face_request_id;
_dst->is_360 = _src->is_360;
if (_src->media_type == MEDIA_CONTENT_TYPE_IMAGE && _src->image_meta) {
return ret;
}
+int media_info_start_face_detection(media_info_h media, media_face_detection_completed_cb callback, void *user_data)
+{
+ int ret = MEDIA_CONTENT_ERROR_NONE;
+ static unsigned int req_id = 0;
+ media_info_s *_media = (media_info_s*)media;
+
+ if (!__media_info_isFaceRecognition_feature_supported()) {
+ media_content_error("NOT_SUPPORTED(0x%08x)", MEDIA_CONTENT_ERROR_NOT_SUPPORTED);
+ return MEDIA_CONTENT_ERROR_NOT_SUPPORTED;
+ }
+
+ if (_media != NULL && STRING_VALID(_media->media_id) && STRING_VALID(_media->file_path)) {
+ media_face_cb_s *_face_cb = (media_face_cb_s*)calloc(1, sizeof(media_face_cb_s));
+ media_content_retvm_if(_face_cb == NULL, MEDIA_CONTENT_ERROR_OUT_OF_MEMORY, "OUT_OF_MEMORY");
+ req_id++;
+ _media->face_request_id = req_id;
+
+ _face_cb->handle = _media;
+ _face_cb->user_data = user_data;
+ _face_cb->face_completed_cb = callback;
+
+ ret = dcm_request_extract_face_async(_media->face_request_id, _media->file_path, (FaceFunc)__media_info_face_completed_cb, (void *)_face_cb, tzplatform_getuid(TZ_USER_NAME));
+ ret = _content_error_capi(MEDIA_THUMBNAIL_TYPE, ret);
+ } else {
+ media_content_error("INVALID_PARAMETER(0x%08x)", MEDIA_CONTENT_ERROR_INVALID_PARAMETER);
+ ret = MEDIA_CONTENT_ERROR_INVALID_PARAMETER;
+ }
+
+ return ret;
+}
+
+int media_info_cancel_face_detection(media_info_h media)
+{
+ int ret = MEDIA_CONTENT_ERROR_NONE;
+ media_info_s *_media = (media_info_s*)media;
+
+ if (!__media_info_isFaceRecognition_feature_supported()) {
+ media_content_error("NOT_SUPPORTED(0x%08x)", MEDIA_CONTENT_ERROR_NOT_SUPPORTED);
+ return MEDIA_CONTENT_ERROR_NOT_SUPPORTED;
+ }
+
+ if (_media != NULL && STRING_VALID(_media->media_id) && STRING_VALID(_media->file_path) && _media->face_request_id > 0) {
+ ret = dcm_request_cancel_face(_media->face_request_id, _media->file_path);
+ ret = _content_error_capi(MEDIA_THUMBNAIL_TYPE, ret);
+ } else {
+ media_content_error("INVALID_PARAMETER(0x%08x)", MEDIA_CONTENT_ERROR_INVALID_PARAMETER);
+ ret = MEDIA_CONTENT_ERROR_INVALID_PARAMETER;
+ }
+
+ return ret;
+}
+
static int __media_info_map_data_usr_to_svc(media_info_s *media, media_svc_content_info_s **service_content, media_content_storage_e storage_type)
{
media_content_retvm_if(media == NULL, MEDIA_CONTENT_ERROR_INVALID_PARAMETER, "Invalid handle");
FOREACH(src ${sources})
GET_FILENAME_COMPONENT(src_name ${src} NAME_WE)
MESSAGE("${src_name}")
- ADD_EXECUTABLE(${src_name} ${src})
- TARGET_LINK_LIBRARIES(${src_name} ${fw_name} ${${fw_test}_LDFLAGS})
+ ADD_EXECUTABLE(${fw_test} ${src})
+ TARGET_LINK_LIBRARIES(${fw_test} ${fw_name} ${${fw_test}_LDFLAGS})
ENDFOREACH()
+
+INSTALL(TARGETS ${fw_test} DESTINATION bin)
int ret = MEDIA_CONTENT_ERROR_NONE;
/* Filter for media */
- const char *condition = "MEDIA_TYPE=3"; /*MEDIA_TYPE 0-image, 1-video, 2-sound, 3-music, 4-other*/
+ const char *condition = "MEDIA_TYPE=0"; /*MEDIA_TYPE 0-image, 1-video, 2-sound, 3-music, 4-other*/
/*const char *condition = "MEDIA_TYPE IS NOT 0 AND MEDIA_DESCRIPTION IS NOT NULL"; */ /*MEDIA_TYPE 0-image, 1-video, 2-sound, 3-music, 4-other*/
ret = media_filter_create(&g_filter);
return ret;
}
+bool face_cb(media_face_h face, void *user_data)
+{
+ if (user_data != NULL) {
+ unsigned x, y, rect_w, rect_h;
+ media_face_get_face_rect(face, &x, &y, &rect_w, &rect_h);
+ media_content_debug("face(%p) x = %d, y = %d [%d, %d]", face, x, y, rect_w, rect_h);
+ return TRUE;
+ }
+ return FALSE;
+}
+
+void face_detection_complete_cb(media_content_error_e error, int count, void *user_data)
+{
+ int ret = MEDIA_CONTENT_ERROR_NONE;
+ g_cnt++;
+
+ media_content_debug("=================[%d][%d]", g_media_cnt, g_cnt);
+ media_content_debug("error_code [%d]", error);
+ media_content_debug("face_count [%d]", count);
+ if (count == 0) {
+ media_content_debug("No faces are detected!");
+ } else if (user_data != NULL) {
+ media_info_h media = (media_info_h)user_data;
+ char *media_id = NULL;
+ ret = media_info_get_media_id(media, &media_id);
+ if (ret != MEDIA_CONTENT_ERROR_NONE)
+ media_content_error("media_info_get_media_id failed: %d", ret);
+ if (media_id != NULL) {
+ ret = media_info_foreach_face_from_db(media_id, NULL, face_cb, NULL);
+ if (ret != MEDIA_CONTENT_ERROR_NONE)
+ media_content_error("media_info_foreach_face_from_db failed: %d", ret);
+ }
+ ret = media_info_destroy(media);
+ if (ret != MEDIA_CONTENT_ERROR_NONE)
+ media_content_error("media_info_destroy failed: %d", ret);
+ }
+
+ if (g_cnt == g_media_cnt)
+ g_main_loop_quit(g_loop);
+
+ return;
+}
+
+bool start_face_detection_cb(media_info_h media, void *user_data)
+{
+ char *media_id = NULL;
+ media_info_h dst = NULL;
+ int ret = MEDIA_CONTENT_ERROR_NONE;
+
+ if (media == NULL) {
+ media_content_debug("NO Item");
+ return true;
+ }
+
+ ret = media_info_get_media_id(media, &media_id);
+ if (ret != MEDIA_CONTENT_ERROR_NONE)
+ media_content_error("media_info_get_media_id failed: %d", ret);
+ else
+ media_content_debug("media_id : [%s]", media_id);
+
+ ret = media_info_clone(&dst, media);
+ if (ret != MEDIA_CONTENT_ERROR_NONE)
+ media_content_error("media_info_clone failed: %d", ret);
+ else {
+ ret = media_info_start_face_detection(dst, face_detection_complete_cb, dst);
+ if (ret != MEDIA_CONTENT_ERROR_NONE)
+ media_content_error("media_info_start_face_detection failed: %d", ret);
+ }
+
+ /* fix prevent: Resource leak */
+ SAFE_FREE(media_id);
+
+ return true;
+}
+
+bool cancel_face_detection_cb(media_info_h media, void *user_data)
+{
+ int ret = MEDIA_CONTENT_ERROR_NONE;
+
+ char *media_id = NULL;
+ media_info_h dst = NULL;
+
+ g_cnt++;
+
+ if (media == NULL) {
+ media_content_debug("NO Item");
+ return true;
+ }
+
+ ret = media_info_get_media_id(media, &media_id);
+ if (ret != MEDIA_CONTENT_ERROR_NONE)
+ media_content_error("media_info_get_media_id failed: %d", ret);
+ else
+ media_content_debug("media_id : [%s]", media_id);
+
+ ret = media_info_clone(&dst, media);
+ if (ret != MEDIA_CONTENT_ERROR_NONE)
+ media_content_error("media_info_clone failed: %d", ret);
+
+ ret = media_info_cancel_face_detection(dst);
+ if (ret != MEDIA_CONTENT_ERROR_NONE)
+ media_content_error("media_info_cancel_face_detection failed: %d", ret);
+
+ ret = media_info_destroy(dst);
+ if (ret != MEDIA_CONTENT_ERROR_NONE)
+ media_content_error("media_info_destroy failed: %d", ret);
+
+ if (g_cnt == g_media_cnt)
+ g_main_loop_quit(g_loop);
+
+ /* fix prevent: Resource leak */
+ SAFE_FREE(media_id);
+
+ return true;
+}
+
+gboolean face_detection_start(gpointer data)
+{
+ int ret = MEDIA_CONTENT_ERROR_NONE;
+
+ ret = media_info_foreach_media_from_db(g_filter, start_face_detection_cb, NULL);
+
+ if (ret == MEDIA_CONTENT_ERROR_NONE)
+ media_content_debug("media_info_foreach_media_from_db is success");
+ else
+ media_content_error("media_info_foreach_media_from_db is failed");
+
+ return false;
+}
+
+gboolean face_detection_cancel(gpointer data)
+{
+ int ret = MEDIA_CONTENT_ERROR_NONE;
+
+ ret = media_info_foreach_media_from_db(g_filter, cancel_face_detection_cb, NULL);
+
+ if (ret == MEDIA_CONTENT_ERROR_NONE)
+ media_content_debug("media_info_foreach_media_from_db is success");
+ else
+ media_content_error("media_info_foreach_media_from_db is failed");
+
+ return false;
+}
+
+int test_start_face_detection(int cancel)
+{
+ int ret = MEDIA_CONTENT_ERROR_NONE;
+ GSource *source = NULL;
+ GMainContext *context = NULL;
+
+ test_filter_create();
+
+ ret = media_info_get_media_count_from_db(g_filter, &g_media_cnt);
+ if (ret != MEDIA_CONTENT_ERROR_NONE)
+ media_content_error("media_info_get_media_count_from_db failed: %d", ret);
+ else
+ media_content_debug("media_count : [%d]", g_media_cnt);
+
+ if (g_media_cnt == 0) {
+ goto END;
+ }
+ g_loop = g_main_loop_new(NULL, FALSE);
+ context = g_main_loop_get_context(g_loop);
+ source = g_idle_source_new();
+ g_source_set_callback(source, face_detection_start, NULL, NULL);
+ g_source_attach(source, context);
+
+ /* Logic to cancel */
+ if (cancel) {
+ GSource *cancel_src = NULL;
+ cancel_src = g_idle_source_new();
+ g_source_set_callback(cancel_src, face_detection_cancel, NULL, NULL);
+ g_source_attach(cancel_src, context);
+ }
+
+ g_main_loop_run(g_loop);
+ g_main_loop_unref(g_loop);
+
+END:
+ test_filter_destroy();
+
+ return ret;
+}
+
int test_disconnect_database(void)
{
int ret = MEDIA_CONTENT_ERROR_NONE;
if (ret != MEDIA_CONTENT_ERROR_NONE)
return MEDIA_CONTENT_ERROR_NONE;
+ ret = test_start_face_detection(FALSE);
+ if (ret != MEDIA_CONTENT_ERROR_NONE)
+ return ret;
+
#if 0
ret = test_move();
if (ret != MEDIA_CONTENT_ERROR_NONE)
if (ret != MEDIA_CONTENT_ERROR_NONE)
return ret;
+ ret = test_extrace_face(TRUE);
+ if (ret != MEDIA_CONTENT_ERROR_NONE)
+ return ret;
+
ret = test_request_update_db();
if (ret != MEDIA_CONTENT_ERROR_NONE)
return ret;