Changeset View
Changeset View
Standalone View
Standalone View
sys/boot/pc98/libpc98/biosdisk.c
Show First 20 Lines • Show All 90 Lines • ▼ Show 20 Lines | |||||
* BIOS unit number. | * BIOS unit number. | ||||
*/ | */ | ||||
static struct bdinfo | static struct bdinfo | ||||
{ | { | ||||
int bd_unit; /* BIOS unit number */ | int bd_unit; /* BIOS unit number */ | ||||
int bd_flags; | int bd_flags; | ||||
int bd_type; /* BIOS 'drive type' (floppy only) */ | int bd_type; /* BIOS 'drive type' (floppy only) */ | ||||
int bd_da_unit; /* kernel unit number for da */ | int bd_da_unit; /* kernel unit number for da */ | ||||
int bd_open; /* reference counter */ | |||||
void *bd_bcache; /* buffer cache data */ | |||||
} bdinfo [MAXBDDEV]; | } bdinfo [MAXBDDEV]; | ||||
static int nbdinfo = 0; | static int nbdinfo = 0; | ||||
#define BD(dev) (bdinfo[(dev)->d_unit]) | |||||
static int bd_getgeom(struct open_disk *od); | static int bd_getgeom(struct open_disk *od); | ||||
static int bd_read(struct open_disk *od, daddr_t dblk, int blks, | static int bd_read(struct open_disk *od, daddr_t dblk, int blks, | ||||
caddr_t dest); | caddr_t dest); | ||||
static int bd_write(struct open_disk *od, daddr_t dblk, int blks, | static int bd_write(struct open_disk *od, daddr_t dblk, int blks, | ||||
caddr_t dest); | caddr_t dest); | ||||
static int bd_int13probe(struct bdinfo *bd); | static int bd_int13probe(struct bdinfo *bd); | ||||
▲ Show 20 Lines • Show All 61 Lines • ▼ Show 20 Lines | |||||
bd_init(void) | bd_init(void) | ||||
{ | { | ||||
int base, unit; | int base, unit; | ||||
int da_drive=0, n=-0x10; | int da_drive=0, n=-0x10; | ||||
/* sequence 0x90, 0x80, 0xa0 */ | /* sequence 0x90, 0x80, 0xa0 */ | ||||
for (base = 0x90; base <= 0xa0; base += n, n += 0x30) { | for (base = 0x90; base <= 0xa0; base += n, n += 0x30) { | ||||
for (unit = base; (nbdinfo < MAXBDDEV) || ((unit & 0x0f) < 4); unit++) { | for (unit = base; (nbdinfo < MAXBDDEV) || ((unit & 0x0f) < 4); unit++) { | ||||
bdinfo[nbdinfo].bd_open = 0; | |||||
bdinfo[nbdinfo].bd_bcache = NULL; | |||||
bdinfo[nbdinfo].bd_unit = unit; | bdinfo[nbdinfo].bd_unit = unit; | ||||
bdinfo[nbdinfo].bd_flags = (unit & 0xf0) == 0x90 ? BD_FLOPPY : 0; | bdinfo[nbdinfo].bd_flags = (unit & 0xf0) == 0x90 ? BD_FLOPPY : 0; | ||||
if (!bd_int13probe(&bdinfo[nbdinfo])){ | if (!bd_int13probe(&bdinfo[nbdinfo])){ | ||||
if (((unit & 0xf0) == 0x90 && (unit & 0x0f) < 4) || | if (((unit & 0xf0) == 0x90 && (unit & 0x0f) < 4) || | ||||
((unit & 0xf0) == 0xa0 && (unit & 0x0f) < 6)) | ((unit & 0xf0) == 0xa0 && (unit & 0x0f) < 6)) | ||||
continue; /* Target IDs are not contiguous. */ | continue; /* Target IDs are not contiguous. */ | ||||
else | else | ||||
Show All 13 Lines | if ((unit & 0xF0) == 0xA0) /* SCSI HD or MO */ | ||||
bdinfo[nbdinfo].bd_da_unit = da_drive++; | bdinfo[nbdinfo].bd_da_unit = da_drive++; | ||||
} | } | ||||
/* XXX we need "disk aliases" to make this simpler */ | /* XXX we need "disk aliases" to make this simpler */ | ||||
printf("BIOS drive %c: is disk%d\n", | printf("BIOS drive %c: is disk%d\n", | ||||
'A' + nbdinfo, nbdinfo); | 'A' + nbdinfo, nbdinfo); | ||||
nbdinfo++; | nbdinfo++; | ||||
} | } | ||||
} | } | ||||
bcache_add_dev(nbdinfo); | |||||
return(0); | return(0); | ||||
} | } | ||||
/* | /* | ||||
* Try to detect a device supported by the legacy int13 BIOS | * Try to detect a device supported by the legacy int13 BIOS | ||||
*/ | */ | ||||
static int | static int | ||||
bd_int13probe(struct bdinfo *bd) | bd_int13probe(struct bdinfo *bd) | ||||
▲ Show 20 Lines • Show All 206 Lines • ▼ Show 20 Lines | bd_open(struct open_file *f, ...) | ||||
int error; | int error; | ||||
va_start(ap, f); | va_start(ap, f); | ||||
dev = va_arg(ap, struct i386_devdesc *); | dev = va_arg(ap, struct i386_devdesc *); | ||||
va_end(ap); | va_end(ap); | ||||
if ((error = bd_opendisk(&od, dev))) | if ((error = bd_opendisk(&od, dev))) | ||||
return(error); | return(error); | ||||
BD(dev).bd_open++; | |||||
if (BD(dev).bd_bcache == NULL) | |||||
BD(dev).bd_bcache = bcache_allocate(); | |||||
/* | /* | ||||
* Save our context | * Save our context | ||||
*/ | */ | ||||
((struct i386_devdesc *)(f->f_devdata))->d_kind.biosdisk.data = od; | ((struct i386_devdesc *)(f->f_devdata))->d_kind.biosdisk.data = od; | ||||
DEBUG("open_disk %p, partition at 0x%x", od, od->od_boff); | DEBUG("open_disk %p, partition at 0x%x", od, od->od_boff); | ||||
return(0); | return(0); | ||||
} | } | ||||
▲ Show 20 Lines • Show All 253 Lines • ▼ Show 20 Lines | for (i = 0; i < od->od_nslices; i++, dp++) { | ||||
} | } | ||||
} | } | ||||
return (prefslice); | return (prefslice); | ||||
} | } | ||||
static int | static int | ||||
bd_close(struct open_file *f) | bd_close(struct open_file *f) | ||||
{ | { | ||||
struct open_disk *od = (struct open_disk *)(((struct i386_devdesc *)(f->f_devdata))->d_kind.biosdisk.data); | struct i386_devdesc *dev = f->f_devdata; | ||||
struct open_disk *od = (struct open_disk *)(dev->d_kind.biosdisk.data); | |||||
BD(dev).bd_open--; | |||||
if (BD(dev).bd_open == 0) { | |||||
bcache_free(BD(dev).bd_bcache); | |||||
BD(dev).bd_bcache = NULL; | |||||
} | |||||
bd_closedisk(od); | bd_closedisk(od); | ||||
return(0); | return(0); | ||||
} | } | ||||
static void | static void | ||||
bd_closedisk(struct open_disk *od) | bd_closedisk(struct open_disk *od) | ||||
{ | { | ||||
DEBUG("open_disk %p", od); | DEBUG("open_disk %p", od); | ||||
#if 0 | #if 0 | ||||
/* XXX is this required? (especially if disk already open...) */ | /* XXX is this required? (especially if disk already open...) */ | ||||
if (od->od_flags & BD_FLOPPY) | if (od->od_flags & BD_FLOPPY) | ||||
delay(3000000); | delay(3000000); | ||||
#endif | #endif | ||||
free(od); | free(od); | ||||
} | } | ||||
static int | static int | ||||
bd_strategy(void *devdata, int rw, daddr_t dblk, size_t size, char *buf, size_t *rsize) | bd_strategy(void *devdata, int rw, daddr_t dblk, size_t offset, size_t size, | ||||
char *buf, size_t *rsize) | |||||
{ | { | ||||
struct bcache_devdata bcd; | struct bcache_devdata bcd; | ||||
struct open_disk *od = (struct open_disk *)(((struct i386_devdesc *)devdata)->d_kind.biosdisk.data); | struct i386_devdesc *dev = f->f_devdata; | ||||
struct open_disk *od = (struct open_disk *)(dev->d_kind.biosdisk.data); | |||||
bcd.dv_strategy = bd_realstrategy; | bcd.dv_strategy = bd_realstrategy; | ||||
bcd.dv_devdata = devdata; | bcd.dv_devdata = devdata; | ||||
return(bcache_strategy(&bcd, od->od_unit, rw, dblk+od->od_boff, size, buf, rsize)); | bcd.dv_cache = BD(dev).bd_bcache; | ||||
return(bcache_strategy(&bcd, od->od_unit, rw, dblk+od->od_boff, offset, | |||||
size, buf, rsize)); | |||||
} | } | ||||
static int | static int | ||||
bd_realstrategy(void *devdata, int rw, daddr_t dblk, size_t size, char *buf, size_t *rsize) | bd_realstrategy(void *devdata, int rw, daddr_t dblk, size_t offset, | ||||
size_t size, char *buf, size_t *rsize) | |||||
{ | { | ||||
struct open_disk *od = (struct open_disk *)(((struct i386_devdesc *)devdata)->d_kind.biosdisk.data); | struct open_disk *od = (struct open_disk *)(((struct i386_devdesc *)devdata)->d_kind.biosdisk.data); | ||||
int blks; | int blks; | ||||
#ifdef BD_SUPPORT_FRAGS | #ifdef BD_SUPPORT_FRAGS | ||||
char fragbuf[BIOSDISK_SECSIZE]; | char fragbuf[BIOSDISK_SECSIZE]; | ||||
size_t fragsize; | size_t fragsize; | ||||
fragsize = size % BIOSDISK_SECSIZE; | fragsize = size % BIOSDISK_SECSIZE; | ||||
▲ Show 20 Lines • Show All 348 Lines • Show Last 20 Lines |