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 tizen_security_finish();
37 free(keyrouter->opts);
39 wl_list_remove(&keyrouter->display_destroy.link);
41 wl_global_destroy(keyrouter->global);
43 keyrouter_grab_destroy(keyrouter->keyrouter_grab);
48 WL_EXPORT struct ds_tizen_keyrouter *
49 ds_tizen_keyrouter_create(struct wl_display *display)
51 struct ds_tizen_keyrouter *keyrouter;
53 keyrouter = calloc(1, sizeof *keyrouter);
58 keyrouter->keyrouter_grab = keyrouter_grab_create();
59 if (keyrouter->keyrouter_grab == NULL) {
60 ds_err("Failed to create keyrouter.");
65 keyrouter->global = wl_global_create(display, &tizen_keyrouter_interface,
66 2, keyrouter, keyrouter_bind);
67 if (!keyrouter->global) {
68 keyrouter_grab_destroy(keyrouter->keyrouter_grab);
73 wl_list_init(&keyrouter->clients);
75 wl_signal_init(&keyrouter->events.destroy);
77 keyrouter->display_destroy.notify = keyrouter_handle_display_destroy;
78 wl_display_add_destroy_listener(display, &keyrouter->display_destroy);
80 keyrouter_options_set(keyrouter);
82 if (!tizen_security_init()) {
83 ds_inf("tizen_security_init() is not sucessful. keyrouter works without security.");
86 ds_inf("Global created: ds_tizen_keyrouter(%p)", keyrouter);
92 ds_tizen_keyrouter_add_destroy_listener(struct ds_tizen_keyrouter *keyrouter,
93 struct wl_listener *listener)
95 wl_signal_add(&keyrouter->events.destroy, listener);
99 keyrouter_handle_keygrab_set(struct wl_client *client,
100 struct wl_resource *resource, struct wl_resource *surface,
101 uint32_t key, uint32_t mode)
103 struct ds_tizen_keyrouter_client *keyrouter_client;
104 struct ds_tizen_keyrouter *keyrouter;
105 int res = TIZEN_KEYROUTER_ERROR_NONE;
108 keyrouter_client = wl_resource_get_user_data(resource);
109 keyrouter = keyrouter_client->keyrouter;
111 ret = keyrouter_check_privilege(keyrouter_client, client, mode, key);
113 tizen_keyrouter_send_keygrab_notify(resource, surface,
114 key, mode, TIZEN_KEYROUTER_ERROR_NO_PERMISSION);
118 res = keyrouter_grab_grab_key(keyrouter->keyrouter_grab,
119 mode, key, (void *)client);
120 if (res == TIZEN_KEYROUTER_ERROR_NONE && keyrouter_client->grabbed != true)
121 keyrouter_client->grabbed = true;
123 tizen_keyrouter_send_keygrab_notify(resource, surface, key, mode, res);
127 keyrouter_handle_keygrab_unset(struct wl_client *client,
128 struct wl_resource *resource, struct wl_resource *surface, uint32_t key)
130 struct ds_tizen_keyrouter_client *keyrouter_client;
131 struct ds_tizen_keyrouter *keyrouter;
132 int res = TIZEN_KEYROUTER_ERROR_NONE;
135 keyrouter_client = wl_resource_get_user_data(resource);
136 keyrouter = keyrouter_client->keyrouter;
138 /* ungrab TOP POSITION grab first, this grab mode is not check privilege */
139 keyrouter_grab_ungrab_key(keyrouter->keyrouter_grab,
140 TIZEN_KEYROUTER_MODE_TOPMOST, key, (void *)client);
142 ret = keyrouter_check_privilege(keyrouter_client,
143 client, TIZEN_KEYROUTER_MODE_NONE, key);
145 tizen_keyrouter_send_keygrab_notify(resource, surface, key,
146 TIZEN_KEYROUTER_MODE_NONE, TIZEN_KEYROUTER_ERROR_NO_PERMISSION);
150 keyrouter_grab_ungrab_key(keyrouter->keyrouter_grab,
151 TIZEN_KEYROUTER_MODE_EXCLUSIVE, key, (void *)client);
152 keyrouter_grab_ungrab_key(keyrouter->keyrouter_grab,
153 TIZEN_KEYROUTER_MODE_OVERRIDABLE_EXCLUSIVE, key, (void *)client);
154 keyrouter_grab_ungrab_key(keyrouter->keyrouter_grab,
155 TIZEN_KEYROUTER_MODE_TOPMOST, key, (void *)client);
156 keyrouter_grab_ungrab_key(keyrouter->keyrouter_grab,
157 TIZEN_KEYROUTER_MODE_SHARED, key, (void *)client);
159 tizen_keyrouter_send_keygrab_notify(resource, surface, key, TIZEN_KEYROUTER_MODE_NONE, res);
163 keyrouter_handle_get_keygrab_status(struct wl_client *client,
164 struct wl_resource *resource, struct wl_resource *surface, uint32_t key)
166 tizen_keyrouter_send_keygrab_notify(resource, surface, key,
167 TIZEN_KEYROUTER_MODE_NONE, TIZEN_KEYROUTER_ERROR_NO_PERMISSION);
171 keyrouter_get_array_length(const struct wl_array *array)
176 wl_array_for_each(data, array) {
184 keyrouter_handle_keygrab_set_list(struct wl_client *client,
185 struct wl_resource *resource, struct wl_resource *surface, struct wl_array *grab_list)
187 struct ds_tizen_keyrouter_client *keyrouter_client;
188 struct ds_tizen_keyrouter *keyrouter;
189 struct wl_array *return_list;
190 struct ds_tizen_grab_data *grab_data = NULL;
191 int res = TIZEN_KEYROUTER_ERROR_NONE;
194 keyrouter_client = wl_resource_get_user_data(resource);
195 keyrouter = keyrouter_client->keyrouter;
197 if ((keyrouter_get_array_length(grab_list) % 3) != 0) {
198 ds_err("Invalid keycode and grab mode pair. Check arguments in a list.");
199 tizen_keyrouter_send_keygrab_notify_list(resource, surface, NULL);
203 wl_array_for_each(grab_data, grab_list) {
204 ret = keyrouter_check_privilege(keyrouter_client, client, grab_data->mode, grab_data->key);
206 grab_data->err = TIZEN_KEYROUTER_ERROR_NO_PERMISSION;
208 res = keyrouter_grab_grab_key(keyrouter->keyrouter_grab,
209 grab_data->mode, grab_data->key, (void *)client);
210 if (res == TIZEN_KEYROUTER_ERROR_NONE && keyrouter_client->grabbed != true)
211 keyrouter_client->grabbed = true;
213 grab_data->err = res;
217 return_list = grab_list;
219 tizen_keyrouter_send_keygrab_notify_list(resource, surface, return_list);
223 keyrouter_handle_keygrab_unset_list(struct wl_client *client,
224 struct wl_resource *resource, struct wl_resource *surface,
225 struct wl_array *ungrab_list)
227 struct ds_tizen_keyrouter_client *keyrouter_client;
228 struct ds_tizen_keyrouter *keyrouter;
229 struct wl_array *return_list = NULL;
230 struct ds_tizen_ungrab_data *ungrab_data = NULL;
233 keyrouter_client = wl_resource_get_user_data(resource);
234 keyrouter = keyrouter_client->keyrouter;
236 if ((keyrouter_get_array_length(ungrab_list) % 3) != 0) {
237 ds_err("Invalid keycode and grab mode pair. Check arguments in a list.");
238 tizen_keyrouter_send_keygrab_notify_list(resource, surface, NULL);
242 wl_array_for_each(ungrab_data, ungrab_list) {
243 keyrouter_grab_ungrab_key(keyrouter->keyrouter_grab,
244 TIZEN_KEYROUTER_MODE_TOPMOST, ungrab_data->key, (void *)client);
246 ret = keyrouter_check_privilege(keyrouter_client, client,
247 TIZEN_KEYROUTER_MODE_TOPMOST, ungrab_data->key);
249 ungrab_data->err = TIZEN_KEYROUTER_ERROR_NO_PERMISSION;
251 keyrouter_grab_ungrab_key(keyrouter->keyrouter_grab,
252 TIZEN_KEYROUTER_MODE_EXCLUSIVE, ungrab_data->key, (void *)client);
254 keyrouter_grab_ungrab_key(keyrouter->keyrouter_grab,
255 TIZEN_KEYROUTER_MODE_OVERRIDABLE_EXCLUSIVE, ungrab_data->key, (void *)client);
257 keyrouter_grab_ungrab_key(keyrouter->keyrouter_grab,
258 TIZEN_KEYROUTER_MODE_TOPMOST, ungrab_data->key, (void *)client);
260 keyrouter_grab_ungrab_key(keyrouter->keyrouter_grab,
261 TIZEN_KEYROUTER_MODE_SHARED, ungrab_data->key, (void *)client);
263 ungrab_data->err = TIZEN_KEYROUTER_ERROR_NONE;
267 return_list = ungrab_list;
269 tizen_keyrouter_send_keygrab_notify_list(resource, surface, return_list);
273 keyrouter_handle_get_keygrab_list(struct wl_client *client,
274 struct wl_resource *resource, struct wl_resource *surface)
276 tizen_keyrouter_send_getgrab_notify_list(resource, surface, NULL);
280 keyrouter_handle_set_register_none_key(struct wl_client *client,
281 struct wl_resource *resource, struct wl_resource *surface,
284 tizen_keyrouter_send_set_register_none_key_notify(resource, NULL, 0);
288 keyrouter_handle_get_keyregister_status(struct wl_client *client,
289 struct wl_resource *resource, uint32_t key)
291 tizen_keyrouter_send_keyregister_notify(resource, (int)false);
295 keyrouter_handle_set_input_config(struct wl_client *client,
296 struct wl_resource *resource, struct wl_resource *surface,
297 uint32_t config_mode, uint32_t value)
299 tizen_keyrouter_send_set_input_config_notify(resource, (int)false);
303 keyrouter_handle_destory(struct wl_client *client,
304 struct wl_resource *resource)
306 wl_resource_destroy(resource);
309 static const struct tizen_keyrouter_interface tizen_keyrouter_impl = {
310 keyrouter_handle_keygrab_set,
311 keyrouter_handle_keygrab_unset,
312 keyrouter_handle_get_keygrab_status,
313 keyrouter_handle_keygrab_set_list,
314 keyrouter_handle_keygrab_unset_list,
315 keyrouter_handle_get_keygrab_list,
316 keyrouter_handle_set_register_none_key,
317 keyrouter_handle_get_keyregister_status,
318 keyrouter_handle_set_input_config,
319 keyrouter_handle_destory
323 keyrouter_handle_resource_destory(struct wl_resource *resource)
325 struct ds_tizen_keyrouter_client *keyrouter_client = wl_resource_get_user_data(resource);
327 wl_list_remove(&keyrouter_client->link);
328 free(keyrouter_client);
332 keyrouter_bind(struct wl_client *client, void *data, uint32_t version,
335 struct ds_tizen_keyrouter *keyrouter = data;
336 struct ds_tizen_keyrouter_client *keyrouter_client;
338 keyrouter_client = calloc(1, sizeof *keyrouter_client);
339 if (keyrouter_client == NULL) {
340 wl_client_post_no_memory(client);
344 keyrouter_client->resource =
345 wl_resource_create(client, &tizen_keyrouter_interface, MIN(version, 2), id);
346 if (keyrouter_client->resource == NULL) {
347 ds_err("wl_resource_create() failed.(version :%d, id:%d)", version, id);
348 free(keyrouter_client);
349 wl_client_post_no_memory(client);
353 wl_resource_set_implementation(keyrouter_client->resource, &tizen_keyrouter_impl,
354 keyrouter_client, keyrouter_handle_resource_destory);
356 wl_list_insert(&keyrouter->clients, &keyrouter_client->link);
360 keyrouter_check_privilege(struct ds_tizen_keyrouter_client *keyrouter_client,
361 struct wl_client *client, uint32_t mode, uint32_t keycode)
363 struct ds_tizen_keyrouter *keyrouter = keyrouter_client->keyrouter;
369 /* Top position grab is always allowed. This mode do not need privilege.*/
370 if (mode == TIZEN_KEYROUTER_MODE_TOPMOST)
373 // check no privilege option on the keycode
374 if (keyrouter->opts) {
375 if (keyrouter->opts[keycode].no_privilege)
379 // grabbed client is already checked the privilege before.
380 if (keyrouter_client->grabbed)
383 wl_client_get_credentials(client, &pid, &uid, &gid);
385 return tizen_security_check_privilege(pid, uid, "http://tizen.org/privilege/keygrab");
389 keyrouter_options_set(struct ds_tizen_keyrouter *keyrouter)
393 char *ret, *tmp, *buf_ptr, buf[1024] = {0,};
395 keyrouter->opts = calloc(KEYROUTER_MAX_KEYS,
396 sizeof(struct ds_tizen_keyrouter_key_options));
397 if (!keyrouter->opts) {
401 file = fopen(KEYLAYOUT_DIR, "r");
403 ds_err("Failed to open key layout file(%s): (err msg: %m)\n", KEYLAYOUT_DIR);
404 free(keyrouter->opts);
405 keyrouter->opts = NULL;
409 while (!feof(file)) {
410 ret = fgets(buf, 1024, file);
413 tmp = strtok_r(buf, " ", &buf_ptr);
414 tmp = strtok_r(NULL, " ", &buf_ptr);
417 if ((0 >= keycode) || (keycode >= KEYROUTER_MAX_KEYS)) {
418 ds_err("Currently %d key is invalid to support\n", keycode);
422 keyrouter->opts[keycode].enabled = true;
424 if (strstr(buf_ptr, "no_priv") != NULL) {
425 keyrouter->opts[keycode].no_privilege = true;