source: mainline/uspace/lib/display/src/disp_srv.c@ d1582b50

lfn serial ticket/834-toolchain-update topic/msim-upgrade topic/simplify-dev-export
Last change on this file since d1582b50 was 5480d5e, checked in by Jiri Svoboda <jiri@…>, 5 years ago

Add libdisplay method for setting window cursor

  • Property mode set to 100644
File size: 9.9 KB
RevLine 
[c8cf261]1/*
2 * Copyright (c) 2019 Jiri Svoboda
3 * All rights reserved.
4 *
5 * Redistribution and use in source and binary forms, with or without
6 * modification, are permitted provided that the following conditions
7 * are met:
8 *
9 * - Redistributions of source code must retain the above copyright
10 * notice, this list of conditions and the following disclaimer.
11 * - Redistributions in binary form must reproduce the above copyright
12 * notice, this list of conditions and the following disclaimer in the
13 * documentation and/or other materials provided with the distribution.
14 * - The name of the author may not be used to endorse or promote products
15 * derived from this software without specific prior written permission.
16 *
17 * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR
18 * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
19 * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
20 * IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT,
21 * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
22 * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
23 * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
24 * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
25 * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
26 * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
27 */
28
[973efd36]29/** @addtogroup libdisplay
[c8cf261]30 * @{
31 */
32/**
33 * @file
34 * @brief Display protocol server stub
35 */
36
37#include <disp_srv.h>
[b3c185b6]38#include <display/event.h>
[aeb3037]39#include <display/info.h>
[1e4a937]40#include <display/wndresize.h>
[c8cf261]41#include <errno.h>
[b3c185b6]42#include <io/log.h>
[c8cf261]43#include <ipc/display.h>
[959b7ec]44#include <mem.h>
[c8cf261]45#include <stdlib.h>
46#include <stddef.h>
[0e6e77f]47#include "../private/params.h"
[c8cf261]48
[b3c185b6]49static void display_callback_create_srv(display_srv_t *srv, ipc_call_t *call)
50{
51 async_sess_t *sess = async_callback_receive(EXCHANGE_SERIALIZE);
52 if (sess == NULL) {
53 async_answer_0(call, ENOMEM);
54 return;
55 }
56
57 srv->client_sess = sess;
58 async_answer_0(call, EOK);
59}
60
[c8cf261]61static void display_window_create_srv(display_srv_t *srv, ipc_call_t *icall)
62{
63 sysarg_t wnd_id;
[4d9c807]64 ipc_call_t call;
65 display_wnd_params_t params;
66 size_t size;
[c8cf261]67 errno_t rc;
68
[4d9c807]69 if (!async_data_write_receive(&call, &size)) {
70 async_answer_0(&call, EREFUSED);
71 async_answer_0(icall, EREFUSED);
72 return;
73 }
74
75 if (size != sizeof(display_wnd_params_t)) {
76 async_answer_0(&call, EINVAL);
77 async_answer_0(icall, EINVAL);
78 return;
79 }
80
81 rc = async_data_write_finalize(&call, &params, size);
82 if (rc != EOK) {
83 async_answer_0(&call, rc);
84 async_answer_0(icall, rc);
85 return;
86 }
87
[c8cf261]88 if (srv->ops->window_create == NULL) {
89 async_answer_0(icall, ENOTSUP);
90 return;
91 }
92
[4d9c807]93 rc = srv->ops->window_create(srv->arg, &params, &wnd_id);
[c8cf261]94 async_answer_1(icall, rc, wnd_id);
95}
96
97static void display_window_destroy_srv(display_srv_t *srv, ipc_call_t *icall)
98{
99 sysarg_t wnd_id;
100 errno_t rc;
101
102 wnd_id = ipc_get_arg1(icall);
103
[a2e104e]104 if (srv->ops->window_destroy == NULL) {
[c8cf261]105 async_answer_0(icall, ENOTSUP);
106 return;
107 }
108
109 rc = srv->ops->window_destroy(srv->arg, wnd_id);
110 async_answer_0(icall, rc);
111}
112
[a2e104e]113static void display_window_move_req_srv(display_srv_t *srv, ipc_call_t *icall)
114{
115 sysarg_t wnd_id;
116 ipc_call_t call;
117 gfx_coord2_t pos;
118 size_t size;
119 errno_t rc;
120
121 wnd_id = ipc_get_arg1(icall);
122
123 if (!async_data_write_receive(&call, &size)) {
124 async_answer_0(&call, EREFUSED);
125 async_answer_0(icall, EREFUSED);
126 return;
127 }
128
129 if (size != sizeof(gfx_coord2_t)) {
130 async_answer_0(&call, EINVAL);
131 async_answer_0(icall, EINVAL);
132 return;
133 }
134
135 rc = async_data_write_finalize(&call, &pos, size);
136 if (rc != EOK) {
137 async_answer_0(&call, rc);
138 async_answer_0(icall, rc);
139 return;
140 }
141
142 if (srv->ops->window_move_req == NULL) {
143 async_answer_0(icall, ENOTSUP);
144 return;
145 }
146
147 rc = srv->ops->window_move_req(srv->arg, wnd_id, &pos);
148 async_answer_0(icall, rc);
149}
150
[0680854]151static void display_window_move_srv(display_srv_t *srv, ipc_call_t *icall)
152{
153 sysarg_t wnd_id;
154 ipc_call_t call;
155 gfx_coord2_t dpos;
156 size_t size;
157 errno_t rc;
158
159 wnd_id = ipc_get_arg1(icall);
160
161 if (!async_data_write_receive(&call, &size)) {
162 async_answer_0(&call, EREFUSED);
163 async_answer_0(icall, EREFUSED);
164 return;
165 }
166
167 if (size != sizeof(gfx_coord2_t)) {
168 async_answer_0(&call, EINVAL);
169 async_answer_0(icall, EINVAL);
170 return;
171 }
172
173 rc = async_data_write_finalize(&call, &dpos, size);
174 if (rc != EOK) {
175 async_answer_0(&call, rc);
176 async_answer_0(icall, rc);
177 return;
178 }
179
180 if (srv->ops->window_move == NULL) {
181 async_answer_0(icall, ENOTSUP);
182 return;
183 }
184
185 rc = srv->ops->window_move(srv->arg, wnd_id, &dpos);
186 async_answer_0(icall, rc);
187}
188
[1e4a937]189static void display_window_resize_req_srv(display_srv_t *srv, ipc_call_t *icall)
190{
191 sysarg_t wnd_id;
192 ipc_call_t call;
193 display_wnd_rsztype_t rsztype;
194 gfx_coord2_t pos;
195 size_t size;
196 errno_t rc;
197
198 wnd_id = ipc_get_arg1(icall);
199 rsztype = (display_wnd_rsztype_t) ipc_get_arg2(icall);
200
201 if (!async_data_write_receive(&call, &size)) {
202 async_answer_0(&call, EREFUSED);
203 async_answer_0(icall, EREFUSED);
204 return;
205 }
206
207 if (size != sizeof(gfx_coord2_t)) {
208 async_answer_0(&call, EINVAL);
209 async_answer_0(icall, EINVAL);
210 return;
211 }
212
213 rc = async_data_write_finalize(&call, &pos, size);
214 if (rc != EOK) {
215 async_answer_0(&call, rc);
216 async_answer_0(icall, rc);
217 return;
218 }
219
220 if (srv->ops->window_resize_req == NULL) {
221 async_answer_0(icall, ENOTSUP);
222 return;
223 }
224
225 rc = srv->ops->window_resize_req(srv->arg, wnd_id, rsztype, &pos);
226 async_answer_0(icall, rc);
227}
228
[0e6e77f]229static void display_window_resize_srv(display_srv_t *srv, ipc_call_t *icall)
230{
231 sysarg_t wnd_id;
232 ipc_call_t call;
[7bb45e3]233 display_wnd_resize_t wresize;
[0e6e77f]234 size_t size;
235 errno_t rc;
236
237 wnd_id = ipc_get_arg1(icall);
238
239 if (!async_data_write_receive(&call, &size)) {
240 async_answer_0(&call, EREFUSED);
241 async_answer_0(icall, EREFUSED);
242 return;
243 }
244
[7bb45e3]245 if (size != sizeof(display_wnd_resize_t)) {
[0e6e77f]246 async_answer_0(&call, EINVAL);
247 async_answer_0(icall, EINVAL);
248 return;
249 }
250
[7bb45e3]251 rc = async_data_write_finalize(&call, &wresize, size);
[0e6e77f]252 if (rc != EOK) {
253 async_answer_0(&call, rc);
254 async_answer_0(icall, rc);
255 return;
256 }
257
258 if (srv->ops->window_resize == NULL) {
259 async_answer_0(icall, ENOTSUP);
260 return;
261 }
262
[7bb45e3]263 rc = srv->ops->window_resize(srv->arg, wnd_id, &wresize.offs,
264 &wresize.nrect);
[0e6e77f]265 async_answer_0(icall, rc);
266}
267
[5480d5e]268static void display_window_set_cursor_srv(display_srv_t *srv, ipc_call_t *icall)
269{
270 sysarg_t wnd_id;
271 display_stock_cursor_t cursor;
272 errno_t rc;
273
274 wnd_id = ipc_get_arg1(icall);
275 cursor = ipc_get_arg2(icall);
276
277 if (srv->ops->window_set_cursor == NULL) {
278 async_answer_0(icall, ENOTSUP);
279 return;
280 }
281
282 rc = srv->ops->window_set_cursor(srv->arg, wnd_id, cursor);
283 async_answer_0(icall, rc);
284}
285
[b3c185b6]286static void display_get_event_srv(display_srv_t *srv, ipc_call_t *icall)
287{
288 sysarg_t wnd_id;
289 display_wnd_ev_t event;
290 ipc_call_t call;
291 size_t size;
292 errno_t rc;
293
294 if (srv->ops->get_event == NULL) {
295 async_answer_0(icall, ENOTSUP);
296 return;
297 }
298
299 rc = srv->ops->get_event(srv->arg, &wnd_id, &event);
[dcac756]300 if (rc != EOK) {
[b3c185b6]301 async_answer_0(icall, rc);
[dcac756]302 return;
303 }
[b3c185b6]304
305 /* Transfer event data */
306 if (!async_data_read_receive(&call, &size)) {
307 async_answer_0(icall, EREFUSED);
308 return;
309 }
310
311 if (size != sizeof(event)) {
312 async_answer_0(icall, EREFUSED);
313 async_answer_0(&call, EREFUSED);
314 return;
315 }
316
317 rc = async_data_read_finalize(&call, &event, sizeof(event));
318 if (rc != EOK) {
319 async_answer_0(icall, rc);
320 async_answer_0(&call, rc);
321 return;
322 }
323
324 async_answer_1(icall, EOK, wnd_id);
325}
326
[aeb3037]327static void display_get_info_srv(display_srv_t *srv, ipc_call_t *icall)
328{
329 display_info_t info;
330 ipc_call_t call;
331 size_t size;
332 errno_t rc;
333
334 if (srv->ops->get_info == NULL) {
335 async_answer_0(icall, ENOTSUP);
336 return;
337 }
338
339 /* Transfer information */
340 if (!async_data_read_receive(&call, &size)) {
341 async_answer_0(icall, EREFUSED);
342 return;
343 }
344
345 if (size != sizeof(info)) {
346 async_answer_0(icall, EREFUSED);
347 async_answer_0(&call, EREFUSED);
348 return;
349 }
350
351 rc = srv->ops->get_info(srv->arg, &info);
352 if (rc != EOK) {
353 async_answer_0(icall, rc);
354 async_answer_0(&call, rc);
355 return;
356 }
357
358 rc = async_data_read_finalize(&call, &info, sizeof(info));
359 if (rc != EOK) {
360 async_answer_0(icall, rc);
361 async_answer_0(&call, rc);
362 return;
363 }
364
365 async_answer_0(icall, EOK);
366}
367
[c8cf261]368void display_conn(ipc_call_t *icall, display_srv_t *srv)
369{
370 /* Accept the connection */
371 async_accept_0(icall);
372
373 while (true) {
374 ipc_call_t call;
375
376 async_get_call(&call);
377 sysarg_t method = ipc_get_imethod(&call);
378
379 if (!method) {
380 /* The other side has hung up */
381 async_answer_0(&call, EOK);
382 break;
383 }
384
385 switch (method) {
[b3c185b6]386 case DISPLAY_CALLBACK_CREATE:
387 display_callback_create_srv(srv, &call);
388 break;
[c8cf261]389 case DISPLAY_WINDOW_CREATE:
390 display_window_create_srv(srv, &call);
391 break;
392 case DISPLAY_WINDOW_DESTROY:
393 display_window_destroy_srv(srv, &call);
394 break;
[a2e104e]395 case DISPLAY_WINDOW_MOVE_REQ:
396 display_window_move_req_srv(srv, &call);
397 break;
[0680854]398 case DISPLAY_WINDOW_MOVE:
399 display_window_move_srv(srv, &call);
400 break;
[1e4a937]401 case DISPLAY_WINDOW_RESIZE_REQ:
402 display_window_resize_req_srv(srv, &call);
403 break;
[0e6e77f]404 case DISPLAY_WINDOW_RESIZE:
405 display_window_resize_srv(srv, &call);
406 break;
[5480d5e]407 case DISPLAY_WINDOW_SET_CURSOR:
408 display_window_set_cursor_srv(srv, &call);
409 break;
[b3c185b6]410 case DISPLAY_GET_EVENT:
411 display_get_event_srv(srv, &call);
412 break;
[aeb3037]413 case DISPLAY_GET_INFO:
414 display_get_info_srv(srv, &call);
415 break;
[c8cf261]416 default:
417 async_answer_0(&call, ENOTSUP);
418 }
419 }
[959b7ec]420
421 /* Hang up callback session */
422 if (srv->client_sess != NULL) {
423 async_hangup(srv->client_sess);
424 srv->client_sess = NULL;
425 }
426}
427
428/** Initialize display server structure
429 *
430 * @param srv Display server structure to initialize
431 */
432void display_srv_initialize(display_srv_t *srv)
433{
434 memset(srv, 0, sizeof(*srv));
[c8cf261]435}
436
[b3c185b6]437/** Send 'pending' event to client.
438 *
439 * @param srv Display server structure
440 */
441void display_srv_ev_pending(display_srv_t *srv)
442{
443 async_exch_t *exch;
444
445 exch = async_exchange_begin(srv->client_sess);
446 async_msg_0(exch, DISPLAY_EV_PENDING);
447 async_exchange_end(exch);
448}
449
[c8cf261]450/** @}
451 */
Note: See TracBrowser for help on using the repository browser.