Commit 4ea19788 authored by Shuhei Matsumoto's avatar Shuhei Matsumoto Committed by Tomasz Zawadzki
Browse files

lib/iscsi: Add iscsi_target_node_set_redirect RPC



Signed-off-by: default avatarShuhei Matsumoto <shuhei.matsumoto.xt@hitachi.com>
Change-Id: I090f55debe4ecdc47459bcfe0571a937f064313b
Reviewed-on: https://review.spdk.io/gerrit/c/spdk/spdk/+/3439


Community-CI: Mellanox Build Bot
Reviewed-by: default avatarJim Harris <james.r.harris@intel.com>
Reviewed-by: default avatarChangpeng Liu <changpeng.liu@intel.com>
Tested-by: default avatarSPDK CI Jenkins <sys_sgci@intel.com>
parent 420b2353
Loading
Loading
Loading
Loading
+45 −0
Original line number Diff line number Diff line
@@ -4098,6 +4098,51 @@ Example response:
}
~~~

## iscsi_target_node_set_redirect method {#rpc_iscsi_target_node_set_redirect}

Update redirect portal of the primary portal group for the target node,
and send asynchronous logout request to all corresponding initiators.

### Parameters

Name                        | Optional | Type    | Description
--------------------------- | -------- | --------| -----------
name                        | Required | string  | Target node name (ASCII)
pg_tag                      | Required | number  | Existing portal group tag
redirect_host               | Optional | string  | Numeric IP address to which the target node is redirected
redirect_port               | Optional | string  | Numeric TCP port to which the target node is redirected

If both redirect_host and redirect_port are omitted, clear the redirect portal.

### Example

Example request:

~~~
{
  "params": {
    "name": "iqn.2016-06.io.spdk:target1",
    "pg_tag": 1,
    "redirect_host": "10.0.0.3",
    "redirect_port": "3260"
  },
  "jsonrpc": "2.0",
  "method": "iscsi_target_node_set_redirect",
  "id": 1
}
~~~

Example response:

~~~
{
  "jsonrpc": "2.0",
  "id": 1,
  "result": true
}
~~~


# NVMe-oF Target {#jsonrpc_components_nvmf_tgt}

## nvmf_create_transport method {#rpc_nvmf_create_transport}
+69 −0
Original line number Diff line number Diff line
@@ -1149,6 +1149,75 @@ SPDK_RPC_REGISTER("iscsi_target_node_set_auth", rpc_iscsi_target_node_set_auth,
		  SPDK_RPC_RUNTIME)
SPDK_RPC_REGISTER_ALIAS_DEPRECATED(iscsi_target_node_set_auth, set_iscsi_target_node_auth)

struct rpc_target_redirect {
	char *name;
	int32_t pg_tag;
	char *redirect_host;
	char *redirect_port;
};

static void
free_rpc_target_redirect(struct rpc_target_redirect *req)
{
	free(req->name);
	free(req->redirect_host);
	free(req->redirect_port);
}

static const struct spdk_json_object_decoder rpc_target_redirect_decoders[] = {
	{"name", offsetof(struct rpc_target_redirect, name), spdk_json_decode_string},
	{"pg_tag", offsetof(struct rpc_target_redirect, pg_tag), spdk_json_decode_int32},
	{"redirect_host", offsetof(struct rpc_target_redirect, redirect_host), spdk_json_decode_string, true},
	{"redirect_port", offsetof(struct rpc_target_redirect, redirect_port), spdk_json_decode_string, true},
};

