Page Menu
Home
FreeBSD
Search
Configure Global Search
Log In
Files
F147291481
D12181.id32545.diff
No One
Temporary
Actions
View File
Edit File
Delete File
View Transforms
Subscribe
Mute Notifications
Flag For Later
Award Token
Size
8 KB
Referenced Files
None
Subscribers
None
D12181.id32545.diff
View Options
Index: sys/cam/ctl/ctl_frontend_iscsi.h
===================================================================
--- sys/cam/ctl/ctl_frontend_iscsi.h
+++ sys/cam/ctl/ctl_frontend_iscsi.h
@@ -47,6 +47,8 @@
int ct_online;
int ct_target_id;
struct ctl_port ct_port;
+ int ct_nb_conn;
+ int ct_max_conn;
};
struct cfiscsi_data_wait {
Index: sys/cam/ctl/ctl_frontend_iscsi.c
===================================================================
--- sys/cam/ctl/ctl_frontend_iscsi.c
+++ sys/cam/ctl/ctl_frontend_iscsi.c
@@ -98,6 +98,9 @@
static int maxtags = 256;
SYSCTL_INT(_kern_cam_ctl_iscsi, OID_AUTO, maxtags, CTLFLAG_RWTUN,
&maxtags, 0, "Max number of requests queued by initiator");
+static int maxconn = 512;
+SYSCTL_INT(_kern_cam_ctl_iscsi, OID_AUTO, maxconn, CTLFLAG_RWTUN,
+ &maxconn, 0, "Default max number of connections to a target");
#define CFISCSI_DEBUG(X, ...) \
do { \
@@ -1309,8 +1312,10 @@
("destroying session with non-empty queue"));
cfiscsi_session_unregister_initiator(cs);
- if (cs->cs_target != NULL)
+ if (cs->cs_target != NULL) {
+ cs->cs_target->ct_nb_conn--;
cfiscsi_target_release(cs->cs_target);
+ }
icl_conn_close(cs->cs_conn);
icl_conn_free(cs->cs_conn);
@@ -1565,6 +1570,7 @@
return;
}
cs->cs_target = ct;
+ ct->ct_nb_conn++;
mtx_unlock(&softc->lock);
refcount_acquire(&cs->cs_outstanding_ctl_pdus);
@@ -1816,6 +1822,32 @@
ci->status = CTL_ISCSI_OK;
}
+static void
+cfiscsi_ioctl_maxconn(struct ctl_iscsi *ci)
+{
+ struct cfiscsi_softc *softc;
+ struct ctl_iscsi_maxconn_params *cihp;
+ struct cfiscsi_target *ct;
+
+ cihp = (struct ctl_iscsi_maxconn_params *)&(ci->data);
+ softc = &cfiscsi_softc;
+
+ ct = cfiscsi_target_find(softc, cihp->target_name,
+ cihp->portal_group_tag);
+
+ if (ct == NULL) {
+ ci->status = CTL_ISCSI_ERROR;
+ snprintf(ci->error_str, sizeof(ci->error_str),
+ "%s: target not found", __func__);
+ return;
+ }
+
+ cihp->max_conn = ct->ct_max_conn;
+ cihp->nb_conn = ct->ct_nb_conn;
+
+ ci->status = CTL_ISCSI_OK;
+}
+
static void
cfiscsi_ioctl_limits(struct ctl_iscsi *ci)
{
@@ -2074,6 +2106,7 @@
struct scsi_vpd_id_descriptor *desc;
ctl_options_t opts;
int retval, len, idlen;
+ uint64_t max_conn;
uint16_t tag;
ctl_init_opts(&opts, req->num_args, req->kern_args);
@@ -2105,6 +2138,10 @@
ctl_free_opts(&opts);
return;
}
+ retval = ctl_get_opt_number(&opts, "cfiscsi_max_conn", &max_conn);
+ if (!retval) {
+ ct->ct_max_conn = max_conn;
+ }
port = &ct->ct_port;
// WAT
if (ct->ct_state == CFISCSI_TARGET_STATE_DYING)
@@ -2266,6 +2303,9 @@
case CTL_ISCSI_LIMITS:
cfiscsi_ioctl_limits(ci);
break;
+ case CTL_ISCSI_MAXCONN:
+ cfiscsi_ioctl_maxconn(ci);
+ break;
#ifdef ICL_KERNEL_PROXY
case CTL_ISCSI_LISTEN:
cfiscsi_ioctl_listen(ci);
@@ -2373,6 +2413,9 @@
return (ct);
}
+ newct->ct_nb_conn = 0;
+ newct->ct_max_conn = maxconn;
+
strlcpy(newct->ct_name, name, sizeof(newct->ct_name));
if (alias != NULL)
strlcpy(newct->ct_alias, alias, sizeof(newct->ct_alias));
Index: sys/cam/ctl/ctl_ioctl.h
===================================================================
--- sys/cam/ctl/ctl_ioctl.h
+++ sys/cam/ctl/ctl_ioctl.h
@@ -671,6 +671,7 @@
CTL_ISCSI_SEND,
CTL_ISCSI_RECEIVE,
#endif
+ CTL_ISCSI_MAXCONN,
} ctl_iscsi_type;
typedef enum {
@@ -747,6 +748,14 @@
int spare[4];
};
+struct ctl_iscsi_maxconn_params {
+ char target_name[CTL_ISCSI_NAME_LEN];
+ int portal_group_tag; /* passed to kernel */
+ int nb_conn; /* filled in kernel */
+ int max_conn; /* filled in kernel */
+ int spare[4];
+};
+
#ifdef ICL_KERNEL_PROXY
struct ctl_iscsi_listen_params {
int iser;
@@ -795,6 +804,7 @@
struct ctl_iscsi_logout_params logout;
struct ctl_iscsi_terminate_params terminate;
struct ctl_iscsi_limits_params limits;
+ struct ctl_iscsi_maxconn_params maxconn;
#ifdef ICL_KERNEL_PROXY
struct ctl_iscsi_listen_params listen;
struct ctl_iscsi_accept_params accept;
Index: usr.sbin/ctld/ctld.h
===================================================================
--- usr.sbin/ctld/ctld.h
+++ usr.sbin/ctld/ctld.h
@@ -187,6 +187,7 @@
char *t_name;
char *t_alias;
char *t_redirection;
+ char *t_max_conn;
};
struct isns {
@@ -403,6 +404,7 @@
int kernel_lun_modify(struct lun *lun);
int kernel_lun_remove(struct lun *lun);
void kernel_handoff(struct connection *conn);
+int kernel_maxconn(struct connection *conn);
void kernel_limits(const char *offload,
size_t *max_data_segment_length);
int kernel_port_add(struct port *port);
Index: usr.sbin/ctld/kernel.c
===================================================================
--- usr.sbin/ctld/kernel.c
+++ usr.sbin/ctld/kernel.c
@@ -922,6 +922,33 @@
}
}
+int
+kernel_maxconn(struct connection *conn)
+{
+ struct ctl_iscsi req;
+
+ bzero(&req, sizeof(req));
+
+ req.type = CTL_ISCSI_MAXCONN;
+ strlcpy(req.data.maxconn.target_name,
+ conn->conn_target->t_name, sizeof(req.data.maxconn.target_name));
+ req.data.maxconn.portal_group_tag =
+ conn->conn_portal->p_portal_group->pg_tag;
+
+ if (ioctl(ctl_fd, CTL_ISCSI, &req) == -1) {
+ log_err(1, "error issuing CTL_ISCSI ioctl; "
+ "dropping connection");
+ return (1);
+ }
+
+ if (req.status != CTL_ISCSI_OK) {
+ log_errx(1, "error returned from CTL iSCSI maxconn request: "
+ "%s; dropping connection", req.error_str);
+ return (1);
+ }
+ return !(req.data.maxconn.nb_conn < req.data.maxconn.max_conn);
+}
+
void
kernel_limits(const char *offload, size_t *max_data_segment_length)
{
@@ -972,7 +999,7 @@
bzero(&req, sizeof(req));
strlcpy(req.driver, "iscsi", sizeof(req.driver));
req.reqtype = CTL_REQ_CREATE;
- req.num_args = 5;
+ req.num_args = 6;
TAILQ_FOREACH(o, &pg->pg_options, o_next)
req.num_args++;
req.args = malloc(req.num_args * sizeof(*req.args));
@@ -989,6 +1016,8 @@
str_arg(&req.args[n++], "cfiscsi_portal_group_tag", tagstr);
if (targ->t_alias)
str_arg(&req.args[n++], "cfiscsi_target_alias", targ->t_alias);
+ if (targ->t_max_conn)
+ str_arg(&req.args[n++], "cfiscsi_max_conn", targ->t_max_conn);
str_arg(&req.args[n++], "ctld_portal_group_name", pg->pg_name);
TAILQ_FOREACH(o, &pg->pg_options, o_next)
str_arg(&req.args[n++], o->o_name, o->o_value);
Index: usr.sbin/ctld/login.c
===================================================================
--- usr.sbin/ctld/login.c
+++ usr.sbin/ctld/login.c
@@ -687,6 +687,11 @@
assert(conn->conn_target != NULL);
kernel_limits(conn->conn_portal->p_portal_group->pg_offload,
&conn->conn_data_segment_limit);
+ if (kernel_maxconn(conn) == true) {
+ login_send_error(request, 0x02, 0x00);
+ log_errx(1, "Max number of connections to target reached");
+ }
+
} else {
conn->conn_data_segment_limit = MAX_DATA_SEGMENT_LENGTH;
}
Index: usr.sbin/ctld/parse.y
===================================================================
--- usr.sbin/ctld/parse.y
+++ usr.sbin/ctld/parse.y
@@ -60,7 +60,7 @@
%token CLOSING_BRACKET CTL_LUN DEBUG DEVICE_ID DEVICE_TYPE
%token DISCOVERY_AUTH_GROUP DISCOVERY_FILTER FOREIGN
%token INITIATOR_NAME INITIATOR_PORTAL ISNS_SERVER ISNS_PERIOD ISNS_TIMEOUT
-%token LISTEN LISTEN_ISER LUN MAXPROC OFFLOAD OPENING_BRACKET OPTION
+%token LISTEN LISTEN_ISER LUN MAXCONN MAXPROC OFFLOAD OPENING_BRACKET OPTION
%token PATH PIDFILE PORT PORTAL_GROUP REDIRECT SEMICOLON SERIAL SIZE STR
%token TAG TARGET TIMEOUT
@@ -524,6 +524,8 @@
target_lun
|
target_lun_ref
+ |
+ target_max_conn
;
target_alias: ALIAS STR
@@ -803,6 +805,17 @@
}
;
+target_max_conn: MAXCONN STR
+ {
+ if (target->t_max_conn != NULL) {
+ log_warnx("max_conn for target \"%s\" "
+ "specified more than once", target->t_name);
+ return (1);
+ }
+ target->t_max_conn = $2;
+ }
+ ;
+
target_lun: LUN lun_number
OPENING_BRACKET lun_entries CLOSING_BRACKET
{
Index: usr.sbin/ctld/token.l
===================================================================
--- usr.sbin/ctld/token.l
+++ usr.sbin/ctld/token.l
@@ -67,6 +67,7 @@
listen-iser { return LISTEN_ISER; }
lun { return LUN; }
maxproc { return MAXPROC; }
+max_conn { return MAXCONN; }
offload { return OFFLOAD; }
option { return OPTION; }
path { return PATH; }
Index: usr.sbin/ctld/uclparse.c
===================================================================
--- usr.sbin/ctld/uclparse.c
+++ usr.sbin/ctld/uclparse.c
@@ -775,6 +775,16 @@
}
}
+ if (!strcmp(key, "max_conn")) {
+ if (obj->type != UCL_STRING) {
+ log_warnx("\"max_conn\" property of target "
+ "\"%s\" is not a string", target->t_name);
+ return (1);
+ }
+
+ target->t_max_conn = strdup(ucl_object_tostring(obj));
+ }
+
if (!strcmp(key, "redirect")) {
if (obj->type != UCL_STRING) {
log_warnx("\"redirect\" property of target "
File Metadata
Details
Attached
Mime Type
text/plain
Expires
Tue, Mar 10, 5:57 PM (9 h, 41 m)
Storage Engine
blob
Storage Format
Raw Data
Storage Handle
29504248
Default Alt Text
D12181.id32545.diff (8 KB)
Attached To
Mode
D12181: [RFC] limit the max number of iscsi connections to a specific target
Attached
Detach File
Event Timeline
Log In to Comment