From nobody Wed Feb 11 16:19:07 2026 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.4.0 (2014-02-07) on aws-us-west-2-korg-lkml-1.web.codeaurora.org Received: from vger.kernel.org (vger.kernel.org [23.128.96.18]) by smtp.lore.kernel.org (Postfix) with ESMTP id E95C8C77B75 for ; Mon, 8 May 2023 12:37:49 +0000 (UTC) Received: (majordomo@vger.kernel.org) by vger.kernel.org via listexpand id S234212AbjEHMhs (ORCPT ); Mon, 8 May 2023 08:37:48 -0400 Received: from lindbergh.monkeyblade.net ([23.128.96.19]:38526 "EHLO lindbergh.monkeyblade.net" rhost-flags-OK-OK-OK-OK) by vger.kernel.org with ESMTP id S232949AbjEHMhp (ORCPT ); Mon, 8 May 2023 08:37:45 -0400 Received: from relayaws-01.paragon-software.com (relayaws-01.paragon-software.com [35.157.23.187]) by lindbergh.monkeyblade.net (Postfix) with ESMTPS id 6881B1FCF; Mon, 8 May 2023 05:37:43 -0700 (PDT) Received: from relayfre-01.paragon-software.com (unknown [172.30.72.12]) by relayaws-01.paragon-software.com (Postfix) with ESMTPS id D959E21C3; Mon, 8 May 2023 12:32:54 +0000 (UTC) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=paragon-software.com; s=mail; t=1683549174; bh=eUdOqgEPzuhDm6m+TY/pQxrmqpwlAoPXqQwZwQwVKkY=; h=Date:Subject:From:To:CC:References:In-Reply-To; b=YxxnbcMTWh4mPw9jfZnz2qtaaE5AKm89YFCKlmka7B2ABUXDCnuRFM+YZRqEYPRRA cjSDow7lrBVbtKBfUaGg6r9QQgVja4CER6+m7RwDrYrb6lc3E8YQmp7oDGtTUe4JdN EbncVRwCMDXO4mpXEVRPLmhqOayU70+JZ3EPAIyQ= Received: from dlg2.mail.paragon-software.com (vdlg-exch-02.paragon-software.com [172.30.1.105]) by relayfre-01.paragon-software.com (Postfix) with ESMTPS id 861E12191; Mon, 8 May 2023 12:37:41 +0000 (UTC) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=paragon-software.com; s=mail; t=1683549461; bh=eUdOqgEPzuhDm6m+TY/pQxrmqpwlAoPXqQwZwQwVKkY=; h=Date:Subject:From:To:CC:References:In-Reply-To; b=HgClNu2/GVnhUC7bcq6YJjoYakmdbi9vxn15wOUXoU35l5qCHFF2DrDNHy/GYrLmW OHodTeo94tL3x8cqCKd5b9Zy3DB3h3RjybM69L7G6hC69mVW0rHEJxenUGWPCC5CjI Z6hXSAe5sajP2XzLMXRUZd3+9V4pu4NSS5C2i2xA= Received: from [192.168.211.146] (192.168.211.146) by vdlg-exch-02.paragon-software.com (172.30.1.105) with Microsoft SMTP Server (version=TLS1_2, cipher=TLS_ECDHE_RSA_WITH_AES_128_GCM_SHA256) id 15.1.2375.7; Mon, 8 May 2023 15:37:41 +0300 Message-ID: <24e18e44-b97b-b896-f1b0-0c7e58f23a1c@paragon-software.com> Date: Mon, 8 May 2023 16:37:40 +0400 MIME-Version: 1.0 User-Agent: Mozilla/5.0 (X11; Linux x86_64; rv:102.0) Gecko/20100101 Thunderbird/102.10.1 Subject: [PATCH 04/10] fs/ntfs3: Alternative boot if primary boot is corrupted Content-Language: en-US From: Konstantin Komarov To: CC: Linux Kernel Mailing List , References: In-Reply-To: Content-Type: text/plain; charset="utf-8"; format="flowed" Content-Transfer-Encoding: quoted-printable X-Originating-IP: [192.168.211.146] X-ClientProxiedBy: vobn-exch-01.paragon-software.com (172.30.72.13) To vdlg-exch-02.paragon-software.com (172.30.1.105) Precedence: bulk List-ID: X-Mailing-List: linux-kernel@vger.kernel.org Some code refactoring added also. Signed-off-by: Konstantin Komarov --- =C2=A0fs/ntfs3/super.c | 98 +++++++++++++++++++++++++++++++++++-----------= -- =C2=A01 file changed, 71 insertions(+), 27 deletions(-) diff --git a/fs/ntfs3/super.c b/fs/ntfs3/super.c index 5158dd31fd97..ecf899d571d8 100644 --- a/fs/ntfs3/super.c +++ b/fs/ntfs3/super.c @@ -724,6 +724,8 @@ static int ntfs_init_from_boot(struct super_block=20 *sb, u32 sector_size, =C2=A0=C2=A0=C2=A0 =C2=A0struct MFT_REC *rec; =C2=A0=C2=A0=C2=A0 =C2=A0u16 fn, ao; =C2=A0=C2=A0=C2=A0 =C2=A0u8 cluster_bits; +=C2=A0=C2=A0 =C2=A0u32 boot_off =3D 0; +=C2=A0=C2=A0 =C2=A0const char *hint =3D "Primary boot"; =C2=A0=C2=A0=C2=A0 =C2=A0sbi->volume.blocks =3D dev_size >> PAGE_SHIFT; @@ -731,11 +733,12 @@ static int ntfs_init_from_boot(struct super_block=20 *sb, u32 sector_size, =C2=A0=C2=A0=C2=A0 =C2=A0if (!bh) =C2=A0=C2=A0=C2=A0 =C2=A0=C2=A0=C2=A0 =C2=A0return -EIO; +check_boot: =C2=A0=C2=A0=C2=A0 =C2=A0err =3D -EINVAL; -=C2=A0=C2=A0 =C2=A0boot =3D (struct NTFS_BOOT *)bh->b_data; +=C2=A0=C2=A0 =C2=A0boot =3D (struct NTFS_BOOT *)Add2Ptr(bh->b_data, boot_o= ff); =C2=A0=C2=A0=C2=A0 =C2=A0if (memcmp(boot->system_id, "NTFS=C2=A0=C2=A0=C2= =A0 ", sizeof("NTFS=C2=A0=C2=A0=C2=A0 ") - 1)) { -=C2=A0=C2=A0 =C2=A0=C2=A0=C2=A0 =C2=A0ntfs_err(sb, "Boot's signature is no= t NTFS."); +=C2=A0=C2=A0 =C2=A0=C2=A0=C2=A0 =C2=A0ntfs_err(sb, "%s signature is not NT= FS.", hint); =C2=A0=C2=A0=C2=A0 =C2=A0=C2=A0=C2=A0 =C2=A0goto out; =C2=A0=C2=A0=C2=A0 =C2=A0} @@ -748,14 +751,16 @@ static int ntfs_init_from_boot(struct super_block=20 *sb, u32 sector_size, =C2=A0=C2=A0=C2=A0 =C2=A0=C2=A0=C2=A0 =C2=A0=C2=A0=C2=A0 =C2=A0=C2=A0=C2= =A0 boot->bytes_per_sector[0]; =C2=A0=C2=A0=C2=A0 =C2=A0if (boot_sector_size < SECTOR_SIZE || =C2=A0=C2=A0=C2=A0 =C2=A0=C2=A0=C2=A0=C2=A0 !is_power_of_2(boot_sector_siz= e)) { -=C2=A0=C2=A0 =C2=A0=C2=A0=C2=A0 =C2=A0ntfs_err(sb, "Invalid bytes per sect= or %u.", boot_sector_size); +=C2=A0=C2=A0 =C2=A0=C2=A0=C2=A0 =C2=A0ntfs_err(sb, "%s: invalid bytes per = sector %u.", hint, +=C2=A0=C2=A0 =C2=A0=C2=A0=C2=A0 =C2=A0=C2=A0=C2=A0 =C2=A0 boot_sector_size= ); =C2=A0=C2=A0=C2=A0 =C2=A0=C2=A0=C2=A0 =C2=A0goto out; =C2=A0=C2=A0=C2=A0 =C2=A0} =C2=A0=C2=A0=C2=A0 =C2=A0/* cluster size: 512, 1K, 2K, 4K, ... 2M */ =C2=A0=C2=A0=C2=A0 =C2=A0sct_per_clst =3D true_sectors_per_clst(boot); =C2=A0=C2=A0=C2=A0 =C2=A0if ((int)sct_per_clst < 0 || !is_power_of_2(sct_p= er_clst)) { -=C2=A0=C2=A0 =C2=A0=C2=A0=C2=A0 =C2=A0ntfs_err(sb, "Invalid sectors per cl= uster %u.", sct_per_clst); +=C2=A0=C2=A0 =C2=A0=C2=A0=C2=A0 =C2=A0ntfs_err(sb, "%s: invalid sectors pe= r cluster %u.", hint, +=C2=A0=C2=A0 =C2=A0=C2=A0=C2=A0 =C2=A0=C2=A0=C2=A0 =C2=A0 sct_per_clst); =C2=A0=C2=A0=C2=A0 =C2=A0=C2=A0=C2=A0 =C2=A0goto out; =C2=A0=C2=A0=C2=A0 =C2=A0} @@ -771,8 +776,8 @@ static int ntfs_init_from_boot(struct super_block=20 *sb, u32 sector_size, =C2=A0=C2=A0=C2=A0 =C2=A0if (mlcn * sct_per_clst >=3D sectors || mlcn2 * s= ct_per_clst >=3D=20 sectors) { =C2=A0=C2=A0=C2=A0 =C2=A0=C2=A0=C2=A0 =C2=A0ntfs_err( =C2=A0=C2=A0=C2=A0 =C2=A0=C2=A0=C2=A0 =C2=A0=C2=A0=C2=A0 =C2=A0sb, -=C2=A0=C2=A0 =C2=A0=C2=A0=C2=A0 =C2=A0=C2=A0=C2=A0 =C2=A0"Start of MFT 0x%= llx (0x%llx) is out of volume 0x%llx.", -=C2=A0=C2=A0 =C2=A0=C2=A0=C2=A0 =C2=A0=C2=A0=C2=A0 =C2=A0mlcn, mlcn2, sect= ors); +=C2=A0=C2=A0 =C2=A0=C2=A0=C2=A0 =C2=A0=C2=A0=C2=A0 =C2=A0"%s: start of MFT= 0x%llx (0x%llx) is out of volume 0x%llx.", +=C2=A0=C2=A0 =C2=A0=C2=A0=C2=A0 =C2=A0=C2=A0=C2=A0 =C2=A0hint, mlcn, mlcn2= , sectors); =C2=A0=C2=A0=C2=A0 =C2=A0=C2=A0=C2=A0 =C2=A0goto out; =C2=A0=C2=A0=C2=A0 =C2=A0} @@ -784,7 +789,7 @@ static int ntfs_init_from_boot(struct super_block=20 *sb, u32 sector_size, =C2=A0=C2=A0=C2=A0 =C2=A0/* Check MFT record size. */ =C2=A0=C2=A0=C2=A0 =C2=A0if (record_size < SECTOR_SIZE || !is_power_of_2(r= ecord_size)) { -=C2=A0=C2=A0 =C2=A0=C2=A0=C2=A0 =C2=A0ntfs_err(sb, "Invalid bytes per MFT = record %u (%d).", +=C2=A0=C2=A0 =C2=A0=C2=A0=C2=A0 =C2=A0ntfs_err(sb, "%s: invalid bytes per = MFT record %u (%d).", hint, =C2=A0=C2=A0=C2=A0 =C2=A0=C2=A0=C2=A0 =C2=A0=C2=A0=C2=A0 =C2=A0 record_siz= e, boot->record_size); =C2=A0=C2=A0=C2=A0 =C2=A0=C2=A0=C2=A0 =C2=A0goto out; =C2=A0=C2=A0=C2=A0 =C2=A0} @@ -801,13 +806,13 @@ static int ntfs_init_from_boot(struct super_block=20 *sb, u32 sector_size, =C2=A0=C2=A0=C2=A0 =C2=A0/* Check index record size. */ =C2=A0=C2=A0=C2=A0 =C2=A0if (sbi->index_size < SECTOR_SIZE ||=20 !is_power_of_2(sbi->index_size)) { -=C2=A0=C2=A0 =C2=A0=C2=A0=C2=A0 =C2=A0ntfs_err(sb, "Invalid bytes per inde= x %u(%d).", sbi->index_size, -=C2=A0=C2=A0 =C2=A0=C2=A0=C2=A0 =C2=A0=C2=A0=C2=A0 =C2=A0 boot->index_size= ); +=C2=A0=C2=A0 =C2=A0=C2=A0=C2=A0 =C2=A0ntfs_err(sb, "%s: invalid bytes per = index %u(%d).", hint, +=C2=A0=C2=A0 =C2=A0=C2=A0=C2=A0 =C2=A0=C2=A0=C2=A0 =C2=A0 sbi->index_size,= boot->index_size); =C2=A0=C2=A0=C2=A0 =C2=A0=C2=A0=C2=A0 =C2=A0goto out; =C2=A0=C2=A0=C2=A0 =C2=A0} =C2=A0=C2=A0=C2=A0 =C2=A0if (sbi->index_size > MAXIMUM_BYTES_PER_INDEX) { -=C2=A0=C2=A0 =C2=A0=C2=A0=C2=A0 =C2=A0ntfs_err(sb, "Unsupported bytes per = index %u.", +=C2=A0=C2=A0 =C2=A0=C2=A0=C2=A0 =C2=A0ntfs_err(sb, "%s: unsupported bytes = per index %u.", hint, =C2=A0=C2=A0=C2=A0 =C2=A0=C2=A0=C2=A0 =C2=A0=C2=A0=C2=A0 =C2=A0 sbi->index= _size); =C2=A0=C2=A0=C2=A0 =C2=A0=C2=A0=C2=A0 =C2=A0goto out; =C2=A0=C2=A0=C2=A0 =C2=A0} @@ -834,7 +839,7 @@ static int ntfs_init_from_boot(struct super_block=20 *sb, u32 sector_size, =C2=A0=C2=A0=C2=A0 =C2=A0/* Compare boot's cluster and sector. */ =C2=A0=C2=A0=C2=A0 =C2=A0if (sbi->cluster_size < boot_sector_size) { -=C2=A0=C2=A0 =C2=A0=C2=A0=C2=A0 =C2=A0ntfs_err(sb, "Invalid bytes per clus= ter (%u).", +=C2=A0=C2=A0 =C2=A0=C2=A0=C2=A0 =C2=A0ntfs_err(sb, "%s: invalid bytes per = cluster (%u).", hint, =C2=A0=C2=A0=C2=A0 =C2=A0=C2=A0=C2=A0 =C2=A0=C2=A0=C2=A0 =C2=A0 sbi->clust= er_size); =C2=A0=C2=A0=C2=A0 =C2=A0=C2=A0=C2=A0 =C2=A0goto out; =C2=A0=C2=A0=C2=A0 =C2=A0} @@ -930,7 +935,46 @@ static int ntfs_init_from_boot(struct super_block=20 *sb, u32 sector_size, =C2=A0=C2=A0=C2=A0 =C2=A0err =3D 0; +=C2=A0=C2=A0 =C2=A0if (bh->b_blocknr && !sb_rdonly(sb)) { +=C2=A0=C2=A0 =C2=A0=C2=A0=C2=A0 =C2=A0/* +=C2=A0=C2=A0 =C2=A0 =C2=A0=C2=A0 =C2=A0 * Alternative boot is ok but prima= ry is not ok. +=C2=A0=C2=A0 =C2=A0 =C2=A0=C2=A0 =C2=A0 * Update primary boot. +=C2=A0=C2=A0 =C2=A0=C2=A0=C2=A0 =C2=A0 */ +=C2=A0=C2=A0 =C2=A0=C2=A0=C2=A0 =C2=A0struct buffer_head *bh0 =3D sb_getbl= k(sb, 0); +=C2=A0=C2=A0 =C2=A0=C2=A0=C2=A0 =C2=A0if (bh0) { +=C2=A0=C2=A0 =C2=A0=C2=A0=C2=A0 =C2=A0=C2=A0=C2=A0 =C2=A0if (buffer_locked= (bh0)) +=C2=A0=C2=A0 =C2=A0=C2=A0=C2=A0 =C2=A0=C2=A0=C2=A0 =C2=A0=C2=A0=C2=A0 =C2= =A0__wait_on_buffer(bh0); + +=C2=A0=C2=A0 =C2=A0=C2=A0=C2=A0 =C2=A0=C2=A0=C2=A0 =C2=A0lock_buffer(bh0); +=C2=A0=C2=A0 =C2=A0=C2=A0=C2=A0 =C2=A0=C2=A0=C2=A0 =C2=A0memcpy(bh0->b_dat= a, boot, sizeof(*boot)); +=C2=A0=C2=A0 =C2=A0=C2=A0=C2=A0 =C2=A0=C2=A0=C2=A0 =C2=A0set_buffer_uptoda= te(bh0); +=C2=A0=C2=A0 =C2=A0=C2=A0=C2=A0 =C2=A0=C2=A0=C2=A0 =C2=A0mark_buffer_dirty= (bh0); +=C2=A0=C2=A0 =C2=A0=C2=A0=C2=A0 =C2=A0=C2=A0=C2=A0 =C2=A0unlock_buffer(bh0= ); +=C2=A0=C2=A0 =C2=A0=C2=A0=C2=A0 =C2=A0=C2=A0=C2=A0 =C2=A0if (!sync_dirty_b= uffer(bh0)) +=C2=A0=C2=A0 =C2=A0=C2=A0=C2=A0 =C2=A0=C2=A0=C2=A0 =C2=A0=C2=A0=C2=A0 =C2= =A0ntfs_warn(sb, "primary boot is updated"); +=C2=A0=C2=A0 =C2=A0=C2=A0=C2=A0 =C2=A0=C2=A0=C2=A0 =C2=A0put_bh(bh0); +=C2=A0=C2=A0 =C2=A0=C2=A0=C2=A0 =C2=A0} +=C2=A0=C2=A0 =C2=A0} + =C2=A0out: +=C2=A0=C2=A0 =C2=A0if (err =3D=3D -EINVAL && !bh->b_blocknr && dev_size > = PAGE_SHIFT) { +=C2=A0=C2=A0 =C2=A0=C2=A0=C2=A0 =C2=A0u32 block_size =3D min_t(u32, sector= _size, PAGE_SIZE); +=C2=A0=C2=A0 =C2=A0=C2=A0=C2=A0 =C2=A0u64 lbo =3D dev_size - sizeof(*boot); + +=C2=A0=C2=A0 =C2=A0=C2=A0=C2=A0 =C2=A0/* +=C2=A0=C2=A0 =C2=A0 =C2=A0=C2=A0 =C2=A0 * Try alternative boot (last secto= r) +=C2=A0=C2=A0 =C2=A0=C2=A0=C2=A0 =C2=A0 */ +=C2=A0=C2=A0 =C2=A0=C2=A0=C2=A0 =C2=A0brelse(bh); + +=C2=A0=C2=A0 =C2=A0=C2=A0=C2=A0 =C2=A0sb_set_blocksize(sb, block_size); +=C2=A0=C2=A0 =C2=A0=C2=A0=C2=A0 =C2=A0bh =3D ntfs_bread(sb, lbo >> blksize= _bits(block_size)); +=C2=A0=C2=A0 =C2=A0=C2=A0=C2=A0 =C2=A0if (!bh) +=C2=A0=C2=A0 =C2=A0=C2=A0=C2=A0 =C2=A0=C2=A0=C2=A0 =C2=A0return -EINVAL; + +=C2=A0=C2=A0 =C2=A0=C2=A0=C2=A0 =C2=A0boot_off =3D lbo & (block_size - 1); +=C2=A0=C2=A0 =C2=A0=C2=A0=C2=A0 =C2=A0hint =3D "Alternative boot"; +=C2=A0=C2=A0 =C2=A0=C2=A0=C2=A0 =C2=A0goto check_boot; +=C2=A0=C2=A0 =C2=A0} =C2=A0=C2=A0=C2=A0 =C2=A0brelse(bh); =C2=A0=C2=A0=C2=A0 =C2=A0return err; @@ -955,6 +999,7 @@ static int ntfs_fill_super(struct super_block *sb,=20 struct fs_context *fc) =C2=A0=C2=A0=C2=A0 =C2=A0struct ATTR_DEF_ENTRY *t; =C2=A0=C2=A0=C2=A0 =C2=A0u16 *shared; =C2=A0=C2=A0=C2=A0 =C2=A0struct MFT_REF ref; +=C2=A0=C2=A0 =C2=A0bool ro =3D sb_rdonly(sb); =C2=A0=C2=A0=C2=A0 =C2=A0ref.high =3D 0; @@ -1035,6 +1080,10 @@ static int ntfs_fill_super(struct super_block=20 *sb, struct fs_context *fc) =C2=A0=C2=A0=C2=A0 =C2=A0sbi->volume.minor_ver =3D info->minor_ver; =C2=A0=C2=A0=C2=A0 =C2=A0sbi->volume.flags =3D info->flags; =C2=A0=C2=A0=C2=A0 =C2=A0sbi->volume.ni =3D ni; +=C2=A0=C2=A0 =C2=A0if (info->flags & VOLUME_FLAG_DIRTY) { +=C2=A0=C2=A0 =C2=A0=C2=A0=C2=A0 =C2=A0sbi->volume.real_dirty =3D true; +=C2=A0=C2=A0 =C2=A0=C2=A0=C2=A0 =C2=A0ntfs_info(sb, "It is recommened to u= se chkdsk."); +=C2=A0=C2=A0 =C2=A0} =C2=A0=C2=A0=C2=A0 =C2=A0/* Load $MFTMirr to estimate recs_mirr. */ =C2=A0=C2=A0=C2=A0 =C2=A0ref.low =3D cpu_to_le32(MFT_REC_MIRR); @@ -1069,21 +1118,16 @@ static int ntfs_fill_super(struct super_block=20 *sb, struct fs_context *fc) =C2=A0=C2=A0=C2=A0 =C2=A0iput(inode); -=C2=A0=C2=A0 =C2=A0if (sbi->flags & NTFS_FLAGS_NEED_REPLAY) { -=C2=A0=C2=A0 =C2=A0=C2=A0=C2=A0 =C2=A0if (!sb_rdonly(sb)) { -=C2=A0=C2=A0 =C2=A0=C2=A0=C2=A0 =C2=A0=C2=A0=C2=A0 =C2=A0ntfs_warn(sb, -=C2=A0=C2=A0 =C2=A0=C2=A0=C2=A0 =C2=A0=C2=A0=C2=A0 =C2=A0=C2=A0=C2=A0 =C2= =A0=C2=A0 "failed to replay log file. Can't mount rw!"); -=C2=A0=C2=A0 =C2=A0=C2=A0=C2=A0 =C2=A0=C2=A0=C2=A0 =C2=A0err =3D -EINVAL; -=C2=A0=C2=A0 =C2=A0=C2=A0=C2=A0 =C2=A0=C2=A0=C2=A0 =C2=A0goto out; -=C2=A0=C2=A0 =C2=A0=C2=A0=C2=A0 =C2=A0} -=C2=A0=C2=A0 =C2=A0} else if (sbi->volume.flags & VOLUME_FLAG_DIRTY) { -=C2=A0=C2=A0 =C2=A0=C2=A0=C2=A0 =C2=A0if (!sb_rdonly(sb) && !options->forc= e) { -=C2=A0=C2=A0 =C2=A0=C2=A0=C2=A0 =C2=A0=C2=A0=C2=A0 =C2=A0ntfs_warn( -=C2=A0=C2=A0 =C2=A0=C2=A0=C2=A0 =C2=A0=C2=A0=C2=A0 =C2=A0=C2=A0=C2=A0 =C2= =A0sb, -=C2=A0=C2=A0 =C2=A0=C2=A0=C2=A0 =C2=A0=C2=A0=C2=A0 =C2=A0=C2=A0=C2=A0 =C2= =A0"volume is dirty and \"force\" flag is not set!"); -=C2=A0=C2=A0 =C2=A0=C2=A0=C2=A0 =C2=A0=C2=A0=C2=A0 =C2=A0err =3D -EINVAL; -=C2=A0=C2=A0 =C2=A0=C2=A0=C2=A0 =C2=A0=C2=A0=C2=A0 =C2=A0goto out; -=C2=A0=C2=A0 =C2=A0=C2=A0=C2=A0 =C2=A0} +=C2=A0=C2=A0 =C2=A0if ((sbi->flags & NTFS_FLAGS_NEED_REPLAY) && !ro) { +=C2=A0=C2=A0 =C2=A0=C2=A0=C2=A0 =C2=A0ntfs_warn(sb, "failed to replay log = file. Can't mount rw!"); +=C2=A0=C2=A0 =C2=A0=C2=A0=C2=A0 =C2=A0err =3D -EINVAL; +=C2=A0=C2=A0 =C2=A0=C2=A0=C2=A0 =C2=A0goto out; +=C2=A0=C2=A0 =C2=A0} + +=C2=A0=C2=A0 =C2=A0if ((sbi->volume.flags & VOLUME_FLAG_DIRTY) && !ro &&=20 !options->force) { +=C2=A0=C2=A0 =C2=A0=C2=A0=C2=A0 =C2=A0ntfs_warn(sb, "volume is dirty and \= "force\" flag is not set!"); +=C2=A0=C2=A0 =C2=A0=C2=A0=C2=A0 =C2=A0err =3D -EINVAL; +=C2=A0=C2=A0 =C2=A0=C2=A0=C2=A0 =C2=A0goto out; =C2=A0=C2=A0=C2=A0 =C2=A0} =C2=A0=C2=A0=C2=A0 =C2=A0/* Load $MFT. */ @@ -1173,7 +1217,7 @@ static int ntfs_fill_super(struct super_block *sb,=20 struct fs_context *fc) =C2=A0=C2=A0=C2=A0 =C2=A0=C2=A0=C2=A0 =C2=A0bad_len +=3D len; =C2=A0=C2=A0=C2=A0 =C2=A0=C2=A0=C2=A0 =C2=A0bad_frags +=3D 1; -=C2=A0=C2=A0 =C2=A0=C2=A0=C2=A0 =C2=A0if (sb_rdonly(sb)) +=C2=A0=C2=A0 =C2=A0=C2=A0=C2=A0 =C2=A0if (ro) =C2=A0=C2=A0=C2=A0 =C2=A0=C2=A0=C2=A0 =C2=A0=C2=A0=C2=A0 =C2=A0continue; =C2=A0=C2=A0=C2=A0 =C2=A0=C2=A0=C2=A0 =C2=A0if (wnd_set_used_safe(&sbi->us= ed.bitmap, lcn, len, &tt) || tt) { --=20 2.34.1