misc: Replace Intel-syntax inline assembly with GAS-syntax inline assembly; ensure we can build with clang
This commit is contained in:
parent
87cc5494c7
commit
6e78e33989
|
@ -28,7 +28,6 @@ INTERNAL_CFLAGS = \
|
|||
-fno-pie \
|
||||
-fomit-frame-pointer \
|
||||
-Wno-address-of-packed-member \
|
||||
-masm=intel \
|
||||
-mno-80387 \
|
||||
-mno-mmx \
|
||||
-mno-3dnow \
|
||||
|
|
|
@ -10,12 +10,13 @@ void entry(uint8_t *compressed_stage2, size_t stage2_size, uint8_t boot_drive, i
|
|||
tinf_gzip_uncompress(dest, compressed_stage2, stage2_size);
|
||||
|
||||
asm volatile (
|
||||
"mov esp, 0x7c00\n\t"
|
||||
"xor ebp, ebp\n\t"
|
||||
"push %1\n\t"
|
||||
"push %0\n\t"
|
||||
"push 0\n\t"
|
||||
"jmp 0x8000\n\t"
|
||||
"movl $0x7c00, %%esp\n\t"
|
||||
"xorl %%ebp, %%ebp\n\t"
|
||||
"pushl %1\n\t"
|
||||
"pushl %0\n\t"
|
||||
"pushl $0\n\t"
|
||||
"pushl $0x8000\n\t"
|
||||
"ret\n\t"
|
||||
:
|
||||
: "r" ((uint32_t)boot_drive), "r" (pxe)
|
||||
: "memory"
|
||||
|
|
|
@ -51,7 +51,6 @@ INTERNAL_CFLAGS := \
|
|||
-fno-lto \
|
||||
-fno-pic \
|
||||
-Wno-address-of-packed-member \
|
||||
-masm=intel \
|
||||
-mno-80387 \
|
||||
-mno-mmx \
|
||||
-mno-3dnow \
|
||||
|
|
|
@ -24,15 +24,16 @@ void stage3_common(void);
|
|||
|
||||
#if defined (uefi)
|
||||
__attribute__((naked))
|
||||
EFI_STATUS efi_main(EFI_HANDLE ImageHandle, EFI_SYSTEM_TABLE *SystemTable) {
|
||||
EFI_STATUS efi_main(
|
||||
__attribute__((unused)) EFI_HANDLE ImageHandle,
|
||||
__attribute__((unused)) EFI_SYSTEM_TABLE *SystemTable) {
|
||||
// Invalid return address of 0 to end stacktraces here
|
||||
asm (
|
||||
"push 0\n\t"
|
||||
"push 0\n\t"
|
||||
"xor eax, eax\n\t"
|
||||
"pushq $0\n\t"
|
||||
"pushq $0\n\t"
|
||||
"xorl %eax, %eax\n\t"
|
||||
"jmp uefi_entry\n\t"
|
||||
);
|
||||
(void)ImageHandle; (void)SystemTable;
|
||||
}
|
||||
|
||||
__attribute__((noreturn))
|
||||
|
|
|
@ -49,9 +49,9 @@ void print_stacktrace(size_t *base_ptr) {
|
|||
if (base_ptr == NULL) {
|
||||
asm volatile (
|
||||
#if defined (bios)
|
||||
"mov %0, ebp"
|
||||
"movl %%ebp, %0"
|
||||
#elif defined (uefi)
|
||||
"mov %0, rbp"
|
||||
"movq %%rbp, %0"
|
||||
#endif
|
||||
: "=g"(base_ptr)
|
||||
:: "memory"
|
||||
|
|
|
@ -21,42 +21,46 @@
|
|||
__attribute__((noinline))
|
||||
__attribute__((section(".realmode")))
|
||||
static void spinup(uint8_t drive) {
|
||||
struct idtr real_mode_idt = { 0x3ff, 0x0 };
|
||||
struct idtr real_mode_idt;
|
||||
real_mode_idt.limit = 0x3ff;
|
||||
real_mode_idt.ptr = 0;
|
||||
|
||||
asm volatile (
|
||||
"cli\n\t"
|
||||
"cld\n\t"
|
||||
|
||||
"lidt [eax]\n\t"
|
||||
"lidt (%%eax)\n\t"
|
||||
|
||||
"jmp 0x08:1f\n\t"
|
||||
"pushl $0x08\n\t"
|
||||
"pushl $1f\n\t"
|
||||
"lret\n\t"
|
||||
"1: .code16\n\t"
|
||||
"mov ax, 0x10\n\t"
|
||||
"mov ds, ax\n\t"
|
||||
"mov es, ax\n\t"
|
||||
"mov fs, ax\n\t"
|
||||
"mov gs, ax\n\t"
|
||||
"mov ss, ax\n\t"
|
||||
"mov eax, cr0\n\t"
|
||||
"and al, 0xfe\n\t"
|
||||
"mov cr0, eax\n\t"
|
||||
"mov eax, OFFSET 1f\n\t"
|
||||
"push 0\n\t"
|
||||
"push ax\n\t"
|
||||
"retf\n\t"
|
||||
"movw $0x10, %%ax\n\t"
|
||||
"movw %%ax, %%ds\n\t"
|
||||
"movw %%ax, %%es\n\t"
|
||||
"movw %%ax, %%fs\n\t"
|
||||
"movw %%ax, %%gs\n\t"
|
||||
"movw %%ax, %%ss\n\t"
|
||||
"movl %%cr0, %%eax\n\t"
|
||||
"andb $0xfe, %%al\n\t"
|
||||
"movl %%eax, %%cr0\n\t"
|
||||
"movl $1f, %%eax\n\t"
|
||||
"pushw $0\n\t"
|
||||
"pushw %%ax\n\t"
|
||||
"lret\n\t"
|
||||
"1:\n\t"
|
||||
"mov ax, 0\n\t"
|
||||
"mov ds, ax\n\t"
|
||||
"mov es, ax\n\t"
|
||||
"mov fs, ax\n\t"
|
||||
"mov gs, ax\n\t"
|
||||
"mov ss, ax\n\t"
|
||||
"xorw %%ax, %%ax\n\t"
|
||||
"movw %%ax, %%ds\n\t"
|
||||
"movw %%ax, %%es\n\t"
|
||||
"movw %%ax, %%fs\n\t"
|
||||
"movw %%ax, %%gs\n\t"
|
||||
"movw %%ax, %%ss\n\t"
|
||||
|
||||
"sti\n\t"
|
||||
|
||||
"push 0\n\t"
|
||||
"push 0x7c00\n\t"
|
||||
"retf\n\t"
|
||||
"pushw $0\n\t"
|
||||
"pushw $0x7c00\n\t"
|
||||
"lret\n\t"
|
||||
|
||||
".code32\n\t"
|
||||
:
|
||||
|
|
|
@ -1,38 +1,32 @@
|
|||
#include <sys/gdt.h>
|
||||
|
||||
__attribute__((noreturn)) void linux_spinup(void *entry, void *boot_params) {
|
||||
struct gdt_desc linux_gdt_descs[] = {
|
||||
{0},
|
||||
struct gdt_desc linux_gdt_descs[4];
|
||||
linux_gdt_descs[0] = (struct gdt_desc){0};
|
||||
linux_gdt_descs[1] = (struct gdt_desc){0};
|
||||
|
||||
{0},
|
||||
|
||||
{
|
||||
.limit = 0xffff,
|
||||
.base_low = 0x0000,
|
||||
.base_mid = 0x00,
|
||||
.access = 0b10011010,
|
||||
.granularity = 0b11001111,
|
||||
.base_hi = 0x00
|
||||
},
|
||||
|
||||
{
|
||||
.limit = 0xffff,
|
||||
.base_low = 0x0000,
|
||||
.base_mid = 0x00,
|
||||
.access = 0b10010010,
|
||||
.granularity = 0b11001111,
|
||||
.base_hi = 0x00
|
||||
}
|
||||
linux_gdt_descs[2] = (struct gdt_desc){
|
||||
.limit = 0xffff,
|
||||
.base_low = 0x0000,
|
||||
.base_mid = 0x00,
|
||||
.access = 0b10011010,
|
||||
.granularity = 0b11001111,
|
||||
.base_hi = 0x00
|
||||
};
|
||||
|
||||
struct gdtr linux_gdt = {
|
||||
sizeof(linux_gdt_descs) - 1,
|
||||
(uintptr_t)linux_gdt_descs,
|
||||
#if defined (bios)
|
||||
0
|
||||
#endif
|
||||
linux_gdt_descs[3] = (struct gdt_desc){
|
||||
.limit = 0xffff,
|
||||
.base_low = 0x0000,
|
||||
.base_mid = 0x00,
|
||||
.access = 0b10010010,
|
||||
.granularity = 0b11001111,
|
||||
.base_hi = 0x00
|
||||
};
|
||||
|
||||
struct gdtr linux_gdt;
|
||||
linux_gdt.limit = sizeof(linux_gdt_descs) - 1;
|
||||
linux_gdt.ptr = (uintptr_t)linux_gdt_descs;
|
||||
|
||||
// Load invalid IDT
|
||||
uint64_t invalid_idt[2] = {0, 0};
|
||||
asm volatile (
|
||||
|
@ -45,24 +39,24 @@ __attribute__((noreturn)) void linux_spinup(void *entry, void *boot_params) {
|
|||
asm volatile (
|
||||
"lgdt %0\n\t"
|
||||
|
||||
"push 0x10\n\t"
|
||||
"pushl $0x10\n\t"
|
||||
"call 1f\n\t"
|
||||
"1:\n\t"
|
||||
"add dword ptr [esp], 5\n\t"
|
||||
"retf\n\t"
|
||||
"addl $5, (%%esp)\n\t"
|
||||
"lret\n\t"
|
||||
|
||||
"mov eax, 0x18\n\t"
|
||||
"mov ds, eax\n\t"
|
||||
"mov es, eax\n\t"
|
||||
"mov fs, eax\n\t"
|
||||
"mov gs, eax\n\t"
|
||||
"mov ss, eax\n\t"
|
||||
"movl $0x18, %%eax\n\t"
|
||||
"movl %%eax, %%ds\n\t"
|
||||
"movl %%eax, %%es\n\t"
|
||||
"movl %%eax, %%fs\n\t"
|
||||
"movl %%eax, %%gs\n\t"
|
||||
"movl %%eax, %%ss\n\t"
|
||||
|
||||
"xor ebp, ebp\n\t"
|
||||
"xor edi, edi\n\t"
|
||||
"xor ebx, ebx\n\t"
|
||||
"xorl %%ebp, %%ebp\n\t"
|
||||
"xorl %%edi, %%edi\n\t"
|
||||
"xorl %%ebx, %%ebx\n\t"
|
||||
|
||||
"jmp ecx\n\t"
|
||||
"jmp *(%%ecx)\n\t"
|
||||
:
|
||||
: "m"(linux_gdt), "c"(entry), "S"(boot_params)
|
||||
: "memory"
|
||||
|
|
|
@ -27,78 +27,79 @@ __attribute__((noreturn)) void stivale_spinup_32(
|
|||
if (level5pg) {
|
||||
// Enable CR4.LA57
|
||||
asm volatile (
|
||||
"mov eax, cr4\n\t"
|
||||
"bts eax, 12\n\t"
|
||||
"mov cr4, eax\n\t" ::: "eax", "memory"
|
||||
"movl %%cr4, %%eax\n\t"
|
||||
"btsl $12, %%eax\n\t"
|
||||
"movl %%eax, %%cr4\n\t"
|
||||
::: "eax", "memory"
|
||||
);
|
||||
}
|
||||
|
||||
asm volatile (
|
||||
"cli\n\t"
|
||||
"cld\n\t"
|
||||
"mov cr3, eax\n\t"
|
||||
"mov eax, cr4\n\t"
|
||||
"or eax, 1 << 5\n\t"
|
||||
"mov cr4, eax\n\t"
|
||||
"mov ecx, 0xc0000080\n\t"
|
||||
"movl %%eax, %%cr3\n\t"
|
||||
"movl %%cr4, %%eax\n\t"
|
||||
"btsl $5, %%eax\n\t"
|
||||
"movl %%eax, %%cr4\n\t"
|
||||
"movl $0xc0000080, %%ecx\n\t"
|
||||
"rdmsr\n\t"
|
||||
"or eax, 1 << 8\n\t"
|
||||
"btsl $8, %%eax\n\t"
|
||||
"wrmsr\n\t"
|
||||
"mov eax, cr0\n\t"
|
||||
"or eax, 1 << 31\n\t"
|
||||
"mov cr0, eax\n\t"
|
||||
"movl %%cr0, %%eax\n\t"
|
||||
"btsl $31, %%eax\n\t"
|
||||
"movl %%eax, %%cr0\n\t"
|
||||
"call 1f\n\t"
|
||||
"1: pop eax\n\t"
|
||||
"add eax, 8\n\t"
|
||||
"push 0x28\n\t"
|
||||
"push eax\n\t"
|
||||
"retf\n\t"
|
||||
"1: popl %%eax\n\t"
|
||||
"addl $8, %%eax\n\t"
|
||||
"pushl $0x28\n\t"
|
||||
"pushl %%eax\n\t"
|
||||
"lret\n\t"
|
||||
".code64\n\t"
|
||||
"mov ax, 0x30\n\t"
|
||||
"mov ds, ax\n\t"
|
||||
"mov es, ax\n\t"
|
||||
"mov fs, ax\n\t"
|
||||
"mov gs, ax\n\t"
|
||||
"mov ss, ax\n\t"
|
||||
"movl $0x30, %%eax\n\t"
|
||||
"movl %%eax, %%ds\n\t"
|
||||
"movl %%eax, %%es\n\t"
|
||||
"movl %%eax, %%fs\n\t"
|
||||
"movl %%eax, %%gs\n\t"
|
||||
"movl %%eax, %%ss\n\t"
|
||||
|
||||
// Since we don't really know what is now present in the upper
|
||||
// 32 bits of the 64 bit registers, clear up the upper bits
|
||||
// of the register that points to the 64-bit casted value array.
|
||||
"mov esi, esi\n\t"
|
||||
"movl %%esi, %%esi\n\t"
|
||||
|
||||
// Move in 64-bit values
|
||||
"mov rdi, qword ptr [rsi + 0]\n\t"
|
||||
"mov rbx, qword ptr [rsi + 8]\n\t"
|
||||
"mov rsi, qword ptr [rsi + 16]\n\t"
|
||||
"movq 0x00(%%rsi), %%rdi\n\t"
|
||||
"movq 0x08(%%rsi), %%rbx\n\t"
|
||||
"movq 0x10(%%rsi), %%rsi\n\t"
|
||||
|
||||
// Let's pretend we push a return address
|
||||
"test rsi, rsi\n\t"
|
||||
"testq %%rsi, %%rsi\n\t"
|
||||
"jz 1f\n\t"
|
||||
|
||||
"sub rsi, 8\n\t"
|
||||
"mov qword ptr [rsi], 0\n\t"
|
||||
"subq $8, %%rsi\n\t"
|
||||
"movq $0, (%%rsi)\n\t"
|
||||
|
||||
"1:\n\t"
|
||||
"push 0x30\n\t"
|
||||
"push rsi\n\t"
|
||||
"pushq $0x30\n\t"
|
||||
"pushq %%rsi\n\t"
|
||||
"pushfq\n\t"
|
||||
"push 0x28\n\t"
|
||||
"push rbx\n\t"
|
||||
"pushq $0x28\n\t"
|
||||
"pushq %%rbx\n\t"
|
||||
|
||||
"xor rax, rax\n\t"
|
||||
"xor rbx, rbx\n\t"
|
||||
"xor rcx, rcx\n\t"
|
||||
"xor rdx, rdx\n\t"
|
||||
"xor rsi, rsi\n\t"
|
||||
"xor rbp, rbp\n\t"
|
||||
"xor r8, r8\n\t"
|
||||
"xor r9, r9\n\t"
|
||||
"xor r10, r10\n\t"
|
||||
"xor r11, r11\n\t"
|
||||
"xor r12, r12\n\t"
|
||||
"xor r13, r13\n\t"
|
||||
"xor r14, r14\n\t"
|
||||
"xor r15, r15\n\t"
|
||||
"xorl %%eax, %%eax\n\t"
|
||||
"xorl %%ebx, %%ebx\n\t"
|
||||
"xorl %%ecx, %%ecx\n\t"
|
||||
"xorl %%edx, %%edx\n\t"
|
||||
"xorl %%esi, %%esi\n\t"
|
||||
"xorl %%ebp, %%ebp\n\t"
|
||||
"xorq %%r8, %%r8\n\t"
|
||||
"xorq %%r9, %%r9\n\t"
|
||||
"xorq %%r10, %%r10\n\t"
|
||||
"xorq %%r11, %%r11\n\t"
|
||||
"xorq %%r12, %%r12\n\t"
|
||||
"xorq %%r13, %%r13\n\t"
|
||||
"xorq %%r14, %%r14\n\t"
|
||||
"xorq %%r15, %%r15\n\t"
|
||||
|
||||
"iretq\n\t"
|
||||
".code32\n\t"
|
||||
|
@ -111,21 +112,21 @@ __attribute__((noreturn)) void stivale_spinup_32(
|
|||
"cli\n\t"
|
||||
"cld\n\t"
|
||||
|
||||
"mov esp, esi\n\t"
|
||||
"push edi\n\t"
|
||||
"push 0\n\t"
|
||||
"movl %%esp, %%esi\n\t"
|
||||
"pushl %%edi\n\t"
|
||||
"pushl $0\n\t"
|
||||
|
||||
"pushfd\n\t"
|
||||
"push 0x18\n\t"
|
||||
"push ebx\n\t"
|
||||
"pushfl\n\t"
|
||||
"pushl $0x18\n\t"
|
||||
"pushl %%ebx\n\t"
|
||||
|
||||
"xor eax, eax\n\t"
|
||||
"xor ebx, ebx\n\t"
|
||||
"xor ecx, ecx\n\t"
|
||||
"xor edx, edx\n\t"
|
||||
"xor esi, esi\n\t"
|
||||
"xor edi, edi\n\t"
|
||||
"xor ebp, ebp\n\t"
|
||||
"xorl %%eax, %%eax\n\t"
|
||||
"xorl %%ebx, %%ebx\n\t"
|
||||
"xorl %%ecx, %%ecx\n\t"
|
||||
"xorl %%edx, %%edx\n\t"
|
||||
"xorl %%esi, %%esi\n\t"
|
||||
"xorl %%edi, %%edi\n\t"
|
||||
"xorl %%ebp, %%ebp\n\t"
|
||||
|
||||
"iret\n\t"
|
||||
:
|
||||
|
|
|
@ -27,38 +27,38 @@ static inline bool cpuid(uint32_t leaf, uint32_t subleaf,
|
|||
}
|
||||
|
||||
static inline void outb(uint16_t port, uint8_t value) {
|
||||
asm volatile ("out %1, al" : : "a" (value), "Nd" (port) : "memory");
|
||||
asm volatile ("outb %%al, %1" : : "a" (value), "Nd" (port) : "memory");
|
||||
}
|
||||
|
||||
static inline void outw(uint16_t port, uint16_t value) {
|
||||
asm volatile ("out %1, ax" : : "a" (value), "Nd" (port) : "memory");
|
||||
asm volatile ("outw %%ax, %1" : : "a" (value), "Nd" (port) : "memory");
|
||||
}
|
||||
|
||||
static inline void outd(uint16_t port, uint32_t value) {
|
||||
asm volatile ("out %1, eax" : : "a" (value), "Nd" (port) : "memory");
|
||||
asm volatile ("outl %%eax, %1" : : "a" (value), "Nd" (port) : "memory");
|
||||
}
|
||||
|
||||
static inline uint8_t inb(uint16_t port) {
|
||||
uint8_t value;
|
||||
asm volatile ("in al, %1" : "=a" (value) : "Nd" (port) : "memory");
|
||||
asm volatile ("inb %1, %%al" : "=a" (value) : "Nd" (port) : "memory");
|
||||
return value;
|
||||
}
|
||||
|
||||
static inline uint16_t inw(uint16_t port) {
|
||||
uint16_t value;
|
||||
asm volatile ("in ax, %1" : "=a" (value) : "Nd" (port) : "memory");
|
||||
asm volatile ("inw %1, %%ax" : "=a" (value) : "Nd" (port) : "memory");
|
||||
return value;
|
||||
}
|
||||
|
||||
static inline uint32_t ind(uint16_t port) {
|
||||
uint32_t value;
|
||||
asm volatile ("in eax, %1" : "=a" (value) : "Nd" (port) : "memory");
|
||||
asm volatile ("inl %1, %%eax" : "=a" (value) : "Nd" (port) : "memory");
|
||||
return value;
|
||||
}
|
||||
|
||||
static inline void mmoutb(uintptr_t addr, uint8_t value) {
|
||||
asm volatile (
|
||||
"mov %0, %1"
|
||||
"movb %1, %0"
|
||||
: "=m" (BYTE_PTR(addr))
|
||||
: "ir" (value)
|
||||
: "memory"
|
||||
|
@ -67,7 +67,7 @@ static inline void mmoutb(uintptr_t addr, uint8_t value) {
|
|||
|
||||
static inline void mmoutw(uintptr_t addr, uint16_t value) {
|
||||
asm volatile (
|
||||
"mov %0, %1"
|
||||
"movw %1, %0"
|
||||
: "=m" (WORD_PTR(addr))
|
||||
: "ir" (value)
|
||||
: "memory"
|
||||
|
@ -76,7 +76,7 @@ static inline void mmoutw(uintptr_t addr, uint16_t value) {
|
|||
|
||||
static inline void mmoutd(uintptr_t addr, uint32_t value) {
|
||||
asm volatile (
|
||||
"mov %0, %1"
|
||||
"movl %1, %0"
|
||||
: "=m" (DWORD_PTR(addr))
|
||||
: "ir" (value)
|
||||
: "memory"
|
||||
|
@ -85,7 +85,7 @@ static inline void mmoutd(uintptr_t addr, uint32_t value) {
|
|||
|
||||
static inline void mmoutq(uintptr_t addr, uint64_t value) {
|
||||
asm volatile (
|
||||
"mov %0, %1"
|
||||
"movq %1, %0"
|
||||
: "=m" (QWORD_PTR(addr))
|
||||
: "ir" (value)
|
||||
: "memory"
|
||||
|
@ -95,7 +95,7 @@ static inline void mmoutq(uintptr_t addr, uint64_t value) {
|
|||
static inline uint8_t mminb(uintptr_t addr) {
|
||||
uint8_t ret;
|
||||
asm volatile (
|
||||
"mov %0, %1"
|
||||
"movb %1, %0"
|
||||
: "=r" (ret)
|
||||
: "m" (BYTE_PTR(addr))
|
||||
: "memory"
|
||||
|
@ -106,7 +106,7 @@ static inline uint8_t mminb(uintptr_t addr) {
|
|||
static inline uint16_t mminw(uintptr_t addr) {
|
||||
uint16_t ret;
|
||||
asm volatile (
|
||||
"mov %0, %1"
|
||||
"movw %1, %0"
|
||||
: "=r" (ret)
|
||||
: "m" (WORD_PTR(addr))
|
||||
: "memory"
|
||||
|
@ -117,7 +117,7 @@ static inline uint16_t mminw(uintptr_t addr) {
|
|||
static inline uint32_t mmind(uintptr_t addr) {
|
||||
uint32_t ret;
|
||||
asm volatile (
|
||||
"mov %0, %1"
|
||||
"movl %1, %0"
|
||||
: "=r" (ret)
|
||||
: "m" (DWORD_PTR(addr))
|
||||
: "memory"
|
||||
|
@ -128,7 +128,7 @@ static inline uint32_t mmind(uintptr_t addr) {
|
|||
static inline uint64_t mminq(uintptr_t addr) {
|
||||
uint64_t ret;
|
||||
asm volatile (
|
||||
"mov %0, %1"
|
||||
"movq %1, %0"
|
||||
: "=r" (ret)
|
||||
: "m" (QWORD_PTR(addr))
|
||||
: "memory"
|
||||
|
@ -155,19 +155,19 @@ static inline void wrmsr(uint32_t msr, uint64_t value) {
|
|||
}
|
||||
|
||||
#define write_cr(reg, val) ({ \
|
||||
asm volatile ("mov cr" reg ", %0" :: "r" (val) : "memory"); \
|
||||
asm volatile ("mov %0, %%cr" reg :: "r" (val) : "memory"); \
|
||||
})
|
||||
|
||||
#define read_cr(reg) ({ \
|
||||
size_t cr; \
|
||||
asm volatile ("mov %0, cr" reg : "=r" (cr) :: "memory"); \
|
||||
asm volatile ("mov %%cr" reg ", %0" : "=r" (cr) :: "memory"); \
|
||||
cr; \
|
||||
})
|
||||
|
||||
#define locked_read(var) ({ \
|
||||
typeof(*var) ret = 0; \
|
||||
asm volatile ( \
|
||||
"lock xadd %1, %0;" \
|
||||
"lock xadd %0, %1" \
|
||||
: "+r" (ret) \
|
||||
: "m" (*(var)) \
|
||||
: "memory" \
|
||||
|
@ -178,7 +178,7 @@ static inline void wrmsr(uint32_t msr, uint64_t value) {
|
|||
#define locked_write(var, val) ({ \
|
||||
typeof(*var) ret = val; \
|
||||
asm volatile ( \
|
||||
"lock xchg %1, %0;" \
|
||||
"lock xchg %0, %1" \
|
||||
: "+r" ((ret)) \
|
||||
: "m" (*(var)) \
|
||||
: "memory" \
|
||||
|
|
Loading…
Reference in New Issue