Donate to e Foundation | Murena handsets with /e/OS | Own a part of Murena! Learn more

Commit f46d6a8a authored by Nicholas Bellinger's avatar Nicholas Bellinger
Browse files

iser-target: Match FRMR descriptors to available session tags



This patch changes isert_conn_create_fastreg_pool() to follow
logic in iscsi_target_locate_portal() for determining how many
FRMR descriptors to allocate based upon the number of possible
per-session command slots that are available.

This addresses an OOPs in isert_reg_rdma() where due to the
use of ISCSI_DEF_XMIT_CMDS_MAX could end up returning a bogus
fast_reg_descriptor when the number of active tags exceeded
the original hardcoded max.

Note this also includes moving isert_conn_create_fastreg_pool()
from isert_connect_request() to isert_put_login_tx() before
posting the final Login Response PDU in order to determine the
se_nacl->queue_depth (eg: number of tags) per session the target
will be enforcing.

v2 changes:
  - Move isert_conn->conn_fr_pool list_head init into
    isert_conn_request()
v3 changes:
  - Drop unnecessary list_empty() check in isert_reg_rdma()
    (Sagi)

Cc: Sagi Grimberg <sagig@mellanox.com>
Cc: Or Gerlitz <ogerlitz@mellanox.com>
Cc: <stable@vger.kernel.org> #3.12+
Signed-off-by: default avatarNicholas Bellinger <nab@linux-iscsi.org>
parent 5bac4b1a
Loading
Loading
Loading
Loading
+23 −15
Original line number Diff line number Diff line
@@ -508,11 +508,18 @@ isert_conn_create_fastreg_pool(struct isert_conn *isert_conn, u8 pi_support)
{
	struct fast_reg_descriptor *fr_desc;
	struct isert_device *device = isert_conn->conn_device;
	int i, ret;
	struct se_session *se_sess = isert_conn->conn->sess->se_sess;
	struct se_node_acl *se_nacl = se_sess->se_node_acl;
	int i, ret, tag_num;
	/*
	 * Setup the number of FRMRs based upon the number of tags
	 * available to session in iscsi_target_locate_portal().
	 */
	tag_num = max_t(u32, ISCSIT_MIN_TAGS, se_nacl->queue_depth);
	tag_num = (tag_num * 2) + ISCSIT_EXTRA_TAGS;

	INIT_LIST_HEAD(&isert_conn->conn_fr_pool);
	isert_conn->conn_fr_pool_size = 0;
	for (i = 0; i < ISCSI_DEF_XMIT_CMDS_MAX; i++) {
	for (i = 0; i < tag_num; i++) {
		fr_desc = kzalloc(sizeof(*fr_desc), GFP_KERNEL);
		if (!fr_desc) {
			pr_err("Failed to allocate fast_reg descriptor\n");
@@ -572,6 +579,7 @@ isert_connect_request(struct rdma_cm_id *cma_id, struct rdma_cm_event *event)
	kref_get(&isert_conn->conn_kref);
	mutex_init(&isert_conn->conn_mutex);
	spin_lock_init(&isert_conn->conn_lock);
	INIT_LIST_HEAD(&isert_conn->conn_fr_pool);

	cma_id->context = isert_conn;
	isert_conn->conn_cm_id = cma_id;
@@ -649,15 +657,6 @@ isert_connect_request(struct rdma_cm_id *cma_id, struct rdma_cm_event *event)
		goto out_mr;
	}

	if (device->use_fastreg) {
		ret = isert_conn_create_fastreg_pool(isert_conn, pi_support);
		if (ret) {
			pr_err("Conn: %p failed to create fastreg pool\n",
			       isert_conn);
			goto out_fastreg;
		}
	}

	ret = isert_conn_setup_qp(isert_conn, cma_id, pi_support);
	if (ret)
		goto out_conn_dev;
@@ -671,9 +670,6 @@ isert_connect_request(struct rdma_cm_id *cma_id, struct rdma_cm_event *event)
	return 0;

out_conn_dev:
	if (device->use_fastreg)
		isert_conn_free_fastreg_pool(isert_conn);
out_fastreg:
	ib_dereg_mr(isert_conn->conn_mr);
out_mr:
	ib_dealloc_pd(isert_conn->conn_pd);
@@ -1047,6 +1043,18 @@ isert_put_login_tx(struct iscsi_conn *conn, struct iscsi_login *login,
	}
	if (!login->login_failed) {
		if (login->login_complete) {
			if (isert_conn->conn_device->use_fastreg) {
				u8 pi_support = login->np->tpg_np->tpg->tpg_attrib.t10_pi;

				ret = isert_conn_create_fastreg_pool(isert_conn,
								     pi_support);
				if (ret) {
					pr_err("Conn: %p failed to create"
					       " fastreg pool\n", isert_conn);
					return ret;
				}
			}

			ret = isert_alloc_rx_descriptors(isert_conn);
			if (ret)
				return ret;