lists.openwall.net   lists  /  announce  owl-users  owl-dev  john-users  john-dev  passwdqc-users  yescrypt  popa3d-users  /  oss-security  kernel-hardening  musl  sabotage  tlsify  passwords  /  crypt-dev  xvendor  /  Bugtraq  Full-Disclosure  linux-kernel  linux-netdev  linux-ext4  linux-hardening  linux-cve-announce  PHC 
Open Source and information security mailing list archives
 
Hash Suite: Windows password security audit tool. GUI, reports in PDF.
[<prev] [next>] [<thread-prev] [thread-next>] [day] [month] [year] [list]
Message-ID: <20180818153518.GB84798@jaegeuk-macbookpro.roam.corp.google.com>
Date:   Sat, 18 Aug 2018 08:35:18 -0700
From:   Jaegeuk Kim <jaegeuk@...nel.org>
To:     Chao Yu <yuchao0@...wei.com>
Cc:     linux-f2fs-devel@...ts.sourceforge.net,
        linux-kernel@...r.kernel.org, chao@...nel.org,
        Weichao Guo <guoweichao@...wei.com>
Subject: Re: [PATCH 2/2] f2fs: guarantee journalled quota data by checkpoint

On 08/17, Chao Yu wrote:
> For journalled quota mode, let checkpoint to flush dquot dirty data
> and quota file data to keep all file quota info are consisting in
> last checkpoint, so that we can avoid quota file being corrupted
> after SPO.

This breaks fault injection + shutdown loop like below.

