/* 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 #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__ */