aboutsummaryrefslogtreecommitdiffstats
path: root/arch/powerpc/kernel/prom_init.c
diff options
context:
space:
mode:
Diffstat (limited to 'arch/powerpc/kernel/prom_init.c')
-rw-r--r--arch/powerpc/kernel/prom_init.c149
1 files changed, 79 insertions, 70 deletions
diff --git a/arch/powerpc/kernel/prom_init.c b/arch/powerpc/kernel/prom_init.c
index 5d89a21dd0d6..5ab4c8466cc9 100644
--- a/arch/powerpc/kernel/prom_init.c
+++ b/arch/powerpc/kernel/prom_init.c
@@ -2142,82 +2142,34 @@ static void __init fixup_device_tree_pmac(void)
2142#endif 2142#endif
2143 2143
2144#ifdef CONFIG_PPC_EFIKA 2144#ifdef CONFIG_PPC_EFIKA
2145/* The current fw of the Efika has a device tree needs quite a few 2145/*
2146 * fixups to be compliant with the mpc52xx bindings. It's currently 2146 * The MPC5200 FEC driver requires an phy-handle property to tell it how
2147 * unknown if it will ever be compliant (come on bPlan ...) so we do fixups. 2147 * to talk to the phy. If the phy-handle property is missing, then this
2148 * NOTE that we (barely) tolerate it because the EFIKA was out before 2148 * function is called to add the appropriate nodes and link it to the
2149 * the bindings were finished, for any new boards -> RTFM ! */ 2149 * ethernet node.
2150 2150 */
2151struct subst_entry { 2151static void __init fixup_device_tree_efika_add_phy(void)
2152 char *path;
2153 char *property;
2154 void *value;
2155 int value_len;
2156};
2157
2158static void __init fixup_device_tree_efika(void)
2159{ 2152{
2160 /* Substitution table */
2161 #define prop_cstr(x) x, sizeof(x)
2162 int prop_sound_irq[3] = { 2, 2, 0 };
2163 int prop_bcomm_irq[3*16] = { 3,0,0, 3,1,0, 3,2,0, 3,3,0,
2164 3,4,0, 3,5,0, 3,6,0, 3,7,0,
2165 3,8,0, 3,9,0, 3,10,0, 3,11,0,
2166 3,12,0, 3,13,0, 3,14,0, 3,15,0 };
2167 struct subst_entry efika_subst_table[] = {
2168 { "/", "device_type", prop_cstr("efika") },
2169 { "/builtin", "device_type", prop_cstr("soc") },
2170 { "/builtin/ata", "compatible", prop_cstr("mpc5200b-ata\0mpc5200-ata"), },
2171 { "/builtin/bestcomm", "compatible", prop_cstr("mpc5200b-bestcomm\0mpc5200-bestcomm") },
2172 { "/builtin/bestcomm", "interrupts", prop_bcomm_irq, sizeof(prop_bcomm_irq) },
2173 { "/builtin/ethernet", "compatible", prop_cstr("mpc5200b-fec\0mpc5200-fec") },
2174 { "/builtin/pic", "compatible", prop_cstr("mpc5200b-pic\0mpc5200-pic") },
2175 { "/builtin/serial", "compatible", prop_cstr("mpc5200b-psc-uart\0mpc5200-psc-uart") },
2176 { "/builtin/sound", "compatible", prop_cstr("mpc5200b-psc-ac97\0mpc5200-psc-ac97") },
2177 { "/builtin/sound", "interrupts", prop_sound_irq, sizeof(prop_sound_irq) },
2178 { "/builtin/sram", "compatible", prop_cstr("mpc5200b-sram\0mpc5200-sram") },
2179 { "/builtin/sram", "device_type", prop_cstr("sram") },
2180 {}
2181 };
2182 #undef prop_cstr
2183
2184 /* Vars */
2185 u32 node; 2153 u32 node;
2186 char prop[64]; 2154 char prop[64];
2187 int rv, i; 2155 int rv;
2188 2156
2189 /* Check if we're really running on a EFIKA */ 2157 /* Check if /builtin/ethernet exists - bail if it doesn't */
2190 node = call_prom("finddevice", 1, 1, ADDR("/")); 2158 node = call_prom("finddevice", 1, 1, ADDR("/builtin/ethernet"));
2191 if (!PHANDLE_VALID(node)) 2159 if (!PHANDLE_VALID(node))
2192 return; 2160 return;
2193 2161
2194 rv = prom_getprop(node, "model", prop, sizeof(prop)); 2162 /* Check if the phy-handle property exists - bail if it does */
2195 if (rv == PROM_ERROR) 2163 rv = prom_getprop(node, "phy-handle", prop, sizeof(prop));
2196 return; 2164 if (!rv)
2197 if (strcmp(prop, "EFIKA5K2"))
2198 return; 2165 return;
2199 2166
2200 prom_printf("Applying EFIKA device tree fixups\n"); 2167 /*
2201 2168 * At this point the ethernet device doesn't have a phy described.
2202 /* Process substitution table */ 2169 * Now we need to add the missing phy node and linkage
2203 for (i=0; efika_subst_table[i].path; i++) { 2170 */
2204 struct subst_entry *se = &efika_subst_table[i];
2205
2206 node = call_prom("finddevice", 1, 1, ADDR(se->path));
2207 if (!PHANDLE_VALID(node)) {
2208 prom_printf("fixup_device_tree_efika: ",
2209 "skipped entry %x - not found\n", i);
2210 continue;
2211 }
2212
2213 rv = prom_setprop(node, se->path, se->property,
2214 se->value, se->value_len );
2215 if (rv == PROM_ERROR)
2216 prom_printf("fixup_device_tree_efika: ",
2217 "skipped entry %x - setprop error\n", i);
2218 }
2219 2171
2220 /* Make sure ethernet mdio bus node exists */ 2172 /* Check for an MDIO bus node - if missing then create one */
2221 node = call_prom("finddevice", 1, 1, ADDR("/builtin/mdio")); 2173 node = call_prom("finddevice", 1, 1, ADDR("/builtin/mdio"));
2222 if (!PHANDLE_VALID(node)) { 2174 if (!PHANDLE_VALID(node)) {
2223 prom_printf("Adding Ethernet MDIO node\n"); 2175 prom_printf("Adding Ethernet MDIO node\n");
@@ -2226,8 +2178,8 @@ static void __init fixup_device_tree_efika(void)
2226 " new-device" 2178 " new-device"
2227 " 1 encode-int s\" #address-cells\" property" 2179 " 1 encode-int s\" #address-cells\" property"
2228 " 0 encode-int s\" #size-cells\" property" 2180 " 0 encode-int s\" #size-cells\" property"
2229 " s\" mdio\" 2dup device-name device-type" 2181 " s\" mdio\" device-name"
2230 " s\" mpc5200b-fec-phy\" encode-string" 2182 " s\" fsl,mpc5200b-mdio\" encode-string"
2231 " s\" compatible\" property" 2183 " s\" compatible\" property"
2232 " 0xf0003000 0x400 reg" 2184 " 0xf0003000 0x400 reg"
2233 " 0x2 encode-int" 2185 " 0x2 encode-int"
@@ -2237,8 +2189,10 @@ static void __init fixup_device_tree_efika(void)
2237 " finish-device"); 2189 " finish-device");
2238 }; 2190 };
2239 2191
2240 /* Make sure ethernet phy device node exist */ 2192 /* Check for a PHY device node - if missing then create one and
2241 node = call_prom("finddevice", 1, 1, ADDR("/builtin/mdio/ethernet-phy")); 2193 * give it's phandle to the ethernet node */
2194 node = call_prom("finddevice", 1, 1,
2195 ADDR("/builtin/mdio/ethernet-phy"));
2242 if (!PHANDLE_VALID(node)) { 2196 if (!PHANDLE_VALID(node)) {
2243 prom_printf("Adding Ethernet PHY node\n"); 2197 prom_printf("Adding Ethernet PHY node\n");
2244 call_prom("interpret", 1, 1, 2198 call_prom("interpret", 1, 1,
@@ -2254,7 +2208,62 @@ static void __init fixup_device_tree_efika(void)
2254 " s\" phy-handle\" property" 2208 " s\" phy-handle\" property"
2255 " device-end"); 2209 " device-end");
2256 } 2210 }
2211}
2212
2213static void __init fixup_device_tree_efika(void)
2214{
2215 int sound_irq[3] = { 2, 2, 0 };
2216 int bcomm_irq[3*16] = { 3,0,0, 3,1,0, 3,2,0, 3,3,0,
2217 3,4,0, 3,5,0, 3,6,0, 3,7,0,
2218 3,8,0, 3,9,0, 3,10,0, 3,11,0,
2219 3,12,0, 3,13,0, 3,14,0, 3,15,0 };
2220 u32 node;
2221 char prop[64];
2222 int rv, len;
2223
2224 /* Check if we're really running on a EFIKA */
2225 node = call_prom("finddevice", 1, 1, ADDR("/"));
2226 if (!PHANDLE_VALID(node))
2227 return;
2228
2229 rv = prom_getprop(node, "model", prop, sizeof(prop));
2230 if (rv == PROM_ERROR)
2231 return;
2232 if (strcmp(prop, "EFIKA5K2"))
2233 return;
2234
2235 prom_printf("Applying EFIKA device tree fixups\n");
2236
2237 /* Claiming to be 'chrp' is death */
2238 node = call_prom("finddevice", 1, 1, ADDR("/"));
2239 rv = prom_getprop(node, "device_type", prop, sizeof(prop));
2240 if (rv != PROM_ERROR && (strcmp(prop, "chrp") == 0))
2241 prom_setprop(node, "/", "device_type", "efika", sizeof("efika"));
2242
2243 /* Fixup bestcomm interrupts property */
2244 node = call_prom("finddevice", 1, 1, ADDR("/builtin/bestcomm"));
2245 if (PHANDLE_VALID(node)) {
2246 len = prom_getproplen(node, "interrupts");
2247 if (len == 12) {
2248 prom_printf("Fixing bestcomm interrupts property\n");
2249 prom_setprop(node, "/builtin/bestcom", "interrupts",
2250 bcomm_irq, sizeof(bcomm_irq));
2251 }
2252 }
2253
2254 /* Fixup sound interrupts property */
2255 node = call_prom("finddevice", 1, 1, ADDR("/builtin/sound"));
2256 if (PHANDLE_VALID(node)) {
2257 rv = prom_getprop(node, "interrupts", prop, sizeof(prop));
2258 if (rv == PROM_ERROR) {
2259 prom_printf("Adding sound interrupts property\n");
2260 prom_setprop(node, "/builtin/sound", "interrupts",
2261 sound_irq, sizeof(sound_irq));
2262 }
2263 }
2257 2264
2265 /* Make sure ethernet phy-handle property exists */
2266 fixup_device_tree_efika_add_phy();
2258} 2267}
2259#else 2268#else
2260#define fixup_device_tree_efika() 2269#define fixup_device_tree_efika()