diff options
author | Atsushi Nemoto <anemo@mba.ocn.ne.jp> | 2008-07-11 10:27:54 -0400 |
---|---|---|
committer | Ralf Baechle <ralf@linux-mips.org> | 2008-07-15 13:44:35 -0400 |
commit | edcaf1a6a77315562e9781245cc8e028c9a921dc (patch) | |
tree | a20a0a85071fa283c36db87a41d1a7e091a35781 /arch/mips/txx9/generic/setup.c | |
parent | 766891565bdaf605ea4aebe3e75de77e848254d0 (diff) |
[MIPS] TXx9: Make single kernel can support multiple boards
Make single kernel can be used on RBTX4927/37/38. Also make
some SoC-specific code independent from board-specific code.
Signed-off-by: Atsushi Nemoto <anemo@mba.ocn.ne.jp>
Signed-off-by: Ralf Baechle <ralf@linux-mips.org>
Diffstat (limited to 'arch/mips/txx9/generic/setup.c')
-rw-r--r-- | arch/mips/txx9/generic/setup.c | 169 |
1 files changed, 169 insertions, 0 deletions
diff --git a/arch/mips/txx9/generic/setup.c b/arch/mips/txx9/generic/setup.c index 46a631177757..66ff74f80c6b 100644 --- a/arch/mips/txx9/generic/setup.c +++ b/arch/mips/txx9/generic/setup.c | |||
@@ -14,7 +14,16 @@ | |||
14 | #include <linux/init.h> | 14 | #include <linux/init.h> |
15 | #include <linux/kernel.h> | 15 | #include <linux/kernel.h> |
16 | #include <linux/types.h> | 16 | #include <linux/types.h> |
17 | #include <linux/interrupt.h> | ||
18 | #include <linux/string.h> | ||
19 | #include <linux/module.h> | ||
20 | #include <linux/clk.h> | ||
21 | #include <linux/err.h> | ||
22 | #include <asm/bootinfo.h> | ||
17 | #include <asm/txx9/generic.h> | 23 | #include <asm/txx9/generic.h> |
24 | #ifdef CONFIG_CPU_TX49XX | ||
25 | #include <asm/txx9/tx4938.h> | ||
26 | #endif | ||
18 | 27 | ||
19 | /* EBUSC settings of TX4927, etc. */ | 28 | /* EBUSC settings of TX4927, etc. */ |
20 | struct resource txx9_ce_res[8]; | 29 | struct resource txx9_ce_res[8]; |
@@ -49,3 +58,163 @@ txx9_reg_res_init(unsigned int pcode, unsigned long base, unsigned long size) | |||
49 | unsigned int txx9_master_clock; | 58 | unsigned int txx9_master_clock; |
50 | unsigned int txx9_cpu_clock; | 59 | unsigned int txx9_cpu_clock; |
51 | unsigned int txx9_gbus_clock; | 60 | unsigned int txx9_gbus_clock; |
61 | |||
62 | |||
63 | /* Minimum CLK support */ | ||
64 | |||
65 | struct clk *clk_get(struct device *dev, const char *id) | ||
66 | { | ||
67 | if (!strcmp(id, "spi-baseclk")) | ||
68 | return (struct clk *)(txx9_gbus_clock / 2 / 4); | ||
69 | if (!strcmp(id, "imbus_clk")) | ||
70 | return (struct clk *)(txx9_gbus_clock / 2); | ||
71 | return ERR_PTR(-ENOENT); | ||
72 | } | ||
73 | EXPORT_SYMBOL(clk_get); | ||
74 | |||
75 | int clk_enable(struct clk *clk) | ||
76 | { | ||
77 | return 0; | ||
78 | } | ||
79 | EXPORT_SYMBOL(clk_enable); | ||
80 | |||
81 | void clk_disable(struct clk *clk) | ||
82 | { | ||
83 | } | ||
84 | EXPORT_SYMBOL(clk_disable); | ||
85 | |||
86 | unsigned long clk_get_rate(struct clk *clk) | ||
87 | { | ||
88 | return (unsigned long)clk; | ||
89 | } | ||
90 | EXPORT_SYMBOL(clk_get_rate); | ||
91 | |||
92 | void clk_put(struct clk *clk) | ||
93 | { | ||
94 | } | ||
95 | EXPORT_SYMBOL(clk_put); | ||
96 | |||
97 | extern struct txx9_board_vec jmr3927_vec; | ||
98 | extern struct txx9_board_vec rbtx4927_vec; | ||
99 | extern struct txx9_board_vec rbtx4937_vec; | ||
100 | extern struct txx9_board_vec rbtx4938_vec; | ||
101 | |||
102 | /* board definitions */ | ||
103 | static struct txx9_board_vec *board_vecs[] __initdata = { | ||
104 | #ifdef CONFIG_TOSHIBA_JMR3927 | ||
105 | &jmr3927_vec, | ||
106 | #endif | ||
107 | #ifdef CONFIG_TOSHIBA_RBTX4927 | ||
108 | &rbtx4927_vec, | ||
109 | &rbtx4937_vec, | ||
110 | #endif | ||
111 | #ifdef CONFIG_TOSHIBA_RBTX4938 | ||
112 | &rbtx4938_vec, | ||
113 | #endif | ||
114 | }; | ||
115 | struct txx9_board_vec *txx9_board_vec __initdata; | ||
116 | static char txx9_system_type[32]; | ||
117 | |||
118 | void __init prom_init_cmdline(void) | ||
119 | { | ||
120 | int argc = (int)fw_arg0; | ||
121 | char **argv = (char **)fw_arg1; | ||
122 | int i; /* Always ignore the "-c" at argv[0] */ | ||
123 | |||
124 | /* ignore all built-in args if any f/w args given */ | ||
125 | if (argc > 1) | ||
126 | *arcs_cmdline = '\0'; | ||
127 | |||
128 | for (i = 1; i < argc; i++) { | ||
129 | if (i != 1) | ||
130 | strcat(arcs_cmdline, " "); | ||
131 | strcat(arcs_cmdline, argv[i]); | ||
132 | } | ||
133 | } | ||
134 | |||
135 | void __init prom_init(void) | ||
136 | { | ||
137 | int i; | ||
138 | |||
139 | #ifdef CONFIG_CPU_TX39XX | ||
140 | mips_machtype = MACH_TOSHIBA_JMR3927; | ||
141 | #endif | ||
142 | #ifdef CONFIG_CPU_TX49XX | ||
143 | switch (TX4938_REV_PCODE()) { | ||
144 | case 0x4927: | ||
145 | mips_machtype = MACH_TOSHIBA_RBTX4927; | ||
146 | break; | ||
147 | case 0x4937: | ||
148 | mips_machtype = MACH_TOSHIBA_RBTX4937; | ||
149 | break; | ||
150 | case 0x4938: | ||
151 | mips_machtype = MACH_TOSHIBA_RBTX4938; | ||
152 | break; | ||
153 | } | ||
154 | #endif | ||
155 | for (i = 0; i < ARRAY_SIZE(board_vecs); i++) { | ||
156 | if (board_vecs[i]->type == mips_machtype) { | ||
157 | txx9_board_vec = board_vecs[i]; | ||
158 | strcpy(txx9_system_type, txx9_board_vec->system); | ||
159 | return txx9_board_vec->prom_init(); | ||
160 | } | ||
161 | } | ||
162 | } | ||
163 | |||
164 | void __init prom_free_prom_memory(void) | ||
165 | { | ||
166 | } | ||
167 | |||
168 | const char *get_system_type(void) | ||
169 | { | ||
170 | return txx9_system_type; | ||
171 | } | ||
172 | |||
173 | char * __init prom_getcmdline(void) | ||
174 | { | ||
175 | return &(arcs_cmdline[0]); | ||
176 | } | ||
177 | |||
178 | /* wrappers */ | ||
179 | void __init plat_mem_setup(void) | ||
180 | { | ||
181 | txx9_board_vec->mem_setup(); | ||
182 | } | ||
183 | |||
184 | void __init arch_init_irq(void) | ||
185 | { | ||
186 | txx9_board_vec->irq_setup(); | ||
187 | } | ||
188 | |||
189 | void __init plat_time_init(void) | ||
190 | { | ||
191 | txx9_board_vec->time_init(); | ||
192 | } | ||
193 | |||
194 | static int __init _txx9_arch_init(void) | ||
195 | { | ||
196 | if (txx9_board_vec->arch_init) | ||
197 | txx9_board_vec->arch_init(); | ||
198 | return 0; | ||
199 | } | ||
200 | arch_initcall(_txx9_arch_init); | ||
201 | |||
202 | static int __init _txx9_device_init(void) | ||
203 | { | ||
204 | if (txx9_board_vec->device_init) | ||
205 | txx9_board_vec->device_init(); | ||
206 | return 0; | ||
207 | } | ||
208 | device_initcall(_txx9_device_init); | ||
209 | |||
210 | int (*txx9_irq_dispatch)(int pending); | ||
211 | asmlinkage void plat_irq_dispatch(void) | ||
212 | { | ||
213 | int pending = read_c0_status() & read_c0_cause() & ST0_IM; | ||
214 | int irq = txx9_irq_dispatch(pending); | ||
215 | |||
216 | if (likely(irq >= 0)) | ||
217 | do_IRQ(irq); | ||
218 | else | ||
219 | spurious_interrupt(); | ||
220 | } | ||