Whamcloud - gitweb
Fix gcc -Wall warnings in e2fsck
[tools/e2fsprogs.git] / e2fsck / pass1.c
1 /*
2  * pass1.c -- pass #1 of e2fsck: sequential scan of the inode table
3  * 
4  * Copyright (C) 1993, 1994, 1995, 1996, 1997 Theodore Ts'o.
5  *
6  * %Begin-Header%
7  * This file may be redistributed under the terms of the GNU Public
8  * License.
9  * %End-Header%
10  * 
11  * Pass 1 of e2fsck iterates over all the inodes in the filesystems,
12  * and applies the following tests to each inode:
13  *
14  *      - The mode field of the inode must be legal.
15  *      - The size and block count fields of the inode are correct.
16  *      - A data block must not be used by another inode
17  *
18  * Pass 1 also gathers the collects the following information:
19  *
20  *      - A bitmap of which inodes are in use.          (inode_used_map)
21  *      - A bitmap of which inodes are directories.     (inode_dir_map)
22  *      - A bitmap of which inodes are regular files.   (inode_reg_map)
23  *      - A bitmap of which inodes have bad fields.     (inode_bad_map)
24  *      - A bitmap of which inodes are in bad blocks.   (inode_bb_map)
25  *      - A bitmap of which inodes are imagic inodes.   (inode_imagic_map)
26  *      - A bitmap of which blocks are in use.          (block_found_map)
27  *      - A bitmap of which blocks are in use by two inodes     (block_dup_map)
28  *      - The data blocks of the directory inodes.      (dir_map)
29  *
30  * Pass 1 is designed to stash away enough information so that the
31  * other passes should not need to read in the inode information
32  * during the normal course of a filesystem check.  (Althogh if an
33  * inconsistency is detected, other passes may need to read in an
34  * inode to fix it.)
35  *
36  * Note that pass 1B will be invoked if there are any duplicate blocks
37  * found.
38  */
39
40 #define _GNU_SOURCE 1 /* get strnlen() */
41 #include <string.h>
42 #include <time.h>
43 #ifdef HAVE_ERRNO_H
44 #include <errno.h>
45 #endif
46
47 #include "e2fsck.h"
48 #include <ext2fs/ext2_ext_attr.h>
49
50 #include "problem.h"
51
52 #ifdef NO_INLINE_FUNCS
53 #define _INLINE_
54 #else
55 #define _INLINE_ inline
56 #endif
57
58 static int process_block(ext2_filsys fs, blk_t  *blocknr,
59                          e2_blkcnt_t blockcnt, blk_t ref_blk, 
60                          int ref_offset, void *priv_data);
61 static int process_bad_block(ext2_filsys fs, blk_t *block_nr,
62                              e2_blkcnt_t blockcnt, blk_t ref_blk,
63                              int ref_offset, void *priv_data);
64 static void check_blocks(e2fsck_t ctx, struct problem_context *pctx,
65                          char *block_buf);
66 static void mark_table_blocks(e2fsck_t ctx);
67 static void alloc_bb_map(e2fsck_t ctx);
68 static void alloc_imagic_map(e2fsck_t ctx);
69 static void mark_inode_bad(e2fsck_t ctx, ino_t ino);
70 static void handle_fs_bad_blocks(e2fsck_t ctx);
71 static void process_inodes(e2fsck_t ctx, char *block_buf);
72 static EXT2_QSORT_TYPE process_inode_cmp(const void *a, const void *b);
73 static errcode_t scan_callback(ext2_filsys fs, ext2_inode_scan scan,
74                                   dgrp_t group, void * priv_data);
75 static void adjust_extattr_refcount(e2fsck_t ctx, ext2_refcount_t refcount, 
76                                     char *block_buf, int adjust_sign);
77 /* static char *describe_illegal_block(ext2_filsys fs, blk_t block); */
78
79 struct process_block_struct {
80         ext2_ino_t      ino;
81         unsigned        is_dir:1, is_reg:1, clear:1, suppress:1,
82                                 fragmented:1, compressed:1, bbcheck:1;
83         blk_t           num_blocks;
84         blk_t           max_blocks;
85         e2_blkcnt_t     last_block;
86         int             num_illegal_blocks;
87         blk_t           previous_block;
88         struct ext2_inode *inode;
89         struct problem_context *pctx;
90         ext2fs_block_bitmap fs_meta_blocks;
91         e2fsck_t        ctx;
92 };
93
94 struct process_inode_block {
95         ext2_ino_t ino;
96         struct ext2_inode inode;
97 };
98
99 struct scan_callback_struct {
100         e2fsck_t        ctx;
101         char            *block_buf;
102 };
103
104 /*
105  * For the inodes to process list.
106  */
107 static struct process_inode_block *inodes_to_process;
108 static int process_inode_count;
109
110 static __u64 ext2_max_sizes[EXT2_MAX_BLOCK_LOG_SIZE -
111                             EXT2_MIN_BLOCK_LOG_SIZE + 1];
112
113 /*
114  * Free all memory allocated by pass1 in preparation for restarting
115  * things.
116  */
117 static void unwind_pass1(ext2_filsys fs EXT2FS_ATTR((unused)))
118 {
119         ext2fs_free_mem(&inodes_to_process);
120         inodes_to_process = 0;
121 }
122
123 /*
124  * Check to make sure a device inode is real.  Returns 1 if the device
125  * checks out, 0 if not.
126  *
127  * Note: this routine is now also used to check FIFO's and Sockets,
128  * since they have the same requirement; the i_block fields should be
129  * zero. 
130  */
131 int e2fsck_pass1_check_device_inode(ext2_filsys fs EXT2FS_ATTR((unused)), 
132                                     struct ext2_inode *inode)
133 {
134         int     i;
135
136         /*
137          * If the index flag is set, then this is a bogus
138          * device/fifo/socket
139          */
140         if (inode->i_flags & EXT2_INDEX_FL)
141                 return 0;
142
143         /*
144          * We should be able to do the test below all the time, but
145          * because the kernel doesn't forcibly clear the device
146          * inode's additional i_block fields, there are some rare
147          * occasions when a legitimate device inode will have non-zero
148          * additional i_block fields.  So for now, we only complain
149          * when the immutable flag is set, which should never happen
150          * for devices.  (And that's when the problem is caused, since
151          * you can't set or clear immutable flags for devices.)  Once
152          * the kernel has been fixed we can change this...
153          */
154         if (inode->i_flags & (EXT2_IMMUTABLE_FL | EXT2_APPEND_FL)) {
155                 for (i=4; i < EXT2_N_BLOCKS; i++) 
156                         if (inode->i_block[i])
157                                 return 0;
158         }
159         return 1;
160 }
161
162 /*
163  * Check to make sure a symlink inode is real.  Returns 1 if the symlink
164  * checks out, 0 if not.
165  */
166 int e2fsck_pass1_check_symlink(ext2_filsys fs, ext2_ino_t ino,
167                                struct ext2_inode *inode, char *buf)
168 {
169         unsigned int len;
170         int i;
171         blk_t   blocks;
172         ext2_extent_handle_t    handle;
173         struct ext2_extent_info info;
174         struct ext2fs_extent    extent;
175
176         if ((inode->i_size_high || inode->i_size == 0) ||
177             (inode->i_flags & EXT2_INDEX_FL))
178                 return 0;
179
180         if (inode->i_flags & EXT4_EXTENTS_FL) {
181                 if (inode->i_size > fs->blocksize)
182                         return 0;
183                 if (ext2fs_extent_open(fs, ino, &handle))
184                         return 0;
185                 i = 0;
186                 if (ext2fs_extent_get_info(handle, &info) ||
187                     (info.num_entries != 1) ||
188                     (info.max_depth != 0))
189                         goto exit_extent;
190                 if (ext2fs_extent_get(handle, EXT2_EXTENT_ROOT, &extent) ||
191                     (extent.e_lblk != 0) ||
192                     (extent.e_len != 1) ||
193                     (extent.e_pblk < fs->super->s_first_data_block) ||
194                     (extent.e_pblk >= fs->super->s_blocks_count))
195                         goto exit_extent;
196                 i = 1;
197         exit_extent:
198                 ext2fs_extent_free(handle);
199                 return i;
200         }
201
202         blocks = ext2fs_inode_data_blocks(fs, inode);
203         if (blocks) {
204                 if ((inode->i_size >= fs->blocksize) ||
205                     (blocks != fs->blocksize >> 9) ||
206                     (inode->i_block[0] < fs->super->s_first_data_block) ||
207                     (inode->i_block[0] >= fs->super->s_blocks_count))
208                         return 0;
209
210                 for (i = 1; i < EXT2_N_BLOCKS; i++)
211                         if (inode->i_block[i])
212                                 return 0;
213
214                 if (io_channel_read_blk(fs->io, inode->i_block[0], 1, buf))
215                         return 0;
216
217                 len = strnlen(buf, fs->blocksize);
218                 if (len == fs->blocksize)
219                         return 0;
220         } else {
221                 if (inode->i_size >= sizeof(inode->i_block))
222                         return 0;
223
224                 len = strnlen((char *)inode->i_block, sizeof(inode->i_block));
225                 if (len == sizeof(inode->i_block))
226                         return 0;
227         }
228         if (len != inode->i_size)
229                 return 0;
230         return 1;
231 }
232
233 /*
234  * If the immutable (or append-only) flag is set on the inode, offer
235  * to clear it.
236  */
237 #define BAD_SPECIAL_FLAGS (EXT2_IMMUTABLE_FL | EXT2_APPEND_FL)
238 static void check_immutable(e2fsck_t ctx, struct problem_context *pctx)
239 {
240         if (!(pctx->inode->i_flags & BAD_SPECIAL_FLAGS))
241                 return;
242
243         if (!fix_problem(ctx, PR_1_SET_IMMUTABLE, pctx))
244                 return;
245
246         pctx->inode->i_flags &= ~BAD_SPECIAL_FLAGS;
247         e2fsck_write_inode(ctx, pctx->ino, pctx->inode, "pass1");
248 }
249
250 /*
251  * If device, fifo or socket, check size is zero -- if not offer to
252  * clear it
253  */
254 static void check_size(e2fsck_t ctx, struct problem_context *pctx)
255 {
256         struct ext2_inode *inode = pctx->inode;
257         
258         if ((inode->i_size == 0) && (inode->i_size_high == 0))
259                 return;
260         
261         if (!fix_problem(ctx, PR_1_SET_NONZSIZE, pctx))
262                 return;
263         
264         inode->i_size = 0;
265         inode->i_size_high = 0;
266         e2fsck_write_inode(ctx, pctx->ino, pctx->inode, "pass1");
267 }
268         
269 static void check_ea_in_inode(e2fsck_t ctx, struct problem_context *pctx)
270 {
271         struct ext2_super_block *sb = ctx->fs->super;
272         struct ext2_inode_large *inode;
273         struct ext2_ext_attr_entry *entry;
274         char *start, *end;
275         unsigned int storage_size, remain;
276         int problem = 0;
277
278         inode = (struct ext2_inode_large *) pctx->inode;
279         storage_size = EXT2_INODE_SIZE(ctx->fs->super) - EXT2_GOOD_OLD_INODE_SIZE -
280                 inode->i_extra_isize;
281         start = ((char *) inode) + EXT2_GOOD_OLD_INODE_SIZE +
282                 inode->i_extra_isize + sizeof(__u32);
283         end = (char *) inode + EXT2_INODE_SIZE(ctx->fs->super);
284         entry = (struct ext2_ext_attr_entry *) start;
285
286         /* scan all entry's headers first */
287
288         /* take finish entry 0UL into account */
289         remain = storage_size - sizeof(__u32); 
290
291         while (!EXT2_EXT_IS_LAST_ENTRY(entry)) {
292                 __u32 hash;
293
294                 /* header eats this space */
295                 remain -= sizeof(struct ext2_ext_attr_entry);
296                 
297                 /* is attribute name valid? */
298                 if (EXT2_EXT_ATTR_SIZE(entry->e_name_len) > remain) {
299                         pctx->num = entry->e_name_len;
300                         problem = PR_1_ATTR_NAME_LEN;
301                         goto fix;
302                 }
303
304                 /* attribute len eats this space */
305                 remain -= EXT2_EXT_ATTR_SIZE(entry->e_name_len);
306
307                 /* check value size */
308                 if (entry->e_value_size == 0 || entry->e_value_size > remain) {
309                         pctx->num = entry->e_value_size;
310                         problem = PR_1_ATTR_VALUE_SIZE;
311                         goto fix;
312                 }
313
314                 /* e_value_block must be 0 in inode's ea */
315                 if (entry->e_value_block != 0) {
316                         pctx->num = entry->e_value_block;
317                         problem = PR_1_ATTR_VALUE_BLOCK;
318                         goto fix;
319                 }
320
321                 hash = ext2fs_ext_attr_hash_entry(entry,
322                                                   start + entry->e_value_offs);
323
324                 /* e_hash may be 0 in older inode's ea */
325                 if (entry->e_hash != 0 && entry->e_hash != hash) {
326                         pctx->num = entry->e_hash;
327                         problem = PR_1_ATTR_HASH;
328                         goto fix;
329                 }
330
331                 remain -= entry->e_value_size;
332
333                 entry = EXT2_EXT_ATTR_NEXT(entry);
334         }
335 fix:
336         /*
337          * it seems like a corruption. it's very unlikely we could repair
338          * EA(s) in automatic fashion -bzzz
339          */
340         if (problem == 0 || !fix_problem(ctx, problem, pctx))
341                 return;
342
343         /* simply remove all possible EA(s) */
344         *((__u32 *)start) = 0UL;
345         e2fsck_write_inode_full(ctx, pctx->ino, pctx->inode,
346                                 EXT2_INODE_SIZE(sb), "pass1");
347 }
348
349 static void check_inode_extra_space(e2fsck_t ctx, struct problem_context *pctx)
350 {
351         struct ext2_super_block *sb = ctx->fs->super;
352         struct ext2_inode_large *inode;
353         __u32 *eamagic;
354         int min, max;
355
356         inode = (struct ext2_inode_large *) pctx->inode;
357         if (EXT2_INODE_SIZE(sb) == EXT2_GOOD_OLD_INODE_SIZE) {
358                 /* this isn't large inode. so, nothing to check */
359                 return;
360         }
361
362 #if 0
363         printf("inode #%u, i_extra_size %d\n", pctx->ino,
364                         inode->i_extra_isize);
365 #endif  
366         /* i_extra_isize must cover i_extra_isize + i_pad1 at least */
367         min = sizeof(inode->i_extra_isize) + sizeof(inode->i_pad1);
368         max = EXT2_INODE_SIZE(sb) - EXT2_GOOD_OLD_INODE_SIZE;
369         /* 
370          * For now we will allow i_extra_isize to be 0, but really
371          * implementations should never allow i_extra_isize to be 0
372          */
373         if (inode->i_extra_isize &&
374             (inode->i_extra_isize < min || inode->i_extra_isize > max)) {
375                 if (!fix_problem(ctx, PR_1_EXTRA_ISIZE, pctx))
376                         return;
377                 inode->i_extra_isize = min;
378                 e2fsck_write_inode_full(ctx, pctx->ino, pctx->inode,
379                                         EXT2_INODE_SIZE(sb), "pass1");
380                 return;
381         }
382
383         eamagic = (__u32 *) (((char *) inode) + EXT2_GOOD_OLD_INODE_SIZE +
384                         inode->i_extra_isize);
385         if (*eamagic == EXT2_EXT_ATTR_MAGIC) {
386                 /* it seems inode has an extended attribute(s) in body */
387                 check_ea_in_inode(ctx, pctx);
388         }
389 }
390
391 /* 
392  * Check to see if the inode might really be a directory, despite i_mode
393  *
394  * This is a lot of complexity for something for which I'm not really
395  * convinced happens frequently in the wild.  If for any reason this
396  * causes any problems, take this code out.
397  * [tytso:20070331.0827EDT]
398  */
399 static void check_is_really_dir(e2fsck_t ctx, struct problem_context *pctx,
400                                 char *buf)
401 {
402         struct ext2_inode *inode = pctx->inode;
403         struct ext2_dir_entry   *dirent;
404         const char              *old_op;
405         errcode_t               retval;
406         blk_t                   blk;
407         int                     i, not_device = 0;
408
409         if (LINUX_S_ISDIR(inode->i_mode) || LINUX_S_ISREG(inode->i_mode) ||
410             LINUX_S_ISLNK(inode->i_mode) || inode->i_block[0] == 0)
411                 return;
412
413         for (i=0; i < EXT2_N_BLOCKS; i++) {
414                 blk = inode->i_block[i];
415                 if (!blk)
416                         continue;
417                 if (i >= 4)
418                         not_device++;
419
420                 if (blk < ctx->fs->super->s_first_data_block ||
421                     blk >= ctx->fs->super->s_blocks_count ||
422                     ext2fs_fast_test_block_bitmap(ctx->block_found_map, blk))
423                         return; /* Invalid block, can't be dir */
424         }
425
426         if ((LINUX_S_ISCHR(inode->i_mode) || LINUX_S_ISBLK(inode->i_mode)) && 
427             (inode->i_links_count == 1) && !not_device)
428                 return;
429
430         old_op = ehandler_operation(_("reading directory block"));
431         retval = ext2fs_read_dir_block(ctx->fs, inode->i_block[0], buf);
432         ehandler_operation(0);
433         if (retval)
434                 return;
435
436         dirent = (struct ext2_dir_entry *) buf;
437         if (((dirent->name_len & 0xFF) != 1) ||
438             (dirent->name[0] != '.') ||
439             (dirent->inode != pctx->ino) ||
440             (dirent->rec_len < 12) ||
441             (dirent->rec_len % 4) ||
442             (dirent->rec_len >= ctx->fs->blocksize - 12))
443                 return;
444
445         dirent = (struct ext2_dir_entry *) (buf + dirent->rec_len);
446         if (((dirent->name_len & 0xFF) != 2) ||
447             (dirent->name[0] != '.') ||
448             (dirent->name[1] != '.') ||
449             (dirent->rec_len < 12) ||
450             (dirent->rec_len % 4))
451                 return;
452
453         if (fix_problem(ctx, PR_1_TREAT_AS_DIRECTORY, pctx)) {
454                 inode->i_mode = (inode->i_mode & 07777) | LINUX_S_IFDIR;
455                 e2fsck_write_inode_full(ctx, pctx->ino, inode, 
456                                         EXT2_INODE_SIZE(ctx->fs->super), 
457                                         "check_is_really_dir");
458         }
459 }
460
461 extern void e2fsck_setup_tdb_icount(e2fsck_t ctx, int flags, 
462                                     ext2_icount_t *ret)
463 {
464         unsigned int            threshold;
465         ext2_ino_t              num_dirs;
466         errcode_t               retval;
467         char                    *tdb_dir;
468         int                     enable;
469
470         *ret = 0;
471
472         profile_get_string(ctx->profile, "scratch_files", "directory", 0, 0,
473                            &tdb_dir);
474         profile_get_uint(ctx->profile, "scratch_files",
475                          "numdirs_threshold", 0, 0, &threshold);
476         profile_get_boolean(ctx->profile, "scratch_files",
477                             "icount", 0, 1, &enable);
478
479         retval = ext2fs_get_num_dirs(ctx->fs, &num_dirs);
480         if (retval)
481                 num_dirs = 1024;        /* Guess */
482
483         if (!enable || !tdb_dir || access(tdb_dir, W_OK) ||
484             (threshold && num_dirs <= threshold))
485                 return;
486
487         retval = ext2fs_create_icount_tdb(ctx->fs, tdb_dir, flags, ret);
488         if (retval)
489                 *ret = 0;
490 }
491
492 void e2fsck_pass1(e2fsck_t ctx)
493 {
494         int     i;
495         __u64   max_sizes;
496         ext2_filsys fs = ctx->fs;
497         ext2_ino_t      ino;
498         struct ext2_inode *inode;
499         ext2_inode_scan scan;
500         char            *block_buf;
501 #ifdef RESOURCE_TRACK
502         struct resource_track   rtrack;
503 #endif
504         unsigned char   frag, fsize;
505         struct          problem_context pctx;
506         struct          scan_callback_struct scan_struct;
507         struct ext2_super_block *sb = ctx->fs->super;
508         const char      *old_op;
509         int             imagic_fs, extent_fs;
510         int             busted_fs_time = 0;
511         int             inode_size;
512         
513 #ifdef RESOURCE_TRACK
514         init_resource_track(&rtrack, ctx->fs->io);
515 #endif
516         clear_problem_context(&pctx);
517
518         if (!(ctx->options & E2F_OPT_PREEN))
519                 fix_problem(ctx, PR_1_PASS_HEADER, &pctx);
520
521         if ((fs->super->s_feature_compat & EXT2_FEATURE_COMPAT_DIR_INDEX) &&
522             !(ctx->options & E2F_OPT_NO)) {
523                 if (ext2fs_u32_list_create(&ctx->dirs_to_hash, 50))
524                         ctx->dirs_to_hash = 0;
525         }
526
527 #ifdef MTRACE
528         mtrace_print("Pass 1");
529 #endif
530
531 #define EXT2_BPP(bits) (1ULL << ((bits) - 2))
532
533         for (i = EXT2_MIN_BLOCK_LOG_SIZE; i <= EXT2_MAX_BLOCK_LOG_SIZE; i++) {
534                 max_sizes = EXT2_NDIR_BLOCKS + EXT2_BPP(i);
535                 max_sizes = max_sizes + EXT2_BPP(i) * EXT2_BPP(i);
536                 max_sizes = max_sizes + EXT2_BPP(i) * EXT2_BPP(i) * EXT2_BPP(i);
537                 max_sizes = (max_sizes * (1UL << i)) - 1;
538                 ext2_max_sizes[i - EXT2_MIN_BLOCK_LOG_SIZE] = max_sizes;
539         }
540 #undef EXT2_BPP
541
542         imagic_fs = (sb->s_feature_compat & EXT2_FEATURE_COMPAT_IMAGIC_INODES);
543         extent_fs = (sb->s_feature_incompat & EXT3_FEATURE_INCOMPAT_EXTENTS);
544
545         /*
546          * Allocate bitmaps structures
547          */
548         pctx.errcode = ext2fs_allocate_inode_bitmap(fs, _("in-use inode map"),
549                                               &ctx->inode_used_map);
550         if (pctx.errcode) {
551                 pctx.num = 1;
552                 fix_problem(ctx, PR_1_ALLOCATE_IBITMAP_ERROR, &pctx);
553                 ctx->flags |= E2F_FLAG_ABORT;
554                 return;
555         }
556         pctx.errcode = ext2fs_allocate_inode_bitmap(fs,
557                                 _("directory inode map"), &ctx->inode_dir_map);
558         if (pctx.errcode) {
559                 pctx.num = 2;
560                 fix_problem(ctx, PR_1_ALLOCATE_IBITMAP_ERROR, &pctx);
561                 ctx->flags |= E2F_FLAG_ABORT;
562                 return;
563         }
564         pctx.errcode = ext2fs_allocate_inode_bitmap(fs,
565                         _("regular file inode map"), &ctx->inode_reg_map);
566         if (pctx.errcode) {
567                 pctx.num = 6;
568                 fix_problem(ctx, PR_1_ALLOCATE_IBITMAP_ERROR, &pctx);
569                 ctx->flags |= E2F_FLAG_ABORT;
570                 return;
571         }
572         pctx.errcode = ext2fs_allocate_block_bitmap(fs, _("in-use block map"),
573                                               &ctx->block_found_map);
574         if (pctx.errcode) {
575                 pctx.num = 1;
576                 fix_problem(ctx, PR_1_ALLOCATE_BBITMAP_ERROR, &pctx);
577                 ctx->flags |= E2F_FLAG_ABORT;
578                 return;
579         }
580         e2fsck_setup_tdb_icount(ctx, 0, &ctx->inode_link_info);
581         if (!ctx->inode_link_info)
582                 pctx.errcode = ext2fs_create_icount2(fs, 0, 0, 0,
583                                                      &ctx->inode_link_info);
584         if (pctx.errcode) {
585                 fix_problem(ctx, PR_1_ALLOCATE_ICOUNT, &pctx);
586                 ctx->flags |= E2F_FLAG_ABORT;
587                 return;
588         }
589         inode_size = EXT2_INODE_SIZE(fs->super);
590         inode = (struct ext2_inode *)
591                 e2fsck_allocate_memory(ctx, inode_size, "scratch inode");
592
593         inodes_to_process = (struct process_inode_block *)
594                 e2fsck_allocate_memory(ctx,
595                                        (ctx->process_inode_size *
596                                         sizeof(struct process_inode_block)),
597                                        "array of inodes to process");
598         process_inode_count = 0;
599
600         pctx.errcode = ext2fs_init_dblist(fs, 0);
601         if (pctx.errcode) {
602                 fix_problem(ctx, PR_1_ALLOCATE_DBCOUNT, &pctx);
603                 ctx->flags |= E2F_FLAG_ABORT;
604                 ext2fs_free_mem(&inode);
605                 return;
606         }
607
608         /*
609          * If the last orphan field is set, clear it, since the pass1
610          * processing will automatically find and clear the orphans.
611          * In the future, we may want to try using the last_orphan
612          * linked list ourselves, but for now, we clear it so that the
613          * ext3 mount code won't get confused.
614          */
615         if (!(ctx->options & E2F_OPT_READONLY)) {
616                 if (fs->super->s_last_orphan) {
617                         fs->super->s_last_orphan = 0;
618                         ext2fs_mark_super_dirty(fs);
619                 }
620         }
621
622         mark_table_blocks(ctx);
623         block_buf = (char *) e2fsck_allocate_memory(ctx, fs->blocksize * 3,
624                                                     "block interate buffer");
625         e2fsck_use_inode_shortcuts(ctx, 1);
626         old_op = ehandler_operation(_("opening inode scan"));
627         pctx.errcode = ext2fs_open_inode_scan(fs, ctx->inode_buffer_blocks, 
628                                               &scan);
629         ehandler_operation(old_op);
630         if (pctx.errcode) {
631                 fix_problem(ctx, PR_1_ISCAN_ERROR, &pctx);
632                 ctx->flags |= E2F_FLAG_ABORT;
633                 ext2fs_free_mem(&block_buf);
634                 ext2fs_free_mem(&inode);
635                 return;
636         }
637         ext2fs_inode_scan_flags(scan, EXT2_SF_SKIP_MISSING_ITABLE, 0);
638         ctx->stashed_inode = inode;
639         scan_struct.ctx = ctx;
640         scan_struct.block_buf = block_buf;
641         ext2fs_set_inode_callback(scan, scan_callback, &scan_struct);
642         if (ctx->progress)
643                 if ((ctx->progress)(ctx, 1, 0, ctx->fs->group_desc_count))
644                         return;
645         if ((fs->super->s_wtime < fs->super->s_inodes_count) ||
646             (fs->super->s_mtime < fs->super->s_inodes_count))
647                 busted_fs_time = 1;
648
649         while (1) {
650                 old_op = ehandler_operation(_("getting next inode from scan"));
651                 pctx.errcode = ext2fs_get_next_inode_full(scan, &ino, 
652                                                           inode, inode_size);
653                 ehandler_operation(old_op);
654                 if (ctx->flags & E2F_FLAG_SIGNAL_MASK)
655                         return;
656                 if (pctx.errcode == EXT2_ET_BAD_BLOCK_IN_INODE_TABLE) {
657                         if (!ctx->inode_bb_map)
658                                 alloc_bb_map(ctx);
659                         ext2fs_mark_inode_bitmap(ctx->inode_bb_map, ino);
660                         ext2fs_mark_inode_bitmap(ctx->inode_used_map, ino);
661                         continue;
662                 }
663                 if (pctx.errcode) {
664                         fix_problem(ctx, PR_1_ISCAN_ERROR, &pctx);
665                         ctx->flags |= E2F_FLAG_ABORT;
666                         return;
667                 }
668                 if (!ino)
669                         break;
670                 pctx.ino = ino;
671                 pctx.inode = inode;
672                 ctx->stashed_ino = ino;
673                 if (inode->i_links_count) {
674                         pctx.errcode = ext2fs_icount_store(ctx->inode_link_info, 
675                                            ino, inode->i_links_count);
676                         if (pctx.errcode) {
677                                 pctx.num = inode->i_links_count;
678                                 fix_problem(ctx, PR_1_ICOUNT_STORE, &pctx);
679                                 ctx->flags |= E2F_FLAG_ABORT;
680                                 return;
681                         }
682                 }
683
684                 /*
685                  * Test for incorrect extent flag settings.
686                  *
687                  * On big-endian machines we must be careful:
688                  * When the inode is read, the i_block array is not swapped
689                  * if the extent flag is set.  Therefore if we are testing
690                  * for or fixing a wrongly-set flag, we must potentially
691                  * (un)swap before testing, or after fixing.
692                  */
693
694                 /*
695                  * In this case the extents flag was set when read, so
696                  * extent_header_verify is ok.  If the inode is cleared,
697                  * no need to swap... so no extra swapping here.
698                  */
699                 if ((inode->i_flags & EXT4_EXTENTS_FL) && !extent_fs && 
700                     (inode->i_links_count || (ino == EXT2_BAD_INO) ||
701                      (ino == EXT2_ROOT_INO) || (ino == EXT2_JOURNAL_INO))) {
702                         if ((ext2fs_extent_header_verify(inode->i_block, 
703                                                  sizeof(inode->i_block)) == 0) &&
704                             fix_problem(ctx, PR_1_EXTENT_FEATURE, &pctx)) {
705                                 sb->s_feature_incompat |= EXT3_FEATURE_INCOMPAT_EXTENTS;
706                                 ext2fs_mark_super_dirty(fs);
707                                 extent_fs = 1;
708                         } else if (fix_problem(ctx, PR_1_EXTENTS_SET, &pctx)) {
709                         clear_inode:
710                                 e2fsck_clear_inode(ctx, ino, inode, 0, "pass1");
711                                 if (ino == EXT2_BAD_INO)
712                                         ext2fs_mark_inode_bitmap(ctx->inode_used_map, 
713                                                                  ino);
714                                 continue;
715                         }
716                 }
717
718                 /*
719                  * For big-endian machines:
720                  * If the inode didn't have the extents flag set when it
721                  * was read, then the i_blocks array was swapped.  To test
722                  * as an extents header, we must swap it back first.
723                  * IF we then set the extents flag, the entire i_block
724                  * array must be un/re-swapped to make it proper extents data.
725                  */
726                 if (extent_fs && !(inode->i_flags & EXT4_EXTENTS_FL) &&
727                     (inode->i_links_count || (ino == EXT2_BAD_INO) ||
728                      (ino == EXT2_ROOT_INO) || (ino == EXT2_JOURNAL_INO)) &&
729                     (LINUX_S_ISREG(inode->i_mode) ||
730                      LINUX_S_ISDIR(inode->i_mode))) {
731                         void *ehp;
732 #ifdef WORDS_BIGENDIAN
733                         __u32 tmp_block[EXT2_N_BLOCKS];
734
735                         for (i = 0; i < EXT2_N_BLOCKS; i++)
736                                 tmp_block[i] = ext2fs_swab32(inode->i_block[i]);
737                         ehp = tmp_block;
738 #else
739                         ehp = inode->i_block;
740 #endif
741                         if ((ext2fs_extent_header_verify(ehp, 
742                                          sizeof(inode->i_block)) == 0) &&
743                             (fix_problem(ctx, PR_1_UNSET_EXTENT_FL, &pctx))) {
744                                 inode->i_flags |= EXT4_EXTENTS_FL;
745 #ifdef WORDS_BIGENDIAN
746                                 memcpy(inode->i_block, tmp_block, 
747                                        sizeof(inode->i_block));
748 #endif
749                                 e2fsck_write_inode(ctx, ino, inode, "pass1");
750                         }
751                 }
752
753                 if (ino == EXT2_BAD_INO) {
754                         struct process_block_struct pb;
755                         
756                         pctx.errcode = ext2fs_copy_bitmap(ctx->block_found_map,
757                                                           &pb.fs_meta_blocks);
758                         if (pctx.errcode) {
759                                 pctx.num = 4;
760                                 fix_problem(ctx, PR_1_ALLOCATE_BBITMAP_ERROR, &pctx);
761                                 ctx->flags |= E2F_FLAG_ABORT;
762                                 return;
763                         }
764                         pb.ino = EXT2_BAD_INO;
765                         pb.num_blocks = pb.last_block = 0;
766                         pb.num_illegal_blocks = 0;
767                         pb.suppress = 0; pb.clear = 0; pb.is_dir = 0;
768                         pb.is_reg = 0; pb.fragmented = 0; pb.bbcheck = 0;
769                         pb.inode = inode;
770                         pb.pctx = &pctx;
771                         pb.ctx = ctx;
772                         pctx.errcode = ext2fs_block_iterate2(fs, ino, 0, 
773                                      block_buf, process_bad_block, &pb);
774                         ext2fs_free_block_bitmap(pb.fs_meta_blocks);
775                         if (pctx.errcode) {
776                                 fix_problem(ctx, PR_1_BLOCK_ITERATE, &pctx);
777                                 ctx->flags |= E2F_FLAG_ABORT;
778                                 return;
779                         }
780                         if (pb.bbcheck)
781                                 if (!fix_problem(ctx, PR_1_BBINODE_BAD_METABLOCK_PROMPT, &pctx)) {
782                                 ctx->flags |= E2F_FLAG_ABORT;
783                                 return;
784                         }
785                         ext2fs_mark_inode_bitmap(ctx->inode_used_map, ino);
786                         clear_problem_context(&pctx);
787                         continue;
788                 } else if (ino == EXT2_ROOT_INO) {
789                         /*
790                          * Make sure the root inode is a directory; if
791                          * not, offer to clear it.  It will be
792                          * regnerated in pass #3.
793                          */
794                         if (!LINUX_S_ISDIR(inode->i_mode)) {
795                                 if (fix_problem(ctx, PR_1_ROOT_NO_DIR, &pctx))
796                                         goto clear_inode;
797                         }
798                         /*
799                          * If dtime is set, offer to clear it.  mke2fs
800                          * version 0.2b created filesystems with the
801                          * dtime field set for the root and lost+found
802                          * directories.  We won't worry about
803                          * /lost+found, since that can be regenerated
804                          * easily.  But we will fix the root directory
805                          * as a special case.
806                          */
807                         if (inode->i_dtime && inode->i_links_count) {
808                                 if (fix_problem(ctx, PR_1_ROOT_DTIME, &pctx)) {
809                                         inode->i_dtime = 0;
810                                         e2fsck_write_inode(ctx, ino, inode,
811                                                            "pass1");
812                                 }
813                         }
814                 } else if (ino == EXT2_JOURNAL_INO) {
815                         ext2fs_mark_inode_bitmap(ctx->inode_used_map, ino);
816                         if (fs->super->s_journal_inum == EXT2_JOURNAL_INO) {
817                                 if (!LINUX_S_ISREG(inode->i_mode) &&
818                                     fix_problem(ctx, PR_1_JOURNAL_BAD_MODE,
819                                                 &pctx)) {
820                                         inode->i_mode = LINUX_S_IFREG;
821                                         e2fsck_write_inode(ctx, ino, inode,
822                                                            "pass1");
823                                 }
824                                 check_blocks(ctx, &pctx, block_buf);
825                                 continue;
826                         }
827                         if ((inode->i_links_count || inode->i_blocks ||
828                              inode->i_blocks || inode->i_block[0]) &&
829                             fix_problem(ctx, PR_1_JOURNAL_INODE_NOT_CLEAR, 
830                                         &pctx)) {
831                                 memset(inode, 0, inode_size);
832                                 ext2fs_icount_store(ctx->inode_link_info,
833                                                     ino, 0);
834                                 e2fsck_write_inode_full(ctx, ino, inode, 
835                                                         inode_size, "pass1");
836                         }
837                 } else if (ino < EXT2_FIRST_INODE(fs->super)) {
838                         int     problem = 0;
839                         
840                         ext2fs_mark_inode_bitmap(ctx->inode_used_map, ino);
841                         if (ino == EXT2_BOOT_LOADER_INO) {
842                                 if (LINUX_S_ISDIR(inode->i_mode))
843                                         problem = PR_1_RESERVED_BAD_MODE;
844                         } else if (ino == EXT2_RESIZE_INO) {
845                                 if (inode->i_mode &&
846                                     !LINUX_S_ISREG(inode->i_mode))
847                                         problem = PR_1_RESERVED_BAD_MODE;
848                         } else {
849                                 if (inode->i_mode != 0)
850                                         problem = PR_1_RESERVED_BAD_MODE;
851                         }
852                         if (problem) {
853                                 if (fix_problem(ctx, problem, &pctx)) {
854                                         inode->i_mode = 0;
855                                         e2fsck_write_inode(ctx, ino, inode,
856                                                            "pass1");
857                                 }
858                         }
859                         check_blocks(ctx, &pctx, block_buf);
860                         continue;
861                 }
862                 /*
863                  * Check for inodes who might have been part of the
864                  * orphaned list linked list.  They should have gotten
865                  * dealt with by now, unless the list had somehow been
866                  * corrupted.
867                  * 
868                  * FIXME: In the future, inodes which are still in use
869                  * (and which are therefore) pending truncation should
870                  * be handled specially.  Right now we just clear the
871                  * dtime field, and the normal e2fsck handling of
872                  * inodes where i_size and the inode blocks are
873                  * inconsistent is to fix i_size, instead of releasing
874                  * the extra blocks.  This won't catch the inodes that
875                  * was at the end of the orphan list, but it's better
876                  * than nothing.  The right answer is that there
877                  * shouldn't be any bugs in the orphan list handling.  :-)
878                  */
879                 if (inode->i_dtime && !busted_fs_time &&
880                     inode->i_dtime < ctx->fs->super->s_inodes_count) {
881                         if (fix_problem(ctx, PR_1_LOW_DTIME, &pctx)) {
882                                 inode->i_dtime = inode->i_links_count ?
883                                         0 : ctx->now;
884                                 e2fsck_write_inode(ctx, ino, inode,
885                                                    "pass1");
886                         }
887                 }
888                 
889                 /*
890                  * This code assumes that deleted inodes have
891                  * i_links_count set to 0.  
892                  */
893                 if (!inode->i_links_count) {
894                         if (!inode->i_dtime && inode->i_mode) {
895                                 if (fix_problem(ctx,
896                                             PR_1_ZERO_DTIME, &pctx)) {
897                                         inode->i_dtime = ctx->now;
898                                         e2fsck_write_inode(ctx, ino, inode,
899                                                            "pass1");
900                                 }
901                         }
902                         continue;
903                 }
904                 /*
905                  * n.b.  0.3c ext2fs code didn't clear i_links_count for
906                  * deleted files.  Oops.
907                  *
908                  * Since all new ext2 implementations get this right,
909                  * we now assume that the case of non-zero
910                  * i_links_count and non-zero dtime means that we
911                  * should keep the file, not delete it.
912                  * 
913                  */
914                 if (inode->i_dtime) {
915                         if (fix_problem(ctx, PR_1_SET_DTIME, &pctx)) {
916                                 inode->i_dtime = 0;
917                                 e2fsck_write_inode(ctx, ino, inode, "pass1");
918                         }
919                 }
920                 
921                 ext2fs_mark_inode_bitmap(ctx->inode_used_map, ino);
922                 switch (fs->super->s_creator_os) {
923                     case EXT2_OS_HURD:
924                         frag = inode->osd2.hurd2.h_i_frag;
925                         fsize = inode->osd2.hurd2.h_i_fsize;
926                         break;
927                     default:
928                         frag = fsize = 0;
929                 }
930                 
931                 if (inode->i_faddr || frag || fsize ||
932                     (LINUX_S_ISDIR(inode->i_mode) && inode->i_dir_acl))
933                         mark_inode_bad(ctx, ino);
934                 if ((fs->super->s_creator_os == EXT2_OS_LINUX) &&
935                     !(fs->super->s_feature_ro_compat & 
936                       EXT4_FEATURE_RO_COMPAT_HUGE_FILE) &&
937                     (inode->osd2.linux2.l_i_blocks_hi != 0))
938                         mark_inode_bad(ctx, ino);
939                 if (inode->i_flags & EXT2_IMAGIC_FL) {
940                         if (imagic_fs) {
941                                 if (!ctx->inode_imagic_map)
942                                         alloc_imagic_map(ctx);
943                                 ext2fs_mark_inode_bitmap(ctx->inode_imagic_map,
944                                                          ino);
945                         } else {
946                                 if (fix_problem(ctx, PR_1_SET_IMAGIC, &pctx)) {
947                                         inode->i_flags &= ~EXT2_IMAGIC_FL;
948                                         e2fsck_write_inode(ctx, ino,
949                                                            inode, "pass1");
950                                 }
951                         }
952                 }
953
954                 check_inode_extra_space(ctx, &pctx);
955                 check_is_really_dir(ctx, &pctx, block_buf);
956
957                 /*
958                  * ext2fs_inode_has_valid_blocks does not actually look
959                  * at i_block[] values, so not endian-sensitive here.
960                  */
961                 if (extent_fs && (inode->i_flags & EXT4_EXTENTS_FL) &&
962                     LINUX_S_ISLNK(inode->i_mode) &&
963                     !ext2fs_inode_has_valid_blocks(inode) &&
964                     fix_problem(ctx, PR_1_FAST_SYMLINK_EXTENT_FL, &pctx)) {
965                         inode->i_flags &= ~EXT4_EXTENTS_FL;
966                         e2fsck_write_inode(ctx, ino, inode, "pass1");
967                 }
968
969                 if (LINUX_S_ISDIR(inode->i_mode)) {
970                         ext2fs_mark_inode_bitmap(ctx->inode_dir_map, ino);
971                         e2fsck_add_dir_info(ctx, ino, 0);
972                         ctx->fs_directory_count++;
973                 } else if (LINUX_S_ISREG (inode->i_mode)) {
974                         ext2fs_mark_inode_bitmap(ctx->inode_reg_map, ino);
975                         ctx->fs_regular_count++;
976                 } else if (LINUX_S_ISCHR (inode->i_mode) &&
977                            e2fsck_pass1_check_device_inode(fs, inode)) {
978                         check_immutable(ctx, &pctx);
979                         check_size(ctx, &pctx);
980                         ctx->fs_chardev_count++;
981                 } else if (LINUX_S_ISBLK (inode->i_mode) &&
982                            e2fsck_pass1_check_device_inode(fs, inode)) {
983                         check_immutable(ctx, &pctx);
984                         check_size(ctx, &pctx);
985                         ctx->fs_blockdev_count++;
986                 } else if (LINUX_S_ISLNK (inode->i_mode) &&
987                            e2fsck_pass1_check_symlink(fs, ino, inode, 
988                                                       block_buf)) {
989                         check_immutable(ctx, &pctx);
990                         ctx->fs_symlinks_count++;
991                         if (ext2fs_inode_data_blocks(fs, inode) == 0) {
992                                 ctx->fs_fast_symlinks_count++;
993                                 check_blocks(ctx, &pctx, block_buf);
994                                 continue;
995                         }
996                 }
997                 else if (LINUX_S_ISFIFO (inode->i_mode) &&
998                          e2fsck_pass1_check_device_inode(fs, inode)) {
999                         check_immutable(ctx, &pctx);
1000                         check_size(ctx, &pctx);
1001                         ctx->fs_fifo_count++;
1002                 } else if ((LINUX_S_ISSOCK (inode->i_mode)) &&
1003                            e2fsck_pass1_check_device_inode(fs, inode)) {
1004                         check_immutable(ctx, &pctx);
1005                         check_size(ctx, &pctx);
1006                         ctx->fs_sockets_count++;
1007                 } else
1008                         mark_inode_bad(ctx, ino);
1009                 if (inode->i_block[EXT2_IND_BLOCK])
1010                         ctx->fs_ind_count++;
1011                 if (inode->i_block[EXT2_DIND_BLOCK])
1012                         ctx->fs_dind_count++;
1013                 if (inode->i_block[EXT2_TIND_BLOCK])
1014                         ctx->fs_tind_count++;
1015                 if (!(inode->i_flags & EXT4_EXTENTS_FL) &&
1016                     (inode->i_block[EXT2_IND_BLOCK] ||
1017                      inode->i_block[EXT2_DIND_BLOCK] ||
1018                      inode->i_block[EXT2_TIND_BLOCK] ||
1019                      inode->i_file_acl)) {
1020                         inodes_to_process[process_inode_count].ino = ino;
1021                         inodes_to_process[process_inode_count].inode = *inode;
1022                         process_inode_count++;
1023                 } else
1024                         check_blocks(ctx, &pctx, block_buf);
1025
1026                 if (ctx->flags & E2F_FLAG_SIGNAL_MASK)
1027                         return;
1028
1029                 if (process_inode_count >= ctx->process_inode_size) {
1030                         process_inodes(ctx, block_buf);
1031
1032                         if (ctx->flags & E2F_FLAG_SIGNAL_MASK)
1033                                 return;
1034                 }
1035         }
1036         process_inodes(ctx, block_buf);
1037         ext2fs_close_inode_scan(scan);
1038
1039         /*
1040          * If any extended attribute blocks' reference counts need to
1041          * be adjusted, either up (ctx->refcount_extra), or down
1042          * (ctx->refcount), then fix them.
1043          */
1044         if (ctx->refcount) {
1045                 adjust_extattr_refcount(ctx, ctx->refcount, block_buf, -1);
1046                 ea_refcount_free(ctx->refcount);
1047                 ctx->refcount = 0;
1048         }
1049         if (ctx->refcount_extra) {
1050                 adjust_extattr_refcount(ctx, ctx->refcount_extra,
1051                                         block_buf, +1);
1052                 ea_refcount_free(ctx->refcount_extra);
1053                 ctx->refcount_extra = 0;
1054         }
1055                 
1056         if (ctx->invalid_bitmaps)
1057                 handle_fs_bad_blocks(ctx);
1058
1059         /* We don't need the block_ea_map any more */
1060         if (ctx->block_ea_map) {
1061                 ext2fs_free_block_bitmap(ctx->block_ea_map);
1062                 ctx->block_ea_map = 0;
1063         }
1064
1065         if (ctx->flags & E2F_FLAG_RESIZE_INODE) {
1066                 ext2fs_block_bitmap save_bmap;
1067
1068                 save_bmap = fs->block_map;
1069                 fs->block_map = ctx->block_found_map;
1070                 clear_problem_context(&pctx);
1071                 pctx.errcode = ext2fs_create_resize_inode(fs);
1072                 if (pctx.errcode) {
1073                         fix_problem(ctx, PR_1_RESIZE_INODE_CREATE, &pctx);
1074                         /* Should never get here */
1075                         ctx->flags |= E2F_FLAG_ABORT;
1076                         return;
1077                 }
1078                 e2fsck_read_inode(ctx, EXT2_RESIZE_INO, inode,
1079                                   "recreate inode");
1080                 inode->i_mtime = ctx->now;
1081                 e2fsck_write_inode(ctx, EXT2_RESIZE_INO, inode, 
1082                                    "recreate inode");
1083                 fs->block_map = save_bmap;
1084                 ctx->flags &= ~E2F_FLAG_RESIZE_INODE;
1085         }
1086                        
1087         if (ctx->flags & E2F_FLAG_RESTART) {
1088                 /*
1089                  * Only the master copy of the superblock and block
1090                  * group descriptors are going to be written during a
1091                  * restart, so set the superblock to be used to be the
1092                  * master superblock.
1093                  */
1094                 ctx->use_superblock = 0;
1095                 unwind_pass1(fs);
1096                 goto endit;
1097         }
1098
1099         if (ctx->block_dup_map) {
1100                 if (ctx->options & E2F_OPT_PREEN) {
1101                         clear_problem_context(&pctx);
1102                         fix_problem(ctx, PR_1_DUP_BLOCKS_PREENSTOP, &pctx);
1103                 }
1104                 e2fsck_pass1_dupblocks(ctx, block_buf);
1105         }
1106         ext2fs_free_mem(&inodes_to_process);
1107 endit:
1108         e2fsck_use_inode_shortcuts(ctx, 0);
1109         
1110         ext2fs_free_mem(&block_buf);
1111         ext2fs_free_mem(&inode);
1112
1113 #ifdef RESOURCE_TRACK
1114         if (ctx->options & E2F_OPT_TIME2) {
1115                 e2fsck_clear_progbar(ctx);
1116                 print_resource_track(_("Pass 1"), &rtrack, ctx->fs->io);
1117         }
1118 #endif
1119 }
1120
1121 /*
1122  * When the inode_scan routines call this callback at the end of the
1123  * glock group, call process_inodes.
1124  */
1125 static errcode_t scan_callback(ext2_filsys fs, 
1126                                ext2_inode_scan scan EXT2FS_ATTR((unused)),
1127                                dgrp_t group, void * priv_data)
1128 {
1129         struct scan_callback_struct *scan_struct;
1130         e2fsck_t ctx;
1131
1132         scan_struct = (struct scan_callback_struct *) priv_data;
1133         ctx = scan_struct->ctx;
1134         
1135         process_inodes((e2fsck_t) fs->priv_data, scan_struct->block_buf);
1136
1137         if (ctx->progress)
1138                 if ((ctx->progress)(ctx, 1, group+1,
1139                                     ctx->fs->group_desc_count))
1140                         return EXT2_ET_CANCEL_REQUESTED;
1141
1142         return 0;
1143 }
1144
1145 /*
1146  * Process the inodes in the "inodes to process" list.
1147  */
1148 static void process_inodes(e2fsck_t ctx, char *block_buf)
1149 {
1150         int                     i;
1151         struct ext2_inode       *old_stashed_inode;
1152         ext2_ino_t              old_stashed_ino;
1153         const char              *old_operation;
1154         char                    buf[80];
1155         struct problem_context  pctx;
1156         
1157 #if 0
1158         printf("begin process_inodes: ");
1159 #endif
1160         if (process_inode_count == 0)
1161                 return;
1162         old_operation = ehandler_operation(0);
1163         old_stashed_inode = ctx->stashed_inode;
1164         old_stashed_ino = ctx->stashed_ino;
1165         qsort(inodes_to_process, process_inode_count,
1166                       sizeof(struct process_inode_block), process_inode_cmp);
1167         clear_problem_context(&pctx);
1168         for (i=0; i < process_inode_count; i++) {
1169                 pctx.inode = ctx->stashed_inode = &inodes_to_process[i].inode;
1170                 pctx.ino = ctx->stashed_ino = inodes_to_process[i].ino;
1171                 
1172 #if 0
1173                 printf("%u ", pctx.ino);
1174 #endif
1175                 sprintf(buf, _("reading indirect blocks of inode %u"),
1176                         pctx.ino);
1177                 ehandler_operation(buf);
1178                 check_blocks(ctx, &pctx, block_buf);
1179                 if (ctx->flags & E2F_FLAG_SIGNAL_MASK)
1180                         break;
1181         }
1182         ctx->stashed_inode = old_stashed_inode;
1183         ctx->stashed_ino = old_stashed_ino;
1184         process_inode_count = 0;
1185 #if 0
1186         printf("end process inodes\n");
1187 #endif
1188         ehandler_operation(old_operation);
1189 }
1190
1191 static EXT2_QSORT_TYPE process_inode_cmp(const void *a, const void *b)
1192 {
1193         const struct process_inode_block *ib_a =
1194                 (const struct process_inode_block *) a;
1195         const struct process_inode_block *ib_b =
1196                 (const struct process_inode_block *) b;
1197         int     ret;
1198         
1199         ret = (ib_a->inode.i_block[EXT2_IND_BLOCK] -
1200                ib_b->inode.i_block[EXT2_IND_BLOCK]);
1201         if (ret == 0)
1202                 ret = ib_a->inode.i_file_acl - ib_b->inode.i_file_acl;
1203         return ret;
1204 }
1205
1206 /*
1207  * Mark an inode as being bad in some what
1208  */
1209 static void mark_inode_bad(e2fsck_t ctx, ino_t ino)
1210 {
1211         struct          problem_context pctx;
1212
1213         if (!ctx->inode_bad_map) {
1214                 clear_problem_context(&pctx);
1215         
1216                 pctx.errcode = ext2fs_allocate_inode_bitmap(ctx->fs,
1217                             _("bad inode map"), &ctx->inode_bad_map);
1218                 if (pctx.errcode) {
1219                         pctx.num = 3;
1220                         fix_problem(ctx, PR_1_ALLOCATE_IBITMAP_ERROR, &pctx);
1221                         /* Should never get here */
1222                         ctx->flags |= E2F_FLAG_ABORT;
1223                         return;
1224                 }
1225         }
1226         ext2fs_mark_inode_bitmap(ctx->inode_bad_map, ino);
1227 }
1228
1229
1230 /*
1231  * This procedure will allocate the inode "bb" (badblock) map table
1232  */
1233 static void alloc_bb_map(e2fsck_t ctx)
1234 {
1235         struct          problem_context pctx;
1236         
1237         clear_problem_context(&pctx);
1238         pctx.errcode = ext2fs_allocate_inode_bitmap(ctx->fs,
1239                                               _("inode in bad block map"),
1240                                               &ctx->inode_bb_map);
1241         if (pctx.errcode) {
1242                 pctx.num = 4;
1243                 fix_problem(ctx, PR_1_ALLOCATE_IBITMAP_ERROR, &pctx);
1244                 /* Should never get here */
1245                 ctx->flags |= E2F_FLAG_ABORT;
1246                 return;
1247         }
1248 }
1249
1250 /*
1251  * This procedure will allocate the inode imagic table
1252  */
1253 static void alloc_imagic_map(e2fsck_t ctx)
1254 {
1255         struct          problem_context pctx;
1256         
1257         clear_problem_context(&pctx);
1258         pctx.errcode = ext2fs_allocate_inode_bitmap(ctx->fs,
1259                                               _("imagic inode map"),
1260                                               &ctx->inode_imagic_map);
1261         if (pctx.errcode) {
1262                 pctx.num = 5;
1263                 fix_problem(ctx, PR_1_ALLOCATE_IBITMAP_ERROR, &pctx);
1264                 /* Should never get here */
1265                 ctx->flags |= E2F_FLAG_ABORT;
1266                 return;
1267         }
1268 }
1269
1270 /*
1271  * Marks a block as in use, setting the dup_map if it's been set
1272  * already.  Called by process_block and process_bad_block.
1273  *
1274  * WARNING: Assumes checks have already been done to make sure block
1275  * is valid.  This is true in both process_block and process_bad_block.
1276  */
1277 static _INLINE_ void mark_block_used(e2fsck_t ctx, blk_t block)
1278 {
1279         struct          problem_context pctx;
1280         
1281         clear_problem_context(&pctx);
1282         
1283         if (ext2fs_fast_test_block_bitmap(ctx->block_found_map, block)) {
1284                 if (!ctx->block_dup_map) {
1285                         pctx.errcode = ext2fs_allocate_block_bitmap(ctx->fs,
1286                               _("multiply claimed block map"),
1287                               &ctx->block_dup_map);
1288                         if (pctx.errcode) {
1289                                 pctx.num = 3;
1290                                 fix_problem(ctx, PR_1_ALLOCATE_BBITMAP_ERROR, 
1291                                             &pctx);
1292                                 /* Should never get here */
1293                                 ctx->flags |= E2F_FLAG_ABORT;
1294                                 return;
1295                         }
1296                 }
1297                 ext2fs_fast_mark_block_bitmap(ctx->block_dup_map, block);
1298         } else {
1299                 ext2fs_fast_mark_block_bitmap(ctx->block_found_map, block);
1300         }
1301 }
1302
1303 /*
1304  * Adjust the extended attribute block's reference counts at the end
1305  * of pass 1, either by subtracting out references for EA blocks that
1306  * are still referenced in ctx->refcount, or by adding references for
1307  * EA blocks that had extra references as accounted for in
1308  * ctx->refcount_extra.
1309  */
1310 static void adjust_extattr_refcount(e2fsck_t ctx, ext2_refcount_t refcount, 
1311                                     char *block_buf, int adjust_sign)
1312 {
1313         struct ext2_ext_attr_header     *header;
1314         struct problem_context          pctx;
1315         ext2_filsys                     fs = ctx->fs;
1316         blk_t                           blk;
1317         __u32                           should_be;
1318         int                             count;
1319
1320         clear_problem_context(&pctx);
1321         
1322         ea_refcount_intr_begin(refcount);
1323         while (1) {
1324                 if ((blk = ea_refcount_intr_next(refcount, &count)) == 0)
1325                         break;
1326                 pctx.blk = blk;
1327                 pctx.errcode = ext2fs_read_ext_attr(fs, blk, block_buf);
1328                 if (pctx.errcode) {
1329                         fix_problem(ctx, PR_1_EXTATTR_READ_ABORT, &pctx);
1330                         return;
1331                 }
1332                 header = (struct ext2_ext_attr_header *) block_buf;
1333                 pctx.blkcount = header->h_refcount;
1334                 should_be = header->h_refcount + adjust_sign * count;
1335                 pctx.num = should_be;
1336                 if (fix_problem(ctx, PR_1_EXTATTR_REFCOUNT, &pctx)) {
1337                         header->h_refcount = should_be;
1338                         pctx.errcode = ext2fs_write_ext_attr(fs, blk,
1339                                                              block_buf);
1340                         if (pctx.errcode) {
1341                                 fix_problem(ctx, PR_1_EXTATTR_WRITE, &pctx);
1342                                 continue;
1343                         }
1344                 }
1345         }
1346 }
1347
1348 /*
1349  * Handle processing the extended attribute blocks
1350  */
1351 static int check_ext_attr(e2fsck_t ctx, struct problem_context *pctx,
1352                            char *block_buf)
1353 {
1354         ext2_filsys fs = ctx->fs;
1355         ext2_ino_t      ino = pctx->ino;
1356         struct ext2_inode *inode = pctx->inode;
1357         blk_t           blk;
1358         char *          end;
1359         struct ext2_ext_attr_header *header;
1360         struct ext2_ext_attr_entry *entry;
1361         int             count;
1362         region_t        region = 0;
1363
1364         blk = inode->i_file_acl;
1365         if (blk == 0)
1366                 return 0;
1367
1368         /*
1369          * If the Extended attribute flag isn't set, then a non-zero
1370          * file acl means that the inode is corrupted.
1371          *
1372          * Or if the extended attribute block is an invalid block,
1373          * then the inode is also corrupted.
1374          */
1375         if (!(fs->super->s_feature_compat & EXT2_FEATURE_COMPAT_EXT_ATTR) ||
1376             (blk < fs->super->s_first_data_block) ||
1377             (blk >= fs->super->s_blocks_count)) {
1378                 mark_inode_bad(ctx, ino);
1379                 return 0;
1380         }
1381
1382         /* If ea bitmap hasn't been allocated, create it */
1383         if (!ctx->block_ea_map) {
1384                 pctx->errcode = ext2fs_allocate_block_bitmap(fs,
1385                                                       _("ext attr block map"),
1386                                                       &ctx->block_ea_map);
1387                 if (pctx->errcode) {
1388                         pctx->num = 2;
1389                         fix_problem(ctx, PR_1_ALLOCATE_BBITMAP_ERROR, pctx);
1390                         ctx->flags |= E2F_FLAG_ABORT;
1391                         return 0;
1392                 }
1393         }
1394
1395         /* Create the EA refcount structure if necessary */
1396         if (!ctx->refcount) {
1397                 pctx->errcode = ea_refcount_create(0, &ctx->refcount);
1398                 if (pctx->errcode) {
1399                         pctx->num = 1;
1400                         fix_problem(ctx, PR_1_ALLOCATE_REFCOUNT, pctx);
1401                         ctx->flags |= E2F_FLAG_ABORT;
1402                         return 0;
1403                 }
1404         }
1405
1406 #if 0
1407         /* Debugging text */
1408         printf("Inode %u has EA block %u\n", ino, blk);
1409 #endif
1410
1411         /* Have we seen this EA block before? */
1412         if (ext2fs_fast_test_block_bitmap(ctx->block_ea_map, blk)) {
1413                 if (ea_refcount_decrement(ctx->refcount, blk, 0) == 0)
1414                         return 1;
1415                 /* Ooops, this EA was referenced more than it stated */
1416                 if (!ctx->refcount_extra) {
1417                         pctx->errcode = ea_refcount_create(0,
1418                                            &ctx->refcount_extra);
1419                         if (pctx->errcode) {
1420                                 pctx->num = 2;
1421                                 fix_problem(ctx, PR_1_ALLOCATE_REFCOUNT, pctx);
1422                                 ctx->flags |= E2F_FLAG_ABORT;
1423                                 return 0;
1424                         }
1425                 }
1426                 ea_refcount_increment(ctx->refcount_extra, blk, 0);
1427                 return 1;
1428         }
1429
1430         /*
1431          * OK, we haven't seen this EA block yet.  So we need to
1432          * validate it
1433          */
1434         pctx->blk = blk;
1435         pctx->errcode = ext2fs_read_ext_attr(fs, blk, block_buf);
1436         if (pctx->errcode && fix_problem(ctx, PR_1_READ_EA_BLOCK, pctx))
1437                 goto clear_extattr;
1438         header = (struct ext2_ext_attr_header *) block_buf;
1439         pctx->blk = inode->i_file_acl;
1440         if (((ctx->ext_attr_ver == 1) &&
1441              (header->h_magic != EXT2_EXT_ATTR_MAGIC_v1)) ||
1442             ((ctx->ext_attr_ver == 2) &&
1443              (header->h_magic != EXT2_EXT_ATTR_MAGIC))) {
1444                 if (fix_problem(ctx, PR_1_BAD_EA_BLOCK, pctx))
1445                         goto clear_extattr;
1446         }
1447
1448         if (header->h_blocks != 1) {
1449                 if (fix_problem(ctx, PR_1_EA_MULTI_BLOCK, pctx))
1450                         goto clear_extattr;
1451         }
1452
1453         region = region_create(0, fs->blocksize);
1454         if (!region) {
1455                 fix_problem(ctx, PR_1_EA_ALLOC_REGION, pctx);
1456                 ctx->flags |= E2F_FLAG_ABORT;
1457                 return 0;
1458         }
1459         if (region_allocate(region, 0, sizeof(struct ext2_ext_attr_header))) {
1460                 if (fix_problem(ctx, PR_1_EA_ALLOC_COLLISION, pctx))
1461                         goto clear_extattr;
1462         }
1463
1464         entry = (struct ext2_ext_attr_entry *)(header+1);
1465         end = block_buf + fs->blocksize;
1466         while ((char *)entry < end && *(__u32 *)entry) {
1467                 __u32 hash;
1468
1469                 if (region_allocate(region, (char *)entry - (char *)header,
1470                                    EXT2_EXT_ATTR_LEN(entry->e_name_len))) {
1471                         if (fix_problem(ctx, PR_1_EA_ALLOC_COLLISION, pctx))
1472                                 goto clear_extattr;
1473                         break;
1474                 }
1475                 if ((ctx->ext_attr_ver == 1 &&
1476                      (entry->e_name_len == 0 || entry->e_name_index != 0)) ||
1477                     (ctx->ext_attr_ver == 2 &&
1478                      entry->e_name_index == 0)) {
1479                         if (fix_problem(ctx, PR_1_EA_BAD_NAME, pctx))
1480                                 goto clear_extattr;
1481                         break;
1482                 }
1483                 if (entry->e_value_block != 0) {
1484                         if (fix_problem(ctx, PR_1_EA_BAD_VALUE, pctx))
1485                                 goto clear_extattr;
1486                 }
1487                 if (entry->e_value_offs + entry->e_value_size > fs->blocksize) {
1488                         if (fix_problem(ctx, PR_1_EA_BAD_VALUE, pctx))
1489                                 goto clear_extattr;
1490                         break;
1491                 }
1492                 if (entry->e_value_size &&
1493                     region_allocate(region, entry->e_value_offs,
1494                                     EXT2_EXT_ATTR_SIZE(entry->e_value_size))) {
1495                         if (fix_problem(ctx, PR_1_EA_ALLOC_COLLISION, pctx))
1496                                 goto clear_extattr;
1497                 }
1498
1499                 hash = ext2fs_ext_attr_hash_entry(entry, block_buf +
1500                                                          entry->e_value_offs);
1501
1502                 if (entry->e_hash != hash) {
1503                         pctx->num = entry->e_hash;
1504                         if (fix_problem(ctx, PR_1_ATTR_HASH, pctx))
1505                                 goto clear_extattr;
1506                         entry->e_hash = hash;
1507                 }
1508
1509                 entry = EXT2_EXT_ATTR_NEXT(entry);
1510         }
1511         if (region_allocate(region, (char *)entry - (char *)header, 4)) {
1512                 if (fix_problem(ctx, PR_1_EA_ALLOC_COLLISION, pctx))
1513                         goto clear_extattr;
1514         }
1515         region_free(region);
1516
1517         count = header->h_refcount - 1;
1518         if (count)
1519                 ea_refcount_store(ctx->refcount, blk, count);
1520         mark_block_used(ctx, blk);
1521         ext2fs_fast_mark_block_bitmap(ctx->block_ea_map, blk);
1522         return 1;
1523
1524 clear_extattr:
1525         if (region)
1526                 region_free(region);
1527         inode->i_file_acl = 0;
1528         e2fsck_write_inode(ctx, ino, inode, "check_ext_attr");
1529         return 0;
1530 }
1531
1532 /* Returns 1 if bad htree, 0 if OK */
1533 static int handle_htree(e2fsck_t ctx, struct problem_context *pctx,
1534                         ext2_ino_t ino, struct ext2_inode *inode,
1535                         char *block_buf)
1536 {
1537         struct ext2_dx_root_info        *root;
1538         ext2_filsys                     fs = ctx->fs;
1539         errcode_t                       retval;
1540         blk_t                           blk;
1541
1542         if ((!LINUX_S_ISDIR(inode->i_mode) &&
1543              fix_problem(ctx, PR_1_HTREE_NODIR, pctx)) ||
1544             (!(fs->super->s_feature_compat & EXT2_FEATURE_COMPAT_DIR_INDEX) &&
1545              fix_problem(ctx, PR_1_HTREE_SET, pctx)))
1546                 return 1;
1547
1548         pctx->errcode = ext2fs_bmap(fs, ino, inode, 0, 0, 0, &blk);
1549
1550         if ((pctx->errcode) ||
1551             (blk == 0) ||
1552             (blk < fs->super->s_first_data_block) ||
1553             (blk >= fs->super->s_blocks_count)) {
1554                 if (fix_problem(ctx, PR_1_HTREE_BADROOT, pctx))
1555                         return 1;
1556                 else
1557                         return 0;
1558         }
1559
1560         retval = io_channel_read_blk(fs->io, blk, 1, block_buf);
1561         if (retval && fix_problem(ctx, PR_1_HTREE_BADROOT, pctx))
1562                 return 1;
1563         
1564         /* XXX should check that beginning matches a directory */
1565         root = (struct ext2_dx_root_info *) (block_buf + 24);
1566
1567         if ((root->reserved_zero || root->info_length < 8) &&
1568             fix_problem(ctx, PR_1_HTREE_BADROOT, pctx))
1569                 return 1;
1570
1571         pctx->num = root->hash_version;
1572         if ((root->hash_version != EXT2_HASH_LEGACY) &&
1573             (root->hash_version != EXT2_HASH_HALF_MD4) &&
1574             (root->hash_version != EXT2_HASH_TEA) &&
1575             fix_problem(ctx, PR_1_HTREE_HASHV, pctx))
1576                 return 1;
1577                 
1578         if ((root->unused_flags & EXT2_HASH_FLAG_INCOMPAT) &&
1579             fix_problem(ctx, PR_1_HTREE_INCOMPAT, pctx))
1580                 return 1;
1581
1582         pctx->num = root->indirect_levels;
1583         if ((root->indirect_levels > 1) &&
1584             fix_problem(ctx, PR_1_HTREE_DEPTH, pctx))
1585                 return 1;
1586         
1587         return 0;
1588 }
1589
1590 void e2fsck_clear_inode(e2fsck_t ctx, ext2_ino_t ino,
1591                         struct ext2_inode *inode, int restart_flag,
1592                         const char *source)
1593 {
1594         inode->i_flags = 0;
1595         inode->i_links_count = 0;
1596         ext2fs_icount_store(ctx->inode_link_info, ino, 0);
1597         inode->i_dtime = ctx->now;
1598
1599         ext2fs_unmark_inode_bitmap(ctx->inode_dir_map, ino);
1600         ext2fs_unmark_inode_bitmap(ctx->inode_used_map, ino);
1601         if (ctx->inode_reg_map)
1602                 ext2fs_unmark_inode_bitmap(ctx->inode_reg_map, ino);
1603         if (ctx->inode_bad_map)
1604                 ext2fs_unmark_inode_bitmap(ctx->inode_bad_map, ino);
1605
1606         /*
1607          * If the inode was partially accounted for before processing
1608          * was aborted, we need to restart the pass 1 scan.
1609          */
1610         ctx->flags |= restart_flag;
1611
1612         e2fsck_write_inode(ctx, ino, inode, source);
1613 }
1614
1615 static void scan_extent_node(e2fsck_t ctx, struct problem_context *pctx,
1616                              struct process_block_struct *pb,
1617                              blk64_t start_block,
1618                              ext2_extent_handle_t ehandle)
1619 {
1620         struct ext2fs_extent    extent;
1621         blk_t                   blk;
1622         e2_blkcnt_t             blockcnt;
1623         unsigned int            i;
1624         int                     is_dir, is_leaf;
1625         errcode_t               problem;
1626         struct ext2_extent_info info;
1627
1628         pctx->errcode = ext2fs_extent_get_info(ehandle, &info);
1629         if (pctx->errcode)
1630                 return;
1631
1632         pctx->errcode = ext2fs_extent_get(ehandle, EXT2_EXTENT_FIRST_SIB,
1633                                           &extent);
1634         while (!pctx->errcode && info.num_entries-- > 0) {
1635                 is_leaf = extent.e_flags & EXT2_EXTENT_FLAGS_LEAF;
1636                 is_dir = LINUX_S_ISDIR(pctx->inode->i_mode);
1637
1638                 problem = 0;
1639                 if (extent.e_pblk < ctx->fs->super->s_first_data_block ||
1640                     extent.e_pblk >= ctx->fs->super->s_blocks_count)
1641                         problem = PR_1_EXTENT_BAD_START_BLK;
1642                 else if (extent.e_lblk < start_block)
1643                         problem = PR_1_OUT_OF_ORDER_EXTENTS;
1644                 else if (is_leaf &&
1645                          (extent.e_pblk + extent.e_len) >
1646                          ctx->fs->super->s_blocks_count)
1647                         problem = PR_1_EXTENT_ENDS_BEYOND;
1648
1649                 if (problem) {
1650                         pctx->blk = extent.e_pblk;
1651                         pctx->blk2 = extent.e_lblk;
1652                         pctx->num = extent.e_len;
1653                         if (fix_problem(ctx, problem, pctx)) {
1654                                 pctx->errcode =
1655                                         ext2fs_extent_delete(ehandle, 0);
1656                                 if (pctx->errcode) {
1657                                         fix_problem(ctx,
1658                                                     PR_1_EXTENT_DELETE_FAIL,
1659                                                     pctx);
1660                                         /* Should never get here */
1661                                         ctx->flags |= E2F_FLAG_ABORT;
1662                                         return;
1663                                 }
1664                                 pctx->errcode = ext2fs_extent_get(ehandle,
1665                                                                   EXT2_EXTENT_CURRENT,
1666                                                                   &extent);
1667                                 if (pctx->errcode == EXT2_ET_NO_CURRENT_NODE) {
1668                                         pctx->errcode = 0;
1669                                         break;
1670                                 }
1671                                 continue;
1672                         }
1673                         goto next;
1674                 }
1675
1676                 if (!is_leaf) {
1677                         mark_block_used(ctx, extent.e_pblk);
1678                         pb->num_blocks++;
1679                         pctx->errcode = ext2fs_extent_get(ehandle,
1680                                                   EXT2_EXTENT_DOWN, &extent);
1681                         if (pctx->errcode) {
1682                                 printf("Error1: %s on inode %u\n",
1683                                         error_message(pctx->errcode), pctx->ino);
1684                                 abort();
1685                         }
1686                         scan_extent_node(ctx, pctx, pb, extent.e_lblk, ehandle);
1687                         pctx->errcode = ext2fs_extent_get(ehandle,
1688                                                   EXT2_EXTENT_UP, &extent);
1689                         if (pctx->errcode) {
1690                                 printf("Error1: %s on inode %u\n",
1691                                         error_message(pctx->errcode), pctx->ino);
1692                                 abort();
1693                         }
1694                         goto next;
1695                 }
1696
1697                 for (blk = extent.e_pblk, blockcnt = extent.e_lblk, i = 0;
1698                      i < extent.e_len;
1699                      blk++, blockcnt++, i++) {
1700                         mark_block_used(ctx, blk);
1701
1702                         if (is_dir) {
1703                                 pctx->errcode = ext2fs_add_dir_block(ctx->fs->dblist, pctx->ino, blk, blockcnt);
1704                                 if (pctx->errcode) {
1705                                         pctx->blk = blk;
1706                                         pctx->num = blockcnt;
1707                                         fix_problem(ctx, PR_1_ADD_DBLOCK, pctx);
1708                                         /* Should never get here */
1709                                         ctx->flags |= E2F_FLAG_ABORT;
1710                                         return;
1711                                 }
1712                         }
1713                 }
1714                 pb->num_blocks += extent.e_len;
1715                 start_block = pb->last_block = extent.e_lblk + extent.e_len - 1;
1716         next:
1717                 pctx->errcode = ext2fs_extent_get(ehandle,
1718                                                   EXT2_EXTENT_NEXT_SIB,
1719                                                   &extent);
1720         }
1721         if (pctx->errcode == EXT2_ET_EXTENT_NO_NEXT)
1722                 pctx->errcode = 0;
1723 }
1724
1725 static void check_blocks_extents(e2fsck_t ctx, struct problem_context *pctx,
1726                                  struct process_block_struct *pb)
1727 {
1728         struct ext2_inode       *inode = pctx->inode;
1729         ext2_extent_handle_t    ehandle;
1730         ext2_filsys             fs = ctx->fs;
1731         ext2_ino_t              ino = pctx->ino;
1732
1733         pctx->errcode = ext2fs_extent_open(fs, ino, &ehandle);
1734         if (pctx->errcode &&
1735             fix_problem(ctx, PR_1_READ_EXTENT, pctx)) {
1736                 e2fsck_clear_inode(ctx, ino, inode, 0, "check_blocks_extents");
1737                 pctx->errcode = 0;
1738                 return;
1739         }
1740
1741         scan_extent_node(ctx, pctx, pb, 0, ehandle);
1742
1743         ext2fs_extent_free(ehandle);
1744 }
1745
1746 /*
1747  * This subroutine is called on each inode to account for all of the
1748  * blocks used by that inode.
1749  */
1750 static void check_blocks(e2fsck_t ctx, struct problem_context *pctx,
1751                          char *block_buf)
1752 {
1753         ext2_filsys fs = ctx->fs;
1754         struct process_block_struct pb;
1755         ext2_ino_t      ino = pctx->ino;
1756         struct ext2_inode *inode = pctx->inode;
1757         int             bad_size = 0;
1758         int             dirty_inode = 0;
1759         __u64           size;
1760         
1761         pb.ino = ino;
1762         pb.num_blocks = 0;
1763         pb.last_block = -1;
1764         pb.num_illegal_blocks = 0;
1765         pb.suppress = 0; pb.clear = 0;
1766         pb.fragmented = 0;
1767         pb.compressed = 0;
1768         pb.previous_block = 0;
1769         pb.is_dir = LINUX_S_ISDIR(inode->i_mode);
1770         pb.is_reg = LINUX_S_ISREG(inode->i_mode);
1771         pb.max_blocks = 1 << (31 - fs->super->s_log_block_size);
1772         pb.inode = inode;
1773         pb.pctx = pctx;
1774         pb.ctx = ctx;
1775         pctx->ino = ino;
1776         pctx->errcode = 0;
1777
1778         if (inode->i_flags & EXT2_COMPRBLK_FL) {
1779                 if (fs->super->s_feature_incompat &
1780                     EXT2_FEATURE_INCOMPAT_COMPRESSION)
1781                         pb.compressed = 1;
1782                 else {
1783                         if (fix_problem(ctx, PR_1_COMPR_SET, pctx)) {
1784                                 inode->i_flags &= ~EXT2_COMPRBLK_FL;
1785                                 dirty_inode++;
1786                         }
1787                 }
1788         }
1789
1790         if (inode->i_file_acl && check_ext_attr(ctx, pctx, block_buf)) {
1791                 if (ctx->flags & E2F_FLAG_SIGNAL_MASK)
1792                         goto out;
1793                 pb.num_blocks++;
1794         }
1795
1796         if (ext2fs_inode_has_valid_blocks(inode)) {
1797                 if ((ctx->fs->super->s_feature_incompat &
1798                      EXT3_FEATURE_INCOMPAT_EXTENTS) &&
1799                     (inode->i_flags & EXT4_EXTENTS_FL))
1800                         check_blocks_extents(ctx, pctx, &pb);
1801                 else
1802                         pctx->errcode = ext2fs_block_iterate2(fs, ino,
1803                                                 pb.is_dir ? BLOCK_FLAG_HOLE : 0,
1804                                                 block_buf, process_block, &pb);
1805         }
1806         end_problem_latch(ctx, PR_LATCH_BLOCK);
1807         end_problem_latch(ctx, PR_LATCH_TOOBIG);
1808         if (ctx->flags & E2F_FLAG_SIGNAL_MASK)
1809                 goto out;
1810         if (pctx->errcode)
1811                 fix_problem(ctx, PR_1_BLOCK_ITERATE, pctx);
1812
1813         if (pb.fragmented && pb.num_blocks < fs->super->s_blocks_per_group)
1814                 ctx->fs_fragmented++;
1815
1816         if (pb.clear) {
1817                 e2fsck_clear_inode(ctx, ino, inode, E2F_FLAG_RESTART,
1818                                    "check_blocks");
1819                 return;
1820         }
1821         
1822         if (pb.is_dir) {
1823                 while (1) {
1824                         struct ext2_db_entry *entry;
1825
1826                         if (ext2fs_dblist_get_last(fs->dblist, &entry) ||
1827                             (entry->ino != ino) ||
1828                             (entry->blk != 0) ||
1829                             (entry->blockcnt == 0))
1830                                 break;
1831                         /* printf("Dropping ino %lu blk %lu blockcnt %d\n", 
1832                                   entry->ino, entry->blk, entry->blockcnt); */
1833                         ext2fs_dblist_drop_last(fs->dblist);
1834                         if (ext2fs_dblist_get_last(fs->dblist, &entry) ||
1835                             (entry->ino != ino))
1836                                 pb.last_block--;
1837                         else
1838                                 pb.last_block = entry->blockcnt;
1839                 }
1840         }
1841
1842         if (inode->i_flags & EXT2_INDEX_FL) {
1843                 if (handle_htree(ctx, pctx, ino, inode, block_buf)) {
1844                         inode->i_flags &= ~EXT2_INDEX_FL;
1845                         dirty_inode++;
1846                 } else {
1847 #ifdef ENABLE_HTREE
1848                         e2fsck_add_dx_dir(ctx, ino, pb.last_block+1);
1849 #endif
1850                 }
1851         }
1852         if (ctx->dirs_to_hash && pb.is_dir &&
1853             !(inode->i_flags & EXT2_INDEX_FL) &&
1854             ((inode->i_size / fs->blocksize) >= 3))
1855                 ext2fs_u32_list_add(ctx->dirs_to_hash, ino);
1856                 
1857         if (!pb.num_blocks && pb.is_dir) {
1858                 if (fix_problem(ctx, PR_1_ZERO_LENGTH_DIR, pctx)) {
1859                         e2fsck_clear_inode(ctx, ino, inode, 0, "check_blocks");
1860                         ctx->fs_directory_count--;
1861                         return;
1862                 }
1863         }
1864
1865         if (!(fs->super->s_feature_ro_compat &
1866               EXT4_FEATURE_RO_COMPAT_HUGE_FILE) ||
1867             !(inode->i_flags & EXT4_HUGE_FILE_FL))
1868                 pb.num_blocks *= (fs->blocksize / 512);
1869 #if 0
1870         printf("inode %u, i_size = %lu, last_block = %lld, i_blocks=%lu, num_blocks = %lu\n",
1871                ino, inode->i_size, pb.last_block, inode->i_blocks,
1872                pb.num_blocks);
1873 #endif
1874         if (pb.is_dir) {
1875                 int nblock = inode->i_size >> EXT2_BLOCK_SIZE_BITS(fs->super);
1876                 if (inode->i_size & (fs->blocksize - 1)) 
1877                         bad_size = 5;
1878                 else if (nblock > (pb.last_block + 1))
1879                         bad_size = 1;
1880                 else if (nblock < (pb.last_block + 1)) {
1881                         if (((pb.last_block + 1) - nblock) >
1882                             fs->super->s_prealloc_dir_blocks)
1883                                 bad_size = 2;
1884                 }
1885         } else {
1886                 e2_blkcnt_t blkpg = ctx->blocks_per_page;
1887
1888                 size = EXT2_I_SIZE(inode);
1889                 if ((pb.last_block >= 0) &&
1890                     /* allow allocated blocks to end of PAGE_SIZE */
1891                     (size < (__u64)pb.last_block * fs->blocksize) &&
1892                     (pb.last_block / blkpg * blkpg != pb.last_block ||
1893                      size < (__u64)(pb.last_block & ~(blkpg-1)) *fs->blocksize))
1894                         bad_size = 3;
1895                 else if (size > ext2_max_sizes[fs->super->s_log_block_size])
1896                         bad_size = 4;
1897         }
1898         /* i_size for symlinks is checked elsewhere */
1899         if (bad_size && !LINUX_S_ISLNK(inode->i_mode)) {
1900                 pctx->num = (pb.last_block+1) * fs->blocksize;
1901                 if (fix_problem(ctx, PR_1_BAD_I_SIZE, pctx)) {
1902                         inode->i_size = pctx->num;
1903                         if (!LINUX_S_ISDIR(inode->i_mode))
1904                                 inode->i_size_high = pctx->num >> 32;
1905                         dirty_inode++;
1906                 }
1907                 pctx->num = 0;
1908         }
1909         if (LINUX_S_ISREG(inode->i_mode) &&
1910             (inode->i_size_high || inode->i_size & 0x80000000UL))
1911                 ctx->large_files++;
1912         if ((pb.num_blocks != inode->i_blocks) ||
1913             ((fs->super->s_feature_ro_compat &
1914               EXT4_FEATURE_RO_COMPAT_HUGE_FILE) &&
1915              (inode->i_flags & EXT4_HUGE_FILE_FL) &&
1916              (inode->osd2.linux2.l_i_blocks_hi != 0))) {
1917                 pctx->num = pb.num_blocks;
1918                 if (fix_problem(ctx, PR_1_BAD_I_BLOCKS, pctx)) {
1919                         inode->i_blocks = pb.num_blocks;
1920                         inode->osd2.linux2.l_i_blocks_hi = 0;
1921                         dirty_inode++;
1922                 }
1923                 pctx->num = 0;
1924         }
1925 out:
1926         if (dirty_inode)
1927                 e2fsck_write_inode(ctx, ino, inode, "check_blocks");
1928 }
1929
1930 #if 0
1931 /*
1932  * Helper function called by process block when an illegal block is
1933  * found.  It returns a description about why the block is illegal
1934  */
1935 static char *describe_illegal_block(ext2_filsys fs, blk_t block)
1936 {
1937         blk_t   super;
1938         int     i;
1939         static char     problem[80];
1940
1941         super = fs->super->s_first_data_block;
1942         strcpy(problem, "PROGRAMMING ERROR: Unknown reason for illegal block");
1943         if (block < super) {
1944                 sprintf(problem, "< FIRSTBLOCK (%u)", super);
1945                 return(problem);
1946         } else if (block >= fs->super->s_blocks_count) {
1947                 sprintf(problem, "> BLOCKS (%u)", fs->super->s_blocks_count);
1948                 return(problem);
1949         }
1950         for (i = 0; i < fs->group_desc_count; i++) {
1951                 if (block == super) {
1952                         sprintf(problem, "is the superblock in group %d", i);
1953                         break;
1954                 }
1955                 if (block > super &&
1956                     block <= (super + fs->desc_blocks)) {
1957                         sprintf(problem, "is in the group descriptors "
1958                                 "of group %d", i);
1959                         break;
1960                 }
1961                 if (block == fs->group_desc[i].bg_block_bitmap) {
1962                         sprintf(problem, "is the block bitmap of group %d", i);
1963                         break;
1964                 }
1965                 if (block == fs->group_desc[i].bg_inode_bitmap) {
1966                         sprintf(problem, "is the inode bitmap of group %d", i);
1967                         break;
1968                 }
1969                 if (block >= fs->group_desc[i].bg_inode_table &&
1970                     (block < fs->group_desc[i].bg_inode_table
1971                      + fs->inode_blocks_per_group)) {
1972                         sprintf(problem, "is in the inode table of group %d",
1973                                 i);
1974                         break;
1975                 }
1976                 super += fs->super->s_blocks_per_group;
1977         }
1978         return(problem);
1979 }
1980 #endif
1981
1982 /*
1983  * This is a helper function for check_blocks().
1984  */
1985 static int process_block(ext2_filsys fs,
1986                   blk_t *block_nr,
1987                   e2_blkcnt_t blockcnt,
1988                   blk_t ref_block EXT2FS_ATTR((unused)),
1989                   int ref_offset EXT2FS_ATTR((unused)),
1990                   void *priv_data)
1991 {
1992         struct process_block_struct *p;
1993         struct problem_context *pctx;
1994         blk_t   blk = *block_nr;
1995         int     ret_code = 0;
1996         int     problem = 0;
1997         e2fsck_t        ctx;
1998
1999         p = (struct process_block_struct *) priv_data;
2000         pctx = p->pctx;
2001         ctx = p->ctx;
2002
2003         if (p->compressed && (blk == EXT2FS_COMPRESSED_BLKADDR)) {
2004                 /* todo: Check that the comprblk_fl is high, that the
2005                    blkaddr pattern looks right (all non-holes up to
2006                    first EXT2FS_COMPRESSED_BLKADDR, then all
2007                    EXT2FS_COMPRESSED_BLKADDR up to end of cluster),
2008                    that the feature_incompat bit is high, and that the
2009                    inode is a regular file.  If we're doing a "full
2010                    check" (a concept introduced to e2fsck by e2compr,
2011                    meaning that we look at data blocks as well as
2012                    metadata) then call some library routine that
2013                    checks the compressed data.  I'll have to think
2014                    about this, because one particularly important
2015                    problem to be able to fix is to recalculate the
2016                    cluster size if necessary.  I think that perhaps
2017                    we'd better do most/all e2compr-specific checks
2018                    separately, after the non-e2compr checks.  If not
2019                    doing a full check, it may be useful to test that
2020                    the personality is linux; e.g. if it isn't then
2021                    perhaps this really is just an illegal block. */
2022                 return 0;
2023         }
2024
2025         if (blk == 0) {
2026                 if (p->is_dir == 0) {
2027                         /*
2028                          * Should never happen, since only directories
2029                          * get called with BLOCK_FLAG_HOLE
2030                          */
2031 #if DEBUG_E2FSCK
2032                         printf("process_block() called with blk == 0, "
2033                                "blockcnt=%d, inode %lu???\n",
2034                                blockcnt, p->ino);
2035 #endif
2036                         return 0;
2037                 }
2038                 if (blockcnt < 0)
2039                         return 0;
2040                 if (blockcnt * fs->blocksize < p->inode->i_size) {
2041 #if 0
2042                         printf("Missing block (#%d) in directory inode %lu!\n",
2043                                blockcnt, p->ino);
2044 #endif
2045                         p->last_block = blockcnt;
2046                         goto mark_dir;
2047                 }
2048                 return 0;
2049         }
2050
2051 #if 0
2052         printf("Process_block, inode %lu, block %u, #%d\n", p->ino, blk,
2053                blockcnt);
2054 #endif
2055         
2056         /*
2057          * Simplistic fragmentation check.  We merely require that the
2058          * file be contiguous.  (Which can never be true for really
2059          * big files that are greater than a block group.)
2060          */
2061         if (!HOLE_BLKADDR(p->previous_block)) {
2062                 if (p->previous_block+1 != blk)
2063                         p->fragmented = 1;
2064         }
2065         p->previous_block = blk;
2066
2067         if (p->is_dir && blockcnt > (1 << (21 - fs->super->s_log_block_size)))
2068                 problem = PR_1_TOOBIG_DIR;
2069         if (p->is_reg && p->num_blocks+1 >= p->max_blocks)
2070                 problem = PR_1_TOOBIG_REG;
2071         if (!p->is_dir && !p->is_reg && blockcnt > 0)
2072                 problem = PR_1_TOOBIG_SYMLINK;
2073             
2074         if (blk < fs->super->s_first_data_block ||
2075             blk >= fs->super->s_blocks_count)
2076                 problem = PR_1_ILLEGAL_BLOCK_NUM;
2077
2078         if (problem) {
2079                 p->num_illegal_blocks++;
2080                 if (!p->suppress && (p->num_illegal_blocks % 12) == 0) {
2081                         if (fix_problem(ctx, PR_1_TOO_MANY_BAD_BLOCKS, pctx)) {
2082                                 p->clear = 1;
2083                                 return BLOCK_ABORT;
2084                         }
2085                         if (fix_problem(ctx, PR_1_SUPPRESS_MESSAGES, pctx)) {
2086                                 p->suppress = 1;
2087                                 set_latch_flags(PR_LATCH_BLOCK,
2088                                                 PRL_SUPPRESS, 0);
2089                         }
2090                 }
2091                 pctx->blk = blk;
2092                 pctx->blkcount = blockcnt;
2093                 if (fix_problem(ctx, problem, pctx)) {
2094                         blk = *block_nr = 0;
2095                         ret_code = BLOCK_CHANGED;
2096                         goto mark_dir;
2097                 } else
2098                         return 0;
2099         }
2100
2101         if (p->ino == EXT2_RESIZE_INO) {
2102                 /* 
2103                  * The resize inode has already be sanity checked
2104                  * during pass #0 (the superblock checks).  All we
2105                  * have to do is mark the double indirect block as
2106                  * being in use; all of the other blocks are handled
2107                  * by mark_table_blocks()).
2108                  */
2109                 if (blockcnt == BLOCK_COUNT_DIND)
2110                         mark_block_used(ctx, blk);
2111         } else
2112                 mark_block_used(ctx, blk);
2113         p->num_blocks++;
2114         if (blockcnt >= 0)
2115                 p->last_block = blockcnt;
2116 mark_dir:
2117         if (p->is_dir && (blockcnt >= 0)) {
2118                 pctx->errcode = ext2fs_add_dir_block(fs->dblist, p->ino,
2119                                                     blk, blockcnt);
2120                 if (pctx->errcode) {
2121                         pctx->blk = blk;
2122                         pctx->num = blockcnt;
2123                         fix_problem(ctx, PR_1_ADD_DBLOCK, pctx);
2124                         /* Should never get here */
2125                         ctx->flags |= E2F_FLAG_ABORT;
2126                         return BLOCK_ABORT;
2127                 }
2128         }
2129         return ret_code;
2130 }
2131
2132 static int process_bad_block(ext2_filsys fs,
2133                       blk_t *block_nr,
2134                       e2_blkcnt_t blockcnt,
2135                       blk_t ref_block EXT2FS_ATTR((unused)),
2136                       int ref_offset EXT2FS_ATTR((unused)),
2137                       void *priv_data)
2138 {
2139         struct process_block_struct *p;
2140         blk_t           blk = *block_nr;
2141         blk_t           first_block;
2142         dgrp_t          i;
2143         struct problem_context *pctx;
2144         e2fsck_t        ctx;
2145
2146         /*
2147          * Note: This function processes blocks for the bad blocks
2148          * inode, which is never compressed.  So we don't use HOLE_BLKADDR().
2149          */
2150
2151         if (!blk)
2152                 return 0;
2153         
2154         p = (struct process_block_struct *) priv_data;
2155         ctx = p->ctx;
2156         pctx = p->pctx;
2157         
2158         pctx->ino = EXT2_BAD_INO;
2159         pctx->blk = blk;
2160         pctx->blkcount = blockcnt;
2161
2162         if ((blk < fs->super->s_first_data_block) ||
2163             (blk >= fs->super->s_blocks_count)) {
2164                 if (fix_problem(ctx, PR_1_BB_ILLEGAL_BLOCK_NUM, pctx)) {
2165                         *block_nr = 0;
2166                         return BLOCK_CHANGED;
2167                 } else
2168                         return 0;
2169         }
2170
2171         if (blockcnt < 0) {
2172                 if (ext2fs_test_block_bitmap(p->fs_meta_blocks, blk)) {
2173                         p->bbcheck = 1;
2174                         if (fix_problem(ctx, PR_1_BB_FS_BLOCK, pctx)) {
2175                                 *block_nr = 0;
2176                                 return BLOCK_CHANGED;
2177                         }
2178                 } else if (ext2fs_test_block_bitmap(ctx->block_found_map, 
2179                                                     blk)) {
2180                         p->bbcheck = 1;
2181                         if (fix_problem(ctx, PR_1_BBINODE_BAD_METABLOCK, 
2182                                         pctx)) {
2183                                 *block_nr = 0;
2184                                 return BLOCK_CHANGED;
2185                         }
2186                         if (ctx->flags & E2F_FLAG_SIGNAL_MASK)
2187                                 return BLOCK_ABORT;
2188                 } else
2189                         mark_block_used(ctx, blk);
2190                 return 0;
2191         }
2192 #if 0 
2193         printf ("DEBUG: Marking %u as bad.\n", blk);
2194 #endif
2195         ctx->fs_badblocks_count++;
2196         /*
2197          * If the block is not used, then mark it as used and return.
2198          * If it is already marked as found, this must mean that
2199          * there's an overlap between the filesystem table blocks
2200          * (bitmaps and inode table) and the bad block list.
2201          */
2202         if (!ext2fs_test_block_bitmap(ctx->block_found_map, blk)) {
2203                 ext2fs_mark_block_bitmap(ctx->block_found_map, blk);
2204                 return 0;
2205         }
2206         /*
2207          * Try to find the where the filesystem block was used...
2208          */
2209         first_block = fs->super->s_first_data_block;
2210         
2211         for (i = 0; i < fs->group_desc_count; i++ ) {
2212                 pctx->group = i;
2213                 pctx->blk = blk;
2214                 if (!ext2fs_bg_has_super(fs, i))
2215                         goto skip_super;
2216                 if (blk == first_block) {
2217                         if (i == 0) {
2218                                 if (fix_problem(ctx,
2219                                                 PR_1_BAD_PRIMARY_SUPERBLOCK,
2220                                                 pctx)) {
2221                                         *block_nr = 0;
2222                                         return BLOCK_CHANGED;
2223                                 }
2224                                 return 0;
2225                         }
2226                         fix_problem(ctx, PR_1_BAD_SUPERBLOCK, pctx);
2227                         return 0;
2228                 }
2229                 if ((blk > first_block) &&
2230                     (blk <= first_block + fs->desc_blocks)) {
2231                         if (i == 0) {
2232                                 pctx->blk = *block_nr;
2233                                 if (fix_problem(ctx,
2234                         PR_1_BAD_PRIMARY_GROUP_DESCRIPTOR, pctx)) {
2235                                         *block_nr = 0;
2236                                         return BLOCK_CHANGED;
2237                                 }
2238                                 return 0;
2239                         }
2240                         fix_problem(ctx, PR_1_BAD_GROUP_DESCRIPTORS, pctx);
2241                         return 0;
2242                 }
2243         skip_super:
2244                 if (blk == fs->group_desc[i].bg_block_bitmap) {
2245                         if (fix_problem(ctx, PR_1_BB_BAD_BLOCK, pctx)) {
2246                                 ctx->invalid_block_bitmap_flag[i]++;
2247                                 ctx->invalid_bitmaps++;
2248                         }
2249                         return 0;
2250                 }
2251                 if (blk == fs->group_desc[i].bg_inode_bitmap) {
2252                         if (fix_problem(ctx, PR_1_IB_BAD_BLOCK, pctx)) {
2253                                 ctx->invalid_inode_bitmap_flag[i]++;
2254                                 ctx->invalid_bitmaps++;
2255                         }
2256                         return 0;
2257                 }
2258                 if ((blk >= fs->group_desc[i].bg_inode_table) &&
2259                     (blk < (fs->group_desc[i].bg_inode_table +
2260                             fs->inode_blocks_per_group))) {
2261                         /*
2262                          * If there are bad blocks in the inode table,
2263                          * the inode scan code will try to do
2264                          * something reasonable automatically.
2265                          */
2266                         return 0;
2267                 }
2268                 first_block += fs->super->s_blocks_per_group;
2269         }
2270         /*
2271          * If we've gotten to this point, then the only
2272          * possibility is that the bad block inode meta data
2273          * is using a bad block.
2274          */
2275         if ((blk == p->inode->i_block[EXT2_IND_BLOCK]) ||
2276             (blk == p->inode->i_block[EXT2_DIND_BLOCK]) ||
2277             (blk == p->inode->i_block[EXT2_TIND_BLOCK])) {
2278                 p->bbcheck = 1;
2279                 if (fix_problem(ctx, PR_1_BBINODE_BAD_METABLOCK, pctx)) {
2280                         *block_nr = 0;
2281                         return BLOCK_CHANGED;
2282                 }
2283                 if (ctx->flags & E2F_FLAG_SIGNAL_MASK)
2284                         return BLOCK_ABORT;
2285                 return 0;
2286         }
2287
2288         pctx->group = -1;
2289
2290         /* Warn user that the block wasn't claimed */
2291         fix_problem(ctx, PR_1_PROGERR_CLAIMED_BLOCK, pctx);
2292
2293         return 0;
2294 }
2295
2296 static void new_table_block(e2fsck_t ctx, blk_t first_block, int group, 
2297                             const char *name, int num, blk_t *new_block)
2298 {
2299         ext2_filsys fs = ctx->fs;
2300         blk_t           old_block = *new_block;
2301         blk_t           last_block;
2302         int             i;
2303         char            *buf;
2304         struct problem_context  pctx;
2305
2306         clear_problem_context(&pctx);
2307
2308         pctx.group = group;
2309         pctx.blk = old_block;
2310         pctx.str = name;
2311
2312         last_block = ext2fs_group_last_block(fs, group);
2313         pctx.errcode = ext2fs_get_free_blocks(fs, first_block, last_block,
2314                                         num, ctx->block_found_map, new_block);
2315         if (pctx.errcode) {
2316                 pctx.num = num;
2317                 fix_problem(ctx, PR_1_RELOC_BLOCK_ALLOCATE, &pctx);
2318                 ext2fs_unmark_valid(fs);
2319                 return;
2320         }
2321         pctx.errcode = ext2fs_get_mem(fs->blocksize, &buf);
2322         if (pctx.errcode) {
2323                 fix_problem(ctx, PR_1_RELOC_MEMORY_ALLOCATE, &pctx);
2324                 ext2fs_unmark_valid(fs);
2325                 return;
2326         }
2327         ext2fs_mark_super_dirty(fs);
2328         fs->flags &= ~EXT2_FLAG_MASTER_SB_ONLY;
2329         pctx.blk2 = *new_block;
2330         fix_problem(ctx, (old_block ? PR_1_RELOC_FROM_TO :
2331                           PR_1_RELOC_TO), &pctx);
2332         pctx.blk2 = 0;
2333         for (i = 0; i < num; i++) {
2334                 pctx.blk = i;
2335                 ext2fs_mark_block_bitmap(ctx->block_found_map, (*new_block)+i);
2336                 if (old_block) {
2337                         pctx.errcode = io_channel_read_blk(fs->io,
2338                                    old_block + i, 1, buf);
2339                         if (pctx.errcode)
2340                                 fix_problem(ctx, PR_1_RELOC_READ_ERR, &pctx);
2341                 } else
2342                         memset(buf, 0, fs->blocksize);
2343
2344                 pctx.blk = (*new_block) + i;
2345                 pctx.errcode = io_channel_write_blk(fs->io, pctx.blk,
2346                                               1, buf);
2347                 if (pctx.errcode)
2348                         fix_problem(ctx, PR_1_RELOC_WRITE_ERR, &pctx);
2349         }
2350         ext2fs_free_mem(&buf);
2351 }
2352
2353 /*
2354  * This routine gets called at the end of pass 1 if bad blocks are
2355  * detected in the superblock, group descriptors, inode_bitmaps, or
2356  * block bitmaps.  At this point, all of the blocks have been mapped
2357  * out, so we can try to allocate new block(s) to replace the bad
2358  * blocks.
2359  */
2360 static void handle_fs_bad_blocks(e2fsck_t ctx)
2361 {
2362         ext2_filsys fs = ctx->fs;
2363         dgrp_t          i;
2364         blk_t           first_block;
2365
2366         for (i = 0; i < fs->group_desc_count; i++) {
2367                 first_block = ext2fs_group_first_block(fs, i);
2368
2369                 if (ctx->invalid_block_bitmap_flag[i]) {
2370                         new_table_block(ctx, first_block, i, _("block bitmap"),
2371                                         1, &fs->group_desc[i].bg_block_bitmap);
2372                 }
2373                 if (ctx->invalid_inode_bitmap_flag[i]) {
2374                         new_table_block(ctx, first_block, i, _("inode bitmap"),
2375                                         1, &fs->group_desc[i].bg_inode_bitmap);
2376                 }
2377                 if (ctx->invalid_inode_table_flag[i]) {
2378                         new_table_block(ctx, first_block, i, _("inode table"),
2379                                         fs->inode_blocks_per_group, 
2380                                         &fs->group_desc[i].bg_inode_table);
2381                         ctx->flags |= E2F_FLAG_RESTART;
2382                 }
2383         }
2384         ctx->invalid_bitmaps = 0;
2385 }
2386
2387 /*
2388  * This routine marks all blocks which are used by the superblock,
2389  * group descriptors, inode bitmaps, and block bitmaps.
2390  */
2391 static void mark_table_blocks(e2fsck_t ctx)
2392 {
2393         ext2_filsys fs = ctx->fs;
2394         blk_t   b;
2395         dgrp_t  i;
2396         int     j;
2397         struct problem_context pctx;
2398         
2399         clear_problem_context(&pctx);
2400         
2401         for (i = 0; i < fs->group_desc_count; i++) {
2402                 pctx.group = i;
2403
2404                 ext2fs_reserve_super_and_bgd(fs, i, ctx->block_found_map);
2405
2406                 /*
2407                  * Mark the blocks used for the inode table
2408                  */
2409                 if (fs->group_desc[i].bg_inode_table) {
2410                         for (j = 0, b = fs->group_desc[i].bg_inode_table;
2411                              j < fs->inode_blocks_per_group;
2412                              j++, b++) {
2413                                 if (ext2fs_test_block_bitmap(ctx->block_found_map,
2414                                                              b)) {
2415                                         pctx.blk = b;
2416                                         if (fix_problem(ctx,
2417                                                 PR_1_ITABLE_CONFLICT, &pctx)) {
2418                                                 ctx->invalid_inode_table_flag[i]++;
2419                                                 ctx->invalid_bitmaps++;
2420                                         }
2421                                 } else {
2422                                     ext2fs_mark_block_bitmap(ctx->block_found_map,
2423                                                              b);
2424                                 }
2425                         }
2426                 }
2427                             
2428                 /*
2429                  * Mark block used for the block bitmap 
2430                  */
2431                 if (fs->group_desc[i].bg_block_bitmap) {
2432                         if (ext2fs_test_block_bitmap(ctx->block_found_map,
2433                                      fs->group_desc[i].bg_block_bitmap)) {
2434                                 pctx.blk = fs->group_desc[i].bg_block_bitmap;
2435                                 if (fix_problem(ctx, PR_1_BB_CONFLICT, &pctx)) {
2436                                         ctx->invalid_block_bitmap_flag[i]++;
2437                                         ctx->invalid_bitmaps++;
2438                                 }
2439                         } else {
2440                             ext2fs_mark_block_bitmap(ctx->block_found_map,
2441                                      fs->group_desc[i].bg_block_bitmap);
2442                     }
2443                         
2444                 }
2445                 /*
2446                  * Mark block used for the inode bitmap 
2447                  */
2448                 if (fs->group_desc[i].bg_inode_bitmap) {
2449                         if (ext2fs_test_block_bitmap(ctx->block_found_map,
2450                                      fs->group_desc[i].bg_inode_bitmap)) {
2451                                 pctx.blk = fs->group_desc[i].bg_inode_bitmap;
2452                                 if (fix_problem(ctx, PR_1_IB_CONFLICT, &pctx)) {
2453                                         ctx->invalid_inode_bitmap_flag[i]++;
2454                                         ctx->invalid_bitmaps++;
2455                                 } 
2456                         } else {
2457                             ext2fs_mark_block_bitmap(ctx->block_found_map,
2458                                      fs->group_desc[i].bg_inode_bitmap);
2459                         }
2460                 }
2461         }
2462 }
2463         
2464 /*
2465  * Thes subroutines short circuits ext2fs_get_blocks and
2466  * ext2fs_check_directory; we use them since we already have the inode
2467  * structure, so there's no point in letting the ext2fs library read
2468  * the inode again.
2469  */
2470 static errcode_t pass1_get_blocks(ext2_filsys fs, ext2_ino_t ino,
2471                                   blk_t *blocks)
2472 {
2473         e2fsck_t ctx = (e2fsck_t) fs->priv_data;
2474         int     i;
2475         
2476         if ((ino != ctx->stashed_ino) || !ctx->stashed_inode)
2477                 return EXT2_ET_CALLBACK_NOTHANDLED;
2478
2479         for (i=0; i < EXT2_N_BLOCKS; i++)
2480                 blocks[i] = ctx->stashed_inode->i_block[i];
2481         return 0;
2482 }
2483
2484 static errcode_t pass1_read_inode(ext2_filsys fs, ext2_ino_t ino,
2485                                   struct ext2_inode *inode)
2486 {
2487         e2fsck_t ctx = (e2fsck_t) fs->priv_data;
2488
2489         if ((ino != ctx->stashed_ino) || !ctx->stashed_inode)
2490                 return EXT2_ET_CALLBACK_NOTHANDLED;
2491         *inode = *ctx->stashed_inode;
2492         return 0;
2493 }
2494
2495 static errcode_t pass1_write_inode(ext2_filsys fs, ext2_ino_t ino,
2496                             struct ext2_inode *inode)
2497 {
2498         e2fsck_t ctx = (e2fsck_t) fs->priv_data;
2499
2500         if ((ino == ctx->stashed_ino) && ctx->stashed_inode &&
2501                 (inode != ctx->stashed_inode))
2502                 *ctx->stashed_inode = *inode;
2503         return EXT2_ET_CALLBACK_NOTHANDLED;
2504 }
2505
2506 static errcode_t pass1_check_directory(ext2_filsys fs, ext2_ino_t ino)
2507 {
2508         e2fsck_t ctx = (e2fsck_t) fs->priv_data;
2509
2510         if ((ino != ctx->stashed_ino) || !ctx->stashed_inode)
2511                 return EXT2_ET_CALLBACK_NOTHANDLED;
2512
2513         if (!LINUX_S_ISDIR(ctx->stashed_inode->i_mode))
2514                 return EXT2_ET_NO_DIRECTORY;
2515         return 0;
2516 }
2517
2518 static errcode_t e2fsck_get_alloc_block(ext2_filsys fs, blk64_t goal,
2519                                         blk64_t *ret)
2520 {
2521         e2fsck_t ctx = (e2fsck_t) fs->priv_data;
2522         errcode_t       retval;
2523         blk_t           new_block;
2524
2525         if (ctx->block_found_map) {
2526                 retval = ext2fs_new_block(fs, (blk_t) goal, 
2527                                           ctx->block_found_map, &new_block);
2528                 if (retval)
2529                         return retval;
2530         } else {
2531                 if (!fs->block_map) {
2532                         retval = ext2fs_read_block_bitmap(fs);
2533                         if (retval)
2534                                 return retval;
2535                 }
2536
2537                 retval = ext2fs_new_block(fs, (blk_t) goal, 0, &new_block);
2538                 if (retval)
2539                         return retval;
2540         }
2541                 
2542         *ret = new_block;
2543         return (0);
2544 }
2545
2546 static void e2fsck_block_alloc_stats(ext2_filsys fs, blk64_t blk, int inuse)
2547 {
2548         e2fsck_t ctx = (e2fsck_t) fs->priv_data;
2549
2550         if (ctx->block_found_map) {
2551                 if (inuse > 0)
2552                         ext2fs_mark_block_bitmap(ctx->block_found_map, 
2553                                                  (blk_t) blk);
2554                 else
2555                         ext2fs_unmark_block_bitmap(ctx->block_found_map, 
2556                                                    (blk_t) blk);
2557         }
2558 }
2559
2560 void e2fsck_use_inode_shortcuts(e2fsck_t ctx, int bool)
2561 {
2562         ext2_filsys fs = ctx->fs;
2563
2564         if (bool) {
2565                 fs->get_blocks = pass1_get_blocks;
2566                 fs->check_directory = pass1_check_directory;
2567                 fs->read_inode = pass1_read_inode;
2568                 fs->write_inode = pass1_write_inode;
2569                 ctx->stashed_ino = 0;
2570                 ext2fs_set_alloc_block_callback(fs, e2fsck_get_alloc_block,
2571                                                 0);
2572                 ext2fs_set_block_alloc_stats_callback(fs,
2573                                                       e2fsck_block_alloc_stats,
2574                                                       0);
2575         } else {
2576                 fs->get_blocks = 0;
2577                 fs->check_directory = 0;
2578                 fs->read_inode = 0;
2579                 fs->write_inode = 0;
2580         }
2581 }