#include <sys/t_lock.h>
#include <sys/param.h>
#include <sys/systm.h>
#include <sys/signal.h>
#include <sys/cred.h>
#include <sys/proc.h>
#include <sys/disp.h>
#include <sys/user.h>
#include <sys/vfs.h>
#include <sys/vnode.h>
#include <sys/stat.h>
#include <sys/mode.h>
#include <sys/buf.h>
#include <sys/uio.h>
#include <sys/dnlc.h>
#include <sys/pathname.h>
#include <sys/fs/ufs_inode.h>
#include <sys/fs/ufs_fs.h>
#include <sys/mount.h>
#include <sys/fs/ufs_fsdir.h>
#include <sys/fs/ufs_trans.h>
#include <sys/fs/ufs_panic.h>
#include <sys/fs/ufs_quota.h>
#include <sys/errno.h>
#include <sys/debug.h>
#include <vm/seg.h>
#include <sys/sysmacros.h>
#include <sys/cmn_err.h>
#include <sys/cpuvar.h>
#include <sys/unistd.h>
int
ufs_xattr_getattrdir(
vnode_t *dvp,
struct inode **sip,
int flags,
struct cred *cr)
{
struct vfs *vfsp;
struct inode *ip, *sdp;
int error;
ip = VTOI(dvp);
if (flags & LOOKUP_XATTR) {
if (ip && ((ip->i_oeftflag) != 0)) {
vfsp = dvp->v_vfsp;
error = ufs_iget(vfsp, ip->i_oeftflag, sip, cr);
if (error)
return (error);
sdp = *sip;
if ((sdp->i_mode & IFMT) != IFATTRDIR) {
cmn_err(CE_NOTE, "ufs_getattrdir: inode %d"
" points to attribute directory %d "
"which is not an attribute directory;"
"run fsck on file system",
(int)ip->i_number, (int)sdp->i_number);
VN_RELE(ITOV(sdp));
return (ENOENT);
}
ITOV(sdp)->v_type = VDIR;
ITOV(sdp)->v_flag |= V_XATTRDIR;
error = 0;
goto out;
} else if (flags & CREATE_XATTR_DIR) {
error = ufs_xattrmkdir(ip, sip, 1, cr);
} else {
error = ENOENT;
goto out;
}
} else if (flags & CREATE_XATTR_DIR) {
error = ufs_xattrmkdir(ip, sip, 1, cr);
} else {
error = ENOENT;
}
out:
return (error);
}
void
ufs_unhook_shadow(struct inode *ip, struct inode *sip)
{
struct vnode *datavp = ITOV(ip);
struct vnode *dirvp = ITOV(sip);
int hno;
kmutex_t *ihm;
ASSERT(RW_WRITE_HELD(&sip->i_contents));
ASSERT(RW_WRITE_HELD(&ip->i_contents));
if (vn_is_readonly(ITOV(ip)))
return;
if (ip->i_ufsvfs == NULL || sip->i_ufsvfs == NULL)
return;
hno = INOHASH(ip->i_number);
ihm = &ih_lock[hno];
mutex_enter(ihm);
mutex_enter(&datavp->v_lock);
mutex_enter(&dirvp->v_lock);
if (dirvp->v_count != 1 && datavp->v_count != 1) {
mutex_exit(&dirvp->v_lock);
mutex_exit(&datavp->v_lock);
mutex_exit(ihm);
return;
}
sip->i_nlink -= 2;
ufs_setreclaim(sip);
TRANS_INODE(sip->i_ufsvfs, sip);
sip->i_flag |= ICHG;
sip->i_seq++;
ITIMES_NOLOCK(sip);
ip->i_oeftflag = 0;
TRANS_INODE(ip->i_ufsvfs, ip);
ip->i_flag |= ICHG;
ip->i_seq++;
ufs_iupdat(ip, 1);
mutex_exit(&dirvp->v_lock);
mutex_exit(&datavp->v_lock);
mutex_exit(ihm);
}