10 #include "libds-tizen/keyrouter.h"
13 #include "keyrouter.h"
16 keyrouter_bind(struct wl_client *client, void *data, uint32_t version,
19 keyrouter_check_privilege(struct ds_tizen_keyrouter_client *keyrouter_client,
20 struct wl_client *client, uint32_t mode, uint32_t keycode);
22 keyrouter_options_set(struct ds_tizen_keyrouter *keyrouter);
25 keyrouter_handle_display_destroy(struct wl_listener *listener, void *data)
27 struct ds_tizen_keyrouter *keyrouter;
29 keyrouter = wl_container_of(listener, keyrouter, display_destroy);
31 ds_inf("Global destroy: ds_tizen_keyrouter(%p)", keyrouter);
33 wl_signal_emit(&keyrouter->events.destroy, keyrouter);
35 if (keyrouter->security_initialized)
36 tizen_security_finish();
38 free(keyrouter->opts);
40 wl_list_remove(&keyrouter->display_destroy.link);
42 wl_global_destroy(keyrouter->global);
44 keyrouter_grab_destroy(keyrouter->keyrouter_grab);
49 WL_EXPORT struct ds_tizen_keyrouter *
50 ds_tizen_keyrouter_create(struct wl_display *display)
52 struct ds_tizen_keyrouter *keyrouter;
54 keyrouter = calloc(1, sizeof *keyrouter);
59 keyrouter->keyrouter_grab = keyrouter_grab_create();
60 if (keyrouter->keyrouter_grab == NULL) {
61 ds_err("Failed to create keyrouter.");
66 keyrouter->global = wl_global_create(display, &tizen_keyrouter_interface,
67 2, keyrouter, keyrouter_bind);
68 if (!keyrouter->global) {
69 keyrouter_grab_destroy(keyrouter->keyrouter_grab);
74 wl_list_init(&keyrouter->clients);
76 wl_signal_init(&keyrouter->events.destroy);
78 keyrouter->display_destroy.notify = keyrouter_handle_display_destroy;
79 wl_display_add_destroy_listener(display, &keyrouter->display_destroy);
81 keyrouter_options_set(keyrouter);
83 keyrouter->security_initialized = tizen_security_init();
84 if (!keyrouter->security_initialized) {
85 ds_inf("tizen_security_init() is not sucessful. "
86 "keyrouter works without security.");
89 ds_inf("Global created: ds_tizen_keyrouter(%p)", keyrouter);
95 ds_tizen_keyrouter_add_destroy_listener(struct ds_tizen_keyrouter *keyrouter,
96 struct wl_listener *listener)
98 wl_signal_add(&keyrouter->events.destroy, listener);
102 keyrouter_handle_keygrab_set(struct wl_client *client,
103 struct wl_resource *resource, struct wl_resource *surface,
104 uint32_t key, uint32_t mode)
106 struct ds_tizen_keyrouter_client *keyrouter_client;
107 struct ds_tizen_keyrouter *keyrouter;
108 int res = TIZEN_KEYROUTER_ERROR_NONE;
111 keyrouter_client = wl_resource_get_user_data(resource);
112 keyrouter = keyrouter_client->keyrouter;
114 ret = keyrouter_check_privilege(keyrouter_client, client, mode, key);
116 tizen_keyrouter_send_keygrab_notify(resource, surface,
117 key, mode, TIZEN_KEYROUTER_ERROR_NO_PERMISSION);
121 res = keyrouter_grab_grab_key(keyrouter->keyrouter_grab,
122 mode, key, (void *)client);
123 if (res == TIZEN_KEYROUTER_ERROR_NONE && keyrouter_client->grabbed != true)
124 keyrouter_client->grabbed = true;
126 tizen_keyrouter_send_keygrab_notify(resource, surface, key, mode, res);
130 keyrouter_handle_keygrab_unset(struct wl_client *client,
131 struct wl_resource *resource, struct wl_resource *surface, uint32_t key)
133 struct ds_tizen_keyrouter_client *keyrouter_client;
134 struct ds_tizen_keyrouter *keyrouter;
135 int res = TIZEN_KEYROUTER_ERROR_NONE;
138 keyrouter_client = wl_resource_get_user_data(resource);
139 keyrouter = keyrouter_client->keyrouter;
141 /* ungrab TOP POSITION grab first, this grab mode is not check privilege */
142 keyrouter_grab_ungrab_key(keyrouter->keyrouter_grab,
143 TIZEN_KEYROUTER_MODE_TOPMOST, key, (void *)client);
145 ret = keyrouter_check_privilege(keyrouter_client,
146 client, TIZEN_KEYROUTER_MODE_NONE, key);
148 tizen_keyrouter_send_keygrab_notify(resource, surface, key,
149 TIZEN_KEYROUTER_MODE_NONE, TIZEN_KEYROUTER_ERROR_NO_PERMISSION);
153 keyrouter_grab_ungrab_key(keyrouter->keyrouter_grab,
154 TIZEN_KEYROUTER_MODE_EXCLUSIVE, key, (void *)client);
155 keyrouter_grab_ungrab_key(keyrouter->keyrouter_grab,
156 TIZEN_KEYROUTER_MODE_OVERRIDABLE_EXCLUSIVE, key, (void *)client);
157 keyrouter_grab_ungrab_key(keyrouter->keyrouter_grab,
158 TIZEN_KEYROUTER_MODE_TOPMOST, key, (void *)client);
159 keyrouter_grab_ungrab_key(keyrouter->keyrouter_grab,
160 TIZEN_KEYROUTER_MODE_SHARED, key, (void *)client);
162 tizen_keyrouter_send_keygrab_notify(resource, surface, key, TIZEN_KEYROUTER_MODE_NONE, res);
166 keyrouter_handle_get_keygrab_status(struct wl_client *client,
167 struct wl_resource *resource, struct wl_resource *surface, uint32_t key)
169 tizen_keyrouter_send_keygrab_notify(resource, surface, key,
170 TIZEN_KEYROUTER_MODE_NONE, TIZEN_KEYROUTER_ERROR_NO_PERMISSION);
174 keyrouter_get_array_length(const struct wl_array *array)
179 wl_array_for_each(data, array) {
187 keyrouter_handle_keygrab_set_list(struct wl_client *client,
188 struct wl_resource *resource, struct wl_resource *surface, struct wl_array *grab_list)
190 struct ds_tizen_keyrouter_client *keyrouter_client;
191 struct ds_tizen_keyrouter *keyrouter;
192 struct wl_array *return_list;
193 struct ds_tizen_grab_data *grab_data = NULL;
194 int res = TIZEN_KEYROUTER_ERROR_NONE;
197 keyrouter_client = wl_resource_get_user_data(resource);
198 keyrouter = keyrouter_client->keyrouter;
200 if ((keyrouter_get_array_length(grab_list) % 3) != 0) {
201 ds_err("Invalid keycode and grab mode pair. Check arguments in a list.");
202 tizen_keyrouter_send_keygrab_notify_list(resource, surface, NULL);
206 wl_array_for_each(grab_data, grab_list) {
207 ret = keyrouter_check_privilege(keyrouter_client, client, grab_data->mode, grab_data->key);
209 grab_data->err = TIZEN_KEYROUTER_ERROR_NO_PERMISSION;
211 res = keyrouter_grab_grab_key(keyrouter->keyrouter_grab,
212 grab_data->mode, grab_data->key, (void *)client);
213 if (res == TIZEN_KEYROUTER_ERROR_NONE && keyrouter_client->grabbed != true)
214 keyrouter_client->grabbed = true;
216 grab_data->err = res;
220 return_list = grab_list;
222 tizen_keyrouter_send_keygrab_notify_list(resource, surface, return_list);
226 keyrouter_handle_keygrab_unset_list(struct wl_client *client,
227 struct wl_resource *resource, struct wl_resource *surface,
228 struct wl_array *ungrab_list)
230 struct ds_tizen_keyrouter_client *keyrouter_client;
231 struct ds_tizen_keyrouter *keyrouter;
232 struct wl_array *return_list = NULL;
233 struct ds_tizen_ungrab_data *ungrab_data = NULL;
236 keyrouter_client = wl_resource_get_user_data(resource);
237 keyrouter = keyrouter_client->keyrouter;
239 if ((keyrouter_get_array_length(ungrab_list) % 3) != 0) {
240 ds_err("Invalid keycode and grab mode pair. Check arguments in a list.");
241 tizen_keyrouter_send_keygrab_notify_list(resource, surface, NULL);
245 wl_array_for_each(ungrab_data, ungrab_list) {
246 keyrouter_grab_ungrab_key(keyrouter->keyrouter_grab,
247 TIZEN_KEYROUTER_MODE_TOPMOST, ungrab_data->key, (void *)client);
249 ret = keyrouter_check_privilege(keyrouter_client, client,
250 TIZEN_KEYROUTER_MODE_TOPMOST, ungrab_data->key);
252 ungrab_data->err = TIZEN_KEYROUTER_ERROR_NO_PERMISSION;
254 keyrouter_grab_ungrab_key(keyrouter->keyrouter_grab,
255 TIZEN_KEYROUTER_MODE_EXCLUSIVE, ungrab_data->key, (void *)client);
257 keyrouter_grab_ungrab_key(keyrouter->keyrouter_grab,
258 TIZEN_KEYROUTER_MODE_OVERRIDABLE_EXCLUSIVE, ungrab_data->key, (void *)client);
260 keyrouter_grab_ungrab_key(keyrouter->keyrouter_grab,
261 TIZEN_KEYROUTER_MODE_TOPMOST, ungrab_data->key, (void *)client);
263 keyrouter_grab_ungrab_key(keyrouter->keyrouter_grab,
264 TIZEN_KEYROUTER_MODE_SHARED, ungrab_data->key, (void *)client);
266 ungrab_data->err = TIZEN_KEYROUTER_ERROR_NONE;
270 return_list = ungrab_list;
272 tizen_keyrouter_send_keygrab_notify_list(resource, surface, return_list);
276 keyrouter_handle_get_keygrab_list(struct wl_client *client,
277 struct wl_resource *resource, struct wl_resource *surface)
279 tizen_keyrouter_send_getgrab_notify_list(resource, surface, NULL);
283 keyrouter_handle_set_register_none_key(struct wl_client *client,
284 struct wl_resource *resource, struct wl_resource *surface,
287 tizen_keyrouter_send_set_register_none_key_notify(resource, NULL, 0);
291 keyrouter_handle_get_keyregister_status(struct wl_client *client,
292 struct wl_resource *resource, uint32_t key)
294 tizen_keyrouter_send_keyregister_notify(resource, (int)false);
298 keyrouter_handle_set_input_config(struct wl_client *client,
299 struct wl_resource *resource, struct wl_resource *surface,
300 uint32_t config_mode, uint32_t value)
302 tizen_keyrouter_send_set_input_config_notify(resource, (int)false);
306 keyrouter_handle_destory(struct wl_client *client,
307 struct wl_resource *resource)
309 wl_resource_destroy(resource);
312 static const struct tizen_keyrouter_interface tizen_keyrouter_impl = {
313 keyrouter_handle_keygrab_set,
314 keyrouter_handle_keygrab_unset,
315 keyrouter_handle_get_keygrab_status,
316 keyrouter_handle_keygrab_set_list,
317 keyrouter_handle_keygrab_unset_list,
318 keyrouter_handle_get_keygrab_list,
319 keyrouter_handle_set_register_none_key,
320 keyrouter_handle_get_keyregister_status,
321 keyrouter_handle_set_input_config,
322 keyrouter_handle_destory
326 keyrouter_handle_resource_destory(struct wl_resource *resource)
328 struct ds_tizen_keyrouter_client *keyrouter_client = wl_resource_get_user_data(resource);
330 wl_list_remove(&keyrouter_client->link);
331 free(keyrouter_client);
335 keyrouter_bind(struct wl_client *client, void *data, uint32_t version,
338 struct ds_tizen_keyrouter *keyrouter = data;
339 struct ds_tizen_keyrouter_client *keyrouter_client;
341 keyrouter_client = calloc(1, sizeof *keyrouter_client);
342 if (keyrouter_client == NULL) {
343 wl_client_post_no_memory(client);
347 keyrouter_client->keyrouter = keyrouter;
348 keyrouter_client->resource =
349 wl_resource_create(client, &tizen_keyrouter_interface, MIN(version, 2), id);
350 if (keyrouter_client->resource == NULL) {
351 ds_err("wl_resource_create() failed.(version :%d, id:%d)", version, id);
352 free(keyrouter_client);
353 wl_client_post_no_memory(client);
357 wl_resource_set_implementation(keyrouter_client->resource, &tizen_keyrouter_impl,
358 keyrouter_client, keyrouter_handle_resource_destory);
360 wl_list_insert(&keyrouter->clients, &keyrouter_client->link);
364 keyrouter_check_privilege(struct ds_tizen_keyrouter_client *keyrouter_client,
365 struct wl_client *client, uint32_t mode, uint32_t keycode)
367 struct ds_tizen_keyrouter *keyrouter = keyrouter_client->keyrouter;
373 /* Top position grab is always allowed. This mode do not need privilege.*/
374 if (mode == TIZEN_KEYROUTER_MODE_TOPMOST)
377 // check no privilege option on the keycode
378 if (keyrouter->opts) {
379 if (keyrouter->opts[keycode].no_privilege)
383 // grabbed client is already checked the privilege before.
384 if (keyrouter_client->grabbed)
387 wl_client_get_credentials(client, &pid, &uid, &gid);
389 return tizen_security_check_privilege(pid, uid, "http://tizen.org/privilege/keygrab");
393 keyrouter_options_set(struct ds_tizen_keyrouter *keyrouter)
397 char *ret, *tmp, *buf_ptr, buf[1024] = {0,};
399 keyrouter->opts = calloc(KEYROUTER_MAX_KEYS,
400 sizeof(struct ds_tizen_keyrouter_key_options));
401 if (!keyrouter->opts) {
405 file = fopen(KEYLAYOUT_DIR, "r");
407 ds_err("Failed to open key layout file(%s): (err msg: %m)\n", KEYLAYOUT_DIR);
408 free(keyrouter->opts);
409 keyrouter->opts = NULL;
413 while (!feof(file)) {
414 ret = fgets(buf, 1024, file);
417 tmp = strtok_r(buf, " ", &buf_ptr);
418 tmp = strtok_r(NULL, " ", &buf_ptr);
421 if ((0 >= keycode) || (keycode >= KEYROUTER_MAX_KEYS)) {
422 ds_err("Currently %d key is invalid to support\n", keycode);
426 keyrouter->opts[keycode].enabled = true;
428 if (strstr(buf_ptr, "no_priv") != NULL) {
429 keyrouter->opts[keycode].no_privilege = true;