1a47a12beSStefan Roese /* 2a47a12beSStefan Roese * (C) Copyright 2002 3a47a12beSStefan Roese * Wolfgang Denk, DENX Software Engineering, wd@denx.de. 4a47a12beSStefan Roese * 5a47a12beSStefan Roese * See file CREDITS for list of people who contributed to this 6a47a12beSStefan Roese * project. 7a47a12beSStefan Roese * 8a47a12beSStefan Roese * This program is free software; you can redistribute it and/or 9a47a12beSStefan Roese * modify it under the terms of the GNU General Public License as 10a47a12beSStefan Roese * published by the Free Software Foundation; either version 2 of 11a47a12beSStefan Roese * the License, or (at your option) any later version. 12a47a12beSStefan Roese * 13a47a12beSStefan Roese * This program is distributed in the hope that it will be useful, 14a47a12beSStefan Roese * but WITHOUT ANY WARRANTY; without even the implied warranty of 15a47a12beSStefan Roese * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 16a47a12beSStefan Roese * GNU General Public License for more details. 17a47a12beSStefan Roese * 18a47a12beSStefan Roese * You should have received a copy of the GNU General Public License 19a47a12beSStefan Roese * along with this program; if not, write to the Free Software 20a47a12beSStefan Roese * Foundation, Inc., 59 Temple Place, Suite 330, Boston, 21a47a12beSStefan Roese * MA 02111-1307 USA 22a47a12beSStefan Roese */ 23a47a12beSStefan Roese 24a47a12beSStefan Roese #include <common.h> 25a47a12beSStefan Roese 26a47a12beSStefan Roese /* 27a47a12beSStefan Roese * CPU test 28a47a12beSStefan Roese * Store instructions: stb(x)(u), sth(x)(u), stw(x)(u) 29a47a12beSStefan Roese * 30a47a12beSStefan Roese * All operations are performed on a 16-byte array. The array 31a47a12beSStefan Roese * is 4-byte aligned. The base register points to offset 8. 32a47a12beSStefan Roese * The immediate offset (index register) ranges in [-8 ... +7]. 33a47a12beSStefan Roese * The test cases are composed so that they do not 34a47a12beSStefan Roese * cause alignment exceptions. 35a47a12beSStefan Roese * The test contains a pre-built table describing all test cases. 36a47a12beSStefan Roese * The table entry contains: 37a47a12beSStefan Roese * the instruction opcode, the value of the index register and 38a47a12beSStefan Roese * the value of the source register. After executing the 39a47a12beSStefan Roese * instruction, the test verifies the contents of the array 40a47a12beSStefan Roese * and the value of the base register (it must change for "store 41a47a12beSStefan Roese * with update" instructions). 42a47a12beSStefan Roese */ 43a47a12beSStefan Roese 44a47a12beSStefan Roese #include <post.h> 45a47a12beSStefan Roese #include "cpu_asm.h" 46a47a12beSStefan Roese 47a47a12beSStefan Roese #if CONFIG_POST & CONFIG_SYS_POST_CPU 48a47a12beSStefan Roese 49a47a12beSStefan Roese extern void cpu_post_exec_12w (ulong *code, ulong *op1, ulong op2, ulong op3); 50a47a12beSStefan Roese extern void cpu_post_exec_11w (ulong *code, ulong *op1, ulong op2); 51a47a12beSStefan Roese 52a47a12beSStefan Roese static struct cpu_post_store_s 53a47a12beSStefan Roese { 54a47a12beSStefan Roese ulong cmd; 55a47a12beSStefan Roese uint width; 56a47a12beSStefan Roese int update; 57a47a12beSStefan Roese int index; 58a47a12beSStefan Roese ulong offset; 59a47a12beSStefan Roese ulong value; 60a47a12beSStefan Roese } cpu_post_store_table[] = 61a47a12beSStefan Roese { 62a47a12beSStefan Roese { 63a47a12beSStefan Roese OP_STW, 64a47a12beSStefan Roese 4, 65a47a12beSStefan Roese 0, 66a47a12beSStefan Roese 0, 67a47a12beSStefan Roese -4, 68a47a12beSStefan Roese 0xff00ff00 69a47a12beSStefan Roese }, 70a47a12beSStefan Roese { 71a47a12beSStefan Roese OP_STH, 72a47a12beSStefan Roese 2, 73a47a12beSStefan Roese 0, 74a47a12beSStefan Roese 0, 75a47a12beSStefan Roese -2, 76a47a12beSStefan Roese 0xff00 77a47a12beSStefan Roese }, 78a47a12beSStefan Roese { 79a47a12beSStefan Roese OP_STB, 80a47a12beSStefan Roese 1, 81a47a12beSStefan Roese 0, 82a47a12beSStefan Roese 0, 83a47a12beSStefan Roese -1, 84a47a12beSStefan Roese 0xff 85a47a12beSStefan Roese }, 86a47a12beSStefan Roese { 87a47a12beSStefan Roese OP_STWU, 88a47a12beSStefan Roese 4, 89a47a12beSStefan Roese 1, 90a47a12beSStefan Roese 0, 91a47a12beSStefan Roese -4, 92a47a12beSStefan Roese 0xff00ff00 93a47a12beSStefan Roese }, 94a47a12beSStefan Roese { 95a47a12beSStefan Roese OP_STHU, 96a47a12beSStefan Roese 2, 97a47a12beSStefan Roese 1, 98a47a12beSStefan Roese 0, 99a47a12beSStefan Roese -2, 100a47a12beSStefan Roese 0xff00 101a47a12beSStefan Roese }, 102a47a12beSStefan Roese { 103a47a12beSStefan Roese OP_STBU, 104a47a12beSStefan Roese 1, 105a47a12beSStefan Roese 1, 106a47a12beSStefan Roese 0, 107a47a12beSStefan Roese -1, 108a47a12beSStefan Roese 0xff 109a47a12beSStefan Roese }, 110a47a12beSStefan Roese { 111a47a12beSStefan Roese OP_STWX, 112a47a12beSStefan Roese 4, 113a47a12beSStefan Roese 0, 114a47a12beSStefan Roese 1, 115a47a12beSStefan Roese -4, 116a47a12beSStefan Roese 0xff00ff00 117a47a12beSStefan Roese }, 118a47a12beSStefan Roese { 119a47a12beSStefan Roese OP_STHX, 120a47a12beSStefan Roese 2, 121a47a12beSStefan Roese 0, 122a47a12beSStefan Roese 1, 123a47a12beSStefan Roese -2, 124a47a12beSStefan Roese 0xff00 125a47a12beSStefan Roese }, 126a47a12beSStefan Roese { 127a47a12beSStefan Roese OP_STBX, 128a47a12beSStefan Roese 1, 129a47a12beSStefan Roese 0, 130a47a12beSStefan Roese 1, 131a47a12beSStefan Roese -1, 132a47a12beSStefan Roese 0xff 133a47a12beSStefan Roese }, 134a47a12beSStefan Roese { 135a47a12beSStefan Roese OP_STWUX, 136a47a12beSStefan Roese 4, 137a47a12beSStefan Roese 1, 138a47a12beSStefan Roese 1, 139a47a12beSStefan Roese -4, 140a47a12beSStefan Roese 0xff00ff00 141a47a12beSStefan Roese }, 142a47a12beSStefan Roese { 143a47a12beSStefan Roese OP_STHUX, 144a47a12beSStefan Roese 2, 145a47a12beSStefan Roese 1, 146a47a12beSStefan Roese 1, 147a47a12beSStefan Roese -2, 148a47a12beSStefan Roese 0xff00 149a47a12beSStefan Roese }, 150a47a12beSStefan Roese { 151a47a12beSStefan Roese OP_STBUX, 152a47a12beSStefan Roese 1, 153a47a12beSStefan Roese 1, 154a47a12beSStefan Roese 1, 155a47a12beSStefan Roese -1, 156a47a12beSStefan Roese 0xff 157a47a12beSStefan Roese }, 158a47a12beSStefan Roese }; 159*d2397817SMike Frysinger static unsigned int cpu_post_store_size = ARRAY_SIZE(cpu_post_store_table); 160a47a12beSStefan Roese 161a47a12beSStefan Roese int cpu_post_test_store (void) 162a47a12beSStefan Roese { 163a47a12beSStefan Roese int ret = 0; 164a47a12beSStefan Roese unsigned int i; 165a47a12beSStefan Roese int flag = disable_interrupts(); 166a47a12beSStefan Roese 167a47a12beSStefan Roese for (i = 0; i < cpu_post_store_size && ret == 0; i++) 168a47a12beSStefan Roese { 169a47a12beSStefan Roese struct cpu_post_store_s *test = cpu_post_store_table + i; 170a47a12beSStefan Roese uchar data[16] = 171a47a12beSStefan Roese { 0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15 }; 172a47a12beSStefan Roese ulong base0 = (ulong) (data + 8); 173a47a12beSStefan Roese ulong base = base0; 174a47a12beSStefan Roese 175a47a12beSStefan Roese if (test->index) 176a47a12beSStefan Roese { 177a47a12beSStefan Roese ulong code[] = 178a47a12beSStefan Roese { 179a47a12beSStefan Roese ASM_12(test->cmd, 5, 3, 4), 180a47a12beSStefan Roese ASM_BLR, 181a47a12beSStefan Roese }; 182a47a12beSStefan Roese 183a47a12beSStefan Roese cpu_post_exec_12w (code, &base, test->offset, test->value); 184a47a12beSStefan Roese } 185a47a12beSStefan Roese else 186a47a12beSStefan Roese { 187a47a12beSStefan Roese ulong code[] = 188a47a12beSStefan Roese { 189a47a12beSStefan Roese ASM_11I(test->cmd, 4, 3, test->offset), 190a47a12beSStefan Roese ASM_BLR, 191a47a12beSStefan Roese }; 192a47a12beSStefan Roese 193a47a12beSStefan Roese cpu_post_exec_11w (code, &base, test->value); 194a47a12beSStefan Roese } 195a47a12beSStefan Roese 196a47a12beSStefan Roese if (ret == 0) 197a47a12beSStefan Roese { 198a47a12beSStefan Roese if (test->update) 199a47a12beSStefan Roese ret = base == base0 + test->offset ? 0 : -1; 200a47a12beSStefan Roese else 201a47a12beSStefan Roese ret = base == base0 ? 0 : -1; 202a47a12beSStefan Roese } 203a47a12beSStefan Roese 204a47a12beSStefan Roese if (ret == 0) 205a47a12beSStefan Roese { 206a47a12beSStefan Roese switch (test->width) 207a47a12beSStefan Roese { 208a47a12beSStefan Roese case 1: 209a47a12beSStefan Roese ret = *(uchar *)(base0 + test->offset) == test->value ? 210a47a12beSStefan Roese 0 : -1; 211a47a12beSStefan Roese break; 212a47a12beSStefan Roese case 2: 213a47a12beSStefan Roese ret = *(ushort *)(base0 + test->offset) == test->value ? 214a47a12beSStefan Roese 0 : -1; 215a47a12beSStefan Roese break; 216a47a12beSStefan Roese case 4: 217a47a12beSStefan Roese ret = *(ulong *)(base0 + test->offset) == test->value ? 218a47a12beSStefan Roese 0 : -1; 219a47a12beSStefan Roese break; 220a47a12beSStefan Roese } 221a47a12beSStefan Roese } 222a47a12beSStefan Roese 223a47a12beSStefan Roese if (ret != 0) 224a47a12beSStefan Roese { 225a47a12beSStefan Roese post_log ("Error at store test %d !\n", i); 226a47a12beSStefan Roese } 227a47a12beSStefan Roese } 228a47a12beSStefan Roese 229a47a12beSStefan Roese if (flag) 230a47a12beSStefan Roese enable_interrupts(); 231a47a12beSStefan Roese 232a47a12beSStefan Roese return ret; 233a47a12beSStefan Roese } 234a47a12beSStefan Roese 235a47a12beSStefan Roese #endif 236