Commit 17b0bcfa authored by FUJITA Tomonori's avatar FUJITA Tomonori Committed by James Bottomley

[SCSI] tgt: convert libsrp and ibmvstgt to use srp_transport

This converts libsrp and ibmvstgt to use srp transport.
Signed-off-by: default avatarFUJITA Tomonori <fujita.tomonori@lab.ntt.co.jp>
Signed-off-by: default avatarMike Christie <michaelc@cs.wisc.edu>
Acked-by: default avatarBrian King <brking@us.ibm.com>
Signed-off-by: default avatarJames Bottomley <James.Bottomley@SteelEye.com>
parent 62fe8826
...@@ -848,7 +848,7 @@ config SCSI_IBMVSCSI ...@@ -848,7 +848,7 @@ config SCSI_IBMVSCSI
config SCSI_IBMVSCSIS config SCSI_IBMVSCSIS
tristate "IBM Virtual SCSI Server support" tristate "IBM Virtual SCSI Server support"
depends on PPC_PSERIES && SCSI_TGT && SCSI_SRP depends on PPC_PSERIES && SCSI_TGT && SCSI_SRP && SCSI_SRP_ATTRS
help help
This is the SRP target driver for IBM pSeries virtual environments. This is the SRP target driver for IBM pSeries virtual environments.
......
...@@ -25,6 +25,7 @@ ...@@ -25,6 +25,7 @@
#include <linux/module.h> #include <linux/module.h>
#include <scsi/scsi.h> #include <scsi/scsi.h>
#include <scsi/scsi_host.h> #include <scsi/scsi_host.h>
#include <scsi/scsi_transport_srp.h>
#include <scsi/scsi_tgt.h> #include <scsi/scsi_tgt.h>
#include <scsi/libsrp.h> #include <scsi/libsrp.h>
#include <asm/hvcall.h> #include <asm/hvcall.h>
...@@ -68,9 +69,12 @@ struct vio_port { ...@@ -68,9 +69,12 @@ struct vio_port {
unsigned long liobn; unsigned long liobn;
unsigned long riobn; unsigned long riobn;
struct srp_target *target; struct srp_target *target;
struct srp_rport *rport;
}; };
static struct workqueue_struct *vtgtd; static struct workqueue_struct *vtgtd;
static struct scsi_transport_template *ibmvstgt_transport_template;
/* /*
* These are fixed for the system and come from the Open Firmware device tree. * These are fixed for the system and come from the Open Firmware device tree.
...@@ -188,6 +192,7 @@ static int send_rsp(struct iu_entry *iue, struct scsi_cmnd *sc, ...@@ -188,6 +192,7 @@ static int send_rsp(struct iu_entry *iue, struct scsi_cmnd *sc,
static void handle_cmd_queue(struct srp_target *target) static void handle_cmd_queue(struct srp_target *target)
{ {
struct Scsi_Host *shost = target->shost; struct Scsi_Host *shost = target->shost;
struct srp_rport *rport = target_to_port(target)->rport;
struct iu_entry *iue; struct iu_entry *iue;
struct srp_cmd *cmd; struct srp_cmd *cmd;
unsigned long flags; unsigned long flags;
...@@ -200,7 +205,8 @@ retry: ...@@ -200,7 +205,8 @@ retry:
if (!test_and_set_bit(V_FLYING, &iue->flags)) { if (!test_and_set_bit(V_FLYING, &iue->flags)) {
spin_unlock_irqrestore(&target->lock, flags); spin_unlock_irqrestore(&target->lock, flags);
cmd = iue->sbuf->buf; cmd = iue->sbuf->buf;
err = srp_cmd_queue(shost, cmd, iue, 0); err = srp_cmd_queue(shost, cmd, iue,
(unsigned long)rport, 0);
if (err) { if (err) {
eprintk("cannot queue cmd %p %d\n", cmd, err); eprintk("cannot queue cmd %p %d\n", cmd, err);
srp_iu_put(iue); srp_iu_put(iue);
...@@ -359,6 +365,16 @@ static void process_login(struct iu_entry *iue) ...@@ -359,6 +365,16 @@ static void process_login(struct iu_entry *iue)
union viosrp_iu *iu = vio_iu(iue); union viosrp_iu *iu = vio_iu(iue);
struct srp_login_rsp *rsp = &iu->srp.login_rsp; struct srp_login_rsp *rsp = &iu->srp.login_rsp;
uint64_t tag = iu->srp.rsp.tag; uint64_t tag = iu->srp.rsp.tag;
struct Scsi_Host *shost = iue->target->shost;
struct srp_target *target = host_to_srp_target(shost);
struct vio_port *vport = target_to_port(target);
struct srp_rport_identifiers ids;
memset(&ids, 0, sizeof(ids));
sprintf(ids.port_id, "%x", vport->dma_dev->unit_address);
ids.roles = SRP_RPORT_ROLE_INITIATOR;
if (!vport->rport)
vport->rport = srp_rport_add(shost, &ids);
/* TODO handle case that requested size is wrong and /* TODO handle case that requested size is wrong and
* buffer format is wrong * buffer format is wrong
...@@ -412,7 +428,9 @@ static int process_tsk_mgmt(struct iu_entry *iue) ...@@ -412,7 +428,9 @@ static int process_tsk_mgmt(struct iu_entry *iue)
fn = 0; fn = 0;
} }
if (fn) if (fn)
scsi_tgt_tsk_mgmt_request(iue->target->shost, fn, scsi_tgt_tsk_mgmt_request(iue->target->shost,
(unsigned long)iue->target->shost,
fn,
iu->srp.tsk_mgmt.task_tag, iu->srp.tsk_mgmt.task_tag,
(struct scsi_lun *) &iu->srp.tsk_mgmt.lun, (struct scsi_lun *) &iu->srp.tsk_mgmt.lun,
iue); iue);
...@@ -721,7 +739,8 @@ static int ibmvstgt_eh_abort_handler(struct scsi_cmnd *sc) ...@@ -721,7 +739,8 @@ static int ibmvstgt_eh_abort_handler(struct scsi_cmnd *sc)
return 0; return 0;
} }
static int ibmvstgt_tsk_mgmt_response(u64 mid, int result) static int ibmvstgt_tsk_mgmt_response(struct Scsi_Host *shost,
u64 itn_id, u64 mid, int result)
{ {
struct iu_entry *iue = (struct iu_entry *) ((void *) mid); struct iu_entry *iue = (struct iu_entry *) ((void *) mid);
union viosrp_iu *iu = vio_iu(iue); union viosrp_iu *iu = vio_iu(iue);
...@@ -747,6 +766,20 @@ static int ibmvstgt_tsk_mgmt_response(u64 mid, int result) ...@@ -747,6 +766,20 @@ static int ibmvstgt_tsk_mgmt_response(u64 mid, int result)
return 0; return 0;
} }
static int ibmvstgt_it_nexus_response(struct Scsi_Host *shost, u64 itn_id,
int result)
{
struct srp_target *target = host_to_srp_target(shost);
struct vio_port *vport = target_to_port(target);
if (result) {
eprintk("%p %d\n", shost, result);
srp_rport_del(vport->rport);
vport->rport = NULL;
}
return 0;
}
static ssize_t system_id_show(struct class_device *cdev, char *buf) static ssize_t system_id_show(struct class_device *cdev, char *buf)
{ {
return snprintf(buf, PAGE_SIZE, "%s\n", system_id); return snprintf(buf, PAGE_SIZE, "%s\n", system_id);
...@@ -804,6 +837,7 @@ static int ibmvstgt_probe(struct vio_dev *dev, const struct vio_device_id *id) ...@@ -804,6 +837,7 @@ static int ibmvstgt_probe(struct vio_dev *dev, const struct vio_device_id *id)
shost = scsi_host_alloc(&ibmvstgt_sht, sizeof(struct srp_target)); shost = scsi_host_alloc(&ibmvstgt_sht, sizeof(struct srp_target));
if (!shost) if (!shost)
goto free_vport; goto free_vport;
shost->transportt = ibmvstgt_transport_template;
err = scsi_tgt_alloc_queue(shost); err = scsi_tgt_alloc_queue(shost);
if (err) if (err)
goto put_host; goto put_host;
...@@ -837,8 +871,8 @@ static int ibmvstgt_probe(struct vio_dev *dev, const struct vio_device_id *id) ...@@ -837,8 +871,8 @@ static int ibmvstgt_probe(struct vio_dev *dev, const struct vio_device_id *id)
err = scsi_add_host(shost, target->dev); err = scsi_add_host(shost, target->dev);
if (err) if (err)
goto destroy_queue; goto destroy_queue;
return 0;
return 0;
destroy_queue: destroy_queue:
crq_queue_destroy(target); crq_queue_destroy(target);
free_srp_target: free_srp_target:
...@@ -857,6 +891,7 @@ static int ibmvstgt_remove(struct vio_dev *dev) ...@@ -857,6 +891,7 @@ static int ibmvstgt_remove(struct vio_dev *dev)
struct vio_port *vport = target->ldata; struct vio_port *vport = target->ldata;
crq_queue_destroy(target); crq_queue_destroy(target);
srp_remove_host(shost);
scsi_remove_host(shost); scsi_remove_host(shost);
scsi_tgt_free_queue(shost); scsi_tgt_free_queue(shost);
srp_target_free(target); srp_target_free(target);
...@@ -909,15 +944,24 @@ static int get_system_info(void) ...@@ -909,15 +944,24 @@ static int get_system_info(void)
return 0; return 0;
} }
static struct srp_function_template ibmvstgt_transport_functions = {
.it_nexus_response = ibmvstgt_it_nexus_response,
};
static int ibmvstgt_init(void) static int ibmvstgt_init(void)
{ {
int err = -ENOMEM; int err = -ENOMEM;
printk("IBM eServer i/pSeries Virtual SCSI Target Driver\n"); printk("IBM eServer i/pSeries Virtual SCSI Target Driver\n");
ibmvstgt_transport_template =
srp_attach_transport(&ibmvstgt_transport_functions);
if (!ibmvstgt_transport_template)
return err;
vtgtd = create_workqueue("ibmvtgtd"); vtgtd = create_workqueue("ibmvtgtd");
if (!vtgtd) if (!vtgtd)
return err; goto release_transport;
err = get_system_info(); err = get_system_info();
if (err) if (err)
...@@ -928,9 +972,10 @@ static int ibmvstgt_init(void) ...@@ -928,9 +972,10 @@ static int ibmvstgt_init(void)
goto destroy_wq; goto destroy_wq;
return 0; return 0;
destroy_wq: destroy_wq:
destroy_workqueue(vtgtd); destroy_workqueue(vtgtd);
release_transport:
srp_release_transport(ibmvstgt_transport_template);
return err; return err;
} }
...@@ -940,6 +985,7 @@ static void ibmvstgt_exit(void) ...@@ -940,6 +985,7 @@ static void ibmvstgt_exit(void)
destroy_workqueue(vtgtd); destroy_workqueue(vtgtd);
vio_unregister_driver(&ibmvstgt_driver); vio_unregister_driver(&ibmvstgt_driver);
srp_release_transport(ibmvstgt_transport_template);
} }
MODULE_DESCRIPTION("IBM Virtual SCSI Target"); MODULE_DESCRIPTION("IBM Virtual SCSI Target");
......
...@@ -392,7 +392,7 @@ static int vscsis_data_length(struct srp_cmd *cmd, enum dma_data_direction dir) ...@@ -392,7 +392,7 @@ static int vscsis_data_length(struct srp_cmd *cmd, enum dma_data_direction dir)
} }
int srp_cmd_queue(struct Scsi_Host *shost, struct srp_cmd *cmd, void *info, int srp_cmd_queue(struct Scsi_Host *shost, struct srp_cmd *cmd, void *info,
u64 addr) u64 itn_id, u64 addr)
{ {
enum dma_data_direction dir; enum dma_data_direction dir;
struct scsi_cmnd *sc; struct scsi_cmnd *sc;
...@@ -428,7 +428,8 @@ int srp_cmd_queue(struct Scsi_Host *shost, struct srp_cmd *cmd, void *info, ...@@ -428,7 +428,8 @@ int srp_cmd_queue(struct Scsi_Host *shost, struct srp_cmd *cmd, void *info,
sc->request_bufflen = len; sc->request_bufflen = len;
sc->request_buffer = (void *) (unsigned long) addr; sc->request_buffer = (void *) (unsigned long) addr;
sc->tag = tag; sc->tag = tag;
err = scsi_tgt_queue_command(sc, (struct scsi_lun *) &cmd->lun, cmd->tag); err = scsi_tgt_queue_command(sc, itn_id, (struct scsi_lun *)&cmd->lun,
cmd->tag);
if (err) if (err)
scsi_host_put_command(shost, sc); scsi_host_put_command(shost, sc);
......
...@@ -59,7 +59,7 @@ extern void srp_target_free(struct srp_target *); ...@@ -59,7 +59,7 @@ extern void srp_target_free(struct srp_target *);
extern struct iu_entry *srp_iu_get(struct srp_target *); extern struct iu_entry *srp_iu_get(struct srp_target *);
extern void srp_iu_put(struct iu_entry *); extern void srp_iu_put(struct iu_entry *);
extern int srp_cmd_queue(struct Scsi_Host *, struct srp_cmd *, void *, u64); extern int srp_cmd_queue(struct Scsi_Host *, struct srp_cmd *, void *, u64, u64);
extern int srp_transfer_data(struct scsi_cmnd *, struct srp_cmd *, extern int srp_transfer_data(struct scsi_cmnd *, struct srp_cmd *,
srp_rdma_t, int, int); srp_rdma_t, int, int);
......
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