aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorMike Frysinger <vapier@gentoo.org>2010-05-04 00:14:08 -0400
committerMike Frysinger <vapier@gentoo.org>2010-05-22 14:19:10 -0400
commitc70dcabc8eba18113a4735e7b1bd09f7493e38f0 (patch)
tree80f2ca9f649b05b2bf0de3027061664db8454748
parent479ba6035862a9c08ce4351c7fff8926fde4ede5 (diff)
Blackfin: isram: clean up ITEST_COMMAND macro and improve the selftests
The IADDR2DTEST() macro had some duplicated logic with bit 11 and some incorrect comments, so scrub all of that. In order to verify these aren't a problem (and won't be in the future), extend the self tests to operate on as much L1 SRAM as possible. Signed-off-by: Mike Frysinger <vapier@gentoo.org>
-rw-r--r--arch/blackfin/mm/isram-driver.c94
1 files changed, 51 insertions, 43 deletions
diff --git a/arch/blackfin/mm/isram-driver.c b/arch/blackfin/mm/isram-driver.c
index 39b058564f62..7e2e674ed444 100644
--- a/arch/blackfin/mm/isram-driver.c
+++ b/arch/blackfin/mm/isram-driver.c
@@ -43,13 +43,12 @@ static DEFINE_SPINLOCK(dtest_lock);
43/* Takes a void pointer */ 43/* Takes a void pointer */
44#define IADDR2DTEST(x) \ 44#define IADDR2DTEST(x) \
45 ({ unsigned long __addr = (unsigned long)(x); \ 45 ({ unsigned long __addr = (unsigned long)(x); \
46 (__addr & 0x47F8) | /* address bits 14 & 10:3 */ \ 46 ((__addr & (1 << 11)) << (26 - 11)) | /* addr bit 11 (Way0/Way1) */ \
47 (__addr & 0x8000) << 23 | /* Bank A/B */ \ 47 (1 << 24) | /* instruction access = 1 */ \
48 (__addr & 0x0800) << 15 | /* address bit 11 */ \ 48 ((__addr & (1 << 15)) << (23 - 15)) | /* addr bit 15 (Data Bank) */ \
49 (__addr & 0x3000) << 4 | /* address bits 13:12 */ \ 49 ((__addr & (3 << 12)) << (16 - 12)) | /* addr bits 13:12 (Subbank) */ \
50 (__addr & 0x8000) << 8 | /* address bit 15 */ \ 50 (__addr & 0x47F8) | /* addr bits 14 & 10:3 */ \
51 (0x1000000) | /* instruction access = 1 */ \ 51 (1 << 2); /* data array = 1 */ \
52 (0x4); /* data array = 1 */ \
53 }) 52 })
54 53
55/* Takes a pointer, and returns the offset (in bits) which things should be shifted */ 54/* Takes a pointer, and returns the offset (in bits) which things should be shifted */
@@ -196,7 +195,7 @@ EXPORT_SYMBOL(isram_memcpy);
196 195
197#ifdef CONFIG_BFIN_ISRAM_SELF_TEST 196#ifdef CONFIG_BFIN_ISRAM_SELF_TEST
198 197
199#define TEST_LEN 0x100 198static int test_len = 0x20000;
200 199
201static __init void hex_dump(unsigned char *buf, int len) 200static __init void hex_dump(unsigned char *buf, int len)
202{ 201{
@@ -212,15 +211,15 @@ static __init int isram_read_test(char *sdram, void *l1inst)
212 pr_info("INFO: running isram_read tests\n"); 211 pr_info("INFO: running isram_read tests\n");
213 212
214 /* setup some different data to play with */ 213 /* setup some different data to play with */
215 for (i = 0; i < TEST_LEN; ++i) 214 for (i = 0; i < test_len; ++i)
216 sdram[i] = i; 215 sdram[i] = i % 255;
217 dma_memcpy(l1inst, sdram, TEST_LEN); 216 dma_memcpy(l1inst, sdram, test_len);
218 217
219 /* make sure we can read the L1 inst */ 218 /* make sure we can read the L1 inst */
220 for (i = 0; i < TEST_LEN; i += sizeof(uint64_t)) { 219 for (i = 0; i < test_len; i += sizeof(uint64_t)) {
221 data1 = isram_read(l1inst + i); 220 data1 = isram_read(l1inst + i);
222 memcpy(&data2, sdram + i, sizeof(data2)); 221 memcpy(&data2, sdram + i, sizeof(data2));
223 if (memcmp(&data1, &data2, sizeof(uint64_t))) { 222 if (data1 != data2) {
224 pr_err("FAIL: isram_read(%p) returned %#llx but wanted %#llx\n", 223 pr_err("FAIL: isram_read(%p) returned %#llx but wanted %#llx\n",
225 l1inst + i, data1, data2); 224 l1inst + i, data1, data2);
226 ++ret; 225 ++ret;
@@ -238,25 +237,25 @@ static __init int isram_write_test(char *sdram, void *l1inst)
238 pr_info("INFO: running isram_write tests\n"); 237 pr_info("INFO: running isram_write tests\n");
239 238
240 /* setup some different data to play with */ 239 /* setup some different data to play with */
241 memset(sdram, 0, TEST_LEN * 2); 240 memset(sdram, 0, test_len * 2);
242 dma_memcpy(l1inst, sdram, TEST_LEN); 241 dma_memcpy(l1inst, sdram, test_len);
243 for (i = 0; i < TEST_LEN; ++i) 242 for (i = 0; i < test_len; ++i)
244 sdram[i] = i; 243 sdram[i] = i % 255;
245 244
246 /* make sure we can write the L1 inst */ 245 /* make sure we can write the L1 inst */
247 for (i = 0; i < TEST_LEN; i += sizeof(uint64_t)) { 246 for (i = 0; i < test_len; i += sizeof(uint64_t)) {
248 memcpy(&data1, sdram + i, sizeof(data1)); 247 memcpy(&data1, sdram + i, sizeof(data1));
249 isram_write(l1inst + i, data1); 248 isram_write(l1inst + i, data1);
250 data2 = isram_read(l1inst + i); 249 data2 = isram_read(l1inst + i);
251 if (memcmp(&data1, &data2, sizeof(uint64_t))) { 250 if (data1 != data2) {
252 pr_err("FAIL: isram_write(%p, %#llx) != %#llx\n", 251 pr_err("FAIL: isram_write(%p, %#llx) != %#llx\n",
253 l1inst + i, data1, data2); 252 l1inst + i, data1, data2);
254 ++ret; 253 ++ret;
255 } 254 }
256 } 255 }
257 256
258 dma_memcpy(sdram + TEST_LEN, l1inst, TEST_LEN); 257 dma_memcpy(sdram + test_len, l1inst, test_len);
259 if (memcmp(sdram, sdram + TEST_LEN, TEST_LEN)) { 258 if (memcmp(sdram, sdram + test_len, test_len)) {
260 pr_err("FAIL: isram_write() did not work properly\n"); 259 pr_err("FAIL: isram_write() did not work properly\n");
261 ++ret; 260 ++ret;
262 } 261 }
@@ -268,12 +267,12 @@ static __init int
268_isram_memcpy_test(char pattern, void *sdram, void *l1inst, const char *smemcpy, 267_isram_memcpy_test(char pattern, void *sdram, void *l1inst, const char *smemcpy,
269 void *(*fmemcpy)(void *, const void *, size_t)) 268 void *(*fmemcpy)(void *, const void *, size_t))
270{ 269{
271 memset(sdram, pattern, TEST_LEN); 270 memset(sdram, pattern, test_len);
272 fmemcpy(l1inst, sdram, TEST_LEN); 271 fmemcpy(l1inst, sdram, test_len);
273 fmemcpy(sdram + TEST_LEN, l1inst, TEST_LEN); 272 fmemcpy(sdram + test_len, l1inst, test_len);
274 if (memcmp(sdram, sdram + TEST_LEN, TEST_LEN)) { 273 if (memcmp(sdram, sdram + test_len, test_len)) {
275 pr_err("FAIL: %s(%p <=> %p, %#x) failed (data is %#x)\n", 274 pr_err("FAIL: %s(%p <=> %p, %#x) failed (data is %#x)\n",
276 smemcpy, l1inst, sdram, TEST_LEN, pattern); 275 smemcpy, l1inst, sdram, test_len, pattern);
277 return 1; 276 return 1;
278 } 277 }
279 return 0; 278 return 0;
@@ -292,12 +291,13 @@ static __init int isram_memcpy_test(char *sdram, void *l1inst)
292 /* check read of small, unaligned, and hardware 64bit limits */ 291 /* check read of small, unaligned, and hardware 64bit limits */
293 pr_info("INFO: running isram_memcpy (read) tests\n"); 292 pr_info("INFO: running isram_memcpy (read) tests\n");
294 293
295 for (i = 0; i < TEST_LEN; ++i) 294 /* setup some different data to play with */
296 sdram[i] = i; 295 for (i = 0; i < test_len; ++i)
297 dma_memcpy(l1inst, sdram, TEST_LEN); 296 sdram[i] = i % 255;
297 dma_memcpy(l1inst, sdram, test_len);
298 298
299 thisret = 0; 299 thisret = 0;
300 for (i = 0; i < TEST_LEN - 32; ++i) { 300 for (i = 0; i < test_len - 32; ++i) {
301 unsigned char cmp[32]; 301 unsigned char cmp[32];
302 for (j = 1; j <= 32; ++j) { 302 for (j = 1; j <= 32; ++j) {
303 memset(cmp, 0, sizeof(cmp)); 303 memset(cmp, 0, sizeof(cmp));
@@ -310,7 +310,7 @@ static __init int isram_memcpy_test(char *sdram, void *l1inst)
310 pr_cont("\n"); 310 pr_cont("\n");
311 if (++thisret > 20) { 311 if (++thisret > 20) {
312 pr_err("FAIL: skipping remaining series\n"); 312 pr_err("FAIL: skipping remaining series\n");
313 i = TEST_LEN; 313 i = test_len;
314 break; 314 break;
315 } 315 }
316 } 316 }
@@ -321,11 +321,11 @@ static __init int isram_memcpy_test(char *sdram, void *l1inst)
321 /* check write of small, unaligned, and hardware 64bit limits */ 321 /* check write of small, unaligned, and hardware 64bit limits */
322 pr_info("INFO: running isram_memcpy (write) tests\n"); 322 pr_info("INFO: running isram_memcpy (write) tests\n");
323 323
324 memset(sdram + TEST_LEN, 0, TEST_LEN); 324 memset(sdram + test_len, 0, test_len);
325 dma_memcpy(l1inst, sdram + TEST_LEN, TEST_LEN); 325 dma_memcpy(l1inst, sdram + test_len, test_len);
326 326
327 thisret = 0; 327 thisret = 0;
328 for (i = 0; i < TEST_LEN - 32; ++i) { 328 for (i = 0; i < test_len - 32; ++i) {
329 unsigned char cmp[32]; 329 unsigned char cmp[32];
330 for (j = 1; j <= 32; ++j) { 330 for (j = 1; j <= 32; ++j) {
331 isram_memcpy(l1inst + i, sdram + i, j); 331 isram_memcpy(l1inst + i, sdram + i, j);
@@ -338,7 +338,7 @@ static __init int isram_memcpy_test(char *sdram, void *l1inst)
338 pr_cont("\n"); 338 pr_cont("\n");
339 if (++thisret > 20) { 339 if (++thisret > 20) {
340 pr_err("FAIL: skipping remaining series\n"); 340 pr_err("FAIL: skipping remaining series\n");
341 i = TEST_LEN; 341 i = test_len;
342 break; 342 break;
343 } 343 }
344 } 344 }
@@ -355,22 +355,30 @@ static __init int isram_test_init(void)
355 char *sdram; 355 char *sdram;
356 void *l1inst; 356 void *l1inst;
357 357
358 sdram = kmalloc(TEST_LEN * 2, GFP_KERNEL); 358 /* Try to test as much of L1SRAM as possible */
359 if (!sdram) { 359 while (test_len) {
360 pr_warning("SKIP: could not allocate sdram\n"); 360 test_len >>= 1;
361 return 0; 361 l1inst = l1_inst_sram_alloc(test_len);
362 if (l1inst)
363 break;
362 } 364 }
363
364 l1inst = l1_inst_sram_alloc(TEST_LEN);
365 if (!l1inst) { 365 if (!l1inst) {
366 kfree(sdram);
367 pr_warning("SKIP: could not allocate L1 inst\n"); 366 pr_warning("SKIP: could not allocate L1 inst\n");
368 return 0; 367 return 0;
369 } 368 }
369 pr_info("INFO: testing %#x bytes (%p - %p)\n",
370 test_len, l1inst, l1inst + test_len);
371
372 sdram = kmalloc(test_len * 2, GFP_KERNEL);
373 if (!sdram) {
374 sram_free(l1inst);
375 pr_warning("SKIP: could not allocate sdram\n");
376 return 0;
377 }
370 378
371 /* sanity check initial L1 inst state */ 379 /* sanity check initial L1 inst state */
372 ret = 1; 380 ret = 1;
373 pr_info("INFO: running initial dma_memcpy checks\n"); 381 pr_info("INFO: running initial dma_memcpy checks %p\n", sdram);
374 if (_isram_memcpy_test(0xa, sdram, l1inst, dma_memcpy)) 382 if (_isram_memcpy_test(0xa, sdram, l1inst, dma_memcpy))
375 goto abort; 383 goto abort;
376 if (_isram_memcpy_test(0x5, sdram, l1inst, dma_memcpy)) 384 if (_isram_memcpy_test(0x5, sdram, l1inst, dma_memcpy))