]> git.kernelconcepts.de Git - karo-tx-uboot.git/blob - post/cpu/ppc4xx/ocm.c
mxc_ipuv3: fix memory alignment of framebuffer
[karo-tx-uboot.git] / post / cpu / ppc4xx / ocm.c
1 /*
2  * (C) Copyright 2008 Ilya Yanok, EmCraft Systems, yanok@emcraft.com
3  *
4  * Developed for DENX Software Engineering GmbH
5  *
6  * See file CREDITS for list of people who contributed to this
7  * project.
8  *
9  * This program is free software; you can redistribute it and/or
10  * modify it under the terms of the GNU General Public License as
11  * published by the Free Software Foundation; either version 2 of
12  * the License, or (at your option) any later version.
13  *
14  * This program is distributed in the hope that it will be useful,
15  * but WITHOUT ANY WARRANTY; without even the implied warranty of
16  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
17  * GNU General Public License for more details.
18  *
19  * You should have received a copy of the GNU General Public License
20  * along with this program; if not, write to the Free Software
21  * Foundation, Inc., 59 Temple Place, Suite 330, Boston,
22  * MA 02111-1307 USA
23  */
24 #include <common.h>
25
26 /*
27  * This test attempts to verify on-chip memory (OCM). Result is written
28  * to the scratch register and if test succeed it won't be run till next
29  * power on.
30  */
31
32 #include <post.h>
33
34 #include <asm/io.h>
35
36 DECLARE_GLOBAL_DATA_PTR;
37
38 #define OCM_TEST_PATTERN1       0x55555555
39 #define OCM_TEST_PATTERN2       0xAAAAAAAA
40
41 #if CONFIG_POST & CONFIG_SYS_POST_OCM
42
43 static uint ocm_status_read(void)
44 {
45         return in_be32((void *)CONFIG_SYS_OCM_STATUS_ADDR) &
46                 CONFIG_SYS_OCM_STATUS_MASK;
47 }
48
49 static void ocm_status_write(uint value)
50 {
51         out_be32((void *)CONFIG_SYS_OCM_STATUS_ADDR, value |
52                 (in_be32((void *)CONFIG_SYS_OCM_STATUS_ADDR) &
53                         ~CONFIG_SYS_OCM_STATUS_MASK));
54 }
55
56 static inline int ocm_test_word(uint value, uint *address)
57 {
58         uint read_value;
59
60         *address = value;
61         sync();
62         read_value = *address;
63
64         return (read_value != value);
65 }
66
67 int ocm_post_test(int flags)
68 {
69         uint   old_value;
70         int    ret = 0;
71         uint  *address = (uint*)CONFIG_SYS_OCM_BASE;
72
73         if (ocm_status_read() == CONFIG_SYS_OCM_STATUS_OK)
74                 return 0;
75         for (; address < (uint*)(CONFIG_SYS_OCM_BASE + CONFIG_SYS_OCM_SIZE); address++) {
76                 old_value = *address;
77                 if (ocm_test_word(OCM_TEST_PATTERN1, address) ||
78                                 ocm_test_word(OCM_TEST_PATTERN2, address)) {
79                         ret = 1;
80                         *address = old_value;
81                         printf("OCM POST failed at %p!\n", address);
82                         break;
83                 }
84                 *address = old_value;
85         }
86         ocm_status_write(ret ? CONFIG_SYS_OCM_STATUS_FAIL : CONFIG_SYS_OCM_STATUS_OK);
87         return ret;
88 }
89 #endif /* CONFIG_POST & CONFIG_SYS_POST_OCM */