Print this page
9286 want refreservation=auto
Split |
Close |
Expand all |
Collapse all |
--- old/usr/src/lib/libzfs/common/libzfs_util.c
+++ new/usr/src/lib/libzfs/common/libzfs_util.c
1 1 /*
2 2 * CDDL HEADER START
3 3 *
4 4 * The contents of this file are subject to the terms of the
5 5 * Common Development and Distribution License (the "License").
6 6 * You may not use this file except in compliance with the License.
7 7 *
8 8 * You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE
9 9 * or http://www.opensolaris.org/os/licensing.
10 10 * See the License for the specific language governing permissions
11 11 * and limitations under the License.
12 12 *
13 13 * When distributing Covered Code, include this CDDL HEADER in each
↓ open down ↓ |
13 lines elided |
↑ open up ↑ |
14 14 * file and include the License file at usr/src/OPENSOLARIS.LICENSE.
15 15 * If applicable, add the following below this CDDL HEADER, with the
16 16 * fields enclosed by brackets "[]" replaced with your own identifying
17 17 * information: Portions Copyright [yyyy] [name of copyright owner]
18 18 *
19 19 * CDDL HEADER END
20 20 */
21 21
22 22 /*
23 23 * Copyright (c) 2005, 2010, Oracle and/or its affiliates. All rights reserved.
24 - * Copyright (c) 2013, Joyent, Inc. All rights reserved.
24 + * Copyright (c) 2018 Joyent, Inc.
25 25 * Copyright (c) 2011, 2017 by Delphix. All rights reserved.
26 26 * Copyright 2016 Igor Kozhukhov <ikozhukhov@gmail.com>
27 27 * Copyright (c) 2017 Datto Inc.
28 28 */
29 29
30 30 /*
31 31 * Internal utility routines for the ZFS library.
32 32 */
33 33
34 34 #include <errno.h>
35 35 #include <fcntl.h>
36 36 #include <libintl.h>
37 37 #include <stdarg.h>
38 38 #include <stdio.h>
39 39 #include <stdlib.h>
40 40 #include <strings.h>
41 41 #include <unistd.h>
42 42 #include <ctype.h>
43 43 #include <math.h>
44 44 #include <sys/filio.h>
45 45 #include <sys/mnttab.h>
46 46 #include <sys/mntent.h>
47 47 #include <sys/types.h>
48 48 #include <libcmdutils.h>
49 49
50 50 #include <libzfs.h>
51 51 #include <libzfs_core.h>
52 52
53 53 #include "libzfs_impl.h"
54 54 #include "zfs_prop.h"
55 55 #include "zfeature_common.h"
56 56
57 57 int
58 58 libzfs_errno(libzfs_handle_t *hdl)
59 59 {
60 60 return (hdl->libzfs_error);
61 61 }
62 62
63 63 const char *
64 64 libzfs_error_action(libzfs_handle_t *hdl)
65 65 {
66 66 return (hdl->libzfs_action);
67 67 }
68 68
69 69 const char *
70 70 libzfs_error_description(libzfs_handle_t *hdl)
71 71 {
72 72 if (hdl->libzfs_desc[0] != '\0')
73 73 return (hdl->libzfs_desc);
74 74
75 75 switch (hdl->libzfs_error) {
76 76 case EZFS_NOMEM:
77 77 return (dgettext(TEXT_DOMAIN, "out of memory"));
78 78 case EZFS_BADPROP:
79 79 return (dgettext(TEXT_DOMAIN, "invalid property value"));
80 80 case EZFS_PROPREADONLY:
81 81 return (dgettext(TEXT_DOMAIN, "read-only property"));
82 82 case EZFS_PROPTYPE:
83 83 return (dgettext(TEXT_DOMAIN, "property doesn't apply to "
84 84 "datasets of this type"));
85 85 case EZFS_PROPNONINHERIT:
86 86 return (dgettext(TEXT_DOMAIN, "property cannot be inherited"));
87 87 case EZFS_PROPSPACE:
88 88 return (dgettext(TEXT_DOMAIN, "invalid quota or reservation"));
89 89 case EZFS_BADTYPE:
90 90 return (dgettext(TEXT_DOMAIN, "operation not applicable to "
91 91 "datasets of this type"));
92 92 case EZFS_BUSY:
93 93 return (dgettext(TEXT_DOMAIN, "pool or dataset is busy"));
94 94 case EZFS_EXISTS:
95 95 return (dgettext(TEXT_DOMAIN, "pool or dataset exists"));
96 96 case EZFS_NOENT:
97 97 return (dgettext(TEXT_DOMAIN, "no such pool or dataset"));
98 98 case EZFS_BADSTREAM:
99 99 return (dgettext(TEXT_DOMAIN, "invalid backup stream"));
100 100 case EZFS_DSREADONLY:
101 101 return (dgettext(TEXT_DOMAIN, "dataset is read-only"));
102 102 case EZFS_VOLTOOBIG:
103 103 return (dgettext(TEXT_DOMAIN, "volume size exceeds limit for "
104 104 "this system"));
105 105 case EZFS_INVALIDNAME:
106 106 return (dgettext(TEXT_DOMAIN, "invalid name"));
107 107 case EZFS_BADRESTORE:
108 108 return (dgettext(TEXT_DOMAIN, "unable to restore to "
109 109 "destination"));
110 110 case EZFS_BADBACKUP:
111 111 return (dgettext(TEXT_DOMAIN, "backup failed"));
112 112 case EZFS_BADTARGET:
113 113 return (dgettext(TEXT_DOMAIN, "invalid target vdev"));
114 114 case EZFS_NODEVICE:
115 115 return (dgettext(TEXT_DOMAIN, "no such device in pool"));
116 116 case EZFS_BADDEV:
117 117 return (dgettext(TEXT_DOMAIN, "invalid device"));
118 118 case EZFS_NOREPLICAS:
119 119 return (dgettext(TEXT_DOMAIN, "no valid replicas"));
120 120 case EZFS_RESILVERING:
121 121 return (dgettext(TEXT_DOMAIN, "currently resilvering"));
122 122 case EZFS_BADVERSION:
123 123 return (dgettext(TEXT_DOMAIN, "unsupported version or "
124 124 "feature"));
125 125 case EZFS_POOLUNAVAIL:
126 126 return (dgettext(TEXT_DOMAIN, "pool is unavailable"));
127 127 case EZFS_DEVOVERFLOW:
128 128 return (dgettext(TEXT_DOMAIN, "too many devices in one vdev"));
129 129 case EZFS_BADPATH:
130 130 return (dgettext(TEXT_DOMAIN, "must be an absolute path"));
131 131 case EZFS_CROSSTARGET:
132 132 return (dgettext(TEXT_DOMAIN, "operation crosses datasets or "
133 133 "pools"));
134 134 case EZFS_ZONED:
135 135 return (dgettext(TEXT_DOMAIN, "dataset in use by local zone"));
136 136 case EZFS_MOUNTFAILED:
137 137 return (dgettext(TEXT_DOMAIN, "mount failed"));
138 138 case EZFS_UMOUNTFAILED:
139 139 return (dgettext(TEXT_DOMAIN, "umount failed"));
140 140 case EZFS_UNSHARENFSFAILED:
141 141 return (dgettext(TEXT_DOMAIN, "unshare(1M) failed"));
142 142 case EZFS_SHARENFSFAILED:
143 143 return (dgettext(TEXT_DOMAIN, "share(1M) failed"));
144 144 case EZFS_UNSHARESMBFAILED:
145 145 return (dgettext(TEXT_DOMAIN, "smb remove share failed"));
146 146 case EZFS_SHARESMBFAILED:
147 147 return (dgettext(TEXT_DOMAIN, "smb add share failed"));
148 148 case EZFS_PERM:
149 149 return (dgettext(TEXT_DOMAIN, "permission denied"));
150 150 case EZFS_NOSPC:
151 151 return (dgettext(TEXT_DOMAIN, "out of space"));
152 152 case EZFS_FAULT:
153 153 return (dgettext(TEXT_DOMAIN, "bad address"));
154 154 case EZFS_IO:
155 155 return (dgettext(TEXT_DOMAIN, "I/O error"));
156 156 case EZFS_INTR:
157 157 return (dgettext(TEXT_DOMAIN, "signal received"));
158 158 case EZFS_ISSPARE:
159 159 return (dgettext(TEXT_DOMAIN, "device is reserved as a hot "
160 160 "spare"));
161 161 case EZFS_INVALCONFIG:
162 162 return (dgettext(TEXT_DOMAIN, "invalid vdev configuration"));
163 163 case EZFS_RECURSIVE:
164 164 return (dgettext(TEXT_DOMAIN, "recursive dataset dependency"));
165 165 case EZFS_NOHISTORY:
166 166 return (dgettext(TEXT_DOMAIN, "no history available"));
167 167 case EZFS_POOLPROPS:
168 168 return (dgettext(TEXT_DOMAIN, "failed to retrieve "
169 169 "pool properties"));
170 170 case EZFS_POOL_NOTSUP:
171 171 return (dgettext(TEXT_DOMAIN, "operation not supported "
172 172 "on this type of pool"));
173 173 case EZFS_POOL_INVALARG:
174 174 return (dgettext(TEXT_DOMAIN, "invalid argument for "
175 175 "this pool operation"));
176 176 case EZFS_NAMETOOLONG:
177 177 return (dgettext(TEXT_DOMAIN, "dataset name is too long"));
178 178 case EZFS_OPENFAILED:
179 179 return (dgettext(TEXT_DOMAIN, "open failed"));
180 180 case EZFS_NOCAP:
181 181 return (dgettext(TEXT_DOMAIN,
182 182 "disk capacity information could not be retrieved"));
183 183 case EZFS_LABELFAILED:
184 184 return (dgettext(TEXT_DOMAIN, "write of label failed"));
185 185 case EZFS_BADWHO:
186 186 return (dgettext(TEXT_DOMAIN, "invalid user/group"));
187 187 case EZFS_BADPERM:
188 188 return (dgettext(TEXT_DOMAIN, "invalid permission"));
189 189 case EZFS_BADPERMSET:
190 190 return (dgettext(TEXT_DOMAIN, "invalid permission set name"));
191 191 case EZFS_NODELEGATION:
192 192 return (dgettext(TEXT_DOMAIN, "delegated administration is "
193 193 "disabled on pool"));
194 194 case EZFS_BADCACHE:
195 195 return (dgettext(TEXT_DOMAIN, "invalid or missing cache file"));
196 196 case EZFS_ISL2CACHE:
197 197 return (dgettext(TEXT_DOMAIN, "device is in use as a cache"));
198 198 case EZFS_VDEVNOTSUP:
199 199 return (dgettext(TEXT_DOMAIN, "vdev specification is not "
200 200 "supported"));
201 201 case EZFS_NOTSUP:
202 202 return (dgettext(TEXT_DOMAIN, "operation not supported "
203 203 "on this dataset"));
204 204 case EZFS_ACTIVE_SPARE:
205 205 return (dgettext(TEXT_DOMAIN, "pool has active shared spare "
206 206 "device"));
207 207 case EZFS_UNPLAYED_LOGS:
208 208 return (dgettext(TEXT_DOMAIN, "log device has unplayed intent "
209 209 "logs"));
210 210 case EZFS_REFTAG_RELE:
211 211 return (dgettext(TEXT_DOMAIN, "no such tag on this dataset"));
212 212 case EZFS_REFTAG_HOLD:
213 213 return (dgettext(TEXT_DOMAIN, "tag already exists on this "
214 214 "dataset"));
215 215 case EZFS_TAGTOOLONG:
216 216 return (dgettext(TEXT_DOMAIN, "tag too long"));
217 217 case EZFS_PIPEFAILED:
218 218 return (dgettext(TEXT_DOMAIN, "pipe create failed"));
219 219 case EZFS_THREADCREATEFAILED:
220 220 return (dgettext(TEXT_DOMAIN, "thread create failed"));
221 221 case EZFS_POSTSPLIT_ONLINE:
222 222 return (dgettext(TEXT_DOMAIN, "disk was split from this pool "
223 223 "into a new one"));
224 224 case EZFS_SCRUB_PAUSED:
225 225 return (dgettext(TEXT_DOMAIN, "scrub is paused; "
226 226 "use 'zpool scrub' to resume"));
227 227 case EZFS_SCRUBBING:
228 228 return (dgettext(TEXT_DOMAIN, "currently scrubbing; "
229 229 "use 'zpool scrub -s' to cancel current scrub"));
230 230 case EZFS_NO_SCRUB:
231 231 return (dgettext(TEXT_DOMAIN, "there is no active scrub"));
232 232 case EZFS_DIFF:
233 233 return (dgettext(TEXT_DOMAIN, "unable to generate diffs"));
234 234 case EZFS_DIFFDATA:
235 235 return (dgettext(TEXT_DOMAIN, "invalid diff data"));
236 236 case EZFS_POOLREADONLY:
237 237 return (dgettext(TEXT_DOMAIN, "pool is read-only"));
238 238 case EZFS_NO_PENDING:
239 239 return (dgettext(TEXT_DOMAIN, "operation is not "
240 240 "in progress"));
241 241 case EZFS_CHECKPOINT_EXISTS:
242 242 return (dgettext(TEXT_DOMAIN, "checkpoint exists"));
243 243 case EZFS_DISCARDING_CHECKPOINT:
244 244 return (dgettext(TEXT_DOMAIN, "currently discarding "
245 245 "checkpoint"));
246 246 case EZFS_NO_CHECKPOINT:
247 247 return (dgettext(TEXT_DOMAIN, "checkpoint does not exist"));
248 248 case EZFS_DEVRM_IN_PROGRESS:
249 249 return (dgettext(TEXT_DOMAIN, "device removal in progress"));
250 250 case EZFS_VDEV_TOO_BIG:
251 251 return (dgettext(TEXT_DOMAIN, "device exceeds supported size"));
252 252 case EZFS_UNKNOWN:
253 253 return (dgettext(TEXT_DOMAIN, "unknown error"));
254 254 default:
255 255 assert(hdl->libzfs_error == 0);
256 256 return (dgettext(TEXT_DOMAIN, "no error"));
257 257 }
258 258 }
259 259
260 260 /*PRINTFLIKE2*/
261 261 void
262 262 zfs_error_aux(libzfs_handle_t *hdl, const char *fmt, ...)
263 263 {
264 264 va_list ap;
265 265
266 266 va_start(ap, fmt);
267 267
268 268 (void) vsnprintf(hdl->libzfs_desc, sizeof (hdl->libzfs_desc),
269 269 fmt, ap);
270 270 hdl->libzfs_desc_active = 1;
271 271
272 272 va_end(ap);
273 273 }
274 274
275 275 static void
276 276 zfs_verror(libzfs_handle_t *hdl, int error, const char *fmt, va_list ap)
277 277 {
278 278 (void) vsnprintf(hdl->libzfs_action, sizeof (hdl->libzfs_action),
279 279 fmt, ap);
280 280 hdl->libzfs_error = error;
281 281
282 282 if (hdl->libzfs_desc_active)
283 283 hdl->libzfs_desc_active = 0;
284 284 else
285 285 hdl->libzfs_desc[0] = '\0';
286 286
287 287 if (hdl->libzfs_printerr) {
288 288 if (error == EZFS_UNKNOWN) {
289 289 (void) fprintf(stderr, dgettext(TEXT_DOMAIN, "internal "
290 290 "error: %s\n"), libzfs_error_description(hdl));
291 291 abort();
292 292 }
293 293
294 294 (void) fprintf(stderr, "%s: %s\n", hdl->libzfs_action,
295 295 libzfs_error_description(hdl));
296 296 if (error == EZFS_NOMEM)
297 297 exit(1);
298 298 }
299 299 }
300 300
301 301 int
302 302 zfs_error(libzfs_handle_t *hdl, int error, const char *msg)
303 303 {
304 304 return (zfs_error_fmt(hdl, error, "%s", msg));
305 305 }
306 306
307 307 /*PRINTFLIKE3*/
308 308 int
309 309 zfs_error_fmt(libzfs_handle_t *hdl, int error, const char *fmt, ...)
310 310 {
311 311 va_list ap;
312 312
313 313 va_start(ap, fmt);
314 314
315 315 zfs_verror(hdl, error, fmt, ap);
316 316
317 317 va_end(ap);
318 318
319 319 return (-1);
320 320 }
321 321
322 322 static int
323 323 zfs_common_error(libzfs_handle_t *hdl, int error, const char *fmt,
324 324 va_list ap)
325 325 {
326 326 switch (error) {
327 327 case EPERM:
328 328 case EACCES:
329 329 zfs_verror(hdl, EZFS_PERM, fmt, ap);
330 330 return (-1);
331 331
332 332 case ECANCELED:
333 333 zfs_verror(hdl, EZFS_NODELEGATION, fmt, ap);
334 334 return (-1);
335 335
336 336 case EIO:
337 337 zfs_verror(hdl, EZFS_IO, fmt, ap);
338 338 return (-1);
339 339
340 340 case EFAULT:
341 341 zfs_verror(hdl, EZFS_FAULT, fmt, ap);
342 342 return (-1);
343 343
344 344 case EINTR:
345 345 zfs_verror(hdl, EZFS_INTR, fmt, ap);
346 346 return (-1);
347 347 }
348 348
349 349 return (0);
350 350 }
351 351
352 352 int
353 353 zfs_standard_error(libzfs_handle_t *hdl, int error, const char *msg)
354 354 {
355 355 return (zfs_standard_error_fmt(hdl, error, "%s", msg));
356 356 }
357 357
358 358 /*PRINTFLIKE3*/
359 359 int
360 360 zfs_standard_error_fmt(libzfs_handle_t *hdl, int error, const char *fmt, ...)
361 361 {
362 362 va_list ap;
363 363
364 364 va_start(ap, fmt);
365 365
366 366 if (zfs_common_error(hdl, error, fmt, ap) != 0) {
367 367 va_end(ap);
368 368 return (-1);
369 369 }
370 370
371 371 switch (error) {
372 372 case ENXIO:
373 373 case ENODEV:
374 374 case EPIPE:
375 375 zfs_verror(hdl, EZFS_IO, fmt, ap);
376 376 break;
377 377
378 378 case ENOENT:
379 379 zfs_error_aux(hdl, dgettext(TEXT_DOMAIN,
380 380 "dataset does not exist"));
381 381 zfs_verror(hdl, EZFS_NOENT, fmt, ap);
382 382 break;
383 383
384 384 case ENOSPC:
385 385 case EDQUOT:
386 386 zfs_verror(hdl, EZFS_NOSPC, fmt, ap);
387 387 return (-1);
388 388
389 389 case EEXIST:
390 390 zfs_error_aux(hdl, dgettext(TEXT_DOMAIN,
391 391 "dataset already exists"));
392 392 zfs_verror(hdl, EZFS_EXISTS, fmt, ap);
393 393 break;
394 394
395 395 case EBUSY:
396 396 zfs_error_aux(hdl, dgettext(TEXT_DOMAIN,
397 397 "dataset is busy"));
398 398 zfs_verror(hdl, EZFS_BUSY, fmt, ap);
399 399 break;
400 400 case EROFS:
401 401 zfs_verror(hdl, EZFS_POOLREADONLY, fmt, ap);
402 402 break;
403 403 case ENAMETOOLONG:
404 404 zfs_verror(hdl, EZFS_NAMETOOLONG, fmt, ap);
405 405 break;
406 406 case ENOTSUP:
407 407 zfs_verror(hdl, EZFS_BADVERSION, fmt, ap);
408 408 break;
409 409 case EAGAIN:
410 410 zfs_error_aux(hdl, dgettext(TEXT_DOMAIN,
411 411 "pool I/O is currently suspended"));
412 412 zfs_verror(hdl, EZFS_POOLUNAVAIL, fmt, ap);
413 413 break;
414 414 default:
415 415 zfs_error_aux(hdl, strerror(error));
416 416 zfs_verror(hdl, EZFS_UNKNOWN, fmt, ap);
417 417 break;
418 418 }
419 419
420 420 va_end(ap);
421 421 return (-1);
422 422 }
423 423
424 424 int
425 425 zpool_standard_error(libzfs_handle_t *hdl, int error, const char *msg)
426 426 {
427 427 return (zpool_standard_error_fmt(hdl, error, "%s", msg));
428 428 }
429 429
430 430 /*PRINTFLIKE3*/
431 431 int
432 432 zpool_standard_error_fmt(libzfs_handle_t *hdl, int error, const char *fmt, ...)
433 433 {
434 434 va_list ap;
435 435
436 436 va_start(ap, fmt);
437 437
438 438 if (zfs_common_error(hdl, error, fmt, ap) != 0) {
439 439 va_end(ap);
440 440 return (-1);
441 441 }
442 442
443 443 switch (error) {
444 444 case ENODEV:
445 445 zfs_verror(hdl, EZFS_NODEVICE, fmt, ap);
446 446 break;
447 447
448 448 case ENOENT:
449 449 zfs_error_aux(hdl,
450 450 dgettext(TEXT_DOMAIN, "no such pool or dataset"));
451 451 zfs_verror(hdl, EZFS_NOENT, fmt, ap);
452 452 break;
453 453
454 454 case EEXIST:
455 455 zfs_error_aux(hdl, dgettext(TEXT_DOMAIN,
456 456 "pool already exists"));
457 457 zfs_verror(hdl, EZFS_EXISTS, fmt, ap);
458 458 break;
459 459
460 460 case EBUSY:
461 461 zfs_error_aux(hdl, dgettext(TEXT_DOMAIN, "pool is busy"));
462 462 zfs_verror(hdl, EZFS_BUSY, fmt, ap);
463 463 break;
464 464
465 465 case ENXIO:
466 466 zfs_error_aux(hdl, dgettext(TEXT_DOMAIN,
467 467 "one or more devices is currently unavailable"));
468 468 zfs_verror(hdl, EZFS_BADDEV, fmt, ap);
469 469 break;
470 470
471 471 case ENAMETOOLONG:
472 472 zfs_verror(hdl, EZFS_DEVOVERFLOW, fmt, ap);
473 473 break;
474 474
475 475 case ENOTSUP:
476 476 zfs_verror(hdl, EZFS_POOL_NOTSUP, fmt, ap);
477 477 break;
478 478
479 479 case EINVAL:
480 480 zfs_verror(hdl, EZFS_POOL_INVALARG, fmt, ap);
481 481 break;
482 482
483 483 case ENOSPC:
484 484 case EDQUOT:
485 485 zfs_verror(hdl, EZFS_NOSPC, fmt, ap);
486 486 return (-1);
487 487
488 488 case EAGAIN:
489 489 zfs_error_aux(hdl, dgettext(TEXT_DOMAIN,
490 490 "pool I/O is currently suspended"));
491 491 zfs_verror(hdl, EZFS_POOLUNAVAIL, fmt, ap);
492 492 break;
493 493
494 494 case EROFS:
495 495 zfs_verror(hdl, EZFS_POOLREADONLY, fmt, ap);
496 496 break;
497 497 /* There is no pending operation to cancel */
498 498 case ENOTACTIVE:
499 499 zfs_verror(hdl, EZFS_NO_PENDING, fmt, ap);
500 500 break;
501 501 case ZFS_ERR_CHECKPOINT_EXISTS:
502 502 zfs_verror(hdl, EZFS_CHECKPOINT_EXISTS, fmt, ap);
503 503 break;
504 504 case ZFS_ERR_DISCARDING_CHECKPOINT:
505 505 zfs_verror(hdl, EZFS_DISCARDING_CHECKPOINT, fmt, ap);
506 506 break;
507 507 case ZFS_ERR_NO_CHECKPOINT:
508 508 zfs_verror(hdl, EZFS_NO_CHECKPOINT, fmt, ap);
509 509 break;
510 510 case ZFS_ERR_DEVRM_IN_PROGRESS:
511 511 zfs_verror(hdl, EZFS_DEVRM_IN_PROGRESS, fmt, ap);
512 512 break;
513 513 case ZFS_ERR_VDEV_TOO_BIG:
514 514 zfs_verror(hdl, EZFS_VDEV_TOO_BIG, fmt, ap);
515 515 break;
516 516 default:
517 517 zfs_error_aux(hdl, strerror(error));
518 518 zfs_verror(hdl, EZFS_UNKNOWN, fmt, ap);
519 519 }
520 520
521 521 va_end(ap);
522 522 return (-1);
523 523 }
524 524
525 525 /*
526 526 * Display an out of memory error message and abort the current program.
527 527 */
528 528 int
529 529 no_memory(libzfs_handle_t *hdl)
530 530 {
531 531 return (zfs_error(hdl, EZFS_NOMEM, "internal error"));
532 532 }
533 533
534 534 /*
535 535 * A safe form of malloc() which will die if the allocation fails.
536 536 */
537 537 void *
538 538 zfs_alloc(libzfs_handle_t *hdl, size_t size)
539 539 {
540 540 void *data;
541 541
542 542 if ((data = calloc(1, size)) == NULL)
543 543 (void) no_memory(hdl);
544 544
545 545 return (data);
546 546 }
547 547
548 548 /*
549 549 * A safe form of asprintf() which will die if the allocation fails.
550 550 */
551 551 /*PRINTFLIKE2*/
552 552 char *
553 553 zfs_asprintf(libzfs_handle_t *hdl, const char *fmt, ...)
554 554 {
555 555 va_list ap;
556 556 char *ret;
557 557 int err;
558 558
559 559 va_start(ap, fmt);
560 560
561 561 err = vasprintf(&ret, fmt, ap);
562 562
563 563 va_end(ap);
564 564
565 565 if (err < 0)
566 566 (void) no_memory(hdl);
567 567
568 568 return (ret);
569 569 }
570 570
571 571 /*
572 572 * A safe form of realloc(), which also zeroes newly allocated space.
573 573 */
574 574 void *
575 575 zfs_realloc(libzfs_handle_t *hdl, void *ptr, size_t oldsize, size_t newsize)
576 576 {
577 577 void *ret;
578 578
579 579 if ((ret = realloc(ptr, newsize)) == NULL) {
580 580 (void) no_memory(hdl);
581 581 return (NULL);
582 582 }
583 583
584 584 bzero((char *)ret + oldsize, (newsize - oldsize));
585 585 return (ret);
586 586 }
587 587
588 588 /*
589 589 * A safe form of strdup() which will die if the allocation fails.
590 590 */
591 591 char *
592 592 zfs_strdup(libzfs_handle_t *hdl, const char *str)
593 593 {
594 594 char *ret;
595 595
596 596 if ((ret = strdup(str)) == NULL)
597 597 (void) no_memory(hdl);
598 598
599 599 return (ret);
600 600 }
601 601
602 602 /*
603 603 * Convert a number to an appropriately human-readable output.
604 604 */
605 605 void
606 606 zfs_nicenum(uint64_t num, char *buf, size_t buflen)
607 607 {
608 608 nicenum(num, buf, buflen);
609 609 }
610 610
611 611 void
612 612 libzfs_print_on_error(libzfs_handle_t *hdl, boolean_t printerr)
613 613 {
614 614 hdl->libzfs_printerr = printerr;
615 615 }
616 616
617 617 libzfs_handle_t *
618 618 libzfs_init(void)
619 619 {
620 620 libzfs_handle_t *hdl;
621 621
622 622 if ((hdl = calloc(1, sizeof (libzfs_handle_t))) == NULL) {
623 623 return (NULL);
624 624 }
625 625
626 626 if ((hdl->libzfs_fd = open(ZFS_DEV, O_RDWR)) < 0) {
627 627 free(hdl);
628 628 return (NULL);
629 629 }
630 630
631 631 if ((hdl->libzfs_mnttab = fopen(MNTTAB, "rF")) == NULL) {
632 632 (void) close(hdl->libzfs_fd);
633 633 free(hdl);
634 634 return (NULL);
635 635 }
636 636
637 637 hdl->libzfs_sharetab = fopen("/etc/dfs/sharetab", "rF");
638 638
639 639 if (libzfs_core_init() != 0) {
640 640 (void) close(hdl->libzfs_fd);
641 641 (void) fclose(hdl->libzfs_mnttab);
642 642 (void) fclose(hdl->libzfs_sharetab);
643 643 free(hdl);
644 644 return (NULL);
645 645 }
646 646
647 647 zfs_prop_init();
648 648 zpool_prop_init();
649 649 zpool_feature_init();
650 650 libzfs_mnttab_init(hdl);
651 651
652 652 if (getenv("ZFS_PROP_DEBUG") != NULL) {
653 653 hdl->libzfs_prop_debug = B_TRUE;
654 654 }
655 655
656 656 return (hdl);
657 657 }
658 658
659 659 void
660 660 libzfs_fini(libzfs_handle_t *hdl)
661 661 {
662 662 (void) close(hdl->libzfs_fd);
663 663 if (hdl->libzfs_mnttab)
664 664 (void) fclose(hdl->libzfs_mnttab);
665 665 if (hdl->libzfs_sharetab)
666 666 (void) fclose(hdl->libzfs_sharetab);
667 667 zfs_uninit_libshare(hdl);
668 668 zpool_free_handles(hdl);
669 669 libzfs_fru_clear(hdl, B_TRUE);
670 670 namespace_clear(hdl);
671 671 libzfs_mnttab_fini(hdl);
672 672 libzfs_core_fini();
673 673 free(hdl);
674 674 }
675 675
676 676 libzfs_handle_t *
677 677 zpool_get_handle(zpool_handle_t *zhp)
678 678 {
679 679 return (zhp->zpool_hdl);
680 680 }
681 681
682 682 libzfs_handle_t *
683 683 zfs_get_handle(zfs_handle_t *zhp)
684 684 {
685 685 return (zhp->zfs_hdl);
686 686 }
687 687
688 688 zpool_handle_t *
689 689 zfs_get_pool_handle(const zfs_handle_t *zhp)
690 690 {
691 691 return (zhp->zpool_hdl);
692 692 }
693 693
694 694 /*
695 695 * Given a name, determine whether or not it's a valid path
696 696 * (starts with '/' or "./"). If so, walk the mnttab trying
697 697 * to match the device number. If not, treat the path as an
698 698 * fs/vol/snap/bkmark name.
699 699 */
700 700 zfs_handle_t *
701 701 zfs_path_to_zhandle(libzfs_handle_t *hdl, char *path, zfs_type_t argtype)
702 702 {
703 703 struct stat64 statbuf;
704 704 struct extmnttab entry;
705 705 int ret;
706 706
707 707 if (path[0] != '/' && strncmp(path, "./", strlen("./")) != 0) {
708 708 /*
709 709 * It's not a valid path, assume it's a name of type 'argtype'.
710 710 */
711 711 return (zfs_open(hdl, path, argtype));
712 712 }
713 713
714 714 if (stat64(path, &statbuf) != 0) {
715 715 (void) fprintf(stderr, "%s: %s\n", path, strerror(errno));
716 716 return (NULL);
717 717 }
718 718
719 719 rewind(hdl->libzfs_mnttab);
720 720 while ((ret = getextmntent(hdl->libzfs_mnttab, &entry, 0)) == 0) {
721 721 if (makedevice(entry.mnt_major, entry.mnt_minor) ==
722 722 statbuf.st_dev) {
723 723 break;
724 724 }
725 725 }
726 726 if (ret != 0) {
727 727 return (NULL);
728 728 }
729 729
730 730 if (strcmp(entry.mnt_fstype, MNTTYPE_ZFS) != 0) {
731 731 (void) fprintf(stderr, gettext("'%s': not a ZFS filesystem\n"),
732 732 path);
733 733 return (NULL);
734 734 }
735 735
736 736 return (zfs_open(hdl, entry.mnt_special, ZFS_TYPE_FILESYSTEM));
737 737 }
738 738
739 739 /*
740 740 * Initialize the zc_nvlist_dst member to prepare for receiving an nvlist from
741 741 * an ioctl().
742 742 */
743 743 int
744 744 zcmd_alloc_dst_nvlist(libzfs_handle_t *hdl, zfs_cmd_t *zc, size_t len)
745 745 {
746 746 if (len == 0)
747 747 len = 16 * 1024;
748 748 zc->zc_nvlist_dst_size = len;
749 749 zc->zc_nvlist_dst =
750 750 (uint64_t)(uintptr_t)zfs_alloc(hdl, zc->zc_nvlist_dst_size);
751 751 if (zc->zc_nvlist_dst == 0)
752 752 return (-1);
753 753
754 754 return (0);
755 755 }
756 756
757 757 /*
758 758 * Called when an ioctl() which returns an nvlist fails with ENOMEM. This will
759 759 * expand the nvlist to the size specified in 'zc_nvlist_dst_size', which was
760 760 * filled in by the kernel to indicate the actual required size.
761 761 */
762 762 int
763 763 zcmd_expand_dst_nvlist(libzfs_handle_t *hdl, zfs_cmd_t *zc)
764 764 {
765 765 free((void *)(uintptr_t)zc->zc_nvlist_dst);
766 766 zc->zc_nvlist_dst =
767 767 (uint64_t)(uintptr_t)zfs_alloc(hdl, zc->zc_nvlist_dst_size);
768 768 if (zc->zc_nvlist_dst == 0)
769 769 return (-1);
770 770
771 771 return (0);
772 772 }
773 773
774 774 /*
775 775 * Called to free the src and dst nvlists stored in the command structure.
776 776 */
777 777 void
778 778 zcmd_free_nvlists(zfs_cmd_t *zc)
779 779 {
780 780 free((void *)(uintptr_t)zc->zc_nvlist_conf);
781 781 free((void *)(uintptr_t)zc->zc_nvlist_src);
782 782 free((void *)(uintptr_t)zc->zc_nvlist_dst);
783 783 zc->zc_nvlist_conf = NULL;
784 784 zc->zc_nvlist_src = NULL;
785 785 zc->zc_nvlist_dst = NULL;
786 786 }
787 787
788 788 static int
789 789 zcmd_write_nvlist_com(libzfs_handle_t *hdl, uint64_t *outnv, uint64_t *outlen,
790 790 nvlist_t *nvl)
791 791 {
792 792 char *packed;
793 793 size_t len;
794 794
795 795 verify(nvlist_size(nvl, &len, NV_ENCODE_NATIVE) == 0);
796 796
797 797 if ((packed = zfs_alloc(hdl, len)) == NULL)
798 798 return (-1);
799 799
800 800 verify(nvlist_pack(nvl, &packed, &len, NV_ENCODE_NATIVE, 0) == 0);
801 801
802 802 *outnv = (uint64_t)(uintptr_t)packed;
803 803 *outlen = len;
804 804
805 805 return (0);
806 806 }
807 807
808 808 int
809 809 zcmd_write_conf_nvlist(libzfs_handle_t *hdl, zfs_cmd_t *zc, nvlist_t *nvl)
810 810 {
811 811 return (zcmd_write_nvlist_com(hdl, &zc->zc_nvlist_conf,
812 812 &zc->zc_nvlist_conf_size, nvl));
813 813 }
814 814
815 815 int
816 816 zcmd_write_src_nvlist(libzfs_handle_t *hdl, zfs_cmd_t *zc, nvlist_t *nvl)
817 817 {
818 818 return (zcmd_write_nvlist_com(hdl, &zc->zc_nvlist_src,
819 819 &zc->zc_nvlist_src_size, nvl));
820 820 }
821 821
822 822 /*
823 823 * Unpacks an nvlist from the ZFS ioctl command structure.
824 824 */
825 825 int
826 826 zcmd_read_dst_nvlist(libzfs_handle_t *hdl, zfs_cmd_t *zc, nvlist_t **nvlp)
827 827 {
828 828 if (nvlist_unpack((void *)(uintptr_t)zc->zc_nvlist_dst,
829 829 zc->zc_nvlist_dst_size, nvlp, 0) != 0)
830 830 return (no_memory(hdl));
831 831
832 832 return (0);
833 833 }
834 834
835 835 int
836 836 zfs_ioctl(libzfs_handle_t *hdl, int request, zfs_cmd_t *zc)
837 837 {
838 838 return (ioctl(hdl->libzfs_fd, request, zc));
839 839 }
840 840
841 841 /*
842 842 * ================================================================
843 843 * API shared by zfs and zpool property management
844 844 * ================================================================
845 845 */
846 846
847 847 static void
848 848 zprop_print_headers(zprop_get_cbdata_t *cbp, zfs_type_t type)
849 849 {
850 850 zprop_list_t *pl = cbp->cb_proplist;
851 851 int i;
852 852 char *title;
853 853 size_t len;
854 854
855 855 cbp->cb_first = B_FALSE;
856 856 if (cbp->cb_scripted)
857 857 return;
858 858
859 859 /*
860 860 * Start with the length of the column headers.
861 861 */
862 862 cbp->cb_colwidths[GET_COL_NAME] = strlen(dgettext(TEXT_DOMAIN, "NAME"));
863 863 cbp->cb_colwidths[GET_COL_PROPERTY] = strlen(dgettext(TEXT_DOMAIN,
864 864 "PROPERTY"));
865 865 cbp->cb_colwidths[GET_COL_VALUE] = strlen(dgettext(TEXT_DOMAIN,
866 866 "VALUE"));
867 867 cbp->cb_colwidths[GET_COL_RECVD] = strlen(dgettext(TEXT_DOMAIN,
868 868 "RECEIVED"));
869 869 cbp->cb_colwidths[GET_COL_SOURCE] = strlen(dgettext(TEXT_DOMAIN,
870 870 "SOURCE"));
871 871
872 872 /* first property is always NAME */
873 873 assert(cbp->cb_proplist->pl_prop ==
874 874 ((type == ZFS_TYPE_POOL) ? ZPOOL_PROP_NAME : ZFS_PROP_NAME));
875 875
876 876 /*
877 877 * Go through and calculate the widths for each column. For the
878 878 * 'source' column, we kludge it up by taking the worst-case scenario of
879 879 * inheriting from the longest name. This is acceptable because in the
880 880 * majority of cases 'SOURCE' is the last column displayed, and we don't
881 881 * use the width anyway. Note that the 'VALUE' column can be oversized,
882 882 * if the name of the property is much longer than any values we find.
883 883 */
884 884 for (pl = cbp->cb_proplist; pl != NULL; pl = pl->pl_next) {
885 885 /*
886 886 * 'PROPERTY' column
887 887 */
888 888 if (pl->pl_prop != ZPROP_INVAL) {
889 889 const char *propname = (type == ZFS_TYPE_POOL) ?
890 890 zpool_prop_to_name(pl->pl_prop) :
891 891 zfs_prop_to_name(pl->pl_prop);
892 892
893 893 len = strlen(propname);
894 894 if (len > cbp->cb_colwidths[GET_COL_PROPERTY])
895 895 cbp->cb_colwidths[GET_COL_PROPERTY] = len;
896 896 } else {
897 897 len = strlen(pl->pl_user_prop);
898 898 if (len > cbp->cb_colwidths[GET_COL_PROPERTY])
899 899 cbp->cb_colwidths[GET_COL_PROPERTY] = len;
900 900 }
901 901
902 902 /*
903 903 * 'VALUE' column. The first property is always the 'name'
904 904 * property that was tacked on either by /sbin/zfs's
905 905 * zfs_do_get() or when calling zprop_expand_list(), so we
906 906 * ignore its width. If the user specified the name property
907 907 * to display, then it will be later in the list in any case.
908 908 */
909 909 if (pl != cbp->cb_proplist &&
910 910 pl->pl_width > cbp->cb_colwidths[GET_COL_VALUE])
911 911 cbp->cb_colwidths[GET_COL_VALUE] = pl->pl_width;
912 912
913 913 /* 'RECEIVED' column. */
914 914 if (pl != cbp->cb_proplist &&
915 915 pl->pl_recvd_width > cbp->cb_colwidths[GET_COL_RECVD])
916 916 cbp->cb_colwidths[GET_COL_RECVD] = pl->pl_recvd_width;
917 917
918 918 /*
919 919 * 'NAME' and 'SOURCE' columns
920 920 */
921 921 if (pl->pl_prop == (type == ZFS_TYPE_POOL ? ZPOOL_PROP_NAME :
922 922 ZFS_PROP_NAME) &&
923 923 pl->pl_width > cbp->cb_colwidths[GET_COL_NAME]) {
924 924 cbp->cb_colwidths[GET_COL_NAME] = pl->pl_width;
925 925 cbp->cb_colwidths[GET_COL_SOURCE] = pl->pl_width +
926 926 strlen(dgettext(TEXT_DOMAIN, "inherited from"));
927 927 }
928 928 }
929 929
930 930 /*
931 931 * Now go through and print the headers.
932 932 */
933 933 for (i = 0; i < ZFS_GET_NCOLS; i++) {
934 934 switch (cbp->cb_columns[i]) {
935 935 case GET_COL_NAME:
936 936 title = dgettext(TEXT_DOMAIN, "NAME");
937 937 break;
938 938 case GET_COL_PROPERTY:
939 939 title = dgettext(TEXT_DOMAIN, "PROPERTY");
940 940 break;
941 941 case GET_COL_VALUE:
942 942 title = dgettext(TEXT_DOMAIN, "VALUE");
943 943 break;
944 944 case GET_COL_RECVD:
945 945 title = dgettext(TEXT_DOMAIN, "RECEIVED");
946 946 break;
947 947 case GET_COL_SOURCE:
948 948 title = dgettext(TEXT_DOMAIN, "SOURCE");
949 949 break;
950 950 default:
951 951 title = NULL;
952 952 }
953 953
954 954 if (title != NULL) {
955 955 if (i == (ZFS_GET_NCOLS - 1) ||
956 956 cbp->cb_columns[i + 1] == GET_COL_NONE)
957 957 (void) printf("%s", title);
958 958 else
959 959 (void) printf("%-*s ",
960 960 cbp->cb_colwidths[cbp->cb_columns[i]],
961 961 title);
962 962 }
963 963 }
964 964 (void) printf("\n");
965 965 }
966 966
967 967 /*
968 968 * Display a single line of output, according to the settings in the callback
969 969 * structure.
970 970 */
971 971 void
972 972 zprop_print_one_property(const char *name, zprop_get_cbdata_t *cbp,
973 973 const char *propname, const char *value, zprop_source_t sourcetype,
974 974 const char *source, const char *recvd_value)
975 975 {
976 976 int i;
977 977 const char *str = NULL;
978 978 char buf[128];
979 979
980 980 /*
981 981 * Ignore those source types that the user has chosen to ignore.
982 982 */
983 983 if ((sourcetype & cbp->cb_sources) == 0)
984 984 return;
985 985
986 986 if (cbp->cb_first)
987 987 zprop_print_headers(cbp, cbp->cb_type);
988 988
989 989 for (i = 0; i < ZFS_GET_NCOLS; i++) {
990 990 switch (cbp->cb_columns[i]) {
991 991 case GET_COL_NAME:
992 992 str = name;
993 993 break;
994 994
995 995 case GET_COL_PROPERTY:
996 996 str = propname;
997 997 break;
998 998
999 999 case GET_COL_VALUE:
1000 1000 str = value;
1001 1001 break;
1002 1002
1003 1003 case GET_COL_SOURCE:
1004 1004 switch (sourcetype) {
1005 1005 case ZPROP_SRC_NONE:
1006 1006 str = "-";
1007 1007 break;
1008 1008
1009 1009 case ZPROP_SRC_DEFAULT:
1010 1010 str = "default";
1011 1011 break;
1012 1012
1013 1013 case ZPROP_SRC_LOCAL:
1014 1014 str = "local";
1015 1015 break;
1016 1016
1017 1017 case ZPROP_SRC_TEMPORARY:
1018 1018 str = "temporary";
1019 1019 break;
1020 1020
1021 1021 case ZPROP_SRC_INHERITED:
1022 1022 (void) snprintf(buf, sizeof (buf),
1023 1023 "inherited from %s", source);
1024 1024 str = buf;
1025 1025 break;
1026 1026 case ZPROP_SRC_RECEIVED:
1027 1027 str = "received";
1028 1028 break;
1029 1029
1030 1030 default:
1031 1031 str = NULL;
1032 1032 assert(!"unhandled zprop_source_t");
1033 1033 }
1034 1034 break;
1035 1035
1036 1036 case GET_COL_RECVD:
1037 1037 str = (recvd_value == NULL ? "-" : recvd_value);
1038 1038 break;
1039 1039
1040 1040 default:
1041 1041 continue;
1042 1042 }
1043 1043
1044 1044 if (cbp->cb_columns[i + 1] == GET_COL_NONE)
1045 1045 (void) printf("%s", str);
1046 1046 else if (cbp->cb_scripted)
1047 1047 (void) printf("%s\t", str);
1048 1048 else
1049 1049 (void) printf("%-*s ",
1050 1050 cbp->cb_colwidths[cbp->cb_columns[i]],
1051 1051 str);
1052 1052 }
1053 1053
1054 1054 (void) printf("\n");
1055 1055 }
1056 1056
1057 1057 /*
1058 1058 * Given a numeric suffix, convert the value into a number of bits that the
1059 1059 * resulting value must be shifted.
1060 1060 */
1061 1061 static int
1062 1062 str2shift(libzfs_handle_t *hdl, const char *buf)
1063 1063 {
1064 1064 const char *ends = "BKMGTPEZ";
1065 1065 int i;
1066 1066
1067 1067 if (buf[0] == '\0')
1068 1068 return (0);
1069 1069 for (i = 0; i < strlen(ends); i++) {
1070 1070 if (toupper(buf[0]) == ends[i])
1071 1071 break;
1072 1072 }
1073 1073 if (i == strlen(ends)) {
1074 1074 zfs_error_aux(hdl, dgettext(TEXT_DOMAIN,
1075 1075 "invalid numeric suffix '%s'"), buf);
1076 1076 return (-1);
1077 1077 }
1078 1078
1079 1079 /*
1080 1080 * We want to allow trailing 'b' characters for 'GB' or 'Mb'. But don't
1081 1081 * allow 'BB' - that's just weird.
1082 1082 */
1083 1083 if (buf[1] == '\0' || (toupper(buf[1]) == 'B' && buf[2] == '\0' &&
1084 1084 toupper(buf[0]) != 'B'))
1085 1085 return (10*i);
1086 1086
1087 1087 zfs_error_aux(hdl, dgettext(TEXT_DOMAIN,
1088 1088 "invalid numeric suffix '%s'"), buf);
1089 1089 return (-1);
1090 1090 }
1091 1091
1092 1092 /*
1093 1093 * Convert a string of the form '100G' into a real number. Used when setting
1094 1094 * properties or creating a volume. 'buf' is used to place an extended error
1095 1095 * message for the caller to use.
1096 1096 */
1097 1097 int
1098 1098 zfs_nicestrtonum(libzfs_handle_t *hdl, const char *value, uint64_t *num)
1099 1099 {
1100 1100 char *end;
1101 1101 int shift;
1102 1102
1103 1103 *num = 0;
1104 1104
1105 1105 /* Check to see if this looks like a number. */
1106 1106 if ((value[0] < '0' || value[0] > '9') && value[0] != '.') {
1107 1107 if (hdl)
1108 1108 zfs_error_aux(hdl, dgettext(TEXT_DOMAIN,
1109 1109 "bad numeric value '%s'"), value);
1110 1110 return (-1);
1111 1111 }
1112 1112
1113 1113 /* Rely on strtoull() to process the numeric portion. */
1114 1114 errno = 0;
1115 1115 *num = strtoull(value, &end, 10);
1116 1116
1117 1117 /*
1118 1118 * Check for ERANGE, which indicates that the value is too large to fit
1119 1119 * in a 64-bit value.
1120 1120 */
1121 1121 if (errno == ERANGE) {
1122 1122 if (hdl)
1123 1123 zfs_error_aux(hdl, dgettext(TEXT_DOMAIN,
1124 1124 "numeric value is too large"));
1125 1125 return (-1);
1126 1126 }
1127 1127
1128 1128 /*
1129 1129 * If we have a decimal value, then do the computation with floating
1130 1130 * point arithmetic. Otherwise, use standard arithmetic.
1131 1131 */
1132 1132 if (*end == '.') {
1133 1133 double fval = strtod(value, &end);
1134 1134
1135 1135 if ((shift = str2shift(hdl, end)) == -1)
1136 1136 return (-1);
1137 1137
1138 1138 fval *= pow(2, shift);
1139 1139
1140 1140 if (fval > UINT64_MAX) {
1141 1141 if (hdl)
1142 1142 zfs_error_aux(hdl, dgettext(TEXT_DOMAIN,
1143 1143 "numeric value is too large"));
1144 1144 return (-1);
1145 1145 }
1146 1146
1147 1147 *num = (uint64_t)fval;
1148 1148 } else {
1149 1149 if ((shift = str2shift(hdl, end)) == -1)
1150 1150 return (-1);
1151 1151
1152 1152 /* Check for overflow */
1153 1153 if (shift >= 64 || (*num << shift) >> shift != *num) {
1154 1154 if (hdl)
1155 1155 zfs_error_aux(hdl, dgettext(TEXT_DOMAIN,
1156 1156 "numeric value is too large"));
1157 1157 return (-1);
1158 1158 }
1159 1159
1160 1160 *num <<= shift;
1161 1161 }
1162 1162
1163 1163 return (0);
1164 1164 }
1165 1165
1166 1166 /*
1167 1167 * Given a propname=value nvpair to set, parse any numeric properties
1168 1168 * (index, boolean, etc) if they are specified as strings and add the
1169 1169 * resulting nvpair to the returned nvlist.
1170 1170 *
1171 1171 * At the DSL layer, all properties are either 64-bit numbers or strings.
1172 1172 * We want the user to be able to ignore this fact and specify properties
1173 1173 * as native values (numbers, for example) or as strings (to simplify
1174 1174 * command line utilities). This also handles converting index types
1175 1175 * (compression, checksum, etc) from strings to their on-disk index.
1176 1176 */
↓ open down ↓ |
1142 lines elided |
↑ open up ↑ |
1177 1177 int
1178 1178 zprop_parse_value(libzfs_handle_t *hdl, nvpair_t *elem, int prop,
1179 1179 zfs_type_t type, nvlist_t *ret, char **svalp, uint64_t *ivalp,
1180 1180 const char *errbuf)
1181 1181 {
1182 1182 data_type_t datatype = nvpair_type(elem);
1183 1183 zprop_type_t proptype;
1184 1184 const char *propname;
1185 1185 char *value;
1186 1186 boolean_t isnone = B_FALSE;
1187 + boolean_t isauto = B_FALSE;
1187 1188
1188 1189 if (type == ZFS_TYPE_POOL) {
1189 1190 proptype = zpool_prop_get_type(prop);
1190 1191 propname = zpool_prop_to_name(prop);
1191 1192 } else {
1192 1193 proptype = zfs_prop_get_type(prop);
1193 1194 propname = zfs_prop_to_name(prop);
1194 1195 }
1195 1196
1196 1197 /*
1197 1198 * Convert any properties to the internal DSL value types.
1198 1199 */
1199 1200 *svalp = NULL;
1200 1201 *ivalp = 0;
1201 1202
1202 1203 switch (proptype) {
1203 1204 case PROP_TYPE_STRING:
1204 1205 if (datatype != DATA_TYPE_STRING) {
1205 1206 zfs_error_aux(hdl, dgettext(TEXT_DOMAIN,
1206 1207 "'%s' must be a string"), nvpair_name(elem));
1207 1208 goto error;
1208 1209 }
1209 1210 (void) nvpair_value_string(elem, svalp);
1210 1211 if (strlen(*svalp) >= ZFS_MAXPROPLEN) {
1211 1212 zfs_error_aux(hdl, dgettext(TEXT_DOMAIN,
↓ open down ↓ |
15 lines elided |
↑ open up ↑ |
1212 1213 "'%s' is too long"), nvpair_name(elem));
1213 1214 goto error;
1214 1215 }
1215 1216 break;
1216 1217
1217 1218 case PROP_TYPE_NUMBER:
1218 1219 if (datatype == DATA_TYPE_STRING) {
1219 1220 (void) nvpair_value_string(elem, &value);
1220 1221 if (strcmp(value, "none") == 0) {
1221 1222 isnone = B_TRUE;
1222 - } else if (zfs_nicestrtonum(hdl, value, ivalp)
1223 - != 0) {
1223 + } else if (strcmp(value, "auto") == 0) {
1224 + isauto = B_TRUE;
1225 + } else if (zfs_nicestrtonum(hdl, value, ivalp) != 0) {
1224 1226 goto error;
1225 1227 }
1226 1228 } else if (datatype == DATA_TYPE_UINT64) {
1227 1229 (void) nvpair_value_uint64(elem, ivalp);
1228 1230 } else {
1229 1231 zfs_error_aux(hdl, dgettext(TEXT_DOMAIN,
1230 1232 "'%s' must be a number"), nvpair_name(elem));
1231 1233 goto error;
1232 1234 }
1233 1235
1234 1236 /*
1235 1237 * Quota special: force 'none' and don't allow 0.
1236 1238 */
1237 1239 if ((type & ZFS_TYPE_DATASET) && *ivalp == 0 && !isnone &&
1238 1240 (prop == ZFS_PROP_QUOTA || prop == ZFS_PROP_REFQUOTA)) {
1239 1241 zfs_error_aux(hdl, dgettext(TEXT_DOMAIN,
1240 1242 "use 'none' to disable quota/refquota"));
1241 1243 goto error;
1242 1244 }
↓ open down ↓ |
9 lines elided |
↑ open up ↑ |
1243 1245
1244 1246 /*
1245 1247 * Special handling for "*_limit=none". In this case it's not
1246 1248 * 0 but UINT64_MAX.
1247 1249 */
1248 1250 if ((type & ZFS_TYPE_DATASET) && isnone &&
1249 1251 (prop == ZFS_PROP_FILESYSTEM_LIMIT ||
1250 1252 prop == ZFS_PROP_SNAPSHOT_LIMIT)) {
1251 1253 *ivalp = UINT64_MAX;
1252 1254 }
1255 +
1256 + /*
1257 + * Special handling for setting 'reservation' and
1258 + * 'refreservation' to 'auto'. Use UINT64_MAX to tell the
1259 + * caller to use zfs_fix_auto_resv(). 'auto' is only allowed on
1260 + * volumes.
1261 + */
1262 + if (isauto) {
1263 + switch (prop) {
1264 + case ZFS_PROP_RESERVATION:
1265 + case ZFS_PROP_REFRESERVATION:
1266 + if ((type & ZFS_TYPE_VOLUME) == 0) {
1267 + zfs_error_aux(hdl, dgettext(TEXT_DOMAIN,
1268 + "'%s=auto' only allowed on "
1269 + "volumes"), nvpair_name(elem));
1270 + goto error;
1271 + }
1272 + *ivalp = UINT64_MAX;
1273 + break;
1274 + default:
1275 + zfs_error_aux(hdl, dgettext(TEXT_DOMAIN,
1276 + "'auto' is invalid value for '%s'"),
1277 + nvpair_name(elem));
1278 + goto error;
1279 + }
1280 + }
1281 +
1253 1282 break;
1254 1283
1255 1284 case PROP_TYPE_INDEX:
1256 1285 if (datatype != DATA_TYPE_STRING) {
1257 1286 zfs_error_aux(hdl, dgettext(TEXT_DOMAIN,
1258 1287 "'%s' must be a string"), nvpair_name(elem));
1259 1288 goto error;
1260 1289 }
1261 1290
1262 1291 (void) nvpair_value_string(elem, &value);
1263 1292
1264 1293 if (zprop_string_to_index(prop, value, ivalp, type) != 0) {
1265 1294 zfs_error_aux(hdl, dgettext(TEXT_DOMAIN,
1266 1295 "'%s' must be one of '%s'"), propname,
1267 1296 zprop_values(prop, type));
1268 1297 goto error;
1269 1298 }
1270 1299 break;
1271 1300
1272 1301 default:
1273 1302 abort();
1274 1303 }
1275 1304
1276 1305 /*
1277 1306 * Add the result to our return set of properties.
1278 1307 */
1279 1308 if (*svalp != NULL) {
1280 1309 if (nvlist_add_string(ret, propname, *svalp) != 0) {
1281 1310 (void) no_memory(hdl);
1282 1311 return (-1);
1283 1312 }
1284 1313 } else {
1285 1314 if (nvlist_add_uint64(ret, propname, *ivalp) != 0) {
1286 1315 (void) no_memory(hdl);
1287 1316 return (-1);
1288 1317 }
1289 1318 }
1290 1319
1291 1320 return (0);
1292 1321 error:
1293 1322 (void) zfs_error(hdl, EZFS_BADPROP, errbuf);
1294 1323 return (-1);
1295 1324 }
1296 1325
1297 1326 static int
1298 1327 addlist(libzfs_handle_t *hdl, char *propname, zprop_list_t **listp,
1299 1328 zfs_type_t type)
1300 1329 {
1301 1330 int prop;
1302 1331 zprop_list_t *entry;
1303 1332
1304 1333 prop = zprop_name_to_prop(propname, type);
1305 1334
1306 1335 if (prop != ZPROP_INVAL && !zprop_valid_for_type(prop, type))
1307 1336 prop = ZPROP_INVAL;
1308 1337
1309 1338 /*
1310 1339 * When no property table entry can be found, return failure if
1311 1340 * this is a pool property or if this isn't a user-defined
1312 1341 * dataset property,
1313 1342 */
1314 1343 if (prop == ZPROP_INVAL && ((type == ZFS_TYPE_POOL &&
1315 1344 !zpool_prop_feature(propname) &&
1316 1345 !zpool_prop_unsupported(propname)) ||
1317 1346 (type == ZFS_TYPE_DATASET && !zfs_prop_user(propname) &&
1318 1347 !zfs_prop_userquota(propname) && !zfs_prop_written(propname)))) {
1319 1348 zfs_error_aux(hdl, dgettext(TEXT_DOMAIN,
1320 1349 "invalid property '%s'"), propname);
1321 1350 return (zfs_error(hdl, EZFS_BADPROP,
1322 1351 dgettext(TEXT_DOMAIN, "bad property list")));
1323 1352 }
1324 1353
1325 1354 if ((entry = zfs_alloc(hdl, sizeof (zprop_list_t))) == NULL)
1326 1355 return (-1);
1327 1356
1328 1357 entry->pl_prop = prop;
1329 1358 if (prop == ZPROP_INVAL) {
1330 1359 if ((entry->pl_user_prop = zfs_strdup(hdl, propname)) ==
1331 1360 NULL) {
1332 1361 free(entry);
1333 1362 return (-1);
1334 1363 }
1335 1364 entry->pl_width = strlen(propname);
1336 1365 } else {
1337 1366 entry->pl_width = zprop_width(prop, &entry->pl_fixed,
1338 1367 type);
1339 1368 }
1340 1369
1341 1370 *listp = entry;
1342 1371
1343 1372 return (0);
1344 1373 }
1345 1374
1346 1375 /*
1347 1376 * Given a comma-separated list of properties, construct a property list
1348 1377 * containing both user-defined and native properties. This function will
1349 1378 * return a NULL list if 'all' is specified, which can later be expanded
1350 1379 * by zprop_expand_list().
1351 1380 */
1352 1381 int
1353 1382 zprop_get_list(libzfs_handle_t *hdl, char *props, zprop_list_t **listp,
1354 1383 zfs_type_t type)
1355 1384 {
1356 1385 *listp = NULL;
1357 1386
1358 1387 /*
1359 1388 * If 'all' is specified, return a NULL list.
1360 1389 */
1361 1390 if (strcmp(props, "all") == 0)
1362 1391 return (0);
1363 1392
1364 1393 /*
1365 1394 * If no props were specified, return an error.
1366 1395 */
1367 1396 if (props[0] == '\0') {
1368 1397 zfs_error_aux(hdl, dgettext(TEXT_DOMAIN,
1369 1398 "no properties specified"));
1370 1399 return (zfs_error(hdl, EZFS_BADPROP, dgettext(TEXT_DOMAIN,
1371 1400 "bad property list")));
1372 1401 }
1373 1402
1374 1403 /*
1375 1404 * It would be nice to use getsubopt() here, but the inclusion of column
1376 1405 * aliases makes this more effort than it's worth.
1377 1406 */
1378 1407 while (*props != '\0') {
1379 1408 size_t len;
1380 1409 char *p;
1381 1410 char c;
1382 1411
1383 1412 if ((p = strchr(props, ',')) == NULL) {
1384 1413 len = strlen(props);
1385 1414 p = props + len;
1386 1415 } else {
1387 1416 len = p - props;
1388 1417 }
1389 1418
1390 1419 /*
1391 1420 * Check for empty options.
1392 1421 */
1393 1422 if (len == 0) {
1394 1423 zfs_error_aux(hdl, dgettext(TEXT_DOMAIN,
1395 1424 "empty property name"));
1396 1425 return (zfs_error(hdl, EZFS_BADPROP,
1397 1426 dgettext(TEXT_DOMAIN, "bad property list")));
1398 1427 }
1399 1428
1400 1429 /*
1401 1430 * Check all regular property names.
1402 1431 */
1403 1432 c = props[len];
1404 1433 props[len] = '\0';
1405 1434
1406 1435 if (strcmp(props, "space") == 0) {
1407 1436 static char *spaceprops[] = {
1408 1437 "name", "avail", "used", "usedbysnapshots",
1409 1438 "usedbydataset", "usedbyrefreservation",
1410 1439 "usedbychildren", NULL
1411 1440 };
1412 1441 int i;
1413 1442
1414 1443 for (i = 0; spaceprops[i]; i++) {
1415 1444 if (addlist(hdl, spaceprops[i], listp, type))
1416 1445 return (-1);
1417 1446 listp = &(*listp)->pl_next;
1418 1447 }
1419 1448 } else {
1420 1449 if (addlist(hdl, props, listp, type))
1421 1450 return (-1);
1422 1451 listp = &(*listp)->pl_next;
1423 1452 }
1424 1453
1425 1454 props = p;
1426 1455 if (c == ',')
1427 1456 props++;
1428 1457 }
1429 1458
1430 1459 return (0);
1431 1460 }
1432 1461
1433 1462 void
1434 1463 zprop_free_list(zprop_list_t *pl)
1435 1464 {
1436 1465 zprop_list_t *next;
1437 1466
1438 1467 while (pl != NULL) {
1439 1468 next = pl->pl_next;
1440 1469 free(pl->pl_user_prop);
1441 1470 free(pl);
1442 1471 pl = next;
1443 1472 }
1444 1473 }
1445 1474
1446 1475 typedef struct expand_data {
1447 1476 zprop_list_t **last;
1448 1477 libzfs_handle_t *hdl;
1449 1478 zfs_type_t type;
1450 1479 } expand_data_t;
1451 1480
1452 1481 int
1453 1482 zprop_expand_list_cb(int prop, void *cb)
1454 1483 {
1455 1484 zprop_list_t *entry;
1456 1485 expand_data_t *edp = cb;
1457 1486
1458 1487 if ((entry = zfs_alloc(edp->hdl, sizeof (zprop_list_t))) == NULL)
1459 1488 return (ZPROP_INVAL);
1460 1489
1461 1490 entry->pl_prop = prop;
1462 1491 entry->pl_width = zprop_width(prop, &entry->pl_fixed, edp->type);
1463 1492 entry->pl_all = B_TRUE;
1464 1493
1465 1494 *(edp->last) = entry;
1466 1495 edp->last = &entry->pl_next;
1467 1496
1468 1497 return (ZPROP_CONT);
1469 1498 }
1470 1499
1471 1500 int
1472 1501 zprop_expand_list(libzfs_handle_t *hdl, zprop_list_t **plp, zfs_type_t type)
1473 1502 {
1474 1503 zprop_list_t *entry;
1475 1504 zprop_list_t **last;
1476 1505 expand_data_t exp;
1477 1506
1478 1507 if (*plp == NULL) {
1479 1508 /*
1480 1509 * If this is the very first time we've been called for an 'all'
1481 1510 * specification, expand the list to include all native
1482 1511 * properties.
1483 1512 */
1484 1513 last = plp;
1485 1514
1486 1515 exp.last = last;
1487 1516 exp.hdl = hdl;
1488 1517 exp.type = type;
1489 1518
1490 1519 if (zprop_iter_common(zprop_expand_list_cb, &exp, B_FALSE,
1491 1520 B_FALSE, type) == ZPROP_INVAL)
1492 1521 return (-1);
1493 1522
1494 1523 /*
1495 1524 * Add 'name' to the beginning of the list, which is handled
1496 1525 * specially.
1497 1526 */
1498 1527 if ((entry = zfs_alloc(hdl, sizeof (zprop_list_t))) == NULL)
1499 1528 return (-1);
1500 1529
1501 1530 entry->pl_prop = (type == ZFS_TYPE_POOL) ? ZPOOL_PROP_NAME :
1502 1531 ZFS_PROP_NAME;
1503 1532 entry->pl_width = zprop_width(entry->pl_prop,
1504 1533 &entry->pl_fixed, type);
1505 1534 entry->pl_all = B_TRUE;
1506 1535 entry->pl_next = *plp;
1507 1536 *plp = entry;
1508 1537 }
1509 1538 return (0);
1510 1539 }
1511 1540
1512 1541 int
1513 1542 zprop_iter(zprop_func func, void *cb, boolean_t show_all, boolean_t ordered,
1514 1543 zfs_type_t type)
1515 1544 {
1516 1545 return (zprop_iter_common(func, cb, show_all, ordered, type));
1517 1546 }
1518 1547
1519 1548 /*
1520 1549 * zfs_get_hole_count retrieves the number of holes (blocks which are
1521 1550 * zero-filled) in the specified file using the _FIO_COUNT_FILLED ioctl. It
1522 1551 * also optionally fetches the block size when bs is non-NULL. With hole count
1523 1552 * and block size the full space consumed by the holes of a file can be
1524 1553 * calculated.
1525 1554 *
1526 1555 * On success, zero is returned, the count argument is set to the
1527 1556 * number of holes, and the bs argument is set to the block size (if it is
1528 1557 * not NULL). On error, a non-zero errno is returned and the values in count
1529 1558 * and bs are undefined.
1530 1559 */
1531 1560 int
1532 1561 zfs_get_hole_count(const char *path, uint64_t *count, uint64_t *bs)
1533 1562 {
1534 1563 int fd, err;
1535 1564 struct stat64 ss;
1536 1565 uint64_t fill;
1537 1566
1538 1567 fd = open(path, O_RDONLY | O_LARGEFILE);
1539 1568 if (fd == -1)
1540 1569 return (errno);
1541 1570
1542 1571 if (ioctl(fd, _FIO_COUNT_FILLED, &fill) == -1) {
1543 1572 err = errno;
1544 1573 (void) close(fd);
1545 1574 return (err);
1546 1575 }
1547 1576
1548 1577 if (fstat64(fd, &ss) == -1) {
1549 1578 err = errno;
1550 1579 (void) close(fd);
1551 1580 return (err);
1552 1581 }
1553 1582
1554 1583 *count = (ss.st_size + ss.st_blksize - 1) / ss.st_blksize - fill;
1555 1584 VERIFY3S(*count, >=, 0);
1556 1585 if (bs != NULL) {
1557 1586 *bs = ss.st_blksize;
1558 1587 }
1559 1588
1560 1589 if (close(fd) == -1) {
1561 1590 return (errno);
1562 1591 }
1563 1592 return (0);
1564 1593 }
↓ open down ↓ |
302 lines elided |
↑ open up ↑ |
XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX