Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Initial support for kernels with IBT #29

Open
wants to merge 2 commits into
base: master
Choose a base branch
from
Open
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
61 changes: 58 additions & 3 deletions module/pteditor.c
Original file line number Diff line number Diff line change
Expand Up @@ -13,6 +13,33 @@
#include <linux/proc_fs.h>
#include <linux/kprobes.h>

#ifdef CONFIG_X86_KERNEL_IBT
__noendbr u64 ibt_save(void)
{
u64 msr = 0;

if (cpu_feature_enabled(X86_FEATURE_IBT)) {
rdmsrl(MSR_IA32_S_CET, msr);
wrmsrl(MSR_IA32_S_CET, msr & ~CET_ENDBR_EN);
}

return msr;
}

__noendbr void ibt_restore(u64 save)
{
u64 msr;

if (cpu_feature_enabled(X86_FEATURE_IBT)) {
rdmsrl(MSR_IA32_S_CET, msr);
msr &= ~CET_ENDBR_EN;
msr |= (save & CET_ENDBR_EN);
wrmsrl(MSR_IA32_S_CET, msr);
}
}

#endif

#if LINUX_VERSION_CODE >= KERNEL_VERSION(5, 8, 0)
#include <linux/mmap_lock.h>
#endif
Expand Down Expand Up @@ -105,7 +132,23 @@ static inline int pmd_large(pmd_t pmd) {
#define KPROBE_KALLSYMS_LOOKUP 1
typedef unsigned long (*kallsyms_lookup_name_t)(const char *name);
kallsyms_lookup_name_t kallsyms_lookup_name_func;

#ifdef CONFIG_X86_KERNEL_IBT
unsigned long kallsyms_lookup_name_func_ibt(const char* name) {
u64 ibt;
unsigned long r;

ibt = ibt_save();
r = kallsyms_lookup_name_func(name);
ibt_restore(ibt);

return r;
}

#define kallsyms_lookup_name kallsyms_lookup_name_func_ibt
#else
#define kallsyms_lookup_name kallsyms_lookup_name_func
#endif

static struct kprobe kp = {
.symbol_name = "kallsyms_lookup_name"
Expand Down Expand Up @@ -214,7 +257,14 @@ void _flush_tlb_page_smp(void* info) {
static void
invalidate_tlb_kernel(unsigned long addr) {
#if defined(__i386__) || defined(__x86_64__)
#ifdef CONFIG_X86_KERNEL_IBT
u64 ibt;
ibt = ibt_save();
#endif
flush_tlb_mm_range_func(get_mm(task_pid_nr(current)), addr, addr + real_page_size, real_page_shift, false);
#ifdef CONFIG_X86_KERNEL_IBT
ibt_restore(ibt);
#endif
#elif defined(__aarch64__)
struct vm_area_struct *vma = find_vma(current->mm, addr);
tlb_page_t tlb_page;
Expand Down Expand Up @@ -679,11 +729,16 @@ static int __init pteditor_init(void) {
#endif

#ifdef KPROBE_KALLSYMS_LOOKUP
register_kprobe(&kp);
kallsyms_lookup_name = (kallsyms_lookup_name_t) kp.addr;
r = register_kprobe(&kp);
if (r != 0) {
pr_alert("Could not register kprobe\n");
return -ENXIO;
}

kallsyms_lookup_name_func = (kallsyms_lookup_name_t) kp.addr;
unregister_kprobe(&kp);

if(!unlikely(kallsyms_lookup_name)) {
if(!unlikely(kallsyms_lookup_name_func)) {
pr_alert("Could not retrieve kallsyms_lookup_name address\n");
return -ENXIO;
}
Expand Down