Commit a0778161 authored by Dave Boutcher's avatar Dave Boutcher Committed by Christoph Hellwig

[PATCH] ibmvscsi driver v1.5.1

Based on comments from hch and jejb, an update to the ibmvscsi
driver patch.  Primarily style issues, though the removal of
gratuitous casting lead to some significant refactoring
of functions.

- Moved #include <asm/...> after #include <linux/...>
- removed the map_direct_data and map_indirect_data and moved
   the function inline
- Fixed function declaration style issues (static on a line by
   itself)
- Removed bogus cast from dma_map_single
- Moved setting of data transfer direction to a single helper
   function
- Fixed up some gratuitous casting of types
- Collapsed a couple of other functions inline
- Removed bogus check for NULL from remove
- Removed the "evt_struct_for" routine as being needlessly obfuscatory
Signed-off-by: default avatarJames Bottomley <James.Bottomley@SteelEye.com>
parent 6ca38fb5
...@@ -780,6 +780,15 @@ config SCSI_IPS ...@@ -780,6 +780,15 @@ config SCSI_IPS
To compile this driver as a module, choose M here: the To compile this driver as a module, choose M here: the
module will be called ips. module will be called ips.
config SCSI_IBMVSCSI
tristate "IBM Virtual SCSI support"
depends on PPC_PSERIES || PPC_ISERIES
help
This is the IBM POWER Virtual SCSI Client
To compile this driver as a module, choose M here: the
module will be called ibmvscsic.
config SCSI_INITIO config SCSI_INITIO
tristate "Initio 9100U(W) support" tristate "Initio 9100U(W) support"
depends on PCI && SCSI && BROKEN depends on PCI && SCSI && BROKEN
......
...@@ -119,6 +119,7 @@ obj-$(CONFIG_SCSI_CPQFCTS) += cpqfc.o ...@@ -119,6 +119,7 @@ obj-$(CONFIG_SCSI_CPQFCTS) += cpqfc.o
obj-$(CONFIG_SCSI_LASI700) += 53c700.o lasi700.o obj-$(CONFIG_SCSI_LASI700) += 53c700.o lasi700.o
obj-$(CONFIG_SCSI_NSP32) += nsp32.o obj-$(CONFIG_SCSI_NSP32) += nsp32.o
obj-$(CONFIG_SCSI_IPR) += ipr.o obj-$(CONFIG_SCSI_IPR) += ipr.o
obj-$(CONFIG_SCSI_IBMVSCSI) += ibmvscsi/
obj-$(CONFIG_SCSI_SATA_SVW) += libata.o sata_svw.o obj-$(CONFIG_SCSI_SATA_SVW) += libata.o sata_svw.o
obj-$(CONFIG_SCSI_ATA_PIIX) += libata.o ata_piix.o obj-$(CONFIG_SCSI_ATA_PIIX) += libata.o ata_piix.o
obj-$(CONFIG_SCSI_SATA_PROMISE) += libata.o sata_promise.o obj-$(CONFIG_SCSI_SATA_PROMISE) += libata.o sata_promise.o
......
obj-$(CONFIG_SCSI_IBMVSCSI) += ibmvscsic.o
ibmvscsic-y += ibmvscsi.o
ibmvscsic-$(CONFIG_PPC_ISERIES) += iseries_vscsi.o
ibmvscsic-$(CONFIG_PPC_PSERIES) += rpa_vscsi.o
This diff is collapsed.
/* ------------------------------------------------------------
* ibmvscsi.h
* (C) Copyright IBM Corporation 1994, 2003
* Authors: Colin DeVilbiss (devilbis@us.ibm.com)
* Santiago Leon (santil@us.ibm.com)
* Dave Boutcher (sleddog@us.ibm.com)
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation; either version 2 of the License, or
* (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307
* USA
*
* ------------------------------------------------------------
* Emulation of a SCSI host adapter for Virtual I/O devices
*
* This driver allows the Linux SCSI peripheral drivers to directly
* access devices in the hosting partition, either on an iSeries
* hypervisor system or a converged hypervisor system.
*/
#ifndef IBMVSCSI_H
#define IBMVSCSI_H
#include <linux/types.h>
#include <linux/list.h>
#include <linux/completion.h>
#include <linux/interrupt.h>
#include "viosrp.h"
struct scsi_cmnd;
struct Scsi_Host;
/* Number of indirect bufs...the list of these has to fit in the
* additional data of the srp_cmd struct along with the indirect
* descriptor
*/
#define MAX_INDIRECT_BUFS 10
/* ------------------------------------------------------------
* Data Structures
*/
/* an RPA command/response transport queue */
struct crq_queue {
struct viosrp_crq *msgs;
int size, cur;
dma_addr_t msg_token;
spinlock_t lock;
};
/* a unit of work for the hosting partition */
struct srp_event_struct {
union viosrp_iu *xfer_iu;
struct scsi_cmnd *cmnd;
struct list_head list;
void (*done) (struct srp_event_struct *);
struct viosrp_crq crq;
struct ibmvscsi_host_data *hostdata;
atomic_t free;
union viosrp_iu iu;
void (*cmnd_done) (struct scsi_cmnd *);
struct completion comp;
};
/* a pool of event structs for use */
struct event_pool {
struct srp_event_struct *events;
u32 size;
int next;
union viosrp_iu *iu_storage;
dma_addr_t iu_token;
};
/* all driver data associated with a host adapter */
struct ibmvscsi_host_data {
atomic_t request_limit;
struct device *dev;
struct event_pool pool;
struct crq_queue queue;
struct tasklet_struct srp_task;
struct list_head sent;
struct Scsi_Host *host;
struct mad_adapter_info_data madapter_info;
};
/* routines for managing a command/response queue */
int ibmvscsi_init_crq_queue(struct crq_queue *queue,
struct ibmvscsi_host_data *hostdata,
int max_requests);
void ibmvscsi_release_crq_queue(struct crq_queue *queue,
struct ibmvscsi_host_data *hostdata,
int max_requests);
void ibmvscsi_reset_crq_queue(struct crq_queue *queue,
struct ibmvscsi_host_data *hostdata);
void ibmvscsi_handle_crq(struct viosrp_crq *crq,
struct ibmvscsi_host_data *hostdata);
int ibmvscsi_send_crq(struct ibmvscsi_host_data *hostdata,
u64 word1, u64 word2);
#endif /* IBMVSCSI_H */
/* ------------------------------------------------------------
* iSeries_vscsi.c
* (C) Copyright IBM Corporation 1994, 2003
* Authors: Colin DeVilbiss (devilbis@us.ibm.com)
* Santiago Leon (santil@us.ibm.com)
* Dave Boutcher (sleddog@us.ibm.com)
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation; either version 2 of the License, or
* (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307
* USA
*
* ------------------------------------------------------------
* iSeries-specific functions of the SCSI host adapter for Virtual I/O devices
*
* This driver allows the Linux SCSI peripheral drivers to directly
* access devices in the hosting partition, either on an iSeries
* hypervisor system or a converged hypervisor system.
*/
#include <asm/iSeries/vio.h>
#include <asm/iSeries/HvLpEvent.h>
#include <asm/iSeries/HvTypes.h>
#include <asm/iSeries/HvLpConfig.h>
#include <asm/vio.h>
#include <linux/device.h>
#include "ibmvscsi.h"
/* global variables */
static struct ibmvscsi_host_data *single_host_data;
/* ------------------------------------------------------------
* Routines for direct interpartition interaction
*/
struct srp_lp_event {
struct HvLpEvent lpevt; /* 0x00-0x17 */
u32 reserved1; /* 0x18-0x1B; unused */
u16 version; /* 0x1C-0x1D; unused */
u16 subtype_rc; /* 0x1E-0x1F; unused */
struct viosrp_crq crq; /* 0x20-0x3F */
};
/**
* standard interface for handling logical partition events.
*/
static void ibmvscsi_handle_event(struct HvLpEvent *lpevt)
{
struct srp_lp_event *evt = (struct srp_lp_event *)lpevt;
if (!evt) {
printk(KERN_ERR "ibmvscsi: received null event\n");
return;
}
if (single_host_data == NULL) {
printk(KERN_ERR
"ibmvscsi: received event, no adapter present\n");
return;
}
ibmvscsi_handle_crq(&evt->crq, single_host_data);
}
/* ------------------------------------------------------------
* Routines for driver initialization
*/
int ibmvscsi_init_crq_queue(struct crq_queue *queue,
struct ibmvscsi_host_data *hostdata,
int max_requests)
{
int rc;
single_host_data = hostdata;
rc = viopath_open(viopath_hostLp, viomajorsubtype_scsi, 0);
if (rc < 0) {
printk("viopath_open failed with rc %d in open_event_path\n",
rc);
goto viopath_open_failed;
}
rc = vio_setHandler(viomajorsubtype_scsi, ibmvscsi_handle_event);
if (rc < 0) {
printk("vio_setHandler failed with rc %d in open_event_path\n",
rc);
goto vio_setHandler_failed;
}
return 0;
vio_setHandler_failed:
viopath_close(viopath_hostLp, viomajorsubtype_scsi, max_requests);
viopath_open_failed:
return -1;
}
void ibmvscsi_release_crq_queue(struct crq_queue *queue,
struct ibmvscsi_host_data *hostdata,
int max_requests)
{
vio_clearHandler(viomajorsubtype_scsi);
viopath_close(viopath_hostLp, viomajorsubtype_scsi, max_requests);
}
/**
* reset_crq_queue: - resets a crq after a failure
* @queue: crq_queue to initialize and register
* @hostdata: ibmvscsi_host_data of host
*
* no-op for iSeries
*/
void ibmvscsi_reset_crq_queue(struct crq_queue *queue,
struct ibmvscsi_host_data *hostdata)
{
}
/**
* ibmvscsi_send_crq: - Send a CRQ
* @hostdata: the adapter
* @word1: the first 64 bits of the data
* @word2: the second 64 bits of the data
*/
int ibmvscsi_send_crq(struct ibmvscsi_host_data *hostdata, u64 word1, u64 word2)
{
single_host_data = hostdata;
return HvCallEvent_signalLpEventFast(viopath_hostLp,
HvLpEvent_Type_VirtualIo,
viomajorsubtype_scsi,
HvLpEvent_AckInd_NoAck,
HvLpEvent_AckType_ImmediateAck,
viopath_sourceinst(viopath_hostLp),
viopath_targetinst(viopath_hostLp),
0,
VIOVERSION << 16, word1, word2, 0,
0);
}
/* ------------------------------------------------------------
* rpa_vscsi.c
* (C) Copyright IBM Corporation 1994, 2003
* Authors: Colin DeVilbiss (devilbis@us.ibm.com)
* Santiago Leon (santil@us.ibm.com)
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation; either version 2 of the License, or
* (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307
* USA
*
* ------------------------------------------------------------
* RPA-specific functions of the SCSI host adapter for Virtual I/O devices
*
* This driver allows the Linux SCSI peripheral drivers to directly
* access devices in the hosting partition, either on an iSeries
* hypervisor system or a converged hypervisor system.
*/
#include <asm/vio.h>
#include <asm/iommu.h>
#include <asm/hvcall.h>
#include <linux/dma-mapping.h>
#include <linux/interrupt.h>
#include "ibmvscsi.h"
/* ------------------------------------------------------------
* Routines for managing the command/response queue
*/
/**
* ibmvscsi_handle_event: - Interrupt handler for crq events
* @irq: number of irq to handle, not used
* @dev_instance: ibmvscsi_host_data of host that received interrupt
* @regs: pt_regs with registers
*
* Disables interrupts and schedules srp_task
* Always returns IRQ_HANDLED
*/
static irqreturn_t ibmvscsi_handle_event(int irq,
void *dev_instance,
struct pt_regs *regs)
{
struct ibmvscsi_host_data *hostdata =
(struct ibmvscsi_host_data *)dev_instance;
vio_disable_interrupts(to_vio_dev(hostdata->dev));
tasklet_schedule(&hostdata->srp_task);
return IRQ_HANDLED;
}
/**
* release_crq_queue: - Deallocates data and unregisters CRQ
* @queue: crq_queue to initialize and register
* @host_data: ibmvscsi_host_data of host
*
* Frees irq, deallocates a page for messages, unmaps dma, and unregisters
* the crq with the hypervisor.
*/
void ibmvscsi_release_crq_queue(struct crq_queue *queue,
struct ibmvscsi_host_data *hostdata,
int max_requests)
{
long rc;
struct vio_dev *vdev = to_vio_dev(hostdata->dev);
free_irq(vdev->irq, (void *)hostdata);
tasklet_kill(&hostdata->srp_task);
do {
rc = plpar_hcall_norets(H_FREE_CRQ, vdev->unit_address);
} while ((rc == H_Busy) || (H_isLongBusy(rc)));
dma_unmap_single(hostdata->dev,
queue->msg_token,
queue->size * sizeof(*queue->msgs), DMA_BIDIRECTIONAL);
free_page((unsigned long)queue->msgs);
}
/**
* crq_queue_next_crq: - Returns the next entry in message queue
* @queue: crq_queue to use
*
* Returns pointer to next entry in queue, or NULL if there are no new
* entried in the CRQ.
*/
static struct viosrp_crq *crq_queue_next_crq(struct crq_queue *queue)
{
struct viosrp_crq *crq;
unsigned long flags;
spin_lock_irqsave(&queue->lock, flags);
crq = &queue->msgs[queue->cur];
if (crq->valid & 0x80) {
if (++queue->cur == queue->size)
queue->cur = 0;
} else
crq = NULL;
spin_unlock_irqrestore(&queue->lock, flags);
return crq;
}
/**
* ibmvscsi_send_crq: - Send a CRQ
* @hostdata: the adapter
* @word1: the first 64 bits of the data
* @word2: the second 64 bits of the data
*/
int ibmvscsi_send_crq(struct ibmvscsi_host_data *hostdata, u64 word1, u64 word2)
{
struct vio_dev *vdev = to_vio_dev(hostdata->dev);
return plpar_hcall_norets(H_SEND_CRQ, vdev->unit_address, word1, word2);
}
/**
* ibmvscsi_task: - Process srps asynchronously
* @data: ibmvscsi_host_data of host
*/
static void ibmvscsi_task(void *data)
{
struct ibmvscsi_host_data *hostdata = (struct ibmvscsi_host_data *)data;
struct vio_dev *vdev = to_vio_dev(hostdata->dev);
struct viosrp_crq *crq;
int done = 0;
while (!done) {
/* Pull all the valid messages off the CRQ */
while ((crq = crq_queue_next_crq(&hostdata->queue)) != NULL) {
ibmvscsi_handle_crq(crq, hostdata);
crq->valid = 0x00;
}
vio_enable_interrupts(vdev);
if ((crq = crq_queue_next_crq(&hostdata->queue)) != NULL) {
vio_disable_interrupts(vdev);
ibmvscsi_handle_crq(crq, hostdata);
crq->valid = 0x00;
} else {
done = 1;
}
}
}
/**
* initialize_crq_queue: - Initializes and registers CRQ with hypervisor
* @queue: crq_queue to initialize and register
* @hostdata: ibmvscsi_host_data of host
*
* Allocates a page for messages, maps it for dma, and registers
* the crq with the hypervisor.
* Returns zero on success.
*/
int ibmvscsi_init_crq_queue(struct crq_queue *queue,
struct ibmvscsi_host_data *hostdata,
int max_requests)
{
int rc;
struct vio_dev *vdev = to_vio_dev(hostdata->dev);
queue->msgs = (struct viosrp_crq *)get_zeroed_page(GFP_KERNEL);
if (!queue->msgs)
goto malloc_failed;
queue->size = PAGE_SIZE / sizeof(*queue->msgs);
queue->msg_token = dma_map_single(hostdata->dev, queue->msgs,
queue->size * sizeof(*queue->msgs),
DMA_BIDIRECTIONAL);
if (dma_mapping_error(queue->msg_token))
goto map_failed;
rc = plpar_hcall_norets(H_REG_CRQ,
vdev->unit_address,
queue->msg_token, PAGE_SIZE);
if (rc == 2) {
/* Adapter is good, but other end is not ready */
printk(KERN_WARNING "ibmvscsi: Partner adapter not ready\n");
} else if (rc != 0) {
printk(KERN_WARNING "ibmvscsi: Error %d opening adapter\n", rc);
goto reg_crq_failed;
}
if (request_irq(vdev->irq,
ibmvscsi_handle_event,
0, "ibmvscsi", (void *)hostdata) != 0) {
printk(KERN_ERR "ibmvscsi: couldn't register irq 0x%x\n",
vdev->irq);
goto req_irq_failed;
}
rc = vio_enable_interrupts(vdev);
if (rc != 0) {
printk(KERN_ERR "ibmvscsi: Error %d enabling interrupts!!!\n",
rc);
goto req_irq_failed;
}
queue->cur = 0;
queue->lock = SPIN_LOCK_UNLOCKED;
tasklet_init(&hostdata->srp_task, (void *)ibmvscsi_task,
(unsigned long)hostdata);
return 0;
req_irq_failed:
do {
rc = plpar_hcall_norets(H_FREE_CRQ, vdev->unit_address);
} while ((rc == H_Busy) || (H_isLongBusy(rc)));
reg_crq_failed:
dma_unmap_single(hostdata->dev,
queue->msg_token,
queue->size * sizeof(*queue->msgs), DMA_BIDIRECTIONAL);
map_failed:
free_page((unsigned long)queue->msgs);
malloc_failed:
return -1;
}
/**
* reset_crq_queue: - resets a crq after a failure
* @queue: crq_queue to initialize and register
* @hostdata: ibmvscsi_host_data of host
*
*/
void ibmvscsi_reset_crq_queue(struct crq_queue *queue,
struct ibmvscsi_host_data *hostdata)
{
int rc;
struct vio_dev *vdev = to_vio_dev(hostdata->dev);
/* Close the CRQ */
do {
rc = plpar_hcall_norets(H_FREE_CRQ, vdev->unit_address);
} while ((rc == H_Busy) || (H_isLongBusy(rc)));
/* Clean out the queue */
memset(queue->msgs, 0x00, PAGE_SIZE);
queue->cur = 0;
/* And re-open it again */
rc = plpar_hcall_norets(H_REG_CRQ,
vdev->unit_address,
queue->msg_token, PAGE_SIZE);
if (rc == 2) {
/* Adapter is good, but other end is not ready */
printk(KERN_WARNING "ibmvscsi: Partner adapter not ready\n");
} else if (rc != 0) {
printk(KERN_WARNING
"ibmvscsi: couldn't register crq--rc 0x%x\n", rc);
}
}
/*****************************************************************************/
/* srp.h -- SCSI RDMA Protocol definitions */
/* */
/* Written By: Colin Devilbis, IBM Corporation */
/* */
/* Copyright (C) 2003 IBM Corporation */
/* */
/* This program is free software; you can redistribute it and/or modify */
/* it under the terms of the GNU General Public License as published by */
/* the Free Software Foundation; either version 2 of the License, or */
/* (at your option) any later version. */
/* */
/* This program is distributed in the hope that it will be useful, */
/* but WITHOUT ANY WARRANTY; without even the implied warranty of */
/* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the */
/* GNU General Public License for more details. */
/* */
/* You should have received a copy of the GNU General Public License */
/* along with this program; if not, write to the Free Software */
/* Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA */
/* */
/* */
/* This file contains structures and definitions for the SCSI RDMA Protocol */
/* (SRP) as defined in the T10 standard available at www.t10.org. This */
/* file was based on the 16a version of the standard */
/* */
/*****************************************************************************/
#ifndef SRP_H
#define SRP_H
#define PACKED __attribute__((packed))
enum srp_types {
SRP_LOGIN_REQ_TYPE = 0x00,
SRP_LOGIN_RSP_TYPE = 0xC0,
SRP_LOGIN_REJ_TYPE = 0x80,
SRP_I_LOGOUT_TYPE = 0x03,
SRP_T_LOGOUT_TYPE = 0x80,
SRP_TSK_MGMT_TYPE = 0x01,
SRP_CMD_TYPE = 0x02,
SRP_RSP_TYPE = 0xC1,
SRP_CRED_REQ_TYPE = 0x81,
SRP_CRED_RSP_TYPE = 0x41,
SRP_AER_REQ_TYPE = 0x82,
SRP_AER_RSP_TYPE = 0x42
};
enum srp_descriptor_formats {
SRP_NO_BUFFER = 0x00,
SRP_DIRECT_BUFFER = 0x01,
SRP_INDIRECT_BUFFER = 0x02
};
struct memory_descriptor {
u64 virtual_address;
u32 memory_handle;
u32 length;
};
struct indirect_descriptor {
struct memory_descriptor head;
u32 total_length;
struct memory_descriptor list[1] PACKED;
};
struct srp_generic {
u8 type;
u8 reserved1[7];
u64 tag;
};
struct srp_login_req {
u8 type;
u8 reserved1[7];
u64 tag;
u32 max_requested_initiator_to_target_iulen;
u32 reserved2;
u16 required_buffer_formats;
u8 reserved3:6;
u8 multi_channel_action:2;
u8 reserved4;
u32 reserved5;
u8 initiator_port_identifier[16];
u8 target_port_identifier[16];
};
struct srp_login_rsp {
u8 type;
u8 reserved1[3];
u32 request_limit_delta;
u64 tag;
u32 max_initiator_to_target_iulen;
u32 max_target_to_initiator_iulen;
u16 supported_buffer_formats;
u8 reserved2:6;
u8 multi_channel_result:2;
u8 reserved3;
u8 reserved4[24];
};
struct srp_login_rej {
u8 type;
u8 reserved1[3];
u32 reason;
u64 tag;
u64 reserved2;
u16 supported_buffer_formats;
u8 reserved3[6];
};
struct srp_i_logout {
u8 type;
u8 reserved1[7];
u64 tag;
};
struct srp_t_logout {
u8 type;
u8 reserved1[3];
u32 reason;
u64 tag;
};
struct srp_tsk_mgmt {
u8 type;
u8 reserved1[7];
u64 tag;
u32 reserved2;
u64 lun PACKED;
u8 reserved3;
u8 reserved4;
u8 task_mgmt_flags;
u8 reserved5;
u64 managed_task_tag;
u64 reserved6;
};
struct srp_cmd {
u8 type;
u32 reserved1 PACKED;
u8 data_out_format:4;
u8 data_in_format:4;
u8 data_out_count;
u8 data_in_count;
u64 tag;
u32 reserved2;
u64 lun PACKED;
u8 reserved3;
u8 reserved4:5;
u8 task_attribute:3;
u8 reserved5;
u8 additional_cdb_len;
u8 cdb[16];
u8 additional_data[0x100 - 0x30];
};
struct srp_rsp {
u8 type;
u8 reserved1[3];
u32 request_limit_delta;
u64 tag;
u16 reserved2;
u8 reserved3:2;
u8 diunder:1;
u8 diover:1;
u8 dounder:1;
u8 doover:1;
u8 snsvalid:1;
u8 rspvalid:1;
u8 status;
u32 data_in_residual_count;
u32 data_out_residual_count;
u32 sense_data_list_length;
u32 response_data_list_length;
u8 sense_and_response_data[18];
};
struct srp_cred_req {
u8 type;
u8 reserved1[3];
u32 request_limit_delta;
u64 tag;
};
struct srp_cred_rsp {
u8 type;
u8 reserved1[7];
u64 tag;
};
struct srp_aer_req {
u8 type;
u8 reserved1[3];
u32 request_limit_delta;
u64 tag;
u32 reserved2;
u64 lun;
u32 sense_data_list_length;
u32 reserved3;
u8 sense_data[20];
};
struct srp_aer_rsp {
u8 type;
u8 reserved1[7];
u64 tag;
};
union srp_iu {
struct srp_generic generic;
struct srp_login_req login_req;
struct srp_login_rsp login_rsp;
struct srp_login_rej login_rej;
struct srp_i_logout i_logout;
struct srp_t_logout t_logout;
struct srp_tsk_mgmt tsk_mgmt;
struct srp_cmd cmd;
struct srp_rsp rsp;
struct srp_cred_req cred_req;
struct srp_cred_rsp cred_rsp;
struct srp_aer_req aer_req;
struct srp_aer_rsp aer_rsp;
};
#endif
/*****************************************************************************/
/* srp.h -- SCSI RDMA Protocol definitions */
/* */
/* Written By: Colin Devilbis, IBM Corporation */
/* */
/* Copyright (C) 2003 IBM Corporation */
/* */
/* This program is free software; you can redistribute it and/or modify */
/* it under the terms of the GNU General Public License as published by */
/* the Free Software Foundation; either version 2 of the License, or */
/* (at your option) any later version. */
/* */
/* This program is distributed in the hope that it will be useful, */
/* but WITHOUT ANY WARRANTY; without even the implied warranty of */
/* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the */
/* GNU General Public License for more details. */
/* */
/* You should have received a copy of the GNU General Public License */
/* along with this program; if not, write to the Free Software */
/* Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA */
/* */
/* */
/* This file contains structures and definitions for IBM RPA (RS/6000 */
/* platform architecture) implementation of the SRP (SCSI RDMA Protocol) */
/* standard. SRP is used on IBM iSeries and pSeries platforms to send SCSI */
/* commands between logical partitions. */
/* */
/* SRP Information Units (IUs) are sent on a "Command/Response Queue" (CRQ) */
/* between partitions. The definitions in this file are architected, */
/* and cannot be changed without breaking compatibility with other versions */
/* of Linux and other operating systems (AIX, OS/400) that talk this protocol*/
/* between logical partitions */
/*****************************************************************************/
#ifndef VIOSRP_H
#define VIOSRP_H
#include "srp.h"
enum viosrp_crq_formats {
VIOSRP_SRP_FORMAT = 0x01,
VIOSRP_MAD_FORMAT = 0x02,
VIOSRP_OS400_FORMAT = 0x03,
VIOSRP_AIX_FORMAT = 0x04,
VIOSRP_LINUX_FORMAT = 0x06,
VIOSRP_INLINE_FORMAT = 0x07
};
struct viosrp_crq {
u8 valid; /* used by RPA */
u8 format; /* SCSI vs out-of-band */
u8 reserved;
u8 status; /* non-scsi failure? (e.g. DMA failure) */
u16 timeout; /* in seconds */
u16 IU_length; /* in bytes */
u64 IU_data_ptr; /* the TCE for transferring data */
};
/* MADs are Management requests above and beyond the IUs defined in the SRP
* standard.
*/
enum viosrp_mad_types {
VIOSRP_EMPTY_IU_TYPE = 0x01,
VIOSRP_ERROR_LOG_TYPE = 0x02,
VIOSRP_ADAPTER_INFO_TYPE = 0x03,
VIOSRP_HOST_CONFIG_TYPE = 0x04
};
/*
* Common MAD header
*/
struct mad_common {
u32 type;
u16 status;
u16 length;
u64 tag;
};
/*
* All SRP (and MAD) requests normally flow from the
* client to the server. There is no way for the server to send
* an asynchronous message back to the client. The Empty IU is used
* to hang out a meaningless request to the server so that it can respond
* asynchrouously with something like a SCSI AER
*/
struct viosrp_empty_iu {
struct mad_common common;
u64 buffer;
u32 port;
};
struct viosrp_error_log {
struct mad_common common;
u64 buffer;
};
struct viosrp_adapter_info {
struct mad_common common;
u64 buffer;
};
struct viosrp_host_config {
struct mad_common common;
u64 buffer;
};
union mad_iu {
struct viosrp_empty_iu empty_iu;
struct viosrp_error_log error_log;
struct viosrp_adapter_info adapter_info;
struct viosrp_host_config host_config;
};
union viosrp_iu {
union srp_iu srp;
union mad_iu mad;
};
struct mad_adapter_info_data {
char srp_version[8];
char partition_name[96];
u32 partition_number;
u32 mad_version;
u32 os_type;
u32 port_max_txu[8]; /* per-port maximum transfer */
};
#endif
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment