aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorGreg Kroah-Hartman <gregkh@linuxfoundation.org>2017-03-22 07:03:17 -0400
committerGreg Kroah-Hartman <gregkh@linuxfoundation.org>2017-03-22 07:03:17 -0400
commit5c1724c42dc1d60addaa67106a4f25c2a9a140de (patch)
treecfc93ca64d0d5ee1075c5a2d7ed2b83f22b77edd
parentc3423563c68fc454b805b46cb69fd4816db933e2 (diff)
parent70216fd937fea79c20705400540fa48f86ddf1c5 (diff)
Merge tag 'extcon-fixes-for-4.11-rc3' of git://git.kernel.org/pub/scm/linux/kernel/git/chanwoo/extcon into char-misc-linus
Chanwoo writes: Update extcon for v4.11-rc3 This patch fixes issues for Intel INT3496 ACPI device as following: - Propagate error code of gpiod_to_irq(). - Set the ID pin as the input direction if firmware has the bug - Rename the gpio name for bining according to the documentation. - Add gpio acpi mapping table and the dependency on X86. - Use the devm_gpiod_get() instead of gpiod_get_index because of acpi mapping table.
-rw-r--r--Documentation/extcon/intel-int3496.txt5
-rw-r--r--drivers/extcon/Kconfig2
-rw-r--r--drivers/extcon/extcon-intel-int3496.c39
3 files changed, 34 insertions, 12 deletions
diff --git a/Documentation/extcon/intel-int3496.txt b/Documentation/extcon/intel-int3496.txt
index af0b366c25b7..8155dbc7fad3 100644
--- a/Documentation/extcon/intel-int3496.txt
+++ b/Documentation/extcon/intel-int3496.txt
@@ -20,3 +20,8 @@ Index 1: The output gpio for enabling Vbus output from the device to the otg
20Index 2: The output gpio for muxing of the data pins between the USB host and 20Index 2: The output gpio for muxing of the data pins between the USB host and
21 the USB peripheral controller, write 1 to mux to the peripheral 21 the USB peripheral controller, write 1 to mux to the peripheral
22 controller 22 controller
23
24There is a mapping between indices and GPIO connection IDs as follows
25 id index 0
26 vbus index 1
27 mux index 2
diff --git a/drivers/extcon/Kconfig b/drivers/extcon/Kconfig
index 96bbae579c0b..fc09c76248b4 100644
--- a/drivers/extcon/Kconfig
+++ b/drivers/extcon/Kconfig
@@ -44,7 +44,7 @@ config EXTCON_GPIO
44 44
45config EXTCON_INTEL_INT3496 45config EXTCON_INTEL_INT3496
46 tristate "Intel INT3496 ACPI device extcon driver" 46 tristate "Intel INT3496 ACPI device extcon driver"
47 depends on GPIOLIB && ACPI 47 depends on GPIOLIB && ACPI && (X86 || COMPILE_TEST)
48 help 48 help
49 Say Y here to enable extcon support for USB OTG ports controlled by 49 Say Y here to enable extcon support for USB OTG ports controlled by
50 an Intel INT3496 ACPI device. 50 an Intel INT3496 ACPI device.
diff --git a/drivers/extcon/extcon-intel-int3496.c b/drivers/extcon/extcon-intel-int3496.c
index a3131b036de6..9d17984bbbd4 100644
--- a/drivers/extcon/extcon-intel-int3496.c
+++ b/drivers/extcon/extcon-intel-int3496.c
@@ -45,6 +45,17 @@ static const unsigned int int3496_cable[] = {
45 EXTCON_NONE, 45 EXTCON_NONE,
46}; 46};
47 47
48static const struct acpi_gpio_params id_gpios = { INT3496_GPIO_USB_ID, 0, false };
49static const struct acpi_gpio_params vbus_gpios = { INT3496_GPIO_VBUS_EN, 0, false };
50static const struct acpi_gpio_params mux_gpios = { INT3496_GPIO_USB_MUX, 0, false };
51
52static const struct acpi_gpio_mapping acpi_int3496_default_gpios[] = {
53 { "id-gpios", &id_gpios, 1 },
54 { "vbus-gpios", &vbus_gpios, 1 },
55 { "mux-gpios", &mux_gpios, 1 },
56 { },
57};
58
48static void int3496_do_usb_id(struct work_struct *work) 59static void int3496_do_usb_id(struct work_struct *work)
49{ 60{
50 struct int3496_data *data = 61 struct int3496_data *data =
@@ -83,6 +94,13 @@ static int int3496_probe(struct platform_device *pdev)
83 struct int3496_data *data; 94 struct int3496_data *data;
84 int ret; 95 int ret;
85 96
97 ret = acpi_dev_add_driver_gpios(ACPI_COMPANION(dev),
98 acpi_int3496_default_gpios);
99 if (ret) {
100 dev_err(dev, "can't add GPIO ACPI mapping\n");
101 return ret;
102 }
103
86 data = devm_kzalloc(dev, sizeof(*data), GFP_KERNEL); 104 data = devm_kzalloc(dev, sizeof(*data), GFP_KERNEL);
87 if (!data) 105 if (!data)
88 return -ENOMEM; 106 return -ENOMEM;
@@ -90,30 +108,27 @@ static int int3496_probe(struct platform_device *pdev)
90 data->dev = dev; 108 data->dev = dev;
91 INIT_DELAYED_WORK(&data->work, int3496_do_usb_id); 109 INIT_DELAYED_WORK(&data->work, int3496_do_usb_id);
92 110
93 data->gpio_usb_id = devm_gpiod_get_index(dev, "id", 111 data->gpio_usb_id = devm_gpiod_get(dev, "id", GPIOD_IN);
94 INT3496_GPIO_USB_ID,
95 GPIOD_IN);
96 if (IS_ERR(data->gpio_usb_id)) { 112 if (IS_ERR(data->gpio_usb_id)) {
97 ret = PTR_ERR(data->gpio_usb_id); 113 ret = PTR_ERR(data->gpio_usb_id);
98 dev_err(dev, "can't request USB ID GPIO: %d\n", ret); 114 dev_err(dev, "can't request USB ID GPIO: %d\n", ret);
99 return ret; 115 return ret;
116 } else if (gpiod_get_direction(data->gpio_usb_id) != GPIOF_DIR_IN) {
117 dev_warn(dev, FW_BUG "USB ID GPIO not in input mode, fixing\n");
118 gpiod_direction_input(data->gpio_usb_id);
100 } 119 }
101 120
102 data->usb_id_irq = gpiod_to_irq(data->gpio_usb_id); 121 data->usb_id_irq = gpiod_to_irq(data->gpio_usb_id);
103 if (data->usb_id_irq <= 0) { 122 if (data->usb_id_irq < 0) {
104 dev_err(dev, "can't get USB ID IRQ: %d\n", data->usb_id_irq); 123 dev_err(dev, "can't get USB ID IRQ: %d\n", data->usb_id_irq);
105 return -EINVAL; 124 return data->usb_id_irq;
106 } 125 }
107 126
108 data->gpio_vbus_en = devm_gpiod_get_index(dev, "vbus en", 127 data->gpio_vbus_en = devm_gpiod_get(dev, "vbus", GPIOD_ASIS);
109 INT3496_GPIO_VBUS_EN,
110 GPIOD_ASIS);
111 if (IS_ERR(data->gpio_vbus_en)) 128 if (IS_ERR(data->gpio_vbus_en))
112 dev_info(dev, "can't request VBUS EN GPIO\n"); 129 dev_info(dev, "can't request VBUS EN GPIO\n");
113 130
114 data->gpio_usb_mux = devm_gpiod_get_index(dev, "usb mux", 131 data->gpio_usb_mux = devm_gpiod_get(dev, "mux", GPIOD_ASIS);
115 INT3496_GPIO_USB_MUX,
116 GPIOD_ASIS);
117 if (IS_ERR(data->gpio_usb_mux)) 132 if (IS_ERR(data->gpio_usb_mux))
118 dev_info(dev, "can't request USB MUX GPIO\n"); 133 dev_info(dev, "can't request USB MUX GPIO\n");
119 134
@@ -154,6 +169,8 @@ static int int3496_remove(struct platform_device *pdev)
154 devm_free_irq(&pdev->dev, data->usb_id_irq, data); 169 devm_free_irq(&pdev->dev, data->usb_id_irq, data);
155 cancel_delayed_work_sync(&data->work); 170 cancel_delayed_work_sync(&data->work);
156 171
172 acpi_dev_remove_driver_gpios(ACPI_COMPANION(&pdev->dev));
173
157 return 0; 174 return 0;
158} 175}
159 176