Module Name:    src
Committed By:   riastradh
Date:           Tue Mar 31 15:47:50 UTC 2015

Modified Files:
        src/share/man/man9: fstrans.9

Log Message:
Revamp fstrans(9) man page.

- Fix example: fstrans_start never fails and returns void.
- Add fstrans_mount/fstrans_unmount.
- Explain intent, not just mechanism.
- Add internal cross-references and redundant information from
  different callers' perspectives.


To generate a diff of this commit:
cvs rdiff -u -r1.16 -r1.17 src/share/man/man9/fstrans.9

Please note that diffs are not public domain; they are subject to the
copyright notices on the relevant files.

Modified files:

Index: src/share/man/man9/fstrans.9
diff -u src/share/man/man9/fstrans.9:1.16 src/share/man/man9/fstrans.9:1.17
--- src/share/man/man9/fstrans.9:1.16	Tue Sep 17 19:58:03 2013
+++ src/share/man/man9/fstrans.9	Tue Mar 31 15:47:50 2015
@@ -1,4 +1,4 @@
-.\"     $NetBSD: fstrans.9,v 1.16 2013/09/17 19:58:03 wiz Exp $
+.\"     $NetBSD: fstrans.9,v 1.17 2015/03/31 15:47:50 riastradh Exp $
 .\"
 .\" Copyright (c) 2007 The NetBSD Foundation, Inc.
 .\" All rights reserved.
@@ -27,7 +27,7 @@
 .\" ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
 .\" POSSIBILITY OF SUCH DAMAGE.
 .\"
-.Dd April 13, 2010
+.Dd March 31, 2015
 .Dt FSTRANS 9
 .Os
 .Sh NAME
@@ -46,9 +46,9 @@
 .In sys/mount.h
 .In sys/fstrans.h
 .Ft int
-.Fn fstrans_setstate "struct mount *mp" "enum fstrans_state new_state"
-.Ft "enum fstrans_state"
-.Fn fstrans_getstate "struct mount *mp"
+.Fn fstrans_mount "struct mount *mp"
+.Ft void
+.Fn fstrans_unmount "struct mount *mp"
 .Ft void
 .Fn fstrans_start "struct mount *mp" "enum fstrans_lock_type lock_type"
 .Ft int
@@ -56,6 +56,10 @@
 .Ft void
 .Fn fstrans_done "struct mount *mp"
 .Ft int
+.Fn fstrans_setstate "struct mount *mp" "enum fstrans_state new_state"
+.Ft "enum fstrans_state"
+.Fn fstrans_getstate "struct mount *mp"
+.Ft int
 .Fn fstrans_is_owner "struct mount *mp"
 .Ft int
 .Fn fscow_establish "struct mount *mp" \
@@ -68,105 +72,224 @@
 .Sh DESCRIPTION
 The
 .Nm
-subsystem is a set of operations to assist file system suspension.
-These operations must not be used outside of file systems.
+subsystem assists file system suspension and copy-on-write snapshots.
 .Pp
-File systems supporting this subsystem must set the flag
-.Dv IMNT_HAS_TRANS
-in
-.Dv "mnt_iflag" .
+For a file system to use
+.Nm ,
+its
+.Xr VFS_MOUNT 9
+method must call
+.Fn fstrans_mount ,
+and its
+.Xr VFS_UNMOUNT 9
+method must call
+.Fn fstrans_unmount .
 .Pp
-File systems are always in one of these states:
+The file system's normal operations, such as its
+.Xr vnodeops 9 ,
+must be bracketed by
+.Fn fstrans_start
+and
+.Fn fstrans_done
+in a
+.Em shared
+transaction, which is blocked by suspending the file system and while
+it is suspended.
 .Pp
-.Bl -tag -offset indent -width FSTRANS_SUSPENDING -compact
-.It Dv FSTRANS_NORMAL
-Normal operations.
-.It Dv FSTRANS_SUSPENDING
-Preparing a suspension.
-.It Dv FSTRANS_SUSPENDED
-Suspended.
-.El
+Operations needed to sync the file system to its backing store must be
+bracketed by
+.Fn fstrans_start
+and
+.Fn fstrans_done
+in a
+.Em lazy
+transaction, which is allowed while suspending the file system in order
+to sync it to its backing store, but blocked while the file system is
+suspended.
 .Pp
