x86-64: handle stack fault for non-canonical address access

* With the amd64 architecture, the stack fault exception got a new
  meaning: it is raised when an instruction tries to access a
  non-canonical address, and the stack is referenced in the
  instruction (e.g. by its addressing mode).
  So unlike on x86, this is not a fatal exception and shouldn't
  trigger a KDL -- instead, it is to be treated like a general
  protection fault, terminating the team which caused it.

* Fixes #13744
This commit is contained in:
jua 2017-11-02 18:54:12 +01:00
parent c64b6fc967
commit 1769813948
2 changed files with 17 additions and 1 deletions

View File

@ -329,6 +329,15 @@ x86_64_general_protection_fault(iframe* frame)
}
static void
x86_64_stack_fault_exception(iframe* frame)
{
// Non-canonical address accesses which reference the stack cause a stack
// fault exception instead of GPF. However, we can treat it like a GPF.
x86_64_general_protection_fault(frame);
}
// #pragma mark -
@ -381,7 +390,7 @@ x86_descriptors_init(kernel_args* args)
table[9] = x86_fatal_exception; // Coprocessor Segment Overrun
table[10] = x86_fatal_exception; // Invalid TSS Exception (#TS)
table[11] = x86_fatal_exception; // Segment Not Present (#NP)
table[12] = x86_fatal_exception; // Stack Fault Exception (#SS)
table[12] = x86_64_stack_fault_exception; // Stack Fault Exception (#SS)
table[13] = x86_64_general_protection_fault; // General Protection Exception (#GP)
table[14] = x86_page_fault_exception; // Page-Fault Exception (#PF)
table[16] = x86_unexpected_exception; // x87 FPU Floating-Point Error (#MF)

View File

@ -139,6 +139,13 @@ x86_unexpected_exception(iframe* frame)
signalAddress = frame->ip;
break;
case 12: // Stack Fault (#SS)
type = B_STACK_FAULT;
signalNumber = SIGBUS;
signalCode = BUS_ADRERR;
signalAddress = frame->ip;
break;
case 13: // General Protection Exception (#GP)
type = B_GENERAL_PROTECTION_FAULT;
signalNumber = SIGILL;