⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 ipr.c

📁 linux 内核源代码
💻 C
📖 第 1 页 / 共 5 页
字号:
	if (len == 0)		return;	if (ioa_cfg->log_level <= IPR_DEFAULT_LOG_LEVEL)		len = min_t(int, len, IPR_DEFAULT_MAX_ERROR_DUMP);	for (i = 0; i < len / 4; i += 4) {		ipr_err("%08X: %08X %08X %08X %08X\n", i*4,			be32_to_cpu(data[i]),			be32_to_cpu(data[i+1]),			be32_to_cpu(data[i+2]),			be32_to_cpu(data[i+3]));	}}/** * ipr_log_enhanced_dual_ioa_error - Log an enhanced dual adapter error. * @ioa_cfg:	ioa config struct * @hostrcb:	hostrcb struct * * Return value: * 	none **/static void ipr_log_enhanced_dual_ioa_error(struct ipr_ioa_cfg *ioa_cfg,					    struct ipr_hostrcb *hostrcb){	struct ipr_hostrcb_type_17_error *error;	error = &hostrcb->hcam.u.error.u.type_17_error;	error->failure_reason[sizeof(error->failure_reason) - 1] = '\0';	strstrip(error->failure_reason);	ipr_hcam_err(hostrcb, "%s [PRC: %08X]\n", error->failure_reason,		     be32_to_cpu(hostrcb->hcam.u.error.prc));	ipr_log_ext_vpd_compact("Remote IOA", hostrcb, &error->vpd);	ipr_log_hex_data(ioa_cfg, error->data,			 be32_to_cpu(hostrcb->hcam.length) -			 (offsetof(struct ipr_hostrcb_error, u) +			  offsetof(struct ipr_hostrcb_type_17_error, data)));}/** * ipr_log_dual_ioa_error - Log a dual adapter error. * @ioa_cfg:	ioa config struct * @hostrcb:	hostrcb struct * * Return value: * 	none **/static void ipr_log_dual_ioa_error(struct ipr_ioa_cfg *ioa_cfg,				   struct ipr_hostrcb *hostrcb){	struct ipr_hostrcb_type_07_error *error;	error = &hostrcb->hcam.u.error.u.type_07_error;	error->failure_reason[sizeof(error->failure_reason) - 1] = '\0';	strstrip(error->failure_reason);	ipr_hcam_err(hostrcb, "%s [PRC: %08X]\n", error->failure_reason,		     be32_to_cpu(hostrcb->hcam.u.error.prc));	ipr_log_vpd_compact("Remote IOA", hostrcb, &error->vpd);	ipr_log_hex_data(ioa_cfg, error->data,			 be32_to_cpu(hostrcb->hcam.length) -			 (offsetof(struct ipr_hostrcb_error, u) +			  offsetof(struct ipr_hostrcb_type_07_error, data)));}static const struct {	u8 active;	char *desc;} path_active_desc[] = {	{ IPR_PATH_NO_INFO, "Path" },	{ IPR_PATH_ACTIVE, "Active path" },	{ IPR_PATH_NOT_ACTIVE, "Inactive path" }};static const struct {	u8 state;	char *desc;} path_state_desc[] = {	{ IPR_PATH_STATE_NO_INFO, "has no path state information available" },	{ IPR_PATH_HEALTHY, "is healthy" },	{ IPR_PATH_DEGRADED, "is degraded" },	{ IPR_PATH_FAILED, "is failed" }};/** * ipr_log_fabric_path - Log a fabric path error * @hostrcb:	hostrcb struct * @fabric:		fabric descriptor * * Return value: * 	none **/static void ipr_log_fabric_path(struct ipr_hostrcb *hostrcb,				struct ipr_hostrcb_fabric_desc *fabric){	int i, j;	u8 path_state = fabric->path_state;	u8 active = path_state & IPR_PATH_ACTIVE_MASK;	u8 state = path_state & IPR_PATH_STATE_MASK;	for (i = 0; i < ARRAY_SIZE(path_active_desc); i++) {		if (path_active_desc[i].active != active)			continue;		for (j = 0; j < ARRAY_SIZE(path_state_desc); j++) {			if (path_state_desc[j].state != state)				continue;			if (fabric->cascaded_expander == 0xff && fabric->phy == 0xff) {				ipr_hcam_err(hostrcb, "%s %s: IOA Port=%d\n",					     path_active_desc[i].desc, path_state_desc[j].desc,					     fabric->ioa_port);			} else if (fabric->cascaded_expander == 0xff) {				ipr_hcam_err(hostrcb, "%s %s: IOA Port=%d, Phy=%d\n",					     path_active_desc[i].desc, path_state_desc[j].desc,					     fabric->ioa_port, fabric->phy);			} else if (fabric->phy == 0xff) {				ipr_hcam_err(hostrcb, "%s %s: IOA Port=%d, Cascade=%d\n",					     path_active_desc[i].desc, path_state_desc[j].desc,					     fabric->ioa_port, fabric->cascaded_expander);			} else {				ipr_hcam_err(hostrcb, "%s %s: IOA Port=%d, Cascade=%d, Phy=%d\n",					     path_active_desc[i].desc, path_state_desc[j].desc,					     fabric->ioa_port, fabric->cascaded_expander, fabric->phy);			}			return;		}	}	ipr_err("Path state=%02X IOA Port=%d Cascade=%d Phy=%d\n", path_state,		fabric->ioa_port, fabric->cascaded_expander, fabric->phy);}static const struct {	u8 type;	char *desc;} path_type_desc[] = {	{ IPR_PATH_CFG_IOA_PORT, "IOA port" },	{ IPR_PATH_CFG_EXP_PORT, "Expander port" },	{ IPR_PATH_CFG_DEVICE_PORT, "Device port" },	{ IPR_PATH_CFG_DEVICE_LUN, "Device LUN" }};static const struct {	u8 status;	char *desc;} path_status_desc[] = {	{ IPR_PATH_CFG_NO_PROB, "Functional" },	{ IPR_PATH_CFG_DEGRADED, "Degraded" },	{ IPR_PATH_CFG_FAILED, "Failed" },	{ IPR_PATH_CFG_SUSPECT, "Suspect" },	{ IPR_PATH_NOT_DETECTED, "Missing" },	{ IPR_PATH_INCORRECT_CONN, "Incorrectly connected" }};static const char *link_rate[] = {	"unknown",	"disabled",	"phy reset problem",	"spinup hold",	"port selector",	"unknown",	"unknown",	"unknown",	"1.5Gbps",	"3.0Gbps",	"unknown",	"unknown",	"unknown",	"unknown",	"unknown",	"unknown"};/** * ipr_log_path_elem - Log a fabric path element. * @hostrcb:	hostrcb struct * @cfg:		fabric path element struct * * Return value: * 	none **/static void ipr_log_path_elem(struct ipr_hostrcb *hostrcb,			      struct ipr_hostrcb_config_element *cfg){	int i, j;	u8 type = cfg->type_status & IPR_PATH_CFG_TYPE_MASK;	u8 status = cfg->type_status & IPR_PATH_CFG_STATUS_MASK;	if (type == IPR_PATH_CFG_NOT_EXIST)		return;	for (i = 0; i < ARRAY_SIZE(path_type_desc); i++) {		if (path_type_desc[i].type != type)			continue;		for (j = 0; j < ARRAY_SIZE(path_status_desc); j++) {			if (path_status_desc[j].status != status)				continue;			if (type == IPR_PATH_CFG_IOA_PORT) {				ipr_hcam_err(hostrcb, "%s %s: Phy=%d, Link rate=%s, WWN=%08X%08X\n",					     path_status_desc[j].desc, path_type_desc[i].desc,					     cfg->phy, link_rate[cfg->link_rate & IPR_PHY_LINK_RATE_MASK],					     be32_to_cpu(cfg->wwid[0]), be32_to_cpu(cfg->wwid[1]));			} else {				if (cfg->cascaded_expander == 0xff && cfg->phy == 0xff) {					ipr_hcam_err(hostrcb, "%s %s: Link rate=%s, WWN=%08X%08X\n",						     path_status_desc[j].desc, path_type_desc[i].desc,						     link_rate[cfg->link_rate & IPR_PHY_LINK_RATE_MASK],						     be32_to_cpu(cfg->wwid[0]), be32_to_cpu(cfg->wwid[1]));				} else if (cfg->cascaded_expander == 0xff) {					ipr_hcam_err(hostrcb, "%s %s: Phy=%d, Link rate=%s, "						     "WWN=%08X%08X\n", path_status_desc[j].desc,						     path_type_desc[i].desc, cfg->phy,						     link_rate[cfg->link_rate & IPR_PHY_LINK_RATE_MASK],						     be32_to_cpu(cfg->wwid[0]), be32_to_cpu(cfg->wwid[1]));				} else if (cfg->phy == 0xff) {					ipr_hcam_err(hostrcb, "%s %s: Cascade=%d, Link rate=%s, "						     "WWN=%08X%08X\n", path_status_desc[j].desc,						     path_type_desc[i].desc, cfg->cascaded_expander,						     link_rate[cfg->link_rate & IPR_PHY_LINK_RATE_MASK],						     be32_to_cpu(cfg->wwid[0]), be32_to_cpu(cfg->wwid[1]));				} else {					ipr_hcam_err(hostrcb, "%s %s: Cascade=%d, Phy=%d, Link rate=%s "						     "WWN=%08X%08X\n", path_status_desc[j].desc,						     path_type_desc[i].desc, cfg->cascaded_expander, cfg->phy,						     link_rate[cfg->link_rate & IPR_PHY_LINK_RATE_MASK],						     be32_to_cpu(cfg->wwid[0]), be32_to_cpu(cfg->wwid[1]));				}			}			return;		}	}	ipr_hcam_err(hostrcb, "Path element=%02X: Cascade=%d Phy=%d Link rate=%s "		     "WWN=%08X%08X\n", cfg->type_status, cfg->cascaded_expander, cfg->phy,		     link_rate[cfg->link_rate & IPR_PHY_LINK_RATE_MASK],		     be32_to_cpu(cfg->wwid[0]), be32_to_cpu(cfg->wwid[1]));}/** * ipr_log_fabric_error - Log a fabric error. * @ioa_cfg:	ioa config struct * @hostrcb:	hostrcb struct * * Return value: * 	none **/static void ipr_log_fabric_error(struct ipr_ioa_cfg *ioa_cfg,				 struct ipr_hostrcb *hostrcb){	struct ipr_hostrcb_type_20_error *error;	struct ipr_hostrcb_fabric_desc *fabric;	struct ipr_hostrcb_config_element *cfg;	int i, add_len;	error = &hostrcb->hcam.u.error.u.type_20_error;	error->failure_reason[sizeof(error->failure_reason) - 1] = '\0';	ipr_hcam_err(hostrcb, "%s\n", error->failure_reason);	add_len = be32_to_cpu(hostrcb->hcam.length) -		(offsetof(struct ipr_hostrcb_error, u) +		 offsetof(struct ipr_hostrcb_type_20_error, desc));	for (i = 0, fabric = error->desc; i < error->num_entries; i++) {		ipr_log_fabric_path(hostrcb, fabric);		for_each_fabric_cfg(fabric, cfg)			ipr_log_path_elem(hostrcb, cfg);		add_len -= be16_to_cpu(fabric->length);		fabric = (struct ipr_hostrcb_fabric_desc *)			((unsigned long)fabric + be16_to_cpu(fabric->length));	}	ipr_log_hex_data(ioa_cfg, (u32 *)fabric, add_len);}/** * ipr_log_generic_error - Log an adapter error. * @ioa_cfg:	ioa config struct * @hostrcb:	hostrcb struct * * Return value: * 	none **/static void ipr_log_generic_error(struct ipr_ioa_cfg *ioa_cfg,				  struct ipr_hostrcb *hostrcb){	ipr_log_hex_data(ioa_cfg, hostrcb->hcam.u.raw.data,			 be32_to_cpu(hostrcb->hcam.length));}/** * ipr_get_error - Find the specfied IOASC in the ipr_error_table. * @ioasc:	IOASC * * This function will return the index of into the ipr_error_table * for the specified IOASC. If the IOASC is not in the table, * 0 will be returned, which points to the entry used for unknown errors. * * Return value: * 	index into the ipr_error_table **/static u32 ipr_get_error(u32 ioasc){	int i;	for (i = 0; i < ARRAY_SIZE(ipr_error_table); i++)		if (ipr_error_table[i].ioasc == (ioasc & IPR_IOASC_IOASC_MASK))			return i;	return 0;}/** * ipr_handle_log_data - Log an adapter error. * @ioa_cfg:	ioa config struct * @hostrcb:	hostrcb struct * * This function logs an adapter error to the system. * * Return value: * 	none **/static void ipr_handle_log_data(struct ipr_ioa_cfg *ioa_cfg,				struct ipr_hostrcb *hostrcb){	u32 ioasc;	int error_index;	if (hostrcb->hcam.notify_type != IPR_HOST_RCB_NOTIF_TYPE_ERROR_LOG_ENTRY)		return;	if (hostrcb->hcam.notifications_lost == IPR_HOST_RCB_NOTIFICATIONS_LOST)		dev_err(&ioa_cfg->pdev->dev, "Error notifications lost\n");	ioasc = be32_to_cpu(hostrcb->hcam.u.error.failing_dev_ioasc);	if (ioasc == IPR_IOASC_BUS_WAS_RESET ||	    ioasc == IPR_IOASC_BUS_WAS_RESET_BY_OTHER) {		/* Tell the midlayer we had a bus reset so it will handle the UA properly */		scsi_report_bus_reset(ioa_cfg->host,				      hostrcb->hcam.u.error.failing_dev_res_addr.bus);	}	error_index = ipr_get_error(ioasc);	if (!ipr_error_table[error_index].log_hcam)		return;	ipr_hcam_err(hostrcb, "%s\n", ipr_error_table[error_index].error);	/* Set indication we have logged an error */	ioa_cfg->errors_logged++;	if (ioa_cfg->log_level < ipr_error_table[error_index].log_hcam)		return;	if (be32_to_cpu(hostrcb->hcam.length) > sizeof(hostrcb->hcam.u.raw))		hostrcb->hcam.length = cpu_to_be32(sizeof(hostrcb->hcam.u.raw));	switch (hostrcb->hcam.overlay_id) {	case IPR_HOST_RCB_OVERLAY_ID_2:		ipr_log_cache_error(ioa_cfg, hostrcb);		break;	case IPR_HOST_RCB_OVERLAY_ID_3:		ipr_log_config_error(ioa_cfg, hostrcb);		break;	case IPR_HOST_RCB_OVERLAY_ID_4:	case IPR_HOST_RCB_OVERLAY_ID_6:		ipr_log_array_error(ioa_cfg, hostrcb);		break;	case IPR_HOST_RCB_OVERLAY_ID_7:		ipr_log_dual_ioa_error(ioa_cfg, hostrcb);		break;	case IPR_HOST_RCB_OVERLAY_ID_12:		ipr_log_enhanced_cache_error(ioa_cfg, hostrcb);		break;	case IPR_HOST_RCB_OVERLAY_ID_13:		ipr_log_enhanced_config_error(ioa_cfg, hostrcb);		break;	case IPR_HOST_RCB_OVERLAY_ID_14:	case IPR_HOST_RCB_OVERLAY_ID_16:		ipr_log_enhanced_array_error(ioa_cfg, hostrcb);		break;	case IPR_HOST_RCB_OVERLAY_ID_17:		ipr_log_enhanced_dual_ioa_error(ioa_cfg, hostrcb);		break;	case IPR_HOST_RCB_OVERLAY_ID_20:		ipr_log_fabric_error(ioa_cfg, hostrcb);		break;	case IPR_HOST_RCB_OVERLAY_ID_1:	case IPR_HOST_RCB_OVERLAY_ID_DEFAULT:	default:		ipr_log_generic_error(ioa_cfg, hostrcb);		break;	}}/** * ipr_process_error - Op done function for an adapter error log. * @ipr_cmd:	ipr command struct * * This function is the op done function for an error log host * controlled async from the adapter. It will log the error and * send the HCAM back to the adapter. * * Return value: * 	none **/static void ipr_process_error(struct ipr_cmnd *ipr_cmd){	struct ipr_ioa_cfg *ioa_cfg = ipr_cmd->ioa_cfg;	struct ipr_hostrcb *hostrcb = ipr_cmd->u.hostrcb;	u32 ioasc = be32_to_cpu(ipr_cmd->ioasa.ioasc);	u32 fd_ioasc = be32_to_cpu(hostrcb->hcam.u.error.failing_dev_ioasc);	list_del(&hostrcb->queue);	list_add_tail(&ipr_cmd->queue, &ioa_cfg->free_q);	if (!ioasc) {		ipr_handle_log_data(ioa_cfg, hostrcb);		if (fd_ioasc == IPR_IOASC_NR_IOA_RESET_REQUIRED)			ipr_initiate_ioa_reset(ioa_cfg, IPR_SHUTDOWN_ABBREV);	} else if (ioasc != IPR_IOASC_IOA_WAS_RESET) {		dev_err(&ioa_cfg->pdev->dev,			"Host RCB failed with IOASC: 0x%08X\n", ioasc);	}	ipr_send_hcam(ioa_cfg, IPR_HCAM_CDB_OP_CODE_LOG_DATA, hostrcb);}

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -