OpenCores
URL https://opencores.org/ocsvn/openrisc/openrisc/trunk

Subversion Repositories openrisc

[/] [openrisc/] [trunk/] [rtos/] [ecos-2.0/] [packages/] [kernel/] [v2_0/] [tests/] [kcache1.c] - Blame information for rev 587

Go to most recent revision | Details | Compare with Previous | View Log

Line No. Rev Author Line
1 27 unneback
/*=================================================================
2
//
3
//        kcache1.c
4
//
5
//        Cache timing test
6
//
7
//==========================================================================
8
//####ECOSGPLCOPYRIGHTBEGIN####
9
// -------------------------------------------
10
// This file is part of eCos, the Embedded Configurable Operating System.
11
// Copyright (C) 1998, 1999, 2000, 2001, 2002 Red Hat, Inc.
12
//
13
// eCos is free software; you can redistribute it and/or modify it under
14
// the terms of the GNU General Public License as published by the Free
15
// Software Foundation; either version 2 or (at your option) any later version.
16
//
17
// eCos is distributed in the hope that it will be useful, but WITHOUT ANY
18
// WARRANTY; without even the implied warranty of MERCHANTABILITY or
19
// FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
20
// for more details.
21
//
22
// You should have received a copy of the GNU General Public License along
23
// with eCos; if not, write to the Free Software Foundation, Inc.,
24
// 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA.
25
//
26
// As a special exception, if other files instantiate templates or use macros
27
// or inline functions from this file, or you compile this file and link it
28
// with other works to produce a work based on this file, this file does not
29
// by itself cause the resulting work to be covered by the GNU General Public
30
// License. However the source code for this file must still be made available
31
// in accordance with section (3) of the GNU General Public License.
32
//
33
// This exception does not invalidate any other reasons why a work based on
34
// this file might be covered by the GNU General Public License.
35
//
36
// Alternative licenses for eCos may be arranged by contacting Red Hat, Inc.
37
// at http://sources.redhat.com/ecos/ecos-license/
38
// -------------------------------------------
39
//####ECOSGPLCOPYRIGHTEND####
40
//==========================================================================
41
//#####DESCRIPTIONBEGIN####
42
//
43
// Author(s):     dsm
44
// Contributors:  dsm, nickg
45
// Date:          1998-06-18
46
//####DESCRIPTIONEND####
47
*/
48
 
49
#include <cyg/hal/hal_arch.h>           // CYGNUM_HAL_STACK_SIZE_TYPICAL
50
 
51
#include <cyg/kernel/kapi.h>
52
 
53
#include <cyg/infra/testcase.h>
54
 
55
#include <cyg/hal/hal_cache.h>
56
 
57
#if defined(HAL_DCACHE_SIZE) || defined(HAL_UCACHE_SIZE)
58
#ifdef CYGVAR_KERNEL_COUNTERS_CLOCK
59
#ifdef CYGFUN_KERNEL_API_C
60
 
61
#include <cyg/infra/diag.h>
62
#include <cyg/hal/hal_intr.h>
63
 
64
// -------------------------------------------------------------------------
65
// If the HAL does not supply this, we supply our own version
66
 
67
#ifndef HAL_DCACHE_PURGE_ALL
68
# ifdef HAL_DCACHE_SYNC
69
 
70
#define HAL_DCACHE_PURGE_ALL() HAL_DCACHE_SYNC()
71
 
72
# else
73
 
74
static cyg_uint8 dca[HAL_DCACHE_SIZE + HAL_DCACHE_LINE_SIZE*2];
75
 
76
#define HAL_DCACHE_PURGE_ALL()                                          \
77
CYG_MACRO_START                                                         \
78
    volatile cyg_uint8 *addr = &dca[HAL_DCACHE_LINE_SIZE];              \
79
    volatile cyg_uint8 tmp = 0;                                         \
80
    int i;                                                              \
81
    for( i = 0; i < HAL_DCACHE_SIZE; i += HAL_DCACHE_LINE_SIZE )        \
82
    {                                                                   \
83
        tmp = addr[i];                                                  \
84
    }                                                                   \
85
CYG_MACRO_END
86
 
87
# endif
88
#endif
89
 
90
// -------------------------------------------------------------------------
91
 
92
#define NTHREADS 1
93
#define STACKSIZE CYGNUM_HAL_STACK_SIZE_TYPICAL
94
 
95
static cyg_handle_t thread[NTHREADS];
96
 
97
static cyg_thread thread_obj[NTHREADS];
98
static char stack[NTHREADS][STACKSIZE];
99
 
