* Zoltan Sogor <weth@inf.u-szeged.hu>,
* Patrik Kluba <pajko@halom.u-szeged.hu>,
* University of Szeged, Hungary
- * 2005 KaiGai Kohei <kaigai@ak.jp.nec.com>
+ * 2006 KaiGai Kohei <kaigai@ak.jp.nec.com>
*
* For licensing information, see the file 'LICENCE' in this directory.
*
return -ENOMEM;
}
- dbg_summary("returned succesfully\n");
+ dbg_summary("returned successfully\n");
return 0;
}
#ifdef CONFIG_JFFS2_FS_XATTR
case JFFS2_NODETYPE_XATTR: {
struct jffs2_sum_xattr_mem *temp;
- if (je32_to_cpu(node->x.version) == 0xffffffff)
- return 0;
temp = kmalloc(sizeof(struct jffs2_sum_xattr_mem), GFP_KERNEL);
if (!temp)
goto no_mem;
}
case JFFS2_NODETYPE_XREF: {
struct jffs2_sum_xref_mem *temp;
-
- if (je32_to_cpu(node->r.ino) == 0xffffffff
- && je32_to_cpu(node->r.xid) == 0xffffffff)
- return 0;
temp = kmalloc(sizeof(struct jffs2_sum_xref_mem), GFP_KERNEL);
if (!temp)
goto no_mem;
dbg_summary("processing summary index %d\n", i);
/* Make sure there's a spare ref for dirty space */
- err = jffs2_prealloc_raw_node_refs(c, 2);
+ err = jffs2_prealloc_raw_node_refs(c, jeb, 2);
if (err)
return err;
dbg_summary("Inode at 0x%08x-0x%08x\n",
jeb->offset + je32_to_cpu(spi->offset),
- jeb->offset + je32_to_cpu(spi->offset) + je32_to_cpu(spu->totlen));
+ jeb->offset + je32_to_cpu(spi->offset) + je32_to_cpu(spi->totlen));
ic = jffs2_scan_make_ino_cache(c, ino);
if (!ic) {
struct jffs2_sum_dirent_flash *spd;
spd = sp;
- dbg_summary("Dirent at 0x%08x\n",
+ dbg_summary("Dirent at 0x%08x-0x%08x\n",
jeb->offset + je32_to_cpu(spd->offset),
jeb->offset + je32_to_cpu(spd->offset) + je32_to_cpu(spd->totlen));
return -ENOMEM;
}
- fd->raw = sum_link_node_ref(c, jeb, je32_to_cpu(spd->offset) | REF_PRISTINE,
+ fd->raw = sum_link_node_ref(c, jeb, je32_to_cpu(spd->offset) | REF_UNCHECKED,
PAD(je32_to_cpu(spd->totlen)), ic);
fd->next = NULL;
xd = jffs2_setup_xattr_datum(c, je32_to_cpu(spx->xid),
je32_to_cpu(spx->version));
- if (IS_ERR(xd)) {
- if (PTR_ERR(xd) == -EEXIST) {
- /* a newer version of xd exists */
- if ((err = jffs2_scan_dirty_space(c, jeb, je32_to_cpu(spx->totlen))))
- return err;
- sp += JFFS2_SUMMARY_XATTR_SIZE;
- break;
- }
- JFFS2_NOTICE("allocation of xattr_datum failed\n");
+ if (IS_ERR(xd))
return PTR_ERR(xd);
+ if (xd->version > je32_to_cpu(spx->version)) {
+ /* node is not the newest one */
+ struct jffs2_raw_node_ref *raw
+ = sum_link_node_ref(c, jeb, je32_to_cpu(spx->offset) | REF_UNCHECKED,
+ PAD(je32_to_cpu(spx->totlen)), NULL);
+ raw->next_in_ino = xd->node->next_in_ino;
+ xd->node->next_in_ino = raw;
+ } else {
+ xd->version = je32_to_cpu(spx->version);
+ sum_link_node_ref(c, jeb, je32_to_cpu(spx->offset) | REF_UNCHECKED,
+ PAD(je32_to_cpu(spx->totlen)), (void *)xd);
}
-
- xd->node = sum_link_node_ref(c, jeb, je32_to_cpu(spx->offset) | REF_UNCHECKED,
- PAD(je32_to_cpu(spx->totlen)), NULL);
- /* FIXME */ xd->node->next_in_ino = (void *)xd;
-
*pseudo_random += je32_to_cpu(spx->xid);
sp += JFFS2_SUMMARY_XATTR_SIZE;
spr = (struct jffs2_sum_xref_flash *)sp;
dbg_summary("xref at %#08x-%#08x\n",
jeb->offset + je32_to_cpu(spr->offset),
- jeb->offset + je32_to_cpu(spr->offset) + PAD(sizeof(struct jffs2_raw_xref)));
+ jeb->offset + je32_to_cpu(spr->offset) +
+ (uint32_t)PAD(sizeof(struct jffs2_raw_xref)));
ref = jffs2_alloc_xattr_ref();
if (!ref) {
JFFS2_NOTICE("allocation of xattr_datum failed\n");
return -ENOMEM;
}
- ref->ino = 0xfffffffe;
- ref->xid = 0xfffffffd;
ref->next = c->xref_temp;
c->xref_temp = ref;
- ref->node = sum_link_node_ref(c, jeb, je32_to_cpu(spr->offset) | REF_UNCHECKED,
- PAD(sizeof(struct jffs2_raw_xref)), NULL);
- /* FIXME */ ref->node->next_in_ino = (void *)ref;
+ sum_link_node_ref(c, jeb, je32_to_cpu(spr->offset) | REF_UNCHECKED,
+ PAD(sizeof(struct jffs2_raw_xref)), (void *)ref);
*pseudo_random += ref->node->flash_offset;
sp += JFFS2_SUMMARY_XREF_SIZE;
struct jffs2_unknown_node crcnode;
int ret, ofs;
uint32_t crc;
- int err;
ofs = c->sector_size - sumsize;
dbg_summary("Summary : CLEANMARKER node \n");
+ ret = jffs2_prealloc_raw_node_refs(c, jeb, 1);
+ if (ret)
+ return ret;
+
if (je32_to_cpu(summary->cln_mkr) != c->cleanmarker_size) {
dbg_summary("CLEANMARKER node has totlen 0x%x != normal 0x%x\n",
je32_to_cpu(summary->cln_mkr), c->cleanmarker_size);
- if ((err = jffs2_scan_dirty_space(c, jeb, PAD(je32_to_cpu(summary->cln_mkr)))))
- return err;
+ if ((ret = jffs2_scan_dirty_space(c, jeb, PAD(je32_to_cpu(summary->cln_mkr)))))
+ return ret;
} else if (jeb->first_node) {
dbg_summary("CLEANMARKER node not first node in block "
"(0x%08x)\n", jeb->offset);
- if ((err = jffs2_scan_dirty_space(c, jeb, PAD(je32_to_cpu(summary->cln_mkr)))))
- return err;
+ if ((ret = jffs2_scan_dirty_space(c, jeb, PAD(je32_to_cpu(summary->cln_mkr)))))
+ return ret;
} else {
jffs2_link_node_ref(c, jeb, jeb->offset | REF_NORMAL,
je32_to_cpu(summary->cln_mkr), NULL);
return ret; /* real error */
/* for PARANOIA_CHECK */
- ret = jffs2_prealloc_raw_node_refs(c, 1);
+ ret = jffs2_prealloc_raw_node_refs(c, jeb, 2);
if (ret)
return ret;
- jffs2_link_node_ref(c, jeb, (jeb->offset + ofs) | REF_NORMAL, sumsize, NULL);
+ sum_link_node_ref(c, jeb, ofs | REF_NORMAL, sumsize, NULL);
if (unlikely(jeb->free_size)) {
JFFS2_WARNING("Free size 0x%x bytes in eraseblock @0x%08x with summary?\n",
JFFS2_WARNING("Write of %u bytes at 0x%08x failed. returned %d, retlen %zd\n",
infosize, sum_ofs, ret, retlen);
- /* Waste remaining space */
- spin_lock(&c->erase_completion_lock);
- jffs2_link_node_ref(c, jeb, sum_ofs | REF_OBSOLETE, infosize, NULL);
- spin_unlock(&c->erase_completion_lock);
+ if (retlen) {
+ /* Waste remaining space */
+ spin_lock(&c->erase_completion_lock);
+ jffs2_link_node_ref(c, jeb, sum_ofs | REF_OBSOLETE, infosize, NULL);
+ spin_unlock(&c->erase_completion_lock);
+ }
c->summary->sum_size = JFFS2_SUMMARY_NOSUM_SIZE;
dbg_summary("called\n");
spin_unlock(&c->erase_completion_lock);
- jffs2_prealloc_raw_node_refs(c, 1);
jeb = c->nextblock;
+ jffs2_prealloc_raw_node_refs(c, jeb, 1);
if (!c->summary->sum_num || !c->summary->sum_list_head) {
JFFS2_WARNING("Empty summary info!!!\n");
jffs2_sum_disable_collecting(c->summary);
JFFS2_WARNING("Not enough space for summary, padsize = %d\n", padsize);
+ spin_lock(&c->erase_completion_lock);
return 0;
}