diff options
-rw-r--r-- | drivers/net/ethernet/amd/pds_core/adminq.c | 2 | ||||
-rw-r--r-- | drivers/net/ethernet/amd/pds_core/core.c | 32 | ||||
-rw-r--r-- | drivers/net/ethernet/amd/pds_core/core.h | 3 | ||||
-rw-r--r-- | include/linux/pds/pds_common.h | 2 |
4 files changed, 39 insertions, 0 deletions
diff --git a/drivers/net/ethernet/amd/pds_core/adminq.c b/drivers/net/ethernet/amd/pds_core/adminq.c index fb2ba3f62480..045fe133f6ee 100644 --- a/drivers/net/ethernet/amd/pds_core/adminq.c +++ b/drivers/net/ethernet/amd/pds_core/adminq.c @@ -29,11 +29,13 @@ static int pdsc_process_notifyq(struct pdsc_qcq *qcq) case PDS_EVENT_LINK_CHANGE: dev_info(pdsc->dev, "NotifyQ LINK_CHANGE ecode %d eid %lld\n", ecode, eid); + pdsc_notify(PDS_EVENT_LINK_CHANGE, comp); break; case PDS_EVENT_RESET: dev_info(pdsc->dev, "NotifyQ RESET ecode %d eid %lld\n", ecode, eid); + pdsc_notify(PDS_EVENT_RESET, comp); break; case PDS_EVENT_XCVR: diff --git a/drivers/net/ethernet/amd/pds_core/core.c b/drivers/net/ethernet/amd/pds_core/core.c index b2fca3b99f02..483a070d96fa 100644 --- a/drivers/net/ethernet/amd/pds_core/core.c +++ b/drivers/net/ethernet/amd/pds_core/core.c @@ -6,6 +6,25 @@ #include "core.h" +static BLOCKING_NOTIFIER_HEAD(pds_notify_chain); + +int pdsc_register_notify(struct notifier_block *nb) +{ + return blocking_notifier_chain_register(&pds_notify_chain, nb); +} +EXPORT_SYMBOL_GPL(pdsc_register_notify); + +void pdsc_unregister_notify(struct notifier_block *nb) +{ + blocking_notifier_chain_unregister(&pds_notify_chain, nb); +} +EXPORT_SYMBOL_GPL(pdsc_unregister_notify); + +void pdsc_notify(unsigned long event, void *data) +{ + blocking_notifier_call_chain(&pds_notify_chain, event, data); +} + void pdsc_intr_free(struct pdsc *pdsc, int index) { struct pdsc_intr_info *intr_info; @@ -494,12 +513,19 @@ void pdsc_stop(struct pdsc *pdsc) static void pdsc_fw_down(struct pdsc *pdsc) { + union pds_core_notifyq_comp reset_event = { + .reset.ecode = cpu_to_le16(PDS_EVENT_RESET), + .reset.state = 0, + }; + if (test_and_set_bit(PDSC_S_FW_DEAD, &pdsc->state)) { dev_err(pdsc->dev, "%s: already happening\n", __func__); return; } + /* Notify clients of fw_down */ devlink_health_report(pdsc->fw_reporter, "FW down reported", pdsc); + pdsc_notify(PDS_EVENT_RESET, &reset_event); pdsc_stop(pdsc); pdsc_teardown(pdsc, PDSC_TEARDOWN_RECOVERY); @@ -507,6 +533,10 @@ static void pdsc_fw_down(struct pdsc *pdsc) static void pdsc_fw_up(struct pdsc *pdsc) { + union pds_core_notifyq_comp reset_event = { + .reset.ecode = cpu_to_le16(PDS_EVENT_RESET), + .reset.state = 1, + }; int err; if (!test_bit(PDSC_S_FW_DEAD, &pdsc->state)) { @@ -522,9 +552,11 @@ static void pdsc_fw_up(struct pdsc *pdsc) if (err) goto err_out; + /* Notify clients of fw_up */ pdsc->fw_recoveries++; devlink_health_reporter_state_update(pdsc->fw_reporter, DEVLINK_HEALTH_REPORTER_STATE_HEALTHY); + pdsc_notify(PDS_EVENT_RESET, &reset_event); return; diff --git a/drivers/net/ethernet/amd/pds_core/core.h b/drivers/net/ethernet/amd/pds_core/core.h index 9e01a9ee6868..e545fafc4819 100644 --- a/drivers/net/ethernet/amd/pds_core/core.h +++ b/drivers/net/ethernet/amd/pds_core/core.h @@ -297,6 +297,9 @@ int pdsc_start(struct pdsc *pdsc); void pdsc_stop(struct pdsc *pdsc); void pdsc_health_thread(struct work_struct *work); +int pdsc_register_notify(struct notifier_block *nb); +void pdsc_unregister_notify(struct notifier_block *nb); +void pdsc_notify(unsigned long event, void *data); int pdsc_auxbus_dev_add(struct pdsc *cf, struct pdsc *pf); int pdsc_auxbus_dev_del(struct pdsc *cf, struct pdsc *pf); diff --git a/include/linux/pds/pds_common.h b/include/linux/pds/pds_common.h index 4b37675fde3e..060331486d50 100644 --- a/include/linux/pds/pds_common.h +++ b/include/linux/pds/pds_common.h @@ -60,6 +60,8 @@ enum pds_core_logical_qtype { PDS_CORE_QTYPE_MAX = 16 /* don't change - used in struct size */ }; +int pdsc_register_notify(struct notifier_block *nb); +void pdsc_unregister_notify(struct notifier_block *nb); void *pdsc_get_pf_struct(struct pci_dev *vf_pdev); int pds_client_register(struct pci_dev *pf_pdev, char *devname); int pds_client_unregister(struct pci_dev *pf_pdev, u16 client_id); |