OSDN Git Service

add riscv64 architecture support
[android-x86/external-musl-libc.git] / src / linux / cache.c
index 84a138a..0eb051c 100644 (file)
@@ -1,4 +1,6 @@
+#include <errno.h>
 #include "syscall.h"
+#include "atomic.h"
 
 #ifdef SYS_cacheflush
 int _flush_cache(void *addr, int len, int op)
@@ -15,3 +17,34 @@ int __cachectl(void *addr, int len, int op)
 }
 weak_alias(__cachectl, cachectl);
 #endif
+
+#ifdef SYS_riscv_flush_icache
+
+#define VDSO_FLUSH_ICACHE_SYM "__vdso_flush_icache"
+#define VDSO_FLUSH_ICACHE_VER "LINUX_4.5"
+
+static void *volatile vdso_func;
+
+static int flush_icache_init(void *start, void *end, unsigned long int flags)
+{
+       void *p = __vdsosym(VDSO_FLUSH_ICACHE_VER, VDSO_FLUSH_ICACHE_SYM);
+       int (*f)(void *, void *, unsigned long int) =
+               (int (*)(void *, void *, unsigned long int))p;
+       a_cas_p(&vdso_func, (void *)flush_icache_init, p);
+       return f ? f(start, end, flags) : -ENOSYS;
+}
+
+static void *volatile vdso_func = (void *)flush_icache_init;
+
+int __riscv_flush_icache(void *start, void *end, unsigned long int flags) 
+{
+       int (*f)(void *, void *, unsigned long int) =
+               (int (*)(void *, void *, unsigned long int))vdso_func;
+       if (f) {
+               int r = f(start, end, flags);
+               if (!r) return r;
+               if (r != -ENOSYS) return __syscall_ret(r);
+       }
+}
+weak_alias(__riscv_flush_icache, riscv_flush_icache);
+#endif