]> git.kernelconcepts.de Git - karo-tx-uboot.git/blob - arch/powerpc/cpu/mpc8xxx/srio.c
Merge branch 'master' of git://git.denx.de/u-boot-mpc85xx
[karo-tx-uboot.git] / arch / powerpc / cpu / mpc8xxx / srio.c
1 /*
2  * Copyright 2011 Freescale Semiconductor, Inc.
3  *
4  * This program is free software; you can redistribute it and/or modify it
5  * under the terms of the GNU General Public License as published by the Free
6  * Software Foundation; either version 2 of the License, or (at your option)
7  * any later version.
8  *
9  * This program is distributed in the hope that it will be useful,
10  * but WITHOUT ANY WARRANTY; without even the implied warranty of
11  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
12  * GNU General Public License for more details.
13  *
14  * You should have received a copy of the GNU General Public License
15  * along with this program; if not, write to the Free Software
16  * Foundation, Inc., 59 Temple Place, Suite 330, Boston,
17  * MA 02111-1307 USA
18  */
19
20 #include <common.h>
21 #include <config.h>
22 #include <asm/fsl_law.h>
23 #include <asm/fsl_serdes.h>
24 #include <asm/fsl_srio.h>
25
26 #define SRIO_PORT_ACCEPT_ALL 0x10000001
27 #define SRIO_IB_ATMU_AR 0x80f55000
28 #define SRIO_OB_ATMU_AR_MAINT 0x80077000
29 #define SRIO_OB_ATMU_AR_RW 0x80045000
30 #define SRIO_LCSBA1CSR_OFFSET 0x5c
31 #define SRIO_MAINT_WIN_SIZE 0x1000000 /* 16M */
32 #define SRIO_RW_WIN_SIZE 0x100000 /* 1M */
33 #define SRIO_LCSBA1CSR 0x60000000
34
35 #if defined(CONFIG_FSL_CORENET)
36         #define _DEVDISR_SRIO1 FSL_CORENET_DEVDISR_SRIO1
37         #define _DEVDISR_SRIO2 FSL_CORENET_DEVDISR_SRIO2
38         #define _DEVDISR_RMU   FSL_CORENET_DEVDISR_RMU
39         #define CONFIG_SYS_MPC8xxx_GUTS_ADDR CONFIG_SYS_MPC85xx_GUTS_ADDR
40 #elif defined(CONFIG_MPC85xx)
41         #define _DEVDISR_SRIO1 MPC85xx_DEVDISR_SRIO
42         #define _DEVDISR_SRIO2 MPC85xx_DEVDISR_SRIO
43         #define _DEVDISR_RMU   MPC85xx_DEVDISR_RMSG
44         #define CONFIG_SYS_MPC8xxx_GUTS_ADDR CONFIG_SYS_MPC85xx_GUTS_ADDR
45 #elif defined(CONFIG_MPC86xx)
46         #define _DEVDISR_SRIO1 MPC86xx_DEVDISR_SRIO
47         #define _DEVDISR_SRIO2 MPC86xx_DEVDISR_SRIO
48         #define _DEVDISR_RMU   MPC86xx_DEVDISR_RMSG
49         #define CONFIG_SYS_MPC8xxx_GUTS_ADDR \
50                 (&((immap_t *)CONFIG_SYS_IMMR)->im_gur)
51 #else
52 #error "No defines for DEVDISR_SRIO"
53 #endif
54
55 void srio_init(void)
56 {
57         ccsr_gur_t *gur = (void *)CONFIG_SYS_MPC8xxx_GUTS_ADDR;
58         int srio1_used = 0, srio2_used = 0;
59
60         if (is_serdes_configured(SRIO1)) {
61                 set_next_law(CONFIG_SYS_SRIO1_MEM_PHYS,
62                                 law_size_bits(CONFIG_SYS_SRIO1_MEM_SIZE),
63                                 LAW_TRGT_IF_RIO_1);
64                 srio1_used = 1;
65                 printf("SRIO1: enabled\n");
66         } else {
67                 printf("SRIO1: disabled\n");
68         }
69
70 #ifdef CONFIG_SRIO2
71         if (is_serdes_configured(SRIO2)) {
72                 set_next_law(CONFIG_SYS_SRIO2_MEM_PHYS,
73                                 law_size_bits(CONFIG_SYS_SRIO2_MEM_SIZE),
74                                 LAW_TRGT_IF_RIO_2);
75                 srio2_used = 1;
76                 printf("SRIO2: enabled\n");
77         } else {
78                 printf("SRIO2: disabled\n");
79         }
80 #endif
81
82 #ifdef CONFIG_FSL_CORENET
83         /* On FSL_CORENET devices we can disable individual ports */
84         if (!srio1_used)
85                 setbits_be32(&gur->devdisr, FSL_CORENET_DEVDISR_SRIO1);
86         if (!srio2_used)
87                 setbits_be32(&gur->devdisr, FSL_CORENET_DEVDISR_SRIO2);
88 #endif
89
90         /* neither port is used - disable everything */
91         if (!srio1_used && !srio2_used) {
92                 setbits_be32(&gur->devdisr, _DEVDISR_SRIO1);
93                 setbits_be32(&gur->devdisr, _DEVDISR_SRIO2);
94                 setbits_be32(&gur->devdisr, _DEVDISR_RMU);
95         }
96 }
97
98 #ifdef CONFIG_SRIOBOOT_MASTER
99 void srio_boot_master(void)
100 {
101         struct ccsr_rio *srio = (void *)CONFIG_SYS_FSL_SRIO_ADDR;
102
103         /* set port accept-all */
104         out_be32((void *)&srio->impl.port[CONFIG_SRIOBOOT_MASTER_PORT].ptaacr,
105                                 SRIO_PORT_ACCEPT_ALL);
106
107         debug("SRIOBOOT - MASTER: Master port [ %d ] for srio boot.\n",
108                         CONFIG_SRIOBOOT_MASTER_PORT);
109         /* configure inbound window for slave's u-boot image */
110         debug("SRIOBOOT - MASTER: Inbound window for slave's image; "
111                         "Local = 0x%llx, Srio = 0x%llx, Size = 0x%x\n",
112                         (u64)CONFIG_SRIOBOOT_SLAVE_IMAGE_LAW_PHYS1,
113                         (u64)CONFIG_SRIOBOOT_SLAVE_IMAGE_SRIO_PHYS1,
114                         CONFIG_SRIOBOOT_SLAVE_IMAGE_SIZE);
115         out_be32((void *)&srio->atmu
116                         .port[CONFIG_SRIOBOOT_MASTER_PORT].inbw[0].riwtar,
117                         CONFIG_SRIOBOOT_SLAVE_IMAGE_LAW_PHYS1 >> 12);
118         out_be32((void *)&srio->atmu
119                         .port[CONFIG_SRIOBOOT_MASTER_PORT].inbw[0].riwbar,
120                         CONFIG_SRIOBOOT_SLAVE_IMAGE_SRIO_PHYS1 >> 12);
121         out_be32((void *)&srio->atmu
122                         .port[CONFIG_SRIOBOOT_MASTER_PORT].inbw[0].riwar,
123                         SRIO_IB_ATMU_AR
124                         | atmu_size_mask(CONFIG_SRIOBOOT_SLAVE_IMAGE_SIZE));
125
126         /* configure inbound window for slave's u-boot image */
127         debug("SRIOBOOT - MASTER: Inbound window for slave's image; "
128                         "Local = 0x%llx, Srio = 0x%llx, Size = 0x%x\n",
129                         (u64)CONFIG_SRIOBOOT_SLAVE_IMAGE_LAW_PHYS2,
130                         (u64)CONFIG_SRIOBOOT_SLAVE_IMAGE_SRIO_PHYS2,
131                         CONFIG_SRIOBOOT_SLAVE_IMAGE_SIZE);
132         out_be32((void *)&srio->atmu
133                         .port[CONFIG_SRIOBOOT_MASTER_PORT].inbw[1].riwtar,
134                         CONFIG_SRIOBOOT_SLAVE_IMAGE_LAW_PHYS2 >> 12);
135         out_be32((void *)&srio->atmu
136                         .port[CONFIG_SRIOBOOT_MASTER_PORT].inbw[1].riwbar,
137                         CONFIG_SRIOBOOT_SLAVE_IMAGE_SRIO_PHYS2 >> 12);
138         out_be32((void *)&srio->atmu
139                         .port[CONFIG_SRIOBOOT_MASTER_PORT].inbw[1].riwar,
140                         SRIO_IB_ATMU_AR
141                         | atmu_size_mask(CONFIG_SRIOBOOT_SLAVE_IMAGE_SIZE));
142
143         /* configure inbound window for slave's ucode */
144         debug("SRIOBOOT - MASTER: Inbound window for slave's ucode; "
145                         "Local = 0x%llx, Srio = 0x%llx, Size = 0x%x\n",
146                         (u64)CONFIG_SRIOBOOT_SLAVE_UCODE_LAW_PHYS,
147                         (u64)CONFIG_SRIOBOOT_SLAVE_UCODE_SRIO_PHYS,
148                         CONFIG_SRIOBOOT_SLAVE_UCODE_SIZE);
149         out_be32((void *)&srio->atmu
150                         .port[CONFIG_SRIOBOOT_MASTER_PORT].inbw[2].riwtar,
151                         CONFIG_SRIOBOOT_SLAVE_UCODE_LAW_PHYS >> 12);
152         out_be32((void *)&srio->atmu
153                         .port[CONFIG_SRIOBOOT_MASTER_PORT].inbw[2].riwbar,
154                         CONFIG_SRIOBOOT_SLAVE_UCODE_SRIO_PHYS >> 12);
155         out_be32((void *)&srio->atmu
156                         .port[CONFIG_SRIOBOOT_MASTER_PORT].inbw[2].riwar,
157                         SRIO_IB_ATMU_AR
158                         | atmu_size_mask(CONFIG_SRIOBOOT_SLAVE_UCODE_SIZE));
159
160         /* configure inbound window for slave's ENV */
161         debug("SRIOBOOT - MASTER: Inbound window for slave's ENV; "
162                         "Local = 0x%llx, Siro = 0x%llx, Size = 0x%x\n",
163                         CONFIG_SRIOBOOT_SLAVE_ENV_LAW_PHYS,
164                         CONFIG_SRIOBOOT_SLAVE_ENV_SRIO_PHYS,
165                         CONFIG_SRIOBOOT_SLAVE_ENV_SIZE);
166         out_be32((void *)&srio->atmu
167                         .port[CONFIG_SRIOBOOT_MASTER_PORT].inbw[3].riwtar,
168                         CONFIG_SRIOBOOT_SLAVE_ENV_LAW_PHYS >> 12);
169         out_be32((void *)&srio->atmu
170                         .port[CONFIG_SRIOBOOT_MASTER_PORT].inbw[3].riwbar,
171                         CONFIG_SRIOBOOT_SLAVE_ENV_SRIO_PHYS >> 12);
172         out_be32((void *)&srio->atmu
173                         .port[CONFIG_SRIOBOOT_MASTER_PORT].inbw[3].riwar,
174                         SRIO_IB_ATMU_AR
175                         | atmu_size_mask(CONFIG_SRIOBOOT_SLAVE_ENV_SIZE));
176 }
177
178 #ifdef CONFIG_SRIOBOOT_SLAVE_HOLDOFF
179 void srio_boot_master_release_slave(void)
180 {
181         struct ccsr_rio *srio = (void *)CONFIG_SYS_FSL_SRIO_ADDR;
182         u32 escsr;
183         debug("SRIOBOOT - MASTER: "
184                         "Check the port status and release slave core ...\n");
185
186         escsr = in_be32((void *)&srio->lp_serial
187                         .port[CONFIG_SRIOBOOT_MASTER_PORT].pescsr);
188         if (escsr & 0x2) {
189                 if (escsr & 0x10100) {
190                         debug("SRIOBOOT - MASTER: Port [ %d ] is error.\n",
191                                         CONFIG_SRIOBOOT_MASTER_PORT);
192                 } else {
193                         debug("SRIOBOOT - MASTER: "
194                                         "Port [ %d ] is ready, now release slave's core ...\n",
195                                         CONFIG_SRIOBOOT_MASTER_PORT);
196                         /*
197                          * configure outbound window
198                          * with maintenance attribute to set slave's LCSBA1CSR
199                          */
200                         out_be32((void *)&srio->atmu
201                                 .port[CONFIG_SRIOBOOT_MASTER_PORT]
202                                 .outbw[1].rowtar, 0);
203                         out_be32((void *)&srio->atmu
204                                 .port[CONFIG_SRIOBOOT_MASTER_PORT]
205                                 .outbw[1].rowtear, 0);
206                         if (CONFIG_SRIOBOOT_MASTER_PORT)
207                                 out_be32((void *)&srio->atmu
208                                         .port[CONFIG_SRIOBOOT_MASTER_PORT]
209                                         .outbw[1].rowbar,
210                                         CONFIG_SYS_SRIO2_MEM_PHYS >> 12);
211                         else
212                                 out_be32((void *)&srio->atmu
213                                         .port[CONFIG_SRIOBOOT_MASTER_PORT]
214                                         .outbw[1].rowbar,
215                                         CONFIG_SYS_SRIO1_MEM_PHYS >> 12);
216                         out_be32((void *)&srio->atmu
217                                         .port[CONFIG_SRIOBOOT_MASTER_PORT]
218                                         .outbw[1].rowar,
219                                         SRIO_OB_ATMU_AR_MAINT
220                                         | atmu_size_mask(SRIO_MAINT_WIN_SIZE));
221
222                         /*
223                          * configure outbound window
224                          * with R/W attribute to set slave's BRR
225                          */
226                         out_be32((void *)&srio->atmu
227                                 .port[CONFIG_SRIOBOOT_MASTER_PORT]
228                                 .outbw[2].rowtar,
229                                 SRIO_LCSBA1CSR >> 9);
230                         out_be32((void *)&srio->atmu
231                                 .port[CONFIG_SRIOBOOT_MASTER_PORT]
232                                 .outbw[2].rowtear, 0);
233                         if (CONFIG_SRIOBOOT_MASTER_PORT)
234                                 out_be32((void *)&srio->atmu
235                                         .port[CONFIG_SRIOBOOT_MASTER_PORT]
236                                         .outbw[2].rowbar,
237                                         (CONFIG_SYS_SRIO2_MEM_PHYS
238                                         + SRIO_MAINT_WIN_SIZE) >> 12);
239                         else
240                                 out_be32((void *)&srio->atmu
241                                         .port[CONFIG_SRIOBOOT_MASTER_PORT]
242                                         .outbw[2].rowbar,
243                                         (CONFIG_SYS_SRIO1_MEM_PHYS
244                                         + SRIO_MAINT_WIN_SIZE) >> 12);
245                         out_be32((void *)&srio->atmu
246                                 .port[CONFIG_SRIOBOOT_MASTER_PORT]
247                                 .outbw[2].rowar,
248                                 SRIO_OB_ATMU_AR_RW
249                                 | atmu_size_mask(SRIO_RW_WIN_SIZE));
250
251                         /*
252                          * Set the LCSBA1CSR register in slave
253                          * by the maint-outbound window
254                          */
255                         if (CONFIG_SRIOBOOT_MASTER_PORT) {
256                                 out_be32((void *)CONFIG_SYS_SRIO2_MEM_VIRT
257                                         + SRIO_LCSBA1CSR_OFFSET,
258                                         SRIO_LCSBA1CSR);
259                                 while (in_be32((void *)CONFIG_SYS_SRIO2_MEM_VIRT
260                                         + SRIO_LCSBA1CSR_OFFSET)
261                                         != SRIO_LCSBA1CSR)
262                                         ;
263                                 /*
264                                  * And then set the BRR register
265                                  * to release slave core
266                                  */
267                                 out_be32((void *)CONFIG_SYS_SRIO2_MEM_VIRT
268                                         + SRIO_MAINT_WIN_SIZE
269                                         + CONFIG_SRIOBOOT_SLAVE_BRR_OFFSET,
270                                         CONFIG_SRIOBOOT_SLAVE_RELEASE_MASK);
271                         } else {
272                                 out_be32((void *)CONFIG_SYS_SRIO1_MEM_VIRT
273                                         + SRIO_LCSBA1CSR_OFFSET,
274                                         SRIO_LCSBA1CSR);
275                                 while (in_be32((void *)CONFIG_SYS_SRIO1_MEM_VIRT
276                                         + SRIO_LCSBA1CSR_OFFSET)
277                                         != SRIO_LCSBA1CSR)
278                                         ;
279                                 /*
280                                  * And then set the BRR register
281                                  * to release slave core
282                                  */
283                                 out_be32((void *)CONFIG_SYS_SRIO1_MEM_VIRT
284                                         + SRIO_MAINT_WIN_SIZE
285                                         + CONFIG_SRIOBOOT_SLAVE_BRR_OFFSET,
286                                         CONFIG_SRIOBOOT_SLAVE_RELEASE_MASK);
287                         }
288                         debug("SRIOBOOT - MASTER: "
289                                         "Release slave successfully! Now the slave should start up!\n");
290                 }
291         } else
292                 debug("SRIOBOOT - MASTER: Port [ %d ] is not ready.\n",
293                                 CONFIG_SRIOBOOT_MASTER_PORT);
294 }
295 #endif
296 #endif