~daniel-mehrmann/e2fsprogs/master

« back to all changes in this revision

Viewing changes to e2fsck/pass5.c

  • Committer: Daniel Mehrmann
  • Date: 2014-12-16 09:16:59 UTC
  • mfrom: (1.2.25)
  • Revision ID: daniel.mehrmann@gmx.de-20141216091659-ymhbl4ualba43vuc
Tags: 1.43-SN-2014-12-16-0ubuntu1
* Merge in snapshot from the maint branch 

Show diffs side-by-side

added added

removed removed

Lines of Context:
27
27
static void check_inode_bitmaps(e2fsck_t ctx);
28
28
static void check_inode_end(e2fsck_t ctx);
29
29
static void check_block_end(e2fsck_t ctx);
 
30
static void check_inode_bitmap_checksum(e2fsck_t ctx);
 
31
static void check_block_bitmap_checksum(e2fsck_t ctx);
30
32
 
31
33
void e2fsck_pass5(e2fsck_t ctx)
32
34
{
64
66
        if (ctx->flags & E2F_FLAG_SIGNAL_MASK)
65
67
                return;
66
68
 
 
69
        check_inode_bitmap_checksum(ctx);
 
70
        check_block_bitmap_checksum(ctx);
 
71
 
67
72
        ext2fs_free_inode_bitmap(ctx->inode_used_map);
68
73
        ctx->inode_used_map = 0;
69
74
        ext2fs_free_inode_bitmap(ctx->inode_dir_map);
70
75
        ctx->inode_dir_map = 0;
71
76
        ext2fs_free_block_bitmap(ctx->block_found_map);
72
77
        ctx->block_found_map = 0;
 
78
        ext2fs_free_block_bitmap(ctx->block_metadata_map);
 
79
        ctx->block_metadata_map = 0;
73
80
 
74
81
        print_resource_track(ctx, _("Pass 5"), &rtrack, ctx->fs->io);
75
82
}
76
83
 
 
84
static void check_inode_bitmap_checksum(e2fsck_t ctx)
 
85
{
 
86
        struct problem_context  pctx;
 
87
        char            *buf = NULL;
 
88
        dgrp_t          i;
 
89
        int             nbytes;
 
90
        ext2_ino_t      ino_itr;
 
91
        errcode_t       retval;
 
92
 
 
93
        if (!EXT2_HAS_RO_COMPAT_FEATURE(ctx->fs->super,
 
94
                                        EXT4_FEATURE_RO_COMPAT_METADATA_CSUM))
 
95
                return;
 
96
 
 
97
        /* If bitmap is dirty from being fixed, checksum will be corrected */
 
98
        if (ext2fs_test_ib_dirty(ctx->fs))
 
99
                return;
 
100
 
 
101
        nbytes = (size_t)(EXT2_INODES_PER_GROUP(ctx->fs->super) / 8);
 
102
        retval = ext2fs_get_mem(ctx->fs->blocksize, &buf);
 
103
        if (retval) {
 
104
                com_err(ctx->program_name, 0, "%s",
 
105
                    _("check_inode_bitmap_checksum: Memory allocation error"));
 
106
                fatal_error(ctx, 0);
 
107
        }
 
108
 
 
109
        clear_problem_context(&pctx);
 
110
        for (i = 0; i < ctx->fs->group_desc_count; i++) {
 
111
                if (ext2fs_bg_flags_test(ctx->fs, i, EXT2_BG_INODE_UNINIT))
 
112
                        continue;
 
113
 
 
114
                ino_itr = 1 + (i * (nbytes << 3));
 
115
                retval = ext2fs_get_inode_bitmap_range2(ctx->fs->inode_map,
 
116
                                                        ino_itr, nbytes << 3,
 
117
                                                        buf);
 
118
                if (retval)
 
119
                        break;
 
120
 
 
121
                if (ext2fs_inode_bitmap_csum_verify(ctx->fs, i, buf, nbytes))
 
122
                        continue;
 
123
                pctx.group = i;
 
124
                if (!fix_problem(ctx, PR_5_INODE_BITMAP_CSUM_INVALID, &pctx))
 
125
                        continue;
 
126
 
 
127
                /*
 
128
                 * Fixing one checksum will rewrite all of them.  The bitmap
 
129
                 * will be checked against the one we made during pass1 for
 
130
                 * discrepancies, and fixed if need be.
 
131
                 */
 
132
                ext2fs_mark_ib_dirty(ctx->fs);
 
133
                break;
 
134
        }
 
135
 
 
136
        ext2fs_free_mem(&buf);
 
137
}
 
