Linux Kernel  3.7.1
 All Data Structures Namespaces Files Functions Variables Typedefs Enumerations Enumerator Macros Groups Pages
segment.c
Go to the documentation of this file.
1 /*
2  * fs/logfs/segment.c - Handling the Object Store
3  *
4  * As should be obvious for Linux kernel code, license is GPLv2
5  *
6  * Copyright (c) 2005-2008 Joern Engel <[email protected]>
7  *
8  * Object store or ostore makes up the complete device with exception of
9  * the superblock and journal areas. Apart from its own metadata it stores
10  * three kinds of objects: inodes, dentries and blocks, both data and indirect.
11  */
12 #include "logfs.h"
13 #include <linux/slab.h>
14 
15 static int logfs_mark_segment_bad(struct super_block *sb, u32 segno)
16 {
17  struct logfs_super *super = logfs_super(sb);
18  struct btree_head32 *head = &super->s_reserved_segments;
19  int err;
20 
21  err = btree_insert32(head, segno, (void *)1, GFP_NOFS);
22  if (err)
23  return err;
25  /* FIXME: write to journal */
26  return 0;
27 }
28 
29 int logfs_erase_segment(struct super_block *sb, u32 segno, int ensure_erase)
30 {
31  struct logfs_super *super = logfs_super(sb);
32 
33  super->s_gec++;
34 
35  return super->s_devops->erase(sb, (u64)segno << super->s_segshift,
36  super->s_segsize, ensure_erase);
37 }
38 
39 static s64 logfs_get_free_bytes(struct logfs_area *area, size_t bytes)
40 {
41  s32 ofs;
42 
43  logfs_open_area(area, bytes);
44 
45  ofs = area->a_used_bytes;
46  area->a_used_bytes += bytes;
47  BUG_ON(area->a_used_bytes >= logfs_super(area->a_sb)->s_segsize);
48 
49  return dev_ofs(area->a_sb, area->a_segno, ofs);
50 }
51 
52 static struct page *get_mapping_page(struct super_block *sb, pgoff_t index,
53  int use_filler)
54 {
55  struct logfs_super *super = logfs_super(sb);
56  struct address_space *mapping = super->s_mapping_inode->i_mapping;
57  filler_t *filler = super->s_devops->readpage;
58  struct page *page;
59 
60  BUG_ON(mapping_gfp_mask(mapping) & __GFP_FS);
61  if (use_filler)
62  page = read_cache_page(mapping, index, filler, sb);
63  else {
64  page = find_or_create_page(mapping, index, GFP_NOFS);
65  unlock_page(page);
66  }
67  return page;
68 }
69 
70 int __logfs_buf_write(struct logfs_area *area, u64 ofs, void *buf, size_t len,
71  int use_filler)
72 {
73  pgoff_t index = ofs >> PAGE_SHIFT;
74  struct page *page;
75  long offset = ofs & (PAGE_SIZE-1);
76  long copylen;
77 
78  /* Only logfs_wbuf_recover may use len==0 */
79  BUG_ON(!len && !use_filler);
80  do {
81  copylen = min((ulong)len, PAGE_SIZE - offset);
82 
83  page = get_mapping_page(area->a_sb, index, use_filler);
84  if (IS_ERR(page))
85  return PTR_ERR(page);
86  BUG_ON(!page); /* FIXME: reserve a pool */
87  SetPageUptodate(page);
88  memcpy(page_address(page) + offset, buf, copylen);
89 
90  if (!PagePrivate(page)) {
91  SetPagePrivate(page);
92  page_cache_get(page);
93  }
94  page_cache_release(page);
95 
96  buf += copylen;
97  len -= copylen;
98  offset = 0;
99  index++;
100  } while (len);
101  return 0;
102 }
103 
104 static void pad_partial_page(struct logfs_area *area)
105 {
106  struct super_block *sb = area->a_sb;
107  struct page *page;
108  u64 ofs = dev_ofs(sb, area->a_segno, area->a_used_bytes);
109  pgoff_t index = ofs >> PAGE_SHIFT;
110  long offset = ofs & (PAGE_SIZE-1);
111  u32 len = PAGE_SIZE - offset;
112 
113  if (len % PAGE_SIZE) {
114  page = get_mapping_page(sb, index, 0);
115  BUG_ON(!page); /* FIXME: reserve a pool */
116  memset(page_address(page) + offset, 0xff, len);
117  if (!PagePrivate(page)) {
118  SetPagePrivate(page);
119  page_cache_get(page);
120  }
121  page_cache_release(page);
122  }
123 }
124 
125 static void pad_full_pages(struct logfs_area *area)
126 {
127  struct super_block *sb = area->a_sb;
128  struct logfs_super *super = logfs_super(sb);
129  u64 ofs = dev_ofs(sb, area->a_segno, area->a_used_bytes);
130  u32 len = super->s_segsize - area->a_used_bytes;
131  pgoff_t index = PAGE_CACHE_ALIGN(ofs) >> PAGE_CACHE_SHIFT;
132  pgoff_t no_indizes = len >> PAGE_CACHE_SHIFT;
133  struct page *page;
134 
135  while (no_indizes) {
136  page = get_mapping_page(sb, index, 0);
137  BUG_ON(!page); /* FIXME: reserve a pool */
138  SetPageUptodate(page);
139  memset(page_address(page), 0xff, PAGE_CACHE_SIZE);
140  if (!PagePrivate(page)) {
141  SetPagePrivate(page);
142  page_cache_get(page);
143  }
144  page_cache_release(page);
145  index++;
146  no_indizes--;
147  }
148 }
149 
150 /*
151  * bdev_writeseg will write full pages. Memset the tail to prevent data leaks.
152  * Also make sure we allocate (and memset) all pages for final writeout.
153  */
154 static void pad_wbuf(struct logfs_area *area, int final)
155 {
156  pad_partial_page(area);
157  if (final)
158  pad_full_pages(area);
159 }
160 
161 /*
162  * We have to be careful with the alias tree. Since lookup is done by bix,
163  * it needs to be normalized, so 14, 15, 16, etc. all match when dealing with
164  * indirect blocks. So always use it through accessor functions.
165  */
166 static void *alias_tree_lookup(struct super_block *sb, u64 ino, u64 bix,
167  level_t level)
168 {
169  struct btree_head128 *head = &logfs_super(sb)->s_object_alias_tree;
170  pgoff_t index = logfs_pack_index(bix, level);
171 
172  return btree_lookup128(head, ino, index);
173 }
174 
175 static int alias_tree_insert(struct super_block *sb, u64 ino, u64 bix,
176  level_t level, void *val)
177 {
178  struct btree_head128 *head = &logfs_super(sb)->s_object_alias_tree;
179  pgoff_t index = logfs_pack_index(bix, level);
180 
181  return btree_insert128(head, ino, index, val, GFP_NOFS);
182 }
183 
184 static int btree_write_alias(struct super_block *sb, struct logfs_block *block,
185  write_alias_t *write_one_alias)
186 {
187  struct object_alias_item *item;
188  int err;
189 
190  list_for_each_entry(item, &block->item_list, list) {
191  err = write_alias_journal(sb, block->ino, block->bix,
192  block->level, item->child_no, item->val);
193  if (err)
194  return err;
195  }
196  return 0;
197 }
198 
199 static struct logfs_block_ops btree_block_ops = {
200  .write_block = btree_write_block,
201  .free_block = __free_block,
202  .write_alias = btree_write_alias,
203 };
204 
206  struct logfs_obj_alias *oa, int count)
207 {
208  struct logfs_super *super = logfs_super(sb);
209  struct logfs_block *block;
210  struct object_alias_item *item;
211  u64 ino, bix;
212  level_t level;
213  int i, err;
214 
216  count /= sizeof(*oa);
217  for (i = 0; i < count; i++) {
218  item = mempool_alloc(super->s_alias_pool, GFP_NOFS);
219  if (!item)
220  return -ENOMEM;
221  memset(item, 0, sizeof(*item));
222 
223  super->s_no_object_aliases++;
224  item->val = oa[i].val;
225  item->child_no = be16_to_cpu(oa[i].child_no);
226 
227  ino = be64_to_cpu(oa[i].ino);
228  bix = be64_to_cpu(oa[i].bix);
229  level = LEVEL(oa[i].level);
230 
231  log_aliases("logfs_load_object_aliases(%llx, %llx, %x, %x) %llx\n",
232  ino, bix, level, item->child_no,
233  be64_to_cpu(item->val));
234  block = alias_tree_lookup(sb, ino, bix, level);
235  if (!block) {
236  block = __alloc_block(sb, ino, bix, level);
237  block->ops = &btree_block_ops;
238  err = alias_tree_insert(sb, ino, bix, level, block);
239  BUG_ON(err); /* mempool empty */
240  }
241  if (test_and_set_bit(item->child_no, block->alias_map)) {
242  printk(KERN_ERR"LogFS: Alias collision detected\n");
243  return -EIO;
244  }
245  list_move_tail(&block->alias_list, &super->s_object_alias);
246  list_add(&item->list, &block->item_list);
247  }
248  return 0;
249 }
250 
251 static void kill_alias(void *_block, unsigned long ignore0,
252  u64 ignore1, u64 ignore2, size_t ignore3)
253 {
254  struct logfs_block *block = _block;
255  struct super_block *sb = block->sb;
256  struct logfs_super *super = logfs_super(sb);
257  struct object_alias_item *item;
258 
259  while (!list_empty(&block->item_list)) {
260  item = list_entry(block->item_list.next, typeof(*item), list);
261  list_del(&item->list);
262  mempool_free(item, super->s_alias_pool);
263  }
264  block->ops->free_block(sb, block);
265 }
266 
267 static int obj_type(struct inode *inode, level_t level)
268 {
269  if (level == 0) {
270  if (S_ISDIR(inode->i_mode))
271  return OBJ_DENTRY;
272  if (inode->i_ino == LOGFS_INO_MASTER)
273  return OBJ_INODE;
274  }
275  return OBJ_BLOCK;
276 }
277 
278 static int obj_len(struct super_block *sb, int obj_type)
279 {
280  switch (obj_type) {
281  case OBJ_DENTRY:
282  return sizeof(struct logfs_disk_dentry);
283  case OBJ_INODE:
284  return sizeof(struct logfs_disk_inode);
285  case OBJ_BLOCK:
286  return sb->s_blocksize;
287  default:
288  BUG();
289  }
290 }
291 
292 static int __logfs_segment_write(struct inode *inode, void *buf,
293  struct logfs_shadow *shadow, int type, int len, int compr)
294 {
295  struct logfs_area *area;
296  struct super_block *sb = inode->i_sb;
297  s64 ofs;
298  struct logfs_object_header h;
299  int acc_len;
300 
301  if (shadow->gc_level == 0)
302  acc_len = len;
303  else
304  acc_len = obj_len(sb, type);
305 
306  area = get_area(sb, shadow->gc_level);
307  ofs = logfs_get_free_bytes(area, len + LOGFS_OBJECT_HEADERSIZE);
308  LOGFS_BUG_ON(ofs <= 0, sb);
309  /*
310  * Order is important. logfs_get_free_bytes(), by modifying the
311  * segment file, may modify the content of the very page we're about
312  * to write now. Which is fine, as long as the calculated crc and
313  * written data still match. So do the modifications _before_
314  * calculating the crc.
315  */
316 
317  h.len = cpu_to_be16(len);
318  h.type = type;
319  h.compr = compr;
320  h.ino = cpu_to_be64(inode->i_ino);
321  h.bix = cpu_to_be64(shadow->bix);
322  h.crc = logfs_crc32(&h, sizeof(h) - 4, 4);
323  h.data_crc = logfs_crc32(buf, len, 0);
324 
325  logfs_buf_write(area, ofs, &h, sizeof(h));
326  logfs_buf_write(area, ofs + LOGFS_OBJECT_HEADERSIZE, buf, len);
327 
328  shadow->new_ofs = ofs;
329  shadow->new_len = acc_len + LOGFS_OBJECT_HEADERSIZE;
330 
331  return 0;
332 }
333 
334 static s64 logfs_segment_write_compress(struct inode *inode, void *buf,
335  struct logfs_shadow *shadow, int type, int len)
336 {
337  struct super_block *sb = inode->i_sb;
338  void *compressor_buf = logfs_super(sb)->s_compressed_je;
339  ssize_t compr_len;
340  int ret;
341 
342  mutex_lock(&logfs_super(sb)->s_journal_mutex);
343  compr_len = logfs_compress(buf, compressor_buf, len, len);
344 
345  if (compr_len >= 0) {
346  ret = __logfs_segment_write(inode, compressor_buf, shadow,
347  type, compr_len, COMPR_ZLIB);
348  } else {
349  ret = __logfs_segment_write(inode, buf, shadow, type, len,
350  COMPR_NONE);
351  }
352  mutex_unlock(&logfs_super(sb)->s_journal_mutex);
353  return ret;
354 }
355 
362 int logfs_segment_write(struct inode *inode, struct page *page,
363  struct logfs_shadow *shadow)
364 {
365  struct super_block *sb = inode->i_sb;
366  struct logfs_super *super = logfs_super(sb);
367  int do_compress, type, len;
368  int ret;
369  void *buf;
370 
371  super->s_flags |= LOGFS_SB_FLAG_DIRTY;
373  do_compress = logfs_inode(inode)->li_flags & LOGFS_IF_COMPRESSED;
374  if (shadow->gc_level != 0) {
375  /* temporarily disable compression for indirect blocks */
376  do_compress = 0;
377  }
378 
379  type = obj_type(inode, shrink_level(shadow->gc_level));
380  len = obj_len(sb, type);
381  buf = kmap(page);
382  if (do_compress)
383  ret = logfs_segment_write_compress(inode, buf, shadow, type,
384  len);
385  else
386  ret = __logfs_segment_write(inode, buf, shadow, type, len,
387  COMPR_NONE);
388  kunmap(page);
389 
390  log_segment("logfs_segment_write(%llx, %llx, %x) %llx->%llx %x->%x\n",
391  shadow->ino, shadow->bix, shadow->gc_level,
392  shadow->old_ofs, shadow->new_ofs,
393  shadow->old_len, shadow->new_len);
394  /* this BUG_ON did catch a locking bug. useful */
395  BUG_ON(!(shadow->new_ofs & (super->s_segsize - 1)));
396  return ret;
397 }
398 
399 int wbuf_read(struct super_block *sb, u64 ofs, size_t len, void *buf)
400 {
401  pgoff_t index = ofs >> PAGE_SHIFT;
402  struct page *page;
403  long offset = ofs & (PAGE_SIZE-1);
404  long copylen;
405 
406  while (len) {
407  copylen = min((ulong)len, PAGE_SIZE - offset);
408 
409  page = get_mapping_page(sb, index, 1);
410  if (IS_ERR(page))
411  return PTR_ERR(page);
412  memcpy(buf, page_address(page) + offset, copylen);
413  page_cache_release(page);
414 
415  buf += copylen;
416  len -= copylen;
417  offset = 0;
418  index++;
419  }
420  return 0;
421 }
422 
423 /*
424  * The "position" of indirect blocks is ambiguous. It can be the position
425  * of any data block somewhere behind this indirect block. So we need to
426  * normalize the positions through logfs_block_mask() before comparing.
427  */
428 static int check_pos(struct super_block *sb, u64 pos1, u64 pos2, level_t level)
429 {
430  return (pos1 & logfs_block_mask(sb, level)) !=
431  (pos2 & logfs_block_mask(sb, level));
432 }
433 
434 #if 0
435 static int read_seg_header(struct super_block *sb, u64 ofs,
436  struct logfs_segment_header *sh)
437 {
438  __be32 crc;
439  int err;
440 
441  err = wbuf_read(sb, ofs, sizeof(*sh), sh);
442  if (err)
443  return err;
444  crc = logfs_crc32(sh, sizeof(*sh), 4);
445  if (crc != sh->crc) {
446  printk(KERN_ERR"LOGFS: header crc error at %llx: expected %x, "
447  "got %x\n", ofs, be32_to_cpu(sh->crc),
448  be32_to_cpu(crc));
449  return -EIO;
450  }
451  return 0;
452 }
453 #endif
454 
455 static int read_obj_header(struct super_block *sb, u64 ofs,
456  struct logfs_object_header *oh)
457 {
458  __be32 crc;
459  int err;
460 
461  err = wbuf_read(sb, ofs, sizeof(*oh), oh);
462  if (err)
463  return err;
464  crc = logfs_crc32(oh, sizeof(*oh) - 4, 4);
465  if (crc != oh->crc) {
466  printk(KERN_ERR"LOGFS: header crc error at %llx: expected %x, "
467  "got %x\n", ofs, be32_to_cpu(oh->crc),
468  be32_to_cpu(crc));
469  return -EIO;
470  }
471  return 0;
472 }
473 
474 static void move_btree_to_page(struct inode *inode, struct page *page,
475  __be64 *data)
476 {
477  struct super_block *sb = inode->i_sb;
478  struct logfs_super *super = logfs_super(sb);
479  struct btree_head128 *head = &super->s_object_alias_tree;
480  struct logfs_block *block;
481  struct object_alias_item *item, *next;
482 
483  if (!(super->s_flags & LOGFS_SB_FLAG_OBJ_ALIAS))
484  return;
485 
486  block = btree_remove128(head, inode->i_ino, page->index);
487  if (!block)
488  return;
489 
490  log_blockmove("move_btree_to_page(%llx, %llx, %x)\n",
491  block->ino, block->bix, block->level);
492  list_for_each_entry_safe(item, next, &block->item_list, list) {
493  data[item->child_no] = item->val;
494  list_del(&item->list);
495  mempool_free(item, super->s_alias_pool);
496  }
497  block->page = page;
498 
499  if (!PagePrivate(page)) {
500  SetPagePrivate(page);
501  page_cache_get(page);
502  set_page_private(page, (unsigned long) block);
503  }
504  block->ops = &indirect_block_ops;
505  initialize_block_counters(page, block, data, 0);
506 }
507 
508 /*
509  * This silences a false, yet annoying gcc warning. I hate it when my editor
510  * jumps into bitops.h each time I recompile this file.
511  * TODO: Complain to gcc folks about this and upgrade compiler.
512  */
513 static unsigned long fnb(const unsigned long *addr,
514  unsigned long size, unsigned long offset)
515 {
516  return find_next_bit(addr, size, offset);
517 }
518 
519 void move_page_to_btree(struct page *page)
520 {
521  struct logfs_block *block = logfs_block(page);
522  struct super_block *sb = block->sb;
523  struct logfs_super *super = logfs_super(sb);
524  struct object_alias_item *item;
525  unsigned long pos;
526  __be64 *child;
527  int err;
528 
529  if (super->s_flags & LOGFS_SB_FLAG_SHUTDOWN) {
530  block->ops->free_block(sb, block);
531  return;
532  }
533  log_blockmove("move_page_to_btree(%llx, %llx, %x)\n",
534  block->ino, block->bix, block->level);
536 
537  for (pos = 0; ; pos++) {
538  pos = fnb(block->alias_map, LOGFS_BLOCK_FACTOR, pos);
539  if (pos >= LOGFS_BLOCK_FACTOR)
540  break;
541 
542  item = mempool_alloc(super->s_alias_pool, GFP_NOFS);
543  BUG_ON(!item); /* mempool empty */
544  memset(item, 0, sizeof(*item));
545 
546  child = kmap_atomic(page);
547  item->val = child[pos];
548  kunmap_atomic(child);
549  item->child_no = pos;
550  list_add(&item->list, &block->item_list);
551  }
552  block->page = NULL;
553 
554  if (PagePrivate(page)) {
555  ClearPagePrivate(page);
556  page_cache_release(page);
557  set_page_private(page, 0);
558  }
559  block->ops = &btree_block_ops;
560  err = alias_tree_insert(block->sb, block->ino, block->bix, block->level,
561  block);
562  BUG_ON(err); /* mempool empty */
563  ClearPageUptodate(page);
564 }
565 
566 static int __logfs_segment_read(struct inode *inode, void *buf,
567  u64 ofs, u64 bix, level_t level)
568 {
569  struct super_block *sb = inode->i_sb;
570  void *compressor_buf = logfs_super(sb)->s_compressed_je;
571  struct logfs_object_header oh;
572  __be32 crc;
573  u16 len;
574  int err, block_len;
575 
576  block_len = obj_len(sb, obj_type(inode, level));
577  err = read_obj_header(sb, ofs, &oh);
578  if (err)
579  goto out_err;
580 
581  err = -EIO;
582  if (be64_to_cpu(oh.ino) != inode->i_ino
583  || check_pos(sb, be64_to_cpu(oh.bix), bix, level)) {
584  printk(KERN_ERR"LOGFS: (ino, bix) don't match at %llx: "
585  "expected (%lx, %llx), got (%llx, %llx)\n",
586  ofs, inode->i_ino, bix,
587  be64_to_cpu(oh.ino), be64_to_cpu(oh.bix));
588  goto out_err;
589  }
590 
591  len = be16_to_cpu(oh.len);
592 
593  switch (oh.compr) {
594  case COMPR_NONE:
595  err = wbuf_read(sb, ofs + LOGFS_OBJECT_HEADERSIZE, len, buf);
596  if (err)
597  goto out_err;
598  crc = logfs_crc32(buf, len, 0);
599  if (crc != oh.data_crc) {
600  printk(KERN_ERR"LOGFS: uncompressed data crc error at "
601  "%llx: expected %x, got %x\n", ofs,
602  be32_to_cpu(oh.data_crc),
603  be32_to_cpu(crc));
604  goto out_err;
605  }
606  break;
607  case COMPR_ZLIB:
608  mutex_lock(&logfs_super(sb)->s_journal_mutex);
609  err = wbuf_read(sb, ofs + LOGFS_OBJECT_HEADERSIZE, len,
610  compressor_buf);
611  if (err) {
612  mutex_unlock(&logfs_super(sb)->s_journal_mutex);
613  goto out_err;
614  }
615  crc = logfs_crc32(compressor_buf, len, 0);
616  if (crc != oh.data_crc) {
617  printk(KERN_ERR"LOGFS: compressed data crc error at "
618  "%llx: expected %x, got %x\n", ofs,
619  be32_to_cpu(oh.data_crc),
620  be32_to_cpu(crc));
621  mutex_unlock(&logfs_super(sb)->s_journal_mutex);
622  goto out_err;
623  }
624  err = logfs_uncompress(compressor_buf, buf, len, block_len);
625  mutex_unlock(&logfs_super(sb)->s_journal_mutex);
626  if (err) {
627  printk(KERN_ERR"LOGFS: uncompress error at %llx\n", ofs);
628  goto out_err;
629  }
630  break;
631  default:
632  LOGFS_BUG(sb);
633  err = -EIO;
634  goto out_err;
635  }
636  return 0;
637 
638 out_err:
639  logfs_set_ro(sb);
640  printk(KERN_ERR"LOGFS: device is read-only now\n");
641  LOGFS_BUG(sb);
642  return err;
643 }
644 
655 int logfs_segment_read(struct inode *inode, struct page *page,
656  u64 ofs, u64 bix, level_t level)
657 {
658  int err;
659  void *buf;
660 
661  if (PageUptodate(page))
662  return 0;
663 
664  ofs &= ~LOGFS_FULLY_POPULATED;
665 
666  buf = kmap(page);
667  err = __logfs_segment_read(inode, buf, ofs, bix, level);
668  if (!err) {
669  move_btree_to_page(inode, page, buf);
670  SetPageUptodate(page);
671  }
672  kunmap(page);
673  log_segment("logfs_segment_read(%lx, %llx, %x) %llx (%d)\n",
674  inode->i_ino, bix, level, ofs, err);
675  return err;
676 }
677 
678 int logfs_segment_delete(struct inode *inode, struct logfs_shadow *shadow)
679 {
680  struct super_block *sb = inode->i_sb;
681  struct logfs_super *super = logfs_super(sb);
682  struct logfs_object_header h;
683  u16 len;
684  int err;
685 
686  super->s_flags |= LOGFS_SB_FLAG_DIRTY;
689  if (!shadow->old_ofs)
690  return 0;
691 
692  log_segment("logfs_segment_delete(%llx, %llx, %x) %llx->%llx %x->%x\n",
693  shadow->ino, shadow->bix, shadow->gc_level,
694  shadow->old_ofs, shadow->new_ofs,
695  shadow->old_len, shadow->new_len);
696  err = read_obj_header(sb, shadow->old_ofs, &h);
697  LOGFS_BUG_ON(err, sb);
698  LOGFS_BUG_ON(be64_to_cpu(h.ino) != inode->i_ino, sb);
699  LOGFS_BUG_ON(check_pos(sb, shadow->bix, be64_to_cpu(h.bix),
700  shrink_level(shadow->gc_level)), sb);
701 
702  if (shadow->gc_level == 0)
703  len = be16_to_cpu(h.len);
704  else
705  len = obj_len(sb, h.type);
706  shadow->old_len = len + sizeof(h);
707  return 0;
708 }
709 
710 void freeseg(struct super_block *sb, u32 segno)
711 {
712  struct logfs_super *super = logfs_super(sb);
713  struct address_space *mapping = super->s_mapping_inode->i_mapping;
714  struct page *page;
715  u64 ofs, start, end;
716 
717  start = dev_ofs(sb, segno, 0);
718  end = dev_ofs(sb, segno + 1, 0);
719  for (ofs = start; ofs < end; ofs += PAGE_SIZE) {
720  page = find_get_page(mapping, ofs >> PAGE_SHIFT);
721  if (!page)
722  continue;
723  if (PagePrivate(page)) {
724  ClearPagePrivate(page);
725  page_cache_release(page);
726  }
727  page_cache_release(page);
728  }
729 }
730 
731 int logfs_open_area(struct logfs_area *area, size_t bytes)
732 {
733  struct super_block *sb = area->a_sb;
734  struct logfs_super *super = logfs_super(sb);
735  int err, closed = 0;
736 
737  if (area->a_is_open && area->a_used_bytes + bytes <= super->s_segsize)
738  return 0;
739 
740  if (area->a_is_open) {
741  u64 ofs = dev_ofs(sb, area->a_segno, area->a_written_bytes);
742  u32 len = super->s_segsize - area->a_written_bytes;
743 
744  log_gc("logfs_close_area(%x)\n", area->a_segno);
745  pad_wbuf(area, 1);
746  super->s_devops->writeseg(area->a_sb, ofs, len);
747  freeseg(sb, area->a_segno);
748  closed = 1;
749  }
750 
751  area->a_used_bytes = 0;
752  area->a_written_bytes = 0;
753 again:
754  area->a_ops->get_free_segment(area);
755  area->a_ops->get_erase_count(area);
756 
757  log_gc("logfs_open_area(%x, %x)\n", area->a_segno, area->a_level);
758  err = area->a_ops->erase_segment(area);
759  if (err) {
760  printk(KERN_WARNING "LogFS: Error erasing segment %x\n",
761  area->a_segno);
762  logfs_mark_segment_bad(sb, area->a_segno);
763  goto again;
764  }
765  area->a_is_open = 1;
766  return closed;
767 }
768 
769 void logfs_sync_area(struct logfs_area *area)
770 {
771  struct super_block *sb = area->a_sb;
772  struct logfs_super *super = logfs_super(sb);
773  u64 ofs = dev_ofs(sb, area->a_segno, area->a_written_bytes);
774  u32 len = (area->a_used_bytes - area->a_written_bytes);
775 
776  if (super->s_writesize)
777  len &= ~(super->s_writesize - 1);
778  if (len == 0)
779  return;
780  pad_wbuf(area, 0);
781  super->s_devops->writeseg(sb, ofs, len);
782  area->a_written_bytes += len;
783 }
784 
786 {
787  struct logfs_super *super = logfs_super(sb);
788  int i;
789 
790  for_each_area(i)
791  logfs_sync_area(super->s_area[i]);
792 }
793 
794 /*
795  * Pick a free segment to be used for this area. Effectively takes a
796  * candidate from the free list (not really a candidate anymore).
797  */
798 static void ostore_get_free_segment(struct logfs_area *area)
799 {
800  struct super_block *sb = area->a_sb;
801  struct logfs_super *super = logfs_super(sb);
802 
803  if (super->s_free_list.count == 0) {
804  printk(KERN_ERR"LOGFS: ran out of free segments\n");
805  LOGFS_BUG(sb);
806  }
807 
808  area->a_segno = get_best_cand(sb, &super->s_free_list, NULL);
809 }
810 
811 static void ostore_get_erase_count(struct logfs_area *area)
812 {
813  struct logfs_segment_entry se;
814  u32 ec_level;
815 
816  logfs_get_segment_entry(area->a_sb, area->a_segno, &se);
817  BUG_ON(se.ec_level == cpu_to_be32(BADSEG) ||
818  se.valid == cpu_to_be32(RESERVED));
819 
820  ec_level = be32_to_cpu(se.ec_level);
821  area->a_erase_count = (ec_level >> 4) + 1;
822 }
823 
824 static int ostore_erase_segment(struct logfs_area *area)
825 {
826  struct super_block *sb = area->a_sb;
827  struct logfs_segment_header sh;
828  u64 ofs;
829  int err;
830 
831  err = logfs_erase_segment(sb, area->a_segno, 0);
832  if (err)
833  return err;
834 
835  sh.pad = 0;
836  sh.type = SEG_OSTORE;
837  sh.level = (__force u8)area->a_level;
838  sh.segno = cpu_to_be32(area->a_segno);
839  sh.ec = cpu_to_be32(area->a_erase_count);
840  sh.gec = cpu_to_be64(logfs_super(sb)->s_gec);
841  sh.crc = logfs_crc32(&sh, sizeof(sh), 4);
842 
844  area->a_level);
845 
846  ofs = dev_ofs(sb, area->a_segno, 0);
847  area->a_used_bytes = sizeof(sh);
848  logfs_buf_write(area, ofs, &sh, sizeof(sh));
849  return 0;
850 }
851 
852 static const struct logfs_area_ops ostore_area_ops = {
853  .get_free_segment = ostore_get_free_segment,
854  .get_erase_count = ostore_get_erase_count,
855  .erase_segment = ostore_erase_segment,
856 };
857 
858 static void free_area(struct logfs_area *area)
859 {
860  if (area)
861  freeseg(area->a_sb, area->a_segno);
862  kfree(area);
863 }
864 
865 void free_areas(struct super_block *sb)
866 {
867  struct logfs_super *super = logfs_super(sb);
868  int i;
869 
870  for_each_area(i)
871  free_area(super->s_area[i]);
872  free_area(super->s_journal_area);
873 }
874 
875 static struct logfs_area *alloc_area(struct super_block *sb)
876 {
877  struct logfs_area *area;
878 
879  area = kzalloc(sizeof(*area), GFP_KERNEL);
880  if (!area)
881  return NULL;
882 
883  area->a_sb = sb;
884  return area;
885 }
886 
887 static void map_invalidatepage(struct page *page, unsigned long l)
888 {
889  return;
890 }
891 
892 static int map_releasepage(struct page *page, gfp_t g)
893 {
894  /* Don't release these pages */
895  return 0;
896 }
897 
898 static const struct address_space_operations mapping_aops = {
899  .invalidatepage = map_invalidatepage,
900  .releasepage = map_releasepage,
901  .set_page_dirty = __set_page_dirty_nobuffers,
902 };
903 
905 {
906  struct logfs_super *super = logfs_super(sb);
907  struct address_space *mapping;
908  struct inode *inode;
909 
911  if (IS_ERR(inode))
912  return PTR_ERR(inode);
913  super->s_mapping_inode = inode;
914  mapping = inode->i_mapping;
915  mapping->a_ops = &mapping_aops;
916  /* Would it be possible to use __GFP_HIGHMEM as well? */
917  mapping_set_gfp_mask(mapping, GFP_NOFS);
918  return 0;
919 }
920 
922 {
923  struct logfs_super *super = logfs_super(sb);
924  int i = -1;
925 
926  super->s_alias_pool = mempool_create_kmalloc_pool(600,
927  sizeof(struct object_alias_item));
928  if (!super->s_alias_pool)
929  return -ENOMEM;
930 
931  super->s_journal_area = alloc_area(sb);
932  if (!super->s_journal_area)
933  goto err;
934 
935  for_each_area(i) {
936  super->s_area[i] = alloc_area(sb);
937  if (!super->s_area[i])
938  goto err;
939  super->s_area[i]->a_level = GC_LEVEL(i);
940  super->s_area[i]->a_ops = &ostore_area_ops;
941  }
942  btree_init_mempool128(&super->s_object_alias_tree,
943  super->s_btree_pool);
944  return 0;
945 
946 err:
947  for (i--; i >= 0; i--)
948  free_area(super->s_area[i]);
949  free_area(super->s_journal_area);
950  logfs_mempool_destroy(super->s_alias_pool);
951  return -ENOMEM;
952 }
953 
955 {
956  struct logfs_super *super = logfs_super(sb);
957 
958  btree_grim_visitor128(&super->s_object_alias_tree, 0, kill_alias);
959 }