On Mon, Mar 01, 2021 at 05:25:09PM +0100, Loic Poulain wrote: > The wake_db register presence is highly speculative and can fuze MHI > devices. Indeed, currently the wake_db register address is defined at > entry 127 of the 'Channel doorbell array', thus writing to this address > is equivalent to ringing the doorbell for channel 127, causing trouble > with some device that get an unexpected channel 127 doorbell interrupt. > what are those "some" devices? > This change fixes that issue by setting wake get/put as no-op for > pci_generic devices. The wake device sideband mechanism seems really > specific to each device, and is AFAIK no defined by the MHI spec. > s/no/not > It also removes zeroing initialization of wake_db register during MMIO > initialization, the register being set via wake_get/put accessors few > cycles later during M0 transition. > IIUC, the DEVICE_WAKE specified in the MHI spec corresponds to the wake doorbell register. But in some cases, this rather happens to be a #WAKE sideband GPIO as in PCIe. > Signed-off-by: Loic Poulain <loic.poulain@xxxxxxxxxx> > --- > drivers/bus/mhi/core/init.c | 2 -- > drivers/bus/mhi/pci_generic.c | 18 ++++++++++++++++++ > 2 files changed, 18 insertions(+), 2 deletions(-) > > diff --git a/drivers/bus/mhi/core/init.c b/drivers/bus/mhi/core/init.c > index 2159dbc..32eb90f 100644 > --- a/drivers/bus/mhi/core/init.c > +++ b/drivers/bus/mhi/core/init.c > @@ -510,8 +510,6 @@ int mhi_init_mmio(struct mhi_controller *mhi_cntrl) > > /* Setup wake db */ > mhi_cntrl->wake_db = base + val + (8 * MHI_DEV_WAKE_DB); > - mhi_write_reg(mhi_cntrl, mhi_cntrl->wake_db, 4, 0); > - mhi_write_reg(mhi_cntrl, mhi_cntrl->wake_db, 0, 0); I need comment from Hemant/Bhaumik on this change since I don't exactly know if this is really required or not. Thanks, Mani > mhi_cntrl->wake_set = false; > > /* Setup channel db address for each channel in tre_ring */ > diff --git a/drivers/bus/mhi/pci_generic.c b/drivers/bus/mhi/pci_generic.c > index 87bab93..8423293 100644 > --- a/drivers/bus/mhi/pci_generic.c > +++ b/drivers/bus/mhi/pci_generic.c > @@ -312,6 +312,21 @@ static void mhi_pci_status_cb(struct mhi_controller *mhi_cntrl, > } > } > > +static void mhi_pci_wake_get_nop(struct mhi_controller *mhi_cntrl, bool force) > +{ > + /* no-op */ > +} > + > +static void mhi_pci_wake_put_nop(struct mhi_controller *mhi_cntrl, bool override) > +{ > + /* no-op */ > +} > + > +static void mhi_pci_wake_toggle_nop(struct mhi_controller *mhi_cntrl) > +{ > + /* no-op */ > +} > + > static bool mhi_pci_is_alive(struct mhi_controller *mhi_cntrl) > { > struct pci_dev *pdev = to_pci_dev(mhi_cntrl->cntrl_dev); > @@ -515,6 +530,9 @@ static int mhi_pci_probe(struct pci_dev *pdev, const struct pci_device_id *id) > mhi_cntrl->status_cb = mhi_pci_status_cb; > mhi_cntrl->runtime_get = mhi_pci_runtime_get; > mhi_cntrl->runtime_put = mhi_pci_runtime_put; > + mhi_cntrl->wake_get = mhi_pci_wake_get_nop; > + mhi_cntrl->wake_put = mhi_pci_wake_put_nop; > + mhi_cntrl->wake_toggle = mhi_pci_wake_toggle_nop; > > err = mhi_pci_claim(mhi_cntrl, info->bar_num, DMA_BIT_MASK(info->dma_data_width)); > if (err) > -- > 2.7.4 >