1 |
/* Fetching and storing the hypermetadata (superblock and bg summary info) |
/* Fetching and storing the hypermetadata (superblock and bg summary info) |
2 |
|
|
3 |
Copyright (C) 1994,95,96,99,2001,02 Free Software Foundation, Inc. |
Copyright (C) 1994,95,96,99,2001,02,05 Free Software Foundation, Inc. |
4 |
Written by Miles Bader <miles@gnu.org> |
Written by Miles Bader <miles@gnu.org> |
5 |
|
|
6 |
This program is free software; you can redistribute it and/or |
This program is free software; you can redistribute it and/or |
51 |
modified_global_blocks = 0; |
modified_global_blocks = 0; |
52 |
} |
} |
53 |
|
|
54 |
|
/* Our in-core copy of the super-block (pointer into the disk_cache). */ |
55 |
|
struct ext2_super_block *sblock; |
56 |
|
/* True if sblock has been modified. */ |
57 |
|
int sblock_dirty; |
58 |
|
|
59 |
unsigned int sblock_block = SBLOCK_BLOCK; /* in 1k blocks */ |
unsigned int sblock_block = SBLOCK_BLOCK; /* in 1k blocks */ |
60 |
|
|
61 |
static int ext2fs_clean; /* fs clean before we started writing? */ |
static int ext2fs_clean; /* fs clean before we started writing? */ |
63 |
void |
void |
64 |
get_hypermetadata (void) |
get_hypermetadata (void) |
65 |
{ |
{ |
66 |
error_t err = diskfs_catch_exception (); |
error_t err; |
67 |
if (err) |
size_t read; |
|
ext2_panic ("can't read superblock: %s", strerror (err)); |
|
|
|
|
|
sblock = (struct ext2_super_block *) boffs_ptr (SBLOCK_OFFS); |
|
68 |
|
|
69 |
|
assert (! sblock); |
70 |
|
err = store_read (store, SBLOCK_OFFS >> store->log2_block_size, |
71 |
|
SBLOCK_SIZE, (void **)&sblock, &read); |
72 |
|
if (err || read != SBLOCK_SIZE) |
73 |
|
ext2_panic ("Cannot read hypermetadata"); |
74 |
|
|
75 |
if (sblock->s_magic != EXT2_SUPER_MAGIC |
if (sblock->s_magic != EXT2_SUPER_MAGIC |
76 |
#ifdef EXT2FS_PRE_02B_COMPAT |
#ifdef EXT2FS_PRE_02B_COMPAT |
77 |
&& sblock->s_magic != EXT2_PRE_02B_MAGIC |
&& sblock->s_magic != EXT2_PRE_02B_MAGIC |
160 |
|
|
161 |
allocate_mod_map (); |
allocate_mod_map (); |
162 |
|
|
163 |
diskfs_end_catch_exception (); |
/* A handy source of page-aligned zeros. */ |
164 |
|
if (zeroblock == 0) |
165 |
|
zeroblock = (vm_address_t) mmap (0, block_size, PROT_READ, MAP_ANON, 0, 0); |
166 |
|
|
167 |
|
munmap (sblock, SBLOCK_SIZE); |
168 |
|
sblock = NULL; |
169 |
|
} |
170 |
|
|
171 |
|
void |
172 |
|
map_hypermetadata (void) |
173 |
|
{ |
174 |
|
sblock = (struct ext2_super_block *) boffs_ptr (SBLOCK_OFFS); |
175 |
|
|
176 |
/* Cache a convenient pointer to the block group descriptors for allocation. |
/* Cache a convenient pointer to the block group descriptors for allocation. |
177 |
These are stored in the filesystem blocks following the superblock. */ |
These are stored in the filesystem blocks following the superblock. */ |
178 |
group_desc_image = (struct ext2_group_desc *) bptr (bptr_block (sblock) + 1); |
group_desc_image = (struct ext2_group_desc *) bptr (bptr_block (sblock) + 1); |
|
|
|
|
/* A handy source of page-aligned zeros. */ |
|
|
if (zeroblock == 0) |
|
|
zeroblock = (vm_address_t) mmap (0, block_size, PROT_READ, MAP_ANON, 0, 0); |
|
179 |
} |
} |
180 |
|
|
181 |
error_t |
error_t |
198 |
if (sblock_dirty) |
if (sblock_dirty) |
199 |
{ |
{ |
200 |
sblock_dirty = 0; |
sblock_dirty = 0; |
201 |
|
buffer_ref (sblock); |
202 |
record_global_poke (sblock); |
record_global_poke (sblock); |
203 |
} |
} |
204 |
|
|
215 |
|
|
216 |
(*(readonly ? store_set_flags : store_clear_flags)) (store, STORE_READONLY); |
(*(readonly ? store_set_flags : store_clear_flags)) (store, STORE_READONLY); |
217 |
|
|
218 |
mprotect (disk_image, store->size, PROT_READ | (readonly ? 0 : PROT_WRITE)); |
mprotect (disk_cache, disk_cache_size, |
219 |
|
PROT_READ | (readonly ? 0 : PROT_WRITE)); |
220 |
|
|
221 |
if (!readonly && !(sblock->s_state & EXT2_VALID_FS)) |
if (!readonly && !(sblock->s_state & EXT2_VALID_FS)) |
222 |
ext2_warning ("UNCLEANED FILESYSTEM NOW WRITABLE"); |
ext2_warning ("UNCLEANED FILESYSTEM NOW WRITABLE"); |