Fix for new automake and 64 bit compatibility.
[platform/core/multimedia/avsystem.git] / avsys-audio-sync.c
1 /*
2  * avsystem
3  *
4  * Copyright (c) 2000 - 2011 Samsung Electronics Co., Ltd. All rights reserved.
5  *
6  * Contact: Jonghyuk Choi <jhchoi.choi@samsung.com>
7  *
8  * Licensed under the Apache License, Version 2.0 (the "License");
9  * you may not use this file except in compliance with the License.
10  * You may obtain a copy of the License at
11  *
12  * http://www.apache.org/licenses/LICENSE-2.0
13  *
14  * Unless required by applicable law or agreed to in writing, software
15  * distributed under the License is distributed on an "AS IS" BASIS,
16  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
17  * See the License for the specific language governing permissions and
18  * limitations under the License.
19  *
20  */
21
22 #include <string.h>
23 #include <dirent.h>
24 #include <errno.h>
25 #include <sys/types.h>
26 #include <unistd.h>
27
28 #include "avsys-common.h"
29 #include "avsys-audio-sync.h"
30 #include "avsys-error.h"
31 #include "avsys-debug.h"
32 #include "avsys-audio-shm.h"
33 #include "avsys-audio-path.h"
34
35 static avsys_sync_param_t g_presettings[AVSYS_AUDIO_SYNC_IDEN_CNT] = {
36         {"audio_handle_lock", AVSYS_KEY_PREFIX_GEN(AVSYS_KEY_PREFIX_AUDIO, AVSYS_AUDIO_SYNC_IDEN_HANDLE)},
37         {"audio_path_lock", AVSYS_KEY_PREFIX_GEN(AVSYS_KEY_PREFIX_AUDIO, AVSYS_AUDIO_SYNC_IDEN_PATH)},
38 };
39
40 int avsys_audio_create_sync(const avsys_audio_sync_iden_t iden)
41 {
42         if (iden >= AVSYS_AUDIO_SYNC_IDEN_CNT || 0 > iden)
43                 return AVSYS_STATE_ERR_INVALID_PARAMETER;
44         return avsys_create_sync(&g_presettings[iden]);
45 }
46
47 int avsys_audio_remove_sync(const avsys_audio_sync_iden_t iden)
48 {
49         if (iden >= AVSYS_AUDIO_SYNC_IDEN_CNT || 0 > iden)
50                 return AVSYS_STATE_ERR_INVALID_PARAMETER;
51         return avsys_remove_sync(&g_presettings[iden]);
52 }
53
54 int avsys_audio_lock_sync(const avsys_audio_sync_iden_t iden)
55 {
56         pid_t pid = -1;
57         int index = 0;
58         int err = AVSYS_STATE_SUCCESS;
59
60         if (iden >= AVSYS_AUDIO_SYNC_IDEN_CNT || 0 > iden) {
61                 return AVSYS_STATE_ERR_INVALID_PARAMETER;
62         }
63         //avsys_info(AVAUDIO,"lock[%d]\n",(int)iden);
64
65         err = avsys_lock_sync(&g_presettings[iden]);
66
67         pid = getpid();
68         if ((iden == AVSYS_AUDIO_SYNC_IDEN_PATH) && (err == AVSYS_STATE_SUCCESS)) {
69                 avsys_audio_path_ex_info_t *control = NULL;
70                 avsys_audio_path_ex_info_t **temp = NULL;
71
72                 temp = &control;
73                 if (AVSYS_FAIL(avsys_audio_get_shm(AVSYS_AUDIO_SHM_IDEN_PATH, (void **)temp))) {
74                         avsys_error_r(AVAUDIO, "avsys_audio_get_shm() for path failed in %s\n", __func__);
75                         return AVSYS_STATE_ERR_INTERNAL;
76                 }
77
78                 do {
79                         /* Add mark */
80                         if (control->pathlock_pid[index] < 0) { /* find empty slot */
81                                 control->pathlock_pid[index] = pid;
82                                 break;
83                         }
84                         index++;
85                         if (index == AVSYS_AUDIO_LOCK_SLOT_MAX) {
86                                 int i;
87                                 avsys_critical(AVAUDIO, "path lock pid slot is full. print stored pid before clear all slot\n");
88                                 /* print and cleanup all stored pid */
89                                 for (i = 0; i < AVSYS_AUDIO_LOCK_SLOT_MAX; i++) {
90                                         avsys_critical(AVAUDIO, "path lock pid : %d\n", control->pathlock_pid[i]);
91                                         control->pathlock_pid[i] = -1;
92                                 }
93                                 control->pathlock_pid[0] = pid; /* add current pid */
94                         }
95                 } while (index < AVSYS_AUDIO_LOCK_SLOT_MAX);
96         } else if ((iden == AVSYS_AUDIO_SYNC_IDEN_HANDLE) && (err == AVSYS_STATE_SUCCESS)) {
97                 avsys_audio_handle_info_t *control = NULL;
98                 avsys_audio_handle_info_t **temp = NULL;
99
100                 temp = &control;
101                 if (AVSYS_FAIL(avsys_audio_get_shm(AVSYS_AUDIO_SHM_IDEN_HANDLE, (void **)temp))) {
102                         avsys_error(AVAUDIO, "avsys_audio_get_shm() for handle failed in %s\n", __func__);
103                         return AVSYS_STATE_ERR_INTERNAL;
104                 }
105
106                 do {
107                         /* Add mark */
108                         if (control->handlelock_pid[index] < 0) {       /* find empty slot */
109                                 control->handlelock_pid[index] = pid;
110                                 break;
111                         }
112                         index++;
113                         if (index == AVSYS_AUDIO_LOCK_SLOT_MAX) {
114                                 int i;
115                                 avsys_critical(AVAUDIO, "handle lock pid slot is full. print stored pid before clear all slot\n");
116                                 /* print and cleanup all stored pid */
117                                 for (i = 0; i < AVSYS_AUDIO_LOCK_SLOT_MAX; i++) {
118                                         avsys_critical(AVAUDIO, "handle lock pid : %d\n", control->handlelock_pid[i]);
119                                         control->handlelock_pid[i] = -1;
120                                 }
121                                 control->handlelock_pid[0] = pid; /*add current pid */
122                         }
123                 } while (index < AVSYS_AUDIO_LOCK_SLOT_MAX);
124         }
125         return err;
126 }
127
128 int avsys_audio_unlock_sync(const avsys_audio_sync_iden_t iden)
129 {
130         pid_t pid = -1;
131         int index = 0;
132         int err = AVSYS_STATE_SUCCESS;
133
134         if (iden >= AVSYS_AUDIO_SYNC_IDEN_CNT || 0 > iden) {
135                 return AVSYS_STATE_ERR_INVALID_PARAMETER;
136         }
137         //avsys_info(AVAUDIO,"unlock[%d]\n",(int)iden);
138
139         err = avsys_unlock_sync(&g_presettings[iden]);
140
141         pid = getpid();
142         if ((iden == AVSYS_AUDIO_SYNC_IDEN_PATH) && (err == AVSYS_STATE_SUCCESS)) {
143                 avsys_audio_path_ex_info_t *control = NULL;
144                 avsys_audio_path_ex_info_t **temp = NULL;
145
146                 temp = &control;
147                 if (AVSYS_FAIL(avsys_audio_get_shm(AVSYS_AUDIO_SHM_IDEN_PATH, (void **)temp))) {
148                         avsys_error_r(AVAUDIO, "avsys_audio_get_shm() failed in %s\n", __func__);
149                         return AVSYS_STATE_ERR_INTERNAL;
150                 }
151
152                 do {
153                         /* Remove mark */
154                         if (control->pathlock_pid[index] == pid) {      /* find empty slot */
155                                 control->pathlock_pid[index] = -1;
156                                 break;
157                         }
158                         index++;
159                         if (index == AVSYS_AUDIO_LOCK_SLOT_MAX)
160                                 avsys_error(AVAUDIO, "Can not find pid (%d) in path_lock_pid slot\n", pid);
161                 } while (index < AVSYS_AUDIO_LOCK_SLOT_MAX);
162         } else if ((iden == AVSYS_AUDIO_SYNC_IDEN_HANDLE) && (err == AVSYS_STATE_SUCCESS)) {
163                 avsys_audio_handle_info_t *control = NULL;
164                 avsys_audio_handle_info_t **temp = NULL;
165
166                 temp = &control;
167                 if (AVSYS_FAIL(avsys_audio_get_shm(AVSYS_AUDIO_SHM_IDEN_HANDLE, (void **)temp))) {
168                         avsys_error(AVAUDIO, "avsys_audio_get_shm() for handle failed in %s\n", __func__);
169                         return AVSYS_STATE_ERR_INTERNAL;
170                 }
171
172                 do {
173                         /* Add mark */
174                         if (control->handlelock_pid[index] == pid) {    /* find empty slot */
175                                 control->handlelock_pid[index] = -1;
176                                 break;
177                         }
178                         index++;
179                         if (index == AVSYS_AUDIO_LOCK_SLOT_MAX)
180                                 avsys_error(AVAUDIO, "Can not find pid (%d) in handlelock_pid slot\n", pid);
181                 } while (index < AVSYS_AUDIO_LOCK_SLOT_MAX);
182         }
183
184         return err;
185 }
186
187 /* find pid information in proc filesystem */
188 /* if pid exist, return AVSYS_STATE_SUCCESS */
189 /* if pid does not exist, return AVSYS_STATE_ERR_ALLOCATION */
190 int avsys_check_process(int check_pid)
191 {
192         DIR *dir = NULL;
193         char check_path[128] = "";
194         int exist = AVSYS_STATE_SUCCESS;
195
196         memset(check_path, '\0', sizeof(check_path));
197         snprintf(check_path, sizeof(check_path) - 1, "/proc/%d", check_pid);
198
199         dir = opendir(check_path);
200         if (dir == NULL) {
201                 switch (errno) {
202                 case ENOENT:
203                         avsys_error(AVAUDIO, "pid %d does not exist anymore\n", check_pid);
204                         exist = AVSYS_STATE_ERR_ALLOCATION;
205                         break;
206                 case EACCES:
207                         avsys_error(AVAUDIO, "Permission denied\n");
208                         break;
209                 case EMFILE:
210                         avsys_error(AVAUDIO, "Too many file descriptors in use by process\n");
211                         break;
212                 case ENFILE:
213                         avsys_error(AVAUDIO, "Too many files are currently open in the system\n");
214                         break;
215                 default:
216                         avsys_error(AVAUDIO, "Other error : %d\n", errno);
217                         break;
218                 }
219         } else {
220                 avsys_warning(AVAUDIO, "pid : %d still alive\n", check_pid);
221                 if (-1 == closedir(dir)) {
222                         avsys_error(AVAUDIO, "[%s] closedir failed with errno : %d\n", __func__, errno);
223                 }
224         }
225         return exist;
226 }
227
228 int avsys_audio_dump_sync(void)
229 {
230         pid_t pid = -1;
231         int index = 0;
232         int err = AVSYS_STATE_SUCCESS;
233         int i = 0;
234         int sem_value = 0;
235
236         fprintf(stdout, "Dump sync : Start\n");
237         for (i = 0; i < AVSYS_AUDIO_SYNC_IDEN_CNT; i++) {
238                 err = avsys_dump_sync(&g_presettings[i]);
239         }
240         fprintf(stdout, "Dump sync : End\n");
241         return err;
242 }