-This state is represented by
-.Vt "enum fstrans_state" .
+Transactions are per-thread and nestable: if a thread is already in a
+transaction, it can enter another transaction.
+Each
+.Fn fstrans_start
+must be paired with
+.Fn fstrans_done .
+Entering a shared transaction while in a lazy transaction is not
+allowed and will lead to deadlock.
 .Pp
-All file system operations use a
-.Em "fstrans lock" .
-This lock is recursive.
-A thread already owning a lock will always get another lock.
-The lock has two variants:
-.Bl -tag -offset indent -width FSTRANS_SHARED
-.It Dv FSTRANS_SHARED
-A lock that will be granted if the file system is in state
-.Dv FSTRANS_NORMAL .
-.It Dv FSTRANS_LAZY
-A lock that will be granted if the file system is in state
+The file system's
+.Xr VFS_SUSPENDCTL 9
+method can use
+.Fn fstrans_setstate
+to:
+.Bl -dash
+.It
+enter the
+.Dv FSTRANS_SUSPENDING
+to suspend all normal operations but allow syncing,
+.It
+enter the
+.Dv FSTRANS_SUSPENDED
+state to suspend all operations once synced, and
+.It
+restore to the
 .Dv FSTRANS_NORMAL
-or
-.Dv FSTRANS_SUSPENDING .
-It needs special care because operations using this variant will not block
-while the file system prepares suspension.
+state to resume all operations.
 .El
 .Pp
-The lock variant is represented by
-.Vt "enum fstrans_lock_type" .
+A file system supporting
+.Nm
+may establish a copy-on-write callback with
+.Fn fscow_establish .
+The copy-on-write callback will be called every time a buffer is
+written to a block device with
+.Fn VOP_STRATEGY
+and every time a buffer is read into the
+.Xr buffercache 9
+with
+.Dv B_MODIFY
+set indicating the caller's intent to modify it.
+Anyone modifying a buffer may additionally use
+.Fn fscow_run
+to explicitly invoke the established callback.
+The copy-on-write callback must be disestablished with
+.Fn fscow_disestablish
+when the file system is done with it.
 .Sh FUNCTIONS
-The following functions comprise the
-.Tn API
-provided by
-.Nm .
-.Bl -tag -width compact
-.It Fn fstrans_getstate "mp"
-Returns the current state of the file system
+.Bl -tag -width abcd
+.It Fn fstrans_mount "mp"
+Initialize the
+.Nm
+subsystem for the file system mounted at
 .Fa mp .
-.It Fn fstrans_setstate "mp" "new_state"
-Changes the state of the file system
-.Fa mp
-to
-.Fa new_state .
+Sets
+.Dv IMNT_HAS_TRANS
+in
+.Fa mp Ns Li "->mnt_iflag" .
+Return zero on success, or error code if
+.Xr vfs_busy 9
+fails.
+.It Fn fstrans_unmount "mp"
+Finalize the
+.Nm
+subsystem.
+Clears
+.Dv IMNT_HAS_TRANS
+in
+.Fa mp Ns Li "->mnt_iflag" .
+Caller is responsible for ensuring that no transactions are active.
 .It Fn fstrans_start "mp" "lock_type"
-Sets a lock of type
+Begin a transaction of type
 .Fa lock_type
 on the file system
-.Fa mp .
+.Fa mp
+in the current thread.
+If the file system is in a state that blocks such transactions, wait
+until it changes state to one that does not.
+.Bl -tag -width FSTRANS_SHARED
+.It Dv FSTRANS_SHARED
+If the file system is suspending or suspended, wait until it is
+resumed.
+Intended for normal file system operations.
+.It Dv FSTRANS_LAZY
+If the file system is suspended, wait until it is resumed.
+Intended for operations needed to sync the file system to its backing
+store in order to suspend it.
+.El
 .It Fn fstrans_start_nowait "mp" "lock_type"
 Like
 .Fn fstrans_start ,
-but will not wait for a state change of the file system when attempting to
-acquire the lock.
-The thread may still sleep while attempting to acquire the lock.
+but return
+.Dv EBUSY
+immediately if
+.Fa lock_type
+transactions are blocked in its current state.
+.Pp
+May sleep nevertheless on internal locks.
 .It Fn fstrans_done "mp"
-Releases a lock on the file system
+End the current transaction on
+.Fa mp .
+.It Fn fstrans_getstate "mp"
+Return the current state of the file system
 .Fa mp .
