|
1 | 1 | /* |
2 | | - * Copyright (c) 1997, 2020, Oracle and/or its affiliates. All rights reserved. |
| 2 | + * Copyright (c) 1997, 2022, Oracle and/or its affiliates. All rights reserved. |
3 | 3 | * Copyright (c) 2020, 2022, Huawei Technologies Co., Ltd. All rights reserved. |
4 | 4 | * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. |
5 | 5 | * |
|
29 | 29 |
|
30 | 30 | #define __ _masm-> |
31 | 31 |
|
| 32 | +// SYSCALL_RISCV_FLUSH_ICACHE is used to flush instruction cache. The "fence.i" instruction |
| 33 | +// only work on the current hart, so kernel provides the icache flush syscall to flush icache |
| 34 | +// on each hart. You can pass a flag to determine a global or local icache flush. |
| 35 | +static void icache_flush(long int start, long int end) |
| 36 | +{ |
| 37 | + const int SYSCALL_RISCV_FLUSH_ICACHE = 259; |
| 38 | + register long int __a7 asm ("a7") = SYSCALL_RISCV_FLUSH_ICACHE; |
| 39 | + register long int __a0 asm ("a0") = start; |
| 40 | + register long int __a1 asm ("a1") = end; |
| 41 | + // the flush can be applied to either all threads or only the current. |
| 42 | + // 0 means a global icache flush, and the icache flush will be applied |
| 43 | + // to other harts concurrently executing. |
| 44 | + register long int __a2 asm ("a2") = 0; |
| 45 | + __asm__ volatile ("ecall\n\t" |
| 46 | + : "+r" (__a0) |
| 47 | + : "r" (__a0), "r" (__a1), "r" (__a2), "r" (__a7) |
| 48 | + : "memory"); |
| 49 | +} |
| 50 | + |
32 | 51 | static int icache_flush(address addr, int lines, int magic) { |
33 | | - os::icache_flush((long int) addr, (long int) (addr + (lines << ICache::log2_line_size))); |
| 52 | + icache_flush((long int) addr, (long int) (addr + (lines << ICache::log2_line_size))); |
34 | 53 | return magic; |
35 | 54 | } |
36 | 55 |
|
|
0 commit comments