Linux-2.6.12-rc2
[linux-2.6/kvm.git] / fs / jffs / jffs_fm.c
blob0cab8da49d3c445fb6ed0d7dda4f9ebbb613f510
1 /*
2 * JFFS -- Journaling Flash File System, Linux implementation.
4 * Copyright (C) 1999, 2000 Axis Communications AB.
6 * Created by Finn Hakansson <finn@axis.com>.
8 * This is free software; you can redistribute it and/or modify it
9 * under the terms of the GNU General Public License as published by
10 * the Free Software Foundation; either version 2 of the License, or
11 * (at your option) any later version.
13 * $Id: jffs_fm.c,v 1.27 2001/09/20 12:29:47 dwmw2 Exp $
15 * Ported to Linux 2.3.x and MTD:
16 * Copyright (C) 2000 Alexander Larsson (alex@cendio.se), Cendio Systems AB
19 #include <linux/slab.h>
20 #include <linux/blkdev.h>
21 #include <linux/jffs.h>
22 #include "jffs_fm.h"
24 #if defined(JFFS_MARK_OBSOLETE) && JFFS_MARK_OBSOLETE
25 static int jffs_mark_obsolete(struct jffs_fmcontrol *fmc, __u32 fm_offset);
26 #endif
28 static struct jffs_fm *jffs_alloc_fm(void);
29 static void jffs_free_fm(struct jffs_fm *n);
31 extern kmem_cache_t *fm_cache;
32 extern kmem_cache_t *node_cache;
34 /* This function creates a new shiny flash memory control structure. */
35 struct jffs_fmcontrol *
36 jffs_build_begin(struct jffs_control *c, int unit)
38 struct jffs_fmcontrol *fmc;
39 struct mtd_info *mtd;
41 D3(printk("jffs_build_begin()\n"));
42 fmc = (struct jffs_fmcontrol *)kmalloc(sizeof(struct jffs_fmcontrol),
43 GFP_KERNEL);
44 if (!fmc) {
45 D(printk("jffs_build_begin(): Allocation of "
46 "struct jffs_fmcontrol failed!\n"));
47 return (struct jffs_fmcontrol *)0;
49 DJM(no_jffs_fmcontrol++);
51 mtd = get_mtd_device(NULL, unit);
53 if (!mtd) {
54 kfree(fmc);
55 DJM(no_jffs_fmcontrol--);
56 return NULL;
59 /* Retrieve the size of the flash memory. */
60 fmc->flash_size = mtd->size;
61 D3(printk(" fmc->flash_size = %d bytes\n", fmc->flash_size));
63 fmc->used_size = 0;
64 fmc->dirty_size = 0;
65 fmc->free_size = mtd->size;
66 fmc->sector_size = mtd->erasesize;
67 fmc->max_chunk_size = fmc->sector_size >> 1;
68 /* min_free_size:
69 1 sector, obviously.
70 + 1 x max_chunk_size, for when a nodes overlaps the end of a sector
71 + 1 x max_chunk_size again, which ought to be enough to handle
72 the case where a rename causes a name to grow, and GC has
73 to write out larger nodes than the ones it's obsoleting.
74 We should fix it so it doesn't have to write the name
75 _every_ time. Later.
76 + another 2 sectors because people keep getting GC stuck and
77 we don't know why. This scares me - I want formal proof
78 of correctness of whatever number we put here. dwmw2.
80 fmc->min_free_size = fmc->sector_size << 2;
81 fmc->mtd = mtd;
82 fmc->c = c;
83 fmc->head = NULL;
84 fmc->tail = NULL;
85 fmc->head_extra = NULL;
86 fmc->tail_extra = NULL;
87 init_MUTEX(&fmc->biglock);
88 return fmc;
92 /* When the flash memory scan has completed, this function should be called
93 before use of the control structure. */
94 void
95 jffs_build_end(struct jffs_fmcontrol *fmc)
97 D3(printk("jffs_build_end()\n"));
99 if (!fmc->head) {
100 fmc->head = fmc->head_extra;
101 fmc->tail = fmc->tail_extra;
103 else if (fmc->head_extra) {
104 fmc->tail_extra->next = fmc->head;
105 fmc->head->prev = fmc->tail_extra;
106 fmc->head = fmc->head_extra;
108 fmc->head_extra = NULL; /* These two instructions should be omitted. */
109 fmc->tail_extra = NULL;
110 D3(jffs_print_fmcontrol(fmc));
114 /* Call this function when the file system is unmounted. This function
115 frees all memory used by this module. */
116 void
117 jffs_cleanup_fmcontrol(struct jffs_fmcontrol *fmc)
119 if (fmc) {
120 struct jffs_fm *next = fmc->head;
121 while (next) {
122 struct jffs_fm *cur = next;
123 next = next->next;
124 jffs_free_fm(cur);
126 put_mtd_device(fmc->mtd);
127 kfree(fmc);
128 DJM(no_jffs_fmcontrol--);
133 /* This function returns the size of the first chunk of free space on the
134 flash memory. This function will return something nonzero if the flash
135 memory contains any free space. */
136 __u32
137 jffs_free_size1(struct jffs_fmcontrol *fmc)
139 __u32 head;
140 __u32 tail;
141 __u32 end = fmc->flash_size;
143 if (!fmc->head) {
144 /* There is nothing on the flash. */
145 return fmc->flash_size;
148 /* Compute the beginning and ending of the contents of the flash. */
149 head = fmc->head->offset;
150 tail = fmc->tail->offset + fmc->tail->size;
151 if (tail == end) {
152 tail = 0;
154 ASSERT(else if (tail > end) {
155 printk(KERN_WARNING "jffs_free_size1(): tail > end\n");
156 tail = 0;
159 if (head <= tail) {
160 return end - tail;
162 else {
163 return head - tail;
167 /* This function will return something nonzero in case there are two free
168 areas on the flash. Like this:
170 +----------------+------------------+----------------+
171 | FREE 1 | USED / DIRTY | FREE 2 |
172 +----------------+------------------+----------------+
173 fmc->head -----^
174 fmc->tail ------------------------^
176 The value returned, will be the size of the first empty area on the
177 flash, in this case marked "FREE 1". */
178 __u32
179 jffs_free_size2(struct jffs_fmcontrol *fmc)
181 if (fmc->head) {
182 __u32 head = fmc->head->offset;
183 __u32 tail = fmc->tail->offset + fmc->tail->size;
184 if (tail == fmc->flash_size) {
185 tail = 0;
188 if (tail >= head) {
189 return head;
192 return 0;
196 /* Allocate a chunk of flash memory. If there is enough space on the
197 device, a reference to the associated node is stored in the jffs_fm
198 struct. */
200 jffs_fmalloc(struct jffs_fmcontrol *fmc, __u32 size, struct jffs_node *node,
201 struct jffs_fm **result)
203 struct jffs_fm *fm;
204 __u32 free_chunk_size1;
205 __u32 free_chunk_size2;
207 D2(printk("jffs_fmalloc(): fmc = 0x%p, size = %d, "
208 "node = 0x%p\n", fmc, size, node));
210 *result = NULL;
212 if (!(fm = jffs_alloc_fm())) {
213 D(printk("jffs_fmalloc(): kmalloc() failed! (fm)\n"));
214 return -ENOMEM;
217 free_chunk_size1 = jffs_free_size1(fmc);
218 free_chunk_size2 = jffs_free_size2(fmc);
219 if (free_chunk_size1 + free_chunk_size2 != fmc->free_size) {
220 printk(KERN_WARNING "Free size accounting screwed\n");
221 printk(KERN_WARNING "free_chunk_size1 == 0x%x, free_chunk_size2 == 0x%x, fmc->free_size == 0x%x\n", free_chunk_size1, free_chunk_size2, fmc->free_size);
224 D3(printk("jffs_fmalloc(): free_chunk_size1 = %u, "
225 "free_chunk_size2 = %u\n",
226 free_chunk_size1, free_chunk_size2));
228 if (size <= free_chunk_size1) {
229 if (!(fm->nodes = (struct jffs_node_ref *)
230 kmalloc(sizeof(struct jffs_node_ref),
231 GFP_KERNEL))) {
232 D(printk("jffs_fmalloc(): kmalloc() failed! "
233 "(node_ref)\n"));
234 jffs_free_fm(fm);
235 return -ENOMEM;
237 DJM(no_jffs_node_ref++);
238 fm->nodes->node = node;
239 fm->nodes->next = NULL;
240 if (fmc->tail) {
241 fm->offset = fmc->tail->offset + fmc->tail->size;
242 if (fm->offset == fmc->flash_size) {
243 fm->offset = 0;
245 ASSERT(else if (fm->offset > fmc->flash_size) {
246 printk(KERN_WARNING "jffs_fmalloc(): "
247 "offset > flash_end\n");
248 fm->offset = 0;
251 else {
252 /* There don't have to be files in the file
253 system yet. */
254 fm->offset = 0;
256 fm->size = size;
257 fmc->free_size -= size;
258 fmc->used_size += size;
260 else if (size > free_chunk_size2) {
261 printk(KERN_WARNING "JFFS: Tried to allocate a too "
262 "large flash memory chunk. (size = %u)\n", size);
263 jffs_free_fm(fm);
264 return -ENOSPC;
266 else {
267 fm->offset = fmc->tail->offset + fmc->tail->size;
268 fm->size = free_chunk_size1;
269 fm->nodes = NULL;
270 fmc->free_size -= fm->size;
271 fmc->dirty_size += fm->size; /* Changed by simonk. This seemingly fixes a
272 bug that caused infinite garbage collection.
273 It previously set fmc->dirty_size to size (which is the
274 size of the requested chunk).
278 fm->next = NULL;
279 if (!fmc->head) {
280 fm->prev = NULL;
281 fmc->head = fm;
282 fmc->tail = fm;
284 else {
285 fm->prev = fmc->tail;
286 fmc->tail->next = fm;
287 fmc->tail = fm;
290 D3(jffs_print_fmcontrol(fmc));
291 D3(jffs_print_fm(fm));
292 *result = fm;
293 return 0;
297 /* The on-flash space is not needed anymore by the passed node. Remove
298 the reference to the node from the node list. If the data chunk in
299 the flash memory isn't used by any more nodes anymore (fm->nodes == 0),
300 then mark that chunk as dirty. */
302 jffs_fmfree(struct jffs_fmcontrol *fmc, struct jffs_fm *fm, struct jffs_node *node)
304 struct jffs_node_ref *ref;
305 struct jffs_node_ref *prev;
306 ASSERT(int del = 0);
308 D2(printk("jffs_fmfree(): node->ino = %u, node->version = %u\n",
309 node->ino, node->version));
311 ASSERT(if (!fmc || !fm || !fm->nodes) {
312 printk(KERN_ERR "jffs_fmfree(): fmc: 0x%p, fm: 0x%p, "
313 "fm->nodes: 0x%p\n",
314 fmc, fm, (fm ? fm->nodes : NULL));
315 return -1;
318 /* Find the reference to the node that is going to be removed
319 and remove it. */
320 for (ref = fm->nodes, prev = NULL; ref; ref = ref->next) {
321 if (ref->node == node) {
322 if (prev) {
323 prev->next = ref->next;
325 else {
326 fm->nodes = ref->next;
328 kfree(ref);
329 DJM(no_jffs_node_ref--);
330 ASSERT(del = 1);
331 break;
333 prev = ref;
336 /* If the data chunk in the flash memory isn't used anymore
337 just mark it as obsolete. */
338 if (!fm->nodes) {
339 /* No node uses this chunk so let's remove it. */
340 fmc->used_size -= fm->size;
341 fmc->dirty_size += fm->size;
342 #if defined(JFFS_MARK_OBSOLETE) && JFFS_MARK_OBSOLETE
343 if (jffs_mark_obsolete(fmc, fm->offset) < 0) {
344 D1(printk("jffs_fmfree(): Failed to mark an on-flash "
345 "node obsolete!\n"));
346 return -1;
348 #endif
351 ASSERT(if (!del) {
352 printk(KERN_WARNING "***jffs_fmfree(): "
353 "Didn't delete any node reference!\n");
356 return 0;
360 /* This allocation function is used during the initialization of
361 the file system. */
362 struct jffs_fm *
363 jffs_fmalloced(struct jffs_fmcontrol *fmc, __u32 offset, __u32 size,
364 struct jffs_node *node)
366 struct jffs_fm *fm;
368 D3(printk("jffs_fmalloced()\n"));
370 if (!(fm = jffs_alloc_fm())) {
371 D(printk("jffs_fmalloced(0x%p, %u, %u, 0x%p): failed!\n",
372 fmc, offset, size, node));
373 return NULL;
375 fm->offset = offset;
376 fm->size = size;
377 fm->prev = NULL;
378 fm->next = NULL;
379 fm->nodes = NULL;
380 if (node) {
381 /* `node' exists and it should be associated with the
382 jffs_fm structure `fm'. */
383 if (!(fm->nodes = (struct jffs_node_ref *)
384 kmalloc(sizeof(struct jffs_node_ref),
385 GFP_KERNEL))) {
386 D(printk("jffs_fmalloced(): !fm->nodes\n"));
387 jffs_free_fm(fm);
388 return NULL;
390 DJM(no_jffs_node_ref++);
391 fm->nodes->node = node;
392 fm->nodes->next = NULL;
393 fmc->used_size += size;
394 fmc->free_size -= size;
396 else {
397 /* If there is no node, then this is just a chunk of dirt. */
398 fmc->dirty_size += size;
399 fmc->free_size -= size;
402 if (fmc->head_extra) {
403 fm->prev = fmc->tail_extra;
404 fmc->tail_extra->next = fm;
405 fmc->tail_extra = fm;
407 else if (!fmc->head) {
408 fmc->head = fm;
409 fmc->tail = fm;
411 else if (fmc->tail->offset + fmc->tail->size < offset) {
412 fmc->head_extra = fm;
413 fmc->tail_extra = fm;
415 else {
416 fm->prev = fmc->tail;
417 fmc->tail->next = fm;
418 fmc->tail = fm;
420 D3(jffs_print_fmcontrol(fmc));
421 D3(jffs_print_fm(fm));
422 return fm;
426 /* Add a new node to an already existing jffs_fm struct. */
428 jffs_add_node(struct jffs_node *node)
430 struct jffs_node_ref *ref;
432 D3(printk("jffs_add_node(): ino = %u\n", node->ino));
434 ref = (struct jffs_node_ref *)kmalloc(sizeof(struct jffs_node_ref),
435 GFP_KERNEL);
436 if (!ref)
437 return -ENOMEM;
439 DJM(no_jffs_node_ref++);
440 ref->node = node;
441 ref->next = node->fm->nodes;
442 node->fm->nodes = ref;
443 return 0;
447 /* Free a part of some allocated space. */
448 void
449 jffs_fmfree_partly(struct jffs_fmcontrol *fmc, struct jffs_fm *fm, __u32 size)
451 D1(printk("***jffs_fmfree_partly(): fm = 0x%p, fm->nodes = 0x%p, "
452 "fm->nodes->node->ino = %u, size = %u\n",
453 fm, (fm ? fm->nodes : 0),
454 (!fm ? 0 : (!fm->nodes ? 0 : fm->nodes->node->ino)), size));
456 if (fm->nodes) {
457 kfree(fm->nodes);
458 DJM(no_jffs_node_ref--);
459 fm->nodes = NULL;
461 fmc->used_size -= fm->size;
462 if (fm == fmc->tail) {
463 fm->size -= size;
464 fmc->free_size += size;
466 fmc->dirty_size += fm->size;
470 /* Find the jffs_fm struct that contains the end of the data chunk that
471 begins at the logical beginning of the flash memory and spans `size'
472 bytes. If we want to erase a sector of the flash memory, we use this
473 function to find where the sector limit cuts a chunk of data. */
474 struct jffs_fm *
475 jffs_cut_node(struct jffs_fmcontrol *fmc, __u32 size)
477 struct jffs_fm *fm;
478 __u32 pos = 0;
480 if (size == 0) {
481 return NULL;
484 ASSERT(if (!fmc) {
485 printk(KERN_ERR "jffs_cut_node(): fmc == NULL\n");
486 return NULL;
489 fm = fmc->head;
491 while (fm) {
492 pos += fm->size;
493 if (pos < size) {
494 fm = fm->next;
496 else if (pos > size) {
497 break;
499 else {
500 fm = NULL;
501 break;
505 return fm;
509 /* Move the head of the fmc structures and delete the obsolete parts. */
510 void
511 jffs_sync_erase(struct jffs_fmcontrol *fmc, int erased_size)
513 struct jffs_fm *fm;
514 struct jffs_fm *del;
516 ASSERT(if (!fmc) {
517 printk(KERN_ERR "jffs_sync_erase(): fmc == NULL\n");
518 return;
521 fmc->dirty_size -= erased_size;
522 fmc->free_size += erased_size;
524 for (fm = fmc->head; fm && (erased_size > 0);) {
525 if (erased_size >= fm->size) {
526 erased_size -= fm->size;
527 del = fm;
528 fm = fm->next;
529 fm->prev = NULL;
530 fmc->head = fm;
531 jffs_free_fm(del);
533 else {
534 fm->size -= erased_size;
535 fm->offset += erased_size;
536 break;
542 /* Return the oldest used node in the flash memory. */
543 struct jffs_node *
544 jffs_get_oldest_node(struct jffs_fmcontrol *fmc)
546 struct jffs_fm *fm;
547 struct jffs_node_ref *nref;
548 struct jffs_node *node = NULL;
550 ASSERT(if (!fmc) {
551 printk(KERN_ERR "jffs_get_oldest_node(): fmc == NULL\n");
552 return NULL;
555 for (fm = fmc->head; fm && !fm->nodes; fm = fm->next);
557 if (!fm) {
558 return NULL;
561 /* The oldest node is the last one in the reference list. This list
562 shouldn't be too long; just one or perhaps two elements. */
563 for (nref = fm->nodes; nref; nref = nref->next) {
564 node = nref->node;
567 D2(printk("jffs_get_oldest_node(): ino = %u, version = %u\n",
568 (node ? node->ino : 0), (node ? node->version : 0)));
570 return node;
574 #if defined(JFFS_MARK_OBSOLETE) && JFFS_MARK_OBSOLETE
576 /* Mark an on-flash node as obsolete.
578 Note that this is just an optimization that isn't necessary for the
579 filesystem to work. */
581 static int
582 jffs_mark_obsolete(struct jffs_fmcontrol *fmc, __u32 fm_offset)
584 /* The `accurate_pos' holds the position of the accurate byte
585 in the jffs_raw_inode structure that we are going to mark
586 as obsolete. */
587 __u32 accurate_pos = fm_offset + JFFS_RAW_INODE_ACCURATE_OFFSET;
588 unsigned char zero = 0x00;
589 size_t len;
591 D3(printk("jffs_mark_obsolete(): accurate_pos = %u\n", accurate_pos));
592 ASSERT(if (!fmc) {
593 printk(KERN_ERR "jffs_mark_obsolete(): fmc == NULL\n");
594 return -1;
597 /* Write 0x00 to the raw inode's accurate member. Don't care
598 about the return value. */
599 MTD_WRITE(fmc->mtd, accurate_pos, 1, &len, &zero);
600 return 0;
603 #endif /* JFFS_MARK_OBSOLETE */
605 /* check if it's possible to erase the wanted range, and if not, return
606 * the range that IS erasable, or a negative error code.
608 static long
609 jffs_flash_erasable_size(struct mtd_info *mtd, __u32 offset, __u32 size)
611 u_long ssize;
613 /* assume that sector size for a partition is constant even
614 * if it spans more than one chip (you usually put the same
615 * type of chips in a system)
618 ssize = mtd->erasesize;
620 if (offset % ssize) {
621 printk(KERN_WARNING "jffs_flash_erasable_size() given non-aligned offset %x (erasesize %lx)\n", offset, ssize);
622 /* The offset is not sector size aligned. */
623 return -1;
625 else if (offset > mtd->size) {
626 printk(KERN_WARNING "jffs_flash_erasable_size given offset off the end of device (%x > %x)\n", offset, mtd->size);
627 return -2;
629 else if (offset + size > mtd->size) {
630 printk(KERN_WARNING "jffs_flash_erasable_size() given length which runs off the end of device (ofs %x + len %x = %x, > %x)\n", offset,size, offset+size, mtd->size);
631 return -3;
634 return (size / ssize) * ssize;
638 /* How much dirty flash memory is possible to erase at the moment? */
639 long
640 jffs_erasable_size(struct jffs_fmcontrol *fmc)
642 struct jffs_fm *fm;
643 __u32 size = 0;
644 long ret;
646 ASSERT(if (!fmc) {
647 printk(KERN_ERR "jffs_erasable_size(): fmc = NULL\n");
648 return -1;
651 if (!fmc->head) {
652 /* The flash memory is totally empty. No nodes. No dirt.
653 Just return. */
654 return 0;
657 /* Calculate how much space that is dirty. */
658 for (fm = fmc->head; fm && !fm->nodes; fm = fm->next) {
659 if (size && fm->offset == 0) {
660 /* We have reached the beginning of the flash. */
661 break;
663 size += fm->size;
666 /* Someone's signature contained this:
667 There's a fine line between fishing and just standing on
668 the shore like an idiot... */
669 ret = jffs_flash_erasable_size(fmc->mtd, fmc->head->offset, size);
671 ASSERT(if (ret < 0) {
672 printk("jffs_erasable_size: flash_erasable_size() "
673 "returned something less than zero (%ld).\n", ret);
674 printk("jffs_erasable_size: offset = 0x%08x\n",
675 fmc->head->offset);
678 /* If there is dirt on the flash (which is the reason to why
679 this function was called in the first place) but no space is
680 possible to erase right now, the initial part of the list of
681 jffs_fm structs, that hold place for dirty space, could perhaps
682 be shortened. The list's initial "dirty" elements are merged
683 into just one large dirty jffs_fm struct. This operation must
684 only be performed if nothing is possible to erase. Otherwise,
685 jffs_clear_end_of_node() won't work as expected. */
686 if (ret == 0) {
687 struct jffs_fm *head = fmc->head;
688 struct jffs_fm *del;
689 /* While there are two dirty nodes beside each other.*/
690 while (head->nodes == 0
691 && head->next
692 && head->next->nodes == 0) {
693 del = head->next;
694 head->size += del->size;
695 head->next = del->next;
696 if (del->next) {
697 del->next->prev = head;
699 jffs_free_fm(del);
703 return (ret >= 0 ? ret : 0);
706 static struct jffs_fm *jffs_alloc_fm(void)
708 struct jffs_fm *fm;
710 fm = kmem_cache_alloc(fm_cache,GFP_KERNEL);
711 DJM(if (fm) no_jffs_fm++;);
713 return fm;
716 static void jffs_free_fm(struct jffs_fm *n)
718 kmem_cache_free(fm_cache,n);
719 DJM(no_jffs_fm--);
724 struct jffs_node *jffs_alloc_node(void)
726 struct jffs_node *n;
728 n = (struct jffs_node *)kmem_cache_alloc(node_cache,GFP_KERNEL);
729 if(n != NULL)
730 no_jffs_node++;
731 return n;
734 void jffs_free_node(struct jffs_node *n)
736 kmem_cache_free(node_cache,n);
737 no_jffs_node--;
741 int jffs_get_node_inuse(void)
743 return no_jffs_node;
746 void
747 jffs_print_fmcontrol(struct jffs_fmcontrol *fmc)
749 D(printk("struct jffs_fmcontrol: 0x%p\n", fmc));
750 D(printk("{\n"));
751 D(printk(" %u, /* flash_size */\n", fmc->flash_size));
752 D(printk(" %u, /* used_size */\n", fmc->used_size));
753 D(printk(" %u, /* dirty_size */\n", fmc->dirty_size));
754 D(printk(" %u, /* free_size */\n", fmc->free_size));
755 D(printk(" %u, /* sector_size */\n", fmc->sector_size));
756 D(printk(" %u, /* min_free_size */\n", fmc->min_free_size));
757 D(printk(" %u, /* max_chunk_size */\n", fmc->max_chunk_size));
758 D(printk(" 0x%p, /* mtd */\n", fmc->mtd));
759 D(printk(" 0x%p, /* head */ "
760 "(head->offset = 0x%08x)\n",
761 fmc->head, (fmc->head ? fmc->head->offset : 0)));
762 D(printk(" 0x%p, /* tail */ "
763 "(tail->offset + tail->size = 0x%08x)\n",
764 fmc->tail,
765 (fmc->tail ? fmc->tail->offset + fmc->tail->size : 0)));
766 D(printk(" 0x%p, /* head_extra */\n", fmc->head_extra));
767 D(printk(" 0x%p, /* tail_extra */\n", fmc->tail_extra));
768 D(printk("}\n"));
771 void
772 jffs_print_fm(struct jffs_fm *fm)
774 D(printk("struct jffs_fm: 0x%p\n", fm));
775 D(printk("{\n"));
776 D(printk(" 0x%08x, /* offset */\n", fm->offset));
777 D(printk(" %u, /* size */\n", fm->size));
778 D(printk(" 0x%p, /* prev */\n", fm->prev));
779 D(printk(" 0x%p, /* next */\n", fm->next));
780 D(printk(" 0x%p, /* nodes */\n", fm->nodes));
781 D(printk("}\n"));
784 #if 0
785 void
786 jffs_print_node_ref(struct jffs_node_ref *ref)
788 D(printk("struct jffs_node_ref: 0x%p\n", ref));
789 D(printk("{\n"));
790 D(printk(" 0x%p, /* node */\n", ref->node));
791 D(printk(" 0x%p, /* next */\n", ref->next));
792 D(printk("}\n"));
794 #endif /* 0 */