linux-stable/include/linux/cfi.h
Masami Hiramatsu b65413768a x86/kprobes: Prohibit probing on compiler generated CFI checking code
Prohibit probing on the compiler generated CFI typeid checking code
because it is used for decoding typeid when CFI error happens.

The compiler generates the following instruction sequence for indirect
call checks on x86;

   movl    -<id>, %r10d       ; 6 bytes
   addl    -4(%reg), %r10d    ; 4 bytes
   je      .Ltmp1             ; 2 bytes
   ud2                        ; <- regs->ip

And handle_cfi_failure() decodes these instructions (movl and addl)
for the typeid and the target address. Thus if we put a kprobe on
those instructions, the decode will fail and report a wrong typeid
and target address.

Signed-off-by: Masami Hiramatsu (Google) <mhiramat@kernel.org>
Signed-off-by: Peter Zijlstra (Intel) <peterz@infradead.org>
Link: https://lore.kernel.org/r/168904025785.116016.12766408611437534723.stgit@devnote2
2023-08-02 16:27:07 +02:00

41 lines
1.1 KiB
C

/* SPDX-License-Identifier: GPL-2.0 */
/*
* Clang Control Flow Integrity (CFI) support.
*
* Copyright (C) 2022 Google LLC
*/
#ifndef _LINUX_CFI_H
#define _LINUX_CFI_H
#include <linux/bug.h>
#include <linux/module.h>
#ifdef CONFIG_CFI_CLANG
enum bug_trap_type report_cfi_failure(struct pt_regs *regs, unsigned long addr,
unsigned long *target, u32 type);
static inline enum bug_trap_type report_cfi_failure_noaddr(struct pt_regs *regs,
unsigned long addr)
{
return report_cfi_failure(regs, addr, NULL, 0);
}
#endif /* CONFIG_CFI_CLANG */
#ifdef CONFIG_ARCH_USES_CFI_TRAPS
bool is_cfi_trap(unsigned long addr);
#else
static inline bool is_cfi_trap(unsigned long addr) { return false; }
#endif
#ifdef CONFIG_MODULES
#ifdef CONFIG_ARCH_USES_CFI_TRAPS
void module_cfi_finalize(const Elf_Ehdr *hdr, const Elf_Shdr *sechdrs,
struct module *mod);
#else
static inline void module_cfi_finalize(const Elf_Ehdr *hdr,
const Elf_Shdr *sechdrs,
struct module *mod) {}
#endif /* CONFIG_ARCH_USES_CFI_TRAPS */
#endif /* CONFIG_MODULES */
#endif /* _LINUX_CFI_H */