f5a8bf58e8bb00f79749625483369c943f879292
[platform/core/api/maps-service.git] / src / plugin / module.cpp
1 /* Copyright (c) 2010-2014 Samsung Electronics Co., Ltd. All rights reserved.
2  *
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 #include <glib/gstdio.h>
18 #include "module.h"
19 #include "maps_util.h"
20 #include "thread.h"
21 #include "command.h"
22 #include "command_queue.h"
23 #include "empty_module.h"
24
25 plugin::scope_mutex::scope_mutex(GMutex *m) : mutex(m)
26 {
27         g_mutex_lock(mutex);
28 }
29
30 plugin::scope_mutex::~scope_mutex()
31 {
32         g_mutex_unlock(mutex);
33 }
34
35 plugin::binary_extractor::binary_extractor()
36 {
37 }
38
39 plugin::provider_info plugin::binary_extractor::get_plugin_info(const
40                                                         string &file_name) const
41 {
42         if (file_name.empty())
43                 return provider_info::empty_instance;
44
45         /* 1.Initialize plugin */
46         GMod *plugin = gmod_new(file_name, FALSE);
47         if (!plugin)
48                 return provider_info::empty_instance;
49
50         provider_info info;
51
52         /* 2. Get plugin info */
53         maps_plugin_get_info_f func =
54                 (maps_plugin_get_info_f) gmod_find_sym(plugin,
55                 "maps_plugin_get_info");
56         if (func) {
57                 maps_plugin_info_h i;
58                 if (func(&i) == MAPS_ERROR_NONE) {
59                         char *provider_name = NULL;
60                         maps_plugin_info_get_provider_name(i, &provider_name);
61
62                         /* Convert plugin info to provider info */
63                         info.construct(string(provider_name), file_name);
64
65                         g_free(provider_name);
66                 }
67                 maps_plugin_info_destroy(i);
68         }
69
70         /* 3. shutdown plugin */
71         gmod_free(plugin);
72
73         return info;
74 }
75
76 maps_plugin_h plugin::binary_extractor::init(const provider_info &info,
77                                              const char *module, int *init_error)
78 {
79         /* 1.Initialize plugin */
80         if (info.file.empty() || !init_error) {
81                 if (init_error)
82                         *init_error = MAPS_ERROR_NOT_SUPPORTED;
83                 return NULL;
84         }
85
86         *init_error = MAPS_ERROR_NONE;
87
88         GMod *plugin = gmod_new(info.file, TRUE);
89         if (!plugin) {
90                 MAPS_LOGE("Open Module Failed: %s", info.file.c_str());
91                 *init_error = MAPS_ERROR_SERVICE_NOT_AVAILABLE;
92                 return NULL;
93         }
94
95         /* 2.1 Create new plugin interface */
96         plugin_s* new_plugin = g_slice_new0(plugin_s);
97
98         /* 2. Perform steps to completely initialize a plugin */
99         do {
100                 if (!new_plugin) {
101                         MAPS_LOGE("OUT_OF_MEMORY(0x%08x)", MAPS_ERROR_OUT_OF_MEMORY);
102                         *init_error = MAPS_ERROR_OUT_OF_MEMORY;
103                         break;
104                 }
105
106                 /* 2.1 Set plugin module handle */
107                 new_plugin->module = plugin;
108
109                 /* 2.2 Set plugin interface */
110                 new_plugin->interface = get_empty_interface();
111
112                 /* Plugin dedicated functions */
113                 new_plugin->interface.maps_plugin_init =
114                         (maps_plugin_init_f) gmod_find_sym(plugin,
115                         "maps_plugin_init");
116                 new_plugin->interface.maps_plugin_init_module =
117                         (maps_plugin_init_module_f) gmod_find_sym(plugin,
118                         "maps_plugin_init_module");
119                 new_plugin->interface.maps_plugin_shutdown =
120                         (maps_plugin_shutdown_f) gmod_find_sym(plugin,
121                         "maps_plugin_shutdown");
122                 new_plugin->interface.maps_plugin_get_info =
123                         (maps_plugin_get_info_f) gmod_find_sym(plugin,
124                         "maps_plugin_get_info");
125                 new_plugin->interface.maps_plugin_request_user_consent =
126                         (maps_plugin_request_user_consent_f) gmod_find_sym(plugin,
127                         "maps_plugin_request_user_consent");
128
129                 /* Maps Provider access key, preference and capabilities */
130                 new_plugin->interface.maps_plugin_set_provider_key =
131                         (maps_plugin_set_provider_key_f) gmod_find_sym(plugin,
132                         "maps_plugin_set_provider_key");
133                 new_plugin->interface.maps_plugin_get_provider_key =
134                         (maps_plugin_get_provider_key_f) gmod_find_sym(plugin,
135                         "maps_plugin_get_provider_key");
136                 new_plugin->interface.maps_plugin_set_preference =
137                         (maps_plugin_set_preference_f) gmod_find_sym(plugin,
138                         "maps_plugin_set_preference");
139                 new_plugin->interface.maps_plugin_get_preference =
140                         (maps_plugin_get_preference_f) gmod_find_sym(plugin,
141                         "maps_plugin_get_preference");
142                 new_plugin->interface.maps_plugin_is_service_supported =
143                         (maps_plugin_is_service_supported_f) gmod_find_sym(plugin,
144                         "maps_plugin_is_service_supported");
145                 new_plugin->interface.maps_plugin_is_data_supported =
146                         (maps_plugin_is_data_supported_f) gmod_find_sym(plugin,
147                         "maps_plugin_is_data_supported");
148
149                 /* Geocode */
150                 new_plugin->interface.maps_plugin_geocode =
151                         (maps_plugin_geocode_f) gmod_find_sym(plugin,
152                         "maps_plugin_geocode");
153                 new_plugin->interface.maps_plugin_geocode_inside_area =
154                         (maps_plugin_geocode_inside_area_f) gmod_find_sym(plugin,
155                         "maps_plugin_geocode_inside_area");
156                 new_plugin->interface.maps_plugin_geocode_by_structured_address =
157                         (maps_plugin_geocode_by_structured_address_f) gmod_find_sym(plugin,
158                         "maps_plugin_geocode_by_structured_address");
159                 new_plugin->interface.maps_plugin_reverse_geocode =
160                         (maps_plugin_reverse_geocode_f) gmod_find_sym(plugin,
161                         "maps_plugin_reverse_geocode");
162                 new_plugin->interface.maps_plugin_multi_reverse_geocode =
163                         (maps_plugin_multi_reverse_geocode_f) gmod_find_sym(plugin,
164                         "maps_plugin_multi_reverse_geocode");
165
166                 /* Place */
167                 new_plugin->interface.maps_plugin_search_place =
168                         (maps_plugin_search_place_f) gmod_find_sym(plugin,
169                         "maps_plugin_search_place");
170                 new_plugin->interface.maps_plugin_search_place_by_area =
171                         (maps_plugin_search_place_by_area_f) gmod_find_sym(plugin,
172                         "maps_plugin_search_place_by_area");
173                 new_plugin->interface.maps_plugin_search_place_by_address =
174                         (maps_plugin_search_place_by_address_f) gmod_find_sym(plugin,
175                         "maps_plugin_search_place_by_address");
176                 new_plugin->interface.maps_plugin_search_place_list =
177                         (maps_plugin_search_place_list_f) gmod_find_sym(plugin,
178                         "maps_plugin_search_place_list");
179                 new_plugin->interface.maps_plugin_get_place_details =
180                         (maps_plugin_get_place_details_f) gmod_find_sym(plugin,
181                         "maps_plugin_get_place_details");
182
183                 /* Route */
184                 new_plugin->interface.maps_plugin_search_route =
185                         (maps_plugin_search_route_f) gmod_find_sym(plugin,
186                         "maps_plugin_search_route");
187                 new_plugin->interface.maps_plugin_search_route_waypoints =
188                         (maps_plugin_search_route_waypoints_f) gmod_find_sym(plugin,
189                         "maps_plugin_search_route_waypoints");
190
191                 /* Cancel Request */
192                 new_plugin->interface.maps_plugin_cancel_request =
193                         (maps_plugin_cancel_request_f) gmod_find_sym(plugin,
194                         "maps_plugin_cancel_request");
195
196                 /* Mapping */
197                 new_plugin->interface.maps_plugin_create_map_view =
198                         (maps_plugin_create_map_view_f) gmod_find_sym(plugin,
199                         "maps_plugin_create_map_view");
200                 new_plugin->interface.maps_plugin_destroy_map_view =
201                         (maps_plugin_destroy_map_view_f) gmod_find_sym(plugin,
202                         "maps_plugin_destroy_map_view");
203                 new_plugin->interface.maps_plugin_render_map =
204                         (maps_plugin_render_map_f) gmod_find_sym(plugin,
205                         "maps_plugin_render_map");
206                 new_plugin->interface.maps_plugin_move_center =
207                         (maps_plugin_move_center_f) gmod_find_sym(plugin,
208                         "maps_plugin_move_center");
209                 new_plugin->interface.maps_plugin_set_scalebar =
210                         (maps_plugin_set_scalebar_f) gmod_find_sym(plugin,
211                         "maps_plugin_set_scalebar");
212                 new_plugin->interface.maps_plugin_get_scalebar =
213                         (maps_plugin_get_scalebar_f) gmod_find_sym(plugin,
214                         "maps_plugin_get_scalebar");
215                 new_plugin->interface.maps_plugin_on_object =
216                         (maps_plugin_on_object_f) gmod_find_sym(plugin,
217                         "maps_plugin_on_object");
218                 new_plugin->interface.maps_plugin_screen_to_geography =
219                         (maps_plugin_screen_to_geography_f) gmod_find_sym(plugin,
220                         "maps_plugin_screen_to_geography");
221                 new_plugin->interface.maps_plugin_geography_to_screen =
222                         (maps_plugin_geography_to_screen_f) gmod_find_sym(plugin,
223                         "maps_plugin_geography_to_screen");
224                 new_plugin->interface.maps_plugin_get_min_zoom_level =
225                         (maps_plugin_get_min_zoom_level_f) gmod_find_sym(plugin,
226                         "maps_plugin_get_min_zoom_level");
227                 new_plugin->interface.maps_plugin_get_max_zoom_level =
228                         (maps_plugin_get_max_zoom_level_f) gmod_find_sym(plugin,
229                         "maps_plugin_get_max_zoom_level");
230                 new_plugin->interface.maps_plugin_get_center =
231                         (maps_plugin_get_center_f) gmod_find_sym(plugin,
232                         "maps_plugin_get_center");
233                 new_plugin->interface.maps_plugin_capture_snapshot =
234                         (maps_plugin_capture_snapshot_f) gmod_find_sym(plugin,
235                         "maps_plugin_capture_snapshot");
236                 new_plugin->interface.maps_plugin_get_view_scale_factor =
237                         (maps_plugin_get_view_scale_factor_f) gmod_find_sym(plugin,
238                         "maps_plugin_get_view_scale_factor");
239                 new_plugin->interface.maps_plugin_set_view_scale_factor =
240                         (maps_plugin_set_view_scale_factor_f) gmod_find_sym(plugin,
241                         "maps_plugin_set_view_scale_factor");
242
243                 /* 2.3 Check whether the plugin init function is valid */
244                 if (!new_plugin->interface.maps_plugin_init) {
245                         MAPS_LOGE("ERROR! Plugin initialization function is invalid");
246                         *init_error = MAPS_ERROR_SERVICE_NOT_AVAILABLE;
247                         break;
248                 }
249
250                 /* 2.4 Call a plugin to initialize itself, send to the plugin
251                 *  its pointer */
252                 int ret;
253                 if (!module || !new_plugin->interface.maps_plugin_init_module)
254                         ret = new_plugin->interface.maps_plugin_init((maps_plugin_h *) (&new_plugin));
255                 else
256                         ret = new_plugin->interface.maps_plugin_init_module((maps_plugin_h *) (&new_plugin), module);
257
258                 if (ret != MAPS_ERROR_NONE) {
259                         MAPS_LOGE("ERROR! Plugin initialization function failed: %d", ret);
260                         *init_error = ret;
261                         break;
262                 }
263
264                 if (!new_plugin->interface.maps_plugin_set_provider_key) {
265                         MAPS_LOGE("ERROR! Plugin set_provider_key function is NULL");
266                         *init_error = MAPS_ERROR_SERVICE_NOT_AVAILABLE;
267                         break;
268                 }
269
270                 if (!new_plugin->interface.maps_plugin_get_provider_key) {
271                         MAPS_LOGE("ERROR! Plugin set_provider_key function is NULL");
272                         *init_error = MAPS_ERROR_SERVICE_NOT_AVAILABLE;
273                         break;
274                 }
275
276                 if (!new_plugin->interface.maps_plugin_set_preference) {
277                         MAPS_LOGE("ERROR! Plugin set_preference function is NULL");
278                         *init_error = MAPS_ERROR_SERVICE_NOT_AVAILABLE;
279                         break;
280                 }
281
282                 if (!new_plugin->interface.maps_plugin_get_preference) {
283                         MAPS_LOGE("ERROR! Plugin get_preference function is NULL");
284                         *init_error = MAPS_ERROR_SERVICE_NOT_AVAILABLE;
285                         break;
286                 }
287
288                 if (!new_plugin->interface.maps_plugin_is_data_supported) {
289                         MAPS_LOGE("ERROR! Plugin support_is_data_supported function is NULL");
290                         *init_error = MAPS_ERROR_SERVICE_NOT_AVAILABLE;
291                         break;
292                 }
293
294                 if (!new_plugin->interface.maps_plugin_is_service_supported) {
295                         MAPS_LOGE("ERROR! Plugin support_is_service_supported function is NULL");
296                         *init_error = MAPS_ERROR_SERVICE_NOT_AVAILABLE;
297                         break;
298                 }
299
300                 /* 2.7 Create a queue with asynchronous requests to plugin */
301                 if (session::command_queue::is_async())
302                         new_plugin->request_queue = g_async_queue_new();
303
304                 /* 2.8 Initialize the mutex for the map of pending requests */
305                 new_plugin->pending_request_maps =
306                         g_hash_table_new_full(g_int_hash, g_int_equal, g_free,
307                         session::command_handler::destroy);
308                 if (!new_plugin->pending_request_maps) {
309                         MAPS_LOGE("OUT_OF_MEMORY(0x%08x)", MAPS_ERROR_OUT_OF_MEMORY);
310                         *init_error = MAPS_ERROR_OUT_OF_MEMORY;
311                         break;
312                 }
313                 g_mutex_init(&new_plugin->pending_request_mutex);
314
315                 /* DEBUG TRACE */
316                 trace_dbg(new_plugin);
317
318                 /* 2.5 Return newly initialized plugin */
319                 return new_plugin;
320         } while (FALSE);
321
322         MAPS_LOGE("Shut down the plugin becuause of error");
323
324         /* 3. shutdown plugin in case of problem */
325         shutdown(new_plugin);
326         return NULL;
327 }
328
329 void plugin::binary_extractor::shutdown(maps_plugin_h plugin_h)
330 {
331         if (!plugin_h)
332                 return;
333
334         plugin_s *plugin = (plugin_s *) plugin_h;
335         g_return_if_fail(plugin->module);
336
337         /* 0. shutdown plugin */
338         if (plugin->interface.maps_plugin_shutdown)
339                 plugin->interface.maps_plugin_shutdown(plugin);
340
341         /* 1. Stop the thread, processing the request queue */
342         session::thread().stop(plugin);
343
344         /* 2. Destroy the request queue */
345         if (plugin->request_queue)
346                 g_async_queue_unref(plugin->request_queue);
347
348         /* 3. Destroy the map of pending requests */
349         if (plugin->pending_request_maps) {
350                 g_hash_table_unref(plugin->pending_request_maps);
351
352                 /* Clear the mutex for the map of pending requests */
353                 g_mutex_clear(&plugin->pending_request_mutex);
354         }
355
356         /* 4. Unload plugin from memory */
357         gmod_free((GMod *) plugin->module);
358
359         /* 5. Destroying the table with plugin capabilities */
360         /*maps_int_hashtable_destroy(plugin->capabilities); */
361
362         /* 6. Release memory used by plugin structure */
363         g_slice_free(plugin_s, plugin);
364 }
365
366 /* Open the binary (which contains a plugin) */
367 plugin::GMod *plugin::binary_extractor::gmod_new(const string &module_file,
368                                                  gboolean is_resident) const
369 {
370         if (!g_module_supported()) {
371                 MAPS_LOGE("ERROR! g_module_supported is false\n\n");
372                 return NULL;
373         }
374
375         if (module_file.empty())
376                 return NULL;
377
378         GMod *gmod = g_new0(GMod, 1);
379
380         gmod->name = g_strdup(module_file.c_str());
381         if (!gmod->name) {
382                 g_free(gmod);
383                 return NULL;
384         }
385
386         gmod->path = g_strnfill(100, 0);
387         g_sprintf(gmod->path, "%s/%s", MAPS_PLUGINS_PATH_PREFIX, gmod->name);
388         if (!gmod->path) {
389                 g_free(gmod->name);
390                 g_free(gmod);
391                 return NULL;
392         }
393
394         gmod->module = g_module_open(gmod->path, G_MODULE_BIND_LAZY);
395         if (!gmod->module) {
396                 MAPS_LOGE("module path not found: %s", gmod->path);
397
398                 const gchar *last_error = g_module_error();
399                 MAPS_LOGE("last module error: %s", last_error);
400
401                 g_free(gmod->name);
402                 g_free(gmod->path);
403                 g_free(gmod);
404                 return NULL;
405         }
406         MAPS_LOGD("open module");
407         /*if (is_resident)
408                 g_module_make_resident(gmod->module);*/
409
410         return gmod;
411 }
412
413 /* Close the binary (which contains a plugin) */
414 void plugin::binary_extractor::gmod_free(GMod *gmod) const
415 {
416         /*g_return_if_fail(gmod); */
417         if (!gmod)
418                 return;
419
420         if (gmod->name)
421                 g_free(gmod->name);
422         if (gmod->path)
423                 g_free(gmod->path);
424         if (gmod->module)
425                 g_module_close(gmod->module);
426         g_free(gmod);
427
428         MAPS_LOGD("close module");
429         MAPS_LOGD("last module error: %s", g_module_error());
430 }
431
432 /* Find the address of a function in a binary (which contains a plugin) */
433 gpointer plugin::binary_extractor::gmod_find_sym(GMod *gmod,
434                                                  const gchar *func_name) const
435 {
436         g_return_val_if_fail(gmod, NULL);
437         g_return_val_if_fail(func_name, NULL);
438
439         gpointer func_ptr = NULL;
440         if (!g_module_symbol(gmod->module, func_name, &func_ptr)) {
441                 MAPS_LOGE("function symbol not found");
442                 MAPS_LOGE("%s", g_module_error());
443                 func_ptr = NULL;
444         }
445         return func_ptr;
446 }
447
448 void plugin::binary_extractor::trace_dbg(const plugin_s *plugin) const
449 {
450         MAPS_LOGD("*********************************************");
451         MAPS_LOGD("PLUGIN INFO");
452         if (!plugin) {
453                 MAPS_LOGD("PLUGIN is NULL");
454                 MAPS_LOGD("*********************************************");
455                 return;
456         }
457
458         const GMod *mod = (const GMod *) plugin->module;
459         if (!mod) {
460                 MAPS_LOGD("PLUGIN module is NULL");
461         } else {
462                 MAPS_LOGD("module address:\t\t\t%p", mod->module);
463                 MAPS_LOGD("module name:\t\t\t%s", mod->name);
464                 MAPS_LOGD("module path:\t\t\t%s", mod->path);
465         }
466
467         if (!plugin->request_queue) {
468                 MAPS_LOGD("PLUGIN request queue is NULL");
469         } else {
470                 MAPS_LOGD("plugin request queue:\t\t\t%p", plugin->request_queue);
471         }
472
473         const interface_s *itf = &plugin->interface;
474         MAPS_LOGD("maps_plugin_init:\t\t\t%p", itf->maps_plugin_init);
475         MAPS_LOGD("maps_plugin_shutdown:\t\t\t%p", itf->maps_plugin_shutdown);
476         MAPS_LOGD("maps_plugin_get_info:\t\t\t%p", itf->maps_plugin_get_info);
477
478         /* Maps Provider access key */
479         MAPS_LOGD("maps_plugin_set_provider_key:\t\t%p",
480                 itf->maps_plugin_set_provider_key);
481         MAPS_LOGD("maps_plugin_get_provider_key:\t\t%p",
482                 itf->maps_plugin_get_provider_key);
483         MAPS_LOGD("maps_plugin_is_service_supported:\t%p",
484                 itf->maps_plugin_is_service_supported);
485         MAPS_LOGD("maps_plugin_is_data_supported:\t\t%p",
486                 itf->maps_plugin_is_data_supported);
487
488         MAPS_LOGD("maps_plugin_geocode:\t\t\t%p", itf->maps_plugin_geocode);
489         MAPS_LOGD("maps_plugin_geocode_inside_area:\t%p",
490                 itf->maps_plugin_geocode_inside_area);
491         MAPS_LOGD("maps_plugin_geocode_by_structured_address: %p",
492                 itf->maps_plugin_geocode_by_structured_address);
493         MAPS_LOGD("maps_plugin_reverse_geocode:\t\t%p",
494                 itf->maps_plugin_reverse_geocode);
495         MAPS_LOGD("maps_plugin_multi_reverse_geocode:\t%p",
496                 itf->maps_plugin_multi_reverse_geocode);
497
498         MAPS_LOGD("maps_plugin_search_place:\t\t%p",
499                 itf->maps_plugin_search_place);
500         MAPS_LOGD("maps_plugin_search_place_by_area:\t%p",
501                 itf->maps_plugin_search_place_by_area);
502         MAPS_LOGD("maps_plugin_search_place_by_address:\t%p",
503                 itf->maps_plugin_search_place_by_address);
504         MAPS_LOGD("maps_plugin_search_place_list:\t\t%p",
505                 itf->maps_plugin_search_place_list);
506         MAPS_LOGD("maps_plugin_get_place_details:\t%p",
507                 itf->maps_plugin_get_place_details);
508
509         MAPS_LOGD("maps_plugin_search_route:\t\t%p",
510                 itf->maps_plugin_search_route);
511         MAPS_LOGD("maps_plugin_search_route_waypoints:\t%p",
512                 itf->maps_plugin_search_route_waypoints);
513
514         MAPS_LOGD("maps_plugin_cancel_request:\t\t%p",
515                 itf->maps_plugin_cancel_request);
516
517         MAPS_LOGD("maps_plugin_create_map_view:\t\t%p",
518                 itf->maps_plugin_create_map_view);
519         MAPS_LOGD("maps_plugin_destroy_map_view:\t\t%p",
520                 itf->maps_plugin_destroy_map_view);
521         MAPS_LOGD("maps_plugin_capture_snapshot:\t\t%p",
522                 itf->maps_plugin_capture_snapshot);
523         MAPS_LOGD("*********************************************");
524 }
525
526 plugin::user_consent_checker::user_consent_checker()
527 {
528 }
529
530 maps_plugin_h plugin::user_consent_checker::init(const provider_info &info,
531                                              const char *module, int *init_error)
532 {
533         /* 1.Initialize plugin */
534         if (info.file.empty() || !init_error) {
535                 if (init_error)
536                         *init_error = MAPS_ERROR_NOT_SUPPORTED;
537                 return NULL;
538         }
539
540         *init_error = MAPS_ERROR_NONE;
541
542         GMod *plugin = gmod_new(info.file, TRUE);
543         if (!plugin) {
544                 MAPS_LOGE("Open Module Failed: %s", info.file.c_str());
545                 *init_error = MAPS_ERROR_SERVICE_NOT_AVAILABLE;
546                 return NULL;
547         }
548
549         /* 2.1 Create new plugin interface */
550         plugin_s* new_plugin = g_slice_new0(plugin_s);
551
552         /* 2. Perform steps to completely initialize a plugin */
553         do {
554                 if (!new_plugin) {
555                         MAPS_LOGE("OUT_OF_MEMORY(0x%08x)", MAPS_ERROR_OUT_OF_MEMORY);
556                         *init_error = MAPS_ERROR_OUT_OF_MEMORY;
557                         break;
558                 }
559
560                 /* 2.1 Set plugin module handle */
561                 new_plugin->module = plugin;
562
563                 /* 2.2 Set plugin interface */
564                 new_plugin->interface = get_empty_interface();
565
566                 /* Plugin dedicated functions */
567                 new_plugin->interface.maps_plugin_request_user_consent =
568                         (maps_plugin_request_user_consent_f) gmod_find_sym(plugin,
569                         "maps_plugin_request_user_consent");
570
571                 if (!new_plugin->interface.maps_plugin_request_user_consent) {
572                         MAPS_LOGE("ERROR! Plugin request_user_consent function is NULL");
573                         *init_error = MAPS_ERROR_SERVICE_NOT_AVAILABLE;
574                         break;
575                 }
576
577                 /* 2.5 Return newly initialized plugin */
578                 return new_plugin;
579         } while (FALSE);
580
581         MAPS_LOGE("Shut down the plugin becuause of error");
582
583         /* 3. shutdown plugin in case of problem */
584         shutdown(new_plugin);
585         return NULL;
586 }
587
588 void plugin::user_consent_checker::shutdown(maps_plugin_h plugin_h)
589 {
590         if (!plugin_h)
591                 return;
592         plugin_s *plugin = (plugin_s *) plugin_h;
593         g_return_if_fail(plugin->module);
594
595         /* 4. Unload plugin from memory */
596         gmod_free((GMod *) plugin->module);
597
598         /* 5. Destroying the table with plugin capabilities */
599         /*maps_int_hashtable_destroy(plugin->capabilities); */
600
601         /* 6. Release memory used by plugin structure */
602         g_slice_free(plugin_s, plugin);
603 }