For example, when you run start randr, will send 5 request, while you go to 3th request, somebody operates on the same output and commit his request, it will interrupt you. This will affect your complete actions on the output.
In order to avoid this case, take request_id, client, output as the unique id to generate a request set in compositor randr, others will not do any operation on your private request structure. After you commit, you only commit your request and without submitting others requests. If only one thread/process uses client and output, just take request_id as 0 is enough. If more threads/process use the same client and output at the same time, client app needs generate a request id to be distinguished from others. Signed-off-by: Quanxian Wang <quanxian.w...@intel.com> --- clients/wrandr.c | 35 ++++++++++++++++++++++++++--------- module/wrandr/wrandr.c | 31 +++++++++++++++++++++---------- protocol/randr.xml | 8 ++++++++ 3 files changed, 55 insertions(+), 19 deletions(-) diff --git a/clients/wrandr.c b/clients/wrandr.c index 86e58a1..05cbd21 100644 --- a/clients/wrandr.c +++ b/clients/wrandr.c @@ -558,10 +558,12 @@ randr_printmode(struct output *output) static void randr_commit(struct randr *randr, - struct wl_output *wayland_output) + struct wl_output *wayland_output, + uint32_t request_id) { weston_randr_commit(randr->randr, - wayland_output); + wayland_output, + request_id); } static void @@ -695,7 +697,8 @@ query_output(struct randr *randr, static int del_new_mode(struct randr *randr, - struct argument *argument) + struct argument *argument, + uint32_t request_id) { int ret = RANDR_EXIT; @@ -703,6 +706,7 @@ del_new_mode(struct randr *randr, if (argument->delmode) { weston_randr_del_mode(randr->randr, randr->wayland_output, + request_id, randr->delmode->width, randr->delmode->height, randr->delmode->refresh); @@ -713,6 +717,7 @@ del_new_mode(struct randr *randr, if (argument->newmode) { weston_randr_new_mode(randr->randr, randr->wayland_output, + request_id, randr->newmode.clock, randr->newmode.hdisplay, randr->newmode.hsync_start, @@ -733,7 +738,8 @@ del_new_mode(struct randr *randr, static int output_modeset(struct randr *randr, - struct argument *argument) + struct argument *argument, + uint32_t request_id) { int ret = RANDR_EXIT; @@ -741,6 +747,7 @@ output_modeset(struct randr *randr, if (randr->mode) { weston_randr_set_mode(randr->randr, randr->wayland_output, + request_id, randr->mode->width, randr->mode->height, randr->mode->refresh); @@ -750,6 +757,7 @@ output_modeset(struct randr *randr, if (argument->scale != -1) { weston_randr_set_scale(randr->randr, randr->wayland_output, + request_id, argument->scale); ret = RANDR_COMMIT; } @@ -757,6 +765,7 @@ output_modeset(struct randr *randr, if (argument->transform >= 0) { weston_randr_set_transform(randr->randr, randr->wayland_output, + request_id, argument->transform); ret = RANDR_COMMIT; @@ -765,6 +774,7 @@ output_modeset(struct randr *randr, if (randr->loutput) { weston_randr_move(randr->randr, randr->wayland_output, + request_id, randr->loutput, WESTON_RANDR_MOVE_LEFTOF); ret = RANDR_COMMIT; @@ -773,6 +783,7 @@ output_modeset(struct randr *randr, if (randr->routput) { weston_randr_move(randr->randr, randr->wayland_output, + request_id, randr->routput, WESTON_RANDR_MOVE_RIGHTOF); ret = RANDR_COMMIT; @@ -789,6 +800,11 @@ main(int argc, char **argv) NULL, NULL, -1, -1, -1, -1}; int ret = 0; int commit = 0; + uint32_t request_id = 0; + + /* Get a request id to unique request process */ + srandom(10000); + request_id = random(); const struct weston_option randr_options[] = { { WESTON_OPTION_STRING, "output", 0, &argument.output}, @@ -830,22 +846,23 @@ main(int argc, char **argv) goto exit; randr.callback = - weston_randr_start(randr.randr, randr.wayland_output); + weston_randr_start(randr.randr, randr.wayland_output, request_id); wrandr_callback_add_listener(randr.callback, &wrandr_listener, &randr); - if (del_new_mode(&randr, &argument) == RANDR_COMMIT) + if (del_new_mode(&randr, &argument, request_id) == RANDR_COMMIT) commit += 1; - if (del_new_mode(&randr, &argument) == RANDR_COMMIT) + if (del_new_mode(&randr, &argument, request_id) == RANDR_COMMIT) commit += 1; - if (output_modeset(&randr, &argument) == RANDR_COMMIT) + if (output_modeset(&randr, &argument, request_id) == RANDR_COMMIT) commit += 1; if (commit > 0) { randr_commit(&randr, - randr.wayland_output); + randr.wayland_output, + request_id); } else goto exit; diff --git a/module/wrandr/wrandr.c b/module/wrandr/wrandr.c index b97d101..f17edc2 100644 --- a/module/wrandr/wrandr.c +++ b/module/wrandr/wrandr.c @@ -42,6 +42,7 @@ struct randr_request { * of these request.*/ struct wl_client *client; struct weston_output *output; + uint32_t request_id; /* output move */ struct weston_output *loutput; @@ -97,6 +98,7 @@ static struct randr_request * get_request(struct wl_resource *resource, struct wl_client *client, struct weston_output *output, + uint32_t request_id, int create) { struct wrandr *randr = @@ -106,6 +108,7 @@ get_request(struct wl_resource *resource, wl_list_for_each(request, &randr->pending.request_list, link) { if (request->client == client && + request->request_id == request_id && request->output == output) return request; } @@ -120,6 +123,7 @@ get_request(struct wl_resource *resource, request->client = client; request->output = output; + request->request_id = request_id; wl_list_insert(&randr->pending.request_list, &request->link); return request; } else @@ -393,13 +397,14 @@ static void randr_set_scale(struct wl_client *client, struct wl_resource *resource, struct wl_resource *output_resource, + uint32_t request_id, int32_t scale) { struct weston_output *output = wl_resource_get_user_data(output_resource); struct randr_request *request; - request = get_request(resource, client, output, 1); + request = get_request(resource, client, output, request_id, 1); if (request) { request->flags |= 1<<WRANDR_CALLBACK_ACTION_SCALE; request->scale = scale; @@ -410,13 +415,14 @@ static void randr_set_transform(struct wl_client *client, struct wl_resource *resource, struct wl_resource *output_resource, + uint32_t request_id, uint32_t transform) { struct weston_output *output = wl_resource_get_user_data(output_resource); struct randr_request *request; - request = get_request(resource, client, output, 1); + request = get_request(resource, client, output, request_id, 1); if (request) { request->flags |= 1<<WRANDR_CALLBACK_ACTION_TRANSFORM; request->transform = transform % 8; @@ -427,13 +433,13 @@ static void randr_start(struct wl_client *client, struct wl_resource *resource, struct wl_resource *output_resource, - uint32_t callback) + uint32_t request_id, uint32_t callback) { struct weston_output *output = wl_resource_get_user_data(output_resource); struct randr_request *request; - request = get_request(resource, client, output, 1); + request = get_request(resource, client, output, request_id, 1); if (!request) { wl_resource_post_no_memory(resource); return; @@ -453,13 +459,14 @@ static void randr_set_mode(struct wl_client *client, struct wl_resource *resource, struct wl_resource *output_resource, + uint32_t request_id, int width, int height, int refresh) { struct weston_output *output = wl_resource_get_user_data(output_resource); struct randr_request *request; - request = get_request(resource, client, output, 1); + request = get_request(resource, client, output, request_id, 1); if (request) { request->flags |= 1<<WRANDR_CALLBACK_ACTION_MODE; request->width = width; @@ -472,13 +479,14 @@ static void randr_move(struct wl_client *client, struct wl_resource *resource, struct wl_resource *target_resource, + uint32_t request_id, struct wl_resource *source_resource, int move) { struct weston_output *output = wl_resource_get_user_data(target_resource); struct randr_request *request; - request = get_request(resource, client, output, 1); + request = get_request(resource, client, output, request_id, 1); if (request) { request->flags |= 1<<WRANDR_CALLBACK_ACTION_MOVE; if (move == WESTON_RANDR_MOVE_LEFTOF) { @@ -563,6 +571,7 @@ static void randr_newmode(struct wl_client *client, struct wl_resource *resource, struct wl_resource *target_resource, + uint32_t request_id, int clock, int hdisplay, int hsync_start, @@ -579,7 +588,7 @@ randr_newmode(struct wl_client *client, wl_resource_get_user_data(target_resource); struct randr_request *request; - request = get_request(resource, client, output, 1); + request = get_request(resource, client, output, request_id, 1); if (request) { request->flags |= 1<<WRANDR_CALLBACK_ACTION_NEWMODE; request->newmode.clock = clock; @@ -631,6 +640,7 @@ static void randr_delmode(struct wl_client *client, struct wl_resource *resource, struct wl_resource *target_resource, + uint32_t request_id, int width, int height, int refresh) @@ -639,7 +649,7 @@ randr_delmode(struct wl_client *client, wl_resource_get_user_data(target_resource); struct randr_request *request; - request = get_request(resource, client, output, 1); + request = get_request(resource, client, output, request_id, 1); if (request) { request->flags |= 1<<WRANDR_CALLBACK_ACTION_DELMODE; request->delmode.width = width; @@ -651,7 +661,8 @@ randr_delmode(struct wl_client *client, static void randr_commit(struct wl_client *client, struct wl_resource *resource, - struct wl_resource *target_resource) + struct wl_resource *target_resource, + uint32_t request_id) { struct wrandr *randr = wl_resource_get_user_data(resource); struct weston_output *output = @@ -661,7 +672,7 @@ randr_commit(struct wl_client *client, int result = 0; /* process pending request for this client */ - request = get_request(resource, client, output, 0); + request = get_request(resource, client, output, request_id, 0); if (!request) { weston_log("No action happens when commit?!\n"); } else { diff --git a/protocol/randr.xml b/protocol/randr.xml index 07f83a4..555e6bf 100644 --- a/protocol/randr.xml +++ b/protocol/randr.xml @@ -56,6 +56,7 @@ posted for one randr request unless requested again. </description> <arg name="output" type="object" interface="wl_output"/> + <arg name="request_id" type="uint" summary="request id of randr"/> <arg name="callback" type="new_id" interface="wrandr_callback"/> </request> @@ -78,6 +79,7 @@ </description> <arg name="output" type="object" interface="wl_output" summary="the output object"/> + <arg name="request_id" type="uint" summary="request id of randr"/> <arg name="width" type="int" summary="width of the mode in hardware units"/> <arg name="height" type="int" summary="height of the mode in hardware units"/> <arg name="refresh" type="int" summary="vertical refresh rate in mHz"/> @@ -92,6 +94,7 @@ </description> <arg name="output" type="object" interface="wl_output" summary="the output object"/> + <arg name="request_id" type="uint" summary="request id of randr"/> <arg name="transform" type="uint" summary="the value should be between 0-7"/> </request> @@ -102,6 +105,7 @@ </description> <arg name="output" type="object" interface="wl_output" summary="the output object"/> + <arg name="request_id" type="uint" summary="request id of randr"/> <arg name="scale" type="int" summary="Scale the output"/> </request> @@ -121,6 +125,7 @@ </description> <arg name="target_output" type="object" interface="wl_output" summary="the target output object"/> + <arg name="request_id" type="uint" summary="request id of randr"/> <arg name="source_output" type="object" interface="wl_output" summary="the source output object"/> <arg name="move" type="int"/> @@ -132,6 +137,7 @@ </description> <arg name="output" type="object" interface="wl_output" summary="the output object"/> + <arg name="request_id" type="uint" summary="request id of randr"/> <arg name="width" type="int" summary="width of the mode in hardware units"/> <arg name="height" type="int" summary="height of the mode in hardware units"/> <arg name="refresh" type="int" summary="vertical refresh rate in mHz"/> @@ -143,6 +149,7 @@ </description> <arg name="output" type="object" interface="wl_output" summary="the output object"/> + <arg name="request_id" type="uint" summary="request id of randr"/> <arg name="fclock" type="int" summary="Pixel clock in hardware units Mhz"/> <arg name="hdisplay" type="int" @@ -176,6 +183,7 @@ </description> <arg name="output" type="object" interface="wl_output" summary="the output object"/> + <arg name="request_id" type="uint" summary="request id of randr"/> </request> </interface> -- 1.8.1.2 _______________________________________________ wayland-devel mailing list wayland-devel@lists.freedesktop.org http://lists.freedesktop.org/mailman/listinfo/wayland-devel