build.c (d55849aa4d219b734795862692cc6981af848357) | build.c (182ec4eee397543101a6db8906ed88727d3f7e53) |
---|---|
1/* 2 * JFFS2 -- Journalling Flash File System, Version 2. 3 * 4 * Copyright (C) 2001-2003 Red Hat, Inc. 5 * 6 * Created by David Woodhouse <dwmw2@infradead.org> 7 * 8 * For licensing information, see the file 'LICENCE' in this directory. 9 * | 1/* 2 * JFFS2 -- Journalling Flash File System, Version 2. 3 * 4 * Copyright (C) 2001-2003 Red Hat, Inc. 5 * 6 * Created by David Woodhouse <dwmw2@infradead.org> 7 * 8 * For licensing information, see the file 'LICENCE' in this directory. 9 * |
10 * $Id: build.c,v 1.84 2005/09/27 13:40:49 dedekind Exp $ | 10 * $Id: build.c,v 1.85 2005/11/07 11:14:38 gleixner Exp $ |
11 * 12 */ 13 14#include <linux/kernel.h> 15#include <linux/sched.h> 16#include <linux/slab.h> 17#include <linux/vmalloc.h> 18#include <linux/mtd/mtd.h> --- 105 unchanged lines hidden (view full) --- 124 children too, and repeat the scan. As that's going to be 125 a fairly uncommon occurrence, it's not so evil to do it this 126 way. Recursion bad. */ 127 dbg_fsbuild("pass 2 starting\n"); 128 129 for_each_inode(i, c, ic) { 130 if (ic->nlink) 131 continue; | 11 * 12 */ 13 14#include <linux/kernel.h> 15#include <linux/sched.h> 16#include <linux/slab.h> 17#include <linux/vmalloc.h> 18#include <linux/mtd/mtd.h> --- 105 unchanged lines hidden (view full) --- 124 children too, and repeat the scan. As that's going to be 125 a fairly uncommon occurrence, it's not so evil to do it this 126 way. Recursion bad. */ 127 dbg_fsbuild("pass 2 starting\n"); 128 129 for_each_inode(i, c, ic) { 130 if (ic->nlink) 131 continue; |
132 | 132 |
133 jffs2_build_remove_unlinked_inode(c, ic, &dead_fds); 134 cond_resched(); | 133 jffs2_build_remove_unlinked_inode(c, ic, &dead_fds); 134 cond_resched(); |
135 } | 135 } |
136 137 dbg_fsbuild("pass 2a starting\n"); 138 139 while (dead_fds) { 140 fd = dead_fds; 141 dead_fds = fd->next; 142 143 ic = jffs2_get_ino_cache(c, fd->ino); 144 145 if (ic) 146 jffs2_build_remove_unlinked_inode(c, ic, &dead_fds); 147 jffs2_free_full_dirent(fd); 148 } 149 150 dbg_fsbuild("pass 2a complete\n"); 151 dbg_fsbuild("freeing temporary data structures\n"); | 136 137 dbg_fsbuild("pass 2a starting\n"); 138 139 while (dead_fds) { 140 fd = dead_fds; 141 dead_fds = fd->next; 142 143 ic = jffs2_get_ino_cache(c, fd->ino); 144 145 if (ic) 146 jffs2_build_remove_unlinked_inode(c, ic, &dead_fds); 147 jffs2_free_full_dirent(fd); 148 } 149 150 dbg_fsbuild("pass 2a complete\n"); 151 dbg_fsbuild("freeing temporary data structures\n"); |
152 | 152 |
153 /* Finally, we can scan again and free the dirent structs */ 154 for_each_inode(i, c, ic) { 155 while(ic->scan_dents) { 156 fd = ic->scan_dents; 157 ic->scan_dents = fd->next; 158 jffs2_free_full_dirent(fd); 159 } 160 ic->scan_dents = NULL; 161 cond_resched(); 162 } 163 c->flags &= ~JFFS2_SB_FLAG_BUILDING; | 153 /* Finally, we can scan again and free the dirent structs */ 154 for_each_inode(i, c, ic) { 155 while(ic->scan_dents) { 156 fd = ic->scan_dents; 157 ic->scan_dents = fd->next; 158 jffs2_free_full_dirent(fd); 159 } 160 ic->scan_dents = NULL; 161 cond_resched(); 162 } 163 c->flags &= ~JFFS2_SB_FLAG_BUILDING; |
164 | 164 |
165 dbg_fsbuild("FS build complete\n"); 166 167 /* Rotate the lists by some number to ensure wear levelling */ 168 jffs2_rotate_lists(c); 169 170 ret = 0; 171 172exit: --- 13 unchanged lines hidden (view full) --- 186static void jffs2_build_remove_unlinked_inode(struct jffs2_sb_info *c, 187 struct jffs2_inode_cache *ic, 188 struct jffs2_full_dirent **dead_fds) 189{ 190 struct jffs2_raw_node_ref *raw; 191 struct jffs2_full_dirent *fd; 192 193 dbg_fsbuild("removing ino #%u with nlink == zero.\n", ic->ino); | 165 dbg_fsbuild("FS build complete\n"); 166 167 /* Rotate the lists by some number to ensure wear levelling */ 168 jffs2_rotate_lists(c); 169 170 ret = 0; 171 172exit: --- 13 unchanged lines hidden (view full) --- 186static void jffs2_build_remove_unlinked_inode(struct jffs2_sb_info *c, 187 struct jffs2_inode_cache *ic, 188 struct jffs2_full_dirent **dead_fds) 189{ 190 struct jffs2_raw_node_ref *raw; 191 struct jffs2_full_dirent *fd; 192 193 dbg_fsbuild("removing ino #%u with nlink == zero.\n", ic->ino); |
194 | 194 |
195 raw = ic->nodes; 196 while (raw != (void *)ic) { 197 struct jffs2_raw_node_ref *next = raw->next_in_ino; 198 dbg_fsbuild("obsoleting node at 0x%08x\n", ref_offset(raw)); 199 jffs2_mark_node_obsolete(c, raw); 200 raw = next; 201 } 202 --- 12 unchanged lines hidden (view full) --- 215 dbg_fsbuild("child \"%s\" is a deletion dirent, skipping...\n", fd->name); 216 jffs2_free_full_dirent(fd); 217 continue; 218 } 219 if (!whinged) 220 whinged = 1; 221 222 dbg_fsbuild("removing child \"%s\", ino #%u\n", fd->name, fd->ino); | 195 raw = ic->nodes; 196 while (raw != (void *)ic) { 197 struct jffs2_raw_node_ref *next = raw->next_in_ino; 198 dbg_fsbuild("obsoleting node at 0x%08x\n", ref_offset(raw)); 199 jffs2_mark_node_obsolete(c, raw); 200 raw = next; 201 } 202 --- 12 unchanged lines hidden (view full) --- 215 dbg_fsbuild("child \"%s\" is a deletion dirent, skipping...\n", fd->name); 216 jffs2_free_full_dirent(fd); 217 continue; 218 } 219 if (!whinged) 220 whinged = 1; 221 222 dbg_fsbuild("removing child \"%s\", ino #%u\n", fd->name, fd->ino); |
223 | 223 |
224 child_ic = jffs2_get_ino_cache(c, fd->ino); 225 if (!child_ic) { 226 dbg_fsbuild("cannot remove child \"%s\", ino #%u, because it doesn't exist\n", 227 fd->name, fd->ino); 228 jffs2_free_full_dirent(fd); 229 continue; 230 } 231 | 224 child_ic = jffs2_get_ino_cache(c, fd->ino); 225 if (!child_ic) { 226 dbg_fsbuild("cannot remove child \"%s\", ino #%u, because it doesn't exist\n", 227 fd->name, fd->ino); 228 jffs2_free_full_dirent(fd); 229 continue; 230 } 231 |
232 /* Reduce nlink of the child. If it's now zero, stick it on the | 232 /* Reduce nlink of the child. If it's now zero, stick it on the |
233 dead_fds list to be cleaned up later. Else just free the fd */ 234 235 child_ic->nlink--; | 233 dead_fds list to be cleaned up later. Else just free the fd */ 234 235 child_ic->nlink--; |
236 | 236 |
237 if (!child_ic->nlink) { 238 dbg_fsbuild("inode #%u (\"%s\") has now got zero nlink, adding to dead_fds list.\n", 239 fd->ino, fd->name); 240 fd->next = *dead_fds; 241 *dead_fds = fd; 242 } else { 243 dbg_fsbuild("inode #%u (\"%s\") has now got nlink %d. Ignoring.\n", 244 fd->ino, fd->name, child_ic->nlink); 245 jffs2_free_full_dirent(fd); 246 } 247 } 248 } 249 250 /* | 237 if (!child_ic->nlink) { 238 dbg_fsbuild("inode #%u (\"%s\") has now got zero nlink, adding to dead_fds list.\n", 239 fd->ino, fd->name); 240 fd->next = *dead_fds; 241 *dead_fds = fd; 242 } else { 243 dbg_fsbuild("inode #%u (\"%s\") has now got nlink %d. Ignoring.\n", 244 fd->ino, fd->name, child_ic->nlink); 245 jffs2_free_full_dirent(fd); 246 } 247 } 248 } 249 250 /* |
251 We don't delete the inocache from the hash list and free it yet. | 251 We don't delete the inocache from the hash list and free it yet. |
252 The erase code will do that, when all the nodes are completely gone. 253 */ 254} 255 256static void jffs2_calc_trigger_levels(struct jffs2_sb_info *c) 257{ 258 uint32_t size; 259 260 /* Deletion should almost _always_ be allowed. We're fairly 261 buggered once we stop allowing people to delete stuff 262 because there's not enough free space... */ 263 c->resv_blocks_deletion = 2; 264 | 252 The erase code will do that, when all the nodes are completely gone. 253 */ 254} 255 256static void jffs2_calc_trigger_levels(struct jffs2_sb_info *c) 257{ 258 uint32_t size; 259 260 /* Deletion should almost _always_ be allowed. We're fairly 261 buggered once we stop allowing people to delete stuff 262 because there's not enough free space... */ 263 c->resv_blocks_deletion = 2; 264 |
265 /* Be conservative about how much space we need before we allow writes. | 265 /* Be conservative about how much space we need before we allow writes. |
266 On top of that which is required for deletia, require an extra 2% 267 of the medium to be available, for overhead caused by nodes being 268 split across blocks, etc. */ 269 270 size = c->flash_size / 50; /* 2% of flash size */ 271 size += c->nr_blocks * 100; /* And 100 bytes per eraseblock */ 272 size += c->sector_size - 1; /* ... and round up */ 273 274 c->resv_blocks_write = c->resv_blocks_deletion + (size / c->sector_size); 275 276 /* When do we let the GC thread run in the background */ 277 278 c->resv_blocks_gctrigger = c->resv_blocks_write + 1; 279 | 266 On top of that which is required for deletia, require an extra 2% 267 of the medium to be available, for overhead caused by nodes being 268 split across blocks, etc. */ 269 270 size = c->flash_size / 50; /* 2% of flash size */ 271 size += c->nr_blocks * 100; /* And 100 bytes per eraseblock */ 272 size += c->sector_size - 1; /* ... and round up */ 273 274 c->resv_blocks_write = c->resv_blocks_deletion + (size / c->sector_size); 275 276 /* When do we let the GC thread run in the background */ 277 278 c->resv_blocks_gctrigger = c->resv_blocks_write + 1; 279 |
280 /* When do we allow garbage collection to merge nodes to make | 280 /* When do we allow garbage collection to merge nodes to make |
281 long-term progress at the expense of short-term space exhaustion? */ 282 c->resv_blocks_gcmerge = c->resv_blocks_deletion + 1; 283 284 /* When do we allow garbage collection to eat from bad blocks rather 285 than actually making progress? */ 286 c->resv_blocks_gcbad = 0;//c->resv_blocks_deletion + 2; 287 288 /* If there's less than this amount of dirty space, don't bother --- 9 unchanged lines hidden (view full) --- 298 dbg_fsbuild("Blocks required to quiesce GC thread: %d (%d KiB)\n", 299 c->resv_blocks_gctrigger, c->resv_blocks_gctrigger*c->sector_size/1024); 300 dbg_fsbuild("Blocks required to allow GC merges: %d (%d KiB)\n", 301 c->resv_blocks_gcmerge, c->resv_blocks_gcmerge*c->sector_size/1024); 302 dbg_fsbuild("Blocks required to GC bad blocks: %d (%d KiB)\n", 303 c->resv_blocks_gcbad, c->resv_blocks_gcbad*c->sector_size/1024); 304 dbg_fsbuild("Amount of dirty space required to GC: %d bytes\n", 305 c->nospc_dirty_size); | 281 long-term progress at the expense of short-term space exhaustion? */ 282 c->resv_blocks_gcmerge = c->resv_blocks_deletion + 1; 283 284 /* When do we allow garbage collection to eat from bad blocks rather 285 than actually making progress? */ 286 c->resv_blocks_gcbad = 0;//c->resv_blocks_deletion + 2; 287 288 /* If there's less than this amount of dirty space, don't bother --- 9 unchanged lines hidden (view full) --- 298 dbg_fsbuild("Blocks required to quiesce GC thread: %d (%d KiB)\n", 299 c->resv_blocks_gctrigger, c->resv_blocks_gctrigger*c->sector_size/1024); 300 dbg_fsbuild("Blocks required to allow GC merges: %d (%d KiB)\n", 301 c->resv_blocks_gcmerge, c->resv_blocks_gcmerge*c->sector_size/1024); 302 dbg_fsbuild("Blocks required to GC bad blocks: %d (%d KiB)\n", 303 c->resv_blocks_gcbad, c->resv_blocks_gcbad*c->sector_size/1024); 304 dbg_fsbuild("Amount of dirty space required to GC: %d bytes\n", 305 c->nospc_dirty_size); |
306} | 306} |
307 308int jffs2_do_mount_fs(struct jffs2_sb_info *c) 309{ 310 int ret; 311 int i; 312 int size; 313 314 c->free_size = c->flash_size; --- 35 unchanged lines hidden (view full) --- 350 351 if (jffs2_build_filesystem(c)) { 352 dbg_fsbuild("build_fs failed\n"); 353 jffs2_free_ino_caches(c); 354 jffs2_free_raw_node_refs(c); 355#ifndef __ECOS 356 if (jffs2_blocks_use_vmalloc(c)) 357 vfree(c->blocks); | 307 308int jffs2_do_mount_fs(struct jffs2_sb_info *c) 309{ 310 int ret; 311 int i; 312 int size; 313 314 c->free_size = c->flash_size; --- 35 unchanged lines hidden (view full) --- 350 351 if (jffs2_build_filesystem(c)) { 352 dbg_fsbuild("build_fs failed\n"); 353 jffs2_free_ino_caches(c); 354 jffs2_free_raw_node_refs(c); 355#ifndef __ECOS 356 if (jffs2_blocks_use_vmalloc(c)) 357 vfree(c->blocks); |
358 else | 358 else |
359#endif 360 kfree(c->blocks); 361 362 return -EIO; 363 } 364 365 jffs2_calc_trigger_levels(c); 366 367 return 0; 368} | 359#endif 360 kfree(c->blocks); 361 362 return -EIO; 363 } 364 365 jffs2_calc_trigger_levels(c); 366 367 return 0; 368} |