1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
|
/* SPDX-License-Identifier: GPL-2.0 */
/*
* Copyright (C) 2021 Broadcom. All Rights Reserved. The term
* “Broadcom” refers to Broadcom Inc. and/or its subsidiaries.
*/
#ifndef __EFCT_LIO_H__
#define __EFCT_LIO_H__
#include "efct_scsi.h"
#include <target/target_core_base.h>
#define efct_lio_io_printf(io, fmt, ...) \
efc_log_debug(io->efct, \
"[%s] [%04x][i:%04x t:%04x h:%04x]" fmt,\
io->node->display_name, io->instance_index, \
io->init_task_tag, io->tgt_task_tag, io->hw_tag,\
##__VA_ARGS__)
#define efct_lio_tmfio_printf(io, fmt, ...) \
efc_log_debug(io->efct, \
"[%s] [%04x][i:%04x t:%04x h:%04x][f:%02x]" fmt,\
io->node->display_name, io->instance_index, \
io->init_task_tag, io->tgt_task_tag, io->hw_tag,\
io->tgt_io.tmf, ##__VA_ARGS__)
#define efct_set_lio_io_state(io, value) (io->tgt_io.state |= value)
struct efct_lio_wq_data {
struct efct *efct;
void *ptr;
struct work_struct work;
};
/* Target private efct structure */
struct efct_scsi_tgt {
u32 max_sge;
u32 max_sgl;
/*
* Variables used to send task set full. We are using a high watermark
* method to send task set full. We will reserve a fixed number of IOs
* per initiator plus a fudge factor. Once we reach this number,
* then the target will start sending task set full/busy responses.
*/
atomic_t initiator_count;
atomic_t ios_in_use;
atomic_t io_high_watermark;
atomic_t watermark_hit;
int watermark_min;
int watermark_max;
struct efct_lio_nport *lio_nport;
struct efct_lio_tpg *tpg;
struct list_head vport_list;
/* Protects vport list*/
spinlock_t efct_lio_lock;
u64 wwnn;
};
struct efct_scsi_tgt_nport {
struct efct_lio_nport *lio_nport;
};
struct efct_node {
struct list_head list_entry;
struct kref ref;
void (*release)(struct kref *arg);
struct efct *efct;
struct efc_node *node;
struct se_session *session;
spinlock_t active_ios_lock;
struct list_head active_ios;
char display_name[EFC_NAME_LENGTH];
u32 port_fc_id;
u32 node_fc_id;
u32 vpi;
u32 rpi;
u32 abort_cnt;
};
#define EFCT_LIO_STATE_SCSI_RECV_CMD (1 << 0)
#define EFCT_LIO_STATE_TGT_SUBMIT_CMD (1 << 1)
#define EFCT_LIO_STATE_TFO_QUEUE_DATA_IN (1 << 2)
#define EFCT_LIO_STATE_TFO_WRITE_PENDING (1 << 3)
#define EFCT_LIO_STATE_TGT_EXECUTE_CMD (1 << 4)
#define EFCT_LIO_STATE_SCSI_SEND_RD_DATA (1 << 5)
#define EFCT_LIO_STATE_TFO_CHK_STOP_FREE (1 << 6)
#define EFCT_LIO_STATE_SCSI_DATA_DONE (1 << 7)
#define EFCT_LIO_STATE_TFO_QUEUE_STATUS (1 << 8)
#define EFCT_LIO_STATE_SCSI_SEND_RSP (1 << 9)
#define EFCT_LIO_STATE_SCSI_RSP_DONE (1 << 10)
#define EFCT_LIO_STATE_TGT_GENERIC_FREE (1 << 11)
#define EFCT_LIO_STATE_SCSI_RECV_TMF (1 << 12)
#define EFCT_LIO_STATE_TGT_SUBMIT_TMR (1 << 13)
#define EFCT_LIO_STATE_TFO_WRITE_PEND_STATUS (1 << 14)
#define EFCT_LIO_STATE_TGT_GENERIC_REQ_FAILURE (1 << 15)
#define EFCT_LIO_STATE_TFO_ABORTED_TASK (1 << 29)
#define EFCT_LIO_STATE_TFO_RELEASE_CMD (1 << 30)
#define EFCT_LIO_STATE_SCSI_CMPL_CMD (1u << 31)
struct efct_scsi_tgt_io {
struct se_cmd cmd;
unsigned char sense_buffer[TRANSPORT_SENSE_BUFFER];
enum dma_data_direction ddir;
int task_attr;
u64 lun;
u32 state;
u8 tmf;
struct efct_io *io_to_abort;
u32 seg_map_cnt;
u32 seg_cnt;
u32 cur_seg;
enum efct_scsi_io_status err;
bool aborting;
bool rsp_sent;
u32 transferred_len;
};
/* Handler return codes */
enum {
SCSI_HANDLER_DATAPHASE_STARTED = 1,
SCSI_HANDLER_RESP_STARTED,
SCSI_HANDLER_VALIDATED_DATAPHASE_STARTED,
SCSI_CMD_NOT_SUPPORTED,
};
#define WWN_NAME_LEN 32
struct efct_lio_vport {
u64 wwpn;
u64 npiv_wwpn;
u64 npiv_wwnn;
unsigned char wwpn_str[WWN_NAME_LEN];
struct se_wwn vport_wwn;
struct efct_lio_tpg *tpg;
struct efct *efct;
struct Scsi_Host *shost;
struct fc_vport *fc_vport;
atomic_t enable;
};
struct efct_lio_nport {
u64 wwpn;
unsigned char wwpn_str[WWN_NAME_LEN];
struct se_wwn nport_wwn;
struct efct_lio_tpg *tpg;
struct efct *efct;
atomic_t enable;
};
struct efct_lio_tpg_attrib {
u32 generate_node_acls;
u32 cache_dynamic_acls;
u32 demo_mode_write_protect;
u32 prod_mode_write_protect;
u32 demo_mode_login_only;
bool session_deletion_wait;
};
struct efct_lio_tpg {
struct se_portal_group tpg;
struct efct_lio_nport *nport;
struct efct_lio_vport *vport;
struct efct_lio_tpg_attrib tpg_attrib;
unsigned short tpgt;
bool enabled;
};
struct efct_lio_nacl {
u64 nport_wwnn;
char nport_name[WWN_NAME_LEN];
struct se_session *session;
struct se_node_acl se_node_acl;
};
struct efct_lio_vport_list_t {
struct list_head list_entry;
struct efct_lio_vport *lio_vport;
};
int efct_scsi_tgt_driver_init(void);
int efct_scsi_tgt_driver_exit(void);
#endif /*__EFCT_LIO_H__ */
|