100
#ifndef MAX_STRIDE
101
#define MAX_STRIDE 64
102
#endif
103
 
104
volatile char m[(HAL_DCACHE_SIZE/HAL_DCACHE_LINE_SIZE)*MAX_STRIDE];
105
 
106
// -------------------------------------------------------------------------
107
 
108
static void time0(register cyg_uint32 stride)
109
{
110
    register cyg_uint32 j,k;
111
    cyg_tick_count_t count0, count1;
112
    cyg_ucount32 t;
113
    register char c;
114
 
115
    count0 = cyg_current_time();
116
 
117
    k = 0;
118
    if ( cyg_test_is_simulator )
119
        k = 3960;
120
 
121
    for(; k<4000;k++) {
122
        for(j=0; j<(HAL_DCACHE_SIZE/HAL_DCACHE_LINE_SIZE); j++) {
123
            c=m[stride*j];
124
        }
125
    }
126
 
127
    count1 = cyg_current_time();
128
    t = count1 - count0;
129
    diag_printf("stride=%d, time=%d\n", stride, t);
130
}
131
 
132
// -------------------------------------------------------------------------
133
 
134
void time1(void)
135
{
136
    cyg_uint32 i;
137
 
138
    for(i=1; i<=MAX_STRIDE; i+=i) {
139
        time0(i);
140
    }
141
}
142
 
143
// -------------------------------------------------------------------------
144
// With an ICache invalidate in the middle:
145
#ifdef HAL_ICACHE_INVALIDATE_ALL
146
static void time0II(register cyg_uint32 stride)
147
{
148
    register cyg_uint32 j,k;
149
    cyg_tick_count_t count0, count1;
150
    cyg_ucount32 t;
151
    register char c;
152
 
153
    count0 = cyg_current_time();
154
 
155
    k = 0;
156
    if ( cyg_test_is_simulator )
157
        k = 3960;
158
 
159
    for(; k<4000;k++) {
160
        for(j=0; j<(HAL_DCACHE_SIZE/HAL_DCACHE_LINE_SIZE); j++) {
161
            HAL_ICACHE_INVALIDATE_ALL();
162
            c=m[stride*j];
163
        }
164
    }
165
 
166
    count1 = cyg_current_time();
167
    t = count1 - count0;
168
    diag_printf("stride=%d, time=%d\n", stride, t);
169
}
170
 
171
// -------------------------------------------------------------------------
172
 
173
void time1II(void)
174
{
175
    cyg_uint32 i;
176
 
177
    for(i=1; i<=MAX_STRIDE; i+=i) {
178
        time0II(i);
179
    }
180
}
181
#endif
182
// -------------------------------------------------------------------------
183
// With a DCache invalidate in the middle:
184
// This is guaranteed to produce bogus timing results since interrupts
185
// have to be disabled to prevent accidental loss of state.
186
#ifdef HAL_DCACHE_INVALIDATE_ALL
187
static void time0DI(register cyg_uint32 stride)
188
{
189
    register cyg_uint32 j,k;
190
    volatile cyg_tick_count_t count0;
191
    cyg_tick_count_t count1;
192
    cyg_ucount32 t;
193
    register char c;
194
    register CYG_INTERRUPT_STATE oldints;
195
 
196
    count0 = cyg_current_time();
197
 
198
    HAL_DISABLE_INTERRUPTS(oldints);
199
    HAL_DCACHE_SYNC();
200
 
201
    k = 0;
202
    if ( cyg_test_is_simulator )
203
        k = 3960;
204
 
205
    for(; k<4000;k++) {
206
        for(j=0; j<(HAL_DCACHE_SIZE/HAL_DCACHE_LINE_SIZE); j++) {
207
            HAL_DCACHE_INVALIDATE_ALL();
208
            c=m[stride*j];
209
        }
210
    }
211
    HAL_RESTORE_INTERRUPTS(oldints);
212
 
213
    count1 = cyg_current_time();
214
    t = count1 - count0;
215
    diag_printf("stride=%d, time=%d\n", stride, t);
216
}
217
 
218
// -------------------------------------------------------------------------
219
 
220
void time1DI(void)
221
{
222
    cyg_uint32 i;
223
 
224
    for(i=1; i<=MAX_STRIDE; i+=i) {
225
        time0DI(i);
226
    }
227
}
228
#endif
229
// -------------------------------------------------------------------------
230
// This test could be improved by counting number of passes possible 
231
// in a given number of ticks.
232
 
