mirror of
https://git.kernel.org/pub/scm/linux/kernel/git/stable/linux.git
synced 2024-12-28 16:56:26 +00:00
scsi: simplify scsi_partsize
Call scsi_bios_ptable from scsi_partsize instead of requiring boilerplate code in the callers. Also switch the calling convention to match that of the ->bios_param instances calling this function, and use true/false for the return value instead of the weird -1 convention. Signed-off-by: Christoph Hellwig <hch@lst.de> Signed-off-by: Jens Axboe <axboe@kernel.dk>
This commit is contained in:
parent
26ae3533a0
commit
a10183d744
@ -299,7 +299,6 @@ Summary:
|
||||
scsi_host_alloc - return a new scsi_host instance whose refcount==1
|
||||
scsi_host_get - increments Scsi_Host instance's refcount
|
||||
scsi_host_put - decrements Scsi_Host instance's refcount (free if 0)
|
||||
scsi_partsize - parse partition table into cylinders, heads + sectors
|
||||
scsi_register - create and register a scsi host adapter instance.
|
||||
scsi_remove_device - detach and remove a SCSI device
|
||||
scsi_remove_host - detach and remove all SCSI devices owned by host
|
||||
@ -472,26 +471,6 @@ void scsi_host_get(struct Scsi_Host *shost)
|
||||
void scsi_host_put(struct Scsi_Host *shost)
|
||||
|
||||
|
||||
/**
|
||||
* scsi_partsize - parse partition table into cylinders, heads + sectors
|
||||
* @buf: pointer to partition table
|
||||
* @capacity: size of (total) disk in 512 byte sectors
|
||||
* @cyls: outputs number of cylinders calculated via this pointer
|
||||
* @hds: outputs number of heads calculated via this pointer
|
||||
* @secs: outputs number of sectors calculated via this pointer
|
||||
*
|
||||
* Returns 0 on success, -1 on failure
|
||||
*
|
||||
* Might block: no
|
||||
*
|
||||
* Notes: Caller owns memory returned (free with kfree() )
|
||||
*
|
||||
* Defined in: drivers/scsi/scsicam.c
|
||||
**/
|
||||
int scsi_partsize(unsigned char *buf, unsigned long capacity,
|
||||
unsigned int *cyls, unsigned int *hds, unsigned int *secs)
|
||||
|
||||
|
||||
/**
|
||||
* scsi_register - create and register a scsi host adapter instance.
|
||||
* @sht: pointer to scsi host template
|
||||
|
@ -723,24 +723,17 @@ static int
|
||||
ahd_linux_biosparam(struct scsi_device *sdev, struct block_device *bdev,
|
||||
sector_t capacity, int geom[])
|
||||
{
|
||||
uint8_t *bh;
|
||||
int heads;
|
||||
int sectors;
|
||||
int cylinders;
|
||||
int ret;
|
||||
int extended;
|
||||
struct ahd_softc *ahd;
|
||||
|
||||
ahd = *((struct ahd_softc **)sdev->host->hostdata);
|
||||
|
||||
bh = scsi_bios_ptable(bdev);
|
||||
if (bh) {
|
||||
ret = scsi_partsize(bh, capacity,
|
||||
&geom[2], &geom[0], &geom[1]);
|
||||
kfree(bh);
|
||||
if (ret != -1)
|
||||
return (ret);
|
||||
}
|
||||
if (scsi_partsize(bdev, capacity, geom))
|
||||
return 0;
|
||||
|
||||
heads = 64;
|
||||
sectors = 32;
|
||||
cylinders = aic_sector_div(capacity, heads, sectors);
|
||||
|
@ -695,11 +695,9 @@ static int
|
||||
ahc_linux_biosparam(struct scsi_device *sdev, struct block_device *bdev,
|
||||
sector_t capacity, int geom[])
|
||||
{
|
||||
uint8_t *bh;
|
||||
int heads;
|
||||
int sectors;
|
||||
int cylinders;
|
||||
int ret;
|
||||
int extended;
|
||||
struct ahc_softc *ahc;
|
||||
u_int channel;
|
||||
@ -707,14 +705,9 @@ ahc_linux_biosparam(struct scsi_device *sdev, struct block_device *bdev,
|
||||
ahc = *((struct ahc_softc **)sdev->host->hostdata);
|
||||
channel = sdev_channel(sdev);
|
||||
|
||||
bh = scsi_bios_ptable(bdev);
|
||||
if (bh) {
|
||||
ret = scsi_partsize(bh, capacity,
|
||||
&geom[2], &geom[0], &geom[1]);
|
||||
kfree(bh);
|
||||
if (ret != -1)
|
||||
return (ret);
|
||||
}
|
||||
if (scsi_partsize(bdev, capacity, geom))
|
||||
return 0;
|
||||
|
||||
heads = 64;
|
||||
sectors = 32;
|
||||
cylinders = aic_sector_div(capacity, heads, sectors);
|
||||
|
@ -353,16 +353,11 @@ static irqreturn_t arcmsr_do_interrupt(int irq, void *dev_id)
|
||||
static int arcmsr_bios_param(struct scsi_device *sdev,
|
||||
struct block_device *bdev, sector_t capacity, int *geom)
|
||||
{
|
||||
int ret, heads, sectors, cylinders, total_capacity;
|
||||
unsigned char *buffer;/* return copy of block device's partition table */
|
||||
int heads, sectors, cylinders, total_capacity;
|
||||
|
||||
if (scsi_partsize(bdev, capacity, geom))
|
||||
return 0;
|
||||
|
||||
buffer = scsi_bios_ptable(bdev);
|
||||
if (buffer) {
|
||||
ret = scsi_partsize(buffer, capacity, &geom[2], &geom[0], &geom[1]);
|
||||
kfree(buffer);
|
||||
if (ret != -1)
|
||||
return ret;
|
||||
}
|
||||
total_capacity = capacity;
|
||||
heads = 64;
|
||||
sectors = 32;
|
||||
|
@ -2795,11 +2795,9 @@ megaraid_biosparam(struct scsi_device *sdev, struct block_device *bdev,
|
||||
sector_t capacity, int geom[])
|
||||
{
|
||||
adapter_t *adapter;
|
||||
unsigned char *bh;
|
||||
int heads;
|
||||
int sectors;
|
||||
int cylinders;
|
||||
int rval;
|
||||
|
||||
/* Get pointer to host config structure */
|
||||
adapter = (adapter_t *)sdev->host->hostdata;
|
||||
@ -2826,15 +2824,8 @@ megaraid_biosparam(struct scsi_device *sdev, struct block_device *bdev,
|
||||
geom[2] = cylinders;
|
||||
}
|
||||
else {
|
||||
bh = scsi_bios_ptable(bdev);
|
||||
|
||||
if( bh ) {
|
||||
rval = scsi_partsize(bh, capacity,
|
||||
&geom[2], &geom[0], &geom[1]);
|
||||
kfree(bh);
|
||||
if( rval != -1 )
|
||||
return rval;
|
||||
}
|
||||
if (scsi_partsize(bdev, capacity, geom))
|
||||
return 0;
|
||||
|
||||
dev_info(&adapter->dev->dev,
|
||||
"invalid partition on this disk on channel %d\n",
|
||||
|
@ -48,29 +48,31 @@ EXPORT_SYMBOL(scsi_bios_ptable);
|
||||
|
||||
/**
|
||||
* scsi_partsize - Parse cylinders/heads/sectors from PC partition table
|
||||
* @buf: partition table, see scsi_bios_ptable()
|
||||
* @bdev: block device to parse
|
||||
* @capacity: size of the disk in sectors
|
||||
* @cyls: put cylinders here
|
||||
* @hds: put heads here
|
||||
* @secs: put sectors here
|
||||
* @geom: output in form of [hds, cylinders, sectors]
|
||||
*
|
||||
* Determine the BIOS mapping/geometry used to create the partition
|
||||
* table, storing the results in @cyls, @hds, and @secs
|
||||
* table, storing the results in @geom.
|
||||
*
|
||||
* Returns: -1 on failure, 0 on success.
|
||||
* Returns: %false on failure, %true on success.
|
||||
*/
|
||||
|
||||
int scsi_partsize(unsigned char *buf, unsigned long capacity,
|
||||
unsigned int *cyls, unsigned int *hds, unsigned int *secs)
|
||||
bool scsi_partsize(struct block_device *bdev, sector_t capacity, int geom[3])
|
||||
{
|
||||
struct partition *p = (struct partition *)buf, *largest = NULL;
|
||||
int i, largest_cyl;
|
||||
int cyl, ext_cyl, end_head, end_cyl, end_sector;
|
||||
unsigned int logical_end, physical_end, ext_physical_end;
|
||||
struct partition *p, *largest = NULL;
|
||||
void *buf;
|
||||
int ret = false;
|
||||
|
||||
buf = scsi_bios_ptable(bdev);
|
||||
if (!buf)
|
||||
return false;
|
||||
|
||||
if (*(unsigned short *) (buf + 64) == 0xAA55) {
|
||||
for (largest_cyl = -1, i = 0; i < 4; ++i, ++p) {
|
||||
int largest_cyl = -1, i;
|
||||
|
||||
for (i = 0, p = buf; i < 4; i++, p++) {
|
||||
if (!p->sys_ind)
|
||||
continue;
|
||||
#ifdef DEBUG
|
||||
@ -90,7 +92,7 @@ int scsi_partsize(unsigned char *buf, unsigned long capacity,
|
||||
end_sector = largest->end_sector & 0x3f;
|
||||
|
||||
if (end_head + 1 == 0 || end_sector == 0)
|
||||
return -1;
|
||||
goto out_free_buf;
|
||||
|
||||
#ifdef DEBUG
|
||||
printk("scsicam_bios_param : end at h = %d, c = %d, s = %d\n",
|
||||
@ -115,19 +117,24 @@ int scsi_partsize(unsigned char *buf, unsigned long capacity,
|
||||
,logical_end, physical_end, ext_physical_end, ext_cyl);
|
||||
#endif
|
||||
|
||||
if ((logical_end == physical_end) ||
|
||||
(end_cyl == 1023 && ext_physical_end == logical_end)) {
|
||||
*secs = end_sector;
|
||||
*hds = end_head + 1;
|
||||
*cyls = capacity / ((end_head + 1) * end_sector);
|
||||
return 0;
|
||||
if (logical_end == physical_end ||
|
||||
(end_cyl == 1023 && ext_physical_end == logical_end)) {
|
||||
geom[0] = end_head + 1;
|
||||
geom[1] = end_sector;
|
||||
geom[2] = (unsigned long)capacity /
|
||||
((end_head + 1) * end_sector);
|
||||
ret = true;
|
||||
goto out_free_buf;
|
||||
}
|
||||
#ifdef DEBUG
|
||||
printk("scsicam_bios_param : logical (%u) != physical (%u)\n",
|
||||
logical_end, physical_end);
|
||||
#endif
|
||||
}
|
||||
return -1;
|
||||
|
||||
out_free_buf:
|
||||
kfree(buf);
|
||||
return ret;
|
||||
}
|
||||
EXPORT_SYMBOL(scsi_partsize);
|
||||
|
||||
@ -210,20 +217,14 @@ static int setsize(unsigned long capacity, unsigned int *cyls, unsigned int *hds
|
||||
*/
|
||||
int scsicam_bios_param(struct block_device *bdev, sector_t capacity, int *ip)
|
||||
{
|
||||
unsigned char *p;
|
||||
u64 capacity64 = capacity; /* Suppress gcc warning */
|
||||
int ret;
|
||||
|
||||
p = scsi_bios_ptable(bdev);
|
||||
if (!p)
|
||||
return -1;
|
||||
int ret = 0;
|
||||
|
||||
/* try to infer mapping from partition table */
|
||||
ret = scsi_partsize(p, (unsigned long)capacity, (unsigned int *)ip + 2,
|
||||
(unsigned int *)ip + 0, (unsigned int *)ip + 1);
|
||||
kfree(p);
|
||||
if (scsi_partsize(bdev, capacity, ip))
|
||||
return 0;
|
||||
|
||||
if (ret == -1 && capacity64 < (1ULL << 32)) {
|
||||
if (capacity64 < (1ULL << 32)) {
|
||||
/*
|
||||
* Pick some standard mapping with at most 1024 cylinders, and
|
||||
* at most 62 sectors per track - this works up to 7905 MB.
|
||||
|
@ -13,8 +13,7 @@
|
||||
|
||||
#ifndef SCSICAM_H
|
||||
#define SCSICAM_H
|
||||
extern int scsicam_bios_param (struct block_device *bdev, sector_t capacity, int *ip);
|
||||
extern int scsi_partsize(unsigned char *buf, unsigned long capacity,
|
||||
unsigned int *cyls, unsigned int *hds, unsigned int *secs);
|
||||
extern unsigned char *scsi_bios_ptable(struct block_device *bdev);
|
||||
int scsicam_bios_param(struct block_device *bdev, sector_t capacity, int *ip);
|
||||
bool scsi_partsize(struct block_device *bdev, sector_t capacity, int geom[3]);
|
||||
unsigned char *scsi_bios_ptable(struct block_device *bdev);
|
||||
#endif /* def SCSICAM_H */
|
||||
|
Loading…
Reference in New Issue
Block a user