Changeset View
Changeset View
Standalone View
Standalone View
sys/ufs/ffs/ffs_inode.c
Show First 20 Lines • Show All 80 Lines • ▼ Show 20 Lines | |||||
int | int | ||||
ffs_update(vp, waitfor) | ffs_update(vp, waitfor) | ||||
struct vnode *vp; | struct vnode *vp; | ||||
int waitfor; | int waitfor; | ||||
{ | { | ||||
struct fs *fs; | struct fs *fs; | ||||
struct buf *bp; | struct buf *bp; | ||||
struct inode *ip; | struct inode *ip; | ||||
daddr_t bn; | |||||
int flags, error; | int flags, error; | ||||
ASSERT_VOP_ELOCKED(vp, "ffs_update"); | ASSERT_VOP_ELOCKED(vp, "ffs_update"); | ||||
ufs_itimes(vp); | ufs_itimes(vp); | ||||
ip = VTOI(vp); | ip = VTOI(vp); | ||||
if ((ip->i_flag & IN_MODIFIED) == 0 && waitfor == 0) | if ((ip->i_flag & IN_MODIFIED) == 0 && waitfor == 0) | ||||
return (0); | return (0); | ||||
ip->i_flag &= ~(IN_LAZYACCESS | IN_LAZYMOD | IN_MODIFIED); | ip->i_flag &= ~(IN_LAZYACCESS | IN_LAZYMOD | IN_MODIFIED); | ||||
Show All 10 Lines | ffs_update(vp, waitfor) | ||||
* and is available to us. We have to grab a reference to the | * and is available to us. We have to grab a reference to the | ||||
* snapshot vnode to prevent it from being removed while we are | * snapshot vnode to prevent it from being removed while we are | ||||
* waiting for the buffer. | * waiting for the buffer. | ||||
*/ | */ | ||||
flags = 0; | flags = 0; | ||||
if (IS_SNAPSHOT(ip)) | if (IS_SNAPSHOT(ip)) | ||||
flags = GB_LOCK_NOWAIT; | flags = GB_LOCK_NOWAIT; | ||||
loop: | loop: | ||||
error = bread_gb(ITODEVVP(ip), | bn = fsbtodb(fs, ino_to_fsba(fs, ip->i_number)); | ||||
fsbtodb(fs, ino_to_fsba(fs, ip->i_number)), | error = ffs_breadz(VFSTOUFS(vp->v_mount), ITODEVVP(ip), bn, bn, | ||||
(int) fs->fs_bsize, NOCRED, flags, &bp); | (int) fs->fs_bsize, NULL, NULL, 0, NOCRED, flags, NULL, &bp); | ||||
if (error != 0) { | if (error != 0) { | ||||
if (error != EBUSY) | if (error != EBUSY) | ||||
return (error); | return (error); | ||||
KASSERT((IS_SNAPSHOT(ip)), ("EBUSY from non-snapshot")); | KASSERT((IS_SNAPSHOT(ip)), ("EBUSY from non-snapshot")); | ||||
/* | /* | ||||
* Wait for our inode block to become available. | * Wait for our inode block to become available. | ||||
* | * | ||||
* Hold a reference to the vnode to protect against | * Hold a reference to the vnode to protect against | ||||
Show All 32 Lines | if (I_IS_UFS1(ip)) { | ||||
*((struct ufs2_dinode *)bp->b_data + | *((struct ufs2_dinode *)bp->b_data + | ||||
ino_to_fsbo(fs, ip->i_number)) = *ip->i_din2; | ino_to_fsbo(fs, ip->i_number)) = *ip->i_din2; | ||||
/* | /* | ||||
* XXX: FIX? The entropy here is desirable, | * XXX: FIX? The entropy here is desirable, | ||||
* but the harvesting may be expensive | * but the harvesting may be expensive | ||||
*/ | */ | ||||
random_harvest_queue(&(ip->i_din2), sizeof(ip->i_din2), RANDOM_FS_ATIME); | random_harvest_queue(&(ip->i_din2), sizeof(ip->i_din2), RANDOM_FS_ATIME); | ||||
} | } | ||||
if (waitfor) | if (waitfor) { | ||||
error = bwrite(bp); | error = bwrite(bp); | ||||
else if (vm_page_count_severe() || buf_dirty_count_severe()) { | if (ffs_fsfail_cleanup(VFSTOUFS(vp->v_mount), error)) | ||||
error = 0; | |||||
} else if (vm_page_count_severe() || buf_dirty_count_severe()) { | |||||
bawrite(bp); | bawrite(bp); | ||||
error = 0; | error = 0; | ||||
} else { | } else { | ||||
if (bp->b_bufsize == fs->fs_bsize) | if (bp->b_bufsize == fs->fs_bsize) | ||||
bp->b_flags |= B_CLUSTEROK; | bp->b_flags |= B_CLUSTEROK; | ||||
bdwrite(bp); | bdwrite(bp); | ||||
error = 0; | error = 0; | ||||
} | } | ||||
▲ Show 20 Lines • Show All 502 Lines • ▼ Show 20 Lines | #define BAP(ip, i) (I_IS_UFS1(ip) ? bap1[i] : bap2[i]) | ||||
* Get buffer of block pointers, zero those entries corresponding | * Get buffer of block pointers, zero those entries corresponding | ||||
* to blocks to be free'd, and update on disk copy first. Since | * to blocks to be free'd, and update on disk copy first. Since | ||||
* double(triple) indirect before single(double) indirect, calls | * double(triple) indirect before single(double) indirect, calls | ||||
* to VOP_BMAP() on these blocks will fail. However, we already | * to VOP_BMAP() on these blocks will fail. However, we already | ||||
* have the on-disk address, so we just pass it to bread() instead | * have the on-disk address, so we just pass it to bread() instead | ||||
* of having bread() attempt to calculate it using VOP_BMAP(). | * of having bread() attempt to calculate it using VOP_BMAP(). | ||||
*/ | */ | ||||
vp = ITOV(ip); | vp = ITOV(ip); | ||||
error = breadn_flags(vp, lbn, dbn, (int)fs->fs_bsize, NULL, NULL, 0, | error = ffs_breadz(ump, vp, lbn, dbn, (int)fs->fs_bsize, NULL, NULL, 0, | ||||
NOCRED, 0, NULL, &bp); | NOCRED, 0, NULL, &bp); | ||||
if (error) { | if (error) { | ||||
*countp = 0; | *countp = 0; | ||||
return (error); | return (error); | ||||
} | } | ||||
if (I_IS_UFS1(ip)) | if (I_IS_UFS1(ip)) | ||||
bap1 = (ufs1_daddr_t *)bp->b_data; | bap1 = (ufs1_daddr_t *)bp->b_data; | ||||
▲ Show 20 Lines • Show All 76 Lines • Show Last 20 Lines |