Donate to e Foundation | Murena handsets with /e/OS | Own a part of Murena! Learn more

Commit a3f72307 authored by Denis Bolotin's avatar Denis Bolotin Committed by David S. Miller
Browse files

qed*: Utilize FW 8.37.7.0



This patch adds a new qed firmware with fixes and support for new features.

Fixes:
- Fix a rare case of device crash with iWARP, iSCSI or FCoE offload.
- Fix GRE tunneled traffic when iWARP offload is enabled.
- Fix RoCE failure in ib_send_bw when using inline data.
- Fix latency optimization flow for inline WQEs.
- BigBear 100G fix

RDMA:
- Reduce task context size.
- Application page sizes above 2GB support.
- Performance improvements.

ETH:
- Tenant DCB support.
- Replace RSS indirection table update interface.

Misc:
- Debug Tools changes.

Signed-off-by: default avatarDenis Bolotin <denis.bolotin@cavium.com>
Signed-off-by: default avatarAriel Elior <ariel.elior@cavium.com>
Signed-off-by: default avatarDavid S. Miller <davem@davemloft.net>
parent 6ef848ef
Loading
Loading
Loading
Loading
+1 −0
Original line number Diff line number Diff line
@@ -623,6 +623,7 @@ struct qed_hwfn {
	void				*unzip_buf;

	struct dbg_tools_data		dbg_info;
	void				*dbg_user_info;

	/* PWM region specific data */
	u16				wid_count;
+143 −105
Original line number Diff line number Diff line
@@ -3454,6 +3454,7 @@ static u32 qed_grc_dump_iors(struct qed_hwfn *p_hwfn,
			addr = BYTES_TO_DWORDS(storm->sem_fast_mem_addr +
					       SEM_FAST_REG_STORM_REG_FILE) +
			       IOR_SET_OFFSET(set_id);
			if (strlen(buf) > 0)
				buf[strlen(buf) - 1] = '0' + set_id;
			offset += qed_grc_dump_mem(p_hwfn,
						   p_ptt,
@@ -5563,35 +5564,6 @@ struct block_info {
	enum block_id id;
};

struct mcp_trace_format {
	u32 data;
#define MCP_TRACE_FORMAT_MODULE_MASK	0x0000ffff
#define MCP_TRACE_FORMAT_MODULE_SHIFT	0
#define MCP_TRACE_FORMAT_LEVEL_MASK	0x00030000
#define MCP_TRACE_FORMAT_LEVEL_SHIFT	16
#define MCP_TRACE_FORMAT_P1_SIZE_MASK	0x000c0000
#define MCP_TRACE_FORMAT_P1_SIZE_SHIFT	18
#define MCP_TRACE_FORMAT_P2_SIZE_MASK	0x00300000
#define MCP_TRACE_FORMAT_P2_SIZE_SHIFT	20
#define MCP_TRACE_FORMAT_P3_SIZE_MASK	0x00c00000
#define MCP_TRACE_FORMAT_P3_SIZE_SHIFT	22
#define MCP_TRACE_FORMAT_LEN_MASK	0xff000000
#define MCP_TRACE_FORMAT_LEN_SHIFT	24

	char *format_str;
};

/* Meta data structure, generated by a perl script during MFW build. therefore,
 * the structs mcp_trace_meta and mcp_trace_format are duplicated in the perl
 * script.
 */
struct mcp_trace_meta {
	u32 modules_num;
	char **modules;
	u32 formats_num;
	struct mcp_trace_format *formats;
};

/* REG fifo element */
struct reg_fifo_element {
	u64 data;
@@ -5714,6 +5686,20 @@ struct igu_fifo_addr_data {
	enum igu_fifo_addr_types type;
};

struct mcp_trace_meta {
	u32 modules_num;
	char **modules;
	u32 formats_num;
	struct mcp_trace_format *formats;
	bool is_allocated;
};

/* Debug Tools user data */
struct dbg_tools_user_data {
	struct mcp_trace_meta mcp_trace_meta;
	const u32 *mcp_trace_user_meta_buf;
};

/******************************** Constants **********************************/

#define MAX_MSG_LEN				1024
@@ -6137,15 +6123,6 @@ static const struct igu_fifo_addr_data s_igu_fifo_addr_data[] = {

/******************************** Variables **********************************/

/* MCP Trace meta data array - used in case the dump doesn't contain the
 * meta data (e.g. due to no NVRAM access).
 */
static struct user_dbg_array s_mcp_trace_meta_arr = { NULL, 0 };

/* Parsed MCP Trace meta data info, based on MCP trace meta array */
static struct mcp_trace_meta s_mcp_trace_meta;
static bool s_mcp_trace_meta_valid;

/* Temporary buffer, used for print size calculations */
static char s_temp_buf[MAX_MSG_LEN];

@@ -6311,6 +6288,12 @@ static u32 qed_print_section_params(u32 *dump_buf,
	return dump_offset;
}

static struct dbg_tools_user_data *
qed_dbg_get_user_data(struct qed_hwfn *p_hwfn)
{
	return (struct dbg_tools_user_data *)p_hwfn->dbg_user_info;
}

/* Parses the idle check rules and returns the number of characters printed.
 * In case of parsing error, returns 0.
 */
@@ -6570,43 +6553,26 @@ static enum dbg_status qed_parse_idle_chk_dump(u32 *dump_buf,
	return DBG_STATUS_OK;
}

/* Frees the specified MCP Trace meta data */
static void qed_mcp_trace_free_meta(struct qed_hwfn *p_hwfn,
				    struct mcp_trace_meta *meta)
{
	u32 i;

	s_mcp_trace_meta_valid = false;

	/* Release modules */
	if (meta->modules) {
		for (i = 0; i < meta->modules_num; i++)
			kfree(meta->modules[i]);
		kfree(meta->modules);
	}

	/* Release formats */
	if (meta->formats) {
		for (i = 0; i < meta->formats_num; i++)
			kfree(meta->formats[i].format_str);
		kfree(meta->formats);
	}
}

/* Allocates and fills MCP Trace meta data based on the specified meta data
 * dump buffer.
 * Returns debug status code.
 */
static enum dbg_status qed_mcp_trace_alloc_meta(struct qed_hwfn *p_hwfn,
						const u32 *meta_buf,
						struct mcp_trace_meta *meta)
static enum dbg_status
qed_mcp_trace_alloc_meta_data(struct qed_hwfn *p_hwfn,
			      const u32 *meta_buf)
{
	u8 *meta_buf_bytes = (u8 *)meta_buf;
	struct dbg_tools_user_data *dev_user_data;
	u32 offset = 0, signature, i;
	struct mcp_trace_meta *meta;
	u8 *meta_buf_bytes;

	dev_user_data = qed_dbg_get_user_data(p_hwfn);
	meta = &dev_user_data->mcp_trace_meta;
	meta_buf_bytes = (u8 *)meta_buf;

	/* Free the previous meta before loading a new one. */
	if (s_mcp_trace_meta_valid)
		qed_mcp_trace_free_meta(p_hwfn, meta);
	if (meta->is_allocated)
		qed_mcp_trace_free_meta_data(p_hwfn);

	memset(meta, 0, sizeof(*meta));

@@ -6674,7 +6640,7 @@ static enum dbg_status qed_mcp_trace_alloc_meta(struct qed_hwfn *p_hwfn,
				      format_len, format_ptr->format_str);
	}

	s_mcp_trace_meta_valid = true;
	meta->is_allocated = true;
	return DBG_STATUS_OK;
}

@@ -6687,21 +6653,26 @@ static enum dbg_status qed_mcp_trace_alloc_meta(struct qed_hwfn *p_hwfn,
 *               buffer.
 * data_size - size in bytes of data to parse.
 * parsed_buf - destination buffer for parsed data.
 * parsed_bytes - size of parsed data in bytes.
 * parsed_results_bytes - size of parsed data in bytes.
 */
static enum dbg_status qed_parse_mcp_trace_buf(u8 *trace_buf,
static enum dbg_status qed_parse_mcp_trace_buf(struct qed_hwfn *p_hwfn,
					       u8 *trace_buf,
					       u32 trace_buf_size,
					       u32 data_offset,
					       u32 data_size,
					       char *parsed_buf,
					       u32 *parsed_bytes)
					       u32 *parsed_results_bytes)
{
	struct dbg_tools_user_data *dev_user_data;
	struct mcp_trace_meta *meta;
	u32 param_mask, param_shift;
	enum dbg_status status;

	*parsed_bytes = 0;
	dev_user_data = qed_dbg_get_user_data(p_hwfn);
	meta = &dev_user_data->mcp_trace_meta;
	*parsed_results_bytes = 0;

	if (!s_mcp_trace_meta_valid)
	if (!meta->is_allocated)
		return DBG_STATUS_MCP_TRACE_BAD_DATA;

	status = DBG_STATUS_OK;
@@ -6723,7 +6694,7 @@ static enum dbg_status qed_parse_mcp_trace_buf(u8 *trace_buf,
		format_idx = header & MFW_TRACE_EVENTID_MASK;

		/* Skip message if its index doesn't exist in the meta data */
		if (format_idx >= s_mcp_trace_meta.formats_num) {
		if (format_idx >= meta->formats_num) {
			u8 format_size =
				(u8)((header & MFW_TRACE_PRM_SIZE_MASK) >>
				     MFW_TRACE_PRM_SIZE_SHIFT);
@@ -6738,7 +6709,7 @@ static enum dbg_status qed_parse_mcp_trace_buf(u8 *trace_buf,
			continue;
		}

		format_ptr = &s_mcp_trace_meta.formats[format_idx];
		format_ptr = &meta->formats[format_idx];

		for (i = 0,
		     param_mask = MCP_TRACE_FORMAT_P1_SIZE_MASK,
@@ -6783,19 +6754,20 @@ static enum dbg_status qed_parse_mcp_trace_buf(u8 *trace_buf,
			return DBG_STATUS_MCP_TRACE_BAD_DATA;

		/* Print current message to results buffer */
		*parsed_bytes +=
			sprintf(qed_get_buf_ptr(parsed_buf, *parsed_bytes),
		*parsed_results_bytes +=
			sprintf(qed_get_buf_ptr(parsed_buf,
						*parsed_results_bytes),
				"%s %-8s: ",
				s_mcp_trace_level_str[format_level],
				s_mcp_trace_meta.modules[format_module]);
		*parsed_bytes +=
		    sprintf(qed_get_buf_ptr(parsed_buf, *parsed_bytes),
				meta->modules[format_module]);
		*parsed_results_bytes +=
		    sprintf(qed_get_buf_ptr(parsed_buf, *parsed_results_bytes),
			    format_ptr->format_str,
			    params[0], params[1], params[2]);
	}

	/* Add string NULL terminator */
	(*parsed_bytes)++;
	(*parsed_results_bytes)++;

	return status;
}
@@ -6803,24 +6775,25 @@ static enum dbg_status qed_parse_mcp_trace_buf(u8 *trace_buf,
/* Parses an MCP Trace dump buffer.
 * If result_buf is not NULL, the MCP Trace results are printed to it.
 * In any case, the required results buffer size is assigned to
 * parsed_bytes.
 * parsed_results_bytes.
 * The parsing status is returned.
 */
static enum dbg_status qed_parse_mcp_trace_dump(struct qed_hwfn *p_hwfn,
						u32 *dump_buf,
						char *parsed_buf,
						u32 *parsed_bytes)
						char *results_buf,
						u32 *parsed_results_bytes,
						bool free_meta_data)
{
	const char *section_name, *param_name, *param_str_val;
	u32 data_size, trace_data_dwords, trace_meta_dwords;
	u32 offset, results_offset, parsed_buf_bytes;
	u32 offset, results_offset, results_buf_bytes;
	u32 param_num_val, num_section_params;
	struct mcp_trace *trace;
	enum dbg_status status;
	const u32 *meta_buf;
	u8 *trace_buf;

	*parsed_bytes = 0;
	*parsed_results_bytes = 0;

	/* Read global_params section */
	dump_buf += qed_read_section_hdr(dump_buf,
@@ -6831,7 +6804,7 @@ static enum dbg_status qed_parse_mcp_trace_dump(struct qed_hwfn *p_hwfn,
	/* Print global params */
	dump_buf += qed_print_section_params(dump_buf,
					     num_section_params,
					     parsed_buf, &results_offset);
					     results_buf, &results_offset);

	/* Read trace_data section */
	dump_buf += qed_read_section_hdr(dump_buf,
@@ -6846,6 +6819,9 @@ static enum dbg_status qed_parse_mcp_trace_dump(struct qed_hwfn *p_hwfn,

	/* Prepare trace info */
	trace = (struct mcp_trace *)dump_buf;
	if (trace->signature != MFW_TRACE_SIGNATURE || !trace->size)
		return DBG_STATUS_MCP_TRACE_BAD_DATA;

	trace_buf = (u8 *)dump_buf + sizeof(*trace);
	offset = trace->trace_oldest;
	data_size = qed_cyclic_sub(trace->trace_prod, offset, trace->size);
@@ -6865,31 +6841,39 @@ static enum dbg_status qed_parse_mcp_trace_dump(struct qed_hwfn *p_hwfn,
	/* Choose meta data buffer */
	if (!trace_meta_dwords) {
		/* Dump doesn't include meta data */
		if (!s_mcp_trace_meta_arr.ptr)
		struct dbg_tools_user_data *dev_user_data =
			qed_dbg_get_user_data(p_hwfn);

		if (!dev_user_data->mcp_trace_user_meta_buf)
			return DBG_STATUS_MCP_TRACE_NO_META;
		meta_buf = s_mcp_trace_meta_arr.ptr;

		meta_buf = dev_user_data->mcp_trace_user_meta_buf;
	} else {
		/* Dump includes meta data */
		meta_buf = dump_buf;
	}

	/* Allocate meta data memory */
	status = qed_mcp_trace_alloc_meta(p_hwfn, meta_buf, &s_mcp_trace_meta);
	status = qed_mcp_trace_alloc_meta_data(p_hwfn, meta_buf);
	if (status != DBG_STATUS_OK)
		return status;

	status = qed_parse_mcp_trace_buf(trace_buf,
	status = qed_parse_mcp_trace_buf(p_hwfn,
					 trace_buf,
					 trace->size,
					 offset,
					 data_size,
					 parsed_buf ?
					 parsed_buf + results_offset :
					 results_buf ?
					 results_buf + results_offset :
					 NULL,
					 &parsed_buf_bytes);
					 &results_buf_bytes);
	if (status != DBG_STATUS_OK)
		return status;

	*parsed_bytes = results_offset + parsed_buf_bytes;
	if (free_meta_data)
		qed_mcp_trace_free_meta_data(p_hwfn);

	*parsed_results_bytes = results_offset + results_buf_bytes;

	return DBG_STATUS_OK;
}
@@ -7361,6 +7345,16 @@ enum dbg_status qed_dbg_user_set_bin_ptr(const u8 * const bin_ptr)
	return DBG_STATUS_OK;
}

enum dbg_status qed_dbg_alloc_user_data(struct qed_hwfn *p_hwfn)
{
	p_hwfn->dbg_user_info = kzalloc(sizeof(struct dbg_tools_user_data),
					GFP_KERNEL);
	if (!p_hwfn->dbg_user_info)
		return DBG_STATUS_VIRT_MEM_ALLOC_FAILED;

	return DBG_STATUS_OK;
}

const char *qed_dbg_get_status_str(enum dbg_status status)
{
	return (status <
@@ -7397,10 +7391,13 @@ enum dbg_status qed_print_idle_chk_results(struct qed_hwfn *p_hwfn,
				       num_errors, num_warnings);
}

void qed_dbg_mcp_trace_set_meta_data(u32 *data, u32 size)
void qed_dbg_mcp_trace_set_meta_data(struct qed_hwfn *p_hwfn,
				     const u32 *meta_buf)
{
	s_mcp_trace_meta_arr.ptr = data;
	s_mcp_trace_meta_arr.size_in_dwords = size;
	struct dbg_tools_user_data *dev_user_data =
		qed_dbg_get_user_data(p_hwfn);

	dev_user_data->mcp_trace_user_meta_buf = meta_buf;
}

enum dbg_status qed_get_mcp_trace_results_buf_size(struct qed_hwfn *p_hwfn,
@@ -7409,7 +7406,7 @@ enum dbg_status qed_get_mcp_trace_results_buf_size(struct qed_hwfn *p_hwfn,
						   u32 *results_buf_size)
{
	return qed_parse_mcp_trace_dump(p_hwfn,
					dump_buf, NULL, results_buf_size);
					dump_buf, NULL, results_buf_size, true);
}

enum dbg_status qed_print_mcp_trace_results(struct qed_hwfn *p_hwfn,
@@ -7421,20 +7418,61 @@ enum dbg_status qed_print_mcp_trace_results(struct qed_hwfn *p_hwfn,

	return qed_parse_mcp_trace_dump(p_hwfn,
					dump_buf,
					results_buf, &parsed_buf_size);
					results_buf, &parsed_buf_size, true);
}

enum dbg_status qed_print_mcp_trace_line(u8 *dump_buf,
enum dbg_status qed_print_mcp_trace_results_cont(struct qed_hwfn *p_hwfn,
						 u32 *dump_buf,
						 char *results_buf)
{
	u32 parsed_buf_size;

	return qed_parse_mcp_trace_dump(p_hwfn, dump_buf, results_buf,
					&parsed_buf_size, false);
}

enum dbg_status qed_print_mcp_trace_line(struct qed_hwfn *p_hwfn,
					 u8 *dump_buf,
					 u32 num_dumped_bytes,
					 char *results_buf)
{
	u32 parsed_bytes;
	u32 parsed_results_bytes;

	return qed_parse_mcp_trace_buf(dump_buf,
	return qed_parse_mcp_trace_buf(p_hwfn,
				       dump_buf,
				       num_dumped_bytes,
				       0,
				       num_dumped_bytes,
				       results_buf, &parsed_bytes);
				       results_buf, &parsed_results_bytes);
}

/* Frees the specified MCP Trace meta data */
void qed_mcp_trace_free_meta_data(struct qed_hwfn *p_hwfn)
{
	struct dbg_tools_user_data *dev_user_data;
	struct mcp_trace_meta *meta;
	u32 i;

	dev_user_data = qed_dbg_get_user_data(p_hwfn);
	meta = &dev_user_data->mcp_trace_meta;
	if (!meta->is_allocated)
		return;

	/* Release modules */
	if (meta->modules) {
		for (i = 0; i < meta->modules_num; i++)
			kfree(meta->modules[i]);
		kfree(meta->modules);
	}

	/* Release formats */
	if (meta->formats) {
		for (i = 0; i < meta->formats_num; i++)
			kfree(meta->formats[i].format_str);
		kfree(meta->formats);
	}

	meta->is_allocated = false;
}

enum dbg_status qed_get_reg_fifo_results_buf_size(struct qed_hwfn *p_hwfn,
+11 −0
Original line number Diff line number Diff line
@@ -144,6 +144,12 @@ static void qed_qm_info_free(struct qed_hwfn *p_hwfn)
	qm_info->wfq_data = NULL;
}

static void qed_dbg_user_data_free(struct qed_hwfn *p_hwfn)
{
	kfree(p_hwfn->dbg_user_info);
	p_hwfn->dbg_user_info = NULL;
}

void qed_resc_free(struct qed_dev *cdev)
{
	int i;
@@ -183,6 +189,7 @@ void qed_resc_free(struct qed_dev *cdev)
		qed_l2_free(p_hwfn);
		qed_dmae_info_free(p_hwfn);
		qed_dcbx_info_free(p_hwfn);
		qed_dbg_user_data_free(p_hwfn);
	}
}

@@ -1083,6 +1090,10 @@ int qed_resc_alloc(struct qed_dev *cdev)
		rc = qed_dcbx_info_alloc(p_hwfn);
		if (rc)
			goto alloc_err;

		rc = qed_dbg_alloc_user_data(p_hwfn);
		if (rc)
			goto alloc_err;
	}

	cdev->reset_stats = kzalloc(sizeof(*cdev->reset_stats), GFP_KERNEL);
+206 −91

File changed.

Preview size limit exceeded, changes collapsed.

+5 −5
Original line number Diff line number Diff line
@@ -110,7 +110,7 @@

#define FW_MAJOR_VERSION	8
#define FW_MINOR_VERSION        37
#define FW_REVISION_VERSION     2
#define FW_REVISION_VERSION     7
#define FW_ENGINEERING_VERSION	0

/***********************/
@@ -931,12 +931,12 @@ struct db_rdma_dpm_params {
#define DB_RDMA_DPM_PARAMS_WQE_SIZE_SHIFT		16
#define DB_RDMA_DPM_PARAMS_RESERVED0_MASK		0x1
#define DB_RDMA_DPM_PARAMS_RESERVED0_SHIFT		27
#define DB_RDMA_DPM_PARAMS_COMPLETION_FLG_MASK		0x1
#define DB_RDMA_DPM_PARAMS_COMPLETION_FLG_SHIFT		28
#define DB_RDMA_DPM_PARAMS_ACK_REQUEST_MASK		0x1
#define DB_RDMA_DPM_PARAMS_ACK_REQUEST_SHIFT		28
#define DB_RDMA_DPM_PARAMS_S_FLG_MASK			0x1
#define DB_RDMA_DPM_PARAMS_S_FLG_SHIFT			29
#define DB_RDMA_DPM_PARAMS_RESERVED1_MASK		0x1
#define DB_RDMA_DPM_PARAMS_RESERVED1_SHIFT		30
#define DB_RDMA_DPM_PARAMS_COMPLETION_FLG_MASK		0x1
#define DB_RDMA_DPM_PARAMS_COMPLETION_FLG_SHIFT		30
#define DB_RDMA_DPM_PARAMS_CONN_TYPE_IS_IWARP_MASK	0x1
#define DB_RDMA_DPM_PARAMS_CONN_TYPE_IS_IWARP_SHIFT	31
};
Loading