source: mainline/uspace/srv/clipboard/clipboard.c@ 837581fd

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

Move clipboard under location service.

  • Property mode set to 100644
File size: 5.1 KB
Line 
1/*
2 * Copyright (c) 2009 Martin Decky
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
29#include <async.h>
30#include <errno.h>
31#include <fibril_synch.h>
32#include <ipc/services.h>
33#include <ipc/clipboard.h>
34#include <loc.h>
35#include <malloc.h>
36#include <stdio.h>
37#include <stdbool.h>
38#include <task.h>
39
40#define NAME "clipboard"
41
42static char *clip_data = NULL;
43static size_t clip_size = 0;
44static clipboard_tag_t clip_tag = CLIPBOARD_TAG_NONE;
45static FIBRIL_MUTEX_INITIALIZE(clip_mtx);
46static service_id_t svc_id;
47
48static void clip_put_data(ipc_callid_t rid, ipc_call_t *request)
49{
50 char *data;
51 int rc;
52 size_t size;
53
54 switch (IPC_GET_ARG1(*request)) {
55 case CLIPBOARD_TAG_NONE:
56 fibril_mutex_lock(&clip_mtx);
57
58 if (clip_data)
59 free(clip_data);
60
61 clip_data = NULL;
62 clip_size = 0;
63 clip_tag = CLIPBOARD_TAG_NONE;
64
65 fibril_mutex_unlock(&clip_mtx);
66 async_answer_0(rid, EOK);
67 break;
68 case CLIPBOARD_TAG_DATA:
69 rc = async_data_write_accept((void **) &data, false, 0, 0, 0, &size);
70 if (rc != EOK) {
71 async_answer_0(rid, rc);
72 break;
73 }
74
75 fibril_mutex_lock(&clip_mtx);
76
77 if (clip_data)
78 free(clip_data);
79
80 clip_data = data;
81 clip_size = size;
82 clip_tag = CLIPBOARD_TAG_DATA;
83
84 fibril_mutex_unlock(&clip_mtx);
85 async_answer_0(rid, EOK);
86 break;
87 default:
88 async_answer_0(rid, EINVAL);
89 }
90}
91
92static void clip_get_data(ipc_callid_t rid, ipc_call_t *request)
93{
94 fibril_mutex_lock(&clip_mtx);
95
96 ipc_callid_t callid;
97 size_t size;
98
99 /* Check for clipboard data tag compatibility */
100 switch (IPC_GET_ARG1(*request)) {
101 case CLIPBOARD_TAG_DATA:
102 if (!async_data_read_receive(&callid, &size)) {
103 async_answer_0(callid, EINVAL);
104 async_answer_0(rid, EINVAL);
105 break;
106 }
107
108 if (clip_tag != CLIPBOARD_TAG_DATA) {
109 /* So far we only understand binary data */
110 async_answer_0(callid, EOVERFLOW);
111 async_answer_0(rid, EOVERFLOW);
112 break;
113 }
114
115 if (clip_size != size) {
116 /* The client expects different size of data */
117 async_answer_0(callid, EOVERFLOW);
118 async_answer_0(rid, EOVERFLOW);
119 break;
120 }
121
122 sysarg_t retval = async_data_read_finalize(callid, clip_data, size);
123 if (retval != EOK) {
124 async_answer_0(rid, retval);
125 break;
126 }
127
128 async_answer_0(rid, EOK);
129 break;
130 default:
131 /*
132 * Sorry, we don't know how to get unknown or NONE
133 * data from the clipbard
134 */
135 async_answer_0(rid, EINVAL);
136 break;
137 }
138
139 fibril_mutex_unlock(&clip_mtx);
140}
141
142static void clip_content(ipc_callid_t rid, ipc_call_t *request)
143{
144 fibril_mutex_lock(&clip_mtx);
145
146 size_t size = clip_size;
147 clipboard_tag_t tag = clip_tag;
148
149 fibril_mutex_unlock(&clip_mtx);
150 async_answer_2(rid, EOK, (sysarg_t) size, (sysarg_t) tag);
151}
152
153static void clip_connection(ipc_callid_t iid, ipc_call_t *icall, void *arg)
154{
155 /* Accept connection */
156 async_answer_0(iid, EOK);
157
158 while (true) {
159 ipc_call_t call;
160 ipc_callid_t callid = async_get_call(&call);
161
162 if (!IPC_GET_IMETHOD(call))
163 break;
164
165 switch (IPC_GET_IMETHOD(call)) {
166 case CLIPBOARD_PUT_DATA:
167 clip_put_data(callid, &call);
168 break;
169 case CLIPBOARD_GET_DATA:
170 clip_get_data(callid, &call);
171 break;
172 case CLIPBOARD_CONTENT:
173 clip_content(callid, &call);
174 break;
175 default:
176 async_answer_0(callid, ENOENT);
177 }
178 }
179}
180
181int main(int argc, char *argv[])
182{
183 int rc;
184
185 printf("%s: HelenOS clipboard service\n", NAME);
186 async_set_fallback_port_handler(clip_connection, NULL);
187
188 rc = loc_server_register(NAME);
189 if (rc != EOK) {
190 printf("%s: Failed registering server. (%d)\n", NAME, rc);
191 return rc;
192 }
193
194 rc = loc_service_register(SERVICE_NAME_CLIPBOARD, &svc_id);
195 if (rc != EOK) {
196 printf("%s: Failed registering service. (%d)\n", NAME, rc);
197 return rc;
198 }
199
200 printf("%s: Accepting connections\n", NAME);
201 task_retval(0);
202 async_manager();
203
204 /* Never reached */
205 return 0;
206}
Note: See TracBrowser for help on using the repository browser.