diff options
author | Greg Kroah-Hartman <gregkh@linuxfoundation.org> | 2022-07-11 12:28:46 +0200 |
---|---|---|
committer | Greg Kroah-Hartman <gregkh@linuxfoundation.org> | 2022-07-11 12:28:46 +0200 |
commit | f5fd903b311fc4fa5511259fcf414d866a016c7c (patch) | |
tree | af5e6acfd2fcbad14aadd0fc4dc7f36ebcce70e1 /drivers/bus | |
parent | 14facbc1871ae15404666747b5319c08e04b875a (diff) | |
parent | 2ebb36ea41a7aaabacd03a48292ca91ed0306453 (diff) |
Merge tag 'mhi-for-v5.20' of git://git.kernel.org/pub/scm/linux/kernel/git/mani/mhi into char-misc-next
Manivannan writes:
MHI Host
--------
Support for new modems:
- Quectel EM120 FCCL based on SDX24. This product MHI configuration is same
as EM120R-GL modem.
- Foxconn Cinterion MV31-W. This product is same as the existing MV31-W
modem but sold as a separate product as it uses a different firmware
baseline.
- Foxconn T99W175 based on SDX55.
Core changes:
- Moved the IRQ allocation to MHI controller registration phase. Since the
MHI endpoint may be powered up/down several times during runtime, it
makes sense to move the IRQ allocation to registration phase and just
enable/disable IRQs during endpoint power up/down.
MHI endpoint
------------
Core changes:
- Added error check for dev_set_name()
* tag 'mhi-for-v5.20' of git://git.kernel.org/pub/scm/linux/kernel/git/mani/mhi:
bus: mhi: ep: Check dev_set_name() return value
bus: mhi: host: pci_generic: Add another Foxconn T99W175
bus: mhi: host: Move IRQ allocation to controller registration phase
bus: mhi: host: pci_generic: Add Cinterion MV31-W with new baseline
bus: mhi: host: pci_generic: Add support for Quectel EM120 FCCL modem
Diffstat (limited to 'drivers/bus')
-rw-r--r-- | drivers/bus/mhi/ep/main.c | 11 | ||||
-rw-r--r-- | drivers/bus/mhi/host/init.c | 17 | ||||
-rw-r--r-- | drivers/bus/mhi/host/pci_generic.c | 8 | ||||
-rw-r--r-- | drivers/bus/mhi/host/pm.c | 19 |
4 files changed, 46 insertions, 9 deletions
diff --git a/drivers/bus/mhi/ep/main.c b/drivers/bus/mhi/ep/main.c index 40109a79017a..1dc8a3557a46 100644 --- a/drivers/bus/mhi/ep/main.c +++ b/drivers/bus/mhi/ep/main.c @@ -1242,9 +1242,13 @@ static int mhi_ep_create_device(struct mhi_ep_cntrl *mhi_cntrl, u32 ch_id) /* Channel name is same for both UL and DL */ mhi_dev->name = mhi_chan->name; - dev_set_name(&mhi_dev->dev, "%s_%s", + ret = dev_set_name(&mhi_dev->dev, "%s_%s", dev_name(&mhi_cntrl->mhi_dev->dev), mhi_dev->name); + if (ret) { + put_device(&mhi_dev->dev); + return ret; + } ret = device_add(&mhi_dev->dev); if (ret) @@ -1408,7 +1412,10 @@ int mhi_ep_register_controller(struct mhi_ep_cntrl *mhi_cntrl, goto err_free_irq; } - dev_set_name(&mhi_dev->dev, "mhi_ep%u", mhi_cntrl->index); + ret = dev_set_name(&mhi_dev->dev, "mhi_ep%u", mhi_cntrl->index); + if (ret) + goto err_put_dev; + mhi_dev->name = dev_name(&mhi_dev->dev); mhi_cntrl->mhi_dev = mhi_dev; diff --git a/drivers/bus/mhi/host/init.c b/drivers/bus/mhi/host/init.c index c137d55ccfa0..bf672de35131 100644 --- a/drivers/bus/mhi/host/init.c +++ b/drivers/bus/mhi/host/init.c @@ -178,6 +178,12 @@ int mhi_init_irq_setup(struct mhi_controller *mhi_cntrl) "bhi", mhi_cntrl); if (ret) return ret; + /* + * IRQs should be enabled during mhi_async_power_up(), so disable them explicitly here. + * Due to the use of IRQF_SHARED flag as default while requesting IRQs, we assume that + * IRQ_NOAUTOEN is not applicable. + */ + disable_irq(mhi_cntrl->irq[0]); for (i = 0; i < mhi_cntrl->total_ev_rings; i++, mhi_event++) { if (mhi_event->offload_ev) @@ -199,6 +205,8 @@ int mhi_init_irq_setup(struct mhi_controller *mhi_cntrl) mhi_cntrl->irq[mhi_event->irq], i); goto error_request; } + + disable_irq(mhi_cntrl->irq[mhi_event->irq]); } return 0; @@ -978,12 +986,16 @@ int mhi_register_controller(struct mhi_controller *mhi_cntrl, goto err_destroy_wq; } + ret = mhi_init_irq_setup(mhi_cntrl); + if (ret) + goto err_ida_free; + /* Register controller with MHI bus */ mhi_dev = mhi_alloc_device(mhi_cntrl); if (IS_ERR(mhi_dev)) { dev_err(mhi_cntrl->cntrl_dev, "Failed to allocate MHI device\n"); ret = PTR_ERR(mhi_dev); - goto err_ida_free; + goto error_setup_irq; } mhi_dev->dev_type = MHI_DEVICE_CONTROLLER; @@ -1006,6 +1018,8 @@ int mhi_register_controller(struct mhi_controller *mhi_cntrl, err_release_dev: put_device(&mhi_dev->dev); +error_setup_irq: + mhi_deinit_free_irq(mhi_cntrl); err_ida_free: ida_free(&mhi_controller_ida, mhi_cntrl->index); err_destroy_wq: @@ -1026,6 +1040,7 @@ void mhi_unregister_controller(struct mhi_controller *mhi_cntrl) struct mhi_chan *mhi_chan = mhi_cntrl->mhi_chan; unsigned int i; + mhi_deinit_free_irq(mhi_cntrl); mhi_destroy_debugfs(mhi_cntrl); destroy_workqueue(mhi_cntrl->hiprio_wq); diff --git a/drivers/bus/mhi/host/pci_generic.c b/drivers/bus/mhi/host/pci_generic.c index 841626727f6b..9e545f2a5a26 100644 --- a/drivers/bus/mhi/host/pci_generic.c +++ b/drivers/bus/mhi/host/pci_generic.c @@ -557,6 +557,8 @@ static const struct pci_device_id mhi_pci_id_table[] = { .driver_data = (kernel_ulong_t) &mhi_quectel_em1xx_info }, { PCI_DEVICE(0x1eac, 0x1002), /* EM160R-GL (sdx24) */ .driver_data = (kernel_ulong_t) &mhi_quectel_em1xx_info }, + { PCI_DEVICE(0x1eac, 0x2001), /* EM120R-GL for FCCL (sdx24) */ + .driver_data = (kernel_ulong_t) &mhi_quectel_em1xx_info }, /* T99W175 (sdx55), Both for eSIM and Non-eSIM */ { PCI_DEVICE(PCI_VENDOR_ID_FOXCONN, 0xe0ab), .driver_data = (kernel_ulong_t) &mhi_foxconn_sdx55_info }, @@ -569,6 +571,9 @@ static const struct pci_device_id mhi_pci_id_table[] = { /* T99W175 (sdx55), Based on Qualcomm new baseline */ { PCI_DEVICE(PCI_VENDOR_ID_FOXCONN, 0xe0bf), .driver_data = (kernel_ulong_t) &mhi_foxconn_sdx55_info }, + /* T99W175 (sdx55) */ + { PCI_DEVICE(PCI_VENDOR_ID_FOXCONN, 0xe0c3), + .driver_data = (kernel_ulong_t) &mhi_foxconn_sdx55_info }, /* T99W368 (sdx65) */ { PCI_DEVICE(PCI_VENDOR_ID_FOXCONN, 0xe0d8), .driver_data = (kernel_ulong_t) &mhi_foxconn_sdx65_info }, @@ -578,6 +583,9 @@ static const struct pci_device_id mhi_pci_id_table[] = { /* MV31-W (Cinterion) */ { PCI_DEVICE(0x1269, 0x00b3), .driver_data = (kernel_ulong_t) &mhi_mv31_info }, + /* MV31-W (Cinterion), based on new baseline */ + { PCI_DEVICE(0x1269, 0x00b4), + .driver_data = (kernel_ulong_t) &mhi_mv31_info }, /* MV32-WA (Cinterion) */ { PCI_DEVICE(0x1269, 0x00ba), .driver_data = (kernel_ulong_t) &mhi_mv32_info }, diff --git a/drivers/bus/mhi/host/pm.c b/drivers/bus/mhi/host/pm.c index dc2e8ff3bff2..4a42186ff111 100644 --- a/drivers/bus/mhi/host/pm.c +++ b/drivers/bus/mhi/host/pm.c @@ -500,7 +500,7 @@ static void mhi_pm_disable_transition(struct mhi_controller *mhi_cntrl) for (i = 0; i < mhi_cntrl->total_ev_rings; i++, mhi_event++) { if (mhi_event->offload_ev) continue; - free_irq(mhi_cntrl->irq[mhi_event->irq], mhi_event); + disable_irq(mhi_cntrl->irq[mhi_event->irq]); tasklet_kill(&mhi_event->task); } @@ -1060,12 +1060,13 @@ static void mhi_deassert_dev_wake(struct mhi_controller *mhi_cntrl, int mhi_async_power_up(struct mhi_controller *mhi_cntrl) { + struct mhi_event *mhi_event = mhi_cntrl->mhi_event; enum mhi_state state; enum mhi_ee_type current_ee; enum dev_st_transition next_state; struct device *dev = &mhi_cntrl->mhi_dev->dev; u32 interval_us = 25000; /* poll register field every 25 milliseconds */ - int ret; + int ret, i; dev_info(dev, "Requested to power ON\n"); @@ -1117,9 +1118,15 @@ int mhi_async_power_up(struct mhi_controller *mhi_cntrl) mhi_write_reg(mhi_cntrl, mhi_cntrl->bhi, BHI_INTVEC, 0); } - ret = mhi_init_irq_setup(mhi_cntrl); - if (ret) - goto error_exit; + /* IRQs have been requested during probe, so we just need to enable them. */ + enable_irq(mhi_cntrl->irq[0]); + + for (i = 0; i < mhi_cntrl->total_ev_rings; i++, mhi_event++) { + if (mhi_event->offload_ev) + continue; + + enable_irq(mhi_cntrl->irq[mhi_event->irq]); + } /* Transition to next state */ next_state = MHI_IN_PBL(current_ee) ? @@ -1182,7 +1189,7 @@ void mhi_power_down(struct mhi_controller *mhi_cntrl, bool graceful) /* Wait for shutdown to complete */ flush_work(&mhi_cntrl->st_worker); - free_irq(mhi_cntrl->irq[0], mhi_cntrl); + disable_irq(mhi_cntrl->irq[0]); } EXPORT_SYMBOL_GPL(mhi_power_down); |