4 * Copyright (c) 2010-2013 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.
28 #include "module-internal.h"
29 #include "location-log.h"
31 #define MAX_MODULE_INDEX 4
33 #define MODULE_PATH_PREFIX LIBDIR"/location/module"
35 static GMod *gmod_new(const char *module_name, gboolean is_resident)
40 GMod *gmod = g_new0(GMod, 1);
41 gmod->name = g_strdup(module_name);
47 char *module_path = g_strndup(MODULE_PATH_PREFIX, strlen(MODULE_PATH_PREFIX)+1);
48 /* gmod->path = g_module_build_path(MODULE_PATH_PREFIX, gmod->name); */
49 gmod->path = g_module_build_path(module_path, gmod->name);
57 gmod->module = g_module_open(gmod->path, G_MODULE_BIND_LAZY);
65 g_module_make_resident(gmod->module);
70 static void gmod_free(GMod *gmod)
77 g_module_close(gmod->module);
82 gmod_find_sym(GMod *gmod, gpointer *init_func, gpointer *shutdown_func)
85 g_stpcpy(sym, "init");
86 if (!g_module_symbol(gmod->module, sym, init_func)) {
87 LOCATION_LOGW("symbol not found: %s", sym);
90 g_stpcpy(sym, "shutdown");
91 if (!g_module_symbol(gmod->module, sym, shutdown_func)) {
92 LOCATION_LOGW("symbol not found: %s", sym);
98 static gpointer mod_new(const char *module_name)
100 gpointer ret_mod = NULL;
105 gpointer init = NULL;
106 gpointer shutdown = NULL;
107 gmod = gmod_new(module_name, TRUE);
109 LOCATION_LOGW("module(%s) new failed", module_name);
112 if (!gmod_find_sym(gmod, &init, &shutdown)) {
113 LOCATION_LOGW("symbol (init, shutdown) finding failed");
117 if (!init || !shutdown) {
118 LOCATION_LOGW("init, shutdown symbol is NULL");
122 if (g_str_has_prefix(module_name, "gps")) {
123 LocationGpsMod *_mod = g_new0(LocationGpsMod, 1);
126 _mod->shutdown = shutdown;
127 _mod->handler = _mod->init(&(_mod->ops));
128 if (!_mod->handler) {
129 LOCATION_LOGW("module init failed : gps");
130 gmod_free(_mod->gmod);
133 ret_mod = (gpointer) _mod;
134 } else if (g_str_has_prefix(module_name, "wps")) {
135 LocationWpsMod *_mod = g_new0(LocationWpsMod, 1);
138 _mod->shutdown = shutdown;
139 _mod->handler = _mod->init(&(_mod->ops));
140 if (!_mod->handler) {
141 LOCATION_LOGW("module init failed : wps");
142 gmod_free(_mod->gmod);
145 ret_mod = (gpointer) _mod;
146 } else if (g_str_has_prefix(module_name, "passive")) {
147 LocationPassiveMod *_mod = g_new0(LocationPassiveMod, 1);
150 _mod->shutdown = shutdown;
151 _mod->handler = _mod->init(&(_mod->ops));
152 if (!_mod->handler) {
153 LOCATION_LOGW("module init failed : passive");
154 gmod_free(_mod->gmod);
157 ret_mod = (gpointer) _mod;
158 } else if (g_str_has_prefix(module_name, "fused")) {
159 LocationFusedMod *_mod = g_new0(LocationFusedMod, 1);
162 _mod->shutdown = shutdown;
163 _mod->handler = _mod->init(&(_mod->ops));
164 if (!_mod->handler) {
165 LOCATION_LOGW("module init failed : fused");
166 gmod_free(_mod->gmod);
169 ret_mod = (gpointer) _mod;
171 LOCATION_LOGW("module name (%s) is wrong", module_name);
177 static void mod_free(gpointer mod, const char *module_name)
179 if (!mod || !module_name)
182 if (0 == g_strcmp0(module_name, "gps")) {
183 LocationGpsMod *_mod = (LocationGpsMod *) mod;
184 if (_mod->shutdown && _mod->handler)
185 _mod->shutdown(_mod->handler);
187 _mod->handler = NULL;
189 _mod->shutdown = NULL;
190 gmod_free(_mod->gmod);
192 } else if (0 == g_strcmp0(module_name, "wps")) {
193 LocationWpsMod *_mod = (LocationWpsMod *) mod;
194 if (_mod->shutdown && _mod->handler)
195 _mod->shutdown(_mod->handler);
197 _mod->handler = NULL;
199 _mod->shutdown = NULL;
200 gmod_free(_mod->gmod);
202 } else if (0 == g_strcmp0(module_name, "passive")) {
203 LocationPassiveMod *_mod = (LocationPassiveMod *)mod;
204 if (_mod->shutdown && _mod->handler)
205 _mod->shutdown(_mod->handler);
207 _mod->handler = NULL;
209 _mod->shutdown = NULL;
210 gmod_free(_mod->gmod);
212 } else if (0 == g_strcmp0(module_name, "fused")) {
213 LocationFusedMod *_mod = (LocationFusedMod *) mod;
214 if (_mod->shutdown && _mod->handler)
215 _mod->shutdown(_mod->handler);
217 _mod->handler = NULL;
219 _mod->shutdown = NULL;
220 gmod_free(_mod->gmod);
223 LOCATION_LOGW("module name (%s) is wrong", module_name);
229 static gboolean mod_is_supported(const char *module_name)
232 gmod = gmod_new(module_name, FALSE);
241 gboolean module_init(void)
243 if (!g_module_supported()) {
244 LOCATION_LOGW("module is not supported");
250 void module_free(gpointer mod, const char *module_name)
252 if (!mod || !module_name)
254 mod_free(mod, module_name);
257 gpointer module_new(const char *module_name)
267 for (index = -1; index < MAX_MODULE_INDEX; index++) {
269 if (0 >= g_snprintf(name, 256, "%s%d", module_name, index)) {
270 LOCATION_LOGW("module name(%s) is wrong", name);
274 if (0 >= g_snprintf(name, 256, "%s", module_name)) {
275 LOCATION_LOGW("module name(%s) is wrong", name);
281 LOCATION_LOGW("module (%s) open success", name);
284 LOCATION_LOGW("module (%s) open failed", name);
287 if (0 >= g_snprintf(name, 256, "%s", module_name)) {
288 LOCATION_LOGW("module name(%s) is wrong", name);
292 LOCATION_LOGW("module (%s) open success", name);
294 LOCATION_LOGW("module (%s) open failed", name);
299 gboolean module_is_supported(const char *module_name)
305 gboolean ret = FALSE;
306 gboolean found = FALSE;
308 char name[256] = { 0, };
310 for (index = -1; index < MAX_MODULE_INDEX; index++) {
312 g_snprintf(name, 256, "%s%d", module_name, index);
314 g_snprintf(name, 256, "%s", module_name);
316 ret = mod_is_supported(name);
319 LOCATION_LOGW("module name(%s) is found", name);
327 gchar *mod_get_realpath(const gchar *module_name)
329 gchar origin_path[PATH_MAX] = { 0, };
330 gchar link_path[PATH_MAX] = { 0, };
333 snprintf(link_path, PATH_MAX, "%s/lib%s.so", MODULE_PATH_PREFIX, module_name);
335 if (realpath(link_path, origin_path) == NULL || strlen(origin_path) == 0) {
336 LOCATION_LOGE("Fail to get real path of [%s]", module_name);
340 path = strrchr(origin_path, '/');
344 return g_strdup(path);