static void
rpc_iscsi_target_node_set_redirect(struct spdk_jsonrpc_request *request,
				   const struct spdk_json_val *params)
{
	struct rpc_target_redirect req = {};
	struct spdk_iscsi_tgt_node *target;
	struct spdk_json_write_ctx *w;
	int rc;

	if (spdk_json_decode_object(params, rpc_target_redirect_decoders,
				    SPDK_COUNTOF(rpc_target_redirect_decoders),
				    &req)) {
		SPDK_ERRLOG("spdk_json_decode_object failed\n");
		spdk_jsonrpc_send_error_response(request, SPDK_JSONRPC_ERROR_INVALID_PARAMS,
						 "Invalid parameters");
		free_rpc_target_redirect(&req);
		return;
	}

	target = iscsi_find_tgt_node(req.name);
	if (target == NULL) {
		SPDK_ERRLOG("target %s is not found\n", req.name);
		spdk_jsonrpc_send_error_response_fmt(request, SPDK_JSONRPC_ERROR_INVALID_PARAMS,
						     "Target %s is not found", req.name);
		free_rpc_target_redirect(&req);
		return;
	}

	rc = iscsi_tgt_node_redirect(target, req.pg_tag, req.redirect_host, req.redirect_port);
	if (rc != 0) {
		SPDK_ERRLOG("failed to redirect target %s\n", req.name);
		spdk_jsonrpc_send_error_response_fmt(request, SPDK_JSONRPC_ERROR_INVALID_PARAMS,
						     "Failed to redirect target %s, (%d): %s",
						     req.name, rc, spdk_strerror(-rc));
		free_rpc_target_redirect(&req);
		return;
	}

	free_rpc_target_redirect(&req);

	w = spdk_jsonrpc_begin_result(request);
	spdk_json_write_bool(w, true);
	spdk_jsonrpc_end_result(request, w);
}
SPDK_RPC_REGISTER("iscsi_target_node_set_redirect", rpc_iscsi_target_node_set_redirect,
		  SPDK_RPC_RUNTIME)

static void
rpc_iscsi_get_options(struct spdk_jsonrpc_request *request,
		      const struct spdk_json_val *params)
+18 −0
Original line number Diff line number Diff line
@@ -1087,6 +1087,24 @@ Format: 'user:u1 secret:s1 muser:mu1 msecret:ms1,user:u2 secret:s2 muser:mu2 mse
    *** The Portal/Initiator Groups must be precreated ***""")
    p.set_defaults(func=iscsi_target_node_remove_pg_ig_maps)

    def iscsi_target_node_set_redirect(args):
        rpc.iscsi.iscsi_target_node_set_redirect(
            args.client,
            name=args.name,
            pg_tag=args.pg_tag,
            redirect_host=args.redirect_host,
            redirect_port=args.redirect_port)

    p = subparsers.add_parser('iscsi_target_node_set_redirect',
                              help="""Update redirect portal of the public portal group for
    the target node, and send asynchronous logout request to all corresponding initiators.
    Omit redirect host and port to clear previously set redirect settings.""")
    p.add_argument('name', help='Target node name (ASCII)')
    p.add_argument('pg_tag', help='Portal group tag (unique, integer > 0)', type=int)
    p.add_argument('-a', '--redirect_host', help='Numeric IP address for redirect portal', required=False)
    p.add_argument('-p', '--redirect_port', help='Numeric TCP port for redirect portal', required=False)
    p.set_defaults(func=iscsi_target_node_set_redirect)

    def iscsi_create_portal_group(args):
        portals = []
        for p in args.portal_list.strip().split(' '):
+25 −0
Original line number Diff line number Diff line
@@ -374,6 +374,31 @@ def iscsi_target_node_add_pg_ig_maps(client, pg_ig_maps, name):
    return client.call('iscsi_target_node_add_pg_ig_maps', params)


def iscsi_target_node_set_redirect(client, name, pg_tag, redirect_host, redirect_port):
    """Update redirect portal of the public portal group for the target node,
       and send asynchronous logout request to all corresponding initiators.

    Args:
        name: Target node name (ASCII)
        pg_tag: Portal group tag (unique, integer > 0)
        redirect_host: Numeric IP address to which the target node is redirected
        redirect_port: Numeric TCP port to which the target node is redirected

    Returns:
        True or False
    """
    params = {
        'name': name,
        'pg_tag': pg_tag
    }

    if redirect_host:
        params['redirect_host'] = redirect_host
    if redirect_port:
        params['redirect_port'] = redirect_port
    return client.call('iscsi_target_node_set_redirect', params)


@deprecated_alias('add_portal_group')
def iscsi_create_portal_group(client, portals, tag, private):
    """Add a portal group.