138
 
 
139
static void check_block_bitmap_checksum(e2fsck_t ctx)
 
140
{
 
141
        struct problem_context  pctx;
 
142
        char            *buf = NULL;
 
143
        dgrp_t          i;
 
144
        int             nbytes;
 
145
        blk64_t         blk_itr;
 
146
        errcode_t       retval;
 
147
 
 
148
        if (!EXT2_HAS_RO_COMPAT_FEATURE(ctx->fs->super,
 
149
                                        EXT4_FEATURE_RO_COMPAT_METADATA_CSUM))
 
150
                return;
 
151
 
 
152
        /* If bitmap is dirty from being fixed, checksum will be corrected */
 
153
        if (ext2fs_test_bb_dirty(ctx->fs))
 
154
                return;
 
155
 
 
156
        nbytes = (size_t)(EXT2_CLUSTERS_PER_GROUP(ctx->fs->super) / 8);
 
157
        retval = ext2fs_get_mem(ctx->fs->blocksize, &buf);
 
158
        if (retval) {
 
159
                com_err(ctx->program_name, 0, "%s",
 
160
                    _("check_block_bitmap_checksum: Memory allocation error"));
 
161
                fatal_error(ctx, 0);
 
162
        }
 
163
 
 
164
        clear_problem_context(&pctx);
 
165
        for (i = 0; i < ctx->fs->group_desc_count; i++) {
 
166
                if (ext2fs_bg_flags_test(ctx->fs, i, EXT2_BG_BLOCK_UNINIT))
 
167
                        continue;
 
168
 
 
169
                blk_itr = EXT2FS_B2C(ctx->fs,
 
170
                                     ctx->fs->super->s_first_data_block) +
 
171
                          ((blk64_t) i * (nbytes << 3));
 
172
                retval = ext2fs_get_block_bitmap_range2(ctx->fs->block_map,
 
173
                                                        blk_itr, nbytes << 3,
 
174
                                                        buf);
 
175
                if (retval)
 
176
                        break;
 
177
 
 
178
                if (ext2fs_block_bitmap_csum_verify(ctx->fs, i, buf, nbytes))
 
179
                        continue;
 
180
                pctx.group = i;
 
181
                if (!fix_problem(ctx, PR_5_BLOCK_BITMAP_CSUM_INVALID, &pctx))
 
182
                        continue;
 
183
 
 
184
                /*
 
185
                 * Fixing one checksum will rewrite all of them.  The bitmap
 
186
                 * will be checked against the one we made during pass1 for
 
187
                 * discrepancies, and fixed if need be.
 
188
                 */
 
189
                ext2fs_mark_bb_dirty(ctx->fs);
 
190
                break;
 
191
        }
 
192
 
 
193
        ext2fs_free_mem(&buf);
 
194
}
 
195
 
77
196
static void e2fsck_discard_blocks(e2fsck_t ctx, blk64_t start,
78
197
                                  blk64_t count)
79
198
{
206
325
        problem_t       problem, save_problem;
207
326
        int             fixit, had_problem;
208
327
        errcode_t       retval;
209
 
        int     old_desc_blocks = 0;
210
 
        int     count = 0;
211
 
        int     cmp_block = 0;
212
328
        int     redo_flag = 0;
213
 
        blk64_t super_blk, old_desc_blk, new_desc_blk;
214
329
        char *actual_buf, *bitmap_buf;
215
330
 
216
331
        actual_buf = (char *) e2fsck_allocate_memory(ctx, fs->blocksize,
502
617
                goto errout;
503
618
        }
504
619
 
505
 
        csum_flag = EXT2_HAS_RO_COMPAT_FEATURE(fs->super,
506
 
                                               EXT4_FEATURE_RO_COMPAT_GDT_CSUM);
 
620
        csum_flag = ext2fs_has_group_desc_csum(fs);
507
621
redo_counts:
508
622
        had_problem = 0;
509
623
        save_problem = 0;