drivers/scsi/fnic/fip.c

Source file repositories/reference/linux-study-clean/drivers/scsi/fnic/fip.c

File Facts

System
Linux kernel
Corpus path
drivers/scsi/fnic/fip.c
Extension
.c
Size
30258 bytes
Lines
1006
Domain
Driver Families
Bucket
drivers/scsi
Inferred role
Driver Families: implementation source
Status
source implementation candidate

Why This File Exists

Repeatable hardware-adapter layer. Deep compatibility for every driver is out of scope; this atlas records patterns, probe lifecycles, bus glue, IRQ/DMA usage, and links back to core abstractions.

Dependency Surface

Detected Declarations

Annotated Snippet

list_for_each_entry_safe(vlan, next, &fnic->vlan_list, list) {
			list_del(&vlan->list);
			kfree(vlan);
		}
	}

	spin_unlock_irqrestore(&fnic->vlans_lock, flags);
	FNIC_FIP_DBG(KERN_INFO, fnic->host, fnic->fnic_num,
		     "Reset vlan complete\n");
}

/**
 * fnic_fcoe_send_vlan_req - Send FIP vlan request to all FCFs MAC
 * @fnic: Handle to fnic driver instance
 */
void fnic_fcoe_send_vlan_req(struct fnic *fnic)
{
	uint8_t *frame;
	struct fnic_iport_s *iport = &fnic->iport;
	struct fnic_stats *fnic_stats = &fnic->fnic_stats;
	u64 vlan_tov;
	struct fip_vlan_req *pvlan_req;
	uint16_t frame_size = sizeof(struct fip_vlan_req);

	frame = fdls_alloc_frame(iport);
	if (frame == NULL) {
		FNIC_FIP_DBG(KERN_ERR, fnic->host, fnic->fnic_num,
		     "Failed to allocate frame to send VLAN req");
		return;
	}

	fnic_fcoe_reset_vlans(fnic);

	fnic->set_vlan(fnic, 0);
	FNIC_FIP_DBG(KERN_INFO, fnic->host, fnic->fnic_num,
		     "set vlan done\n");

	FNIC_FIP_DBG(KERN_INFO, fnic->host, fnic->fnic_num,
		     "got MAC 0x%x:%x:%x:%x:%x:%x\n", iport->hwmac[0],
		     iport->hwmac[1], iport->hwmac[2], iport->hwmac[3],
		     iport->hwmac[4], iport->hwmac[5]);

	pvlan_req = (struct fip_vlan_req *) frame;
	*pvlan_req = (struct fip_vlan_req) {
		.eth = {.h_dest = FCOE_ALL_FCFS_MAC,
			.h_proto = cpu_to_be16(ETH_P_FIP)},
		.fip = {.fip_ver = FIP_VER_ENCAPS(FIP_VER),
			.fip_op = cpu_to_be16(FIP_OP_VLAN),
			.fip_subcode = FIP_SC_REQ,
			.fip_dl_len = cpu_to_be16(FIP_VLAN_REQ_LEN)},
		.mac_desc = {.fd_desc = {.fip_dtype = FIP_DT_MAC,
						.fip_dlen = 2}}
	};

	memcpy(pvlan_req->eth.h_source, iport->hwmac, ETH_ALEN);
	memcpy(pvlan_req->mac_desc.fd_mac, iport->hwmac, ETH_ALEN);

	atomic64_inc(&fnic_stats->vlan_stats.vlan_disc_reqs);

	iport->fip.state = FDLS_FIP_VLAN_DISCOVERY_STARTED;

	FNIC_FIP_DBG(KERN_INFO, fnic->host, fnic->fnic_num,
		     "Send VLAN req\n");
	fnic_send_fip_frame(iport, frame, frame_size);

	vlan_tov = jiffies + msecs_to_jiffies(FCOE_CTLR_FIPVLAN_TOV);
	mod_timer(&fnic->retry_fip_timer, round_jiffies(vlan_tov));
	FNIC_FIP_DBG(KERN_INFO, fnic->host, fnic->fnic_num,
		     "fip timer set\n");
}

/**
 * fnic_fcoe_process_vlan_resp - Processes the vlan response from one FCF and
 * populates VLAN list.
 * @fnic: Handle to fnic driver instance
 * @fiph: Received FIP frame
 *
 * Will wait for responses from multiple FCFs until timeout.
 */
void fnic_fcoe_process_vlan_resp(struct fnic *fnic, struct fip_header *fiph)
{
	struct fip_vlan_notif *vlan_notif = (struct fip_vlan_notif *)fiph;

	struct fnic_stats *fnic_stats = &fnic->fnic_stats;
	u16 vid;
	int num_vlan = 0;
	int cur_desc, desc_len;
	struct fcoe_vlan *vlan;
	struct fip_vlan_desc *vlan_desc;
	unsigned long flags;

Annotation

Implementation Notes