os_windows.hpp revision 13268:786437c6344b
11541Srgrimes/*
21541Srgrimes * Copyright (c) 1997, 2017, Oracle and/or its affiliates. All rights reserved.
31541Srgrimes * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
41541Srgrimes *
51541Srgrimes * This code is free software; you can redistribute it and/or modify it
61541Srgrimes * under the terms of the GNU General Public License version 2 only, as
71541Srgrimes * published by the Free Software Foundation.
81541Srgrimes *
91541Srgrimes * This code is distributed in the hope that it will be useful, but WITHOUT
101541Srgrimes * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
111541Srgrimes * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
121541Srgrimes * version 2 for more details (a copy is included in the LICENSE file that
131541Srgrimes * accompanied this code).
141541Srgrimes *
151541Srgrimes * You should have received a copy of the GNU General Public License version
161541Srgrimes * 2 along with this work; if not, write to the Free Software Foundation,
171541Srgrimes * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
181541Srgrimes *
191541Srgrimes * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
201541Srgrimes * or visit www.oracle.com if you need additional information or have any
211541Srgrimes * questions.
221541Srgrimes *
231541Srgrimes */
241541Srgrimes
251541Srgrimes#ifndef OS_WINDOWS_VM_OS_WINDOWS_HPP
261541Srgrimes#define OS_WINDOWS_VM_OS_WINDOWS_HPP
271541Srgrimes// Win32_OS defines the interface to windows operating systems
281541Srgrimes
291541Srgrimes// Information about the protection of the page at address '0' on this os.
301541Srgrimesstatic bool zero_page_read_protected() { return true; }
311541Srgrimes
321541Srgrimes// File conventions
331541Srgrimesstatic const char* file_separator() { return "\\"; }
3444510Swollmanstatic const char* line_separator() { return "\r\n"; }
351541Srgrimesstatic const char* path_separator() { return ";"; }
361541Srgrimes
37116182Sobrienclass win32 {
38116182Sobrien  friend class os;
39116182Sobrien  friend unsigned __stdcall thread_native_entry(class Thread*);
401541Srgrimes
411541Srgrimes protected:
4233392Sphk  static int    _vm_page_size;
43127969Scperciva  static int    _vm_allocation_granularity;
441541Srgrimes  static int    _processor_type;
4574914Sjhb  static int    _processor_level;
4668840Sjhb  static julong _physical_memory;
47115810Sphk  static size_t _default_stack_size;
481541Srgrimes  static bool   _is_windows_server;
49115810Sphk  static bool   _has_exit_bug;
50115810Sphk
51115810Sphk  static void print_windows_version(outputStream* st);
52115810Sphk
53115810Sphk public:
54115810Sphk  // Windows-specific interface:
55115810Sphk  static void   initialize_system_info();
56115810Sphk  static void   setmode_streams();
57115810Sphk
5833392Sphk  // Processor info as provided by NT
5933392Sphk  static int processor_type()  { return _processor_type;  }
6033392Sphk  static int processor_level() {
6133392Sphk    return _processor_level;
6233392Sphk  }
6333392Sphk  static julong available_memory();
6429680Sgibbs  static julong physical_memory() { return _physical_memory; }
6529680Sgibbs
6629680Sgibbs  // load dll from Windows system directory or Windows directory
6729680Sgibbs  static HINSTANCE load_Windows_dll(const char* name, char *ebuf, int ebuflen);
6833392Sphk
69116606Sphk private:
70122585Smckusick  enum Ept { EPT_THREAD, EPT_PROCESS, EPT_PROCESS_DIE };
71122761Sphk  // Wrapper around _endthreadex(), exit() and _exit()
72122585Smckusick  static int exit_process_or_thread(Ept what, int exit_code);
732112Swollman
7429680Sgibbs  static void initialize_performance_counter();
75128024Scperciva
76128024Scperciva public:
77127969Scperciva  // Generic interface:
78127969Scperciva
79127969Scperciva  // Trace number of created threads
80127969Scperciva  static          intx  _os_thread_limit;
81127969Scperciva  static volatile intx  _os_thread_count;
82128024Scperciva
83128024Scperciva  // Tells whether this is a server version of Windows
84128024Scperciva  static bool is_windows_server() { return _is_windows_server; }
85127969Scperciva
86127969Scperciva  // Tells whether there can be the race bug during process exit on this platform
87127969Scperciva  static bool has_exit_bug() { return _has_exit_bug; }
88127969Scperciva
89127969Scperciva  // Returns the byte size of a virtual memory page
90128024Scperciva  static int vm_page_size() { return _vm_page_size; }
91127969Scperciva
92128024Scperciva  // Returns the size in bytes of memory blocks which can be allocated.
93128024Scperciva  static int vm_allocation_granularity() { return _vm_allocation_granularity; }
94127969Scperciva
95127969Scperciva  // Read the headers for the executable that started the current process into
96127969Scperciva  // the structure passed in (see winnt.h).
97127969Scperciva  static void read_executable_headers(PIMAGE_NT_HEADERS);
98127969Scperciva
99127969Scperciva  // Default stack size for the current process.
100127969Scperciva  static size_t default_stack_size() { return _default_stack_size; }
101127969Scperciva
102127969Scperciva  static bool get_frame_at_stack_banging_point(JavaThread* thread,
1031541Srgrimes                          struct _EXCEPTION_POINTERS* exceptionInfo,
1041541Srgrimes                          address pc, frame* fr);
10582127Sdillon
10682127Sdillon#ifndef _WIN64
10782127Sdillon  // A wrapper to install a structured exception handler for fast JNI accesors.
10882127Sdillon  static address fast_jni_accessor_wrapper(BasicType);
10982127Sdillon#endif
11082127Sdillon
11182127Sdillon  // filter function to ignore faults on serializations page
11282127Sdillon  static LONG WINAPI serialize_fault_filter(struct _EXCEPTION_POINTERS* e);
11382127Sdillon
11482127Sdillon  // Fast access to current thread
11582127Sdillonprotected:
11682127Sdillon  static int _thread_ptr_offset;
11782127Sdillonprivate:
11882127Sdillon  static void initialize_thread_ptr_offset();
11982127Sdillonpublic:
12082127Sdillon  static inline void set_thread_ptr_offset(int offset) {
12182127Sdillon    _thread_ptr_offset = offset;
12282127Sdillon  }
12382127Sdillon  static inline int get_thread_ptr_offset() { return _thread_ptr_offset; }
12482127Sdillon};
12582127Sdillon
12682127Sdillonstatic void write_memory_serialize_page_with_handler(JavaThread* thread) {
12782127Sdillon  // Due to chained nature of SEH handlers we have to be sure
12882127Sdillon  // that our handler is always last handler before an attempt to write
12982127Sdillon  // into serialization page - it can fault if we access this page
13082127Sdillon  // right in the middle of protect/unprotect sequence by remote
13182127Sdillon  // membar logic.
13282127Sdillon  // __try/__except are very lightweight operations (only several
13382127Sdillon  // instructions not affecting control flow directly on x86)
13482127Sdillon  // so we can use it here, on very time critical path
13582127Sdillon  __try {
13682127Sdillon    write_memory_serialize_page(thread);
13782127Sdillon  } __except (win32::serialize_fault_filter((_EXCEPTION_POINTERS*)_exception_info()))
13882127Sdillon    {}
13982127Sdillon}
14082127Sdillon
14182127Sdillon/*
14282127Sdillon * Crash protection for the watcher thread. Wrap the callback
14382127Sdillon * with a __try { call() }
14482127Sdillon * To be able to use this - don't take locks, don't rely on destructors,
14582127Sdillon * don't make OS library calls, don't allocate memory, don't print,
14682127Sdillon * don't call code that could leave the heap / memory in an inconsistent state,
14782127Sdillon * or anything else where we are not in control if we suddenly jump out.
14882127Sdillon */
14982127Sdillonclass ThreadCrashProtection : public StackObj {
15093818Sjhbpublic:
151122585Smckusick  static bool is_crash_protected(Thread* thr) {
152122761Sphk    return _crash_protection != NULL && _protected_thread == thr;
153122585Smckusick  }
154127969Scperciva
155127969Scperciva  ThreadCrashProtection();
15682127Sdillon  bool call(os::CrashProtectionCallback& cb);
15782127Sdillonprivate:
15882127Sdillon  static Thread* _protected_thread;
15929680Sgibbs  static ThreadCrashProtection* _crash_protection;
16029680Sgibbs  static volatile intptr_t _crash_mux;
16129680Sgibbs};
16229680Sgibbs
16329680Sgibbsclass PlatformEvent : public CHeapObj<mtInternal> {
16429680Sgibbs  private:
16529680Sgibbs    double CachePad [4] ;   // increase odds that _Event is sole occupant of cache line
16629680Sgibbs    volatile int _Event ;
16729680Sgibbs    HANDLE _ParkHandle ;
16829680Sgibbs
16932388Sphk  public:       // TODO-FIXME: make dtor private
17029680Sgibbs    ~PlatformEvent() { guarantee (0, "invariant") ; }
1711541Srgrimes
1721541Srgrimes  public:
1731541Srgrimes    PlatformEvent() {
1741541Srgrimes      _Event   = 0 ;
17567551Sjhb      _ParkHandle = CreateEvent (NULL, false, false, NULL) ;
1761541Srgrimes      guarantee (_ParkHandle != NULL, "invariant") ;
177102936Sphk    }
178102936Sphk
179102936Sphk    // Exercise caution using reset() and fired() - they may require MEMBARs
180102936Sphk    void reset() { _Event = 0 ; }
181115810Sphk    int  fired() { return _Event; }
182115810Sphk    void park () ;
183115810Sphk    void unpark () ;
184127969Scperciva    int  park (jlong millis) ;
185122585Smckusick} ;
186122585Smckusick
187122585Smckusick
188122585Smckusick
189123254Sphkclass PlatformParker : public CHeapObj<mtInternal> {
190122585Smckusick  protected:
1911541Srgrimes    HANDLE _ParkEvent ;
19233392Sphk
19333392Sphk  public:
19433392Sphk    ~PlatformParker () { guarantee (0, "invariant") ; }
19529680Sgibbs    PlatformParker  () {
196115810Sphk      _ParkEvent = CreateEvent (NULL, true, false, NULL) ;
197115810Sphk      guarantee (_ParkEvent != NULL, "invariant") ;
198115810Sphk    }
19929680Sgibbs
20072200Sbmilekic} ;
20129680Sgibbs
20229805Sgibbs#endif // OS_WINDOWS_VM_OS_WINDOWS_HPP
20329805Sgibbs