in fusion/mptspi.c [513:573]
static int mptspi_read_spi_device_pg0(struct scsi_target *starget,
struct _CONFIG_PAGE_SCSI_DEVICE_0 *pass_pg0)
{
struct Scsi_Host *shost = dev_to_shost(&starget->dev);
struct _MPT_SCSI_HOST *hd = shost_priv(shost);
struct _MPT_ADAPTER *ioc = hd->ioc;
struct _CONFIG_PAGE_SCSI_DEVICE_0 *spi_dev_pg0;
dma_addr_t spi_dev_pg0_dma;
int size;
struct _x_config_parms cfg;
struct _CONFIG_PAGE_HEADER hdr;
int err = -EBUSY;
/* No SPI parameters for RAID devices */
if (starget->channel == 0 &&
mptspi_is_raid(hd, starget->id))
return -1;
size = ioc->spi_data.sdp0length * 4;
/*
if (ioc->spi_data.sdp0length & 1)
size += size + 4;
size += 2048;
*/
spi_dev_pg0 = dma_alloc_coherent(&ioc->pcidev->dev, size, &spi_dev_pg0_dma, GFP_KERNEL);
if (spi_dev_pg0 == NULL) {
starget_printk(KERN_ERR, starget, MYIOC_s_FMT
"dma_alloc_coherent for parameters failed\n", ioc->name);
return -EINVAL;
}
memset(&hdr, 0, sizeof(hdr));
hdr.PageVersion = ioc->spi_data.sdp0version;
hdr.PageLength = ioc->spi_data.sdp0length;
hdr.PageNumber = 0;
hdr.PageType = MPI_CONFIG_PAGETYPE_SCSI_DEVICE;
memset(&cfg, 0, sizeof(cfg));
cfg.cfghdr.hdr = &hdr;
cfg.physAddr = spi_dev_pg0_dma;
cfg.action = MPI_CONFIG_ACTION_PAGE_READ_CURRENT;
cfg.dir = 0;
cfg.pageAddr = starget->id;
cfg.timeout = 60;
if (mpt_config(ioc, &cfg)) {
starget_printk(KERN_ERR, starget, MYIOC_s_FMT "mpt_config failed\n", ioc->name);
goto out_free;
}
err = 0;
memcpy(pass_pg0, spi_dev_pg0, size);
mptspi_print_read_nego(hd, starget, le32_to_cpu(spi_dev_pg0->NegotiatedParameters));
out_free:
dma_free_coherent(&ioc->pcidev->dev, size, spi_dev_pg0, spi_dev_pg0_dma);
return err;
}