You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

307 lines
7.9 KiB

/*
* Copyright (c) Hisilicon Technologies Co., Ltd. 2020-2020. All rights reserved.
* Description: drvier
* Create: 2020-10-12
*/
#include "drv_event.h"
#include "osal_ext.h"
#include "soc_log.h"
#include "drv_base_ext.h"
#include "linux/huanglong/securec.h"
#define EVENT_MAX_HANDLE_NUM 128
typedef struct {
td_handle handle;
td_bool busy;
struct dft_event *event;
osal_mutex event_mutex;
} dft_event_instance;
static osal_mutex g_instance_mutex;
static dft_event_instance g_instance_set[EVENT_MAX_HANDLE_NUM];
td_handle event_index_to_handle(td_u32 index)
{
return TD_HANDLE_INIT(SOC_ID_EVENT, 0, index);
}
td_u32 event_handle_to_index(td_handle handle)
{
return TD_HANDLE_GET_CHAN_ID(handle);
}
td_s32 get_index_by_handle(td_handle handle, td_u32 *index)
{
td_s32 ret;
if (index == NULL) {
osal_printk("%s[%d]: index points to NULL!\n", __FUNCTION__, __LINE__);
ret = TD_FAILURE;
goto OUT;
}
*index = event_handle_to_index(handle);
if (*index >= EVENT_MAX_HANDLE_NUM) {
osal_printk("%s[%d]: invalid index\n", __FUNCTION__, __LINE__);
ret = TD_FAILURE;
goto OUT;
}
ret = TD_SUCCESS;
OUT:
return ret;
}
td_s32 instance_lock(td_u32 index)
{
td_s32 ret;
osal_mutex_lock(&g_instance_set[index].event_mutex);
if (g_instance_set[index].busy == TD_FALSE) {
osal_printk("%s[%d]: handle is not used\n", __FUNCTION__, __LINE__);
ret = TD_FAILURE;
goto OUT;
}
ret = TD_SUCCESS;
OUT:
return ret;
}
td_void instance_unlock(td_u32 index)
{
osal_mutex_unlock(&g_instance_set[index].event_mutex);
}
/* drv interface */
td_s32 dft_drv_event_create(td_u32 id, td_handle *handle)
{
struct dft_event *event = NULL;
td_s32 ret;
td_u32 index;
osal_mutex_lock(&g_instance_mutex);
if (handle == NULL) {
osal_printk("%s[%d]: invalid parameter!\n", __FUNCTION__, __LINE__);
goto OUT;
}
ret = drv_event_create(id, &event);
if ((ret != TD_SUCCESS) || (event == NULL)) {
osal_printk("%s[%d]: event create failed!\n", __FUNCTION__, __LINE__);
goto OUT;
}
for (index = 0; index < EVENT_MAX_HANDLE_NUM; index++) {
if (g_instance_set[index].busy == TD_FALSE) {
break;
}
}
if (index == EVENT_MAX_HANDLE_NUM) {
osal_printk("%s[%d]: handle busy!\n", __FUNCTION__, __LINE__);
goto OUT;
}
osal_mutex_lock(&g_instance_set[index].event_mutex);
*handle = event_index_to_handle(index);
g_instance_set[index].busy = TD_TRUE;
g_instance_set[index].event = event;
g_instance_set[index].handle = *handle;
osal_mutex_unlock(&g_instance_set[index].event_mutex);
osal_mutex_unlock(&g_instance_mutex);
return TD_SUCCESS;
OUT:
osal_mutex_unlock(&g_instance_mutex);
return TD_FAILURE;
}
EXPORT_SYMBOL(dft_drv_event_create);
td_s32 dft_drv_event_set_time(td_handle handle, td_s64 seconds)
{
td_u32 index;
td_s32 ret;
if ((handle == TD_INVALID_HANDLE) || (seconds == 0)) {
osal_printk("%s[%d]: invalid parameter!\n", __FUNCTION__, __LINE__);
ret = TD_FAILURE;
goto OUT;
}
ret = get_index_by_handle(handle, &index);
if (ret == TD_SUCCESS) {
ret = instance_lock(index);
if (ret == TD_SUCCESS) {
ret = drv_event_set_time(g_instance_set[index].event, seconds);
}
instance_unlock(index);
}
OUT:
return ret;
}
EXPORT_SYMBOL(dft_drv_event_set_time);
td_s32 dft_drv_event_put_integral(td_handle handle, const td_char *key, td_slong value)
{
td_u32 index;
td_s32 ret;
if ((handle == TD_INVALID_HANDLE) || (key == NULL)) {
osal_printk("%s[%d]: invalid parameter!\n", __FUNCTION__, __LINE__);
ret = TD_FAILURE;
goto OUT;
}
ret = get_index_by_handle(handle, &index);
if (ret == TD_SUCCESS) {
ret = instance_lock(index);
if (ret == TD_SUCCESS) {
ret = drv_event_put_integral(g_instance_set[index].event, key, value);
}
instance_unlock(index);
}
OUT:
return ret;
}
EXPORT_SYMBOL(dft_drv_event_put_integral);
td_s32 dft_drv_event_put_string(td_handle handle, const td_char *key, const td_char *value)
{
td_u32 index;
td_s32 ret;
if ((handle == TD_INVALID_HANDLE) || (key == NULL) || (value == NULL)) {
osal_printk("%s[%d]: invalid parameter!\n", __FUNCTION__, __LINE__);
ret = TD_FAILURE;
goto OUT;
}
ret = get_index_by_handle(handle, &index);
if (ret == TD_SUCCESS) {
ret = instance_lock(index);
if (ret == TD_SUCCESS) {
ret = drv_event_put_string(g_instance_set[index].event, key, value);
}
instance_unlock(index);
}
OUT:
return ret;
}
EXPORT_SYMBOL(dft_drv_event_put_string);
td_s32 dft_drv_event_add_file_path(td_handle handle, const td_char *path)
{
td_u32 index;
td_s32 ret;
if ((handle == TD_INVALID_HANDLE) || (path == NULL)) {
osal_printk("%s[%d]: invalid parameter!\n", __FUNCTION__, __LINE__);
ret = TD_FAILURE;
goto OUT;
}
ret = get_index_by_handle(handle, &index);
if (ret == TD_SUCCESS) {
ret = instance_lock(index);
if (ret == TD_SUCCESS) {
ret = drv_event_add_file_path(g_instance_set[index].event, path);
}
instance_unlock(index);
}
OUT:
return ret;
}
EXPORT_SYMBOL(dft_drv_event_add_file_path);
td_s32 dft_drv_event_report(td_handle handle)
{
td_u32 index;
td_s32 ret;
if (handle == TD_INVALID_HANDLE) {
osal_printk("%s[%d]: invalid parameter!\n", __FUNCTION__, __LINE__);
ret = TD_FAILURE;
}
ret = get_index_by_handle(handle, &index);
if (ret == TD_SUCCESS) {
ret = instance_lock(index);
if (ret == TD_SUCCESS) {
ret = drv_event_report(g_instance_set[index].event);
}
instance_unlock(index);
}
OUT:
return ret;
}
EXPORT_SYMBOL(dft_drv_event_report);
td_void dft_drv_event_destroy(td_handle handle)
{
td_u32 index;
td_s32 ret;
if (handle == TD_INVALID_HANDLE) {
osal_printk("%s[%d]: invalid parameter!\n", __FUNCTION__, __LINE__);
return;
}
osal_mutex_lock(&g_instance_mutex);
ret = get_index_by_handle(handle, &index);
if (ret == TD_SUCCESS) {
ret = instance_lock(index);
if (ret == TD_SUCCESS) {
drv_event_destroy(g_instance_set[index].event);
g_instance_set[index].busy = TD_FALSE;
g_instance_set[index].event = TD_NULL;
g_instance_set[index].handle = TD_INVALID_HANDLE;
}
instance_unlock(index);
}
osal_mutex_unlock(&g_instance_mutex);
}
EXPORT_SYMBOL(dft_drv_event_destroy);
td_s32 dft_event_mod_init(td_void)
{
td_s32 ret;
td_u32 index;
ret = osal_exportfunc_register(SOC_ID_EVENT, "DFT_EVENT", TD_NULL);
if (ret != TD_SUCCESS) {
osal_printk("register dft event module failed\n");
goto OUT;
}
osal_mutex_init(&g_instance_mutex);
for (index = 0; index < EVENT_MAX_HANDLE_NUM; index++) {
osal_mutex_init(&g_instance_set[index].event_mutex);
g_instance_set[index].busy = TD_FALSE;
g_instance_set[index].event = TD_NULL;
g_instance_set[index].handle = TD_INVALID_HANDLE;
}
return TD_SUCCESS;
OUT:
return ret;
}
td_void dft_event_mod_exit(td_void)
{
td_u32 index;
osal_mutex_destroy(&g_instance_mutex);
for (index = 0; index < EVENT_MAX_HANDLE_NUM; index++) {
osal_mutex_destroy(&g_instance_set[index].event_mutex);
g_instance_set[index].busy = TD_FALSE;
g_instance_set[index].event = TD_NULL;
g_instance_set[index].handle = TD_INVALID_HANDLE;
}
osal_exportfunc_unregister(SOC_ID_EVENT);
}
#ifdef MODULE
module_init(dft_event_mod_init);
module_exit(dft_event_mod_exit);
#else
#ifndef CONFIG_SOCT_RECOVERY_SUPPORT
soc_initcall(dft_event_mod_init);
#endif
#endif
MODULE_AUTHOR("HUANGLONG");
MODULE_LICENSE("GPL");