4 * Copyright (c) 2000 - 2011 Samsung Electronics Co., Ltd. All rights reserved.
6 * Licensed under the Apache License, Version 2.0 (the "License");
7 * you may not use this file except in compliance with the License.
8 * You may obtain a copy of the License at
10 * http://www.apache.org/licenses/LICENSE-2.0
12 * Unless required by applicable law or agreed to in writing, software
13 * distributed under the License is distributed on an "AS IS" BASIS,
14 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
15 * See the License for the specific language governing permissions and
16 * limitations under the License.
20 #include "mm_camcorder_internal.h"
21 #include "mm_camcorder_resource.h"
22 #include <murphy/common/glib-glue.h>
24 #define MRP_APP_CLASS_FOR_CAMCORDER "media"
25 #define MRP_RESOURCE_TYPE_MANDATORY TRUE
26 #define MRP_RESOURCE_TYPE_EXCLUSIVE FALSE
29 MRP_RESOURCE_FOR_VIDEO_OVERLAY,
30 MRP_RESOURCE_FOR_CAMERA,
33 const char* resource_str[MRP_RESOURCE_MAX] = {
38 #define MMCAMCORDER_CHECK_RESOURCE_MANAGER_INSTANCE(x_camcorder_resource_manager) \
40 if (!x_camcorder_resource_manager) { \
41 _mmcam_dbg_err("no resource manager instance"); \
42 return MM_ERROR_INVALID_ARGUMENT; \
46 #define MMCAMCORDER_CHECK_CONNECTION_RESOURCE_MANAGER(x_camcorder_resource_manager) \
48 if (!x_camcorder_resource_manager) { \
49 _mmcam_dbg_err("no resource manager instance"); \
50 return MM_ERROR_INVALID_ARGUMENT; \
52 if (!x_camcorder_resource_manager->is_connected) { \
53 _mmcam_dbg_err("not connected to resource server yet"); \
54 return MM_ERROR_RESOURCE_NOT_INITIALIZED; \
59 static char *state_to_str(mrp_res_resource_state_t st)
61 char *state = "unknown";
63 case MRP_RES_RESOURCE_ACQUIRED:
66 case MRP_RES_RESOURCE_LOST:
69 case MRP_RES_RESOURCE_AVAILABLE:
72 case MRP_RES_RESOURCE_PENDING:
75 case MRP_RES_RESOURCE_ABOUT_TO_LOOSE:
76 state = "about to loose";
82 static void mrp_state_callback(mrp_res_context_t *context, mrp_res_error_t err, void *user_data)
85 const mrp_res_resource_set_t *rset;
86 mrp_res_resource_t *resource;
87 mmf_camcorder_t* camcorder = NULL;
90 if (err != MRP_RES_ERROR_NONE) {
91 _mmcam_dbg_err(" - error message received from Murphy, err(0x%x)", err);
95 camcorder = (mmf_camcorder_t*)user_data;
97 mmf_return_if_fail((MMHandleType)camcorder);
99 switch (context->state) {
100 case MRP_RES_CONNECTED:
101 _mmcam_dbg_log(" - connected to Murphy");
102 if ((rset = mrp_res_list_resources(context)) != NULL) {
103 mrp_res_string_array_t *resource_names;
104 resource_names = mrp_res_list_resource_names(rset);
105 if (!resource_names) {
106 _mmcam_dbg_err(" - no resources available");
109 for (i = 0; i < resource_names->num_strings; i++) {
110 resource = mrp_res_get_resource_by_name(rset, resource_names->strings[i]);
112 _mmcam_dbg_log(" - available resource: %s", resource->name);
115 mrp_res_free_string_array(resource_names);
117 camcorder->resource_manager.is_connected = TRUE;
119 case MRP_RES_DISCONNECTED:
120 _mmcam_dbg_log(" - disconnected from Murphy");
121 if (camcorder->resource_manager.rset) {
122 mrp_res_delete_resource_set(camcorder->resource_manager.rset);
123 camcorder->resource_manager.rset = NULL;
125 if (camcorder->resource_manager.context) {
126 mrp_res_destroy(camcorder->resource_manager.context);
127 camcorder->resource_manager.context = NULL;
128 camcorder->resource_manager.is_connected = FALSE;
136 static void mrp_rset_state_callback(mrp_res_context_t *cx, const mrp_res_resource_set_t *rs, void *user_data)
139 mmf_camcorder_t *camcorder = (mmf_camcorder_t *)user_data;
140 mrp_res_resource_t *res;
142 mmf_return_if_fail((MMHandleType)camcorder);
144 if (!mrp_res_equal_resource_set(rs, camcorder->resource_manager.rset)) {
145 _mmcam_dbg_warn("- resource set(%p) is not same as this camcorder handle's(%p)", rs, camcorder->resource_manager.rset);
149 _mmcam_dbg_log(" - resource set state of camcorder(%p) is changed to [%s]", camcorder, state_to_str(rs->state));
150 for (i = 0; i < MRP_RESOURCE_MAX; i++) {
151 res = mrp_res_get_resource_by_name(rs, resource_str[i]);
153 _mmcam_dbg_warn(" -- %s not present in resource set", resource_str[i]);
155 _mmcam_dbg_log(" -- resource name [%s] -> [%s]", res->name, state_to_str(res->state));
159 mrp_res_delete_resource_set(camcorder->resource_manager.rset);
160 camcorder->resource_manager.rset = mrp_res_copy_resource_set(rs);
166 static void mrp_resource_release_cb (mrp_res_context_t *cx, const mrp_res_resource_set_t *rs, void *user_data)
169 int result = MM_ERROR_NONE;
170 int current_state = MM_CAMCORDER_STATE_NONE;
171 mmf_camcorder_t* camcorder = (mmf_camcorder_t*)user_data;
172 mrp_res_resource_t *res;
174 mmf_return_if_fail((MMHandleType)camcorder);
176 current_state = _mmcamcorder_get_state((MMHandleType)camcorder);
177 if (current_state <= MM_CAMCORDER_STATE_NONE ||
178 current_state >= MM_CAMCORDER_STATE_NUM) {
179 _mmcam_dbg_err("Abnormal state. Or null handle. (%p, %d)", camcorder, current_state);
183 /* set value to inform a status is changed by resource manaer */
184 camcorder->state_change_by_system = _MMCAMCORDER_STATE_CHANGE_BY_RM;
186 _MMCAMCORDER_LOCK_ASM(camcorder);
188 if (!mrp_res_equal_resource_set(rs, camcorder->resource_manager.rset)) {
189 _mmcam_dbg_warn("- resource set(%p) is not same as this camcorder handle's(%p)", rs, camcorder->resource_manager.rset);
193 _mmcam_dbg_log(" - resource set state of camcorder(%p) is changed to [%s]", camcorder, state_to_str(rs->state));
194 for (i = 0; i < MRP_RESOURCE_MAX; i++) {
195 res = mrp_res_get_resource_by_name(rs, resource_str[i]);
197 _mmcam_dbg_warn(" -- %s not present in resource set", resource_str[i]);
199 _mmcam_dbg_log(" -- resource name [%s] -> [%s]", res->name, state_to_str(res->state));
203 /* Stop the camera */
204 __mmcamcorder_force_stop(camcorder);
207 camcorder->state_change_by_system = _MMCAMCORDER_STATE_CHANGE_NORMAL;
209 _MMCAMCORDER_UNLOCK_ASM(camcorder);
214 static int create_rset(MMCamcorderResourceManager *resource_manager)
216 if (resource_manager->rset) {
217 _mmcam_dbg_err(" - resource set was already created\n");
218 return MM_ERROR_RESOURCE_INVALID_STATE;
221 resource_manager->rset = mrp_res_create_resource_set(resource_manager->context,
222 MRP_APP_CLASS_FOR_CAMCORDER,
223 mrp_rset_state_callback,
224 (void*)resource_manager->user_data);
225 if (resource_manager->rset == NULL) {
226 _mmcam_dbg_err(" - could not create resource set\n");
227 return MM_ERROR_RESOURCE_INTERNAL;
230 if (!mrp_res_set_autorelease(TRUE, resource_manager->rset)) {
231 _mmcam_dbg_warn(" - could not set autorelease flag!\n");
234 return MM_ERROR_NONE;
237 static int include_resource(MMCamcorderResourceManager *resource_manager, const char *resource_name)
239 mrp_res_resource_t *resource = NULL;
240 resource = mrp_res_create_resource(resource_manager->rset,
242 MRP_RESOURCE_TYPE_MANDATORY,
243 MRP_RESOURCE_TYPE_EXCLUSIVE);
244 if (resource == NULL) {
245 _mmcam_dbg_err(" - could not include resource[%s]\n", resource_name);
246 return MM_ERROR_RESOURCE_INTERNAL;
249 _mmcam_dbg_log(" - include resource[%s]\n", resource_name);
251 return MM_ERROR_NONE;
254 static int set_resource_release_cb(MMCamcorderResourceManager *resource_manager)
256 int ret = MM_ERROR_NONE;
257 bool mrp_ret = FALSE;
259 if (resource_manager->rset) {
260 mrp_ret = mrp_res_set_release_callback(resource_manager->rset, mrp_resource_release_cb, resource_manager->user_data);
262 _mmcam_dbg_err(" - could not set release callback\n");
263 ret = MM_ERROR_RESOURCE_INTERNAL;
266 _mmcam_dbg_err(" - resource set is null\n");
267 ret = MM_ERROR_RESOURCE_INVALID_STATE;
273 int _mmcamcorder_resource_manager_init(MMCamcorderResourceManager *resource_manager, void *user_data)
275 MMCAMCORDER_CHECK_RESOURCE_MANAGER_INSTANCE(resource_manager);
277 resource_manager->mloop = mrp_mainloop_glib_get(g_main_loop_new(NULL, TRUE));
278 if (resource_manager->mloop) {
279 resource_manager->context = mrp_res_create(resource_manager->mloop, mrp_state_callback, user_data);
280 if (resource_manager->context == NULL) {
281 _mmcam_dbg_err(" - could not get context for resource manager\n");
282 mrp_mainloop_destroy(resource_manager->mloop);
283 resource_manager->mloop = NULL;
284 return MM_ERROR_RESOURCE_INTERNAL;
286 resource_manager->user_data = user_data;
288 _mmcam_dbg_err("- could not get mainloop for resource manager\n");
289 return MM_ERROR_RESOURCE_INTERNAL;
292 return MM_ERROR_NONE;
295 int _mmcamcorder_resource_manager_prepare(MMCamcorderResourceManager *resource_manager, MMCamcorderResourceType resource_type)
297 int ret = MM_ERROR_NONE;
298 MMCAMCORDER_CHECK_RESOURCE_MANAGER_INSTANCE(resource_manager);
299 MMCAMCORDER_CHECK_CONNECTION_RESOURCE_MANAGER(resource_manager);
301 if (!resource_manager->rset) {
302 ret = create_rset(resource_manager);
304 if (ret == MM_ERROR_NONE) {
305 switch (resource_type) {
306 case RESOURCE_TYPE_VIDEO_OVERLAY:
307 ret = include_resource(resource_manager, resource_str[MRP_RESOURCE_FOR_VIDEO_OVERLAY]);
309 case RESOURCE_TYPE_CAMERA:
310 ret = include_resource(resource_manager, resource_str[MRP_RESOURCE_FOR_CAMERA]);
318 int _mmcamcorder_resource_manager_acquire(MMCamcorderResourceManager *resource_manager)
320 int ret = MM_ERROR_NONE;
321 MMCAMCORDER_CHECK_RESOURCE_MANAGER_INSTANCE(resource_manager);
322 MMCAMCORDER_CHECK_CONNECTION_RESOURCE_MANAGER(resource_manager);
324 if (resource_manager->rset == NULL) {
325 _mmcam_dbg_err("- could not acquire resource, resource set is null\n");
326 ret = MM_ERROR_RESOURCE_INVALID_STATE;
328 ret = set_resource_release_cb(resource_manager);
330 _mmcam_dbg_err("- could not set resource release cb, ret(%d)\n", ret);
331 ret = MM_ERROR_RESOURCE_INTERNAL;
333 ret = mrp_res_acquire_resource_set(resource_manager->rset);
335 _mmcam_dbg_err("- could not acquire resource, ret(%d)\n", ret);
336 ret = MM_ERROR_RESOURCE_INTERNAL;
344 int _mmcamcorder_resource_manager_release(MMCamcorderResourceManager *resource_manager)
346 int ret = MM_ERROR_NONE;
347 MMCAMCORDER_CHECK_RESOURCE_MANAGER_INSTANCE(resource_manager);
348 MMCAMCORDER_CHECK_CONNECTION_RESOURCE_MANAGER(resource_manager);
350 if (resource_manager->rset == NULL) {
351 _mmcam_dbg_err("- could not release resource, resource set is null\n");
352 ret = MM_ERROR_RESOURCE_INVALID_STATE;
354 if (resource_manager->rset->state != MRP_RES_RESOURCE_ACQUIRED) {
355 _mmcam_dbg_err("- could not release resource, resource set state is [%s]\n", state_to_str(resource_manager->rset->state));
356 ret = MM_ERROR_RESOURCE_INVALID_STATE;
358 ret = mrp_res_release_resource_set(resource_manager->rset);
360 _mmcam_dbg_err("- could not release resource, ret(%d)\n", ret);
361 ret = MM_ERROR_RESOURCE_INTERNAL;
369 int _mmcamcorder_resource_manager_unprepare(MMCamcorderResourceManager *resource_manager)
371 int ret = MM_ERROR_NONE;
372 MMCAMCORDER_CHECK_RESOURCE_MANAGER_INSTANCE(resource_manager);
373 MMCAMCORDER_CHECK_CONNECTION_RESOURCE_MANAGER(resource_manager);
375 if (resource_manager->rset == NULL) {
376 _mmcam_dbg_err("- could not unprepare for resource_manager, _mmcamcorder_resource_manager_prepare() first\n");
377 ret = MM_ERROR_RESOURCE_INVALID_STATE;
379 mrp_res_delete_resource_set(resource_manager->rset);
380 resource_manager->rset = NULL;
386 int _mmcamcorder_resource_manager_deinit(MMCamcorderResourceManager *resource_manager)
388 MMCAMCORDER_CHECK_RESOURCE_MANAGER_INSTANCE(resource_manager);
389 MMCAMCORDER_CHECK_CONNECTION_RESOURCE_MANAGER(resource_manager);
391 if (resource_manager->rset) {
392 if (resource_manager->rset->state == MRP_RES_RESOURCE_ACQUIRED) {
393 if (mrp_res_release_resource_set(resource_manager->rset))
394 _mmcam_dbg_err("- could not release resource");
396 mrp_res_delete_resource_set(resource_manager->rset);
397 resource_manager->rset = NULL;
399 if (resource_manager->context) {
400 mrp_res_destroy(resource_manager->context);
401 resource_manager->context = NULL;
403 if (resource_manager->mloop) {
404 mrp_mainloop_destroy(resource_manager->mloop);
405 resource_manager->mloop = NULL;
408 return MM_ERROR_NONE;