233
static void entry0( cyg_addrword_t data )
234
{
235
    register CYG_INTERRUPT_STATE oldints;
236
 
237
#ifdef HAL_CACHE_UNIFIED
238
 
239
    HAL_DISABLE_INTERRUPTS(oldints);
240
    HAL_DCACHE_PURGE_ALL();             // rely on above definition
241
    HAL_UCACHE_INVALIDATE_ALL();
242
    HAL_UCACHE_DISABLE();
243
    HAL_RESTORE_INTERRUPTS(oldints);
244
    CYG_TEST_INFO("Cache off");
245
    time1();
246
 
247
    HAL_DISABLE_INTERRUPTS(oldints);
248
    HAL_DCACHE_PURGE_ALL();             // rely on above definition
249
    HAL_UCACHE_INVALIDATE_ALL();
250
    HAL_UCACHE_ENABLE();
251
    HAL_RESTORE_INTERRUPTS(oldints);
252
    CYG_TEST_INFO("Cache on");
253
    time1();
254
 
255
#ifdef HAL_DCACHE_INVALIDATE_ALL
256
    HAL_DISABLE_INTERRUPTS(oldints);
257
    HAL_DCACHE_PURGE_ALL();
258
    HAL_UCACHE_INVALIDATE_ALL();
259
    HAL_UCACHE_ENABLE();
260
    HAL_RESTORE_INTERRUPTS(oldints);
261
    CYG_TEST_INFO("Cache on: invalidate Cache (expect bogus timing)");
262
    time1DI();
263
#endif
264
 
265
#else // HAL_CACHE_UNIFIED
266
 
267
    HAL_DISABLE_INTERRUPTS(oldints);
268
    HAL_DCACHE_PURGE_ALL();
269
    HAL_ICACHE_INVALIDATE_ALL();
270
    HAL_DCACHE_INVALIDATE_ALL();
271
    HAL_ICACHE_DISABLE();
272
    HAL_DCACHE_DISABLE();
273
    HAL_RESTORE_INTERRUPTS(oldints);
274
    CYG_TEST_INFO("Dcache off Icache off");
275
    time1();
276
 
277
    HAL_DISABLE_INTERRUPTS(oldints);
278
    HAL_DCACHE_PURGE_ALL();
279
    HAL_ICACHE_INVALIDATE_ALL();
280
    HAL_DCACHE_INVALIDATE_ALL();
281
    HAL_ICACHE_DISABLE();
282
    HAL_DCACHE_ENABLE();
283
    HAL_RESTORE_INTERRUPTS(oldints);
284
    CYG_TEST_INFO("Dcache on  Icache off");
285
    time1();
286
 
287
    HAL_DISABLE_INTERRUPTS(oldints);
288
    HAL_DCACHE_PURGE_ALL();
289
    HAL_ICACHE_INVALIDATE_ALL();
290
    HAL_DCACHE_INVALIDATE_ALL();
291
    HAL_ICACHE_ENABLE();
292
    HAL_DCACHE_DISABLE();
293
    HAL_RESTORE_INTERRUPTS(oldints);
294
    CYG_TEST_INFO("Dcache off Icache on");
295
    time1();
296
 
297
    HAL_DISABLE_INTERRUPTS(oldints);
298
    HAL_DCACHE_PURGE_ALL();
299
    HAL_ICACHE_INVALIDATE_ALL();
300
    HAL_DCACHE_INVALIDATE_ALL();
301
    HAL_ICACHE_ENABLE();
302
    HAL_DCACHE_ENABLE();
303
    HAL_RESTORE_INTERRUPTS(oldints);
304
    CYG_TEST_INFO("Dcache on Icache on");
305
    time1();
306
 
307
 
308
    HAL_DISABLE_INTERRUPTS(oldints);
309
    HAL_DCACHE_PURGE_ALL();
310
    HAL_ICACHE_INVALIDATE_ALL();
311
    HAL_DCACHE_INVALIDATE_ALL();
312
    HAL_ICACHE_DISABLE();
313
    HAL_DCACHE_DISABLE();
314
    HAL_RESTORE_INTERRUPTS(oldints);
315
    CYG_TEST_INFO("Dcache off Icache off (again)");
316
    time1();
317
 
318
#if defined(HAL_DCACHE_INVALIDATE_ALL) || defined(HAL_ICACHE_INVALIDATE_ALL)
319
    HAL_DISABLE_INTERRUPTS(oldints);
320
    HAL_DCACHE_PURGE_ALL();
321
    HAL_ICACHE_INVALIDATE_ALL();
322
    HAL_DCACHE_INVALIDATE_ALL();
323
    HAL_ICACHE_ENABLE();
324
    HAL_DCACHE_ENABLE();
325
    HAL_RESTORE_INTERRUPTS(oldints);
326
    CYG_TEST_INFO("Dcache on Icache on (again)");
327
    time1();
328
 
329
#if defined(CYGPKG_HAL_MIPS)
330
    // In some architectures, the time taken for the next two tests is
331
    // very long, partly because HAL_XCACHE_INVALIDATE_ALL() is implemented
332
    // with a loop over the cache. Hence these tests take longer than the
333
    // testing infrastructure is prepared to wait. The simplest way to get
334
    // these tests to run quickly is to make them think they are running
335
    // under a simulator.
336
    // If the target actually is a simulator, skip the below - it's very
337
    // slow on the simulator, even with reduced loop counts.
338
    if (cyg_test_is_simulator)
339
        CYG_TEST_PASS_FINISH("End of test");
340
 
341
#if defined(CYGPKG_HAL_MIPS_TX49)
342
    // The TX49 has a large cache, and even with reduced loop count,
343
    // 90+ seconds elapses between each INFO output.
344
    CYG_TEST_PASS_FINISH("End of test");
345
#endif
346
 
347
    cyg_test_is_simulator = 1;
348
#endif    
349
 
350
#ifdef HAL_ICACHE_INVALIDATE_ALL
351
    HAL_DISABLE_INTERRUPTS(oldints);
352
    HAL_DCACHE_PURGE_ALL();
353
    HAL_ICACHE_INVALIDATE_ALL();
354
    HAL_DCACHE_INVALIDATE_ALL();
355
    HAL_ICACHE_ENABLE();
356
    HAL_DCACHE_ENABLE();
357
    HAL_RESTORE_INTERRUPTS(oldints);
358
    CYG_TEST_INFO("Dcache on Icache on: invalidate ICache each time");
359
    time1II();
360
#endif
361
#ifdef HAL_DCACHE_INVALIDATE_ALL
362
    HAL_DISABLE_INTERRUPTS(oldints);
363
    HAL_DCACHE_PURGE_ALL();
364
    HAL_ICACHE_INVALIDATE_ALL();
365
    HAL_DCACHE_INVALIDATE_ALL();
366
    HAL_ICACHE_ENABLE();
367
    HAL_DCACHE_ENABLE();
368
    HAL_RESTORE_INTERRUPTS(oldints);
369
    CYG_TEST_INFO("Dcache on Icache on: invalidate DCache (expect bogus times)");
370
    time1DI();
371
#endif
372
#endif // either INVALIDATE_ALL macro
373
 
374
#endif // HAL_CACHE_UNIFIED
375
 
376
    CYG_TEST_PASS_FINISH("End of test");
377
}
378
 
