summaryrefslogtreecommitdiff
path: root/drivers/media/pci/solo6x10
diff options
context:
space:
mode:
authorLinus Torvalds <torvalds@linux-foundation.org>2017-09-07 12:53:14 -0700
committerLinus Torvalds <torvalds@linux-foundation.org>2017-09-07 12:53:14 -0700
commitc0da4fa0d1a54495d6055c009ac46b76d1da2c86 (patch)
tree81b00d651c7fd8adf91984c69331074af2a71c32 /drivers/media/pci/solo6x10
parentd969443064abf2f51510559a5b01325eaabfcb1d (diff)
parent1efdf1776e2253b77413c997bed862410e4b6aaf (diff)
Merge tag 'media/v4.14-1' of git://git.kernel.org/pub/scm/linux/kernel/git/mchehab/linux-media
Pull media updates from Mauro Carvalho Chehab: "Brazil's Independence Day pull request :-) This is one of the biggest media pull requests, with 625 patches affecting almost all parts of media (RC, DVB, V4L2, CEC, docs). This contains: - A lot of new drivers: * DVB frontends: mxl5xx, stv0910, stv6111; * camera flash: as3645a led driver; * HDMI receiver: adv748X; * camera sensor: Omnivision 6650 5M driver (ov6650); * HDMI CEC: ao-cec meson driver; * V4L2: Qualcom camss driver; * Remote controller: gpio-ir-tx, pwm-ir-tx and zx-irdec drivers. - The DDbridge DVB driver got a massive update, with makes it in sync with modern hardware from that vendor; - There's an important milestone on this series: the DVB documentation was written in 2003, but only started to be updated in 2007. It also used to contain several gaps from the time it was kept out of tree, mentioning error codes and device nodes that never existed upstream. On this series, it received a massive update: all non-deprecated digital TV APIs are now in sync with the current implementation; - Some DVB APIs that aren't used by any upstream driver got removed; - Other parts of the media documentation algo got updated, fixing some bugs on its PDF output and making it compatible with Sphinx version 1.6. As the number of hacks required to build PDF output reduced, I hope we'll have less troubles as newer versions of our documentation toolchain are released (famous last words); - As usual, lots of driver cleanups and improvements" * tag 'media/v4.14-1' of git://git.kernel.org/pub/scm/linux/kernel/git/mchehab/linux-media: (624 commits) media: leds: as3645a: add V4L2_FLASH_LED_CLASS dependency media: get rid of removed DMX_GET_CAPS and DMX_SET_SOURCE leftovers media: Revert "[media] v4l: async: make v4l2 coexist with devicetree nodes in a dt overlay" media: staging: atomisp: sh_css_calloc shall return a pointer to the allocated space media: Revert "[media] lirc_dev: remove superfluous get/put_device() calls" media: add qcom_camss.rst to v4l-drivers rst file media: dvb headers: make checkpatch happier media: dvb uapi: move frontend legacy API to another part of the book media: pixfmt-srggb12p.rst: better format the table for PDF output media: docs-rst: media: Don't use \small for V4L2_PIX_FMT_SRGGB10 documentation media: index.rst: don't write "Contents:" on PDF output media: pixfmt*.rst: replace a two dots by a comma media: vidioc-g-fmt.rst: adjust table format media: vivid.rst: add a blank line to correct ReST format media: v4l2 uapi book: get rid of driver programming's chapter media: format.rst: use the right markup for important notes media: docs-rst: cardlists: change their format to flat-tables media: em28xx-cardlist.rst: update to reflect last changes media: v4l2-event.rst: adjust table to fit on PDF output media: docs: don't show ToC for each part on PDF output ...
Diffstat (limited to 'drivers/media/pci/solo6x10')
-rw-r--r--drivers/media/pci/solo6x10/solo6x10-g723.c2
-rw-r--r--drivers/media/pci/solo6x10/solo6x10-gpio.c97
-rw-r--r--drivers/media/pci/solo6x10/solo6x10-tw28.c3
-rw-r--r--drivers/media/pci/solo6x10/solo6x10-v4l2.c2
-rw-r--r--drivers/media/pci/solo6x10/solo6x10.h5
5 files changed, 106 insertions, 3 deletions
diff --git a/drivers/media/pci/solo6x10/solo6x10-g723.c b/drivers/media/pci/solo6x10/solo6x10-g723.c
index 3ca947092775..81be1b8df758 100644
--- a/drivers/media/pci/solo6x10/solo6x10-g723.c
+++ b/drivers/media/pci/solo6x10/solo6x10-g723.c
@@ -319,7 +319,7 @@ static int snd_solo_capture_volume_put(struct snd_kcontrol *kcontrol,
return 1;
}
-static struct snd_kcontrol_new snd_solo_capture_volume = {
+static const struct snd_kcontrol_new snd_solo_capture_volume = {
.iface = SNDRV_CTL_ELEM_IFACE_MIXER,
.name = "Capture Volume",
.info = snd_solo_capture_volume_info,
diff --git a/drivers/media/pci/solo6x10/solo6x10-gpio.c b/drivers/media/pci/solo6x10/solo6x10-gpio.c
index 6d3b4a36bc11..3d0d1aa2f6a8 100644
--- a/drivers/media/pci/solo6x10/solo6x10-gpio.c
+++ b/drivers/media/pci/solo6x10/solo6x10-gpio.c
@@ -57,6 +57,9 @@ static void solo_gpio_mode(struct solo_dev *solo_dev,
ret |= 1 << port;
}
+ /* Enable GPIO[31:16] */
+ ret |= 0xffff0000;
+
solo_reg_write(solo_dev, SOLO_GPIO_CONFIG_1, ret);
}
@@ -90,16 +93,110 @@ static void solo_gpio_config(struct solo_dev *solo_dev)
/* Initially set relay status to 0 */
solo_gpio_clear(solo_dev, 0xff00);
+
+ /* Set input pins direction */
+ solo_gpio_mode(solo_dev, 0xffff0000, 0);
+}
+
+#ifdef CONFIG_GPIOLIB
+/* Pins 0-7 are not exported, because it seems from code above they are
+ * used for internal purposes. So offset 0 corresponds to pin 8, therefore
+ * offsets 0-7 are relay GPIOs, 8-23 - input GPIOs.
+ */
+static int solo_gpiochip_get_direction(struct gpio_chip *chip,
+ unsigned int offset)
+{
+ int ret, mode;
+ struct solo_dev *solo_dev = gpiochip_get_data(chip);
+
+ if (offset < 8) {
+ ret = solo_reg_read(solo_dev, SOLO_GPIO_CONFIG_0);
+ mode = 3 & (ret >> ((offset + 8) * 2));
+ } else {
+ ret = solo_reg_read(solo_dev, SOLO_GPIO_CONFIG_1);
+ mode = 1 & (ret >> (offset - 8));
+ }
+
+ if (!mode)
+ return 1;
+ else if (mode == 1)
+ return 0;
+
+ return -1;
}
+static int solo_gpiochip_direction_input(struct gpio_chip *chip,
+ unsigned int offset)
+{
+ return -1;
+}
+
+static int solo_gpiochip_direction_output(struct gpio_chip *chip,
+ unsigned int offset, int value)
+{
+ return -1;
+}
+
+static int solo_gpiochip_get(struct gpio_chip *chip,
+ unsigned int offset)
+{
+ int ret;
+ struct solo_dev *solo_dev = gpiochip_get_data(chip);
+
+ ret = solo_reg_read(solo_dev, SOLO_GPIO_DATA_IN);
+
+ return 1 & (ret >> (offset + 8));
+}
+
+static void solo_gpiochip_set(struct gpio_chip *chip,
+ unsigned int offset, int value)
+{
+ struct solo_dev *solo_dev = gpiochip_get_data(chip);
+
+ if (value)
+ solo_gpio_set(solo_dev, 1 << (offset + 8));
+ else
+ solo_gpio_clear(solo_dev, 1 << (offset + 8));
+}
+#endif
+
int solo_gpio_init(struct solo_dev *solo_dev)
{
+ int ret;
+
solo_gpio_config(solo_dev);
+#ifdef CONFIG_GPIOLIB
+ solo_dev->gpio_dev.label = SOLO6X10_NAME"_gpio";
+ solo_dev->gpio_dev.parent = &solo_dev->pdev->dev;
+ solo_dev->gpio_dev.owner = THIS_MODULE;
+ solo_dev->gpio_dev.base = -1;
+ solo_dev->gpio_dev.ngpio = 24;
+ solo_dev->gpio_dev.can_sleep = 0;
+
+ solo_dev->gpio_dev.get_direction = solo_gpiochip_get_direction;
+ solo_dev->gpio_dev.direction_input = solo_gpiochip_direction_input;
+ solo_dev->gpio_dev.direction_output = solo_gpiochip_direction_output;
+ solo_dev->gpio_dev.get = solo_gpiochip_get;
+ solo_dev->gpio_dev.set = solo_gpiochip_set;
+
+ ret = gpiochip_add_data(&solo_dev->gpio_dev, solo_dev);
+
+ if (ret) {
+ solo_dev->gpio_dev.label = NULL;
+ return -1;
+ }
+#endif
return 0;
}
void solo_gpio_exit(struct solo_dev *solo_dev)
{
+#ifdef CONFIG_GPIOLIB
+ if (solo_dev->gpio_dev.label) {
+ gpiochip_remove(&solo_dev->gpio_dev);
+ solo_dev->gpio_dev.label = NULL;
+ }
+#endif
solo_gpio_clear(solo_dev, 0x30);
solo_gpio_config(solo_dev);
}
diff --git a/drivers/media/pci/solo6x10/solo6x10-tw28.c b/drivers/media/pci/solo6x10/solo6x10-tw28.c
index 0632d3f7c73c..7ecb725b6dd2 100644
--- a/drivers/media/pci/solo6x10/solo6x10-tw28.c
+++ b/drivers/media/pci/solo6x10/solo6x10-tw28.c
@@ -532,7 +532,7 @@ static void saa712x_write_regs(struct solo_dev *dev, const u8 *vals,
static void saa712x_setup(struct solo_dev *dev)
{
const int reg_start = 0x26;
- const u8 saa7128_regs_ntsc[] = {
+ static const u8 saa7128_regs_ntsc[] = {
/* :0x26 */
0x0d, 0x00,
/* :0x28 */
@@ -606,6 +606,7 @@ int solo_tw28_init(struct solo_dev *solo_dev)
solo_dev->tw28_cnt++;
break;
case 0x0c:
+ case 0x0d:
solo_dev->tw2864 |= 1 << i;
solo_dev->tw28_cnt++;
break;
diff --git a/drivers/media/pci/solo6x10/solo6x10-v4l2.c b/drivers/media/pci/solo6x10/solo6x10-v4l2.c
index 3266fc21825f..99ffd1ed4a73 100644
--- a/drivers/media/pci/solo6x10/solo6x10-v4l2.c
+++ b/drivers/media/pci/solo6x10/solo6x10-v4l2.c
@@ -630,7 +630,7 @@ static const struct v4l2_ioctl_ops solo_v4l2_ioctl_ops = {
.vidioc_unsubscribe_event = v4l2_event_unsubscribe,
};
-static struct video_device solo_v4l2_template = {
+static const struct video_device solo_v4l2_template = {
.name = SOLO6X10_NAME,
.fops = &solo_v4l2_fops,
.ioctl_ops = &solo_v4l2_ioctl_ops,
diff --git a/drivers/media/pci/solo6x10/solo6x10.h b/drivers/media/pci/solo6x10/solo6x10.h
index 3f8da5e8c430..3a1893ae2dad 100644
--- a/drivers/media/pci/solo6x10/solo6x10.h
+++ b/drivers/media/pci/solo6x10/solo6x10.h
@@ -31,6 +31,7 @@
#include <linux/atomic.h>
#include <linux/slab.h>
#include <linux/videodev2.h>
+#include <linux/gpio/driver.h>
#include <media/v4l2-dev.h>
#include <media/v4l2-device.h>
@@ -199,6 +200,10 @@ struct solo_dev {
u32 irq_mask;
u32 motion_mask;
struct v4l2_device v4l2_dev;
+#ifdef CONFIG_GPIOLIB
+ /* GPIO */
+ struct gpio_chip gpio_dev;
+#endif
/* tw28xx accounting */
u8 tw2865, tw2864, tw2815;