+.Pp
+Must be called within a transaction for the answer to be stable.
+.It Fn fstrans_setstate "mp" "new_state"
+Change the state of the file system
+.Fa mp
+to
+.Fa new_state ,
+and wait for all transactions not allowed in
+.Fa new_state
+to complete.
+.Bl -tag -width FSTRANS_SUSPENDING
+.It Dv FSTRANS_NORMAL
+Allow all transactions.
+.It Dv FSTRANS_SUSPENDING
+Block
+.Dv FSTRANS_SHARED
+transactions but allow
+.Dv FSTRANS_LAZY
+transactions.
+.It Dv FSTRANS_SUSPENDED
+Block all transactions.
+.El
+.Pp
+A thread that changes a file system to a state other than
+.Dv FSTRANS_NORMAL
+enters a transaction for the purposes of
+.Fn fstrans_getstate
+until it changes state back to
+.Dv FSTRANS_NORMAL .
+.Pp
+Additionally, a thread that changes a file system to a state other than
+.Dv FSTRANS_NORMAL
+acquires an exclusive lock on the file system state, so that
+.Fn fstrans_is_owner
+will return true in that thread, and no other thread can change the
+file system's state until the owner restores it to
+.Dv FSTRANS_NORMAL .
+.Pp
+May sleep, and may be interrupted by a signal.
+On success, return zero.
+On failure, restore the file system to the
+.Dv FSTRANS_NORMAL
+state and return an error code.
+.Fn fstrans_setstate
+never fails if
+.Fa new_state
+is
+.Dv FSTRANS_NORMAL .
 .It Fn fstrans_is_owner "mp"
-Returns
+Return
 .Dv true
-if this thread is currently suspending the file system
+if the current thread is currently suspending the file system
 .Fa mp .
 .It Fn fscow_establish "mp" "func" "cookie"
 Establish a copy-on-write callback for the file system
 .Fa mp .
 The function
 .Fa func
-will be called for every buffer written through this file system.
+will be called for every buffer
+.Fa bp
+written through this file system as
+.Dl Fa func Ns Li "(" Ns Fa cookie Ns Li "," Fa bp Ns Li "," Fa data_valid Ns Li ")"
+where
+.Fa data_valid
+is true if and only if the buffer
+.Fa bp
+has not yet been modified.
 .It Fn fscow_disestablish "mp" "func" "cookie"
-Disestablish a copy-on-write callback registered with
+Disestablish a copy-on-write callback established with
 .Fn fscow_establish .
 .It Fn fscow_run "bp" "data_valid"
 Run all copy-on-write callbacks established for the file system this buffer
-belongs to.
+belongs to, if they have not already been run for this buffer.
 If
 .Fa data_valid
 is
 .Dv true
 the buffer data has not yet been modified.
 .El
-.Sh RETURN VALUES
-The functions
-.Fn fstrans_setstate
-and
-.Fn fstrans_start_nowait
-return zero on success and an error value on failure.
 .Sh EXAMPLES
 The following is an example of a file system suspend operation.
 .Bd -literal
@@ -178,7 +301,7 @@ xxx_suspendctl(struct mount *mp, int cmd
 	switch (cmd) {
 	case SUSPEND_SUSPEND:
 		error = fstrans_setstate(mp, FSTRANS_SUSPENDING);
-		if (error != 0)
+		if (error)
 			return error;
 
 		/* Sync file system state to disk. */
@@ -203,8 +326,7 @@ xxx_create(void *v)
 	struct mount *mp = ap-\*[Gt]a_dvp-\*[Gt]v_mount;
 	int error;
 
-	if ((error = fstrans_start(mp, FSTRANS_SHARED)) != 0)
-		return error;
+	fstrans_start(mp, FSTRANS_SHARED);
 
 	/* Actually create the node. */
 
@@ -214,7 +336,9 @@ xxx_create(void *v)
 }
 .Ed
 .Sh CODE REFERENCES
-The actual code implementing this subsystem can be found in the file
+The
+.Nm
+subsystem is implemented in the file
 .Pa sys/kern/vfs_trans.c .
 .Sh SEE ALSO
 .Xr vfs_resume 9 ,
@@ -230,3 +354,9 @@ The
 subsystem was written by
 .An J\(:urgen Hannken-Illjes
 .Aq hann...@netbsd.org .
+.Sh BUGS
+.Nm
+is useful only for temporary suspension -- it does not help to
+permanently block file system operations for unmounting, because
+.Fn fstrans_start
+cannot fail.

Reply via email to