Lines Matching refs:master

267 static inline bool svc_has_quirk(struct svc_i3c_master *master, u32 quirk)  in svc_has_quirk()  argument
269 return (master->drvdata->quirks & quirk); in svc_has_quirk()
272 static inline bool svc_has_daa_corrupt(struct svc_i3c_master *master) in svc_has_daa_corrupt() argument
274 return ((master->drvdata->quirks & SVC_I3C_QUIRK_DAA_CORRUPT) && in svc_has_daa_corrupt()
275 !(master->mctrl_config & in svc_has_daa_corrupt()
279 static inline bool is_events_enabled(struct svc_i3c_master *master, u32 mask) in is_events_enabled() argument
281 return !!(master->enabled_events & mask); in is_events_enabled()
284 static bool svc_i3c_master_error(struct svc_i3c_master *master) in svc_i3c_master_error() argument
288 mstatus = readl(master->regs + SVC_I3C_MSTATUS); in svc_i3c_master_error()
290 merrwarn = readl(master->regs + SVC_I3C_MERRWARN); in svc_i3c_master_error()
291 writel(merrwarn, master->regs + SVC_I3C_MERRWARN); in svc_i3c_master_error()
295 dev_dbg(master->dev, "Warning condition: MSTATUS 0x%08x, MERRWARN 0x%08x\n", in svc_i3c_master_error()
300 dev_err(master->dev, in svc_i3c_master_error()
310 static void svc_i3c_master_enable_interrupts(struct svc_i3c_master *master, u32 mask) in svc_i3c_master_enable_interrupts() argument
312 writel(mask, master->regs + SVC_I3C_MINTSET); in svc_i3c_master_enable_interrupts()
315 static void svc_i3c_master_disable_interrupts(struct svc_i3c_master *master) in svc_i3c_master_disable_interrupts() argument
317 u32 mask = readl(master->regs + SVC_I3C_MINTSET); in svc_i3c_master_disable_interrupts()
319 writel(mask, master->regs + SVC_I3C_MINTCLR); in svc_i3c_master_disable_interrupts()
322 static void svc_i3c_master_clear_merrwarn(struct svc_i3c_master *master) in svc_i3c_master_clear_merrwarn() argument
325 writel(readl(master->regs + SVC_I3C_MERRWARN), in svc_i3c_master_clear_merrwarn()
326 master->regs + SVC_I3C_MERRWARN); in svc_i3c_master_clear_merrwarn()
329 static void svc_i3c_master_flush_fifo(struct svc_i3c_master *master) in svc_i3c_master_flush_fifo() argument
333 master->regs + SVC_I3C_MDATACTRL); in svc_i3c_master_flush_fifo()
336 static void svc_i3c_master_reset_fifo_trigger(struct svc_i3c_master *master) in svc_i3c_master_reset_fifo_trigger() argument
346 writel(reg, master->regs + SVC_I3C_MDATACTRL); in svc_i3c_master_reset_fifo_trigger()
349 static void svc_i3c_master_reset(struct svc_i3c_master *master) in svc_i3c_master_reset() argument
351 svc_i3c_master_clear_merrwarn(master); in svc_i3c_master_reset()
352 svc_i3c_master_reset_fifo_trigger(master); in svc_i3c_master_reset()
353 svc_i3c_master_disable_interrupts(master); in svc_i3c_master_reset()
357 to_svc_i3c_master(struct i3c_master_controller *master) in to_svc_i3c_master() argument
359 return container_of(master, struct svc_i3c_master, base); in to_svc_i3c_master()
364 struct svc_i3c_master *master; in svc_i3c_master_hj_work() local
366 master = container_of(work, struct svc_i3c_master, hj_work); in svc_i3c_master_hj_work()
367 i3c_master_do_daa(&master->base); in svc_i3c_master_hj_work()
371 svc_i3c_master_dev_from_addr(struct svc_i3c_master *master, in svc_i3c_master_dev_from_addr() argument
377 if (master->addrs[i] == ibiaddr) in svc_i3c_master_dev_from_addr()
383 return master->descs[i]; in svc_i3c_master_dev_from_addr()
386 static void svc_i3c_master_emit_stop(struct svc_i3c_master *master) in svc_i3c_master_emit_stop() argument
388 writel(SVC_I3C_MCTRL_REQUEST_STOP, master->regs + SVC_I3C_MCTRL); in svc_i3c_master_emit_stop()
399 static int svc_i3c_master_handle_ibi(struct svc_i3c_master *master, in svc_i3c_master_handle_ibi() argument
416 ret = readl_relaxed_poll_timeout(master->regs + SVC_I3C_MSTATUS, val, in svc_i3c_master_handle_ibi()
419 dev_err(master->dev, "Timeout when polling for COMPLETE\n"); in svc_i3c_master_handle_ibi()
424 while (SVC_I3C_MSTATUS_RXPEND(readl(master->regs + SVC_I3C_MSTATUS)) && in svc_i3c_master_handle_ibi()
426 mdatactrl = readl(master->regs + SVC_I3C_MDATACTRL); in svc_i3c_master_handle_ibi()
428 readsb(master->regs + SVC_I3C_MRDATAB, buf, count); in svc_i3c_master_handle_ibi()
433 master->ibi.tbq_slot = slot; in svc_i3c_master_handle_ibi()
438 static int svc_i3c_master_ack_ibi(struct svc_i3c_master *master, in svc_i3c_master_ack_ibi() argument
450 writel(ibi_ack_nack, master->regs + SVC_I3C_MCTRL); in svc_i3c_master_ack_ibi()
452 return readl_poll_timeout_atomic(master->regs + SVC_I3C_MSTATUS, reg, in svc_i3c_master_ack_ibi()
457 static int svc_i3c_master_nack_ibi(struct svc_i3c_master *master) in svc_i3c_master_nack_ibi() argument
464 master->regs + SVC_I3C_MCTRL); in svc_i3c_master_nack_ibi()
466 ret = readl_poll_timeout_atomic(master->regs + SVC_I3C_MSTATUS, reg, in svc_i3c_master_nack_ibi()
471 static int svc_i3c_master_handle_ibi_won(struct svc_i3c_master *master, u32 mstatus) in svc_i3c_master_handle_ibi_won() argument
478 writel(SVC_I3C_MINT_IBIWON, master->regs + SVC_I3C_MSTATUS); in svc_i3c_master_handle_ibi_won()
484 ret = svc_i3c_master_nack_ibi(master); in svc_i3c_master_handle_ibi_won()
490 static void svc_i3c_master_ibi_isr(struct svc_i3c_master *master) in svc_i3c_master_ibi_isr() argument
506 guard(spinlock)(&master->xferqueue.lock); in svc_i3c_master_ibi_isr()
519 writel(SVC_I3C_MINT_IBIWON, master->regs + SVC_I3C_MSTATUS); in svc_i3c_master_ibi_isr()
539 master->regs + SVC_I3C_MCTRL); in svc_i3c_master_ibi_isr()
542 ret = readl_relaxed_poll_timeout_atomic(master->regs + SVC_I3C_MSTATUS, val, in svc_i3c_master_ibi_isr()
545 dev_err(master->dev, "Timeout when polling for IBIWON\n"); in svc_i3c_master_ibi_isr()
546 svc_i3c_master_emit_stop(master); in svc_i3c_master_ibi_isr()
550 status = readl(master->regs + SVC_I3C_MSTATUS); in svc_i3c_master_ibi_isr()
557 dev = svc_i3c_master_dev_from_addr(master, ibiaddr); in svc_i3c_master_ibi_isr()
558 if (!dev || !is_events_enabled(master, SVC_I3C_EVENT_IBI)) { in svc_i3c_master_ibi_isr()
559 svc_i3c_master_nack_ibi(master); in svc_i3c_master_ibi_isr()
562 svc_i3c_master_ack_ibi(master, true); in svc_i3c_master_ibi_isr()
564 svc_i3c_master_ack_ibi(master, false); in svc_i3c_master_ibi_isr()
565 svc_i3c_master_handle_ibi(master, dev); in svc_i3c_master_ibi_isr()
569 if (is_events_enabled(master, SVC_I3C_EVENT_HOTJOIN)) in svc_i3c_master_ibi_isr()
570 svc_i3c_master_ack_ibi(master, false); in svc_i3c_master_ibi_isr()
572 svc_i3c_master_nack_ibi(master); in svc_i3c_master_ibi_isr()
575 svc_i3c_master_nack_ibi(master); in svc_i3c_master_ibi_isr()
586 if (svc_i3c_master_error(master)) { in svc_i3c_master_ibi_isr()
587 if (master->ibi.tbq_slot) { in svc_i3c_master_ibi_isr()
590 master->ibi.tbq_slot); in svc_i3c_master_ibi_isr()
591 master->ibi.tbq_slot = NULL; in svc_i3c_master_ibi_isr()
594 svc_i3c_master_emit_stop(master); in svc_i3c_master_ibi_isr()
602 svc_i3c_master_emit_stop(master); in svc_i3c_master_ibi_isr()
604 i3c_master_queue_ibi(dev, master->ibi.tbq_slot); in svc_i3c_master_ibi_isr()
605 master->ibi.tbq_slot = NULL; in svc_i3c_master_ibi_isr()
609 svc_i3c_master_emit_stop(master); in svc_i3c_master_ibi_isr()
610 if (is_events_enabled(master, SVC_I3C_EVENT_HOTJOIN)) in svc_i3c_master_ibi_isr()
611 queue_work(master->base.wq, &master->hj_work); in svc_i3c_master_ibi_isr()
614 svc_i3c_master_emit_stop(master); in svc_i3c_master_ibi_isr()
623 struct svc_i3c_master *master = (struct svc_i3c_master *)dev_id; in svc_i3c_master_irq_handler() local
624 u32 active = readl(master->regs + SVC_I3C_MSTATUS); in svc_i3c_master_irq_handler()
630 writel(SVC_I3C_MINT_SLVSTART, master->regs + SVC_I3C_MSTATUS); in svc_i3c_master_irq_handler()
633 if (svc_has_quirk(master, SVC_I3C_QUIRK_FALSE_SLVSTART) && in svc_i3c_master_irq_handler()
642 svc_i3c_master_ibi_isr(master); in svc_i3c_master_irq_handler()
650 struct svc_i3c_master *master = to_svc_i3c_master(m); in svc_i3c_master_set_speed() local
651 struct i3c_bus *bus = i3c_master_get_bus(&master->base); in svc_i3c_master_set_speed()
656 ret = pm_runtime_resume_and_get(master->dev); in svc_i3c_master_set_speed()
658 dev_err(master->dev, "<%s> Cannot get runtime PM.\n", __func__); in svc_i3c_master_set_speed()
664 fclk_rate = clk_get_rate(master->fclk); in svc_i3c_master_set_speed()
675 mconfig = master->mctrl_config; in svc_i3c_master_set_speed()
681 writel(mconfig, master->regs + SVC_I3C_MCONFIG); in svc_i3c_master_set_speed()
684 writel(master->mctrl_config, master->regs + SVC_I3C_MCONFIG); in svc_i3c_master_set_speed()
689 pm_runtime_put_autosuspend(master->dev); in svc_i3c_master_set_speed()
696 struct svc_i3c_master *master = to_svc_i3c_master(m); in svc_i3c_master_bus_init() local
705 ret = pm_runtime_resume_and_get(master->dev); in svc_i3c_master_bus_init()
707 dev_err(master->dev, in svc_i3c_master_bus_init()
714 fclk_rate = clk_get_rate(master->fclk); in svc_i3c_master_bus_init()
785 writel(reg, master->regs + SVC_I3C_MCONFIG); in svc_i3c_master_bus_init()
787 master->mctrl_config = reg; in svc_i3c_master_bus_init()
796 master->regs + SVC_I3C_MDYNADDR); in svc_i3c_master_bus_init()
798 ret = i3c_master_set_info(&master->base, &info); in svc_i3c_master_bus_init()
803 pm_runtime_put_autosuspend(master->dev); in svc_i3c_master_bus_init()
810 struct svc_i3c_master *master = to_svc_i3c_master(m); in svc_i3c_master_bus_cleanup() local
813 ret = pm_runtime_resume_and_get(master->dev); in svc_i3c_master_bus_cleanup()
815 dev_err(master->dev, "<%s> Cannot get runtime PM.\n", __func__); in svc_i3c_master_bus_cleanup()
819 svc_i3c_master_disable_interrupts(master); in svc_i3c_master_bus_cleanup()
822 writel(0, master->regs + SVC_I3C_MCONFIG); in svc_i3c_master_bus_cleanup()
824 pm_runtime_put_autosuspend(master->dev); in svc_i3c_master_bus_cleanup()
827 static int svc_i3c_master_reserve_slot(struct svc_i3c_master *master) in svc_i3c_master_reserve_slot() argument
831 if (!(master->free_slots & GENMASK(SVC_I3C_MAX_DEVS - 1, 0))) in svc_i3c_master_reserve_slot()
834 slot = ffs(master->free_slots) - 1; in svc_i3c_master_reserve_slot()
836 master->free_slots &= ~BIT(slot); in svc_i3c_master_reserve_slot()
841 static void svc_i3c_master_release_slot(struct svc_i3c_master *master, in svc_i3c_master_release_slot() argument
844 master->free_slots |= BIT(slot); in svc_i3c_master_release_slot()
850 struct svc_i3c_master *master = to_svc_i3c_master(m); in svc_i3c_master_attach_i3c_dev() local
854 slot = svc_i3c_master_reserve_slot(master); in svc_i3c_master_attach_i3c_dev()
860 svc_i3c_master_release_slot(master, slot); in svc_i3c_master_attach_i3c_dev()
866 master->addrs[slot] = dev->info.dyn_addr ? dev->info.dyn_addr : in svc_i3c_master_attach_i3c_dev()
868 master->descs[slot] = dev; in svc_i3c_master_attach_i3c_dev()
879 struct svc_i3c_master *master = to_svc_i3c_master(m); in svc_i3c_master_reattach_i3c_dev() local
882 master->addrs[data->index] = dev->info.dyn_addr ? dev->info.dyn_addr : in svc_i3c_master_reattach_i3c_dev()
892 struct svc_i3c_master *master = to_svc_i3c_master(m); in svc_i3c_master_detach_i3c_dev() local
894 master->addrs[data->index] = 0; in svc_i3c_master_detach_i3c_dev()
895 svc_i3c_master_release_slot(master, data->index); in svc_i3c_master_detach_i3c_dev()
903 struct svc_i3c_master *master = to_svc_i3c_master(m); in svc_i3c_master_attach_i2c_dev() local
907 slot = svc_i3c_master_reserve_slot(master); in svc_i3c_master_attach_i2c_dev()
913 svc_i3c_master_release_slot(master, slot); in svc_i3c_master_attach_i2c_dev()
918 master->addrs[slot] = dev->addr; in svc_i3c_master_attach_i2c_dev()
929 struct svc_i3c_master *master = to_svc_i3c_master(m); in svc_i3c_master_detach_i2c_dev() local
931 svc_i3c_master_release_slot(master, data->index); in svc_i3c_master_detach_i2c_dev()
936 static int svc_i3c_master_readb(struct svc_i3c_master *master, u8 *dst, in svc_i3c_master_readb() argument
943 ret = readl_poll_timeout_atomic(master->regs + SVC_I3C_MSTATUS, in svc_i3c_master_readb()
950 dst[i] = readl(master->regs + SVC_I3C_MRDATAB); in svc_i3c_master_readb()
956 static int svc_i3c_master_do_daa_locked(struct svc_i3c_master *master, in svc_i3c_master_do_daa_locked() argument
964 svc_i3c_master_flush_fifo(master); in svc_i3c_master_do_daa_locked()
968 writel(SVC_I3C_MINT_IBIWON, master->regs + SVC_I3C_MSTATUS); in svc_i3c_master_do_daa_locked()
988 master->regs + SVC_I3C_MCTRL); in svc_i3c_master_do_daa_locked()
994 ret = readl_poll_timeout_atomic(master->regs + SVC_I3C_MSTATUS, in svc_i3c_master_do_daa_locked()
1018 ret = i3c_master_get_free_addr(&master->base, last_addr + 1); in svc_i3c_master_do_daa_locked()
1023 writel(dyn_addr, master->regs + SVC_I3C_MWDATAB); in svc_i3c_master_do_daa_locked()
1030 ret = svc_i3c_master_readb(master, data, 6); in svc_i3c_master_do_daa_locked()
1038 ret = svc_i3c_master_readb(master, data, 2); in svc_i3c_master_do_daa_locked()
1042 ret = svc_i3c_master_handle_ibi_won(master, reg); in svc_i3c_master_do_daa_locked()
1085 svc_i3c_master_emit_stop(master); in svc_i3c_master_do_daa_locked()
1094 ret = readl_poll_timeout_atomic(master->regs + SVC_I3C_MSTATUS, in svc_i3c_master_do_daa_locked()
1104 dev_dbg(master->dev, "DAA: device %d assigned to 0x%02x\n", in svc_i3c_master_do_daa_locked()
1110 svc_i3c_master_emit_stop(master); in svc_i3c_master_do_daa_locked()
1111 svc_i3c_master_flush_fifo(master); in svc_i3c_master_do_daa_locked()
1116 static int svc_i3c_update_ibirules(struct svc_i3c_master *master) in svc_i3c_update_ibirules() argument
1125 i3c_bus_for_each_i3cdev(&master->base.bus, dev) { in svc_i3c_update_ibirules()
1163 writel(reg_mbyte, master->regs + SVC_I3C_IBIRULES); in svc_i3c_update_ibirules()
1165 writel(reg_nobyte, master->regs + SVC_I3C_IBIRULES); in svc_i3c_update_ibirules()
1172 struct svc_i3c_master *master = to_svc_i3c_master(m); in svc_i3c_master_do_daa() local
1178 ret = pm_runtime_resume_and_get(master->dev); in svc_i3c_master_do_daa()
1180 dev_err(master->dev, "<%s> Cannot get runtime PM.\n", __func__); in svc_i3c_master_do_daa()
1184 spin_lock_irqsave(&master->xferqueue.lock, flags); in svc_i3c_master_do_daa()
1186 if (svc_has_daa_corrupt(master)) in svc_i3c_master_do_daa()
1187 writel(master->mctrl_config | SVC_I3C_MCONFIG_SKEW(1), in svc_i3c_master_do_daa()
1188 master->regs + SVC_I3C_MCONFIG); in svc_i3c_master_do_daa()
1190 ret = svc_i3c_master_do_daa_locked(master, addrs, &dev_nb); in svc_i3c_master_do_daa()
1192 if (svc_has_daa_corrupt(master)) in svc_i3c_master_do_daa()
1193 writel(master->mctrl_config, master->regs + SVC_I3C_MCONFIG); in svc_i3c_master_do_daa()
1195 spin_unlock_irqrestore(&master->xferqueue.lock, flags); in svc_i3c_master_do_daa()
1197 svc_i3c_master_clear_merrwarn(master); in svc_i3c_master_do_daa()
1224 ret = svc_i3c_update_ibirules(master); in svc_i3c_master_do_daa()
1226 dev_err(master->dev, "Cannot handle such a list of devices"); in svc_i3c_master_do_daa()
1229 pm_runtime_put_autosuspend(master->dev); in svc_i3c_master_do_daa()
1234 static int svc_i3c_master_read(struct svc_i3c_master *master, in svc_i3c_master_read() argument
1244 mstatus = readl(master->regs + SVC_I3C_MSTATUS); in svc_i3c_master_read()
1249 dev_dbg(master->dev, "I3C read timeout\n"); in svc_i3c_master_read()
1253 mdctrl = readl(master->regs + SVC_I3C_MDATACTRL); in svc_i3c_master_read()
1256 dev_err(master->dev, "I3C receive length too long!\n"); in svc_i3c_master_read()
1260 in[offset + i] = readl(master->regs + SVC_I3C_MRDATAB); in svc_i3c_master_read()
1268 static int svc_i3c_master_write(struct svc_i3c_master *master, in svc_i3c_master_write() argument
1275 ret = readl_poll_timeout(master->regs + SVC_I3C_MDATACTRL, in svc_i3c_master_write()
1287 writel(out[offset++], master->regs + SVC_I3C_MWDATAB); in svc_i3c_master_write()
1289 writel(out[offset++], master->regs + SVC_I3C_MWDATABE); in svc_i3c_master_write()
1295 static int svc_i3c_master_xfer(struct svc_i3c_master *master, in svc_i3c_master_xfer() argument
1305 writel(SVC_I3C_MINT_IBIWON, master->regs + SVC_I3C_MSTATUS); in svc_i3c_master_xfer()
1315 master->regs + SVC_I3C_MCTRL); in svc_i3c_master_xfer()
1324 if (svc_has_quirk(master, SVC_I3C_QUIRK_FIFO_EMPTY) && !rnw && xfer_len) { in svc_i3c_master_xfer()
1327 reg = readl(master->regs + SVC_I3C_MDATACTRL); in svc_i3c_master_xfer()
1332 writesb(master->regs + SVC_I3C_MWDATAB1, out, len - 1); in svc_i3c_master_xfer()
1334 writel(out[len - 1] | end, master->regs + SVC_I3C_MWDATAB); in svc_i3c_master_xfer()
1340 ret = readl_poll_timeout(master->regs + SVC_I3C_MSTATUS, reg, in svc_i3c_master_xfer()
1359 ret = svc_i3c_master_handle_ibi_won(master, reg); in svc_i3c_master_xfer()
1365 if (readl(master->regs + SVC_I3C_MERRWARN) & SVC_I3C_MERRWARN_NACK) { in svc_i3c_master_xfer()
1387 writel(SVC_I3C_MERRWARN_NACK, master->regs + SVC_I3C_MERRWARN); in svc_i3c_master_xfer()
1399 ret = svc_i3c_master_read(master, in, xfer_len); in svc_i3c_master_xfer()
1401 ret = svc_i3c_master_write(master, out, xfer_len); in svc_i3c_master_xfer()
1408 ret = readl_poll_timeout(master->regs + SVC_I3C_MSTATUS, reg, in svc_i3c_master_xfer()
1413 writel(SVC_I3C_MINT_COMPLETE, master->regs + SVC_I3C_MSTATUS); in svc_i3c_master_xfer()
1416 svc_i3c_master_emit_stop(master); in svc_i3c_master_xfer()
1419 readl_poll_timeout(master->regs + SVC_I3C_MSTATUS, reg, in svc_i3c_master_xfer()
1426 svc_i3c_master_emit_stop(master); in svc_i3c_master_xfer()
1427 svc_i3c_master_clear_merrwarn(master); in svc_i3c_master_xfer()
1428 svc_i3c_master_flush_fifo(master); in svc_i3c_master_xfer()
1434 svc_i3c_master_alloc_xfer(struct svc_i3c_master *master, unsigned int ncmds) in svc_i3c_master_alloc_xfer() argument
1454 static void svc_i3c_master_dequeue_xfer_locked(struct svc_i3c_master *master, in svc_i3c_master_dequeue_xfer_locked() argument
1457 if (master->xferqueue.cur == xfer) in svc_i3c_master_dequeue_xfer_locked()
1458 master->xferqueue.cur = NULL; in svc_i3c_master_dequeue_xfer_locked()
1463 static void svc_i3c_master_dequeue_xfer(struct svc_i3c_master *master, in svc_i3c_master_dequeue_xfer() argument
1468 spin_lock_irqsave(&master->xferqueue.lock, flags); in svc_i3c_master_dequeue_xfer()
1469 svc_i3c_master_dequeue_xfer_locked(master, xfer); in svc_i3c_master_dequeue_xfer()
1470 spin_unlock_irqrestore(&master->xferqueue.lock, flags); in svc_i3c_master_dequeue_xfer()
1473 static void svc_i3c_master_start_xfer_locked(struct svc_i3c_master *master) in svc_i3c_master_start_xfer_locked() argument
1475 struct svc_i3c_xfer *xfer = master->xferqueue.cur; in svc_i3c_master_start_xfer_locked()
1481 svc_i3c_master_clear_merrwarn(master); in svc_i3c_master_start_xfer_locked()
1482 svc_i3c_master_flush_fifo(master); in svc_i3c_master_start_xfer_locked()
1487 ret = svc_i3c_master_xfer(master, cmd->rnw, xfer->type, in svc_i3c_master_start_xfer_locked()
1503 svc_i3c_master_dequeue_xfer_locked(master, xfer); in svc_i3c_master_start_xfer_locked()
1505 xfer = list_first_entry_or_null(&master->xferqueue.list, in svc_i3c_master_start_xfer_locked()
1511 master->xferqueue.cur = xfer; in svc_i3c_master_start_xfer_locked()
1512 svc_i3c_master_start_xfer_locked(master); in svc_i3c_master_start_xfer_locked()
1515 static void svc_i3c_master_enqueue_xfer(struct svc_i3c_master *master, in svc_i3c_master_enqueue_xfer() argument
1521 ret = pm_runtime_resume_and_get(master->dev); in svc_i3c_master_enqueue_xfer()
1523 dev_err(master->dev, "<%s> Cannot get runtime PM.\n", __func__); in svc_i3c_master_enqueue_xfer()
1528 spin_lock_irqsave(&master->xferqueue.lock, flags); in svc_i3c_master_enqueue_xfer()
1529 if (master->xferqueue.cur) { in svc_i3c_master_enqueue_xfer()
1530 list_add_tail(&xfer->node, &master->xferqueue.list); in svc_i3c_master_enqueue_xfer()
1532 master->xferqueue.cur = xfer; in svc_i3c_master_enqueue_xfer()
1533 svc_i3c_master_start_xfer_locked(master); in svc_i3c_master_enqueue_xfer()
1535 spin_unlock_irqrestore(&master->xferqueue.lock, flags); in svc_i3c_master_enqueue_xfer()
1537 pm_runtime_put_autosuspend(master->dev); in svc_i3c_master_enqueue_xfer()
1541 svc_i3c_master_supports_ccc_cmd(struct i3c_master_controller *master, in svc_i3c_master_supports_ccc_cmd() argument
1548 static int svc_i3c_master_send_bdcast_ccc_cmd(struct svc_i3c_master *master, in svc_i3c_master_send_bdcast_ccc_cmd() argument
1557 xfer = svc_i3c_master_alloc_xfer(master, 1); in svc_i3c_master_send_bdcast_ccc_cmd()
1581 mutex_lock(&master->lock); in svc_i3c_master_send_bdcast_ccc_cmd()
1582 svc_i3c_master_enqueue_xfer(master, xfer); in svc_i3c_master_send_bdcast_ccc_cmd()
1584 svc_i3c_master_dequeue_xfer(master, xfer); in svc_i3c_master_send_bdcast_ccc_cmd()
1585 mutex_unlock(&master->lock); in svc_i3c_master_send_bdcast_ccc_cmd()
1594 static int svc_i3c_master_send_direct_ccc_cmd(struct svc_i3c_master *master, in svc_i3c_master_send_direct_ccc_cmd() argument
1603 xfer = svc_i3c_master_alloc_xfer(master, 2); in svc_i3c_master_send_direct_ccc_cmd()
1629 mutex_lock(&master->lock); in svc_i3c_master_send_direct_ccc_cmd()
1630 svc_i3c_master_enqueue_xfer(master, xfer); in svc_i3c_master_send_direct_ccc_cmd()
1632 svc_i3c_master_dequeue_xfer(master, xfer); in svc_i3c_master_send_direct_ccc_cmd()
1633 mutex_unlock(&master->lock); in svc_i3c_master_send_direct_ccc_cmd()
1647 struct svc_i3c_master *master = to_svc_i3c_master(m); in svc_i3c_master_send_ccc_cmd() local
1652 ret = svc_i3c_master_send_bdcast_ccc_cmd(master, cmd); in svc_i3c_master_send_ccc_cmd()
1654 ret = svc_i3c_master_send_direct_ccc_cmd(master, cmd); in svc_i3c_master_send_ccc_cmd()
1667 struct svc_i3c_master *master = to_svc_i3c_master(m); in svc_i3c_master_priv_xfers() local
1672 xfer = svc_i3c_master_alloc_xfer(master, nxfers); in svc_i3c_master_priv_xfers()
1682 cmd->addr = master->addrs[data->index]; in svc_i3c_master_priv_xfers()
1691 mutex_lock(&master->lock); in svc_i3c_master_priv_xfers()
1692 svc_i3c_master_enqueue_xfer(master, xfer); in svc_i3c_master_priv_xfers()
1694 svc_i3c_master_dequeue_xfer(master, xfer); in svc_i3c_master_priv_xfers()
1695 mutex_unlock(&master->lock); in svc_i3c_master_priv_xfers()
1708 struct svc_i3c_master *master = to_svc_i3c_master(m); in svc_i3c_master_i2c_xfers() local
1713 xfer = svc_i3c_master_alloc_xfer(master, nxfers); in svc_i3c_master_i2c_xfers()
1722 cmd->addr = master->addrs[data->index]; in svc_i3c_master_i2c_xfers()
1731 mutex_lock(&master->lock); in svc_i3c_master_i2c_xfers()
1732 svc_i3c_master_enqueue_xfer(master, xfer); in svc_i3c_master_i2c_xfers()
1734 svc_i3c_master_dequeue_xfer(master, xfer); in svc_i3c_master_i2c_xfers()
1735 mutex_unlock(&master->lock); in svc_i3c_master_i2c_xfers()
1747 struct svc_i3c_master *master = to_svc_i3c_master(m); in svc_i3c_master_request_ibi() local
1753 dev_err(master->dev, "IBI max payload %d should be < %d\n", in svc_i3c_master_request_ibi()
1762 spin_lock_irqsave(&master->ibi.lock, flags); in svc_i3c_master_request_ibi()
1763 for (i = 0; i < master->ibi.num_slots; i++) { in svc_i3c_master_request_ibi()
1764 if (!master->ibi.slots[i]) { in svc_i3c_master_request_ibi()
1766 master->ibi.slots[i] = dev; in svc_i3c_master_request_ibi()
1770 spin_unlock_irqrestore(&master->ibi.lock, flags); in svc_i3c_master_request_ibi()
1772 if (i < master->ibi.num_slots) in svc_i3c_master_request_ibi()
1784 struct svc_i3c_master *master = to_svc_i3c_master(m); in svc_i3c_master_free_ibi() local
1788 spin_lock_irqsave(&master->ibi.lock, flags); in svc_i3c_master_free_ibi()
1789 master->ibi.slots[data->ibi] = NULL; in svc_i3c_master_free_ibi()
1791 spin_unlock_irqrestore(&master->ibi.lock, flags); in svc_i3c_master_free_ibi()
1799 struct svc_i3c_master *master = to_svc_i3c_master(m); in svc_i3c_master_enable_ibi() local
1802 ret = pm_runtime_resume_and_get(master->dev); in svc_i3c_master_enable_ibi()
1804 dev_err(master->dev, "<%s> Cannot get runtime PM.\n", __func__); in svc_i3c_master_enable_ibi()
1808 master->enabled_events++; in svc_i3c_master_enable_ibi()
1809 svc_i3c_master_enable_interrupts(master, SVC_I3C_MINT_SLVSTART); in svc_i3c_master_enable_ibi()
1817 struct svc_i3c_master *master = to_svc_i3c_master(m); in svc_i3c_master_disable_ibi() local
1820 master->enabled_events--; in svc_i3c_master_disable_ibi()
1821 if (!master->enabled_events) in svc_i3c_master_disable_ibi()
1822 svc_i3c_master_disable_interrupts(master); in svc_i3c_master_disable_ibi()
1826 pm_runtime_put_autosuspend(master->dev); in svc_i3c_master_disable_ibi()
1833 struct svc_i3c_master *master = to_svc_i3c_master(m); in svc_i3c_master_enable_hotjoin() local
1836 ret = pm_runtime_resume_and_get(master->dev); in svc_i3c_master_enable_hotjoin()
1838 dev_err(master->dev, "<%s> Cannot get runtime PM.\n", __func__); in svc_i3c_master_enable_hotjoin()
1842 master->enabled_events |= SVC_I3C_EVENT_HOTJOIN; in svc_i3c_master_enable_hotjoin()
1844 svc_i3c_master_enable_interrupts(master, SVC_I3C_MINT_SLVSTART); in svc_i3c_master_enable_hotjoin()
1851 struct svc_i3c_master *master = to_svc_i3c_master(m); in svc_i3c_master_disable_hotjoin() local
1853 master->enabled_events &= ~SVC_I3C_EVENT_HOTJOIN; in svc_i3c_master_disable_hotjoin()
1855 if (!master->enabled_events) in svc_i3c_master_disable_hotjoin()
1856 svc_i3c_master_disable_interrupts(master); in svc_i3c_master_disable_hotjoin()
1858 pm_runtime_put_autosuspend(master->dev); in svc_i3c_master_disable_hotjoin()
1897 struct svc_i3c_master *master; in svc_i3c_master_probe() local
1900 master = devm_kzalloc(dev, sizeof(*master), GFP_KERNEL); in svc_i3c_master_probe()
1901 if (!master) in svc_i3c_master_probe()
1904 master->drvdata = of_device_get_match_data(dev); in svc_i3c_master_probe()
1905 if (!master->drvdata) in svc_i3c_master_probe()
1908 master->regs = devm_platform_ioremap_resource(pdev, 0); in svc_i3c_master_probe()
1909 if (IS_ERR(master->regs)) in svc_i3c_master_probe()
1910 return PTR_ERR(master->regs); in svc_i3c_master_probe()
1912 master->num_clks = devm_clk_bulk_get_all(dev, &master->clks); in svc_i3c_master_probe()
1913 if (master->num_clks < 0) in svc_i3c_master_probe()
1916 for (i = 0; i < master->num_clks; i++) { in svc_i3c_master_probe()
1917 if (!strcmp(master->clks[i].id, "fast_clk")) in svc_i3c_master_probe()
1921 if (i == master->num_clks) in svc_i3c_master_probe()
1925 master->fclk = master->clks[i].clk; in svc_i3c_master_probe()
1926 if (IS_ERR(master->fclk)) in svc_i3c_master_probe()
1927 return PTR_ERR(master->fclk); in svc_i3c_master_probe()
1929 master->irq = platform_get_irq(pdev, 0); in svc_i3c_master_probe()
1930 if (master->irq < 0) in svc_i3c_master_probe()
1931 return master->irq; in svc_i3c_master_probe()
1933 master->dev = dev; in svc_i3c_master_probe()
1934 ret = clk_bulk_prepare_enable(master->num_clks, master->clks); in svc_i3c_master_probe()
1938 INIT_WORK(&master->hj_work, svc_i3c_master_hj_work); in svc_i3c_master_probe()
1939 mutex_init(&master->lock); in svc_i3c_master_probe()
1941 ret = devm_request_irq(dev, master->irq, svc_i3c_master_irq_handler, in svc_i3c_master_probe()
1942 IRQF_NO_SUSPEND, "svc-i3c-irq", master); in svc_i3c_master_probe()
1946 master->free_slots = GENMASK(SVC_I3C_MAX_DEVS - 1, 0); in svc_i3c_master_probe()
1948 spin_lock_init(&master->xferqueue.lock); in svc_i3c_master_probe()
1949 INIT_LIST_HEAD(&master->xferqueue.list); in svc_i3c_master_probe()
1951 spin_lock_init(&master->ibi.lock); in svc_i3c_master_probe()
1952 master->ibi.num_slots = SVC_I3C_MAX_DEVS; in svc_i3c_master_probe()
1953 master->ibi.slots = devm_kcalloc(&pdev->dev, master->ibi.num_slots, in svc_i3c_master_probe()
1954 sizeof(*master->ibi.slots), in svc_i3c_master_probe()
1956 if (!master->ibi.slots) { in svc_i3c_master_probe()
1961 platform_set_drvdata(pdev, master); in svc_i3c_master_probe()
1969 svc_i3c_master_reset(master); in svc_i3c_master_probe()
1972 ret = i3c_master_register(&master->base, &pdev->dev, in svc_i3c_master_probe()
1988 clk_bulk_disable_unprepare(master->num_clks, master->clks); in svc_i3c_master_probe()
1995 struct svc_i3c_master *master = platform_get_drvdata(pdev); in svc_i3c_master_remove() local
1997 cancel_work_sync(&master->hj_work); in svc_i3c_master_remove()
1998 i3c_master_unregister(&master->base); in svc_i3c_master_remove()
2004 static void svc_i3c_save_regs(struct svc_i3c_master *master) in svc_i3c_save_regs() argument
2006 master->saved_regs.mconfig = readl(master->regs + SVC_I3C_MCONFIG); in svc_i3c_save_regs()
2007 master->saved_regs.mdynaddr = readl(master->regs + SVC_I3C_MDYNADDR); in svc_i3c_save_regs()
2010 static void svc_i3c_restore_regs(struct svc_i3c_master *master) in svc_i3c_restore_regs() argument
2012 if (readl(master->regs + SVC_I3C_MDYNADDR) != in svc_i3c_restore_regs()
2013 master->saved_regs.mdynaddr) { in svc_i3c_restore_regs()
2014 writel(master->saved_regs.mconfig, in svc_i3c_restore_regs()
2015 master->regs + SVC_I3C_MCONFIG); in svc_i3c_restore_regs()
2016 writel(master->saved_regs.mdynaddr, in svc_i3c_restore_regs()
2017 master->regs + SVC_I3C_MDYNADDR); in svc_i3c_restore_regs()
2023 struct svc_i3c_master *master = dev_get_drvdata(dev); in svc_i3c_runtime_suspend() local
2025 svc_i3c_save_regs(master); in svc_i3c_runtime_suspend()
2026 clk_bulk_disable_unprepare(master->num_clks, master->clks); in svc_i3c_runtime_suspend()
2034 struct svc_i3c_master *master = dev_get_drvdata(dev); in svc_i3c_runtime_resume() local
2038 ret = clk_bulk_prepare_enable(master->num_clks, master->clks); in svc_i3c_runtime_resume()
2042 svc_i3c_restore_regs(master); in svc_i3c_runtime_resume()