source: mainline/uspace/lib/c/generic/vol.c@ 3061bc1

lfn serial ticket/834-toolchain-update topic/msim-upgrade topic/simplify-dev-export
Last change on this file since 3061bc1 was b7fd2a0, checked in by Jiří Zárevúcky <zarevucky.jiri@…>, 7 years ago

Use errno_t in all uspace and kernel code.

Change type of every variable, parameter and return value that holds an
<errno.h> constant to either errno_t (the usual case), or sys_errno_t
(some places in kernel). This is for the purpose of self-documentation,
as well as for type-checking with a bit of type definition hackery.

Although this is a massive commit, it is a simple text replacement, and thus
is very easy to verify. Simply do the following:

`
git checkout <this commit's hash>
git reset HEAD
git add .
tools/srepl '\berrno_t\b' int
git add .
tools/srepl '\bsys_errno_t\b' sysarg_t
git reset
git diff
`

While this doesn't ensure that the replacements are correct, it does ensure
that the commit doesn't do anything except those replacements. Since errno_t
is typedef'd to int in the usual case (and sys_errno_t to sysarg_t), even if
incorrect, this commit cannot change behavior.

  • Property mode set to 100644
File size: 7.1 KB
Line 
1/*
2 * Copyright (c) 2015 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
29/** @addtogroup libc
30 * @{
31 */
32/** @file Volume service API
33 */
34
35#include <abi/ipc/interfaces.h>
36#include <errno.h>
37#include <ipc/services.h>
38#include <ipc/vol.h>
39#include <loc.h>
40#include <stdlib.h>
41#include <str.h>
42#include <vol.h>
43
44/** Create Volume service session.
45 *
46 * @param rvol Place to store pointer to volume service session.
47 * @return EOK on success, ENOMEM if out of memory, EIO if service
48 * cannot be contacted.
49 */
50errno_t vol_create(vol_t **rvol)
51{
52 vol_t *vol;
53 service_id_t vol_svcid;
54 errno_t rc;
55
56 vol = calloc(1, sizeof(vol_t));
57 if (vol == NULL) {
58 rc = ENOMEM;
59 goto error;
60 }
61
62 rc = loc_service_get_id(SERVICE_NAME_VOLSRV, &vol_svcid, 0);
63 if (rc != EOK) {
64 rc = ENOENT;
65 goto error;
66 }
67
68 vol->sess = loc_service_connect(vol_svcid, INTERFACE_VOL, 0);
69 if (vol->sess == NULL) {
70 rc = EIO;
71 goto error;
72 }
73
74 *rvol = vol;
75 return EOK;
76error:
77 free(vol);
78 return rc;
79}
80
81/** Destroy volume service session.
82 *
83 * @param vol Volume service session
84 */
85void vol_destroy(vol_t *vol)
86{
87 if (vol == NULL)
88 return;
89
90 async_hangup(vol->sess);
91 free(vol);
92}
93
94/** Get list of IDs into a buffer of fixed size.
95 *
96 * @param vol Volume service
97 * @param method IPC method
98 * @param arg1 First argument
99 * @param id_buf Buffer to store IDs
100 * @param buf_size Buffer size
101 * @param act_size Place to store actual size of complete data.
102 *
103 * @return EOK on success or an error code.
104 */
105static errno_t vol_get_ids_once(vol_t *vol, sysarg_t method, sysarg_t arg1,
106 sysarg_t *id_buf, size_t buf_size, size_t *act_size)
107{
108 async_exch_t *exch = async_exchange_begin(vol->sess);
109
110 ipc_call_t answer;
111 aid_t req = async_send_1(exch, method, arg1, &answer);
112 errno_t rc = async_data_read_start(exch, id_buf, buf_size);
113
114 async_exchange_end(exch);
115
116 if (rc != EOK) {
117 async_forget(req);
118 return rc;
119 }
120
121 errno_t retval;
122 async_wait_for(req, &retval);
123
124 if (retval != EOK) {
125 return retval;
126 }
127
128 *act_size = IPC_GET_ARG1(answer);
129 return EOK;
130}
131
132/** Get list of IDs.
133 *
134 * Returns an allocated array of service IDs.
135 *
136 * @param vol Volume service
137 * @param method IPC method
138 * @param arg1 IPC argument 1
139 * @param data Place to store pointer to array of IDs
140 * @param count Place to store number of IDs
141 * @return EOK on success or an error code
142 */
143static errno_t vol_get_ids_internal(vol_t *vol, sysarg_t method, sysarg_t arg1,
144 sysarg_t **data, size_t *count)
145{
146 *data = NULL;
147 *count = 0;
148
149 size_t act_size = 0;
150 errno_t rc = vol_get_ids_once(vol, method, arg1, NULL, 0, &act_size);
151 if (rc != EOK)
152 return rc;
153
154 size_t alloc_size = act_size;
155 service_id_t *ids = malloc(alloc_size);
156 if (ids == NULL)
157 return ENOMEM;
158
159 while (true) {
160 rc = vol_get_ids_once(vol, method, arg1, ids, alloc_size,
161 &act_size);
162 if (rc != EOK)
163 return rc;
164
165 if (act_size <= alloc_size)
166 break;
167
168 alloc_size = act_size;
169 ids = realloc(ids, alloc_size);
170 if (ids == NULL)
171 return ENOMEM;
172 }
173
174 *count = act_size / sizeof(service_id_t);
175 *data = ids;
176 return EOK;
177}
178
179/** Get list of partitions as array of service IDs.
180 *
181 * @param vol Volume service
182 * @param data Place to store pointer to array
183 * @param count Place to store length of array (number of entries)
184 *
185 * @return EOK on success or an error code
186 */
187errno_t vol_get_parts(vol_t *vol, service_id_t **data, size_t *count)
188{
189 return vol_get_ids_internal(vol, VOL_GET_PARTS, 0, data, count);
190}
191
192/** Add partition.
193 *
194 * After a partition is created (e.g. as a result of deleting a label
195 * the dummy partition is created), it can take some (unknown) time
196 * until it is discovered.
197 */
198errno_t vol_part_add(vol_t *vol, service_id_t sid)
199{
200 async_exch_t *exch;
201 errno_t retval;
202
203 exch = async_exchange_begin(vol->sess);
204 retval = async_req_1_0(exch, VOL_PART_ADD, sid);
205 async_exchange_end(exch);
206
207 if (retval != EOK)
208 return retval;
209
210 return EOK;
211}
212
213/** Get partition information. */
214errno_t vol_part_info(vol_t *vol, service_id_t sid, vol_part_info_t *vinfo)
215{
216 async_exch_t *exch;
217 errno_t retval;
218 ipc_call_t answer;
219
220 exch = async_exchange_begin(vol->sess);
221 aid_t req = async_send_1(exch, VOL_PART_INFO, sid, &answer);
222 errno_t rc = async_data_read_start(exch, vinfo, sizeof(vol_part_info_t));
223 async_exchange_end(exch);
224
225 if (rc != EOK) {
226 async_forget(req);
227 return EIO;
228 }
229
230 async_wait_for(req, &retval);
231 if (retval != EOK)
232 return EIO;
233
234 return EOK;
235}
236
237/** Erase partition (to the extent where we will consider it not containing
238 * a file system. */
239errno_t vol_part_empty(vol_t *vol, service_id_t sid)
240{
241 async_exch_t *exch;
242 errno_t retval;
243
244 exch = async_exchange_begin(vol->sess);
245 retval = async_req_1_0(exch, VOL_PART_EMPTY, sid);
246 async_exchange_end(exch);
247
248 if (retval != EOK)
249 return retval;
250
251 return EOK;
252}
253
254/** Get volume label support. */
255errno_t vol_part_get_lsupp(vol_t *vol, vol_fstype_t fstype,
256 vol_label_supp_t *vlsupp)
257{
258 async_exch_t *exch;
259 errno_t retval;
260 ipc_call_t answer;
261
262 exch = async_exchange_begin(vol->sess);
263 aid_t req = async_send_1(exch, VOL_PART_LSUPP, fstype, &answer);
264 errno_t rc = async_data_read_start(exch, vlsupp, sizeof(vol_label_supp_t));
265 async_exchange_end(exch);
266
267 if (rc != EOK) {
268 async_forget(req);
269 return EIO;
270 }
271
272 async_wait_for(req, &retval);
273 if (retval != EOK)
274 return EIO;
275
276 return EOK;
277}
278
279/** Create file system. */
280errno_t vol_part_mkfs(vol_t *vol, service_id_t sid, vol_fstype_t fstype,
281 const char *label)
282{
283 async_exch_t *exch;
284 ipc_call_t answer;
285 errno_t retval;
286
287 exch = async_exchange_begin(vol->sess);
288 aid_t req = async_send_2(exch, VOL_PART_MKFS, sid, fstype, &answer);
289 retval = async_data_write_start(exch, label, str_size(label));
290 async_exchange_end(exch);
291
292 if (retval != EOK) {
293 async_forget(req);
294 return retval;
295 }
296
297 async_wait_for(req, &retval);
298
299 if (retval != EOK)
300 return retval;
301
302 return EOK;
303}
304
305/** @}
306 */
Note: See TracBrowser for help on using the repository browser.