Exemplo n.º 1
0
static void
ecore_dcbx_set_params(struct ecore_dcbx_results *p_data,
		      struct ecore_hwfn *p_hwfn,
		      bool enable, u8 prio, u8 tc,
		      enum dcbx_protocol_type type,
		      enum ecore_pci_personality personality)
{
	/* PF update ramrod data */
	p_data->arr[type].enable = enable;
	p_data->arr[type].priority = prio;
	p_data->arr[type].tc = tc;
	p_data->arr[type].dscp_val = ecore_dcbx_get_dscp_value(p_hwfn, prio);
	if (p_data->arr[type].dscp_val == ECORE_DCBX_DSCP_DISABLED) {
		p_data->arr[type].dscp_enable = false;
		p_data->arr[type].dscp_val = 0;
	} else {
		p_data->arr[type].dscp_enable = true;
	}
	p_data->arr[type].update = UPDATE_DCB_DSCP;

	/* Do not add valn tag 0 when DCB is enabled and port is in UFP mode */
	if (OSAL_TEST_BIT(ECORE_MF_UFP_SPECIFIC, &p_hwfn->p_dev->mf_bits))
		p_data->arr[type].dont_add_vlan0 = true;

	/* QM reconf data */
	if (p_hwfn->hw_info.personality == personality)
		p_hwfn->hw_info.offload_tc = tc;
}
Exemplo n.º 2
0
enum _ecore_status_t ecore_sp_pf_start(struct ecore_hwfn *p_hwfn,
				       struct ecore_ptt *p_ptt,
				       struct ecore_tunnel_info *p_tunn,
				       bool allow_npar_tx_switch)
{
	struct pf_start_ramrod_data *p_ramrod = OSAL_NULL;
	u16 sb = ecore_int_get_sp_sb_id(p_hwfn);
	u8 sb_index = p_hwfn->p_eq->eq_sb_index;
	struct ecore_spq_entry *p_ent = OSAL_NULL;
	struct ecore_sp_init_data init_data;
	enum _ecore_status_t rc = ECORE_NOTIMPL;
	u8 page_cnt;
	u8 i;

	/* update initial eq producer */
	ecore_eq_prod_update(p_hwfn,
			     ecore_chain_get_prod_idx(&p_hwfn->p_eq->chain));

	/* Initialize the SPQ entry for the ramrod */
	OSAL_MEMSET(&init_data, 0, sizeof(init_data));
	init_data.cid = ecore_spq_get_cid(p_hwfn);
	init_data.opaque_fid = p_hwfn->hw_info.opaque_fid;
	init_data.comp_mode = ECORE_SPQ_MODE_EBLOCK;

	rc = ecore_sp_init_request(p_hwfn, &p_ent,
				   COMMON_RAMROD_PF_START,
				   PROTOCOLID_COMMON, &init_data);
	if (rc != ECORE_SUCCESS)
		return rc;

	/* Fill the ramrod data */
	p_ramrod = &p_ent->ramrod.pf_start;
	p_ramrod->event_ring_sb_id = OSAL_CPU_TO_LE16(sb);
	p_ramrod->event_ring_sb_index = sb_index;
	p_ramrod->path_id = ECORE_PATH_ID(p_hwfn);

	/* For easier debugging */
	p_ramrod->dont_log_ramrods = 0;
	p_ramrod->log_type_mask = OSAL_CPU_TO_LE16(0x8f);

	if (OSAL_TEST_BIT(ECORE_MF_OVLAN_CLSS, &p_hwfn->p_dev->mf_bits))
		p_ramrod->mf_mode = MF_OVLAN;
	else
		p_ramrod->mf_mode = MF_NPAR;

	p_ramrod->outer_tag_config.outer_tag.tci =
		OSAL_CPU_TO_LE16(p_hwfn->hw_info.ovlan);
	if (OSAL_TEST_BIT(ECORE_MF_8021Q_TAGGING, &p_hwfn->p_dev->mf_bits)) {
		p_ramrod->outer_tag_config.outer_tag.tpid = ETH_P_8021Q;
	} else if (OSAL_TEST_BIT(ECORE_MF_8021AD_TAGGING,
		 &p_hwfn->p_dev->mf_bits)) {
		p_ramrod->outer_tag_config.outer_tag.tpid = ETH_P_8021AD;
		p_ramrod->outer_tag_config.enable_stag_pri_change = 1;
	}

	p_ramrod->outer_tag_config.pri_map_valid = 1;
	for (i = 0; i < ECORE_MAX_PFC_PRIORITIES; i++)
		p_ramrod->outer_tag_config.inner_to_outer_pri_map[i] = i;

	/* enable_stag_pri_change should be set if port is in BD mode or,
	 * UFP with Host Control mode or, UFP with DCB over base interface.
	 */
	if (OSAL_TEST_BIT(ECORE_MF_UFP_SPECIFIC, &p_hwfn->p_dev->mf_bits)) {
		if ((p_hwfn->ufp_info.pri_type == ECORE_UFP_PRI_OS) ||
		    (p_hwfn->p_dcbx_info->results.dcbx_enabled))
			p_ramrod->outer_tag_config.enable_stag_pri_change = 1;
		else
			p_ramrod->outer_tag_config.enable_stag_pri_change = 0;
	}

	/* Place EQ address in RAMROD */
	DMA_REGPAIR_LE(p_ramrod->event_ring_pbl_addr,
		       p_hwfn->p_eq->chain.pbl_sp.p_phys_table);
	page_cnt = (u8)ecore_chain_get_page_cnt(&p_hwfn->p_eq->chain);
	p_ramrod->event_ring_num_pages = page_cnt;
	DMA_REGPAIR_LE(p_ramrod->consolid_q_pbl_addr,
		       p_hwfn->p_consq->chain.pbl_sp.p_phys_table);

	ecore_tunn_set_pf_start_params(p_hwfn, p_tunn,
				       &p_ramrod->tunnel_config);

	if (OSAL_TEST_BIT(ECORE_MF_INTER_PF_SWITCH,
			  &p_hwfn->p_dev->mf_bits))
		p_ramrod->allow_npar_tx_switching = allow_npar_tx_switch;

	switch (p_hwfn->hw_info.personality) {
	case ECORE_PCI_ETH:
		p_ramrod->personality = PERSONALITY_ETH;
		break;
	default:
		DP_NOTICE(p_hwfn, true, "Unknown personality %d\n",
			 p_hwfn->hw_info.personality);
		p_ramrod->personality = PERSONALITY_ETH;
	}

	if (p_hwfn->p_dev->p_iov_info) {
		struct ecore_hw_sriov_info *p_iov = p_hwfn->p_dev->p_iov_info;

		p_ramrod->base_vf_id = (u8)p_iov->first_vf_in_pf;
		p_ramrod->num_vfs = (u8)p_iov->total_vfs;
	}
	/* @@@TBD - update also the "ROCE_VER_KEY" entries when the FW RoCE HSI
	 * version is available.
	 */
	p_ramrod->hsi_fp_ver.major_ver_arr[ETH_VER_KEY] = ETH_HSI_VER_MAJOR;
	p_ramrod->hsi_fp_ver.minor_ver_arr[ETH_VER_KEY] = ETH_HSI_VER_MINOR;

	DP_VERBOSE(p_hwfn, ECORE_MSG_SPQ,
		   "Setting event_ring_sb [id %04x index %02x], outer_tag.tpid [%d], outer_tag.tci [%d]\n",
		   sb, sb_index, p_ramrod->outer_tag_config.outer_tag.tpid,
		   p_ramrod->outer_tag_config.outer_tag.tci);

	rc = ecore_spq_post(p_hwfn, p_ent, OSAL_NULL);

	if (p_tunn)
		ecore_set_hw_tunn_mode_port(p_hwfn, p_ptt,
					    &p_hwfn->p_dev->tunnel);

	return rc;
}
Exemplo n.º 3
0
/* Parse app TLV's to update TC information in hw_info structure for
 * reconfiguring QM. Get protocol specific data for PF update ramrod command.
 */
