diff options
-rw-r--r-- | Documentation/devicetree/bindings/clock/zynq-7000.txt | 4 | ||||
-rw-r--r-- | arch/arm/boot/dts/zynq-7000.dtsi | 43 | ||||
-rw-r--r-- | arch/arm/include/debug/zynq.S | 3 | ||||
-rw-r--r-- | arch/arm/mach-zynq/Kconfig | 1 | ||||
-rw-r--r-- | arch/arm/mach-zynq/common.c | 8 | ||||
-rw-r--r-- | arch/arm/mach-zynq/common.h | 2 | ||||
-rw-r--r-- | arch/arm/mach-zynq/slcr.c | 104 | ||||
-rw-r--r-- | drivers/clk/zynq/clkc.c | 89 | ||||
-rw-r--r-- | include/linux/clk/zynq.h | 2 |
9 files changed, 188 insertions, 68 deletions
diff --git a/Documentation/devicetree/bindings/clock/zynq-7000.txt b/Documentation/devicetree/bindings/clock/zynq-7000.txt index 17b4a94916d6..d93746cf2975 100644 --- a/Documentation/devicetree/bindings/clock/zynq-7000.txt +++ b/Documentation/devicetree/bindings/clock/zynq-7000.txt | |||
@@ -14,6 +14,7 @@ for all clock consumers of PS clocks. | |||
14 | Required properties: | 14 | Required properties: |
15 | - #clock-cells : Must be 1 | 15 | - #clock-cells : Must be 1 |
16 | - compatible : "xlnx,ps7-clkc" | 16 | - compatible : "xlnx,ps7-clkc" |
17 | - reg : SLCR offset and size taken via syscon < 0x100 0x100 > | ||
17 | - ps-clk-frequency : Frequency of the oscillator providing ps_clk in HZ | 18 | - ps-clk-frequency : Frequency of the oscillator providing ps_clk in HZ |
18 | (usually 33 MHz oscillators are used for Zynq platforms) | 19 | (usually 33 MHz oscillators are used for Zynq platforms) |
19 | - clock-output-names : List of strings used to name the clock outputs. Shall be | 20 | - clock-output-names : List of strings used to name the clock outputs. Shall be |
@@ -87,10 +88,11 @@ Clock outputs: | |||
87 | 47: dbg_apb | 88 | 47: dbg_apb |
88 | 89 | ||
89 | Example: | 90 | Example: |
90 | clkc: clkc { | 91 | clkc: clkc@100 { |
91 | #clock-cells = <1>; | 92 | #clock-cells = <1>; |
92 | compatible = "xlnx,ps7-clkc"; | 93 | compatible = "xlnx,ps7-clkc"; |
93 | ps-clk-frequency = <33333333>; | 94 | ps-clk-frequency = <33333333>; |
95 | reg = <0x100 0x100>; | ||
94 | clock-output-names = "armpll", "ddrpll", "iopll", "cpu_6or4x", | 96 | clock-output-names = "armpll", "ddrpll", "iopll", "cpu_6or4x", |
95 | "cpu_3or2x", "cpu_2x", "cpu_1x", "ddr2x", "ddr3x", | 97 | "cpu_3or2x", "cpu_2x", "cpu_1x", "ddr2x", "ddr3x", |
96 | "dci", "lqspi", "smc", "pcap", "gem0", "gem1", | 98 | "dci", "lqspi", "smc", "pcap", "gem0", "gem1", |
diff --git a/arch/arm/boot/dts/zynq-7000.dtsi b/arch/arm/boot/dts/zynq-7000.dtsi index 8b67b19392ec..602e12eedb01 100644 --- a/arch/arm/boot/dts/zynq-7000.dtsi +++ b/arch/arm/boot/dts/zynq-7000.dtsi | |||
@@ -123,29 +123,28 @@ | |||
123 | } ; | 123 | } ; |
124 | 124 | ||
125 | slcr: slcr@f8000000 { | 125 | slcr: slcr@f8000000 { |
126 | compatible = "xlnx,zynq-slcr"; | 126 | #address-cells = <1>; |
127 | #size-cells = <1>; | ||
128 | compatible = "xlnx,zynq-slcr", "syscon"; | ||
127 | reg = <0xF8000000 0x1000>; | 129 | reg = <0xF8000000 0x1000>; |
128 | 130 | ranges; | |
129 | clocks { | 131 | clkc: clkc@100 { |
130 | #address-cells = <1>; | 132 | #clock-cells = <1>; |
131 | #size-cells = <0>; | 133 | compatible = "xlnx,ps7-clkc"; |
132 | 134 | ps-clk-frequency = <33333333>; | |
133 | clkc: clkc { | 135 | fclk-enable = <0>; |
134 | #clock-cells = <1>; | 136 | clock-output-names = "armpll", "ddrpll", "iopll", "cpu_6or4x", |
135 | compatible = "xlnx,ps7-clkc"; | 137 | "cpu_3or2x", "cpu_2x", "cpu_1x", "ddr2x", "ddr3x", |
136 | ps-clk-frequency = <33333333>; | 138 | "dci", "lqspi", "smc", "pcap", "gem0", "gem1", |
137 | clock-output-names = "armpll", "ddrpll", "iopll", "cpu_6or4x", | 139 | "fclk0", "fclk1", "fclk2", "fclk3", "can0", "can1", |
138 | "cpu_3or2x", "cpu_2x", "cpu_1x", "ddr2x", "ddr3x", | 140 | "sdio0", "sdio1", "uart0", "uart1", "spi0", "spi1", |
139 | "dci", "lqspi", "smc", "pcap", "gem0", "gem1", | 141 | "dma", "usb0_aper", "usb1_aper", "gem0_aper", |
140 | "fclk0", "fclk1", "fclk2", "fclk3", "can0", "can1", | 142 | "gem1_aper", "sdio0_aper", "sdio1_aper", |
141 | "sdio0", "sdio1", "uart0", "uart1", "spi0", "spi1", | 143 | "spi0_aper", "spi1_aper", "can0_aper", "can1_aper", |
142 | "dma", "usb0_aper", "usb1_aper", "gem0_aper", | 144 | "i2c0_aper", "i2c1_aper", "uart0_aper", "uart1_aper", |
143 | "gem1_aper", "sdio0_aper", "sdio1_aper", | 145 | "gpio_aper", "lqspi_aper", "smc_aper", "swdt", |
144 | "spi0_aper", "spi1_aper", "can0_aper", "can1_aper", | 146 | "dbg_trc", "dbg_apb"; |
145 | "i2c0_aper", "i2c1_aper", "uart0_aper", "uart1_aper", | 147 | reg = <0x100 0x100>; |
146 | "gpio_aper", "lqspi_aper", "smc_aper", "swdt", | ||
147 | "dbg_trc", "dbg_apb"; | ||
148 | }; | ||
149 | }; | 148 | }; |
150 | }; | 149 | }; |
151 | 150 | ||
diff --git a/arch/arm/include/debug/zynq.S b/arch/arm/include/debug/zynq.S index f9aa9740a73f..0b762fafa758 100644 --- a/arch/arm/include/debug/zynq.S +++ b/arch/arm/include/debug/zynq.S | |||
@@ -42,6 +42,9 @@ | |||
42 | .endm | 42 | .endm |
43 | 43 | ||
44 | .macro waituart,rd,rx | 44 | .macro waituart,rd,rx |
45 | 1001: ldr \rd, [\rx, #UART_SR_OFFSET] | ||
46 | tst \rd, #UART_SR_TXEMPTY | ||
47 | beq 1001b | ||
45 | .endm | 48 | .endm |
46 | 49 | ||
47 | .macro busyuart,rd,rx | 50 | .macro busyuart,rd,rx |
diff --git a/arch/arm/mach-zynq/Kconfig b/arch/arm/mach-zynq/Kconfig index 6b04260aa142..323e5053cb9f 100644 --- a/arch/arm/mach-zynq/Kconfig +++ b/arch/arm/mach-zynq/Kconfig | |||
@@ -14,5 +14,6 @@ config ARCH_ZYNQ | |||
14 | select SPARSE_IRQ | 14 | select SPARSE_IRQ |
15 | select CADENCE_TTC_TIMER | 15 | select CADENCE_TTC_TIMER |
16 | select ARM_GLOBAL_TIMER | 16 | select ARM_GLOBAL_TIMER |
17 | select MFD_SYSCON | ||
17 | help | 18 | help |
18 | Support for Xilinx Zynq ARM Cortex A9 Platform | 19 | Support for Xilinx Zynq ARM Cortex A9 Platform |
diff --git a/arch/arm/mach-zynq/common.c b/arch/arm/mach-zynq/common.c index 8c09a8393fb6..dca60d5ba756 100644 --- a/arch/arm/mach-zynq/common.c +++ b/arch/arm/mach-zynq/common.c | |||
@@ -19,6 +19,7 @@ | |||
19 | #include <linux/cpumask.h> | 19 | #include <linux/cpumask.h> |
20 | #include <linux/platform_device.h> | 20 | #include <linux/platform_device.h> |
21 | #include <linux/clk.h> | 21 | #include <linux/clk.h> |
22 | #include <linux/clk-provider.h> | ||
22 | #include <linux/clk/zynq.h> | 23 | #include <linux/clk/zynq.h> |
23 | #include <linux/clocksource.h> | 24 | #include <linux/clocksource.h> |
24 | #include <linux/of_address.h> | 25 | #include <linux/of_address.h> |
@@ -72,11 +73,16 @@ static void __init zynq_init_machine(void) | |||
72 | of_platform_populate(NULL, of_default_bus_match_table, NULL, NULL); | 73 | of_platform_populate(NULL, of_default_bus_match_table, NULL, NULL); |
73 | 74 | ||
74 | platform_device_register(&zynq_cpuidle_device); | 75 | platform_device_register(&zynq_cpuidle_device); |
76 | |||
77 | zynq_slcr_init(); | ||
75 | } | 78 | } |
76 | 79 | ||
77 | static void __init zynq_timer_init(void) | 80 | static void __init zynq_timer_init(void) |
78 | { | 81 | { |
79 | zynq_slcr_init(); | 82 | zynq_early_slcr_init(); |
83 | |||
84 | zynq_clock_init(); | ||
85 | of_clk_init(NULL); | ||
80 | clocksource_of_init(); | 86 | clocksource_of_init(); |
81 | } | 87 | } |
82 | 88 | ||
diff --git a/arch/arm/mach-zynq/common.h b/arch/arm/mach-zynq/common.h index c22c92cea8cb..b097844d3175 100644 --- a/arch/arm/mach-zynq/common.h +++ b/arch/arm/mach-zynq/common.h | |||
@@ -20,6 +20,7 @@ | |||
20 | void zynq_secondary_startup(void); | 20 | void zynq_secondary_startup(void); |
21 | 21 | ||
22 | extern int zynq_slcr_init(void); | 22 | extern int zynq_slcr_init(void); |
23 | extern int zynq_early_slcr_init(void); | ||
23 | extern void zynq_slcr_system_reset(void); | 24 | extern void zynq_slcr_system_reset(void); |
24 | extern void zynq_slcr_cpu_stop(int cpu); | 25 | extern void zynq_slcr_cpu_stop(int cpu); |
25 | extern void zynq_slcr_cpu_start(int cpu); | 26 | extern void zynq_slcr_cpu_start(int cpu); |
@@ -33,7 +34,6 @@ extern int zynq_cpun_start(u32 address, int cpu); | |||
33 | extern struct smp_operations zynq_smp_ops __initdata; | 34 | extern struct smp_operations zynq_smp_ops __initdata; |
34 | #endif | 35 | #endif |
35 | 36 | ||
36 | extern void __iomem *zynq_slcr_base; | ||
37 | extern void __iomem *zynq_scu_base; | 37 | extern void __iomem *zynq_scu_base; |
38 | 38 | ||
39 | /* Hotplug */ | 39 | /* Hotplug */ |
diff --git a/arch/arm/mach-zynq/slcr.c b/arch/arm/mach-zynq/slcr.c index 1836d5a34606..a37d49a6e657 100644 --- a/arch/arm/mach-zynq/slcr.c +++ b/arch/arm/mach-zynq/slcr.c | |||
@@ -15,7 +15,9 @@ | |||
15 | */ | 15 | */ |
16 | 16 | ||
17 | #include <linux/io.h> | 17 | #include <linux/io.h> |
18 | #include <linux/mfd/syscon.h> | ||
18 | #include <linux/of_address.h> | 19 | #include <linux/of_address.h> |
20 | #include <linux/regmap.h> | ||
19 | #include <linux/clk/zynq.h> | 21 | #include <linux/clk/zynq.h> |
20 | #include "common.h" | 22 | #include "common.h" |
21 | 23 | ||
@@ -29,7 +31,56 @@ | |||
29 | #define SLCR_A9_CPU_CLKSTOP 0x10 | 31 | #define SLCR_A9_CPU_CLKSTOP 0x10 |
30 | #define SLCR_A9_CPU_RST 0x1 | 32 | #define SLCR_A9_CPU_RST 0x1 |
31 | 33 | ||
32 | void __iomem *zynq_slcr_base; | 34 | static void __iomem *zynq_slcr_base; |
35 | static struct regmap *zynq_slcr_regmap; | ||
36 | |||
37 | /** | ||
38 | * zynq_slcr_write - Write to a register in SLCR block | ||
39 | * | ||
40 | * @val: Value to write to the register | ||
41 | * @offset: Register offset in SLCR block | ||
42 | * | ||
43 | * Return: a negative value on error, 0 on success | ||
44 | */ | ||
45 | static int zynq_slcr_write(u32 val, u32 offset) | ||
46 | { | ||
47 | if (!zynq_slcr_regmap) { | ||
48 | writel(val, zynq_slcr_base + offset); | ||
49 | return 0; | ||
50 | } | ||
51 | |||
52 | return regmap_write(zynq_slcr_regmap, offset, val); | ||
53 | } | ||
54 | |||
55 | /** | ||
56 | * zynq_slcr_read - Read a register in SLCR block | ||
57 | * | ||
58 | * @val: Pointer to value to be read from SLCR | ||
59 | * @offset: Register offset in SLCR block | ||
60 | * | ||
61 | * Return: a negative value on error, 0 on success | ||
62 | */ | ||
63 | static int zynq_slcr_read(u32 *val, u32 offset) | ||
64 | { | ||
65 | if (zynq_slcr_regmap) | ||
66 | return regmap_read(zynq_slcr_regmap, offset, val); | ||
67 | |||
68 | *val = readl(zynq_slcr_base + offset); | ||
69 | |||
70 | return 0; | ||
71 | } | ||
72 | |||
73 | /** | ||
74 | * zynq_slcr_unlock - Unlock SLCR registers | ||
75 | * | ||
76 | * Return: a negative value on error, 0 on success | ||
77 | */ | ||
78 | static inline int zynq_slcr_unlock(void) | ||
79 | { | ||
80 | zynq_slcr_write(SLCR_UNLOCK_MAGIC, SLCR_UNLOCK_OFFSET); | ||
81 | |||
82 | return 0; | ||
83 | } | ||
33 | 84 | ||
34 | /** | 85 | /** |
35 | * zynq_slcr_system_reset - Reset the entire system. | 86 | * zynq_slcr_system_reset - Reset the entire system. |
@@ -43,16 +94,16 @@ void zynq_slcr_system_reset(void) | |||
43 | * Note that this seems to require raw i/o | 94 | * Note that this seems to require raw i/o |
44 | * functions or there's a lockup? | 95 | * functions or there's a lockup? |
45 | */ | 96 | */ |
46 | writel(SLCR_UNLOCK_MAGIC, zynq_slcr_base + SLCR_UNLOCK_OFFSET); | 97 | zynq_slcr_unlock(); |
47 | 98 | ||
48 | /* | 99 | /* |
49 | * Clear 0x0F000000 bits of reboot status register to workaround | 100 | * Clear 0x0F000000 bits of reboot status register to workaround |
50 | * the FSBL not loading the bitstream after soft-reboot | 101 | * the FSBL not loading the bitstream after soft-reboot |
51 | * This is a temporary solution until we know more. | 102 | * This is a temporary solution until we know more. |
52 | */ | 103 | */ |
53 | reboot = readl(zynq_slcr_base + SLCR_REBOOT_STATUS_OFFSET); | 104 | zynq_slcr_read(&reboot, SLCR_REBOOT_STATUS_OFFSET); |
54 | writel(reboot & 0xF0FFFFFF, zynq_slcr_base + SLCR_REBOOT_STATUS_OFFSET); | 105 | zynq_slcr_write(reboot & 0xF0FFFFFF, SLCR_REBOOT_STATUS_OFFSET); |
55 | writel(1, zynq_slcr_base + SLCR_PS_RST_CTRL_OFFSET); | 106 | zynq_slcr_write(1, SLCR_PS_RST_CTRL_OFFSET); |
56 | } | 107 | } |
57 | 108 | ||
58 | /** | 109 | /** |
@@ -61,11 +112,13 @@ void zynq_slcr_system_reset(void) | |||
61 | */ | 112 | */ |
62 | void zynq_slcr_cpu_start(int cpu) | 113 | void zynq_slcr_cpu_start(int cpu) |
63 | { | 114 | { |
64 | u32 reg = readl(zynq_slcr_base + SLCR_A9_CPU_RST_CTRL_OFFSET); | 115 | u32 reg; |
116 | |||
117 | zynq_slcr_read(®, SLCR_A9_CPU_RST_CTRL_OFFSET); | ||
65 | reg &= ~(SLCR_A9_CPU_RST << cpu); | 118 | reg &= ~(SLCR_A9_CPU_RST << cpu); |
66 | writel(reg, zynq_slcr_base + SLCR_A9_CPU_RST_CTRL_OFFSET); | 119 | zynq_slcr_write(reg, SLCR_A9_CPU_RST_CTRL_OFFSET); |
67 | reg &= ~(SLCR_A9_CPU_CLKSTOP << cpu); | 120 | reg &= ~(SLCR_A9_CPU_CLKSTOP << cpu); |
68 | writel(reg, zynq_slcr_base + SLCR_A9_CPU_RST_CTRL_OFFSET); | 121 | zynq_slcr_write(reg, SLCR_A9_CPU_RST_CTRL_OFFSET); |
69 | } | 122 | } |
70 | 123 | ||
71 | /** | 124 | /** |
@@ -74,19 +127,40 @@ void zynq_slcr_cpu_start(int cpu) | |||
74 | */ | 127 | */ |
75 | void zynq_slcr_cpu_stop(int cpu) | 128 | void zynq_slcr_cpu_stop(int cpu) |
76 | { | 129 | { |
77 | u32 reg = readl(zynq_slcr_base + SLCR_A9_CPU_RST_CTRL_OFFSET); | 130 | u32 reg; |
131 | |||
132 | zynq_slcr_read(®, SLCR_A9_CPU_RST_CTRL_OFFSET); | ||
78 | reg |= (SLCR_A9_CPU_CLKSTOP | SLCR_A9_CPU_RST) << cpu; | 133 | reg |= (SLCR_A9_CPU_CLKSTOP | SLCR_A9_CPU_RST) << cpu; |
79 | writel(reg, zynq_slcr_base + SLCR_A9_CPU_RST_CTRL_OFFSET); | 134 | zynq_slcr_write(reg, SLCR_A9_CPU_RST_CTRL_OFFSET); |
80 | } | 135 | } |
81 | 136 | ||
82 | /** | 137 | /** |
83 | * zynq_slcr_init | 138 | * zynq_slcr_init - Regular slcr driver init |
84 | * Returns 0 on success, negative errno otherwise. | 139 | * |
140 | * Return: 0 on success, negative errno otherwise. | ||
85 | * | 141 | * |
86 | * Called early during boot from platform code to remap SLCR area. | 142 | * Called early during boot from platform code to remap SLCR area. |
87 | */ | 143 | */ |
88 | int __init zynq_slcr_init(void) | 144 | int __init zynq_slcr_init(void) |
89 | { | 145 | { |
146 | zynq_slcr_regmap = syscon_regmap_lookup_by_compatible("xlnx,zynq-slcr"); | ||
147 | if (IS_ERR(zynq_slcr_regmap)) { | ||
148 | pr_err("%s: failed to find zynq-slcr\n", __func__); | ||
149 | return -ENODEV; | ||
150 | } | ||
151 | |||
152 | return 0; | ||
153 | } | ||
154 | |||
155 | /** | ||
156 | * zynq_early_slcr_init - Early slcr init function | ||
157 | * | ||
158 | * Return: 0 on success, negative errno otherwise. | ||
159 | * | ||
160 | * Called very early during boot from platform code to unlock SLCR. | ||
161 | */ | ||
162 | int __init zynq_early_slcr_init(void) | ||
163 | { | ||
90 | struct device_node *np; | 164 | struct device_node *np; |
91 | 165 | ||
92 | np = of_find_compatible_node(NULL, NULL, "xlnx,zynq-slcr"); | 166 | np = of_find_compatible_node(NULL, NULL, "xlnx,zynq-slcr"); |
@@ -101,13 +175,13 @@ int __init zynq_slcr_init(void) | |||
101 | BUG(); | 175 | BUG(); |
102 | } | 176 | } |
103 | 177 | ||
178 | np->data = (__force void *)zynq_slcr_base; | ||
179 | |||
104 | /* unlock the SLCR so that registers can be changed */ | 180 | /* unlock the SLCR so that registers can be changed */ |
105 | writel(SLCR_UNLOCK_MAGIC, zynq_slcr_base + SLCR_UNLOCK_OFFSET); | 181 | zynq_slcr_unlock(); |
106 | 182 | ||
107 | pr_info("%s mapped to %p\n", np->name, zynq_slcr_base); | 183 | pr_info("%s mapped to %p\n", np->name, zynq_slcr_base); |
108 | 184 | ||
109 | zynq_clock_init(zynq_slcr_base); | ||
110 | |||
111 | of_node_put(np); | 185 | of_node_put(np); |
112 | 186 | ||
113 | return 0; | 187 | return 0; |
diff --git a/drivers/clk/zynq/clkc.c b/drivers/clk/zynq/clkc.c index 09dd0173ea0a..c812b93a52b2 100644 --- a/drivers/clk/zynq/clkc.c +++ b/drivers/clk/zynq/clkc.c | |||
@@ -21,34 +21,35 @@ | |||
21 | #include <linux/clk/zynq.h> | 21 | #include <linux/clk/zynq.h> |
22 | #include <linux/clk-provider.h> | 22 | #include <linux/clk-provider.h> |
23 | #include <linux/of.h> | 23 | #include <linux/of.h> |
24 | #include <linux/of_address.h> | ||
24 | #include <linux/slab.h> | 25 | #include <linux/slab.h> |
25 | #include <linux/string.h> | 26 | #include <linux/string.h> |
26 | #include <linux/io.h> | 27 | #include <linux/io.h> |
27 | 28 | ||
28 | static void __iomem *zynq_slcr_base_priv; | 29 | static void __iomem *zynq_clkc_base; |
29 | 30 | ||
30 | #define SLCR_ARMPLL_CTRL (zynq_slcr_base_priv + 0x100) | 31 | #define SLCR_ARMPLL_CTRL (zynq_clkc_base + 0x00) |
31 | #define SLCR_DDRPLL_CTRL (zynq_slcr_base_priv + 0x104) | 32 | #define SLCR_DDRPLL_CTRL (zynq_clkc_base + 0x04) |
32 | #define SLCR_IOPLL_CTRL (zynq_slcr_base_priv + 0x108) | 33 | #define SLCR_IOPLL_CTRL (zynq_clkc_base + 0x08) |
33 | #define SLCR_PLL_STATUS (zynq_slcr_base_priv + 0x10c) | 34 | #define SLCR_PLL_STATUS (zynq_clkc_base + 0x0c) |
34 | #define SLCR_ARM_CLK_CTRL (zynq_slcr_base_priv + 0x120) | 35 | #define SLCR_ARM_CLK_CTRL (zynq_clkc_base + 0x20) |
35 | #define SLCR_DDR_CLK_CTRL (zynq_slcr_base_priv + 0x124) | 36 | #define SLCR_DDR_CLK_CTRL (zynq_clkc_base + 0x24) |
36 | #define SLCR_DCI_CLK_CTRL (zynq_slcr_base_priv + 0x128) | 37 | #define SLCR_DCI_CLK_CTRL (zynq_clkc_base + 0x28) |
37 | #define SLCR_APER_CLK_CTRL (zynq_slcr_base_priv + 0x12c) | 38 | #define SLCR_APER_CLK_CTRL (zynq_clkc_base + 0x2c) |
38 | #define SLCR_GEM0_CLK_CTRL (zynq_slcr_base_priv + 0x140) | 39 | #define SLCR_GEM0_CLK_CTRL (zynq_clkc_base + 0x40) |
39 | #define SLCR_GEM1_CLK_CTRL (zynq_slcr_base_priv + 0x144) | 40 | #define SLCR_GEM1_CLK_CTRL (zynq_clkc_base + 0x44) |
40 | #define SLCR_SMC_CLK_CTRL (zynq_slcr_base_priv + 0x148) | 41 | #define SLCR_SMC_CLK_CTRL (zynq_clkc_base + 0x48) |
41 | #define SLCR_LQSPI_CLK_CTRL (zynq_slcr_base_priv + 0x14c) | 42 | #define SLCR_LQSPI_CLK_CTRL (zynq_clkc_base + 0x4c) |
42 | #define SLCR_SDIO_CLK_CTRL (zynq_slcr_base_priv + 0x150) | 43 | #define SLCR_SDIO_CLK_CTRL (zynq_clkc_base + 0x50) |
43 | #define SLCR_UART_CLK_CTRL (zynq_slcr_base_priv + 0x154) | 44 | #define SLCR_UART_CLK_CTRL (zynq_clkc_base + 0x54) |
44 | #define SLCR_SPI_CLK_CTRL (zynq_slcr_base_priv + 0x158) | 45 | #define SLCR_SPI_CLK_CTRL (zynq_clkc_base + 0x58) |
45 | #define SLCR_CAN_CLK_CTRL (zynq_slcr_base_priv + 0x15c) | 46 | #define SLCR_CAN_CLK_CTRL (zynq_clkc_base + 0x5c) |
46 | #define SLCR_CAN_MIOCLK_CTRL (zynq_slcr_base_priv + 0x160) | 47 | #define SLCR_CAN_MIOCLK_CTRL (zynq_clkc_base + 0x60) |
47 | #define SLCR_DBG_CLK_CTRL (zynq_slcr_base_priv + 0x164) | 48 | #define SLCR_DBG_CLK_CTRL (zynq_clkc_base + 0x64) |
48 | #define SLCR_PCAP_CLK_CTRL (zynq_slcr_base_priv + 0x168) | 49 | #define SLCR_PCAP_CLK_CTRL (zynq_clkc_base + 0x68) |
49 | #define SLCR_FPGA0_CLK_CTRL (zynq_slcr_base_priv + 0x170) | 50 | #define SLCR_FPGA0_CLK_CTRL (zynq_clkc_base + 0x70) |
50 | #define SLCR_621_TRUE (zynq_slcr_base_priv + 0x1c4) | 51 | #define SLCR_621_TRUE (zynq_clkc_base + 0xc4) |
51 | #define SLCR_SWDT_CLK_SEL (zynq_slcr_base_priv + 0x304) | 52 | #define SLCR_SWDT_CLK_SEL (zynq_clkc_base + 0x204) |
52 | 53 | ||
53 | #define NUM_MIO_PINS 54 | 54 | #define NUM_MIO_PINS 54 |
54 | 55 | ||
@@ -569,8 +570,42 @@ static void __init zynq_clk_setup(struct device_node *np) | |||
569 | 570 | ||
570 | CLK_OF_DECLARE(zynq_clkc, "xlnx,ps7-clkc", zynq_clk_setup); | 571 | CLK_OF_DECLARE(zynq_clkc, "xlnx,ps7-clkc", zynq_clk_setup); |
571 | 572 | ||
572 | void __init zynq_clock_init(void __iomem *slcr_base) | 573 | void __init zynq_clock_init(void) |
573 | { | 574 | { |
574 | zynq_slcr_base_priv = slcr_base; | 575 | struct device_node *np; |
575 | of_clk_init(NULL); | 576 | struct device_node *slcr; |
577 | struct resource res; | ||
578 | |||
579 | np = of_find_compatible_node(NULL, NULL, "xlnx,ps7-clkc"); | ||
580 | if (!np) { | ||
581 | pr_err("%s: clkc node not found\n", __func__); | ||
582 | goto np_err; | ||
583 | } | ||
584 | |||
585 | if (of_address_to_resource(np, 0, &res)) { | ||
586 | pr_err("%s: failed to get resource\n", np->name); | ||
587 | goto np_err; | ||
588 | } | ||
589 | |||
590 | slcr = of_get_parent(np); | ||
591 | |||
592 | if (slcr->data) { | ||
593 | zynq_clkc_base = (__force void __iomem *)slcr->data + res.start; | ||
594 | } else { | ||
595 | pr_err("%s: Unable to get I/O memory\n", np->name); | ||
596 | of_node_put(slcr); | ||
597 | goto np_err; | ||
598 | } | ||
599 | |||
600 | pr_info("%s: clkc starts at %p\n", __func__, zynq_clkc_base); | ||
601 | |||
602 | of_node_put(slcr); | ||
603 | of_node_put(np); | ||
604 | |||
605 | return; | ||
606 | |||
607 | np_err: | ||
608 | of_node_put(np); | ||
609 | BUG(); | ||
610 | return; | ||
576 | } | 611 | } |
diff --git a/include/linux/clk/zynq.h b/include/linux/clk/zynq.h index e062d317ccce..7a5633b71533 100644 --- a/include/linux/clk/zynq.h +++ b/include/linux/clk/zynq.h | |||
@@ -22,7 +22,7 @@ | |||
22 | 22 | ||
23 | #include <linux/spinlock.h> | 23 | #include <linux/spinlock.h> |
24 | 24 | ||
25 | void zynq_clock_init(void __iomem *slcr); | 25 | void zynq_clock_init(void); |
26 | 26 | ||
27 | struct clk *clk_register_zynq_pll(const char *name, const char *parent, | 27 | struct clk *clk_register_zynq_pll(const char *name, const char *parent, |
28 | void __iomem *pll_ctrl, void __iomem *pll_status, u8 lock_index, | 28 | void __iomem *pll_ctrl, void __iomem *pll_status, u8 lock_index, |