Donate to e Foundation | Murena handsets with /e/OS | Own a part of Murena! Learn more

Commit 054d4b7b authored by Wenyou Yang's avatar Wenyou Yang Committed by Greg Kroah-Hartman
Browse files

usb: ohci-at91: Use descriptor-based gpio APIs



Use the descriptor-based interface to manipulate GPIOs, instead of
the legacy integer-based interface.

Signed-off-by: default avatarWenyou Yang <wenyou.yang@atmel.com>
Signed-off-by: default avatarGreg Kroah-Hartman <gregkh@linuxfoundation.org>
parent 629dd219
Loading
Loading
Loading
Loading
+31 −90
Original line number Diff line number Diff line
@@ -14,8 +14,8 @@

#include <linux/clk.h>
#include <linux/dma-mapping.h>
#include <linux/gpio/consumer.h>
#include <linux/of_platform.h>
#include <linux/of_gpio.h>
#include <linux/platform_device.h>
#include <linux/platform_data/atmel.h>
#include <linux/io.h>
@@ -39,8 +39,8 @@

#define AT91_MAX_USBH_PORTS	3
struct at91_usbh_data {
	int vbus_pin[AT91_MAX_USBH_PORTS];	/* port power-control pin */
	int overcurrent_pin[AT91_MAX_USBH_PORTS];
	struct gpio_desc *vbus_pin[AT91_MAX_USBH_PORTS];
	struct gpio_desc *overcurrent_pin[AT91_MAX_USBH_PORTS];
	u8 ports;				/* number of ports on root hub */
	u8 overcurrent_supported;
	u8 vbus_pin_active_low[AT91_MAX_USBH_PORTS];
@@ -262,10 +262,7 @@ static void ohci_at91_usb_set_power(struct at91_usbh_data *pdata, int port, int
	if (!valid_port(port))
		return;

	if (!gpio_is_valid(pdata->vbus_pin[port]))
		return;

	gpio_set_value(pdata->vbus_pin[port],
	gpiod_set_value(pdata->vbus_pin[port],
			pdata->vbus_pin_active_low[port] ^ enable);
}

@@ -274,10 +271,7 @@ static int ohci_at91_usb_get_power(struct at91_usbh_data *pdata, int port)
	if (!valid_port(port))
		return -EINVAL;

	if (!gpio_is_valid(pdata->vbus_pin[port]))
		return -EINVAL;

	return gpio_get_value(pdata->vbus_pin[port]) ^
	return gpiod_get_value(pdata->vbus_pin[port]) ^
	       pdata->vbus_pin_active_low[port];
}

@@ -468,24 +462,21 @@ static irqreturn_t ohci_hcd_at91_overcurrent_irq(int irq, void *data)
{
	struct platform_device *pdev = data;
	struct at91_usbh_data *pdata = dev_get_platdata(&pdev->dev);
	int val, gpio, port;
	int val, port;

	/* From the GPIO notifying the over-current situation, find
	 * out the corresponding port */
	at91_for_each_port(port) {
		if (gpio_is_valid(pdata->overcurrent_pin[port]) &&
				gpio_to_irq(pdata->overcurrent_pin[port]) == irq) {
			gpio = pdata->overcurrent_pin[port];
		if (gpiod_to_irq(pdata->overcurrent_pin[port]) == irq)
			break;
	}
	}

	if (port == AT91_MAX_USBH_PORTS) {
		dev_err(& pdev->dev, "overcurrent interrupt from unknown GPIO\n");
		return IRQ_HANDLED;
	}

	val = gpio_get_value(gpio);
	val = gpiod_get_value(pdata->overcurrent_pin[port]);

	/* When notified of an over-current situation, disable power
	   on the corresponding port, and mark this port in
@@ -516,9 +507,8 @@ static int ohci_hcd_at91_drv_probe(struct platform_device *pdev)
	struct device_node *np = pdev->dev.of_node;
	struct at91_usbh_data	*pdata;
	int			i;
	int			gpio;
	int			ret;
	enum of_gpio_flags	flags;
	int			err;
	u32			ports;

	/* Right now device-tree probed devices don't get dma_mask set.
@@ -539,38 +529,16 @@ static int ohci_hcd_at91_drv_probe(struct platform_device *pdev)
		pdata->ports = ports;

	at91_for_each_port(i) {
		/*
		 * do not configure PIO if not in relation with
		 * real USB port on board
		 */
		if (i >= pdata->ports) {
			pdata->vbus_pin[i] = -EINVAL;
			pdata->overcurrent_pin[i] = -EINVAL;
		pdata->vbus_pin[i] = devm_gpiod_get_optional(&pdev->dev,
							     "atmel,vbus-gpio",
							     GPIOD_IN);
		if (IS_ERR(pdata->vbus_pin[i])) {
			err = PTR_ERR(pdata->vbus_pin[i]);
			dev_err(&pdev->dev, "unable to claim gpio \"vbus\": %d\n", err);
			continue;
		}

		gpio = of_get_named_gpio_flags(np, "atmel,vbus-gpio", i,
					       &flags);
		pdata->vbus_pin[i] = gpio;
		if (!gpio_is_valid(gpio))
			continue;
		pdata->vbus_pin_active_low[i] = flags & OF_GPIO_ACTIVE_LOW;

		ret = gpio_request(gpio, "ohci_vbus");
		if (ret) {
			dev_err(&pdev->dev,
				"can't request vbus gpio %d\n", gpio);
			continue;
		}
		ret = gpio_direction_output(gpio,
					!pdata->vbus_pin_active_low[i]);
		if (ret) {
			dev_err(&pdev->dev,
				"can't put vbus gpio %d as output %d\n",
				gpio, !pdata->vbus_pin_active_low[i]);
			gpio_free(gpio);
			continue;
		}
		pdata->vbus_pin_active_low[i] = gpiod_get_value(pdata->vbus_pin[i]);

		ohci_at91_usb_set_power(pdata, i, 1);
	}
@@ -580,37 +548,21 @@ static int ohci_hcd_at91_drv_probe(struct platform_device *pdev)
			break;

		pdata->overcurrent_pin[i] =
			of_get_named_gpio_flags(np, "atmel,oc-gpio", i, &flags);

		if (!gpio_is_valid(pdata->overcurrent_pin[i]))
			continue;
		gpio = pdata->overcurrent_pin[i];

		ret = gpio_request(gpio, "ohci_overcurrent");
		if (ret) {
			dev_err(&pdev->dev,
				"can't request overcurrent gpio %d\n",
				gpio);
			continue;
		}

		ret = gpio_direction_input(gpio);
		if (ret) {
			dev_err(&pdev->dev,
				"can't configure overcurrent gpio %d as input\n",
				gpio);
			gpio_free(gpio);
			devm_gpiod_get_optional(&pdev->dev,
						"atmel,oc-gpio", GPIOD_IN);
		if (IS_ERR(pdata->overcurrent_pin[i])) {
			err = PTR_ERR(pdata->overcurrent_pin[i]);
			dev_err(&pdev->dev, "unable to claim gpio \"overcurrent\": %d\n", err);
			continue;
		}

		ret = request_irq(gpio_to_irq(gpio),
		ret = devm_request_irq(&pdev->dev,
				       gpiod_to_irq(pdata->overcurrent_pin[i]),
				       ohci_hcd_at91_overcurrent_irq,
				  IRQF_SHARED, "ohci_overcurrent", pdev);
		if (ret) {
			gpio_free(gpio);
			dev_err(&pdev->dev,
				"can't get gpio IRQ for overcurrent\n");
		}
				       IRQF_SHARED,
				       "ohci_overcurrent", pdev);
		if (ret)
			dev_info(&pdev->dev, "failed to request gpio \"overcurrent\" IRQ\n");
	}

	device_init_wakeup(&pdev->dev, 1);
@@ -623,19 +575,8 @@ static int ohci_hcd_at91_drv_remove(struct platform_device *pdev)
	int			i;

	if (pdata) {
		at91_for_each_port(i) {
			if (!gpio_is_valid(pdata->vbus_pin[i]))
				continue;
		at91_for_each_port(i)
			ohci_at91_usb_set_power(pdata, i, 0);
			gpio_free(pdata->vbus_pin[i]);
		}

		at91_for_each_port(i) {
			if (!gpio_is_valid(pdata->overcurrent_pin[i]))
				continue;
			free_irq(gpio_to_irq(pdata->overcurrent_pin[i]), pdev);
			gpio_free(pdata->overcurrent_pin[i]);
		}
	}

	device_init_wakeup(&pdev->dev, 0);