halapi: common: Add debug log for init/exit/dlopen/dlclose 66/316666/1 accepted/tizen_8.0_unified tizen_8.0 accepted/tizen/8.0/unified/20241217.171850
authorChanwoo Choi <cw00.choi@samsung.com>
Mon, 16 Dec 2024 10:12:02 +0000 (19:12 +0900)
committerChanwoo Choi <cw00.choi@samsung.com>
Mon, 16 Dec 2024 10:13:29 +0000 (19:13 +0900)
Add debug log for each init/exit/dlopen/dlclose step to catch the
latency issue.

[Details description of newly added log]
(snip) __get_backend(361) > HAL_MODULE_TBM: Prepare to open HAL backend: (snip)
-> Execute dlopen() and dlsym()
(snip) __get_backend(369) > HAL_MODULE_TBM: Open and Prepare to get HAL backend: (snip)
-> Execute 'init' function on hal-backend
(snip) __get_backend(384) > HAL_MODULE_TBM: Get HAL backend: (snip)

(snip) __put_backend(435) > HAL_MODULE_TBM: Prepare to exit HAL backend: (snip)
-> Execute 'exit' function on hal-backend
(snip) __put_backend(450) > HAL_MODULE_TBM: Exit and prepare to put HAL backend: (snip)
-> Execute dlclose()
(snip) __put_backend(462) > HAL_MODULE_TBM: Put HAL backend: (snip)

Change-Id: I82be532584dffb90095fcaa809050a7f7ed25c48
Signed-off-by: Chanwoo Choi <cw00.choi@samsung.com>
src/hal-api-common.c
src/hal-api-common.c.orig [new file with mode: 0644]
src/hal-api-common.c.rej [new file with mode: 0644]

index 3520a5892fc728f48b057d61b0427a33a6202172..88cb7ef60734090c6148236531e93aa9b02b6923 100644 (file)
@@ -202,11 +202,6 @@ static int __open_backend(struct __hal_module_info *info)
                goto err_dlclose;
        }
 
-       _I("%s: Open HAL backend: name(%s)/vendor(%s)/library(%s)/count(%d) by %s\n",
-               info->module_name, info->backend->name, info->backend->vendor,
-               backend_library_name, info->usage_count,
-               program_invocation_name);
-
        return 0;
 
 err_dlclose:
@@ -223,11 +218,6 @@ static void __close_backend(struct __hal_module_info *info)
        if (!info->backend || !info->handle)
                return;
 
-       _I("%s: Close HAL backend: name(%s)/vendor(%s)/library(%s)/count(%d) by %s\n",
-               info->module_name, info->backend->name, info->backend->vendor,
-               get_backend_library_name(info), info->usage_count,
-               program_invocation_name);
-
        if (info->handle)
                dlclose(info->handle);
 
@@ -322,10 +312,19 @@ static int __get_backend(enum hal_module module, void **data,
                goto err;
        }
 
+       _I("%s: Prepare to open HAL backend: library(%s)/count(%d) by %s\n",
+               info->module_name, get_backend_library_name(info), info->usage_count,
+               program_invocation_name);
+
        ret = __open_backend(info);
        if (ret < 0)
                goto err;
 
