Skip to content

Commit

Permalink
---
Browse files Browse the repository at this point in the history
yaml
---
r: 27827
b: refs/heads/master
c: 6171586
h: refs/heads/master
i:
  27825: 57c7f1e
  27823: 6533ccf
v: v3
  • Loading branch information
David Woodhouse committed May 20, 2006
1 parent b5fe3de commit b3c9b7d
Show file tree
Hide file tree
Showing 5 changed files with 56 additions and 24 deletions.
2 changes: 1 addition & 1 deletion [refs]
Original file line number Diff line number Diff line change
@@ -1,2 +1,2 @@
---
refs/heads/master: fb9fbbcc9389edabb172ac1b6419c01e32046787
refs/heads/master: 6171586a7ae5198988774e8480631e8d15f65dfe
49 changes: 29 additions & 20 deletions trunk/fs/jffs2/gc.c
Original file line number Diff line number Diff line change
Expand Up @@ -256,10 +256,14 @@ int jffs2_garbage_collect_pass(struct jffs2_sb_info *c)

if (!raw->next_in_ino) {
/* Inode-less node. Clean marker, snapshot or something like that */
/* FIXME: If it's something that needs to be copied, including something
we don't grok that has JFFS2_NODETYPE_RWCOMPAT_COPY, we should do so */
spin_unlock(&c->erase_completion_lock);
jffs2_mark_node_obsolete(c, raw);
if (ref_flags(raw) == REF_PRISTINE) {
/* It's an unknown node with JFFS2_FEATURE_RWCOMPAT_COPY */
jffs2_garbage_collect_pristine(c, NULL, raw);
} else {
/* Just mark it obsolete */
jffs2_mark_node_obsolete(c, raw);
}
up(&c->alloc_sem);
goto eraseit_lock;
}
Expand Down Expand Up @@ -533,15 +537,16 @@ static int jffs2_garbage_collect_pristine(struct jffs2_sb_info *c,

D1(printk(KERN_DEBUG "Going to GC REF_PRISTINE node at 0x%08x\n", ref_offset(raw)));

rawlen = ref_totlen(c, c->gcblock, raw);
alloclen = rawlen = ref_totlen(c, c->gcblock, raw);

/* Ask for a small amount of space (or the totlen if smaller) because we
don't want to force wastage of the end of a block if splitting would
work. */
ret = jffs2_reserve_space_gc(c, min_t(uint32_t, sizeof(struct jffs2_raw_inode) +
JFFS2_MIN_DATA_LEN, rawlen), &phys_ofs, &alloclen, rawlen);
/* this is not the exact summary size of it,
it is only an upper estimation */
if (ic && alloclen > sizeof(struct jffs2_raw_inode) + JFFS2_MIN_DATA_LEN)
alloclen = sizeof(struct jffs2_raw_inode) + JFFS2_MIN_DATA_LEN;

ret = jffs2_reserve_space_gc(c, alloclen, &phys_ofs, &alloclen, rawlen);
/* 'rawlen' is not the exact summary size; it is only an upper estimation */

if (ret)
return ret;
Expand Down Expand Up @@ -605,9 +610,12 @@ static int jffs2_garbage_collect_pristine(struct jffs2_sb_info *c,
}
break;
default:
printk(KERN_WARNING "Unknown node type for REF_PRISTINE node at 0x%08x: 0x%04x\n",
ref_offset(raw), je16_to_cpu(node->u.nodetype));
goto bail;
/* If it's inode-less, we don't _know_ what it is. Just copy it intact */
if (ic) {
printk(KERN_WARNING "Unknown node type for REF_PRISTINE node at 0x%08x: 0x%04x\n",
ref_offset(raw), je16_to_cpu(node->u.nodetype));
goto bail;
}
}

