aboutsummaryrefslogtreecommitdiffstats
path: root/arch/xtensa/platforms/xtfpga/setup.c
diff options
context:
space:
mode:
Diffstat (limited to 'arch/xtensa/platforms/xtfpga/setup.c')
-rw-r--r--arch/xtensa/platforms/xtfpga/setup.c269
1 files changed, 269 insertions, 0 deletions
diff --git a/arch/xtensa/platforms/xtfpga/setup.c b/arch/xtensa/platforms/xtfpga/setup.c
new file mode 100644
index 000000000000..71d61ca6a4af
--- /dev/null
+++ b/arch/xtensa/platforms/xtfpga/setup.c
@@ -0,0 +1,269 @@
1/*
2 *
3 * arch/xtensa/platform/xtavnet/setup.c
4 *
5 * ...
6 *
7 * Authors: Chris Zankel <chris@zankel.net>
8 * Joe Taylor <joe@tensilica.com>
9 *
10 * Copyright 2001 - 2006 Tensilica Inc.
11 *
12 * This program is free software; you can redistribute it and/or modify it
13 * under the terms of the GNU General Public License as published by the
14 * Free Software Foundation; either version 2 of the License, or (at your
15 * option) any later version.
16 *
17 */
18#include <linux/stddef.h>
19#include <linux/kernel.h>
20#include <linux/init.h>
21#include <linux/errno.h>
22#include <linux/reboot.h>
23#include <linux/kdev_t.h>
24#include <linux/types.h>
25#include <linux/major.h>
26#include <linux/console.h>
27#include <linux/delay.h>
28#include <linux/of.h>
29
30#include <asm/timex.h>
31#include <asm/processor.h>
32#include <asm/platform.h>
33#include <asm/bootparam.h>
34#include <platform/lcd.h>
35
36void platform_halt(void)
37{
38 lcd_disp_at_pos(" HALT ", 0);
39 local_irq_disable();
40 while (1)
41 cpu_relax();
42}
43
44void platform_power_off(void)
45{
46 lcd_disp_at_pos("POWEROFF", 0);
47 local_irq_disable();
48 while (1)
49 cpu_relax();
50}
51
52void platform_restart(void)
53{
54 /* Flush and reset the mmu, simulate a processor reset, and
55 * jump to the reset vector. */
56
57
58 __asm__ __volatile__ ("movi a2, 15\n\t"
59 "wsr a2, icountlevel\n\t"
60 "movi a2, 0\n\t"
61 "wsr a2, icount\n\t"
62 "wsr a2, ibreakenable\n\t"
63 "wsr a2, lcount\n\t"
64 "movi a2, 0x1f\n\t"
65 "wsr a2, ps\n\t"
66 "isync\n\t"
67 "jx %0\n\t"
68 :
69 : "a" (XCHAL_RESET_VECTOR_VADDR)
70 : "a2"
71 );
72
73 /* control never gets here */
74}
75
76void __init platform_setup(char **cmdline)
77{
78}
79
80#ifdef CONFIG_OF
81
82static void __init update_clock_frequency(struct device_node *node)
83{
84 struct property *newfreq;
85 u32 freq;
86
87 if (!of_property_read_u32(node, "clock-frequency", &freq) &&
88 freq != 0)
89 return;
90
91 newfreq = kzalloc(sizeof(*newfreq) + sizeof(u32), GFP_KERNEL);
92 if (!newfreq)
93 return;
94 newfreq->value = newfreq + 1;
95 newfreq->length = sizeof(freq);
96 newfreq->name = kstrdup("clock-frequency", GFP_KERNEL);
97 if (!newfreq->name) {
98 kfree(newfreq);
99 return;
100 }
101
102 *(u32 *)newfreq->value = cpu_to_be32(*(u32 *)XTFPGA_CLKFRQ_VADDR);
103 prom_update_property(node, newfreq);
104}
105
106static int __init machine_setup(void)
107{
108 struct device_node *serial = NULL;
109
110 while ((serial = of_find_compatible_node(serial, NULL, "ns16550a")))
111 update_clock_frequency(serial);
112 return 0;
113}
114arch_initcall(machine_setup);
115
116#endif
117
118/* early initialization */
119
120void __init platform_init(bp_tag_t *first)
121{
122}
123
124/* Heartbeat. */
125
126void platform_heartbeat(void)
127{
128}
129
130#ifdef CONFIG_XTENSA_CALIBRATE_CCOUNT
131
132void platform_calibrate_ccount(void)
133{
134 long clk_freq = 0;
135#ifdef CONFIG_OF
136 struct device_node *cpu =
137 of_find_compatible_node(NULL, NULL, "xtensa,cpu");
138 if (cpu) {
139 u32 freq;
140 update_clock_frequency(cpu);
141 if (!of_property_read_u32(cpu, "clock-frequency", &freq))
142 clk_freq = freq;
143 }
144#endif
145 if (!clk_freq)
146 clk_freq = *(long *)XTFPGA_CLKFRQ_VADDR;
147
148 ccount_per_jiffy = clk_freq / HZ;
149 nsec_per_ccount = 1000000000UL / clk_freq;
150}
151
152#endif
153
154#ifndef CONFIG_OF
155
156#include <linux/serial_8250.h>
157#include <linux/if.h>
158#include <net/ethoc.h>
159
160/*----------------------------------------------------------------------------
161 * Ethernet -- OpenCores Ethernet MAC (ethoc driver)
162 */
163
164static struct resource ethoc_res[] __initdata = {
165 [0] = { /* register space */
166 .start = OETH_REGS_PADDR,
167 .end = OETH_REGS_PADDR + OETH_REGS_SIZE - 1,
168 .flags = IORESOURCE_MEM,
169 },
170 [1] = { /* buffer space */
171 .start = OETH_SRAMBUFF_PADDR,
172 .end = OETH_SRAMBUFF_PADDR + OETH_SRAMBUFF_SIZE - 1,
173 .flags = IORESOURCE_MEM,
174 },
175 [2] = { /* IRQ number */
176 .start = OETH_IRQ,
177 .end = OETH_IRQ,
178 .flags = IORESOURCE_IRQ,
179 },
180};
181
182static struct ethoc_platform_data ethoc_pdata __initdata = {
183 /*
184 * The MAC address for these boards is 00:50:c2:13:6f:xx.
185 * The last byte (here as zero) is read from the DIP switches on the
186 * board.
187 */
188 .hwaddr = { 0x00, 0x50, 0xc2, 0x13, 0x6f, 0 },
189 .phy_id = -1,
190};
191
192static struct platform_device ethoc_device __initdata = {
193 .name = "ethoc",
194 .id = -1,
195 .num_resources = ARRAY_SIZE(ethoc_res),
196 .resource = ethoc_res,
197 .dev = {
198 .platform_data = &ethoc_pdata,
199 },
200};
201
202/*----------------------------------------------------------------------------
203 * UART
204 */
205
206static struct resource serial_resource __initdata = {
207 .start = DUART16552_PADDR,
208 .end = DUART16552_PADDR + 0x1f,
209 .flags = IORESOURCE_MEM,
210};
211
212static struct plat_serial8250_port serial_platform_data[] __initdata = {
213 [0] = {
214 .mapbase = DUART16552_PADDR,
215 .irq = DUART16552_INTNUM,
216 .flags = UPF_BOOT_AUTOCONF | UPF_SKIP_TEST |
217 UPF_IOREMAP,
218 .iotype = UPIO_MEM32,
219 .regshift = 2,
220 .uartclk = 0, /* set in xtavnet_init() */
221 },
222 { },
223};
224
225static struct platform_device xtavnet_uart __initdata = {
226 .name = "serial8250",
227 .id = PLAT8250_DEV_PLATFORM,
228 .dev = {
229 .platform_data = serial_platform_data,
230 },
231 .num_resources = 1,
232 .resource = &serial_resource,
233};
234
235/* platform devices */
236static struct platform_device *platform_devices[] __initdata = {
237 &ethoc_device,
238 &xtavnet_uart,
239};
240
241
242static int __init xtavnet_init(void)
243{
244 /* Ethernet MAC address. */
245 ethoc_pdata.hwaddr[5] = *(u32 *)DIP_SWITCHES_VADDR;
246
247 /* Clock rate varies among FPGA bitstreams; board specific FPGA register
248 * reports the actual clock rate.
249 */
250 serial_platform_data[0].uartclk = *(long *)XTFPGA_CLKFRQ_VADDR;
251
252
253 /* register platform devices */
254 platform_add_devices(platform_devices, ARRAY_SIZE(platform_devices));
255
256 /* ETHOC driver is a bit quiet; at least display Ethernet MAC, so user
257 * knows whether they set it correctly on the DIP switches.
258 */
259 pr_info("XTFPGA: Ethernet MAC %pM\n", ethoc_pdata.hwaddr);
260
261 return 0;
262}
263
264/*
265 * Register to be done during do_initcalls().
266 */
267arch_initcall(xtavnet_init);
268
269#endif /* CONFIG_OF */