Path: blob/master/arch/powerpc/sysdev/micropatch.c
10817 views
1/* Microcode patches for the CPM as supplied by Motorola.2* This is the one for IIC/SPI. There is a newer one that3* also relocates SMC2, but this would require additional changes4* to uart.c, so I am holding off on that for a moment.5*/6#include <linux/init.h>7#include <linux/errno.h>8#include <linux/sched.h>9#include <linux/kernel.h>10#include <linux/param.h>11#include <linux/string.h>12#include <linux/mm.h>13#include <linux/interrupt.h>14#include <asm/irq.h>15#include <asm/mpc8xx.h>16#include <asm/page.h>17#include <asm/pgtable.h>18#include <asm/8xx_immap.h>19#include <asm/cpm.h>20#include <asm/cpm1.h>2122/*23* I2C/SPI relocation patch arrays.24*/2526#ifdef CONFIG_I2C_SPI_UCODE_PATCH2728static uint patch_2000[] __initdata = {290x7FFFEFD9,300x3FFD0000,310x7FFB49F7,320x7FF90000,330x5FEFADF7,340x5F89ADF7,350x5FEFAFF7,360x5F89AFF7,370x3A9CFBC8,380xE7C0EDF0,390x77C1E1BB,400xF4DC7F1D,410xABAD932F,420x4E08FDCF,430x6E0FAFF8,440x7CCF76CF,450xFD1FF9CF,460xABF88DC6,470xAB5679F7,480xB0937383,490xDFCE79F7,500xB091E6BB,510xE5BBE74F,520xB3FA6F0F,530x6FFB76CE,540xEE0DF9CF,550x2BFBEFEF,560xCFEEF9CF,570x76CEAD24,580x90B2DF9A,590x7FDDD0BF,600x4BF847FD,610x7CCF76CE,620xCFEF7E1F,630x7F1D7DFD,640xF0B6EF71,650x7FC177C1,660xFBC86079,670xE722FBC8,680x5FFFDFFF,690x5FB2FFFB,700xFBC8F3C8,710x94A67F01,720x7F1D5F39,730xAFE85F5E,740xFFDFDF96,750xCB9FAF7D,760x5FC1AFED,770x8C1C5FC1,780xAFDD5FC3,790xDF9A7EFD,800xB0B25FB2,810xFFFEABAD,820x5FB2FFFE,830x5FCE600B,840xE6BB600B,850x5FCEDFC6,860x27FBEFDF,870x5FC8CFDE,880x3A9CE7C0,890xEDF0F3C8,900x7F0154CD,910x7F1D2D3D,920x363A7570,930x7E0AF1CE,940x37EF2E68,950x7FEE10EC,960xADF8EFDE,970xCFEAE52F,980x7D0FE12B,990xF1CE5F65,1000x7E0A4DF8,1010xCFEA5F72,1020x7D0BEFEE,1030xCFEA5F74,1040xE522EFDE,1050x5F74CFDA,1060x0B627385,1070xDF627E0A,1080x30D8145B,1090xBFFFF3C8,1100x5FFFDFFF,1110xA7F85F5E,1120xBFFE7F7D,1130x10D31450,1140x5F36BFFF,1150xAF785F5E,1160xBFFDA7F8,1170x5F36BFFE,1180x77FD30C0,1190x4E08FDCF,1200xE5FF6E0F,1210xAFF87E1F,1220x7E0FFD1F,1230xF1CF5F1B,1240xABF80D5E,1250x5F5EFFEF,1260x79F730A2,1270xAFDD5F34,1280x47F85F34,1290xAFED7FDD,1300x50B24978,1310x47FD7F1D,1320x7DFD70AD,1330xEF717EC1,1340x6BA47F01,1350x2D267EFD,1360x30DE5F5E,1370xFFFD5F5E,1380xFFEF5F5E,1390xFFDF0CA0,1400xAFED0A9E,1410xAFDD0C3A,1420x5F3AAFBD,1430x7FBDB082,1440x5F8247F8145};146147static uint patch_2f00[] __initdata = {1480x3E303430,1490x34343737,1500xABF7BF9B,1510x994B4FBD,1520xBD599493,1530x349FFF37,1540xFB9B177D,1550xD9936956,1560xBBFDD697,1570xBDD2FD11,1580x31DB9BB3,1590x63139637,1600x93733693,1610x193137F7,1620x331737AF,1630x7BB9B999,1640xBB197957,1650x7FDFD3D5,1660x73B773F7,1670x37933B99,1680x1D115316,1690x99315315,1700x31694BF4,1710xFBDBD359,1720x31497353,1730x76956D69,1740x7B9D9693,1750x13131979,1760x79376935177};178#endif179180/*181* I2C/SPI/SMC1 relocation patch arrays.182*/183184#ifdef CONFIG_I2C_SPI_SMC1_UCODE_PATCH185186static uint patch_2000[] __initdata = {1870x3fff0000,1880x3ffd0000,1890x3ffb0000,1900x3ff90000,1910x5f13eff8,1920x5eb5eff8,1930x5f88adf7,1940x5fefadf7,1950x3a9cfbc8,1960x77cae1bb,1970xf4de7fad,1980xabae9330,1990x4e08fdcf,2000x6e0faff8,2010x7ccf76cf,2020xfdaff9cf,2030xabf88dc8,2040xab5879f7,2050xb0925d8d,2060xdfd079f7,2070xb090e6bb,2080xe5bbe74f,2090x9e046f0f,2100x6ffb76ce,2110xee0cf9cf,2120x2bfbefef,2130xcfeef9cf,2140x76cead23,2150x90b3df99,2160x7fddd0c1,2170x4bf847fd,2180x7ccf76ce,2190xcfef77ca,2200x7eaf7fad,2210x7dfdf0b7,2220xef7a7fca,2230x77cafbc8,2240x6079e722,2250xfbc85fff,2260xdfff5fb3,2270xfffbfbc8,2280xf3c894a5,2290xe7c9edf9,2300x7f9a7fad,2310x5f36afe8,2320x5f5bffdf,2330xdf95cb9e,2340xaf7d5fc3,2350xafed8c1b,2360x5fc3afdd,2370x5fc5df99,2380x7efdb0b3,2390x5fb3fffe,2400xabae5fb3,2410xfffe5fd0,2420x600be6bb,2430x600b5fd0,2440xdfc827fb,2450xefdf5fca,2460xcfde3a9c,2470xe7c9edf9,2480xf3c87f9e,2490x54ca7fed,2500x2d3a3637,2510x756f7e9a,2520xf1ce37ef,2530x2e677fee,2540x10ebadf8,2550xefdecfea,2560xe52f7d9f,2570xe12bf1ce,2580x5f647e9a,2590x4df8cfea,2600x5f717d9b,2610xefeecfea,2620x5f73e522,2630xefde5f73,2640xcfda0b61,2650x5d8fdf61,2660xe7c9edf9,2670x7e9a30d5,2680x1458bfff,2690xf3c85fff,2700xdfffa7f8,2710x5f5bbffe,2720x7f7d10d0,2730x144d5f33,2740xbfffaf78,2750x5f5bbffd,2760xa7f85f33,2770xbffe77fd,2780x30bd4e08,2790xfdcfe5ff,2800x6e0faff8,2810x7eef7e9f,2820xfdeff1cf,2830x5f17abf8,2840x0d5b5f5b,2850xffef79f7,2860x309eafdd,2870x5f3147f8,2880x5f31afed,2890x7fdd50af,2900x497847fd,2910x7f9e7fed,2920x7dfd70a9,2930xef7e7ece,2940x6ba07f9e,2950x2d227efd,2960x30db5f5b,2970xfffd5f5b,2980xffef5f5b,2990xffdf0c9c,3000xafed0a9a,3010xafdd0c37,3020x5f37afbd,3030x7fbdb081,3040x5f8147f8,3050x3a11e710,3060xedf0ccdd,3070xf3186d0a,3080x7f0e5f06,3090x7fedbb38,3100x3afe7468,3110x7fedf4fc,3120x8ffbb951,3130xb85f77fd,3140xb0df5ddd,3150xdefe7fed,3160x90e1e74d,3170x6f0dcbf7,3180xe7decfed,3190xcb74cfed,3200xcfeddf6d,3210x91714f74,3220x5dd2deef,3230x9e04e7df,3240xefbb6ffb,3250xe7ef7f0e,3260x9e097fed,3270xebdbeffa,3280xeb54affb,3290x7fea90d7,3300x7e0cf0c3,3310xbffff318,3320x5fffdfff,3330xac59efea,3340x7fce1ee5,3350xe2ff5ee1,3360xaffbe2ff,3370x5ee3affb,3380xf9cc7d0f,3390xaef8770f,3400x7d0fb0c6,3410xeffbbfff,3420xcfef5ede,3430x7d0fbfff,3440x5ede4cf8,3450x7fddd0bf,3460x49f847fd,3470x7efdf0bb,3480x7fedfffd,3490x7dfdf0b7,3500xef7e7e1e,3510x5ede7f0e,3520x3a11e710,3530xedf0ccab,3540xfb18ad2e,3550x1ea9bbb8,3560x74283b7e,3570x73c2e4bb,3580x2ada4fb8,3590xdc21e4bb,3600xb2a1ffbf,3610x5e2c43f8,3620xfc87e1bb,3630xe74ffd91,3640x6f0f4fe8,3650xc7ba32e2,3660xf396efeb,3670x600b4f78,3680xe5bb760b,3690x53acaef8,3700x4ef88b0e,3710xcfef9e09,3720xabf8751f,3730xefef5bac,3740x741f4fe8,3750x751e760d,3760x7fdbf081,3770x741cafce,3780xefcc7fce,3790x751e70ac,3800x741ce7bb,3810x3372cfed,3820xafdbefeb,3830xe5bb760b,3840x53f2aef8,3850xafe8e7eb,3860x4bf8771e,3870x7e247fed,3880x4fcbe2cc,3890x7fbc30a9,3900x7b0f7a0f,3910x34d577fd,3920x308b5db7,3930xde553e5f,3940xaf78741f,3950x741f30f0,3960xcfef5e2c,3970x741f3eac,3980xafb8771e,3990x5e677fed,4000x0bd3e2cc,4010x741ccfec,4020xe5ca53cd,4030x6fcb4f74,4040x5dadde4b,4050x2ab63d38,4060x4bb3de30,4070x751f741c,4080x6c42effa,4090xefea7fce,4100x6ffc30be,4110xefec3fca,4120x30b3de2e,4130xadf85d9e,4140xaf7daefd,4150x5d9ede2e,4160x5d9eafdd,4170x761f10ac,4180x1da07efd,4190x30adfffe,4200x4908fb18,4210x5fffdfff,4220xafbb709b,4230x4ef85e67,4240xadf814ad,4250x7a0f70ad,4260xcfef50ad,4270x7a0fde30,4280x5da0afed,4290x3c12780f,4300xefef780f,4310xefef790f,4320xa7f85e0f,4330xffef790f,4340xefef790f,4350x14adde2e,4360x5d9eadfd,4370x5e2dfffb,4380xe79addfd,4390xeff96079,4400x607ae79a,4410xddfceff9,4420x60795dff,4430x607acfef,4440xefefefdf,4450xefbfef7f,4460xeeffedff,4470xebffe7ff,4480xafefafdf,4490xafbfaf7f,4500xaeffadff,4510xabffa7ff,4520x6fef6fdf,4530x6fbf6f7f,4540x6eff6dff,4550x6bff67ff,4560x2fef2fdf,4570x2fbf2f7f,4580x2eff2dff,4590x2bff27ff,4600x4e08fd1f,4610xe5ff6e0f,4620xaff87eef,4630x7e0ffdef,4640xf11f6079,4650xabf8f542,4660x7e0af11c,4670x37cfae3a,4680x7fec90be,4690xadf8efdc,4700xcfeae52f,4710x7d0fe12b,4720xf11c6079,4730x7e0a4df8,4740xcfea5dc4,4750x7d0befec,4760xcfea5dc6,4770xe522efdc,4780x5dc6cfda,4790x4e08fd1f,4800x6e0faff8,4810x7c1f761f,4820xfdeff91f,4830x6079abf8,4840x761cee24,4850xf91f2bfb,4860xefefcfec,4870xf91f6079,4880x761c27fb,4890xefdf5da7,4900xcfdc7fdd,4910xd09c4bf8,4920x47fd7c1f,4930x761ccfcf,4940x7eef7fed,4950x7dfdf093,4960xef7e7f1e,4970x771efb18,4980x6079e722,4990xe6bbe5bb,5000xae0ae5bb,5010x600bae85,5020xe2bbe2bb,5030xe2bbe2bb,5040xaf02e2bb,5050xe2bb2ff9,5060x6079e2bb507};508509static uint patch_2f00[] __initdata = {5100x30303030,5110x3e3e3434,5120xabbf9b99,5130x4b4fbdbd,5140x59949334,5150x9fff37fb,5160x9b177dd9,5170x936956bb,5180xfbdd697b,5190xdd2fd113,5200x1db9f7bb,5210x36313963,5220x79373369,5230x3193137f,5240x7331737a,5250xf7bb9b99,5260x9bb19795,5270x77fdfd3d,5280x573b773f,5290x737933f7,5300xb991d115,5310x31699315,5320x31531694,5330xbf4fbdbd,5340x35931497,5350x35376956,5360xbd697b9d,5370x96931313,5380x19797937,5390x6935af78,5400xb9b3baa3,5410xb8788683,5420x368f78f7,5430x87778733,5440x3ffffb3b,5450x8e8f78b8,5460x1d118e13,5470xf3ff3f8b,5480x6bd8e173,5490xd1366856,5500x68d1687b,5510x3daf78b8,5520x3a3a3f87,5530x8f81378f,5540xf876f887,5550x77fd8778,5560x737de8d6,5570xbbf8bfff,5580xd8df87f7,5590xfd876f7b,5600x8bfff8bd,5610x8683387d,5620xb873d87b,5630x3b8fd7f8,5640xf7338883,5650xbb8ee1f8,5660xef837377,5670x3337b836,5680x817d11f8,5690x7378b878,5700xd3368b7d,5710xed731b7d,5720x833731f3,5730xf22f3f23574};575576static uint patch_2e00[] __initdata = {5770x27eeeeee,5780xeeeeeeee,5790xeeeeeeee,5800xeeeeeeee,5810xee4bf4fb,5820xdbd259bb,5830x1979577f,5840xdfd2d573,5850xb773f737,5860x4b4fbdbd,5870x25b9b177,5880xd2d17376,5890x956bbfdd,5900x697bdd2f,5910xff9f79ff,5920xff9ff22f593};594#endif595596/*597* USB SOF patch arrays.598*/599600#ifdef CONFIG_USB_SOF_UCODE_PATCH601602static uint patch_2000[] __initdata = {6030x7fff0000,6040x7ffd0000,6050x7ffb0000,6060x49f7ba5b,6070xba383ffb,6080xf9b8b46d,6090xe5ab4e07,6100xaf77bffe,6110x3f7bbf79,6120xba5bba38,6130xe7676076,6140x60750000615};616617static uint patch_2f00[] __initdata = {6180x3030304c,6190xcab9e441,6200xa1aaf220621};622#endif623624void __init cpm_load_patch(cpm8xx_t *cp)625{626volatile uint *dp; /* Dual-ported RAM. */627volatile cpm8xx_t *commproc;628#if defined(CONFIG_I2C_SPI_UCODE_PATCH) || \629defined(CONFIG_I2C_SPI_SMC1_UCODE_PATCH)630volatile iic_t *iip;631volatile struct spi_pram *spp;632#ifdef CONFIG_I2C_SPI_SMC1_UCODE_PATCH633volatile smc_uart_t *smp;634#endif635#endif636int i;637638commproc = cp;639640#ifdef CONFIG_USB_SOF_UCODE_PATCH641commproc->cp_rccr = 0;642643dp = (uint *)(commproc->cp_dpmem);644for (i=0; i<(sizeof(patch_2000)/4); i++)645*dp++ = patch_2000[i];646647dp = (uint *)&(commproc->cp_dpmem[0x0f00]);648for (i=0; i<(sizeof(patch_2f00)/4); i++)649*dp++ = patch_2f00[i];650651commproc->cp_rccr = 0x0009;652653printk("USB SOF microcode patch installed\n");654#endif /* CONFIG_USB_SOF_UCODE_PATCH */655656#if defined(CONFIG_I2C_SPI_UCODE_PATCH) || \657defined(CONFIG_I2C_SPI_SMC1_UCODE_PATCH)658659commproc->cp_rccr = 0;660661dp = (uint *)(commproc->cp_dpmem);662for (i=0; i<(sizeof(patch_2000)/4); i++)663*dp++ = patch_2000[i];664665dp = (uint *)&(commproc->cp_dpmem[0x0f00]);666for (i=0; i<(sizeof(patch_2f00)/4); i++)667*dp++ = patch_2f00[i];668669iip = (iic_t *)&commproc->cp_dparam[PROFF_IIC];670# define RPBASE 0x0500671iip->iic_rpbase = RPBASE;672673/* Put SPI above the IIC, also 32-byte aligned.674*/675i = (RPBASE + sizeof(iic_t) + 31) & ~31;676spp = (struct spi_pram *)&commproc->cp_dparam[PROFF_SPI];677spp->rpbase = i;678679# if defined(CONFIG_I2C_SPI_UCODE_PATCH)680commproc->cp_cpmcr1 = 0x802a;681commproc->cp_cpmcr2 = 0x8028;682commproc->cp_cpmcr3 = 0x802e;683commproc->cp_cpmcr4 = 0x802c;684commproc->cp_rccr = 1;685686printk("I2C/SPI microcode patch installed.\n");687# endif /* CONFIG_I2C_SPI_UCODE_PATCH */688689# if defined(CONFIG_I2C_SPI_SMC1_UCODE_PATCH)690691dp = (uint *)&(commproc->cp_dpmem[0x0e00]);692for (i=0; i<(sizeof(patch_2e00)/4); i++)693*dp++ = patch_2e00[i];694695commproc->cp_cpmcr1 = 0x8080;696commproc->cp_cpmcr2 = 0x808a;697commproc->cp_cpmcr3 = 0x8028;698commproc->cp_cpmcr4 = 0x802a;699commproc->cp_rccr = 3;700701smp = (smc_uart_t *)&commproc->cp_dparam[PROFF_SMC1];702smp->smc_rpbase = 0x1FC0;703704printk("I2C/SPI/SMC1 microcode patch installed.\n");705# endif /* CONFIG_I2C_SPI_SMC1_UCODE_PATCH) */706707#endif /* some variation of the I2C/SPI patch was selected */708}709710/*711* Take this entire routine out, since no one calls it and its712* logic is suspect.713*/714715#if 0716void717verify_patch(volatile immap_t *immr)718{719volatile uint *dp;720volatile cpm8xx_t *commproc;721int i;722723commproc = (cpm8xx_t *)&immr->im_cpm;724725printk("cp_rccr %x\n", commproc->cp_rccr);726commproc->cp_rccr = 0;727728dp = (uint *)(commproc->cp_dpmem);729for (i=0; i<(sizeof(patch_2000)/4); i++)730if (*dp++ != patch_2000[i]) {731printk("patch_2000 bad at %d\n", i);732dp--;733printk("found 0x%X, wanted 0x%X\n", *dp, patch_2000[i]);734break;735}736737dp = (uint *)&(commproc->cp_dpmem[0x0f00]);738for (i=0; i<(sizeof(patch_2f00)/4); i++)739if (*dp++ != patch_2f00[i]) {740printk("patch_2f00 bad at %d\n", i);741dp--;742printk("found 0x%X, wanted 0x%X\n", *dp, patch_2f00[i]);743break;744}745746commproc->cp_rccr = 0x0009;747}748#endif749750751