busybox/e2fsprogs/old_e2fsprogs/ext2fs/sparse.c
<<
>>
Prefs
   1/* vi: set sw=4 ts=4: */
   2/*
   3 * sparse.c --- find the groups in an ext2 filesystem with metadata backups
   4 *
   5 * Copyright (C) 1993, 1994, 1995, 1996 Theodore Ts'o.
   6 * Copyright (C) 2002 Andreas Dilger.
   7 *
   8 * %Begin-Header%
   9 * This file may be redistributed under the terms of the GNU Public
  10 * License.
  11 * %End-Header%
  12 */
  13
  14#include <stdio.h>
  15
  16#include "ext2_fs.h"
  17#include "ext2fsP.h"
  18
  19static int test_root(int a, int b)
  20{
  21        if (a == 0)
  22                return 1;
  23        while (1) {
  24                if (a == 1)
  25                        return 1;
  26                if (a % b)
  27                        return 0;
  28                a = a / b;
  29        }
  30}
  31
  32int ext2fs_bg_has_super(ext2_filsys fs, int group_block)
  33{
  34        if (!(fs->super->s_feature_ro_compat &
  35              EXT2_FEATURE_RO_COMPAT_SPARSE_SUPER))
  36                return 1;
  37
  38        if (test_root(group_block, 3) || (test_root(group_block, 5)) ||
  39            test_root(group_block, 7))
  40                return 1;
  41
  42        return 0;
  43}
  44
  45/*
  46 * Iterate through the groups which hold BACKUP superblock/GDT copies in an
  47 * ext3 filesystem.  The counters should be initialized to 1, 5, and 7 before
  48 * calling this for the first time.  In a sparse filesystem it will be the
  49 * sequence of powers of 3, 5, and 7: 1, 3, 5, 7, 9, 25, 27, 49, 81, ...
  50 * For a non-sparse filesystem it will be every group: 1, 2, 3, 4, ...
  51 */
  52unsigned int ext2fs_list_backups(ext2_filsys fs, unsigned int *three,
  53                                 unsigned int *five, unsigned int *seven)
  54{
  55        unsigned int *min = three;
  56        int mult = 3;
  57        unsigned int ret;
  58
  59        if (!(fs->super->s_feature_ro_compat &
  60              EXT2_FEATURE_RO_COMPAT_SPARSE_SUPER)) {
  61                ret = *min;
  62                *min += 1;
  63                return ret;
  64        }
  65
  66        if (*five < *min) {
  67                min = five;
  68                mult = 5;
  69        }
  70        if (*seven < *min) {
  71                min = seven;
  72                mult = 7;
  73        }
  74
  75        ret = *min;
  76        *min *= mult;
  77
  78        return ret;
  79}
  80