xref: /dpdk/drivers/common/sfc_efx/base/ef10_intr.c (revision 672386c1e9e1f64f7aa3b1360ad22dc737ea8d72)
15e111ed8SAndrew Rybchenko /* SPDX-License-Identifier: BSD-3-Clause
25e111ed8SAndrew Rybchenko  *
3*672386c1SAndrew Rybchenko  * Copyright(c) 2019-2021 Xilinx, Inc.
45e111ed8SAndrew Rybchenko  * Copyright(c) 2012-2019 Solarflare Communications Inc.
55e111ed8SAndrew Rybchenko  */
65e111ed8SAndrew Rybchenko 
75e111ed8SAndrew Rybchenko #include "efx.h"
85e111ed8SAndrew Rybchenko #include "efx_impl.h"
95e111ed8SAndrew Rybchenko 
105e111ed8SAndrew Rybchenko 
115e111ed8SAndrew Rybchenko #if EFX_OPTS_EF10()
125e111ed8SAndrew Rybchenko 
135e111ed8SAndrew Rybchenko 	__checkReturn	efx_rc_t
ef10_intr_init(__in efx_nic_t * enp,__in efx_intr_type_t type,__in efsys_mem_t * esmp)145e111ed8SAndrew Rybchenko ef10_intr_init(
155e111ed8SAndrew Rybchenko 	__in		efx_nic_t *enp,
165e111ed8SAndrew Rybchenko 	__in		efx_intr_type_t type,
175e111ed8SAndrew Rybchenko 	__in		efsys_mem_t *esmp)
185e111ed8SAndrew Rybchenko {
195e111ed8SAndrew Rybchenko 	_NOTE(ARGUNUSED(enp, type, esmp))
205e111ed8SAndrew Rybchenko 	return (0);
215e111ed8SAndrew Rybchenko }
225e111ed8SAndrew Rybchenko 
235e111ed8SAndrew Rybchenko 
245e111ed8SAndrew Rybchenko 			void
ef10_intr_enable(__in efx_nic_t * enp)255e111ed8SAndrew Rybchenko ef10_intr_enable(
265e111ed8SAndrew Rybchenko 	__in		efx_nic_t *enp)
275e111ed8SAndrew Rybchenko {
285e111ed8SAndrew Rybchenko 	_NOTE(ARGUNUSED(enp))
295e111ed8SAndrew Rybchenko }
305e111ed8SAndrew Rybchenko 
315e111ed8SAndrew Rybchenko 
325e111ed8SAndrew Rybchenko 			void
ef10_intr_disable(__in efx_nic_t * enp)335e111ed8SAndrew Rybchenko ef10_intr_disable(
345e111ed8SAndrew Rybchenko 	__in		efx_nic_t *enp)
355e111ed8SAndrew Rybchenko {
365e111ed8SAndrew Rybchenko 	_NOTE(ARGUNUSED(enp))
375e111ed8SAndrew Rybchenko }
385e111ed8SAndrew Rybchenko 
395e111ed8SAndrew Rybchenko 
405e111ed8SAndrew Rybchenko 			void
ef10_intr_disable_unlocked(__in efx_nic_t * enp)415e111ed8SAndrew Rybchenko ef10_intr_disable_unlocked(
425e111ed8SAndrew Rybchenko 	__in		efx_nic_t *enp)
435e111ed8SAndrew Rybchenko {
445e111ed8SAndrew Rybchenko 	_NOTE(ARGUNUSED(enp))
455e111ed8SAndrew Rybchenko }
465e111ed8SAndrew Rybchenko 
475e111ed8SAndrew Rybchenko 
485e111ed8SAndrew Rybchenko static	__checkReturn	efx_rc_t
efx_mcdi_trigger_interrupt(__in efx_nic_t * enp,__in unsigned int level)495e111ed8SAndrew Rybchenko efx_mcdi_trigger_interrupt(
505e111ed8SAndrew Rybchenko 	__in		efx_nic_t *enp,
515e111ed8SAndrew Rybchenko 	__in		unsigned int level)
525e111ed8SAndrew Rybchenko {
535e111ed8SAndrew Rybchenko 	efx_mcdi_req_t req;
545e111ed8SAndrew Rybchenko 	EFX_MCDI_DECLARE_BUF(payload, MC_CMD_TRIGGER_INTERRUPT_IN_LEN,
555e111ed8SAndrew Rybchenko 		MC_CMD_TRIGGER_INTERRUPT_OUT_LEN);
565e111ed8SAndrew Rybchenko 	efx_rc_t rc;
575e111ed8SAndrew Rybchenko 
585e111ed8SAndrew Rybchenko 	EFSYS_ASSERT(EFX_FAMILY_IS_EF10(enp));
595e111ed8SAndrew Rybchenko 
605e111ed8SAndrew Rybchenko 	if (level >= enp->en_nic_cfg.enc_intr_limit) {
615e111ed8SAndrew Rybchenko 		rc = EINVAL;
625e111ed8SAndrew Rybchenko 		goto fail1;
635e111ed8SAndrew Rybchenko 	}
645e111ed8SAndrew Rybchenko 
655e111ed8SAndrew Rybchenko 	req.emr_cmd = MC_CMD_TRIGGER_INTERRUPT;
665e111ed8SAndrew Rybchenko 	req.emr_in_buf = payload;
675e111ed8SAndrew Rybchenko 	req.emr_in_length = MC_CMD_TRIGGER_INTERRUPT_IN_LEN;
685e111ed8SAndrew Rybchenko 	req.emr_out_buf = payload;
695e111ed8SAndrew Rybchenko 	req.emr_out_length = MC_CMD_TRIGGER_INTERRUPT_OUT_LEN;
705e111ed8SAndrew Rybchenko 
715e111ed8SAndrew Rybchenko 	MCDI_IN_SET_DWORD(req, TRIGGER_INTERRUPT_IN_INTR_LEVEL, level);
725e111ed8SAndrew Rybchenko 
735e111ed8SAndrew Rybchenko 	efx_mcdi_execute(enp, &req);
745e111ed8SAndrew Rybchenko 
755e111ed8SAndrew Rybchenko 	if (req.emr_rc != 0) {
765e111ed8SAndrew Rybchenko 		rc = req.emr_rc;
775e111ed8SAndrew Rybchenko 		goto fail2;
785e111ed8SAndrew Rybchenko 	}
795e111ed8SAndrew Rybchenko 
805e111ed8SAndrew Rybchenko 	return (0);
815e111ed8SAndrew Rybchenko 
825e111ed8SAndrew Rybchenko fail2:
835e111ed8SAndrew Rybchenko 	EFSYS_PROBE(fail2);
845e111ed8SAndrew Rybchenko 
855e111ed8SAndrew Rybchenko fail1:
865e111ed8SAndrew Rybchenko 	EFSYS_PROBE1(fail1, efx_rc_t, rc);
875e111ed8SAndrew Rybchenko 
885e111ed8SAndrew Rybchenko 	return (rc);
895e111ed8SAndrew Rybchenko }
905e111ed8SAndrew Rybchenko 
915e111ed8SAndrew Rybchenko 	__checkReturn	efx_rc_t
ef10_intr_trigger(__in efx_nic_t * enp,__in unsigned int level)925e111ed8SAndrew Rybchenko ef10_intr_trigger(
935e111ed8SAndrew Rybchenko 	__in		efx_nic_t *enp,
945e111ed8SAndrew Rybchenko 	__in		unsigned int level)
955e111ed8SAndrew Rybchenko {
965e111ed8SAndrew Rybchenko 	efx_nic_cfg_t *encp = &(enp->en_nic_cfg);
975e111ed8SAndrew Rybchenko 	efx_rc_t rc;
985e111ed8SAndrew Rybchenko 
995e111ed8SAndrew Rybchenko 	if (encp->enc_bug41750_workaround) {
1005e111ed8SAndrew Rybchenko 		/*
1015e111ed8SAndrew Rybchenko 		 * bug 41750: Test interrupts don't work on Greenport
1025e111ed8SAndrew Rybchenko 		 * bug 50084: Test interrupts don't work on VFs
1035e111ed8SAndrew Rybchenko 		 */
1045e111ed8SAndrew Rybchenko 		rc = ENOTSUP;
1055e111ed8SAndrew Rybchenko 		goto fail1;
1065e111ed8SAndrew Rybchenko 	}
1075e111ed8SAndrew Rybchenko 
1085e111ed8SAndrew Rybchenko 	if ((rc = efx_mcdi_trigger_interrupt(enp, level)) != 0)
1095e111ed8SAndrew Rybchenko 		goto fail2;
1105e111ed8SAndrew Rybchenko 
1115e111ed8SAndrew Rybchenko 	return (0);
1125e111ed8SAndrew Rybchenko 
1135e111ed8SAndrew Rybchenko fail2:
1145e111ed8SAndrew Rybchenko 	EFSYS_PROBE(fail2);
1155e111ed8SAndrew Rybchenko fail1:
1165e111ed8SAndrew Rybchenko 	EFSYS_PROBE1(fail1, efx_rc_t, rc);
1175e111ed8SAndrew Rybchenko 
1185e111ed8SAndrew Rybchenko 	return (rc);
1195e111ed8SAndrew Rybchenko }
1205e111ed8SAndrew Rybchenko 
1215e111ed8SAndrew Rybchenko 			void
ef10_intr_status_line(__in efx_nic_t * enp,__out boolean_t * fatalp,__out uint32_t * qmaskp)1225e111ed8SAndrew Rybchenko ef10_intr_status_line(
1235e111ed8SAndrew Rybchenko 	__in		efx_nic_t *enp,
1245e111ed8SAndrew Rybchenko 	__out		boolean_t *fatalp,
1255e111ed8SAndrew Rybchenko 	__out		uint32_t *qmaskp)
1265e111ed8SAndrew Rybchenko {
1275e111ed8SAndrew Rybchenko 	efx_dword_t dword;
1285e111ed8SAndrew Rybchenko 
1295e111ed8SAndrew Rybchenko 	EFSYS_ASSERT(EFX_FAMILY_IS_EF10(enp));
1305e111ed8SAndrew Rybchenko 
1315e111ed8SAndrew Rybchenko 	/* Read the queue mask and implicitly acknowledge the interrupt. */
1325e111ed8SAndrew Rybchenko 	EFX_BAR_READD(enp, ER_DZ_BIU_INT_ISR_REG, &dword, B_FALSE);
1335e111ed8SAndrew Rybchenko 	*qmaskp = EFX_DWORD_FIELD(dword, EFX_DWORD_0);
1345e111ed8SAndrew Rybchenko 
1355e111ed8SAndrew Rybchenko 	EFSYS_PROBE1(qmask, uint32_t, *qmaskp);
1365e111ed8SAndrew Rybchenko 
1375e111ed8SAndrew Rybchenko 	*fatalp = B_FALSE;
1385e111ed8SAndrew Rybchenko }
1395e111ed8SAndrew Rybchenko 
1405e111ed8SAndrew Rybchenko 			void
ef10_intr_status_message(__in efx_nic_t * enp,__in unsigned int message,__out boolean_t * fatalp)1415e111ed8SAndrew Rybchenko ef10_intr_status_message(
1425e111ed8SAndrew Rybchenko 	__in		efx_nic_t *enp,
1435e111ed8SAndrew Rybchenko 	__in		unsigned int message,
1445e111ed8SAndrew Rybchenko 	__out		boolean_t *fatalp)
1455e111ed8SAndrew Rybchenko {
1465e111ed8SAndrew Rybchenko 	EFSYS_ASSERT(EFX_FAMILY_IS_EF10(enp));
1475e111ed8SAndrew Rybchenko 
1485e111ed8SAndrew Rybchenko 	_NOTE(ARGUNUSED(enp, message))
1495e111ed8SAndrew Rybchenko 
1505e111ed8SAndrew Rybchenko 	/* EF10 fatal errors are reported via events */
1515e111ed8SAndrew Rybchenko 	*fatalp = B_FALSE;
1525e111ed8SAndrew Rybchenko }
1535e111ed8SAndrew Rybchenko 
1545e111ed8SAndrew Rybchenko 			void
ef10_intr_fatal(__in efx_nic_t * enp)1555e111ed8SAndrew Rybchenko ef10_intr_fatal(
1565e111ed8SAndrew Rybchenko 	__in		efx_nic_t *enp)
1575e111ed8SAndrew Rybchenko {
1585e111ed8SAndrew Rybchenko 	/* EF10 fatal errors are reported via events */
1595e111ed8SAndrew Rybchenko 	_NOTE(ARGUNUSED(enp))
1605e111ed8SAndrew Rybchenko }
1615e111ed8SAndrew Rybchenko 
1625e111ed8SAndrew Rybchenko 			void
ef10_intr_fini(__in efx_nic_t * enp)1635e111ed8SAndrew Rybchenko ef10_intr_fini(
1645e111ed8SAndrew Rybchenko 	__in		efx_nic_t *enp)
1655e111ed8SAndrew Rybchenko {
1665e111ed8SAndrew Rybchenko 	_NOTE(ARGUNUSED(enp))
1675e111ed8SAndrew Rybchenko }
1685e111ed8SAndrew Rybchenko 
1695e111ed8SAndrew Rybchenko #endif	/* EFX_OPTS_EF10() */
170