1 /*
2 * Copyright (C) 2013 SAMSUNG S.LSI
3 *
4 * Licensed under the Apache License, Version 2.0 (the "License");
5 * you may not use this file except in compliance with the License.
6 * You may obtain a copy of the License at:
7 *
8 * http://www.apache.org/licenses/LICENSE-2.0
9 *
10 * Unless required by applicable law or agreed to in writing, software
11 * distributed under the License is distributed on an "AS IS" BASIS,
12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13 * See the License for the specific language governing permissions and
14 * limitations under the License.
15 *
16 *
17 */
18
19 /************************************************************************
20 ** OS interface for task handling
21 *************************************************************************/
22 #include <pthread.h>
23 #include <signal.h>
24 #include <string.h>
25 #include "osi.h"
26
27 /************************************************************************
28 ** Internal function prototype
29 *************************************************************************/
30
31 /************************************************************************
32 ** Public functions
33 *************************************************************************/
osi_task_entry(void * arg)34 void osi_task_entry(void* arg) {
35 tOSI_TASK_ENTRY task_entry = (tOSI_TASK_ENTRY)arg;
36
37 // pthread_setcancelstate(PTHREAD_CANCEL_ENABLE, NULL);
38
39 task_entry();
40 OSI_logt("%s : exit task", __func__);
41
42 pthread_exit(NULL);
43 }
44
OSI_task_allocate(const char * task_name,tOSI_TASK_ENTRY task_entry)45 tOSI_TASK_HANDLER OSI_task_allocate(const char* task_name,
46 tOSI_TASK_ENTRY task_entry) {
47 tOSI_TASK_HANDLER free_task = NULL;
48 int index;
49
50 /* Find free task */
51 osi_lock();
52 for (index = 0; index < OSI_MAX_TASK; index++) {
53 if (osi_info.task[index].state == OSI_FREE) {
54 if (free_task == NULL)
55 free_task = (tOSI_TASK_HANDLER)&osi_info.task[index];
56 } else {
57 if (osi_info.task[index].name == NULL) continue;
58
59 /* User can't not make same name of task */
60 if (strcmp((char const*)osi_info.task[index].name,
61 (char const*)task_name) == 0) {
62 OSI_loge("%s : %s task is already allocated [%d]", __func__, task_name,
63 index);
64 free_task = NULL;
65 break;
66 }
67 }
68 }
69
70 if (free_task == NULL) {
71 OSI_loge("%s : Failed to find free task(max: %d)", __func__, OSI_MAX_TASK);
72 } else {
73 free_task->state = OSI_ALLOCATED;
74 free_task->name = task_name;
75 free_task->task_entry = task_entry;
76 }
77
78 osi_unlock();
79 return free_task;
80 }
OSI_task_run(tOSI_TASK_HANDLER task_handler)81 OSI_STATE OSI_task_run(tOSI_TASK_HANDLER task_handler) {
82 pthread_attr_t attr;
83 int ret = OSI_FAIL;
84
85 osi_lock();
86 if (!task_handler) {
87 OSI_loge("%s : task handler is not exist!!", __func__);
88 } else if (task_handler->state != OSI_ALLOCATED) {
89 OSI_loge("%s : task state is not ALLOCATED!! (%d)", __func__,
90 task_handler->state);
91 } else {
92 /* Thread attr configuration */
93 pthread_attr_init(&attr);
94 if (!pthread_create(&(task_handler->task), &attr,
95 (void* (*)(void*))osi_task_entry,
96 (void*)(task_handler->task_entry))) { //
97 task_handler->state = OSI_RUN;
98 ret = OSI_OK;
99 } else {
100 OSI_loge("%s : pthread_create failed(%d), %s", __func__, ret,
101 task_handler->name);
102 }
103 pthread_attr_destroy(&attr);
104 }
105
106 osi_unlock();
107 return ret;
108 }
109
OSI_task_isRun(tOSI_TASK_HANDLER task_handler)110 OSI_STATE OSI_task_isRun(tOSI_TASK_HANDLER task_handler) {
111 OSI_STATE ret = OSI_FAIL;
112 osi_lock();
113 if (task_handler && task_handler->state == OSI_RUN) ret = OSI_RUN;
114 osi_unlock();
115 return ret;
116 }
117
OSI_task_stop(tOSI_TASK_HANDLER task_handler)118 OSI_STATE OSI_task_stop(tOSI_TASK_HANDLER task_handler) {
119 OSI_STATE ret = OSI_OK;
120 if (!task_handler) return OSI_OK;
121
122 osi_lock();
123 if (task_handler->state == OSI_RUN) {
124 osi_unlock();
125 // ret = pthread_cancel(task_handler->task);
126 ret = (OSI_STATE)pthread_join(task_handler->task, NULL);
127 osi_lock();
128 }
129
130 task_handler->state = OSI_ALLOCATED;
131 osi_unlock();
132
133 return ret;
134 }
135
OSI_task_free(tOSI_TASK_HANDLER task_handler)136 OSI_STATE OSI_task_free(tOSI_TASK_HANDLER task_handler) {
137 OSI_STATE ret = OSI_OK;
138
139 OSI_task_stop(task_handler);
140 osi_lock();
141 task_handler->name = NULL;
142 task_handler->state = OSI_FREE;
143 osi_unlock();
144
145 return ret;
146 }
147
OSI_task_kill(tOSI_TASK_HANDLER task_handler)148 OSI_STATE OSI_task_kill(tOSI_TASK_HANDLER task_handler) {
149 OSI_STATE ret = OSI_OK;
150 if (!task_handler) return OSI_OK;
151
152 osi_lock();
153 if (task_handler->state == OSI_RUN) {
154 osi_unlock();
155 // ret = pthread_cancel(task_handler->task);
156 ret = (OSI_STATE)pthread_join(task_handler->task, NULL);
157 osi_lock();
158 }
159
160 task_handler->name = NULL;
161 task_handler->state = OSI_FREE;
162 osi_unlock();
163
164 return ret;
165 }
166
OSI_task_get_handler(char * name)167 tOSI_TASK_HANDLER OSI_task_get_handler(char* name) {
168 tOSI_TASK_HANDLER task = NULL;
169 int index;
170
171 if (!name) return NULL;
172
173 osi_lock();
174 for (index = 0; index < OSI_MAX_TASK; index++) {
175 if ((char const*)osi_info.task[index].name == NULL) continue;
176
177 if (strcmp((char const*)osi_info.task[index].name, (char const*)name) ==
178 0) {
179 task = &osi_info.task[index];
180 break;
181 }
182 }
183 osi_unlock();
184
185 return task;
186 }
187