akaros/kern/arch/x86/fsgsbase.h
<<
>>
Prefs
   1/* Copyright (c) 2016 Google Inc.
   2 * Barret Rhoden <brho@cs.berkeley.edu>
   3 * See LICENSE for details.
   4 *
   5 * Getters and setters for FS Base and GS base. */
   6
   7#pragma once
   8
   9#include <cpu_feat.h>
  10#include <arch/x86.h>
  11
  12static inline uintptr_t read_fsbase(void)
  13{
  14        uintptr_t base;
  15
  16        if (!cpu_has_feat(CPU_FEAT_X86_FSGSBASE))
  17                return read_msr(MSR_FS_BASE);
  18        asm volatile ("rdfsbase %0" : "=r"(base));
  19        return base;
  20}
  21
  22static inline void write_fsbase(uintptr_t base)
  23{
  24        if (!cpu_has_feat(CPU_FEAT_X86_FSGSBASE)) {
  25                write_msr(MSR_FS_BASE, base);
  26                return;
  27        }
  28        asm volatile ("wrfsbase %0" : : "r"(base));
  29}
  30
  31static inline uintptr_t read_gsbase(void)
  32{
  33        uintptr_t base;
  34
  35        if (!cpu_has_feat(CPU_FEAT_X86_FSGSBASE))
  36                return read_msr(MSR_GS_BASE);
  37        asm volatile ("rdgsbase %0" : "=r"(base));
  38        return base;
  39}
  40
  41static inline void write_gsbase(uintptr_t base)
  42{
  43        if (!cpu_has_feat(CPU_FEAT_X86_FSGSBASE)) {
  44                write_msr(MSR_GS_BASE, base);
  45                return;
  46        }
  47        asm volatile ("wrgsbase %0" : : "r"(base));
  48}
  49
  50/* If we have fast FS/GS access, we can use swapgs to quickly access
  51 * kern_gsbase. */
  52static inline uintptr_t read_kern_gsbase(void)
  53{
  54        uintptr_t base;
  55        int8_t irq_state = 0;
  56
  57        if (!cpu_has_feat(CPU_FEAT_X86_FSGSBASE))
  58                return read_msr(MSR_KERNEL_GS_BASE);
  59        disable_irqsave(&irq_state);
  60        swap_gs();
  61        base = read_gsbase();
  62        swap_gs();
  63        enable_irqsave(&irq_state);
  64        return base;
  65}
  66
  67static inline void write_kern_gsbase(uintptr_t base)
  68{
  69        int8_t irq_state = 0;
  70
  71        if (!cpu_has_feat(CPU_FEAT_X86_FSGSBASE)) {
  72                write_msr(MSR_KERNEL_GS_BASE, base);
  73                return;
  74        }
  75        disable_irqsave(&irq_state);
  76        swap_gs();
  77        write_gsbase(base);
  78        swap_gs();
  79        enable_irqsave(&irq_state);
  80}
  81