diff options
-rw-r--r-- | include/sway/commands.h | 2 | ||||
-rw-r--r-- | include/sway/security.h | 2 | ||||
-rw-r--r-- | sway/commands.c | 12 | ||||
-rw-r--r-- | sway/handlers.c | 14 | ||||
-rw-r--r-- | sway/ipc-server.c | 2 | ||||
-rw-r--r-- | sway/security.c | 17 |
6 files changed, 39 insertions, 10 deletions
diff --git a/include/sway/commands.h b/include/sway/commands.h index ccc3cf58..9e8d013e 100644 --- a/include/sway/commands.h +++ b/include/sway/commands.h | |||
@@ -54,7 +54,7 @@ int sp_index; | |||
54 | /** | 54 | /** |
55 | * Parse and handles a command. | 55 | * Parse and handles a command. |
56 | */ | 56 | */ |
57 | struct cmd_results *handle_command(char *command); | 57 | struct cmd_results *handle_command(char *command, enum command_context context); |
58 | /** | 58 | /** |
59 | * Parse and handles a command during config file loading. | 59 | * Parse and handles a command during config file loading. |
60 | * | 60 | * |
diff --git a/include/sway/security.h b/include/sway/security.h index aa51fd81..1cc85bee 100644 --- a/include/sway/security.h +++ b/include/sway/security.h | |||
@@ -6,6 +6,8 @@ | |||
6 | enum secure_feature get_feature_policy(pid_t pid); | 6 | enum secure_feature get_feature_policy(pid_t pid); |
7 | enum command_context get_command_policy(const char *cmd); | 7 | enum command_context get_command_policy(const char *cmd); |
8 | 8 | ||
9 | const char *command_policy_str(enum command_context context); | ||
10 | |||
9 | struct feature_policy *alloc_feature_policy(const char *program); | 11 | struct feature_policy *alloc_feature_policy(const char *program); |
10 | struct command_policy *alloc_command_policy(const char *command); | 12 | struct command_policy *alloc_command_policy(const char *command); |
11 | 13 | ||
diff --git a/sway/commands.c b/sway/commands.c index 0bfe9d13..5d5087b1 100644 --- a/sway/commands.c +++ b/sway/commands.c | |||
@@ -323,7 +323,7 @@ static struct cmd_handler *find_handler(char *line, enum cmd_status block) { | |||
323 | return res; | 323 | return res; |
324 | } | 324 | } |
325 | 325 | ||
326 | struct cmd_results *handle_command(char *_exec) { | 326 | struct cmd_results *handle_command(char *_exec, enum command_context context) { |
327 | // Even though this function will process multiple commands we will only | 327 | // Even though this function will process multiple commands we will only |
328 | // return the last error, if any (for now). (Since we have access to an | 328 | // return the last error, if any (for now). (Since we have access to an |
329 | // error string we could e.g. concatonate all errors there.) | 329 | // error string we could e.g. concatonate all errors there.) |
@@ -397,6 +397,16 @@ struct cmd_results *handle_command(char *_exec) { | |||
397 | free_argv(argc, argv); | 397 | free_argv(argc, argv); |
398 | goto cleanup; | 398 | goto cleanup; |
399 | } | 399 | } |
400 | if (!(get_command_policy(argv[0]) & context)) { | ||
401 | if (results) { | ||
402 | free_cmd_results(results); | ||
403 | } | ||
404 | results = cmd_results_new(CMD_INVALID, cmd, | ||
405 | "Permission denied for %s via %s", cmd, | ||
406 | command_policy_str(context)); | ||
407 | free_argv(argc, argv); | ||
408 | goto cleanup; | ||
409 | } | ||
400 | struct cmd_results *res = handler->handle(argc-1, argv+1); | 410 | struct cmd_results *res = handler->handle(argc-1, argv+1); |
401 | if (res->status != CMD_SUCCESS) { | 411 | if (res->status != CMD_SUCCESS) { |
402 | free_argv(argc, argv); | 412 | free_argv(argc, argv); |
diff --git a/sway/handlers.c b/sway/handlers.c index a329329d..ee52ba38 100644 --- a/sway/handlers.c +++ b/sway/handlers.c | |||
@@ -386,7 +386,7 @@ static bool handle_view_created(wlc_handle handle) { | |||
386 | struct criteria *crit = criteria->items[i]; | 386 | struct criteria *crit = criteria->items[i]; |
387 | sway_log(L_DEBUG, "for_window '%s' matches new view %p, cmd: '%s'", | 387 | sway_log(L_DEBUG, "for_window '%s' matches new view %p, cmd: '%s'", |
388 | crit->crit_raw, newview, crit->cmdlist); | 388 | crit->crit_raw, newview, crit->cmdlist); |
389 | struct cmd_results *res = handle_command(crit->cmdlist); | 389 | struct cmd_results *res = handle_command(crit->cmdlist, CONTEXT_CRITERIA); |
390 | if (res->status != CMD_SUCCESS) { | 390 | if (res->status != CMD_SUCCESS) { |
391 | sway_log(L_ERROR, "Command '%s' failed: %s", res->input, res->error); | 391 | sway_log(L_ERROR, "Command '%s' failed: %s", res->input, res->error); |
392 | } | 392 | } |
@@ -585,7 +585,7 @@ static void handle_binding_command(struct sway_binding *binding) { | |||
585 | reload = true; | 585 | reload = true; |
586 | } | 586 | } |
587 | 587 | ||
588 | struct cmd_results *res = handle_command(binding->command); | 588 | struct cmd_results *res = handle_command(binding->command, CONTEXT_BINDING); |
589 | if (res->status != CMD_SUCCESS) { | 589 | if (res->status != CMD_SUCCESS) { |
590 | sway_log(L_ERROR, "Command '%s' failed: %s", res->input, res->error); | 590 | sway_log(L_ERROR, "Command '%s' failed: %s", res->input, res->error); |
591 | } | 591 | } |
@@ -936,18 +936,18 @@ bool handle_pointer_scroll(wlc_handle view, uint32_t time, const struct wlc_modi | |||
936 | int y_amount = (int)_amount[1]; | 936 | int y_amount = (int)_amount[1]; |
937 | 937 | ||
938 | if (x_amount > 0 && strcmp(config->floating_scroll_up_cmd, "")) { | 938 | if (x_amount > 0 && strcmp(config->floating_scroll_up_cmd, "")) { |
939 | handle_command(config->floating_scroll_up_cmd); | 939 | handle_command(config->floating_scroll_up_cmd, CONTEXT_BINDING); |
940 | return EVENT_HANDLED; | 940 | return EVENT_HANDLED; |
941 | } else if (x_amount < 0 && strcmp(config->floating_scroll_down_cmd, "")) { | 941 | } else if (x_amount < 0 && strcmp(config->floating_scroll_down_cmd, "")) { |
942 | handle_command(config->floating_scroll_down_cmd); | 942 | handle_command(config->floating_scroll_down_cmd, CONTEXT_BINDING); |
943 | return EVENT_HANDLED; | 943 | return EVENT_HANDLED; |
944 | } | 944 | } |
945 | 945 | ||
946 | if (y_amount > 0 && strcmp(config->floating_scroll_right_cmd, "")) { | 946 | if (y_amount > 0 && strcmp(config->floating_scroll_right_cmd, "")) { |
947 | handle_command(config->floating_scroll_right_cmd); | 947 | handle_command(config->floating_scroll_right_cmd, CONTEXT_BINDING); |
948 | return EVENT_HANDLED; | 948 | return EVENT_HANDLED; |
949 | } else if (y_amount < 0 && strcmp(config->floating_scroll_left_cmd, "")) { | 949 | } else if (y_amount < 0 && strcmp(config->floating_scroll_left_cmd, "")) { |
950 | handle_command(config->floating_scroll_left_cmd); | 950 | handle_command(config->floating_scroll_left_cmd, CONTEXT_BINDING); |
951 | return EVENT_HANDLED; | 951 | return EVENT_HANDLED; |
952 | } | 952 | } |
953 | } | 953 | } |
@@ -960,7 +960,7 @@ static void handle_wlc_ready(void) { | |||
960 | config->active = true; | 960 | config->active = true; |
961 | while (config->cmd_queue->length) { | 961 | while (config->cmd_queue->length) { |
962 | char *line = config->cmd_queue->items[0]; | 962 | char *line = config->cmd_queue->items[0]; |
963 | struct cmd_results *res = handle_command(line); | 963 | struct cmd_results *res = handle_command(line, CONTEXT_CONFIG); |
964 | if (res->status != CMD_SUCCESS) { | 964 | if (res->status != CMD_SUCCESS) { |
965 | sway_log(L_ERROR, "Error on line '%s': %s", line, res->error); | 965 | sway_log(L_ERROR, "Error on line '%s': %s", line, res->error); |
966 | } | 966 | } |
diff --git a/sway/ipc-server.c b/sway/ipc-server.c index ebb5ce58..e575081b 100644 --- a/sway/ipc-server.c +++ b/sway/ipc-server.c | |||
@@ -312,7 +312,7 @@ void ipc_client_handle_command(struct ipc_client *client) { | |||
312 | switch (client->current_command) { | 312 | switch (client->current_command) { |
313 | case IPC_COMMAND: | 313 | case IPC_COMMAND: |
314 | { | 314 | { |
315 | struct cmd_results *results = handle_command(buf); | 315 | struct cmd_results *results = handle_command(buf, CONTEXT_IPC); |
316 | const char *json = cmd_results_to_json(results); | 316 | const char *json = cmd_results_to_json(results); |
317 | char reply[256]; | 317 | char reply[256]; |
318 | int length = snprintf(reply, sizeof(reply), "%s", json); | 318 | int length = snprintf(reply, sizeof(reply), "%s", json); |
diff --git a/sway/security.c b/sway/security.c index 670cae56..2ccc30fd 100644 --- a/sway/security.c +++ b/sway/security.c | |||
@@ -64,3 +64,20 @@ enum command_context get_command_policy(const char *cmd) { | |||
64 | 64 | ||
65 | return default_policy; | 65 | return default_policy; |
66 | } | 66 | } |
67 | |||
68 | const char *command_policy_str(enum command_context context) { | ||
69 | switch (context) { | ||
70 | case CONTEXT_ALL: | ||
71 | return "all"; | ||
72 | case CONTEXT_CONFIG: | ||
73 | return "config"; | ||
74 | case CONTEXT_BINDING: | ||
75 | return "binding"; | ||
76 | case CONTEXT_IPC: | ||
77 | return "IPC"; | ||
78 | case CONTEXT_CRITERIA: | ||
79 | return "criteria"; | ||
80 | default: | ||
81 | return "unknown"; | ||
82 | } | ||
83 | } | ||