kern

annotate src/bdev.c @ 94:b3351d018ac6

read/write superblock, get/put inode
author John Tsiombikas <nuclear@member.fsf.org>
date Sun, 11 Dec 2011 11:12:30 +0200
parents f83f50c17c3b
children
rev   line source
nuclear@90 1 #include <stdlib.h>
nuclear@91 2 #include <string.h>
nuclear@90 3 #include <assert.h>
nuclear@90 4 #include "bdev.h"
nuclear@90 5 #include "ata.h"
nuclear@90 6 #include "part.h"
nuclear@90 7
nuclear@91 8 #define MKMINOR(disk, part) ((((disk) & 0xf) << 4) | ((part) & 0xf))
nuclear@91 9 #define MINOR_DISK(x) (((x) >> 4) & 0xf)
nuclear@91 10 #define MINOR_PART(x) ((x) & 0xf)
nuclear@90 11
nuclear@90 12 struct block_device *blk_open(dev_t dev)
nuclear@90 13 {
nuclear@90 14 struct block_device *bdev;
nuclear@90 15 int i, minor, devno, part;
nuclear@90 16
nuclear@90 17 /* XXX for now ignore the major number as we only have ata devices */
nuclear@90 18 minor = DEV_MINOR(dev);
nuclear@90 19 devno = MINOR_DISK(minor);
nuclear@90 20 part = MINOR_PART(minor);
nuclear@90 21
nuclear@90 22 bdev = malloc(sizeof *bdev);
nuclear@90 23 assert(bdev);
nuclear@90 24
nuclear@90 25 bdev->ata_dev = devno;
nuclear@90 26
nuclear@90 27 if(part) {
nuclear@90 28 struct partition *plist = get_part_list(devno);
nuclear@90 29 assert(plist);
nuclear@90 30
nuclear@90 31 for(i=1; i<part; i++) {
nuclear@90 32 if(!plist) break;
nuclear@90 33 plist = plist->next;
nuclear@90 34 }
nuclear@90 35 if(!plist) {
nuclear@90 36 free(bdev);
nuclear@90 37 free_part_list(plist);
nuclear@90 38 return 0;
nuclear@90 39 }
nuclear@90 40
nuclear@90 41 bdev->offset = SECT_TO_BLK(plist->start_sect);
nuclear@90 42 bdev->size = SECT_TO_BLK(plist->size_sect);
nuclear@93 43 bdev->ptype = get_part_type(plist);
nuclear@90 44
nuclear@90 45 free_part_list(plist);
nuclear@90 46 } else {
nuclear@90 47 bdev->offset = 0;
nuclear@90 48 bdev->size = SECT_TO_BLK(ata_num_sectors(devno));
nuclear@93 49 bdev->ptype = 0;
nuclear@90 50 }
nuclear@90 51
nuclear@90 52 return bdev;
nuclear@90 53 }
nuclear@90 54
nuclear@90 55 void blk_close(struct block_device *bdev)
nuclear@90 56 {
nuclear@90 57 free(bdev);
nuclear@90 58 }
nuclear@90 59
nuclear@90 60 #define NSECT (BLKSZ / 512)
nuclear@90 61
nuclear@93 62 int blk_read(struct block_device *bdev, uint32_t blk, int count, void *buf)
nuclear@90 63 {
nuclear@90 64 int i;
nuclear@90 65 char *ptr = buf;
nuclear@93 66 uint32_t sect = blk * NSECT + bdev->offset;
nuclear@90 67
nuclear@93 68 for(i=0; i<NSECT * count; i++) {
nuclear@90 69 if(ata_read_pio(bdev->ata_dev, sect++, ptr) == -1) {
nuclear@90 70 return -1;
nuclear@90 71 }
nuclear@90 72 ptr += 512;
nuclear@90 73 }
nuclear@90 74 return 0;
nuclear@90 75 }
nuclear@90 76
nuclear@93 77 int blk_write(struct block_device *bdev, uint32_t blk, int count, void *buf)
nuclear@90 78 {
nuclear@90 79 int i;
nuclear@90 80 char *ptr = buf;
nuclear@93 81 uint32_t sect = blk * NSECT + bdev->offset;
nuclear@90 82
nuclear@93 83 for(i=0; i<NSECT * count; i++) {
nuclear@90 84 if(ata_write_pio(bdev->ata_dev, sect++, ptr) == -1) {
nuclear@90 85 return -1;
nuclear@90 86 }
nuclear@90 87 ptr += 512;
nuclear@90 88 }
nuclear@90 89 return 0;
nuclear@90 90 }
nuclear@91 91
nuclear@91 92 dev_t bdev_by_name(const char *name)
nuclear@91 93 {
nuclear@91 94 int minor;
nuclear@91 95 int atadev, part = 0;
nuclear@91 96
nuclear@91 97 char *tmp = strrchr(name, '/');
nuclear@91 98 if(tmp) {
nuclear@91 99 name = tmp + 1;
nuclear@91 100 }
nuclear@91 101
nuclear@91 102 if(strstr(name, "ata") != name) {
nuclear@91 103 return 0;
nuclear@91 104 }
nuclear@91 105 name += 3;
nuclear@91 106
nuclear@91 107 atadev = strtol(name, &tmp, 10);
nuclear@91 108 if(tmp == name) {
nuclear@91 109 return 0;
nuclear@91 110 }
nuclear@91 111 name = tmp;
nuclear@91 112
nuclear@91 113 if(*name++ == 'p') {
nuclear@91 114 part = strtol(name, &tmp, 10) + 1;
nuclear@91 115 if(tmp == name) {
nuclear@91 116 return 0;
nuclear@91 117 }
nuclear@91 118 }
nuclear@91 119
nuclear@91 120 minor = MKMINOR(atadev, part);
nuclear@93 121 return DEVNO(1, minor);
nuclear@91 122 }