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

Commit 3ae2da7b authored by Gregory CLEMENT's avatar Gregory CLEMENT Committed by Greg Kroah-Hartman
Browse files

usb: host: xhci-plat: Fix clock resource by adding a register clock



On Armada 7K/8K we need to explicitly enable the register clock. This
clock is optional because not all the SoCs using this IP need it but at
least for Armada 7K/8K it is actually mandatory.

The change was done at xhci-plat level and not at a xhci-mvebu.c because,
it is expected that other SoC would have this kind of constraint.

The binding documentation is updating accordingly.

Signed-off-by: default avatarGregory CLEMENT <gregory.clement@bootlin.com>
Signed-off-by: default avatarMathias Nyman <mathias.nyman@linux.intel.com>
Signed-off-by: default avatarGreg Kroah-Hartman <gregkh@linuxfoundation.org>
parent 2d79609b
Loading
Loading
Loading
Loading
+4 −1
Original line number Original line Diff line number Diff line
@@ -28,7 +28,10 @@ Required properties:
  - interrupts: one XHCI interrupt should be described here.
  - interrupts: one XHCI interrupt should be described here.


Optional properties:
Optional properties:
  - clocks: reference to a clock
  - clocks: reference to the clocks
  - clock-names: mandatory if there is a second clock, in this case
    the name must be "core" for the first clock and "reg" for the
    second one
  - usb2-lpm-disable: indicate if we don't want to enable USB2 HW LPM
  - usb2-lpm-disable: indicate if we don't want to enable USB2 HW LPM
  - usb3-lpm-capable: determines if platform is USB3 LPM capable
  - usb3-lpm-capable: determines if platform is USB3 LPM capable
  - quirk-broken-port-ped: set if the controller has broken port disable mechanism
  - quirk-broken-port-ped: set if the controller has broken port disable mechanism
+21 −4
Original line number Original line Diff line number Diff line
@@ -157,6 +157,7 @@ static int xhci_plat_probe(struct platform_device *pdev)
	struct resource         *res;
	struct resource         *res;
	struct usb_hcd		*hcd;
	struct usb_hcd		*hcd;
	struct clk              *clk;
	struct clk              *clk;
	struct clk              *reg_clk;
	int			ret;
	int			ret;
	int			irq;
	int			irq;


@@ -226,17 +227,27 @@ static int xhci_plat_probe(struct platform_device *pdev)
	hcd->rsrc_len = resource_size(res);
	hcd->rsrc_len = resource_size(res);


	/*
	/*
	 * Not all platforms have a clk so it is not an error if the
	 * Not all platforms have clks so it is not an error if the
	 * clock does not exists.
	 * clock do not exist.
	 */
	 */
	reg_clk = devm_clk_get(&pdev->dev, "reg");
	if (!IS_ERR(reg_clk)) {
		ret = clk_prepare_enable(reg_clk);
		if (ret)
			goto put_hcd;
	} else if (PTR_ERR(reg_clk) == -EPROBE_DEFER) {
		ret = -EPROBE_DEFER;
		goto put_hcd;
	}

	clk = devm_clk_get(&pdev->dev, NULL);
	clk = devm_clk_get(&pdev->dev, NULL);
	if (!IS_ERR(clk)) {
	if (!IS_ERR(clk)) {
		ret = clk_prepare_enable(clk);
		ret = clk_prepare_enable(clk);
		if (ret)
		if (ret)
			goto put_hcd;
			goto disable_reg_clk;
	} else if (PTR_ERR(clk) == -EPROBE_DEFER) {
	} else if (PTR_ERR(clk) == -EPROBE_DEFER) {
		ret = -EPROBE_DEFER;
		ret = -EPROBE_DEFER;
		goto put_hcd;
		goto disable_reg_clk;
	}
	}


	xhci = hcd_to_xhci(hcd);
	xhci = hcd_to_xhci(hcd);
@@ -252,6 +263,7 @@ static int xhci_plat_probe(struct platform_device *pdev)
	device_wakeup_enable(hcd->self.controller);
	device_wakeup_enable(hcd->self.controller);


	xhci->clk = clk;
	xhci->clk = clk;
	xhci->reg_clk = reg_clk;
	xhci->main_hcd = hcd;
	xhci->main_hcd = hcd;
	xhci->shared_hcd = __usb_create_hcd(driver, sysdev, &pdev->dev,
	xhci->shared_hcd = __usb_create_hcd(driver, sysdev, &pdev->dev,
			dev_name(&pdev->dev), hcd);
			dev_name(&pdev->dev), hcd);
@@ -322,6 +334,9 @@ static int xhci_plat_probe(struct platform_device *pdev)
disable_clk:
disable_clk:
	clk_disable_unprepare(clk);
	clk_disable_unprepare(clk);


disable_reg_clk:
	clk_disable_unprepare(reg_clk);

put_hcd:
put_hcd:
	usb_put_hcd(hcd);
	usb_put_hcd(hcd);


@@ -337,6 +352,7 @@ static int xhci_plat_remove(struct platform_device *dev)
	struct usb_hcd	*hcd = platform_get_drvdata(dev);
	struct usb_hcd	*hcd = platform_get_drvdata(dev);
	struct xhci_hcd	*xhci = hcd_to_xhci(hcd);
	struct xhci_hcd	*xhci = hcd_to_xhci(hcd);
	struct clk *clk = xhci->clk;
	struct clk *clk = xhci->clk;
	struct clk *reg_clk = xhci->reg_clk;


	xhci->xhc_state |= XHCI_STATE_REMOVING;
	xhci->xhc_state |= XHCI_STATE_REMOVING;


@@ -347,6 +363,7 @@ static int xhci_plat_remove(struct platform_device *dev)
	usb_put_hcd(xhci->shared_hcd);
	usb_put_hcd(xhci->shared_hcd);


	clk_disable_unprepare(clk);
	clk_disable_unprepare(clk);
	clk_disable_unprepare(reg_clk);
	usb_put_hcd(hcd);
	usb_put_hcd(hcd);


	pm_runtime_set_suspended(&dev->dev);
	pm_runtime_set_suspended(&dev->dev);
+2 −1
Original line number Original line Diff line number Diff line
@@ -1729,8 +1729,9 @@ struct xhci_hcd {
	int		page_shift;
	int		page_shift;
	/* msi-x vectors */
	/* msi-x vectors */
	int		msix_count;
	int		msix_count;
	/* optional clock */
	/* optional clocks */
	struct clk		*clk;
	struct clk		*clk;
	struct clk		*reg_clk;
	/* data structures */
	/* data structures */
	struct xhci_device_context_array *dcbaa;
	struct xhci_device_context_array *dcbaa;
	struct xhci_ring	*cmd_ring;
	struct xhci_ring	*cmd_ring;