1 /* 2 * CDDL HEADER START 3 * 4 * The contents of this file are subject to the terms of the 5 * Common Development and Distribution License (the "License"). 6 * You may not use this file except in compliance with the License. 7 * 8 * You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE 9 * or http://www.opensolaris.org/os/licensing. 10 * See the License for the specific language governing permissions 11 * and limitations under the License. 12 * 13 * When distributing Covered Code, include this CDDL HEADER in each 14 * file and include the License file at usr/src/OPENSOLARIS.LICENSE. 15 * If applicable, add the following below this CDDL HEADER, with the 16 * fields enclosed by brackets "[]" replaced with your own identifying 17 * information: Portions Copyright [yyyy] [name of copyright owner] 18 * 19 * CDDL HEADER END 20 */ 21 /* 22 * Copyright 2006 Sun Microsystems, Inc. All rights reserved. 23 * Use is subject to license terms. 24 */ 25 26 #pragma ident "%Z%%M% %I% %E% SMI" 27 28 #include <sys/types.h> 29 #include <sys/param.h> 30 #include <sys/errno.h> 31 #include <sys/uio.h> 32 #include <sys/buf.h> 33 #include <sys/modctl.h> 34 #include <sys/open.h> 35 #include <sys/file.h> 36 #include <sys/kmem.h> 37 #include <sys/conf.h> 38 #include <sys/cmn_err.h> 39 #include <sys/stat.h> 40 #include <sys/zfs_ioctl.h> 41 #include <sys/zap.h> 42 #include <sys/spa.h> 43 #include <sys/vdev.h> 44 #include <sys/dmu.h> 45 #include <sys/dsl_dir.h> 46 #include <sys/dsl_dataset.h> 47 #include <sys/dsl_prop.h> 48 #include <sys/ddi.h> 49 #include <sys/sunddi.h> 50 #include <sys/sunldi.h> 51 #include <sys/policy.h> 52 #include <sys/zone.h> 53 #include <sys/nvpair.h> 54 #include <sys/pathname.h> 55 #include <sys/mount.h> 56 #include <sys/sdt.h> 57 #include <sys/fs/zfs.h> 58 #include <sys/zfs_ctldir.h> 59 #include <sys/zvol.h> 60 61 #include "zfs_namecheck.h" 62 #include "zfs_prop.h" 63 64 extern struct modlfs zfs_modlfs; 65 66 extern void zfs_init(void); 67 extern void zfs_fini(void); 68 69 ldi_ident_t zfs_li = NULL; 70 dev_info_t *zfs_dip; 71 72 typedef int zfs_ioc_func_t(zfs_cmd_t *); 73 typedef int zfs_secpolicy_func_t(const char *, cred_t *); 74 75 typedef struct zfs_ioc_vec { 76 zfs_ioc_func_t *zvec_func; 77 zfs_secpolicy_func_t *zvec_secpolicy; 78 enum { 79 no_name, 80 pool_name, 81 dataset_name 82 } zvec_namecheck; 83 } zfs_ioc_vec_t; 84 85 /* _NOTE(PRINTFLIKE(4)) - this is printf-like, but lint is too whiney */ 86 void 87 __dprintf(const char *file, const char *func, int line, const char *fmt, ...) 88 { 89 const char *newfile; 90 char buf[256]; 91 va_list adx; 92 93 /* 94 * Get rid of annoying "../common/" prefix to filename. 95 */ 96 newfile = strrchr(file, '/'); 97 if (newfile != NULL) { 98 newfile = newfile + 1; /* Get rid of leading / */ 99 } else { 100 newfile = file; 101 } 102 103 va_start(adx, fmt); 104 (void) vsnprintf(buf, sizeof (buf), fmt, adx); 105 va_end(adx); 106 107 /* 108 * To get this data, use the zfs-dprintf probe as so: 109 * dtrace -q -n 'zfs-dprintf \ 110 * /stringof(arg0) == "dbuf.c"/ \ 111 * {printf("%s: %s", stringof(arg1), stringof(arg3))}' 112 * arg0 = file name 113 * arg1 = function name 114 * arg2 = line number 115 * arg3 = message 116 */ 117 DTRACE_PROBE4(zfs__dprintf, 118 char *, newfile, char *, func, int, line, char *, buf); 119 } 120 121 /* 122 * Policy for top-level read operations (list pools). Requires no privileges, 123 * and can be used in the local zone, as there is no associated dataset. 124 */ 125 /* ARGSUSED */ 126 static int 127 zfs_secpolicy_none(const char *unused1, cred_t *cr) 128 { 129 return (0); 130 } 131 132 /* 133 * Policy for dataset read operations (list children, get statistics). Requires 134 * no privileges, but must be visible in the local zone. 135 */ 136 /* ARGSUSED */ 137 static int 138 zfs_secpolicy_read(const char *dataset, cred_t *cr) 139 { 140 if (INGLOBALZONE(curproc) || 141 zone_dataset_visible(dataset, NULL)) 142 return (0); 143 144 return (ENOENT); 145 } 146 147 static int 148 zfs_dozonecheck(const char *dataset, cred_t *cr) 149 { 150 uint64_t zoned; 151 int writable = 1; 152 153 /* 154 * The dataset must be visible by this zone -- check this first 155 * so they don't see EPERM on something they shouldn't know about. 156 */ 157 if (!INGLOBALZONE(curproc) && 158 !zone_dataset_visible(dataset, &writable)) 159 return (ENOENT); 160 161 if (dsl_prop_get_integer(dataset, "zoned", &zoned, NULL)) 162 return (ENOENT); 163 164 if (INGLOBALZONE(curproc)) { 165 /* 166 * If the fs is zoned, only root can access it from the 167 * global zone. 168 */ 169 if (secpolicy_zfs(cr) && zoned) 170 return (EPERM); 171 } else { 172 /* 173 * If we are in a local zone, the 'zoned' property must be set. 174 */ 175 if (!zoned) 176 return (EPERM); 177 178 /* must be writable by this zone */ 179 if (!writable) 180 return (EPERM); 181 } 182 return (0); 183 } 184 185 /* 186 * Policy for dataset write operations (create children, set properties, etc). 187 * Requires SYS_MOUNT privilege, and must be writable in the local zone. 188 */ 189 int 190 zfs_secpolicy_write(const char *dataset, cred_t *cr) 191 { 192 int error; 193 194 if (error = zfs_dozonecheck(dataset, cr)) 195 return (error); 196 197 return (secpolicy_zfs(cr)); 198 } 199 200 /* 201 * Policy for operations that want to write a dataset's parent: 202 * create, destroy, snapshot, clone, restore. 203 */ 204 static int 205 zfs_secpolicy_parent(const char *dataset, cred_t *cr) 206 { 207 char parentname[MAXNAMELEN]; 208 char *cp; 209 210 /* 211 * Remove the @bla or /bla from the end of the name to get the parent. 212 */ 213 (void) strncpy(parentname, dataset, sizeof (parentname)); 214 cp = strrchr(parentname, '@'); 215 if (cp != NULL) { 216 cp[0] = '\0'; 217 } else { 218 cp = strrchr(parentname, '/'); 219 if (cp == NULL) 220 return (ENOENT); 221 cp[0] = '\0'; 222 223 } 224 225 return (zfs_secpolicy_write(parentname, cr)); 226 } 227 228 /* 229 * Policy for pool operations - create/destroy pools, add vdevs, etc. Requires 230 * SYS_CONFIG privilege, which is not available in a local zone. 231 */ 232 /* ARGSUSED */ 233 static int 234 zfs_secpolicy_config(const char *unused, cred_t *cr) 235 { 236 if (secpolicy_sys_config(cr, B_FALSE) != 0) 237 return (EPERM); 238 239 return (0); 240 } 241 242 /* 243 * Policy for fault injection. Requires all privileges. 244 */ 245 /* ARGSUSED */ 246 static int 247 zfs_secpolicy_inject(const char *unused, cred_t *cr) 248 { 249 return (secpolicy_zinject(cr)); 250 } 251 252 /* 253 * Returns the nvlist as specified by the user in the zfs_cmd_t. 254 */ 255 static int 256 get_nvlist(zfs_cmd_t *zc, nvlist_t **nvp) 257 { 258 char *packed; 259 size_t size; 260 int error; 261 nvlist_t *config = NULL; 262 263 /* 264 * Read in and unpack the user-supplied nvlist. 265 */ 266 if ((size = zc->zc_nvlist_src_size) == 0) 267 return (EINVAL); 268 269 packed = kmem_alloc(size, KM_SLEEP); 270 271 if ((error = xcopyin((void *)(uintptr_t)zc->zc_nvlist_src, packed, 272 size)) != 0) { 273 kmem_free(packed, size); 274 return (error); 275 } 276 277 if ((error = nvlist_unpack(packed, size, &config, 0)) != 0) { 278 kmem_free(packed, size); 279 return (error); 280 } 281 282 kmem_free(packed, size); 283 284 *nvp = config; 285 return (0); 286 } 287 288 static int 289 put_nvlist(zfs_cmd_t *zc, nvlist_t *nvl) 290 { 291 char *packed = NULL; 292 size_t size; 293 int error; 294 295 VERIFY(nvlist_size(nvl, &size, NV_ENCODE_NATIVE) == 0); 296 297 if (size > zc->zc_nvlist_dst_size) { 298 error = ENOMEM; 299 } else { 300 VERIFY(nvlist_pack(nvl, &packed, &size, NV_ENCODE_NATIVE, 301 KM_SLEEP) == 0); 302 error = xcopyout(packed, (void *)(uintptr_t)zc->zc_nvlist_dst, 303 size); 304 kmem_free(packed, size); 305 } 306 307 zc->zc_nvlist_dst_size = size; 308 return (error); 309 } 310 311 static int 312 zfs_ioc_pool_create(zfs_cmd_t *zc) 313 { 314 int error; 315 nvlist_t *config; 316 317 if ((error = get_nvlist(zc, &config)) != 0) 318 return (error); 319 320 error = spa_create(zc->zc_name, config, zc->zc_value[0] == '\0' ? 321 NULL : zc->zc_value); 322 323 nvlist_free(config); 324 325 return (error); 326 } 327 328 static int 329 zfs_ioc_pool_destroy(zfs_cmd_t *zc) 330 { 331 return (spa_destroy(zc->zc_name)); 332 } 333 334 static int 335 zfs_ioc_pool_import(zfs_cmd_t *zc) 336 { 337 int error; 338 nvlist_t *config; 339 uint64_t guid; 340 341 if ((error = get_nvlist(zc, &config)) != 0) 342 return (error); 343 344 if (nvlist_lookup_uint64(config, ZPOOL_CONFIG_POOL_GUID, &guid) != 0 || 345 guid != zc->zc_guid) 346 error = EINVAL; 347 else 348 error = spa_import(zc->zc_name, config, 349 zc->zc_value[0] == '\0' ? NULL : zc->zc_value); 350 351 nvlist_free(config); 352 353 return (error); 354 } 355 356 static int 357 zfs_ioc_pool_export(zfs_cmd_t *zc) 358 { 359 return (spa_export(zc->zc_name, NULL)); 360 } 361 362 static int 363 zfs_ioc_pool_configs(zfs_cmd_t *zc) 364 { 365 nvlist_t *configs; 366 int error; 367 368 if ((configs = spa_all_configs(&zc->zc_cookie)) == NULL) 369 return (EEXIST); 370 371 error = put_nvlist(zc, configs); 372 373 nvlist_free(configs); 374 375 return (error); 376 } 377 378 static int 379 zfs_ioc_pool_stats(zfs_cmd_t *zc) 380 { 381 nvlist_t *config; 382 int error; 383 int ret = 0; 384 385 error = spa_get_stats(zc->zc_name, &config, zc->zc_value, 386 sizeof (zc->zc_value)); 387 388 if (config != NULL) { 389 ret = put_nvlist(zc, config); 390 nvlist_free(config); 391 392 /* 393 * The config may be present even if 'error' is non-zero. 394 * In this case we return success, and preserve the real errno 395 * in 'zc_cookie'. 396 */ 397 zc->zc_cookie = error; 398 } else { 399 ret = error; 400 } 401 402 return (ret); 403 } 404 405 /* 406 * Try to import the given pool, returning pool stats as appropriate so that 407 * user land knows which devices are available and overall pool health. 408 */ 409 static int 410 zfs_ioc_pool_tryimport(zfs_cmd_t *zc) 411 { 412 nvlist_t *tryconfig, *config; 413 int error; 414 415 if ((error = get_nvlist(zc, &tryconfig)) != 0) 416 return (error); 417 418 config = spa_tryimport(tryconfig); 419 420 nvlist_free(tryconfig); 421 422 if (config == NULL) 423 return (EINVAL); 424 425 error = put_nvlist(zc, config); 426 nvlist_free(config); 427 428 return (error); 429 } 430 431 static int 432 zfs_ioc_pool_scrub(zfs_cmd_t *zc) 433 { 434 spa_t *spa; 435 int error; 436 437 if ((error = spa_open(zc->zc_name, &spa, FTAG)) != 0) 438 return (error); 439 440 error = spa_scrub(spa, zc->zc_cookie, B_FALSE); 441 442 spa_close(spa, FTAG); 443 444 return (error); 445 } 446 447 static int 448 zfs_ioc_pool_freeze(zfs_cmd_t *zc) 449 { 450 spa_t *spa; 451 int error; 452 453 error = spa_open(zc->zc_name, &spa, FTAG); 454 if (error == 0) { 455 spa_freeze(spa); 456 spa_close(spa, FTAG); 457 } 458 return (error); 459 } 460 461 static int 462 zfs_ioc_pool_upgrade(zfs_cmd_t *zc) 463 { 464 spa_t *spa; 465 int error; 466 467 if ((error = spa_open(zc->zc_name, &spa, FTAG)) != 0) 468 return (error); 469 470 spa_upgrade(spa); 471 472 spa_close(spa, FTAG); 473 474 return (error); 475 } 476 477 static int 478 zfs_ioc_pool_get_history(zfs_cmd_t *zc) 479 { 480 spa_t *spa; 481 char *hist_buf; 482 uint64_t size; 483 int error; 484 485 if ((size = zc->zc_history_len) == 0) 486 return (EINVAL); 487 488 if ((error = spa_open(zc->zc_name, &spa, FTAG)) != 0) 489 return (error); 490 491 hist_buf = kmem_alloc(size, KM_SLEEP); 492 if ((error = spa_history_get(spa, &zc->zc_history_offset, 493 &zc->zc_history_len, hist_buf)) == 0) { 494 error = xcopyout(hist_buf, (char *)(uintptr_t)zc->zc_history, 495 zc->zc_history_len); 496 } 497 498 spa_close(spa, FTAG); 499 kmem_free(hist_buf, size); 500 return (error); 501 } 502 503 static int 504 zfs_ioc_pool_log_history(zfs_cmd_t *zc) 505 { 506 spa_t *spa; 507 char *history_str = NULL; 508 size_t size; 509 int error; 510 511 size = zc->zc_history_len; 512 if (size == 0 || size > HIS_MAX_RECORD_LEN) 513 return (EINVAL); 514 515 if ((error = spa_open(zc->zc_name, &spa, FTAG)) != 0) 516 return (error); 517 518 /* add one for the NULL delimiter */ 519 size++; 520 history_str = kmem_alloc(size, KM_SLEEP); 521 if ((error = xcopyin((void *)(uintptr_t)zc->zc_history, history_str, 522 size)) != 0) { 523 spa_close(spa, FTAG); 524 kmem_free(history_str, size); 525 return (error); 526 } 527 history_str[size - 1] = '\0'; 528 529 error = spa_history_log(spa, history_str, zc->zc_history_offset); 530 531 spa_close(spa, FTAG); 532 kmem_free(history_str, size); 533 534 return (error); 535 } 536 537 static int 538 zfs_ioc_vdev_add(zfs_cmd_t *zc) 539 { 540 spa_t *spa; 541 int error; 542 nvlist_t *config; 543 544 error = spa_open(zc->zc_name, &spa, FTAG); 545 if (error != 0) 546 return (error); 547 548 if ((error = get_nvlist(zc, &config)) == 0) { 549 error = spa_vdev_add(spa, config); 550 nvlist_free(config); 551 } 552 553 spa_close(spa, FTAG); 554 return (error); 555 } 556 557 static int 558 zfs_ioc_vdev_remove(zfs_cmd_t *zc) 559 { 560 spa_t *spa; 561 int error; 562 563 error = spa_open(zc->zc_name, &spa, FTAG); 564 if (error != 0) 565 return (error); 566 error = spa_vdev_remove(spa, zc->zc_guid, B_FALSE); 567 spa_close(spa, FTAG); 568 return (error); 569 } 570 571 static int 572 zfs_ioc_vdev_online(zfs_cmd_t *zc) 573 { 574 spa_t *spa; 575 int error; 576 577 if ((error = spa_open(zc->zc_name, &spa, FTAG)) != 0) 578 return (error); 579 error = vdev_online(spa, zc->zc_guid); 580 spa_close(spa, FTAG); 581 return (error); 582 } 583 584 static int 585 zfs_ioc_vdev_offline(zfs_cmd_t *zc) 586 { 587 spa_t *spa; 588 int istmp = zc->zc_cookie; 589 int error; 590 591 if ((error = spa_open(zc->zc_name, &spa, FTAG)) != 0) 592 return (error); 593 error = vdev_offline(spa, zc->zc_guid, istmp); 594 spa_close(spa, FTAG); 595 return (error); 596 } 597 598 static int 599 zfs_ioc_vdev_attach(zfs_cmd_t *zc) 600 { 601 spa_t *spa; 602 int replacing = zc->zc_cookie; 603 nvlist_t *config; 604 int error; 605 606 if ((error = spa_open(zc->zc_name, &spa, FTAG)) != 0) 607 return (error); 608 609 if ((error = get_nvlist(zc, &config)) == 0) { 610 error = spa_vdev_attach(spa, zc->zc_guid, config, replacing); 611 nvlist_free(config); 612 } 613 614 spa_close(spa, FTAG); 615 return (error); 616 } 617 618 static int 619 zfs_ioc_vdev_detach(zfs_cmd_t *zc) 620 { 621 spa_t *spa; 622 int error; 623 624 if ((error = spa_open(zc->zc_name, &spa, FTAG)) != 0) 625 return (error); 626 627 error = spa_vdev_detach(spa, zc->zc_guid, B_FALSE); 628 629 spa_close(spa, FTAG); 630 return (error); 631 } 632 633 static int 634 zfs_ioc_vdev_setpath(zfs_cmd_t *zc) 635 { 636 spa_t *spa; 637 char *path = zc->zc_value; 638 uint64_t guid = zc->zc_guid; 639 int error; 640 641 error = spa_open(zc->zc_name, &spa, FTAG); 642 if (error != 0) 643 return (error); 644 645 error = spa_vdev_setpath(spa, guid, path); 646 spa_close(spa, FTAG); 647 return (error); 648 } 649 650 static int 651 zfs_ioc_objset_stats(zfs_cmd_t *zc) 652 { 653 objset_t *os = NULL; 654 int error; 655 nvlist_t *nv; 656 657 retry: 658 error = dmu_objset_open(zc->zc_name, DMU_OST_ANY, 659 DS_MODE_STANDARD | DS_MODE_READONLY, &os); 660 if (error != 0) { 661 /* 662 * This is ugly: dmu_objset_open() can return EBUSY if 663 * the objset is held exclusively. Fortunately this hold is 664 * only for a short while, so we retry here. 665 * This avoids user code having to handle EBUSY, 666 * for example for a "zfs list". 667 */ 668 if (error == EBUSY) { 669 delay(1); 670 goto retry; 671 } 672 return (error); 673 } 674 675 dmu_objset_fast_stat(os, &zc->zc_objset_stats); 676 677 if (zc->zc_nvlist_dst != 0 && 678 (error = dsl_prop_get_all(os, &nv)) == 0) { 679 dmu_objset_stats(os, nv); 680 /* 681 * NB: zvol_get_stats() will read the objset contents, 682 * which we aren't supposed to do with a 683 * DS_MODE_STANDARD open, because it could be 684 * inconsistent. So this is a bit of a workaround... 685 */ 686 if (!zc->zc_objset_stats.dds_inconsistent && 687 dmu_objset_type(os) == DMU_OST_ZVOL) 688 VERIFY(zvol_get_stats(os, nv) == 0); 689 error = put_nvlist(zc, nv); 690 nvlist_free(nv); 691 } 692 693 spa_altroot(dmu_objset_spa(os), zc->zc_value, sizeof (zc->zc_value)); 694 695 dmu_objset_close(os); 696 return (error); 697 } 698 699 static int 700 zfs_ioc_dataset_list_next(zfs_cmd_t *zc) 701 { 702 objset_t *os; 703 int error; 704 char *p; 705 706 retry: 707 error = dmu_objset_open(zc->zc_name, DMU_OST_ANY, 708 DS_MODE_STANDARD | DS_MODE_READONLY, &os); 709 if (error != 0) { 710 /* 711 * This is ugly: dmu_objset_open() can return EBUSY if 712 * the objset is held exclusively. Fortunately this hold is 713 * only for a short while, so we retry here. 714 * This avoids user code having to handle EBUSY, 715 * for example for a "zfs list". 716 */ 717 if (error == EBUSY) { 718 delay(1); 719 goto retry; 720 } 721 if (error == ENOENT) 722 error = ESRCH; 723 return (error); 724 } 725 726 p = strrchr(zc->zc_name, '/'); 727 if (p == NULL || p[1] != '\0') 728 (void) strlcat(zc->zc_name, "/", sizeof (zc->zc_name)); 729 p = zc->zc_name + strlen(zc->zc_name); 730 731 do { 732 error = dmu_dir_list_next(os, 733 sizeof (zc->zc_name) - (p - zc->zc_name), p, 734 NULL, &zc->zc_cookie); 735 if (error == ENOENT) 736 error = ESRCH; 737 } while (error == 0 && !INGLOBALZONE(curproc) && 738 !zone_dataset_visible(zc->zc_name, NULL)); 739 740 /* 741 * If it's a hidden dataset (ie. with a '$' in its name), don't 742 * try to get stats for it. Userland will skip over it. 743 */ 744 if (error == 0 && strchr(zc->zc_name, '$') == NULL) 745 error = zfs_ioc_objset_stats(zc); /* fill in the stats */ 746 747 dmu_objset_close(os); 748 return (error); 749 } 750 751 static int 752 zfs_ioc_snapshot_list_next(zfs_cmd_t *zc) 753 { 754 objset_t *os; 755 int error; 756 757 retry: 758 error = dmu_objset_open(zc->zc_name, DMU_OST_ANY, 759 DS_MODE_STANDARD | DS_MODE_READONLY, &os); 760 if (error != 0) { 761 /* 762 * This is ugly: dmu_objset_open() can return EBUSY if 763 * the objset is held exclusively. Fortunately this hold is 764 * only for a short while, so we retry here. 765 * This avoids user code having to handle EBUSY, 766 * for example for a "zfs list". 767 */ 768 if (error == EBUSY) { 769 delay(1); 770 goto retry; 771 } 772 if (error == ENOENT) 773 error = ESRCH; 774 return (error); 775 } 776 777 /* 778 * A dataset name of maximum length cannot have any snapshots, 779 * so exit immediately. 780 */ 781 if (strlcat(zc->zc_name, "@", sizeof (zc->zc_name)) >= MAXNAMELEN) { 782 dmu_objset_close(os); 783 return (ESRCH); 784 } 785 786 error = dmu_snapshot_list_next(os, 787 sizeof (zc->zc_name) - strlen(zc->zc_name), 788 zc->zc_name + strlen(zc->zc_name), NULL, &zc->zc_cookie); 789 if (error == ENOENT) 790 error = ESRCH; 791 792 if (error == 0) 793 error = zfs_ioc_objset_stats(zc); /* fill in the stats */ 794 795 dmu_objset_close(os); 796 return (error); 797 } 798 799 static int 800 zfs_set_prop_nvlist(const char *name, dev_t dev, cred_t *cr, nvlist_t *nvl) 801 { 802 nvpair_t *elem; 803 int error; 804 const char *propname; 805 zfs_prop_t prop; 806 uint64_t intval; 807 char *strval; 808 809 elem = NULL; 810 while ((elem = nvlist_next_nvpair(nvl, elem)) != NULL) { 811 propname = nvpair_name(elem); 812 813 if ((prop = zfs_name_to_prop(propname)) == 814 ZFS_PROP_INVAL) { 815 /* 816 * If this is a user-defined property, it must be a 817 * string, and there is no further validation to do. 818 */ 819 if (!zfs_prop_user(propname) || 820 nvpair_type(elem) != DATA_TYPE_STRING) 821 return (EINVAL); 822 823 VERIFY(nvpair_value_string(elem, &strval) == 0); 824 error = dsl_prop_set(name, propname, 1, 825 strlen(strval) + 1, strval); 826 if (error == 0) 827 continue; 828 else 829 break; 830 } 831 832 /* 833 * Check permissions for special properties. 834 */ 835 switch (prop) { 836 case ZFS_PROP_ZONED: 837 /* 838 * Disallow setting of 'zoned' from within a local zone. 839 */ 840 if (!INGLOBALZONE(curproc)) 841 return (EPERM); 842 break; 843 844 case ZFS_PROP_QUOTA: 845 if (error = zfs_dozonecheck(name, cr)) 846 return (error); 847 848 if (!INGLOBALZONE(curproc)) { 849 uint64_t zoned; 850 char setpoint[MAXNAMELEN]; 851 int dslen; 852 /* 853 * Unprivileged users are allowed to modify the 854 * quota on things *under* (ie. contained by) 855 * the thing they own. 856 */ 857 if (dsl_prop_get_integer(name, "zoned", &zoned, 858 setpoint)) 859 return (EPERM); 860 if (!zoned) /* this shouldn't happen */ 861 return (EPERM); 862 dslen = strlen(name); 863 if (dslen <= strlen(setpoint)) 864 return (EPERM); 865 } 866 } 867 868 switch (prop) { 869 case ZFS_PROP_QUOTA: 870 if ((error = nvpair_value_uint64(elem, &intval)) != 0 || 871 (error = dsl_dir_set_quota(name, 872 intval)) != 0) 873 return (error); 874 break; 875 876 case ZFS_PROP_RESERVATION: 877 if ((error = nvpair_value_uint64(elem, &intval)) != 0 || 878 (error = dsl_dir_set_reservation(name, 879 intval)) != 0) 880 return (error); 881 break; 882 883 case ZFS_PROP_VOLSIZE: 884 if ((error = nvpair_value_uint64(elem, &intval)) != 0 || 885 (error = zvol_set_volsize(name, dev, 886 intval)) != 0) 887 return (error); 888 break; 889 890 case ZFS_PROP_VOLBLOCKSIZE: 891 if ((error = nvpair_value_uint64(elem, &intval)) != 0 || 892 (error = zvol_set_volblocksize(name, 893 intval)) != 0) 894 return (error); 895 break; 896 897 default: 898 if (nvpair_type(elem) == DATA_TYPE_STRING) { 899 if (zfs_prop_get_type(prop) != 900 prop_type_string) 901 return (EINVAL); 902 VERIFY(nvpair_value_string(elem, &strval) == 0); 903 if ((error = dsl_prop_set(name, 904 nvpair_name(elem), 1, strlen(strval) + 1, 905 strval)) != 0) 906 return (error); 907 } else if (nvpair_type(elem) == DATA_TYPE_UINT64) { 908 const char *unused; 909 910 VERIFY(nvpair_value_uint64(elem, &intval) == 0); 911 912 switch (zfs_prop_get_type(prop)) { 913 case prop_type_number: 914 break; 915 case prop_type_boolean: 916 if (intval > 1) 917 return (EINVAL); 918 break; 919 case prop_type_string: 920 return (EINVAL); 921 case prop_type_index: 922 if (zfs_prop_index_to_string(prop, 923 intval, &unused) != 0) 924 return (EINVAL); 925 break; 926 default: 927 cmn_err(CE_PANIC, "unknown property " 928 "type"); 929 break; 930 } 931 932 if ((error = dsl_prop_set(name, propname, 933 8, 1, &intval)) != 0) 934 return (error); 935 } else { 936 return (EINVAL); 937 } 938 break; 939 } 940 } 941 942 return (0); 943 } 944 945 static int 946 zfs_ioc_set_prop(zfs_cmd_t *zc) 947 { 948 nvlist_t *nvl; 949 int error; 950 zfs_prop_t prop; 951 952 /* 953 * If zc_value is set, then this is an attempt to inherit a value. 954 * Otherwise, zc_nvlist refers to a list of properties to set. 955 */ 956 if (zc->zc_value[0] != '\0') { 957 if (!zfs_prop_user(zc->zc_value) && 958 ((prop = zfs_name_to_prop(zc->zc_value)) == 959 ZFS_PROP_INVAL || 960 !zfs_prop_inheritable(prop))) 961 return (EINVAL); 962 963 return (dsl_prop_set(zc->zc_name, zc->zc_value, 0, 0, NULL)); 964 } 965 966 if ((error = get_nvlist(zc, &nvl)) != 0) 967 return (error); 968 969 error = zfs_set_prop_nvlist(zc->zc_name, zc->zc_dev, 970 (cred_t *)(uintptr_t)zc->zc_cred, nvl); 971 nvlist_free(nvl); 972 return (error); 973 } 974 975 static int 976 zfs_ioc_create_minor(zfs_cmd_t *zc) 977 { 978 return (zvol_create_minor(zc->zc_name, zc->zc_dev)); 979 } 980 981 static int 982 zfs_ioc_remove_minor(zfs_cmd_t *zc) 983 { 984 return (zvol_remove_minor(zc->zc_name)); 985 } 986 987 /* 988 * Search the vfs list for a specified resource. Returns a pointer to it 989 * or NULL if no suitable entry is found. The caller of this routine 990 * is responsible for releasing the returned vfs pointer. 991 */ 992 static vfs_t * 993 zfs_get_vfs(const char *resource) 994 { 995 struct vfs *vfsp; 996 struct vfs *vfs_found = NULL; 997 998 vfs_list_read_lock(); 999 vfsp = rootvfs; 1000 do { 1001 if (strcmp(refstr_value(vfsp->vfs_resource), resource) == 0) { 1002 VFS_HOLD(vfsp); 1003 vfs_found = vfsp; 1004 break; 1005 } 1006 vfsp = vfsp->vfs_next; 1007 } while (vfsp != rootvfs); 1008 vfs_list_unlock(); 1009 return (vfs_found); 1010 } 1011 1012 static void 1013 zfs_create_cb(objset_t *os, void *arg, dmu_tx_t *tx) 1014 { 1015 zfs_create_data_t *zc = arg; 1016 zfs_create_fs(os, (cred_t *)(uintptr_t)zc->zc_cred, tx); 1017 } 1018 1019 static int 1020 zfs_ioc_create(zfs_cmd_t *zc) 1021 { 1022 objset_t *clone; 1023 int error = 0; 1024 zfs_create_data_t cbdata = { 0 }; 1025 void (*cbfunc)(objset_t *os, void *arg, dmu_tx_t *tx); 1026 dmu_objset_type_t type = zc->zc_objset_type; 1027 1028 switch (type) { 1029 1030 case DMU_OST_ZFS: 1031 cbfunc = zfs_create_cb; 1032 break; 1033 1034 case DMU_OST_ZVOL: 1035 cbfunc = zvol_create_cb; 1036 break; 1037 1038 default: 1039 cbfunc = NULL; 1040 } 1041 if (strchr(zc->zc_name, '@')) 1042 return (EINVAL); 1043 1044 if (zc->zc_nvlist_src != NULL && 1045 (error = get_nvlist(zc, &cbdata.zc_props)) != 0) 1046 return (error); 1047 1048 cbdata.zc_cred = (cred_t *)(uintptr_t)zc->zc_cred; 1049 cbdata.zc_dev = (dev_t)zc->zc_dev; 1050 1051 if (zc->zc_value[0] != '\0') { 1052 /* 1053 * We're creating a clone of an existing snapshot. 1054 */ 1055 zc->zc_value[sizeof (zc->zc_value) - 1] = '\0'; 1056 if (dataset_namecheck(zc->zc_value, NULL, NULL) != 0) { 1057 nvlist_free(cbdata.zc_props); 1058 return (EINVAL); 1059 } 1060 1061 error = dmu_objset_open(zc->zc_value, type, 1062 DS_MODE_STANDARD | DS_MODE_READONLY, &clone); 1063 if (error) { 1064 nvlist_free(cbdata.zc_props); 1065 return (error); 1066 } 1067 error = dmu_objset_create(zc->zc_name, type, clone, NULL, NULL); 1068 dmu_objset_close(clone); 1069 } else { 1070 if (cbfunc == NULL) { 1071 nvlist_free(cbdata.zc_props); 1072 return (EINVAL); 1073 } 1074 1075 if (type == DMU_OST_ZVOL) { 1076 uint64_t volsize, volblocksize; 1077 1078 if (cbdata.zc_props == NULL || 1079 nvlist_lookup_uint64(cbdata.zc_props, 1080 zfs_prop_to_name(ZFS_PROP_VOLSIZE), 1081 &volsize) != 0) { 1082 nvlist_free(cbdata.zc_props); 1083 return (EINVAL); 1084 } 1085 1086 if ((error = nvlist_lookup_uint64(cbdata.zc_props, 1087 zfs_prop_to_name(ZFS_PROP_VOLBLOCKSIZE), 1088 &volblocksize)) != 0 && error != ENOENT) { 1089 nvlist_free(cbdata.zc_props); 1090 return (EINVAL); 1091 } 1092 1093 if (error != 0) 1094 volblocksize = zfs_prop_default_numeric( 1095 ZFS_PROP_VOLBLOCKSIZE); 1096 1097 if ((error = zvol_check_volblocksize( 1098 volblocksize)) != 0 || 1099 (error = zvol_check_volsize(volsize, 1100 volblocksize)) != 0) { 1101 nvlist_free(cbdata.zc_props); 1102 return (error); 1103 } 1104 } 1105 1106 error = dmu_objset_create(zc->zc_name, type, NULL, cbfunc, 1107 &cbdata); 1108 } 1109 1110 /* 1111 * It would be nice to do this atomically. 1112 */ 1113 if (error == 0) { 1114 if ((error = zfs_set_prop_nvlist(zc->zc_name, 1115 zc->zc_dev, (cred_t *)(uintptr_t)zc->zc_cred, 1116 cbdata.zc_props)) != 0) 1117 (void) dmu_objset_destroy(zc->zc_name); 1118 } 1119 1120 nvlist_free(cbdata.zc_props); 1121 return (error); 1122 } 1123 1124 static int 1125 zfs_ioc_snapshot(zfs_cmd_t *zc) 1126 { 1127 if (snapshot_namecheck(zc->zc_value, NULL, NULL) != 0) 1128 return (EINVAL); 1129 return (dmu_objset_snapshot(zc->zc_name, 1130 zc->zc_value, zc->zc_cookie)); 1131 } 1132 1133 static int 1134 zfs_unmount_snap(char *name, void *arg) 1135 { 1136 char *snapname = arg; 1137 char *cp; 1138 vfs_t *vfsp = NULL; 1139 1140 /* 1141 * Snapshots (which are under .zfs control) must be unmounted 1142 * before they can be destroyed. 1143 */ 1144 1145 if (snapname) { 1146 (void) strcat(name, "@"); 1147 (void) strcat(name, snapname); 1148 vfsp = zfs_get_vfs(name); 1149 cp = strchr(name, '@'); 1150 *cp = '\0'; 1151 } else if (strchr(name, '@')) { 1152 vfsp = zfs_get_vfs(name); 1153 } 1154 1155 if (vfsp) { 1156 /* 1157 * Always force the unmount for snapshots. 1158 */ 1159 int flag = MS_FORCE; 1160 int err; 1161 1162 if ((err = vn_vfswlock(vfsp->vfs_vnodecovered)) != 0) { 1163 VFS_RELE(vfsp); 1164 return (err); 1165 } 1166 VFS_RELE(vfsp); 1167 if ((err = dounmount(vfsp, flag, kcred)) != 0) 1168 return (err); 1169 } 1170 return (0); 1171 } 1172 1173 static int 1174 zfs_ioc_destroy_snaps(zfs_cmd_t *zc) 1175 { 1176 int err; 1177 1178 if (snapshot_namecheck(zc->zc_value, NULL, NULL) != 0) 1179 return (EINVAL); 1180 err = dmu_objset_find(zc->zc_name, 1181 zfs_unmount_snap, zc->zc_value, DS_FIND_CHILDREN); 1182 if (err) 1183 return (err); 1184 return (dmu_snapshots_destroy(zc->zc_name, zc->zc_value)); 1185 } 1186 1187 static int 1188 zfs_ioc_destroy(zfs_cmd_t *zc) 1189 { 1190 if (strchr(zc->zc_name, '@') && zc->zc_objset_type == DMU_OST_ZFS) { 1191 int err = zfs_unmount_snap(zc->zc_name, NULL); 1192 if (err) 1193 return (err); 1194 } 1195 1196 return (dmu_objset_destroy(zc->zc_name)); 1197 } 1198 1199 static int 1200 zfs_ioc_rollback(zfs_cmd_t *zc) 1201 { 1202 return (dmu_objset_rollback(zc->zc_name)); 1203 } 1204 1205 static int 1206 zfs_ioc_rename(zfs_cmd_t *zc) 1207 { 1208 zc->zc_value[sizeof (zc->zc_value) - 1] = '\0'; 1209 if (dataset_namecheck(zc->zc_value, NULL, NULL) != 0) 1210 return (EINVAL); 1211 1212 if (strchr(zc->zc_name, '@') != NULL && 1213 zc->zc_objset_type == DMU_OST_ZFS) { 1214 int err = zfs_unmount_snap(zc->zc_name, NULL); 1215 if (err) 1216 return (err); 1217 } 1218 1219 return (dmu_objset_rename(zc->zc_name, zc->zc_value)); 1220 } 1221 1222 static int 1223 zfs_ioc_recvbackup(zfs_cmd_t *zc) 1224 { 1225 file_t *fp; 1226 int error, fd; 1227 offset_t new_off; 1228 1229 if (dataset_namecheck(zc->zc_value, NULL, NULL) != 0 || 1230 strchr(zc->zc_value, '@') == NULL) 1231 return (EINVAL); 1232 1233 fd = zc->zc_cookie; 1234 fp = getf(fd); 1235 if (fp == NULL) 1236 return (EBADF); 1237 error = dmu_recvbackup(zc->zc_value, &zc->zc_begin_record, 1238 &zc->zc_cookie, (boolean_t)zc->zc_guid, fp->f_vnode, 1239 fp->f_offset); 1240 1241 new_off = fp->f_offset + zc->zc_cookie; 1242 if (VOP_SEEK(fp->f_vnode, fp->f_offset, &new_off) == 0) 1243 fp->f_offset = new_off; 1244 1245 releasef(fd); 1246 return (error); 1247 } 1248 1249 static int 1250 zfs_ioc_sendbackup(zfs_cmd_t *zc) 1251 { 1252 objset_t *fromsnap = NULL; 1253 objset_t *tosnap; 1254 file_t *fp; 1255 int error; 1256 1257 error = dmu_objset_open(zc->zc_name, DMU_OST_ANY, 1258 DS_MODE_STANDARD | DS_MODE_READONLY, &tosnap); 1259 if (error) 1260 return (error); 1261 1262 if (zc->zc_value[0] != '\0') { 1263 char buf[MAXPATHLEN]; 1264 char *cp; 1265 1266 (void) strncpy(buf, zc->zc_name, sizeof (buf)); 1267 cp = strchr(buf, '@'); 1268 if (cp) 1269 *(cp+1) = 0; 1270 (void) strncat(buf, zc->zc_value, sizeof (buf)); 1271 error = dmu_objset_open(buf, DMU_OST_ANY, 1272 DS_MODE_STANDARD | DS_MODE_READONLY, &fromsnap); 1273 if (error) { 1274 dmu_objset_close(tosnap); 1275 return (error); 1276 } 1277 } 1278 1279 fp = getf(zc->zc_cookie); 1280 if (fp == NULL) { 1281 dmu_objset_close(tosnap); 1282 if (fromsnap) 1283 dmu_objset_close(fromsnap); 1284 return (EBADF); 1285 } 1286 1287 error = dmu_sendbackup(tosnap, fromsnap, fp->f_vnode); 1288 1289 releasef(zc->zc_cookie); 1290 if (fromsnap) 1291 dmu_objset_close(fromsnap); 1292 dmu_objset_close(tosnap); 1293 return (error); 1294 } 1295 1296 static int 1297 zfs_ioc_inject_fault(zfs_cmd_t *zc) 1298 { 1299 int id, error; 1300 1301 error = zio_inject_fault(zc->zc_name, (int)zc->zc_guid, &id, 1302 &zc->zc_inject_record); 1303 1304 if (error == 0) 1305 zc->zc_guid = (uint64_t)id; 1306 1307 return (error); 1308 } 1309 1310 static int 1311 zfs_ioc_clear_fault(zfs_cmd_t *zc) 1312 { 1313 return (zio_clear_fault((int)zc->zc_guid)); 1314 } 1315 1316 static int 1317 zfs_ioc_inject_list_next(zfs_cmd_t *zc) 1318 { 1319 int id = (int)zc->zc_guid; 1320 int error; 1321 1322 error = zio_inject_list_next(&id, zc->zc_name, sizeof (zc->zc_name), 1323 &zc->zc_inject_record); 1324 1325 zc->zc_guid = id; 1326 1327 return (error); 1328 } 1329 1330 static int 1331 zfs_ioc_error_log(zfs_cmd_t *zc) 1332 { 1333 spa_t *spa; 1334 int error; 1335 size_t count = (size_t)zc->zc_nvlist_dst_size; 1336 1337 if ((error = spa_open(zc->zc_name, &spa, FTAG)) != 0) 1338 return (error); 1339 1340 error = spa_get_errlog(spa, (void *)(uintptr_t)zc->zc_nvlist_dst, 1341 &count); 1342 if (error == 0) 1343 zc->zc_nvlist_dst_size = count; 1344 else 1345 zc->zc_nvlist_dst_size = spa_get_errlog_size(spa); 1346 1347 spa_close(spa, FTAG); 1348 1349 return (error); 1350 } 1351 1352 static int 1353 zfs_ioc_clear(zfs_cmd_t *zc) 1354 { 1355 spa_t *spa; 1356 vdev_t *vd; 1357 int error; 1358 1359 if ((error = spa_open(zc->zc_name, &spa, FTAG)) != 0) 1360 return (error); 1361 1362 spa_config_enter(spa, RW_WRITER, FTAG); 1363 1364 if (zc->zc_guid == 0) { 1365 vd = NULL; 1366 } else if ((vd = spa_lookup_by_guid(spa, zc->zc_guid)) == NULL) { 1367 spa_config_exit(spa, FTAG); 1368 spa_close(spa, FTAG); 1369 return (ENODEV); 1370 } 1371 1372 vdev_clear(spa, vd); 1373 1374 spa_config_exit(spa, FTAG); 1375 1376 spa_close(spa, FTAG); 1377 1378 return (0); 1379 } 1380 1381 static int 1382 zfs_ioc_bookmark_name(zfs_cmd_t *zc) 1383 { 1384 spa_t *spa; 1385 int error; 1386 nvlist_t *nvl; 1387 1388 if ((error = spa_open(zc->zc_name, &spa, FTAG)) != 0) 1389 return (error); 1390 1391 VERIFY(nvlist_alloc(&nvl, NV_UNIQUE_NAME, KM_SLEEP) == 0); 1392 1393 error = spa_bookmark_name(spa, &zc->zc_bookmark, nvl); 1394 if (error == 0) 1395 error = put_nvlist(zc, nvl); 1396 nvlist_free(nvl); 1397 1398 spa_close(spa, FTAG); 1399 1400 return (error); 1401 } 1402 1403 static int 1404 zfs_ioc_promote(zfs_cmd_t *zc) 1405 { 1406 char *cp; 1407 1408 /* 1409 * We don't need to unmount *all* the origin fs's snapshots, but 1410 * it's easier. 1411 */ 1412 cp = strchr(zc->zc_value, '@'); 1413 if (cp) 1414 *cp = '\0'; 1415 (void) dmu_objset_find(zc->zc_value, 1416 zfs_unmount_snap, NULL, DS_FIND_SNAPSHOTS); 1417 return (dsl_dataset_promote(zc->zc_name)); 1418 } 1419 1420 static zfs_ioc_vec_t zfs_ioc_vec[] = { 1421 { zfs_ioc_pool_create, zfs_secpolicy_config, pool_name }, 1422 { zfs_ioc_pool_destroy, zfs_secpolicy_config, pool_name }, 1423 { zfs_ioc_pool_import, zfs_secpolicy_config, pool_name }, 1424 { zfs_ioc_pool_export, zfs_secpolicy_config, pool_name }, 1425 { zfs_ioc_pool_configs, zfs_secpolicy_none, no_name }, 1426 { zfs_ioc_pool_stats, zfs_secpolicy_read, pool_name }, 1427 { zfs_ioc_pool_tryimport, zfs_secpolicy_config, no_name }, 1428 { zfs_ioc_pool_scrub, zfs_secpolicy_config, pool_name }, 1429 { zfs_ioc_pool_freeze, zfs_secpolicy_config, no_name }, 1430 { zfs_ioc_pool_upgrade, zfs_secpolicy_config, pool_name }, 1431 { zfs_ioc_pool_get_history, zfs_secpolicy_config, pool_name }, 1432 { zfs_ioc_pool_log_history, zfs_secpolicy_config, pool_name }, 1433 { zfs_ioc_vdev_add, zfs_secpolicy_config, pool_name }, 1434 { zfs_ioc_vdev_remove, zfs_secpolicy_config, pool_name }, 1435 { zfs_ioc_vdev_online, zfs_secpolicy_config, pool_name }, 1436 { zfs_ioc_vdev_offline, zfs_secpolicy_config, pool_name }, 1437 { zfs_ioc_vdev_attach, zfs_secpolicy_config, pool_name }, 1438 { zfs_ioc_vdev_detach, zfs_secpolicy_config, pool_name }, 1439 { zfs_ioc_vdev_setpath, zfs_secpolicy_config, pool_name }, 1440 { zfs_ioc_objset_stats, zfs_secpolicy_read, dataset_name }, 1441 { zfs_ioc_dataset_list_next, zfs_secpolicy_read, dataset_name }, 1442 { zfs_ioc_snapshot_list_next, zfs_secpolicy_read, dataset_name }, 1443 { zfs_ioc_set_prop, zfs_secpolicy_write, dataset_name }, 1444 { zfs_ioc_create_minor, zfs_secpolicy_config, dataset_name }, 1445 { zfs_ioc_remove_minor, zfs_secpolicy_config, dataset_name }, 1446 { zfs_ioc_create, zfs_secpolicy_parent, dataset_name }, 1447 { zfs_ioc_destroy, zfs_secpolicy_parent, dataset_name }, 1448 { zfs_ioc_rollback, zfs_secpolicy_write, dataset_name }, 1449 { zfs_ioc_rename, zfs_secpolicy_write, dataset_name }, 1450 { zfs_ioc_recvbackup, zfs_secpolicy_write, dataset_name }, 1451 { zfs_ioc_sendbackup, zfs_secpolicy_write, dataset_name }, 1452 { zfs_ioc_inject_fault, zfs_secpolicy_inject, no_name }, 1453 { zfs_ioc_clear_fault, zfs_secpolicy_inject, no_name }, 1454 { zfs_ioc_inject_list_next, zfs_secpolicy_inject, no_name }, 1455 { zfs_ioc_error_log, zfs_secpolicy_inject, pool_name }, 1456 { zfs_ioc_clear, zfs_secpolicy_config, pool_name }, 1457 { zfs_ioc_bookmark_name, zfs_secpolicy_inject, pool_name }, 1458 { zfs_ioc_promote, zfs_secpolicy_write, dataset_name }, 1459 { zfs_ioc_destroy_snaps, zfs_secpolicy_write, dataset_name }, 1460 { zfs_ioc_snapshot, zfs_secpolicy_write, dataset_name } 1461 }; 1462 1463 static int 1464 zfsdev_ioctl(dev_t dev, int cmd, intptr_t arg, int flag, cred_t *cr, int *rvalp) 1465 { 1466 zfs_cmd_t *zc; 1467 uint_t vec; 1468 int error, rc; 1469 1470 if (getminor(dev) != 0) 1471 return (zvol_ioctl(dev, cmd, arg, flag, cr, rvalp)); 1472 1473 vec = cmd - ZFS_IOC; 1474 1475 if (vec >= sizeof (zfs_ioc_vec) / sizeof (zfs_ioc_vec[0])) 1476 return (EINVAL); 1477 1478 zc = kmem_zalloc(sizeof (zfs_cmd_t), KM_SLEEP); 1479 1480 error = xcopyin((void *)arg, zc, sizeof (zfs_cmd_t)); 1481 1482 if (error == 0) { 1483 zc->zc_cred = (uintptr_t)cr; 1484 zc->zc_dev = dev; 1485 error = zfs_ioc_vec[vec].zvec_secpolicy(zc->zc_name, cr); 1486 } 1487 1488 /* 1489 * Ensure that all pool/dataset names are valid before we pass down to 1490 * the lower layers. 1491 */ 1492 if (error == 0) { 1493 zc->zc_name[sizeof (zc->zc_name) - 1] = '\0'; 1494 switch (zfs_ioc_vec[vec].zvec_namecheck) { 1495 case pool_name: 1496 if (pool_namecheck(zc->zc_name, NULL, NULL) != 0) 1497 error = EINVAL; 1498 break; 1499 1500 case dataset_name: 1501 if (dataset_namecheck(zc->zc_name, NULL, NULL) != 0) 1502 error = EINVAL; 1503 break; 1504 1505 case no_name: 1506 break; 1507 } 1508 } 1509 1510 if (error == 0) 1511 error = zfs_ioc_vec[vec].zvec_func(zc); 1512 1513 rc = xcopyout(zc, (void *)arg, sizeof (zfs_cmd_t)); 1514 if (error == 0) 1515 error = rc; 1516 1517 kmem_free(zc, sizeof (zfs_cmd_t)); 1518 return (error); 1519 } 1520 1521 static int 1522 zfs_attach(dev_info_t *dip, ddi_attach_cmd_t cmd) 1523 { 1524 if (cmd != DDI_ATTACH) 1525 return (DDI_FAILURE); 1526 1527 if (ddi_create_minor_node(dip, "zfs", S_IFCHR, 0, 1528 DDI_PSEUDO, 0) == DDI_FAILURE) 1529 return (DDI_FAILURE); 1530 1531 zfs_dip = dip; 1532 1533 ddi_report_dev(dip); 1534 1535 return (DDI_SUCCESS); 1536 } 1537 1538 static int 1539 zfs_detach(dev_info_t *dip, ddi_detach_cmd_t cmd) 1540 { 1541 if (spa_busy() || zfs_busy() || zvol_busy()) 1542 return (DDI_FAILURE); 1543 1544 if (cmd != DDI_DETACH) 1545 return (DDI_FAILURE); 1546 1547 zfs_dip = NULL; 1548 1549 ddi_prop_remove_all(dip); 1550 ddi_remove_minor_node(dip, NULL); 1551 1552 return (DDI_SUCCESS); 1553 } 1554 1555 /*ARGSUSED*/ 1556 static int 1557 zfs_info(dev_info_t *dip, ddi_info_cmd_t infocmd, void *arg, void **result) 1558 { 1559 switch (infocmd) { 1560 case DDI_INFO_DEVT2DEVINFO: 1561 *result = zfs_dip; 1562 return (DDI_SUCCESS); 1563 1564 case DDI_INFO_DEVT2INSTANCE: 1565 *result = (void *)0; 1566 return (DDI_SUCCESS); 1567 } 1568 1569 return (DDI_FAILURE); 1570 } 1571 1572 /* 1573 * OK, so this is a little weird. 1574 * 1575 * /dev/zfs is the control node, i.e. minor 0. 1576 * /dev/zvol/[r]dsk/pool/dataset are the zvols, minor > 0. 1577 * 1578 * /dev/zfs has basically nothing to do except serve up ioctls, 1579 * so most of the standard driver entry points are in zvol.c. 1580 */ 1581 static struct cb_ops zfs_cb_ops = { 1582 zvol_open, /* open */ 1583 zvol_close, /* close */ 1584 zvol_strategy, /* strategy */ 1585 nodev, /* print */ 1586 nodev, /* dump */ 1587 zvol_read, /* read */ 1588 zvol_write, /* write */ 1589 zfsdev_ioctl, /* ioctl */ 1590 nodev, /* devmap */ 1591 nodev, /* mmap */ 1592 nodev, /* segmap */ 1593 nochpoll, /* poll */ 1594 ddi_prop_op, /* prop_op */ 1595 NULL, /* streamtab */ 1596 D_NEW | D_MP | D_64BIT, /* Driver compatibility flag */ 1597 CB_REV, /* version */ 1598 zvol_aread, /* async read */ 1599 zvol_awrite, /* async write */ 1600 }; 1601 1602 static struct dev_ops zfs_dev_ops = { 1603 DEVO_REV, /* version */ 1604 0, /* refcnt */ 1605 zfs_info, /* info */ 1606 nulldev, /* identify */ 1607 nulldev, /* probe */ 1608 zfs_attach, /* attach */ 1609 zfs_detach, /* detach */ 1610 nodev, /* reset */ 1611 &zfs_cb_ops, /* driver operations */ 1612 NULL /* no bus operations */ 1613 }; 1614 1615 static struct modldrv zfs_modldrv = { 1616 &mod_driverops, "ZFS storage pool version " ZFS_VERSION_STRING, 1617 &zfs_dev_ops 1618 }; 1619 1620 static struct modlinkage modlinkage = { 1621 MODREV_1, 1622 (void *)&zfs_modlfs, 1623 (void *)&zfs_modldrv, 1624 NULL 1625 }; 1626 1627 int 1628 _init(void) 1629 { 1630 int error; 1631 1632 spa_init(FREAD | FWRITE); 1633 zfs_init(); 1634 zvol_init(); 1635 1636 if ((error = mod_install(&modlinkage)) != 0) { 1637 zvol_fini(); 1638 zfs_fini(); 1639 spa_fini(); 1640 return (error); 1641 } 1642 1643 error = ldi_ident_from_mod(&modlinkage, &zfs_li); 1644 ASSERT(error == 0); 1645 1646 return (0); 1647 } 1648 1649 int 1650 _fini(void) 1651 { 1652 int error; 1653 1654 if (spa_busy() || zfs_busy() || zvol_busy() || zio_injection_enabled) 1655 return (EBUSY); 1656 1657 if ((error = mod_remove(&modlinkage)) != 0) 1658 return (error); 1659 1660 zvol_fini(); 1661 zfs_fini(); 1662 spa_fini(); 1663 1664 ldi_ident_release(zfs_li); 1665 zfs_li = NULL; 1666 1667 return (error); 1668 } 1669 1670 int 1671 _info(struct modinfo *modinfop) 1672 { 1673 return (mod_info(&modlinkage, modinfop)); 1674 } 1675