diff options
author | Emre Ucan <eucan@de.adit-jv.com> | 2019-04-09 14:49:01 +0200 |
---|---|---|
committer | Emre Ucan <eucan@de.adit-jv.com> | 2019-04-09 14:49:01 +0200 |
commit | e9c2fe4c5034a06b159cfd45dbd485755cbaf4c8 (patch) | |
tree | 19f440848758df57fdf8b14ad58ee323ee70ac9d | |
parent | 10584b4d55c231a11964db0191c3707459982d4b (diff) | |
parent | 7f286a27564fe8e8101afee3295b7a2b7b52a605 (diff) | |
download | wayland-ivi-extension-e9c2fe4c5034a06b159cfd45dbd485755cbaf4c8.tar.gz |
Merge remote-tracking branch 'upstream/pull/105'
* upstream/pull/105
ivi-controller: load id-agent module
ivi-id-agent: added ivi-id-agent
Added ivi-id-agent to CMake
Reviewed-by: Eugen Friedrich <efriedrich@de.adit-jv.com>
Reviewed-by: Emre Ucan <eucan@de.adit-jv.com>
Tested-by: Emre Ucan <eucan@de.adit-jv.com>
-rw-r--r-- | CMakeLists.txt | 1 | ||||
-rw-r--r-- | ivi-id-agent-modules/ivi-id-agent/CMakeLists.txt | 69 | ||||
-rw-r--r-- | ivi-id-agent-modules/ivi-id-agent/src/ivi-id-agent.c | 381 | ||||
-rw-r--r-- | ivi-id-agent-modules/ivi-id-agent/weston.ini.in | 20 | ||||
-rw-r--r-- | weston-ivi-shell/src/ivi-controller.c | 36 |
5 files changed, 507 insertions, 0 deletions
diff --git a/CMakeLists.txt b/CMakeLists.txt index 7d0044a..988fc89 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -40,6 +40,7 @@ add_subdirectory(ivi-layermanagement-api/test) add_subdirectory(ivi-layermanagement-examples) add_subdirectory(ivi-layermanagement-api/ilmInput) add_subdirectory(ivi-input-modules/ivi-input-controller) +add_subdirectory(ivi-id-agent-modules/ivi-id-agent) #============================================================================================= diff --git a/ivi-id-agent-modules/ivi-id-agent/CMakeLists.txt b/ivi-id-agent-modules/ivi-id-agent/CMakeLists.txt new file mode 100644 index 0000000..3e604a5 --- /dev/null +++ b/ivi-id-agent-modules/ivi-id-agent/CMakeLists.txt @@ -0,0 +1,69 @@ +############################################################################### +# +# Copyright (C) 2017 Advanced Driver Information Technology Joint Venture GmbH +# +# +# Licensed under the Apache License, Version 2.0 (the "License"); +# you may not use this file except in compliance with the License. +# You may obtain a copy of the License at +# +# http://www.apache.org/licenses/LICENSE-2.0 +# +# Unless required by applicable law or agreed to in writing, software +# distributed under the License is distributed on an "AS IS" BASIS, +# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +# See the License for the specific language governing permissions and +# limitations under the License. +# +############################################################################### + +cmake_minimum_required (VERSION 2.6) + +project(ivi-id-agent) + +find_package(PkgConfig REQUIRED) +pkg_check_modules(WAYLAND_SERVER wayland-server REQUIRED) +pkg_check_modules(WESTON weston>=6.0.0 REQUIRED) +pkg_check_modules(PIXMAN pixman-1 REQUIRED) +pkg_check_modules(LIBWESTON_DESKTOP libweston-desktop-6 REQUIRED) + +find_package(Threads REQUIRED) + +include_directories( + src + ${WAYLAND_SERVER_INCLUDE_DIRS} + ${WESTON_INCLUDE_DIRS} + ${PIXMAN_INCLUDE_DIRS} +) + +link_directories( + ${WAYLAND_SERVER_LIBRARY_DIRS} + ${PIXMAN_LIBRARY_DIRS} +) + + +add_library(${PROJECT_NAME} MODULE + src/ivi-id-agent.c +) + +set_target_properties(${PROJECT_NAME} PROPERTIES PREFIX "") + +add_dependencies(${PROJECT_NAME} + ${WAYLAND_SERVER_LIBRARIES} + ${PIXMAN_LIBRARIES} +) + +set(LIBS + ${LIBS} + ${WAYLAND_SERVER_LIBRARIES} + ${LIBWESTON_DESKTOP_LIBRARIES} +) + +set(CMAKE_C_LDFLAGS "-module -avoid-version") + +target_link_libraries(${PROJECT_NAME} ${LIBS}) + +install ( + TARGETS ${PROJECT_NAME} + LIBRARY DESTINATION lib${LIB_SUFFIX}/weston +) diff --git a/ivi-id-agent-modules/ivi-id-agent/src/ivi-id-agent.c b/ivi-id-agent-modules/ivi-id-agent/src/ivi-id-agent.c new file mode 100644 index 0000000..8f0c199 --- /dev/null +++ b/ivi-id-agent-modules/ivi-id-agent/src/ivi-id-agent.c @@ -0,0 +1,381 @@ +/* + * Copyright (C) 2017 Advanced Driver Information Technology Joint Venture GmbH + * + * Permission to use, copy, modify, distribute, and sell this software and + * its documentation for any purpose is hereby granted without fee, provided + * that the above copyright notice appear in all copies and that both that + * copyright notice and this permission notice appear in supporting + * documentation, and that the name of the copyright holders not be used in + * advertising or publicity pertaining to distribution of the software + * without specific, written prior permission. The copyright holders make + * no representations about the suitability of this software for any + * purpose. It is provided "as is" without express or implied warranty. + * + * THE COPYRIGHT HOLDERS DISCLAIM ALL WARRANTIES WITH REGARD TO THIS + * SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY AND + * FITNESS, IN NO EVENT SHALL THE COPYRIGHT HOLDERS BE LIABLE FOR ANY + * SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES WHATSOEVER + * RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN ACTION OF + * CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF OR IN + * CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. + */ + +#include <stdlib.h> +#include <stdio.h> +#include <string.h> +#include <limits.h> + +#include <weston.h> +#include <libweston-6/libweston-desktop.h> +#include "config-parser.h" +#include <weston/ivi-layout-export.h> + +#ifndef INVALID_ID +#define INVALID_ID 0xFFFFFFFF +#endif + +struct db_elem +{ + struct wl_list link; + uint32_t surface_id; + char *cfg_app_id; + char *cfg_title; + struct ivi_layout_surface *layout_surface; +}; + +struct ivi_id_agent +{ + uint32_t default_behavior_set; + uint32_t default_surface_id; + uint32_t default_surface_id_max; + struct wl_list app_list; + struct weston_compositor *compositor; + const struct ivi_layout_interface *interface; + + struct wl_listener desktop_surface_configured; + struct wl_listener destroy_listener; + struct wl_listener surface_removed; +}; + +static int32_t +check_config_parameter(char *cfg_val, char *val) +{ + if (cfg_val == NULL) + return IVI_SUCCEEDED; + else if (val == NULL || strcmp(cfg_val, val) != 0) + return IVI_FAILED; + + return IVI_SUCCEEDED; +} + +static int32_t +get_id_from_config(struct ivi_id_agent *ida, struct ivi_layout_surface + *layout_surface) { + struct db_elem *db_elem; + char *temp_app_id = NULL; + char *temp_title = NULL; + int ret = IVI_FAILED; + + struct weston_surface *weston_surface = + ida->interface->surface_get_weston_surface(layout_surface); + + /* Get app id and title */ + struct weston_desktop_surface *wds = weston_surface_get_desktop_surface( + weston_surface); + + if (weston_desktop_surface_get_app_id(wds) != NULL) + temp_app_id = strdup(weston_desktop_surface_get_app_id(wds)); + + if (weston_desktop_surface_get_title(wds) != NULL) + temp_title = strdup(weston_desktop_surface_get_title(wds)); + + /* + * Check for every config parameter to be fulfilled. This part must be + * extended, if additional attributes are desired to be checked. + */ + wl_list_for_each(db_elem, &ida->app_list, link) + { + if (check_config_parameter(db_elem->cfg_app_id, temp_app_id) == 0) { + if (check_config_parameter(db_elem->cfg_title, temp_title) == 0) { + /* Found configuration for application. */ + int res = ida->interface->surface_set_id(layout_surface, + db_elem->surface_id); + if (res) + continue; + + db_elem->layout_surface = layout_surface; + ret = IVI_SUCCEEDED; + + break; + } + } + } + + free(temp_app_id); + free(temp_title); + + return ret; +} + +/* + * This function generates the id of a surface in regard to the desired + * parameters. For implementation of different behavior in id generation please + * adjust this function. + * In this implementation the app_id and/or title of the application is used for + * identification. It is also possible to use the pid, uid or gid for example. + */ +static int32_t +get_id(struct ivi_id_agent *ida, struct ivi_layout_surface *layout_surface) +{ + if (get_id_from_config(ida, layout_surface) == IVI_SUCCEEDED) + return IVI_SUCCEEDED; + + /* No default layer available */ + if (ida->default_behavior_set == 0) { + weston_log("ivi-id-agent: Could not find configuration for application\n"); + goto ivi_failed; + + /* Default behavior for unknown applications */ + } else if (ida->default_surface_id < ida->default_surface_id_max) { + weston_log("ivi-id-agent: No configuration for application adding to " + "default layer\n"); + + /* + * Check if ivi-shell application already created an application with + * desired surface_id + */ + struct ivi_layout_surface *temp_layout_surf = + ida->interface->get_surface_from_id( + ida->default_surface_id); + if ((temp_layout_surf != NULL) && (temp_layout_surf != layout_surface)) { + weston_log("ivi-id-agent: surface_id already used by an ivi-shell " + "application\n"); + goto ivi_failed; + } + + ida->interface->surface_set_id(layout_surface, + ida->default_surface_id); + ida->default_surface_id++; + + } else { + weston_log("ivi-id-agent: Interval for default surface_id generation " + "exceeded\n"); + goto ivi_failed; + } + + return IVI_SUCCEEDED; + +ivi_failed: + return IVI_FAILED; +} + +static void +desktop_surface_event_configure(struct wl_listener *listener, + void *data) +{ + struct ivi_id_agent *ida = wl_container_of(listener, ida, + desktop_surface_configured); + + struct ivi_layout_surface *layout_surface = + (struct ivi_layout_surface *) data; + + if (get_id(ida, layout_surface) == IVI_FAILED) + weston_log("ivi-id-agent: Could not create surface_id for application\n"); +} + +static void +surface_event_remove(struct wl_listener *listener, void *data) { + struct ivi_id_agent *ida = wl_container_of(listener, ida, + surface_removed); + struct ivi_layout_surface *layout_surface = + (struct ivi_layout_surface *) data; + struct db_elem *db_elem = NULL; + + wl_list_for_each(db_elem, &ida->app_list, link) + { + if(db_elem->layout_surface == layout_surface) { + db_elem->layout_surface = NULL; + break; + } + } +} + +static int32_t deinit(struct ivi_id_agent *ida); + +static void +id_agent_module_deinit(struct wl_listener *listener, void *data) { + (void)data; + struct ivi_id_agent *ida = wl_container_of(listener, ida, destroy_listener); + + deinit(ida); +} + +static int32_t +check_config(struct db_elem *curr_db_elem, struct ivi_id_agent *ida) +{ + struct db_elem *db_elem; + + if (ida->default_surface_id <= curr_db_elem->surface_id + && curr_db_elem->surface_id <= ida->default_surface_id_max) { + weston_log("ivi-id-agent: surface_id: %d in default id interval " + "[%d, %d] (CONFIG ERROR)\n", curr_db_elem->surface_id, + ida->default_surface_id, ida->default_surface_id_max); + goto ivi_failed; + } + + wl_list_for_each(db_elem, &ida->app_list, link) + { + if(curr_db_elem == db_elem) + continue; + + if (db_elem->surface_id == curr_db_elem->surface_id) { + weston_log("ivi-id-agent: Duplicate surface_id: %d (CONFIG ERROR)\n", + curr_db_elem->surface_id); + goto ivi_failed; + } + } + + return IVI_SUCCEEDED; + +ivi_failed: + return IVI_FAILED; +} + +static int32_t +read_config(struct ivi_id_agent *ida) +{ + struct weston_config *config = NULL; + struct weston_config_section *section = NULL; + const char *name = NULL; + + config = wet_get_config(ida->compositor); + if (!config) + goto ivi_failed; + + section = weston_config_get_section(config, "desktop-app-default", NULL, + NULL); + + if (section) { + weston_log("ivi-id-agent: Default behavior for unknown applications is " + "set\n"); + ida->default_behavior_set = 1; + + weston_config_section_get_uint(section, "default-surface-id", + &ida->default_surface_id, INVALID_ID); + weston_config_section_get_uint(section, "default-surface-id-max", + &ida->default_surface_id_max, INVALID_ID); + + if (ida->default_surface_id == INVALID_ID || + ida->default_surface_id_max == INVALID_ID) { + weston_log("ivi-id-agent: Missing configuration for default " + "behavior\n"); + ida->default_behavior_set = 0; + } + } else { + ida->default_behavior_set = 0; + } + + section = NULL; + while (weston_config_next_section(config, §ion, &name)) { + struct db_elem *db_elem = NULL; + + if (strcmp(name, "desktop-app") != 0) + continue; + + db_elem = calloc(1, sizeof *db_elem); + if (db_elem == NULL) { + weston_log("ivi-id-agent: No memory to allocate\n"); + goto ivi_failed; + } + + wl_list_insert(&ida->app_list, &db_elem->link); + + weston_config_section_get_uint(section, "surface-id", + &db_elem->surface_id, INVALID_ID); + + if (db_elem->surface_id == INVALID_ID) { + weston_log("ivi-id-agent: surface-id is not set in configuration\n"); + goto ivi_failed; + } + + weston_config_section_get_string(section, "app-id", + &db_elem->cfg_app_id, NULL); + weston_config_section_get_string(section, "app-title", + &db_elem->cfg_title, NULL); + + if (db_elem->cfg_app_id == NULL && db_elem->cfg_title == NULL) { + weston_log("ivi-id-agent: Every parameter is NULL in app " + "configuration\n"); + goto ivi_failed; + } + + if (check_config(db_elem, ida) == IVI_FAILED) { + weston_log("ivi-id-agent: No valid config found, deinit...\n"); + goto ivi_failed; + } + } + + if(ida->default_behavior_set == 0 && wl_list_empty(&ida->app_list)) { + weston_log("ivi-id-agent: No valid config found, deinit...\n"); + goto ivi_failed; + } + + return IVI_SUCCEEDED; + +ivi_failed: + return IVI_FAILED; +} + +WL_EXPORT int32_t +id_agent_module_init(struct weston_compositor *compositor, + const struct ivi_layout_interface *interface) +{ + struct ivi_id_agent *ida = NULL; + + ida = calloc(1, sizeof *ida); + if (ida == NULL) { + weston_log("failed to allocate ivi_id_agent\n"); + goto ivi_failed; + } + + ida->compositor = compositor; + ida->interface = interface; + ida->desktop_surface_configured.notify = desktop_surface_event_configure; + ida->destroy_listener.notify = id_agent_module_deinit; + ida->surface_removed.notify = surface_event_remove; + + wl_signal_add(&compositor->destroy_signal, &ida->destroy_listener); + ida->interface->add_listener_configure_desktop_surface( + &ida->desktop_surface_configured); + interface->add_listener_remove_surface(&ida->surface_removed); + + wl_list_init(&ida->app_list); + if(read_config(ida) != 0) { + weston_log("ivi-id-agent: Read config failed\n"); + deinit(ida); + goto ivi_failed; + } + + return IVI_SUCCEEDED; + +ivi_failed: + return IVI_FAILED; +} + +static int32_t +deinit(struct ivi_id_agent *ida) +{ + struct db_elem *db_elem; + wl_list_for_each(db_elem, &ida->app_list, link) { + free(db_elem->cfg_app_id); + free(db_elem->cfg_title); + free(db_elem); + } + + wl_list_remove(&ida->desktop_surface_configured.link); + wl_list_remove(&ida->destroy_listener.link); + wl_list_remove(&ida->surface_removed.link); + free(ida); + + return IVI_SUCCEEDED; +} diff --git a/ivi-id-agent-modules/ivi-id-agent/weston.ini.in b/ivi-id-agent-modules/ivi-id-agent/weston.ini.in new file mode 100644 index 0000000..4e0bded --- /dev/null +++ b/ivi-id-agent-modules/ivi-id-agent/weston.ini.in @@ -0,0 +1,20 @@ +[core] +shell=ivi-shell.so +require-input=false +modules=ivi-controller.so + +[ivi-shell] +ivi-input-module=ivi-input-controller.so +ivi-id-agent-module=ivi-id-agent.so + +[desktop-app] +surface-id=111 +app-title=Flower + +[desktop-app] +surface-id=251 +app-title=Flower + +[desktop-app-default] +default-surface-id=2000000 +default-surface-id-max=2001000 diff --git a/weston-ivi-shell/src/ivi-controller.c b/weston-ivi-shell/src/ivi-controller.c index 8faec2a..fd6c7d8 100644 --- a/weston-ivi-shell/src/ivi-controller.c +++ b/weston-ivi-shell/src/ivi-controller.c @@ -2170,6 +2170,38 @@ launch_client_process(void *data) free(shell->ivi_client_name); } +static int load_id_agent_module(struct ivishell *shell) +{ + struct weston_config *config = wet_get_config(shell->compositor); + struct weston_config_section *section; + char *id_agent_module = NULL; + + int (*id_agent_module_init)(struct weston_compositor *compositor, + const struct ivi_layout_interface *interface); + + section = weston_config_get_section(config, "ivi-shell", NULL, NULL); + + if (weston_config_section_get_string(section, "ivi-id-agent-module", + &id_agent_module, NULL) < 0) { + /* input events are handled by weston's default grabs */ + weston_log("ivi-controller: No ivi-id-agent-module set\n"); + return 0; + } + + id_agent_module_init = wet_load_module_entrypoint(id_agent_module, "id_agent_module_init"); + if (!id_agent_module_init) + return -1; + + if (id_agent_module_init(shell->compositor, shell->interface) != 0) { + weston_log("ivi-controller: Initialization of id-agent module failed\n"); + return -1; + } + + free(id_agent_module); + + return 0; +} + WL_EXPORT int wet_module_init(struct weston_compositor *compositor, int *argc, char *argv[]) @@ -2226,5 +2258,9 @@ wet_module_init(struct weston_compositor *compositor, wl_event_loop_add_idle(loop, launch_client_process, shell); } + if (load_id_agent_module(shell) < 0) { + weston_log("ivi-controller: id-agent module not loaded\n"); + } + return 0; } |