Page Menu
Home
FreeBSD
Search
Configure Global Search
Log In
Files
F136426050
D6857.id17617.diff
No One
Temporary
Actions
View File
Edit File
Delete File
View Transforms
Subscribe
Mute Notifications
Flag For Later
Award Token
Size
7 KB
Referenced Files
None
Subscribers
None
D6857.id17617.diff
View Options
Index: sys/boot/zfs/libzfs.h
===================================================================
--- sys/boot/zfs/libzfs.h
+++ sys/boot/zfs/libzfs.h
@@ -65,7 +65,7 @@
int zfs_list(const char *name);
void init_zfs_bootenv(char *currdev);
int zfs_bootenv(const char *name);
-int zfs_belist_add(const char *name);
+int zfs_belist_add(const char *name, uint64_t);
int zfs_set_env(void);
extern struct devsw zfs_dev;
Index: sys/boot/zfs/zfs.c
===================================================================
--- sys/boot/zfs/zfs.c
+++ sys/boot/zfs/zfs.c
@@ -801,7 +801,7 @@
}
int
-zfs_belist_add(const char *name)
+zfs_belist_add(const char *name, uint64_t value __attribute__((unused)))
{
/* Skip special datasets that start with a $ character */
Index: sys/boot/zfs/zfsimpl.c
===================================================================
--- sys/boot/zfs/zfsimpl.c
+++ sys/boot/zfs/zfsimpl.c
@@ -1473,12 +1473,12 @@
* the directory contents.
*/
static int
-mzap_list(const dnode_phys_t *dnode, int (*callback)(const char *))
+mzap_list(const dnode_phys_t *dnode, int (*callback)(const char *, uint64_t))
{
const mzap_phys_t *mz;
const mzap_ent_phys_t *mze;
size_t size;
- int chunks, i;
+ int chunks, i, rc;
/*
* Microzap objects use exactly one block. Read the whole
@@ -1492,7 +1492,9 @@
mze = &mz->mz_chunk[i];
if (mze->mze_name[0])
//printf("%-32s 0x%jx\n", mze->mze_name, (uintmax_t)mze->mze_value);
- callback(mze->mze_name);
+ rc = callback(mze->mze_name, mze->mze_value);
+ if (rc != 0)
+ return (rc);
}
return (0);
@@ -1503,12 +1505,12 @@
* the directory header.
*/
static int
-fzap_list(const spa_t *spa, const dnode_phys_t *dnode, int (*callback)(const char *))
+fzap_list(const spa_t *spa, const dnode_phys_t *dnode, int (*callback)(const char *, uint64_t))
{
int bsize = dnode->dn_datablkszsec << SPA_MINBLOCKSHIFT;
zap_phys_t zh = *(zap_phys_t *) zap_scratch;
fat_zap_t z;
- int i, j;
+ int i, j, rc;
if (zh.zap_magic != ZAP_MAGIC)
return (EIO);
@@ -1566,14 +1568,16 @@
value = fzap_leaf_value(&zl, zc);
//printf("%s 0x%jx\n", name, (uintmax_t)value);
- callback((const char *)name);
+ rc = callback((const char *)name, value);
+ if (rc != 0)
+ return (rc);
}
}
return (0);
}
-static int zfs_printf(const char *name)
+static int zfs_printf(const char *name, uint64_t value __attribute__((unused)))
{
printf("%s\n", name);
@@ -1868,7 +1872,7 @@
}
int
-zfs_callback_dataset(const spa_t *spa, uint64_t objnum, int (*callback)(const char *name))
+zfs_callback_dataset(const spa_t *spa, uint64_t objnum, int (*callback)(const char *name, uint64_t))
{
uint64_t dir_obj, child_dir_zapobj, zap_type;
dnode_phys_t child_dir_zap, dir, dataset;
@@ -2008,9 +2012,67 @@
return (0);
}
+/*
+ * callback function for feature name checks.
+ */
+static int
+check_feature(const char *name, uint64_t value)
+{
+ int i;
+
+ if (value == 0)
+ return (0);
+ if (name[0] == '\0')
+ return (0);
+
+ for (i = 0; features_for_read[i] != NULL; i++) {
+ if (strcmp (name, features_for_read[i]) == 0)
+ return (0);
+ }
+ printf("ZFS: unsupported feature: %s\n", name);
+ return (EIO);
+}
+
+/*
+ * Checks whether the MOS features that are active are supported.
+ */
+static int
+check_mos_features(const spa_t *spa)
+{
+ dnode_phys_t dir;
+ uint64_t objnum, zap_type;
+ size_t size;
+ int rc;
+
+ if ((rc = objset_get_dnode(spa, &spa->spa_mos, DMU_OT_OBJECT_DIRECTORY,
+ &dir)) != 0)
+ return (rc);
+ if ((rc = zap_lookup(spa, &dir, DMU_POOL_FEATURES_FOR_READ, &objnum)) != 0)
+ return (rc);
+
+ if ((rc = objset_get_dnode(spa, &spa->spa_mos, objnum, &dir)) != 0)
+ return (rc);
+ if (dir.dn_type != DMU_OTN_ZAP_METADATA) {
+ /* printf("dir.dn_type: %x\n", dir.dn_type); */
+ return (EIO);
+ }
+ size = dir.dn_datablkszsec * 512;
+ if (dnode_read(spa, &dir, 0, zap_scratch, size))
+ return (EIO);
+
+ zap_type = *(uint64_t *) zap_scratch;
+ if (zap_type == ZBT_MICRO)
+ rc = mzap_list(&dir, check_feature);
+ else
+ rc = fzap_list(spa, &dir, check_feature);
+
+ return (rc);
+}
+
static int
zfs_spa_init(spa_t *spa)
{
+ int rc;
if (zio_read(spa, &spa->spa_uberblock.ub_rootbp, &spa->spa_mos)) {
printf("ZFS: can't read MOS of pool %s\n", spa->spa_name);
@@ -2020,7 +2082,13 @@
printf("ZFS: corrupted MOS of pool %s\n", spa->spa_name);
return (EIO);
}
- return (0);
+
+ rc = check_mos_features(spa);
+ if (rc != 0) {
+ printf("ZFS: pool %s is not supported\n", spa->spa_name);
+ }
+
+ return (rc);
}
static int
Index: sys/cddl/boot/zfs/zfsimpl.h
===================================================================
--- sys/cddl/boot/zfs/zfsimpl.h
+++ sys/cddl/boot/zfs/zfsimpl.h
@@ -63,6 +63,8 @@
#define _NOTE(s)
+typedef enum { B_FALSE, B_TRUE } boolean_t;
+
/* CRC64 table */
#define ZFS_CRC64_POLY 0xC96C5795D7870F42ULL /* ECMA-182, reflected form */
@@ -899,6 +901,41 @@
blkptr_t dn_spill;
} dnode_phys_t;
+typedef enum dmu_object_byteswap {
+ DMU_BSWAP_UINT8,
+ DMU_BSWAP_UINT16,
+ DMU_BSWAP_UINT32,
+ DMU_BSWAP_UINT64,
+ DMU_BSWAP_ZAP,
+ DMU_BSWAP_DNODE,
+ DMU_BSWAP_OBJSET,
+ DMU_BSWAP_ZNODE,
+ DMU_BSWAP_OLDACL,
+ DMU_BSWAP_ACL,
+ /*
+ * Allocating a new byteswap type number makes the on-disk format
+ * incompatible with any other format that uses the same number.
+ *
+ * Data can usually be structured to work with one of the
+ * DMU_BSWAP_UINT* or DMU_BSWAP_ZAP types.
+ */
+ DMU_BSWAP_NUMFUNCS
+} dmu_object_byteswap_t;
+
+#define DMU_OT_NEWTYPE 0x80
+#define DMU_OT_METADATA 0x40
+#define DMU_OT_BYTESWAP_MASK 0x3f
+
+/*
+ * Defines a uint8_t object type. Object types specify if the data
+ * in the object is metadata (boolean) and how to byteswap the data
+ * (dmu_object_byteswap_t).
+ */
+#define DMU_OT(byteswap, metadata) \
+ (DMU_OT_NEWTYPE | \
+ ((metadata) ? DMU_OT_METADATA : 0) | \
+ ((byteswap) & DMU_OT_BYTESWAP_MASK))
+
typedef enum dmu_object_type {
DMU_OT_NONE,
/* general: */
@@ -959,7 +996,21 @@
DMU_OT_SA_ATTR_LAYOUTS, /* ZAP */
DMU_OT_SCAN_XLATE, /* ZAP */
DMU_OT_DEDUP, /* fake dedup BP from ddt_bp_create() */
- DMU_OT_NUMTYPES
+ DMU_OT_NUMTYPES,
+
+ /*
+ * Names for valid types declared with DMU_OT().
+ */
+ DMU_OTN_UINT8_DATA = DMU_OT(DMU_BSWAP_UINT8, B_FALSE),
+ DMU_OTN_UINT8_METADATA = DMU_OT(DMU_BSWAP_UINT8, B_TRUE),
+ DMU_OTN_UINT16_DATA = DMU_OT(DMU_BSWAP_UINT16, B_FALSE),
+ DMU_OTN_UINT16_METADATA = DMU_OT(DMU_BSWAP_UINT16, B_TRUE),
+ DMU_OTN_UINT32_DATA = DMU_OT(DMU_BSWAP_UINT32, B_FALSE),
+ DMU_OTN_UINT32_METADATA = DMU_OT(DMU_BSWAP_UINT32, B_TRUE),
+ DMU_OTN_UINT64_DATA = DMU_OT(DMU_BSWAP_UINT64, B_FALSE),
+ DMU_OTN_UINT64_METADATA = DMU_OT(DMU_BSWAP_UINT64, B_TRUE),
+ DMU_OTN_ZAP_DATA = DMU_OT(DMU_BSWAP_ZAP, B_FALSE),
+ DMU_OTN_ZAP_METADATA = DMU_OT(DMU_BSWAP_ZAP, B_TRUE)
} dmu_object_type_t;
typedef enum dmu_objset_type {
@@ -1097,6 +1148,7 @@
*/
#define DMU_POOL_DIRECTORY_OBJECT 1
#define DMU_POOL_CONFIG "config"
+#define DMU_POOL_FEATURES_FOR_READ "features_for_read"
#define DMU_POOL_ROOT_DATASET "root_dataset"
#define DMU_POOL_SYNC_BPLIST "sync_bplist"
#define DMU_POOL_ERRLOG_SCRUB "errlog_scrub"
File Metadata
Details
Attached
Mime Type
text/plain
Expires
Tue, Nov 18, 6:07 PM (18 h, 13 m)
Storage Engine
blob
Storage Format
Raw Data
Storage Handle
25532817
Default Alt Text
D6857.id17617.diff (7 KB)
Attached To
Mode
D6857: loader zfs should check for MOS features
Attached
Detach File
Event Timeline
Log In to Comment