diff options
author | Jean Delvare <khali@linux-fr.org> | 2009-03-06 10:05:43 -0500 |
---|---|---|
committer | Mauro Carvalho Chehab <mchehab@redhat.com> | 2009-03-30 11:43:11 -0400 |
commit | cea0c681bef872d0618d87be078cb006665a6fdf (patch) | |
tree | 6f0efeac300e293af83398c7a6c949e9bc2184e6 /drivers | |
parent | a0720d3b7b80163150fde73aa43ba8fcd417b9cb (diff) |
V4L/DVB (10867): vino: fold i2c-algo-sgi code into vino.
Signed-off-by: Jean Delvare <khali@linux-fr.org>
Signed-off-by: Hans Verkuil <hverkuil@xs4all.nl>
Signed-off-by: Mauro Carvalho Chehab <mchehab@redhat.com>
Diffstat (limited to 'drivers')
-rw-r--r-- | drivers/media/video/Kconfig | 1 | ||||
-rw-r--r-- | drivers/media/video/vino.c | 247 |
2 files changed, 194 insertions, 54 deletions
diff --git a/drivers/media/video/Kconfig b/drivers/media/video/Kconfig index 6c26618b8869..534a022c4d1b 100644 --- a/drivers/media/video/Kconfig +++ b/drivers/media/video/Kconfig | |||
@@ -582,7 +582,6 @@ config VIDEO_SAA5249 | |||
582 | config VIDEO_VINO | 582 | config VIDEO_VINO |
583 | tristate "SGI Vino Video For Linux (EXPERIMENTAL)" | 583 | tristate "SGI Vino Video For Linux (EXPERIMENTAL)" |
584 | depends on I2C && SGI_IP22 && EXPERIMENTAL && VIDEO_V4L2 | 584 | depends on I2C && SGI_IP22 && EXPERIMENTAL && VIDEO_V4L2 |
585 | select I2C_ALGO_SGI | ||
586 | select VIDEO_SAA7191 if VIDEO_HELPER_CHIPS_AUTO | 585 | select VIDEO_SAA7191 if VIDEO_HELPER_CHIPS_AUTO |
587 | help | 586 | help |
588 | Say Y here to build in support for the Vino video input system found | 587 | Say Y here to build in support for the Vino video input system found |
diff --git a/drivers/media/video/vino.c b/drivers/media/video/vino.c index 96ce68a3dd95..b62e030ba83a 100644 --- a/drivers/media/video/vino.c +++ b/drivers/media/video/vino.c | |||
@@ -33,7 +33,6 @@ | |||
33 | #include <linux/kmod.h> | 33 | #include <linux/kmod.h> |
34 | 34 | ||
35 | #include <linux/i2c.h> | 35 | #include <linux/i2c.h> |
36 | #include <linux/i2c-algo-sgi.h> | ||
37 | 36 | ||
38 | #include <linux/videodev2.h> | 37 | #include <linux/videodev2.h> |
39 | #include <media/v4l2-device.h> | 38 | #include <media/v4l2-device.h> |
@@ -141,6 +140,20 @@ MODULE_LICENSE("GPL"); | |||
141 | 140 | ||
142 | #define VINO_DATA_NORM_COUNT 4 | 141 | #define VINO_DATA_NORM_COUNT 4 |
143 | 142 | ||
143 | /* I2C controller flags */ | ||
144 | #define SGI_I2C_FORCE_IDLE (0 << 0) | ||
145 | #define SGI_I2C_NOT_IDLE (1 << 0) | ||
146 | #define SGI_I2C_WRITE (0 << 1) | ||
147 | #define SGI_I2C_READ (1 << 1) | ||
148 | #define SGI_I2C_RELEASE_BUS (0 << 2) | ||
149 | #define SGI_I2C_HOLD_BUS (1 << 2) | ||
150 | #define SGI_I2C_XFER_DONE (0 << 4) | ||
151 | #define SGI_I2C_XFER_BUSY (1 << 4) | ||
152 | #define SGI_I2C_ACK (0 << 5) | ||
153 | #define SGI_I2C_NACK (1 << 5) | ||
154 | #define SGI_I2C_BUS_OK (0 << 7) | ||
155 | #define SGI_I2C_BUS_ERR (1 << 7) | ||
156 | |||
144 | /* Internal data structure definitions */ | 157 | /* Internal data structure definitions */ |
145 | 158 | ||
146 | struct vino_input { | 159 | struct vino_input { |
@@ -640,56 +653,6 @@ struct v4l2_queryctrl vino_saa7191_v4l2_controls[] = { | |||
640 | } | 653 | } |
641 | }; | 654 | }; |
642 | 655 | ||
643 | /* VINO I2C bus functions */ | ||
644 | |||
645 | unsigned i2c_vino_getctrl(void *data) | ||
646 | { | ||
647 | return vino->i2c_control; | ||
648 | } | ||
649 | |||
650 | void i2c_vino_setctrl(void *data, unsigned val) | ||
651 | { | ||
652 | vino->i2c_control = val; | ||
653 | } | ||
654 | |||
655 | unsigned i2c_vino_rdata(void *data) | ||
656 | { | ||
657 | return vino->i2c_data; | ||
658 | } | ||
659 | |||
660 | void i2c_vino_wdata(void *data, unsigned val) | ||
661 | { | ||
662 | vino->i2c_data = val; | ||
663 | } | ||
664 | |||
665 | static struct i2c_algo_sgi_data i2c_sgi_vino_data = | ||
666 | { | ||
667 | .getctrl = &i2c_vino_getctrl, | ||
668 | .setctrl = &i2c_vino_setctrl, | ||
669 | .rdata = &i2c_vino_rdata, | ||
670 | .wdata = &i2c_vino_wdata, | ||
671 | .xfer_timeout = 200, | ||
672 | .ack_timeout = 1000, | ||
673 | }; | ||
674 | |||
675 | static struct i2c_adapter vino_i2c_adapter = | ||
676 | { | ||
677 | .name = "VINO I2C bus", | ||
678 | .id = I2C_HW_SGI_VINO, | ||
679 | .algo_data = &i2c_sgi_vino_data, | ||
680 | .owner = THIS_MODULE, | ||
681 | }; | ||
682 | |||
683 | static int vino_i2c_add_bus(void) | ||
684 | { | ||
685 | return i2c_sgi_add_bus(&vino_i2c_adapter); | ||
686 | } | ||
687 | |||
688 | static int vino_i2c_del_bus(void) | ||
689 | { | ||
690 | return i2c_del_adapter(&vino_i2c_adapter); | ||
691 | } | ||
692 | |||
693 | /* VINO framebuffer/DMA descriptor management */ | 656 | /* VINO framebuffer/DMA descriptor management */ |
694 | 657 | ||
695 | static void vino_free_buffer_with_count(struct vino_framebuffer *fb, | 658 | static void vino_free_buffer_with_count(struct vino_framebuffer *fb, |
@@ -1635,6 +1598,184 @@ static inline void vino_set_default_framerate(struct | |||
1635 | vino_set_framerate(vcs, vino_data_norms[vcs->data_norm].fps_max); | 1598 | vino_set_framerate(vcs, vino_data_norms[vcs->data_norm].fps_max); |
1636 | } | 1599 | } |
1637 | 1600 | ||
1601 | /* VINO I2C bus functions */ | ||
1602 | |||
1603 | struct i2c_algo_sgi_data { | ||
1604 | void *data; /* private data for lowlevel routines */ | ||
1605 | unsigned (*getctrl)(void *data); | ||
1606 | void (*setctrl)(void *data, unsigned val); | ||
1607 | unsigned (*rdata)(void *data); | ||
1608 | void (*wdata)(void *data, unsigned val); | ||
1609 | |||
1610 | int xfer_timeout; | ||
1611 | int ack_timeout; | ||
1612 | }; | ||
1613 | |||
1614 | static int wait_xfer_done(struct i2c_algo_sgi_data *adap) | ||
1615 | { | ||
1616 | int i; | ||
1617 | |||
1618 | for (i = 0; i < adap->xfer_timeout; i++) { | ||
1619 | if ((adap->getctrl(adap->data) & SGI_I2C_XFER_BUSY) == 0) | ||
1620 | return 0; | ||
1621 | udelay(1); | ||
1622 | } | ||
1623 | |||
1624 | return -ETIMEDOUT; | ||
1625 | } | ||
1626 | |||
1627 | static int wait_ack(struct i2c_algo_sgi_data *adap) | ||
1628 | { | ||
1629 | int i; | ||
1630 | |||
1631 | if (wait_xfer_done(adap)) | ||
1632 | return -ETIMEDOUT; | ||
1633 | for (i = 0; i < adap->ack_timeout; i++) { | ||
1634 | if ((adap->getctrl(adap->data) & SGI_I2C_NACK) == 0) | ||
1635 | return 0; | ||
1636 | udelay(1); | ||
1637 | } | ||
1638 | |||
1639 | return -ETIMEDOUT; | ||
1640 | } | ||
1641 | |||
1642 | static int force_idle(struct i2c_algo_sgi_data *adap) | ||
1643 | { | ||
1644 | int i; | ||
1645 | |||
1646 | adap->setctrl(adap->data, SGI_I2C_FORCE_IDLE); | ||
1647 | for (i = 0; i < adap->xfer_timeout; i++) { | ||
1648 | if ((adap->getctrl(adap->data) & SGI_I2C_NOT_IDLE) == 0) | ||
1649 | goto out; | ||
1650 | udelay(1); | ||
1651 | } | ||
1652 | return -ETIMEDOUT; | ||
1653 | out: | ||
1654 | if (adap->getctrl(adap->data) & SGI_I2C_BUS_ERR) | ||
1655 | return -EIO; | ||
1656 | return 0; | ||
1657 | } | ||
1658 | |||
1659 | static int do_address(struct i2c_algo_sgi_data *adap, unsigned int addr, | ||
1660 | int rd) | ||
1661 | { | ||
1662 | if (rd) | ||
1663 | adap->setctrl(adap->data, SGI_I2C_NOT_IDLE); | ||
1664 | /* Check if bus is idle, eventually force it to do so */ | ||
1665 | if (adap->getctrl(adap->data) & SGI_I2C_NOT_IDLE) | ||
1666 | if (force_idle(adap)) | ||
1667 | return -EIO; | ||
1668 | /* Write out the i2c chip address and specify operation */ | ||
1669 | adap->setctrl(adap->data, | ||
1670 | SGI_I2C_HOLD_BUS | SGI_I2C_WRITE | SGI_I2C_NOT_IDLE); | ||
1671 | if (rd) | ||
1672 | addr |= 1; | ||
1673 | adap->wdata(adap->data, addr); | ||
1674 | if (wait_ack(adap)) | ||
1675 | return -EIO; | ||
1676 | return 0; | ||
1677 | } | ||
1678 | |||
1679 | static int i2c_read(struct i2c_algo_sgi_data *adap, unsigned char *buf, | ||
1680 | unsigned int len) | ||
1681 | { | ||
1682 | int i; | ||
1683 | |||
1684 | adap->setctrl(adap->data, | ||
1685 | SGI_I2C_HOLD_BUS | SGI_I2C_READ | SGI_I2C_NOT_IDLE); | ||
1686 | for (i = 0; i < len; i++) { | ||
1687 | if (wait_xfer_done(adap)) | ||
1688 | return -EIO; | ||
1689 | buf[i] = adap->rdata(adap->data); | ||
1690 | } | ||
1691 | adap->setctrl(adap->data, SGI_I2C_RELEASE_BUS | SGI_I2C_FORCE_IDLE); | ||
1692 | |||
1693 | return 0; | ||
1694 | |||
1695 | } | ||
1696 | |||
1697 | static int i2c_write(struct i2c_algo_sgi_data *adap, unsigned char *buf, | ||
1698 | unsigned int len) | ||
1699 | { | ||
1700 | int i; | ||
1701 | |||
1702 | /* We are already in write state */ | ||
1703 | for (i = 0; i < len; i++) { | ||
1704 | adap->wdata(adap->data, buf[i]); | ||
1705 | if (wait_ack(adap)) | ||
1706 | return -EIO; | ||
1707 | } | ||
1708 | return 0; | ||
1709 | } | ||
1710 | |||
1711 | static int sgi_xfer(struct i2c_adapter *i2c_adap, struct i2c_msg *msgs, | ||
1712 | int num) | ||
1713 | { | ||
1714 | struct i2c_algo_sgi_data *adap = i2c_adap->algo_data; | ||
1715 | struct i2c_msg *p; | ||
1716 | int i, err = 0; | ||
1717 | |||
1718 | for (i = 0; !err && i < num; i++) { | ||
1719 | p = &msgs[i]; | ||
1720 | err = do_address(adap, p->addr, p->flags & I2C_M_RD); | ||
1721 | if (err || !p->len) | ||
1722 | continue; | ||
1723 | if (p->flags & I2C_M_RD) | ||
1724 | err = i2c_read(adap, p->buf, p->len); | ||
1725 | else | ||
1726 | err = i2c_write(adap, p->buf, p->len); | ||
1727 | } | ||
1728 | |||
1729 | return (err < 0) ? err : i; | ||
1730 | } | ||
1731 | |||
1732 | static u32 sgi_func(struct i2c_adapter *adap) | ||
1733 | { | ||
1734 | return I2C_FUNC_SMBUS_EMUL; | ||
1735 | } | ||
1736 | |||
1737 | static const struct i2c_algorithm sgi_algo = { | ||
1738 | .master_xfer = sgi_xfer, | ||
1739 | .functionality = sgi_func, | ||
1740 | }; | ||
1741 | |||
1742 | static unsigned i2c_vino_getctrl(void *data) | ||
1743 | { | ||
1744 | return vino->i2c_control; | ||
1745 | } | ||
1746 | |||
1747 | static void i2c_vino_setctrl(void *data, unsigned val) | ||
1748 | { | ||
1749 | vino->i2c_control = val; | ||
1750 | } | ||
1751 | |||
1752 | static unsigned i2c_vino_rdata(void *data) | ||
1753 | { | ||
1754 | return vino->i2c_data; | ||
1755 | } | ||
1756 | |||
1757 | static void i2c_vino_wdata(void *data, unsigned val) | ||
1758 | { | ||
1759 | vino->i2c_data = val; | ||
1760 | } | ||
1761 | |||
1762 | static struct i2c_algo_sgi_data i2c_sgi_vino_data = { | ||
1763 | .getctrl = &i2c_vino_getctrl, | ||
1764 | .setctrl = &i2c_vino_setctrl, | ||
1765 | .rdata = &i2c_vino_rdata, | ||
1766 | .wdata = &i2c_vino_wdata, | ||
1767 | .xfer_timeout = 200, | ||
1768 | .ack_timeout = 1000, | ||
1769 | }; | ||
1770 | |||
1771 | static struct i2c_adapter vino_i2c_adapter = { | ||
1772 | .name = "VINO I2C bus", | ||
1773 | .id = I2C_HW_SGI_VINO, | ||
1774 | .algo = &sgi_algo, | ||
1775 | .algo_data = &i2c_sgi_vino_data, | ||
1776 | .owner = THIS_MODULE, | ||
1777 | }; | ||
1778 | |||
1638 | /* | 1779 | /* |
1639 | * Prepare VINO for DMA transfer... | 1780 | * Prepare VINO for DMA transfer... |
1640 | * (execute only with vino_lock and input_lock locked) | 1781 | * (execute only with vino_lock and input_lock locked) |
@@ -3999,7 +4140,7 @@ static void vino_module_cleanup(int stage) | |||
3999 | video_unregister_device(vino_drvdata->a.vdev); | 4140 | video_unregister_device(vino_drvdata->a.vdev); |
4000 | vino_drvdata->a.vdev = NULL; | 4141 | vino_drvdata->a.vdev = NULL; |
4001 | case 9: | 4142 | case 9: |
4002 | vino_i2c_del_bus(); | 4143 | i2c_del_adapter(&vino_i2c_adapter); |
4003 | case 8: | 4144 | case 8: |
4004 | free_irq(SGI_VINO_IRQ, NULL); | 4145 | free_irq(SGI_VINO_IRQ, NULL); |
4005 | case 7: | 4146 | case 7: |
@@ -4222,7 +4363,7 @@ static int __init vino_module_init(void) | |||
4222 | } | 4363 | } |
4223 | vino_init_stage++; | 4364 | vino_init_stage++; |
4224 | 4365 | ||
4225 | ret = vino_i2c_add_bus(); | 4366 | ret = i2c_add_adapter(&vino_i2c_adapter); |
4226 | if (ret) { | 4367 | if (ret) { |
4227 | printk(KERN_ERR "VINO I2C bus registration failed\n"); | 4368 | printk(KERN_ERR "VINO I2C bus registration failed\n"); |
4228 | vino_module_cleanup(vino_init_stage); | 4369 | vino_module_cleanup(vino_init_stage); |