src/os/windows/vm/os_windows.cpp

Print this page
rev 4810 : 8016697: PPC64 (part 5): Use stubs to implement safefetch
Summary: Implement Safefetch as stub routines. This reduces compiler and os dependencies.
Reviewed-by: twisti, kvn


2300 //-----------------------------------------------------------------------------
2301 LONG WINAPI topLevelExceptionFilter(struct _EXCEPTION_POINTERS* exceptionInfo) {
2302   if (InterceptOSException) return EXCEPTION_CONTINUE_SEARCH;
2303   DWORD exception_code = exceptionInfo->ExceptionRecord->ExceptionCode;
2304 #ifdef _M_IA64
2305   // On Itanium, we need the "precise pc", which has the slot number coded
2306   // into the least 4 bits: 0000=slot0, 0100=slot1, 1000=slot2 (Windows format).
2307   address pc = (address) exceptionInfo->ExceptionRecord->ExceptionAddress;
2308   // Convert the pc to "Unix format", which has the slot number coded
2309   // into the least 2 bits: 0000=slot0, 0001=slot1, 0010=slot2
2310   // This is needed for IA64 because "relocation" / "implicit null check" / "poll instruction"
2311   // information is saved in the Unix format.
2312   address pc_unix_format = (address) ((((uint64_t)pc) & 0xFFFFFFFFFFFFFFF0) | ((((uint64_t)pc) & 0xF) >> 2));
2313 #elif _M_AMD64
2314   address pc = (address) exceptionInfo->ContextRecord->Rip;
2315 #else
2316   address pc = (address) exceptionInfo->ContextRecord->Eip;
2317 #endif
2318   Thread* t = ThreadLocalStorage::get_thread_slow();          // slow & steady
2319 





2320 #ifndef _WIN64
2321   // Execution protection violation - win32 running on AMD64 only
2322   // Handled first to avoid misdiagnosis as a "normal" access violation;
2323   // This is safe to do because we have a new/unique ExceptionInformation
2324   // code for this condition.
2325   if (exception_code == EXCEPTION_ACCESS_VIOLATION) {
2326     PEXCEPTION_RECORD exceptionRecord = exceptionInfo->ExceptionRecord;
2327     int exception_subcode = (int) exceptionRecord->ExceptionInformation[0];
2328     address addr = (address) exceptionRecord->ExceptionInformation[1];
2329 
2330     if (exception_subcode == EXCEPTION_INFO_EXEC_VIOLATION) {
2331       int page_size = os::vm_page_size();
2332 
2333       // Make sure the pc and the faulting address are sane.
2334       //
2335       // If an instruction spans a page boundary, and the page containing
2336       // the beginning of the instruction is executable but the following
2337       // page is not, the pc and the faulting address might be slightly
2338       // different - we still want to unguard the 2nd page in this case.
2339       //




2300 //-----------------------------------------------------------------------------
2301 LONG WINAPI topLevelExceptionFilter(struct _EXCEPTION_POINTERS* exceptionInfo) {
2302   if (InterceptOSException) return EXCEPTION_CONTINUE_SEARCH;
2303   DWORD exception_code = exceptionInfo->ExceptionRecord->ExceptionCode;
2304 #ifdef _M_IA64
2305   // On Itanium, we need the "precise pc", which has the slot number coded
2306   // into the least 4 bits: 0000=slot0, 0100=slot1, 1000=slot2 (Windows format).
2307   address pc = (address) exceptionInfo->ExceptionRecord->ExceptionAddress;
2308   // Convert the pc to "Unix format", which has the slot number coded
2309   // into the least 2 bits: 0000=slot0, 0001=slot1, 0010=slot2
2310   // This is needed for IA64 because "relocation" / "implicit null check" / "poll instruction"
2311   // information is saved in the Unix format.
2312   address pc_unix_format = (address) ((((uint64_t)pc) & 0xFFFFFFFFFFFFFFF0) | ((((uint64_t)pc) & 0xF) >> 2));
2313 #elif _M_AMD64
2314   address pc = (address) exceptionInfo->ContextRecord->Rip;
2315 #else
2316   address pc = (address) exceptionInfo->ContextRecord->Eip;
2317 #endif
2318   Thread* t = ThreadLocalStorage::get_thread_slow();          // slow & steady
2319 
2320   // Handle SafeFetch32 and SafeFetchN exceptions.
2321   if (StubRoutines::is_safefetch_fault(pc)) {
2322     return Handle_Exception(exceptionInfo, StubRoutines::continuation_for_safefetch_fault(pc));
2323   }
2324 
2325 #ifndef _WIN64
2326   // Execution protection violation - win32 running on AMD64 only
2327   // Handled first to avoid misdiagnosis as a "normal" access violation;
2328   // This is safe to do because we have a new/unique ExceptionInformation
2329   // code for this condition.
2330   if (exception_code == EXCEPTION_ACCESS_VIOLATION) {
2331     PEXCEPTION_RECORD exceptionRecord = exceptionInfo->ExceptionRecord;
2332     int exception_subcode = (int) exceptionRecord->ExceptionInformation[0];
2333     address addr = (address) exceptionRecord->ExceptionInformation[1];
2334 
2335     if (exception_subcode == EXCEPTION_INFO_EXEC_VIOLATION) {
2336       int page_size = os::vm_page_size();
2337 
2338       // Make sure the pc and the faulting address are sane.
2339       //
2340       // If an instruction spans a page boundary, and the page containing
2341       // the beginning of the instruction is executable but the following
2342       // page is not, the pc and the faulting address might be slightly
2343       // different - we still want to unguard the 2nd page in this case.
2344       //