379
// -------------------------------------------------------------------------
380
 
381
void kcache2_main( void )
382
{
383
    CYG_TEST_INIT();
384
 
385
    cyg_thread_create(4, entry0 , (cyg_addrword_t)0, "kcache1",
386
        (void *)stack[0], STACKSIZE, &thread[0], &thread_obj[0]);
387
    cyg_thread_resume(thread[0]);
388
 
389
    cyg_scheduler_start();
390
}
391
 
392
// -------------------------------------------------------------------------
393
 
394
externC void
395
cyg_start( void )
396
{
397
    kcache2_main();
398
}
399
 
400
// -------------------------------------------------------------------------
401
 
402
#else // def CYGFUN_KERNEL_API_C
403
#define N_A_MSG "Kernel C API layer disabled"
404
#endif // def CYGFUN_KERNEL_API_C
405
#else // def CYGVAR_KERNEL_COUNTERS_CLOCK
406
#define N_A_MSG "Kernel real-time clock disabled"
407
#endif // def CYGVAR_KERNEL_COUNTERS_CLOCK
408
#else // def HAL_DCACHE_SIZE
409
#define N_A_MSG "No caches defined"
410
#endif // def HAL_DCACHE_SIZE
411
 
412
#ifdef N_A_MSG
413
externC void
414
cyg_start( void )
415
{
416
    CYG_TEST_INIT();
417
    CYG_TEST_NA( N_A_MSG );
418
}
419
#endif // N_A_MSG
420
 
421
// -------------------------------------------------------------------------
422
/* EOF kcache1.c */

powered by: WebSVN 2.1.0

© copyright 1999-2024 OpenCores.org, equivalent to Oliscience, all rights reserved. OpenCores®, registered trademark.