FreeBSD ZFS
The Zettabyte File System
Functions

zfs_dir.c File Reference

#include <sys/types.h>
#include <sys/param.h>
#include <sys/time.h>
#include <sys/systm.h>
#include <sys/sysmacros.h>
#include <sys/resource.h>
#include <sys/vfs.h>
#include <sys/vnode.h>
#include <sys/file.h>
#include <sys/kmem.h>
#include <sys/uio.h>
#include <sys/cmn_err.h>
#include <sys/errno.h>
#include <sys/stat.h>
#include <sys/unistd.h>
#include <sys/sunddi.h>
#include <sys/random.h>
#include <sys/policy.h>
#include <sys/kcondvar.h>
#include <sys/callb.h>
#include <sys/smp.h>
#include <sys/zfs_dir.h>
#include <sys/zfs_acl.h>
#include <sys/fs/zfs.h>
#include <sys/zap.h>
#include <sys/dmu.h>
#include <sys/atomic.h>
#include <sys/zfs_ctldir.h>
#include <sys/zfs_fuid.h>
#include <sys/sa.h>
#include <sys/zfs_sa.h>
#include <sys/dnlc.h>
#include <sys/extdirent.h>
Include dependency graph for zfs_dir.c:

Go to the source code of this file.

Functions

static int zfs_match_find (zfsvfs_t *zfsvfs, znode_t *dzp, char *name, boolean_t exact, boolean_t update, int *deflags, pathname_t *rpnp, uint64_t *zoid)
 zfs_match_find() is used by zfs_dirent_lock() to peform zap lookups of names after deciding which is the appropriate lookup interface.
int zfs_dirent_lock (zfs_dirlock_t **dlpp, znode_t *dzp, char *name, znode_t **zpp, int flag, int *direntflags, pathname_t *realpnp)
 Lock a directory entry.
void zfs_dirent_unlock (zfs_dirlock_t *dl)
 Unlock this directory entry and wake anyone who was waiting for it.
int zfs_dirlook (znode_t *dzp, char *name, vnode_t **vpp, int flags, int *deflg, pathname_t *rpnp)
 Look up an entry in a directory.
void zfs_unlinked_add (znode_t *zp, dmu_tx_t *tx)
 unlinked Set (formerly known as the "delete queue") Error Handling
void zfs_unlinked_drain (zfsvfs_t *zfsvfs)
static int zfs_purgedir (znode_t *dzp)
 Delete the entire contents of a directory.
void zfs_rmnode (znode_t *zp)
static uint64_t zfs_dirent (znode_t *zp, uint64_t mode)
int zfs_link_create (zfs_dirlock_t *dl, znode_t *zp, dmu_tx_t *tx, int flag)
 Link zp into dl.
static int zfs_dropname (zfs_dirlock_t *dl, znode_t *zp, znode_t *dzp, dmu_tx_t *tx, int flag)
int zfs_link_destroy (zfs_dirlock_t *dl, znode_t *zp, dmu_tx_t *tx, int flag, boolean_t *unlinkedp)
 Unlink zp from dl, and mark zp for deletion if this was the last link.
boolean_t zfs_dirempty (znode_t *dzp)
 Indicate whether the directory is empty.
int zfs_make_xattrdir (znode_t *zp, vattr_t *vap, vnode_t **xvpp, cred_t *cr)
int zfs_get_xattrdir (znode_t *zp, vnode_t **xvpp, cred_t *cr, int flags)
 Return a znode for the extended attribute directory for zp.
int zfs_sticky_remove_access (znode_t *zdp, znode_t *zp, cred_t *cr)
 Decide whether it is okay to remove within a sticky directory.

Function Documentation

boolean_t zfs_dirempty ( znode_t dzp)

Indicate whether the directory is empty.

Works with or without z_lock held, but can only be consider a hint in the latter case. Returns true if only "." and ".." remain and there's no work in progress.

Definition at line 914 of file zfs_dir.c.

static uint64_t zfs_dirent ( znode_t zp,
uint64_t  mode 
) [static]

Definition at line 691 of file zfs_dir.c.

int zfs_dirent_lock ( zfs_dirlock_t **  dlpp,
znode_t dzp,
char *  name,
znode_t **  zpp,
int  flag,
int *  direntflags,
pathname_t *  realpnp 
)

Lock a directory entry.

A dirlock on <dzp, name> protects that name in dzp's directory zap object. As long as you hold a dirlock, you can assume two things: (1) dzp cannot be reaped, and (2) no other thread can change the zap entry for (i.e. link or unlink) this name.

Input arguments: dzp - znode for directory name - name of entry to lock flag - ZNEW: if the entry already exists, fail with EEXIST. ZEXISTS: if the entry does not exist, fail with ENOENT. ZSHARED: allow concurrent access with other ZSHARED callers. ZXATTR: we want dzp's xattr directory ZCILOOK: On a mixed sensitivity file system, this lookup should be case-insensitive. ZCIEXACT: On a purely case-insensitive file system, this lookup should be case-sensitive. ZRENAMING: we are locking for renaming, force narrow locks ZHAVELOCK: Don't grab the z_name_lock for this call. The current thread already holds it.

