xref: /dpdk/drivers/net/qede/qede_main.c (revision c2069af8f36ca85a67174d9b45f2efaab3b5a2cb)
12ea6f76aSRasesh Mody /*
22ea6f76aSRasesh Mody  * Copyright (c) 2016 QLogic Corporation.
32ea6f76aSRasesh Mody  * All rights reserved.
42ea6f76aSRasesh Mody  * www.qlogic.com
52ea6f76aSRasesh Mody  *
62ea6f76aSRasesh Mody  * See LICENSE.qede_pmd for copyright and licensing details.
72ea6f76aSRasesh Mody  */
82ea6f76aSRasesh Mody 
92ea6f76aSRasesh Mody #include <limits.h>
10301ea2d7SRasesh Mody #include <time.h>
1186a2265eSRasesh Mody #include <rte_alarm.h>
122ea6f76aSRasesh Mody 
132ea6f76aSRasesh Mody #include "qede_ethdev.h"
142ea6f76aSRasesh Mody 
1586a2265eSRasesh Mody /* Alarm timeout. */
1686a2265eSRasesh Mody #define QEDE_ALARM_TIMEOUT_US 100000
1786a2265eSRasesh Mody 
182ea6f76aSRasesh Mody /* Global variable to hold absolute path of fw file */
192ea6f76aSRasesh Mody char fw_file[PATH_MAX];
202ea6f76aSRasesh Mody 
212ea6f76aSRasesh Mody const char *QEDE_DEFAULT_FIRMWARE =
22806474a6SRasesh Mody 	"/lib/firmware/qed/qed_init_values-8.18.9.0.bin";
232ea6f76aSRasesh Mody 
242ea6f76aSRasesh Mody static void
252ea6f76aSRasesh Mody qed_update_pf_params(struct ecore_dev *edev, struct ecore_pf_params *params)
262ea6f76aSRasesh Mody {
272ea6f76aSRasesh Mody 	int i;
282ea6f76aSRasesh Mody 
292ea6f76aSRasesh Mody 	for (i = 0; i < edev->num_hwfns; i++) {
302ea6f76aSRasesh Mody 		struct ecore_hwfn *p_hwfn = &edev->hwfns[i];
312ea6f76aSRasesh Mody 		p_hwfn->pf_params = *params;
322ea6f76aSRasesh Mody 	}
332ea6f76aSRasesh Mody }
342ea6f76aSRasesh Mody 
352ea6f76aSRasesh Mody static void qed_init_pci(struct ecore_dev *edev, struct rte_pci_device *pci_dev)
362ea6f76aSRasesh Mody {
372ea6f76aSRasesh Mody 	edev->regview = pci_dev->mem_resource[0].addr;
382ea6f76aSRasesh Mody 	edev->doorbells = pci_dev->mem_resource[2].addr;
392ea6f76aSRasesh Mody }
402ea6f76aSRasesh Mody 
412ea6f76aSRasesh Mody static int
422ea6f76aSRasesh Mody qed_probe(struct ecore_dev *edev, struct rte_pci_device *pci_dev,
432ea6f76aSRasesh Mody 	  enum qed_protocol protocol, uint32_t dp_module,
442ea6f76aSRasesh Mody 	  uint8_t dp_level, bool is_vf)
452ea6f76aSRasesh Mody {
4622d07d93SRasesh Mody 	struct ecore_hw_prepare_params hw_prepare_params;
472ea6f76aSRasesh Mody 	struct qede_dev *qdev = (struct qede_dev *)edev;
482ea6f76aSRasesh Mody 	int rc;
492ea6f76aSRasesh Mody 
502ea6f76aSRasesh Mody 	ecore_init_struct(edev);
51de5588afSRasesh Mody 	edev->drv_type = DRV_ID_DRV_TYPE_LINUX;
522ea6f76aSRasesh Mody 	qdev->protocol = protocol;
53de5588afSRasesh Mody 
54c0bd1181SRasesh Mody 	if (is_vf)
552ea6f76aSRasesh Mody 		edev->b_is_vf = true;
56c0bd1181SRasesh Mody 
572ea6f76aSRasesh Mody 	ecore_init_dp(edev, dp_module, dp_level, NULL);
582ea6f76aSRasesh Mody 	qed_init_pci(edev, pci_dev);
5922d07d93SRasesh Mody 
6022d07d93SRasesh Mody 	memset(&hw_prepare_params, 0, sizeof(hw_prepare_params));
6122d07d93SRasesh Mody 	hw_prepare_params.personality = ECORE_PCI_ETH;
6222d07d93SRasesh Mody 	hw_prepare_params.drv_resc_alloc = false;
6322d07d93SRasesh Mody 	hw_prepare_params.chk_reg_fifo = false;
649e2f08a4SRasesh Mody 	hw_prepare_params.initiate_pf_flr = true;
65f8da0cd6SRasesh Mody 	hw_prepare_params.epoch = (u32)time(NULL);
6622d07d93SRasesh Mody 	rc = ecore_hw_prepare(edev, &hw_prepare_params);
672ea6f76aSRasesh Mody 	if (rc) {
682ea6f76aSRasesh Mody 		DP_ERR(edev, "hw prepare failed\n");
692ea6f76aSRasesh Mody 		return rc;
702ea6f76aSRasesh Mody 	}
712ea6f76aSRasesh Mody 
722ea6f76aSRasesh Mody 	return rc;
732ea6f76aSRasesh Mody }
742ea6f76aSRasesh Mody 
752ea6f76aSRasesh Mody static int qed_nic_setup(struct ecore_dev *edev)
762ea6f76aSRasesh Mody {
772ea6f76aSRasesh Mody 	int rc, i;
782ea6f76aSRasesh Mody 
792ea6f76aSRasesh Mody 	rc = ecore_resc_alloc(edev);
802ea6f76aSRasesh Mody 	if (rc)
812ea6f76aSRasesh Mody 		return rc;
822ea6f76aSRasesh Mody 
832ea6f76aSRasesh Mody 	DP_INFO(edev, "Allocated qed resources\n");
842ea6f76aSRasesh Mody 	ecore_resc_setup(edev);
852ea6f76aSRasesh Mody 
862ea6f76aSRasesh Mody 	return rc;
872ea6f76aSRasesh Mody }
882ea6f76aSRasesh Mody 
8948e8d239SRasesh Mody #ifdef CONFIG_ECORE_ZIPPED_FW
902ea6f76aSRasesh Mody static int qed_alloc_stream_mem(struct ecore_dev *edev)
912ea6f76aSRasesh Mody {
922ea6f76aSRasesh Mody 	int i;
932ea6f76aSRasesh Mody 
942ea6f76aSRasesh Mody 	for_each_hwfn(edev, i) {
952ea6f76aSRasesh Mody 		struct ecore_hwfn *p_hwfn = &edev->hwfns[i];
962ea6f76aSRasesh Mody 
972ea6f76aSRasesh Mody 		p_hwfn->stream = OSAL_ZALLOC(p_hwfn->p_dev, GFP_KERNEL,
982ea6f76aSRasesh Mody 					     sizeof(*p_hwfn->stream));
992ea6f76aSRasesh Mody 		if (!p_hwfn->stream)
1002ea6f76aSRasesh Mody 			return -ENOMEM;
1012ea6f76aSRasesh Mody 	}
1022ea6f76aSRasesh Mody 
1032ea6f76aSRasesh Mody 	return 0;
1042ea6f76aSRasesh Mody }
1052ea6f76aSRasesh Mody 
1062ea6f76aSRasesh Mody static void qed_free_stream_mem(struct ecore_dev *edev)
1072ea6f76aSRasesh Mody {
1082ea6f76aSRasesh Mody 	int i;
1092ea6f76aSRasesh Mody 
1102ea6f76aSRasesh Mody 	for_each_hwfn(edev, i) {
1112ea6f76aSRasesh Mody 		struct ecore_hwfn *p_hwfn = &edev->hwfns[i];
1122ea6f76aSRasesh Mody 
1132ea6f76aSRasesh Mody 		if (!p_hwfn->stream)
1142ea6f76aSRasesh Mody 			return;
1152ea6f76aSRasesh Mody 
1162ea6f76aSRasesh Mody 		OSAL_FREE(p_hwfn->p_dev, p_hwfn->stream);
1172ea6f76aSRasesh Mody 	}
1182ea6f76aSRasesh Mody }
11948e8d239SRasesh Mody #endif
1202ea6f76aSRasesh Mody 
12148e8d239SRasesh Mody #ifdef CONFIG_ECORE_BINARY_FW
1222ea6f76aSRasesh Mody static int qed_load_firmware_data(struct ecore_dev *edev)
1232ea6f76aSRasesh Mody {
1242ea6f76aSRasesh Mody 	int fd;
1252ea6f76aSRasesh Mody 	struct stat st;
1262ea6f76aSRasesh Mody 	const char *fw = RTE_LIBRTE_QEDE_FW;
1272ea6f76aSRasesh Mody 
1282ea6f76aSRasesh Mody 	if (strcmp(fw, "") == 0)
1292ea6f76aSRasesh Mody 		strcpy(fw_file, QEDE_DEFAULT_FIRMWARE);
1302ea6f76aSRasesh Mody 	else
1312ea6f76aSRasesh Mody 		strcpy(fw_file, fw);
1322ea6f76aSRasesh Mody 
1332ea6f76aSRasesh Mody 	fd = open(fw_file, O_RDONLY);
1342ea6f76aSRasesh Mody 	if (fd < 0) {
1352ea6f76aSRasesh Mody 		DP_NOTICE(edev, false, "Can't open firmware file\n");
1362ea6f76aSRasesh Mody 		return -ENOENT;
1372ea6f76aSRasesh Mody 	}
1382ea6f76aSRasesh Mody 
1392ea6f76aSRasesh Mody 	if (fstat(fd, &st) < 0) {
1402ea6f76aSRasesh Mody 		DP_NOTICE(edev, false, "Can't stat firmware file\n");
1417bb4b070SYong Wang 		close(fd);
1422ea6f76aSRasesh Mody 		return -1;
1432ea6f76aSRasesh Mody 	}
1442ea6f76aSRasesh Mody 
1452ea6f76aSRasesh Mody 	edev->firmware = rte_zmalloc("qede_fw", st.st_size,
1462ea6f76aSRasesh Mody 				    RTE_CACHE_LINE_SIZE);
1472ea6f76aSRasesh Mody 	if (!edev->firmware) {
1482ea6f76aSRasesh Mody 		DP_NOTICE(edev, false, "Can't allocate memory for firmware\n");
1492ea6f76aSRasesh Mody 		close(fd);
1502ea6f76aSRasesh Mody 		return -ENOMEM;
1512ea6f76aSRasesh Mody 	}
1522ea6f76aSRasesh Mody 
1532ea6f76aSRasesh Mody 	if (read(fd, edev->firmware, st.st_size) != st.st_size) {
1542ea6f76aSRasesh Mody 		DP_NOTICE(edev, false, "Can't read firmware data\n");
1552ea6f76aSRasesh Mody 		close(fd);
1562ea6f76aSRasesh Mody 		return -1;
1572ea6f76aSRasesh Mody 	}
1582ea6f76aSRasesh Mody 
1592ea6f76aSRasesh Mody 	edev->fw_len = st.st_size;
1602ea6f76aSRasesh Mody 	if (edev->fw_len < 104) {
1612ea6f76aSRasesh Mody 		DP_NOTICE(edev, false, "Invalid fw size: %" PRIu64 "\n",
1622ea6f76aSRasesh Mody 			  edev->fw_len);
1637bb4b070SYong Wang 		close(fd);
1642ea6f76aSRasesh Mody 		return -EINVAL;
1652ea6f76aSRasesh Mody 	}
1662ea6f76aSRasesh Mody 
1677bb4b070SYong Wang 	close(fd);
1682ea6f76aSRasesh Mody 	return 0;
1692ea6f76aSRasesh Mody }
17048e8d239SRasesh Mody #endif
1712ea6f76aSRasesh Mody 
17286a2265eSRasesh Mody static void qed_handle_bulletin_change(struct ecore_hwfn *hwfn)
17386a2265eSRasesh Mody {
17486a2265eSRasesh Mody 	uint8_t mac[ETH_ALEN], is_mac_exist, is_mac_forced;
17586a2265eSRasesh Mody 
17686a2265eSRasesh Mody 	is_mac_exist = ecore_vf_bulletin_get_forced_mac(hwfn, mac,
17786a2265eSRasesh Mody 						      &is_mac_forced);
17886a2265eSRasesh Mody 	if (is_mac_exist && is_mac_forced)
17986a2265eSRasesh Mody 		rte_memcpy(hwfn->hw_info.hw_mac_addr, mac, ETH_ALEN);
18086a2265eSRasesh Mody 
18186a2265eSRasesh Mody 	/* Always update link configuration according to bulletin */
18286a2265eSRasesh Mody 	qed_link_update(hwfn);
18386a2265eSRasesh Mody }
18486a2265eSRasesh Mody 
18586a2265eSRasesh Mody static void qede_vf_task(void *arg)
18686a2265eSRasesh Mody {
18786a2265eSRasesh Mody 	struct ecore_hwfn *p_hwfn = arg;
18886a2265eSRasesh Mody 	uint8_t change = 0;
18986a2265eSRasesh Mody 
19086a2265eSRasesh Mody 	/* Read the bulletin board, and re-schedule the task */
19186a2265eSRasesh Mody 	ecore_vf_read_bulletin(p_hwfn, &change);
19286a2265eSRasesh Mody 	if (change)
19386a2265eSRasesh Mody 		qed_handle_bulletin_change(p_hwfn);
19486a2265eSRasesh Mody 
19586a2265eSRasesh Mody 	rte_eal_alarm_set(QEDE_ALARM_TIMEOUT_US, qede_vf_task, p_hwfn);
19686a2265eSRasesh Mody }
19786a2265eSRasesh Mody 
19886a2265eSRasesh Mody static void qed_start_iov_task(struct ecore_dev *edev)
19986a2265eSRasesh Mody {
20086a2265eSRasesh Mody 	struct ecore_hwfn *p_hwfn;
20186a2265eSRasesh Mody 	int i;
20286a2265eSRasesh Mody 
20386a2265eSRasesh Mody 	for_each_hwfn(edev, i) {
20486a2265eSRasesh Mody 		p_hwfn = &edev->hwfns[i];
20586a2265eSRasesh Mody 		if (!IS_PF(edev))
20686a2265eSRasesh Mody 			rte_eal_alarm_set(QEDE_ALARM_TIMEOUT_US, qede_vf_task,
20786a2265eSRasesh Mody 					  p_hwfn);
20886a2265eSRasesh Mody 	}
20986a2265eSRasesh Mody }
21086a2265eSRasesh Mody 
21186a2265eSRasesh Mody static void qed_stop_iov_task(struct ecore_dev *edev)
21286a2265eSRasesh Mody {
21386a2265eSRasesh Mody 	struct ecore_hwfn *p_hwfn;
21486a2265eSRasesh Mody 	int i;
21586a2265eSRasesh Mody 
21686a2265eSRasesh Mody 	for_each_hwfn(edev, i) {
21786a2265eSRasesh Mody 		p_hwfn = &edev->hwfns[i];
21886a2265eSRasesh Mody 		if (!IS_PF(edev))
21986a2265eSRasesh Mody 			rte_eal_alarm_cancel(qede_vf_task, p_hwfn);
22086a2265eSRasesh Mody 	}
22186a2265eSRasesh Mody }
2222ea6f76aSRasesh Mody static int qed_slowpath_start(struct ecore_dev *edev,
2232ea6f76aSRasesh Mody 			      struct qed_slowpath_params *params)
2242ea6f76aSRasesh Mody {
2252ea6f76aSRasesh Mody 	const uint8_t *data = NULL;
2262ea6f76aSRasesh Mody 	struct ecore_hwfn *hwfn;
2272ea6f76aSRasesh Mody 	struct ecore_mcp_drv_version drv_version;
228301ea2d7SRasesh Mody 	struct ecore_hw_init_params hw_init_params;
2292ea6f76aSRasesh Mody 	struct qede_dev *qdev = (struct qede_dev *)edev;
23062207535SHarish Patil 	struct ecore_ptt *p_ptt;
2312ea6f76aSRasesh Mody 	int rc;
2322ea6f76aSRasesh Mody 
23386a2265eSRasesh Mody 	if (IS_PF(edev)) {
23462207535SHarish Patil #ifdef CONFIG_ECORE_BINARY_FW
2352ea6f76aSRasesh Mody 		rc = qed_load_firmware_data(edev);
2362ea6f76aSRasesh Mody 		if (rc) {
237869c47d0SRasesh Mody 			DP_ERR(edev, "Failed to find fw file %s\n", fw_file);
2382ea6f76aSRasesh Mody 			goto err;
2392ea6f76aSRasesh Mody 		}
2402ea6f76aSRasesh Mody #endif
24162207535SHarish Patil 		hwfn = ECORE_LEADING_HWFN(edev);
24262207535SHarish Patil 		if (edev->num_hwfns == 1) { /* skip aRFS for 100G device */
24362207535SHarish Patil 			p_ptt = ecore_ptt_acquire(hwfn);
24462207535SHarish Patil 			if (p_ptt) {
24562207535SHarish Patil 				ECORE_LEADING_HWFN(edev)->p_arfs_ptt = p_ptt;
24662207535SHarish Patil 			} else {
24762207535SHarish Patil 				DP_ERR(edev, "Failed to acquire PTT for flowdir\n");
24862207535SHarish Patil 				rc = -ENOMEM;
24962207535SHarish Patil 				goto err;
25062207535SHarish Patil 			}
25162207535SHarish Patil 		}
25262207535SHarish Patil 	}
2532ea6f76aSRasesh Mody 
2542ea6f76aSRasesh Mody 	rc = qed_nic_setup(edev);
2552ea6f76aSRasesh Mody 	if (rc)
2562ea6f76aSRasesh Mody 		goto err;
2572ea6f76aSRasesh Mody 
2582ea6f76aSRasesh Mody 	/* set int_coalescing_mode */
2592ea6f76aSRasesh Mody 	edev->int_coalescing_mode = ECORE_COAL_MODE_ENABLE;
2602ea6f76aSRasesh Mody 
26148e8d239SRasesh Mody #ifdef CONFIG_ECORE_ZIPPED_FW
26286a2265eSRasesh Mody 	if (IS_PF(edev)) {
2632ea6f76aSRasesh Mody 		/* Allocate stream for unzipping */
2642ea6f76aSRasesh Mody 		rc = qed_alloc_stream_mem(edev);
2652ea6f76aSRasesh Mody 		if (rc) {
2662ea6f76aSRasesh Mody 			DP_NOTICE(edev, true,
2672ea6f76aSRasesh Mody 			"Failed to allocate stream memory\n");
268*c2069af8SRasesh Mody 			goto err1;
2692ea6f76aSRasesh Mody 		}
27086a2265eSRasesh Mody 	}
27186a2265eSRasesh Mody 
27286a2265eSRasesh Mody 	qed_start_iov_task(edev);
27348e8d239SRasesh Mody #endif
2742ea6f76aSRasesh Mody 
27548e8d239SRasesh Mody #ifdef CONFIG_ECORE_BINARY_FW
27686a2265eSRasesh Mody 	if (IS_PF(edev))
27722d07d93SRasesh Mody 		data = (const uint8_t *)edev->firmware + sizeof(u32);
2782ea6f76aSRasesh Mody #endif
27922d07d93SRasesh Mody 
280301ea2d7SRasesh Mody 	/* Start the slowpath */
281301ea2d7SRasesh Mody 	memset(&hw_init_params, 0, sizeof(hw_init_params));
282301ea2d7SRasesh Mody 	hw_init_params.b_hw_start = true;
283301ea2d7SRasesh Mody 	hw_init_params.int_mode = ECORE_INT_MODE_MSIX;
28462207535SHarish Patil 	hw_init_params.allow_npar_tx_switch = true;
285301ea2d7SRasesh Mody 	hw_init_params.bin_fw_data = data;
2860b6bf70dSRasesh Mody 	hw_init_params.mfw_timeout_val = ECORE_LOAD_REQ_LOCK_TO_DEFAULT;
2870b6bf70dSRasesh Mody 	hw_init_params.avoid_eng_reset = false;
288301ea2d7SRasesh Mody 	rc = ecore_hw_init(edev, &hw_init_params);
2892ea6f76aSRasesh Mody 	if (rc) {
2902ea6f76aSRasesh Mody 		DP_ERR(edev, "ecore_hw_init failed\n");
2912ea6f76aSRasesh Mody 		goto err2;
2922ea6f76aSRasesh Mody 	}
2932ea6f76aSRasesh Mody 
2942ea6f76aSRasesh Mody 	DP_INFO(edev, "HW inited and function started\n");
2952ea6f76aSRasesh Mody 
29686a2265eSRasesh Mody 	if (IS_PF(edev)) {
2972ea6f76aSRasesh Mody 		hwfn = ECORE_LEADING_HWFN(edev);
2982ea6f76aSRasesh Mody 		drv_version.version = (params->drv_major << 24) |
2992ea6f76aSRasesh Mody 		    (params->drv_minor << 16) |
3002ea6f76aSRasesh Mody 		    (params->drv_rev << 8) | (params->drv_eng);
3012ea6f76aSRasesh Mody 		/* TBD: strlcpy() */
3022ea6f76aSRasesh Mody 		strncpy((char *)drv_version.name, (const char *)params->name,
3032ea6f76aSRasesh Mody 			MCP_DRV_VER_STR_SIZE - 4);
3042ea6f76aSRasesh Mody 		rc = ecore_mcp_send_drv_version(hwfn, hwfn->p_main_ptt,
3052ea6f76aSRasesh Mody 						&drv_version);
3062ea6f76aSRasesh Mody 		if (rc) {
3072ea6f76aSRasesh Mody 			DP_NOTICE(edev, true,
3082ea6f76aSRasesh Mody 				  "Failed sending drv version command\n");
309*c2069af8SRasesh Mody 			goto err3;
3102ea6f76aSRasesh Mody 		}
31186a2265eSRasesh Mody 	}
3122ea6f76aSRasesh Mody 
3135cdd769aSRasesh Mody 	ecore_reset_vport_stats(edev);
3145cdd769aSRasesh Mody 
3152ea6f76aSRasesh Mody 	return 0;
3162ea6f76aSRasesh Mody 
317*c2069af8SRasesh Mody err3:
3182ea6f76aSRasesh Mody 	ecore_hw_stop(edev);
3192ea6f76aSRasesh Mody err2:
320*c2069af8SRasesh Mody 	qed_stop_iov_task(edev);
321*c2069af8SRasesh Mody #ifdef CONFIG_ECORE_ZIPPED_FW
322*c2069af8SRasesh Mody 	qed_free_stream_mem(edev);
323*c2069af8SRasesh Mody err1:
324*c2069af8SRasesh Mody #endif
3252ea6f76aSRasesh Mody 	ecore_resc_free(edev);
3262ea6f76aSRasesh Mody err:
32748e8d239SRasesh Mody #ifdef CONFIG_ECORE_BINARY_FW
32886a2265eSRasesh Mody 	if (IS_PF(edev)) {
3292ea6f76aSRasesh Mody 		if (edev->firmware)
3302ea6f76aSRasesh Mody 			rte_free(edev->firmware);
3312ea6f76aSRasesh Mody 		edev->firmware = NULL;
33286a2265eSRasesh Mody 	}
3332ea6f76aSRasesh Mody #endif
33486a2265eSRasesh Mody 	qed_stop_iov_task(edev);
33586a2265eSRasesh Mody 
3362ea6f76aSRasesh Mody 	return rc;
3372ea6f76aSRasesh Mody }
3382ea6f76aSRasesh Mody 
3392ea6f76aSRasesh Mody static int
3402ea6f76aSRasesh Mody qed_fill_dev_info(struct ecore_dev *edev, struct qed_dev_info *dev_info)
3412ea6f76aSRasesh Mody {
3422ea6f76aSRasesh Mody 	struct ecore_ptt *ptt = NULL;
343a7f3cac3SRasesh Mody 	struct ecore_tunnel_info *tun = &edev->tunnel;
3442ea6f76aSRasesh Mody 
3452ea6f76aSRasesh Mody 	memset(dev_info, 0, sizeof(struct qed_dev_info));
346a7f3cac3SRasesh Mody 
347adce1f86SRasesh Mody 	if (tun->vxlan.tun_cls == ECORE_TUNN_CLSS_MAC_VLAN &&
348adce1f86SRasesh Mody 	    tun->vxlan.b_mode_enabled)
349a7f3cac3SRasesh Mody 		dev_info->vxlan_enable = true;
350a7f3cac3SRasesh Mody 
351adce1f86SRasesh Mody 	if (tun->l2_gre.b_mode_enabled && tun->ip_gre.b_mode_enabled &&
352adce1f86SRasesh Mody 	    tun->l2_gre.tun_cls == ECORE_TUNN_CLSS_MAC_VLAN &&
353adce1f86SRasesh Mody 	    tun->ip_gre.tun_cls == ECORE_TUNN_CLSS_MAC_VLAN)
354a7f3cac3SRasesh Mody 		dev_info->gre_enable = true;
355a7f3cac3SRasesh Mody 
356adce1f86SRasesh Mody 	if (tun->l2_geneve.b_mode_enabled && tun->ip_geneve.b_mode_enabled &&
357adce1f86SRasesh Mody 	    tun->l2_geneve.tun_cls == ECORE_TUNN_CLSS_MAC_VLAN &&
358adce1f86SRasesh Mody 	    tun->ip_geneve.tun_cls == ECORE_TUNN_CLSS_MAC_VLAN)
359a7f3cac3SRasesh Mody 		dev_info->geneve_enable = true;
360a7f3cac3SRasesh Mody 
3612ea6f76aSRasesh Mody 	dev_info->num_hwfns = edev->num_hwfns;
3622ea6f76aSRasesh Mody 	dev_info->is_mf_default = IS_MF_DEFAULT(&edev->hwfns[0]);
3634fc58baeSRasesh Mody 	dev_info->mtu = ECORE_LEADING_HWFN(edev)->hw_info.mtu;
3644fc58baeSRasesh Mody 
3652ea6f76aSRasesh Mody 	rte_memcpy(&dev_info->hw_mac, &edev->hwfns[0].hw_info.hw_mac_addr,
3662ea6f76aSRasesh Mody 	       ETHER_ADDR_LEN);
3672ea6f76aSRasesh Mody 
3682ea6f76aSRasesh Mody 	dev_info->fw_major = FW_MAJOR_VERSION;
3692ea6f76aSRasesh Mody 	dev_info->fw_minor = FW_MINOR_VERSION;
3702ea6f76aSRasesh Mody 	dev_info->fw_rev = FW_REVISION_VERSION;
3712ea6f76aSRasesh Mody 	dev_info->fw_eng = FW_ENGINEERING_VERSION;
372738f56d4SRasesh Mody 
373738f56d4SRasesh Mody 	if (IS_PF(edev)) {
3742ea6f76aSRasesh Mody 		dev_info->mf_mode = edev->mf_mode;
3752ea6f76aSRasesh Mody 		dev_info->tx_switching = false;
3762ea6f76aSRasesh Mody 
3772ea6f76aSRasesh Mody 		ptt = ecore_ptt_acquire(ECORE_LEADING_HWFN(edev));
3782ea6f76aSRasesh Mody 		if (ptt) {
37922d07d93SRasesh Mody 			ecore_mcp_get_mfw_ver(ECORE_LEADING_HWFN(edev), ptt,
3802ea6f76aSRasesh Mody 					      &dev_info->mfw_rev, NULL);
3812ea6f76aSRasesh Mody 
3822ea6f76aSRasesh Mody 			ecore_mcp_get_flash_size(ECORE_LEADING_HWFN(edev), ptt,
3832ea6f76aSRasesh Mody 						 &dev_info->flash_size);
3842ea6f76aSRasesh Mody 
3852ea6f76aSRasesh Mody 			/* Workaround to allow PHY-read commands for
3862ea6f76aSRasesh Mody 			 * B0 bringup.
3872ea6f76aSRasesh Mody 			 */
3882ea6f76aSRasesh Mody 			if (ECORE_IS_BB_B0(edev))
3892ea6f76aSRasesh Mody 				dev_info->flash_size = 0xffffffff;
3902ea6f76aSRasesh Mody 
3912ea6f76aSRasesh Mody 			ecore_ptt_release(ECORE_LEADING_HWFN(edev), ptt);
3922ea6f76aSRasesh Mody 		}
39386a2265eSRasesh Mody 	} else {
39422d07d93SRasesh Mody 		ecore_mcp_get_mfw_ver(ECORE_LEADING_HWFN(edev), ptt,
39522d07d93SRasesh Mody 				      &dev_info->mfw_rev, NULL);
39686a2265eSRasesh Mody 	}
3972ea6f76aSRasesh Mody 
3982ea6f76aSRasesh Mody 	return 0;
3992ea6f76aSRasesh Mody }
4002ea6f76aSRasesh Mody 
4012ea6f76aSRasesh Mody int
4022ea6f76aSRasesh Mody qed_fill_eth_dev_info(struct ecore_dev *edev, struct qed_dev_eth_info *info)
4032ea6f76aSRasesh Mody {
4042ea6f76aSRasesh Mody 	struct qede_dev *qdev = (struct qede_dev *)edev;
405f1e4b6c0SHarish Patil 	uint8_t queues = 0;
4062ea6f76aSRasesh Mody 	int i;
4072ea6f76aSRasesh Mody 
4082ea6f76aSRasesh Mody 	memset(info, 0, sizeof(*info));
4092ea6f76aSRasesh Mody 
4102ea6f76aSRasesh Mody 	info->num_tc = 1 /* @@@TBD aelior MULTI_COS */;
4112ea6f76aSRasesh Mody 
41286a2265eSRasesh Mody 	if (IS_PF(edev)) {
413d6cb1753SHarish Patil 		int max_vf_vlan_filters = 0;
414d6cb1753SHarish Patil 
4152ea6f76aSRasesh Mody 		info->num_queues = 0;
4162ea6f76aSRasesh Mody 		for_each_hwfn(edev, i)
4172ea6f76aSRasesh Mody 			info->num_queues +=
4182ea6f76aSRasesh Mody 			FEAT_NUM(&edev->hwfns[i], ECORE_PF_L2_QUE);
4192ea6f76aSRasesh Mody 
420d6cb1753SHarish Patil 		if (edev->p_iov_info)
421d6cb1753SHarish Patil 			max_vf_vlan_filters = edev->p_iov_info->total_vfs *
422d6cb1753SHarish Patil 					      ECORE_ETH_VF_NUM_VLAN_FILTERS;
423d6cb1753SHarish Patil 		info->num_vlan_filters = RESC_NUM(&edev->hwfns[0], ECORE_VLAN) -
424d6cb1753SHarish Patil 					 max_vf_vlan_filters;
4252ea6f76aSRasesh Mody 
4262ea6f76aSRasesh Mody 		rte_memcpy(&info->port_mac, &edev->hwfns[0].hw_info.hw_mac_addr,
4272ea6f76aSRasesh Mody 			   ETHER_ADDR_LEN);
42886a2265eSRasesh Mody 	} else {
429f1e4b6c0SHarish Patil 		ecore_vf_get_num_rxqs(ECORE_LEADING_HWFN(edev),
430f1e4b6c0SHarish Patil 				      &info->num_queues);
431f1e4b6c0SHarish Patil 		if (edev->num_hwfns > 1) {
432f1e4b6c0SHarish Patil 			ecore_vf_get_num_rxqs(&edev->hwfns[1], &queues);
433f1e4b6c0SHarish Patil 			info->num_queues += queues;
434f1e4b6c0SHarish Patil 		}
43586a2265eSRasesh Mody 
43686a2265eSRasesh Mody 		ecore_vf_get_num_vlan_filters(&edev->hwfns[0],
437d6cb1753SHarish Patil 					      (u8 *)&info->num_vlan_filters);
43886a2265eSRasesh Mody 
43986a2265eSRasesh Mody 		ecore_vf_get_port_mac(&edev->hwfns[0],
44086a2265eSRasesh Mody 				      (uint8_t *)&info->port_mac);
4413d4bb441SHarish Patil 
4423d4bb441SHarish Patil 		info->is_legacy = ecore_vf_get_pre_fp_hsi(&edev->hwfns[0]);
44386a2265eSRasesh Mody 	}
4442ea6f76aSRasesh Mody 
4452ea6f76aSRasesh Mody 	qed_fill_dev_info(edev, &info->common);
4462ea6f76aSRasesh Mody 
44786a2265eSRasesh Mody 	if (IS_VF(edev))
44886a2265eSRasesh Mody 		memset(&info->common.hw_mac, 0, ETHER_ADDR_LEN);
44986a2265eSRasesh Mody 
4502ea6f76aSRasesh Mody 	return 0;
4512ea6f76aSRasesh Mody }
4522ea6f76aSRasesh Mody 
453de5588afSRasesh Mody static void qed_set_name(struct ecore_dev *edev, char name[NAME_SIZE])
4542ea6f76aSRasesh Mody {
4552ea6f76aSRasesh Mody 	int i;
4562ea6f76aSRasesh Mody 
4572ea6f76aSRasesh Mody 	rte_memcpy(edev->name, name, NAME_SIZE);
4582ea6f76aSRasesh Mody 	for_each_hwfn(edev, i) {
4592ea6f76aSRasesh Mody 		snprintf(edev->hwfns[i].name, NAME_SIZE, "%s-%d", name, i);
4602ea6f76aSRasesh Mody 	}
4612ea6f76aSRasesh Mody }
4622ea6f76aSRasesh Mody 
4632ea6f76aSRasesh Mody static uint32_t
4642ea6f76aSRasesh Mody qed_sb_init(struct ecore_dev *edev, struct ecore_sb_info *sb_info,
4652ea6f76aSRasesh Mody 	    void *sb_virt_addr, dma_addr_t sb_phy_addr,
4662ea6f76aSRasesh Mody 	    uint16_t sb_id, enum qed_sb_type type)
4672ea6f76aSRasesh Mody {
4682ea6f76aSRasesh Mody 	struct ecore_hwfn *p_hwfn;
4692ea6f76aSRasesh Mody 	int hwfn_index;
4702ea6f76aSRasesh Mody 	uint16_t rel_sb_id;
4712ea6f76aSRasesh Mody 	uint8_t n_hwfns;
4722ea6f76aSRasesh Mody 	uint32_t rc;
4732ea6f76aSRasesh Mody 
4742ea6f76aSRasesh Mody 	/* RoCE uses single engine and CMT uses two engines. When using both
4752ea6f76aSRasesh Mody 	 * we force only a single engine. Storage uses only engine 0 too.
4762ea6f76aSRasesh Mody 	 */
4772ea6f76aSRasesh Mody 	if (type == QED_SB_TYPE_L2_QUEUE)
4782ea6f76aSRasesh Mody 		n_hwfns = edev->num_hwfns;
4792ea6f76aSRasesh Mody 	else
4802ea6f76aSRasesh Mody 		n_hwfns = 1;
4812ea6f76aSRasesh Mody 
4822ea6f76aSRasesh Mody 	hwfn_index = sb_id % n_hwfns;
4832ea6f76aSRasesh Mody 	p_hwfn = &edev->hwfns[hwfn_index];
4842ea6f76aSRasesh Mody 	rel_sb_id = sb_id / n_hwfns;
4852ea6f76aSRasesh Mody 
4862ea6f76aSRasesh Mody 	DP_INFO(edev, "hwfn [%d] <--[init]-- SB %04x [0x%04x upper]\n",
4872ea6f76aSRasesh Mody 		hwfn_index, rel_sb_id, sb_id);
4882ea6f76aSRasesh Mody 
4892ea6f76aSRasesh Mody 	rc = ecore_int_sb_init(p_hwfn, p_hwfn->p_main_ptt, sb_info,
4902ea6f76aSRasesh Mody 			       sb_virt_addr, sb_phy_addr, rel_sb_id);
4912ea6f76aSRasesh Mody 
4922ea6f76aSRasesh Mody 	return rc;
4932ea6f76aSRasesh Mody }
4942ea6f76aSRasesh Mody 
4952ea6f76aSRasesh Mody static void qed_fill_link(struct ecore_hwfn *hwfn,
4962ea6f76aSRasesh Mody 			  struct qed_link_output *if_link)
4972ea6f76aSRasesh Mody {
4982ea6f76aSRasesh Mody 	struct ecore_mcp_link_params params;
4992ea6f76aSRasesh Mody 	struct ecore_mcp_link_state link;
5002ea6f76aSRasesh Mody 	struct ecore_mcp_link_capabilities link_caps;
5012ea6f76aSRasesh Mody 	uint32_t media_type;
5022ea6f76aSRasesh Mody 	uint8_t change = 0;
5032ea6f76aSRasesh Mody 
5042ea6f76aSRasesh Mody 	memset(if_link, 0, sizeof(*if_link));
5052ea6f76aSRasesh Mody 
5062ea6f76aSRasesh Mody 	/* Prepare source inputs */
50786a2265eSRasesh Mody 	if (IS_PF(hwfn->p_dev)) {
5082ea6f76aSRasesh Mody 		rte_memcpy(&params, ecore_mcp_get_link_params(hwfn),
5092ea6f76aSRasesh Mody 		       sizeof(params));
5102ea6f76aSRasesh Mody 		rte_memcpy(&link, ecore_mcp_get_link_state(hwfn), sizeof(link));
5112ea6f76aSRasesh Mody 		rte_memcpy(&link_caps, ecore_mcp_get_link_capabilities(hwfn),
5122ea6f76aSRasesh Mody 		       sizeof(link_caps));
51386a2265eSRasesh Mody 	} else {
51486a2265eSRasesh Mody 		ecore_vf_read_bulletin(hwfn, &change);
51586a2265eSRasesh Mody 		ecore_vf_get_link_params(hwfn, &params);
51686a2265eSRasesh Mody 		ecore_vf_get_link_state(hwfn, &link);
51786a2265eSRasesh Mody 		ecore_vf_get_link_caps(hwfn, &link_caps);
51886a2265eSRasesh Mody 	}
5192ea6f76aSRasesh Mody 
5202ea6f76aSRasesh Mody 	/* Set the link parameters to pass to protocol driver */
5212ea6f76aSRasesh Mody 	if (link.link_up)
5222ea6f76aSRasesh Mody 		if_link->link_up = true;
5232ea6f76aSRasesh Mody 
5242ea6f76aSRasesh Mody 	if (link.link_up)
5252ea6f76aSRasesh Mody 		if_link->speed = link.speed;
5262ea6f76aSRasesh Mody 
5272ea6f76aSRasesh Mody 	if_link->duplex = QEDE_DUPLEX_FULL;
5282ea6f76aSRasesh Mody 
5291ea56b80SHarish Patil 	/* Fill up the native advertised speed cap mask */
5301ea56b80SHarish Patil 	if_link->adv_speed = params.speed.advertised_speeds;
53164c239b7SHarish Patil 
5322ea6f76aSRasesh Mody 	if (params.speed.autoneg)
5332ea6f76aSRasesh Mody 		if_link->supported_caps |= QEDE_SUPPORTED_AUTONEG;
5342ea6f76aSRasesh Mody 
5352ea6f76aSRasesh Mody 	if (params.pause.autoneg || params.pause.forced_rx ||
5362ea6f76aSRasesh Mody 	    params.pause.forced_tx)
5372ea6f76aSRasesh Mody 		if_link->supported_caps |= QEDE_SUPPORTED_PAUSE;
5382ea6f76aSRasesh Mody 
5392ea6f76aSRasesh Mody 	if (params.pause.autoneg)
5402ea6f76aSRasesh Mody 		if_link->pause_config |= QED_LINK_PAUSE_AUTONEG_ENABLE;
5412ea6f76aSRasesh Mody 
5422ea6f76aSRasesh Mody 	if (params.pause.forced_rx)
5432ea6f76aSRasesh Mody 		if_link->pause_config |= QED_LINK_PAUSE_RX_ENABLE;
5442ea6f76aSRasesh Mody 
5452ea6f76aSRasesh Mody 	if (params.pause.forced_tx)
5462ea6f76aSRasesh Mody 		if_link->pause_config |= QED_LINK_PAUSE_TX_ENABLE;
5472ea6f76aSRasesh Mody }
5482ea6f76aSRasesh Mody 
5492ea6f76aSRasesh Mody static void
5502ea6f76aSRasesh Mody qed_get_current_link(struct ecore_dev *edev, struct qed_link_output *if_link)
5512ea6f76aSRasesh Mody {
5522ea6f76aSRasesh Mody 	qed_fill_link(&edev->hwfns[0], if_link);
5532ea6f76aSRasesh Mody 
5542ea6f76aSRasesh Mody #ifdef CONFIG_QED_SRIOV
5552ea6f76aSRasesh Mody 	for_each_hwfn(cdev, i)
5562ea6f76aSRasesh Mody 		qed_inform_vf_link_state(&cdev->hwfns[i]);
5572ea6f76aSRasesh Mody #endif
5582ea6f76aSRasesh Mody }
5592ea6f76aSRasesh Mody 
5602ea6f76aSRasesh Mody static int qed_set_link(struct ecore_dev *edev, struct qed_link_params *params)
5612ea6f76aSRasesh Mody {
5622ea6f76aSRasesh Mody 	struct ecore_hwfn *hwfn;
5632ea6f76aSRasesh Mody 	struct ecore_ptt *ptt;
5642ea6f76aSRasesh Mody 	struct ecore_mcp_link_params *link_params;
5652ea6f76aSRasesh Mody 	int rc;
5662ea6f76aSRasesh Mody 
56786a2265eSRasesh Mody 	if (IS_VF(edev))
56886a2265eSRasesh Mody 		return 0;
56986a2265eSRasesh Mody 
5702ea6f76aSRasesh Mody 	/* The link should be set only once per PF */
5712ea6f76aSRasesh Mody 	hwfn = &edev->hwfns[0];
5722ea6f76aSRasesh Mody 
5732ea6f76aSRasesh Mody 	ptt = ecore_ptt_acquire(hwfn);
5742ea6f76aSRasesh Mody 	if (!ptt)
5752ea6f76aSRasesh Mody 		return -EBUSY;
5762ea6f76aSRasesh Mody 
5772ea6f76aSRasesh Mody 	link_params = ecore_mcp_get_link_params(hwfn);
5782ea6f76aSRasesh Mody 	if (params->override_flags & QED_LINK_OVERRIDE_SPEED_AUTONEG)
5792ea6f76aSRasesh Mody 		link_params->speed.autoneg = params->autoneg;
5802ea6f76aSRasesh Mody 
5812ea6f76aSRasesh Mody 	if (params->override_flags & QED_LINK_OVERRIDE_PAUSE_CONFIG) {
5822ea6f76aSRasesh Mody 		if (params->pause_config & QED_LINK_PAUSE_AUTONEG_ENABLE)
5832ea6f76aSRasesh Mody 			link_params->pause.autoneg = true;
5842ea6f76aSRasesh Mody 		else
5852ea6f76aSRasesh Mody 			link_params->pause.autoneg = false;
5862ea6f76aSRasesh Mody 		if (params->pause_config & QED_LINK_PAUSE_RX_ENABLE)
5872ea6f76aSRasesh Mody 			link_params->pause.forced_rx = true;
5882ea6f76aSRasesh Mody 		else
5892ea6f76aSRasesh Mody 			link_params->pause.forced_rx = false;
5902ea6f76aSRasesh Mody 		if (params->pause_config & QED_LINK_PAUSE_TX_ENABLE)
5912ea6f76aSRasesh Mody 			link_params->pause.forced_tx = true;
5922ea6f76aSRasesh Mody 		else
5932ea6f76aSRasesh Mody 			link_params->pause.forced_tx = false;
5942ea6f76aSRasesh Mody 	}
5952ea6f76aSRasesh Mody 
5962ea6f76aSRasesh Mody 	rc = ecore_mcp_set_link(hwfn, ptt, params->link_up);
5972ea6f76aSRasesh Mody 
5982ea6f76aSRasesh Mody 	ecore_ptt_release(hwfn, ptt);
5992ea6f76aSRasesh Mody 
6002ea6f76aSRasesh Mody 	return rc;
6012ea6f76aSRasesh Mody }
6022ea6f76aSRasesh Mody 
60386a2265eSRasesh Mody void qed_link_update(struct ecore_hwfn *hwfn)
60486a2265eSRasesh Mody {
60586a2265eSRasesh Mody 	struct qed_link_output if_link;
60686a2265eSRasesh Mody 
60786a2265eSRasesh Mody 	qed_fill_link(hwfn, &if_link);
60886a2265eSRasesh Mody }
60986a2265eSRasesh Mody 
6102ea6f76aSRasesh Mody static int qed_drain(struct ecore_dev *edev)
6112ea6f76aSRasesh Mody {
6122ea6f76aSRasesh Mody 	struct ecore_hwfn *hwfn;
6132ea6f76aSRasesh Mody 	struct ecore_ptt *ptt;
6142ea6f76aSRasesh Mody 	int i, rc;
6152ea6f76aSRasesh Mody 
61686a2265eSRasesh Mody 	if (IS_VF(edev))
61786a2265eSRasesh Mody 		return 0;
61886a2265eSRasesh Mody 
6192ea6f76aSRasesh Mody 	for_each_hwfn(edev, i) {
6202ea6f76aSRasesh Mody 		hwfn = &edev->hwfns[i];
6212ea6f76aSRasesh Mody 		ptt = ecore_ptt_acquire(hwfn);
6222ea6f76aSRasesh Mody 		if (!ptt) {
6232ea6f76aSRasesh Mody 			DP_NOTICE(hwfn, true, "Failed to drain NIG; No PTT\n");
6242ea6f76aSRasesh Mody 			return -EBUSY;
6252ea6f76aSRasesh Mody 		}
6262ea6f76aSRasesh Mody 		rc = ecore_mcp_drain(hwfn, ptt);
6272ea6f76aSRasesh Mody 		if (rc)
6282ea6f76aSRasesh Mody 			return rc;
6292ea6f76aSRasesh Mody 		ecore_ptt_release(hwfn, ptt);
6302ea6f76aSRasesh Mody 	}
6312ea6f76aSRasesh Mody 
6322ea6f76aSRasesh Mody 	return 0;
6332ea6f76aSRasesh Mody }
6342ea6f76aSRasesh Mody 
6352ea6f76aSRasesh Mody static int qed_nic_stop(struct ecore_dev *edev)
6362ea6f76aSRasesh Mody {
6372ea6f76aSRasesh Mody 	int i, rc;
6382ea6f76aSRasesh Mody 
6392ea6f76aSRasesh Mody 	rc = ecore_hw_stop(edev);
6402ea6f76aSRasesh Mody 	for (i = 0; i < edev->num_hwfns; i++) {
6412ea6f76aSRasesh Mody 		struct ecore_hwfn *p_hwfn = &edev->hwfns[i];
6422ea6f76aSRasesh Mody 
6432ea6f76aSRasesh Mody 		if (p_hwfn->b_sp_dpc_enabled)
6442ea6f76aSRasesh Mody 			p_hwfn->b_sp_dpc_enabled = false;
6452ea6f76aSRasesh Mody 	}
6462ea6f76aSRasesh Mody 	return rc;
6472ea6f76aSRasesh Mody }
6482ea6f76aSRasesh Mody 
6492ea6f76aSRasesh Mody static int qed_slowpath_stop(struct ecore_dev *edev)
6502ea6f76aSRasesh Mody {
6512ea6f76aSRasesh Mody #ifdef CONFIG_QED_SRIOV
6522ea6f76aSRasesh Mody 	int i;
6532ea6f76aSRasesh Mody #endif
6542ea6f76aSRasesh Mody 
6552ea6f76aSRasesh Mody 	if (!edev)
6562ea6f76aSRasesh Mody 		return -ENODEV;
6572ea6f76aSRasesh Mody 
65886a2265eSRasesh Mody 	if (IS_PF(edev)) {
65948e8d239SRasesh Mody #ifdef CONFIG_ECORE_ZIPPED_FW
6602ea6f76aSRasesh Mody 		qed_free_stream_mem(edev);
66148e8d239SRasesh Mody #endif
6622ea6f76aSRasesh Mody 
66386a2265eSRasesh Mody #ifdef CONFIG_QED_SRIOV
66486a2265eSRasesh Mody 		if (IS_QED_ETH_IF(edev))
66586a2265eSRasesh Mody 			qed_sriov_disable(edev, true);
66686a2265eSRasesh Mody #endif
66786a2265eSRasesh Mody 	}
6682ea6f76aSRasesh Mody 
66939f0eb3bSRasesh Mody 	qed_nic_stop(edev);
67039f0eb3bSRasesh Mody 
67139f0eb3bSRasesh Mody 	ecore_resc_free(edev);
67286a2265eSRasesh Mody 	qed_stop_iov_task(edev);
6732ea6f76aSRasesh Mody 
6742ea6f76aSRasesh Mody 	return 0;
6752ea6f76aSRasesh Mody }
6762ea6f76aSRasesh Mody 
6772ea6f76aSRasesh Mody static void qed_remove(struct ecore_dev *edev)
6782ea6f76aSRasesh Mody {
6792ea6f76aSRasesh Mody 	if (!edev)
6802ea6f76aSRasesh Mody 		return;
6812ea6f76aSRasesh Mody 
6822ea6f76aSRasesh Mody 	ecore_hw_remove(edev);
6832ea6f76aSRasesh Mody }
6842ea6f76aSRasesh Mody 
6853ca097bbSRasesh Mody static int qed_send_drv_state(struct ecore_dev *edev, bool active)
6863ca097bbSRasesh Mody {
6873ca097bbSRasesh Mody 	struct ecore_hwfn *hwfn = ECORE_LEADING_HWFN(edev);
6883ca097bbSRasesh Mody 	struct ecore_ptt *ptt;
6893ca097bbSRasesh Mody 	int status = 0;
6903ca097bbSRasesh Mody 
6913ca097bbSRasesh Mody 	ptt = ecore_ptt_acquire(hwfn);
6923ca097bbSRasesh Mody 	if (!ptt)
6933ca097bbSRasesh Mody 		return -EAGAIN;
6943ca097bbSRasesh Mody 
6953ca097bbSRasesh Mody 	status = ecore_mcp_ov_update_driver_state(hwfn, ptt, active ?
6963ca097bbSRasesh Mody 						  ECORE_OV_DRIVER_STATE_ACTIVE :
6973ca097bbSRasesh Mody 						ECORE_OV_DRIVER_STATE_DISABLED);
6983ca097bbSRasesh Mody 
6993ca097bbSRasesh Mody 	ecore_ptt_release(hwfn, ptt);
7003ca097bbSRasesh Mody 
7013ca097bbSRasesh Mody 	return status;
7023ca097bbSRasesh Mody }
7033ca097bbSRasesh Mody 
7041a998268SRasesh Mody static int qed_get_sb_info(struct ecore_dev *edev, struct ecore_sb_info *sb,
7051a998268SRasesh Mody 			   u16 qid, struct ecore_sb_info_dbg *sb_dbg)
7061a998268SRasesh Mody {
7071a998268SRasesh Mody 	struct ecore_hwfn *hwfn = &edev->hwfns[qid % edev->num_hwfns];
7081a998268SRasesh Mody 	struct ecore_ptt *ptt;
7091a998268SRasesh Mody 	int rc;
7101a998268SRasesh Mody 
7111a998268SRasesh Mody 	if (IS_VF(edev))
7121a998268SRasesh Mody 		return -EINVAL;
7131a998268SRasesh Mody 
7141a998268SRasesh Mody 	ptt = ecore_ptt_acquire(hwfn);
7151a998268SRasesh Mody 	if (!ptt) {
7161a998268SRasesh Mody 		DP_NOTICE(hwfn, true, "Can't acquire PTT\n");
7171a998268SRasesh Mody 		return -EAGAIN;
7181a998268SRasesh Mody 	}
7191a998268SRasesh Mody 
7201a998268SRasesh Mody 	memset(sb_dbg, 0, sizeof(*sb_dbg));
7211a998268SRasesh Mody 	rc = ecore_int_get_sb_dbg(hwfn, ptt, sb, sb_dbg);
7221a998268SRasesh Mody 
7231a998268SRasesh Mody 	ecore_ptt_release(hwfn, ptt);
7241a998268SRasesh Mody 	return rc;
7251a998268SRasesh Mody }
7261a998268SRasesh Mody 
7272ea6f76aSRasesh Mody const struct qed_common_ops qed_common_ops_pass = {
7282ea6f76aSRasesh Mody 	INIT_STRUCT_FIELD(probe, &qed_probe),
7292ea6f76aSRasesh Mody 	INIT_STRUCT_FIELD(update_pf_params, &qed_update_pf_params),
7302ea6f76aSRasesh Mody 	INIT_STRUCT_FIELD(slowpath_start, &qed_slowpath_start),
731de5588afSRasesh Mody 	INIT_STRUCT_FIELD(set_name, &qed_set_name),
7322ea6f76aSRasesh Mody 	INIT_STRUCT_FIELD(chain_alloc, &ecore_chain_alloc),
7332ea6f76aSRasesh Mody 	INIT_STRUCT_FIELD(chain_free, &ecore_chain_free),
7342ea6f76aSRasesh Mody 	INIT_STRUCT_FIELD(sb_init, &qed_sb_init),
7352ea6f76aSRasesh Mody 	INIT_STRUCT_FIELD(get_link, &qed_get_current_link),
7362ea6f76aSRasesh Mody 	INIT_STRUCT_FIELD(set_link, &qed_set_link),
7372ea6f76aSRasesh Mody 	INIT_STRUCT_FIELD(drain, &qed_drain),
7382ea6f76aSRasesh Mody 	INIT_STRUCT_FIELD(slowpath_stop, &qed_slowpath_stop),
7392ea6f76aSRasesh Mody 	INIT_STRUCT_FIELD(remove, &qed_remove),
7403ca097bbSRasesh Mody 	INIT_STRUCT_FIELD(send_drv_state, &qed_send_drv_state),
7412ea6f76aSRasesh Mody };
742