* Determine if a device is in use. The 'spare_guid' parameter will be filled * in with the device guid if this spare is active elsewhere on the system. */
| 841 | * in with the device guid if this spare is active elsewhere on the system. |
| 842 | */ |
| 843 | static boolean_t |
| 844 | vdev_inuse(vdev_t *vd, uint64_t crtxg, vdev_labeltype_t reason, |
| 845 | uint64_t *spare_guid, uint64_t *l2cache_guid) |
| 846 | { |
| 847 | spa_t *spa = vd->vdev_spa; |
| 848 | uint64_t state, pool_guid, device_guid, txg, spare_pool; |
| 849 | uint64_t vdtxg = 0; |
| 850 | nvlist_t *label; |
| 851 | |
| 852 | if (spare_guid) |
| 853 | *spare_guid = 0ULL; |
| 854 | if (l2cache_guid) |
| 855 | *l2cache_guid = 0ULL; |
| 856 | |
| 857 | /* |
| 858 | * Read the label, if any, and perform some basic sanity checks. |
| 859 | */ |
| 860 | if ((label = vdev_label_read_config(vd, -1ULL)) == NULL) |
| 861 | return (B_FALSE); |
| 862 | |
| 863 | (void) nvlist_lookup_uint64(label, ZPOOL_CONFIG_CREATE_TXG, |
| 864 | &vdtxg); |
| 865 | |
| 866 | if (nvlist_lookup_uint64(label, ZPOOL_CONFIG_POOL_STATE, |
| 867 | &state) != 0 || |
| 868 | nvlist_lookup_uint64(label, ZPOOL_CONFIG_GUID, |
| 869 | &device_guid) != 0) { |
| 870 | nvlist_free(label); |
| 871 | return (B_FALSE); |
| 872 | } |
| 873 | |
| 874 | if (state != POOL_STATE_SPARE && state != POOL_STATE_L2CACHE && |
| 875 | (nvlist_lookup_uint64(label, ZPOOL_CONFIG_POOL_GUID, |
| 876 | &pool_guid) != 0 || |
| 877 | nvlist_lookup_uint64(label, ZPOOL_CONFIG_POOL_TXG, |
| 878 | &txg) != 0)) { |
| 879 | nvlist_free(label); |
| 880 | return (B_FALSE); |
| 881 | } |
| 882 | |
| 883 | nvlist_free(label); |
| 884 | |
| 885 | /* |
| 886 | * Check to see if this device indeed belongs to the pool it claims to |
| 887 | * be a part of. The only way this is allowed is if the device is a hot |
| 888 | * spare (which we check for later on). |
| 889 | */ |
| 890 | if (state != POOL_STATE_SPARE && state != POOL_STATE_L2CACHE && |
| 891 | !spa_guid_exists(pool_guid, device_guid) && |
| 892 | !spa_spare_exists(device_guid, NULL, NULL) && |
| 893 | !spa_l2cache_exists(device_guid, NULL)) |
| 894 | return (B_FALSE); |
| 895 | |
| 896 | /* |
| 897 | * If the transaction group is zero, then this an initialized (but |
| 898 | * unused) label. This is only an error if the create transaction |
| 899 | * on-disk is the same as the one we're using now, in which case the |
| 900 | * user has attempted to add the same vdev multiple times in the same |
no test coverage detected