1 /*
2 * Copyright (c) 2020 - 2024 Renesas Electronics Corporation and/or its affiliates
3 *
4 * SPDX-License-Identifier: BSD-3-Clause
5 */
6
7 /***********************************************************************************************************************
8 * Includes <System Includes> , "Project Includes"
9 **********************************************************************************************************************/
10 #include "bsp_api.h"
11
12 /***********************************************************************************************************************
13 * Macro definitions
14 **********************************************************************************************************************/
15 #define BSP_PRV_SCTLR_ELX_BIT_I (0x1000U)
16 #define BSP_PRV_SCTLR_ELX_BIT_C (0x4U)
17 #define BSP_PRV_SCTLR_ELX_BIT_M (0x1U)
18
19 #define BSP_PRV_CLIDR_CTYPE_OFFSET (3U)
20 #define BSP_PRV_CLIDR_CTYPE_MASK (7U)
21 #define BSP_PRV_CLIDR_CTYPE_EXIST_DATACACHE (2U)
22 #define BSP_PRV_CLIDR_LOC_OFFSET (24U)
23 #define BSP_PRV_CLIDR_LOC_MASK (7U)
24
25 #define BSP_PRV_CCSIDR_LINESIZE_OFFSET (0U)
26 #define BSP_PRV_CCSIDR_LINESIZE_MASK (7U)
27 #define BSP_PRV_CCSIDR_LINESIZE_ACTUAL_VALUE (4U)
28 #define BSP_PRV_CCSIDR_ASSOCIATIVITY_OFFSET (3U)
29 #define BSP_PRV_CCSIDR_ASSOCIATIVITY_MASK (0x3FFU)
30 #define BSP_PRV_CCSIDR_NUMSETS_OFFSET (13U)
31 #define BSP_PRV_CCSIDR_NUMSETS_MASK (0x7FFFU)
32 #define BSP_PRV_CCSIDR_SHIFT_MAX (32U)
33
34 #define BSP_PRV_CSSELR_LEVEL_OFFSET (1U)
35
36 #define BSP_PRV_CTR_IMINLINE_OFFSET (0U)
37 #define BSP_PRV_CTR_IMINLINE_MASK (0xFU)
38 #define BSP_PRV_CTR_IMINLINE_NUMBER_OF_WORDS (4U)
39 #define BSP_PRV_CTR_IMINLINE_ADDRESS_MASK (1U)
40 #define BSP_PRV_CTR_DMINLINE_OFFSET (16U)
41 #define BSP_PRV_CTR_DMINLINE_MASK (0xFU)
42 #define BSP_PRV_CTR_DMINLINE_NUMBER_OF_WORDS (4U)
43 #define BSP_PRV_CTR_DMINLINE_ADDRESS_MASK (1U)
44
45 /***********************************************************************************************************************
46 * Typedef definitions
47 **********************************************************************************************************************/
48
49 /***********************************************************************************************************************
50 * Exported global variables (to be accessed by other files)
51 **********************************************************************************************************************/
52
53 /***********************************************************************************************************************
54 * Private global variables and functions
55 **********************************************************************************************************************/
56
57 /*******************************************************************************************************************//**
58 * @addtogroup BSP_MCU
59 * @{
60 **********************************************************************************************************************/
61
62 /*******************************************************************************************************************//**
63 * Enable instruction caching.
64 **********************************************************************************************************************/
R_BSP_CacheEnableInst(void)65 void R_BSP_CacheEnableInst (void)
66 {
67 uintptr_t sctlr;
68
69 sctlr = __get_SCTLR();
70 sctlr |= BSP_PRV_SCTLR_ELX_BIT_I;
71
72 __asm volatile ("DSB SY");
73
74 __set_SCTLR(sctlr);
75
76 __asm volatile ("ISB SY");
77 }
78
79 /*******************************************************************************************************************//**
80 * Enable data caching.
81 **********************************************************************************************************************/
R_BSP_CacheEnableData(void)82 void R_BSP_CacheEnableData (void)
83 {
84 uintptr_t sctlr;
85
86 sctlr = __get_SCTLR();
87 sctlr |= BSP_PRV_SCTLR_ELX_BIT_C;
88
89 __asm volatile ("DSB SY");
90
91 __set_SCTLR(sctlr);
92
93 __asm volatile ("ISB SY");
94 }
95
96 /*******************************************************************************************************************//**
97 * Enable memory protect.
98 **********************************************************************************************************************/
R_BSP_CacheEnableMemoryProtect(void)99 void R_BSP_CacheEnableMemoryProtect (void)
100 {
101 uintptr_t sctlr;
102
103 sctlr = __get_SCTLR();
104 sctlr |= BSP_PRV_SCTLR_ELX_BIT_M;
105
106 __asm volatile ("DSB SY");
107
108 __set_SCTLR(sctlr);
109
110 __asm volatile ("ISB SY");
111 }
112
113 /*******************************************************************************************************************//**
114 * Disable instruction caching.
115 **********************************************************************************************************************/
R_BSP_CacheDisableInst(void)116 void R_BSP_CacheDisableInst (void)
117 {
118 uintptr_t sctlr;
119
120 sctlr = __get_SCTLR();
121 sctlr &= ~(BSP_PRV_SCTLR_ELX_BIT_I);
122
123 __asm volatile ("DSB SY");
124
125 __set_SCTLR(sctlr);
126
127 __asm volatile ("ISB SY");
128 }
129
130 /*******************************************************************************************************************//**
131 * Disable data caching.
132 **********************************************************************************************************************/
R_BSP_CacheDisableData(void)133 void R_BSP_CacheDisableData (void)
134 {
135 uintptr_t sctlr;
136
137 sctlr = __get_SCTLR();
138 sctlr &= ~(BSP_PRV_SCTLR_ELX_BIT_C);
139
140 __asm volatile ("DSB SY");
141
142 __set_SCTLR(sctlr);
143
144 __asm volatile ("ISB SY");
145 }
146
147 /*******************************************************************************************************************//**
148 * Disable memory protect.
149 **********************************************************************************************************************/
R_BSP_CacheDisableMemoryProtect(void)150 void R_BSP_CacheDisableMemoryProtect (void)
151 {
152 uintptr_t sctlr;
153
154 sctlr = __get_SCTLR();
155 sctlr &= ~(BSP_PRV_SCTLR_ELX_BIT_M);
156
157 __asm volatile ("DSB SY");
158
159 __set_SCTLR(sctlr);
160
161 __asm volatile ("ISB SY");
162 }
163
164 /*******************************************************************************************************************//**
165 * Clean data cache by set/way.
166 * Clean means writing the cache data to memory and clear the dirty bits
167 * if there is a discrepancy between the cache and memory data.
168 **********************************************************************************************************************/
R_BSP_CacheCleanAll(void)169 void R_BSP_CacheCleanAll (void)
170 {
171 uintptr_t clidr;
172 uintptr_t clidr_loc;
173 uintptr_t clidr_ctype;
174 uintptr_t clidr_ctype_shift;
175
176 uintptr_t csselr;
177 uintptr_t csselr_level;
178
179 uintptr_t ccsidr;
180 uintptr_t ccsidr_linesize;
181 uintptr_t ccsidr_associativity;
182 uintptr_t ccsidr_associativity_clz;
183 uintptr_t ccsidr_associativity_value;
184 uintptr_t ccsidr_associativity_msb;
185 uintptr_t ccsidr_numsets;
186 uintptr_t ccsidr_numsets_total;
187
188 uintptr_t dccsw;
189
190 __asm volatile ("DSB SY");
191
192 __set_ICIALLU(0);
193
194 __asm volatile ("DMB SY");
195
196 /* Reads the maximum level of cache implemented */
197 clidr = __get_CLIDR();
198 clidr_loc = (clidr >> BSP_PRV_CLIDR_LOC_OFFSET) & BSP_PRV_CLIDR_LOC_MASK;
199
200 /* If the cache does not exist, do not process */
201 if (0 != clidr_loc)
202 {
203 /* Loop until all levels of cache are processed */
204 for (csselr = 0; csselr < clidr_loc; csselr++)
205 {
206 /* Read the current level cache type */
207 clidr_ctype_shift = csselr * BSP_PRV_CLIDR_CTYPE_OFFSET;
208 clidr_ctype = (clidr >> clidr_ctype_shift) & BSP_PRV_CLIDR_CTYPE_MASK;
209
210 /* If no data cache exists in the current level of cache, do not process */
211 if (BSP_PRV_CLIDR_CTYPE_EXIST_DATACACHE <= clidr_ctype)
212 {
213 /* Set the current level to Cache Size Selection Register */
214 csselr_level = csselr << BSP_PRV_CSSELR_LEVEL_OFFSET;
215 __set_CSSELR(csselr_level);
216
217 __asm volatile ("DSB SY");
218
219 /* Read the line size, number of ways, and number of sets for the current level of cache */
220 ccsidr = __get_CCSIDR();
221 ccsidr_linesize = ((ccsidr >> BSP_PRV_CCSIDR_LINESIZE_OFFSET) & BSP_PRV_CCSIDR_LINESIZE_MASK) +
222 BSP_PRV_CCSIDR_LINESIZE_ACTUAL_VALUE;
223 ccsidr_associativity = (ccsidr >> BSP_PRV_CCSIDR_ASSOCIATIVITY_OFFSET) &
224 BSP_PRV_CCSIDR_ASSOCIATIVITY_MASK;
225 ccsidr_numsets = (ccsidr >> BSP_PRV_CCSIDR_NUMSETS_OFFSET) & BSP_PRV_CCSIDR_NUMSETS_MASK;
226
227 /* Count consecutive number of 0 starting from the most significant bit (CLZ = Count Leading Zeros) */
228 ccsidr_associativity_clz = __CLZ((uint32_t) ccsidr_associativity);
229 if (BSP_PRV_CCSIDR_SHIFT_MAX == ccsidr_associativity_clz)
230 {
231 ccsidr_associativity_clz--;
232 }
233 else
234 {
235 /* Do Nothing */
236 }
237
238 /* Loop until all sets are processed */
239 while (1)
240 {
241 /* Working copy of number of ways */
242 ccsidr_associativity_value = ccsidr_associativity;
243
244 /* Loop until all ways are processed */
245 while (1)
246 {
247 ccsidr_associativity_msb = (ccsidr_associativity_value << ccsidr_associativity_clz) |
248 csselr_level; /* Left shift way */
249 ccsidr_numsets_total = ccsidr_numsets << ccsidr_linesize; /* Left shift set */
250 dccsw = ccsidr_associativity_msb | ccsidr_numsets_total; /* Combine set and way */
251
252 /* DCCSW - Data or unified Cache line Clean by Set/Way */
253 __set_DCCSW(dccsw);
254
255 if (0 != ccsidr_associativity_value)
256 {
257 ccsidr_associativity_value--;
258 }
259 else
260 {
261 break;
262 }
263 }
264
265 if (0 != ccsidr_numsets)
266 {
267 ccsidr_numsets--;
268 }
269 else
270 {
271 break;
272 }
273 }
274 }
275 else
276 {
277 /* Do Nothing */
278 }
279 }
280
281 __asm volatile ("DSB SY");
282 __asm volatile ("ISB SY");
283 }
284 else
285 {
286 /* Do Nothing */
287 }
288 }
289
290 /*******************************************************************************************************************//**
291 * Invalidate data cache by set/way.
292 * Also Invalidate instruction cache.
293 *
294 * Invalidate means to delete cache data.
295 **********************************************************************************************************************/
R_BSP_CacheInvalidateAll(void)296 void R_BSP_CacheInvalidateAll (void)
297 {
298 uintptr_t clidr;
299 uintptr_t clidr_loc;
300 uintptr_t clidr_ctype;
301 uintptr_t clidr_ctype_shift;
302
303 uintptr_t csselr;
304 uintptr_t csselr_level;
305
306 uintptr_t ccsidr;
307 uintptr_t ccsidr_linesize;
308 uintptr_t ccsidr_associativity;
309 uintptr_t ccsidr_associativity_clz;
310 uintptr_t ccsidr_associativity_value;
311 uintptr_t ccsidr_associativity_msb;
312 uintptr_t ccsidr_numsets;
313 uintptr_t ccsidr_numsets_total;
314
315 uintptr_t dcisw;
316
317 __asm volatile ("DSB SY");
318
319 __set_ICIALLU(0);
320
321 __asm volatile ("DMB SY");
322
323 /* Reads the maximum level of cache implemented */
324 clidr = __get_CLIDR();
325 clidr_loc = (clidr >> BSP_PRV_CLIDR_LOC_OFFSET) & BSP_PRV_CLIDR_LOC_MASK;
326
327 /* If the cache does not exist, do not process */
328 if (0 != clidr_loc)
329 {
330 /* Loop until all levels of cache are processed */
331 for (csselr = 0; csselr < clidr_loc; csselr++)
332 {
333 /* Read the current level cache type */
334 clidr_ctype_shift = csselr * BSP_PRV_CLIDR_CTYPE_OFFSET;
335 clidr_ctype = (clidr >> clidr_ctype_shift) & BSP_PRV_CLIDR_CTYPE_MASK;
336
337 /* If no data cache exists in the current level of cache, do not process */
338 if (BSP_PRV_CLIDR_CTYPE_EXIST_DATACACHE <= clidr_ctype)
339 {
340 /* Set the current level to Cache Size Selection Register */
341 csselr_level = csselr << BSP_PRV_CSSELR_LEVEL_OFFSET;
342 __set_CSSELR(csselr_level);
343
344 __asm volatile ("DSB SY");
345
346 /* Read the line size, number of ways, and number of sets for the current level of cache */
347 ccsidr = __get_CCSIDR();
348 ccsidr_linesize = ((ccsidr >> BSP_PRV_CCSIDR_LINESIZE_OFFSET) & BSP_PRV_CCSIDR_LINESIZE_MASK) +
349 BSP_PRV_CCSIDR_LINESIZE_ACTUAL_VALUE;
350 ccsidr_associativity = (ccsidr >> BSP_PRV_CCSIDR_ASSOCIATIVITY_OFFSET) &
351 BSP_PRV_CCSIDR_ASSOCIATIVITY_MASK;
352 ccsidr_numsets = (ccsidr >> BSP_PRV_CCSIDR_NUMSETS_OFFSET) & BSP_PRV_CCSIDR_NUMSETS_MASK;
353
354 /* Count consecutive number of 0 starting from the most significant bit (CLZ = Count Leading Zeros) */
355 ccsidr_associativity_clz = __CLZ((uint32_t) ccsidr_associativity);
356 if (BSP_PRV_CCSIDR_SHIFT_MAX == ccsidr_associativity_clz)
357 {
358 ccsidr_associativity_clz--;
359 }
360 else
361 {
362 /* Do Nothing */
363 }
364
365 /* Loop until all sets are processed */
366 while (1)
367 {
368 /* Working copy of number of ways */
369 ccsidr_associativity_value = ccsidr_associativity;
370
371 /* Loop until all ways are processed */
372 while (1)
373 {
374 ccsidr_associativity_msb = (ccsidr_associativity_value << ccsidr_associativity_clz) |
375 csselr_level; /* Left shift way */
376 ccsidr_numsets_total = ccsidr_numsets << ccsidr_linesize; /* Left shift set */
377 dcisw = ccsidr_associativity_msb | ccsidr_numsets_total; /* Combine set and way */
378
379 /* DCISW - Data or unified Cache line Invalidate by Set/Way */
380 __set_DCISW(dcisw);
381
382 if (0 != ccsidr_associativity_value)
383 {
384 ccsidr_associativity_value--;
385 }
386 else
387 {
388 break;
389 }
390 }
391
392 if (0 != ccsidr_numsets)
393 {
394 ccsidr_numsets--;
395 }
396 else
397 {
398 break;
399 }
400 }
401 }
402 else
403 {
404 /* Do Nothing */
405 }
406 }
407
408 __asm volatile ("DSB SY");
409 __asm volatile ("ISB SY");
410 }
411 else
412 {
413 /* Do Nothing */
414 }
415 }
416
417 /*******************************************************************************************************************//**
418 * Clean and Invalidate data cache by set/way.
419 * Also Invalidate instruction cache.
420 *
421 * Clean means writing the cache data to memory and clear the dirty bits
422 * if there is a discrepancy between the cache and memory data.
423 *
424 * Invalidate means to delete cache data.
425 **********************************************************************************************************************/
R_BSP_CacheCleanInvalidateAll(void)426 void R_BSP_CacheCleanInvalidateAll (void)
427 {
428 uintptr_t clidr;
429 uintptr_t clidr_loc;
430 uintptr_t clidr_ctype;
431 uintptr_t clidr_ctype_shift;
432
433 uintptr_t csselr;
434 uintptr_t csselr_level;
435
436 uintptr_t ccsidr;
437 uintptr_t ccsidr_linesize;
438 uintptr_t ccsidr_associativity;
439 uintptr_t ccsidr_associativity_clz;
440 uintptr_t ccsidr_associativity_value;
441 uintptr_t ccsidr_associativity_msb;
442 uintptr_t ccsidr_numsets;
443 uintptr_t ccsidr_numsets_total;
444
445 uintptr_t dccisw;
446
447 __asm volatile ("DSB SY");
448
449 __set_ICIALLU(0);
450
451 __asm volatile ("DMB SY");
452
453 /* Reads the maximum level of cache implemented */
454 clidr = __get_CLIDR();
455 clidr_loc = (clidr >> BSP_PRV_CLIDR_LOC_OFFSET) & BSP_PRV_CLIDR_LOC_MASK;
456
457 /* If the cache does not exist, do not process */
458 if (0 != clidr_loc)
459 {
460 /* Loop until all levels of cache are processed */
461 for (csselr = 0; csselr < clidr_loc; csselr++)
462 {
463 /* Read the current level cache type */
464 clidr_ctype_shift = csselr * BSP_PRV_CLIDR_CTYPE_OFFSET;
465 clidr_ctype = (clidr >> clidr_ctype_shift) & BSP_PRV_CLIDR_CTYPE_MASK;
466
467 /* If no data cache exists in the current level of cache, do not process */
468 if (BSP_PRV_CLIDR_CTYPE_EXIST_DATACACHE <= clidr_ctype)
469 {
470 /* Set the current level to Cache Size Selection Register */
471 csselr_level = csselr << BSP_PRV_CSSELR_LEVEL_OFFSET;
472 __set_CSSELR(csselr_level);
473
474 __asm volatile ("DSB SY");
475
476 /* Read the line size, number of ways, and number of sets for the current level of cache */
477 ccsidr = __get_CCSIDR();
478 ccsidr_linesize = ((ccsidr >> BSP_PRV_CCSIDR_LINESIZE_OFFSET) & BSP_PRV_CCSIDR_LINESIZE_MASK) +
479 BSP_PRV_CCSIDR_LINESIZE_ACTUAL_VALUE;
480 ccsidr_associativity = (ccsidr >> BSP_PRV_CCSIDR_ASSOCIATIVITY_OFFSET) &
481 BSP_PRV_CCSIDR_ASSOCIATIVITY_MASK;
482 ccsidr_numsets = (ccsidr >> BSP_PRV_CCSIDR_NUMSETS_OFFSET) & BSP_PRV_CCSIDR_NUMSETS_MASK;
483
484 /* Count consecutive number of 0 starting from the most significant bit (CLZ = Count Leading Zeros) */
485 ccsidr_associativity_clz = __CLZ((uint32_t) ccsidr_associativity);
486 if (BSP_PRV_CCSIDR_SHIFT_MAX == ccsidr_associativity_clz)
487 {
488 ccsidr_associativity_clz--;
489 }
490 else
491 {
492 /* Do Nothing */
493 }
494
495 /* Loop until all sets are processed */
496 while (1)
497 {
498 /* Working copy of number of ways */
499 ccsidr_associativity_value = ccsidr_associativity;
500
501 /* Loop until all ways are processed */
502 while (1)
503 {
504 ccsidr_associativity_msb = (ccsidr_associativity_value << ccsidr_associativity_clz) |
505 csselr_level; /* Left shift way */
506 ccsidr_numsets_total = ccsidr_numsets << ccsidr_linesize; /* Left shift set */
507 dccisw = ccsidr_associativity_msb | ccsidr_numsets_total; /* Combine set and way */
508
509 /* DCCISW - Data or unified Cache line Clean and Invalidate by Set/Way */
510 __set_DCCISW(dccisw);
511
512 if (0 != ccsidr_associativity_value)
513 {
514 ccsidr_associativity_value--;
515 }
516 else
517 {
518 break;
519 }
520 }
521
522 if (0 != ccsidr_numsets)
523 {
524 ccsidr_numsets--;
525 }
526 else
527 {
528 break;
529 }
530 }
531 }
532 else
533 {
534 /* Do Nothing */
535 }
536 }
537
538 __asm volatile ("DSB SY");
539 __asm volatile ("ISB SY");
540 }
541 else
542 {
543 /* Do Nothing */
544 }
545 }
546
547 /*******************************************************************************************************************//**
548 * Clean data cache and Invalidate instruction cache by address.
549 *
550 * Clean means writing the cache data to memory and clear the dirty bits
551 * if there is a discrepancy between the cache and memory data.
552 *
553 * Invalidate means to delete cache data.
554 *
555 * @param[in] base_address Start address of area you want to Clean.
556 * @param[in] length Size of area you want to Clean.
557 **********************************************************************************************************************/
R_BSP_CacheCleanRange(uintptr_t base_address,uintptr_t length)558 void R_BSP_CacheCleanRange (uintptr_t base_address, uintptr_t length)
559 {
560 uintptr_t end_address;
561 uintptr_t ctr;
562
563 uintptr_t dminline;
564 uintptr_t dminline_size;
565 uintptr_t dccvac;
566
567 uintptr_t iminline;
568 uintptr_t iminline_size;
569 uintptr_t icivau;
570
571 end_address = base_address + length;
572
573 /* Calculate data cache line size */
574 ctr = __get_CTR();
575 dminline = (ctr >> BSP_PRV_CTR_DMINLINE_OFFSET) & BSP_PRV_CTR_DMINLINE_MASK;
576 dminline_size = (BSP_PRV_CTR_DMINLINE_NUMBER_OF_WORDS << dminline);
577
578 /* Align base address with cache line */
579 dccvac = base_address & ~(dminline_size - BSP_PRV_CTR_DMINLINE_ADDRESS_MASK);
580 do
581 {
582 /* Data or unified Cache line Clean by VA to PoC */
583 __set_DCCVAC(dccvac);
584
585 dccvac += dminline_size; /* Next data line */
586 } while (end_address > dccvac);
587
588 __asm volatile ("DSB SY");
589
590 /* Calculate instruction cache line size */
591 iminline = (ctr >> BSP_PRV_CTR_IMINLINE_OFFSET) & BSP_PRV_CTR_IMINLINE_MASK;
592 iminline_size = (BSP_PRV_CTR_IMINLINE_NUMBER_OF_WORDS << iminline);
593
594 /* Align base address with cache line */
595 icivau = base_address & ~(iminline_size - BSP_PRV_CTR_IMINLINE_ADDRESS_MASK);
596 do
597 {
598 /* Instruction Cache line Invalidate by VA to PoU */
599 __set_ICIVAU(icivau);
600
601 icivau += iminline_size; /* Next data line */
602 } while (end_address == icivau);
603
604 __asm volatile ("DSB SY");
605 __asm volatile ("ISB SY");
606 }
607
608 /*******************************************************************************************************************//**
609 * Invalidate instruction and data cache by address.
610 *
611 * Invalidate means to delete cache data.
612 *
613 * @param[in] base_address Start address of area you want to Invalidate.
614 * @param[in] length Size of area you want to Invalidate.
615 **********************************************************************************************************************/
R_BSP_CacheInvalidateRange(uintptr_t base_address,uintptr_t length)616 void R_BSP_CacheInvalidateRange (uintptr_t base_address, uintptr_t length)
617 {
618 uintptr_t end_address;
619 uintptr_t ctr;
620
621 uintptr_t dminline;
622 uintptr_t dminline_size;
623 uintptr_t dcivac;
624
625 uintptr_t iminline;
626 uintptr_t iminline_size;
627 uintptr_t icivau;
628
629 end_address = base_address + length;
630
631 /* Calculate data cache line size */
632 ctr = __get_CTR();
633 dminline = (ctr >> BSP_PRV_CTR_DMINLINE_OFFSET) & BSP_PRV_CTR_DMINLINE_MASK;
634 dminline_size = (BSP_PRV_CTR_DMINLINE_NUMBER_OF_WORDS << dminline);
635
636 /* Align base address with cache line */
637 dcivac = base_address & ~(dminline_size - BSP_PRV_CTR_DMINLINE_ADDRESS_MASK);
638 do
639 {
640 /* Data or unified Cache line Invalidate by VA to PoC */
641 __set_DCIVAC(dcivac);
642
643 dcivac += dminline_size; /* Next data line */
644 } while (end_address > dcivac);
645
646 __asm volatile ("DSB SY");
647
648 /* Calculate instruction cache line size */
649 iminline = (ctr >> BSP_PRV_CTR_IMINLINE_OFFSET) & BSP_PRV_CTR_IMINLINE_MASK;
650 iminline_size = (BSP_PRV_CTR_IMINLINE_NUMBER_OF_WORDS << iminline);
651
652 /* Align base address with cache line */
653 icivau = base_address & ~(iminline_size - BSP_PRV_CTR_IMINLINE_ADDRESS_MASK);
654 do
655 {
656 /* Instruction Cache line Invalidate by VA to PoU */
657 __set_ICIVAU(icivau);
658
659 icivau += iminline_size; /* Next data line */
660 } while (end_address == icivau);
661
662 __asm volatile ("DSB SY");
663 __asm volatile ("ISB SY");
664 }
665
666 /*******************************************************************************************************************//**
667 * Clean and Invalidate data cache and Invalidate instruction cache by address.
668 *
669 * Clean means writing the cache data to memory and clear the dirty bits
670 * if there is a discrepancy between the cache and memory data.
671 *
672 * Invalidate means to delete cache data.
673 *
674 * @param[in] base_address Start address of area you want to Clean and Invalidate.
675 * @param[in] length Size of area you want to Clean and Invalidate.
676 **********************************************************************************************************************/
R_BSP_CacheCleanInvalidateRange(uintptr_t base_address,uintptr_t length)677 void R_BSP_CacheCleanInvalidateRange (uintptr_t base_address, uintptr_t length)
678 {
679 uintptr_t end_address;
680 uintptr_t ctr;
681
682 uintptr_t dminline;
683 uintptr_t dminline_size;
684 uintptr_t dccivac;
685
686 uintptr_t iminline;
687 uintptr_t iminline_size;
688 uintptr_t icivau;
689
690 end_address = base_address + length;
691
692 /* Calculate data cache line size */
693 ctr = __get_CTR();
694 dminline = (ctr >> BSP_PRV_CTR_DMINLINE_OFFSET) & BSP_PRV_CTR_DMINLINE_MASK;
695 dminline_size = (BSP_PRV_CTR_DMINLINE_NUMBER_OF_WORDS << dminline);
696
697 /* Align base address with cache line */
698 dccivac = base_address & ~(dminline_size - BSP_PRV_CTR_DMINLINE_ADDRESS_MASK);
699 do
700 {
701 /* Data or unified Cache line Clean and Invalidate by VA to PoC */
702 __set_DCCIVAC(dccivac);
703
704 dccivac += dminline_size; /* Next data line */
705 } while (end_address > dccivac);
706
707 __asm volatile ("DSB SY");
708
709 /* Calculate instruction cache line size */
710 iminline = (ctr >> BSP_PRV_CTR_IMINLINE_OFFSET) & BSP_PRV_CTR_IMINLINE_MASK;
711 iminline_size = (BSP_PRV_CTR_IMINLINE_NUMBER_OF_WORDS << iminline);
712
713 /* Align base address with cache line */
714 icivau = base_address & ~(iminline_size - BSP_PRV_CTR_IMINLINE_ADDRESS_MASK);
715 do
716 {
717 /* Instruction Cache line Invalidate by VA to PoU */
718 __set_ICIVAU(icivau);
719
720 icivau += iminline_size; /* Next data line */
721 } while (end_address == icivau);
722
723 __asm volatile ("DSB SY");
724 __asm volatile ("ISB SY");
725 }
726
727 /*******************************************************************************************************************//**
728 * Powers on and off the L3 cache way.
729 * CA55 only.
730 **********************************************************************************************************************/
R_BSP_CacheL3PowerCtrl(void)731 void R_BSP_CacheL3PowerCtrl (void)
732 {
733 r_bsp_cache_l3_power_ctrl();
734 }
735
736 /*******************************************************************************************************************//**
737 * @} (end addtogroup BSP_MCU)
738 **********************************************************************************************************************/
739