Output arguments: zpp - pointer to the znode for the entry (NULL if there isn't one) dlpp - pointer to the dirlock for this entry (NULL on error) direntflags - (case-insensitive lookup only) flags if multiple case-sensitive matches exist in directory realpnp - (case-insensitive lookup only) actual name matched within the directory

Return value: 0 on success or errno on failure.

NOTE: Always checks for, and rejects, '.' and '..'. NOTE: For case-insensitive file systems we take wide locks (see below), but return znode pointers to a single match.

Definition at line 136 of file zfs_dir.c.

void zfs_dirent_unlock ( zfs_dirlock_t dl)

Unlock this directory entry and wake anyone who was waiting for it.

Definition at line 335 of file zfs_dir.c.

int zfs_dirlook ( znode_t dzp,
char *  name,
vnode_t **  vpp,
int  flags,
int *  deflg,
pathname_t *  rpnp 
)

Look up an entry in a directory.

NOTE: '.' and '..' are handled as special cases because no directory entries are actually stored for them. If this is the root of a filesystem, then '.zfs' is also treated as a special pseudo-directory.

Definition at line 370 of file zfs_dir.c.

static int zfs_dropname ( zfs_dirlock_t dl,
znode_t zp,
znode_t dzp,
dmu_tx_t tx,
int  flag 
) [static]

Definition at line 775 of file zfs_dir.c.

int zfs_get_xattrdir ( znode_t zp,
vnode_t **  xvpp,
cred_t *  cr,
int  flags 
)

Return a znode for the extended attribute directory for zp.

** If the directory does not already exist, it is created **

IN: zp - znode to obtain attribute directory from cr - credentials of caller flags - flags from the VOP_LOOKUP call

OUT: xzpp - pointer to extended attribute znode

RETURN: 0 on success error number on failure

Definition at line 1008 of file zfs_dir.c.

int zfs_link_create ( zfs_dirlock_t dl,
znode_t zp,
dmu_tx_t tx,
int  flag 
)

Link zp into dl.

Can only fail if zp has been unlinked.

Definition at line 704 of file zfs_dir.c.

int zfs_link_destroy ( zfs_dirlock_t dl,
znode_t zp,
dmu_tx_t tx,
int  flag,
boolean_t *  unlinkedp 
)

Unlink zp from dl, and mark zp for deletion if this was the last link.

Can fail if zp is a mount point (EBUSY) or a non-empty directory (EEXIST). If 'unlinkedp' is NULL, we put unlinked znodes on the unlinked list. If it's non-NULL, we use it to indicate whether the znode needs deletion, and it's the caller's job to do it.

Definition at line 806 of file zfs_dir.c.

int zfs_make_xattrdir ( znode_t zp,
vattr_t *  vap,
vnode_t **  xvpp,
cred_t *  cr 
)

Definition at line 920 of file zfs_dir.c.

static int zfs_match_find ( zfsvfs_t zfsvfs,
znode_t dzp,
char *  name,
boolean_t  exact,
boolean_t  update,
int *  deflags,
pathname_t *  rpnp,
uint64_t *  zoid 
) [static]

zfs_match_find() is used by zfs_dirent_lock() to peform zap lookups of names after deciding which is the appropriate lookup interface.

Definition at line 64 of file zfs_dir.c.

static int zfs_purgedir ( znode_t dzp) [static]

Delete the entire contents of a directory.

Return a count of the number of entries that could not be deleted. If we encounter an error, return a count of at least one so that the directory stays in the unlinked set.

NOTE: this function assumes that the directory is inactive, so there is no need to lock its entries before deletion. Also, it assumes the directory contents is *only* regular files.

Definition at line 530 of file zfs_dir.c.

void zfs_rmnode ( znode_t zp)

Definition at line 586 of file zfs_dir.c.

int zfs_sticky_remove_access ( znode_t zdp,
znode_t zp,
cred_t *  cr 
)

Decide whether it is okay to remove within a sticky directory.

In sticky directories, write access is not sufficient; you can remove entries from a directory only if:

you own the directory, you own the entry, the entry is a plain file and you have write access, or you are privileged (checked in secpolicy...).

The function returns 0 if remove access is granted.

Definition at line 1083 of file zfs_dir.c.

void zfs_unlinked_add ( znode_t zp,
dmu_tx_t tx 
)

unlinked Set (formerly known as the "delete queue") Error Handling

When dealing with the unlinked set, we dmu_tx_hold_zap(), but we don't specify the name of the entry that we will be manipulating. We also fib and say that we won't be adding any new entries to the unlinked set, even though we might (this is to lower the minimum file size that can be deleted in a full filesystem). So on the small chance that the nlink list is using a fat zap (ie. has more than 2000 entries), we *may* not pre-read a block that's needed. Therefore it is remotely possible for some of the assertions regarding the unlinked set below to fail due to i/o error. On a nondebug system, this will result in the space being leaked.

Definition at line 455 of file zfs_dir.c.

void zfs_unlinked_drain ( zfsvfs_t zfsvfs)

Definition at line 471 of file zfs_dir.c.

 All Data Structures Files Functions Variables Typedefs Enumerations Enumerator Defines