Lines Matching refs:pd
193 static void iic_wr(struct sh_mobile_i2c_data *pd, int offs, unsigned char data) in iic_wr() argument
196 data |= pd->icic; in iic_wr()
198 iowrite8(data, pd->reg + offs); in iic_wr()
201 static unsigned char iic_rd(struct sh_mobile_i2c_data *pd, int offs) in iic_rd() argument
203 return ioread8(pd->reg + offs); in iic_rd()
206 static void iic_set_clr(struct sh_mobile_i2c_data *pd, int offs, in iic_set_clr() argument
209 iic_wr(pd, offs, (iic_rd(pd, offs) | set) & ~clr); in iic_set_clr()
246 static int sh_mobile_i2c_init(struct sh_mobile_i2c_data *pd) in sh_mobile_i2c_init() argument
253 clk_prepare_enable(pd->clk); in sh_mobile_i2c_init()
254 i2c_clk_khz = clk_get_rate(pd->clk) / 1000; in sh_mobile_i2c_init()
255 clk_disable_unprepare(pd->clk); in sh_mobile_i2c_init()
256 i2c_clk_khz /= pd->clks_per_count; in sh_mobile_i2c_init()
258 if (pd->bus_speed == STANDARD_MODE) { in sh_mobile_i2c_init()
262 } else if (pd->bus_speed == FAST_MODE) { in sh_mobile_i2c_init()
267 dev_err(pd->dev, "unrecognized bus speed %lu Hz\n", in sh_mobile_i2c_init()
268 pd->bus_speed); in sh_mobile_i2c_init()
272 pd->iccl = sh_mobile_i2c_iccl(i2c_clk_khz, tLOW, tf); in sh_mobile_i2c_init()
273 pd->icch = sh_mobile_i2c_icch(i2c_clk_khz, tHIGH, tf); in sh_mobile_i2c_init()
275 max_val = pd->flags & IIC_FLAG_HAS_ICIC67 ? 0x1ff : 0xff; in sh_mobile_i2c_init()
276 if (pd->iccl > max_val || pd->icch > max_val) { in sh_mobile_i2c_init()
277 dev_err(pd->dev, "timing values out of range: L/H=0x%x/0x%x\n", in sh_mobile_i2c_init()
278 pd->iccl, pd->icch); in sh_mobile_i2c_init()
283 if (pd->iccl & 0x100) in sh_mobile_i2c_init()
284 pd->icic |= ICIC_ICCLB8; in sh_mobile_i2c_init()
286 pd->icic &= ~ICIC_ICCLB8; in sh_mobile_i2c_init()
289 if (pd->icch & 0x100) in sh_mobile_i2c_init()
290 pd->icic |= ICIC_ICCHB8; in sh_mobile_i2c_init()
292 pd->icic &= ~ICIC_ICCHB8; in sh_mobile_i2c_init()
294 dev_dbg(pd->dev, "timing values: L/H=0x%x/0x%x\n", pd->iccl, pd->icch); in sh_mobile_i2c_init()
298 static void activate_ch(struct sh_mobile_i2c_data *pd) in activate_ch() argument
301 pm_runtime_get_sync(pd->dev); in activate_ch()
302 clk_prepare_enable(pd->clk); in activate_ch()
305 iic_set_clr(pd, ICCR, ICCR_ICE, 0); in activate_ch()
308 iic_wr(pd, ICIC, 0); in activate_ch()
311 iic_wr(pd, ICCL, pd->iccl & 0xff); in activate_ch()
312 iic_wr(pd, ICCH, pd->icch & 0xff); in activate_ch()
315 static void deactivate_ch(struct sh_mobile_i2c_data *pd) in deactivate_ch() argument
318 iic_wr(pd, ICSR, 0); in deactivate_ch()
319 iic_wr(pd, ICIC, 0); in deactivate_ch()
322 iic_set_clr(pd, ICCR, 0, ICCR_ICE); in deactivate_ch()
325 clk_disable_unprepare(pd->clk); in deactivate_ch()
326 pm_runtime_put_sync(pd->dev); in deactivate_ch()
329 static unsigned char i2c_op(struct sh_mobile_i2c_data *pd, in i2c_op() argument
335 dev_dbg(pd->dev, "op %d, data in 0x%02x\n", op, data); in i2c_op()
337 spin_lock_irqsave(&pd->lock, flags); in i2c_op()
341 iic_wr(pd, ICCR, ICCR_ICE | ICCR_TRS | ICCR_BBSY); in i2c_op()
344 iic_wr(pd, ICIC, ICIC_WAITE | ICIC_ALE | ICIC_TACKE); in i2c_op()
345 iic_wr(pd, ICDR, data); in i2c_op()
348 iic_wr(pd, ICDR, data); in i2c_op()
351 iic_wr(pd, ICDR, data); in i2c_op()
354 iic_wr(pd, ICCR, pd->send_stop ? ICCR_ICE | ICCR_TRS in i2c_op()
358 iic_wr(pd, ICCR, ICCR_ICE | ICCR_SCP); in i2c_op()
361 ret = iic_rd(pd, ICDR); in i2c_op()
364 iic_wr(pd, ICIC, in i2c_op()
366 iic_wr(pd, ICCR, ICCR_ICE | ICCR_RACK); in i2c_op()
369 iic_wr(pd, ICIC, in i2c_op()
371 ret = iic_rd(pd, ICDR); in i2c_op()
372 iic_wr(pd, ICCR, ICCR_ICE | ICCR_RACK); in i2c_op()
376 spin_unlock_irqrestore(&pd->lock, flags); in i2c_op()
378 dev_dbg(pd->dev, "op %d, data out 0x%02x\n", op, ret); in i2c_op()
382 static bool sh_mobile_i2c_is_first_byte(struct sh_mobile_i2c_data *pd) in sh_mobile_i2c_is_first_byte() argument
384 return pd->pos == -1; in sh_mobile_i2c_is_first_byte()
387 static bool sh_mobile_i2c_is_last_byte(struct sh_mobile_i2c_data *pd) in sh_mobile_i2c_is_last_byte() argument
389 return pd->pos == pd->msg->len - 1; in sh_mobile_i2c_is_last_byte()
392 static void sh_mobile_i2c_get_data(struct sh_mobile_i2c_data *pd, in sh_mobile_i2c_get_data() argument
395 switch (pd->pos) { in sh_mobile_i2c_get_data()
397 *buf = (pd->msg->addr & 0x7f) << 1; in sh_mobile_i2c_get_data()
398 *buf |= (pd->msg->flags & I2C_M_RD) ? 1 : 0; in sh_mobile_i2c_get_data()
401 *buf = pd->msg->buf[pd->pos]; in sh_mobile_i2c_get_data()
405 static int sh_mobile_i2c_isr_tx(struct sh_mobile_i2c_data *pd) in sh_mobile_i2c_isr_tx() argument
409 if (pd->pos == pd->msg->len) { in sh_mobile_i2c_isr_tx()
411 if (pd->send_stop && pd->stop_after_dma) in sh_mobile_i2c_isr_tx()
412 i2c_op(pd, OP_TX_STOP, 0); in sh_mobile_i2c_isr_tx()
416 sh_mobile_i2c_get_data(pd, &data); in sh_mobile_i2c_isr_tx()
418 if (sh_mobile_i2c_is_last_byte(pd)) in sh_mobile_i2c_isr_tx()
419 i2c_op(pd, OP_TX_STOP_DATA, data); in sh_mobile_i2c_isr_tx()
420 else if (sh_mobile_i2c_is_first_byte(pd)) in sh_mobile_i2c_isr_tx()
421 i2c_op(pd, OP_TX_FIRST, data); in sh_mobile_i2c_isr_tx()
423 i2c_op(pd, OP_TX, data); in sh_mobile_i2c_isr_tx()
425 pd->pos++; in sh_mobile_i2c_isr_tx()
429 static int sh_mobile_i2c_isr_rx(struct sh_mobile_i2c_data *pd) in sh_mobile_i2c_isr_rx() argument
435 if (pd->pos <= -1) { in sh_mobile_i2c_isr_rx()
436 sh_mobile_i2c_get_data(pd, &data); in sh_mobile_i2c_isr_rx()
438 if (sh_mobile_i2c_is_first_byte(pd)) in sh_mobile_i2c_isr_rx()
439 i2c_op(pd, OP_TX_FIRST, data); in sh_mobile_i2c_isr_rx()
441 i2c_op(pd, OP_TX, data); in sh_mobile_i2c_isr_rx()
445 if (pd->pos == 0) { in sh_mobile_i2c_isr_rx()
446 i2c_op(pd, OP_TX_TO_RX, 0); in sh_mobile_i2c_isr_rx()
450 real_pos = pd->pos - 2; in sh_mobile_i2c_isr_rx()
452 if (pd->pos == pd->msg->len) { in sh_mobile_i2c_isr_rx()
453 if (pd->stop_after_dma) { in sh_mobile_i2c_isr_rx()
455 i2c_op(pd, OP_RX_STOP, 0); in sh_mobile_i2c_isr_rx()
456 pd->pos++; in sh_mobile_i2c_isr_rx()
461 i2c_op(pd, OP_RX_STOP, 0); in sh_mobile_i2c_isr_rx()
464 data = i2c_op(pd, OP_RX_STOP_DATA, 0); in sh_mobile_i2c_isr_rx()
466 data = i2c_op(pd, OP_RX, 0); in sh_mobile_i2c_isr_rx()
469 pd->msg->buf[real_pos] = data; in sh_mobile_i2c_isr_rx()
472 pd->pos++; in sh_mobile_i2c_isr_rx()
473 return pd->pos == (pd->msg->len + 2); in sh_mobile_i2c_isr_rx()
478 struct sh_mobile_i2c_data *pd = dev_id; in sh_mobile_i2c_isr() local
482 sr = iic_rd(pd, ICSR); in sh_mobile_i2c_isr()
483 pd->sr |= sr; /* remember state */ in sh_mobile_i2c_isr()
485 dev_dbg(pd->dev, "i2c_isr 0x%02x 0x%02x %s %d %d!\n", sr, pd->sr, in sh_mobile_i2c_isr()
486 (pd->msg->flags & I2C_M_RD) ? "read" : "write", in sh_mobile_i2c_isr()
487 pd->pos, pd->msg->len); in sh_mobile_i2c_isr()
490 if (pd->dma_direction == DMA_TO_DEVICE && pd->pos == 0) in sh_mobile_i2c_isr()
491 iic_set_clr(pd, ICIC, ICIC_TDMAE, 0); in sh_mobile_i2c_isr()
494 iic_wr(pd, ICSR, sr & ~(ICSR_AL | ICSR_TACK)); in sh_mobile_i2c_isr()
495 else if (pd->msg->flags & I2C_M_RD) in sh_mobile_i2c_isr()
496 wakeup = sh_mobile_i2c_isr_rx(pd); in sh_mobile_i2c_isr()
498 wakeup = sh_mobile_i2c_isr_tx(pd); in sh_mobile_i2c_isr()
501 if (pd->dma_direction == DMA_FROM_DEVICE && pd->pos == 1) in sh_mobile_i2c_isr()
502 iic_set_clr(pd, ICIC, ICIC_RDMAE, 0); in sh_mobile_i2c_isr()
505 iic_wr(pd, ICSR, sr & ~ICSR_WAIT); in sh_mobile_i2c_isr()
508 pd->sr |= SW_DONE; in sh_mobile_i2c_isr()
509 wake_up(&pd->wait); in sh_mobile_i2c_isr()
513 iic_rd(pd, ICSR); in sh_mobile_i2c_isr()
518 static void sh_mobile_i2c_dma_unmap(struct sh_mobile_i2c_data *pd) in sh_mobile_i2c_dma_unmap() argument
520 struct dma_chan *chan = pd->dma_direction == DMA_FROM_DEVICE in sh_mobile_i2c_dma_unmap()
521 ? pd->dma_rx : pd->dma_tx; in sh_mobile_i2c_dma_unmap()
523 dma_unmap_single(chan->device->dev, sg_dma_address(&pd->sg), in sh_mobile_i2c_dma_unmap()
524 pd->msg->len, pd->dma_direction); in sh_mobile_i2c_dma_unmap()
526 pd->dma_direction = DMA_NONE; in sh_mobile_i2c_dma_unmap()
529 static void sh_mobile_i2c_cleanup_dma(struct sh_mobile_i2c_data *pd) in sh_mobile_i2c_cleanup_dma() argument
531 if (pd->dma_direction == DMA_NONE) in sh_mobile_i2c_cleanup_dma()
533 else if (pd->dma_direction == DMA_FROM_DEVICE) in sh_mobile_i2c_cleanup_dma()
534 dmaengine_terminate_all(pd->dma_rx); in sh_mobile_i2c_cleanup_dma()
535 else if (pd->dma_direction == DMA_TO_DEVICE) in sh_mobile_i2c_cleanup_dma()
536 dmaengine_terminate_all(pd->dma_tx); in sh_mobile_i2c_cleanup_dma()
538 sh_mobile_i2c_dma_unmap(pd); in sh_mobile_i2c_cleanup_dma()
543 struct sh_mobile_i2c_data *pd = data; in sh_mobile_i2c_dma_callback() local
545 sh_mobile_i2c_dma_unmap(pd); in sh_mobile_i2c_dma_callback()
546 pd->pos = pd->msg->len; in sh_mobile_i2c_dma_callback()
547 pd->stop_after_dma = true; in sh_mobile_i2c_dma_callback()
549 iic_set_clr(pd, ICIC, 0, ICIC_TDMAE | ICIC_RDMAE); in sh_mobile_i2c_dma_callback()
588 static void sh_mobile_i2c_xfer_dma(struct sh_mobile_i2c_data *pd) in sh_mobile_i2c_xfer_dma() argument
590 bool read = pd->msg->flags & I2C_M_RD; in sh_mobile_i2c_xfer_dma()
592 struct dma_chan *chan = read ? pd->dma_rx : pd->dma_tx; in sh_mobile_i2c_xfer_dma()
599 chan = pd->dma_rx = sh_mobile_i2c_request_dma_chan(pd->dev, DMA_DEV_TO_MEM, in sh_mobile_i2c_xfer_dma()
600 pd->res->start + ICDR); in sh_mobile_i2c_xfer_dma()
602 chan = pd->dma_tx = sh_mobile_i2c_request_dma_chan(pd->dev, DMA_MEM_TO_DEV, in sh_mobile_i2c_xfer_dma()
603 pd->res->start + ICDR); in sh_mobile_i2c_xfer_dma()
609 dma_addr = dma_map_single(chan->device->dev, pd->msg->buf, pd->msg->len, dir); in sh_mobile_i2c_xfer_dma()
610 if (dma_mapping_error(pd->dev, dma_addr)) { in sh_mobile_i2c_xfer_dma()
611 dev_dbg(pd->dev, "dma map failed, using PIO\n"); in sh_mobile_i2c_xfer_dma()
615 sg_dma_len(&pd->sg) = pd->msg->len; in sh_mobile_i2c_xfer_dma()
616 sg_dma_address(&pd->sg) = dma_addr; in sh_mobile_i2c_xfer_dma()
618 pd->dma_direction = dir; in sh_mobile_i2c_xfer_dma()
620 txdesc = dmaengine_prep_slave_sg(chan, &pd->sg, 1, in sh_mobile_i2c_xfer_dma()
624 dev_dbg(pd->dev, "dma prep slave sg failed, using PIO\n"); in sh_mobile_i2c_xfer_dma()
625 sh_mobile_i2c_cleanup_dma(pd); in sh_mobile_i2c_xfer_dma()
630 txdesc->callback_param = pd; in sh_mobile_i2c_xfer_dma()
634 dev_dbg(pd->dev, "submitting dma failed, using PIO\n"); in sh_mobile_i2c_xfer_dma()
635 sh_mobile_i2c_cleanup_dma(pd); in sh_mobile_i2c_xfer_dma()
642 static int start_ch(struct sh_mobile_i2c_data *pd, struct i2c_msg *usr_msg, in start_ch() argument
646 dev_err(pd->dev, "Unsupported zero length i2c read\n"); in start_ch()
652 iic_set_clr(pd, ICCR, 0, ICCR_ICE); in start_ch()
655 iic_set_clr(pd, ICCR, ICCR_ICE, 0); in start_ch()
658 iic_wr(pd, ICCL, pd->iccl & 0xff); in start_ch()
659 iic_wr(pd, ICCH, pd->icch & 0xff); in start_ch()
662 pd->msg = usr_msg; in start_ch()
663 pd->pos = -1; in start_ch()
664 pd->sr = 0; in start_ch()
666 if (pd->msg->len > 8) in start_ch()
667 sh_mobile_i2c_xfer_dma(pd); in start_ch()
670 iic_wr(pd, ICIC, ICIC_DTEE | ICIC_WAITE | ICIC_ALE | ICIC_TACKE); in start_ch()
674 static int poll_dte(struct sh_mobile_i2c_data *pd) in poll_dte() argument
679 u_int8_t val = iic_rd(pd, ICSR); in poll_dte()
693 static int poll_busy(struct sh_mobile_i2c_data *pd) in poll_busy() argument
698 u_int8_t val = iic_rd(pd, ICSR); in poll_busy()
700 dev_dbg(pd->dev, "val 0x%02x pd->sr 0x%02x\n", val, pd->sr); in poll_busy()
708 val |= pd->sr; in poll_busy()
726 struct sh_mobile_i2c_data *pd = i2c_get_adapdata(adapter); in sh_mobile_i2c_xfer() local
731 activate_ch(pd); in sh_mobile_i2c_xfer()
735 bool do_start = pd->send_stop || !i; in sh_mobile_i2c_xfer()
737 pd->send_stop = i == num - 1 || msg->flags & I2C_M_STOP; in sh_mobile_i2c_xfer()
738 pd->stop_after_dma = false; in sh_mobile_i2c_xfer()
740 err = start_ch(pd, msg, do_start); in sh_mobile_i2c_xfer()
745 i2c_op(pd, OP_START, 0); in sh_mobile_i2c_xfer()
748 k = wait_event_timeout(pd->wait, in sh_mobile_i2c_xfer()
749 pd->sr & (ICSR_TACK | SW_DONE), in sh_mobile_i2c_xfer()
752 dev_err(pd->dev, "Transfer request timed out\n"); in sh_mobile_i2c_xfer()
753 if (pd->dma_direction != DMA_NONE) in sh_mobile_i2c_xfer()
754 sh_mobile_i2c_cleanup_dma(pd); in sh_mobile_i2c_xfer()
760 if (pd->send_stop) in sh_mobile_i2c_xfer()
761 err = poll_busy(pd); in sh_mobile_i2c_xfer()
763 err = poll_dte(pd); in sh_mobile_i2c_xfer()
768 deactivate_ch(pd); in sh_mobile_i2c_xfer()
806 static void sh_mobile_i2c_release_dma(struct sh_mobile_i2c_data *pd) in sh_mobile_i2c_release_dma() argument
808 if (!IS_ERR(pd->dma_tx)) { in sh_mobile_i2c_release_dma()
809 dma_release_channel(pd->dma_tx); in sh_mobile_i2c_release_dma()
810 pd->dma_tx = ERR_PTR(-EPROBE_DEFER); in sh_mobile_i2c_release_dma()
813 if (!IS_ERR(pd->dma_rx)) { in sh_mobile_i2c_release_dma()
814 dma_release_channel(pd->dma_rx); in sh_mobile_i2c_release_dma()
815 pd->dma_rx = ERR_PTR(-EPROBE_DEFER); in sh_mobile_i2c_release_dma()
819 static int sh_mobile_i2c_hook_irqs(struct platform_device *dev, struct sh_mobile_i2c_data *pd) in sh_mobile_i2c_hook_irqs() argument
828 0, dev_name(&dev->dev), pd); in sh_mobile_i2c_hook_irqs()
843 struct sh_mobile_i2c_data *pd; in sh_mobile_i2c_probe() local
849 pd = devm_kzalloc(&dev->dev, sizeof(struct sh_mobile_i2c_data), GFP_KERNEL); in sh_mobile_i2c_probe()
850 if (!pd) in sh_mobile_i2c_probe()
853 pd->clk = devm_clk_get(&dev->dev, NULL); in sh_mobile_i2c_probe()
854 if (IS_ERR(pd->clk)) { in sh_mobile_i2c_probe()
856 return PTR_ERR(pd->clk); in sh_mobile_i2c_probe()
859 ret = sh_mobile_i2c_hook_irqs(dev, pd); in sh_mobile_i2c_probe()
863 pd->dev = &dev->dev; in sh_mobile_i2c_probe()
864 platform_set_drvdata(dev, pd); in sh_mobile_i2c_probe()
868 pd->res = res; in sh_mobile_i2c_probe()
869 pd->reg = devm_ioremap_resource(&dev->dev, res); in sh_mobile_i2c_probe()
870 if (IS_ERR(pd->reg)) in sh_mobile_i2c_probe()
871 return PTR_ERR(pd->reg); in sh_mobile_i2c_probe()
875 pd->bus_speed = ret ? STANDARD_MODE : bus_speed; in sh_mobile_i2c_probe()
877 pd->clks_per_count = 1; in sh_mobile_i2c_probe()
887 pd->clks_per_count = config->clks_per_count; in sh_mobile_i2c_probe()
891 pd->bus_speed = pdata->bus_speed; in sh_mobile_i2c_probe()
893 pd->clks_per_count = pdata->clks_per_count; in sh_mobile_i2c_probe()
900 pd->flags |= IIC_FLAG_HAS_ICIC67; in sh_mobile_i2c_probe()
902 ret = sh_mobile_i2c_init(pd); in sh_mobile_i2c_probe()
907 sg_init_table(&pd->sg, 1); in sh_mobile_i2c_probe()
908 pd->dma_direction = DMA_NONE; in sh_mobile_i2c_probe()
909 pd->dma_rx = pd->dma_tx = ERR_PTR(-EPROBE_DEFER); in sh_mobile_i2c_probe()
925 adap = &pd->adap; in sh_mobile_i2c_probe()
926 i2c_set_adapdata(adap, pd); in sh_mobile_i2c_probe()
937 spin_lock_init(&pd->lock); in sh_mobile_i2c_probe()
938 init_waitqueue_head(&pd->wait); in sh_mobile_i2c_probe()
942 sh_mobile_i2c_release_dma(pd); in sh_mobile_i2c_probe()
947 dev_info(&dev->dev, "I2C adapter %d, bus speed %lu Hz\n", adap->nr, pd->bus_speed); in sh_mobile_i2c_probe()
954 struct sh_mobile_i2c_data *pd = platform_get_drvdata(dev); in sh_mobile_i2c_remove() local
956 i2c_del_adapter(&pd->adap); in sh_mobile_i2c_remove()
957 sh_mobile_i2c_release_dma(pd); in sh_mobile_i2c_remove()