2018-06-06 10:42:14 +08:00
|
|
|
// SPDX-License-Identifier: GPL-2.0
|
2008-10-30 14:06:18 +08:00
|
|
|
/*
|
|
|
|
* Copyright (c) 2000-2006 Silicon Graphics, Inc.
|
|
|
|
* All Rights Reserved.
|
|
|
|
*/
|
2008-10-30 14:06:08 +08:00
|
|
|
#ifndef XFS_SYNC_H
|
|
|
|
#define XFS_SYNC_H 1
|
|
|
|
|
2008-10-30 14:06:18 +08:00
|
|
|
struct xfs_mount;
|
2009-02-09 15:47:34 +08:00
|
|
|
struct xfs_perag;
|
2008-10-30 14:06:18 +08:00
|
|
|
|
2021-06-08 00:34:51 +08:00
|
|
|
struct xfs_icwalk {
|
|
|
|
__u32 icw_flags;
|
|
|
|
kuid_t icw_uid;
|
|
|
|
kgid_t icw_gid;
|
|
|
|
prid_t icw_prid;
|
|
|
|
__u64 icw_min_file_size;
|
2021-06-19 02:57:06 +08:00
|
|
|
long icw_scan_limit;
|
2013-08-16 02:08:02 +08:00
|
|
|
};
|
|
|
|
|
2021-06-08 00:34:51 +08:00
|
|
|
/* Flags that reflect xfs_fs_eofblocks functionality. */
|
|
|
|
#define XFS_ICWALK_FLAG_SYNC (1U << 0) /* sync/wait mode scan */
|
|
|
|
#define XFS_ICWALK_FLAG_UID (1U << 1) /* filter by uid */
|
|
|
|
#define XFS_ICWALK_FLAG_GID (1U << 2) /* filter by gid */
|
|
|
|
#define XFS_ICWALK_FLAG_PRID (1U << 3) /* filter by project id */
|
|
|
|
#define XFS_ICWALK_FLAG_MINFILESIZE (1U << 4) /* filter by min file size */
|
|
|
|
|
|
|
|
#define XFS_ICWALK_FLAGS_VALID (XFS_ICWALK_FLAG_SYNC | \
|
|
|
|
XFS_ICWALK_FLAG_UID | \
|
|
|
|
XFS_ICWALK_FLAG_GID | \
|
|
|
|
XFS_ICWALK_FLAG_PRID | \
|
|
|
|
XFS_ICWALK_FLAG_MINFILESIZE)
|
|
|
|
|
2013-08-12 18:49:34 +08:00
|
|
|
/*
|
|
|
|
* Flags for xfs_iget()
|
|
|
|
*/
|
|
|
|
#define XFS_IGET_CREATE 0x1
|
|
|
|
#define XFS_IGET_UNTRUSTED 0x2
|
|
|
|
#define XFS_IGET_DONTCACHE 0x4
|
2017-06-19 23:58:56 +08:00
|
|
|
#define XFS_IGET_INCORE 0x8 /* don't read from disk or reinit */
|
2013-08-12 18:49:34 +08:00
|
|
|
|
2012-10-08 18:56:11 +08:00
|
|
|
int xfs_iget(struct xfs_mount *mp, struct xfs_trans *tp, xfs_ino_t ino,
|
|
|
|
uint flags, uint lock_flags, xfs_inode_t **ipp);
|
|
|
|
|
xfs: recovery of swap extents operations for CRC filesystems
This is the recovery side of the btree block owner change operation
performed by swapext on CRC enabled filesystems. We detect that an
owner change is needed by the flag that has been placed on the inode
log format flag field. Because the inode recovery is being replayed
after the buffers that make up the BMBT in the given checkpoint, we
can walk all the buffers and directly modify them when we see the
flag set on an inode.
Because the inode can be relogged and hence present in multiple
chekpoints with the "change owner" flag set, we could do multiple
passes across the inode to do this change. While this isn't optimal,
we can't directly ignore the flag as there may be multiple
independent swap extent operations being replayed on the same inode
in different checkpoints so we can't ignore them.
Further, because the owner change operation uses ordered buffers, we
might have buffers that are newer on disk than the current
checkpoint and so already have the owner changed in them. Hence we
cannot just peek at a buffer in the tree and check that it has the
correct owner and assume that the change was completed.
So, for the moment just brute force the owner change every time we
see an inode with the flag set. Note that we have to be careful here
because the owner of the buffers may point to either the old owner
or the new owner. Currently the verifier can't verify the owner
directly, so there is no failure case here right now. If we verify
the owner exactly in future, then we'll have to take this into
account.
This was tested in terms of normal operation via xfstests - all of
the fsr tests now pass without failure. however, we really need to
modify xfs/227 to stress v3 inodes correctly to ensure we fully
cover this case for v5 filesystems.
In terms of recovery testing, I used a hacked version of xfs_fsr
that held the temp inode open for a few seconds before exiting so
that the filesystem could be shut down with an open owner change
recovery flags set on at least the temp inode. fsr leaves the temp
inode unlinked and in btree format, so this was necessary for the
owner change to be reliably replayed.
logprint confirmed the tmp inode in the log had the correct flag set:
INO: cnt:3 total:3 a:0x69e9e0 len:56 a:0x69ea20 len:176 a:0x69eae0 len:88
INODE: #regs:3 ino:0x44 flags:0x209 dsize:88
^^^^^
0x200 is set, indicating a data fork owner change needed to be
replayed on inode 0x44. A printk in the revoery code confirmed that
the inode change was recovered:
XFS (vdc): Mounting Filesystem
XFS (vdc): Starting recovery (logdev: internal)
recovering owner change ino 0x44
XFS (vdc): Version 5 superblock detected. This kernel L support enabled!
Use of these features in this kernel is at your own risk!
XFS (vdc): Ending recovery (logdev: internal)
The script used to test this was:
$ cat ./recovery-fsr.sh
#!/bin/bash
dev=/dev/vdc
mntpt=/mnt/scratch
testfile=$mntpt/testfile
umount $mntpt
mkfs.xfs -f -m crc=1 $dev
mount $dev $mntpt
chmod 777 $mntpt
for i in `seq 10000 -1 0`; do
xfs_io -f -d -c "pwrite $(($i * 4096)) 4096" $testfile > /dev/null 2>&1
done
xfs_bmap -vp $testfile |head -20
xfs_fsr -d -v $testfile &
sleep 10
/home/dave/src/xfstests-dev/src/godown -f $mntpt
wait
umount $mntpt
xfs_logprint -t $dev |tail -20
time mount $dev $mntpt
xfs_bmap -vp $testfile
umount $mntpt
$
Signed-off-by: Dave Chinner <dchinner@redhat.com>
Reviewed-by: Mark Tinguely <tinguely@sgi.com>
Signed-off-by: Ben Myers <bpm@sgi.com>
2013-08-30 08:23:45 +08:00
|
|
|
/* recovery needs direct inode allocation capability */
|
|
|
|
struct xfs_inode * xfs_inode_alloc(struct xfs_mount *mp, xfs_ino_t ino);
|
|
|
|
void xfs_inode_free(struct xfs_inode *ip);
|
|
|
|
|
2012-10-08 18:55:59 +08:00
|
|
|
void xfs_reclaim_worker(struct work_struct *work);
|
2008-10-30 14:06:18 +08:00
|
|
|
|
2020-07-02 01:21:28 +08:00
|
|
|
void xfs_reclaim_inodes(struct xfs_mount *mp);
|
2021-06-19 02:57:06 +08:00
|
|
|
long xfs_reclaim_inodes_count(struct xfs_mount *mp);
|
|
|
|
long xfs_reclaim_inodes_nr(struct xfs_mount *mp, unsigned long nr_to_scan);
|
2008-10-30 14:37:03 +08:00
|
|
|
|
2021-06-01 02:32:02 +08:00
|
|
|
void xfs_inode_mark_reclaimable(struct xfs_inode *ip);
|
2009-06-08 21:35:27 +08:00
|
|
|
|
2021-01-23 08:48:37 +08:00
|
|
|
int xfs_blockgc_free_dquots(struct xfs_mount *mp, struct xfs_dquot *udqp,
|
|
|
|
struct xfs_dquot *gdqp, struct xfs_dquot *pdqp,
|
2021-06-08 00:34:51 +08:00
|
|
|
unsigned int iwalk_flags);
|
|
|
|
int xfs_blockgc_free_quota(struct xfs_inode *ip, unsigned int iwalk_flags);
|
2021-06-08 00:34:51 +08:00
|
|
|
int xfs_blockgc_free_space(struct xfs_mount *mp, struct xfs_icwalk *icm);
|
2021-08-07 02:05:42 +08:00
|
|
|
void xfs_blockgc_flush_all(struct xfs_mount *mp);
|
2021-01-23 08:48:34 +08:00
|
|
|
|
2012-11-06 22:50:38 +08:00
|
|
|
void xfs_inode_set_eofblocks_tag(struct xfs_inode *ip);
|
|
|
|
void xfs_inode_clear_eofblocks_tag(struct xfs_inode *ip);
|
|
|
|
|
2016-10-04 00:11:46 +08:00
|
|
|
void xfs_inode_set_cowblocks_tag(struct xfs_inode *ip);
|
|
|
|
void xfs_inode_clear_cowblocks_tag(struct xfs_inode *ip);
|
2021-01-23 08:48:43 +08:00
|
|
|
|
|
|
|
void xfs_blockgc_worker(struct work_struct *work);
|
2016-10-04 00:11:46 +08:00
|
|
|
|
2017-06-19 23:58:56 +08:00
|
|
|
int xfs_icache_inode_is_allocated(struct xfs_mount *mp, struct xfs_trans *tp,
|
|
|
|
xfs_ino_t ino, bool *inuse);
|
|
|
|
|
2021-01-23 08:48:44 +08:00
|
|
|
void xfs_blockgc_stop(struct xfs_mount *mp);
|
|
|
|
void xfs_blockgc_start(struct xfs_mount *mp);
|
2018-05-10 01:03:56 +08:00
|
|
|
|
2021-08-07 02:05:39 +08:00
|
|
|
void xfs_inodegc_worker(struct work_struct *work);
|
|
|
|
void xfs_inodegc_flush(struct xfs_mount *mp);
|
|
|
|
void xfs_inodegc_stop(struct xfs_mount *mp);
|
|
|
|
void xfs_inodegc_start(struct xfs_mount *mp);
|
|
|
|
void xfs_inodegc_cpu_dead(struct xfs_mount *mp, unsigned int cpu);
|
2021-08-07 02:05:43 +08:00
|
|
|
int xfs_inodegc_register_shrinker(struct xfs_mount *mp);
|
2021-08-07 02:05:39 +08:00
|
|
|
|
2008-10-30 14:06:08 +08:00
|
|
|
#endif
|