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

Commit 97efe9ae authored by holt@sgi.com's avatar holt@sgi.com Committed by David S. Miller
Browse files

flexcan: Prefer device tree clock frequency if available.



If our CAN device's device tree node has a clock-frequency property,
then use that value for the can devices clock frequency.  If not, fall
back to asking the platform/mach code for the clock frequency associated
with the flexcan device.

Signed-off-by: default avatarRobin Holt <holt@sgi.com>
Acked-by: default avatarWolfgang Grandegger <wg@grandegger.com&gt;,>
Cc: Kumar Gala <galak@kernel.crashing.org>
Cc: Marc Kleine-Budde <mkl@pengutronix.de>,
Cc: U Bhaskar-B22300 <B22300@freescale.com>
Cc: Scott Wood <scottwood@freescale.com>
Cc: Grant Likely <grant.likely@secretlab.ca>
Cc: socketcan-core@lists.berlios.de,
Cc: netdev@vger.kernel.org,
Cc: PPC list <linuxppc-dev@lists.ozlabs.org>
Cc: devicetree-discuss@lists.ozlabs.org
Signed-off-by: default avatarDavid S. Miller <davem@davemloft.net>
parent c8aef4cb
Loading
Loading
Loading
Loading
+2 −0
Original line number Diff line number Diff line
@@ -11,6 +11,7 @@ Required properties:

- reg : Offset and length of the register set for this device
- interrupts : Interrupt tuple for this device
- clock-frequency : The oscillator frequency driving the flexcan device

Example:

@@ -19,4 +20,5 @@ Example:
		reg = <0x1c000 0x1000>;
		interrupts = <48 0x2>;
		interrupt-parent = <&mpic>;
		clock-frequency = <200000000>; // filled in by bootloader
	};
+25 −9
Original line number Diff line number Diff line
@@ -33,6 +33,7 @@
#include <linux/kernel.h>
#include <linux/list.h>
#include <linux/module.h>
#include <linux/of.h>
#include <linux/platform_device.h>

#define DRV_NAME			"flexcan"
@@ -925,17 +926,30 @@ static int __devinit flexcan_probe(struct platform_device *pdev)
	struct net_device *dev;
	struct flexcan_priv *priv;
	struct resource *mem;
	struct clk *clk;
	struct clk *clk = NULL;
	void __iomem *base;
	resource_size_t mem_size;
	int err, irq;
	u32 clock_freq = 0;

	if (pdev->dev.of_node) {
		const u32 *clock_freq_p;

		clock_freq_p = of_get_property(pdev->dev.of_node,
						"clock-frequency", NULL);
		if (clock_freq_p)
			clock_freq = *clock_freq_p;
	}

	if (!clock_freq) {
		clk = clk_get(&pdev->dev, NULL);
		if (IS_ERR(clk)) {
			dev_err(&pdev->dev, "no clock defined\n");
			err = PTR_ERR(clk);
			goto failed_clock;
		}
		clock_freq = clk_get_rate(clk);
	}

	mem = platform_get_resource(pdev, IORESOURCE_MEM, 0);
	irq = platform_get_irq(pdev, 0);
@@ -967,7 +981,7 @@ static int __devinit flexcan_probe(struct platform_device *pdev)
	dev->flags |= IFF_ECHO; /* we support local echo in hardware */

	priv = netdev_priv(dev);
	priv->can.clock.freq = clk_get_rate(clk);
	priv->can.clock.freq = clock_freq;
	priv->can.bittiming_const = &flexcan_bittiming_const;
	priv->can.do_set_mode = flexcan_set_mode;
	priv->can.do_get_berr_counter = flexcan_get_berr_counter;
@@ -1002,6 +1016,7 @@ static int __devinit flexcan_probe(struct platform_device *pdev)
 failed_map:
	release_mem_region(mem->start, mem_size);
 failed_get:
	if (clk)
		clk_put(clk);
 failed_clock:
	return err;
@@ -1020,6 +1035,7 @@ static int __devexit flexcan_remove(struct platform_device *pdev)
	mem = platform_get_resource(pdev, IORESOURCE_MEM, 0);
	release_mem_region(mem->start, resource_size(mem));

	if (priv->clk)
		clk_put(priv->clk);

	free_candev(dev);