1e48354ceSNicholas Bellinger /*******************************************************************************
2e48354ceSNicholas Bellinger  * Modern ConfigFS group context specific iSCSI statistics based on original
3e48354ceSNicholas Bellinger  * iscsi_target_mib.c code
4e48354ceSNicholas Bellinger  *
5e48354ceSNicholas Bellinger  * Copyright (c) 2011 Rising Tide Systems
6e48354ceSNicholas Bellinger  *
7e48354ceSNicholas Bellinger  * Licensed to the Linux Foundation under the General Public License (GPL) version 2.
8e48354ceSNicholas Bellinger  *
9e48354ceSNicholas Bellinger  * Author: Nicholas A. Bellinger <nab@linux-iscsi.org>
10e48354ceSNicholas Bellinger  *
11e48354ceSNicholas Bellinger  * This program is free software; you can redistribute it and/or modify
12e48354ceSNicholas Bellinger  * it under the terms of the GNU General Public License as published by
13e48354ceSNicholas Bellinger  * the Free Software Foundation; either version 2 of the License, or
14e48354ceSNicholas Bellinger  * (at your option) any later version.
15e48354ceSNicholas Bellinger  *
16e48354ceSNicholas Bellinger  * This program is distributed in the hope that it will be useful,
17e48354ceSNicholas Bellinger  * but WITHOUT ANY WARRANTY; without even the implied warranty of
18e48354ceSNicholas Bellinger  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
19e48354ceSNicholas Bellinger  * GNU General Public License for more details.
20e48354ceSNicholas Bellinger  ******************************************************************************/
21e48354ceSNicholas Bellinger 
22e48354ceSNicholas Bellinger #include <linux/configfs.h>
23c53181afSPaul Gortmaker #include <linux/export.h>
24e48354ceSNicholas Bellinger #include <scsi/iscsi_proto.h>
25e48354ceSNicholas Bellinger #include <target/target_core_base.h>
26e48354ceSNicholas Bellinger #include <target/target_core_transport.h>
27e48354ceSNicholas Bellinger #include <target/configfs_macros.h>
28e48354ceSNicholas Bellinger 
29e48354ceSNicholas Bellinger #include "iscsi_target_core.h"
30e48354ceSNicholas Bellinger #include "iscsi_target_parameters.h"
31e48354ceSNicholas Bellinger #include "iscsi_target_device.h"
32e48354ceSNicholas Bellinger #include "iscsi_target_tpg.h"
33e48354ceSNicholas Bellinger #include "iscsi_target_util.h"
34e48354ceSNicholas Bellinger #include "iscsi_target_stat.h"
35e48354ceSNicholas Bellinger 
36e48354ceSNicholas Bellinger #ifndef INITIAL_JIFFIES
37e48354ceSNicholas Bellinger #define INITIAL_JIFFIES ((unsigned long)(unsigned int) (-300*HZ))
38e48354ceSNicholas Bellinger #endif
39e48354ceSNicholas Bellinger 
40e48354ceSNicholas Bellinger /* Instance Attributes Table */
41e48354ceSNicholas Bellinger #define ISCSI_INST_NUM_NODES		1
42e48354ceSNicholas Bellinger #define ISCSI_INST_DESCR		"Storage Engine Target"
43e48354ceSNicholas Bellinger #define ISCSI_INST_LAST_FAILURE_TYPE	0
44e48354ceSNicholas Bellinger #define ISCSI_DISCONTINUITY_TIME	0
45e48354ceSNicholas Bellinger 
46e48354ceSNicholas Bellinger #define ISCSI_NODE_INDEX		1
47e48354ceSNicholas Bellinger 
48e48354ceSNicholas Bellinger #define ISPRINT(a)   ((a >= ' ') && (a <= '~'))
49e48354ceSNicholas Bellinger 
50e48354ceSNicholas Bellinger /****************************************************************************
51e48354ceSNicholas Bellinger  * iSCSI MIB Tables
52e48354ceSNicholas Bellinger  ****************************************************************************/
53e48354ceSNicholas Bellinger /*
54e48354ceSNicholas Bellinger  * Instance Attributes Table
55e48354ceSNicholas Bellinger  */
56e48354ceSNicholas Bellinger CONFIGFS_EATTR_STRUCT(iscsi_stat_instance, iscsi_wwn_stat_grps);
57e48354ceSNicholas Bellinger #define ISCSI_STAT_INSTANCE_ATTR(_name, _mode)			\
58e48354ceSNicholas Bellinger static struct iscsi_stat_instance_attribute			\
59e48354ceSNicholas Bellinger 			iscsi_stat_instance_##_name =		\
60e48354ceSNicholas Bellinger 	__CONFIGFS_EATTR(_name, _mode,				\
61e48354ceSNicholas Bellinger 	iscsi_stat_instance_show_attr_##_name,			\
62e48354ceSNicholas Bellinger 	iscsi_stat_instance_store_attr_##_name);
63e48354ceSNicholas Bellinger 
64e48354ceSNicholas Bellinger #define ISCSI_STAT_INSTANCE_ATTR_RO(_name)			\
65e48354ceSNicholas Bellinger static struct iscsi_stat_instance_attribute			\
66e48354ceSNicholas Bellinger 			iscsi_stat_instance_##_name =		\
67e48354ceSNicholas Bellinger 	__CONFIGFS_EATTR_RO(_name,				\
68e48354ceSNicholas Bellinger 	iscsi_stat_instance_show_attr_##_name);
69e48354ceSNicholas Bellinger 
70e48354ceSNicholas Bellinger static ssize_t iscsi_stat_instance_show_attr_inst(
71e48354ceSNicholas Bellinger 	struct iscsi_wwn_stat_grps *igrps, char *page)
72e48354ceSNicholas Bellinger {
73e48354ceSNicholas Bellinger 	struct iscsi_tiqn *tiqn = container_of(igrps,
74e48354ceSNicholas Bellinger 				struct iscsi_tiqn, tiqn_stat_grps);
75e48354ceSNicholas Bellinger 
76e48354ceSNicholas Bellinger 	return snprintf(page, PAGE_SIZE, "%u\n", tiqn->tiqn_index);
77e48354ceSNicholas Bellinger }
78e48354ceSNicholas Bellinger ISCSI_STAT_INSTANCE_ATTR_RO(inst);
79e48354ceSNicholas Bellinger 
80e48354ceSNicholas Bellinger static ssize_t iscsi_stat_instance_show_attr_min_ver(
81e48354ceSNicholas Bellinger 	struct iscsi_wwn_stat_grps *igrps, char *page)
82e48354ceSNicholas Bellinger {
83e48354ceSNicholas Bellinger 	return snprintf(page, PAGE_SIZE, "%u\n", ISCSI_DRAFT20_VERSION);
84e48354ceSNicholas Bellinger }
85e48354ceSNicholas Bellinger ISCSI_STAT_INSTANCE_ATTR_RO(min_ver);
86e48354ceSNicholas Bellinger 
87e48354ceSNicholas Bellinger static ssize_t iscsi_stat_instance_show_attr_max_ver(
88e48354ceSNicholas Bellinger 	struct iscsi_wwn_stat_grps *igrps, char *page)
89e48354ceSNicholas Bellinger {
90e48354ceSNicholas Bellinger 	return snprintf(page, PAGE_SIZE, "%u\n", ISCSI_DRAFT20_VERSION);
91e48354ceSNicholas Bellinger }
92e48354ceSNicholas Bellinger ISCSI_STAT_INSTANCE_ATTR_RO(max_ver);
93e48354ceSNicholas Bellinger 
94e48354ceSNicholas Bellinger static ssize_t iscsi_stat_instance_show_attr_portals(
95e48354ceSNicholas Bellinger 	struct iscsi_wwn_stat_grps *igrps, char *page)
96e48354ceSNicholas Bellinger {
97e48354ceSNicholas Bellinger 	struct iscsi_tiqn *tiqn = container_of(igrps,
98e48354ceSNicholas Bellinger 				struct iscsi_tiqn, tiqn_stat_grps);
99e48354ceSNicholas Bellinger 
100e48354ceSNicholas Bellinger 	return snprintf(page, PAGE_SIZE, "%u\n", tiqn->tiqn_num_tpg_nps);
101e48354ceSNicholas Bellinger }
102e48354ceSNicholas Bellinger ISCSI_STAT_INSTANCE_ATTR_RO(portals);
103e48354ceSNicholas Bellinger 
104e48354ceSNicholas Bellinger static ssize_t iscsi_stat_instance_show_attr_nodes(
105e48354ceSNicholas Bellinger 	struct iscsi_wwn_stat_grps *igrps, char *page)
106e48354ceSNicholas Bellinger {
107e48354ceSNicholas Bellinger 	return snprintf(page, PAGE_SIZE, "%u\n", ISCSI_INST_NUM_NODES);
108e48354ceSNicholas Bellinger }
109e48354ceSNicholas Bellinger ISCSI_STAT_INSTANCE_ATTR_RO(nodes);
110e48354ceSNicholas Bellinger 
111e48354ceSNicholas Bellinger static ssize_t iscsi_stat_instance_show_attr_sessions(
112e48354ceSNicholas Bellinger 	struct iscsi_wwn_stat_grps *igrps, char *page)
113e48354ceSNicholas Bellinger {
114e48354ceSNicholas Bellinger 	struct iscsi_tiqn *tiqn = container_of(igrps,
115e48354ceSNicholas Bellinger 				struct iscsi_tiqn, tiqn_stat_grps);
116e48354ceSNicholas Bellinger 
117e48354ceSNicholas Bellinger 	return snprintf(page, PAGE_SIZE, "%u\n", tiqn->tiqn_nsessions);
118e48354ceSNicholas Bellinger }
119e48354ceSNicholas Bellinger ISCSI_STAT_INSTANCE_ATTR_RO(sessions);
120e48354ceSNicholas Bellinger 
121e48354ceSNicholas Bellinger static ssize_t iscsi_stat_instance_show_attr_fail_sess(
122e48354ceSNicholas Bellinger 	struct iscsi_wwn_stat_grps *igrps, char *page)
123e48354ceSNicholas Bellinger {
124e48354ceSNicholas Bellinger 	struct iscsi_tiqn *tiqn = container_of(igrps,
125e48354ceSNicholas Bellinger 				struct iscsi_tiqn, tiqn_stat_grps);
126e48354ceSNicholas Bellinger 	struct iscsi_sess_err_stats *sess_err = &tiqn->sess_err_stats;
127e48354ceSNicholas Bellinger 	u32 sess_err_count;
128e48354ceSNicholas Bellinger 
129e48354ceSNicholas Bellinger 	spin_lock_bh(&sess_err->lock);
130e48354ceSNicholas Bellinger 	sess_err_count = (sess_err->digest_errors +
131e48354ceSNicholas Bellinger 			  sess_err->cxn_timeout_errors +
132e48354ceSNicholas Bellinger 			  sess_err->pdu_format_errors);
133e48354ceSNicholas Bellinger 	spin_unlock_bh(&sess_err->lock);
134e48354ceSNicholas Bellinger 
135e48354ceSNicholas Bellinger 	return snprintf(page, PAGE_SIZE, "%u\n", sess_err_count);
136e48354ceSNicholas Bellinger }
137e48354ceSNicholas Bellinger ISCSI_STAT_INSTANCE_ATTR_RO(fail_sess);
138e48354ceSNicholas Bellinger 
139e48354ceSNicholas Bellinger static ssize_t iscsi_stat_instance_show_attr_fail_type(
140e48354ceSNicholas Bellinger 	struct iscsi_wwn_stat_grps *igrps, char *page)
141e48354ceSNicholas Bellinger {
142e48354ceSNicholas Bellinger 	struct iscsi_tiqn *tiqn = container_of(igrps,
143e48354ceSNicholas Bellinger 				struct iscsi_tiqn, tiqn_stat_grps);
144e48354ceSNicholas Bellinger 	struct iscsi_sess_err_stats *sess_err = &tiqn->sess_err_stats;
145e48354ceSNicholas Bellinger 
146e48354ceSNicholas Bellinger 	return snprintf(page, PAGE_SIZE, "%u\n",
147e48354ceSNicholas Bellinger 			sess_err->last_sess_failure_type);
148e48354ceSNicholas Bellinger }
149e48354ceSNicholas Bellinger ISCSI_STAT_INSTANCE_ATTR_RO(fail_type);
150e48354ceSNicholas Bellinger 
151e48354ceSNicholas Bellinger static ssize_t iscsi_stat_instance_show_attr_fail_rem_name(
152e48354ceSNicholas Bellinger 	struct iscsi_wwn_stat_grps *igrps, char *page)
153e48354ceSNicholas Bellinger {
154e48354ceSNicholas Bellinger 	struct iscsi_tiqn *tiqn = container_of(igrps,
155e48354ceSNicholas Bellinger 				struct iscsi_tiqn, tiqn_stat_grps);
156e48354ceSNicholas Bellinger 	struct iscsi_sess_err_stats *sess_err = &tiqn->sess_err_stats;
157e48354ceSNicholas Bellinger 
158e48354ceSNicholas Bellinger 	return snprintf(page, PAGE_SIZE, "%s\n",
159e48354ceSNicholas Bellinger 			sess_err->last_sess_fail_rem_name[0] ?
160e48354ceSNicholas Bellinger 			sess_err->last_sess_fail_rem_name : NONE);
161e48354ceSNicholas Bellinger }
162e48354ceSNicholas Bellinger ISCSI_STAT_INSTANCE_ATTR_RO(fail_rem_name);
163e48354ceSNicholas Bellinger 
164e48354ceSNicholas Bellinger static ssize_t iscsi_stat_instance_show_attr_disc_time(
165e48354ceSNicholas Bellinger 	struct iscsi_wwn_stat_grps *igrps, char *page)
166e48354ceSNicholas Bellinger {
167e48354ceSNicholas Bellinger 	return snprintf(page, PAGE_SIZE, "%u\n", ISCSI_DISCONTINUITY_TIME);
168e48354ceSNicholas Bellinger }
169e48354ceSNicholas Bellinger ISCSI_STAT_INSTANCE_ATTR_RO(disc_time);
170e48354ceSNicholas Bellinger 
171e48354ceSNicholas Bellinger static ssize_t iscsi_stat_instance_show_attr_description(
172e48354ceSNicholas Bellinger 	struct iscsi_wwn_stat_grps *igrps, char *page)
173e48354ceSNicholas Bellinger {
174e48354ceSNicholas Bellinger 	return snprintf(page, PAGE_SIZE, "%s\n", ISCSI_INST_DESCR);
175e48354ceSNicholas Bellinger }
176e48354ceSNicholas Bellinger ISCSI_STAT_INSTANCE_ATTR_RO(description);
177e48354ceSNicholas Bellinger 
178e48354ceSNicholas Bellinger static ssize_t iscsi_stat_instance_show_attr_vendor(
179e48354ceSNicholas Bellinger 	struct iscsi_wwn_stat_grps *igrps, char *page)
180e48354ceSNicholas Bellinger {
181e48354ceSNicholas Bellinger 	return snprintf(page, PAGE_SIZE, "RisingTide Systems iSCSI-Target\n");
182e48354ceSNicholas Bellinger }
183e48354ceSNicholas Bellinger ISCSI_STAT_INSTANCE_ATTR_RO(vendor);
184e48354ceSNicholas Bellinger 
185e48354ceSNicholas Bellinger static ssize_t iscsi_stat_instance_show_attr_version(
186e48354ceSNicholas Bellinger 	struct iscsi_wwn_stat_grps *igrps, char *page)
187e48354ceSNicholas Bellinger {
188e48354ceSNicholas Bellinger 	return snprintf(page, PAGE_SIZE, "%s\n", ISCSIT_VERSION);
189e48354ceSNicholas Bellinger }
190e48354ceSNicholas Bellinger ISCSI_STAT_INSTANCE_ATTR_RO(version);
191e48354ceSNicholas Bellinger 
192e48354ceSNicholas Bellinger CONFIGFS_EATTR_OPS(iscsi_stat_instance, iscsi_wwn_stat_grps,
193e48354ceSNicholas Bellinger 		iscsi_instance_group);
194e48354ceSNicholas Bellinger 
195e48354ceSNicholas Bellinger static struct configfs_attribute *iscsi_stat_instance_attrs[] = {
196e48354ceSNicholas Bellinger 	&iscsi_stat_instance_inst.attr,
197e48354ceSNicholas Bellinger 	&iscsi_stat_instance_min_ver.attr,
198e48354ceSNicholas Bellinger 	&iscsi_stat_instance_max_ver.attr,
199e48354ceSNicholas Bellinger 	&iscsi_stat_instance_portals.attr,
200e48354ceSNicholas Bellinger 	&iscsi_stat_instance_nodes.attr,
201e48354ceSNicholas Bellinger 	&iscsi_stat_instance_sessions.attr,
202e48354ceSNicholas Bellinger 	&iscsi_stat_instance_fail_sess.attr,
203e48354ceSNicholas Bellinger 	&iscsi_stat_instance_fail_type.attr,
204e48354ceSNicholas Bellinger 	&iscsi_stat_instance_fail_rem_name.attr,
205e48354ceSNicholas Bellinger 	&iscsi_stat_instance_disc_time.attr,
206e48354ceSNicholas Bellinger 	&iscsi_stat_instance_description.attr,
207e48354ceSNicholas Bellinger 	&iscsi_stat_instance_vendor.attr,
208e48354ceSNicholas Bellinger 	&iscsi_stat_instance_version.attr,
209e48354ceSNicholas Bellinger 	NULL,
210e48354ceSNicholas Bellinger };
211e48354ceSNicholas Bellinger 
212e48354ceSNicholas Bellinger static struct configfs_item_operations iscsi_stat_instance_item_ops = {
213e48354ceSNicholas Bellinger 	.show_attribute		= iscsi_stat_instance_attr_show,
214e48354ceSNicholas Bellinger 	.store_attribute	= iscsi_stat_instance_attr_store,
215e48354ceSNicholas Bellinger };
216e48354ceSNicholas Bellinger 
217e48354ceSNicholas Bellinger struct config_item_type iscsi_stat_instance_cit = {
218e48354ceSNicholas Bellinger 	.ct_item_ops		= &iscsi_stat_instance_item_ops,
219e48354ceSNicholas Bellinger 	.ct_attrs		= iscsi_stat_instance_attrs,
220e48354ceSNicholas Bellinger 	.ct_owner		= THIS_MODULE,
221e48354ceSNicholas Bellinger };
222e48354ceSNicholas Bellinger 
223e48354ceSNicholas Bellinger /*
224e48354ceSNicholas Bellinger  * Instance Session Failure Stats Table
225e48354ceSNicholas Bellinger  */
226e48354ceSNicholas Bellinger CONFIGFS_EATTR_STRUCT(iscsi_stat_sess_err, iscsi_wwn_stat_grps);
227e48354ceSNicholas Bellinger #define ISCSI_STAT_SESS_ERR_ATTR(_name, _mode)			\
228e48354ceSNicholas Bellinger static struct iscsi_stat_sess_err_attribute			\
229e48354ceSNicholas Bellinger 			iscsi_stat_sess_err_##_name =		\
230e48354ceSNicholas Bellinger 	__CONFIGFS_EATTR(_name, _mode,				\
231e48354ceSNicholas Bellinger 	iscsi_stat_sess_err_show_attr_##_name,			\
232e48354ceSNicholas Bellinger 	iscsi_stat_sess_err_store_attr_##_name);
233e48354ceSNicholas Bellinger 
234e48354ceSNicholas Bellinger #define ISCSI_STAT_SESS_ERR_ATTR_RO(_name)			\
235e48354ceSNicholas Bellinger static struct iscsi_stat_sess_err_attribute			\
236e48354ceSNicholas Bellinger 			iscsi_stat_sess_err_##_name =		\
237e48354ceSNicholas Bellinger 	__CONFIGFS_EATTR_RO(_name,				\
238e48354ceSNicholas Bellinger 	iscsi_stat_sess_err_show_attr_##_name);
239e48354ceSNicholas Bellinger 
240e48354ceSNicholas Bellinger static ssize_t iscsi_stat_sess_err_show_attr_inst(
241e48354ceSNicholas Bellinger 	struct iscsi_wwn_stat_grps *igrps, char *page)
242e48354ceSNicholas Bellinger {
243e48354ceSNicholas Bellinger 	struct iscsi_tiqn *tiqn = container_of(igrps,
244e48354ceSNicholas Bellinger 				struct iscsi_tiqn, tiqn_stat_grps);
245e48354ceSNicholas Bellinger 
246e48354ceSNicholas Bellinger 	return snprintf(page, PAGE_SIZE, "%u\n", tiqn->tiqn_index);
247e48354ceSNicholas Bellinger }
248e48354ceSNicholas Bellinger ISCSI_STAT_SESS_ERR_ATTR_RO(inst);
249e48354ceSNicholas Bellinger 
250e48354ceSNicholas Bellinger static ssize_t iscsi_stat_sess_err_show_attr_digest_errors(
251e48354ceSNicholas Bellinger 	struct iscsi_wwn_stat_grps *igrps, char *page)
252e48354ceSNicholas Bellinger {
253e48354ceSNicholas Bellinger 	struct iscsi_tiqn *tiqn = container_of(igrps,
254e48354ceSNicholas Bellinger 				struct iscsi_tiqn, tiqn_stat_grps);
255e48354ceSNicholas Bellinger 	struct iscsi_sess_err_stats *sess_err = &tiqn->sess_err_stats;
256e48354ceSNicholas Bellinger 
257e48354ceSNicholas Bellinger 	return snprintf(page, PAGE_SIZE, "%u\n", sess_err->digest_errors);
258e48354ceSNicholas Bellinger }
259e48354ceSNicholas Bellinger ISCSI_STAT_SESS_ERR_ATTR_RO(digest_errors);
260e48354ceSNicholas Bellinger 
261e48354ceSNicholas Bellinger static ssize_t iscsi_stat_sess_err_show_attr_cxn_errors(
262e48354ceSNicholas Bellinger 	struct iscsi_wwn_stat_grps *igrps, char *page)
263e48354ceSNicholas Bellinger {
264e48354ceSNicholas Bellinger 	struct iscsi_tiqn *tiqn = container_of(igrps,
265e48354ceSNicholas Bellinger 				struct iscsi_tiqn, tiqn_stat_grps);
266e48354ceSNicholas Bellinger 	struct iscsi_sess_err_stats *sess_err = &tiqn->sess_err_stats;
267e48354ceSNicholas Bellinger 
268e48354ceSNicholas Bellinger 	return snprintf(page, PAGE_SIZE, "%u\n", sess_err->cxn_timeout_errors);
269e48354ceSNicholas Bellinger }
270e48354ceSNicholas Bellinger ISCSI_STAT_SESS_ERR_ATTR_RO(cxn_errors);
271e48354ceSNicholas Bellinger 
272e48354ceSNicholas Bellinger static ssize_t iscsi_stat_sess_err_show_attr_format_errors(
273e48354ceSNicholas Bellinger 	struct iscsi_wwn_stat_grps *igrps, char *page)
274e48354ceSNicholas Bellinger {
275e48354ceSNicholas Bellinger 	struct iscsi_tiqn *tiqn = container_of(igrps,
276e48354ceSNicholas Bellinger 				struct iscsi_tiqn, tiqn_stat_grps);
277e48354ceSNicholas Bellinger 	struct iscsi_sess_err_stats *sess_err = &tiqn->sess_err_stats;
278e48354ceSNicholas Bellinger 
279e48354ceSNicholas Bellinger 	return snprintf(page, PAGE_SIZE, "%u\n", sess_err->pdu_format_errors);
280e48354ceSNicholas Bellinger }
281e48354ceSNicholas Bellinger ISCSI_STAT_SESS_ERR_ATTR_RO(format_errors);
282e48354ceSNicholas Bellinger 
283e48354ceSNicholas Bellinger CONFIGFS_EATTR_OPS(iscsi_stat_sess_err, iscsi_wwn_stat_grps,
284e48354ceSNicholas Bellinger 		iscsi_sess_err_group);
285e48354ceSNicholas Bellinger 
286e48354ceSNicholas Bellinger static struct configfs_attribute *iscsi_stat_sess_err_attrs[] = {
287e48354ceSNicholas Bellinger 	&iscsi_stat_sess_err_inst.attr,
288e48354ceSNicholas Bellinger 	&iscsi_stat_sess_err_digest_errors.attr,
289e48354ceSNicholas Bellinger 	&iscsi_stat_sess_err_cxn_errors.attr,
290e48354ceSNicholas Bellinger 	&iscsi_stat_sess_err_format_errors.attr,
291e48354ceSNicholas Bellinger 	NULL,
292e48354ceSNicholas Bellinger };
293e48354ceSNicholas Bellinger 
294e48354ceSNicholas Bellinger static struct configfs_item_operations iscsi_stat_sess_err_item_ops = {
295e48354ceSNicholas Bellinger 	.show_attribute		= iscsi_stat_sess_err_attr_show,
296e48354ceSNicholas Bellinger 	.store_attribute	= iscsi_stat_sess_err_attr_store,
297e48354ceSNicholas Bellinger };
298e48354ceSNicholas Bellinger 
299e48354ceSNicholas Bellinger struct config_item_type iscsi_stat_sess_err_cit = {
300e48354ceSNicholas Bellinger 	.ct_item_ops		= &iscsi_stat_sess_err_item_ops,
301e48354ceSNicholas Bellinger 	.ct_attrs		= iscsi_stat_sess_err_attrs,
302e48354ceSNicholas Bellinger 	.ct_owner		= THIS_MODULE,
303e48354ceSNicholas Bellinger };
304e48354ceSNicholas Bellinger 
305e48354ceSNicholas Bellinger /*
306e48354ceSNicholas Bellinger  * Target Attributes Table
307e48354ceSNicholas Bellinger  */
308e48354ceSNicholas Bellinger CONFIGFS_EATTR_STRUCT(iscsi_stat_tgt_attr, iscsi_wwn_stat_grps);
309e48354ceSNicholas Bellinger #define ISCSI_STAT_TGT_ATTR(_name, _mode)			\
310e48354ceSNicholas Bellinger static struct iscsi_stat_tgt_attr_attribute			\
311e48354ceSNicholas Bellinger 			iscsi_stat_tgt_attr_##_name =		\
312e48354ceSNicholas Bellinger 	__CONFIGFS_EATTR(_name, _mode,				\
313e48354ceSNicholas Bellinger 	iscsi_stat_tgt-attr_show_attr_##_name,			\
314e48354ceSNicholas Bellinger 	iscsi_stat_tgt_attr_store_attr_##_name);
315e48354ceSNicholas Bellinger 
316e48354ceSNicholas Bellinger #define ISCSI_STAT_TGT_ATTR_RO(_name)				\
317e48354ceSNicholas Bellinger static struct iscsi_stat_tgt_attr_attribute			\
318e48354ceSNicholas Bellinger 			iscsi_stat_tgt_attr_##_name =		\
319e48354ceSNicholas Bellinger 	__CONFIGFS_EATTR_RO(_name,				\
320e48354ceSNicholas Bellinger 	iscsi_stat_tgt_attr_show_attr_##_name);
321e48354ceSNicholas Bellinger 
322e48354ceSNicholas Bellinger static ssize_t iscsi_stat_tgt_attr_show_attr_inst(
323e48354ceSNicholas Bellinger 	struct iscsi_wwn_stat_grps *igrps, char *page)
324e48354ceSNicholas Bellinger {
325e48354ceSNicholas Bellinger 	struct iscsi_tiqn *tiqn = container_of(igrps,
326e48354ceSNicholas Bellinger 				struct iscsi_tiqn, tiqn_stat_grps);
327e48354ceSNicholas Bellinger 
328e48354ceSNicholas Bellinger 	return snprintf(page, PAGE_SIZE, "%u\n", tiqn->tiqn_index);
329e48354ceSNicholas Bellinger }
330e48354ceSNicholas Bellinger ISCSI_STAT_TGT_ATTR_RO(inst);
331e48354ceSNicholas Bellinger 
332e48354ceSNicholas Bellinger static ssize_t iscsi_stat_tgt_attr_show_attr_indx(
333e48354ceSNicholas Bellinger 	struct iscsi_wwn_stat_grps *igrps, char *page)
334e48354ceSNicholas Bellinger {
335e48354ceSNicholas Bellinger 	return snprintf(page, PAGE_SIZE, "%u\n", ISCSI_NODE_INDEX);
336e48354ceSNicholas Bellinger }
337e48354ceSNicholas Bellinger ISCSI_STAT_TGT_ATTR_RO(indx);
338e48354ceSNicholas Bellinger 
339e48354ceSNicholas Bellinger static ssize_t iscsi_stat_tgt_attr_show_attr_login_fails(
340e48354ceSNicholas Bellinger 	struct iscsi_wwn_stat_grps *igrps, char *page)
341e48354ceSNicholas Bellinger {
342e48354ceSNicholas Bellinger 	struct iscsi_tiqn *tiqn = container_of(igrps,
343e48354ceSNicholas Bellinger 				struct iscsi_tiqn, tiqn_stat_grps);
344e48354ceSNicholas Bellinger 	struct iscsi_login_stats *lstat = &tiqn->login_stats;
345e48354ceSNicholas Bellinger 	u32 fail_count;
346e48354ceSNicholas Bellinger 
347e48354ceSNicholas Bellinger 	spin_lock(&lstat->lock);
348e48354ceSNicholas Bellinger 	fail_count = (lstat->redirects + lstat->authorize_fails +
349e48354ceSNicholas Bellinger 			lstat->authenticate_fails + lstat->negotiate_fails +
350e48354ceSNicholas Bellinger 			lstat->other_fails);
351e48354ceSNicholas Bellinger 	spin_unlock(&lstat->lock);
352e48354ceSNicholas Bellinger 
353e48354ceSNicholas Bellinger 	return snprintf(page, PAGE_SIZE, "%u\n", fail_count);
354e48354ceSNicholas Bellinger }
355e48354ceSNicholas Bellinger ISCSI_STAT_TGT_ATTR_RO(login_fails);
356e48354ceSNicholas Bellinger 
357e48354ceSNicholas Bellinger static ssize_t iscsi_stat_tgt_attr_show_attr_last_fail_time(
358e48354ceSNicholas Bellinger 	struct iscsi_wwn_stat_grps *igrps, char *page)
359e48354ceSNicholas Bellinger {
360e48354ceSNicholas Bellinger 	struct iscsi_tiqn *tiqn = container_of(igrps,
361e48354ceSNicholas Bellinger 				struct iscsi_tiqn, tiqn_stat_grps);
362e48354ceSNicholas Bellinger 	struct iscsi_login_stats *lstat = &tiqn->login_stats;
363e48354ceSNicholas Bellinger 	u32 last_fail_time;
364e48354ceSNicholas Bellinger 
365e48354ceSNicholas Bellinger 	spin_lock(&lstat->lock);
366e48354ceSNicholas Bellinger 	last_fail_time = lstat->last_fail_time ?
367e48354ceSNicholas Bellinger 			(u32)(((u32)lstat->last_fail_time -
368e48354ceSNicholas Bellinger 				INITIAL_JIFFIES) * 100 / HZ) : 0;
369e48354ceSNicholas Bellinger 	spin_unlock(&lstat->lock);
370e48354ceSNicholas Bellinger 
371e48354ceSNicholas Bellinger 	return snprintf(page, PAGE_SIZE, "%u\n", last_fail_time);
372e48354ceSNicholas Bellinger }
373e48354ceSNicholas Bellinger ISCSI_STAT_TGT_ATTR_RO(last_fail_time);
374e48354ceSNicholas Bellinger 
375e48354ceSNicholas Bellinger static ssize_t iscsi_stat_tgt_attr_show_attr_last_fail_type(
376e48354ceSNicholas Bellinger 	struct iscsi_wwn_stat_grps *igrps, char *page)
377e48354ceSNicholas Bellinger {
378e48354ceSNicholas Bellinger 	struct iscsi_tiqn *tiqn = container_of(igrps,
379e48354ceSNicholas Bellinger 				struct iscsi_tiqn, tiqn_stat_grps);
380e48354ceSNicholas Bellinger 	struct iscsi_login_stats *lstat = &tiqn->login_stats;
381e48354ceSNicholas Bellinger 	u32 last_fail_type;
382e48354ceSNicholas Bellinger 
383e48354ceSNicholas Bellinger 	spin_lock(&lstat->lock);
384e48354ceSNicholas Bellinger 	last_fail_type = lstat->last_fail_type;
385e48354ceSNicholas Bellinger 	spin_unlock(&lstat->lock);
386e48354ceSNicholas Bellinger 
387e48354ceSNicholas Bellinger 	return snprintf(page, PAGE_SIZE, "%u\n", last_fail_type);
388e48354ceSNicholas Bellinger }
389e48354ceSNicholas Bellinger ISCSI_STAT_TGT_ATTR_RO(last_fail_type);
390e48354ceSNicholas Bellinger 
391e48354ceSNicholas Bellinger static ssize_t iscsi_stat_tgt_attr_show_attr_fail_intr_name(
392e48354ceSNicholas Bellinger 	struct iscsi_wwn_stat_grps *igrps, char *page)
393e48354ceSNicholas Bellinger {
394e48354ceSNicholas Bellinger 	struct iscsi_tiqn *tiqn = container_of(igrps,
395e48354ceSNicholas Bellinger 				struct iscsi_tiqn, tiqn_stat_grps);
396e48354ceSNicholas Bellinger 	struct iscsi_login_stats *lstat = &tiqn->login_stats;
397e48354ceSNicholas Bellinger 	unsigned char buf[224];
398e48354ceSNicholas Bellinger 
399e48354ceSNicholas Bellinger 	spin_lock(&lstat->lock);
400e48354ceSNicholas Bellinger 	snprintf(buf, 224, "%s", lstat->last_intr_fail_name[0] ?
401e48354ceSNicholas Bellinger 				lstat->last_intr_fail_name : NONE);
402e48354ceSNicholas Bellinger 	spin_unlock(&lstat->lock);
403e48354ceSNicholas Bellinger 
404e48354ceSNicholas Bellinger 	return snprintf(page, PAGE_SIZE, "%s\n", buf);
405e48354ceSNicholas Bellinger }
406e48354ceSNicholas Bellinger ISCSI_STAT_TGT_ATTR_RO(fail_intr_name);
407e48354ceSNicholas Bellinger 
408e48354ceSNicholas Bellinger static ssize_t iscsi_stat_tgt_attr_show_attr_fail_intr_addr_type(
409e48354ceSNicholas Bellinger 	struct iscsi_wwn_stat_grps *igrps, char *page)
410e48354ceSNicholas Bellinger {
411e48354ceSNicholas Bellinger 	struct iscsi_tiqn *tiqn = container_of(igrps,
412e48354ceSNicholas Bellinger 			struct iscsi_tiqn, tiqn_stat_grps);
413e48354ceSNicholas Bellinger 	struct iscsi_login_stats *lstat = &tiqn->login_stats;
414e48354ceSNicholas Bellinger 	unsigned char buf[8];
415e48354ceSNicholas Bellinger 
416e48354ceSNicholas Bellinger 	spin_lock(&lstat->lock);
417e48354ceSNicholas Bellinger 	snprintf(buf, 8, "%s", (lstat->last_intr_fail_ip_addr != NULL) ?
418e48354ceSNicholas Bellinger 				"ipv6" : "ipv4");
419e48354ceSNicholas Bellinger 	spin_unlock(&lstat->lock);
420e48354ceSNicholas Bellinger 
421e48354ceSNicholas Bellinger 	return snprintf(page, PAGE_SIZE, "%s\n", buf);
422e48354ceSNicholas Bellinger }
423e48354ceSNicholas Bellinger ISCSI_STAT_TGT_ATTR_RO(fail_intr_addr_type);
424e48354ceSNicholas Bellinger 
425e48354ceSNicholas Bellinger static ssize_t iscsi_stat_tgt_attr_show_attr_fail_intr_addr(
426e48354ceSNicholas Bellinger 	struct iscsi_wwn_stat_grps *igrps, char *page)
427e48354ceSNicholas Bellinger {
428e48354ceSNicholas Bellinger 	struct iscsi_tiqn *tiqn = container_of(igrps,
429e48354ceSNicholas Bellinger 			struct iscsi_tiqn, tiqn_stat_grps);
430e48354ceSNicholas Bellinger 	struct iscsi_login_stats *lstat = &tiqn->login_stats;
431e48354ceSNicholas Bellinger 	unsigned char buf[32];
432e48354ceSNicholas Bellinger 
433e48354ceSNicholas Bellinger 	spin_lock(&lstat->lock);
434e48354ceSNicholas Bellinger 	if (lstat->last_intr_fail_ip_family == AF_INET6)
435e48354ceSNicholas Bellinger 		snprintf(buf, 32, "[%s]", lstat->last_intr_fail_ip_addr);
436e48354ceSNicholas Bellinger 	else
437e48354ceSNicholas Bellinger 		snprintf(buf, 32, "%s", lstat->last_intr_fail_ip_addr);
438e48354ceSNicholas Bellinger 	spin_unlock(&lstat->lock);
439e48354ceSNicholas Bellinger 
440e48354ceSNicholas Bellinger 	return snprintf(page, PAGE_SIZE, "%s\n", buf);
441e48354ceSNicholas Bellinger }
442e48354ceSNicholas Bellinger ISCSI_STAT_TGT_ATTR_RO(fail_intr_addr);
443e48354ceSNicholas Bellinger 
444e48354ceSNicholas Bellinger CONFIGFS_EATTR_OPS(iscsi_stat_tgt_attr, iscsi_wwn_stat_grps,
445e48354ceSNicholas Bellinger 		iscsi_tgt_attr_group);
446e48354ceSNicholas Bellinger 
447e48354ceSNicholas Bellinger static struct configfs_attribute *iscsi_stat_tgt_attr_attrs[] = {
448e48354ceSNicholas Bellinger 	&iscsi_stat_tgt_attr_inst.attr,
449e48354ceSNicholas Bellinger 	&iscsi_stat_tgt_attr_indx.attr,
450e48354ceSNicholas Bellinger 	&iscsi_stat_tgt_attr_login_fails.attr,
451e48354ceSNicholas Bellinger 	&iscsi_stat_tgt_attr_last_fail_time.attr,
452e48354ceSNicholas Bellinger 	&iscsi_stat_tgt_attr_last_fail_type.attr,
453e48354ceSNicholas Bellinger 	&iscsi_stat_tgt_attr_fail_intr_name.attr,
454e48354ceSNicholas Bellinger 	&iscsi_stat_tgt_attr_fail_intr_addr_type.attr,
455e48354ceSNicholas Bellinger 	&iscsi_stat_tgt_attr_fail_intr_addr.attr,
456e48354ceSNicholas Bellinger 	NULL,
457e48354ceSNicholas Bellinger };
458e48354ceSNicholas Bellinger 
459e48354ceSNicholas Bellinger static struct configfs_item_operations iscsi_stat_tgt_attr_item_ops = {
460e48354ceSNicholas Bellinger 	.show_attribute		= iscsi_stat_tgt_attr_attr_show,
461e48354ceSNicholas Bellinger 	.store_attribute	= iscsi_stat_tgt_attr_attr_store,
462e48354ceSNicholas Bellinger };
463e48354ceSNicholas Bellinger 
464e48354ceSNicholas Bellinger struct config_item_type iscsi_stat_tgt_attr_cit = {
465e48354ceSNicholas Bellinger 	.ct_item_ops		= &iscsi_stat_tgt_attr_item_ops,
466e48354ceSNicholas Bellinger 	.ct_attrs		= iscsi_stat_tgt_attr_attrs,
467e48354ceSNicholas Bellinger 	.ct_owner		= THIS_MODULE,
468e48354ceSNicholas Bellinger };
469e48354ceSNicholas Bellinger 
470e48354ceSNicholas Bellinger /*
471e48354ceSNicholas Bellinger  * Target Login Stats Table
472e48354ceSNicholas Bellinger  */
473e48354ceSNicholas Bellinger CONFIGFS_EATTR_STRUCT(iscsi_stat_login, iscsi_wwn_stat_grps);
474e48354ceSNicholas Bellinger #define ISCSI_STAT_LOGIN(_name, _mode)				\
475e48354ceSNicholas Bellinger static struct iscsi_stat_login_attribute			\
476e48354ceSNicholas Bellinger 			iscsi_stat_login_##_name =		\
477e48354ceSNicholas Bellinger 	__CONFIGFS_EATTR(_name, _mode,				\
478e48354ceSNicholas Bellinger 	iscsi_stat_login_show_attr_##_name,			\
479e48354ceSNicholas Bellinger 	iscsi_stat_login_store_attr_##_name);
480e48354ceSNicholas Bellinger 
481e48354ceSNicholas Bellinger #define ISCSI_STAT_LOGIN_RO(_name)				\
482e48354ceSNicholas Bellinger static struct iscsi_stat_login_attribute			\
483e48354ceSNicholas Bellinger 			iscsi_stat_login_##_name =		\
484e48354ceSNicholas Bellinger 	__CONFIGFS_EATTR_RO(_name,				\
485e48354ceSNicholas Bellinger 	iscsi_stat_login_show_attr_##_name);
486e48354ceSNicholas Bellinger 
487e48354ceSNicholas Bellinger static ssize_t iscsi_stat_login_show_attr_inst(
488e48354ceSNicholas Bellinger 	struct iscsi_wwn_stat_grps *igrps, char *page)
489e48354ceSNicholas Bellinger {
490e48354ceSNicholas Bellinger 	struct iscsi_tiqn *tiqn = container_of(igrps,
491e48354ceSNicholas Bellinger 				struct iscsi_tiqn, tiqn_stat_grps);
492e48354ceSNicholas Bellinger 
493e48354ceSNicholas Bellinger 	return snprintf(page, PAGE_SIZE, "%u\n", tiqn->tiqn_index);
494e48354ceSNicholas Bellinger }
495e48354ceSNicholas Bellinger ISCSI_STAT_LOGIN_RO(inst);
496e48354ceSNicholas Bellinger 
497e48354ceSNicholas Bellinger static ssize_t iscsi_stat_login_show_attr_indx(
498e48354ceSNicholas Bellinger 	struct iscsi_wwn_stat_grps *igrps, char *page)
499e48354ceSNicholas Bellinger {
500e48354ceSNicholas Bellinger 	return snprintf(page, PAGE_SIZE, "%u\n", ISCSI_NODE_INDEX);
501e48354ceSNicholas Bellinger }
502e48354ceSNicholas Bellinger ISCSI_STAT_LOGIN_RO(indx);
503e48354ceSNicholas Bellinger 
504e48354ceSNicholas Bellinger static ssize_t iscsi_stat_login_show_attr_accepts(
505e48354ceSNicholas Bellinger 	struct iscsi_wwn_stat_grps *igrps, char *page)
506e48354ceSNicholas Bellinger {
507e48354ceSNicholas Bellinger 	struct iscsi_tiqn *tiqn = container_of(igrps,
508e48354ceSNicholas Bellinger 				struct iscsi_tiqn, tiqn_stat_grps);
509e48354ceSNicholas Bellinger 	struct iscsi_login_stats *lstat = &tiqn->login_stats;
510e48354ceSNicholas Bellinger 	ssize_t ret;
511e48354ceSNicholas Bellinger 
512e48354ceSNicholas Bellinger 	spin_lock(&lstat->lock);
513e48354ceSNicholas Bellinger 	ret = snprintf(page, PAGE_SIZE, "%u\n", lstat->accepts);
514e48354ceSNicholas Bellinger 	spin_unlock(&lstat->lock);
515e48354ceSNicholas Bellinger 
516e48354ceSNicholas Bellinger 	return ret;
517e48354ceSNicholas Bellinger }
518e48354ceSNicholas Bellinger ISCSI_STAT_LOGIN_RO(accepts);
519e48354ceSNicholas Bellinger 
520e48354ceSNicholas Bellinger static ssize_t iscsi_stat_login_show_attr_other_fails(
521e48354ceSNicholas Bellinger 	struct iscsi_wwn_stat_grps *igrps, char *page)
522e48354ceSNicholas Bellinger {
523e48354ceSNicholas Bellinger 	struct iscsi_tiqn *tiqn = container_of(igrps,
524e48354ceSNicholas Bellinger 				struct iscsi_tiqn, tiqn_stat_grps);
525e48354ceSNicholas Bellinger 	struct iscsi_login_stats *lstat = &tiqn->login_stats;
526e48354ceSNicholas Bellinger 	ssize_t ret;
527e48354ceSNicholas Bellinger 
528e48354ceSNicholas Bellinger 	spin_lock(&lstat->lock);
529e48354ceSNicholas Bellinger 	ret = snprintf(page, PAGE_SIZE, "%u\n", lstat->other_fails);
530e48354ceSNicholas Bellinger 	spin_unlock(&lstat->lock);
531e48354ceSNicholas Bellinger 
532e48354ceSNicholas Bellinger 	return ret;
533e48354ceSNicholas Bellinger }
534e48354ceSNicholas Bellinger ISCSI_STAT_LOGIN_RO(other_fails);
535e48354ceSNicholas Bellinger 
536e48354ceSNicholas Bellinger static ssize_t iscsi_stat_login_show_attr_redirects(
537e48354ceSNicholas Bellinger 	struct iscsi_wwn_stat_grps *igrps, char *page)
538e48354ceSNicholas Bellinger {
539e48354ceSNicholas Bellinger 	struct iscsi_tiqn *tiqn = container_of(igrps,
540e48354ceSNicholas Bellinger 				struct iscsi_tiqn, tiqn_stat_grps);
541e48354ceSNicholas Bellinger 	struct iscsi_login_stats *lstat = &tiqn->login_stats;
542e48354ceSNicholas Bellinger 	ssize_t ret;
543e48354ceSNicholas Bellinger 
544e48354ceSNicholas Bellinger 	spin_lock(&lstat->lock);
545e48354ceSNicholas Bellinger 	ret = snprintf(page, PAGE_SIZE, "%u\n", lstat->redirects);
546e48354ceSNicholas Bellinger 	spin_unlock(&lstat->lock);
547e48354ceSNicholas Bellinger 
548e48354ceSNicholas Bellinger 	return ret;
549e48354ceSNicholas Bellinger }
550e48354ceSNicholas Bellinger ISCSI_STAT_LOGIN_RO(redirects);
551e48354ceSNicholas Bellinger 
552e48354ceSNicholas Bellinger static ssize_t iscsi_stat_login_show_attr_authorize_fails(
553e48354ceSNicholas Bellinger 	struct iscsi_wwn_stat_grps *igrps, char *page)
554e48354ceSNicholas Bellinger {
555e48354ceSNicholas Bellinger 	struct iscsi_tiqn *tiqn = container_of(igrps,
556e48354ceSNicholas Bellinger 				struct iscsi_tiqn, tiqn_stat_grps);
557e48354ceSNicholas Bellinger 	struct iscsi_login_stats *lstat = &tiqn->login_stats;
558e48354ceSNicholas Bellinger 	ssize_t ret;
559e48354ceSNicholas Bellinger 
560e48354ceSNicholas Bellinger 	spin_lock(&lstat->lock);
561e48354ceSNicholas Bellinger 	ret = snprintf(page, PAGE_SIZE, "%u\n", lstat->authorize_fails);
562e48354ceSNicholas Bellinger 	spin_unlock(&lstat->lock);
563e48354ceSNicholas Bellinger 
564e48354ceSNicholas Bellinger 	return ret;
565e48354ceSNicholas Bellinger }
566e48354ceSNicholas Bellinger ISCSI_STAT_LOGIN_RO(authorize_fails);
567e48354ceSNicholas Bellinger 
568e48354ceSNicholas Bellinger static ssize_t iscsi_stat_login_show_attr_authenticate_fails(
569e48354ceSNicholas Bellinger 	struct iscsi_wwn_stat_grps *igrps, char *page)
570e48354ceSNicholas Bellinger {
571e48354ceSNicholas Bellinger 	struct iscsi_tiqn *tiqn = container_of(igrps,
572e48354ceSNicholas Bellinger 				struct iscsi_tiqn, tiqn_stat_grps);
573e48354ceSNicholas Bellinger 	struct iscsi_login_stats *lstat = &tiqn->login_stats;
574e48354ceSNicholas Bellinger 	ssize_t ret;
575e48354ceSNicholas Bellinger 
576e48354ceSNicholas Bellinger 	spin_lock(&lstat->lock);
577e48354ceSNicholas Bellinger 	ret = snprintf(page, PAGE_SIZE, "%u\n", lstat->authenticate_fails);
578e48354ceSNicholas Bellinger 	spin_unlock(&lstat->lock);
579e48354ceSNicholas Bellinger 
580e48354ceSNicholas Bellinger 	return ret;
581e48354ceSNicholas Bellinger }
582e48354ceSNicholas Bellinger ISCSI_STAT_LOGIN_RO(authenticate_fails);
583e48354ceSNicholas Bellinger 
584e48354ceSNicholas Bellinger static ssize_t iscsi_stat_login_show_attr_negotiate_fails(
585e48354ceSNicholas Bellinger 	struct iscsi_wwn_stat_grps *igrps, char *page)
586e48354ceSNicholas Bellinger {
587e48354ceSNicholas Bellinger 	struct iscsi_tiqn *tiqn = container_of(igrps,
588e48354ceSNicholas Bellinger 				struct iscsi_tiqn, tiqn_stat_grps);
589e48354ceSNicholas Bellinger 	struct iscsi_login_stats *lstat = &tiqn->login_stats;
590e48354ceSNicholas Bellinger 	ssize_t ret;
591e48354ceSNicholas Bellinger 
592e48354ceSNicholas Bellinger 	spin_lock(&lstat->lock);
593e48354ceSNicholas Bellinger 	ret = snprintf(page, PAGE_SIZE, "%u\n", lstat->negotiate_fails);
594e48354ceSNicholas Bellinger 	spin_unlock(&lstat->lock);
595e48354ceSNicholas Bellinger 
596e48354ceSNicholas Bellinger 	return ret;
597e48354ceSNicholas Bellinger }
598e48354ceSNicholas Bellinger ISCSI_STAT_LOGIN_RO(negotiate_fails);
599e48354ceSNicholas Bellinger 
600e48354ceSNicholas Bellinger CONFIGFS_EATTR_OPS(iscsi_stat_login, iscsi_wwn_stat_grps,
601e48354ceSNicholas Bellinger 		iscsi_login_stats_group);
602e48354ceSNicholas Bellinger 
603e48354ceSNicholas Bellinger static struct configfs_attribute *iscsi_stat_login_stats_attrs[] = {
604e48354ceSNicholas Bellinger 	&iscsi_stat_login_inst.attr,
605e48354ceSNicholas Bellinger 	&iscsi_stat_login_indx.attr,
606e48354ceSNicholas Bellinger 	&iscsi_stat_login_accepts.attr,
607e48354ceSNicholas Bellinger 	&iscsi_stat_login_other_fails.attr,
608e48354ceSNicholas Bellinger 	&iscsi_stat_login_redirects.attr,
609e48354ceSNicholas Bellinger 	&iscsi_stat_login_authorize_fails.attr,
610e48354ceSNicholas Bellinger 	&iscsi_stat_login_authenticate_fails.attr,
611e48354ceSNicholas Bellinger 	&iscsi_stat_login_negotiate_fails.attr,
612e48354ceSNicholas Bellinger 	NULL,
613e48354ceSNicholas Bellinger };
614e48354ceSNicholas Bellinger 
615e48354ceSNicholas Bellinger static struct configfs_item_operations iscsi_stat_login_stats_item_ops = {
616e48354ceSNicholas Bellinger 	.show_attribute		= iscsi_stat_login_attr_show,
617e48354ceSNicholas Bellinger 	.store_attribute	= iscsi_stat_login_attr_store,
618e48354ceSNicholas Bellinger };
619e48354ceSNicholas Bellinger 
620e48354ceSNicholas Bellinger struct config_item_type iscsi_stat_login_cit = {
621e48354ceSNicholas Bellinger 	.ct_item_ops		= &iscsi_stat_login_stats_item_ops,
622e48354ceSNicholas Bellinger 	.ct_attrs		= iscsi_stat_login_stats_attrs,
623e48354ceSNicholas Bellinger 	.ct_owner		= THIS_MODULE,
624e48354ceSNicholas Bellinger };
625e48354ceSNicholas Bellinger 
626e48354ceSNicholas Bellinger /*
627e48354ceSNicholas Bellinger  * Target Logout Stats Table
628e48354ceSNicholas Bellinger  */
629e48354ceSNicholas Bellinger 
630e48354ceSNicholas Bellinger CONFIGFS_EATTR_STRUCT(iscsi_stat_logout, iscsi_wwn_stat_grps);
631e48354ceSNicholas Bellinger #define ISCSI_STAT_LOGOUT(_name, _mode)				\
632e48354ceSNicholas Bellinger static struct iscsi_stat_logout_attribute			\
633e48354ceSNicholas Bellinger 			iscsi_stat_logout_##_name =		\
634e48354ceSNicholas Bellinger 	__CONFIGFS_EATTR(_name, _mode,				\
635e48354ceSNicholas Bellinger 	iscsi_stat_logout_show_attr_##_name,			\
636e48354ceSNicholas Bellinger 	iscsi_stat_logout_store_attr_##_name);
637e48354ceSNicholas Bellinger 
638e48354ceSNicholas Bellinger #define ISCSI_STAT_LOGOUT_RO(_name)				\
639e48354ceSNicholas Bellinger static struct iscsi_stat_logout_attribute			\
640e48354ceSNicholas Bellinger 			iscsi_stat_logout_##_name =		\
641e48354ceSNicholas Bellinger 	__CONFIGFS_EATTR_RO(_name,				\
642e48354ceSNicholas Bellinger 	iscsi_stat_logout_show_attr_##_name);
643e48354ceSNicholas Bellinger 
644e48354ceSNicholas Bellinger static ssize_t iscsi_stat_logout_show_attr_inst(
645e48354ceSNicholas Bellinger 	struct iscsi_wwn_stat_grps *igrps, char *page)
646e48354ceSNicholas Bellinger {
647e48354ceSNicholas Bellinger 	struct iscsi_tiqn *tiqn = container_of(igrps,
648e48354ceSNicholas Bellinger 			struct iscsi_tiqn, tiqn_stat_grps);
649e48354ceSNicholas Bellinger 
650e48354ceSNicholas Bellinger 	return snprintf(page, PAGE_SIZE, "%u\n", tiqn->tiqn_index);
651e48354ceSNicholas Bellinger }
652e48354ceSNicholas Bellinger ISCSI_STAT_LOGOUT_RO(inst);
653e48354ceSNicholas Bellinger 
654e48354ceSNicholas Bellinger static ssize_t iscsi_stat_logout_show_attr_indx(
655e48354ceSNicholas Bellinger 	struct iscsi_wwn_stat_grps *igrps, char *page)
656e48354ceSNicholas Bellinger {
657e48354ceSNicholas Bellinger 	return snprintf(page, PAGE_SIZE, "%u\n", ISCSI_NODE_INDEX);
658e48354ceSNicholas Bellinger }
659e48354ceSNicholas Bellinger ISCSI_STAT_LOGOUT_RO(indx);
660e48354ceSNicholas Bellinger 
661e48354ceSNicholas Bellinger static ssize_t iscsi_stat_logout_show_attr_normal_logouts(
662e48354ceSNicholas Bellinger 	struct iscsi_wwn_stat_grps *igrps, char *page)
663e48354ceSNicholas Bellinger {
664e48354ceSNicholas Bellinger 	struct iscsi_tiqn *tiqn = container_of(igrps,
665e48354ceSNicholas Bellinger 			struct iscsi_tiqn, tiqn_stat_grps);
666e48354ceSNicholas Bellinger 	struct iscsi_logout_stats *lstats = &tiqn->logout_stats;
667e48354ceSNicholas Bellinger 
668e48354ceSNicholas Bellinger 	return snprintf(page, PAGE_SIZE, "%u\n", lstats->normal_logouts);
669e48354ceSNicholas Bellinger }
670e48354ceSNicholas Bellinger ISCSI_STAT_LOGOUT_RO(normal_logouts);
671e48354ceSNicholas Bellinger 
672e48354ceSNicholas Bellinger static ssize_t iscsi_stat_logout_show_attr_abnormal_logouts(
673e48354ceSNicholas Bellinger 	struct iscsi_wwn_stat_grps *igrps, char *page)
674e48354ceSNicholas Bellinger {
675e48354ceSNicholas Bellinger 	struct iscsi_tiqn *tiqn = container_of(igrps,
676e48354ceSNicholas Bellinger 			struct iscsi_tiqn, tiqn_stat_grps);
677e48354ceSNicholas Bellinger 	struct iscsi_logout_stats *lstats = &tiqn->logout_stats;
678e48354ceSNicholas Bellinger 
679e48354ceSNicholas Bellinger 	return snprintf(page, PAGE_SIZE, "%u\n", lstats->abnormal_logouts);
680e48354ceSNicholas Bellinger }
681e48354ceSNicholas Bellinger ISCSI_STAT_LOGOUT_RO(abnormal_logouts);
682e48354ceSNicholas Bellinger 
683e48354ceSNicholas Bellinger CONFIGFS_EATTR_OPS(iscsi_stat_logout, iscsi_wwn_stat_grps,
684e48354ceSNicholas Bellinger 		iscsi_logout_stats_group);
685e48354ceSNicholas Bellinger 
686e48354ceSNicholas Bellinger static struct configfs_attribute *iscsi_stat_logout_stats_attrs[] = {
687e48354ceSNicholas Bellinger 	&iscsi_stat_logout_inst.attr,
688e48354ceSNicholas Bellinger 	&iscsi_stat_logout_indx.attr,
689e48354ceSNicholas Bellinger 	&iscsi_stat_logout_normal_logouts.attr,
690e48354ceSNicholas Bellinger 	&iscsi_stat_logout_abnormal_logouts.attr,
691e48354ceSNicholas Bellinger 	NULL,
692e48354ceSNicholas Bellinger };
693e48354ceSNicholas Bellinger 
694e48354ceSNicholas Bellinger static struct configfs_item_operations iscsi_stat_logout_stats_item_ops = {
695e48354ceSNicholas Bellinger 	.show_attribute		= iscsi_stat_logout_attr_show,
696e48354ceSNicholas Bellinger 	.store_attribute	= iscsi_stat_logout_attr_store,
697e48354ceSNicholas Bellinger };
698e48354ceSNicholas Bellinger 
699e48354ceSNicholas Bellinger struct config_item_type iscsi_stat_logout_cit = {
700e48354ceSNicholas Bellinger 	.ct_item_ops		= &iscsi_stat_logout_stats_item_ops,
701e48354ceSNicholas Bellinger 	.ct_attrs		= iscsi_stat_logout_stats_attrs,
702e48354ceSNicholas Bellinger 	.ct_owner		= THIS_MODULE,
703e48354ceSNicholas Bellinger };
704e48354ceSNicholas Bellinger 
705e48354ceSNicholas Bellinger /*
706e48354ceSNicholas Bellinger  * Session Stats Table
707e48354ceSNicholas Bellinger  */
708e48354ceSNicholas Bellinger 
709e48354ceSNicholas Bellinger CONFIGFS_EATTR_STRUCT(iscsi_stat_sess, iscsi_node_stat_grps);
710e48354ceSNicholas Bellinger #define ISCSI_STAT_SESS(_name, _mode)				\
711e48354ceSNicholas Bellinger static struct iscsi_stat_sess_attribute				\
712e48354ceSNicholas Bellinger 			iscsi_stat_sess_##_name =		\
713e48354ceSNicholas Bellinger 	__CONFIGFS_EATTR(_name, _mode,				\
714e48354ceSNicholas Bellinger 	iscsi_stat_sess_show_attr_##_name,			\
715e48354ceSNicholas Bellinger 	iscsi_stat_sess_store_attr_##_name);
716e48354ceSNicholas Bellinger 
717e48354ceSNicholas Bellinger #define ISCSI_STAT_SESS_RO(_name)				\
718e48354ceSNicholas Bellinger static struct iscsi_stat_sess_attribute				\
719e48354ceSNicholas Bellinger 			iscsi_stat_sess_##_name =		\
720e48354ceSNicholas Bellinger 	__CONFIGFS_EATTR_RO(_name,				\
721e48354ceSNicholas Bellinger 	iscsi_stat_sess_show_attr_##_name);
722e48354ceSNicholas Bellinger 
723e48354ceSNicholas Bellinger static ssize_t iscsi_stat_sess_show_attr_inst(
724e48354ceSNicholas Bellinger 	struct iscsi_node_stat_grps *igrps, char *page)
725e48354ceSNicholas Bellinger {
726e48354ceSNicholas Bellinger 	struct iscsi_node_acl *acl = container_of(igrps,
727e48354ceSNicholas Bellinger 			struct iscsi_node_acl, node_stat_grps);
728e48354ceSNicholas Bellinger 	struct se_wwn *wwn = acl->se_node_acl.se_tpg->se_tpg_wwn;
729e48354ceSNicholas Bellinger 	struct iscsi_tiqn *tiqn = container_of(wwn,
730e48354ceSNicholas Bellinger 			struct iscsi_tiqn, tiqn_wwn);
731e48354ceSNicholas Bellinger 
732e48354ceSNicholas Bellinger 	return snprintf(page, PAGE_SIZE, "%u\n", tiqn->tiqn_index);
733e48354ceSNicholas Bellinger }
734e48354ceSNicholas Bellinger ISCSI_STAT_SESS_RO(inst);
735e48354ceSNicholas Bellinger 
736e48354ceSNicholas Bellinger static ssize_t iscsi_stat_sess_show_attr_node(
737e48354ceSNicholas Bellinger 	struct iscsi_node_stat_grps *igrps, char *page)
738e48354ceSNicholas Bellinger {
739e48354ceSNicholas Bellinger 	struct iscsi_node_acl *acl = container_of(igrps,
740e48354ceSNicholas Bellinger 			struct iscsi_node_acl, node_stat_grps);
741e48354ceSNicholas Bellinger 	struct se_node_acl *se_nacl = &acl->se_node_acl;
742e48354ceSNicholas Bellinger 	struct iscsi_session *sess;
743e48354ceSNicholas Bellinger 	struct se_session *se_sess;
744e48354ceSNicholas Bellinger 	ssize_t ret = 0;
745e48354ceSNicholas Bellinger 
746e48354ceSNicholas Bellinger 	spin_lock_bh(&se_nacl->nacl_sess_lock);
747e48354ceSNicholas Bellinger 	se_sess = se_nacl->nacl_sess;
748e48354ceSNicholas Bellinger 	if (se_sess) {
749e48354ceSNicholas Bellinger 		sess = (struct iscsi_session *)se_sess->fabric_sess_ptr;
750e48354ceSNicholas Bellinger 		if (sess)
751e48354ceSNicholas Bellinger 			ret = snprintf(page, PAGE_SIZE, "%u\n",
752e48354ceSNicholas Bellinger 				sess->sess_ops->SessionType ? 0 : ISCSI_NODE_INDEX);
753e48354ceSNicholas Bellinger 	}
754e48354ceSNicholas Bellinger 	spin_unlock_bh(&se_nacl->nacl_sess_lock);
755e48354ceSNicholas Bellinger 
756e48354ceSNicholas Bellinger 	return ret;
757e48354ceSNicholas Bellinger }
758e48354ceSNicholas Bellinger ISCSI_STAT_SESS_RO(node);
759e48354ceSNicholas Bellinger 
760e48354ceSNicholas Bellinger static ssize_t iscsi_stat_sess_show_attr_indx(
761e48354ceSNicholas Bellinger 	struct iscsi_node_stat_grps *igrps, char *page)
762e48354ceSNicholas Bellinger {
763e48354ceSNicholas Bellinger 	struct iscsi_node_acl *acl = container_of(igrps,
764e48354ceSNicholas Bellinger 			struct iscsi_node_acl, node_stat_grps);
765e48354ceSNicholas Bellinger 	struct se_node_acl *se_nacl = &acl->se_node_acl;
766e48354ceSNicholas Bellinger 	struct iscsi_session *sess;
767e48354ceSNicholas Bellinger 	struct se_session *se_sess;
768e48354ceSNicholas Bellinger 	ssize_t ret = 0;
769e48354ceSNicholas Bellinger 
770e48354ceSNicholas Bellinger 	spin_lock_bh(&se_nacl->nacl_sess_lock);
771e48354ceSNicholas Bellinger 	se_sess = se_nacl->nacl_sess;
772e48354ceSNicholas Bellinger 	if (se_sess) {
773e48354ceSNicholas Bellinger 		sess = (struct iscsi_session *)se_sess->fabric_sess_ptr;
774e48354ceSNicholas Bellinger 		if (sess)
775e48354ceSNicholas Bellinger 			ret = snprintf(page, PAGE_SIZE, "%u\n",
776e48354ceSNicholas Bellinger 					sess->session_index);
777e48354ceSNicholas Bellinger 	}
778e48354ceSNicholas Bellinger 	spin_unlock_bh(&se_nacl->nacl_sess_lock);
779e48354ceSNicholas Bellinger 
780e48354ceSNicholas Bellinger 	return ret;
781e48354ceSNicholas Bellinger }
782e48354ceSNicholas Bellinger ISCSI_STAT_SESS_RO(indx);
783e48354ceSNicholas Bellinger 
784e48354ceSNicholas Bellinger static ssize_t iscsi_stat_sess_show_attr_cmd_pdus(
785e48354ceSNicholas Bellinger 	struct iscsi_node_stat_grps *igrps, char *page)
786e48354ceSNicholas Bellinger {
787e48354ceSNicholas Bellinger 	struct iscsi_node_acl *acl = container_of(igrps,
788e48354ceSNicholas Bellinger 			struct iscsi_node_acl, node_stat_grps);
789e48354ceSNicholas Bellinger 	struct se_node_acl *se_nacl = &acl->se_node_acl;
790e48354ceSNicholas Bellinger 	struct iscsi_session *sess;
791e48354ceSNicholas Bellinger 	struct se_session *se_sess;
792e48354ceSNicholas Bellinger 	ssize_t ret = 0;
793e48354ceSNicholas Bellinger 
794e48354ceSNicholas Bellinger 	spin_lock_bh(&se_nacl->nacl_sess_lock);
795e48354ceSNicholas Bellinger 	se_sess = se_nacl->nacl_sess;
796e48354ceSNicholas Bellinger 	if (se_sess) {
797e48354ceSNicholas Bellinger 		sess = (struct iscsi_session *)se_sess->fabric_sess_ptr;
798e48354ceSNicholas Bellinger 		if (sess)
799e48354ceSNicholas Bellinger 			ret = snprintf(page, PAGE_SIZE, "%u\n", sess->cmd_pdus);
800e48354ceSNicholas Bellinger 	}
801e48354ceSNicholas Bellinger 	spin_unlock_bh(&se_nacl->nacl_sess_lock);
802e48354ceSNicholas Bellinger 
803e48354ceSNicholas Bellinger 	return ret;
804e48354ceSNicholas Bellinger }
805e48354ceSNicholas Bellinger ISCSI_STAT_SESS_RO(cmd_pdus);
806e48354ceSNicholas Bellinger 
807e48354ceSNicholas Bellinger static ssize_t iscsi_stat_sess_show_attr_rsp_pdus(
808e48354ceSNicholas Bellinger 	struct iscsi_node_stat_grps *igrps, char *page)
809e48354ceSNicholas Bellinger {
810e48354ceSNicholas Bellinger 	struct iscsi_node_acl *acl = container_of(igrps,
811e48354ceSNicholas Bellinger 			struct iscsi_node_acl, node_stat_grps);
812e48354ceSNicholas Bellinger 	struct se_node_acl *se_nacl = &acl->se_node_acl;
813e48354ceSNicholas Bellinger 	struct iscsi_session *sess;
814e48354ceSNicholas Bellinger 	struct se_session *se_sess;
815e48354ceSNicholas Bellinger 	ssize_t ret = 0;
816e48354ceSNicholas Bellinger 
817e48354ceSNicholas Bellinger 	spin_lock_bh(&se_nacl->nacl_sess_lock);
818e48354ceSNicholas Bellinger 	se_sess = se_nacl->nacl_sess;
819e48354ceSNicholas Bellinger 	if (se_sess) {
820e48354ceSNicholas Bellinger 		sess = (struct iscsi_session *)se_sess->fabric_sess_ptr;
821e48354ceSNicholas Bellinger 		if (sess)
822e48354ceSNicholas Bellinger 			ret = snprintf(page, PAGE_SIZE, "%u\n", sess->rsp_pdus);
823e48354ceSNicholas Bellinger 	}
824e48354ceSNicholas Bellinger 	spin_unlock_bh(&se_nacl->nacl_sess_lock);
825e48354ceSNicholas Bellinger 
826e48354ceSNicholas Bellinger 	return ret;
827e48354ceSNicholas Bellinger }
828e48354ceSNicholas Bellinger ISCSI_STAT_SESS_RO(rsp_pdus);
829e48354ceSNicholas Bellinger 
830e48354ceSNicholas Bellinger static ssize_t iscsi_stat_sess_show_attr_txdata_octs(
831e48354ceSNicholas Bellinger 	struct iscsi_node_stat_grps *igrps, char *page)
832e48354ceSNicholas Bellinger {
833e48354ceSNicholas Bellinger 	struct iscsi_node_acl *acl = container_of(igrps,
834e48354ceSNicholas Bellinger 			struct iscsi_node_acl, node_stat_grps);
835e48354ceSNicholas Bellinger 	struct se_node_acl *se_nacl = &acl->se_node_acl;
836e48354ceSNicholas Bellinger 	struct iscsi_session *sess;
837e48354ceSNicholas Bellinger 	struct se_session *se_sess;
838e48354ceSNicholas Bellinger 	ssize_t ret = 0;
839e48354ceSNicholas Bellinger 
840e48354ceSNicholas Bellinger 	spin_lock_bh(&se_nacl->nacl_sess_lock);
841e48354ceSNicholas Bellinger 	se_sess = se_nacl->nacl_sess;
842e48354ceSNicholas Bellinger 	if (se_sess) {
843e48354ceSNicholas Bellinger 		sess = (struct iscsi_session *)se_sess->fabric_sess_ptr;
844e48354ceSNicholas Bellinger 		if (sess)
845e48354ceSNicholas Bellinger 			ret = snprintf(page, PAGE_SIZE, "%llu\n",
846e48354ceSNicholas Bellinger 				(unsigned long long)sess->tx_data_octets);
847e48354ceSNicholas Bellinger 	}
848e48354ceSNicholas Bellinger 	spin_unlock_bh(&se_nacl->nacl_sess_lock);
849e48354ceSNicholas Bellinger 
850e48354ceSNicholas Bellinger 	return ret;
851e48354ceSNicholas Bellinger }
852e48354ceSNicholas Bellinger ISCSI_STAT_SESS_RO(txdata_octs);
853e48354ceSNicholas Bellinger 
854e48354ceSNicholas Bellinger static ssize_t iscsi_stat_sess_show_attr_rxdata_octs(
855e48354ceSNicholas Bellinger 	struct iscsi_node_stat_grps *igrps, char *page)
856e48354ceSNicholas Bellinger {
857e48354ceSNicholas Bellinger 	struct iscsi_node_acl *acl = container_of(igrps,
858e48354ceSNicholas Bellinger 			struct iscsi_node_acl, node_stat_grps);
859e48354ceSNicholas Bellinger 	struct se_node_acl *se_nacl = &acl->se_node_acl;
860e48354ceSNicholas Bellinger 	struct iscsi_session *sess;
861e48354ceSNicholas Bellinger 	struct se_session *se_sess;
862e48354ceSNicholas Bellinger 	ssize_t ret = 0;
863e48354ceSNicholas Bellinger 
864e48354ceSNicholas Bellinger 	spin_lock_bh(&se_nacl->nacl_sess_lock);
865e48354ceSNicholas Bellinger 	se_sess = se_nacl->nacl_sess;
866e48354ceSNicholas Bellinger 	if (se_sess) {
867e48354ceSNicholas Bellinger 		sess = (struct iscsi_session *)se_sess->fabric_sess_ptr;
868e48354ceSNicholas Bellinger 		if (sess)
869e48354ceSNicholas Bellinger 			ret = snprintf(page, PAGE_SIZE, "%llu\n",
870e48354ceSNicholas Bellinger 				(unsigned long long)sess->rx_data_octets);
871e48354ceSNicholas Bellinger 	}
872e48354ceSNicholas Bellinger 	spin_unlock_bh(&se_nacl->nacl_sess_lock);
873e48354ceSNicholas Bellinger 
874e48354ceSNicholas Bellinger 	return ret;
875e48354ceSNicholas Bellinger }
876e48354ceSNicholas Bellinger ISCSI_STAT_SESS_RO(rxdata_octs);
877e48354ceSNicholas Bellinger 
878e48354ceSNicholas Bellinger static ssize_t iscsi_stat_sess_show_attr_conn_digest_errors(
879e48354ceSNicholas Bellinger 	struct iscsi_node_stat_grps *igrps, char *page)
880e48354ceSNicholas Bellinger {
881e48354ceSNicholas Bellinger 	struct iscsi_node_acl *acl = container_of(igrps,
882e48354ceSNicholas Bellinger 			struct iscsi_node_acl, node_stat_grps);
883e48354ceSNicholas Bellinger 	struct se_node_acl *se_nacl = &acl->se_node_acl;
884e48354ceSNicholas Bellinger 	struct iscsi_session *sess;
885e48354ceSNicholas Bellinger 	struct se_session *se_sess;
886e48354ceSNicholas Bellinger 	ssize_t ret = 0;
887e48354ceSNicholas Bellinger 
888e48354ceSNicholas Bellinger 	spin_lock_bh(&se_nacl->nacl_sess_lock);
889e48354ceSNicholas Bellinger 	se_sess = se_nacl->nacl_sess;
890e48354ceSNicholas Bellinger 	if (se_sess) {
891e48354ceSNicholas Bellinger 		sess = (struct iscsi_session *)se_sess->fabric_sess_ptr;
892e48354ceSNicholas Bellinger 		if (sess)
893e48354ceSNicholas Bellinger 			ret = snprintf(page, PAGE_SIZE, "%u\n",
894e48354ceSNicholas Bellinger 					sess->conn_digest_errors);
895e48354ceSNicholas Bellinger 	}
896e48354ceSNicholas Bellinger 	spin_unlock_bh(&se_nacl->nacl_sess_lock);
897e48354ceSNicholas Bellinger 
898e48354ceSNicholas Bellinger 	return ret;
899e48354ceSNicholas Bellinger }
900e48354ceSNicholas Bellinger ISCSI_STAT_SESS_RO(conn_digest_errors);
901e48354ceSNicholas Bellinger 
902e48354ceSNicholas Bellinger static ssize_t iscsi_stat_sess_show_attr_conn_timeout_errors(
903e48354ceSNicholas Bellinger 	struct iscsi_node_stat_grps *igrps, char *page)
904e48354ceSNicholas Bellinger {
905e48354ceSNicholas Bellinger 	struct iscsi_node_acl *acl = container_of(igrps,
906e48354ceSNicholas Bellinger 			struct iscsi_node_acl, node_stat_grps);
907e48354ceSNicholas Bellinger 	struct se_node_acl *se_nacl = &acl->se_node_acl;
908e48354ceSNicholas Bellinger 	struct iscsi_session *sess;
909e48354ceSNicholas Bellinger 	struct se_session *se_sess;
910e48354ceSNicholas Bellinger 	ssize_t ret = 0;
911e48354ceSNicholas Bellinger 
912e48354ceSNicholas Bellinger 	spin_lock_bh(&se_nacl->nacl_sess_lock);
913e48354ceSNicholas Bellinger 	se_sess = se_nacl->nacl_sess;
914e48354ceSNicholas Bellinger 	if (se_sess) {
915e48354ceSNicholas Bellinger 		sess = (struct iscsi_session *)se_sess->fabric_sess_ptr;
916e48354ceSNicholas Bellinger 		if (sess)
917e48354ceSNicholas Bellinger 			ret = snprintf(page, PAGE_SIZE, "%u\n",
918e48354ceSNicholas Bellinger 					sess->conn_timeout_errors);
919e48354ceSNicholas Bellinger 	}
920e48354ceSNicholas Bellinger 	spin_unlock_bh(&se_nacl->nacl_sess_lock);
921e48354ceSNicholas Bellinger 
922e48354ceSNicholas Bellinger 	return ret;
923e48354ceSNicholas Bellinger }
924e48354ceSNicholas Bellinger ISCSI_STAT_SESS_RO(conn_timeout_errors);
925e48354ceSNicholas Bellinger 
926e48354ceSNicholas Bellinger CONFIGFS_EATTR_OPS(iscsi_stat_sess, iscsi_node_stat_grps,
927e48354ceSNicholas Bellinger 		iscsi_sess_stats_group);
928e48354ceSNicholas Bellinger 
929e48354ceSNicholas Bellinger static struct configfs_attribute *iscsi_stat_sess_stats_attrs[] = {
930e48354ceSNicholas Bellinger 	&iscsi_stat_sess_inst.attr,
931e48354ceSNicholas Bellinger 	&iscsi_stat_sess_node.attr,
932e48354ceSNicholas Bellinger 	&iscsi_stat_sess_indx.attr,
933e48354ceSNicholas Bellinger 	&iscsi_stat_sess_cmd_pdus.attr,
934e48354ceSNicholas Bellinger 	&iscsi_stat_sess_rsp_pdus.attr,
935e48354ceSNicholas Bellinger 	&iscsi_stat_sess_txdata_octs.attr,
936e48354ceSNicholas Bellinger 	&iscsi_stat_sess_rxdata_octs.attr,
937e48354ceSNicholas Bellinger 	&iscsi_stat_sess_conn_digest_errors.attr,
938e48354ceSNicholas Bellinger 	&iscsi_stat_sess_conn_timeout_errors.attr,
939e48354ceSNicholas Bellinger 	NULL,
940e48354ceSNicholas Bellinger };
941e48354ceSNicholas Bellinger 
942e48354ceSNicholas Bellinger static struct configfs_item_operations iscsi_stat_sess_stats_item_ops = {
943e48354ceSNicholas Bellinger 	.show_attribute		= iscsi_stat_sess_attr_show,
944e48354ceSNicholas Bellinger 	.store_attribute	= iscsi_stat_sess_attr_store,
945e48354ceSNicholas Bellinger };
946e48354ceSNicholas Bellinger 
947e48354ceSNicholas Bellinger struct config_item_type iscsi_stat_sess_cit = {
948e48354ceSNicholas Bellinger 	.ct_item_ops		= &iscsi_stat_sess_stats_item_ops,
949e48354ceSNicholas Bellinger 	.ct_attrs		= iscsi_stat_sess_stats_attrs,
950e48354ceSNicholas Bellinger 	.ct_owner		= THIS_MODULE,
951e48354ceSNicholas Bellinger };
952