summaryrefslogtreecommitdiffstats
path: root/sys/cddl/contrib/opensolaris/uts/common/fs/zfs/vdev_file.c
diff options
context:
space:
mode:
authorpjd <pjd@FreeBSD.org>2011-02-27 19:41:40 +0000
committerpjd <pjd@FreeBSD.org>2011-02-27 19:41:40 +0000
commit1b03c5bf41222b723415638f03e00ed12cac076a (patch)
treeef515cadc08bf427e4d3f1360199ec9827b1596b /sys/cddl/contrib/opensolaris/uts/common/fs/zfs/vdev_file.c
parentc67d387baf03726323703774b1b320235fb1f24b (diff)
downloadFreeBSD-src-1b03c5bf41222b723415638f03e00ed12cac076a.zip
FreeBSD-src-1b03c5bf41222b723415638f03e00ed12cac076a.tar.gz
Finally... Import the latest open-source ZFS version - (SPA) 28.
Few new things available from now on: - Data deduplication. - Triple parity RAIDZ (RAIDZ3). - zfs diff. - zpool split. - Snapshot holds. - zpool import -F. Allows to rewind corrupted pool to earlier transaction group. - Possibility to import pool in read-only mode. MFC after: 1 month
Diffstat (limited to 'sys/cddl/contrib/opensolaris/uts/common/fs/zfs/vdev_file.c')
-rw-r--r--sys/cddl/contrib/opensolaris/uts/common/fs/zfs/vdev_file.c45
1 files changed, 41 insertions, 4 deletions
diff --git a/sys/cddl/contrib/opensolaris/uts/common/fs/zfs/vdev_file.c b/sys/cddl/contrib/opensolaris/uts/common/fs/zfs/vdev_file.c
index 67bd110..be3cefc 100644
--- a/sys/cddl/contrib/opensolaris/uts/common/fs/zfs/vdev_file.c
+++ b/sys/cddl/contrib/opensolaris/uts/common/fs/zfs/vdev_file.c
@@ -19,8 +19,7 @@
* CDDL HEADER END
*/
/*
- * Copyright 2008 Sun Microsystems, Inc. All rights reserved.
- * Use is subject to license terms.
+ * Copyright (c) 2005, 2010, Oracle and/or its affiliates. All rights reserved.
*/
#include <sys/zfs_context.h>
@@ -35,6 +34,18 @@
* Virtual device vector for files.
*/
+static void
+vdev_file_hold(vdev_t *vd)
+{
+ ASSERT(vd->vdev_path != NULL);
+}
+
+static void
+vdev_file_rele(vdev_t *vd)
+{
+ ASSERT(vd->vdev_path != NULL);
+}
+
static int
vdev_file_open(vdev_t *vd, uint64_t *psize, uint64_t *ashift)
{
@@ -51,6 +62,17 @@ vdev_file_open(vdev_t *vd, uint64_t *psize, uint64_t *ashift)
return (EINVAL);
}
+ /*
+ * Reopen the device if it's not currently open. Otherwise,
+ * just update the physical size of the device.
+ */
+ if (vd->vdev_tsd != NULL) {
+ ASSERT(vd->vdev_reopening);
+ vf = vd->vdev_tsd;
+ vp = vf->vf_vnode;
+ goto skip_open;
+ }
+
vf = vd->vdev_tsd = kmem_zalloc(sizeof (vdev_file_t), KM_SLEEP);
/*
@@ -65,6 +87,8 @@ vdev_file_open(vdev_t *vd, uint64_t *psize, uint64_t *ashift)
if (error) {
vd->vdev_stat.vs_aux = VDEV_AUX_OPEN_FAILED;
+ kmem_free(vd->vdev_tsd, sizeof (vdev_file_t));
+ vd->vdev_tsd = NULL;
return (error);
}
@@ -77,9 +101,13 @@ vdev_file_open(vdev_t *vd, uint64_t *psize, uint64_t *ashift)
if (vp->v_type != VREG) {
(void) VOP_CLOSE(vp, spa_mode(vd->vdev_spa), 1, 0, kcred, NULL);
vd->vdev_stat.vs_aux = VDEV_AUX_OPEN_FAILED;
+ kmem_free(vd->vdev_tsd, sizeof (vdev_file_t));
+ vd->vdev_tsd = NULL;
return (ENODEV);
}
#endif
+
+skip_open:
/*
* Determine the physical size of the file.
*/
@@ -92,6 +120,8 @@ vdev_file_open(vdev_t *vd, uint64_t *psize, uint64_t *ashift)
if (error) {
(void) VOP_CLOSE(vp, spa_mode(vd->vdev_spa), 1, 0, kcred, NULL);
vd->vdev_stat.vs_aux = VDEV_AUX_OPEN_FAILED;
+ kmem_free(vd->vdev_tsd, sizeof (vdev_file_t));
+ vd->vdev_tsd = NULL;
return (error);
}
@@ -106,12 +136,15 @@ vdev_file_close(vdev_t *vd)
{
vdev_file_t *vf = vd->vdev_tsd;
- if (vf == NULL)
+ if (vd->vdev_reopening || vf == NULL)
return;
- if (vf->vf_vnode != NULL)
+ if (vf->vf_vnode != NULL) {
(void) VOP_CLOSE(vf->vf_vnode, spa_mode(vd->vdev_spa), 1, 0,
kcred, NULL);
+ }
+
+ vd->vdev_delayed_close = B_FALSE;
kmem_free(vf, sizeof (vdev_file_t));
vd->vdev_tsd = NULL;
}
@@ -168,6 +201,8 @@ vdev_ops_t vdev_file_ops = {
vdev_file_io_start,
vdev_file_io_done,
NULL,
+ vdev_file_hold,
+ vdev_file_rele,
VDEV_TYPE_FILE, /* name of this vdev type */
B_TRUE /* leaf vdev */
};
@@ -184,6 +219,8 @@ vdev_ops_t vdev_disk_ops = {
vdev_file_io_start,
vdev_file_io_done,
NULL,
+ vdev_file_hold,
+ vdev_file_rele,
VDEV_TYPE_DISK, /* name of this vdev type */
B_TRUE /* leaf vdev */
};
OpenPOWER on IntegriCloud