• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /*
2  * Copyright (C) 2021 HiSilicon (Shanghai) Technologies CO., LIMITED.
3  *
4  * This program is free software; you can redistribute it and/or
5  * modify it under the terms of the GNU General Public License
6  * as published by the Free Software Foundation; either version 2
7  * of the License, or (at your option) any later version.
8  *
9  * This program is distributed in the hope that it will be useful,
10  * but WITHOUT ANY WARRANTY; without even the implied warranty of
11  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
12  * GNU General Public License for more details.
13  *
14  * You should have received a copy of the GNU General Public License
15  * along with this program; if not, write to the Free Software
16  * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA  02110-1301, USA.
17  */
18 #include "hdmi_hal_machine.h"
19 #include "hdmi_osal.h"
20 #include "drv_hdmi_common.h"
21 
22 #define MACHINE_MAX_ID_NUM     19
23 #define MACHIME_NULL_TINTERVAL 20
24 #define MACHIME_MIN_TINTERVAL  5
25 
26 typedef struct {
27     osal_semaphore_t mach_mutex;
28     hi_bool init;
29     hi_u32 total;
30     hdmi_mach_elem mach_elem[MACHINE_MAX_ID_NUM];
31 } hdmi_mach_info;
32 
33 static hdmi_mach_info g_machine_info;
34 
hal_hdmi_mach_init(hi_void)35 hi_s32 hal_hdmi_mach_init(hi_void)
36 {
37     hdmi_mach_info *mach_info = &g_machine_info;
38 
39     if (!mach_info->init) {
40         osal_sema_init(&mach_info->mach_mutex, 1);
41         (hi_void)memset_s(mach_info->mach_elem, MACHINE_MAX_ID_NUM * sizeof(hdmi_mach_elem), 0,
42             MACHINE_MAX_ID_NUM * sizeof(hdmi_mach_elem));
43         mach_info->total = 0;
44         mach_info->init  = HI_TRUE;
45     }
46 
47     return HI_SUCCESS;
48 }
49 
hal_hdmi_mach_deinit(hi_void)50 hi_s32 hal_hdmi_mach_deinit(hi_void)
51 {
52     hdmi_mach_info *mach_info = &g_machine_info;
53 
54     hdmi_if_false_return(mach_info->init, HI_FAILURE);
55 
56     hdmi_mutex_lock(mach_info->mach_mutex);
57     (hi_void)memset_s(mach_info->mach_elem, sizeof(mach_info->mach_elem), 0, sizeof(mach_info->mach_elem));
58     mach_info->total = 0;
59     mach_info->init = HI_FALSE;
60     hdmi_mutex_unlock(mach_info->mach_mutex);
61     osal_sema_destroy(&mach_info->mach_mutex);
62 
63     return HI_SUCCESS;
64 }
65 
hal_hdmi_mach_invoke(hi_void)66 hi_s32 hal_hdmi_mach_invoke(hi_void)
67 {
68     hi_u32 i;
69     hdmi_mach_elem *tmp_elem  = HI_NULL;
70     hdmi_mach_info *mach_info = &g_machine_info;
71 
72     hdmi_if_false_return(mach_info->init, HI_FAILURE);
73 
74     if (mach_info->total == 0) {
75         osal_msleep(MACHIME_NULL_TINTERVAL);
76     } else {
77         for (i = 0; i < MACHINE_MAX_ID_NUM; ++i) {
78             tmp_elem = &mach_info->mach_elem[i];
79             if (!(tmp_elem->mach_run.valid_id) || !(tmp_elem->mach_run.enable) ||
80                 ((hdmi_osal_get_time_in_ms() - tmp_elem->mach_run.last_time) <= tmp_elem->mach_ctrl.interval)) {
81                 continue;
82             }
83             if (tmp_elem->mach_ctrl.callback != HI_NULL) {
84                 tmp_elem->mach_ctrl.callback(tmp_elem->mach_ctrl.data);
85             }
86             hdmi_mutex_lock(mach_info->mach_mutex);
87             tmp_elem->mach_run.last_time = hdmi_osal_get_time_in_ms();
88             tmp_elem->mach_run.timestamp[tmp_elem->mach_run.stamp_idx] = hdmi_osal_get_time_in_ms();
89             tmp_elem->mach_run.stamp_idx = (tmp_elem->mach_run.stamp_idx + 1) % HDMI_MACH_MAX_STAMPE_NUM;
90             tmp_elem->mach_run.run_cnt++;
91             hdmi_mutex_unlock(mach_info->mach_mutex);
92         }
93     }
94 
95     return HI_SUCCESS;
96 }
97 
hal_hdmi_mach_register(const hdmi_mach_ctrl * mach_ctrl,hi_u32 * mach_id)98 hi_s32 hal_hdmi_mach_register(const hdmi_mach_ctrl *mach_ctrl, hi_u32 *mach_id)
99 {
100     errno_t errnumber;
101     hi_u32 i;
102     hi_s32 name_len, ret;
103     hdmi_mach_elem *tmp_elem  = HI_NULL;
104     hdmi_mach_info *mach_info = &g_machine_info;
105 
106     hdmi_if_null_return(mach_ctrl, HI_FAILURE);
107     hdmi_if_null_return(mach_id, HI_FAILURE);
108     hdmi_if_false_return(mach_info->init, HI_FAILURE);
109 
110     if (mach_info->total >= MACHINE_MAX_ID_NUM) {
111         hdmi_warn("FULL num=%u! register machine fail! \n", MACHINE_MAX_ID_NUM);
112         ret = HI_FAILURE;
113     } else {
114         hdmi_mutex_lock(mach_info->mach_mutex);
115         for (i = 0; i < MACHINE_MAX_ID_NUM; ++i) {
116             tmp_elem = &mach_info->mach_elem[i];
117             if (!tmp_elem->mach_run.valid_id) {
118                 (hi_void)memset_s(&tmp_elem->mach_run, sizeof(tmp_elem->mach_run), 0, sizeof(hdmi_mach_run));
119                 errnumber = memcpy_s(&tmp_elem->mach_ctrl, sizeof(tmp_elem->mach_ctrl),
120                     mach_ctrl, sizeof(hdmi_mach_ctrl));
121                 hdmi_unlock_unequal_eok_return(errnumber, mach_info->mach_mutex, HI_ERR_HDMI_INVALID_PARA);
122                 hdmi_unlock_if_null_return(tmp_elem->mach_ctrl.name, mach_info->mach_mutex, HI_FAILURE);
123                 name_len = osal_strlen(tmp_elem->mach_ctrl.name);
124                 name_len = (name_len < HDMI_MACH_MAX_NAME_SIZE) ? name_len : (HDMI_MACH_MAX_NAME_SIZE - 1);
125                 ret = strncpy_s(tmp_elem->mach_run.name, HDMI_MACH_MAX_NAME_SIZE, tmp_elem->mach_ctrl.name, name_len);
126                 hdmi_unlock_unequal_eok_return(ret, mach_info->mach_mutex, HI_ERR_HDMI_INVALID_PARA);
127                 tmp_elem->mach_run.name[name_len] = '\0';
128                 tmp_elem->mach_ctrl.name = tmp_elem->mach_run.name;
129                 mach_info->total++;
130                 tmp_elem->mach_run.valid_id = HI_TRUE;
131                 *mach_id = i;
132                 break;
133             }
134         }
135         hdmi_mutex_unlock(mach_info->mach_mutex);
136 
137         if (i < MACHINE_MAX_ID_NUM) {
138             hdmi_info("register new machine id=%u success!\n", *mach_id);
139             ret = HI_SUCCESS;
140         } else {
141             hdmi_info("register new machine id=%u fail!\n", *mach_id);
142             ret = HI_FAILURE;
143         }
144     }
145 
146     return ret;
147 }
148 
hal_hdmi_mach_unregister(hi_u32 mach_id)149 hi_s32 hal_hdmi_mach_unregister(hi_u32 mach_id)
150 {
151     hdmi_mach_elem *tmp_elem = HI_NULL;
152     hdmi_mach_info *mach_info = &g_machine_info;
153 
154     hdmi_if_false_return(mach_info->init, HI_FAILURE);
155     hdmi_check_max_return(mach_id, MACHINE_MAX_ID_NUM - 1, HI_FAILURE);
156 
157     hdmi_mutex_lock(mach_info->mach_mutex);
158     tmp_elem = &mach_info->mach_elem[mach_id];
159     (hi_void)memset_s(&tmp_elem->mach_run, sizeof(tmp_elem->mach_run), 0, sizeof(hdmi_mach_run));
160     (hi_void)memset_s(&tmp_elem->mach_ctrl, sizeof(tmp_elem->mach_ctrl), 0, sizeof(hdmi_mach_ctrl));
161     mach_info->total--;
162     hdmi_mutex_unlock(mach_info->mach_mutex);
163 
164     return HI_SUCCESS;
165 }
166 
hal_hdmi_mach_cfg_get(hi_u32 mach_id,hdmi_mach_ctrl * mach_ctrl)167 hi_s32 hal_hdmi_mach_cfg_get(hi_u32 mach_id, hdmi_mach_ctrl *mach_ctrl)
168 {
169     errno_t errnumber;
170     hdmi_mach_elem *tmp_elem = HI_NULL;
171     hdmi_mach_info *mach_info = &g_machine_info;
172 
173     hdmi_if_null_return(mach_ctrl, HI_FAILURE);
174     hdmi_if_false_return(mach_info->init, HI_FAILURE);
175     hdmi_check_max_return(mach_id, MACHINE_MAX_ID_NUM - 1, HI_FAILURE);
176 
177     hdmi_mutex_lock(mach_info->mach_mutex);
178     tmp_elem = &mach_info->mach_elem[mach_id];
179     errnumber = memcpy_s(mach_ctrl, sizeof(hdmi_mach_ctrl), &tmp_elem->mach_ctrl, sizeof(hdmi_mach_ctrl));
180     hdmi_unlock_unequal_eok_return(errnumber, mach_info->mach_mutex, HI_ERR_HDMI_INVALID_PARA);
181     hdmi_mutex_unlock(mach_info->mach_mutex);
182 
183     return HI_SUCCESS;
184 }
185 
hal_hdmi_mach_cfg_set(hi_u32 mach_id,const hdmi_mach_ctrl * mach_ctrl)186 hi_s32 hal_hdmi_mach_cfg_set(hi_u32 mach_id, const hdmi_mach_ctrl *mach_ctrl)
187 {
188     errno_t errnumber;
189     hdmi_mach_elem *tmp_elem = HI_NULL;
190     hdmi_mach_info *mach_info = &g_machine_info;
191 
192     hdmi_if_null_return(mach_ctrl, HI_FAILURE);
193     hdmi_if_false_return(mach_info->init, HI_FAILURE);
194     hdmi_check_max_return(mach_id, MACHINE_MAX_ID_NUM - 1, HI_FAILURE);
195 
196     hdmi_mutex_lock(mach_info->mach_mutex);
197     tmp_elem = &mach_info->mach_elem[mach_id];
198     errnumber = memcpy_s(&tmp_elem->mach_ctrl, sizeof(hdmi_mach_ctrl), mach_ctrl, sizeof(hdmi_mach_ctrl));
199     hdmi_unlock_unequal_eok_return(errnumber, mach_info->mach_mutex, HI_ERR_HDMI_INVALID_PARA);
200     hdmi_mutex_unlock(mach_info->mach_mutex);
201 
202     return HI_SUCCESS;
203 }
204 
hal_hdmi_mach_start(hi_u32 mach_id)205 hi_s32 hal_hdmi_mach_start(hi_u32 mach_id)
206 {
207     hdmi_mach_elem *tmp_elem = HI_NULL;
208     hdmi_mach_info *mach_info = &g_machine_info;
209 
210     hdmi_if_false_return(mach_info->init, HI_FAILURE);
211     hdmi_check_max_return(mach_id, MACHINE_MAX_ID_NUM - 1, HI_FAILURE);
212 
213     hdmi_mutex_lock(mach_info->mach_mutex);
214     tmp_elem = &mach_info->mach_elem[mach_id];
215     tmp_elem->mach_run.enable = HI_TRUE;
216     tmp_elem->mach_run.enable_time = hdmi_osal_get_time_in_ms();
217     hdmi_mutex_unlock(mach_info->mach_mutex);
218 
219     return HI_SUCCESS;
220 }
221 
hal_hdmi_mach_stop(hi_u32 mach_id)222 hi_s32 hal_hdmi_mach_stop(hi_u32 mach_id)
223 {
224     hdmi_mach_elem *tmp_elem = HI_NULL;
225     hdmi_mach_info *mach_info = &g_machine_info;
226 
227     hdmi_if_false_return(mach_info->init, HI_FAILURE);
228     hdmi_check_max_return(mach_id, MACHINE_MAX_ID_NUM - 1, HI_FAILURE);
229 
230     hdmi_mutex_lock(mach_info->mach_mutex);
231     tmp_elem = &mach_info->mach_elem[mach_id];
232     tmp_elem->mach_run.enable = HI_FALSE;
233     tmp_elem->mach_run.disable_time = hdmi_osal_get_time_in_ms();
234     hdmi_mutex_unlock(mach_info->mach_mutex);
235 
236     return HI_SUCCESS;
237 }
238 
hal_hdmi_mach_status_get(hdmi_mach_status * status)239 hi_s32 hal_hdmi_mach_status_get(hdmi_mach_status *status)
240 {
241     hdmi_mach_info *mach_info = &g_machine_info;
242 
243     hdmi_if_null_return(status, HI_FAILURE);
244     hdmi_if_false_return(mach_info->init, HI_FAILURE);
245 
246     hdmi_mutex_lock(mach_info->mach_mutex);
247     status->init = mach_info->init;
248     status->total = mach_info->total;
249     hdmi_mutex_unlock(mach_info->mach_mutex);
250 
251     return HI_SUCCESS;
252 }
253 
hal_hdmi_mach_elem_status_get(hi_u32 mach_id,hdmi_mach_elem_status * status)254 hi_s32 hal_hdmi_mach_elem_status_get(hi_u32 mach_id, hdmi_mach_elem_status *status)
255 {
256     errno_t errnumber;
257     hdmi_mach_elem *tmp_elem = HI_NULL;
258     hdmi_mach_info *mach_info = &g_machine_info;
259 
260     hdmi_if_null_return(status, HI_FAILURE);
261     hdmi_if_false_return(mach_info->init, HI_FAILURE);
262     hdmi_check_max_return(mach_id, MACHINE_MAX_ID_NUM - 1, HI_FAILURE);
263 
264     hdmi_mutex_lock(mach_info->mach_mutex);
265     tmp_elem = &mach_info->mach_elem[mach_id];
266     errnumber = memcpy_s(&status->mach_ctrl, sizeof(hdmi_mach_ctrl), &tmp_elem->mach_ctrl, sizeof(hdmi_mach_ctrl));
267     hdmi_unlock_unequal_eok_return(errnumber, mach_info->mach_mutex, HI_ERR_HDMI_INVALID_PARA);
268     errnumber = memcpy_s(&status->mach_run, sizeof(hdmi_mach_run), &tmp_elem->mach_run, sizeof(hdmi_mach_run));
269     hdmi_unlock_unequal_eok_return(errnumber, mach_info->mach_mutex, HI_ERR_HDMI_INVALID_PARA);
270     hdmi_mutex_unlock(mach_info->mach_mutex);
271 
272     return HI_SUCCESS;
273 }
274 
hal_hdmi_mach_ms_get(hi_void)275 hi_u64 hal_hdmi_mach_ms_get(hi_void)
276 {
277     return (hi_u64)hdmi_osal_get_time_in_ms();
278 }
279 
280