x86.h (2243B)
1 #ifndef __X86_H__ 2 #define __X86_H__ 3 4 #include <stdint.h> 5 #include <common.h> 6 7 /* useful macros */ 8 #define GET_ESP(esp) asm volatile ("movl %%esp, %0" : "=r"(esp)); 9 #define PUT_ESP(esp) asm volatile ("movl %0, %%esp" :: "r"(esp)); 10 #define GET_EBP(ebp) asm volatile ("movl %%ebp, %0" : "=r"(ebp)); 11 #define PUT_EBP(ebp) asm volatile ("movl %0, %%ebp" :: "r"(ebp)); 12 13 extern void save_flags(uint32_t *state); 14 extern void load_flags(uint32_t state); 15 extern uint32_t fetch_eip(void); 16 extern void do_cpuid(void); 17 18 typedef int spinlock_t; 19 20 static inline void 21 cli(void) 22 { 23 asm volatile ("cli"); 24 } 25 26 static inline void 27 sti(void) 28 { 29 asm volatile ("sti"); 30 } 31 32 static inline bool 33 ints_on(void) 34 { 35 uint32_t state; 36 37 save_flags(&state); 38 return state & (1 << 9); 39 } 40 41 static inline void 42 hlt(void) 43 { 44 asm volatile ("hlt"); 45 } 46 47 static inline void 48 jmp(uint32_t addr) 49 { 50 asm volatile ("call *%0" :: "a"(addr)); 51 } 52 53 static inline void 54 outb(uint16_t port, uint8_t val) 55 { 56 asm volatile ("outb %0, %1" :: "a"(val), "Nd"(port)); 57 } 58 59 static inline void 60 outw(uint16_t port, uint16_t val) 61 { 62 asm volatile ("outw %0, %1" :: "a"(val), "Nd"(port)); 63 } 64 65 static inline void 66 outl(uint16_t port, uint32_t val) 67 { 68 asm volatile ("outl %0, %1" :: "a"(val), "Nd"(port)); 69 } 70 71 static inline uint8_t 72 inb(uint16_t port) 73 { 74 uint8_t ret; 75 76 asm volatile ("inb %1, %0" : "=a"(ret) : "Nd"(port)); 77 return ret; 78 } 79 80 static inline uint16_t 81 inw(uint16_t port) 82 { 83 uint16_t ret; 84 85 asm volatile ("inw %1, %0" : "=a"(ret) : "Nd"(port)); 86 return ret; 87 } 88 89 static inline uint32_t 90 inl(uint16_t port) 91 { 92 uint32_t ret; 93 94 asm volatile ("inl %1, %0" : "=a"(ret) : "Nd"(port)); 95 return ret; 96 } 97 98 static inline uint32_t 99 read_cr3(void) 100 { 101 uint32_t cr3; 102 103 asm volatile ("movl %%cr3, %0" : "=r"(cr3)); 104 return cr3; 105 } 106 107 static inline void 108 initspinlock(spinlock_t *spinlock) 109 { 110 assert(spinlock != NULL); 111 __sync_lock_release(spinlock); 112 } 113 114 static inline void 115 acquire(spinlock_t *spinlock) 116 { 117 assert(spinlock != NULL); 118 while (__sync_lock_test_and_set(spinlock, 1) == 1) 119 ; 120 } 121 122 static inline int 123 try_acquire(spinlock_t *spinlock) 124 { 125 assert(spinlock != NULL); 126 return __sync_lock_test_and_set(spinlock, 1); 127 } 128 129 static inline void 130 release(spinlock_t *spinlock) 131 { 132 assert(spinlock != NULL); 133 __sync_lock_release(spinlock); 134 } 135 136 #endif 137