+       _I("%s: Open and Prepare to get HAL backend: name(%s)/vendor(%s)/library(%s)/count(%d) by %s\n",
+               info->module_name, info->backend->name, info->backend->vendor,
+               get_backend_library_name(info), info->usage_count,
+               program_invocation_name);
+
        ret = __init_backend(info, data, NULL);
        if (ret < 0) {
                _E("%s: Failed to initialize the backend library\n",
@@ -385,6 +384,11 @@ static int __put_backend(enum hal_module module, void *data,
                goto out;
        }
 
+       _I("%s: Prepare to exit HAL backend: name(%s)/vendor(%s)/library(%s)/count(%d) by %s\n",
+               info->module_name, info->backend->name, info->backend->vendor,
+               get_backend_library_name(info), info->usage_count,
+               program_invocation_name);
+
        ret = __exit_backend(info, data, NULL);
        if (ret < 0) {
                _E("%s: Failed to exit the backend library\n",
@@ -395,7 +399,7 @@ static int __put_backend(enum hal_module module, void *data,
 
        info->usage_count--;
 
-       _I("%s: Put HAL backend: name(%s)/vendor(%s)/library(%s)/count(%d) by %s\n",
+       _I("%s: Exit and Prepare to put HAL backend: name(%s)/vendor(%s)/library(%s)/count(%d) by %s\n",
                info->module_name, info->backend->name, info->backend->vendor,
                get_backend_library_name(info), info->usage_count,
                program_invocation_name);
@@ -406,12 +410,18 @@ static int __put_backend(enum hal_module module, void *data,
        }
 
        __close_backend(info);
+
+       _I("%s: Put HAL backend: library(%s)/count(%d) by %s\n",
+               info->module_name, get_backend_library_name(info), info->usage_count,
+               program_invocation_name);
+
        _hal_api_conf_exit();
 
        ret = 0;
 
 out:
        G_UNLOCK(hal_common_lock);
+
        return ret;
 }
 
diff --git a/src/hal-api-common.c.orig b/src/hal-api-common.c.orig
new file mode 100644 (file)
index 0000000..3520a58
--- /dev/null
@@ -0,0 +1,746 @@
+/*
+ * HAL Common API
+ *
+ * Copyright (c) 2020 Samsung Electronics Co., Ltd.
+ *
+ * Licensed under the Apache License, Version 2.0 (the License);
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *     http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#include <stdio.h>
+#include <stdint.h>
+#include <unistd.h>
+#include <stdbool.h>
+#include <dlfcn.h>
+#include <dirent.h>
+
+#define _GNU_SOURCE
+#include <errno.h>
+
+#include <glib-object.h>
+
+#include "common.h"
+#include "hal-api-conf.h"
+
+extern char *program_invocation_name;
+
+#ifndef EXPORT
+#define EXPORT __attribute__ ((visibility("default")))
+#endif
+
+#define HAL_BACKEND_SYMBOL_NAME                1
+#define HAL_BACKEND_MODULE_NAME                2
+
+static enum hal_abi_version g_platform_curr_abi_version;
+G_LOCK_DEFINE_STATIC(hal_common_lock);
+
+EXPORT
+int hal_common_get_backend_library_name(enum hal_module module, char *name, int size)
+{
+       const char *library_name = NULL;
+       struct __hal_module_info *info = NULL;
+       int ret;
+       int len_library_name;
+
+       /* Check parameter whether is valid or not */
+       if (module <= HAL_MODULE_UNKNOWN || module >= HAL_MODULE_END) {
+               _E("Invalid parameter of HAL module (%d)\n", module);
+               return -EINVAL;
+       }
+
+       if (_hal_api_conf_init())
+               return -EINVAL;
+
+       info = _hal_api_conf_get_module_info(module, NULL);
+       if (info == NULL) {
+               _E("Failed to get HAL module(%d) information\n", module);
+               ret = -EINVAL;
+               goto out;
+       }
+
+       library_name = get_backend_library_name(info);
+       if (!library_name) {
+               _E("%s backend library name is NULL\n", info->module_name);
+               ret = 0;
+               goto out;
+       }
+
+       len_library_name = strlen(library_name);
+       if (!name || (len_library_name + 1 > size) || len_library_name == 0) {
+               ret = -EINVAL;
+               name = NULL;
+               goto out;
+       }
+       strncpy(name, library_name, len_library_name);
+       name[len_library_name] = '\0';
+
+       ret = 0;
+out:
+       _hal_api_conf_exit();
+
+       return ret;
+}
+
+static int __hal_common_get_backend_name(enum hal_module module, char *name, int size, int name_type)
+{
+       struct __hal_module_info *info = NULL;
+       char *str = NULL;
+       int ret;
+       int len_str;
+
+       /* Check parameter whether is valid or not */
+       if (module <= HAL_MODULE_UNKNOWN || module >= HAL_MODULE_END) {
+               _E("Invalid paramer of HAL module (%d)\n", module);
+               return -EINVAL;
+       }
+
+       if (_hal_api_conf_init())
+               return -EINVAL;
+
+       info = _hal_api_conf_get_module_info(module, NULL);
+       if (info == NULL) {
+               _E("Failed to get HAL module(%d) information\n", module);
+               ret = -EINVAL;
+               goto out;
+       }
+
+       switch (name_type) {
+       case HAL_BACKEND_SYMBOL_NAME:
+               str = info->symbol_name;
+               break;
+       case HAL_BACKEND_MODULE_NAME:
+               str = info->module_name;
+               break;
+       default:
+               break;
+       }
+
+       if (!str) {
+               _I("%s backend name is NULL\n", info->module_name);
+               ret = 0;
+               goto out;
+       }
+
+       len_str = strlen(str);
+       if (!str || (len_str + 1 > size) || len_str == 0) {
+               ret = -EINVAL;
+               str = NULL;
+               goto out;
+       }
+       strncpy(name, str, len_str);
+       name[len_str] = '\0';
+
+       ret = 0;
+out:
+       _hal_api_conf_exit();
+
+       return ret;
+}
+
+EXPORT
+int hal_common_get_backend_symbol_name(enum hal_module module, char *name, int size)
+{
+       return __hal_common_get_backend_name(module, name, size, HAL_BACKEND_SYMBOL_NAME);
+}
+
+EXPORT
+int hal_common_get_backend_module_name(enum hal_module module, char *name, int size)
+{
+       return __hal_common_get_backend_name(module, name, size, HAL_BACKEND_MODULE_NAME);
+}
+
+static int __open_backend(struct __hal_module_info *info)
+{
+       const char *backend_library_name = NULL;
+       int ret;
+
+       if (info->backend && info->handle)
+               return 0;
+
+       backend_library_name = get_backend_library_name(info);
+       if (!backend_library_name) {
+               _E("%s: Failed to get backend library name\n",
+                               info->module_name);
+               ret = -EINVAL;
+               goto err;
+       } else if (access(backend_library_name, F_OK) == -1) {
+               _I("%s: There is no backend library\n",
+                               info->module_name);
+               ret = -ENOENT;
+               goto err;
+       }
+
+       if (!info->symbol_name) {
+               _E("%s: Failed to get backend symbol name\n",
+                               info->module_name);
+               ret = -EINVAL;
+               goto err;
+       }
+
+       info->handle = dlopen(backend_library_name, RTLD_LAZY);
+       if (!info->handle) {
+               _E("%s: Failed to load backend library (%s)\n",
+                               info->module_name, dlerror());
+               ret = -EINVAL;
+               goto err;
+       }
+
+       info->backend = dlsym(info->handle, info->symbol_name);
+       if (!info->backend) {
+               _E("%s: Failed to find backend data (%s)\n",
+                               info->module_name, dlerror());
+               ret = -EINVAL;
+               goto err_dlclose;
+       }
+
+       _I("%s: Open HAL backend: name(%s)/vendor(%s)/library(%s)/count(%d) by %s\n",
+               info->module_name, info->backend->name, info->backend->vendor,
+               backend_library_name, info->usage_count,
+               program_invocation_name);
+
+       return 0;
+
+err_dlclose:
+       dlclose(info->handle);
+err:
+       info->backend = NULL;
+       info->handle = NULL;
+
+       return ret;
+}
+
+static void __close_backend(struct __hal_module_info *info)
+{
+       if (!info->backend || !info->handle)
+               return;
+
+       _I("%s: Close HAL backend: name(%s)/vendor(%s)/library(%s)/count(%d) by %s\n",
+               info->module_name, info->backend->name, info->backend->vendor,
+               get_backend_library_name(info), info->usage_count,
+               program_invocation_name);
+
+       if (info->handle)
+               dlclose(info->handle);
+
+       info->backend = NULL;
+       info->handle = NULL;
+}
+
+static int __init_backend(struct __hal_module_info *info, void **data,
+                               const char *library_name)
+{
+       int ret;
+
+       if (!info->handle || !info->backend) {
+               _I("%s: Has not yet dlopend backend\n", info->module_name);
+               return 0;
+       }
+
+       if (!info->backend->init) {
+               _E("%s: hal_backend->init() is NULL\n", info->module_name);
+               return -EINVAL;
+       }
+
+       /* Check HAL ABI Version */
+       ret = hal_common_check_backend_abi_version(info->module,
+                                               info->backend->abi_version);
+       if (ret < 0) {
+               _E("%s: Failed to check ABI version\n", info->module_name);
+               return -EINVAL;
+       }
+
+       /* Initialize backend */
+       ret = info->backend->init(data);
+       if (ret < 0) {
+               _E("%s: Failed to initialize backend: name(%s)/vendor(%s)\n",
+                       info->module_name, info->backend->name,
+                       info->backend->vendor);
+               return -EINVAL;
+       }
+
+       return 0;
+}
+
+static int __exit_backend(struct __hal_module_info *info, void *data,
+                               const char *library_name)
+{
+       int ret;
+
+       if (!info->handle || !info->backend) {
+               _I("%s: Has not yet dlopend backend\n", info->module_name);
+               return 0;
+       }
+
+       /* Exit backend */
+       if (info->backend->exit) {
+               ret = info->backend->exit(data);
+               if (ret < 0) {
+                       _E("%s: Failed to exit backend: name(%s)/vendor(%s)\n",
+                               info->module_name, info->backend->name,
+                               info->backend->vendor);
+                       return -EINVAL;
+               }
+       }
+
+       return 0;
+}
+
+static int __get_backend(enum hal_module module, void **data,
+                               const char *library_name)
+{
+       struct __hal_module_info *info = NULL;
+       int ret;
+
+       if (module <= HAL_MODULE_UNKNOWN || module >= HAL_MODULE_END) {
+               _E("Invalid parameter of HAL module (%d)\n", module);
+               return -EINVAL;
+       }
+
+       G_LOCK(hal_common_lock);
+       if (_hal_api_conf_init()) {
+               ret = -EINVAL;
+               goto err;
+       }
+
+       info = _hal_api_conf_get_module_info(module, library_name);
+       if (info == NULL) {
+               if (!library_name)
+                       _E("Failed to get HAL module(%d) information\n", module);
+               else
+                       _E("Failed to get HAL module(%d) information (%s)\n",
+                               module, library_name);
+               ret = -EINVAL;
+               goto err;
+       }
+
+       ret = __open_backend(info);
+       if (ret < 0)
+               goto err;
+
+       ret = __init_backend(info, data, NULL);
+       if (ret < 0) {
+               _E("%s: Failed to initialize the backend library\n",
+                               info->module_name);
+               ret = -EINVAL;
+               goto err_dlclose;
+       }
+
+       info->usage_count++;
+
+       _I("%s: Get HAL backend: name(%s)/vendor(%s)/library(%s)/count(%d) by %s\n",
+               info->module_name, info->backend->name, info->backend->vendor,
+               get_backend_library_name(info), info->usage_count,
+               program_invocation_name);
+
+       G_UNLOCK(hal_common_lock);
+       return 0;
+
+err_dlclose:
+       __close_backend(info);
+       _hal_api_conf_exit();
+err:
+       G_UNLOCK(hal_common_lock);
+       return ret;
+}
+
+static int __put_backend(enum hal_module module, void *data,
+                               const char *library_name)
+{
+       struct __hal_module_info *info = NULL;
+       int ret;
+
+       /* Check parameter whether is valid or not */
+       if (module <= HAL_MODULE_UNKNOWN || module >= HAL_MODULE_END) {
+               _E("Invalid parameter of HAL module (%d)\n", module);
+               return -EINVAL;
+       }
+
+       G_LOCK(hal_common_lock);
+
+       info = _hal_api_conf_get_module_info(module, library_name);
+       if (info == NULL) {
+               _E("Failed to get HAL module(%d) information\n", module);
+               ret =  -EINVAL;
+               goto out;
+       }
+
+       if (!info->handle || !info->backend) {
+               _I("%s: Has not yet dlopend backend\n", info->module_name);
+               ret = 0;
+               goto out;
+       }
+
+       if (!info->usage_count) {
+               _I("%s: Already fully put for HAL module\n", info->module_name);
+               ret =  0;
+               goto out;
+       }
+
+       ret = __exit_backend(info, data, NULL);
+       if (ret < 0) {
+               _E("%s: Failed to exit the backend library\n",
+                               info->module_name);
+               ret = -EINVAL;
+               goto out;
+       }
+
+       info->usage_count--;
+
+       _I("%s: Put HAL backend: name(%s)/vendor(%s)/library(%s)/count(%d) by %s\n",
+               info->module_name, info->backend->name, info->backend->vendor,
+               get_backend_library_name(info), info->usage_count,
+               program_invocation_name);
+
+       if (info->usage_count > 0) {
+               ret = 0;
+               goto out;
+       }
+
+       __close_backend(info);
+       _hal_api_conf_exit();
+
+       ret = 0;
+
+out:
+       G_UNLOCK(hal_common_lock);
+       return ret;
+}
+
+static int __get_backend_data(enum hal_module module, unsigned int *abi_version,
+                       char *name, int name_size, char *vendor, int vendor_size)
+{
+       struct __hal_module_info *info = NULL;
+       int ret, len;
+
+       if (module <= HAL_MODULE_UNKNOWN || module >= HAL_MODULE_END) {
+               _E("Invalid parameter of HAL module (%d)\n", module);
+               return 0;
+       }
+
+       G_LOCK(hal_common_lock);
+
+       if (_hal_api_conf_init()) {
+               ret = HAL_ABI_VERSION_UNKNOWN;
+               goto err_unlock;
+       }
+
+       info = _hal_api_conf_get_module_info(module, NULL);
+       if (info == NULL) {
+               _E("Failed to get HAL module(%d) information\n", module);
+               ret = HAL_ABI_VERSION_UNKNOWN;
+               goto err_conf_exit;
+       }
+
+       ret = __open_backend(info);
+       if (ret < 0)
+               goto err_conf_exit;
+
+       /* Return abi_verion of hal_backend structure */
+       if (!name_size && !vendor_size) {
+               *abi_version = info->backend->abi_version;
+
+       /* Return name of hal_backend structure */
+       } else if (info->backend->name && name_size && !vendor_size) {
+               len = strlen(info->backend->name);
+
+               if (!info->backend->name || (len + 1 > name_size)) {
+                       _E("%s: Invalid size of name[] array\n", info->module_name);
+                       ret = -EINVAL;
+                       goto err_conf_exit;
+               }
+
+               strncpy(name, info->backend->name, len);
+               name[len] = '\0';
+
+       /* Return vendor of hal_backend structure */
+       } else if (info->backend->vendor && !name_size && vendor_size) {
+               len = strlen(info->backend->vendor);
+
+               if (!info->backend->vendor || (len + 1 > vendor_size)) {
+                       _E("%s: Invalid size of vendor[] array\n", info->module_name);
+                       ret = -EINVAL;
+                       goto err_conf_exit;
+               }
+
+               strncpy(vendor, info->backend->vendor, len);
+               vendor[len] = '\0';
+       } else {
+               _E("%s: Failed to get backend data\n", info->module_name);
+               ret = -EINVAL;
+               goto err_conf_exit;
+       }
+       ret = 0;
+
+err_conf_exit:
+       _hal_api_conf_exit();
+err_unlock:
+       G_UNLOCK(hal_common_lock);
+       return ret;
+}
+
+EXPORT
+int hal_common_get_backend(enum hal_module module, void **data)
+{
+       return __get_backend(module, data, NULL);
+}
+
+EXPORT
+int hal_common_put_backend(enum hal_module module, void *data)
+{
+       return __put_backend(module, data, NULL);
+}
+
+EXPORT
+int hal_common_get_backend_with_library_name(enum hal_module module,
+                                       void **data, const char *library_name)
+{
+       return __get_backend(module, data, library_name);
+}
+
+EXPORT
+int hal_common_put_backend_with_library_name(enum hal_module module,
+                                       void *data, const char *library_name)
+{
+       return __put_backend(module, data, library_name);
+}
+
+EXPORT
+int hal_common_check_backend_abi_version(enum hal_module module,
+                               enum hal_abi_version abi_version)
+{
+       struct __hal_module_info *info = NULL;
+       int i;
+       int ret;
+
+       /* Check parameter whether is valid or not */
+       if (module <= HAL_MODULE_UNKNOWN || module >= HAL_MODULE_END) {
+               _E("Invalid paramer of HAL module(%d)\n", module);
+               return -EINVAL;
+       }
+
+       if (abi_version <= HAL_ABI_VERSION_UNKNOWN
+                       || abi_version >= HAL_ABI_VERSION_END) {
+               _E("Invalid paramer of HAL ABI version(%d) for HAL module(%d)\n",
+                               abi_version, module);
+               return -EINVAL;
+       }
+
+       if (_hal_api_conf_init())
+               return -EINVAL;
+
+       info = _hal_api_conf_get_module_info(module, NULL);
+       if (info == NULL) {
+               _E("Failed to get HAL module(%d) information\n", module);
+               ret = -EINVAL;
+               goto out;
+       }
+
+       /* Check abi_version whether is supported or not */
+       if (!info->hal_api) {
+               _E("%s: Doesn't support HAL API\n", info->module_name);
+               ret = -EINVAL;
+               goto out;
+       }
+
+       if (!info->num_abi_versions
+                       || !info->abi_versions) {
+               _E("%s: Doesn't have the ABI version information\n",
+                                               info->module_name);
+               ret = -EINVAL;
+               goto out;
+       }
+
+       g_platform_curr_abi_version = _hal_api_conf_get_platform_abi_version();
+
+       if (g_platform_curr_abi_version <= HAL_ABI_VERSION_UNKNOWN
+                       || g_platform_curr_abi_version >= HAL_ABI_VERSION_END) {
+               _E("Invalid paramer of current HAL ABI version(%d)(%d)\n",
+                               g_platform_curr_abi_version, module);
+               ret = -EINVAL;
+               goto out;
+       }
+
+       for (i = 0; i < info->num_abi_versions; i++) {
+               struct hal_abi_version_match *data
+                               = &info->abi_versions[i];
+
+               if (g_platform_curr_abi_version != data->platform_abi_version)
+                       continue;
+
+               if (data->backend_min_abi_version <= HAL_ABI_VERSION_UNKNOWN ||
+                       data->backend_min_abi_version >= HAL_ABI_VERSION_END) {
+                       _E("%s: abi_versions[%d].backend_min_abi_version(%d) is invalid\n",
+                               info->module_name, i, data->backend_min_abi_version);
+                       ret = -EINVAL;
+                       goto out;
+               }
+
+               if (abi_version <= data->platform_abi_version
+                               && abi_version >= data->backend_min_abi_version) {
+                       ret = 0;
+                       goto out;
+               }
+
+               _E("%s: \'%s\' doesn't support \'%s\'\n",
+                               info->module_name,
+                               hal_abi_version_str[g_platform_curr_abi_version],
+                               hal_abi_version_str[abi_version]);
+               _E("%s: Must use ABI versions from \'%s\' to \'%s\'\n",
+                               info->module_name,
+                               hal_abi_version_str[data->backend_min_abi_version],
+                               hal_abi_version_str[data->platform_abi_version]);
+       }
+       ret = -EINVAL;
+
+out:
+       _hal_api_conf_exit();
+       return ret;
+}
+
+EXPORT
+unsigned int hal_common_get_backend_abi_version(enum hal_module module)
+{
+       unsigned int abi_version;
+       int ret;
+
+       ret = __get_backend_data(module, &abi_version, NULL, 0, NULL, 0);
+       if (ret < 0)
+               return HAL_ABI_VERSION_UNKNOWN;
+
+       return abi_version;
+}
+
+EXPORT
+int hal_common_get_backend_name(enum hal_module module, char *name, int size)
+{
+       return __get_backend_data(module, NULL, name, size, NULL, 0);
+}
+
+EXPORT
+int hal_common_get_backend_vendor(enum hal_module module, char *vendor, int size)
+{
+       return __get_backend_data(module, NULL, NULL, 0, vendor, size);
+}
+
+
+static int __get_backend_library_data(enum hal_module module,
+                                       char **lib_names,
+                                       int lib_count,
+                                       int lib_name_size)
+{
+       struct __hal_module_info *info = NULL;
+       struct dirent *de;
+       DIR *dir;
+       char *backend_module_name = NULL;
+       int count, i, ret, len;
+#if defined(__aarch64__) || defined(__x86_64__) || defined (__riscv)
+       const char hal_backend_path[] = "/hal/lib64";
+#else
+       const char hal_backend_path[] = "/hal/lib";
+#endif
+
+       /* Check parameter whether is valid or not */
+       if (module <= HAL_MODULE_UNKNOWN || module >= HAL_MODULE_END) {
+               _E("Invalid parameter of HAL module (%d)\n", module);
+               return -EINVAL;
+       }
+
+       if (_hal_api_conf_init())
+               return -EINVAL;
+
+       info = _hal_api_conf_get_module_info(module, NULL);
+       if (info == NULL) {
+               _E("Failed to get HAL module(%d) information\n", module);
+               ret = -EINVAL;
+               goto err;
+       }
+
+       if (info->backend_module_name == NULL) {
+               _E("Don't support HAL backend of HAL module(%s)\n",
+                                       info->module_name);
+               ret = -EINVAL;
+               goto err;
+       }
+       backend_module_name = g_strdup_printf("libhal-backend-%s",
+                                       info->backend_module_name);
+       if (!backend_module_name) {
+               _E("Failed to allocate the backend_module_name of HAL module(%s)\n",
+                                       info->module_name);
+               ret = -EINVAL;
+               goto err;
+       }
+
+       /* Find HAL backend libraries */
+       dir = opendir(hal_backend_path);
+       if (!dir) {
+               _E("Failed to find HAL backend path(%s) for HAL module(%s)\n",
+                                       hal_backend_path, info->module_name);
+               ret = -EINVAL;
+               goto err_free_backend_module_name;
+       }
+
+       count = 0;
+       while ((de = readdir(dir)) != NULL) {
+               if (!g_str_has_prefix(de->d_name, backend_module_name))
+                       continue;
+
+               if (lib_count == 0)
+                       count++;
+               else if (lib_count > 0) {
+                       len = strlen(de->d_name) + 1;
+
+                       if (len > lib_name_size)
+                               len = lib_name_size;
+
+                       strncpy(lib_names[count++], de->d_name, len);
+               }
+       }
+
+       if (lib_count > 0 && count != lib_count) {
+               ret = -EINVAL;
+               goto err_mismatch_count;
+       }
+
+       closedir(dir);
+       _hal_api_conf_exit();
+       g_free(backend_module_name);
+
+       return count;
+
+err_mismatch_count:
+       for (i = count - 1; i >= 0; i--)
+               memset(lib_names[i], 0, strlen(lib_names[i]));
+
+       closedir(dir);
+err_free_backend_module_name:
+       g_free(backend_module_name);
+err:
+       _hal_api_conf_exit();
+       return ret;
+}
+
+EXPORT
+int hal_common_get_backend_count(enum hal_module module)
+{
+       return __get_backend_library_data(module, NULL, 0, 0);
+}
+
+EXPORT
+int hal_common_get_backend_library_names(enum hal_module module,
+                                       char **library_names,
+                                       int library_count,
+                                       int library_name_size)
+{
+       int ret = __get_backend_library_data(module, library_names,
+                                       library_count, library_name_size);
+       return (ret < 0) ? ret : 0;
+}
diff --git a/src/hal-api-common.c.rej b/src/hal-api-common.c.rej
new file mode 100644 (file)
index 0000000..ffc40b1
--- /dev/null
@@ -0,0 +1,34 @@
+--- src/hal-api-common.c
++++ src/hal-api-common.c
+@@ -358,10 +348,19 @@ static int __get_backend(enum hal_module module,
+               goto err;
+       }
++      _I("%s: Prepare to open HAL backend: library(%s)/count(%d) by %s\n",
++              info->module_name, get_backend_library_name(info), info->usage_count,
++              program_invocation_name);
++
+       ret = __open_backend(info);
+       if (ret < 0)
+               goto err;
++      _I("%s: Open and Prepare to get HAL backend: name(%s)/vendor(%s)/library(%s)/count(%d) by %s\n",
++              info->module_name, info->backend->name, info->backend->vendor,
++              get_backend_library_name(info), info->usage_count,
++              program_invocation_name);
++
+       ret = __init_backend(info, data, user_data, init_backend);
+       if (ret < 0) {
+               _E("%s: Failed to initialize the backend library\n",
+@@ -423,6 +422,11 @@ static int __put_backend(enum hal_module module,
+               goto out;
+       }
++      _I("%s: Prepare to exit HAL backend: name(%s)/vendor(%s)/library(%s)/count(%d) by %s\n",
++              info->module_name, info->backend->name, info->backend->vendor,
++              get_backend_library_name(info), info->usage_count,
++              program_invocation_name);
++
+       ret = __exit_backend(info, data, user_data, exit_backend);
+       if (ret < 0) {
+               _E("%s: Failed to exit the backend library\n",