nraw = jffs2_alloc_raw_node_ref();
Expand Down Expand Up @@ -674,15 +682,16 @@ static int jffs2_garbage_collect_pristine(struct jffs2_sb_info *c,
nraw->flash_offset |= REF_PRISTINE;
jffs2_add_physical_node_ref(c, nraw);

/* Link into per-inode list. This is safe because of the ic
state being INO_STATE_GC. Note that if we're doing this
for an inode which is in-core, the 'nraw' pointer is then
going to be fetched from ic->nodes by our caller. */
spin_lock(&c->erase_completion_lock);
nraw->next_in_ino = ic->nodes;
ic->nodes = nraw;
spin_unlock(&c->erase_completion_lock);

if (ic) {
/* Link into per-inode list. This is safe because of the ic
state being INO_STATE_GC. Note that if we're doing this
for an inode which is in-core, the 'nraw' pointer is then
going to be fetched from ic->nodes by our caller. */
spin_lock(&c->erase_completion_lock);
nraw->next_in_ino = ic->nodes;
ic->nodes = nraw;
spin_unlock(&c->erase_completion_lock);
}
jffs2_mark_node_obsolete(c, raw);
D1(printk(KERN_DEBUG "WHEEE! GC REF_PRISTINE node at 0x%08x succeeded\n", ref_offset(raw)));

Expand Down
5 changes: 5 additions & 0 deletions trunk/fs/jffs2/nodelist.h
Original file line number Diff line number Diff line change
Expand Up @@ -97,6 +97,11 @@ struct jffs2_raw_node_ref
#define ref_obsolete(ref) (((ref)->flash_offset & 3) == REF_OBSOLETE)
#define mark_ref_normal(ref) do { (ref)->flash_offset = ref_offset(ref) | REF_NORMAL; } while(0)

/* NB: REF_PRISTINE for an inode-less node (ref->next_in_ino == NULL) indicates
it is an unknown node of type JFFS2_NODETYPE_RWCOMPAT_COPY, so it'll get
copied. If you need to do anything different to GC inode-less nodes, then
you need to modify gc.c accordingly. */

/* For each inode in the filesystem, we need to keep a record of
nlink, because it would be a PITA to scan the whole directory tree
at read_inode() time to calculate it, and to keep sufficient information
Expand Down
15 changes: 13 additions & 2 deletions trunk/fs/jffs2/scan.c
Original file line number Diff line number Diff line change
Expand Up @@ -851,11 +851,22 @@ static int jffs2_scan_eraseblock (struct jffs2_sb_info *c, struct jffs2_eraseblo
ofs += PAD(je32_to_cpu(node->totlen));
break;

case JFFS2_FEATURE_RWCOMPAT_COPY:
case JFFS2_FEATURE_RWCOMPAT_COPY: {
struct jffs2_raw_node_ref *ref;
D1(printk(KERN_NOTICE "Unknown but compatible feature node (0x%04x) found at offset 0x%08x\n", je16_to_cpu(node->nodetype), ofs));
USED_SPACE(PAD(je32_to_cpu(node->totlen)));

ref = jffs2_alloc_raw_node_ref();
if (!ref)
return -ENOMEM;
ref->flash_offset = ofs | REF_PRISTINE;
ref->next_in_ino = 0;
jffs2_link_node_ref(c, jeb, ref, PAD(je32_to_cpu(node->totlen)));

/* We can't summarise nodes we don't grok */
jffs2_sum_disable_collecting(s);
ofs += PAD(je32_to_cpu(node->totlen));
break;
}
}
}
}
Expand Down
9 changes: 8 additions & 1 deletion trunk/fs/jffs2/summary.c
Original file line number Diff line number Diff line change
Expand Up @@ -760,7 +760,14 @@ static int jffs2_sum_write_data(struct jffs2_sb_info *c, struct jffs2_eraseblock
}
#endif
default : {
BUG(); /* unknown node in summary information */
if ((je16_to_cpu(temp->u.nodetype) & JFFS2_COMPAT_MASK)
== JFFS2_FEATURE_RWCOMPAT_COPY) {
dbg_summary("Writing unknown RWCOMPAT_COPY node type %x\n",
je16_to_cpu(temp->u.nodetype));
jffs2_sum_disable_collecting(c->summary);
} else {
BUG(); /* unknown node in summary information */
}
}
}

Expand Down

0 comments on commit b3c9b7d

Please sign in to comment.