linux/fs/hpfs/buffer.c
<<
>>
Prefs
   1/*
   2 *  linux/fs/hpfs/buffer.c
   3 *
   4 *  Mikulas Patocka (mikulas@artax.karlin.mff.cuni.cz), 1998-1999
   5 *
   6 *  general buffer i/o
   7 */
   8#include <linux/sched.h>
   9#include <linux/slab.h>
  10#include "hpfs_fn.h"
  11
  12/* Map a sector into a buffer and return pointers to it and to the buffer. */
  13
  14void *hpfs_map_sector(struct super_block *s, unsigned secno, struct buffer_head **bhp,
  15                 int ahead)
  16{
  17        struct buffer_head *bh;
  18
  19        hpfs_lock_assert(s);
  20
  21        cond_resched();
  22
  23        *bhp = bh = sb_bread(s, secno);
  24        if (bh != NULL)
  25                return bh->b_data;
  26        else {
  27                printk("HPFS: hpfs_map_sector: read error\n");
  28                return NULL;
  29        }
  30}
  31
  32/* Like hpfs_map_sector but don't read anything */
  33
  34void *hpfs_get_sector(struct super_block *s, unsigned secno, struct buffer_head **bhp)
  35{
  36        struct buffer_head *bh;
  37        /*return hpfs_map_sector(s, secno, bhp, 0);*/
  38
  39        hpfs_lock_assert(s);
  40
  41        cond_resched();
  42
  43        if ((*bhp = bh = sb_getblk(s, secno)) != NULL) {
  44                if (!buffer_uptodate(bh)) wait_on_buffer(bh);
  45                set_buffer_uptodate(bh);
  46                return bh->b_data;
  47        } else {
  48                printk("HPFS: hpfs_get_sector: getblk failed\n");
  49                return NULL;
  50        }
  51}
  52
  53/* Map 4 sectors into a 4buffer and return pointers to it and to the buffer. */
  54
  55void *hpfs_map_4sectors(struct super_block *s, unsigned secno, struct quad_buffer_head *qbh,
  56                   int ahead)
  57{
  58        struct buffer_head *bh;
  59        char *data;
  60
  61        hpfs_lock_assert(s);
  62
  63        cond_resched();
  64
  65        if (secno & 3) {
  66                printk("HPFS: hpfs_map_4sectors: unaligned read\n");
  67                return NULL;
  68        }
  69
  70        qbh->data = data = kmalloc(2048, GFP_NOFS);
  71        if (!data) {
  72                printk("HPFS: hpfs_map_4sectors: out of memory\n");
  73                goto bail;
  74        }
  75
  76        qbh->bh[0] = bh = sb_bread(s, secno);
  77        if (!bh)
  78                goto bail0;
  79        memcpy(data, bh->b_data, 512);
  80
  81        qbh->bh[1] = bh = sb_bread(s, secno + 1);
  82        if (!bh)
  83                goto bail1;
  84        memcpy(data + 512, bh->b_data, 512);
  85
  86        qbh->bh[2] = bh = sb_bread(s, secno + 2);
  87        if (!bh)
  88                goto bail2;
  89        memcpy(data + 2 * 512, bh->b_data, 512);
  90
  91        qbh->bh[3] = bh = sb_bread(s, secno + 3);
  92        if (!bh)
  93                goto bail3;
  94        memcpy(data + 3 * 512, bh->b_data, 512);
  95
  96        return data;
  97
  98 bail3:
  99        brelse(qbh->bh[2]);
 100 bail2:
 101        brelse(qbh->bh[1]);
 102 bail1:
 103        brelse(qbh->bh[0]);
 104 bail0:
 105        kfree(data);
 106        printk("HPFS: hpfs_map_4sectors: read error\n");
 107 bail:
 108        return NULL;
 109}
 110
 111/* Don't read sectors */
 112
 113void *hpfs_get_4sectors(struct super_block *s, unsigned secno,
 114                          struct quad_buffer_head *qbh)
 115{
 116        cond_resched();
 117
 118        hpfs_lock_assert(s);
 119
 120        if (secno & 3) {
 121                printk("HPFS: hpfs_get_4sectors: unaligned read\n");
 122                return NULL;
 123        }
 124
 125        /*return hpfs_map_4sectors(s, secno, qbh, 0);*/
 126        if (!(qbh->data = kmalloc(2048, GFP_NOFS))) {
 127                printk("HPFS: hpfs_get_4sectors: out of memory\n");
 128                return NULL;
 129        }
 130        if (!(hpfs_get_sector(s, secno, &qbh->bh[0]))) goto bail0;
 131        if (!(hpfs_get_sector(s, secno + 1, &qbh->bh[1]))) goto bail1;
 132        if (!(hpfs_get_sector(s, secno + 2, &qbh->bh[2]))) goto bail2;
 133        if (!(hpfs_get_sector(s, secno + 3, &qbh->bh[3]))) goto bail3;
 134        memcpy(qbh->data, qbh->bh[0]->b_data, 512);
 135        memcpy(qbh->data + 512, qbh->bh[1]->b_data, 512);
 136        memcpy(qbh->data + 2*512, qbh->bh[2]->b_data, 512);
 137        memcpy(qbh->data + 3*512, qbh->bh[3]->b_data, 512);
 138        return qbh->data;
 139
 140        bail3:  brelse(qbh->bh[2]);
 141        bail2:  brelse(qbh->bh[1]);
 142        bail1:  brelse(qbh->bh[0]);
 143        bail0:
 144        return NULL;
 145}
 146        
 147
 148void hpfs_brelse4(struct quad_buffer_head *qbh)
 149{
 150        brelse(qbh->bh[3]);
 151        brelse(qbh->bh[2]);
 152        brelse(qbh->bh[1]);
 153        brelse(qbh->bh[0]);
 154        kfree(qbh->data);
 155}       
 156
 157void hpfs_mark_4buffers_dirty(struct quad_buffer_head *qbh)
 158{
 159        memcpy(qbh->bh[0]->b_data, qbh->data, 512);
 160        memcpy(qbh->bh[1]->b_data, qbh->data + 512, 512);
 161        memcpy(qbh->bh[2]->b_data, qbh->data + 2 * 512, 512);
 162        memcpy(qbh->bh[3]->b_data, qbh->data + 3 * 512, 512);
 163        mark_buffer_dirty(qbh->bh[0]);
 164        mark_buffer_dirty(qbh->bh[1]);
 165        mark_buffer_dirty(qbh->bh[2]);
 166        mark_buffer_dirty(qbh->bh[3]);
 167}
 168