static enum _ecore_status_t
ecore_dcbx_process_tlv(struct ecore_hwfn *p_hwfn,
		       struct ecore_dcbx_results *p_data,
		       struct dcbx_app_priority_entry *p_tbl, u32 pri_tc_tbl,
		       int count, u8 dcbx_version)
{
	enum dcbx_protocol_type type;
	bool enable, ieee, eth_tlv;
	u8 tc, priority_map;
	u16 protocol_id;
	u8 priority;
	enum _ecore_status_t rc = ECORE_SUCCESS;
	int i;

	DP_VERBOSE(p_hwfn, ECORE_MSG_DCB,
		   "Num APP entries = %d pri_tc_tbl = 0x%x dcbx_version = %u\n",
		   count, pri_tc_tbl, dcbx_version);

	ieee = (dcbx_version == DCBX_CONFIG_VERSION_IEEE);
	eth_tlv = false;
	/* Parse APP TLV */
	for (i = 0; i < count; i++) {
		protocol_id = GET_MFW_FIELD(p_tbl[i].entry,
					    DCBX_APP_PROTOCOL_ID);
		priority_map = GET_MFW_FIELD(p_tbl[i].entry, DCBX_APP_PRI_MAP);
		DP_VERBOSE(p_hwfn, ECORE_MSG_DCB, "Id = 0x%x pri_map = %u\n",
			   protocol_id, priority_map);
		rc = ecore_dcbx_get_app_priority(priority_map, &priority);
		if (rc == ECORE_INVAL) {
			DP_ERR(p_hwfn, "Invalid priority\n");
			return ECORE_INVAL;
		}

		tc = ECORE_DCBX_PRIO2TC(pri_tc_tbl, priority);
		if (ecore_dcbx_get_app_protocol_type(p_hwfn, p_tbl[i].entry,
						     protocol_id, &type,
						     ieee)) {
			/* ETH always have the enable bit reset, as it gets
			 * vlan information per packet. For other protocols,
			 * should be set according to the dcbx_enabled
			 * indication, but we only got here if there was an
			 * app tlv for the protocol, so dcbx must be enabled.
			 */
			if (type == DCBX_PROTOCOL_ETH) {
				enable = false;
				eth_tlv = true;
			} else {
				enable = true;
			}

			ecore_dcbx_update_app_info(p_data, p_hwfn, enable,
						   priority, tc, type);
		}
	}

	/* If Eth TLV is not detected, use UFP TC as default TC */
	if (OSAL_TEST_BIT(ECORE_MF_UFP_SPECIFIC,
			  &p_hwfn->p_dev->mf_bits) && !eth_tlv)
		p_data->arr[DCBX_PROTOCOL_ETH].tc = p_hwfn->ufp_info.tc;

	/* Update ramrod protocol data and hw_info fields
	 * with default info when corresponding APP TLV's are not detected.
	 * The enabled field has a different logic for ethernet as only for
	 * ethernet dcb should disabled by default, as the information arrives
	 * from the OS (unless an explicit app tlv was present).
	 */
	tc = p_data->arr[DCBX_PROTOCOL_ETH].tc;
	priority = p_data->arr[DCBX_PROTOCOL_ETH].priority;
	for (type = 0; type < DCBX_MAX_PROTOCOL_TYPE; type++) {
		if (p_data->arr[type].update)
			continue;

		enable = (type == DCBX_PROTOCOL_ETH) ? false : !!dcbx_version;
		ecore_dcbx_update_app_info(p_data, p_hwfn, enable,
					   priority, tc, type);
	}

	return ECORE_SUCCESS;
}