diff options
Diffstat (limited to 'arch/ppc/boot/simple/iic.c')
-rw-r--r-- | arch/ppc/boot/simple/iic.c | 214 |
1 files changed, 0 insertions, 214 deletions
diff --git a/arch/ppc/boot/simple/iic.c b/arch/ppc/boot/simple/iic.c deleted file mode 100644 index 5e91489426b4..000000000000 --- a/arch/ppc/boot/simple/iic.c +++ /dev/null | |||
@@ -1,214 +0,0 @@ | |||
1 | /* Minimal support functions to read configuration from IIC EEPROMS | ||
2 | * on MPC8xx boards. Originally written for RPGC RPX-Lite. | ||
3 | * Dan Malek (dmalek@jlc.net). | ||
4 | */ | ||
5 | #include <linux/types.h> | ||
6 | #include <asm/uaccess.h> | ||
7 | #include <asm/mpc8xx.h> | ||
8 | #include <asm/cpm1.h> | ||
9 | |||
10 | |||
11 | /* IIC functions. | ||
12 | * These are just the basic master read/write operations so we can | ||
13 | * examine serial EEPROM. | ||
14 | */ | ||
15 | void iic_read(uint devaddr, u_char *buf, uint offset, uint count); | ||
16 | |||
17 | static int iic_init_done; | ||
18 | |||
19 | static void | ||
20 | iic_init(void) | ||
21 | { | ||
22 | volatile iic_t *iip; | ||
23 | volatile i2c8xx_t *i2c; | ||
24 | volatile cpm8xx_t *cp; | ||
25 | volatile immap_t *immap; | ||
26 | uint dpaddr; | ||
27 | |||
28 | immap = (immap_t *)IMAP_ADDR; | ||
29 | cp = (cpm8xx_t *)&(immap->im_cpm); | ||
30 | |||
31 | /* Reset the CPM. This is necessary on the 860 processors | ||
32 | * that may have started the SCC1 ethernet without relocating | ||
33 | * the IIC. | ||
34 | * This also stops the Ethernet in case we were loaded by a | ||
35 | * BOOTP rom monitor. | ||
36 | */ | ||
37 | cp->cp_cpcr = (CPM_CR_RST | CPM_CR_FLG); | ||
38 | |||
39 | /* Wait for it. | ||
40 | */ | ||
41 | while (cp->cp_cpcr & (CPM_CR_RST | CPM_CR_FLG)); | ||
42 | |||
43 | /* Remove any microcode patches. We will install our own | ||
44 | * later. | ||
45 | */ | ||
46 | cp->cp_cpmcr1 = 0; | ||
47 | cp->cp_cpmcr2 = 0; | ||
48 | cp->cp_cpmcr3 = 0; | ||
49 | cp->cp_cpmcr4 = 0; | ||
50 | cp->cp_rccr = 0; | ||
51 | |||
52 | iip = (iic_t *)&cp->cp_dparam[PROFF_IIC]; | ||
53 | i2c = (i2c8xx_t *)&(immap->im_i2c); | ||
54 | |||
55 | /* Initialize Port B IIC pins. | ||
56 | */ | ||
57 | cp->cp_pbpar |= 0x00000030; | ||
58 | cp->cp_pbdir |= 0x00000030; | ||
59 | cp->cp_pbodr |= 0x00000030; | ||
60 | |||
61 | /* Initialize the parameter ram. | ||
62 | */ | ||
63 | |||
64 | /* Allocate space for a two transmit and one receive buffer | ||
65 | * descriptor in the DP ram. | ||
66 | * For now, this address seems OK, but it may have to | ||
67 | * change with newer versions of the firmware. | ||
68 | */ | ||
69 | dpaddr = 0x0840; | ||
70 | |||
71 | /* Set up the IIC parameters in the parameter ram. | ||
72 | */ | ||
73 | iip->iic_tbase = dpaddr; | ||
74 | iip->iic_rbase = dpaddr + (2 * sizeof(cbd_t)); | ||
75 | |||
76 | iip->iic_tfcr = SMC_EB; | ||
77 | iip->iic_rfcr = SMC_EB; | ||
78 | |||
79 | /* This should really be done by the reader/writer. | ||
80 | */ | ||
81 | iip->iic_mrblr = 128; | ||
82 | |||
83 | /* Initialize Tx/Rx parameters. | ||
84 | */ | ||
85 | cp->cp_cpcr = mk_cr_cmd(CPM_CR_CH_I2C, CPM_CR_INIT_TRX) | CPM_CR_FLG; | ||
86 | while (cp->cp_cpcr & CPM_CR_FLG); | ||
87 | |||
88 | /* Select an arbitrary address. Just make sure it is unique. | ||
89 | */ | ||
90 | i2c->i2c_i2add = 0x34; | ||
91 | |||
92 | /* Make clock run maximum slow. | ||
93 | */ | ||
94 | i2c->i2c_i2brg = 7; | ||
95 | |||
96 | /* Disable interrupts. | ||
97 | */ | ||
98 | i2c->i2c_i2cmr = 0; | ||
99 | i2c->i2c_i2cer = 0xff; | ||
100 | |||
101 | /* Enable SDMA. | ||
102 | */ | ||
103 | immap->im_siu_conf.sc_sdcr = 1; | ||
104 | |||
105 | iic_init_done = 1; | ||
106 | } | ||
107 | |||
108 | /* Read from IIC. | ||
109 | * Caller provides device address, memory buffer, and byte count. | ||
110 | */ | ||
111 | static u_char iitemp[32]; | ||
112 | |||
113 | void | ||
114 | iic_read(uint devaddr, u_char *buf, uint offset, uint count) | ||
115 | { | ||
116 | volatile iic_t *iip; | ||
117 | volatile i2c8xx_t *i2c; | ||
118 | volatile cbd_t *tbdf, *rbdf; | ||
119 | volatile cpm8xx_t *cp; | ||
120 | volatile immap_t *immap; | ||
121 | u_char *tb; | ||
122 | uint temp; | ||
123 | |||
124 | /* If the interface has not been initialized, do that now. | ||
125 | */ | ||
126 | if (!iic_init_done) | ||
127 | iic_init(); | ||
128 | |||
129 | immap = (immap_t *)IMAP_ADDR; | ||
130 | cp = (cpm8xx_t *)&(immap->im_cpm); | ||
131 | |||
132 | iip = (iic_t *)&cp->cp_dparam[PROFF_IIC]; | ||
133 | i2c = (i2c8xx_t *)&(immap->im_i2c); | ||
134 | |||
135 | tbdf = (cbd_t *)&cp->cp_dpmem[iip->iic_tbase]; | ||
136 | rbdf = (cbd_t *)&cp->cp_dpmem[iip->iic_rbase]; | ||
137 | |||
138 | /* Send a "dummy write" operation. This is a write request with | ||
139 | * only the offset sent, followed by another start condition. | ||
140 | * This will ensure we start reading from the first location | ||
141 | * of the EEPROM. | ||
142 | */ | ||
143 | tb = iitemp; | ||
144 | tb = (u_char *)(((uint)tb + 15) & ~15); | ||
145 | tbdf->cbd_bufaddr = (int)tb; | ||
146 | *tb = devaddr & 0xfe; /* Device address */ | ||
147 | *(tb+1) = offset; /* Offset */ | ||
148 | tbdf->cbd_datlen = 2; /* Length */ | ||
149 | tbdf->cbd_sc = | ||
150 | BD_SC_READY | BD_SC_LAST | BD_SC_WRAP | BD_IIC_START; | ||
151 | |||
152 | i2c->i2c_i2mod = 1; /* Enable */ | ||
153 | i2c->i2c_i2cer = 0xff; | ||
154 | i2c->i2c_i2com = 0x81; /* Start master */ | ||
155 | |||
156 | /* Wait for IIC transfer. | ||
157 | */ | ||
158 | #if 0 | ||
159 | while ((i2c->i2c_i2cer & 3) == 0); | ||
160 | |||
161 | if (tbdf->cbd_sc & BD_SC_READY) | ||
162 | printf("IIC ra complete but tbuf ready\n"); | ||
163 | #else | ||
164 | temp = 10000000; | ||
165 | while ((tbdf->cbd_sc & BD_SC_READY) && (temp != 0)) | ||
166 | temp--; | ||
167 | #if 0 | ||
168 | /* We can't do this...there is no serial port yet! | ||
169 | */ | ||
170 | if (temp == 0) { | ||
171 | printf("Timeout reading EEPROM\n"); | ||
172 | return; | ||
173 | } | ||
174 | #endif | ||
175 | #endif | ||
176 | |||
177 | /* Chip errata, clear enable. | ||
178 | */ | ||
179 | i2c->i2c_i2mod = 0; | ||
180 | |||
181 | /* To read, we need an empty buffer of the proper length. | ||
182 | * All that is used is the first byte for address, the remainder | ||
183 | * is just used for timing (and doesn't really have to exist). | ||
184 | */ | ||
185 | tbdf->cbd_bufaddr = (int)tb; | ||
186 | *tb = devaddr | 1; /* Device address */ | ||
187 | rbdf->cbd_bufaddr = (uint)buf; /* Desination buffer */ | ||
188 | tbdf->cbd_datlen = rbdf->cbd_datlen = count + 1; /* Length */ | ||
189 | tbdf->cbd_sc = BD_SC_READY | BD_SC_LAST | BD_SC_WRAP | BD_IIC_START; | ||
190 | rbdf->cbd_sc = BD_SC_EMPTY | BD_SC_WRAP; | ||
191 | |||
192 | /* Chip bug, set enable here. | ||
193 | */ | ||
194 | i2c->i2c_i2mod = 1; /* Enable */ | ||
195 | i2c->i2c_i2cer = 0xff; | ||
196 | i2c->i2c_i2com = 0x81; /* Start master */ | ||
197 | |||
198 | /* Wait for IIC transfer. | ||
199 | */ | ||
200 | #if 0 | ||
201 | while ((i2c->i2c_i2cer & 1) == 0); | ||
202 | |||
203 | if (rbdf->cbd_sc & BD_SC_EMPTY) | ||
204 | printf("IIC read complete but rbuf empty\n"); | ||
205 | #else | ||
206 | temp = 10000000; | ||
207 | while ((tbdf->cbd_sc & BD_SC_READY) && (temp != 0)) | ||
208 | temp--; | ||
209 | #endif | ||
210 | |||
211 | /* Chip errata, clear enable. | ||
212 | */ | ||
213 | i2c->i2c_i2mod = 0; | ||
214 | } | ||