[736914.430526] WARNING: CPU: 1 PID: 22233 at fs/quota/dquot.c:626 dquot_writeback_dquots+0x27d/0x290
[736914.434605] Modules linked in: f2fs(OE) quota_v2 quota_tree brd sb_edac crct10dif_pclmul crc32_pclmul ghash_clmulni_intel pcbc aesni_intel aes_x86_64 crypto_simd cryptd glue_helper vmw_balloon intel_rapl_perf joydev input_leds serio_raw i2c_piix4 mac_hid vmw_vsock_vmci_transport vsock vmw_vmci ip_tables x_tables autofs4 vmwgfx ttm drm_kms_helper syscopyarea mptspi sysfillrect mptscsih sysimgblt mptbase fb_sys_fops psmouse pata_acpi scsi_transport_spi ahci drm e1000 libahci [last unloaded: f2fs]
[736914.450269] CPU: 1 PID: 22233 Comm: fsstress Tainted: G        W  OE     4.18.0-rc3+ #5
[736914.453262] Hardware name: VMware, Inc. VMware Virtual Platform/440BX Desktop Reference Platform, BIOS 6.00 05/19/2017
[736914.457537] RIP: 0010:dquot_writeback_dquots+0x27d/0x290
[736914.459664] Code: 4d 89 7f 08 4c 89 f7 e8 51 17 70 00 8b 54 24 0c e9 e2 fe ff ff 0f 0b e9 7d fe ff ff 0f 0b e9 67 fe ff ff 0f 0b e9 51 fe ff ff <0f> 0b e9 a2 fd ff ff 66 90 66 2e 0f 1f 84 00 00 00 00 00 0f 1f 44
[736914.467064] RSP: 0018:ffffb1f20111bb40 EFLAGS: 00010246
[736914.469132] RAX: 0000000000000000 RBX: ffff8e93f284a000 RCX: 0000000000000000
[736914.471581] RDX: ffffb1f20111bbf0 RSI: 00000000ffffffff RDI: ffff8e93f0674000
[736914.474043] RBP: ffff8e93f0674000 R08: ffffffffc06a9aa0 R09: 0000000000000000
[736914.476470] R10: ffffb1f20111bcc0 R11: 0000000000000000 R12: 00000000ffffffff
[736914.479092] R13: ffff8e93f0674000 R14: 0000000000000001 R15: ffff8e93f0674000
[736914.481765] FS:  00007f2b98aa3b80(0000) GS:ffff8e93f9640000(0000) knlGS:0000000000000000
[736914.484568] CS:  0010 DS: 0000 ES: 0000 CR0: 0000000080050033
[736914.486713] CR2: 00007f2b98aa2000 CR3: 0000000131c3c001 CR4: 00000000003606e0
[736914.489213] DR0: 0000000000000000 DR1: 0000000000000000 DR2: 0000000000000000
[736914.491660] DR3: 0000000000000000 DR6: 00000000fffe0ff0 DR7: 0000000000000400
[736914.494085] Call Trace:
[736914.495365]  f2fs_quota_sync+0x1a/0xd0 [f2fs]
[736914.497054]  block_operations+0x94/0x2c0 [f2fs]
[736914.499032]  ? f2fs_write_checkpoint+0x50/0x11e0 [f2fs]
[736914.500897]  ? f2fs_write_checkpoint+0xbb/0x11e0 [f2fs]
[736914.502770]  f2fs_write_checkpoint+0xbb/0x11e0 [f2fs]
[736914.504580]  ? f2fs_sync_fs+0xb0/0x1f0 [f2fs]
[736914.506252]  ? __mutex_lock+0x7f/0xa10
[736914.507710]  ? f2fs_sync_fs+0xb0/0x1f0 [f2fs]
[736914.509333]  ? pagevec_lookup_range_tag+0x24/0x30
[736914.510989]  ? __filemap_fdatawait_range+0x7d/0x150
[736914.512724]  f2fs_sync_fs+0xbd/0x1f0 [f2fs]
[736914.514344]  f2fs_do_sync_file+0x196/0xa30 [f2fs]
[736914.515995]  do_fsync+0x38/0x60
[736914.517289]  __x64_sys_fdatasync+0x13/0x20
[736914.518912]  do_syscall_64+0x60/0x1b0
[736914.520398]  entry_SYSCALL_64_after_hwframe+0x49/0xbe
...
[736920.063443] BUG: unable to handle kernel paging request at ffffffffd9c019eb
[736920.066262] PGD 78414067 P4D 78414067 PUD 78416067 PMD 0 
[736920.068403] Oops: 0000 [#1] SMP PTI
[736920.070055] CPU: 2 PID: 22236 Comm: fsstress Tainted: G        W  OE     4.18.0-rc3+ #5
[736920.072792] Hardware name: VMware, Inc. VMware Virtual Platform/440BX Desktop Reference Platform, BIOS 6.00 05/19/2017
[736920.076756] RIP: 0010:do_raw_spin_lock+0x6/0xc0
[736920.078644] Code: 49 89 f9 48 c7 c7 c8 8b ee b3 65 8b 15 13 c0 30 4d e8 2c 00 01 00 e9 5e 50 92 00 66 0f 1f 84 00 00 00 00 00 0f 1f 44 00 00 53 <81> 7f 04 ad 4e ad de 48 89 fb 75 43 65 48 8b 04 25 c0 5d 01 00 48 
[736920.085417] RSP: 0018:ffffb1f20128fbc8 EFLAGS: 00010286
[736920.087505] RAX: ffffffffb2f4a1d3 RBX: ffffffffd9c01927 RCX: 0000000000000000
[736920.090068] RDX: 0000000000000001 RSI: 0000000000000000 RDI: ffffffffd9c019e7
[736920.092589] RBP: 0000000000000001 R08: ffffffffb2f4a1d3 R09: 0000000000000000
[736920.095009] R10: ffffb1f20128fb58 R11: 0000000000000000 R12: ffffb1f20128fc58
[736920.097437] R13: ffffffffd9c019e7 R14: 0000000000000000 R15: ffff8e934fe29788
[736920.099823] FS:  00007f2b98aa3b80(0000) GS:ffff8e93f9680000(0000) knlGS:0000000000000000
[736920.102469] CS:  0010 DS: 0000 ES: 0000 CR0: 0000000080050033
[736920.104569] CR2: ffffffffd9c019eb CR3: 00000001282dc002 CR4: 00000000003606e0
[736920.107140] DR0: 0000000000000000 DR1: 0000000000000000 DR2: 0000000000000000
[736920.109517] DR3: 0000000000000000 DR6: 00000000fffe0ff0 DR7: 0000000000000400
[736920.111845] Call Trace:
[736920.113111]  dquot_add_inodes+0x23/0x1a0
[736920.114665]  __dquot_transfer+0x3d6/0x5f0
[736920.116233]  ? lock_acquire+0xb4/0x220
[736920.117718]  ? dqput.part.14+0x35/0x200
[736920.119212]  ? online_pages+0x1a0/0x2d0
[736920.120699]  ? dqget+0x424/0x490
[736920.122038]  dquot_transfer+0xce/0x150
[736920.123500]  f2fs_setattr+0xba/0x420 [f2fs]
[736920.125138]  ? current_time+0x4d/0x90
[736920.126676]  notify_change+0x2eb/0x440
[736920.128117]  chown_common+0x1ac/0x1d0
[736920.129670]  do_fchownat+0xc7/0xe0
[736920.131070]  __x64_sys_lchown+0x21/0x30
[736920.132559]  do_syscall_64+0x60/0x1b0
[736920.134011]  entry_SYSCALL_64_after_hwframe+0x49/0xbe
[736920.135699] RIP: 0033:0x7f2b97f893a7

> 
> Signed-off-by: Weichao Guo <guoweichao@...wei.com>
> Signed-off-by: Chao Yu <yuchao0@...wei.com>
> ---
>  fs/f2fs/checkpoint.c | 12 ++++++++
>  fs/f2fs/data.c       |  4 ++-
>  fs/f2fs/f2fs.h       |  2 ++
>  fs/f2fs/super.c      | 67 ++++++++++++++++++++++++++++++++++++++++----
>  4 files changed, 78 insertions(+), 7 deletions(-)
> 
> diff --git a/fs/f2fs/checkpoint.c b/fs/f2fs/checkpoint.c
> index 0274446f585e..cf8d1bb8ec3e 100644
> --- a/fs/f2fs/checkpoint.c
> +++ b/fs/f2fs/checkpoint.c
> @@ -1100,7 +1100,19 @@ static int block_operations(struct f2fs_sb_info *sbi)
>  	blk_start_plug(&plug);
>  
>  retry_flush_dents:
> +	if (is_sbi_flag_set(sbi, SBI_NEED_FLUSH_QUOTA)) {
> +		clear_sbi_flag(sbi, SBI_NEED_FLUSH_QUOTA);
> +		err = f2fs_quota_sync(sbi->sb, -1);
> +		if (err)
> +			goto out;
> +	}
> +
>  	f2fs_lock_all(sbi);
> +	if (is_sbi_flag_set(sbi, SBI_NEED_FLUSH_QUOTA)) {
> +		f2fs_unlock_all(sbi);
> +		goto retry_flush_dents;
> +	}
> +
>  	/* write all the dirty dentry pages */
>  	if (get_pages(sbi, F2FS_DIRTY_DENTS)) {
>  		f2fs_unlock_all(sbi);
> diff --git a/fs/f2fs/data.c b/fs/f2fs/data.c
> index 8e754710c746..0bfb10cd9ad2 100644
> --- a/fs/f2fs/data.c
> +++ b/fs/f2fs/data.c
> @@ -49,7 +49,7 @@ static bool __is_cp_guaranteed(struct page *page)
>  			inode->i_ino ==  F2FS_NODE_INO(sbi) ||
>  			S_ISDIR(inode->i_mode) ||
>  			(S_ISREG(inode->i_mode) &&
> -			is_inode_flag_set(inode, FI_ATOMIC_FILE)) ||
> +			(f2fs_is_atomic_file(inode) || IS_NOQUOTA(inode))) ||
>  			is_cold_data(page))
>  		return true;
>  	return false;
> @@ -1721,6 +1721,8 @@ bool f2fs_should_update_outplace(struct inode *inode, struct f2fs_io_info *fio)
>  	}
>  	if (S_ISDIR(inode->i_mode))
>  		return true;
> +	if (IS_NOQUOTA(inode))
> +		return true;
>  	if (f2fs_is_atomic_file(inode))
>  		return true;
>  	if (fio) {
> diff --git a/fs/f2fs/f2fs.h b/fs/f2fs/f2fs.h
> index 54ee8217092e..b7ba5aaeb61e 100644
> --- a/fs/f2fs/f2fs.h
> +++ b/fs/f2fs/f2fs.h
> @@ -1093,6 +1093,7 @@ enum {
>  	SBI_NEED_CP,				/* need to checkpoint */
>  	SBI_IS_SHUTDOWN,			/* shutdown by ioctl */
>  	SBI_CP_DISABLED,			/* CP was disabled last mount */
> +	SBI_NEED_FLUSH_QUOTA,			/* need to flush quota info in CP */
>  };
>  
>  enum {
> @@ -2888,6 +2889,7 @@ static inline int f2fs_add_link(struct dentry *dentry, struct inode *inode)
>  int f2fs_inode_dirtied(struct inode *inode, bool sync);
>  void f2fs_inode_synced(struct inode *inode);
>  int f2fs_enable_quota_files(struct f2fs_sb_info *sbi, bool rdonly);
> +int f2fs_quota_sync(struct super_block *sb, int type);
>  void f2fs_quota_off_umount(struct super_block *sb);
>  int f2fs_commit_super(struct f2fs_sb_info *sbi, bool recover);
>  int f2fs_sync_fs(struct super_block *sb, int sync);
> diff --git a/fs/f2fs/super.c b/fs/f2fs/super.c
> index 9647bbcdfd2b..f1482363b4eb 100644
> --- a/fs/f2fs/super.c
> +++ b/fs/f2fs/super.c
> @@ -1886,7 +1886,7 @@ static int f2fs_enable_quotas(struct super_block *sb)
>  	return 0;
>  }
>  
> -static int f2fs_quota_sync(struct super_block *sb, int type)
> +int f2fs_quota_sync(struct super_block *sb, int type)
>  {
>  	struct quota_info *dqopt = sb_dqopt(sb);
>  	int cnt;
> @@ -1988,6 +1988,61 @@ void f2fs_quota_off_umount(struct super_block *sb)
>  	}
>  }
>  
> +static int f2fs_dquot_commit(struct dquot *dquot)
> +{
> +	int ret;
> +
> +	ret = dquot_commit(dquot);
> +	if (ret == -ENOSPC || ret == -EIO)
> +		set_sbi_flag(F2FS_SB(dquot->dq_sb), SBI_NEED_FSCK);
> +	return ret;
> +}
> +
> +static int f2fs_dquot_acquire(struct dquot *dquot)
> +{
> +	int ret;
> +
> +	ret = dquot_acquire(dquot);
> +	if (ret == -ENOSPC || ret == -EIO)
> +		set_sbi_flag(F2FS_SB(dquot->dq_sb), SBI_NEED_FSCK);
> +	return ret;
> +}
> +
> +static int f2fs_dquot_release(struct dquot *dquot)
> +{
> +	int ret;
> +
> +	ret = dquot_release(dquot);
> +	if (ret == -ENOSPC || ret == -EIO)
> +		set_sbi_flag(F2FS_SB(dquot->dq_sb), SBI_NEED_FSCK);
> +	return ret;
> +}
> +
> +static int f2fs_dquot_mark_dquot_dirty(struct dquot *dquot)
> +{
> +	struct super_block *sb = dquot->dq_sb;
> +	struct f2fs_sb_info *sbi = F2FS_SB(sb);
> +
> +	/* if we are using journalled quota */
> +	if (f2fs_sb_has_quota_ino(sbi) ||
> +		F2FS_OPTION(sbi).s_qf_names[USRQUOTA] ||
> +		F2FS_OPTION(sbi).s_qf_names[GRPQUOTA] ||
> +		F2FS_OPTION(sbi).s_qf_names[PRJQUOTA])
> +		set_sbi_flag(sbi, SBI_NEED_FLUSH_QUOTA);
> +
> +	return dquot_mark_dquot_dirty(dquot);
> +}
> +
> +static int f2fs_dquot_commit_info(struct super_block *sb, int type)
> +{
> +	int ret;
> +
> +	ret = dquot_commit_info(sb, type);
> +	if (ret == -ENOSPC || ret == -EIO)
> +		set_sbi_flag(F2FS_SB(sb), SBI_NEED_FSCK);
> +	return ret;
> +}
> +
>  static int f2fs_get_projid(struct inode *inode, kprojid_t *projid)
>  {
>  	*projid = F2FS_I(inode)->i_projid;
> @@ -1996,11 +2051,11 @@ static int f2fs_get_projid(struct inode *inode, kprojid_t *projid)
>  
>  static const struct dquot_operations f2fs_quota_operations = {
>  	.get_reserved_space = f2fs_get_reserved_space,
> -	.write_dquot	= dquot_commit,
> -	.acquire_dquot	= dquot_acquire,
> -	.release_dquot	= dquot_release,
> -	.mark_dirty	= dquot_mark_dquot_dirty,
> -	.write_info	= dquot_commit_info,
> +	.write_dquot	= f2fs_dquot_commit,
> +	.acquire_dquot	= f2fs_dquot_acquire,
> +	.release_dquot	= f2fs_dquot_release,
> +	.mark_dirty	= f2fs_dquot_mark_dquot_dirty,
> +	.write_info	= f2fs_dquot_commit_info,
>  	.alloc_dquot	= dquot_alloc,
>  	.destroy_dquot	= dquot_destroy,
>  	.get_projid	= f2fs_get_projid,
> -- 
> 2.18.0.rc1

Powered by blists - more mailing lists

Powered by Openwall GNU/*/Linux Powered by OpenVZ