diff --git a/fcst/fcst.h b/fcst/fcst.h index 4f993eb9d..98ff0af0c 100644 --- a/fcst/fcst.h +++ b/fcst/fcst.h @@ -125,7 +125,7 @@ void ft_cmd_free(struct scst_cmd *); void ft_cmd_tm_done(struct scst_mgmt_cmd *); int ft_tgt_detect(struct scst_tgt_template *); int ft_tgt_release(struct scst_tgt *); -ssize_t ft_tgt_enable(struct scst_tgt *, const char *, size_t); +int ft_tgt_enable(struct scst_tgt *, bool); bool ft_tgt_enabled(struct scst_tgt *); int ft_report_aen(struct scst_aen *); diff --git a/fcst/ft_sess.c b/fcst/ft_sess.c index 5580dc0ad..ec119e987 100644 --- a/fcst/ft_sess.c +++ b/fcst/ft_sess.c @@ -496,26 +496,20 @@ int ft_tgt_release(struct scst_tgt *tgt) return 0; } -ssize_t ft_tgt_enable(struct scst_tgt *tgt, const char *buf, size_t len) +int ft_tgt_enable(struct scst_tgt *tgt, bool enable) { struct ft_tport *tport; - ssize_t ret = len; + int ret = 0; mutex_lock(&ft_lport_lock); - switch (buf[0]) { - case '0': - FT_SESS_DBG("disable tgt %s\n", tgt->tgt_name); - ft_tgt_release(tgt); - break; - case '1': + if (enable) { FT_SESS_DBG("enable tgt %s\n", tgt->tgt_name); tport = scst_tgt_get_tgt_priv(tgt); tport->enabled = 1; tport->lport->service_params |= FCP_SPPF_TARG_FCN; - break; - default: - ret = -EINVAL; - break; + } else { + FT_SESS_DBG("disable tgt %s\n", tgt->tgt_name); + ft_tgt_release(tgt); } mutex_unlock(&ft_lport_lock); return ret; diff --git a/iscsi-scst/kernel/iscsi.h b/iscsi-scst/kernel/iscsi.h index 51f8982c7..b9b42c661 100644 --- a/iscsi-scst/kernel/iscsi.h +++ b/iscsi-scst/kernel/iscsi.h @@ -524,8 +524,7 @@ extern void req_add_to_write_timeout_list(struct iscsi_cmnd *req); extern const struct seq_operations iscsi_seq_op; #else extern const struct attribute *iscsi_tgt_attrs[]; -extern ssize_t iscsi_enable_target(struct scst_tgt *scst_tgt, const char *buf, - size_t size); +extern int iscsi_enable_target(struct scst_tgt *scst_tgt, bool enable); extern bool iscsi_is_target_enabled(struct scst_tgt *scst_tgt); extern ssize_t iscsi_sysfs_send_event(uint32_t tid, enum iscsi_kern_event_code code, diff --git a/iscsi-scst/kernel/target.c b/iscsi-scst/kernel/target.c index 7fb131860..702d9af10 100644 --- a/iscsi-scst/kernel/target.c +++ b/iscsi-scst/kernel/target.c @@ -503,38 +503,24 @@ out: return res; } -ssize_t iscsi_enable_target(struct scst_tgt *scst_tgt, const char *buf, - size_t size) +int iscsi_enable_target(struct scst_tgt *scst_tgt, bool enable) { struct iscsi_target *tgt = (struct iscsi_target *)scst_tgt_get_tgt_priv(scst_tgt); int res; - bool enable; uint32_t type; TRACE_ENTRY(); - switch (buf[0]) { - case '0': - type = E_DISABLE_TARGET; - enable = false; - break; - case '1': + if (enable) type = E_ENABLE_TARGET; - enable = true; - break; - default: - PRINT_ERROR("%s: Requested action not understood: %s", - __func__, buf); - res = -EINVAL; - goto out; - } + else + type = E_DISABLE_TARGET; TRACE_DBG("%s target %d", enable ? "Enabling" : "Disabling", tgt->tid); res = iscsi_sysfs_send_event(tgt->tid, type, NULL, NULL, NULL); -out: TRACE_EXIT_RES(res); return res; } diff --git a/qla2x00t/qla2x00-target/qla2x00t.c b/qla2x00t/qla2x00-target/qla2x00t.c index b083a92ee..297a3585e 100644 --- a/qla2x00t/qla2x00-target/qla2x00t.c +++ b/qla2x00t/qla2x00-target/qla2x00t.c @@ -119,15 +119,21 @@ struct kobj_attribute q2t_expl_conf_attr = __ATTR(explicit_confirmation, S_IRUGO|S_IWUSR, q2t_show_expl_conf_enabled, q2t_store_expl_conf_enabled); +static ssize_t q2t_abort_isp_store(struct kobject *kobj, + struct kobj_attribute *attr, const char *buffer, size_t size); + +struct kobj_attribute q2t_abort_isp_attr = + __ATTR(abort_isp, S_IWUSR, NULL, q2t_abort_isp_store); + static const struct attribute *q2t_tgt_attrs[] = { &q2t_expl_conf_attr.attr, + &q2t_abort_isp_attr.attr, NULL, }; #endif /* CONFIG_SCST_PROC */ -static ssize_t q2t_enable_tgt(struct scst_tgt *tgt, const char *buf, - size_t size); +static int q2t_enable_tgt(struct scst_tgt *tgt, bool enable); static bool q2t_is_tgt_enabled(struct scst_tgt *tgt); /* @@ -5175,36 +5181,17 @@ out: return res; } -static ssize_t q2t_enable_tgt(struct scst_tgt *scst_tgt, const char *buffer, - size_t size) +static int q2t_enable_tgt(struct scst_tgt *scst_tgt, bool enable) { struct q2t_tgt *tgt = (struct q2t_tgt *)scst_tgt_get_tgt_priv(scst_tgt); scsi_qla_host_t *ha = tgt->ha; - int res = 0; + int res; - switch (buffer[0]) { - case '0': - res = q2t_host_action(ha, DISABLE_TARGET_MODE); - break; - case '1': + if (enable) res = q2t_host_action(ha, ENABLE_TARGET_MODE); - break; - default: - PRINT_ERROR("%s: Requested action not understood: %s", - __func__, buffer); - res = -EINVAL; - goto out; - } + else + res = q2t_host_action(ha, DISABLE_TARGET_MODE); - if (res == 0) - res = size; - - if ((size > 1) && (buffer[1] == 'r')) { - set_bit(ISP_ABORT_NEEDED, &ha->dpc_flags); - qla2x00_wait_for_hba_online(ha); - } - -out: return res; } @@ -5273,6 +5260,25 @@ static ssize_t q2t_store_expl_conf_enabled(struct kobject *kobj, return size; } +static ssize_t q2t_abort_isp_store(struct kobject *kobj, + struct kobj_attribute *attr, const char *buffer, size_t size) +{ + struct scst_tgt *scst_tgt; + struct q2t_tgt *tgt; + scsi_qla_host_t *ha; + + scst_tgt = container_of(kobj, struct scst_tgt, tgt_kobj); + tgt = (struct q2t_tgt *)scst_tgt_get_tgt_priv(scst_tgt); + ha = tgt->ha; + + PRINT_INFO("qla2xxx(%ld): Aborting ISP", ha->instance); + + set_bit(ISP_ABORT_NEEDED, &ha->dpc_flags); + qla2x00_wait_for_hba_online(ha); + + return size; +} + static ssize_t q2t_version_show(struct kobject *kobj, struct kobj_attribute *attr, char *buf) { diff --git a/scst/include/scst.h b/scst/include/scst.h index 7be9118fe..4cb0b7855 100644 --- a/scst/include/scst.h +++ b/scst/include/scst.h @@ -820,8 +820,7 @@ struct scst_tgt_template { * case the too early connected initiators would see not those devices, * which they intended to see. */ - ssize_t (*enable_target) (struct scst_tgt *tgt, const char *buffer, - size_t size); + int (*enable_target) (struct scst_tgt *tgt, bool enable); /* * This function shows if particular target is enabled or not. diff --git a/scst/src/scst_sysfs.c b/scst/src/scst_sysfs.c index 105cfd5f1..9ed692b69 100644 --- a/scst/src/scst_sysfs.c +++ b/scst/src/scst_sysfs.c @@ -541,22 +541,30 @@ static ssize_t scst_tgt_enable_store(struct kobject *kobj, { int res; struct scst_tgt *tgt; + bool enable; TRACE_ENTRY(); - if (buf == NULL) - goto out_err; + if (buf == NULL) { + PRINT_ERROR("%s: NULL buffer?", __func__); + res = -EINVAL; + goto out; + } tgt = container_of(kobj, struct scst_tgt, tgt_kobj); - if (buf[0] == '1') { + switch (buf[0]) { + case '0': + enable = false; + break; + case '1': if (tgt->rel_tgt_id == 0) { res = gen_relative_target_port_id(&tgt->rel_tgt_id); if (res) goto out; PRINT_INFO("Using autogenerated rel ID %d for target " "%s", tgt->rel_tgt_id, tgt->tgt_name); - } else + } else { if (!scst_is_relative_target_port_id_unique( tgt->rel_tgt_id, tgt)) { PRINT_ERROR("Relative port id %d is not unique", @@ -564,20 +572,23 @@ static ssize_t scst_tgt_enable_store(struct kobject *kobj, res = -EBADSLT; goto out; } + } + enable = true; + break; + default: + PRINT_ERROR("%s: Requested action not understood: %s", + __func__, buf); + res = -EINVAL; + goto out; } - res = tgt->tgtt->enable_target(tgt, buf, count); + res = tgt->tgtt->enable_target(tgt, enable); if (res == 0) res = count; out: TRACE_EXIT_RES(res); return res; - -out_err: - PRINT_ERROR("%s: Requested action not understood: %s", __func__, buf); - res = -EINVAL; - goto out; } static struct kobj_attribute tgt_enable_attr =