Formatting/renaming some RISC-V stuff
[akaros.git] / kern / arch / riscv / arch.h
1 #ifndef ROS_INC_ARCH_H
2 #define ROS_INC_ARCH_H
3
4 #include <ros/arch/arch.h>
5 #include <arch/mmu.h>
6 #include <ros/common.h>
7 #include <ros/arch/membar.h>
8 #include <arch/riscv.h>
9 #include <arch/time.h>
10
11 /* Arch Constants */
12 #define ARCH_CL_SIZE 64
13
14 #ifdef __riscv64
15 # define KERN64
16 #endif
17
18 void print_cpuinfo(void);
19 void show_mapping(uintptr_t start, size_t size);
20 void backtrace(void);
21
22 static __inline void breakpoint(void)
23 {
24         asm volatile ("break");
25 }
26
27 static __inline void tlbflush(void)
28 {
29         lcr3(rcr3());
30 }
31
32 static __inline void invlpg(void *addr)
33
34         tlbflush();
35 }
36
37 static __inline void icache_flush_page(void* va, void* kva)
38 {
39         asm volatile ("fence.i");
40 }
41
42 static __inline uint64_t read_tsc(void)
43 {
44         unsigned long t;
45         asm volatile ("rdtime %0" : "=r"(t));
46         return t;
47 }
48
49 /* Continuing the poor tradition of x86 opcode functions... */
50 static __inline uint64_t read_tscp(void)
51 {
52         return read_tsc();
53 }
54
55 static __inline uint64_t read_tsc_serialized(void)
56 {
57         mb();
58         return read_tsc();
59 }
60
61 static __inline uintptr_t enable_fp(void)
62 {
63         return setpcr(PCR_SR, SR_EF);
64 }
65
66 static __inline uintptr_t enable_irq(void)
67 {
68         return setpcr(PCR_SR, SR_ET);
69 }
70
71 static __inline uintptr_t disable_irq(void)
72 {
73         return clearpcr(PCR_SR, SR_ET);
74 }
75
76 static __inline void restore_irq(uintptr_t val)
77 {
78         mtpcr(PCR_SR, val);
79 }
80
81 static __inline int irq_is_enabled(void)
82 {
83         return mfpcr(PCR_SR) & SR_ET;
84 }
85
86 static __inline void enable_irqsave(int8_t* state)
87 {
88         // *state tracks the number of nested enables and disables
89         // initial value of state: 0 = first run / no favorite
90         // > 0 means more enabled calls have been made
91         // < 0 means more disabled calls have been made
92         // Mostly doing this so we can call disable_irqsave first if we want
93
94         // one side or another "gets a point" if interrupts were already the
95         // way it wanted to go.  o/w, state stays at 0.  if the state was not 0
96         // then, enabling/disabling isn't even an option.  just increment/decrement
97
98         // if enabling is winning or tied, make sure it's enabled
99         if ((*state == 0) && !irq_is_enabled())
100                 enable_irq();
101         else
102                 (*state)++;
103 }
104
105 static __inline void disable_irqsave(int8_t* state)
106 {
107         if ((*state == 0) && irq_is_enabled())
108                 disable_irq();
109         else 
110                 (*state)--;
111 }
112
113 static __inline void cpu_relax(void)
114 {
115         for(int i = 0; i < 100; i++)
116                 asm ("nop");
117 }
118
119 static __inline void clflush(uintptr_t* addr)
120 {
121 }
122
123 /* os_coreid -> hw_coreid */
124 static __inline int get_hw_coreid(int coreid)
125 {
126         return coreid;
127 }
128
129 static __inline int hw_core_id(void)
130 {
131         return mfpcr(PCR_COREID);
132 }
133
134 /* hw_coreid -> os_coreid */
135 static __inline int get_os_coreid(int hw_coreid)
136 {
137         return hw_coreid;
138 }
139
140 /* core_id() returns the OS core number, not to be confused with the
141  * hardware-specific core identifier (such as the lapic id) returned by
142  * hw_core_id() */
143 static __inline int core_id(void)
144 {
145         return get_os_coreid(hw_core_id());
146 }
147
148 static __inline void cache_flush(void)
149 {
150 }
151
152 static __inline void reboot(void)
153 {
154         extern void cputchar(int ch);
155         cputchar(0);
156 }
157
158 extern void cpu_halt(void);
159
160 #endif /* !ROS_INC_ARCH_H */