@@ -34,7 +34,8 @@ void arm64_enter_nmi(struct pt_regs *regs);
void arm64_exit_nmi(struct pt_regs *regs);
void do_mem_abort(unsigned long addr, unsigned int esr, struct pt_regs *regs);
void do_undefinstr(struct pt_regs *regs, unsigned long esr);
-void do_bti(struct pt_regs *regs);
+void do_el0_bti(struct pt_regs *regs);
+void do_el1_bti(struct pt_regs *regs, unsigned long esr);
asmlinkage void bad_mode(struct pt_regs *regs, int reason, unsigned int esr);
void do_debug_exception(unsigned long addr_if_watchpoint, unsigned int esr,
struct pt_regs *regs);
@@ -141,6 +141,15 @@ static void noinstr el1_undef(struct pt_regs *regs, unsigned long esr)
exit_to_kernel_mode(regs);
}
+static void noinstr el1_bti(struct pt_regs *regs, unsigned long esr)
+{
+ enter_from_kernel_mode(regs);
+ local_daif_inherit(regs);
+ do_el1_bti(regs, esr);
+ local_daif_mask();
+ exit_to_kernel_mode(regs);
+}
+
static void noinstr el1_inv(struct pt_regs *regs, unsigned long esr)
{
enter_from_kernel_mode(regs);
@@ -212,6 +221,9 @@ asmlinkage void noinstr el1_sync_handler(struct pt_regs *regs)
case ESR_ELx_EC_UNKNOWN:
el1_undef(regs, esr);
break;
+ case ESR_ELx_EC_BTI:
+ el1_bti(regs, esr);
+ break;
case ESR_ELx_EC_BREAKPT_CUR:
case ESR_ELx_EC_SOFTSTP_CUR:
case ESR_ELx_EC_WATCHPT_CUR:
@@ -327,7 +339,7 @@ static void noinstr el0_bti(struct pt_regs *regs)
{
enter_from_user_mode();
local_daif_restore(DAIF_PROCCTX);
- do_bti(regs);
+ do_el0_bti(regs);
}
static void noinstr el0_inv(struct pt_regs *regs, unsigned long esr)
@@ -411,12 +411,16 @@ void do_undefinstr(struct pt_regs *regs, unsigned long esr)
}
NOKPROBE_SYMBOL(do_undefinstr);
-void do_bti(struct pt_regs *regs)
+void do_el0_bti(struct pt_regs *regs)
{
- BUG_ON(!user_mode(regs));
force_signal_inject(SIGILL, ILL_ILLOPC, regs->pc, 0);
}
-NOKPROBE_SYMBOL(do_bti);
+
+void do_el1_bti(struct pt_regs *regs, unsigned long esr)
+{
+ die("Oops - BTI", regs, esr);
+}
+NOKPROBE_SYMBOL(do_el1_bti);
void do_el0_fpac(struct pt_regs *regs, unsigned long esr)
{