hotspot/src/os/linux/vm/os_linux.cpp
author minqi
Wed, 15 Apr 2015 17:34:28 -0700
changeset 30240 a7ba42fa1df6
parent 30139 a2ae06b774e5
child 30252 b9faf31ff015
permissions -rw-r--r--
8074354: Make CreateMinidumpOnCrash a new name and available on all platforms Summary: Rename CreateMinidumpOnCrash which is used only for Windows as CreateCoredumpOnCrash and make it available for all platforms. Changed order for dumping core on Windows to be similar on other platforms. Also reviewed by thomas.stuefe@gmail.com Reviewed-by: dcubed Contributed-by: yumin.qi@oracle.com, thomas.stuefe@gmail.com
Ignore whitespace changes - Everywhere: Within whitespace: At end of lines:
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
     1
/*
28737
ca4b6a6e5cc8 8068730: Increase the precision of the implementation of java.time.Clock.systemUTC()
dfuchs
parents: 28172
diff changeset
     2
 * Copyright (c) 1999, 2015, Oracle and/or its affiliates. All rights reserved.
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
     3
 * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
489c9b5090e2 Initial load
duke
parents:
diff changeset
     4
 *
489c9b5090e2 Initial load
duke
parents:
diff changeset
     5
 * This code is free software; you can redistribute it and/or modify it
489c9b5090e2 Initial load
duke
parents:
diff changeset
     6
 * under the terms of the GNU General Public License version 2 only, as
489c9b5090e2 Initial load
duke
parents:
diff changeset
     7
 * published by the Free Software Foundation.
489c9b5090e2 Initial load
duke
parents:
diff changeset
     8
 *
489c9b5090e2 Initial load
duke
parents:
diff changeset
     9
 * This code is distributed in the hope that it will be useful, but WITHOUT
489c9b5090e2 Initial load
duke
parents:
diff changeset
    10
 * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
489c9b5090e2 Initial load
duke
parents:
diff changeset
    11
 * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
489c9b5090e2 Initial load
duke
parents:
diff changeset
    12
 * version 2 for more details (a copy is included in the LICENSE file that
489c9b5090e2 Initial load
duke
parents:
diff changeset
    13
 * accompanied this code).
489c9b5090e2 Initial load
duke
parents:
diff changeset
    14
 *
489c9b5090e2 Initial load
duke
parents:
diff changeset
    15
 * You should have received a copy of the GNU General Public License version
489c9b5090e2 Initial load
duke
parents:
diff changeset
    16
 * 2 along with this work; if not, write to the Free Software Foundation,
489c9b5090e2 Initial load
duke
parents:
diff changeset
    17
 * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
489c9b5090e2 Initial load
duke
parents:
diff changeset
    18
 *
5547
f4b087cbb361 6941466: Oracle rebranding changes for Hotspot repositories
trims
parents: 5532
diff changeset
    19
 * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
f4b087cbb361 6941466: Oracle rebranding changes for Hotspot repositories
trims
parents: 5532
diff changeset
    20
 * or visit www.oracle.com if you need additional information or have any
f4b087cbb361 6941466: Oracle rebranding changes for Hotspot repositories
trims
parents: 5532
diff changeset
    21
 * questions.
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
    22
 *
489c9b5090e2 Initial load
duke
parents:
diff changeset
    23
 */
489c9b5090e2 Initial load
duke
parents:
diff changeset
    24
7397
5b173b4ca846 6989984: Use standard include model for Hospot
stefank
parents: 6964
diff changeset
    25
// no precompiled headers
5b173b4ca846 6989984: Use standard include model for Hospot
stefank
parents: 6964
diff changeset
    26
#include "classfile/classLoader.hpp"
5b173b4ca846 6989984: Use standard include model for Hospot
stefank
parents: 6964
diff changeset
    27
#include "classfile/systemDictionary.hpp"
5b173b4ca846 6989984: Use standard include model for Hospot
stefank
parents: 6964
diff changeset
    28
#include "classfile/vmSymbols.hpp"
5b173b4ca846 6989984: Use standard include model for Hospot
stefank
parents: 6964
diff changeset
    29
#include "code/icBuffer.hpp"
5b173b4ca846 6989984: Use standard include model for Hospot
stefank
parents: 6964
diff changeset
    30
#include "code/vtableStubs.hpp"
5b173b4ca846 6989984: Use standard include model for Hospot
stefank
parents: 6964
diff changeset
    31
#include "compiler/compileBroker.hpp"
14626
0cf4eccf130f 8003240: x86: move MacroAssembler into separate file
twisti
parents: 14471
diff changeset
    32
#include "compiler/disassembler.hpp"
7397
5b173b4ca846 6989984: Use standard include model for Hospot
stefank
parents: 6964
diff changeset
    33
#include "interpreter/interpreter.hpp"
5b173b4ca846 6989984: Use standard include model for Hospot
stefank
parents: 6964
diff changeset
    34
#include "jvm_linux.h"
5b173b4ca846 6989984: Use standard include model for Hospot
stefank
parents: 6964
diff changeset
    35
#include "memory/allocation.inline.hpp"
5b173b4ca846 6989984: Use standard include model for Hospot
stefank
parents: 6964
diff changeset
    36
#include "memory/filemap.hpp"
5b173b4ca846 6989984: Use standard include model for Hospot
stefank
parents: 6964
diff changeset
    37
#include "mutex_linux.inline.hpp"
5b173b4ca846 6989984: Use standard include model for Hospot
stefank
parents: 6964
diff changeset
    38
#include "oops/oop.inline.hpp"
25468
5331df506290 8048241: Introduce umbrella header os.inline.hpp and clean up includes
goetz
parents: 25354
diff changeset
    39
#include "os_linux.inline.hpp"
7397
5b173b4ca846 6989984: Use standard include model for Hospot
stefank
parents: 6964
diff changeset
    40
#include "os_share_linux.hpp"
5b173b4ca846 6989984: Use standard include model for Hospot
stefank
parents: 6964
diff changeset
    41
#include "prims/jniFastGetField.hpp"
5b173b4ca846 6989984: Use standard include model for Hospot
stefank
parents: 6964
diff changeset
    42
#include "prims/jvm.h"
5b173b4ca846 6989984: Use standard include model for Hospot
stefank
parents: 6964
diff changeset
    43
#include "prims/jvm_misc.hpp"
5b173b4ca846 6989984: Use standard include model for Hospot
stefank
parents: 6964
diff changeset
    44
#include "runtime/arguments.hpp"
25351
7c198a690050 8044775: Improve usage of umbrella header atomic.inline.hpp.
goetz
parents: 25064
diff changeset
    45
#include "runtime/atomic.inline.hpp"
7397
5b173b4ca846 6989984: Use standard include model for Hospot
stefank
parents: 6964
diff changeset
    46
#include "runtime/extendedPC.hpp"
5b173b4ca846 6989984: Use standard include model for Hospot
stefank
parents: 6964
diff changeset
    47
#include "runtime/globals.hpp"
5b173b4ca846 6989984: Use standard include model for Hospot
stefank
parents: 6964
diff changeset
    48
#include "runtime/interfaceSupport.hpp"
15926
8e87d545195f 7107135: Stack guard pages are no more protected after loading a shared library with executable stack
iklam
parents: 15855
diff changeset
    49
#include "runtime/init.hpp"
7397
5b173b4ca846 6989984: Use standard include model for Hospot
stefank
parents: 6964
diff changeset
    50
#include "runtime/java.hpp"
5b173b4ca846 6989984: Use standard include model for Hospot
stefank
parents: 6964
diff changeset
    51
#include "runtime/javaCalls.hpp"
5b173b4ca846 6989984: Use standard include model for Hospot
stefank
parents: 6964
diff changeset
    52
#include "runtime/mutexLocker.hpp"
5b173b4ca846 6989984: Use standard include model for Hospot
stefank
parents: 6964
diff changeset
    53
#include "runtime/objectMonitor.hpp"
24351
61b33cc6d3cf 8042195: Introduce umbrella header orderAccess.inline.hpp.
goetz
parents: 23868
diff changeset
    54
#include "runtime/orderAccess.inline.hpp"
7397
5b173b4ca846 6989984: Use standard include model for Hospot
stefank
parents: 6964
diff changeset
    55
#include "runtime/osThread.hpp"
5b173b4ca846 6989984: Use standard include model for Hospot
stefank
parents: 6964
diff changeset
    56
#include "runtime/perfMemory.hpp"
5b173b4ca846 6989984: Use standard include model for Hospot
stefank
parents: 6964
diff changeset
    57
#include "runtime/sharedRuntime.hpp"
5b173b4ca846 6989984: Use standard include model for Hospot
stefank
parents: 6964
diff changeset
    58
#include "runtime/statSampler.hpp"
5b173b4ca846 6989984: Use standard include model for Hospot
stefank
parents: 6964
diff changeset
    59
#include "runtime/stubRoutines.hpp"
14583
d70ee55535f4 8003935: Simplify the needed includes for using Thread::current()
stefank
parents: 14471
diff changeset
    60
#include "runtime/thread.inline.hpp"
7397
5b173b4ca846 6989984: Use standard include model for Hospot
stefank
parents: 6964
diff changeset
    61
#include "runtime/threadCritical.hpp"
5b173b4ca846 6989984: Use standard include model for Hospot
stefank
parents: 6964
diff changeset
    62
#include "runtime/timer.hpp"
5b173b4ca846 6989984: Use standard include model for Hospot
stefank
parents: 6964
diff changeset
    63
#include "services/attachListener.hpp"
15927
f256c20146f4 8008257: NMT: assert(new_rec->is_allocation_record()) failed when running with shared memory option
zgu
parents: 15926
diff changeset
    64
#include "services/memTracker.hpp"
7397
5b173b4ca846 6989984: Use standard include model for Hospot
stefank
parents: 6964
diff changeset
    65
#include "services/runtimeService.hpp"
7447
32c42d627f41 7003748: Decode C stack frames when symbols are presented (PhoneHome project)
zgu
parents: 7397
diff changeset
    66
#include "utilities/decoder.hpp"
7397
5b173b4ca846 6989984: Use standard include model for Hospot
stefank
parents: 6964
diff changeset
    67
#include "utilities/defaultStream.hpp"
5b173b4ca846 6989984: Use standard include model for Hospot
stefank
parents: 6964
diff changeset
    68
#include "utilities/events.hpp"
15926
8e87d545195f 7107135: Stack guard pages are no more protected after loading a shared library with executable stack
iklam
parents: 15855
diff changeset
    69
#include "utilities/elfFile.hpp"
7397
5b173b4ca846 6989984: Use standard include model for Hospot
stefank
parents: 6964
diff changeset
    70
#include "utilities/growableArray.hpp"
27683
1d5707553fff 8064580: Move INCLUDE_CDS include section to the end of the include list
stefank
parents: 27400
diff changeset
    71
#include "utilities/macros.hpp"
7397
5b173b4ca846 6989984: Use standard include model for Hospot
stefank
parents: 6964
diff changeset
    72
#include "utilities/vmError.hpp"
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
    73
489c9b5090e2 Initial load
duke
parents:
diff changeset
    74
// put OS-includes here
489c9b5090e2 Initial load
duke
parents:
diff changeset
    75
# include <sys/types.h>
489c9b5090e2 Initial load
duke
parents:
diff changeset
    76
# include <sys/mman.h>
6176
4d9030fe341f 6953477: Increase portability and flexibility of building Hotspot
bobv
parents: 5922
diff changeset
    77
# include <sys/stat.h>
4d9030fe341f 6953477: Increase portability and flexibility of building Hotspot
bobv
parents: 5922
diff changeset
    78
# include <sys/select.h>
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
    79
# include <pthread.h>
489c9b5090e2 Initial load
duke
parents:
diff changeset
    80
# include <signal.h>
489c9b5090e2 Initial load
duke
parents:
diff changeset
    81
# include <errno.h>
489c9b5090e2 Initial load
duke
parents:
diff changeset
    82
# include <dlfcn.h>
489c9b5090e2 Initial load
duke
parents:
diff changeset
    83
# include <stdio.h>
489c9b5090e2 Initial load
duke
parents:
diff changeset
    84
# include <unistd.h>
489c9b5090e2 Initial load
duke
parents:
diff changeset
    85
# include <sys/resource.h>
489c9b5090e2 Initial load
duke
parents:
diff changeset
    86
# include <pthread.h>
489c9b5090e2 Initial load
duke
parents:
diff changeset
    87
# include <sys/stat.h>
489c9b5090e2 Initial load
duke
parents:
diff changeset
    88
# include <sys/time.h>
489c9b5090e2 Initial load
duke
parents:
diff changeset
    89
# include <sys/times.h>
489c9b5090e2 Initial load
duke
parents:
diff changeset
    90
# include <sys/utsname.h>
489c9b5090e2 Initial load
duke
parents:
diff changeset
    91
# include <sys/socket.h>
489c9b5090e2 Initial load
duke
parents:
diff changeset
    92
# include <sys/wait.h>
489c9b5090e2 Initial load
duke
parents:
diff changeset
    93
# include <pwd.h>
489c9b5090e2 Initial load
duke
parents:
diff changeset
    94
# include <poll.h>
489c9b5090e2 Initial load
duke
parents:
diff changeset
    95
# include <semaphore.h>
489c9b5090e2 Initial load
duke
parents:
diff changeset
    96
# include <fcntl.h>
489c9b5090e2 Initial load
duke
parents:
diff changeset
    97
# include <string.h>
489c9b5090e2 Initial load
duke
parents:
diff changeset
    98
# include <syscall.h>
489c9b5090e2 Initial load
duke
parents:
diff changeset
    99
# include <sys/sysinfo.h>
489c9b5090e2 Initial load
duke
parents:
diff changeset
   100
# include <gnu/libc-version.h>
489c9b5090e2 Initial load
duke
parents:
diff changeset
   101
# include <sys/ipc.h>
489c9b5090e2 Initial load
duke
parents:
diff changeset
   102
# include <sys/shm.h>
489c9b5090e2 Initial load
duke
parents:
diff changeset
   103
# include <link.h>
5085
4f0c435f8c3c 6929067: Stack guard pages should be removed when thread is detached
coleenp
parents: 4493
diff changeset
   104
# include <stdint.h>
4f0c435f8c3c 6929067: Stack guard pages should be removed when thread is detached
coleenp
parents: 4493
diff changeset
   105
# include <inttypes.h>
7458
3f956542f1fd 7003707: need to remove (some) system include files from the HotSpot header files
dholmes
parents: 7448
diff changeset
   106
# include <sys/ioctl.h>
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
   107
24424
2658d7834c6e 8037816: Fix for 8036122 breaks build with Xcode5/clang
drchase
parents: 24352
diff changeset
   108
PRAGMA_FORMAT_MUTE_WARNINGS_FOR_GCC
2658d7834c6e 8037816: Fix for 8036122 breaks build with Xcode5/clang
drchase
parents: 24352
diff changeset
   109
17854
d65bc1546091 8013895: G1: G1SummarizeRSetStats output on Linux needs improvemen
tschatzl
parents: 17134
diff changeset
   110
// if RUSAGE_THREAD for getrusage() has not been defined, do it here. The code calling
d65bc1546091 8013895: G1: G1SummarizeRSetStats output on Linux needs improvemen
tschatzl
parents: 17134
diff changeset
   111
// getrusage() is prepared to handle the associated failure.
d65bc1546091 8013895: G1: G1SummarizeRSetStats output on Linux needs improvemen
tschatzl
parents: 17134
diff changeset
   112
#ifndef RUSAGE_THREAD
26684
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
   113
  #define RUSAGE_THREAD   (1)               /* only the calling thread */
17854
d65bc1546091 8013895: G1: G1SummarizeRSetStats output on Linux needs improvemen
tschatzl
parents: 17134
diff changeset
   114
#endif
d65bc1546091 8013895: G1: G1SummarizeRSetStats output on Linux needs improvemen
tschatzl
parents: 17134
diff changeset
   115
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
   116
#define MAX_PATH    (2 * K)
489c9b5090e2 Initial load
duke
parents:
diff changeset
   117
23479
c8d925d6c93f 8037340: Linux semaphores to use CLOCK_REALTIME
mgronlun
parents: 23444
diff changeset
   118
#define MAX_SECS 100000000
c8d925d6c93f 8037340: Linux semaphores to use CLOCK_REALTIME
mgronlun
parents: 23444
diff changeset
   119
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
   120
// for timer info max values which include all bits
489c9b5090e2 Initial load
duke
parents:
diff changeset
   121
#define ALL_64_BITS CONST64(0xFFFFFFFFFFFFFFFF)
489c9b5090e2 Initial load
duke
parents:
diff changeset
   122
8119
81eef1b06988 7014918: Improve core/minidump handling in Hotspot
ctornqvi
parents: 8108
diff changeset
   123
#define LARGEPAGES_BIT (1 << 6)
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
   124
////////////////////////////////////////////////////////////////////////////////
489c9b5090e2 Initial load
duke
parents:
diff changeset
   125
// global variables
489c9b5090e2 Initial load
duke
parents:
diff changeset
   126
julong os::Linux::_physical_memory = 0;
489c9b5090e2 Initial load
duke
parents:
diff changeset
   127
489c9b5090e2 Initial load
duke
parents:
diff changeset
   128
address   os::Linux::_initial_thread_stack_bottom = NULL;
489c9b5090e2 Initial load
duke
parents:
diff changeset
   129
uintptr_t os::Linux::_initial_thread_stack_size   = 0;
489c9b5090e2 Initial load
duke
parents:
diff changeset
   130
489c9b5090e2 Initial load
duke
parents:
diff changeset
   131
int (*os::Linux::_clock_gettime)(clockid_t, struct timespec *) = NULL;
489c9b5090e2 Initial load
duke
parents:
diff changeset
   132
int (*os::Linux::_pthread_getcpuclockid)(pthread_t, clockid_t *) = NULL;
27164
6523fa019ffa 7102541: RFE: os::set_native_thread_name() cleanups
sla
parents: 27157
diff changeset
   133
int (*os::Linux::_pthread_setname_np)(pthread_t, const char*) = NULL;
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
   134
Mutex* os::Linux::_createThread_lock = NULL;
489c9b5090e2 Initial load
duke
parents:
diff changeset
   135
pthread_t os::Linux::_main_thread;
489c9b5090e2 Initial load
duke
parents:
diff changeset
   136
int os::Linux::_page_size = -1;
17090
98a9d26f1ef1 8013398: Adjust number of stack guard pages on systems with large memory page size
vladidan
parents: 17083
diff changeset
   137
const int os::Linux::_vm_default_page_size = (8 * K);
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
   138
bool os::Linux::_is_floating_stack = false;
489c9b5090e2 Initial load
duke
parents:
diff changeset
   139
bool os::Linux::_is_NPTL = false;
489c9b5090e2 Initial load
duke
parents:
diff changeset
   140
bool os::Linux::_supports_fast_thread_cpu_time = false;
745
47129a5cacd3 6681796: hotspot build failure on gcc 4.2.x (ubuntu 8.04) w/ openjdk 6
xlu
parents: 388
diff changeset
   141
const char * os::Linux::_glibc_version = NULL;
47129a5cacd3 6681796: hotspot build failure on gcc 4.2.x (ubuntu 8.04) w/ openjdk 6
xlu
parents: 388
diff changeset
   142
const char * os::Linux::_libpthread_version = NULL;
19964
a3a04a9d29ac 6900441: PlatformEvent.park(millis) on Linux could still be affected by changes to the time-of-day clock
dholmes
parents: 19732
diff changeset
   143
pthread_condattr_t os::Linux::_condattr[1];
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
   144
489c9b5090e2 Initial load
duke
parents:
diff changeset
   145
static jlong initial_time_count=0;
489c9b5090e2 Initial load
duke
parents:
diff changeset
   146
489c9b5090e2 Initial load
duke
parents:
diff changeset
   147
static int clock_tics_per_sec = 100;
489c9b5090e2 Initial load
duke
parents:
diff changeset
   148
489c9b5090e2 Initial load
duke
parents:
diff changeset
   149
// For diagnostics to print a message once. see run_periodic_checks
489c9b5090e2 Initial load
duke
parents:
diff changeset
   150
static sigset_t check_signal_done;
22807
1cf02ef734e2 8016586: PPC64 (part 3): basic changes for PPC64
goetz
parents: 22806
diff changeset
   151
static bool check_signals = true;
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
   152
489c9b5090e2 Initial load
duke
parents:
diff changeset
   153
static pid_t _initial_pid = 0;
489c9b5090e2 Initial load
duke
parents:
diff changeset
   154
26684
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
   155
// Signal number used to suspend/resume a thread
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
   156
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
   157
// do not use any signal number less than SIGSEGV, see 4355769
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
   158
static int SR_signum = SIGUSR2;
489c9b5090e2 Initial load
duke
parents:
diff changeset
   159
sigset_t SR_sigset;
489c9b5090e2 Initial load
duke
parents:
diff changeset
   160
18025
b7bcf7497f93 8005849: JEP 167: Event-Based JVM Tracing
sla
parents: 17854
diff changeset
   161
// Declarations
b7bcf7497f93 8005849: JEP 167: Event-Based JVM Tracing
sla
parents: 17854
diff changeset
   162
static void unpackTime(timespec* absTime, bool isAbsolute, jlong time);
b7bcf7497f93 8005849: JEP 167: Event-Based JVM Tracing
sla
parents: 17854
diff changeset
   163
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
   164
// utility functions
489c9b5090e2 Initial load
duke
parents:
diff changeset
   165
489c9b5090e2 Initial load
duke
parents:
diff changeset
   166
static int SR_initialize();
489c9b5090e2 Initial load
duke
parents:
diff changeset
   167
489c9b5090e2 Initial load
duke
parents:
diff changeset
   168
julong os::available_memory() {
489c9b5090e2 Initial load
duke
parents:
diff changeset
   169
  return Linux::available_memory();
489c9b5090e2 Initial load
duke
parents:
diff changeset
   170
}
489c9b5090e2 Initial load
duke
parents:
diff changeset
   171
489c9b5090e2 Initial load
duke
parents:
diff changeset
   172
julong os::Linux::available_memory() {
489c9b5090e2 Initial load
duke
parents:
diff changeset
   173
  // values in struct sysinfo are "unsigned long"
489c9b5090e2 Initial load
duke
parents:
diff changeset
   174
  struct sysinfo si;
489c9b5090e2 Initial load
duke
parents:
diff changeset
   175
  sysinfo(&si);
489c9b5090e2 Initial load
duke
parents:
diff changeset
   176
489c9b5090e2 Initial load
duke
parents:
diff changeset
   177
  return (julong)si.freeram * si.mem_unit;
489c9b5090e2 Initial load
duke
parents:
diff changeset
   178
}
489c9b5090e2 Initial load
duke
parents:
diff changeset
   179
489c9b5090e2 Initial load
duke
parents:
diff changeset
   180
julong os::physical_memory() {
489c9b5090e2 Initial load
duke
parents:
diff changeset
   181
  return Linux::physical_memory();
489c9b5090e2 Initial load
duke
parents:
diff changeset
   182
}
489c9b5090e2 Initial load
duke
parents:
diff changeset
   183
489c9b5090e2 Initial load
duke
parents:
diff changeset
   184
// Return true if user is running as root.
489c9b5090e2 Initial load
duke
parents:
diff changeset
   185
489c9b5090e2 Initial load
duke
parents:
diff changeset
   186
bool os::have_special_privileges() {
489c9b5090e2 Initial load
duke
parents:
diff changeset
   187
  static bool init = false;
489c9b5090e2 Initial load
duke
parents:
diff changeset
   188
  static bool privileges = false;
489c9b5090e2 Initial load
duke
parents:
diff changeset
   189
  if (!init) {
489c9b5090e2 Initial load
duke
parents:
diff changeset
   190
    privileges = (getuid() != geteuid()) || (getgid() != getegid());
489c9b5090e2 Initial load
duke
parents:
diff changeset
   191
    init = true;
489c9b5090e2 Initial load
duke
parents:
diff changeset
   192
  }
489c9b5090e2 Initial load
duke
parents:
diff changeset
   193
  return privileges;
489c9b5090e2 Initial load
duke
parents:
diff changeset
   194
}
489c9b5090e2 Initial load
duke
parents:
diff changeset
   195
489c9b5090e2 Initial load
duke
parents:
diff changeset
   196
489c9b5090e2 Initial load
duke
parents:
diff changeset
   197
#ifndef SYS_gettid
489c9b5090e2 Initial load
duke
parents:
diff changeset
   198
// i386: 224, ia64: 1105, amd64: 186, sparc 143
26684
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
   199
  #ifdef __ia64__
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
   200
    #define SYS_gettid 1105
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
   201
  #elif __i386__
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
   202
    #define SYS_gettid 224
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
   203
  #elif __amd64__
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
   204
    #define SYS_gettid 186
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
   205
  #elif __sparc__
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
   206
    #define SYS_gettid 143
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
   207
  #else
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
   208
    #error define gettid for the arch
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
   209
  #endif
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
   210
#endif
489c9b5090e2 Initial load
duke
parents:
diff changeset
   211
489c9b5090e2 Initial load
duke
parents:
diff changeset
   212
// Cpu architecture string
29474
81a5c5330d08 8072383: resolve conflicts between open and closed ports
dlong
parents: 29193
diff changeset
   213
static char cpu_arch[] = HOTSPOT_LIB_ARCH;
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
   214
489c9b5090e2 Initial load
duke
parents:
diff changeset
   215
489c9b5090e2 Initial load
duke
parents:
diff changeset
   216
// pid_t gettid()
489c9b5090e2 Initial load
duke
parents:
diff changeset
   217
//
489c9b5090e2 Initial load
duke
parents:
diff changeset
   218
// Returns the kernel thread id of the currently running thread. Kernel
489c9b5090e2 Initial load
duke
parents:
diff changeset
   219
// thread id is used to access /proc.
489c9b5090e2 Initial load
duke
parents:
diff changeset
   220
//
489c9b5090e2 Initial load
duke
parents:
diff changeset
   221
// (Note that getpid() on LinuxThreads returns kernel thread id too; but
489c9b5090e2 Initial load
duke
parents:
diff changeset
   222
// on NPTL, it returns the same pid for all threads, as required by POSIX.)
489c9b5090e2 Initial load
duke
parents:
diff changeset
   223
//
489c9b5090e2 Initial load
duke
parents:
diff changeset
   224
pid_t os::Linux::gettid() {
489c9b5090e2 Initial load
duke
parents:
diff changeset
   225
  int rslt = syscall(SYS_gettid);
489c9b5090e2 Initial load
duke
parents:
diff changeset
   226
  if (rslt == -1) {
26683
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
   227
    // old kernel, no NPTL support
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
   228
    return getpid();
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
   229
  } else {
26683
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
   230
    return (pid_t)rslt;
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
   231
  }
489c9b5090e2 Initial load
duke
parents:
diff changeset
   232
}
489c9b5090e2 Initial load
duke
parents:
diff changeset
   233
489c9b5090e2 Initial load
duke
parents:
diff changeset
   234
// Most versions of linux have a bug where the number of processors are
489c9b5090e2 Initial load
duke
parents:
diff changeset
   235
// determined by looking at the /proc file system.  In a chroot environment,
489c9b5090e2 Initial load
duke
parents:
diff changeset
   236
// the system call returns 1.  This causes the VM to act as if it is
489c9b5090e2 Initial load
duke
parents:
diff changeset
   237
// a single processor and elide locking (see is_MP() call).
489c9b5090e2 Initial load
duke
parents:
diff changeset
   238
static bool unsafe_chroot_detected = false;
745
47129a5cacd3 6681796: hotspot build failure on gcc 4.2.x (ubuntu 8.04) w/ openjdk 6
xlu
parents: 388
diff changeset
   239
static const char *unstable_chroot_error = "/proc file system not found.\n"
47129a5cacd3 6681796: hotspot build failure on gcc 4.2.x (ubuntu 8.04) w/ openjdk 6
xlu
parents: 388
diff changeset
   240
                     "Java may be unstable running multithreaded in a chroot "
47129a5cacd3 6681796: hotspot build failure on gcc 4.2.x (ubuntu 8.04) w/ openjdk 6
xlu
parents: 388
diff changeset
   241
                     "environment on Linux when /proc filesystem is not mounted.";
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
   242
489c9b5090e2 Initial load
duke
parents:
diff changeset
   243
void os::Linux::initialize_system_info() {
4493
9204129f065e 6843629: Make current hotspot build part of jdk5 control build
phh
parents: 4487
diff changeset
   244
  set_processor_count(sysconf(_SC_NPROCESSORS_CONF));
9204129f065e 6843629: Make current hotspot build part of jdk5 control build
phh
parents: 4487
diff changeset
   245
  if (processor_count() == 1) {
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
   246
    pid_t pid = os::Linux::gettid();
489c9b5090e2 Initial load
duke
parents:
diff changeset
   247
    char fname[32];
489c9b5090e2 Initial load
duke
parents:
diff changeset
   248
    jio_snprintf(fname, sizeof(fname), "/proc/%d", pid);
489c9b5090e2 Initial load
duke
parents:
diff changeset
   249
    FILE *fp = fopen(fname, "r");
489c9b5090e2 Initial load
duke
parents:
diff changeset
   250
    if (fp == NULL) {
489c9b5090e2 Initial load
duke
parents:
diff changeset
   251
      unsafe_chroot_detected = true;
489c9b5090e2 Initial load
duke
parents:
diff changeset
   252
    } else {
489c9b5090e2 Initial load
duke
parents:
diff changeset
   253
      fclose(fp);
489c9b5090e2 Initial load
duke
parents:
diff changeset
   254
    }
489c9b5090e2 Initial load
duke
parents:
diff changeset
   255
  }
489c9b5090e2 Initial load
duke
parents:
diff changeset
   256
  _physical_memory = (julong)sysconf(_SC_PHYS_PAGES) * (julong)sysconf(_SC_PAGESIZE);
4493
9204129f065e 6843629: Make current hotspot build part of jdk5 control build
phh
parents: 4487
diff changeset
   257
  assert(processor_count() > 0, "linux error");
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
   258
}
489c9b5090e2 Initial load
duke
parents:
diff changeset
   259
489c9b5090e2 Initial load
duke
parents:
diff changeset
   260
void os::init_system_properties_values() {
489c9b5090e2 Initial load
duke
parents:
diff changeset
   261
  // The next steps are taken in the product version:
489c9b5090e2 Initial load
duke
parents:
diff changeset
   262
  //
15096
3db45569f8c0 8005044: remove crufty '_g' support from HS runtime code
dcubed
parents: 14633
diff changeset
   263
  // Obtain the JAVA_HOME value from the location of libjvm.so.
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
   264
  // This library should be located at:
15096
3db45569f8c0 8005044: remove crufty '_g' support from HS runtime code
dcubed
parents: 14633
diff changeset
   265
  // <JAVA_HOME>/jre/lib/<arch>/{client|server}/libjvm.so.
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
   266
  //
489c9b5090e2 Initial load
duke
parents:
diff changeset
   267
  // If "/jre/lib/" appears at the right place in the path, then we
15096
3db45569f8c0 8005044: remove crufty '_g' support from HS runtime code
dcubed
parents: 14633
diff changeset
   268
  // assume libjvm.so is installed in a JDK and we use this path.
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
   269
  //
489c9b5090e2 Initial load
duke
parents:
diff changeset
   270
  // Otherwise exit with message: "Could not create the Java virtual machine."
489c9b5090e2 Initial load
duke
parents:
diff changeset
   271
  //
489c9b5090e2 Initial load
duke
parents:
diff changeset
   272
  // The following extra steps are taken in the debugging version:
489c9b5090e2 Initial load
duke
parents:
diff changeset
   273
  //
489c9b5090e2 Initial load
duke
parents:
diff changeset
   274
  // If "/jre/lib/" does NOT appear at the right place in the path
489c9b5090e2 Initial load
duke
parents:
diff changeset
   275
  // instead of exit check for $JAVA_HOME environment variable.
489c9b5090e2 Initial load
duke
parents:
diff changeset
   276
  //
489c9b5090e2 Initial load
duke
parents:
diff changeset
   277
  // If it is defined and we are able to locate $JAVA_HOME/jre/lib/<arch>,
15096
3db45569f8c0 8005044: remove crufty '_g' support from HS runtime code
dcubed
parents: 14633
diff changeset
   278
  // then we append a fake suffix "hotspot/libjvm.so" to this path so
3db45569f8c0 8005044: remove crufty '_g' support from HS runtime code
dcubed
parents: 14633
diff changeset
   279
  // it looks like libjvm.so is installed there
3db45569f8c0 8005044: remove crufty '_g' support from HS runtime code
dcubed
parents: 14633
diff changeset
   280
  // <JAVA_HOME>/jre/lib/<arch>/hotspot/libjvm.so.
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
   281
  //
489c9b5090e2 Initial load
duke
parents:
diff changeset
   282
  // Otherwise exit.
489c9b5090e2 Initial load
duke
parents:
diff changeset
   283
  //
489c9b5090e2 Initial load
duke
parents:
diff changeset
   284
  // Important note: if the location of libjvm.so changes this
489c9b5090e2 Initial load
duke
parents:
diff changeset
   285
  // code needs to be changed accordingly.
489c9b5090e2 Initial load
duke
parents:
diff changeset
   286
26684
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
   287
  // See ld(1):
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
   288
  //      The linker uses the following search paths to locate required
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
   289
  //      shared libraries:
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
   290
  //        1: ...
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
   291
  //        ...
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
   292
  //        7: The default directories, normally /lib and /usr/lib.
1885
ae1dcaf4363f 6778662: fixes 64-bits libraries directory search paths on linux
kvn
parents: 1664
diff changeset
   293
#if defined(AMD64) || defined(_LP64) && (defined(SPARC) || defined(PPC) || defined(S390))
26684
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
   294
  #define DEFAULT_LIBPATH "/usr/lib64:/lib64:/lib:/usr/lib"
1885
ae1dcaf4363f 6778662: fixes 64-bits libraries directory search paths on linux
kvn
parents: 1664
diff changeset
   295
#else
26684
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
   296
  #define DEFAULT_LIBPATH "/lib:/usr/lib"
1885
ae1dcaf4363f 6778662: fixes 64-bits libraries directory search paths on linux
kvn
parents: 1664
diff changeset
   297
#endif
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
   298
23522
217a6a90aad3 8038201: Clean up misleading usage of malloc() in init_system_properties_values()
goetz
parents: 23479
diff changeset
   299
// Base path of extensions installed on the system.
217a6a90aad3 8038201: Clean up misleading usage of malloc() in init_system_properties_values()
goetz
parents: 23479
diff changeset
   300
#define SYS_EXT_DIR     "/usr/java/packages"
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
   301
#define EXTENSIONS_DIR  "/lib/ext"
23522
217a6a90aad3 8038201: Clean up misleading usage of malloc() in init_system_properties_values()
goetz
parents: 23479
diff changeset
   302
217a6a90aad3 8038201: Clean up misleading usage of malloc() in init_system_properties_values()
goetz
parents: 23479
diff changeset
   303
  // Buffer that fits several sprintfs.
217a6a90aad3 8038201: Clean up misleading usage of malloc() in init_system_properties_values()
goetz
parents: 23479
diff changeset
   304
  // Note that the space for the colon and the trailing null are provided
217a6a90aad3 8038201: Clean up misleading usage of malloc() in init_system_properties_values()
goetz
parents: 23479
diff changeset
   305
  // by the nulls included by the sizeof operator.
217a6a90aad3 8038201: Clean up misleading usage of malloc() in init_system_properties_values()
goetz
parents: 23479
diff changeset
   306
  const size_t bufsize =
27562
47f369e3c69c 8049367: Modular Run-Time Images
chegar
parents: 27474
diff changeset
   307
    MAX2((size_t)MAXPATHLEN,  // For dll_dir & friends.
47f369e3c69c 8049367: Modular Run-Time Images
chegar
parents: 27474
diff changeset
   308
         (size_t)MAXPATHLEN + sizeof(EXTENSIONS_DIR) + sizeof(SYS_EXT_DIR) + sizeof(EXTENSIONS_DIR)); // extensions dir
23522
217a6a90aad3 8038201: Clean up misleading usage of malloc() in init_system_properties_values()
goetz
parents: 23479
diff changeset
   309
  char *buf = (char *)NEW_C_HEAP_ARRAY(char, bufsize, mtInternal);
217a6a90aad3 8038201: Clean up misleading usage of malloc() in init_system_properties_values()
goetz
parents: 23479
diff changeset
   310
217a6a90aad3 8038201: Clean up misleading usage of malloc() in init_system_properties_values()
goetz
parents: 23479
diff changeset
   311
  // sysclasspath, java_home, dll_dir
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
   312
  {
23522
217a6a90aad3 8038201: Clean up misleading usage of malloc() in init_system_properties_values()
goetz
parents: 23479
diff changeset
   313
    char *pslash;
217a6a90aad3 8038201: Clean up misleading usage of malloc() in init_system_properties_values()
goetz
parents: 23479
diff changeset
   314
    os::jvm_path(buf, bufsize);
217a6a90aad3 8038201: Clean up misleading usage of malloc() in init_system_properties_values()
goetz
parents: 23479
diff changeset
   315
217a6a90aad3 8038201: Clean up misleading usage of malloc() in init_system_properties_values()
goetz
parents: 23479
diff changeset
   316
    // Found the full path to libjvm.so.
217a6a90aad3 8038201: Clean up misleading usage of malloc() in init_system_properties_values()
goetz
parents: 23479
diff changeset
   317
    // Now cut the path to <java_home>/jre if we can.
27471
6e56277909f1 8062370: Various minor code improvements
goetz
parents: 27458
diff changeset
   318
    pslash = strrchr(buf, '/');
6e56277909f1 8062370: Various minor code improvements
goetz
parents: 27458
diff changeset
   319
    if (pslash != NULL) {
6e56277909f1 8062370: Various minor code improvements
goetz
parents: 27458
diff changeset
   320
      *pslash = '\0';            // Get rid of /libjvm.so.
6e56277909f1 8062370: Various minor code improvements
goetz
parents: 27458
diff changeset
   321
    }
23522
217a6a90aad3 8038201: Clean up misleading usage of malloc() in init_system_properties_values()
goetz
parents: 23479
diff changeset
   322
    pslash = strrchr(buf, '/');
217a6a90aad3 8038201: Clean up misleading usage of malloc() in init_system_properties_values()
goetz
parents: 23479
diff changeset
   323
    if (pslash != NULL) {
217a6a90aad3 8038201: Clean up misleading usage of malloc() in init_system_properties_values()
goetz
parents: 23479
diff changeset
   324
      *pslash = '\0';            // Get rid of /{client|server|hotspot}.
217a6a90aad3 8038201: Clean up misleading usage of malloc() in init_system_properties_values()
goetz
parents: 23479
diff changeset
   325
    }
217a6a90aad3 8038201: Clean up misleading usage of malloc() in init_system_properties_values()
goetz
parents: 23479
diff changeset
   326
    Arguments::set_dll_dir(buf);
217a6a90aad3 8038201: Clean up misleading usage of malloc() in init_system_properties_values()
goetz
parents: 23479
diff changeset
   327
217a6a90aad3 8038201: Clean up misleading usage of malloc() in init_system_properties_values()
goetz
parents: 23479
diff changeset
   328
    if (pslash != NULL) {
217a6a90aad3 8038201: Clean up misleading usage of malloc() in init_system_properties_values()
goetz
parents: 23479
diff changeset
   329
      pslash = strrchr(buf, '/');
217a6a90aad3 8038201: Clean up misleading usage of malloc() in init_system_properties_values()
goetz
parents: 23479
diff changeset
   330
      if (pslash != NULL) {
217a6a90aad3 8038201: Clean up misleading usage of malloc() in init_system_properties_values()
goetz
parents: 23479
diff changeset
   331
        *pslash = '\0';          // Get rid of /<arch>.
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
   332
        pslash = strrchr(buf, '/');
489c9b5090e2 Initial load
duke
parents:
diff changeset
   333
        if (pslash != NULL) {
23522
217a6a90aad3 8038201: Clean up misleading usage of malloc() in init_system_properties_values()
goetz
parents: 23479
diff changeset
   334
          *pslash = '\0';        // Get rid of /lib.
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
   335
        }
23522
217a6a90aad3 8038201: Clean up misleading usage of malloc() in init_system_properties_values()
goetz
parents: 23479
diff changeset
   336
      }
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
   337
    }
23522
217a6a90aad3 8038201: Clean up misleading usage of malloc() in init_system_properties_values()
goetz
parents: 23479
diff changeset
   338
    Arguments::set_java_home(buf);
217a6a90aad3 8038201: Clean up misleading usage of malloc() in init_system_properties_values()
goetz
parents: 23479
diff changeset
   339
    set_boot_path('/', ':');
217a6a90aad3 8038201: Clean up misleading usage of malloc() in init_system_properties_values()
goetz
parents: 23479
diff changeset
   340
  }
217a6a90aad3 8038201: Clean up misleading usage of malloc() in init_system_properties_values()
goetz
parents: 23479
diff changeset
   341
217a6a90aad3 8038201: Clean up misleading usage of malloc() in init_system_properties_values()
goetz
parents: 23479
diff changeset
   342
  // Where to look for native libraries.
217a6a90aad3 8038201: Clean up misleading usage of malloc() in init_system_properties_values()
goetz
parents: 23479
diff changeset
   343
  //
217a6a90aad3 8038201: Clean up misleading usage of malloc() in init_system_properties_values()
goetz
parents: 23479
diff changeset
   344
  // Note: Due to a legacy implementation, most of the library path
217a6a90aad3 8038201: Clean up misleading usage of malloc() in init_system_properties_values()
goetz
parents: 23479
diff changeset
   345
  // is set in the launcher. This was to accomodate linking restrictions
217a6a90aad3 8038201: Clean up misleading usage of malloc() in init_system_properties_values()
goetz
parents: 23479
diff changeset
   346
  // on legacy Linux implementations (which are no longer supported).
217a6a90aad3 8038201: Clean up misleading usage of malloc() in init_system_properties_values()
goetz
parents: 23479
diff changeset
   347
  // Eventually, all the library path setting will be done here.
217a6a90aad3 8038201: Clean up misleading usage of malloc() in init_system_properties_values()
goetz
parents: 23479
diff changeset
   348
  //
217a6a90aad3 8038201: Clean up misleading usage of malloc() in init_system_properties_values()
goetz
parents: 23479
diff changeset
   349
  // However, to prevent the proliferation of improperly built native
217a6a90aad3 8038201: Clean up misleading usage of malloc() in init_system_properties_values()
goetz
parents: 23479
diff changeset
   350
  // libraries, the new path component /usr/java/packages is added here.
217a6a90aad3 8038201: Clean up misleading usage of malloc() in init_system_properties_values()
goetz
parents: 23479
diff changeset
   351
  // Eventually, all the library path setting will be done here.
217a6a90aad3 8038201: Clean up misleading usage of malloc() in init_system_properties_values()
goetz
parents: 23479
diff changeset
   352
  {
217a6a90aad3 8038201: Clean up misleading usage of malloc() in init_system_properties_values()
goetz
parents: 23479
diff changeset
   353
    // Get the user setting of LD_LIBRARY_PATH, and prepended it. It
217a6a90aad3 8038201: Clean up misleading usage of malloc() in init_system_properties_values()
goetz
parents: 23479
diff changeset
   354
    // should always exist (until the legacy problem cited above is
217a6a90aad3 8038201: Clean up misleading usage of malloc() in init_system_properties_values()
goetz
parents: 23479
diff changeset
   355
    // addressed).
217a6a90aad3 8038201: Clean up misleading usage of malloc() in init_system_properties_values()
goetz
parents: 23479
diff changeset
   356
    const char *v = ::getenv("LD_LIBRARY_PATH");
217a6a90aad3 8038201: Clean up misleading usage of malloc() in init_system_properties_values()
goetz
parents: 23479
diff changeset
   357
    const char *v_colon = ":";
217a6a90aad3 8038201: Clean up misleading usage of malloc() in init_system_properties_values()
goetz
parents: 23479
diff changeset
   358
    if (v == NULL) { v = ""; v_colon = ""; }
217a6a90aad3 8038201: Clean up misleading usage of malloc() in init_system_properties_values()
goetz
parents: 23479
diff changeset
   359
    // That's +1 for the colon and +1 for the trailing '\0'.
217a6a90aad3 8038201: Clean up misleading usage of malloc() in init_system_properties_values()
goetz
parents: 23479
diff changeset
   360
    char *ld_library_path = (char *)NEW_C_HEAP_ARRAY(char,
217a6a90aad3 8038201: Clean up misleading usage of malloc() in init_system_properties_values()
goetz
parents: 23479
diff changeset
   361
                                                     strlen(v) + 1 +
217a6a90aad3 8038201: Clean up misleading usage of malloc() in init_system_properties_values()
goetz
parents: 23479
diff changeset
   362
                                                     sizeof(SYS_EXT_DIR) + sizeof("/lib/") + strlen(cpu_arch) + sizeof(DEFAULT_LIBPATH) + 1,
217a6a90aad3 8038201: Clean up misleading usage of malloc() in init_system_properties_values()
goetz
parents: 23479
diff changeset
   363
                                                     mtInternal);
217a6a90aad3 8038201: Clean up misleading usage of malloc() in init_system_properties_values()
goetz
parents: 23479
diff changeset
   364
    sprintf(ld_library_path, "%s%s" SYS_EXT_DIR "/lib/%s:" DEFAULT_LIBPATH, v, v_colon, cpu_arch);
217a6a90aad3 8038201: Clean up misleading usage of malloc() in init_system_properties_values()
goetz
parents: 23479
diff changeset
   365
    Arguments::set_library_path(ld_library_path);
27880
afb974a04396 8060074: os::free() takes MemoryTrackingLevel but doesn't need it
coleenp
parents: 27474
diff changeset
   366
    FREE_C_HEAP_ARRAY(char, ld_library_path);
23522
217a6a90aad3 8038201: Clean up misleading usage of malloc() in init_system_properties_values()
goetz
parents: 23479
diff changeset
   367
  }
217a6a90aad3 8038201: Clean up misleading usage of malloc() in init_system_properties_values()
goetz
parents: 23479
diff changeset
   368
217a6a90aad3 8038201: Clean up misleading usage of malloc() in init_system_properties_values()
goetz
parents: 23479
diff changeset
   369
  // Extensions directories.
217a6a90aad3 8038201: Clean up misleading usage of malloc() in init_system_properties_values()
goetz
parents: 23479
diff changeset
   370
  sprintf(buf, "%s" EXTENSIONS_DIR ":" SYS_EXT_DIR EXTENSIONS_DIR, Arguments::get_java_home());
217a6a90aad3 8038201: Clean up misleading usage of malloc() in init_system_properties_values()
goetz
parents: 23479
diff changeset
   371
  Arguments::set_ext_dirs(buf);
217a6a90aad3 8038201: Clean up misleading usage of malloc() in init_system_properties_values()
goetz
parents: 23479
diff changeset
   372
27880
afb974a04396 8060074: os::free() takes MemoryTrackingLevel but doesn't need it
coleenp
parents: 27474
diff changeset
   373
  FREE_C_HEAP_ARRAY(char, buf);
23522
217a6a90aad3 8038201: Clean up misleading usage of malloc() in init_system_properties_values()
goetz
parents: 23479
diff changeset
   374
217a6a90aad3 8038201: Clean up misleading usage of malloc() in init_system_properties_values()
goetz
parents: 23479
diff changeset
   375
#undef DEFAULT_LIBPATH
217a6a90aad3 8038201: Clean up misleading usage of malloc() in init_system_properties_values()
goetz
parents: 23479
diff changeset
   376
#undef SYS_EXT_DIR
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
   377
#undef EXTENSIONS_DIR
489c9b5090e2 Initial load
duke
parents:
diff changeset
   378
}
489c9b5090e2 Initial load
duke
parents:
diff changeset
   379
489c9b5090e2 Initial load
duke
parents:
diff changeset
   380
////////////////////////////////////////////////////////////////////////////////
489c9b5090e2 Initial load
duke
parents:
diff changeset
   381
// breakpoint support
489c9b5090e2 Initial load
duke
parents:
diff changeset
   382
489c9b5090e2 Initial load
duke
parents:
diff changeset
   383
void os::breakpoint() {
489c9b5090e2 Initial load
duke
parents:
diff changeset
   384
  BREAKPOINT;
489c9b5090e2 Initial load
duke
parents:
diff changeset
   385
}
489c9b5090e2 Initial load
duke
parents:
diff changeset
   386
489c9b5090e2 Initial load
duke
parents:
diff changeset
   387
extern "C" void breakpoint() {
489c9b5090e2 Initial load
duke
parents:
diff changeset
   388
  // use debugger to set breakpoint here
489c9b5090e2 Initial load
duke
parents:
diff changeset
   389
}
489c9b5090e2 Initial load
duke
parents:
diff changeset
   390
489c9b5090e2 Initial load
duke
parents:
diff changeset
   391
////////////////////////////////////////////////////////////////////////////////
489c9b5090e2 Initial load
duke
parents:
diff changeset
   392
// signal support
489c9b5090e2 Initial load
duke
parents:
diff changeset
   393
489c9b5090e2 Initial load
duke
parents:
diff changeset
   394
debug_only(static bool signal_sets_initialized = false);
489c9b5090e2 Initial load
duke
parents:
diff changeset
   395
static sigset_t unblocked_sigs, vm_sigs, allowdebug_blocked_sigs;
489c9b5090e2 Initial load
duke
parents:
diff changeset
   396
489c9b5090e2 Initial load
duke
parents:
diff changeset
   397
bool os::Linux::is_sig_ignored(int sig) {
26683
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
   398
  struct sigaction oact;
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
   399
  sigaction(sig, (struct sigaction*)NULL, &oact);
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
   400
  void* ohlr = oact.sa_sigaction ? CAST_FROM_FN_PTR(void*,  oact.sa_sigaction)
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
   401
                                 : CAST_FROM_FN_PTR(void*,  oact.sa_handler);
26684
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
   402
  if (ohlr == CAST_FROM_FN_PTR(void*, SIG_IGN)) {
26683
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
   403
    return true;
26684
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
   404
  } else {
26683
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
   405
    return false;
26684
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
   406
  }
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
   407
}
489c9b5090e2 Initial load
duke
parents:
diff changeset
   408
489c9b5090e2 Initial load
duke
parents:
diff changeset
   409
void os::Linux::signal_sets_init() {
489c9b5090e2 Initial load
duke
parents:
diff changeset
   410
  // Should also have an assertion stating we are still single-threaded.
489c9b5090e2 Initial load
duke
parents:
diff changeset
   411
  assert(!signal_sets_initialized, "Already initialized");
489c9b5090e2 Initial load
duke
parents:
diff changeset
   412
  // Fill in signals that are necessarily unblocked for all threads in
489c9b5090e2 Initial load
duke
parents:
diff changeset
   413
  // the VM. Currently, we unblock the following signals:
489c9b5090e2 Initial load
duke
parents:
diff changeset
   414
  // SHUTDOWN{1,2,3}_SIGNAL: for shutdown hooks support (unless over-ridden
489c9b5090e2 Initial load
duke
parents:
diff changeset
   415
  //                         by -Xrs (=ReduceSignalUsage));
489c9b5090e2 Initial load
duke
parents:
diff changeset
   416
  // BREAK_SIGNAL which is unblocked only by the VM thread and blocked by all
489c9b5090e2 Initial load
duke
parents:
diff changeset
   417
  // other threads. The "ReduceSignalUsage" boolean tells us not to alter
489c9b5090e2 Initial load
duke
parents:
diff changeset
   418
  // the dispositions or masks wrt these signals.
489c9b5090e2 Initial load
duke
parents:
diff changeset
   419
  // Programs embedding the VM that want to use the above signals for their
489c9b5090e2 Initial load
duke
parents:
diff changeset
   420
  // own purposes must, at this time, use the "-Xrs" option to prevent
489c9b5090e2 Initial load
duke
parents:
diff changeset
   421
  // interference with shutdown hooks and BREAK_SIGNAL thread dumping.
489c9b5090e2 Initial load
duke
parents:
diff changeset
   422
  // (See bug 4345157, and other related bugs).
489c9b5090e2 Initial load
duke
parents:
diff changeset
   423
  // In reality, though, unblocking these signals is really a nop, since
489c9b5090e2 Initial load
duke
parents:
diff changeset
   424
  // these signals are not blocked by default.
489c9b5090e2 Initial load
duke
parents:
diff changeset
   425
  sigemptyset(&unblocked_sigs);
489c9b5090e2 Initial load
duke
parents:
diff changeset
   426
  sigemptyset(&allowdebug_blocked_sigs);
489c9b5090e2 Initial load
duke
parents:
diff changeset
   427
  sigaddset(&unblocked_sigs, SIGILL);
489c9b5090e2 Initial load
duke
parents:
diff changeset
   428
  sigaddset(&unblocked_sigs, SIGSEGV);
489c9b5090e2 Initial load
duke
parents:
diff changeset
   429
  sigaddset(&unblocked_sigs, SIGBUS);
489c9b5090e2 Initial load
duke
parents:
diff changeset
   430
  sigaddset(&unblocked_sigs, SIGFPE);
22848
c1a044cf0c07 8028470: PPC64 (part 214): linux: extend signal handler to catch SIGTRAP on ppc64.
goetz
parents: 22838
diff changeset
   431
#if defined(PPC64)
c1a044cf0c07 8028470: PPC64 (part 214): linux: extend signal handler to catch SIGTRAP on ppc64.
goetz
parents: 22838
diff changeset
   432
  sigaddset(&unblocked_sigs, SIGTRAP);
c1a044cf0c07 8028470: PPC64 (part 214): linux: extend signal handler to catch SIGTRAP on ppc64.
goetz
parents: 22838
diff changeset
   433
#endif
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
   434
  sigaddset(&unblocked_sigs, SR_signum);
489c9b5090e2 Initial load
duke
parents:
diff changeset
   435
489c9b5090e2 Initial load
duke
parents:
diff changeset
   436
  if (!ReduceSignalUsage) {
26683
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
   437
    if (!os::Linux::is_sig_ignored(SHUTDOWN1_SIGNAL)) {
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
   438
      sigaddset(&unblocked_sigs, SHUTDOWN1_SIGNAL);
489c9b5090e2 Initial load
duke
parents:
diff changeset
   439
      sigaddset(&allowdebug_blocked_sigs, SHUTDOWN1_SIGNAL);
26683
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
   440
    }
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
   441
    if (!os::Linux::is_sig_ignored(SHUTDOWN2_SIGNAL)) {
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
   442
      sigaddset(&unblocked_sigs, SHUTDOWN2_SIGNAL);
489c9b5090e2 Initial load
duke
parents:
diff changeset
   443
      sigaddset(&allowdebug_blocked_sigs, SHUTDOWN2_SIGNAL);
26683
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
   444
    }
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
   445
    if (!os::Linux::is_sig_ignored(SHUTDOWN3_SIGNAL)) {
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
   446
      sigaddset(&unblocked_sigs, SHUTDOWN3_SIGNAL);
489c9b5090e2 Initial load
duke
parents:
diff changeset
   447
      sigaddset(&allowdebug_blocked_sigs, SHUTDOWN3_SIGNAL);
26683
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
   448
    }
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
   449
  }
489c9b5090e2 Initial load
duke
parents:
diff changeset
   450
  // Fill in signals that are blocked by all but the VM thread.
489c9b5090e2 Initial load
duke
parents:
diff changeset
   451
  sigemptyset(&vm_sigs);
26684
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
   452
  if (!ReduceSignalUsage) {
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
   453
    sigaddset(&vm_sigs, BREAK_SIGNAL);
26684
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
   454
  }
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
   455
  debug_only(signal_sets_initialized = true);
489c9b5090e2 Initial load
duke
parents:
diff changeset
   456
489c9b5090e2 Initial load
duke
parents:
diff changeset
   457
}
489c9b5090e2 Initial load
duke
parents:
diff changeset
   458
489c9b5090e2 Initial load
duke
parents:
diff changeset
   459
// These are signals that are unblocked while a thread is running Java.
489c9b5090e2 Initial load
duke
parents:
diff changeset
   460
// (For some reason, they get blocked by default.)
489c9b5090e2 Initial load
duke
parents:
diff changeset
   461
sigset_t* os::Linux::unblocked_signals() {
489c9b5090e2 Initial load
duke
parents:
diff changeset
   462
  assert(signal_sets_initialized, "Not initialized");
489c9b5090e2 Initial load
duke
parents:
diff changeset
   463
  return &unblocked_sigs;
489c9b5090e2 Initial load
duke
parents:
diff changeset
   464
}
489c9b5090e2 Initial load
duke
parents:
diff changeset
   465
489c9b5090e2 Initial load
duke
parents:
diff changeset
   466
// These are the signals that are blocked while a (non-VM) thread is
489c9b5090e2 Initial load
duke
parents:
diff changeset
   467
// running Java. Only the VM thread handles these signals.
489c9b5090e2 Initial load
duke
parents:
diff changeset
   468
sigset_t* os::Linux::vm_signals() {
489c9b5090e2 Initial load
duke
parents:
diff changeset
   469
  assert(signal_sets_initialized, "Not initialized");
489c9b5090e2 Initial load
duke
parents:
diff changeset
   470
  return &vm_sigs;
489c9b5090e2 Initial load
duke
parents:
diff changeset
   471
}
489c9b5090e2 Initial load
duke
parents:
diff changeset
   472
489c9b5090e2 Initial load
duke
parents:
diff changeset
   473
// These are signals that are blocked during cond_wait to allow debugger in
489c9b5090e2 Initial load
duke
parents:
diff changeset
   474
sigset_t* os::Linux::allowdebug_blocked_signals() {
489c9b5090e2 Initial load
duke
parents:
diff changeset
   475
  assert(signal_sets_initialized, "Not initialized");
489c9b5090e2 Initial load
duke
parents:
diff changeset
   476
  return &allowdebug_blocked_sigs;
489c9b5090e2 Initial load
duke
parents:
diff changeset
   477
}
489c9b5090e2 Initial load
duke
parents:
diff changeset
   478
489c9b5090e2 Initial load
duke
parents:
diff changeset
   479
void os::Linux::hotspot_sigmask(Thread* thread) {
489c9b5090e2 Initial load
duke
parents:
diff changeset
   480
489c9b5090e2 Initial load
duke
parents:
diff changeset
   481
  //Save caller's signal mask before setting VM signal mask
489c9b5090e2 Initial load
duke
parents:
diff changeset
   482
  sigset_t caller_sigmask;
489c9b5090e2 Initial load
duke
parents:
diff changeset
   483
  pthread_sigmask(SIG_BLOCK, NULL, &caller_sigmask);
489c9b5090e2 Initial load
duke
parents:
diff changeset
   484
489c9b5090e2 Initial load
duke
parents:
diff changeset
   485
  OSThread* osthread = thread->osthread();
489c9b5090e2 Initial load
duke
parents:
diff changeset
   486
  osthread->set_caller_sigmask(caller_sigmask);
489c9b5090e2 Initial load
duke
parents:
diff changeset
   487
489c9b5090e2 Initial load
duke
parents:
diff changeset
   488
  pthread_sigmask(SIG_UNBLOCK, os::Linux::unblocked_signals(), NULL);
489c9b5090e2 Initial load
duke
parents:
diff changeset
   489
489c9b5090e2 Initial load
duke
parents:
diff changeset
   490
  if (!ReduceSignalUsage) {
489c9b5090e2 Initial load
duke
parents:
diff changeset
   491
    if (thread->is_VM_thread()) {
489c9b5090e2 Initial load
duke
parents:
diff changeset
   492
      // Only the VM thread handles BREAK_SIGNAL ...
489c9b5090e2 Initial load
duke
parents:
diff changeset
   493
      pthread_sigmask(SIG_UNBLOCK, vm_signals(), NULL);
489c9b5090e2 Initial load
duke
parents:
diff changeset
   494
    } else {
489c9b5090e2 Initial load
duke
parents:
diff changeset
   495
      // ... all other threads block BREAK_SIGNAL
489c9b5090e2 Initial load
duke
parents:
diff changeset
   496
      pthread_sigmask(SIG_BLOCK, vm_signals(), NULL);
489c9b5090e2 Initial load
duke
parents:
diff changeset
   497
    }
489c9b5090e2 Initial load
duke
parents:
diff changeset
   498
  }
489c9b5090e2 Initial load
duke
parents:
diff changeset
   499
}
489c9b5090e2 Initial load
duke
parents:
diff changeset
   500
489c9b5090e2 Initial load
duke
parents:
diff changeset
   501
//////////////////////////////////////////////////////////////////////////////
489c9b5090e2 Initial load
duke
parents:
diff changeset
   502
// detecting pthread library
489c9b5090e2 Initial load
duke
parents:
diff changeset
   503
489c9b5090e2 Initial load
duke
parents:
diff changeset
   504
void os::Linux::libpthread_init() {
489c9b5090e2 Initial load
duke
parents:
diff changeset
   505
  // Save glibc and pthread version strings. Note that _CS_GNU_LIBC_VERSION
489c9b5090e2 Initial load
duke
parents:
diff changeset
   506
  // and _CS_GNU_LIBPTHREAD_VERSION are supported in glibc >= 2.3.2. Use a
489c9b5090e2 Initial load
duke
parents:
diff changeset
   507
  // generic name for earlier versions.
489c9b5090e2 Initial load
duke
parents:
diff changeset
   508
  // Define macros here so we can build HotSpot on old systems.
26684
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
   509
#ifndef _CS_GNU_LIBC_VERSION
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
   510
  #define _CS_GNU_LIBC_VERSION 2
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
   511
#endif
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
   512
#ifndef _CS_GNU_LIBPTHREAD_VERSION
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
   513
  #define _CS_GNU_LIBPTHREAD_VERSION 3
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
   514
#endif
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
   515
489c9b5090e2 Initial load
duke
parents:
diff changeset
   516
  size_t n = confstr(_CS_GNU_LIBC_VERSION, NULL, 0);
489c9b5090e2 Initial load
duke
parents:
diff changeset
   517
  if (n > 0) {
26683
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
   518
    char *str = (char *)malloc(n, mtInternal);
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
   519
    confstr(_CS_GNU_LIBC_VERSION, str, n);
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
   520
    os::Linux::set_glibc_version(str);
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
   521
  } else {
26683
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
   522
    // _CS_GNU_LIBC_VERSION is not supported, try gnu_get_libc_version()
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
   523
    static char _gnu_libc_version[32];
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
   524
    jio_snprintf(_gnu_libc_version, sizeof(_gnu_libc_version),
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
   525
                 "glibc %s %s", gnu_get_libc_version(), gnu_get_libc_release());
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
   526
    os::Linux::set_glibc_version(_gnu_libc_version);
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
   527
  }
489c9b5090e2 Initial load
duke
parents:
diff changeset
   528
489c9b5090e2 Initial load
duke
parents:
diff changeset
   529
  n = confstr(_CS_GNU_LIBPTHREAD_VERSION, NULL, 0);
489c9b5090e2 Initial load
duke
parents:
diff changeset
   530
  if (n > 0) {
26683
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
   531
    char *str = (char *)malloc(n, mtInternal);
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
   532
    confstr(_CS_GNU_LIBPTHREAD_VERSION, str, n);
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
   533
    // Vanilla RH-9 (glibc 2.3.2) has a bug that confstr() always tells
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
   534
    // us "NPTL-0.29" even we are running with LinuxThreads. Check if this
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
   535
    // is the case. LinuxThreads has a hard limit on max number of threads.
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
   536
    // So sysconf(_SC_THREAD_THREADS_MAX) will return a positive value.
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
   537
    // On the other hand, NPTL does not have such a limit, sysconf()
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
   538
    // will return -1 and errno is not changed. Check if it is really NPTL.
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
   539
    if (strcmp(os::Linux::glibc_version(), "glibc 2.3.2") == 0 &&
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
   540
        strstr(str, "NPTL") &&
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
   541
        sysconf(_SC_THREAD_THREADS_MAX) > 0) {
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
   542
      free(str);
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
   543
      os::Linux::set_libpthread_version("linuxthreads");
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
   544
    } else {
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
   545
      os::Linux::set_libpthread_version(str);
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
   546
    }
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
   547
  } else {
745
47129a5cacd3 6681796: hotspot build failure on gcc 4.2.x (ubuntu 8.04) w/ openjdk 6
xlu
parents: 388
diff changeset
   548
    // glibc before 2.3.2 only has LinuxThreads.
47129a5cacd3 6681796: hotspot build failure on gcc 4.2.x (ubuntu 8.04) w/ openjdk 6
xlu
parents: 388
diff changeset
   549
    os::Linux::set_libpthread_version("linuxthreads");
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
   550
  }
489c9b5090e2 Initial load
duke
parents:
diff changeset
   551
489c9b5090e2 Initial load
duke
parents:
diff changeset
   552
  if (strstr(libpthread_version(), "NPTL")) {
26683
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
   553
    os::Linux::set_is_NPTL();
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
   554
  } else {
26683
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
   555
    os::Linux::set_is_LinuxThreads();
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
   556
  }
489c9b5090e2 Initial load
duke
parents:
diff changeset
   557
489c9b5090e2 Initial load
duke
parents:
diff changeset
   558
  // LinuxThreads have two flavors: floating-stack mode, which allows variable
489c9b5090e2 Initial load
duke
parents:
diff changeset
   559
  // stack size; and fixed-stack mode. NPTL is always floating-stack.
489c9b5090e2 Initial load
duke
parents:
diff changeset
   560
  if (os::Linux::is_NPTL() || os::Linux::supports_variable_stack_size()) {
26683
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
   561
    os::Linux::set_is_floating_stack();
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
   562
  }
489c9b5090e2 Initial load
duke
parents:
diff changeset
   563
}
489c9b5090e2 Initial load
duke
parents:
diff changeset
   564
489c9b5090e2 Initial load
duke
parents:
diff changeset
   565
/////////////////////////////////////////////////////////////////////////////
489c9b5090e2 Initial load
duke
parents:
diff changeset
   566
// thread stack
489c9b5090e2 Initial load
duke
parents:
diff changeset
   567
489c9b5090e2 Initial load
duke
parents:
diff changeset
   568
// Force Linux kernel to expand current thread stack. If "bottom" is close
489c9b5090e2 Initial load
duke
parents:
diff changeset
   569
// to the stack guard, caller should block all signals.
489c9b5090e2 Initial load
duke
parents:
diff changeset
   570
//
489c9b5090e2 Initial load
duke
parents:
diff changeset
   571
// MAP_GROWSDOWN:
489c9b5090e2 Initial load
duke
parents:
diff changeset
   572
//   A special mmap() flag that is used to implement thread stacks. It tells
489c9b5090e2 Initial load
duke
parents:
diff changeset
   573
//   kernel that the memory region should extend downwards when needed. This
489c9b5090e2 Initial load
duke
parents:
diff changeset
   574
//   allows early versions of LinuxThreads to only mmap the first few pages
489c9b5090e2 Initial load
duke
parents:
diff changeset
   575
//   when creating a new thread. Linux kernel will automatically expand thread
489c9b5090e2 Initial load
duke
parents:
diff changeset
   576
//   stack as needed (on page faults).
489c9b5090e2 Initial load
duke
parents:
diff changeset
   577
//
489c9b5090e2 Initial load
duke
parents:
diff changeset
   578
//   However, because the memory region of a MAP_GROWSDOWN stack can grow on
489c9b5090e2 Initial load
duke
parents:
diff changeset
   579
//   demand, if a page fault happens outside an already mapped MAP_GROWSDOWN
489c9b5090e2 Initial load
duke
parents:
diff changeset
   580
//   region, it's hard to tell if the fault is due to a legitimate stack
489c9b5090e2 Initial load
duke
parents:
diff changeset
   581
//   access or because of reading/writing non-exist memory (e.g. buffer
489c9b5090e2 Initial load
duke
parents:
diff changeset
   582
//   overrun). As a rule, if the fault happens below current stack pointer,
489c9b5090e2 Initial load
duke
parents:
diff changeset
   583
//   Linux kernel does not expand stack, instead a SIGSEGV is sent to the
489c9b5090e2 Initial load
duke
parents:
diff changeset
   584
//   application (see Linux kernel fault.c).
489c9b5090e2 Initial load
duke
parents:
diff changeset
   585
//
489c9b5090e2 Initial load
duke
parents:
diff changeset
   586
//   This Linux feature can cause SIGSEGV when VM bangs thread stack for
489c9b5090e2 Initial load
duke
parents:
diff changeset
   587
//   stack overflow detection.
489c9b5090e2 Initial load
duke
parents:
diff changeset
   588
//
489c9b5090e2 Initial load
duke
parents:
diff changeset
   589
//   Newer version of LinuxThreads (since glibc-2.2, or, RH-7.x) and NPTL do
489c9b5090e2 Initial load
duke
parents:
diff changeset
   590
//   not use this flag. However, the stack of initial thread is not created
489c9b5090e2 Initial load
duke
parents:
diff changeset
   591
//   by pthread, it is still MAP_GROWSDOWN. Also it's possible (though
489c9b5090e2 Initial load
duke
parents:
diff changeset
   592
//   unlikely) that user code can create a thread with MAP_GROWSDOWN stack
489c9b5090e2 Initial load
duke
parents:
diff changeset
   593
//   and then attach the thread to JVM.
489c9b5090e2 Initial load
duke
parents:
diff changeset
   594
//
489c9b5090e2 Initial load
duke
parents:
diff changeset
   595
// To get around the problem and allow stack banging on Linux, we need to
489c9b5090e2 Initial load
duke
parents:
diff changeset
   596
// manually expand thread stack after receiving the SIGSEGV.
489c9b5090e2 Initial load
duke
parents:
diff changeset
   597
//
489c9b5090e2 Initial load
duke
parents:
diff changeset
   598
// There are two ways to expand thread stack to address "bottom", we used
489c9b5090e2 Initial load
duke
parents:
diff changeset
   599
// both of them in JVM before 1.5:
489c9b5090e2 Initial load
duke
parents:
diff changeset
   600
//   1. adjust stack pointer first so that it is below "bottom", and then
489c9b5090e2 Initial load
duke
parents:
diff changeset
   601
//      touch "bottom"
489c9b5090e2 Initial load
duke
parents:
diff changeset
   602
//   2. mmap() the page in question
489c9b5090e2 Initial load
duke
parents:
diff changeset
   603
//
489c9b5090e2 Initial load
duke
parents:
diff changeset
   604
// Now alternate signal stack is gone, it's harder to use 2. For instance,
489c9b5090e2 Initial load
duke
parents:
diff changeset
   605
// if current sp is already near the lower end of page 101, and we need to
489c9b5090e2 Initial load
duke
parents:
diff changeset
   606
// call mmap() to map page 100, it is possible that part of the mmap() frame
489c9b5090e2 Initial load
duke
parents:
diff changeset
   607
// will be placed in page 100. When page 100 is mapped, it is zero-filled.
489c9b5090e2 Initial load
duke
parents:
diff changeset
   608
// That will destroy the mmap() frame and cause VM to crash.
489c9b5090e2 Initial load
duke
parents:
diff changeset
   609
//
489c9b5090e2 Initial load
duke
parents:
diff changeset
   610
// The following code works by adjusting sp first, then accessing the "bottom"
489c9b5090e2 Initial load
duke
parents:
diff changeset
   611
// page to force a page fault. Linux kernel will then automatically expand the
489c9b5090e2 Initial load
duke
parents:
diff changeset
   612
// stack mapping.
489c9b5090e2 Initial load
duke
parents:
diff changeset
   613
//
489c9b5090e2 Initial load
duke
parents:
diff changeset
   614
// _expand_stack_to() assumes its frame size is less than page size, which
489c9b5090e2 Initial load
duke
parents:
diff changeset
   615
// should always be true if the function is not inlined.
489c9b5090e2 Initial load
duke
parents:
diff changeset
   616
489c9b5090e2 Initial load
duke
parents:
diff changeset
   617
#if __GNUC__ < 3    // gcc 2.x does not support noinline attribute
26684
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
   618
  #define NOINLINE
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
   619
#else
26684
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
   620
  #define NOINLINE __attribute__ ((noinline))
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
   621
#endif
489c9b5090e2 Initial load
duke
parents:
diff changeset
   622
489c9b5090e2 Initial load
duke
parents:
diff changeset
   623
static void _expand_stack_to(address bottom) NOINLINE;
489c9b5090e2 Initial load
duke
parents:
diff changeset
   624
489c9b5090e2 Initial load
duke
parents:
diff changeset
   625
static void _expand_stack_to(address bottom) {
489c9b5090e2 Initial load
duke
parents:
diff changeset
   626
  address sp;
489c9b5090e2 Initial load
duke
parents:
diff changeset
   627
  size_t size;
489c9b5090e2 Initial load
duke
parents:
diff changeset
   628
  volatile char *p;
489c9b5090e2 Initial load
duke
parents:
diff changeset
   629
489c9b5090e2 Initial load
duke
parents:
diff changeset
   630
  // Adjust bottom to point to the largest address within the same page, it
489c9b5090e2 Initial load
duke
parents:
diff changeset
   631
  // gives us a one-page buffer if alloca() allocates slightly more memory.
489c9b5090e2 Initial load
duke
parents:
diff changeset
   632
  bottom = (address)align_size_down((uintptr_t)bottom, os::Linux::page_size());
489c9b5090e2 Initial load
duke
parents:
diff changeset
   633
  bottom += os::Linux::page_size() - 1;
489c9b5090e2 Initial load
duke
parents:
diff changeset
   634
489c9b5090e2 Initial load
duke
parents:
diff changeset
   635
  // sp might be slightly above current stack pointer; if that's the case, we
489c9b5090e2 Initial load
duke
parents:
diff changeset
   636
  // will alloca() a little more space than necessary, which is OK. Don't use
489c9b5090e2 Initial load
duke
parents:
diff changeset
   637
  // os::current_stack_pointer(), as its result can be slightly below current
489c9b5090e2 Initial load
duke
parents:
diff changeset
   638
  // stack pointer, causing us to not alloca enough to reach "bottom".
489c9b5090e2 Initial load
duke
parents:
diff changeset
   639
  sp = (address)&sp;
489c9b5090e2 Initial load
duke
parents:
diff changeset
   640
489c9b5090e2 Initial load
duke
parents:
diff changeset
   641
  if (sp > bottom) {
489c9b5090e2 Initial load
duke
parents:
diff changeset
   642
    size = sp - bottom;
489c9b5090e2 Initial load
duke
parents:
diff changeset
   643
    p = (volatile char *)alloca(size);
489c9b5090e2 Initial load
duke
parents:
diff changeset
   644
    assert(p != NULL && p <= (volatile char *)bottom, "alloca problem?");
489c9b5090e2 Initial load
duke
parents:
diff changeset
   645
    p[0] = '\0';
489c9b5090e2 Initial load
duke
parents:
diff changeset
   646
  }
489c9b5090e2 Initial load
duke
parents:
diff changeset
   647
}
489c9b5090e2 Initial load
duke
parents:
diff changeset
   648
489c9b5090e2 Initial load
duke
parents:
diff changeset
   649
bool os::Linux::manually_expand_stack(JavaThread * t, address addr) {
489c9b5090e2 Initial load
duke
parents:
diff changeset
   650
  assert(t!=NULL, "just checking");
489c9b5090e2 Initial load
duke
parents:
diff changeset
   651
  assert(t->osthread()->expanding_stack(), "expand should be set");
489c9b5090e2 Initial load
duke
parents:
diff changeset
   652
  assert(t->stack_base() != NULL, "stack_base was not initialized");
489c9b5090e2 Initial load
duke
parents:
diff changeset
   653
489c9b5090e2 Initial load
duke
parents:
diff changeset
   654
  if (addr <  t->stack_base() && addr >= t->stack_yellow_zone_base()) {
489c9b5090e2 Initial load
duke
parents:
diff changeset
   655
    sigset_t mask_all, old_sigset;
489c9b5090e2 Initial load
duke
parents:
diff changeset
   656
    sigfillset(&mask_all);
489c9b5090e2 Initial load
duke
parents:
diff changeset
   657
    pthread_sigmask(SIG_SETMASK, &mask_all, &old_sigset);
489c9b5090e2 Initial load
duke
parents:
diff changeset
   658
    _expand_stack_to(addr);
489c9b5090e2 Initial load
duke
parents:
diff changeset
   659
    pthread_sigmask(SIG_SETMASK, &old_sigset, NULL);
489c9b5090e2 Initial load
duke
parents:
diff changeset
   660
    return true;
489c9b5090e2 Initial load
duke
parents:
diff changeset
   661
  }
489c9b5090e2 Initial load
duke
parents:
diff changeset
   662
  return false;
489c9b5090e2 Initial load
duke
parents:
diff changeset
   663
}
489c9b5090e2 Initial load
duke
parents:
diff changeset
   664
489c9b5090e2 Initial load
duke
parents:
diff changeset
   665
//////////////////////////////////////////////////////////////////////////////
489c9b5090e2 Initial load
duke
parents:
diff changeset
   666
// create new thread
489c9b5090e2 Initial load
duke
parents:
diff changeset
   667
489c9b5090e2 Initial load
duke
parents:
diff changeset
   668
static address highest_vm_reserved_address();
489c9b5090e2 Initial load
duke
parents:
diff changeset
   669
489c9b5090e2 Initial load
duke
parents:
diff changeset
   670
// check if it's safe to start a new thread
489c9b5090e2 Initial load
duke
parents:
diff changeset
   671
static bool _thread_safety_check(Thread* thread) {
489c9b5090e2 Initial load
duke
parents:
diff changeset
   672
  if (os::Linux::is_LinuxThreads() && !os::Linux::is_floating_stack()) {
489c9b5090e2 Initial load
duke
parents:
diff changeset
   673
    // Fixed stack LinuxThreads (SuSE Linux/x86, and some versions of Redhat)
489c9b5090e2 Initial load
duke
parents:
diff changeset
   674
    //   Heap is mmap'ed at lower end of memory space. Thread stacks are
489c9b5090e2 Initial load
duke
parents:
diff changeset
   675
    //   allocated (MAP_FIXED) from high address space. Every thread stack
489c9b5090e2 Initial load
duke
parents:
diff changeset
   676
    //   occupies a fixed size slot (usually 2Mbytes, but user can change
489c9b5090e2 Initial load
duke
parents:
diff changeset
   677
    //   it to other values if they rebuild LinuxThreads).
489c9b5090e2 Initial load
duke
parents:
diff changeset
   678
    //
489c9b5090e2 Initial load
duke
parents:
diff changeset
   679
    // Problem with MAP_FIXED is that mmap() can still succeed even part of
489c9b5090e2 Initial load
duke
parents:
diff changeset
   680
    // the memory region has already been mmap'ed. That means if we have too
489c9b5090e2 Initial load
duke
parents:
diff changeset
   681
    // many threads and/or very large heap, eventually thread stack will
489c9b5090e2 Initial load
duke
parents:
diff changeset
   682
    // collide with heap.
489c9b5090e2 Initial load
duke
parents:
diff changeset
   683
    //
489c9b5090e2 Initial load
duke
parents:
diff changeset
   684
    // Here we try to prevent heap/stack collision by comparing current
489c9b5090e2 Initial load
duke
parents:
diff changeset
   685
    // stack bottom with the highest address that has been mmap'ed by JVM
489c9b5090e2 Initial load
duke
parents:
diff changeset
   686
    // plus a safety margin for memory maps created by native code.
489c9b5090e2 Initial load
duke
parents:
diff changeset
   687
    //
489c9b5090e2 Initial load
duke
parents:
diff changeset
   688
    // This feature can be disabled by setting ThreadSafetyMargin to 0
489c9b5090e2 Initial load
duke
parents:
diff changeset
   689
    //
489c9b5090e2 Initial load
duke
parents:
diff changeset
   690
    if (ThreadSafetyMargin > 0) {
489c9b5090e2 Initial load
duke
parents:
diff changeset
   691
      address stack_bottom = os::current_stack_base() - os::current_stack_size();
489c9b5090e2 Initial load
duke
parents:
diff changeset
   692
489c9b5090e2 Initial load
duke
parents:
diff changeset
   693
      // not safe if our stack extends below the safety margin
489c9b5090e2 Initial load
duke
parents:
diff changeset
   694
      return stack_bottom - ThreadSafetyMargin >= highest_vm_reserved_address();
489c9b5090e2 Initial load
duke
parents:
diff changeset
   695
    } else {
489c9b5090e2 Initial load
duke
parents:
diff changeset
   696
      return true;
489c9b5090e2 Initial load
duke
parents:
diff changeset
   697
    }
489c9b5090e2 Initial load
duke
parents:
diff changeset
   698
  } else {
489c9b5090e2 Initial load
duke
parents:
diff changeset
   699
    // Floating stack LinuxThreads or NPTL:
489c9b5090e2 Initial load
duke
parents:
diff changeset
   700
    //   Unlike fixed stack LinuxThreads, thread stacks are not MAP_FIXED. When
489c9b5090e2 Initial load
duke
parents:
diff changeset
   701
    //   there's not enough space left, pthread_create() will fail. If we come
489c9b5090e2 Initial load
duke
parents:
diff changeset
   702
    //   here, that means enough space has been reserved for stack.
489c9b5090e2 Initial load
duke
parents:
diff changeset
   703
    return true;
489c9b5090e2 Initial load
duke
parents:
diff changeset
   704
  }
489c9b5090e2 Initial load
duke
parents:
diff changeset
   705
}
489c9b5090e2 Initial load
duke
parents:
diff changeset
   706
489c9b5090e2 Initial load
duke
parents:
diff changeset
   707
// Thread start routine for all newly created threads
489c9b5090e2 Initial load
duke
parents:
diff changeset
   708
static void *java_start(Thread *thread) {
489c9b5090e2 Initial load
duke
parents:
diff changeset
   709
  // Try to randomize the cache line index of hot stack frames.
489c9b5090e2 Initial load
duke
parents:
diff changeset
   710
  // This helps when threads of the same stack traces evict each other's
489c9b5090e2 Initial load
duke
parents:
diff changeset
   711
  // cache lines. The threads can be either from the same JVM instance, or
489c9b5090e2 Initial load
duke
parents:
diff changeset
   712
  // from different JVM instances. The benefit is especially true for
489c9b5090e2 Initial load
duke
parents:
diff changeset
   713
  // processors with hyperthreading technology.
489c9b5090e2 Initial load
duke
parents:
diff changeset
   714
  static int counter = 0;
489c9b5090e2 Initial load
duke
parents:
diff changeset
   715
  int pid = os::current_process_id();
489c9b5090e2 Initial load
duke
parents:
diff changeset
   716
  alloca(((pid ^ counter++) & 7) * 128);
489c9b5090e2 Initial load
duke
parents:
diff changeset
   717
489c9b5090e2 Initial load
duke
parents:
diff changeset
   718
  ThreadLocalStorage::set_thread(thread);
489c9b5090e2 Initial load
duke
parents:
diff changeset
   719
489c9b5090e2 Initial load
duke
parents:
diff changeset
   720
  OSThread* osthread = thread->osthread();
489c9b5090e2 Initial load
duke
parents:
diff changeset
   721
  Monitor* sync = osthread->startThread_lock();
489c9b5090e2 Initial load
duke
parents:
diff changeset
   722
489c9b5090e2 Initial load
duke
parents:
diff changeset
   723
  // non floating stack LinuxThreads needs extra check, see above
489c9b5090e2 Initial load
duke
parents:
diff changeset
   724
  if (!_thread_safety_check(thread)) {
489c9b5090e2 Initial load
duke
parents:
diff changeset
   725
    // notify parent thread
489c9b5090e2 Initial load
duke
parents:
diff changeset
   726
    MutexLockerEx ml(sync, Mutex::_no_safepoint_check_flag);
489c9b5090e2 Initial load
duke
parents:
diff changeset
   727
    osthread->set_state(ZOMBIE);
489c9b5090e2 Initial load
duke
parents:
diff changeset
   728
    sync->notify_all();
489c9b5090e2 Initial load
duke
parents:
diff changeset
   729
    return NULL;
489c9b5090e2 Initial load
duke
parents:
diff changeset
   730
  }
489c9b5090e2 Initial load
duke
parents:
diff changeset
   731
489c9b5090e2 Initial load
duke
parents:
diff changeset
   732
  // thread_id is kernel thread id (similar to Solaris LWP id)
489c9b5090e2 Initial load
duke
parents:
diff changeset
   733
  osthread->set_thread_id(os::Linux::gettid());
489c9b5090e2 Initial load
duke
parents:
diff changeset
   734
489c9b5090e2 Initial load
duke
parents:
diff changeset
   735
  if (UseNUMA) {
489c9b5090e2 Initial load
duke
parents:
diff changeset
   736
    int lgrp_id = os::numa_get_group_id();
489c9b5090e2 Initial load
duke
parents:
diff changeset
   737
    if (lgrp_id != -1) {
489c9b5090e2 Initial load
duke
parents:
diff changeset
   738
      thread->set_lgrp_id(lgrp_id);
489c9b5090e2 Initial load
duke
parents:
diff changeset
   739
    }
489c9b5090e2 Initial load
duke
parents:
diff changeset
   740
  }
489c9b5090e2 Initial load
duke
parents:
diff changeset
   741
  // initialize signal mask for this thread
489c9b5090e2 Initial load
duke
parents:
diff changeset
   742
  os::Linux::hotspot_sigmask(thread);
489c9b5090e2 Initial load
duke
parents:
diff changeset
   743
489c9b5090e2 Initial load
duke
parents:
diff changeset
   744
  // initialize floating point control register
489c9b5090e2 Initial load
duke
parents:
diff changeset
   745
  os::Linux::init_thread_fpu_state();
489c9b5090e2 Initial load
duke
parents:
diff changeset
   746
489c9b5090e2 Initial load
duke
parents:
diff changeset
   747
  // handshaking with parent thread
489c9b5090e2 Initial load
duke
parents:
diff changeset
   748
  {
489c9b5090e2 Initial load
duke
parents:
diff changeset
   749
    MutexLockerEx ml(sync, Mutex::_no_safepoint_check_flag);
489c9b5090e2 Initial load
duke
parents:
diff changeset
   750
489c9b5090e2 Initial load
duke
parents:
diff changeset
   751
    // notify parent thread
489c9b5090e2 Initial load
duke
parents:
diff changeset
   752
    osthread->set_state(INITIALIZED);
489c9b5090e2 Initial load
duke
parents:
diff changeset
   753
    sync->notify_all();
489c9b5090e2 Initial load
duke
parents:
diff changeset
   754
489c9b5090e2 Initial load
duke
parents:
diff changeset
   755
    // wait until os::start_thread()
489c9b5090e2 Initial load
duke
parents:
diff changeset
   756
    while (osthread->get_state() == INITIALIZED) {
489c9b5090e2 Initial load
duke
parents:
diff changeset
   757
      sync->wait(Mutex::_no_safepoint_check_flag);
489c9b5090e2 Initial load
duke
parents:
diff changeset
   758
    }
489c9b5090e2 Initial load
duke
parents:
diff changeset
   759
  }
489c9b5090e2 Initial load
duke
parents:
diff changeset
   760
489c9b5090e2 Initial load
duke
parents:
diff changeset
   761
  // call one more level start routine
489c9b5090e2 Initial load
duke
parents:
diff changeset
   762
  thread->run();
489c9b5090e2 Initial load
duke
parents:
diff changeset
   763
489c9b5090e2 Initial load
duke
parents:
diff changeset
   764
  return 0;
489c9b5090e2 Initial load
duke
parents:
diff changeset
   765
}
489c9b5090e2 Initial load
duke
parents:
diff changeset
   766
26684
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
   767
bool os::create_thread(Thread* thread, ThreadType thr_type,
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
   768
                       size_t stack_size) {
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
   769
  assert(thread->osthread() == NULL, "caller responsible");
489c9b5090e2 Initial load
duke
parents:
diff changeset
   770
489c9b5090e2 Initial load
duke
parents:
diff changeset
   771
  // Allocate the OSThread object
489c9b5090e2 Initial load
duke
parents:
diff changeset
   772
  OSThread* osthread = new OSThread(NULL, NULL);
489c9b5090e2 Initial load
duke
parents:
diff changeset
   773
  if (osthread == NULL) {
489c9b5090e2 Initial load
duke
parents:
diff changeset
   774
    return false;
489c9b5090e2 Initial load
duke
parents:
diff changeset
   775
  }
489c9b5090e2 Initial load
duke
parents:
diff changeset
   776
489c9b5090e2 Initial load
duke
parents:
diff changeset
   777
  // set the correct thread state
489c9b5090e2 Initial load
duke
parents:
diff changeset
   778
  osthread->set_thread_type(thr_type);
489c9b5090e2 Initial load
duke
parents:
diff changeset
   779
489c9b5090e2 Initial load
duke
parents:
diff changeset
   780
  // Initial state is ALLOCATED but not INITIALIZED
489c9b5090e2 Initial load
duke
parents:
diff changeset
   781
  osthread->set_state(ALLOCATED);
489c9b5090e2 Initial load
duke
parents:
diff changeset
   782
489c9b5090e2 Initial load
duke
parents:
diff changeset
   783
  thread->set_osthread(osthread);
489c9b5090e2 Initial load
duke
parents:
diff changeset
   784
489c9b5090e2 Initial load
duke
parents:
diff changeset
   785
  // init thread attributes
489c9b5090e2 Initial load
duke
parents:
diff changeset
   786
  pthread_attr_t attr;
489c9b5090e2 Initial load
duke
parents:
diff changeset
   787
  pthread_attr_init(&attr);
489c9b5090e2 Initial load
duke
parents:
diff changeset
   788
  pthread_attr_setdetachstate(&attr, PTHREAD_CREATE_DETACHED);
489c9b5090e2 Initial load
duke
parents:
diff changeset
   789
489c9b5090e2 Initial load
duke
parents:
diff changeset
   790
  // stack size
489c9b5090e2 Initial load
duke
parents:
diff changeset
   791
  if (os::Linux::supports_variable_stack_size()) {
489c9b5090e2 Initial load
duke
parents:
diff changeset
   792
    // calculate stack size if it's not specified by caller
489c9b5090e2 Initial load
duke
parents:
diff changeset
   793
    if (stack_size == 0) {
489c9b5090e2 Initial load
duke
parents:
diff changeset
   794
      stack_size = os::Linux::default_stack_size(thr_type);
489c9b5090e2 Initial load
duke
parents:
diff changeset
   795
489c9b5090e2 Initial load
duke
parents:
diff changeset
   796
      switch (thr_type) {
489c9b5090e2 Initial load
duke
parents:
diff changeset
   797
      case os::java_thread:
6964
6e45ffa3bccf 6983240: guarantee((Solaris::min_stack_allowed >= (StackYellowPages+StackRedPages...) wrong
coleenp
parents: 6962
diff changeset
   798
        // Java threads use ThreadStackSize which default value can be
6e45ffa3bccf 6983240: guarantee((Solaris::min_stack_allowed >= (StackYellowPages+StackRedPages...) wrong
coleenp
parents: 6962
diff changeset
   799
        // changed with the flag -Xss
25064
244218e6ec0a 8046758: cleanup non-indent white space issues prior to Contended Locking cleanup bucket
dcubed
parents: 24931
diff changeset
   800
        assert(JavaThread::stack_size_at_create() > 0, "this should be set");
6964
6e45ffa3bccf 6983240: guarantee((Solaris::min_stack_allowed >= (StackYellowPages+StackRedPages...) wrong
coleenp
parents: 6962
diff changeset
   801
        stack_size = JavaThread::stack_size_at_create();
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
   802
        break;
489c9b5090e2 Initial load
duke
parents:
diff changeset
   803
      case os::compiler_thread:
489c9b5090e2 Initial load
duke
parents:
diff changeset
   804
        if (CompilerThreadStackSize > 0) {
489c9b5090e2 Initial load
duke
parents:
diff changeset
   805
          stack_size = (size_t)(CompilerThreadStackSize * K);
489c9b5090e2 Initial load
duke
parents:
diff changeset
   806
          break;
489c9b5090e2 Initial load
duke
parents:
diff changeset
   807
        } // else fall through:
489c9b5090e2 Initial load
duke
parents:
diff changeset
   808
          // use VMThreadStackSize if CompilerThreadStackSize is not defined
489c9b5090e2 Initial load
duke
parents:
diff changeset
   809
      case os::vm_thread:
489c9b5090e2 Initial load
duke
parents:
diff changeset
   810
      case os::pgc_thread:
489c9b5090e2 Initial load
duke
parents:
diff changeset
   811
      case os::cgc_thread:
489c9b5090e2 Initial load
duke
parents:
diff changeset
   812
      case os::watcher_thread:
489c9b5090e2 Initial load
duke
parents:
diff changeset
   813
        if (VMThreadStackSize > 0) stack_size = (size_t)(VMThreadStackSize * K);
489c9b5090e2 Initial load
duke
parents:
diff changeset
   814
        break;
489c9b5090e2 Initial load
duke
parents:
diff changeset
   815
      }
489c9b5090e2 Initial load
duke
parents:
diff changeset
   816
    }
489c9b5090e2 Initial load
duke
parents:
diff changeset
   817
489c9b5090e2 Initial load
duke
parents:
diff changeset
   818
    stack_size = MAX2(stack_size, os::Linux::min_stack_allowed);
489c9b5090e2 Initial load
duke
parents:
diff changeset
   819
    pthread_attr_setstacksize(&attr, stack_size);
489c9b5090e2 Initial load
duke
parents:
diff changeset
   820
  } else {
489c9b5090e2 Initial load
duke
parents:
diff changeset
   821
    // let pthread_create() pick the default value.
489c9b5090e2 Initial load
duke
parents:
diff changeset
   822
  }
489c9b5090e2 Initial load
duke
parents:
diff changeset
   823
489c9b5090e2 Initial load
duke
parents:
diff changeset
   824
  // glibc guard page
489c9b5090e2 Initial load
duke
parents:
diff changeset
   825
  pthread_attr_setguardsize(&attr, os::Linux::default_guard_size(thr_type));
489c9b5090e2 Initial load
duke
parents:
diff changeset
   826
489c9b5090e2 Initial load
duke
parents:
diff changeset
   827
  ThreadState state;
489c9b5090e2 Initial load
duke
parents:
diff changeset
   828
489c9b5090e2 Initial load
duke
parents:
diff changeset
   829
  {
489c9b5090e2 Initial load
duke
parents:
diff changeset
   830
    // Serialize thread creation if we are running with fixed stack LinuxThreads
489c9b5090e2 Initial load
duke
parents:
diff changeset
   831
    bool lock = os::Linux::is_LinuxThreads() && !os::Linux::is_floating_stack();
489c9b5090e2 Initial load
duke
parents:
diff changeset
   832
    if (lock) {
489c9b5090e2 Initial load
duke
parents:
diff changeset
   833
      os::Linux::createThread_lock()->lock_without_safepoint_check();
489c9b5090e2 Initial load
duke
parents:
diff changeset
   834
    }
489c9b5090e2 Initial load
duke
parents:
diff changeset
   835
489c9b5090e2 Initial load
duke
parents:
diff changeset
   836
    pthread_t tid;
489c9b5090e2 Initial load
duke
parents:
diff changeset
   837
    int ret = pthread_create(&tid, &attr, (void* (*)(void*)) java_start, thread);
489c9b5090e2 Initial load
duke
parents:
diff changeset
   838
489c9b5090e2 Initial load
duke
parents:
diff changeset
   839
    pthread_attr_destroy(&attr);
489c9b5090e2 Initial load
duke
parents:
diff changeset
   840
489c9b5090e2 Initial load
duke
parents:
diff changeset
   841
    if (ret != 0) {
489c9b5090e2 Initial load
duke
parents:
diff changeset
   842
      if (PrintMiscellaneous && (Verbose || WizardMode)) {
489c9b5090e2 Initial load
duke
parents:
diff changeset
   843
        perror("pthread_create()");
489c9b5090e2 Initial load
duke
parents:
diff changeset
   844
      }
489c9b5090e2 Initial load
duke
parents:
diff changeset
   845
      // Need to clean up stuff we've allocated so far
489c9b5090e2 Initial load
duke
parents:
diff changeset
   846
      thread->set_osthread(NULL);
489c9b5090e2 Initial load
duke
parents:
diff changeset
   847
      delete osthread;
489c9b5090e2 Initial load
duke
parents:
diff changeset
   848
      if (lock) os::Linux::createThread_lock()->unlock();
489c9b5090e2 Initial load
duke
parents:
diff changeset
   849
      return false;
489c9b5090e2 Initial load
duke
parents:
diff changeset
   850
    }
489c9b5090e2 Initial load
duke
parents:
diff changeset
   851
489c9b5090e2 Initial load
duke
parents:
diff changeset
   852
    // Store pthread info into the OSThread
489c9b5090e2 Initial load
duke
parents:
diff changeset
   853
    osthread->set_pthread_id(tid);
489c9b5090e2 Initial load
duke
parents:
diff changeset
   854
489c9b5090e2 Initial load
duke
parents:
diff changeset
   855
    // Wait until child thread is either initialized or aborted
489c9b5090e2 Initial load
duke
parents:
diff changeset
   856
    {
489c9b5090e2 Initial load
duke
parents:
diff changeset
   857
      Monitor* sync_with_child = osthread->startThread_lock();
489c9b5090e2 Initial load
duke
parents:
diff changeset
   858
      MutexLockerEx ml(sync_with_child, Mutex::_no_safepoint_check_flag);
489c9b5090e2 Initial load
duke
parents:
diff changeset
   859
      while ((state = osthread->get_state()) == ALLOCATED) {
489c9b5090e2 Initial load
duke
parents:
diff changeset
   860
        sync_with_child->wait(Mutex::_no_safepoint_check_flag);
489c9b5090e2 Initial load
duke
parents:
diff changeset
   861
      }
489c9b5090e2 Initial load
duke
parents:
diff changeset
   862
    }
489c9b5090e2 Initial load
duke
parents:
diff changeset
   863
489c9b5090e2 Initial load
duke
parents:
diff changeset
   864
    if (lock) {
489c9b5090e2 Initial load
duke
parents:
diff changeset
   865
      os::Linux::createThread_lock()->unlock();
489c9b5090e2 Initial load
duke
parents:
diff changeset
   866
    }
489c9b5090e2 Initial load
duke
parents:
diff changeset
   867
  }
489c9b5090e2 Initial load
duke
parents:
diff changeset
   868
489c9b5090e2 Initial load
duke
parents:
diff changeset
   869
  // Aborted due to thread limit being reached
489c9b5090e2 Initial load
duke
parents:
diff changeset
   870
  if (state == ZOMBIE) {
26683
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
   871
    thread->set_osthread(NULL);
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
   872
    delete osthread;
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
   873
    return false;
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
   874
  }
489c9b5090e2 Initial load
duke
parents:
diff changeset
   875
489c9b5090e2 Initial load
duke
parents:
diff changeset
   876
  // The thread is returned suspended (in state INITIALIZED),
489c9b5090e2 Initial load
duke
parents:
diff changeset
   877
  // and is started higher up in the call chain
489c9b5090e2 Initial load
duke
parents:
diff changeset
   878
  assert(state == INITIALIZED, "race condition");
489c9b5090e2 Initial load
duke
parents:
diff changeset
   879
  return true;
489c9b5090e2 Initial load
duke
parents:
diff changeset
   880
}
489c9b5090e2 Initial load
duke
parents:
diff changeset
   881
489c9b5090e2 Initial load
duke
parents:
diff changeset
   882
/////////////////////////////////////////////////////////////////////////////
489c9b5090e2 Initial load
duke
parents:
diff changeset
   883
// attach existing thread
489c9b5090e2 Initial load
duke
parents:
diff changeset
   884
489c9b5090e2 Initial load
duke
parents:
diff changeset
   885
// bootstrap the main thread
489c9b5090e2 Initial load
duke
parents:
diff changeset
   886
bool os::create_main_thread(JavaThread* thread) {
489c9b5090e2 Initial load
duke
parents:
diff changeset
   887
  assert(os::Linux::_main_thread == pthread_self(), "should be called inside main thread");
489c9b5090e2 Initial load
duke
parents:
diff changeset
   888
  return create_attached_thread(thread);
489c9b5090e2 Initial load
duke
parents:
diff changeset
   889
}
489c9b5090e2 Initial load
duke
parents:
diff changeset
   890
489c9b5090e2 Initial load
duke
parents:
diff changeset
   891
bool os::create_attached_thread(JavaThread* thread) {
489c9b5090e2 Initial load
duke
parents:
diff changeset
   892
#ifdef ASSERT
26683
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
   893
  thread->verify_not_published();
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
   894
#endif
489c9b5090e2 Initial load
duke
parents:
diff changeset
   895
489c9b5090e2 Initial load
duke
parents:
diff changeset
   896
  // Allocate the OSThread object
489c9b5090e2 Initial load
duke
parents:
diff changeset
   897
  OSThread* osthread = new OSThread(NULL, NULL);
489c9b5090e2 Initial load
duke
parents:
diff changeset
   898
489c9b5090e2 Initial load
duke
parents:
diff changeset
   899
  if (osthread == NULL) {
489c9b5090e2 Initial load
duke
parents:
diff changeset
   900
    return false;
489c9b5090e2 Initial load
duke
parents:
diff changeset
   901
  }
489c9b5090e2 Initial load
duke
parents:
diff changeset
   902
489c9b5090e2 Initial load
duke
parents:
diff changeset
   903
  // Store pthread info into the OSThread
489c9b5090e2 Initial load
duke
parents:
diff changeset
   904
  osthread->set_thread_id(os::Linux::gettid());
489c9b5090e2 Initial load
duke
parents:
diff changeset
   905
  osthread->set_pthread_id(::pthread_self());
489c9b5090e2 Initial load
duke
parents:
diff changeset
   906
489c9b5090e2 Initial load
duke
parents:
diff changeset
   907
  // initialize floating point control register
489c9b5090e2 Initial load
duke
parents:
diff changeset
   908
  os::Linux::init_thread_fpu_state();
489c9b5090e2 Initial load
duke
parents:
diff changeset
   909
489c9b5090e2 Initial load
duke
parents:
diff changeset
   910
  // Initial thread state is RUNNABLE
489c9b5090e2 Initial load
duke
parents:
diff changeset
   911
  osthread->set_state(RUNNABLE);
489c9b5090e2 Initial load
duke
parents:
diff changeset
   912
489c9b5090e2 Initial load
duke
parents:
diff changeset
   913
  thread->set_osthread(osthread);
489c9b5090e2 Initial load
duke
parents:
diff changeset
   914
489c9b5090e2 Initial load
duke
parents:
diff changeset
   915
  if (UseNUMA) {
489c9b5090e2 Initial load
duke
parents:
diff changeset
   916
    int lgrp_id = os::numa_get_group_id();
489c9b5090e2 Initial load
duke
parents:
diff changeset
   917
    if (lgrp_id != -1) {
489c9b5090e2 Initial load
duke
parents:
diff changeset
   918
      thread->set_lgrp_id(lgrp_id);
489c9b5090e2 Initial load
duke
parents:
diff changeset
   919
    }
489c9b5090e2 Initial load
duke
parents:
diff changeset
   920
  }
489c9b5090e2 Initial load
duke
parents:
diff changeset
   921
489c9b5090e2 Initial load
duke
parents:
diff changeset
   922
  if (os::Linux::is_initial_thread()) {
489c9b5090e2 Initial load
duke
parents:
diff changeset
   923
    // If current thread is initial thread, its stack is mapped on demand,
489c9b5090e2 Initial load
duke
parents:
diff changeset
   924
    // see notes about MAP_GROWSDOWN. Here we try to force kernel to map
489c9b5090e2 Initial load
duke
parents:
diff changeset
   925
    // the entire stack region to avoid SEGV in stack banging.
489c9b5090e2 Initial load
duke
parents:
diff changeset
   926
    // It is also useful to get around the heap-stack-gap problem on SuSE
489c9b5090e2 Initial load
duke
parents:
diff changeset
   927
    // kernel (see 4821821 for details). We first expand stack to the top
489c9b5090e2 Initial load
duke
parents:
diff changeset
   928
    // of yellow zone, then enable stack yellow zone (order is significant,
489c9b5090e2 Initial load
duke
parents:
diff changeset
   929
    // enabling yellow zone first will crash JVM on SuSE Linux), so there
489c9b5090e2 Initial load
duke
parents:
diff changeset
   930
    // is no gap between the last two virtual memory regions.
489c9b5090e2 Initial load
duke
parents:
diff changeset
   931
489c9b5090e2 Initial load
duke
parents:
diff changeset
   932
    JavaThread *jt = (JavaThread *)thread;
489c9b5090e2 Initial load
duke
parents:
diff changeset
   933
    address addr = jt->stack_yellow_zone_base();
489c9b5090e2 Initial load
duke
parents:
diff changeset
   934
    assert(addr != NULL, "initialization problem?");
489c9b5090e2 Initial load
duke
parents:
diff changeset
   935
    assert(jt->stack_available(addr) > 0, "stack guard should not be enabled");
489c9b5090e2 Initial load
duke
parents:
diff changeset
   936
489c9b5090e2 Initial load
duke
parents:
diff changeset
   937
    osthread->set_expanding_stack();
489c9b5090e2 Initial load
duke
parents:
diff changeset
   938
    os::Linux::manually_expand_stack(jt, addr);
489c9b5090e2 Initial load
duke
parents:
diff changeset
   939
    osthread->clear_expanding_stack();
489c9b5090e2 Initial load
duke
parents:
diff changeset
   940
  }
489c9b5090e2 Initial load
duke
parents:
diff changeset
   941
489c9b5090e2 Initial load
duke
parents:
diff changeset
   942
  // initialize signal mask for this thread
489c9b5090e2 Initial load
duke
parents:
diff changeset
   943
  // and save the caller's signal mask
489c9b5090e2 Initial load
duke
parents:
diff changeset
   944
  os::Linux::hotspot_sigmask(thread);
489c9b5090e2 Initial load
duke
parents:
diff changeset
   945
489c9b5090e2 Initial load
duke
parents:
diff changeset
   946
  return true;
489c9b5090e2 Initial load
duke
parents:
diff changeset
   947
}
489c9b5090e2 Initial load
duke
parents:
diff changeset
   948
489c9b5090e2 Initial load
duke
parents:
diff changeset
   949
void os::pd_start_thread(Thread* thread) {
489c9b5090e2 Initial load
duke
parents:
diff changeset
   950
  OSThread * osthread = thread->osthread();
489c9b5090e2 Initial load
duke
parents:
diff changeset
   951
  assert(osthread->get_state() != INITIALIZED, "just checking");
489c9b5090e2 Initial load
duke
parents:
diff changeset
   952
  Monitor* sync_with_child = osthread->startThread_lock();
489c9b5090e2 Initial load
duke
parents:
diff changeset
   953
  MutexLockerEx ml(sync_with_child, Mutex::_no_safepoint_check_flag);
489c9b5090e2 Initial load
duke
parents:
diff changeset
   954
  sync_with_child->notify();
489c9b5090e2 Initial load
duke
parents:
diff changeset
   955
}
489c9b5090e2 Initial load
duke
parents:
diff changeset
   956
489c9b5090e2 Initial load
duke
parents:
diff changeset
   957
// Free Linux resources related to the OSThread
489c9b5090e2 Initial load
duke
parents:
diff changeset
   958
void os::free_thread(OSThread* osthread) {
489c9b5090e2 Initial load
duke
parents:
diff changeset
   959
  assert(osthread != NULL, "osthread not set");
489c9b5090e2 Initial load
duke
parents:
diff changeset
   960
489c9b5090e2 Initial load
duke
parents:
diff changeset
   961
  if (Thread::current()->osthread() == osthread) {
489c9b5090e2 Initial load
duke
parents:
diff changeset
   962
    // Restore caller's signal mask
489c9b5090e2 Initial load
duke
parents:
diff changeset
   963
    sigset_t sigmask = osthread->caller_sigmask();
489c9b5090e2 Initial load
duke
parents:
diff changeset
   964
    pthread_sigmask(SIG_SETMASK, &sigmask, NULL);
26683
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
   965
  }
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
   966
489c9b5090e2 Initial load
duke
parents:
diff changeset
   967
  delete osthread;
489c9b5090e2 Initial load
duke
parents:
diff changeset
   968
}
489c9b5090e2 Initial load
duke
parents:
diff changeset
   969
489c9b5090e2 Initial load
duke
parents:
diff changeset
   970
//////////////////////////////////////////////////////////////////////////////
489c9b5090e2 Initial load
duke
parents:
diff changeset
   971
// thread local storage
489c9b5090e2 Initial load
duke
parents:
diff changeset
   972
23864
8af6bd3b1375 8033696: "assert(thread != NULL) failed: just checking" due to Thread::current() and JNI pthread interaction
kevinw
parents: 23522
diff changeset
   973
// Restore the thread pointer if the destructor is called. This is in case
8af6bd3b1375 8033696: "assert(thread != NULL) failed: just checking" due to Thread::current() and JNI pthread interaction
kevinw
parents: 23522
diff changeset
   974
// someone from JNI code sets up a destructor with pthread_key_create to run
8af6bd3b1375 8033696: "assert(thread != NULL) failed: just checking" due to Thread::current() and JNI pthread interaction
kevinw
parents: 23522
diff changeset
   975
// detachCurrentThread on thread death. Unless we restore the thread pointer we
8af6bd3b1375 8033696: "assert(thread != NULL) failed: just checking" due to Thread::current() and JNI pthread interaction
kevinw
parents: 23522
diff changeset
   976
// will hang or crash. When detachCurrentThread is called the key will be set
8af6bd3b1375 8033696: "assert(thread != NULL) failed: just checking" due to Thread::current() and JNI pthread interaction
kevinw
parents: 23522
diff changeset
   977
// to null and we will not be called again. If detachCurrentThread is never
8af6bd3b1375 8033696: "assert(thread != NULL) failed: just checking" due to Thread::current() and JNI pthread interaction
kevinw
parents: 23522
diff changeset
   978
// called we could loop forever depending on the pthread implementation.
8af6bd3b1375 8033696: "assert(thread != NULL) failed: just checking" due to Thread::current() and JNI pthread interaction
kevinw
parents: 23522
diff changeset
   979
static void restore_thread_pointer(void* p) {
8af6bd3b1375 8033696: "assert(thread != NULL) failed: just checking" due to Thread::current() and JNI pthread interaction
kevinw
parents: 23522
diff changeset
   980
  Thread* thread = (Thread*) p;
8af6bd3b1375 8033696: "assert(thread != NULL) failed: just checking" due to Thread::current() and JNI pthread interaction
kevinw
parents: 23522
diff changeset
   981
  os::thread_local_storage_at_put(ThreadLocalStorage::thread_index(), thread);
8af6bd3b1375 8033696: "assert(thread != NULL) failed: just checking" due to Thread::current() and JNI pthread interaction
kevinw
parents: 23522
diff changeset
   982
}
8af6bd3b1375 8033696: "assert(thread != NULL) failed: just checking" due to Thread::current() and JNI pthread interaction
kevinw
parents: 23522
diff changeset
   983
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
   984
int os::allocate_thread_local_storage() {
489c9b5090e2 Initial load
duke
parents:
diff changeset
   985
  pthread_key_t key;
23864
8af6bd3b1375 8033696: "assert(thread != NULL) failed: just checking" due to Thread::current() and JNI pthread interaction
kevinw
parents: 23522
diff changeset
   986
  int rslt = pthread_key_create(&key, restore_thread_pointer);
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
   987
  assert(rslt == 0, "cannot allocate thread local storage");
489c9b5090e2 Initial load
duke
parents:
diff changeset
   988
  return (int)key;
489c9b5090e2 Initial load
duke
parents:
diff changeset
   989
}
489c9b5090e2 Initial load
duke
parents:
diff changeset
   990
489c9b5090e2 Initial load
duke
parents:
diff changeset
   991
// Note: This is currently not used by VM, as we don't destroy TLS key
489c9b5090e2 Initial load
duke
parents:
diff changeset
   992
// on VM exit.
489c9b5090e2 Initial load
duke
parents:
diff changeset
   993
void os::free_thread_local_storage(int index) {
489c9b5090e2 Initial load
duke
parents:
diff changeset
   994
  int rslt = pthread_key_delete((pthread_key_t)index);
489c9b5090e2 Initial load
duke
parents:
diff changeset
   995
  assert(rslt == 0, "invalid index");
489c9b5090e2 Initial load
duke
parents:
diff changeset
   996
}
489c9b5090e2 Initial load
duke
parents:
diff changeset
   997
489c9b5090e2 Initial load
duke
parents:
diff changeset
   998
void os::thread_local_storage_at_put(int index, void* value) {
489c9b5090e2 Initial load
duke
parents:
diff changeset
   999
  int rslt = pthread_setspecific((pthread_key_t)index, value);
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1000
  assert(rslt == 0, "pthread_setspecific failed");
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1001
}
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1002
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1003
extern "C" Thread* get_thread() {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1004
  return ThreadLocalStorage::thread();
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1005
}
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1006
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1007
//////////////////////////////////////////////////////////////////////////////
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1008
// initial thread
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1009
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1010
// Check if current thread is the initial thread, similar to Solaris thr_main.
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1011
bool os::Linux::is_initial_thread(void) {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1012
  char dummy;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1013
  // If called before init complete, thread stack bottom will be null.
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1014
  // Can be called if fatal error occurs before initialization.
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1015
  if (initial_thread_stack_bottom() == NULL) return false;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1016
  assert(initial_thread_stack_bottom() != NULL &&
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1017
         initial_thread_stack_size()   != 0,
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1018
         "os::init did not locate initial thread's stack region");
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1019
  if ((address)&dummy >= initial_thread_stack_bottom() &&
26684
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
  1020
      (address)&dummy < initial_thread_stack_bottom() + initial_thread_stack_size()) {
26683
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  1021
    return true;
26684
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
  1022
  } else {
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
  1023
    return false;
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
  1024
  }
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1025
}
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1026
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1027
// Find the virtual memory area that contains addr
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1028
static bool find_vma(address addr, address* vma_low, address* vma_high) {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1029
  FILE *fp = fopen("/proc/self/maps", "r");
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1030
  if (fp) {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1031
    address low, high;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1032
    while (!feof(fp)) {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1033
      if (fscanf(fp, "%p-%p", &low, &high) == 2) {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1034
        if (low <= addr && addr < high) {
26683
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  1035
          if (vma_low)  *vma_low  = low;
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  1036
          if (vma_high) *vma_high = high;
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  1037
          fclose(fp);
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  1038
          return true;
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1039
        }
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1040
      }
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1041
      for (;;) {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1042
        int ch = fgetc(fp);
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1043
        if (ch == EOF || ch == (int)'\n') break;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1044
      }
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1045
    }
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1046
    fclose(fp);
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1047
  }
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1048
  return false;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1049
}
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1050
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1051
// Locate initial thread stack. This special handling of initial thread stack
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1052
// is needed because pthread_getattr_np() on most (all?) Linux distros returns
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1053
// bogus value for initial thread.
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1054
void os::Linux::capture_initial_stack(size_t max_size) {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1055
  // stack size is the easy part, get it from RLIMIT_STACK
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1056
  size_t stack_size;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1057
  struct rlimit rlim;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1058
  getrlimit(RLIMIT_STACK, &rlim);
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1059
  stack_size = rlim.rlim_cur;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1060
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1061
  // 6308388: a bug in ld.so will relocate its own .data section to the
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1062
  //   lower end of primordial stack; reduce ulimit -s value a little bit
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1063
  //   so we won't install guard page on ld.so's data section.
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1064
  stack_size -= 2 * page_size();
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1065
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1066
  // 4441425: avoid crash with "unlimited" stack size on SuSE 7.1 or Redhat
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1067
  //   7.1, in both cases we will get 2G in return value.
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1068
  // 4466587: glibc 2.2.x compiled w/o "--enable-kernel=2.4.0" (RH 7.0,
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1069
  //   SuSE 7.2, Debian) can not handle alternate signal stack correctly
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1070
  //   for initial thread if its stack size exceeds 6M. Cap it at 2M,
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1071
  //   in case other parts in glibc still assumes 2M max stack size.
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1072
  // FIXME: alt signal stack is gone, maybe we can relax this constraint?
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1073
  // Problem still exists RH7.2 (IA64 anyway) but 2MB is a little small
26684
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
  1074
  if (stack_size > 2 * K * K IA64_ONLY(*2)) {
26683
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  1075
    stack_size = 2 * K * K IA64_ONLY(*2);
26684
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
  1076
  }
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1077
  // Try to figure out where the stack base (top) is. This is harder.
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1078
  //
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1079
  // When an application is started, glibc saves the initial stack pointer in
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1080
  // a global variable "__libc_stack_end", which is then used by system
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1081
  // libraries. __libc_stack_end should be pretty close to stack top. The
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1082
  // variable is available since the very early days. However, because it is
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1083
  // a private interface, it could disappear in the future.
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1084
  //
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1085
  // Linux kernel saves start_stack information in /proc/<pid>/stat. Similar
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1086
  // to __libc_stack_end, it is very close to stack top, but isn't the real
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1087
  // stack top. Note that /proc may not exist if VM is running as a chroot
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1088
  // program, so reading /proc/<pid>/stat could fail. Also the contents of
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1089
  // /proc/<pid>/stat could change in the future (though unlikely).
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1090
  //
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1091
  // We try __libc_stack_end first. If that doesn't work, look for
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1092
  // /proc/<pid>/stat. If neither of them works, we use current stack pointer
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1093
  // as a hint, which should work well in most cases.
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1094
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1095
  uintptr_t stack_start;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1096
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1097
  // try __libc_stack_end first
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1098
  uintptr_t *p = (uintptr_t *)dlsym(RTLD_DEFAULT, "__libc_stack_end");
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1099
  if (p && *p) {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1100
    stack_start = *p;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1101
  } else {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1102
    // see if we can get the start_stack field from /proc/self/stat
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1103
    FILE *fp;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1104
    int pid;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1105
    char state;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1106
    int ppid;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1107
    int pgrp;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1108
    int session;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1109
    int nr;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1110
    int tpgrp;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1111
    unsigned long flags;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1112
    unsigned long minflt;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1113
    unsigned long cminflt;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1114
    unsigned long majflt;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1115
    unsigned long cmajflt;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1116
    unsigned long utime;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1117
    unsigned long stime;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1118
    long cutime;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1119
    long cstime;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1120
    long prio;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1121
    long nice;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1122
    long junk;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1123
    long it_real;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1124
    uintptr_t start;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1125
    uintptr_t vsize;
6176
4d9030fe341f 6953477: Increase portability and flexibility of building Hotspot
bobv
parents: 5922
diff changeset
  1126
    intptr_t rss;
4d9030fe341f 6953477: Increase portability and flexibility of building Hotspot
bobv
parents: 5922
diff changeset
  1127
    uintptr_t rsslim;
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1128
    uintptr_t scodes;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1129
    uintptr_t ecode;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1130
    int i;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1131
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1132
    // Figure what the primordial thread stack base is. Code is inspired
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1133
    // by email from Hans Boehm. /proc/self/stat begins with current pid,
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1134
    // followed by command name surrounded by parentheses, state, etc.
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1135
    char stat[2048];
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1136
    int statlen;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1137
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1138
    fp = fopen("/proc/self/stat", "r");
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1139
    if (fp) {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1140
      statlen = fread(stat, 1, 2047, fp);
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1141
      stat[statlen] = '\0';
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1142
      fclose(fp);
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1143
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1144
      // Skip pid and the command string. Note that we could be dealing with
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1145
      // weird command names, e.g. user could decide to rename java launcher
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1146
      // to "java 1.4.2 :)", then the stat file would look like
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1147
      //                1234 (java 1.4.2 :)) R ... ...
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1148
      // We don't really need to know the command string, just find the last
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1149
      // occurrence of ")" and then start parsing from there. See bug 4726580.
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1150
      char * s = strrchr(stat, ')');
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1151
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1152
      i = 0;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1153
      if (s) {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1154
        // Skip blank chars
27471
6e56277909f1 8062370: Various minor code improvements
goetz
parents: 27458
diff changeset
  1155
        do { s++; } while (s && isspace(*s));
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1156
6176
4d9030fe341f 6953477: Increase portability and flexibility of building Hotspot
bobv
parents: 5922
diff changeset
  1157
#define _UFM UINTX_FORMAT
4d9030fe341f 6953477: Increase portability and flexibility of building Hotspot
bobv
parents: 5922
diff changeset
  1158
#define _DFM INTX_FORMAT
4d9030fe341f 6953477: Increase portability and flexibility of building Hotspot
bobv
parents: 5922
diff changeset
  1159
26684
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
  1160
        //                                     1   1   1   1   1   1   1   1   1   1   2   2    2    2    2    2    2    2    2
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
  1161
        //              3  4  5  6  7  8   9   0   1   2   3   4   5   6   7   8   9   0   1    2    3    4    5    6    7    8
6176
4d9030fe341f 6953477: Increase portability and flexibility of building Hotspot
bobv
parents: 5922
diff changeset
  1162
        i = sscanf(s, "%c %d %d %d %d %d %lu %lu %lu %lu %lu %lu %lu %ld %ld %ld %ld %ld %ld " _UFM _UFM _DFM _UFM _UFM _UFM _UFM,
26684
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
  1163
                   &state,          // 3  %c
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
  1164
                   &ppid,           // 4  %d
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
  1165
                   &pgrp,           // 5  %d
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
  1166
                   &session,        // 6  %d
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
  1167
                   &nr,             // 7  %d
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
  1168
                   &tpgrp,          // 8  %d
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
  1169
                   &flags,          // 9  %lu
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
  1170
                   &minflt,         // 10 %lu
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
  1171
                   &cminflt,        // 11 %lu
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
  1172
                   &majflt,         // 12 %lu
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
  1173
                   &cmajflt,        // 13 %lu
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
  1174
                   &utime,          // 14 %lu
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
  1175
                   &stime,          // 15 %lu
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
  1176
                   &cutime,         // 16 %ld
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
  1177
                   &cstime,         // 17 %ld
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
  1178
                   &prio,           // 18 %ld
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
  1179
                   &nice,           // 19 %ld
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
  1180
                   &junk,           // 20 %ld
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
  1181
                   &it_real,        // 21 %ld
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
  1182
                   &start,          // 22 UINTX_FORMAT
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
  1183
                   &vsize,          // 23 UINTX_FORMAT
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
  1184
                   &rss,            // 24 INTX_FORMAT
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
  1185
                   &rsslim,         // 25 UINTX_FORMAT
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
  1186
                   &scodes,         // 26 UINTX_FORMAT
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
  1187
                   &ecode,          // 27 UINTX_FORMAT
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
  1188
                   &stack_start);   // 28 UINTX_FORMAT
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1189
      }
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1190
6176
4d9030fe341f 6953477: Increase portability and flexibility of building Hotspot
bobv
parents: 5922
diff changeset
  1191
#undef _UFM
4d9030fe341f 6953477: Increase portability and flexibility of building Hotspot
bobv
parents: 5922
diff changeset
  1192
#undef _DFM
4d9030fe341f 6953477: Increase portability and flexibility of building Hotspot
bobv
parents: 5922
diff changeset
  1193
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1194
      if (i != 28 - 2) {
26683
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  1195
        assert(false, "Bad conversion from /proc/self/stat");
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  1196
        // product mode - assume we are the initial thread, good luck in the
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  1197
        // embedded case.
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  1198
        warning("Can't detect initial thread stack location - bad conversion");
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  1199
        stack_start = (uintptr_t) &rlim;
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1200
      }
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1201
    } else {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1202
      // For some reason we can't open /proc/self/stat (for example, running on
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1203
      // FreeBSD with a Linux emulator, or inside chroot), this should work for
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1204
      // most cases, so don't abort:
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1205
      warning("Can't detect initial thread stack location - no /proc/self/stat");
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1206
      stack_start = (uintptr_t) &rlim;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1207
    }
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1208
  }
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1209
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1210
  // Now we have a pointer (stack_start) very close to the stack top, the
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1211
  // next thing to do is to figure out the exact location of stack top. We
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1212
  // can find out the virtual memory area that contains stack_start by
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1213
  // reading /proc/self/maps, it should be the last vma in /proc/self/maps,
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1214
  // and its upper limit is the real stack top. (again, this would fail if
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1215
  // running inside chroot, because /proc may not exist.)
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1216
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1217
  uintptr_t stack_top;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1218
  address low, high;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1219
  if (find_vma((address)stack_start, &low, &high)) {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1220
    // success, "high" is the true stack top. (ignore "low", because initial
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1221
    // thread stack grows on demand, its real bottom is high - RLIMIT_STACK.)
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1222
    stack_top = (uintptr_t)high;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1223
  } else {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1224
    // failed, likely because /proc/self/maps does not exist
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1225
    warning("Can't detect initial thread stack location - find_vma failed");
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1226
    // best effort: stack_start is normally within a few pages below the real
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1227
    // stack top, use it as stack top, and reduce stack size so we won't put
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1228
    // guard page outside stack.
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1229
    stack_top = stack_start;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1230
    stack_size -= 16 * page_size();
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1231
  }
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1232
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1233
  // stack_top could be partially down the page so align it
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1234
  stack_top = align_size_up(stack_top, page_size());
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1235
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1236
  if (max_size && stack_size > max_size) {
26683
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  1237
    _initial_thread_stack_size = max_size;
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1238
  } else {
26683
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  1239
    _initial_thread_stack_size = stack_size;
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1240
  }
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1241
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1242
  _initial_thread_stack_size = align_size_down(_initial_thread_stack_size, page_size());
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1243
  _initial_thread_stack_bottom = (address)stack_top - _initial_thread_stack_size;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1244
}
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1245
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1246
////////////////////////////////////////////////////////////////////////////////
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1247
// time support
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1248
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1249
// Time since start-up in seconds to a fine granularity.
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1250
// Used by VMSelfDestructTimer and the MemProfiler.
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1251
double os::elapsedTime() {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1252
21185
9d53434b1ef5 8027294: Prepare hotspot for non TOD based uptime counter
jbachorik
parents: 20408
diff changeset
  1253
  return ((double)os::elapsed_counter()) / os::elapsed_frequency(); // nanosecond resolution
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1254
}
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1255
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1256
jlong os::elapsed_counter() {
21185
9d53434b1ef5 8027294: Prepare hotspot for non TOD based uptime counter
jbachorik
parents: 20408
diff changeset
  1257
  return javaTimeNanos() - initial_time_count;
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1258
}
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1259
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1260
jlong os::elapsed_frequency() {
21185
9d53434b1ef5 8027294: Prepare hotspot for non TOD based uptime counter
jbachorik
parents: 20408
diff changeset
  1261
  return NANOSECS_PER_SEC; // nanosecond resolution
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1262
}
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1263
17854
d65bc1546091 8013895: G1: G1SummarizeRSetStats output on Linux needs improvemen
tschatzl
parents: 17134
diff changeset
  1264
bool os::supports_vtime() { return true; }
1374
4c24294029a9 6711316: Open source the Garbage-First garbage collector
ysr
parents: 388
diff changeset
  1265
bool os::enable_vtime()   { return false; }
4c24294029a9 6711316: Open source the Garbage-First garbage collector
ysr
parents: 388
diff changeset
  1266
bool os::vtime_enabled()  { return false; }
17854
d65bc1546091 8013895: G1: G1SummarizeRSetStats output on Linux needs improvemen
tschatzl
parents: 17134
diff changeset
  1267
1374
4c24294029a9 6711316: Open source the Garbage-First garbage collector
ysr
parents: 388
diff changeset
  1268
double os::elapsedVTime() {
17854
d65bc1546091 8013895: G1: G1SummarizeRSetStats output on Linux needs improvemen
tschatzl
parents: 17134
diff changeset
  1269
  struct rusage usage;
d65bc1546091 8013895: G1: G1SummarizeRSetStats output on Linux needs improvemen
tschatzl
parents: 17134
diff changeset
  1270
  int retval = getrusage(RUSAGE_THREAD, &usage);
d65bc1546091 8013895: G1: G1SummarizeRSetStats output on Linux needs improvemen
tschatzl
parents: 17134
diff changeset
  1271
  if (retval == 0) {
d65bc1546091 8013895: G1: G1SummarizeRSetStats output on Linux needs improvemen
tschatzl
parents: 17134
diff changeset
  1272
    return (double) (usage.ru_utime.tv_sec + usage.ru_stime.tv_sec) + (double) (usage.ru_utime.tv_usec + usage.ru_stime.tv_usec) / (1000 * 1000);
d65bc1546091 8013895: G1: G1SummarizeRSetStats output on Linux needs improvemen
tschatzl
parents: 17134
diff changeset
  1273
  } else {
d65bc1546091 8013895: G1: G1SummarizeRSetStats output on Linux needs improvemen
tschatzl
parents: 17134
diff changeset
  1274
    // better than nothing, but not much
d65bc1546091 8013895: G1: G1SummarizeRSetStats output on Linux needs improvemen
tschatzl
parents: 17134
diff changeset
  1275
    return elapsedTime();
d65bc1546091 8013895: G1: G1SummarizeRSetStats output on Linux needs improvemen
tschatzl
parents: 17134
diff changeset
  1276
  }
1374
4c24294029a9 6711316: Open source the Garbage-First garbage collector
ysr
parents: 388
diff changeset
  1277
}
4c24294029a9 6711316: Open source the Garbage-First garbage collector
ysr
parents: 388
diff changeset
  1278
234
4da9c1bbc810 6667833: Remove CacheTimeMillis
sbohne
parents: 1
diff changeset
  1279
jlong os::javaTimeMillis() {
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1280
  timeval time;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1281
  int status = gettimeofday(&time, NULL);
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1282
  assert(status != -1, "linux error");
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1283
  return jlong(time.tv_sec) * 1000  +  jlong(time.tv_usec / 1000);
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1284
}
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1285
28737
ca4b6a6e5cc8 8068730: Increase the precision of the implementation of java.time.Clock.systemUTC()
dfuchs
parents: 28172
diff changeset
  1286
void os::javaTimeSystemUTC(jlong &seconds, jlong &nanos) {
ca4b6a6e5cc8 8068730: Increase the precision of the implementation of java.time.Clock.systemUTC()
dfuchs
parents: 28172
diff changeset
  1287
  timeval time;
ca4b6a6e5cc8 8068730: Increase the precision of the implementation of java.time.Clock.systemUTC()
dfuchs
parents: 28172
diff changeset
  1288
  int status = gettimeofday(&time, NULL);
ca4b6a6e5cc8 8068730: Increase the precision of the implementation of java.time.Clock.systemUTC()
dfuchs
parents: 28172
diff changeset
  1289
  assert(status != -1, "linux error");
ca4b6a6e5cc8 8068730: Increase the precision of the implementation of java.time.Clock.systemUTC()
dfuchs
parents: 28172
diff changeset
  1290
  seconds = jlong(time.tv_sec);
ca4b6a6e5cc8 8068730: Increase the precision of the implementation of java.time.Clock.systemUTC()
dfuchs
parents: 28172
diff changeset
  1291
  nanos = jlong(time.tv_usec) * 1000;
ca4b6a6e5cc8 8068730: Increase the precision of the implementation of java.time.Clock.systemUTC()
dfuchs
parents: 28172
diff changeset
  1292
}
ca4b6a6e5cc8 8068730: Increase the precision of the implementation of java.time.Clock.systemUTC()
dfuchs
parents: 28172
diff changeset
  1293
ca4b6a6e5cc8 8068730: Increase the precision of the implementation of java.time.Clock.systemUTC()
dfuchs
parents: 28172
diff changeset
  1294
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1295
#ifndef CLOCK_MONOTONIC
26684
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
  1296
  #define CLOCK_MONOTONIC (1)
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1297
#endif
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1298
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1299
void os::Linux::clock_init() {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1300
  // we do dlopen's in this particular order due to bug in linux
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1301
  // dynamical loader (see 6348968) leading to crash on exit
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1302
  void* handle = dlopen("librt.so.1", RTLD_LAZY);
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1303
  if (handle == NULL) {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1304
    handle = dlopen("librt.so", RTLD_LAZY);
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1305
  }
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1306
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1307
  if (handle) {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1308
    int (*clock_getres_func)(clockid_t, struct timespec*) =
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1309
           (int(*)(clockid_t, struct timespec*))dlsym(handle, "clock_getres");
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1310
    int (*clock_gettime_func)(clockid_t, struct timespec*) =
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1311
           (int(*)(clockid_t, struct timespec*))dlsym(handle, "clock_gettime");
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1312
    if (clock_getres_func && clock_gettime_func) {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1313
      // See if monotonic clock is supported by the kernel. Note that some
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1314
      // early implementations simply return kernel jiffies (updated every
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1315
      // 1/100 or 1/1000 second). It would be bad to use such a low res clock
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1316
      // for nano time (though the monotonic property is still nice to have).
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1317
      // It's fixed in newer kernels, however clock_getres() still returns
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1318
      // 1/HZ. We check if clock_getres() works, but will ignore its reported
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1319
      // resolution for now. Hopefully as people move to new kernels, this
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1320
      // won't be a problem.
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1321
      struct timespec res;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1322
      struct timespec tp;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1323
      if (clock_getres_func (CLOCK_MONOTONIC, &res) == 0 &&
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1324
          clock_gettime_func(CLOCK_MONOTONIC, &tp)  == 0) {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1325
        // yes, monotonic clock is supported
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1326
        _clock_gettime = clock_gettime_func;
19964
a3a04a9d29ac 6900441: PlatformEvent.park(millis) on Linux could still be affected by changes to the time-of-day clock
dholmes
parents: 19732
diff changeset
  1327
        return;
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1328
      } else {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1329
        // close librt if there is no monotonic clock
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1330
        dlclose(handle);
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1331
      }
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1332
    }
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1333
  }
19964
a3a04a9d29ac 6900441: PlatformEvent.park(millis) on Linux could still be affected by changes to the time-of-day clock
dholmes
parents: 19732
diff changeset
  1334
  warning("No monotonic clock was available - timed services may " \
a3a04a9d29ac 6900441: PlatformEvent.park(millis) on Linux could still be affected by changes to the time-of-day clock
dholmes
parents: 19732
diff changeset
  1335
          "be adversely affected if the time-of-day clock changes");
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1336
}
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1337
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1338
#ifndef SYS_clock_getres
26684
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
  1339
  #if defined(IA32) || defined(AMD64)
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
  1340
    #define SYS_clock_getres IA32_ONLY(266)  AMD64_ONLY(229)
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
  1341
    #define sys_clock_getres(x,y)  ::syscall(SYS_clock_getres, x, y)
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
  1342
  #else
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
  1343
    #warning "SYS_clock_getres not defined for this platform, disabling fast_thread_cpu_time"
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
  1344
    #define sys_clock_getres(x,y)  -1
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
  1345
  #endif
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1346
#else
26684
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
  1347
  #define sys_clock_getres(x,y)  ::syscall(SYS_clock_getres, x, y)
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1348
#endif
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1349
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1350
void os::Linux::fast_thread_clock_init() {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1351
  if (!UseLinuxPosixThreadCPUClocks) {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1352
    return;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1353
  }
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1354
  clockid_t clockid;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1355
  struct timespec tp;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1356
  int (*pthread_getcpuclockid_func)(pthread_t, clockid_t *) =
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1357
      (int(*)(pthread_t, clockid_t *)) dlsym(RTLD_DEFAULT, "pthread_getcpuclockid");
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1358
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1359
  // Switch to using fast clocks for thread cpu time if
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1360
  // the sys_clock_getres() returns 0 error code.
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1361
  // Note, that some kernels may support the current thread
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1362
  // clock (CLOCK_THREAD_CPUTIME_ID) but not the clocks
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1363
  // returned by the pthread_getcpuclockid().
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1364
  // If the fast Posix clocks are supported then the sys_clock_getres()
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1365
  // must return at least tp.tv_sec == 0 which means a resolution
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1366
  // better than 1 sec. This is extra check for reliability.
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1367
25064
244218e6ec0a 8046758: cleanup non-indent white space issues prior to Contended Locking cleanup bucket
dcubed
parents: 24931
diff changeset
  1368
  if (pthread_getcpuclockid_func &&
26683
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  1369
      pthread_getcpuclockid_func(_main_thread, &clockid) == 0 &&
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  1370
      sys_clock_getres(clockid, &tp) == 0 && tp.tv_sec == 0) {
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1371
    _supports_fast_thread_cpu_time = true;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1372
    _pthread_getcpuclockid = pthread_getcpuclockid_func;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1373
  }
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1374
}
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1375
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1376
jlong os::javaTimeNanos() {
22891
1f5d1fff23fa 6546236: Thread interrupt() of Thread.sleep() can be lost on Solaris due to race with signal handler
fparain
parents: 22749
diff changeset
  1377
  if (os::supports_monotonic_clock()) {
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1378
    struct timespec tp;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1379
    int status = Linux::clock_gettime(CLOCK_MONOTONIC, &tp);
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1380
    assert(status == 0, "gettime error");
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1381
    jlong result = jlong(tp.tv_sec) * (1000 * 1000 * 1000) + jlong(tp.tv_nsec);
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1382
    return result;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1383
  } else {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1384
    timeval time;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1385
    int status = gettimeofday(&time, NULL);
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1386
    assert(status != -1, "linux error");
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1387
    jlong usecs = jlong(time.tv_sec) * (1000 * 1000) + jlong(time.tv_usec);
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1388
    return 1000 * usecs;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1389
  }
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1390
}
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1391
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1392
void os::javaTimeNanos_info(jvmtiTimerInfo *info_ptr) {
22891
1f5d1fff23fa 6546236: Thread interrupt() of Thread.sleep() can be lost on Solaris due to race with signal handler
fparain
parents: 22749
diff changeset
  1393
  if (os::supports_monotonic_clock()) {
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1394
    info_ptr->max_value = ALL_64_BITS;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1395
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1396
    // CLOCK_MONOTONIC - amount of time since some arbitrary point in the past
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1397
    info_ptr->may_skip_backward = false;      // not subject to resetting or drifting
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1398
    info_ptr->may_skip_forward = false;       // not subject to resetting or drifting
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1399
  } else {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1400
    // gettimeofday - based on time in seconds since the Epoch thus does not wrap
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1401
    info_ptr->max_value = ALL_64_BITS;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1402
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1403
    // gettimeofday is a real time clock so it skips
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1404
    info_ptr->may_skip_backward = true;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1405
    info_ptr->may_skip_forward = true;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1406
  }
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1407
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1408
  info_ptr->kind = JVMTI_TIMER_ELAPSED;                // elapsed not CPU time
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1409
}
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1410
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1411
// Return the real, user, and system times in seconds from an
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1412
// arbitrary fixed point in the past.
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1413
bool os::getTimesSecs(double* process_real_time,
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1414
                      double* process_user_time,
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1415
                      double* process_system_time) {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1416
  struct tms ticks;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1417
  clock_t real_ticks = times(&ticks);
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1418
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1419
  if (real_ticks == (clock_t) (-1)) {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1420
    return false;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1421
  } else {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1422
    double ticks_per_second = (double) clock_tics_per_sec;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1423
    *process_user_time = ((double) ticks.tms_utime) / ticks_per_second;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1424
    *process_system_time = ((double) ticks.tms_stime) / ticks_per_second;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1425
    *process_real_time = ((double) real_ticks) / ticks_per_second;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1426
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1427
    return true;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1428
  }
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1429
}
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1430
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1431
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1432
char * os::local_time_string(char *buf, size_t buflen) {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1433
  struct tm t;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1434
  time_t long_time;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1435
  time(&long_time);
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1436
  localtime_r(&long_time, &t);
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1437
  jio_snprintf(buf, buflen, "%d-%02d-%02d %02d:%02d:%02d",
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1438
               t.tm_year + 1900, t.tm_mon + 1, t.tm_mday,
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1439
               t.tm_hour, t.tm_min, t.tm_sec);
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1440
  return buf;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1441
}
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1442
2012
041fbc6030dd 6800586: -XX:+PrintGCDateStamps is using mt-unsafe localtime function
ysr
parents: 1892
diff changeset
  1443
struct tm* os::localtime_pd(const time_t* clock, struct tm*  res) {
041fbc6030dd 6800586: -XX:+PrintGCDateStamps is using mt-unsafe localtime function
ysr
parents: 1892
diff changeset
  1444
  return localtime_r(clock, res);
041fbc6030dd 6800586: -XX:+PrintGCDateStamps is using mt-unsafe localtime function
ysr
parents: 1892
diff changeset
  1445
}
041fbc6030dd 6800586: -XX:+PrintGCDateStamps is using mt-unsafe localtime function
ysr
parents: 1892
diff changeset
  1446
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1447
////////////////////////////////////////////////////////////////////////////////
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1448
// runtime exit support
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1449
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1450
// Note: os::shutdown() might be called very early during initialization, or
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1451
// called from signal handler. Before adding something to os::shutdown(), make
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1452
// sure it is async-safe and can handle partially initialized VM.
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1453
void os::shutdown() {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1454
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1455
  // allow PerfMemory to attempt cleanup of any persistent resources
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1456
  perfMemory_exit();
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1457
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1458
  // needs to remove object in file system
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1459
  AttachListener::abort();
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1460
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1461
  // flush buffered output, finish log files
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1462
  ostream_abort();
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1463
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1464
  // Check for abort hook
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1465
  abort_hook_t abort_hook = Arguments::abort_hook();
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1466
  if (abort_hook != NULL) {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1467
    abort_hook();
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1468
  }
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1469
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1470
}
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1471
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1472
// Note: os::abort() might be called very early during initialization, or
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1473
// called from signal handler. Before adding something to os::abort(), make
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1474
// sure it is async-safe and can handle partially initialized VM.
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1475
void os::abort(bool dump_core) {
30240
a7ba42fa1df6 8074354: Make CreateMinidumpOnCrash a new name and available on all platforms
minqi
parents: 30139
diff changeset
  1476
  abort(dump_core, NULL, NULL);
a7ba42fa1df6 8074354: Make CreateMinidumpOnCrash a new name and available on all platforms
minqi
parents: 30139
diff changeset
  1477
}
a7ba42fa1df6 8074354: Make CreateMinidumpOnCrash a new name and available on all platforms
minqi
parents: 30139
diff changeset
  1478
a7ba42fa1df6 8074354: Make CreateMinidumpOnCrash a new name and available on all platforms
minqi
parents: 30139
diff changeset
  1479
void os::abort(bool dump_core, void* siginfo, void* context) {
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1480
  os::shutdown();
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1481
  if (dump_core) {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1482
#ifndef PRODUCT
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1483
    fdStream out(defaultStream::output_fd());
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1484
    out.print_raw("Current thread is ");
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1485
    char buf[16];
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1486
    jio_snprintf(buf, sizeof(buf), UINTX_FORMAT, os::current_thread_id());
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1487
    out.print_raw_cr(buf);
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1488
    out.print_raw_cr("Dumping core ...");
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1489
#endif
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1490
    ::abort(); // dump core
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1491
  }
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1492
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1493
  ::exit(1);
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1494
}
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1495
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1496
// Die immediately, no exit hook, no abort hook, no cleanup.
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1497
void os::die() {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1498
  // _exit() on LinuxThreads only kills current thread
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1499
  ::abort();
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1500
}
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1501
7405
e6fc8d3926f8 6348631: remove the use of the HPI library from Hotspot
ikrylov
parents: 7397
diff changeset
  1502
e6fc8d3926f8 6348631: remove the use of the HPI library from Hotspot
ikrylov
parents: 7397
diff changeset
  1503
// This method is a copy of JDK's sysGetLastErrorString
e6fc8d3926f8 6348631: remove the use of the HPI library from Hotspot
ikrylov
parents: 7397
diff changeset
  1504
// from src/solaris/hpi/src/system_md.c
e6fc8d3926f8 6348631: remove the use of the HPI library from Hotspot
ikrylov
parents: 7397
diff changeset
  1505
e6fc8d3926f8 6348631: remove the use of the HPI library from Hotspot
ikrylov
parents: 7397
diff changeset
  1506
size_t os::lasterror(char *buf, size_t len) {
e6fc8d3926f8 6348631: remove the use of the HPI library from Hotspot
ikrylov
parents: 7397
diff changeset
  1507
  if (errno == 0)  return 0;
e6fc8d3926f8 6348631: remove the use of the HPI library from Hotspot
ikrylov
parents: 7397
diff changeset
  1508
e6fc8d3926f8 6348631: remove the use of the HPI library from Hotspot
ikrylov
parents: 7397
diff changeset
  1509
  const char *s = ::strerror(errno);
e6fc8d3926f8 6348631: remove the use of the HPI library from Hotspot
ikrylov
parents: 7397
diff changeset
  1510
  size_t n = ::strlen(s);
e6fc8d3926f8 6348631: remove the use of the HPI library from Hotspot
ikrylov
parents: 7397
diff changeset
  1511
  if (n >= len) {
e6fc8d3926f8 6348631: remove the use of the HPI library from Hotspot
ikrylov
parents: 7397
diff changeset
  1512
    n = len - 1;
e6fc8d3926f8 6348631: remove the use of the HPI library from Hotspot
ikrylov
parents: 7397
diff changeset
  1513
  }
e6fc8d3926f8 6348631: remove the use of the HPI library from Hotspot
ikrylov
parents: 7397
diff changeset
  1514
  ::strncpy(buf, s, n);
e6fc8d3926f8 6348631: remove the use of the HPI library from Hotspot
ikrylov
parents: 7397
diff changeset
  1515
  buf[n] = '\0';
e6fc8d3926f8 6348631: remove the use of the HPI library from Hotspot
ikrylov
parents: 7397
diff changeset
  1516
  return n;
e6fc8d3926f8 6348631: remove the use of the HPI library from Hotspot
ikrylov
parents: 7397
diff changeset
  1517
}
e6fc8d3926f8 6348631: remove the use of the HPI library from Hotspot
ikrylov
parents: 7397
diff changeset
  1518
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1519
intx os::current_thread_id() { return (intx)pthread_self(); }
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1520
int os::current_process_id() {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1521
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1522
  // Under the old linux thread library, linux gives each thread
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1523
  // its own process id. Because of this each thread will return
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1524
  // a different pid if this method were to return the result
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1525
  // of getpid(2). Linux provides no api that returns the pid
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1526
  // of the launcher thread for the vm. This implementation
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1527
  // returns a unique pid, the pid of the launcher thread
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1528
  // that starts the vm 'process'.
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1529
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1530
  // Under the NPTL, getpid() returns the same pid as the
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1531
  // launcher thread rather than a unique pid per thread.
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1532
  // Use gettid() if you want the old pre NPTL behaviour.
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1533
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1534
  // if you are looking for the result of a call to getpid() that
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1535
  // returns a unique pid for the calling thread, then look at the
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1536
  // OSThread::thread_id() method in osThread_linux.hpp file
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1537
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1538
  return (int)(_initial_pid ? _initial_pid : getpid());
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1539
}
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1540
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1541
// DLL functions
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1542
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1543
const char* os::dll_file_extension() { return ".so"; }
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1544
7901
ea3d83447861 7009828: Fix for 6938627 breaks visualvm monitoring when -Djava.io.tmpdir is defined
coleenp
parents: 7458
diff changeset
  1545
// This must be hard coded because it's the system's temporary
ea3d83447861 7009828: Fix for 6938627 breaks visualvm monitoring when -Djava.io.tmpdir is defined
coleenp
parents: 7458
diff changeset
  1546
// directory not the java application's temp directory, ala java.io.tmpdir.
ea3d83447861 7009828: Fix for 6938627 breaks visualvm monitoring when -Djava.io.tmpdir is defined
coleenp
parents: 7458
diff changeset
  1547
const char* os::get_temp_directory() { return "/tmp"; }
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1548
2358
7c8346929fc6 6819213: revive sun.boot.library.path
phh
parents: 2268
diff changeset
  1549
static bool file_exists(const char* filename) {
7c8346929fc6 6819213: revive sun.boot.library.path
phh
parents: 2268
diff changeset
  1550
  struct stat statbuf;
7c8346929fc6 6819213: revive sun.boot.library.path
phh
parents: 2268
diff changeset
  1551
  if (filename == NULL || strlen(filename) == 0) {
7c8346929fc6 6819213: revive sun.boot.library.path
phh
parents: 2268
diff changeset
  1552
    return false;
7c8346929fc6 6819213: revive sun.boot.library.path
phh
parents: 2268
diff changeset
  1553
  }
7c8346929fc6 6819213: revive sun.boot.library.path
phh
parents: 2268
diff changeset
  1554
  return os::stat(filename, &statbuf) == 0;
7c8346929fc6 6819213: revive sun.boot.library.path
phh
parents: 2268
diff changeset
  1555
}
7c8346929fc6 6819213: revive sun.boot.library.path
phh
parents: 2268
diff changeset
  1556
14471
f3a6b82e25cf 8001185: parsing of sun.boot.library.path in os::dll_build_name somewhat broken
bpittore
parents: 13932
diff changeset
  1557
bool os::dll_build_name(char* buffer, size_t buflen,
2358
7c8346929fc6 6819213: revive sun.boot.library.path
phh
parents: 2268
diff changeset
  1558
                        const char* pname, const char* fname) {
14471
f3a6b82e25cf 8001185: parsing of sun.boot.library.path in os::dll_build_name somewhat broken
bpittore
parents: 13932
diff changeset
  1559
  bool retval = false;
2358
7c8346929fc6 6819213: revive sun.boot.library.path
phh
parents: 2268
diff changeset
  1560
  // Copied from libhpi
950
6112b627bb36 6721093: -XX:AppendRatio=N not supported
kamg
parents: 823
diff changeset
  1561
  const size_t pnamelen = pname ? strlen(pname) : 0;
6112b627bb36 6721093: -XX:AppendRatio=N not supported
kamg
parents: 823
diff changeset
  1562
14471
f3a6b82e25cf 8001185: parsing of sun.boot.library.path in os::dll_build_name somewhat broken
bpittore
parents: 13932
diff changeset
  1563
  // Return error on buffer overflow.
950
6112b627bb36 6721093: -XX:AppendRatio=N not supported
kamg
parents: 823
diff changeset
  1564
  if (pnamelen + strlen(fname) + 10 > (size_t) buflen) {
14471
f3a6b82e25cf 8001185: parsing of sun.boot.library.path in os::dll_build_name somewhat broken
bpittore
parents: 13932
diff changeset
  1565
    return retval;
950
6112b627bb36 6721093: -XX:AppendRatio=N not supported
kamg
parents: 823
diff changeset
  1566
  }
6112b627bb36 6721093: -XX:AppendRatio=N not supported
kamg
parents: 823
diff changeset
  1567
6112b627bb36 6721093: -XX:AppendRatio=N not supported
kamg
parents: 823
diff changeset
  1568
  if (pnamelen == 0) {
2358
7c8346929fc6 6819213: revive sun.boot.library.path
phh
parents: 2268
diff changeset
  1569
    snprintf(buffer, buflen, "lib%s.so", fname);
14471
f3a6b82e25cf 8001185: parsing of sun.boot.library.path in os::dll_build_name somewhat broken
bpittore
parents: 13932
diff changeset
  1570
    retval = true;
2358
7c8346929fc6 6819213: revive sun.boot.library.path
phh
parents: 2268
diff changeset
  1571
  } else if (strchr(pname, *os::path_separator()) != NULL) {
7c8346929fc6 6819213: revive sun.boot.library.path
phh
parents: 2268
diff changeset
  1572
    int n;
7c8346929fc6 6819213: revive sun.boot.library.path
phh
parents: 2268
diff changeset
  1573
    char** pelements = split_path(pname, &n);
16669
fb3397cee116 8006103: [parfait] Possible null pointer dereference at hotspot/src/os/linux/vm/os_linux.cpp; os_windows.cpp; os_solaris.cpp; os_bsd.cpp
ccheung
parents: 16438
diff changeset
  1574
    if (pelements == NULL) {
16672
dcubed
parents: 16609 16670
diff changeset
  1575
      return false;
16669
fb3397cee116 8006103: [parfait] Possible null pointer dereference at hotspot/src/os/linux/vm/os_linux.cpp; os_windows.cpp; os_solaris.cpp; os_bsd.cpp
ccheung
parents: 16438
diff changeset
  1576
    }
25064
244218e6ec0a 8046758: cleanup non-indent white space issues prior to Contended Locking cleanup bucket
dcubed
parents: 24931
diff changeset
  1577
    for (int i = 0; i < n; i++) {
2358
7c8346929fc6 6819213: revive sun.boot.library.path
phh
parents: 2268
diff changeset
  1578
      // Really shouldn't be NULL, but check can't hurt
7c8346929fc6 6819213: revive sun.boot.library.path
phh
parents: 2268
diff changeset
  1579
      if (pelements[i] == NULL || strlen(pelements[i]) == 0) {
7c8346929fc6 6819213: revive sun.boot.library.path
phh
parents: 2268
diff changeset
  1580
        continue; // skip the empty path values
7c8346929fc6 6819213: revive sun.boot.library.path
phh
parents: 2268
diff changeset
  1581
      }
7c8346929fc6 6819213: revive sun.boot.library.path
phh
parents: 2268
diff changeset
  1582
      snprintf(buffer, buflen, "%s/lib%s.so", pelements[i], fname);
7c8346929fc6 6819213: revive sun.boot.library.path
phh
parents: 2268
diff changeset
  1583
      if (file_exists(buffer)) {
14471
f3a6b82e25cf 8001185: parsing of sun.boot.library.path in os::dll_build_name somewhat broken
bpittore
parents: 13932
diff changeset
  1584
        retval = true;
2358
7c8346929fc6 6819213: revive sun.boot.library.path
phh
parents: 2268
diff changeset
  1585
        break;
7c8346929fc6 6819213: revive sun.boot.library.path
phh
parents: 2268
diff changeset
  1586
      }
7c8346929fc6 6819213: revive sun.boot.library.path
phh
parents: 2268
diff changeset
  1587
    }
7c8346929fc6 6819213: revive sun.boot.library.path
phh
parents: 2268
diff changeset
  1588
    // release the storage
25064
244218e6ec0a 8046758: cleanup non-indent white space issues prior to Contended Locking cleanup bucket
dcubed
parents: 24931
diff changeset
  1589
    for (int i = 0; i < n; i++) {
2358
7c8346929fc6 6819213: revive sun.boot.library.path
phh
parents: 2268
diff changeset
  1590
      if (pelements[i] != NULL) {
27880
afb974a04396 8060074: os::free() takes MemoryTrackingLevel but doesn't need it
coleenp
parents: 27474
diff changeset
  1591
        FREE_C_HEAP_ARRAY(char, pelements[i]);
2358
7c8346929fc6 6819213: revive sun.boot.library.path
phh
parents: 2268
diff changeset
  1592
      }
7c8346929fc6 6819213: revive sun.boot.library.path
phh
parents: 2268
diff changeset
  1593
    }
7c8346929fc6 6819213: revive sun.boot.library.path
phh
parents: 2268
diff changeset
  1594
    if (pelements != NULL) {
27880
afb974a04396 8060074: os::free() takes MemoryTrackingLevel but doesn't need it
coleenp
parents: 27474
diff changeset
  1595
      FREE_C_HEAP_ARRAY(char*, pelements);
2358
7c8346929fc6 6819213: revive sun.boot.library.path
phh
parents: 2268
diff changeset
  1596
    }
950
6112b627bb36 6721093: -XX:AppendRatio=N not supported
kamg
parents: 823
diff changeset
  1597
  } else {
2358
7c8346929fc6 6819213: revive sun.boot.library.path
phh
parents: 2268
diff changeset
  1598
    snprintf(buffer, buflen, "%s/lib%s.so", pname, fname);
14471
f3a6b82e25cf 8001185: parsing of sun.boot.library.path in os::dll_build_name somewhat broken
bpittore
parents: 13932
diff changeset
  1599
    retval = true;
f3a6b82e25cf 8001185: parsing of sun.boot.library.path in os::dll_build_name somewhat broken
bpittore
parents: 13932
diff changeset
  1600
  }
f3a6b82e25cf 8001185: parsing of sun.boot.library.path in os::dll_build_name somewhat broken
bpittore
parents: 13932
diff changeset
  1601
  return retval;
950
6112b627bb36 6721093: -XX:AppendRatio=N not supported
kamg
parents: 823
diff changeset
  1602
}
6112b627bb36 6721093: -XX:AppendRatio=N not supported
kamg
parents: 823
diff changeset
  1603
15096
3db45569f8c0 8005044: remove crufty '_g' support from HS runtime code
dcubed
parents: 14633
diff changeset
  1604
// check if addr is inside libjvm.so
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1605
bool os::address_is_in_vm(address addr) {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1606
  static address libjvm_base_addr;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1607
  Dl_info dlinfo;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1608
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1609
  if (libjvm_base_addr == NULL) {
18683
a6418e038255 8015884: runThese crashed with SIGSEGV, hs_err has an error instead of stacktrace
dcubed
parents: 18086
diff changeset
  1610
    if (dladdr(CAST_FROM_FN_PTR(void *, os::address_is_in_vm), &dlinfo) != 0) {
a6418e038255 8015884: runThese crashed with SIGSEGV, hs_err has an error instead of stacktrace
dcubed
parents: 18086
diff changeset
  1611
      libjvm_base_addr = (address)dlinfo.dli_fbase;
a6418e038255 8015884: runThese crashed with SIGSEGV, hs_err has an error instead of stacktrace
dcubed
parents: 18086
diff changeset
  1612
    }
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1613
    assert(libjvm_base_addr !=NULL, "Cannot obtain base address for libjvm");
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1614
  }
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1615
18683
a6418e038255 8015884: runThese crashed with SIGSEGV, hs_err has an error instead of stacktrace
dcubed
parents: 18086
diff changeset
  1616
  if (dladdr((void *)addr, &dlinfo) != 0) {
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1617
    if (libjvm_base_addr == (address)dlinfo.dli_fbase) return true;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1618
  }
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1619
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1620
  return false;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1621
}
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1622
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1623
bool os::dll_address_to_function_name(address addr, char *buf,
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1624
                                      int buflen, int *offset) {
18683
a6418e038255 8015884: runThese crashed with SIGSEGV, hs_err has an error instead of stacktrace
dcubed
parents: 18086
diff changeset
  1625
  // buf is not optional, but offset is optional
a6418e038255 8015884: runThese crashed with SIGSEGV, hs_err has an error instead of stacktrace
dcubed
parents: 18086
diff changeset
  1626
  assert(buf != NULL, "sanity check");
a6418e038255 8015884: runThese crashed with SIGSEGV, hs_err has an error instead of stacktrace
dcubed
parents: 18086
diff changeset
  1627
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1628
  Dl_info dlinfo;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1629
18683
a6418e038255 8015884: runThese crashed with SIGSEGV, hs_err has an error instead of stacktrace
dcubed
parents: 18086
diff changeset
  1630
  if (dladdr((void*)addr, &dlinfo) != 0) {
a6418e038255 8015884: runThese crashed with SIGSEGV, hs_err has an error instead of stacktrace
dcubed
parents: 18086
diff changeset
  1631
    // see if we have a matching symbol
a6418e038255 8015884: runThese crashed with SIGSEGV, hs_err has an error instead of stacktrace
dcubed
parents: 18086
diff changeset
  1632
    if (dlinfo.dli_saddr != NULL && dlinfo.dli_sname != NULL) {
a6418e038255 8015884: runThese crashed with SIGSEGV, hs_err has an error instead of stacktrace
dcubed
parents: 18086
diff changeset
  1633
      if (!Decoder::demangle(dlinfo.dli_sname, buf, buflen)) {
7447
32c42d627f41 7003748: Decode C stack frames when symbols are presented (PhoneHome project)
zgu
parents: 7397
diff changeset
  1634
        jio_snprintf(buf, buflen, "%s", dlinfo.dli_sname);
32c42d627f41 7003748: Decode C stack frames when symbols are presented (PhoneHome project)
zgu
parents: 7397
diff changeset
  1635
      }
18683
a6418e038255 8015884: runThese crashed with SIGSEGV, hs_err has an error instead of stacktrace
dcubed
parents: 18086
diff changeset
  1636
      if (offset != NULL) *offset = addr - (address)dlinfo.dli_saddr;
a6418e038255 8015884: runThese crashed with SIGSEGV, hs_err has an error instead of stacktrace
dcubed
parents: 18086
diff changeset
  1637
      return true;
a6418e038255 8015884: runThese crashed with SIGSEGV, hs_err has an error instead of stacktrace
dcubed
parents: 18086
diff changeset
  1638
    }
a6418e038255 8015884: runThese crashed with SIGSEGV, hs_err has an error instead of stacktrace
dcubed
parents: 18086
diff changeset
  1639
    // no matching symbol so try for just file info
a6418e038255 8015884: runThese crashed with SIGSEGV, hs_err has an error instead of stacktrace
dcubed
parents: 18086
diff changeset
  1640
    if (dlinfo.dli_fname != NULL && dlinfo.dli_fbase != NULL) {
a6418e038255 8015884: runThese crashed with SIGSEGV, hs_err has an error instead of stacktrace
dcubed
parents: 18086
diff changeset
  1641
      if (Decoder::decode((address)(addr - (address)dlinfo.dli_fbase),
a6418e038255 8015884: runThese crashed with SIGSEGV, hs_err has an error instead of stacktrace
dcubed
parents: 18086
diff changeset
  1642
                          buf, buflen, offset, dlinfo.dli_fname)) {
a6418e038255 8015884: runThese crashed with SIGSEGV, hs_err has an error instead of stacktrace
dcubed
parents: 18086
diff changeset
  1643
        return true;
a6418e038255 8015884: runThese crashed with SIGSEGV, hs_err has an error instead of stacktrace
dcubed
parents: 18086
diff changeset
  1644
      }
7447
32c42d627f41 7003748: Decode C stack frames when symbols are presented (PhoneHome project)
zgu
parents: 7397
diff changeset
  1645
    }
18683
a6418e038255 8015884: runThese crashed with SIGSEGV, hs_err has an error instead of stacktrace
dcubed
parents: 18086
diff changeset
  1646
  }
a6418e038255 8015884: runThese crashed with SIGSEGV, hs_err has an error instead of stacktrace
dcubed
parents: 18086
diff changeset
  1647
a6418e038255 8015884: runThese crashed with SIGSEGV, hs_err has an error instead of stacktrace
dcubed
parents: 18086
diff changeset
  1648
  buf[0] = '\0';
7447
32c42d627f41 7003748: Decode C stack frames when symbols are presented (PhoneHome project)
zgu
parents: 7397
diff changeset
  1649
  if (offset != NULL) *offset = -1;
32c42d627f41 7003748: Decode C stack frames when symbols are presented (PhoneHome project)
zgu
parents: 7397
diff changeset
  1650
  return false;
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1651
}
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1652
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1653
struct _address_to_library_name {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1654
  address addr;          // input : memory address
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1655
  size_t  buflen;        //         size of fname
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1656
  char*   fname;         // output: library name
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1657
  address base;          //         library base addr
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1658
};
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1659
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1660
static int address_to_library_name_callback(struct dl_phdr_info *info,
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1661
                                            size_t size, void *data) {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1662
  int i;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1663
  bool found = false;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1664
  address libbase = NULL;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1665
  struct _address_to_library_name * d = (struct _address_to_library_name *)data;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1666
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1667
  // iterate through all loadable segments
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1668
  for (i = 0; i < info->dlpi_phnum; i++) {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1669
    address segbase = (address)(info->dlpi_addr + info->dlpi_phdr[i].p_vaddr);
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1670
    if (info->dlpi_phdr[i].p_type == PT_LOAD) {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1671
      // base address of a library is the lowest address of its loaded
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1672
      // segments.
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1673
      if (libbase == NULL || libbase > segbase) {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1674
        libbase = segbase;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1675
      }
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1676
      // see if 'addr' is within current segment
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1677
      if (segbase <= d->addr &&
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1678
          d->addr < segbase + info->dlpi_phdr[i].p_memsz) {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1679
        found = true;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1680
      }
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1681
    }
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1682
  }
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1683
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1684
  // dlpi_name is NULL or empty if the ELF file is executable, return 0
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1685
  // so dll_address_to_library_name() can fall through to use dladdr() which
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1686
  // can figure out executable name from argv[0].
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1687
  if (found && info->dlpi_name && info->dlpi_name[0]) {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1688
    d->base = libbase;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1689
    if (d->fname) {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1690
      jio_snprintf(d->fname, d->buflen, "%s", info->dlpi_name);
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1691
    }
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1692
    return 1;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1693
  }
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1694
  return 0;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1695
}
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1696
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1697
bool os::dll_address_to_library_name(address addr, char* buf,
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1698
                                     int buflen, int* offset) {
18683
a6418e038255 8015884: runThese crashed with SIGSEGV, hs_err has an error instead of stacktrace
dcubed
parents: 18086
diff changeset
  1699
  // buf is not optional, but offset is optional
a6418e038255 8015884: runThese crashed with SIGSEGV, hs_err has an error instead of stacktrace
dcubed
parents: 18086
diff changeset
  1700
  assert(buf != NULL, "sanity check");
a6418e038255 8015884: runThese crashed with SIGSEGV, hs_err has an error instead of stacktrace
dcubed
parents: 18086
diff changeset
  1701
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1702
  Dl_info dlinfo;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1703
  struct _address_to_library_name data;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1704
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1705
  // There is a bug in old glibc dladdr() implementation that it could resolve
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1706
  // to wrong library name if the .so file has a base address != NULL. Here
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1707
  // we iterate through the program headers of all loaded libraries to find
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1708
  // out which library 'addr' really belongs to. This workaround can be
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1709
  // removed once the minimum requirement for glibc is moved to 2.3.x.
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1710
  data.addr = addr;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1711
  data.fname = buf;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1712
  data.buflen = buflen;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1713
  data.base = NULL;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1714
  int rslt = dl_iterate_phdr(address_to_library_name_callback, (void *)&data);
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1715
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1716
  if (rslt) {
26683
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  1717
    // buf already contains library name
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  1718
    if (offset) *offset = addr - data.base;
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  1719
    return true;
18683
a6418e038255 8015884: runThese crashed with SIGSEGV, hs_err has an error instead of stacktrace
dcubed
parents: 18086
diff changeset
  1720
  }
a6418e038255 8015884: runThese crashed with SIGSEGV, hs_err has an error instead of stacktrace
dcubed
parents: 18086
diff changeset
  1721
  if (dladdr((void*)addr, &dlinfo) != 0) {
a6418e038255 8015884: runThese crashed with SIGSEGV, hs_err has an error instead of stacktrace
dcubed
parents: 18086
diff changeset
  1722
    if (dlinfo.dli_fname != NULL) {
a6418e038255 8015884: runThese crashed with SIGSEGV, hs_err has an error instead of stacktrace
dcubed
parents: 18086
diff changeset
  1723
      jio_snprintf(buf, buflen, "%s", dlinfo.dli_fname);
a6418e038255 8015884: runThese crashed with SIGSEGV, hs_err has an error instead of stacktrace
dcubed
parents: 18086
diff changeset
  1724
    }
a6418e038255 8015884: runThese crashed with SIGSEGV, hs_err has an error instead of stacktrace
dcubed
parents: 18086
diff changeset
  1725
    if (dlinfo.dli_fbase != NULL && offset != NULL) {
a6418e038255 8015884: runThese crashed with SIGSEGV, hs_err has an error instead of stacktrace
dcubed
parents: 18086
diff changeset
  1726
      *offset = addr - (address)dlinfo.dli_fbase;
a6418e038255 8015884: runThese crashed with SIGSEGV, hs_err has an error instead of stacktrace
dcubed
parents: 18086
diff changeset
  1727
    }
a6418e038255 8015884: runThese crashed with SIGSEGV, hs_err has an error instead of stacktrace
dcubed
parents: 18086
diff changeset
  1728
    return true;
a6418e038255 8015884: runThese crashed with SIGSEGV, hs_err has an error instead of stacktrace
dcubed
parents: 18086
diff changeset
  1729
  }
a6418e038255 8015884: runThese crashed with SIGSEGV, hs_err has an error instead of stacktrace
dcubed
parents: 18086
diff changeset
  1730
a6418e038255 8015884: runThese crashed with SIGSEGV, hs_err has an error instead of stacktrace
dcubed
parents: 18086
diff changeset
  1731
  buf[0] = '\0';
a6418e038255 8015884: runThese crashed with SIGSEGV, hs_err has an error instead of stacktrace
dcubed
parents: 18086
diff changeset
  1732
  if (offset) *offset = -1;
a6418e038255 8015884: runThese crashed with SIGSEGV, hs_err has an error instead of stacktrace
dcubed
parents: 18086
diff changeset
  1733
  return false;
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1734
}
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1735
26683
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  1736
// Loads .dll/.so and
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  1737
// in case of error it checks if .dll/.so was built for the
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  1738
// same architecture as Hotspot is running on
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1739
15926
8e87d545195f 7107135: Stack guard pages are no more protected after loading a shared library with executable stack
iklam
parents: 15855
diff changeset
  1740
8e87d545195f 7107135: Stack guard pages are no more protected after loading a shared library with executable stack
iklam
parents: 15855
diff changeset
  1741
// Remember the stack's state. The Linux dynamic linker will change
8e87d545195f 7107135: Stack guard pages are no more protected after loading a shared library with executable stack
iklam
parents: 15855
diff changeset
  1742
// the stack to 'executable' at most once, so we must safepoint only once.
8e87d545195f 7107135: Stack guard pages are no more protected after loading a shared library with executable stack
iklam
parents: 15855
diff changeset
  1743
bool os::Linux::_stack_is_executable = false;
8e87d545195f 7107135: Stack guard pages are no more protected after loading a shared library with executable stack
iklam
parents: 15855
diff changeset
  1744
8e87d545195f 7107135: Stack guard pages are no more protected after loading a shared library with executable stack
iklam
parents: 15855
diff changeset
  1745
// VM operation that loads a library.  This is necessary if stack protection
8e87d545195f 7107135: Stack guard pages are no more protected after loading a shared library with executable stack
iklam
parents: 15855
diff changeset
  1746
// of the Java stacks can be lost during loading the library.  If we
8e87d545195f 7107135: Stack guard pages are no more protected after loading a shared library with executable stack
iklam
parents: 15855
diff changeset
  1747
// do not stop the Java threads, they can stack overflow before the stacks
8e87d545195f 7107135: Stack guard pages are no more protected after loading a shared library with executable stack
iklam
parents: 15855
diff changeset
  1748
// are protected again.
8e87d545195f 7107135: Stack guard pages are no more protected after loading a shared library with executable stack
iklam
parents: 15855
diff changeset
  1749
class VM_LinuxDllLoad: public VM_Operation {
8e87d545195f 7107135: Stack guard pages are no more protected after loading a shared library with executable stack
iklam
parents: 15855
diff changeset
  1750
 private:
8e87d545195f 7107135: Stack guard pages are no more protected after loading a shared library with executable stack
iklam
parents: 15855
diff changeset
  1751
  const char *_filename;
16438
245d5c0a8dd8 8010389: After fix for 7107135 a failed dlopen() call results in a VM crash
iklam
parents: 15927
diff changeset
  1752
  char *_ebuf;
245d5c0a8dd8 8010389: After fix for 7107135 a failed dlopen() call results in a VM crash
iklam
parents: 15927
diff changeset
  1753
  int _ebuflen;
15926
8e87d545195f 7107135: Stack guard pages are no more protected after loading a shared library with executable stack
iklam
parents: 15855
diff changeset
  1754
  void *_lib;
8e87d545195f 7107135: Stack guard pages are no more protected after loading a shared library with executable stack
iklam
parents: 15855
diff changeset
  1755
 public:
16438
245d5c0a8dd8 8010389: After fix for 7107135 a failed dlopen() call results in a VM crash
iklam
parents: 15927
diff changeset
  1756
  VM_LinuxDllLoad(const char *fn, char *ebuf, int ebuflen) :
245d5c0a8dd8 8010389: After fix for 7107135 a failed dlopen() call results in a VM crash
iklam
parents: 15927
diff changeset
  1757
    _filename(fn), _ebuf(ebuf), _ebuflen(ebuflen), _lib(NULL) {}
15926
8e87d545195f 7107135: Stack guard pages are no more protected after loading a shared library with executable stack
iklam
parents: 15855
diff changeset
  1758
  VMOp_Type type() const { return VMOp_LinuxDllLoad; }
8e87d545195f 7107135: Stack guard pages are no more protected after loading a shared library with executable stack
iklam
parents: 15855
diff changeset
  1759
  void doit() {
16438
245d5c0a8dd8 8010389: After fix for 7107135 a failed dlopen() call results in a VM crash
iklam
parents: 15927
diff changeset
  1760
    _lib = os::Linux::dll_load_in_vmthread(_filename, _ebuf, _ebuflen);
15926
8e87d545195f 7107135: Stack guard pages are no more protected after loading a shared library with executable stack
iklam
parents: 15855
diff changeset
  1761
    os::Linux::_stack_is_executable = true;
8e87d545195f 7107135: Stack guard pages are no more protected after loading a shared library with executable stack
iklam
parents: 15855
diff changeset
  1762
  }
8e87d545195f 7107135: Stack guard pages are no more protected after loading a shared library with executable stack
iklam
parents: 15855
diff changeset
  1763
  void* loaded_library() { return _lib; }
8e87d545195f 7107135: Stack guard pages are no more protected after loading a shared library with executable stack
iklam
parents: 15855
diff changeset
  1764
};
8e87d545195f 7107135: Stack guard pages are no more protected after loading a shared library with executable stack
iklam
parents: 15855
diff changeset
  1765
26684
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
  1766
void * os::dll_load(const char *filename, char *ebuf, int ebuflen) {
15926
8e87d545195f 7107135: Stack guard pages are no more protected after loading a shared library with executable stack
iklam
parents: 15855
diff changeset
  1767
  void * result = NULL;
8e87d545195f 7107135: Stack guard pages are no more protected after loading a shared library with executable stack
iklam
parents: 15855
diff changeset
  1768
  bool load_attempted = false;
8e87d545195f 7107135: Stack guard pages are no more protected after loading a shared library with executable stack
iklam
parents: 15855
diff changeset
  1769
8e87d545195f 7107135: Stack guard pages are no more protected after loading a shared library with executable stack
iklam
parents: 15855
diff changeset
  1770
  // Check whether the library to load might change execution rights
8e87d545195f 7107135: Stack guard pages are no more protected after loading a shared library with executable stack
iklam
parents: 15855
diff changeset
  1771
  // of the stack. If they are changed, the protection of the stack
8e87d545195f 7107135: Stack guard pages are no more protected after loading a shared library with executable stack
iklam
parents: 15855
diff changeset
  1772
  // guard pages will be lost. We need a safepoint to fix this.
8e87d545195f 7107135: Stack guard pages are no more protected after loading a shared library with executable stack
iklam
parents: 15855
diff changeset
  1773
  //
8e87d545195f 7107135: Stack guard pages are no more protected after loading a shared library with executable stack
iklam
parents: 15855
diff changeset
  1774
  // See Linux man page execstack(8) for more info.
8e87d545195f 7107135: Stack guard pages are no more protected after loading a shared library with executable stack
iklam
parents: 15855
diff changeset
  1775
  if (os::uses_stack_guard_pages() && !os::Linux::_stack_is_executable) {
8e87d545195f 7107135: Stack guard pages are no more protected after loading a shared library with executable stack
iklam
parents: 15855
diff changeset
  1776
    ElfFile ef(filename);
8e87d545195f 7107135: Stack guard pages are no more protected after loading a shared library with executable stack
iklam
parents: 15855
diff changeset
  1777
    if (!ef.specifies_noexecstack()) {
8e87d545195f 7107135: Stack guard pages are no more protected after loading a shared library with executable stack
iklam
parents: 15855
diff changeset
  1778
      if (!is_init_completed()) {
8e87d545195f 7107135: Stack guard pages are no more protected after loading a shared library with executable stack
iklam
parents: 15855
diff changeset
  1779
        os::Linux::_stack_is_executable = true;
8e87d545195f 7107135: Stack guard pages are no more protected after loading a shared library with executable stack
iklam
parents: 15855
diff changeset
  1780
        // This is OK - No Java threads have been created yet, and hence no
8e87d545195f 7107135: Stack guard pages are no more protected after loading a shared library with executable stack
iklam
parents: 15855
diff changeset
  1781
        // stack guard pages to fix.
8e87d545195f 7107135: Stack guard pages are no more protected after loading a shared library with executable stack
iklam
parents: 15855
diff changeset
  1782
        //
8e87d545195f 7107135: Stack guard pages are no more protected after loading a shared library with executable stack
iklam
parents: 15855
diff changeset
  1783
        // This should happen only when you are building JDK7 using a very
8e87d545195f 7107135: Stack guard pages are no more protected after loading a shared library with executable stack
iklam
parents: 15855
diff changeset
  1784
        // old version of JDK6 (e.g., with JPRT) and running test_gamma.
8e87d545195f 7107135: Stack guard pages are no more protected after loading a shared library with executable stack
iklam
parents: 15855
diff changeset
  1785
        //
8e87d545195f 7107135: Stack guard pages are no more protected after loading a shared library with executable stack
iklam
parents: 15855
diff changeset
  1786
        // Dynamic loader will make all stacks executable after
8e87d545195f 7107135: Stack guard pages are no more protected after loading a shared library with executable stack
iklam
parents: 15855
diff changeset
  1787
        // this function returns, and will not do that again.
8e87d545195f 7107135: Stack guard pages are no more protected after loading a shared library with executable stack
iklam
parents: 15855
diff changeset
  1788
        assert(Threads::first() == NULL, "no Java threads should exist yet.");
8e87d545195f 7107135: Stack guard pages are no more protected after loading a shared library with executable stack
iklam
parents: 15855
diff changeset
  1789
      } else {
8e87d545195f 7107135: Stack guard pages are no more protected after loading a shared library with executable stack
iklam
parents: 15855
diff changeset
  1790
        warning("You have loaded library %s which might have disabled stack guard. "
8e87d545195f 7107135: Stack guard pages are no more protected after loading a shared library with executable stack
iklam
parents: 15855
diff changeset
  1791
                "The VM will try to fix the stack guard now.\n"
8e87d545195f 7107135: Stack guard pages are no more protected after loading a shared library with executable stack
iklam
parents: 15855
diff changeset
  1792
                "It's highly recommended that you fix the library with "
8e87d545195f 7107135: Stack guard pages are no more protected after loading a shared library with executable stack
iklam
parents: 15855
diff changeset
  1793
                "'execstack -c <libfile>', or link it with '-z noexecstack'.",
8e87d545195f 7107135: Stack guard pages are no more protected after loading a shared library with executable stack
iklam
parents: 15855
diff changeset
  1794
                filename);
8e87d545195f 7107135: Stack guard pages are no more protected after loading a shared library with executable stack
iklam
parents: 15855
diff changeset
  1795
8e87d545195f 7107135: Stack guard pages are no more protected after loading a shared library with executable stack
iklam
parents: 15855
diff changeset
  1796
        assert(Thread::current()->is_Java_thread(), "must be Java thread");
8e87d545195f 7107135: Stack guard pages are no more protected after loading a shared library with executable stack
iklam
parents: 15855
diff changeset
  1797
        JavaThread *jt = JavaThread::current();
8e87d545195f 7107135: Stack guard pages are no more protected after loading a shared library with executable stack
iklam
parents: 15855
diff changeset
  1798
        if (jt->thread_state() != _thread_in_native) {
8e87d545195f 7107135: Stack guard pages are no more protected after loading a shared library with executable stack
iklam
parents: 15855
diff changeset
  1799
          // This happens when a compiler thread tries to load a hsdis-<arch>.so file
8e87d545195f 7107135: Stack guard pages are no more protected after loading a shared library with executable stack
iklam
parents: 15855
diff changeset
  1800
          // that requires ExecStack. Cannot enter safe point. Let's give up.
8e87d545195f 7107135: Stack guard pages are no more protected after loading a shared library with executable stack
iklam
parents: 15855
diff changeset
  1801
          warning("Unable to fix stack guard. Giving up.");
8e87d545195f 7107135: Stack guard pages are no more protected after loading a shared library with executable stack
iklam
parents: 15855
diff changeset
  1802
        } else {
8e87d545195f 7107135: Stack guard pages are no more protected after loading a shared library with executable stack
iklam
parents: 15855
diff changeset
  1803
          if (!LoadExecStackDllInVMThread) {
8e87d545195f 7107135: Stack guard pages are no more protected after loading a shared library with executable stack
iklam
parents: 15855
diff changeset
  1804
            // This is for the case where the DLL has an static
8e87d545195f 7107135: Stack guard pages are no more protected after loading a shared library with executable stack
iklam
parents: 15855
diff changeset
  1805
            // constructor function that executes JNI code. We cannot
8e87d545195f 7107135: Stack guard pages are no more protected after loading a shared library with executable stack
iklam
parents: 15855
diff changeset
  1806
            // load such DLLs in the VMThread.
16438
245d5c0a8dd8 8010389: After fix for 7107135 a failed dlopen() call results in a VM crash
iklam
parents: 15927
diff changeset
  1807
            result = os::Linux::dlopen_helper(filename, ebuf, ebuflen);
15926
8e87d545195f 7107135: Stack guard pages are no more protected after loading a shared library with executable stack
iklam
parents: 15855
diff changeset
  1808
          }
8e87d545195f 7107135: Stack guard pages are no more protected after loading a shared library with executable stack
iklam
parents: 15855
diff changeset
  1809
8e87d545195f 7107135: Stack guard pages are no more protected after loading a shared library with executable stack
iklam
parents: 15855
diff changeset
  1810
          ThreadInVMfromNative tiv(jt);
8e87d545195f 7107135: Stack guard pages are no more protected after loading a shared library with executable stack
iklam
parents: 15855
diff changeset
  1811
          debug_only(VMNativeEntryWrapper vew;)
8e87d545195f 7107135: Stack guard pages are no more protected after loading a shared library with executable stack
iklam
parents: 15855
diff changeset
  1812
16438
245d5c0a8dd8 8010389: After fix for 7107135 a failed dlopen() call results in a VM crash
iklam
parents: 15927
diff changeset
  1813
          VM_LinuxDllLoad op(filename, ebuf, ebuflen);
15926
8e87d545195f 7107135: Stack guard pages are no more protected after loading a shared library with executable stack
iklam
parents: 15855
diff changeset
  1814
          VMThread::execute(&op);
8e87d545195f 7107135: Stack guard pages are no more protected after loading a shared library with executable stack
iklam
parents: 15855
diff changeset
  1815
          if (LoadExecStackDllInVMThread) {
8e87d545195f 7107135: Stack guard pages are no more protected after loading a shared library with executable stack
iklam
parents: 15855
diff changeset
  1816
            result = op.loaded_library();
8e87d545195f 7107135: Stack guard pages are no more protected after loading a shared library with executable stack
iklam
parents: 15855
diff changeset
  1817
          }
8e87d545195f 7107135: Stack guard pages are no more protected after loading a shared library with executable stack
iklam
parents: 15855
diff changeset
  1818
          load_attempted = true;
8e87d545195f 7107135: Stack guard pages are no more protected after loading a shared library with executable stack
iklam
parents: 15855
diff changeset
  1819
        }
8e87d545195f 7107135: Stack guard pages are no more protected after loading a shared library with executable stack
iklam
parents: 15855
diff changeset
  1820
      }
8e87d545195f 7107135: Stack guard pages are no more protected after loading a shared library with executable stack
iklam
parents: 15855
diff changeset
  1821
    }
8e87d545195f 7107135: Stack guard pages are no more protected after loading a shared library with executable stack
iklam
parents: 15855
diff changeset
  1822
  }
8e87d545195f 7107135: Stack guard pages are no more protected after loading a shared library with executable stack
iklam
parents: 15855
diff changeset
  1823
8e87d545195f 7107135: Stack guard pages are no more protected after loading a shared library with executable stack
iklam
parents: 15855
diff changeset
  1824
  if (!load_attempted) {
16438
245d5c0a8dd8 8010389: After fix for 7107135 a failed dlopen() call results in a VM crash
iklam
parents: 15927
diff changeset
  1825
    result = os::Linux::dlopen_helper(filename, ebuf, ebuflen);
15926
8e87d545195f 7107135: Stack guard pages are no more protected after loading a shared library with executable stack
iklam
parents: 15855
diff changeset
  1826
  }
8e87d545195f 7107135: Stack guard pages are no more protected after loading a shared library with executable stack
iklam
parents: 15855
diff changeset
  1827
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1828
  if (result != NULL) {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1829
    // Successful loading
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1830
    return result;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1831
  }
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1832
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1833
  Elf32_Ehdr elf_head;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1834
  int diag_msg_max_length=ebuflen-strlen(ebuf);
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1835
  char* diag_msg_buf=ebuf+strlen(ebuf);
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1836
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1837
  if (diag_msg_max_length==0) {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1838
    // No more space in ebuf for additional diagnostics message
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1839
    return NULL;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1840
  }
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1841
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1842
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1843
  int file_descriptor= ::open(filename, O_RDONLY | O_NONBLOCK);
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1844
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1845
  if (file_descriptor < 0) {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1846
    // Can't open library, report dlerror() message
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1847
    return NULL;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1848
  }
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1849
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1850
  bool failed_to_read_elf_head=
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1851
    (sizeof(elf_head)!=
26683
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  1852
     (::read(file_descriptor, &elf_head,sizeof(elf_head))));
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1853
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1854
  ::close(file_descriptor);
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1855
  if (failed_to_read_elf_head) {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1856
    // file i/o error - report dlerror() msg
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1857
    return NULL;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1858
  }
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1859
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1860
  typedef struct {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1861
    Elf32_Half  code;         // Actual value as defined in elf.h
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1862
    Elf32_Half  compat_class; // Compatibility of archs at VM's sense
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1863
    char        elf_class;    // 32 or 64 bit
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1864
    char        endianess;    // MSB or LSB
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1865
    char*       name;         // String representation
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1866
  } arch_t;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1867
26684
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
  1868
#ifndef EM_486
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1869
  #define EM_486          6               /* Intel 80486 */
26684
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
  1870
#endif
29180
50369728b00e 8064611: AARCH64: Changes to HotSpot shared code
aph
parents: 27474
diff changeset
  1871
#ifndef EM_AARCH64
50369728b00e 8064611: AARCH64: Changes to HotSpot shared code
aph
parents: 27474
diff changeset
  1872
  #define EM_AARCH64    183               /* ARM AARCH64 */
50369728b00e 8064611: AARCH64: Changes to HotSpot shared code
aph
parents: 27474
diff changeset
  1873
#endif
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1874
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1875
  static const arch_t arch_array[]={
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1876
    {EM_386,         EM_386,     ELFCLASS32, ELFDATA2LSB, (char*)"IA 32"},
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1877
    {EM_486,         EM_386,     ELFCLASS32, ELFDATA2LSB, (char*)"IA 32"},
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1878
    {EM_IA_64,       EM_IA_64,   ELFCLASS64, ELFDATA2LSB, (char*)"IA 64"},
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1879
    {EM_X86_64,      EM_X86_64,  ELFCLASS64, ELFDATA2LSB, (char*)"AMD 64"},
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1880
    {EM_SPARC,       EM_SPARC,   ELFCLASS32, ELFDATA2MSB, (char*)"Sparc 32"},
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1881
    {EM_SPARC32PLUS, EM_SPARC,   ELFCLASS32, ELFDATA2MSB, (char*)"Sparc 32"},
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1882
    {EM_SPARCV9,     EM_SPARCV9, ELFCLASS64, ELFDATA2MSB, (char*)"Sparc v9 64"},
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1883
    {EM_PPC,         EM_PPC,     ELFCLASS32, ELFDATA2MSB, (char*)"Power PC 32"},
23532
7e8719ce96ea 8036767: PPC64: Support for little endian execution model
kvn
parents: 23479
diff changeset
  1884
#if defined(VM_LITTLE_ENDIAN)
7e8719ce96ea 8036767: PPC64: Support for little endian execution model
kvn
parents: 23479
diff changeset
  1885
    {EM_PPC64,       EM_PPC64,   ELFCLASS64, ELFDATA2LSB, (char*)"Power PC 64"},
7e8719ce96ea 8036767: PPC64: Support for little endian execution model
kvn
parents: 23479
diff changeset
  1886
#else
4013
b154310845de 6890308: integrate zero assembler hotspot changes
never
parents: 2753
diff changeset
  1887
    {EM_PPC64,       EM_PPC64,   ELFCLASS64, ELFDATA2MSB, (char*)"Power PC 64"},
23532
7e8719ce96ea 8036767: PPC64: Support for little endian execution model
kvn
parents: 23479
diff changeset
  1888
#endif
4013
b154310845de 6890308: integrate zero assembler hotspot changes
never
parents: 2753
diff changeset
  1889
    {EM_ARM,         EM_ARM,     ELFCLASS32,   ELFDATA2LSB, (char*)"ARM"},
b154310845de 6890308: integrate zero assembler hotspot changes
never
parents: 2753
diff changeset
  1890
    {EM_S390,        EM_S390,    ELFCLASSNONE, ELFDATA2MSB, (char*)"IBM System/390"},
b154310845de 6890308: integrate zero assembler hotspot changes
never
parents: 2753
diff changeset
  1891
    {EM_ALPHA,       EM_ALPHA,   ELFCLASS64, ELFDATA2LSB, (char*)"Alpha"},
b154310845de 6890308: integrate zero assembler hotspot changes
never
parents: 2753
diff changeset
  1892
    {EM_MIPS_RS3_LE, EM_MIPS_RS3_LE, ELFCLASS32, ELFDATA2LSB, (char*)"MIPSel"},
b154310845de 6890308: integrate zero assembler hotspot changes
never
parents: 2753
diff changeset
  1893
    {EM_MIPS,        EM_MIPS,    ELFCLASS32, ELFDATA2MSB, (char*)"MIPS"},
b154310845de 6890308: integrate zero assembler hotspot changes
never
parents: 2753
diff changeset
  1894
    {EM_PARISC,      EM_PARISC,  ELFCLASS32, ELFDATA2MSB, (char*)"PARISC"},
29180
50369728b00e 8064611: AARCH64: Changes to HotSpot shared code
aph
parents: 27474
diff changeset
  1895
    {EM_68K,         EM_68K,     ELFCLASS32, ELFDATA2MSB, (char*)"M68k"},
50369728b00e 8064611: AARCH64: Changes to HotSpot shared code
aph
parents: 27474
diff changeset
  1896
    {EM_AARCH64,     EM_AARCH64, ELFCLASS64, ELFDATA2LSB, (char*)"AARCH64"},
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1897
  };
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1898
26684
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
  1899
#if  (defined IA32)
26683
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  1900
  static  Elf32_Half running_arch_code=EM_386;
26684
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
  1901
#elif   (defined AMD64)
26683
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  1902
  static  Elf32_Half running_arch_code=EM_X86_64;
26684
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
  1903
#elif  (defined IA64)
26683
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  1904
  static  Elf32_Half running_arch_code=EM_IA_64;
26684
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
  1905
#elif  (defined __sparc) && (defined _LP64)
26683
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  1906
  static  Elf32_Half running_arch_code=EM_SPARCV9;
26684
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
  1907
#elif  (defined __sparc) && (!defined _LP64)
26683
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  1908
  static  Elf32_Half running_arch_code=EM_SPARC;
26684
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
  1909
#elif  (defined __powerpc64__)
26683
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  1910
  static  Elf32_Half running_arch_code=EM_PPC64;
26684
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
  1911
#elif  (defined __powerpc__)
26683
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  1912
  static  Elf32_Half running_arch_code=EM_PPC;
26684
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
  1913
#elif  (defined ARM)
26683
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  1914
  static  Elf32_Half running_arch_code=EM_ARM;
26684
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
  1915
#elif  (defined S390)
26683
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  1916
  static  Elf32_Half running_arch_code=EM_S390;
26684
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
  1917
#elif  (defined ALPHA)
26683
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  1918
  static  Elf32_Half running_arch_code=EM_ALPHA;
26684
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
  1919
#elif  (defined MIPSEL)
26683
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  1920
  static  Elf32_Half running_arch_code=EM_MIPS_RS3_LE;
26684
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
  1921
#elif  (defined PARISC)
26683
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  1922
  static  Elf32_Half running_arch_code=EM_PARISC;
26684
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
  1923
#elif  (defined MIPS)
26683
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  1924
  static  Elf32_Half running_arch_code=EM_MIPS;
26684
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
  1925
#elif  (defined M68K)
26683
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  1926
  static  Elf32_Half running_arch_code=EM_68K;
29180
50369728b00e 8064611: AARCH64: Changes to HotSpot shared code
aph
parents: 27474
diff changeset
  1927
#elif  (defined AARCH64)
50369728b00e 8064611: AARCH64: Changes to HotSpot shared code
aph
parents: 27474
diff changeset
  1928
  static  Elf32_Half running_arch_code=EM_AARCH64;
26684
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
  1929
#else
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1930
    #error Method os::dll_load requires that one of following is defined:\
29180
50369728b00e 8064611: AARCH64: Changes to HotSpot shared code
aph
parents: 27474
diff changeset
  1931
         IA32, AMD64, IA64, __sparc, __powerpc__, ARM, S390, ALPHA, MIPS, MIPSEL, PARISC, M68K, AARCH64
26684
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
  1932
#endif
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1933
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1934
  // Identify compatability class for VM's architecture and library's architecture
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1935
  // Obtain string descriptions for architectures
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1936
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1937
  arch_t lib_arch={elf_head.e_machine,0,elf_head.e_ident[EI_CLASS], elf_head.e_ident[EI_DATA], NULL};
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1938
  int running_arch_index=-1;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1939
25064
244218e6ec0a 8046758: cleanup non-indent white space issues prior to Contended Locking cleanup bucket
dcubed
parents: 24931
diff changeset
  1940
  for (unsigned int i=0; i < ARRAY_SIZE(arch_array); i++) {
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1941
    if (running_arch_code == arch_array[i].code) {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1942
      running_arch_index    = i;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1943
    }
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1944
    if (lib_arch.code == arch_array[i].code) {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1945
      lib_arch.compat_class = arch_array[i].compat_class;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1946
      lib_arch.name         = arch_array[i].name;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1947
    }
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1948
  }
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1949
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1950
  assert(running_arch_index != -1,
26683
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  1951
         "Didn't find running architecture code (running_arch_code) in arch_array");
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1952
  if (running_arch_index == -1) {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1953
    // Even though running architecture detection failed
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1954
    // we may still continue with reporting dlerror() message
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1955
    return NULL;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1956
  }
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1957
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1958
  if (lib_arch.endianess != arch_array[running_arch_index].endianess) {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1959
    ::snprintf(diag_msg_buf, diag_msg_max_length-1," (Possible cause: endianness mismatch)");
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1960
    return NULL;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1961
  }
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1962
4013
b154310845de 6890308: integrate zero assembler hotspot changes
never
parents: 2753
diff changeset
  1963
#ifndef S390
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1964
  if (lib_arch.elf_class != arch_array[running_arch_index].elf_class) {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1965
    ::snprintf(diag_msg_buf, diag_msg_max_length-1," (Possible cause: architecture word width mismatch)");
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1966
    return NULL;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1967
  }
4013
b154310845de 6890308: integrate zero assembler hotspot changes
never
parents: 2753
diff changeset
  1968
#endif // !S390
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1969
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1970
  if (lib_arch.compat_class != arch_array[running_arch_index].compat_class) {
25064
244218e6ec0a 8046758: cleanup non-indent white space issues prior to Contended Locking cleanup bucket
dcubed
parents: 24931
diff changeset
  1971
    if (lib_arch.name!=NULL) {
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1972
      ::snprintf(diag_msg_buf, diag_msg_max_length-1,
26683
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  1973
                 " (Possible cause: can't load %s-bit .so on a %s-bit platform)",
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  1974
                 lib_arch.name, arch_array[running_arch_index].name);
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1975
    } else {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1976
      ::snprintf(diag_msg_buf, diag_msg_max_length-1,
26683
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  1977
                 " (Possible cause: can't load this .so (machine code=0x%x) on a %s-bit platform)",
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  1978
                 lib_arch.code,
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  1979
                 arch_array[running_arch_index].name);
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1980
    }
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1981
  }
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1982
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1983
  return NULL;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1984
}
489c9b5090e2 Initial load
duke
parents:
diff changeset
  1985
26684
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
  1986
void * os::Linux::dlopen_helper(const char *filename, char *ebuf,
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
  1987
                                int ebuflen) {
16438
245d5c0a8dd8 8010389: After fix for 7107135 a failed dlopen() call results in a VM crash
iklam
parents: 15927
diff changeset
  1988
  void * result = ::dlopen(filename, RTLD_LAZY);
245d5c0a8dd8 8010389: After fix for 7107135 a failed dlopen() call results in a VM crash
iklam
parents: 15927
diff changeset
  1989
  if (result == NULL) {
245d5c0a8dd8 8010389: After fix for 7107135 a failed dlopen() call results in a VM crash
iklam
parents: 15927
diff changeset
  1990
    ::strncpy(ebuf, ::dlerror(), ebuflen - 1);
245d5c0a8dd8 8010389: After fix for 7107135 a failed dlopen() call results in a VM crash
iklam
parents: 15927
diff changeset
  1991
    ebuf[ebuflen-1] = '\0';
245d5c0a8dd8 8010389: After fix for 7107135 a failed dlopen() call results in a VM crash
iklam
parents: 15927
diff changeset
  1992
  }
245d5c0a8dd8 8010389: After fix for 7107135 a failed dlopen() call results in a VM crash
iklam
parents: 15927
diff changeset
  1993
  return result;
245d5c0a8dd8 8010389: After fix for 7107135 a failed dlopen() call results in a VM crash
iklam
parents: 15927
diff changeset
  1994
}
245d5c0a8dd8 8010389: After fix for 7107135 a failed dlopen() call results in a VM crash
iklam
parents: 15927
diff changeset
  1995
26684
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
  1996
void * os::Linux::dll_load_in_vmthread(const char *filename, char *ebuf,
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
  1997
                                       int ebuflen) {
15926
8e87d545195f 7107135: Stack guard pages are no more protected after loading a shared library with executable stack
iklam
parents: 15855
diff changeset
  1998
  void * result = NULL;
8e87d545195f 7107135: Stack guard pages are no more protected after loading a shared library with executable stack
iklam
parents: 15855
diff changeset
  1999
  if (LoadExecStackDllInVMThread) {
16438
245d5c0a8dd8 8010389: After fix for 7107135 a failed dlopen() call results in a VM crash
iklam
parents: 15927
diff changeset
  2000
    result = dlopen_helper(filename, ebuf, ebuflen);
15926
8e87d545195f 7107135: Stack guard pages are no more protected after loading a shared library with executable stack
iklam
parents: 15855
diff changeset
  2001
  }
8e87d545195f 7107135: Stack guard pages are no more protected after loading a shared library with executable stack
iklam
parents: 15855
diff changeset
  2002
8e87d545195f 7107135: Stack guard pages are no more protected after loading a shared library with executable stack
iklam
parents: 15855
diff changeset
  2003
  // Since 7019808, libjvm.so is linked with -noexecstack. If the VM loads a
8e87d545195f 7107135: Stack guard pages are no more protected after loading a shared library with executable stack
iklam
parents: 15855
diff changeset
  2004
  // library that requires an executable stack, or which does not have this
8e87d545195f 7107135: Stack guard pages are no more protected after loading a shared library with executable stack
iklam
parents: 15855
diff changeset
  2005
  // stack attribute set, dlopen changes the stack attribute to executable. The
8e87d545195f 7107135: Stack guard pages are no more protected after loading a shared library with executable stack
iklam
parents: 15855
diff changeset
  2006
  // read protection of the guard pages gets lost.
8e87d545195f 7107135: Stack guard pages are no more protected after loading a shared library with executable stack
iklam
parents: 15855
diff changeset
  2007
  //
8e87d545195f 7107135: Stack guard pages are no more protected after loading a shared library with executable stack
iklam
parents: 15855
diff changeset
  2008
  // Need to check _stack_is_executable again as multiple VM_LinuxDllLoad
8e87d545195f 7107135: Stack guard pages are no more protected after loading a shared library with executable stack
iklam
parents: 15855
diff changeset
  2009
  // may have been queued at the same time.
8e87d545195f 7107135: Stack guard pages are no more protected after loading a shared library with executable stack
iklam
parents: 15855
diff changeset
  2010
8e87d545195f 7107135: Stack guard pages are no more protected after loading a shared library with executable stack
iklam
parents: 15855
diff changeset
  2011
  if (!_stack_is_executable) {
8e87d545195f 7107135: Stack guard pages are no more protected after loading a shared library with executable stack
iklam
parents: 15855
diff changeset
  2012
    JavaThread *jt = Threads::first();
8e87d545195f 7107135: Stack guard pages are no more protected after loading a shared library with executable stack
iklam
parents: 15855
diff changeset
  2013
8e87d545195f 7107135: Stack guard pages are no more protected after loading a shared library with executable stack
iklam
parents: 15855
diff changeset
  2014
    while (jt) {
8e87d545195f 7107135: Stack guard pages are no more protected after loading a shared library with executable stack
iklam
parents: 15855
diff changeset
  2015
      if (!jt->stack_guard_zone_unused() &&        // Stack not yet fully initialized
8e87d545195f 7107135: Stack guard pages are no more protected after loading a shared library with executable stack
iklam
parents: 15855
diff changeset
  2016
          jt->stack_yellow_zone_enabled()) {       // No pending stack overflow exceptions
8e87d545195f 7107135: Stack guard pages are no more protected after loading a shared library with executable stack
iklam
parents: 15855
diff changeset
  2017
        if (!os::guard_memory((char *) jt->stack_red_zone_base() - jt->stack_red_zone_size(),
8e87d545195f 7107135: Stack guard pages are no more protected after loading a shared library with executable stack
iklam
parents: 15855
diff changeset
  2018
                              jt->stack_yellow_zone_size() + jt->stack_red_zone_size())) {
8e87d545195f 7107135: Stack guard pages are no more protected after loading a shared library with executable stack
iklam
parents: 15855
diff changeset
  2019
          warning("Attempt to reguard stack yellow zone failed.");
8e87d545195f 7107135: Stack guard pages are no more protected after loading a shared library with executable stack
iklam
parents: 15855
diff changeset
  2020
        }
8e87d545195f 7107135: Stack guard pages are no more protected after loading a shared library with executable stack
iklam
parents: 15855
diff changeset
  2021
      }
8e87d545195f 7107135: Stack guard pages are no more protected after loading a shared library with executable stack
iklam
parents: 15855
diff changeset
  2022
      jt = jt->next();
8e87d545195f 7107135: Stack guard pages are no more protected after loading a shared library with executable stack
iklam
parents: 15855
diff changeset
  2023
    }
8e87d545195f 7107135: Stack guard pages are no more protected after loading a shared library with executable stack
iklam
parents: 15855
diff changeset
  2024
  }
8e87d545195f 7107135: Stack guard pages are no more protected after loading a shared library with executable stack
iklam
parents: 15855
diff changeset
  2025
8e87d545195f 7107135: Stack guard pages are no more protected after loading a shared library with executable stack
iklam
parents: 15855
diff changeset
  2026
  return result;
8e87d545195f 7107135: Stack guard pages are no more protected after loading a shared library with executable stack
iklam
parents: 15855
diff changeset
  2027
}
8e87d545195f 7107135: Stack guard pages are no more protected after loading a shared library with executable stack
iklam
parents: 15855
diff changeset
  2028
950
6112b627bb36 6721093: -XX:AppendRatio=N not supported
kamg
parents: 823
diff changeset
  2029
void* os::dll_lookup(void* handle, const char* name) {
6112b627bb36 6721093: -XX:AppendRatio=N not supported
kamg
parents: 823
diff changeset
  2030
  void* res = dlsym(handle, name);
6112b627bb36 6721093: -XX:AppendRatio=N not supported
kamg
parents: 823
diff changeset
  2031
  return res;
6112b627bb36 6721093: -XX:AppendRatio=N not supported
kamg
parents: 823
diff changeset
  2032
}
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2033
22528
bd3821442010 8031968: Mac OS X: VM starts the agent by calling both Agent_OnAttach and Agent_OnAttach_L functions if its agent library is dynamically linked.
sla
parents: 21185
diff changeset
  2034
void* os::get_default_process_handle() {
bd3821442010 8031968: Mac OS X: VM starts the agent by calling both Agent_OnAttach and Agent_OnAttach_L functions if its agent library is dynamically linked.
sla
parents: 21185
diff changeset
  2035
  return (void*)::dlopen(NULL, RTLD_LAZY);
bd3821442010 8031968: Mac OS X: VM starts the agent by calling both Agent_OnAttach and Agent_OnAttach_L functions if its agent library is dynamically linked.
sla
parents: 21185
diff changeset
  2036
}
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2037
7405
e6fc8d3926f8 6348631: remove the use of the HPI library from Hotspot
ikrylov
parents: 7397
diff changeset
  2038
static bool _print_ascii_file(const char* filename, outputStream* st) {
e6fc8d3926f8 6348631: remove the use of the HPI library from Hotspot
ikrylov
parents: 7397
diff changeset
  2039
  int fd = ::open(filename, O_RDONLY);
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2040
  if (fd == -1) {
26683
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  2041
    return false;
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2042
  }
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2043
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2044
  char buf[32];
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2045
  int bytes;
7405
e6fc8d3926f8 6348631: remove the use of the HPI library from Hotspot
ikrylov
parents: 7397
diff changeset
  2046
  while ((bytes = ::read(fd, buf, sizeof(buf))) > 0) {
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2047
    st->print_raw(buf, bytes);
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2048
  }
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2049
7405
e6fc8d3926f8 6348631: remove the use of the HPI library from Hotspot
ikrylov
parents: 7397
diff changeset
  2050
  ::close(fd);
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2051
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2052
  return true;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2053
}
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2054
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2055
void os::print_dll_info(outputStream *st) {
26683
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  2056
  st->print_cr("Dynamic libraries:");
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  2057
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  2058
  char fname[32];
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  2059
  pid_t pid = os::Linux::gettid();
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  2060
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  2061
  jio_snprintf(fname, sizeof(fname), "/proc/%d/maps", pid);
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  2062
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  2063
  if (!_print_ascii_file(fname, st)) {
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  2064
    st->print("Can not get library information for pid = %d\n", pid);
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  2065
  }
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2066
}
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2067
26557
e399effe36f9 8056242: Add function to return structured information about loaded libraries.
sla
parents: 26135
diff changeset
  2068
int os::get_loaded_modules_info(os::LoadedModulesCallbackFunc callback, void *param) {
e399effe36f9 8056242: Add function to return structured information about loaded libraries.
sla
parents: 26135
diff changeset
  2069
  FILE *procmapsFile = NULL;
e399effe36f9 8056242: Add function to return structured information about loaded libraries.
sla
parents: 26135
diff changeset
  2070
e399effe36f9 8056242: Add function to return structured information about loaded libraries.
sla
parents: 26135
diff changeset
  2071
  // Open the procfs maps file for the current process
e399effe36f9 8056242: Add function to return structured information about loaded libraries.
sla
parents: 26135
diff changeset
  2072
  if ((procmapsFile = fopen("/proc/self/maps", "r")) != NULL) {
e399effe36f9 8056242: Add function to return structured information about loaded libraries.
sla
parents: 26135
diff changeset
  2073
    // Allocate PATH_MAX for file name plus a reasonable size for other fields.
e399effe36f9 8056242: Add function to return structured information about loaded libraries.
sla
parents: 26135
diff changeset
  2074
    char line[PATH_MAX + 100];
e399effe36f9 8056242: Add function to return structured information about loaded libraries.
sla
parents: 26135
diff changeset
  2075
e399effe36f9 8056242: Add function to return structured information about loaded libraries.
sla
parents: 26135
diff changeset
  2076
    // Read line by line from 'file'
e399effe36f9 8056242: Add function to return structured information about loaded libraries.
sla
parents: 26135
diff changeset
  2077
    while (fgets(line, sizeof(line), procmapsFile) != NULL) {
e399effe36f9 8056242: Add function to return structured information about loaded libraries.
sla
parents: 26135
diff changeset
  2078
      u8 base, top, offset, inode;
e399effe36f9 8056242: Add function to return structured information about loaded libraries.
sla
parents: 26135
diff changeset
  2079
      char permissions[5];
e399effe36f9 8056242: Add function to return structured information about loaded libraries.
sla
parents: 26135
diff changeset
  2080
      char device[6];
e399effe36f9 8056242: Add function to return structured information about loaded libraries.
sla
parents: 26135
diff changeset
  2081
      char name[PATH_MAX + 1];
e399effe36f9 8056242: Add function to return structured information about loaded libraries.
sla
parents: 26135
diff changeset
  2082
e399effe36f9 8056242: Add function to return structured information about loaded libraries.
sla
parents: 26135
diff changeset
  2083
      // Parse fields from line
e399effe36f9 8056242: Add function to return structured information about loaded libraries.
sla
parents: 26135
diff changeset
  2084
      sscanf(line, "%lx-%lx %4s %lx %5s %ld %s", &base, &top, permissions, &offset, device, &inode, name);
e399effe36f9 8056242: Add function to return structured information about loaded libraries.
sla
parents: 26135
diff changeset
  2085
e399effe36f9 8056242: Add function to return structured information about loaded libraries.
sla
parents: 26135
diff changeset
  2086
      // Filter by device id '00:00' so that we only get file system mapped files.
e399effe36f9 8056242: Add function to return structured information about loaded libraries.
sla
parents: 26135
diff changeset
  2087
      if (strcmp(device, "00:00") != 0) {
e399effe36f9 8056242: Add function to return structured information about loaded libraries.
sla
parents: 26135
diff changeset
  2088
e399effe36f9 8056242: Add function to return structured information about loaded libraries.
sla
parents: 26135
diff changeset
  2089
        // Call callback with the fields of interest
e399effe36f9 8056242: Add function to return structured information about loaded libraries.
sla
parents: 26135
diff changeset
  2090
        if(callback(name, (address)base, (address)top, param)) {
e399effe36f9 8056242: Add function to return structured information about loaded libraries.
sla
parents: 26135
diff changeset
  2091
          // Oops abort, callback aborted
e399effe36f9 8056242: Add function to return structured information about loaded libraries.
sla
parents: 26135
diff changeset
  2092
          fclose(procmapsFile);
e399effe36f9 8056242: Add function to return structured information about loaded libraries.
sla
parents: 26135
diff changeset
  2093
          return 1;
e399effe36f9 8056242: Add function to return structured information about loaded libraries.
sla
parents: 26135
diff changeset
  2094
        }
e399effe36f9 8056242: Add function to return structured information about loaded libraries.
sla
parents: 26135
diff changeset
  2095
      }
e399effe36f9 8056242: Add function to return structured information about loaded libraries.
sla
parents: 26135
diff changeset
  2096
    }
e399effe36f9 8056242: Add function to return structured information about loaded libraries.
sla
parents: 26135
diff changeset
  2097
    fclose(procmapsFile);
e399effe36f9 8056242: Add function to return structured information about loaded libraries.
sla
parents: 26135
diff changeset
  2098
  }
e399effe36f9 8056242: Add function to return structured information about loaded libraries.
sla
parents: 26135
diff changeset
  2099
  return 0;
e399effe36f9 8056242: Add function to return structured information about loaded libraries.
sla
parents: 26135
diff changeset
  2100
}
e399effe36f9 8056242: Add function to return structured information about loaded libraries.
sla
parents: 26135
diff changeset
  2101
12735
3e2e491f4f69 7165755: OS Information much longer on linux than other platforms
nloodin
parents: 12116
diff changeset
  2102
void os::print_os_info_brief(outputStream* st) {
3e2e491f4f69 7165755: OS Information much longer on linux than other platforms
nloodin
parents: 12116
diff changeset
  2103
  os::Linux::print_distro_info(st);
3e2e491f4f69 7165755: OS Information much longer on linux than other platforms
nloodin
parents: 12116
diff changeset
  2104
3e2e491f4f69 7165755: OS Information much longer on linux than other platforms
nloodin
parents: 12116
diff changeset
  2105
  os::Posix::print_uname_info(st);
3e2e491f4f69 7165755: OS Information much longer on linux than other platforms
nloodin
parents: 12116
diff changeset
  2106
3e2e491f4f69 7165755: OS Information much longer on linux than other platforms
nloodin
parents: 12116
diff changeset
  2107
  os::Linux::print_libversion_info(st);
3e2e491f4f69 7165755: OS Information much longer on linux than other platforms
nloodin
parents: 12116
diff changeset
  2108
3e2e491f4f69 7165755: OS Information much longer on linux than other platforms
nloodin
parents: 12116
diff changeset
  2109
}
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2110
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2111
void os::print_os_info(outputStream* st) {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2112
  st->print("OS:");
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2113
12735
3e2e491f4f69 7165755: OS Information much longer on linux than other platforms
nloodin
parents: 12116
diff changeset
  2114
  os::Linux::print_distro_info(st);
3e2e491f4f69 7165755: OS Information much longer on linux than other platforms
nloodin
parents: 12116
diff changeset
  2115
3e2e491f4f69 7165755: OS Information much longer on linux than other platforms
nloodin
parents: 12116
diff changeset
  2116
  os::Posix::print_uname_info(st);
3e2e491f4f69 7165755: OS Information much longer on linux than other platforms
nloodin
parents: 12116
diff changeset
  2117
3e2e491f4f69 7165755: OS Information much longer on linux than other platforms
nloodin
parents: 12116
diff changeset
  2118
  // Print warning if unsafe chroot environment detected
3e2e491f4f69 7165755: OS Information much longer on linux than other platforms
nloodin
parents: 12116
diff changeset
  2119
  if (unsafe_chroot_detected) {
3e2e491f4f69 7165755: OS Information much longer on linux than other platforms
nloodin
parents: 12116
diff changeset
  2120
    st->print("WARNING!! ");
24424
2658d7834c6e 8037816: Fix for 8036122 breaks build with Xcode5/clang
drchase
parents: 24352
diff changeset
  2121
    st->print_cr("%s", unstable_chroot_error);
12735
3e2e491f4f69 7165755: OS Information much longer on linux than other platforms
nloodin
parents: 12116
diff changeset
  2122
  }
3e2e491f4f69 7165755: OS Information much longer on linux than other platforms
nloodin
parents: 12116
diff changeset
  2123
3e2e491f4f69 7165755: OS Information much longer on linux than other platforms
nloodin
parents: 12116
diff changeset
  2124
  os::Linux::print_libversion_info(st);
3e2e491f4f69 7165755: OS Information much longer on linux than other platforms
nloodin
parents: 12116
diff changeset
  2125
3e2e491f4f69 7165755: OS Information much longer on linux than other platforms
nloodin
parents: 12116
diff changeset
  2126
  os::Posix::print_rlimit_info(st);
3e2e491f4f69 7165755: OS Information much longer on linux than other platforms
nloodin
parents: 12116
diff changeset
  2127
3e2e491f4f69 7165755: OS Information much longer on linux than other platforms
nloodin
parents: 12116
diff changeset
  2128
  os::Posix::print_load_average(st);
3e2e491f4f69 7165755: OS Information much longer on linux than other platforms
nloodin
parents: 12116
diff changeset
  2129
3e2e491f4f69 7165755: OS Information much longer on linux than other platforms
nloodin
parents: 12116
diff changeset
  2130
  os::Linux::print_full_memory_info(st);
3e2e491f4f69 7165755: OS Information much longer on linux than other platforms
nloodin
parents: 12116
diff changeset
  2131
}
3e2e491f4f69 7165755: OS Information much longer on linux than other platforms
nloodin
parents: 12116
diff changeset
  2132
3e2e491f4f69 7165755: OS Information much longer on linux than other platforms
nloodin
parents: 12116
diff changeset
  2133
// Try to identify popular distros.
19965
7d9d20ec275b 6986195: correctly identify Ubuntu as the operating system in crash report instead of "Debian"
dcubed
parents: 19964
diff changeset
  2134
// Most Linux distributions have a /etc/XXX-release file, which contains
7d9d20ec275b 6986195: correctly identify Ubuntu as the operating system in crash report instead of "Debian"
dcubed
parents: 19964
diff changeset
  2135
// the OS version string. Newer Linux distributions have a /etc/lsb-release
7d9d20ec275b 6986195: correctly identify Ubuntu as the operating system in crash report instead of "Debian"
dcubed
parents: 19964
diff changeset
  2136
// file that also contains the OS version string. Some have more than one
7d9d20ec275b 6986195: correctly identify Ubuntu as the operating system in crash report instead of "Debian"
dcubed
parents: 19964
diff changeset
  2137
// /etc/XXX-release file (e.g. Mandrake has both /etc/mandrake-release and
7d9d20ec275b 6986195: correctly identify Ubuntu as the operating system in crash report instead of "Debian"
dcubed
parents: 19964
diff changeset
  2138
// /etc/redhat-release.), so the order is important.
7d9d20ec275b 6986195: correctly identify Ubuntu as the operating system in crash report instead of "Debian"
dcubed
parents: 19964
diff changeset
  2139
// Any Linux that is based on Redhat (i.e. Oracle, Mandrake, Sun JDS...) have
7d9d20ec275b 6986195: correctly identify Ubuntu as the operating system in crash report instead of "Debian"
dcubed
parents: 19964
diff changeset
  2140
// their own specific XXX-release file as well as a redhat-release file.
7d9d20ec275b 6986195: correctly identify Ubuntu as the operating system in crash report instead of "Debian"
dcubed
parents: 19964
diff changeset
  2141
// Because of this the XXX-release file needs to be searched for before the
7d9d20ec275b 6986195: correctly identify Ubuntu as the operating system in crash report instead of "Debian"
dcubed
parents: 19964
diff changeset
  2142
// redhat-release file.
7d9d20ec275b 6986195: correctly identify Ubuntu as the operating system in crash report instead of "Debian"
dcubed
parents: 19964
diff changeset
  2143
// Since Red Hat has a lsb-release file that is not very descriptive the
7d9d20ec275b 6986195: correctly identify Ubuntu as the operating system in crash report instead of "Debian"
dcubed
parents: 19964
diff changeset
  2144
// search for redhat-release needs to be before lsb-release.
7d9d20ec275b 6986195: correctly identify Ubuntu as the operating system in crash report instead of "Debian"
dcubed
parents: 19964
diff changeset
  2145
// Since the lsb-release file is the new standard it needs to be searched
7d9d20ec275b 6986195: correctly identify Ubuntu as the operating system in crash report instead of "Debian"
dcubed
parents: 19964
diff changeset
  2146
// before the older style release files.
7d9d20ec275b 6986195: correctly identify Ubuntu as the operating system in crash report instead of "Debian"
dcubed
parents: 19964
diff changeset
  2147
// Searching system-release (Red Hat) and os-release (other Linuxes) are a
7d9d20ec275b 6986195: correctly identify Ubuntu as the operating system in crash report instead of "Debian"
dcubed
parents: 19964
diff changeset
  2148
// next to last resort.  The os-release file is a new standard that contains
7d9d20ec275b 6986195: correctly identify Ubuntu as the operating system in crash report instead of "Debian"
dcubed
parents: 19964
diff changeset
  2149
// distribution information and the system-release file seems to be an old
7d9d20ec275b 6986195: correctly identify Ubuntu as the operating system in crash report instead of "Debian"
dcubed
parents: 19964
diff changeset
  2150
// standard that has been replaced by the lsb-release and os-release files.
7d9d20ec275b 6986195: correctly identify Ubuntu as the operating system in crash report instead of "Debian"
dcubed
parents: 19964
diff changeset
  2151
// Searching for the debian_version file is the last resort.  It contains
7d9d20ec275b 6986195: correctly identify Ubuntu as the operating system in crash report instead of "Debian"
dcubed
parents: 19964
diff changeset
  2152
// an informative string like "6.0.6" or "wheezy/sid". Because of this
7d9d20ec275b 6986195: correctly identify Ubuntu as the operating system in crash report instead of "Debian"
dcubed
parents: 19964
diff changeset
  2153
// "Debian " is printed before the contents of the debian_version file.
12735
3e2e491f4f69 7165755: OS Information much longer on linux than other platforms
nloodin
parents: 12116
diff changeset
  2154
void os::Linux::print_distro_info(outputStream* st) {
26683
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  2155
  if (!_print_ascii_file("/etc/oracle-release", st) &&
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  2156
      !_print_ascii_file("/etc/mandriva-release", st) &&
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  2157
      !_print_ascii_file("/etc/mandrake-release", st) &&
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  2158
      !_print_ascii_file("/etc/sun-release", st) &&
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  2159
      !_print_ascii_file("/etc/redhat-release", st) &&
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  2160
      !_print_ascii_file("/etc/lsb-release", st) &&
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  2161
      !_print_ascii_file("/etc/SuSE-release", st) &&
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  2162
      !_print_ascii_file("/etc/turbolinux-release", st) &&
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  2163
      !_print_ascii_file("/etc/gentoo-release", st) &&
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  2164
      !_print_ascii_file("/etc/ltib-release", st) &&
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  2165
      !_print_ascii_file("/etc/angstrom-version", st) &&
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  2166
      !_print_ascii_file("/etc/system-release", st) &&
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  2167
      !_print_ascii_file("/etc/os-release", st)) {
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  2168
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  2169
    if (file_exists("/etc/debian_version")) {
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  2170
      st->print("Debian ");
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  2171
      _print_ascii_file("/etc/debian_version", st);
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  2172
    } else {
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  2173
      st->print("Linux");
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  2174
    }
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  2175
  }
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  2176
  st->cr();
12735
3e2e491f4f69 7165755: OS Information much longer on linux than other platforms
nloodin
parents: 12116
diff changeset
  2177
}
3e2e491f4f69 7165755: OS Information much longer on linux than other platforms
nloodin
parents: 12116
diff changeset
  2178
3e2e491f4f69 7165755: OS Information much longer on linux than other platforms
nloodin
parents: 12116
diff changeset
  2179
void os::Linux::print_libversion_info(outputStream* st) {
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2180
  // libc, pthread
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2181
  st->print("libc:");
24424
2658d7834c6e 8037816: Fix for 8036122 breaks build with Xcode5/clang
drchase
parents: 24352
diff changeset
  2182
  st->print("%s ", os::Linux::glibc_version());
2658d7834c6e 8037816: Fix for 8036122 breaks build with Xcode5/clang
drchase
parents: 24352
diff changeset
  2183
  st->print("%s ", os::Linux::libpthread_version());
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2184
  if (os::Linux::is_LinuxThreads()) {
26683
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  2185
    st->print("(%s stack)", os::Linux::is_floating_stack() ? "floating" : "fixed");
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2186
  }
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2187
  st->cr();
12735
3e2e491f4f69 7165755: OS Information much longer on linux than other platforms
nloodin
parents: 12116
diff changeset
  2188
}
3e2e491f4f69 7165755: OS Information much longer on linux than other platforms
nloodin
parents: 12116
diff changeset
  2189
3e2e491f4f69 7165755: OS Information much longer on linux than other platforms
nloodin
parents: 12116
diff changeset
  2190
void os::Linux::print_full_memory_info(outputStream* st) {
26683
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  2191
  st->print("\n/proc/meminfo:\n");
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  2192
  _print_ascii_file("/proc/meminfo", st);
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  2193
  st->cr();
10023
e99d9a03c0f5 7061225: os::print_cpu_info() should support os-specific data
jcoomes
parents: 9625
diff changeset
  2194
}
e99d9a03c0f5 7061225: os::print_cpu_info() should support os-specific data
jcoomes
parents: 9625
diff changeset
  2195
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2196
void os::print_memory_info(outputStream* st) {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2197
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2198
  st->print("Memory:");
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2199
  st->print(" %dk page", os::vm_page_size()>>10);
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2200
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2201
  // values in struct sysinfo are "unsigned long"
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2202
  struct sysinfo si;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2203
  sysinfo(&si);
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2204
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2205
  st->print(", physical " UINT64_FORMAT "k",
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2206
            os::physical_memory() >> 10);
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2207
  st->print("(" UINT64_FORMAT "k free)",
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2208
            os::available_memory() >> 10);
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2209
  st->print(", swap " UINT64_FORMAT "k",
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2210
            ((jlong)si.totalswap * si.mem_unit) >> 10);
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2211
  st->print("(" UINT64_FORMAT "k free)",
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2212
            ((jlong)si.freeswap * si.mem_unit) >> 10);
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2213
  st->cr();
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2214
}
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2215
12735
3e2e491f4f69 7165755: OS Information much longer on linux than other platforms
nloodin
parents: 12116
diff changeset
  2216
void os::pd_print_cpu_info(outputStream* st) {
3e2e491f4f69 7165755: OS Information much longer on linux than other platforms
nloodin
parents: 12116
diff changeset
  2217
  st->print("\n/proc/cpuinfo:\n");
3e2e491f4f69 7165755: OS Information much longer on linux than other platforms
nloodin
parents: 12116
diff changeset
  2218
  if (!_print_ascii_file("/proc/cpuinfo", st)) {
3e2e491f4f69 7165755: OS Information much longer on linux than other platforms
nloodin
parents: 12116
diff changeset
  2219
    st->print("  <Not Available>");
3e2e491f4f69 7165755: OS Information much longer on linux than other platforms
nloodin
parents: 12116
diff changeset
  2220
  }
3e2e491f4f69 7165755: OS Information much longer on linux than other platforms
nloodin
parents: 12116
diff changeset
  2221
  st->cr();
3e2e491f4f69 7165755: OS Information much longer on linux than other platforms
nloodin
parents: 12116
diff changeset
  2222
}
3e2e491f4f69 7165755: OS Information much longer on linux than other platforms
nloodin
parents: 12116
diff changeset
  2223
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2224
void os::print_siginfo(outputStream* st, void* siginfo) {
22826
3ee6886e718d 8020775: PPC64 (part 12): posix signal printing
goetz
parents: 22821
diff changeset
  2225
  const siginfo_t* si = (const siginfo_t*)siginfo;
3ee6886e718d 8020775: PPC64 (part 12): posix signal printing
goetz
parents: 22821
diff changeset
  2226
3ee6886e718d 8020775: PPC64 (part 12): posix signal printing
goetz
parents: 22821
diff changeset
  2227
  os::Posix::print_siginfo_brief(st, si);
26135
82b516c550f7 8046070: Class Data Sharing clean up and refactoring
iklam
parents: 25946
diff changeset
  2228
#if INCLUDE_CDS
22826
3ee6886e718d 8020775: PPC64 (part 12): posix signal printing
goetz
parents: 22821
diff changeset
  2229
  if (si && (si->si_signo == SIGBUS || si->si_signo == SIGSEGV) &&
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2230
      UseSharedSpaces) {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2231
    FileMapInfo* mapinfo = FileMapInfo::current_info();
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2232
    if (mapinfo->is_in_shared_space(si->si_addr)) {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2233
      st->print("\n\nError accessing class data sharing archive."   \
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2234
                " Mapped file inaccessible during execution, "      \
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2235
                " possible disk/network problem.");
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2236
    }
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2237
  }
26135
82b516c550f7 8046070: Class Data Sharing clean up and refactoring
iklam
parents: 25946
diff changeset
  2238
#endif
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2239
  st->cr();
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2240
}
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2241
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2242
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2243
static void print_signal_handler(outputStream* st, int sig,
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2244
                                 char* buf, size_t buflen);
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2245
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2246
void os::print_signal_handlers(outputStream* st, char* buf, size_t buflen) {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2247
  st->print_cr("Signal Handlers:");
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2248
  print_signal_handler(st, SIGSEGV, buf, buflen);
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2249
  print_signal_handler(st, SIGBUS , buf, buflen);
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2250
  print_signal_handler(st, SIGFPE , buf, buflen);
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2251
  print_signal_handler(st, SIGPIPE, buf, buflen);
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2252
  print_signal_handler(st, SIGXFSZ, buf, buflen);
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2253
  print_signal_handler(st, SIGILL , buf, buflen);
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2254
  print_signal_handler(st, INTERRUPT_SIGNAL, buf, buflen);
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2255
  print_signal_handler(st, SR_signum, buf, buflen);
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2256
  print_signal_handler(st, SHUTDOWN1_SIGNAL, buf, buflen);
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2257
  print_signal_handler(st, SHUTDOWN2_SIGNAL , buf, buflen);
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2258
  print_signal_handler(st, SHUTDOWN3_SIGNAL , buf, buflen);
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2259
  print_signal_handler(st, BREAK_SIGNAL, buf, buflen);
22848
c1a044cf0c07 8028470: PPC64 (part 214): linux: extend signal handler to catch SIGTRAP on ppc64.
goetz
parents: 22838
diff changeset
  2260
#if defined(PPC64)
c1a044cf0c07 8028470: PPC64 (part 214): linux: extend signal handler to catch SIGTRAP on ppc64.
goetz
parents: 22838
diff changeset
  2261
  print_signal_handler(st, SIGTRAP, buf, buflen);
c1a044cf0c07 8028470: PPC64 (part 214): linux: extend signal handler to catch SIGTRAP on ppc64.
goetz
parents: 22838
diff changeset
  2262
#endif
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2263
}
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2264
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2265
static char saved_jvm_path[MAXPATHLEN] = {0};
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2266
15096
3db45569f8c0 8005044: remove crufty '_g' support from HS runtime code
dcubed
parents: 14633
diff changeset
  2267
// Find the full path to the current module, libjvm.so
5922
883ecb03d008 6967423: Hotspot support for modules image
mchung
parents: 5547
diff changeset
  2268
void os::jvm_path(char *buf, jint buflen) {
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2269
  // Error checking.
5922
883ecb03d008 6967423: Hotspot support for modules image
mchung
parents: 5547
diff changeset
  2270
  if (buflen < MAXPATHLEN) {
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2271
    assert(false, "must use a large-enough buffer");
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2272
    buf[0] = '\0';
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2273
    return;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2274
  }
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2275
  // Lazy resolve the path to current module.
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2276
  if (saved_jvm_path[0] != 0) {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2277
    strcpy(buf, saved_jvm_path);
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2278
    return;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2279
  }
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2280
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2281
  char dli_fname[MAXPATHLEN];
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2282
  bool ret = dll_address_to_library_name(
26683
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  2283
                                         CAST_FROM_FN_PTR(address, os::jvm_path),
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  2284
                                         dli_fname, sizeof(dli_fname), NULL);
18683
a6418e038255 8015884: runThese crashed with SIGSEGV, hs_err has an error instead of stacktrace
dcubed
parents: 18086
diff changeset
  2285
  assert(ret, "cannot locate libjvm");
a6418e038255 8015884: runThese crashed with SIGSEGV, hs_err has an error instead of stacktrace
dcubed
parents: 18086
diff changeset
  2286
  char *rp = NULL;
a6418e038255 8015884: runThese crashed with SIGSEGV, hs_err has an error instead of stacktrace
dcubed
parents: 18086
diff changeset
  2287
  if (ret && dli_fname[0] != '\0') {
a6418e038255 8015884: runThese crashed with SIGSEGV, hs_err has an error instead of stacktrace
dcubed
parents: 18086
diff changeset
  2288
    rp = realpath(dli_fname, buf);
a6418e038255 8015884: runThese crashed with SIGSEGV, hs_err has an error instead of stacktrace
dcubed
parents: 18086
diff changeset
  2289
  }
26684
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
  2290
  if (rp == NULL) {
1889
24b003a6fe46 6781583: Hotspot build fails on linux 64 bit platform with gcc 4.3.2
xlu
parents: 1664
diff changeset
  2291
    return;
26684
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
  2292
  }
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2293
22734
41757c1f3946 8027113: decouple the '-XXaltjvm=<path>' option from the gamma launcher
rdurbin
parents: 22533
diff changeset
  2294
  if (Arguments::sun_java_launcher_is_altjvm()) {
41757c1f3946 8027113: decouple the '-XXaltjvm=<path>' option from the gamma launcher
rdurbin
parents: 22533
diff changeset
  2295
    // Support for the java launcher's '-XXaltjvm=<path>' option. Typical
41757c1f3946 8027113: decouple the '-XXaltjvm=<path>' option from the gamma launcher
rdurbin
parents: 22533
diff changeset
  2296
    // value for buf is "<JAVA_HOME>/jre/lib/<arch>/<vmtype>/libjvm.so".
41757c1f3946 8027113: decouple the '-XXaltjvm=<path>' option from the gamma launcher
rdurbin
parents: 22533
diff changeset
  2297
    // If "/jre/lib/" appears at the right place in the string, then
41757c1f3946 8027113: decouple the '-XXaltjvm=<path>' option from the gamma launcher
rdurbin
parents: 22533
diff changeset
  2298
    // assume we are installed in a JDK and we're done. Otherwise, check
41757c1f3946 8027113: decouple the '-XXaltjvm=<path>' option from the gamma launcher
rdurbin
parents: 22533
diff changeset
  2299
    // for a JAVA_HOME environment variable and fix up the path so it
41757c1f3946 8027113: decouple the '-XXaltjvm=<path>' option from the gamma launcher
rdurbin
parents: 22533
diff changeset
  2300
    // looks like libjvm.so is installed there (append a fake suffix
41757c1f3946 8027113: decouple the '-XXaltjvm=<path>' option from the gamma launcher
rdurbin
parents: 22533
diff changeset
  2301
    // hotspot/libjvm.so).
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2302
    const char *p = buf + strlen(buf) - 1;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2303
    for (int count = 0; p > buf && count < 5; ++count) {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2304
      for (--p; p > buf && *p != '/'; --p)
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2305
        /* empty */ ;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2306
    }
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2307
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2308
    if (strncmp(p, "/jre/lib/", 9) != 0) {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2309
      // Look for JAVA_HOME in the environment.
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2310
      char* java_home_var = ::getenv("JAVA_HOME");
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2311
      if (java_home_var != NULL && java_home_var[0] != 0) {
5922
883ecb03d008 6967423: Hotspot support for modules image
mchung
parents: 5547
diff changeset
  2312
        char* jrelib_p;
883ecb03d008 6967423: Hotspot support for modules image
mchung
parents: 5547
diff changeset
  2313
        int len;
883ecb03d008 6967423: Hotspot support for modules image
mchung
parents: 5547
diff changeset
  2314
15096
3db45569f8c0 8005044: remove crufty '_g' support from HS runtime code
dcubed
parents: 14633
diff changeset
  2315
        // Check the current module name "libjvm.so".
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2316
        p = strrchr(buf, '/');
27471
6e56277909f1 8062370: Various minor code improvements
goetz
parents: 27458
diff changeset
  2317
        if (p == NULL) {
6e56277909f1 8062370: Various minor code improvements
goetz
parents: 27458
diff changeset
  2318
          return;
6e56277909f1 8062370: Various minor code improvements
goetz
parents: 27458
diff changeset
  2319
        }
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2320
        assert(strstr(p, "/libjvm") == p, "invalid library name");
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2321
6176
4d9030fe341f 6953477: Increase portability and flexibility of building Hotspot
bobv
parents: 5922
diff changeset
  2322
        rp = realpath(java_home_var, buf);
26684
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
  2323
        if (rp == NULL) {
1889
24b003a6fe46 6781583: Hotspot build fails on linux 64 bit platform with gcc 4.3.2
xlu
parents: 1664
diff changeset
  2324
          return;
26684
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
  2325
        }
5922
883ecb03d008 6967423: Hotspot support for modules image
mchung
parents: 5547
diff changeset
  2326
883ecb03d008 6967423: Hotspot support for modules image
mchung
parents: 5547
diff changeset
  2327
        // determine if this is a legacy image or modules image
883ecb03d008 6967423: Hotspot support for modules image
mchung
parents: 5547
diff changeset
  2328
        // modules image doesn't have "jre" subdirectory
883ecb03d008 6967423: Hotspot support for modules image
mchung
parents: 5547
diff changeset
  2329
        len = strlen(buf);
25503
9f471b837330 8030763: Validate global memory allocation
hseigel
parents: 25477
diff changeset
  2330
        assert(len < buflen, "Ran out of buffer room");
5922
883ecb03d008 6967423: Hotspot support for modules image
mchung
parents: 5547
diff changeset
  2331
        jrelib_p = buf + len;
883ecb03d008 6967423: Hotspot support for modules image
mchung
parents: 5547
diff changeset
  2332
        snprintf(jrelib_p, buflen-len, "/jre/lib/%s", cpu_arch);
883ecb03d008 6967423: Hotspot support for modules image
mchung
parents: 5547
diff changeset
  2333
        if (0 != access(buf, F_OK)) {
883ecb03d008 6967423: Hotspot support for modules image
mchung
parents: 5547
diff changeset
  2334
          snprintf(jrelib_p, buflen-len, "/lib/%s", cpu_arch);
883ecb03d008 6967423: Hotspot support for modules image
mchung
parents: 5547
diff changeset
  2335
        }
883ecb03d008 6967423: Hotspot support for modules image
mchung
parents: 5547
diff changeset
  2336
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2337
        if (0 == access(buf, F_OK)) {
15096
3db45569f8c0 8005044: remove crufty '_g' support from HS runtime code
dcubed
parents: 14633
diff changeset
  2338
          // Use current module name "libjvm.so"
5922
883ecb03d008 6967423: Hotspot support for modules image
mchung
parents: 5547
diff changeset
  2339
          len = strlen(buf);
15096
3db45569f8c0 8005044: remove crufty '_g' support from HS runtime code
dcubed
parents: 14633
diff changeset
  2340
          snprintf(buf + len, buflen-len, "/hotspot/libjvm.so");
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2341
        } else {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2342
          // Go back to path of .so
6176
4d9030fe341f 6953477: Increase portability and flexibility of building Hotspot
bobv
parents: 5922
diff changeset
  2343
          rp = realpath(dli_fname, buf);
26684
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
  2344
          if (rp == NULL) {
1889
24b003a6fe46 6781583: Hotspot build fails on linux 64 bit platform with gcc 4.3.2
xlu
parents: 1664
diff changeset
  2345
            return;
26684
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
  2346
          }
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2347
        }
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2348
      }
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2349
    }
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2350
  }
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2351
25503
9f471b837330 8030763: Validate global memory allocation
hseigel
parents: 25477
diff changeset
  2352
  strncpy(saved_jvm_path, buf, MAXPATHLEN);
27471
6e56277909f1 8062370: Various minor code improvements
goetz
parents: 27458
diff changeset
  2353
  saved_jvm_path[MAXPATHLEN - 1] = '\0';
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2354
}
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2355
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2356
void os::print_jni_name_prefix_on(outputStream* st, int args_size) {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2357
  // no prefix required, not even "_"
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2358
}
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2359
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2360
void os::print_jni_name_suffix_on(outputStream* st, int args_size) {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2361
  // no suffix required
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2362
}
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2363
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2364
////////////////////////////////////////////////////////////////////////////////
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2365
// sun.misc.Signal support
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2366
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2367
static volatile jint sigint_count = 0;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2368
26684
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
  2369
static void UserHandler(int sig, void *siginfo, void *context) {
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2370
  // 4511530 - sem_post is serialized and handled by the manager thread. When
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2371
  // the program is interrupted by Ctrl-C, SIGINT is sent to every thread. We
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2372
  // don't want to flood the manager thread with sem_post requests.
26684
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
  2373
  if (sig == SIGINT && Atomic::add(1, &sigint_count) > 1) {
26683
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  2374
    return;
26684
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
  2375
  }
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2376
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2377
  // Ctrl-C is pressed during error reporting, likely because the error
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2378
  // handler fails to abort. Let VM die immediately.
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2379
  if (sig == SIGINT && is_error_reported()) {
26683
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  2380
    os::die();
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2381
  }
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2382
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2383
  os::signal_notify(sig);
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2384
}
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2385
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2386
void* os::user_handler() {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2387
  return CAST_FROM_FN_PTR(void*, UserHandler);
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2388
}
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2389
18025
b7bcf7497f93 8005849: JEP 167: Event-Based JVM Tracing
sla
parents: 17854
diff changeset
  2390
class Semaphore : public StackObj {
26683
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  2391
 public:
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  2392
  Semaphore();
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  2393
  ~Semaphore();
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  2394
  void signal();
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  2395
  void wait();
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  2396
  bool trywait();
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  2397
  bool timedwait(unsigned int sec, int nsec);
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  2398
 private:
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  2399
  sem_t _semaphore;
18025
b7bcf7497f93 8005849: JEP 167: Event-Based JVM Tracing
sla
parents: 17854
diff changeset
  2400
};
b7bcf7497f93 8005849: JEP 167: Event-Based JVM Tracing
sla
parents: 17854
diff changeset
  2401
b7bcf7497f93 8005849: JEP 167: Event-Based JVM Tracing
sla
parents: 17854
diff changeset
  2402
Semaphore::Semaphore() {
b7bcf7497f93 8005849: JEP 167: Event-Based JVM Tracing
sla
parents: 17854
diff changeset
  2403
  sem_init(&_semaphore, 0, 0);
b7bcf7497f93 8005849: JEP 167: Event-Based JVM Tracing
sla
parents: 17854
diff changeset
  2404
}
b7bcf7497f93 8005849: JEP 167: Event-Based JVM Tracing
sla
parents: 17854
diff changeset
  2405
b7bcf7497f93 8005849: JEP 167: Event-Based JVM Tracing
sla
parents: 17854
diff changeset
  2406
Semaphore::~Semaphore() {
b7bcf7497f93 8005849: JEP 167: Event-Based JVM Tracing
sla
parents: 17854
diff changeset
  2407
  sem_destroy(&_semaphore);
b7bcf7497f93 8005849: JEP 167: Event-Based JVM Tracing
sla
parents: 17854
diff changeset
  2408
}
b7bcf7497f93 8005849: JEP 167: Event-Based JVM Tracing
sla
parents: 17854
diff changeset
  2409
b7bcf7497f93 8005849: JEP 167: Event-Based JVM Tracing
sla
parents: 17854
diff changeset
  2410
void Semaphore::signal() {
b7bcf7497f93 8005849: JEP 167: Event-Based JVM Tracing
sla
parents: 17854
diff changeset
  2411
  sem_post(&_semaphore);
b7bcf7497f93 8005849: JEP 167: Event-Based JVM Tracing
sla
parents: 17854
diff changeset
  2412
}
b7bcf7497f93 8005849: JEP 167: Event-Based JVM Tracing
sla
parents: 17854
diff changeset
  2413
b7bcf7497f93 8005849: JEP 167: Event-Based JVM Tracing
sla
parents: 17854
diff changeset
  2414
void Semaphore::wait() {
b7bcf7497f93 8005849: JEP 167: Event-Based JVM Tracing
sla
parents: 17854
diff changeset
  2415
  sem_wait(&_semaphore);
b7bcf7497f93 8005849: JEP 167: Event-Based JVM Tracing
sla
parents: 17854
diff changeset
  2416
}
b7bcf7497f93 8005849: JEP 167: Event-Based JVM Tracing
sla
parents: 17854
diff changeset
  2417
b7bcf7497f93 8005849: JEP 167: Event-Based JVM Tracing
sla
parents: 17854
diff changeset
  2418
bool Semaphore::trywait() {
b7bcf7497f93 8005849: JEP 167: Event-Based JVM Tracing
sla
parents: 17854
diff changeset
  2419
  return sem_trywait(&_semaphore) == 0;
b7bcf7497f93 8005849: JEP 167: Event-Based JVM Tracing
sla
parents: 17854
diff changeset
  2420
}
b7bcf7497f93 8005849: JEP 167: Event-Based JVM Tracing
sla
parents: 17854
diff changeset
  2421
b7bcf7497f93 8005849: JEP 167: Event-Based JVM Tracing
sla
parents: 17854
diff changeset
  2422
bool Semaphore::timedwait(unsigned int sec, int nsec) {
23479
c8d925d6c93f 8037340: Linux semaphores to use CLOCK_REALTIME
mgronlun
parents: 23444
diff changeset
  2423
18025
b7bcf7497f93 8005849: JEP 167: Event-Based JVM Tracing
sla
parents: 17854
diff changeset
  2424
  struct timespec ts;
23479
c8d925d6c93f 8037340: Linux semaphores to use CLOCK_REALTIME
mgronlun
parents: 23444
diff changeset
  2425
  // Semaphore's are always associated with CLOCK_REALTIME
c8d925d6c93f 8037340: Linux semaphores to use CLOCK_REALTIME
mgronlun
parents: 23444
diff changeset
  2426
  os::Linux::clock_gettime(CLOCK_REALTIME, &ts);
c8d925d6c93f 8037340: Linux semaphores to use CLOCK_REALTIME
mgronlun
parents: 23444
diff changeset
  2427
  // see unpackTime for discussion on overflow checking
c8d925d6c93f 8037340: Linux semaphores to use CLOCK_REALTIME
mgronlun
parents: 23444
diff changeset
  2428
  if (sec >= MAX_SECS) {
c8d925d6c93f 8037340: Linux semaphores to use CLOCK_REALTIME
mgronlun
parents: 23444
diff changeset
  2429
    ts.tv_sec += MAX_SECS;
c8d925d6c93f 8037340: Linux semaphores to use CLOCK_REALTIME
mgronlun
parents: 23444
diff changeset
  2430
    ts.tv_nsec = 0;
c8d925d6c93f 8037340: Linux semaphores to use CLOCK_REALTIME
mgronlun
parents: 23444
diff changeset
  2431
  } else {
c8d925d6c93f 8037340: Linux semaphores to use CLOCK_REALTIME
mgronlun
parents: 23444
diff changeset
  2432
    ts.tv_sec += sec;
c8d925d6c93f 8037340: Linux semaphores to use CLOCK_REALTIME
mgronlun
parents: 23444
diff changeset
  2433
    ts.tv_nsec += nsec;
c8d925d6c93f 8037340: Linux semaphores to use CLOCK_REALTIME
mgronlun
parents: 23444
diff changeset
  2434
    if (ts.tv_nsec >= NANOSECS_PER_SEC) {
c8d925d6c93f 8037340: Linux semaphores to use CLOCK_REALTIME
mgronlun
parents: 23444
diff changeset
  2435
      ts.tv_nsec -= NANOSECS_PER_SEC;
c8d925d6c93f 8037340: Linux semaphores to use CLOCK_REALTIME
mgronlun
parents: 23444
diff changeset
  2436
      ++ts.tv_sec; // note: this must be <= max_secs
c8d925d6c93f 8037340: Linux semaphores to use CLOCK_REALTIME
mgronlun
parents: 23444
diff changeset
  2437
    }
c8d925d6c93f 8037340: Linux semaphores to use CLOCK_REALTIME
mgronlun
parents: 23444
diff changeset
  2438
  }
18025
b7bcf7497f93 8005849: JEP 167: Event-Based JVM Tracing
sla
parents: 17854
diff changeset
  2439
b7bcf7497f93 8005849: JEP 167: Event-Based JVM Tracing
sla
parents: 17854
diff changeset
  2440
  while (1) {
b7bcf7497f93 8005849: JEP 167: Event-Based JVM Tracing
sla
parents: 17854
diff changeset
  2441
    int result = sem_timedwait(&_semaphore, &ts);
b7bcf7497f93 8005849: JEP 167: Event-Based JVM Tracing
sla
parents: 17854
diff changeset
  2442
    if (result == 0) {
b7bcf7497f93 8005849: JEP 167: Event-Based JVM Tracing
sla
parents: 17854
diff changeset
  2443
      return true;
b7bcf7497f93 8005849: JEP 167: Event-Based JVM Tracing
sla
parents: 17854
diff changeset
  2444
    } else if (errno == EINTR) {
b7bcf7497f93 8005849: JEP 167: Event-Based JVM Tracing
sla
parents: 17854
diff changeset
  2445
      continue;
b7bcf7497f93 8005849: JEP 167: Event-Based JVM Tracing
sla
parents: 17854
diff changeset
  2446
    } else if (errno == ETIMEDOUT) {
b7bcf7497f93 8005849: JEP 167: Event-Based JVM Tracing
sla
parents: 17854
diff changeset
  2447
      return false;
b7bcf7497f93 8005849: JEP 167: Event-Based JVM Tracing
sla
parents: 17854
diff changeset
  2448
    } else {
b7bcf7497f93 8005849: JEP 167: Event-Based JVM Tracing
sla
parents: 17854
diff changeset
  2449
      return false;
b7bcf7497f93 8005849: JEP 167: Event-Based JVM Tracing
sla
parents: 17854
diff changeset
  2450
    }
b7bcf7497f93 8005849: JEP 167: Event-Based JVM Tracing
sla
parents: 17854
diff changeset
  2451
  }
b7bcf7497f93 8005849: JEP 167: Event-Based JVM Tracing
sla
parents: 17854
diff changeset
  2452
}
b7bcf7497f93 8005849: JEP 167: Event-Based JVM Tracing
sla
parents: 17854
diff changeset
  2453
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2454
extern "C" {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2455
  typedef void (*sa_handler_t)(int);
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2456
  typedef void (*sa_sigaction_t)(int, siginfo_t *, void *);
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2457
}
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2458
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2459
void* os::signal(int signal_number, void* handler) {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2460
  struct sigaction sigAct, oldSigAct;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2461
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2462
  sigfillset(&(sigAct.sa_mask));
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2463
  sigAct.sa_flags   = SA_RESTART|SA_SIGINFO;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2464
  sigAct.sa_handler = CAST_TO_FN_PTR(sa_handler_t, handler);
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2465
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2466
  if (sigaction(signal_number, &sigAct, &oldSigAct)) {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2467
    // -1 means registration failed
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2468
    return (void *)-1;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2469
  }
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2470
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2471
  return CAST_FROM_FN_PTR(void*, oldSigAct.sa_handler);
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2472
}
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2473
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2474
void os::signal_raise(int signal_number) {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2475
  ::raise(signal_number);
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2476
}
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2477
26684
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
  2478
// The following code is moved from os.cpp for making this
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
  2479
// code platform specific, which it is by its very nature.
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2480
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2481
// Will be modified when max signal is changed to be dynamic
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2482
int os::sigexitnum_pd() {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2483
  return NSIG;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2484
}
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2485
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2486
// a counter for each possible signal value
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2487
static volatile jint pending_signals[NSIG+1] = { 0 };
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2488
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2489
// Linux(POSIX) specific hand shaking semaphore.
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2490
static sem_t sig_sem;
18025
b7bcf7497f93 8005849: JEP 167: Event-Based JVM Tracing
sla
parents: 17854
diff changeset
  2491
static Semaphore sr_semaphore;
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2492
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2493
void os::signal_init_pd() {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2494
  // Initialize signal structures
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2495
  ::memset((void*)pending_signals, 0, sizeof(pending_signals));
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2496
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2497
  // Initialize signal semaphore
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2498
  ::sem_init(&sig_sem, 0, 0);
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2499
}
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2500
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2501
void os::signal_notify(int sig) {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2502
  Atomic::inc(&pending_signals[sig]);
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2503
  ::sem_post(&sig_sem);
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2504
}
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2505
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2506
static int check_pending_signals(bool wait) {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2507
  Atomic::store(0, &sigint_count);
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2508
  for (;;) {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2509
    for (int i = 0; i < NSIG + 1; i++) {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2510
      jint n = pending_signals[i];
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2511
      if (n > 0 && n == Atomic::cmpxchg(n - 1, &pending_signals[i], n)) {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2512
        return i;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2513
      }
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2514
    }
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2515
    if (!wait) {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2516
      return -1;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2517
    }
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2518
    JavaThread *thread = JavaThread::current();
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2519
    ThreadBlockInVM tbivm(thread);
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2520
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2521
    bool threadIsSuspended;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2522
    do {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2523
      thread->set_suspend_equivalent();
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2524
      // cleared by handle_special_suspend_equivalent_condition() or java_suspend_self()
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2525
      ::sem_wait(&sig_sem);
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2526
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2527
      // were we externally suspended while we were waiting?
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2528
      threadIsSuspended = thread->handle_special_suspend_equivalent_condition();
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2529
      if (threadIsSuspended) {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2530
        // The semaphore has been incremented, but while we were waiting
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2531
        // another thread suspended us. We don't want to continue running
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2532
        // while suspended because that would surprise the thread that
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2533
        // suspended us.
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2534
        ::sem_post(&sig_sem);
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2535
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2536
        thread->java_suspend_self();
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2537
      }
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2538
    } while (threadIsSuspended);
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2539
  }
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2540
}
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2541
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2542
int os::signal_lookup() {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2543
  return check_pending_signals(false);
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2544
}
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2545
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2546
int os::signal_wait() {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2547
  return check_pending_signals(true);
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2548
}
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2549
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2550
////////////////////////////////////////////////////////////////////////////////
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2551
// Virtual Memory
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2552
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2553
int os::vm_page_size() {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2554
  // Seems redundant as all get out
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2555
  assert(os::Linux::page_size() != -1, "must call os::init");
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2556
  return os::Linux::page_size();
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2557
}
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2558
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2559
// Solaris allocates memory by pages.
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2560
int os::vm_allocation_granularity() {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2561
  assert(os::Linux::page_size() != -1, "must call os::init");
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2562
  return os::Linux::page_size();
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2563
}
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2564
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2565
// Rationale behind this function:
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2566
//  current (Mon Apr 25 20:12:18 MSD 2005) oprofile drops samples without executable
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2567
//  mapping for address (see lookup_dcookie() in the kernel module), thus we cannot get
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2568
//  samples for JITted code. Here we create private executable mapping over the code cache
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2569
//  and then we can use standard (well, almost, as mapping can change) way to provide
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2570
//  info for the reporting script by storing timestamp and location of symbol
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2571
void linux_wrap_code(char* base, size_t size) {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2572
  static volatile jint cnt = 0;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2573
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2574
  if (!UseOprofile) {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2575
    return;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2576
  }
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2577
5410
c4b979417733 6944822: Fix for 6938627 exposes problem with hard-coded buffer sizes
coleenp
parents: 5237
diff changeset
  2578
  char buf[PATH_MAX+1];
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2579
  int num = Atomic::add(1, &cnt);
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2580
5237
aab592fd4f44 6938627: Make temporary directory use property java.io.tmpdir when specified
coleenp
parents: 5090
diff changeset
  2581
  snprintf(buf, sizeof(buf), "%s/hs-vm-%d-%d",
aab592fd4f44 6938627: Make temporary directory use property java.io.tmpdir when specified
coleenp
parents: 5090
diff changeset
  2582
           os::get_temp_directory(), os::current_process_id(), num);
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2583
  unlink(buf);
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2584
7405
e6fc8d3926f8 6348631: remove the use of the HPI library from Hotspot
ikrylov
parents: 7397
diff changeset
  2585
  int fd = ::open(buf, O_CREAT | O_RDWR, S_IRWXU);
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2586
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2587
  if (fd != -1) {
7405
e6fc8d3926f8 6348631: remove the use of the HPI library from Hotspot
ikrylov
parents: 7397
diff changeset
  2588
    off_t rv = ::lseek(fd, size-2, SEEK_SET);
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2589
    if (rv != (off_t)-1) {
7405
e6fc8d3926f8 6348631: remove the use of the HPI library from Hotspot
ikrylov
parents: 7397
diff changeset
  2590
      if (::write(fd, "", 1) == 1) {
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2591
        mmap(base, size,
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2592
             PROT_READ|PROT_WRITE|PROT_EXEC,
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2593
             MAP_PRIVATE|MAP_FIXED|MAP_NORESERVE, fd, 0);
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2594
      }
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2595
    }
7405
e6fc8d3926f8 6348631: remove the use of the HPI library from Hotspot
ikrylov
parents: 7397
diff changeset
  2596
    ::close(fd);
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2597
    unlink(buf);
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2598
  }
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2599
}
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2600
18069
e6d4971c8650 8013057: assert(_needs_gc || SafepointSynchronize::is_at_safepoint()) failed: only read at safepoint
dcubed
parents: 18025
diff changeset
  2601
static bool recoverable_mmap_error(int err) {
e6d4971c8650 8013057: assert(_needs_gc || SafepointSynchronize::is_at_safepoint()) failed: only read at safepoint
dcubed
parents: 18025
diff changeset
  2602
  // See if the error is one we can let the caller handle. This
e6d4971c8650 8013057: assert(_needs_gc || SafepointSynchronize::is_at_safepoint()) failed: only read at safepoint
dcubed
parents: 18025
diff changeset
  2603
  // list of errno values comes from JBS-6843484. I can't find a
e6d4971c8650 8013057: assert(_needs_gc || SafepointSynchronize::is_at_safepoint()) failed: only read at safepoint
dcubed
parents: 18025
diff changeset
  2604
  // Linux man page that documents this specific set of errno
e6d4971c8650 8013057: assert(_needs_gc || SafepointSynchronize::is_at_safepoint()) failed: only read at safepoint
dcubed
parents: 18025
diff changeset
  2605
  // values so while this list currently matches Solaris, it may
e6d4971c8650 8013057: assert(_needs_gc || SafepointSynchronize::is_at_safepoint()) failed: only read at safepoint
dcubed
parents: 18025
diff changeset
  2606
  // change as we gain experience with this failure mode.
e6d4971c8650 8013057: assert(_needs_gc || SafepointSynchronize::is_at_safepoint()) failed: only read at safepoint
dcubed
parents: 18025
diff changeset
  2607
  switch (err) {
e6d4971c8650 8013057: assert(_needs_gc || SafepointSynchronize::is_at_safepoint()) failed: only read at safepoint
dcubed
parents: 18025
diff changeset
  2608
  case EBADF:
e6d4971c8650 8013057: assert(_needs_gc || SafepointSynchronize::is_at_safepoint()) failed: only read at safepoint
dcubed
parents: 18025
diff changeset
  2609
  case EINVAL:
e6d4971c8650 8013057: assert(_needs_gc || SafepointSynchronize::is_at_safepoint()) failed: only read at safepoint
dcubed
parents: 18025
diff changeset
  2610
  case ENOTSUP:
e6d4971c8650 8013057: assert(_needs_gc || SafepointSynchronize::is_at_safepoint()) failed: only read at safepoint
dcubed
parents: 18025
diff changeset
  2611
    // let the caller deal with these errors
e6d4971c8650 8013057: assert(_needs_gc || SafepointSynchronize::is_at_safepoint()) failed: only read at safepoint
dcubed
parents: 18025
diff changeset
  2612
    return true;
e6d4971c8650 8013057: assert(_needs_gc || SafepointSynchronize::is_at_safepoint()) failed: only read at safepoint
dcubed
parents: 18025
diff changeset
  2613
e6d4971c8650 8013057: assert(_needs_gc || SafepointSynchronize::is_at_safepoint()) failed: only read at safepoint
dcubed
parents: 18025
diff changeset
  2614
  default:
e6d4971c8650 8013057: assert(_needs_gc || SafepointSynchronize::is_at_safepoint()) failed: only read at safepoint
dcubed
parents: 18025
diff changeset
  2615
    // Any remaining errors on this OS can cause our reserved mapping
e6d4971c8650 8013057: assert(_needs_gc || SafepointSynchronize::is_at_safepoint()) failed: only read at safepoint
dcubed
parents: 18025
diff changeset
  2616
    // to be lost. That can cause confusion where different data
e6d4971c8650 8013057: assert(_needs_gc || SafepointSynchronize::is_at_safepoint()) failed: only read at safepoint
dcubed
parents: 18025
diff changeset
  2617
    // structures think they have the same memory mapped. The worst
e6d4971c8650 8013057: assert(_needs_gc || SafepointSynchronize::is_at_safepoint()) failed: only read at safepoint
dcubed
parents: 18025
diff changeset
  2618
    // scenario is if both the VM and a library think they have the
e6d4971c8650 8013057: assert(_needs_gc || SafepointSynchronize::is_at_safepoint()) failed: only read at safepoint
dcubed
parents: 18025
diff changeset
  2619
    // same memory mapped.
e6d4971c8650 8013057: assert(_needs_gc || SafepointSynchronize::is_at_safepoint()) failed: only read at safepoint
dcubed
parents: 18025
diff changeset
  2620
    return false;
e6d4971c8650 8013057: assert(_needs_gc || SafepointSynchronize::is_at_safepoint()) failed: only read at safepoint
dcubed
parents: 18025
diff changeset
  2621
  }
e6d4971c8650 8013057: assert(_needs_gc || SafepointSynchronize::is_at_safepoint()) failed: only read at safepoint
dcubed
parents: 18025
diff changeset
  2622
}
e6d4971c8650 8013057: assert(_needs_gc || SafepointSynchronize::is_at_safepoint()) failed: only read at safepoint
dcubed
parents: 18025
diff changeset
  2623
e6d4971c8650 8013057: assert(_needs_gc || SafepointSynchronize::is_at_safepoint()) failed: only read at safepoint
dcubed
parents: 18025
diff changeset
  2624
static void warn_fail_commit_memory(char* addr, size_t size, bool exec,
e6d4971c8650 8013057: assert(_needs_gc || SafepointSynchronize::is_at_safepoint()) failed: only read at safepoint
dcubed
parents: 18025
diff changeset
  2625
                                    int err) {
e6d4971c8650 8013057: assert(_needs_gc || SafepointSynchronize::is_at_safepoint()) failed: only read at safepoint
dcubed
parents: 18025
diff changeset
  2626
  warning("INFO: os::commit_memory(" PTR_FORMAT ", " SIZE_FORMAT
e6d4971c8650 8013057: assert(_needs_gc || SafepointSynchronize::is_at_safepoint()) failed: only read at safepoint
dcubed
parents: 18025
diff changeset
  2627
          ", %d) failed; error='%s' (errno=%d)", addr, size, exec,
e6d4971c8650 8013057: assert(_needs_gc || SafepointSynchronize::is_at_safepoint()) failed: only read at safepoint
dcubed
parents: 18025
diff changeset
  2628
          strerror(err), err);
e6d4971c8650 8013057: assert(_needs_gc || SafepointSynchronize::is_at_safepoint()) failed: only read at safepoint
dcubed
parents: 18025
diff changeset
  2629
}
e6d4971c8650 8013057: assert(_needs_gc || SafepointSynchronize::is_at_safepoint()) failed: only read at safepoint
dcubed
parents: 18025
diff changeset
  2630
e6d4971c8650 8013057: assert(_needs_gc || SafepointSynchronize::is_at_safepoint()) failed: only read at safepoint
dcubed
parents: 18025
diff changeset
  2631
static void warn_fail_commit_memory(char* addr, size_t size,
e6d4971c8650 8013057: assert(_needs_gc || SafepointSynchronize::is_at_safepoint()) failed: only read at safepoint
dcubed
parents: 18025
diff changeset
  2632
                                    size_t alignment_hint, bool exec,
e6d4971c8650 8013057: assert(_needs_gc || SafepointSynchronize::is_at_safepoint()) failed: only read at safepoint
dcubed
parents: 18025
diff changeset
  2633
                                    int err) {
e6d4971c8650 8013057: assert(_needs_gc || SafepointSynchronize::is_at_safepoint()) failed: only read at safepoint
dcubed
parents: 18025
diff changeset
  2634
  warning("INFO: os::commit_memory(" PTR_FORMAT ", " SIZE_FORMAT
e6d4971c8650 8013057: assert(_needs_gc || SafepointSynchronize::is_at_safepoint()) failed: only read at safepoint
dcubed
parents: 18025
diff changeset
  2635
          ", " SIZE_FORMAT ", %d) failed; error='%s' (errno=%d)", addr, size,
e6d4971c8650 8013057: assert(_needs_gc || SafepointSynchronize::is_at_safepoint()) failed: only read at safepoint
dcubed
parents: 18025
diff changeset
  2636
          alignment_hint, exec, strerror(err), err);
e6d4971c8650 8013057: assert(_needs_gc || SafepointSynchronize::is_at_safepoint()) failed: only read at safepoint
dcubed
parents: 18025
diff changeset
  2637
}
e6d4971c8650 8013057: assert(_needs_gc || SafepointSynchronize::is_at_safepoint()) failed: only read at safepoint
dcubed
parents: 18025
diff changeset
  2638
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2639
// NOTE: Linux kernel does not really reserve the pages for us.
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2640
//       All it does is to check if there are enough free pages
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2641
//       left at the time of mmap(). This could be a potential
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2642
//       problem.
18069
e6d4971c8650 8013057: assert(_needs_gc || SafepointSynchronize::is_at_safepoint()) failed: only read at safepoint
dcubed
parents: 18025
diff changeset
  2643
int os::Linux::commit_memory_impl(char* addr, size_t size, bool exec) {
2268
bea8be80ec88 6541756: Reduce executable C-heap
coleenp
parents: 2259
diff changeset
  2644
  int prot = exec ? PROT_READ|PROT_WRITE|PROT_EXEC : PROT_READ|PROT_WRITE;
bea8be80ec88 6541756: Reduce executable C-heap
coleenp
parents: 2259
diff changeset
  2645
  uintptr_t res = (uintptr_t) ::mmap(addr, size, prot,
26683
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  2646
                                     MAP_PRIVATE|MAP_FIXED|MAP_ANONYMOUS, -1, 0);
10494
3f347ed8bd3c 7082969: NUMA interleaving
iveresov
parents: 10239
diff changeset
  2647
  if (res != (uintptr_t) MAP_FAILED) {
3f347ed8bd3c 7082969: NUMA interleaving
iveresov
parents: 10239
diff changeset
  2648
    if (UseNUMAInterleaving) {
3f347ed8bd3c 7082969: NUMA interleaving
iveresov
parents: 10239
diff changeset
  2649
      numa_make_global(addr, size);
3f347ed8bd3c 7082969: NUMA interleaving
iveresov
parents: 10239
diff changeset
  2650
    }
18069
e6d4971c8650 8013057: assert(_needs_gc || SafepointSynchronize::is_at_safepoint()) failed: only read at safepoint
dcubed
parents: 18025
diff changeset
  2651
    return 0;
e6d4971c8650 8013057: assert(_needs_gc || SafepointSynchronize::is_at_safepoint()) failed: only read at safepoint
dcubed
parents: 18025
diff changeset
  2652
  }
e6d4971c8650 8013057: assert(_needs_gc || SafepointSynchronize::is_at_safepoint()) failed: only read at safepoint
dcubed
parents: 18025
diff changeset
  2653
e6d4971c8650 8013057: assert(_needs_gc || SafepointSynchronize::is_at_safepoint()) failed: only read at safepoint
dcubed
parents: 18025
diff changeset
  2654
  int err = errno;  // save errno from mmap() call above
e6d4971c8650 8013057: assert(_needs_gc || SafepointSynchronize::is_at_safepoint()) failed: only read at safepoint
dcubed
parents: 18025
diff changeset
  2655
e6d4971c8650 8013057: assert(_needs_gc || SafepointSynchronize::is_at_safepoint()) failed: only read at safepoint
dcubed
parents: 18025
diff changeset
  2656
  if (!recoverable_mmap_error(err)) {
e6d4971c8650 8013057: assert(_needs_gc || SafepointSynchronize::is_at_safepoint()) failed: only read at safepoint
dcubed
parents: 18025
diff changeset
  2657
    warn_fail_commit_memory(addr, size, exec, err);
e6d4971c8650 8013057: assert(_needs_gc || SafepointSynchronize::is_at_safepoint()) failed: only read at safepoint
dcubed
parents: 18025
diff changeset
  2658
    vm_exit_out_of_memory(size, OOM_MMAP_ERROR, "committing reserved memory.");
e6d4971c8650 8013057: assert(_needs_gc || SafepointSynchronize::is_at_safepoint()) failed: only read at safepoint
dcubed
parents: 18025
diff changeset
  2659
  }
e6d4971c8650 8013057: assert(_needs_gc || SafepointSynchronize::is_at_safepoint()) failed: only read at safepoint
dcubed
parents: 18025
diff changeset
  2660
e6d4971c8650 8013057: assert(_needs_gc || SafepointSynchronize::is_at_safepoint()) failed: only read at safepoint
dcubed
parents: 18025
diff changeset
  2661
  return err;
e6d4971c8650 8013057: assert(_needs_gc || SafepointSynchronize::is_at_safepoint()) failed: only read at safepoint
dcubed
parents: 18025
diff changeset
  2662
}
e6d4971c8650 8013057: assert(_needs_gc || SafepointSynchronize::is_at_safepoint()) failed: only read at safepoint
dcubed
parents: 18025
diff changeset
  2663
e6d4971c8650 8013057: assert(_needs_gc || SafepointSynchronize::is_at_safepoint()) failed: only read at safepoint
dcubed
parents: 18025
diff changeset
  2664
bool os::pd_commit_memory(char* addr, size_t size, bool exec) {
e6d4971c8650 8013057: assert(_needs_gc || SafepointSynchronize::is_at_safepoint()) failed: only read at safepoint
dcubed
parents: 18025
diff changeset
  2665
  return os::Linux::commit_memory_impl(addr, size, exec) == 0;
e6d4971c8650 8013057: assert(_needs_gc || SafepointSynchronize::is_at_safepoint()) failed: only read at safepoint
dcubed
parents: 18025
diff changeset
  2666
}
e6d4971c8650 8013057: assert(_needs_gc || SafepointSynchronize::is_at_safepoint()) failed: only read at safepoint
dcubed
parents: 18025
diff changeset
  2667
e6d4971c8650 8013057: assert(_needs_gc || SafepointSynchronize::is_at_safepoint()) failed: only read at safepoint
dcubed
parents: 18025
diff changeset
  2668
void os::pd_commit_memory_or_exit(char* addr, size_t size, bool exec,
e6d4971c8650 8013057: assert(_needs_gc || SafepointSynchronize::is_at_safepoint()) failed: only read at safepoint
dcubed
parents: 18025
diff changeset
  2669
                                  const char* mesg) {
e6d4971c8650 8013057: assert(_needs_gc || SafepointSynchronize::is_at_safepoint()) failed: only read at safepoint
dcubed
parents: 18025
diff changeset
  2670
  assert(mesg != NULL, "mesg must be specified");
e6d4971c8650 8013057: assert(_needs_gc || SafepointSynchronize::is_at_safepoint()) failed: only read at safepoint
dcubed
parents: 18025
diff changeset
  2671
  int err = os::Linux::commit_memory_impl(addr, size, exec);
e6d4971c8650 8013057: assert(_needs_gc || SafepointSynchronize::is_at_safepoint()) failed: only read at safepoint
dcubed
parents: 18025
diff changeset
  2672
  if (err != 0) {
e6d4971c8650 8013057: assert(_needs_gc || SafepointSynchronize::is_at_safepoint()) failed: only read at safepoint
dcubed
parents: 18025
diff changeset
  2673
    // the caller wants all commit errors to exit with the specified mesg:
e6d4971c8650 8013057: assert(_needs_gc || SafepointSynchronize::is_at_safepoint()) failed: only read at safepoint
dcubed
parents: 18025
diff changeset
  2674
    warn_fail_commit_memory(addr, size, exec, err);
e6d4971c8650 8013057: assert(_needs_gc || SafepointSynchronize::is_at_safepoint()) failed: only read at safepoint
dcubed
parents: 18025
diff changeset
  2675
    vm_exit_out_of_memory(size, OOM_MMAP_ERROR, mesg);
e6d4971c8650 8013057: assert(_needs_gc || SafepointSynchronize::is_at_safepoint()) failed: only read at safepoint
dcubed
parents: 18025
diff changeset
  2676
  }
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2677
}
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2678
9335
7bdd2a3ab3d8 7034464: Support transparent large pages on Linux
iveresov
parents: 8476
diff changeset
  2679
// Define MAP_HUGETLB here so we can build HotSpot on old systems.
7bdd2a3ab3d8 7034464: Support transparent large pages on Linux
iveresov
parents: 8476
diff changeset
  2680
#ifndef MAP_HUGETLB
26684
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
  2681
  #define MAP_HUGETLB 0x40000
9335
7bdd2a3ab3d8 7034464: Support transparent large pages on Linux
iveresov
parents: 8476
diff changeset
  2682
#endif
7bdd2a3ab3d8 7034464: Support transparent large pages on Linux
iveresov
parents: 8476
diff changeset
  2683
7bdd2a3ab3d8 7034464: Support transparent large pages on Linux
iveresov
parents: 8476
diff changeset
  2684
// Define MADV_HUGEPAGE here so we can build HotSpot on old systems.
7bdd2a3ab3d8 7034464: Support transparent large pages on Linux
iveresov
parents: 8476
diff changeset
  2685
#ifndef MADV_HUGEPAGE
26684
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
  2686
  #define MADV_HUGEPAGE 14
9335
7bdd2a3ab3d8 7034464: Support transparent large pages on Linux
iveresov
parents: 8476
diff changeset
  2687
#endif
7bdd2a3ab3d8 7034464: Support transparent large pages on Linux
iveresov
parents: 8476
diff changeset
  2688
18069
e6d4971c8650 8013057: assert(_needs_gc || SafepointSynchronize::is_at_safepoint()) failed: only read at safepoint
dcubed
parents: 18025
diff changeset
  2689
int os::Linux::commit_memory_impl(char* addr, size_t size,
e6d4971c8650 8013057: assert(_needs_gc || SafepointSynchronize::is_at_safepoint()) failed: only read at safepoint
dcubed
parents: 18025
diff changeset
  2690
                                  size_t alignment_hint, bool exec) {
19546
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  2691
  int err = os::Linux::commit_memory_impl(addr, size, exec);
18069
e6d4971c8650 8013057: assert(_needs_gc || SafepointSynchronize::is_at_safepoint()) failed: only read at safepoint
dcubed
parents: 18025
diff changeset
  2692
  if (err == 0) {
10522
23830453e083 7087583: Hotspot fails to allocate heap with mmap(MAP_HUGETLB)
iveresov
parents: 10496
diff changeset
  2693
    realign_memory(addr, size, alignment_hint);
18069
e6d4971c8650 8013057: assert(_needs_gc || SafepointSynchronize::is_at_safepoint()) failed: only read at safepoint
dcubed
parents: 18025
diff changeset
  2694
  }
e6d4971c8650 8013057: assert(_needs_gc || SafepointSynchronize::is_at_safepoint()) failed: only read at safepoint
dcubed
parents: 18025
diff changeset
  2695
  return err;
e6d4971c8650 8013057: assert(_needs_gc || SafepointSynchronize::is_at_safepoint()) failed: only read at safepoint
dcubed
parents: 18025
diff changeset
  2696
}
e6d4971c8650 8013057: assert(_needs_gc || SafepointSynchronize::is_at_safepoint()) failed: only read at safepoint
dcubed
parents: 18025
diff changeset
  2697
e6d4971c8650 8013057: assert(_needs_gc || SafepointSynchronize::is_at_safepoint()) failed: only read at safepoint
dcubed
parents: 18025
diff changeset
  2698
bool os::pd_commit_memory(char* addr, size_t size, size_t alignment_hint,
e6d4971c8650 8013057: assert(_needs_gc || SafepointSynchronize::is_at_safepoint()) failed: only read at safepoint
dcubed
parents: 18025
diff changeset
  2699
                          bool exec) {
e6d4971c8650 8013057: assert(_needs_gc || SafepointSynchronize::is_at_safepoint()) failed: only read at safepoint
dcubed
parents: 18025
diff changeset
  2700
  return os::Linux::commit_memory_impl(addr, size, alignment_hint, exec) == 0;
e6d4971c8650 8013057: assert(_needs_gc || SafepointSynchronize::is_at_safepoint()) failed: only read at safepoint
dcubed
parents: 18025
diff changeset
  2701
}
e6d4971c8650 8013057: assert(_needs_gc || SafepointSynchronize::is_at_safepoint()) failed: only read at safepoint
dcubed
parents: 18025
diff changeset
  2702
e6d4971c8650 8013057: assert(_needs_gc || SafepointSynchronize::is_at_safepoint()) failed: only read at safepoint
dcubed
parents: 18025
diff changeset
  2703
void os::pd_commit_memory_or_exit(char* addr, size_t size,
e6d4971c8650 8013057: assert(_needs_gc || SafepointSynchronize::is_at_safepoint()) failed: only read at safepoint
dcubed
parents: 18025
diff changeset
  2704
                                  size_t alignment_hint, bool exec,
e6d4971c8650 8013057: assert(_needs_gc || SafepointSynchronize::is_at_safepoint()) failed: only read at safepoint
dcubed
parents: 18025
diff changeset
  2705
                                  const char* mesg) {
e6d4971c8650 8013057: assert(_needs_gc || SafepointSynchronize::is_at_safepoint()) failed: only read at safepoint
dcubed
parents: 18025
diff changeset
  2706
  assert(mesg != NULL, "mesg must be specified");
e6d4971c8650 8013057: assert(_needs_gc || SafepointSynchronize::is_at_safepoint()) failed: only read at safepoint
dcubed
parents: 18025
diff changeset
  2707
  int err = os::Linux::commit_memory_impl(addr, size, alignment_hint, exec);
e6d4971c8650 8013057: assert(_needs_gc || SafepointSynchronize::is_at_safepoint()) failed: only read at safepoint
dcubed
parents: 18025
diff changeset
  2708
  if (err != 0) {
e6d4971c8650 8013057: assert(_needs_gc || SafepointSynchronize::is_at_safepoint()) failed: only read at safepoint
dcubed
parents: 18025
diff changeset
  2709
    // the caller wants all commit errors to exit with the specified mesg:
e6d4971c8650 8013057: assert(_needs_gc || SafepointSynchronize::is_at_safepoint()) failed: only read at safepoint
dcubed
parents: 18025
diff changeset
  2710
    warn_fail_commit_memory(addr, size, alignment_hint, exec, err);
e6d4971c8650 8013057: assert(_needs_gc || SafepointSynchronize::is_at_safepoint()) failed: only read at safepoint
dcubed
parents: 18025
diff changeset
  2711
    vm_exit_out_of_memory(size, OOM_MMAP_ERROR, mesg);
e6d4971c8650 8013057: assert(_needs_gc || SafepointSynchronize::is_at_safepoint()) failed: only read at safepoint
dcubed
parents: 18025
diff changeset
  2712
  }
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2713
}
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2714
13195
be27e1b6a4b9 6995781: Native Memory Tracking (Phase 1)
zgu
parents: 12735
diff changeset
  2715
void os::pd_realign_memory(char *addr, size_t bytes, size_t alignment_hint) {
19546
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  2716
  if (UseTransparentHugePages && alignment_hint > (size_t)vm_page_size()) {
9335
7bdd2a3ab3d8 7034464: Support transparent large pages on Linux
iveresov
parents: 8476
diff changeset
  2717
    // We don't check the return value: madvise(MADV_HUGEPAGE) may not
7bdd2a3ab3d8 7034464: Support transparent large pages on Linux
iveresov
parents: 8476
diff changeset
  2718
    // be supported or the memory may already be backed by huge pages.
7bdd2a3ab3d8 7034464: Support transparent large pages on Linux
iveresov
parents: 8476
diff changeset
  2719
    ::madvise(addr, bytes, MADV_HUGEPAGE);
7bdd2a3ab3d8 7034464: Support transparent large pages on Linux
iveresov
parents: 8476
diff changeset
  2720
  }
7bdd2a3ab3d8 7034464: Support transparent large pages on Linux
iveresov
parents: 8476
diff changeset
  2721
}
388
bcc631c5bbec 6684395: Port NUMA-aware allocator to linux
iveresov
parents: 252
diff changeset
  2722
13195
be27e1b6a4b9 6995781: Native Memory Tracking (Phase 1)
zgu
parents: 12735
diff changeset
  2723
void os::pd_free_memory(char *addr, size_t bytes, size_t alignment_hint) {
12116
d81396ae8bf6 7151089: PS NUMA: NUMA allocator should not attempt to free pages when using SHM large pages
iveresov
parents: 11967
diff changeset
  2724
  // This method works by doing an mmap over an existing mmaping and effectively discarding
d81396ae8bf6 7151089: PS NUMA: NUMA allocator should not attempt to free pages when using SHM large pages
iveresov
parents: 11967
diff changeset
  2725
  // the existing pages. However it won't work for SHM-based large pages that cannot be
d81396ae8bf6 7151089: PS NUMA: NUMA allocator should not attempt to free pages when using SHM large pages
iveresov
parents: 11967
diff changeset
  2726
  // uncommitted at all. We don't do anything in this case to avoid creating a segment with
d81396ae8bf6 7151089: PS NUMA: NUMA allocator should not attempt to free pages when using SHM large pages
iveresov
parents: 11967
diff changeset
  2727
  // small pages on top of the SHM segment. This method always works for small pages, so we
d81396ae8bf6 7151089: PS NUMA: NUMA allocator should not attempt to free pages when using SHM large pages
iveresov
parents: 11967
diff changeset
  2728
  // allow that in any case.
19546
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  2729
  if (alignment_hint <= (size_t)os::vm_page_size() || can_commit_large_page_memory()) {
18069
e6d4971c8650 8013057: assert(_needs_gc || SafepointSynchronize::is_at_safepoint()) failed: only read at safepoint
dcubed
parents: 18025
diff changeset
  2730
    commit_memory(addr, bytes, alignment_hint, !ExecMem);
12116
d81396ae8bf6 7151089: PS NUMA: NUMA allocator should not attempt to free pages when using SHM large pages
iveresov
parents: 11967
diff changeset
  2731
  }
388
bcc631c5bbec 6684395: Port NUMA-aware allocator to linux
iveresov
parents: 252
diff changeset
  2732
}
bcc631c5bbec 6684395: Port NUMA-aware allocator to linux
iveresov
parents: 252
diff changeset
  2733
1615
b46d9f19bde2 6779436: NUMA allocator: libnuma expects certain size of the buffer in numa_node_to_cpus()
iveresov
parents: 1388
diff changeset
  2734
void os::numa_make_global(char *addr, size_t bytes) {
b46d9f19bde2 6779436: NUMA allocator: libnuma expects certain size of the buffer in numa_node_to_cpus()
iveresov
parents: 1388
diff changeset
  2735
  Linux::numa_interleave_memory(addr, bytes);
b46d9f19bde2 6779436: NUMA allocator: libnuma expects certain size of the buffer in numa_node_to_cpus()
iveresov
parents: 1388
diff changeset
  2736
}
388
bcc631c5bbec 6684395: Port NUMA-aware allocator to linux
iveresov
parents: 252
diff changeset
  2737
19726
c086d352d3f7 8016155: SIGBUS when running Kitchensink with ParallelScavenge and ParallelOld
mgerdin
parents: 18683
diff changeset
  2738
// Define for numa_set_bind_policy(int). Setting the argument to 0 will set the
c086d352d3f7 8016155: SIGBUS when running Kitchensink with ParallelScavenge and ParallelOld
mgerdin
parents: 18683
diff changeset
  2739
// bind policy to MPOL_PREFERRED for the current thread.
c086d352d3f7 8016155: SIGBUS when running Kitchensink with ParallelScavenge and ParallelOld
mgerdin
parents: 18683
diff changeset
  2740
#define USE_MPOL_PREFERRED 0
c086d352d3f7 8016155: SIGBUS when running Kitchensink with ParallelScavenge and ParallelOld
mgerdin
parents: 18683
diff changeset
  2741
388
bcc631c5bbec 6684395: Port NUMA-aware allocator to linux
iveresov
parents: 252
diff changeset
  2742
void os::numa_make_local(char *addr, size_t bytes, int lgrp_hint) {
19726
c086d352d3f7 8016155: SIGBUS when running Kitchensink with ParallelScavenge and ParallelOld
mgerdin
parents: 18683
diff changeset
  2743
  // To make NUMA and large pages more robust when both enabled, we need to ease
c086d352d3f7 8016155: SIGBUS when running Kitchensink with ParallelScavenge and ParallelOld
mgerdin
parents: 18683
diff changeset
  2744
  // the requirements on where the memory should be allocated. MPOL_BIND is the
c086d352d3f7 8016155: SIGBUS when running Kitchensink with ParallelScavenge and ParallelOld
mgerdin
parents: 18683
diff changeset
  2745
  // default policy and it will force memory to be allocated on the specified
c086d352d3f7 8016155: SIGBUS when running Kitchensink with ParallelScavenge and ParallelOld
mgerdin
parents: 18683
diff changeset
  2746
  // node. Changing this to MPOL_PREFERRED will prefer to allocate the memory on
c086d352d3f7 8016155: SIGBUS when running Kitchensink with ParallelScavenge and ParallelOld
mgerdin
parents: 18683
diff changeset
  2747
  // the specified node, but will not force it. Using this policy will prevent
c086d352d3f7 8016155: SIGBUS when running Kitchensink with ParallelScavenge and ParallelOld
mgerdin
parents: 18683
diff changeset
  2748
  // getting SIGBUS when trying to allocate large pages on NUMA nodes with no
c086d352d3f7 8016155: SIGBUS when running Kitchensink with ParallelScavenge and ParallelOld
mgerdin
parents: 18683
diff changeset
  2749
  // free large pages.
c086d352d3f7 8016155: SIGBUS when running Kitchensink with ParallelScavenge and ParallelOld
mgerdin
parents: 18683
diff changeset
  2750
  Linux::numa_set_bind_policy(USE_MPOL_PREFERRED);
388
bcc631c5bbec 6684395: Port NUMA-aware allocator to linux
iveresov
parents: 252
diff changeset
  2751
  Linux::numa_tonode_memory(addr, bytes, lgrp_hint);
bcc631c5bbec 6684395: Port NUMA-aware allocator to linux
iveresov
parents: 252
diff changeset
  2752
}
bcc631c5bbec 6684395: Port NUMA-aware allocator to linux
iveresov
parents: 252
diff changeset
  2753
26684
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
  2754
bool os::numa_topology_changed() { return false; }
388
bcc631c5bbec 6684395: Port NUMA-aware allocator to linux
iveresov
parents: 252
diff changeset
  2755
bcc631c5bbec 6684395: Port NUMA-aware allocator to linux
iveresov
parents: 252
diff changeset
  2756
size_t os::numa_get_groups_num() {
bcc631c5bbec 6684395: Port NUMA-aware allocator to linux
iveresov
parents: 252
diff changeset
  2757
  int max_node = Linux::numa_max_node();
bcc631c5bbec 6684395: Port NUMA-aware allocator to linux
iveresov
parents: 252
diff changeset
  2758
  return max_node > 0 ? max_node + 1 : 1;
bcc631c5bbec 6684395: Port NUMA-aware allocator to linux
iveresov
parents: 252
diff changeset
  2759
}
bcc631c5bbec 6684395: Port NUMA-aware allocator to linux
iveresov
parents: 252
diff changeset
  2760
bcc631c5bbec 6684395: Port NUMA-aware allocator to linux
iveresov
parents: 252
diff changeset
  2761
int os::numa_get_group_id() {
bcc631c5bbec 6684395: Port NUMA-aware allocator to linux
iveresov
parents: 252
diff changeset
  2762
  int cpu_id = Linux::sched_getcpu();
bcc631c5bbec 6684395: Port NUMA-aware allocator to linux
iveresov
parents: 252
diff changeset
  2763
  if (cpu_id != -1) {
bcc631c5bbec 6684395: Port NUMA-aware allocator to linux
iveresov
parents: 252
diff changeset
  2764
    int lgrp_id = Linux::get_node_by_cpu(cpu_id);
bcc631c5bbec 6684395: Port NUMA-aware allocator to linux
iveresov
parents: 252
diff changeset
  2765
    if (lgrp_id != -1) {
bcc631c5bbec 6684395: Port NUMA-aware allocator to linux
iveresov
parents: 252
diff changeset
  2766
      return lgrp_id;
bcc631c5bbec 6684395: Port NUMA-aware allocator to linux
iveresov
parents: 252
diff changeset
  2767
    }
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2768
  }
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2769
  return 0;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2770
}
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2771
388
bcc631c5bbec 6684395: Port NUMA-aware allocator to linux
iveresov
parents: 252
diff changeset
  2772
size_t os::numa_get_leaf_groups(int *ids, size_t size) {
bcc631c5bbec 6684395: Port NUMA-aware allocator to linux
iveresov
parents: 252
diff changeset
  2773
  for (size_t i = 0; i < size; i++) {
bcc631c5bbec 6684395: Port NUMA-aware allocator to linux
iveresov
parents: 252
diff changeset
  2774
    ids[i] = i;
bcc631c5bbec 6684395: Port NUMA-aware allocator to linux
iveresov
parents: 252
diff changeset
  2775
  }
bcc631c5bbec 6684395: Port NUMA-aware allocator to linux
iveresov
parents: 252
diff changeset
  2776
  return size;
bcc631c5bbec 6684395: Port NUMA-aware allocator to linux
iveresov
parents: 252
diff changeset
  2777
}
bcc631c5bbec 6684395: Port NUMA-aware allocator to linux
iveresov
parents: 252
diff changeset
  2778
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2779
bool os::get_page_info(char *start, page_info* info) {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2780
  return false;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2781
}
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2782
26684
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
  2783
char *os::scan_pages(char *start, char* end, page_info* page_expected,
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
  2784
                     page_info* page_found) {
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2785
  return end;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2786
}
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2787
10239
c7af330d33d9 7060836: RHEL 5.5 and 5.6 should support UseNUMA
iveresov
parents: 10238
diff changeset
  2788
c7af330d33d9 7060836: RHEL 5.5 and 5.6 should support UseNUMA
iveresov
parents: 10238
diff changeset
  2789
int os::Linux::sched_getcpu_syscall(void) {
c7af330d33d9 7060836: RHEL 5.5 and 5.6 should support UseNUMA
iveresov
parents: 10238
diff changeset
  2790
  unsigned int cpu;
c7af330d33d9 7060836: RHEL 5.5 and 5.6 should support UseNUMA
iveresov
parents: 10238
diff changeset
  2791
  int retval = -1;
c7af330d33d9 7060836: RHEL 5.5 and 5.6 should support UseNUMA
iveresov
parents: 10238
diff changeset
  2792
c7af330d33d9 7060836: RHEL 5.5 and 5.6 should support UseNUMA
iveresov
parents: 10238
diff changeset
  2793
#if defined(IA32)
26684
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
  2794
  #ifndef SYS_getcpu
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
  2795
    #define SYS_getcpu 318
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
  2796
  #endif
10239
c7af330d33d9 7060836: RHEL 5.5 and 5.6 should support UseNUMA
iveresov
parents: 10238
diff changeset
  2797
  retval = syscall(SYS_getcpu, &cpu, NULL, NULL);
c7af330d33d9 7060836: RHEL 5.5 and 5.6 should support UseNUMA
iveresov
parents: 10238
diff changeset
  2798
#elif defined(AMD64)
10496
b209db6147cf 7082645: Hotspot doesn't compile on old linuxes after 7060836
iveresov
parents: 10494
diff changeset
  2799
// Unfortunately we have to bring all these macros here from vsyscall.h
b209db6147cf 7082645: Hotspot doesn't compile on old linuxes after 7060836
iveresov
parents: 10494
diff changeset
  2800
// to be able to compile on old linuxes.
26684
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
  2801
  #define __NR_vgetcpu 2
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
  2802
  #define VSYSCALL_START (-10UL << 20)
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
  2803
  #define VSYSCALL_SIZE 1024
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
  2804
  #define VSYSCALL_ADDR(vsyscall_nr) (VSYSCALL_START+VSYSCALL_SIZE*(vsyscall_nr))
10239
c7af330d33d9 7060836: RHEL 5.5 and 5.6 should support UseNUMA
iveresov
parents: 10238
diff changeset
  2805
  typedef long (*vgetcpu_t)(unsigned int *cpu, unsigned int *node, unsigned long *tcache);
c7af330d33d9 7060836: RHEL 5.5 and 5.6 should support UseNUMA
iveresov
parents: 10238
diff changeset
  2806
  vgetcpu_t vgetcpu = (vgetcpu_t)VSYSCALL_ADDR(__NR_vgetcpu);
c7af330d33d9 7060836: RHEL 5.5 and 5.6 should support UseNUMA
iveresov
parents: 10238
diff changeset
  2807
  retval = vgetcpu(&cpu, NULL, NULL);
c7af330d33d9 7060836: RHEL 5.5 and 5.6 should support UseNUMA
iveresov
parents: 10238
diff changeset
  2808
#endif
c7af330d33d9 7060836: RHEL 5.5 and 5.6 should support UseNUMA
iveresov
parents: 10238
diff changeset
  2809
c7af330d33d9 7060836: RHEL 5.5 and 5.6 should support UseNUMA
iveresov
parents: 10238
diff changeset
  2810
  return (retval == -1) ? retval : cpu;
c7af330d33d9 7060836: RHEL 5.5 and 5.6 should support UseNUMA
iveresov
parents: 10238
diff changeset
  2811
}
c7af330d33d9 7060836: RHEL 5.5 and 5.6 should support UseNUMA
iveresov
parents: 10238
diff changeset
  2812
8106
19106a0203fb 6588413: Use -fvisibility=hidden for gcc compiles
coleenp
parents: 7901
diff changeset
  2813
// Something to do with the numa-aware allocator needs these symbols
19106a0203fb 6588413: Use -fvisibility=hidden for gcc compiles
coleenp
parents: 7901
diff changeset
  2814
extern "C" JNIEXPORT void numa_warn(int number, char *where, ...) { }
19106a0203fb 6588413: Use -fvisibility=hidden for gcc compiles
coleenp
parents: 7901
diff changeset
  2815
extern "C" JNIEXPORT void numa_error(char *where) { }
19106a0203fb 6588413: Use -fvisibility=hidden for gcc compiles
coleenp
parents: 7901
diff changeset
  2816
extern "C" JNIEXPORT int fork1() { return fork(); }
388
bcc631c5bbec 6684395: Port NUMA-aware allocator to linux
iveresov
parents: 252
diff changeset
  2817
2753
1e9bbaae891b 6840196: NUMA allocator: crash in fastdebug during startup on Linux
iveresov
parents: 2751
diff changeset
  2818
1e9bbaae891b 6840196: NUMA allocator: crash in fastdebug during startup on Linux
iveresov
parents: 2751
diff changeset
  2819
// If we are running with libnuma version > 2, then we should
1e9bbaae891b 6840196: NUMA allocator: crash in fastdebug during startup on Linux
iveresov
parents: 2751
diff changeset
  2820
// be trying to use symbols with versions 1.1
1e9bbaae891b 6840196: NUMA allocator: crash in fastdebug during startup on Linux
iveresov
parents: 2751
diff changeset
  2821
// If we are running with earlier version, which did not have symbol versions,
1e9bbaae891b 6840196: NUMA allocator: crash in fastdebug during startup on Linux
iveresov
parents: 2751
diff changeset
  2822
// we should use the base version.
1e9bbaae891b 6840196: NUMA allocator: crash in fastdebug during startup on Linux
iveresov
parents: 2751
diff changeset
  2823
void* os::Linux::libnuma_dlsym(void* handle, const char *name) {
1e9bbaae891b 6840196: NUMA allocator: crash in fastdebug during startup on Linux
iveresov
parents: 2751
diff changeset
  2824
  void *f = dlvsym(handle, name, "libnuma_1.1");
1e9bbaae891b 6840196: NUMA allocator: crash in fastdebug during startup on Linux
iveresov
parents: 2751
diff changeset
  2825
  if (f == NULL) {
1e9bbaae891b 6840196: NUMA allocator: crash in fastdebug during startup on Linux
iveresov
parents: 2751
diff changeset
  2826
    f = dlsym(handle, name);
1e9bbaae891b 6840196: NUMA allocator: crash in fastdebug during startup on Linux
iveresov
parents: 2751
diff changeset
  2827
  }
1e9bbaae891b 6840196: NUMA allocator: crash in fastdebug during startup on Linux
iveresov
parents: 2751
diff changeset
  2828
  return f;
1e9bbaae891b 6840196: NUMA allocator: crash in fastdebug during startup on Linux
iveresov
parents: 2751
diff changeset
  2829
}
1e9bbaae891b 6840196: NUMA allocator: crash in fastdebug during startup on Linux
iveresov
parents: 2751
diff changeset
  2830
1615
b46d9f19bde2 6779436: NUMA allocator: libnuma expects certain size of the buffer in numa_node_to_cpus()
iveresov
parents: 1388
diff changeset
  2831
bool os::Linux::libnuma_init() {
388
bcc631c5bbec 6684395: Port NUMA-aware allocator to linux
iveresov
parents: 252
diff changeset
  2832
  // sched_getcpu() should be in libc.
bcc631c5bbec 6684395: Port NUMA-aware allocator to linux
iveresov
parents: 252
diff changeset
  2833
  set_sched_getcpu(CAST_TO_FN_PTR(sched_getcpu_func_t,
bcc631c5bbec 6684395: Port NUMA-aware allocator to linux
iveresov
parents: 252
diff changeset
  2834
                                  dlsym(RTLD_DEFAULT, "sched_getcpu")));
bcc631c5bbec 6684395: Port NUMA-aware allocator to linux
iveresov
parents: 252
diff changeset
  2835
10239
c7af330d33d9 7060836: RHEL 5.5 and 5.6 should support UseNUMA
iveresov
parents: 10238
diff changeset
  2836
  // If it's not, try a direct syscall.
26684
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
  2837
  if (sched_getcpu() == -1) {
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
  2838
    set_sched_getcpu(CAST_TO_FN_PTR(sched_getcpu_func_t,
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
  2839
                                    (void*)&sched_getcpu_syscall));
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
  2840
  }
10239
c7af330d33d9 7060836: RHEL 5.5 and 5.6 should support UseNUMA
iveresov
parents: 10238
diff changeset
  2841
388
bcc631c5bbec 6684395: Port NUMA-aware allocator to linux
iveresov
parents: 252
diff changeset
  2842
  if (sched_getcpu() != -1) { // Does it work?
975
ad7da100aa6a 6720130: NUMA allocator: The linux version should search for libnuma.so.1
iveresov
parents: 745
diff changeset
  2843
    void *handle = dlopen("libnuma.so.1", RTLD_LAZY);
388
bcc631c5bbec 6684395: Port NUMA-aware allocator to linux
iveresov
parents: 252
diff changeset
  2844
    if (handle != NULL) {
bcc631c5bbec 6684395: Port NUMA-aware allocator to linux
iveresov
parents: 252
diff changeset
  2845
      set_numa_node_to_cpus(CAST_TO_FN_PTR(numa_node_to_cpus_func_t,
2753
1e9bbaae891b 6840196: NUMA allocator: crash in fastdebug during startup on Linux
iveresov
parents: 2751
diff changeset
  2846
                                           libnuma_dlsym(handle, "numa_node_to_cpus")));
388
bcc631c5bbec 6684395: Port NUMA-aware allocator to linux
iveresov
parents: 252
diff changeset
  2847
      set_numa_max_node(CAST_TO_FN_PTR(numa_max_node_func_t,
2753
1e9bbaae891b 6840196: NUMA allocator: crash in fastdebug during startup on Linux
iveresov
parents: 2751
diff changeset
  2848
                                       libnuma_dlsym(handle, "numa_max_node")));
388
bcc631c5bbec 6684395: Port NUMA-aware allocator to linux
iveresov
parents: 252
diff changeset
  2849
      set_numa_available(CAST_TO_FN_PTR(numa_available_func_t,
2753
1e9bbaae891b 6840196: NUMA allocator: crash in fastdebug during startup on Linux
iveresov
parents: 2751
diff changeset
  2850
                                        libnuma_dlsym(handle, "numa_available")));
388
bcc631c5bbec 6684395: Port NUMA-aware allocator to linux
iveresov
parents: 252
diff changeset
  2851
      set_numa_tonode_memory(CAST_TO_FN_PTR(numa_tonode_memory_func_t,
2753
1e9bbaae891b 6840196: NUMA allocator: crash in fastdebug during startup on Linux
iveresov
parents: 2751
diff changeset
  2852
                                            libnuma_dlsym(handle, "numa_tonode_memory")));
1615
b46d9f19bde2 6779436: NUMA allocator: libnuma expects certain size of the buffer in numa_node_to_cpus()
iveresov
parents: 1388
diff changeset
  2853
      set_numa_interleave_memory(CAST_TO_FN_PTR(numa_interleave_memory_func_t,
26683
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  2854
                                                libnuma_dlsym(handle, "numa_interleave_memory")));
19726
c086d352d3f7 8016155: SIGBUS when running Kitchensink with ParallelScavenge and ParallelOld
mgerdin
parents: 18683
diff changeset
  2855
      set_numa_set_bind_policy(CAST_TO_FN_PTR(numa_set_bind_policy_func_t,
26683
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  2856
                                              libnuma_dlsym(handle, "numa_set_bind_policy")));
1615
b46d9f19bde2 6779436: NUMA allocator: libnuma expects certain size of the buffer in numa_node_to_cpus()
iveresov
parents: 1388
diff changeset
  2857
b46d9f19bde2 6779436: NUMA allocator: libnuma expects certain size of the buffer in numa_node_to_cpus()
iveresov
parents: 1388
diff changeset
  2858
388
bcc631c5bbec 6684395: Port NUMA-aware allocator to linux
iveresov
parents: 252
diff changeset
  2859
      if (numa_available() != -1) {
2753
1e9bbaae891b 6840196: NUMA allocator: crash in fastdebug during startup on Linux
iveresov
parents: 2751
diff changeset
  2860
        set_numa_all_nodes((unsigned long*)libnuma_dlsym(handle, "numa_all_nodes"));
388
bcc631c5bbec 6684395: Port NUMA-aware allocator to linux
iveresov
parents: 252
diff changeset
  2861
        // Create a cpu -> node mapping
13195
be27e1b6a4b9 6995781: Native Memory Tracking (Phase 1)
zgu
parents: 12735
diff changeset
  2862
        _cpu_to_node = new (ResourceObj::C_HEAP, mtInternal) GrowableArray<int>(0, true);
388
bcc631c5bbec 6684395: Port NUMA-aware allocator to linux
iveresov
parents: 252
diff changeset
  2863
        rebuild_cpu_to_node_map();
1615
b46d9f19bde2 6779436: NUMA allocator: libnuma expects certain size of the buffer in numa_node_to_cpus()
iveresov
parents: 1388
diff changeset
  2864
        return true;
388
bcc631c5bbec 6684395: Port NUMA-aware allocator to linux
iveresov
parents: 252
diff changeset
  2865
      }
bcc631c5bbec 6684395: Port NUMA-aware allocator to linux
iveresov
parents: 252
diff changeset
  2866
    }
bcc631c5bbec 6684395: Port NUMA-aware allocator to linux
iveresov
parents: 252
diff changeset
  2867
  }
1615
b46d9f19bde2 6779436: NUMA allocator: libnuma expects certain size of the buffer in numa_node_to_cpus()
iveresov
parents: 1388
diff changeset
  2868
  return false;
388
bcc631c5bbec 6684395: Port NUMA-aware allocator to linux
iveresov
parents: 252
diff changeset
  2869
}
bcc631c5bbec 6684395: Port NUMA-aware allocator to linux
iveresov
parents: 252
diff changeset
  2870
bcc631c5bbec 6684395: Port NUMA-aware allocator to linux
iveresov
parents: 252
diff changeset
  2871
// rebuild_cpu_to_node_map() constructs a table mapping cpud id to node id.
bcc631c5bbec 6684395: Port NUMA-aware allocator to linux
iveresov
parents: 252
diff changeset
  2872
// The table is later used in get_node_by_cpu().
bcc631c5bbec 6684395: Port NUMA-aware allocator to linux
iveresov
parents: 252
diff changeset
  2873
void os::Linux::rebuild_cpu_to_node_map() {
1615
b46d9f19bde2 6779436: NUMA allocator: libnuma expects certain size of the buffer in numa_node_to_cpus()
iveresov
parents: 1388
diff changeset
  2874
  const size_t NCPUS = 32768; // Since the buffer size computation is very obscure
b46d9f19bde2 6779436: NUMA allocator: libnuma expects certain size of the buffer in numa_node_to_cpus()
iveresov
parents: 1388
diff changeset
  2875
                              // in libnuma (possible values are starting from 16,
b46d9f19bde2 6779436: NUMA allocator: libnuma expects certain size of the buffer in numa_node_to_cpus()
iveresov
parents: 1388
diff changeset
  2876
                              // and continuing up with every other power of 2, but less
b46d9f19bde2 6779436: NUMA allocator: libnuma expects certain size of the buffer in numa_node_to_cpus()
iveresov
parents: 1388
diff changeset
  2877
                              // than the maximum number of CPUs supported by kernel), and
b46d9f19bde2 6779436: NUMA allocator: libnuma expects certain size of the buffer in numa_node_to_cpus()
iveresov
parents: 1388
diff changeset
  2878
                              // is a subject to change (in libnuma version 2 the requirements
b46d9f19bde2 6779436: NUMA allocator: libnuma expects certain size of the buffer in numa_node_to_cpus()
iveresov
parents: 1388
diff changeset
  2879
                              // are more reasonable) we'll just hardcode the number they use
b46d9f19bde2 6779436: NUMA allocator: libnuma expects certain size of the buffer in numa_node_to_cpus()
iveresov
parents: 1388
diff changeset
  2880
                              // in the library.
b46d9f19bde2 6779436: NUMA allocator: libnuma expects certain size of the buffer in numa_node_to_cpus()
iveresov
parents: 1388
diff changeset
  2881
  const size_t BitsPerCLong = sizeof(long) * CHAR_BIT;
b46d9f19bde2 6779436: NUMA allocator: libnuma expects certain size of the buffer in numa_node_to_cpus()
iveresov
parents: 1388
diff changeset
  2882
b46d9f19bde2 6779436: NUMA allocator: libnuma expects certain size of the buffer in numa_node_to_cpus()
iveresov
parents: 1388
diff changeset
  2883
  size_t cpu_num = os::active_processor_count();
b46d9f19bde2 6779436: NUMA allocator: libnuma expects certain size of the buffer in numa_node_to_cpus()
iveresov
parents: 1388
diff changeset
  2884
  size_t cpu_map_size = NCPUS / BitsPerCLong;
b46d9f19bde2 6779436: NUMA allocator: libnuma expects certain size of the buffer in numa_node_to_cpus()
iveresov
parents: 1388
diff changeset
  2885
  size_t cpu_map_valid_size =
b46d9f19bde2 6779436: NUMA allocator: libnuma expects certain size of the buffer in numa_node_to_cpus()
iveresov
parents: 1388
diff changeset
  2886
    MIN2((cpu_num + BitsPerCLong - 1) / BitsPerCLong, cpu_map_size);
b46d9f19bde2 6779436: NUMA allocator: libnuma expects certain size of the buffer in numa_node_to_cpus()
iveresov
parents: 1388
diff changeset
  2887
388
bcc631c5bbec 6684395: Port NUMA-aware allocator to linux
iveresov
parents: 252
diff changeset
  2888
  cpu_to_node()->clear();
bcc631c5bbec 6684395: Port NUMA-aware allocator to linux
iveresov
parents: 252
diff changeset
  2889
  cpu_to_node()->at_grow(cpu_num - 1);
1615
b46d9f19bde2 6779436: NUMA allocator: libnuma expects certain size of the buffer in numa_node_to_cpus()
iveresov
parents: 1388
diff changeset
  2890
  size_t node_num = numa_get_groups_num();
b46d9f19bde2 6779436: NUMA allocator: libnuma expects certain size of the buffer in numa_node_to_cpus()
iveresov
parents: 1388
diff changeset
  2891
13195
be27e1b6a4b9 6995781: Native Memory Tracking (Phase 1)
zgu
parents: 12735
diff changeset
  2892
  unsigned long *cpu_map = NEW_C_HEAP_ARRAY(unsigned long, cpu_map_size, mtInternal);
1615
b46d9f19bde2 6779436: NUMA allocator: libnuma expects certain size of the buffer in numa_node_to_cpus()
iveresov
parents: 1388
diff changeset
  2893
  for (size_t i = 0; i < node_num; i++) {
388
bcc631c5bbec 6684395: Port NUMA-aware allocator to linux
iveresov
parents: 252
diff changeset
  2894
    if (numa_node_to_cpus(i, cpu_map, cpu_map_size * sizeof(unsigned long)) != -1) {
1615
b46d9f19bde2 6779436: NUMA allocator: libnuma expects certain size of the buffer in numa_node_to_cpus()
iveresov
parents: 1388
diff changeset
  2895
      for (size_t j = 0; j < cpu_map_valid_size; j++) {
388
bcc631c5bbec 6684395: Port NUMA-aware allocator to linux
iveresov
parents: 252
diff changeset
  2896
        if (cpu_map[j] != 0) {
1615
b46d9f19bde2 6779436: NUMA allocator: libnuma expects certain size of the buffer in numa_node_to_cpus()
iveresov
parents: 1388
diff changeset
  2897
          for (size_t k = 0; k < BitsPerCLong; k++) {
388
bcc631c5bbec 6684395: Port NUMA-aware allocator to linux
iveresov
parents: 252
diff changeset
  2898
            if (cpu_map[j] & (1UL << k)) {
1615
b46d9f19bde2 6779436: NUMA allocator: libnuma expects certain size of the buffer in numa_node_to_cpus()
iveresov
parents: 1388
diff changeset
  2899
              cpu_to_node()->at_put(j * BitsPerCLong + k, i);
388
bcc631c5bbec 6684395: Port NUMA-aware allocator to linux
iveresov
parents: 252
diff changeset
  2900
            }
bcc631c5bbec 6684395: Port NUMA-aware allocator to linux
iveresov
parents: 252
diff changeset
  2901
          }
bcc631c5bbec 6684395: Port NUMA-aware allocator to linux
iveresov
parents: 252
diff changeset
  2902
        }
bcc631c5bbec 6684395: Port NUMA-aware allocator to linux
iveresov
parents: 252
diff changeset
  2903
      }
bcc631c5bbec 6684395: Port NUMA-aware allocator to linux
iveresov
parents: 252
diff changeset
  2904
    }
bcc631c5bbec 6684395: Port NUMA-aware allocator to linux
iveresov
parents: 252
diff changeset
  2905
  }
27880
afb974a04396 8060074: os::free() takes MemoryTrackingLevel but doesn't need it
coleenp
parents: 27474
diff changeset
  2906
  FREE_C_HEAP_ARRAY(unsigned long, cpu_map);
388
bcc631c5bbec 6684395: Port NUMA-aware allocator to linux
iveresov
parents: 252
diff changeset
  2907
}
bcc631c5bbec 6684395: Port NUMA-aware allocator to linux
iveresov
parents: 252
diff changeset
  2908
bcc631c5bbec 6684395: Port NUMA-aware allocator to linux
iveresov
parents: 252
diff changeset
  2909
int os::Linux::get_node_by_cpu(int cpu_id) {
bcc631c5bbec 6684395: Port NUMA-aware allocator to linux
iveresov
parents: 252
diff changeset
  2910
  if (cpu_to_node() != NULL && cpu_id >= 0 && cpu_id < cpu_to_node()->length()) {
bcc631c5bbec 6684395: Port NUMA-aware allocator to linux
iveresov
parents: 252
diff changeset
  2911
    return cpu_to_node()->at(cpu_id);
bcc631c5bbec 6684395: Port NUMA-aware allocator to linux
iveresov
parents: 252
diff changeset
  2912
  }
bcc631c5bbec 6684395: Port NUMA-aware allocator to linux
iveresov
parents: 252
diff changeset
  2913
  return -1;
bcc631c5bbec 6684395: Port NUMA-aware allocator to linux
iveresov
parents: 252
diff changeset
  2914
}
bcc631c5bbec 6684395: Port NUMA-aware allocator to linux
iveresov
parents: 252
diff changeset
  2915
bcc631c5bbec 6684395: Port NUMA-aware allocator to linux
iveresov
parents: 252
diff changeset
  2916
GrowableArray<int>* os::Linux::_cpu_to_node;
bcc631c5bbec 6684395: Port NUMA-aware allocator to linux
iveresov
parents: 252
diff changeset
  2917
os::Linux::sched_getcpu_func_t os::Linux::_sched_getcpu;
bcc631c5bbec 6684395: Port NUMA-aware allocator to linux
iveresov
parents: 252
diff changeset
  2918
os::Linux::numa_node_to_cpus_func_t os::Linux::_numa_node_to_cpus;
bcc631c5bbec 6684395: Port NUMA-aware allocator to linux
iveresov
parents: 252
diff changeset
  2919
os::Linux::numa_max_node_func_t os::Linux::_numa_max_node;
bcc631c5bbec 6684395: Port NUMA-aware allocator to linux
iveresov
parents: 252
diff changeset
  2920
os::Linux::numa_available_func_t os::Linux::_numa_available;
bcc631c5bbec 6684395: Port NUMA-aware allocator to linux
iveresov
parents: 252
diff changeset
  2921
os::Linux::numa_tonode_memory_func_t os::Linux::_numa_tonode_memory;
1615
b46d9f19bde2 6779436: NUMA allocator: libnuma expects certain size of the buffer in numa_node_to_cpus()
iveresov
parents: 1388
diff changeset
  2922
os::Linux::numa_interleave_memory_func_t os::Linux::_numa_interleave_memory;
19726
c086d352d3f7 8016155: SIGBUS when running Kitchensink with ParallelScavenge and ParallelOld
mgerdin
parents: 18683
diff changeset
  2923
os::Linux::numa_set_bind_policy_func_t os::Linux::_numa_set_bind_policy;
1615
b46d9f19bde2 6779436: NUMA allocator: libnuma expects certain size of the buffer in numa_node_to_cpus()
iveresov
parents: 1388
diff changeset
  2924
unsigned long* os::Linux::_numa_all_nodes;
388
bcc631c5bbec 6684395: Port NUMA-aware allocator to linux
iveresov
parents: 252
diff changeset
  2925
13195
be27e1b6a4b9 6995781: Native Memory Tracking (Phase 1)
zgu
parents: 12735
diff changeset
  2926
bool os::pd_uncommit_memory(char* addr, size_t size) {
6176
4d9030fe341f 6953477: Increase portability and flexibility of building Hotspot
bobv
parents: 5922
diff changeset
  2927
  uintptr_t res = (uintptr_t) ::mmap(addr, size, PROT_NONE,
26683
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  2928
                                     MAP_PRIVATE|MAP_FIXED|MAP_NORESERVE|MAP_ANONYMOUS, -1, 0);
6176
4d9030fe341f 6953477: Increase portability and flexibility of building Hotspot
bobv
parents: 5922
diff changeset
  2929
  return res  != (uintptr_t) MAP_FAILED;
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2930
}
489c9b5090e2 Initial load
duke
parents:
diff changeset
  2931
26684
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
  2932
static address get_stack_commited_bottom(address bottom, size_t size) {
19694
84bcddefd0d7 8009062: poor performance of JNI AttachCurrentThread after fix for 7017193
dsamersoff
parents: 19546
diff changeset
  2933
  address nbot = bottom;
84bcddefd0d7 8009062: poor performance of JNI AttachCurrentThread after fix for 7017193
dsamersoff
parents: 19546
diff changeset
  2934
  address ntop = bottom + size;
84bcddefd0d7 8009062: poor performance of JNI AttachCurrentThread after fix for 7017193
dsamersoff
parents: 19546
diff changeset
  2935
84bcddefd0d7 8009062: poor performance of JNI AttachCurrentThread after fix for 7017193
dsamersoff
parents: 19546
diff changeset
  2936
  size_t page_sz = os::vm_page_size();
84bcddefd0d7 8009062: poor performance of JNI AttachCurrentThread after fix for 7017193
dsamersoff
parents: 19546
diff changeset
  2937
  unsigned pages = size / page_sz;
84bcddefd0d7 8009062: poor performance of JNI AttachCurrentThread after fix for 7017193
dsamersoff
parents: 19546
diff changeset
  2938
84bcddefd0d7 8009062: poor performance of JNI AttachCurrentThread after fix for 7017193
dsamersoff
parents: 19546
diff changeset
  2939
  unsigned char vec[1];
84bcddefd0d7 8009062: poor performance of JNI AttachCurrentThread after fix for 7017193
dsamersoff
parents: 19546
diff changeset
  2940
  unsigned imin = 1, imax = pages + 1, imid;
22745
4acf6ad4c462 8029775: Solaris code cleanup
coleenp
parents: 22734
diff changeset
  2941
  int mincore_return_value = 0;
4acf6ad4c462 8029775: Solaris code cleanup
coleenp
parents: 22734
diff changeset
  2942
22749
8121b1d5f498 8033931: Several nightly tests failing with assert(imin < imax) failed: Unexpected page size
dcubed
parents: 22745
diff changeset
  2943
  assert(imin <= imax, "Unexpected page size");
19694
84bcddefd0d7 8009062: poor performance of JNI AttachCurrentThread after fix for 7017193
dsamersoff
parents: 19546
diff changeset
  2944
84bcddefd0d7 8009062: poor performance of JNI AttachCurrentThread after fix for 7017193
dsamersoff
parents: 19546
diff changeset
  2945
  while (imin < imax) {
84bcddefd0d7 8009062: poor performance of JNI AttachCurrentThread after fix for 7017193
dsamersoff
parents: 19546
diff changeset
  2946
    imid = (imax + imin) / 2;
84bcddefd0d7 8009062: poor performance of JNI AttachCurrentThread after fix for 7017193
dsamersoff
parents: 19546
diff changeset
  2947
    nbot = ntop - (imid * page_sz);
84bcddefd0d7 8009062: poor performance of JNI AttachCurrentThread after fix for 7017193
dsamersoff
parents: 19546
diff changeset
  2948
84bcddefd0d7 8009062: poor performance of JNI AttachCurrentThread after fix for 7017193
dsamersoff
parents: 19546
diff changeset
  2949
    // Use a trick with mincore to check whether the page is mapped or not.
84bcddefd0d7 8009062: poor performance of JNI AttachCurrentThread after fix for 7017193
dsamersoff
parents: 19546
diff changeset
  2950
    // mincore sets vec to 1 if page resides in memory and to 0 if page
84bcddefd0d7 8009062: poor performance of JNI AttachCurrentThread after fix for 7017193
dsamersoff
parents: 19546
diff changeset
  2951
    // is swapped output but if page we are asking for is unmapped
84bcddefd0d7 8009062: poor performance of JNI AttachCurrentThread after fix for 7017193
dsamersoff
parents: 19546
diff changeset
  2952
    // it returns -1,ENOMEM
84bcddefd0d7 8009062: poor performance of JNI AttachCurrentThread after fix for 7017193
dsamersoff
parents: 19546
diff changeset
  2953
    mincore_return_value = mincore(nbot, page_sz, vec);
84bcddefd0d7 8009062: poor performance of JNI AttachCurrentThread after fix for 7017193
dsamersoff
parents: 19546
diff changeset
  2954
84bcddefd0d7 8009062: poor performance of JNI AttachCurrentThread after fix for 7017193
dsamersoff
parents: 19546
diff changeset
  2955
    if (mincore_return_value == -1) {
84bcddefd0d7 8009062: poor performance of JNI AttachCurrentThread after fix for 7017193
dsamersoff
parents: 19546
diff changeset
  2956
      // Page is not mapped go up
84bcddefd0d7 8009062: poor performance of JNI AttachCurrentThread after fix for 7017193
dsamersoff
parents: 19546
diff changeset
  2957
      // to find first mapped page
84bcddefd0d7 8009062: poor performance of JNI AttachCurrentThread after fix for 7017193
dsamersoff
parents: 19546
diff changeset
  2958
      if (errno != EAGAIN) {
84bcddefd0d7 8009062: poor performance of JNI AttachCurrentThread after fix for 7017193
dsamersoff
parents: 19546
diff changeset
  2959
        assert(errno == ENOMEM, "Unexpected mincore errno");
84bcddefd0d7 8009062: poor performance of JNI AttachCurrentThread after fix for 7017193
dsamersoff
parents: 19546
diff changeset
  2960
        imax = imid;
84bcddefd0d7 8009062: poor performance of JNI AttachCurrentThread after fix for 7017193
dsamersoff
parents: 19546
diff changeset
  2961
      }
84bcddefd0d7 8009062: poor performance of JNI AttachCurrentThread after fix for 7017193
dsamersoff
parents: 19546
diff changeset
  2962
    } else {
84bcddefd0d7 8009062: poor performance of JNI AttachCurrentThread after fix for 7017193
dsamersoff
parents: 19546
diff changeset
  2963
      // Page is mapped go down
84bcddefd0d7 8009062: poor performance of JNI AttachCurrentThread after fix for 7017193
dsamersoff
parents: 19546
diff changeset
  2964
      // to find first not mapped page
84bcddefd0d7 8009062: poor performance of JNI AttachCurrentThread after fix for 7017193
dsamersoff
parents: 19546
diff changeset
  2965
      imin = imid + 1;
84bcddefd0d7 8009062: poor performance of JNI AttachCurrentThread after fix for 7017193
dsamersoff
parents: 19546
diff changeset
  2966
    }
84bcddefd0d7 8009062: poor performance of JNI AttachCurrentThread after fix for 7017193
dsamersoff
parents: 19546
diff changeset
  2967
  }
84bcddefd0d7 8009062: poor performance of JNI AttachCurrentThread after fix for 7017193
dsamersoff
parents: 19546
diff changeset
  2968
84bcddefd0d7 8009062: poor performance of JNI AttachCurrentThread after fix for 7017193
dsamersoff
parents: 19546
diff changeset
  2969
  nbot = nbot + page_sz;
84bcddefd0d7 8009062: poor performance of JNI AttachCurrentThread after fix for 7017193
dsamersoff
parents: 19546
diff changeset
  2970
84bcddefd0d7 8009062: poor performance of JNI AttachCurrentThread after fix for 7017193
dsamersoff
parents: 19546
diff changeset
  2971
  // Adjust stack bottom one page up if last checked page is not mapped
84bcddefd0d7 8009062: poor performance of JNI AttachCurrentThread after fix for 7017193
dsamersoff
parents: 19546
diff changeset
  2972
  if (mincore_return_value == -1) {
84bcddefd0d7 8009062: poor performance of JNI AttachCurrentThread after fix for 7017193
dsamersoff
parents: 19546
diff changeset
  2973
    nbot = nbot + page_sz;
84bcddefd0d7 8009062: poor performance of JNI AttachCurrentThread after fix for 7017193
dsamersoff
parents: 19546
diff changeset
  2974
  }
84bcddefd0d7 8009062: poor performance of JNI AttachCurrentThread after fix for 7017193
dsamersoff
parents: 19546
diff changeset
  2975
84bcddefd0d7 8009062: poor performance of JNI AttachCurrentThread after fix for 7017193
dsamersoff
parents: 19546
diff changeset
  2976
  return nbot;
84bcddefd0d7 8009062: poor performance of JNI AttachCurrentThread after fix for 7017193
dsamersoff
parents: 19546
diff changeset
  2977
}
84bcddefd0d7 8009062: poor performance of JNI AttachCurrentThread after fix for 7017193
dsamersoff
parents: 19546
diff changeset
  2978
84bcddefd0d7 8009062: poor performance of JNI AttachCurrentThread after fix for 7017193
dsamersoff
parents: 19546
diff changeset
  2979
5085
4f0c435f8c3c 6929067: Stack guard pages should be removed when thread is detached
coleenp
parents: 4493
diff changeset
  2980
// Linux uses a growable mapping for the stack, and if the mapping for
4f0c435f8c3c 6929067: Stack guard pages should be removed when thread is detached
coleenp
parents: 4493
diff changeset
  2981
// the stack guard pages is not removed when we detach a thread the
4f0c435f8c3c 6929067: Stack guard pages should be removed when thread is detached
coleenp
parents: 4493
diff changeset
  2982
// stack cannot grow beyond the pages where the stack guard was
4f0c435f8c3c 6929067: Stack guard pages should be removed when thread is detached
coleenp
parents: 4493
diff changeset
  2983
// mapped.  If at some point later in the process the stack expands to
4f0c435f8c3c 6929067: Stack guard pages should be removed when thread is detached
coleenp
parents: 4493
diff changeset
  2984
// that point, the Linux kernel cannot expand the stack any further
4f0c435f8c3c 6929067: Stack guard pages should be removed when thread is detached
coleenp
parents: 4493
diff changeset
  2985
// because the guard pages are in the way, and a segfault occurs.
4f0c435f8c3c 6929067: Stack guard pages should be removed when thread is detached
coleenp
parents: 4493
diff changeset
  2986
//
4f0c435f8c3c 6929067: Stack guard pages should be removed when thread is detached
coleenp
parents: 4493
diff changeset
  2987
// However, it's essential not to split the stack region by unmapping
4f0c435f8c3c 6929067: Stack guard pages should be removed when thread is detached
coleenp
parents: 4493
diff changeset
  2988
// a region (leaving a hole) that's already part of the stack mapping,
4f0c435f8c3c 6929067: Stack guard pages should be removed when thread is detached
coleenp
parents: 4493
diff changeset
  2989
// so if the stack mapping has already grown beyond the guard pages at
4f0c435f8c3c 6929067: Stack guard pages should be removed when thread is detached
coleenp
parents: 4493
diff changeset
  2990
// the time we create them, we have to truncate the stack mapping.
4f0c435f8c3c 6929067: Stack guard pages should be removed when thread is detached
coleenp
parents: 4493
diff changeset
  2991
// So, we need to know the extent of the stack mapping when
4f0c435f8c3c 6929067: Stack guard pages should be removed when thread is detached
coleenp
parents: 4493
diff changeset
  2992
// create_stack_guard_pages() is called.
4f0c435f8c3c 6929067: Stack guard pages should be removed when thread is detached
coleenp
parents: 4493
diff changeset
  2993
4f0c435f8c3c 6929067: Stack guard pages should be removed when thread is detached
coleenp
parents: 4493
diff changeset
  2994
// We only need this for stacks that are growable: at the time of
4f0c435f8c3c 6929067: Stack guard pages should be removed when thread is detached
coleenp
parents: 4493
diff changeset
  2995
// writing thread stacks don't use growable mappings (i.e. those
4f0c435f8c3c 6929067: Stack guard pages should be removed when thread is detached
coleenp
parents: 4493
diff changeset
  2996
// creeated with MAP_GROWSDOWN), and aren't marked "[stack]", so this
4f0c435f8c3c 6929067: Stack guard pages should be removed when thread is detached
coleenp
parents: 4493
diff changeset
  2997
// only applies to the main thread.
9125
3b9a527cd492 7017193: Small memory leak in get_stack_bounds os::create_stack_guard_pages
dsamersoff
parents: 8476
diff changeset
  2998
5085
4f0c435f8c3c 6929067: Stack guard pages should be removed when thread is detached
coleenp
parents: 4493
diff changeset
  2999
// If the (growable) stack mapping already extends beyond the point
4f0c435f8c3c 6929067: Stack guard pages should be removed when thread is detached
coleenp
parents: 4493
diff changeset
  3000
// where we're going to put our guard pages, truncate the mapping at
4f0c435f8c3c 6929067: Stack guard pages should be removed when thread is detached
coleenp
parents: 4493
diff changeset
  3001
// that point by munmap()ping it.  This ensures that when we later
4f0c435f8c3c 6929067: Stack guard pages should be removed when thread is detached
coleenp
parents: 4493
diff changeset
  3002
// munmap() the guard pages we don't leave a hole in the stack
19694
84bcddefd0d7 8009062: poor performance of JNI AttachCurrentThread after fix for 7017193
dsamersoff
parents: 19546
diff changeset
  3003
// mapping. This only affects the main/initial thread
84bcddefd0d7 8009062: poor performance of JNI AttachCurrentThread after fix for 7017193
dsamersoff
parents: 19546
diff changeset
  3004
13195
be27e1b6a4b9 6995781: Native Memory Tracking (Phase 1)
zgu
parents: 12735
diff changeset
  3005
bool os::pd_create_stack_guard_pages(char* addr, size_t size) {
19694
84bcddefd0d7 8009062: poor performance of JNI AttachCurrentThread after fix for 7017193
dsamersoff
parents: 19546
diff changeset
  3006
  if (os::Linux::is_initial_thread()) {
84bcddefd0d7 8009062: poor performance of JNI AttachCurrentThread after fix for 7017193
dsamersoff
parents: 19546
diff changeset
  3007
    // As we manually grow stack up to bottom inside create_attached_thread(),
84bcddefd0d7 8009062: poor performance of JNI AttachCurrentThread after fix for 7017193
dsamersoff
parents: 19546
diff changeset
  3008
    // it's likely that os::Linux::initial_thread_stack_bottom is mapped and
84bcddefd0d7 8009062: poor performance of JNI AttachCurrentThread after fix for 7017193
dsamersoff
parents: 19546
diff changeset
  3009
    // we don't need to do anything special.
84bcddefd0d7 8009062: poor performance of JNI AttachCurrentThread after fix for 7017193
dsamersoff
parents: 19546
diff changeset
  3010
    // Check it first, before calling heavy function.
84bcddefd0d7 8009062: poor performance of JNI AttachCurrentThread after fix for 7017193
dsamersoff
parents: 19546
diff changeset
  3011
    uintptr_t stack_extent = (uintptr_t) os::Linux::initial_thread_stack_bottom();
84bcddefd0d7 8009062: poor performance of JNI AttachCurrentThread after fix for 7017193
dsamersoff
parents: 19546
diff changeset
  3012
    unsigned char vec[1];
84bcddefd0d7 8009062: poor performance of JNI AttachCurrentThread after fix for 7017193
dsamersoff
parents: 19546
diff changeset
  3013
84bcddefd0d7 8009062: poor performance of JNI AttachCurrentThread after fix for 7017193
dsamersoff
parents: 19546
diff changeset
  3014
    if (mincore((address)stack_extent, os::vm_page_size(), vec) == -1) {
84bcddefd0d7 8009062: poor performance of JNI AttachCurrentThread after fix for 7017193
dsamersoff
parents: 19546
diff changeset
  3015
      // Fallback to slow path on all errors, including EAGAIN
84bcddefd0d7 8009062: poor performance of JNI AttachCurrentThread after fix for 7017193
dsamersoff
parents: 19546
diff changeset
  3016
      stack_extent = (uintptr_t) get_stack_commited_bottom(
26683
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  3017
                                                           os::Linux::initial_thread_stack_bottom(),
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  3018
                                                           (size_t)addr - stack_extent);
19694
84bcddefd0d7 8009062: poor performance of JNI AttachCurrentThread after fix for 7017193
dsamersoff
parents: 19546
diff changeset
  3019
    }
84bcddefd0d7 8009062: poor performance of JNI AttachCurrentThread after fix for 7017193
dsamersoff
parents: 19546
diff changeset
  3020
84bcddefd0d7 8009062: poor performance of JNI AttachCurrentThread after fix for 7017193
dsamersoff
parents: 19546
diff changeset
  3021
    if (stack_extent < (uintptr_t)addr) {
84bcddefd0d7 8009062: poor performance of JNI AttachCurrentThread after fix for 7017193
dsamersoff
parents: 19546
diff changeset
  3022
      ::munmap((void*)stack_extent, (uintptr_t)(addr - stack_extent));
84bcddefd0d7 8009062: poor performance of JNI AttachCurrentThread after fix for 7017193
dsamersoff
parents: 19546
diff changeset
  3023
    }
5085
4f0c435f8c3c 6929067: Stack guard pages should be removed when thread is detached
coleenp
parents: 4493
diff changeset
  3024
  }
4f0c435f8c3c 6929067: Stack guard pages should be removed when thread is detached
coleenp
parents: 4493
diff changeset
  3025
18069
e6d4971c8650 8013057: assert(_needs_gc || SafepointSynchronize::is_at_safepoint()) failed: only read at safepoint
dcubed
parents: 18025
diff changeset
  3026
  return os::commit_memory(addr, size, !ExecMem);
5085
4f0c435f8c3c 6929067: Stack guard pages should be removed when thread is detached
coleenp
parents: 4493
diff changeset
  3027
}
4f0c435f8c3c 6929067: Stack guard pages should be removed when thread is detached
coleenp
parents: 4493
diff changeset
  3028
4f0c435f8c3c 6929067: Stack guard pages should be removed when thread is detached
coleenp
parents: 4493
diff changeset
  3029
// If this is a growable mapping, remove the guard pages entirely by
6420
a4205fed5b18 6978641: Fix for 6929067 introduces additional overhead in thread creation/termination paths
dholmes
parents: 6176
diff changeset
  3030
// munmap()ping them.  If not, just call uncommit_memory(). This only
a4205fed5b18 6978641: Fix for 6929067 introduces additional overhead in thread creation/termination paths
dholmes
parents: 6176
diff changeset
  3031
// affects the main/initial thread, but guard against future OS changes
19694
84bcddefd0d7 8009062: poor performance of JNI AttachCurrentThread after fix for 7017193
dsamersoff
parents: 19546
diff changeset
  3032
// It's safe to always unmap guard pages for initial thread because we
84bcddefd0d7 8009062: poor performance of JNI AttachCurrentThread after fix for 7017193
dsamersoff
parents: 19546
diff changeset
  3033
// always place it right after end of the mapped region
84bcddefd0d7 8009062: poor performance of JNI AttachCurrentThread after fix for 7017193
dsamersoff
parents: 19546
diff changeset
  3034
5085
4f0c435f8c3c 6929067: Stack guard pages should be removed when thread is detached
coleenp
parents: 4493
diff changeset
  3035
bool os::remove_stack_guard_pages(char* addr, size_t size) {
4f0c435f8c3c 6929067: Stack guard pages should be removed when thread is detached
coleenp
parents: 4493
diff changeset
  3036
  uintptr_t stack_extent, stack_base;
19694
84bcddefd0d7 8009062: poor performance of JNI AttachCurrentThread after fix for 7017193
dsamersoff
parents: 19546
diff changeset
  3037
84bcddefd0d7 8009062: poor performance of JNI AttachCurrentThread after fix for 7017193
dsamersoff
parents: 19546
diff changeset
  3038
  if (os::Linux::is_initial_thread()) {
5085
4f0c435f8c3c 6929067: Stack guard pages should be removed when thread is detached
coleenp
parents: 4493
diff changeset
  3039
    return ::munmap(addr, size) == 0;
4f0c435f8c3c 6929067: Stack guard pages should be removed when thread is detached
coleenp
parents: 4493
diff changeset
  3040
  }
4f0c435f8c3c 6929067: Stack guard pages should be removed when thread is detached
coleenp
parents: 4493
diff changeset
  3041
4f0c435f8c3c 6929067: Stack guard pages should be removed when thread is detached
coleenp
parents: 4493
diff changeset
  3042
  return os::uncommit_memory(addr, size);
4f0c435f8c3c 6929067: Stack guard pages should be removed when thread is detached
coleenp
parents: 4493
diff changeset
  3043
}
4f0c435f8c3c 6929067: Stack guard pages should be removed when thread is detached
coleenp
parents: 4493
diff changeset
  3044
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3045
static address _highest_vm_reserved_address = NULL;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3046
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3047
// If 'fixed' is true, anon_mmap() will attempt to reserve anonymous memory
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3048
// at 'requested_addr'. If there are existing memory mappings at the same
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3049
// location, however, they will be overwritten. If 'fixed' is false,
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3050
// 'requested_addr' is only treated as a hint, the return value may or
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3051
// may not start from the requested address. Unlike Linux mmap(), this
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3052
// function returns NULL to indicate failure.
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3053
static char* anon_mmap(char* requested_addr, size_t bytes, bool fixed) {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3054
  char * addr;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3055
  int flags;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3056
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3057
  flags = MAP_PRIVATE | MAP_NORESERVE | MAP_ANONYMOUS;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3058
  if (fixed) {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3059
    assert((uintptr_t)requested_addr % os::Linux::page_size() == 0, "unaligned address");
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3060
    flags |= MAP_FIXED;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3061
  }
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3062
17083
14000894ef39 8012015: Use PROT_NONE when reserving memory
mikael
parents: 16672
diff changeset
  3063
  // Map reserved/uncommitted pages PROT_NONE so we fail early if we
14000894ef39 8012015: Use PROT_NONE when reserving memory
mikael
parents: 16672
diff changeset
  3064
  // touch an uncommitted page. Otherwise, the read/write might
14000894ef39 8012015: Use PROT_NONE when reserving memory
mikael
parents: 16672
diff changeset
  3065
  // succeed if we have enough swap space to back the physical page.
14000894ef39 8012015: Use PROT_NONE when reserving memory
mikael
parents: 16672
diff changeset
  3066
  addr = (char*)::mmap(requested_addr, bytes, PROT_NONE,
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3067
                       flags, -1, 0);
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3068
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3069
  if (addr != MAP_FAILED) {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3070
    // anon_mmap() should only get called during VM initialization,
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3071
    // don't need lock (actually we can skip locking even it can be called
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3072
    // from multiple threads, because _highest_vm_reserved_address is just a
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3073
    // hint about the upper limit of non-stack memory regions.)
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3074
    if ((address)addr + bytes > _highest_vm_reserved_address) {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3075
      _highest_vm_reserved_address = (address)addr + bytes;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3076
    }
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3077
  }
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3078
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3079
  return addr == MAP_FAILED ? NULL : addr;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3080
}
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3081
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3082
// Don't update _highest_vm_reserved_address, because there might be memory
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3083
// regions above addr + size. If so, releasing a memory region only creates
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3084
// a hole in the address space, it doesn't help prevent heap-stack collision.
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3085
//
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3086
static int anon_munmap(char * addr, size_t size) {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3087
  return ::munmap(addr, size) == 0;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3088
}
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3089
13195
be27e1b6a4b9 6995781: Native Memory Tracking (Phase 1)
zgu
parents: 12735
diff changeset
  3090
char* os::pd_reserve_memory(size_t bytes, char* requested_addr,
26683
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  3091
                            size_t alignment_hint) {
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3092
  return anon_mmap(requested_addr, bytes, (requested_addr != NULL));
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3093
}
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3094
13195
be27e1b6a4b9 6995781: Native Memory Tracking (Phase 1)
zgu
parents: 12735
diff changeset
  3095
bool os::pd_release_memory(char* addr, size_t size) {
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3096
  return anon_munmap(addr, size);
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3097
}
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3098
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3099
static address highest_vm_reserved_address() {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3100
  return _highest_vm_reserved_address;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3101
}
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3102
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3103
static bool linux_mprotect(char* addr, size_t size, int prot) {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3104
  // Linux wants the mprotect address argument to be page aligned.
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3105
  char* bottom = (char*)align_size_down((intptr_t)addr, os::Linux::page_size());
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3106
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3107
  // According to SUSv3, mprotect() should only be used with mappings
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3108
  // established by mmap(), and mmap() always maps whole pages. Unaligned
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3109
  // 'addr' likely indicates problem in the VM (e.g. trying to change
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3110
  // protection of malloc'ed or statically allocated memory). Check the
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3111
  // caller if you hit this assert.
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3112
  assert(addr == bottom, "sanity check");
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3113
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3114
  size = align_size_up(pointer_delta(addr, bottom, 1) + size, os::Linux::page_size());
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3115
  return ::mprotect(bottom, size, prot) == 0;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3116
}
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3117
823
9a5271881bc0 6716785: implicit null checks not triggering with CompressedOops
coleenp
parents: 781
diff changeset
  3118
// Set protections specified
9a5271881bc0 6716785: implicit null checks not triggering with CompressedOops
coleenp
parents: 781
diff changeset
  3119
bool os::protect_memory(char* addr, size_t bytes, ProtType prot,
9a5271881bc0 6716785: implicit null checks not triggering with CompressedOops
coleenp
parents: 781
diff changeset
  3120
                        bool is_committed) {
9a5271881bc0 6716785: implicit null checks not triggering with CompressedOops
coleenp
parents: 781
diff changeset
  3121
  unsigned int p = 0;
9a5271881bc0 6716785: implicit null checks not triggering with CompressedOops
coleenp
parents: 781
diff changeset
  3122
  switch (prot) {
9a5271881bc0 6716785: implicit null checks not triggering with CompressedOops
coleenp
parents: 781
diff changeset
  3123
  case MEM_PROT_NONE: p = PROT_NONE; break;
9a5271881bc0 6716785: implicit null checks not triggering with CompressedOops
coleenp
parents: 781
diff changeset
  3124
  case MEM_PROT_READ: p = PROT_READ; break;
9a5271881bc0 6716785: implicit null checks not triggering with CompressedOops
coleenp
parents: 781
diff changeset
  3125
  case MEM_PROT_RW:   p = PROT_READ|PROT_WRITE; break;
9a5271881bc0 6716785: implicit null checks not triggering with CompressedOops
coleenp
parents: 781
diff changeset
  3126
  case MEM_PROT_RWX:  p = PROT_READ|PROT_WRITE|PROT_EXEC; break;
9a5271881bc0 6716785: implicit null checks not triggering with CompressedOops
coleenp
parents: 781
diff changeset
  3127
  default:
9a5271881bc0 6716785: implicit null checks not triggering with CompressedOops
coleenp
parents: 781
diff changeset
  3128
    ShouldNotReachHere();
9a5271881bc0 6716785: implicit null checks not triggering with CompressedOops
coleenp
parents: 781
diff changeset
  3129
  }
9a5271881bc0 6716785: implicit null checks not triggering with CompressedOops
coleenp
parents: 781
diff changeset
  3130
  // is_committed is unused.
9a5271881bc0 6716785: implicit null checks not triggering with CompressedOops
coleenp
parents: 781
diff changeset
  3131
  return linux_mprotect(addr, bytes, p);
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3132
}
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3133
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3134
bool os::guard_memory(char* addr, size_t size) {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3135
  return linux_mprotect(addr, size, PROT_NONE);
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3136
}
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3137
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3138
bool os::unguard_memory(char* addr, size_t size) {
1664
fc9ed50498fb 6727377: VM stack guard pages on Windows should PAGE_READWRITE not PAGE_EXECUTE_READWRITE
coleenp
parents: 1615
diff changeset
  3139
  return linux_mprotect(addr, size, PROT_READ|PROT_WRITE);
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3140
}
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3141
26684
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
  3142
bool os::Linux::transparent_huge_pages_sanity_check(bool warn,
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
  3143
                                                    size_t page_size) {
19546
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3144
  bool result = false;
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3145
  void *p = mmap(NULL, page_size * 2, PROT_READ|PROT_WRITE,
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3146
                 MAP_ANONYMOUS|MAP_PRIVATE,
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3147
                 -1, 0);
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3148
  if (p != MAP_FAILED) {
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3149
    void *aligned_p = align_ptr_up(p, page_size);
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3150
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3151
    result = madvise(aligned_p, page_size, MADV_HUGEPAGE) == 0;
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3152
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3153
    munmap(p, page_size * 2);
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3154
  }
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3155
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3156
  if (warn && !result) {
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3157
    warning("TransparentHugePages is not supported by the operating system.");
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3158
  }
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3159
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3160
  return result;
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3161
}
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3162
9335
7bdd2a3ab3d8 7034464: Support transparent large pages on Linux
iveresov
parents: 8476
diff changeset
  3163
bool os::Linux::hugetlbfs_sanity_check(bool warn, size_t page_size) {
7bdd2a3ab3d8 7034464: Support transparent large pages on Linux
iveresov
parents: 8476
diff changeset
  3164
  bool result = false;
19546
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3165
  void *p = mmap(NULL, page_size, PROT_READ|PROT_WRITE,
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3166
                 MAP_ANONYMOUS|MAP_PRIVATE|MAP_HUGETLB,
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3167
                 -1, 0);
9335
7bdd2a3ab3d8 7034464: Support transparent large pages on Linux
iveresov
parents: 8476
diff changeset
  3168
18069
e6d4971c8650 8013057: assert(_needs_gc || SafepointSynchronize::is_at_safepoint()) failed: only read at safepoint
dcubed
parents: 18025
diff changeset
  3169
  if (p != MAP_FAILED) {
9335
7bdd2a3ab3d8 7034464: Support transparent large pages on Linux
iveresov
parents: 8476
diff changeset
  3170
    // We don't know if this really is a huge page or not.
7bdd2a3ab3d8 7034464: Support transparent large pages on Linux
iveresov
parents: 8476
diff changeset
  3171
    FILE *fp = fopen("/proc/self/maps", "r");
7bdd2a3ab3d8 7034464: Support transparent large pages on Linux
iveresov
parents: 8476
diff changeset
  3172
    if (fp) {
7bdd2a3ab3d8 7034464: Support transparent large pages on Linux
iveresov
parents: 8476
diff changeset
  3173
      while (!feof(fp)) {
7bdd2a3ab3d8 7034464: Support transparent large pages on Linux
iveresov
parents: 8476
diff changeset
  3174
        char chars[257];
7bdd2a3ab3d8 7034464: Support transparent large pages on Linux
iveresov
parents: 8476
diff changeset
  3175
        long x = 0;
7bdd2a3ab3d8 7034464: Support transparent large pages on Linux
iveresov
parents: 8476
diff changeset
  3176
        if (fgets(chars, sizeof(chars), fp)) {
9625
822a93889b58 7043564: compile warning and copyright fixes
iveresov
parents: 9419
diff changeset
  3177
          if (sscanf(chars, "%lx-%*x", &x) == 1
9335
7bdd2a3ab3d8 7034464: Support transparent large pages on Linux
iveresov
parents: 8476
diff changeset
  3178
              && x == (long)p) {
7bdd2a3ab3d8 7034464: Support transparent large pages on Linux
iveresov
parents: 8476
diff changeset
  3179
            if (strstr (chars, "hugepage")) {
7bdd2a3ab3d8 7034464: Support transparent large pages on Linux
iveresov
parents: 8476
diff changeset
  3180
              result = true;
7bdd2a3ab3d8 7034464: Support transparent large pages on Linux
iveresov
parents: 8476
diff changeset
  3181
              break;
7bdd2a3ab3d8 7034464: Support transparent large pages on Linux
iveresov
parents: 8476
diff changeset
  3182
            }
7bdd2a3ab3d8 7034464: Support transparent large pages on Linux
iveresov
parents: 8476
diff changeset
  3183
          }
7bdd2a3ab3d8 7034464: Support transparent large pages on Linux
iveresov
parents: 8476
diff changeset
  3184
        }
7bdd2a3ab3d8 7034464: Support transparent large pages on Linux
iveresov
parents: 8476
diff changeset
  3185
      }
7bdd2a3ab3d8 7034464: Support transparent large pages on Linux
iveresov
parents: 8476
diff changeset
  3186
      fclose(fp);
7bdd2a3ab3d8 7034464: Support transparent large pages on Linux
iveresov
parents: 8476
diff changeset
  3187
    }
19546
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3188
    munmap(p, page_size);
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3189
  }
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3190
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3191
  if (warn && !result) {
9335
7bdd2a3ab3d8 7034464: Support transparent large pages on Linux
iveresov
parents: 8476
diff changeset
  3192
    warning("HugeTLBFS is not supported by the operating system.");
7bdd2a3ab3d8 7034464: Support transparent large pages on Linux
iveresov
parents: 8476
diff changeset
  3193
  }
7bdd2a3ab3d8 7034464: Support transparent large pages on Linux
iveresov
parents: 8476
diff changeset
  3194
7bdd2a3ab3d8 7034464: Support transparent large pages on Linux
iveresov
parents: 8476
diff changeset
  3195
  return result;
7bdd2a3ab3d8 7034464: Support transparent large pages on Linux
iveresov
parents: 8476
diff changeset
  3196
}
7bdd2a3ab3d8 7034464: Support transparent large pages on Linux
iveresov
parents: 8476
diff changeset
  3197
26684
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
  3198
// Set the coredump_filter bits to include largepages in core dump (bit 6)
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
  3199
//
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
  3200
// From the coredump_filter documentation:
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
  3201
//
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
  3202
// - (bit 0) anonymous private memory
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
  3203
// - (bit 1) anonymous shared memory
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
  3204
// - (bit 2) file-backed private memory
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
  3205
// - (bit 3) file-backed shared memory
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
  3206
// - (bit 4) ELF header pages in file-backed private memory areas (it is
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
  3207
//           effective only if the bit 2 is cleared)
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
  3208
// - (bit 5) hugetlb private memory
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
  3209
// - (bit 6) hugetlb shared memory
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
  3210
//
8119
81eef1b06988 7014918: Improve core/minidump handling in Hotspot
ctornqvi
parents: 8108
diff changeset
  3211
static void set_coredump_filter(void) {
81eef1b06988 7014918: Improve core/minidump handling in Hotspot
ctornqvi
parents: 8108
diff changeset
  3212
  FILE *f;
81eef1b06988 7014918: Improve core/minidump handling in Hotspot
ctornqvi
parents: 8108
diff changeset
  3213
  long cdm;
81eef1b06988 7014918: Improve core/minidump handling in Hotspot
ctornqvi
parents: 8108
diff changeset
  3214
81eef1b06988 7014918: Improve core/minidump handling in Hotspot
ctornqvi
parents: 8108
diff changeset
  3215
  if ((f = fopen("/proc/self/coredump_filter", "r+")) == NULL) {
81eef1b06988 7014918: Improve core/minidump handling in Hotspot
ctornqvi
parents: 8108
diff changeset
  3216
    return;
81eef1b06988 7014918: Improve core/minidump handling in Hotspot
ctornqvi
parents: 8108
diff changeset
  3217
  }
81eef1b06988 7014918: Improve core/minidump handling in Hotspot
ctornqvi
parents: 8108
diff changeset
  3218
81eef1b06988 7014918: Improve core/minidump handling in Hotspot
ctornqvi
parents: 8108
diff changeset
  3219
  if (fscanf(f, "%lx", &cdm) != 1) {
81eef1b06988 7014918: Improve core/minidump handling in Hotspot
ctornqvi
parents: 8108
diff changeset
  3220
    fclose(f);
81eef1b06988 7014918: Improve core/minidump handling in Hotspot
ctornqvi
parents: 8108
diff changeset
  3221
    return;
81eef1b06988 7014918: Improve core/minidump handling in Hotspot
ctornqvi
parents: 8108
diff changeset
  3222
  }
81eef1b06988 7014918: Improve core/minidump handling in Hotspot
ctornqvi
parents: 8108
diff changeset
  3223
81eef1b06988 7014918: Improve core/minidump handling in Hotspot
ctornqvi
parents: 8108
diff changeset
  3224
  rewind(f);
81eef1b06988 7014918: Improve core/minidump handling in Hotspot
ctornqvi
parents: 8108
diff changeset
  3225
81eef1b06988 7014918: Improve core/minidump handling in Hotspot
ctornqvi
parents: 8108
diff changeset
  3226
  if ((cdm & LARGEPAGES_BIT) == 0) {
81eef1b06988 7014918: Improve core/minidump handling in Hotspot
ctornqvi
parents: 8108
diff changeset
  3227
    cdm |= LARGEPAGES_BIT;
81eef1b06988 7014918: Improve core/minidump handling in Hotspot
ctornqvi
parents: 8108
diff changeset
  3228
    fprintf(f, "%#lx", cdm);
81eef1b06988 7014918: Improve core/minidump handling in Hotspot
ctornqvi
parents: 8108
diff changeset
  3229
  }
81eef1b06988 7014918: Improve core/minidump handling in Hotspot
ctornqvi
parents: 8108
diff changeset
  3230
81eef1b06988 7014918: Improve core/minidump handling in Hotspot
ctornqvi
parents: 8108
diff changeset
  3231
  fclose(f);
81eef1b06988 7014918: Improve core/minidump handling in Hotspot
ctornqvi
parents: 8108
diff changeset
  3232
}
81eef1b06988 7014918: Improve core/minidump handling in Hotspot
ctornqvi
parents: 8108
diff changeset
  3233
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3234
// Large page support
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3235
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3236
static size_t _large_page_size = 0;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3237
19546
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3238
size_t os::Linux::find_large_page_size() {
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3239
  size_t large_page_size = 0;
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3240
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3241
  // large_page_size on Linux is used to round up heap size. x86 uses either
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3242
  // 2M or 4M page, depending on whether PAE (Physical Address Extensions)
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3243
  // mode is enabled. AMD64/EM64T uses 2M page in 64bit mode. IA64 can use
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3244
  // page as large as 256M.
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3245
  //
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3246
  // Here we try to figure out page size by parsing /proc/meminfo and looking
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3247
  // for a line with the following format:
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3248
  //    Hugepagesize:     2048 kB
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3249
  //
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3250
  // If we can't determine the value (e.g. /proc is not mounted, or the text
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3251
  // format has been changed), we'll use the largest page size supported by
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3252
  // the processor.
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3253
4013
b154310845de 6890308: integrate zero assembler hotspot changes
never
parents: 2753
diff changeset
  3254
#ifndef ZERO
19546
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3255
  large_page_size = IA32_ONLY(4 * M) AMD64_ONLY(2 * M) IA64_ONLY(256 * M) SPARC_ONLY(4 * M)
29474
81a5c5330d08 8072383: resolve conflicts between open and closed ports
dlong
parents: 29193
diff changeset
  3256
                     ARM32_ONLY(2 * M) PPC_ONLY(4 * M) AARCH64_ONLY(2 * M);
4013
b154310845de 6890308: integrate zero assembler hotspot changes
never
parents: 2753
diff changeset
  3257
#endif // ZERO
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3258
19546
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3259
  FILE *fp = fopen("/proc/meminfo", "r");
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3260
  if (fp) {
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3261
    while (!feof(fp)) {
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3262
      int x = 0;
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3263
      char buf[16];
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3264
      if (fscanf(fp, "Hugepagesize: %d", &x) == 1) {
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3265
        if (x && fgets(buf, sizeof(buf), fp) && strcmp(buf, " kB\n") == 0) {
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3266
          large_page_size = x * K;
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3267
          break;
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3268
        }
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3269
      } else {
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3270
        // skip to next line
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3271
        for (;;) {
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3272
          int ch = fgetc(fp);
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3273
          if (ch == EOF || ch == (int)'\n') break;
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3274
        }
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3275
      }
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3276
    }
19546
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3277
    fclose(fp);
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3278
  }
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3279
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3280
  if (!FLAG_IS_DEFAULT(LargePageSizeInBytes) && LargePageSizeInBytes != large_page_size) {
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3281
    warning("Setting LargePageSizeInBytes has no effect on this OS. Large page size is "
26683
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  3282
            SIZE_FORMAT "%s.", byte_size_in_proper_unit(large_page_size),
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  3283
            proper_unit_for_byte_size(large_page_size));
19546
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3284
  }
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3285
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3286
  return large_page_size;
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3287
}
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3288
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3289
size_t os::Linux::setup_large_page_size() {
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3290
  _large_page_size = Linux::find_large_page_size();
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3291
  const size_t default_page_size = (size_t)Linux::page_size();
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3292
  if (_large_page_size > default_page_size) {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3293
    _page_sizes[0] = _large_page_size;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3294
    _page_sizes[1] = default_page_size;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3295
    _page_sizes[2] = 0;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3296
  }
19546
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3297
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3298
  return _large_page_size;
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3299
}
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3300
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3301
bool os::Linux::setup_large_page_type(size_t page_size) {
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3302
  if (FLAG_IS_DEFAULT(UseHugeTLBFS) &&
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3303
      FLAG_IS_DEFAULT(UseSHM) &&
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3304
      FLAG_IS_DEFAULT(UseTransparentHugePages)) {
20400
1c658ebcb3c1 8024838: Significant slowdown due to transparent huge pages
stefank
parents: 20005
diff changeset
  3305
1c658ebcb3c1 8024838: Significant slowdown due to transparent huge pages
stefank
parents: 20005
diff changeset
  3306
    // The type of large pages has not been specified by the user.
1c658ebcb3c1 8024838: Significant slowdown due to transparent huge pages
stefank
parents: 20005
diff changeset
  3307
1c658ebcb3c1 8024838: Significant slowdown due to transparent huge pages
stefank
parents: 20005
diff changeset
  3308
    // Try UseHugeTLBFS and then UseSHM.
1c658ebcb3c1 8024838: Significant slowdown due to transparent huge pages
stefank
parents: 20005
diff changeset
  3309
    UseHugeTLBFS = UseSHM = true;
1c658ebcb3c1 8024838: Significant slowdown due to transparent huge pages
stefank
parents: 20005
diff changeset
  3310
1c658ebcb3c1 8024838: Significant slowdown due to transparent huge pages
stefank
parents: 20005
diff changeset
  3311
    // Don't try UseTransparentHugePages since there are known
1c658ebcb3c1 8024838: Significant slowdown due to transparent huge pages
stefank
parents: 20005
diff changeset
  3312
    // performance issues with it turned on. This might change in the future.
1c658ebcb3c1 8024838: Significant slowdown due to transparent huge pages
stefank
parents: 20005
diff changeset
  3313
    UseTransparentHugePages = false;
19546
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3314
  }
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3315
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3316
  if (UseTransparentHugePages) {
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3317
    bool warn_on_failure = !FLAG_IS_DEFAULT(UseTransparentHugePages);
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3318
    if (transparent_huge_pages_sanity_check(warn_on_failure, page_size)) {
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3319
      UseHugeTLBFS = false;
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3320
      UseSHM = false;
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3321
      return true;
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3322
    }
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3323
    UseTransparentHugePages = false;
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3324
  }
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3325
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3326
  if (UseHugeTLBFS) {
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3327
    bool warn_on_failure = !FLAG_IS_DEFAULT(UseHugeTLBFS);
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3328
    if (hugetlbfs_sanity_check(warn_on_failure, page_size)) {
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3329
      UseSHM = false;
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3330
      return true;
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3331
    }
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3332
    UseHugeTLBFS = false;
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3333
  }
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3334
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3335
  return UseSHM;
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3336
}
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3337
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3338
void os::large_page_init() {
20400
1c658ebcb3c1 8024838: Significant slowdown due to transparent huge pages
stefank
parents: 20005
diff changeset
  3339
  if (!UseLargePages &&
1c658ebcb3c1 8024838: Significant slowdown due to transparent huge pages
stefank
parents: 20005
diff changeset
  3340
      !UseTransparentHugePages &&
1c658ebcb3c1 8024838: Significant slowdown due to transparent huge pages
stefank
parents: 20005
diff changeset
  3341
      !UseHugeTLBFS &&
1c658ebcb3c1 8024838: Significant slowdown due to transparent huge pages
stefank
parents: 20005
diff changeset
  3342
      !UseSHM) {
1c658ebcb3c1 8024838: Significant slowdown due to transparent huge pages
stefank
parents: 20005
diff changeset
  3343
    // Not using large pages.
1c658ebcb3c1 8024838: Significant slowdown due to transparent huge pages
stefank
parents: 20005
diff changeset
  3344
    return;
1c658ebcb3c1 8024838: Significant slowdown due to transparent huge pages
stefank
parents: 20005
diff changeset
  3345
  }
1c658ebcb3c1 8024838: Significant slowdown due to transparent huge pages
stefank
parents: 20005
diff changeset
  3346
1c658ebcb3c1 8024838: Significant slowdown due to transparent huge pages
stefank
parents: 20005
diff changeset
  3347
  if (!FLAG_IS_DEFAULT(UseLargePages) && !UseLargePages) {
1c658ebcb3c1 8024838: Significant slowdown due to transparent huge pages
stefank
parents: 20005
diff changeset
  3348
    // The user explicitly turned off large pages.
1c658ebcb3c1 8024838: Significant slowdown due to transparent huge pages
stefank
parents: 20005
diff changeset
  3349
    // Ignore the rest of the large pages flags.
1c658ebcb3c1 8024838: Significant slowdown due to transparent huge pages
stefank
parents: 20005
diff changeset
  3350
    UseTransparentHugePages = false;
19546
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3351
    UseHugeTLBFS = false;
9335
7bdd2a3ab3d8 7034464: Support transparent large pages on Linux
iveresov
parents: 8476
diff changeset
  3352
    UseSHM = false;
19546
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3353
    return;
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3354
  }
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3355
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3356
  size_t large_page_size = Linux::setup_large_page_size();
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3357
  UseLargePages          = Linux::setup_large_page_type(large_page_size);
9335
7bdd2a3ab3d8 7034464: Support transparent large pages on Linux
iveresov
parents: 8476
diff changeset
  3358
8119
81eef1b06988 7014918: Improve core/minidump handling in Hotspot
ctornqvi
parents: 8108
diff changeset
  3359
  set_coredump_filter();
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3360
}
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3361
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3362
#ifndef SHM_HUGETLB
26684
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
  3363
  #define SHM_HUGETLB 04000
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3364
#endif
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3365
26684
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
  3366
char* os::Linux::reserve_memory_special_shm(size_t bytes, size_t alignment,
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
  3367
                                            char* req_addr, bool exec) {
2268
bea8be80ec88 6541756: Reduce executable C-heap
coleenp
parents: 2259
diff changeset
  3368
  // "exec" is passed in but not used.  Creating the shared image for
bea8be80ec88 6541756: Reduce executable C-heap
coleenp
parents: 2259
diff changeset
  3369
  // the code cache doesn't have an SHM_X executable permission to check.
9335
7bdd2a3ab3d8 7034464: Support transparent large pages on Linux
iveresov
parents: 8476
diff changeset
  3370
  assert(UseLargePages && UseSHM, "only for SHM large pages");
19546
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3371
  assert(is_ptr_aligned(req_addr, os::large_page_size()), "Unaligned address");
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3372
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3373
  if (!is_size_aligned(bytes, os::large_page_size()) || alignment > os::large_page_size()) {
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3374
    return NULL; // Fallback to small pages.
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3375
  }
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3376
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3377
  key_t key = IPC_PRIVATE;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3378
  char *addr;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3379
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3380
  bool warn_on_failure = UseLargePages &&
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3381
                        (!FLAG_IS_DEFAULT(UseLargePages) ||
19546
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3382
                         !FLAG_IS_DEFAULT(UseSHM) ||
26684
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
  3383
                         !FLAG_IS_DEFAULT(LargePageSizeInBytes));
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3384
  char msg[128];
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3385
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3386
  // Create a large shared memory region to attach to based on size.
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3387
  // Currently, size is the total size of the heap
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3388
  int shmid = shmget(key, bytes, SHM_HUGETLB|IPC_CREAT|SHM_R|SHM_W);
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3389
  if (shmid == -1) {
26683
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  3390
    // Possible reasons for shmget failure:
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  3391
    // 1. shmmax is too small for Java heap.
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  3392
    //    > check shmmax value: cat /proc/sys/kernel/shmmax
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  3393
    //    > increase shmmax value: echo "0xffffffff" > /proc/sys/kernel/shmmax
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  3394
    // 2. not enough large page memory.
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  3395
    //    > check available large pages: cat /proc/meminfo
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  3396
    //    > increase amount of large pages:
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  3397
    //          echo new_value > /proc/sys/vm/nr_hugepages
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  3398
    //      Note 1: different Linux may use different name for this property,
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  3399
    //            e.g. on Redhat AS-3 it is "hugetlb_pool".
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  3400
    //      Note 2: it's possible there's enough physical memory available but
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  3401
    //            they are so fragmented after a long run that they can't
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  3402
    //            coalesce into large pages. Try to reserve large pages when
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  3403
    //            the system is still "fresh".
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  3404
    if (warn_on_failure) {
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  3405
      jio_snprintf(msg, sizeof(msg), "Failed to reserve shared memory (errno = %d).", errno);
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  3406
      warning("%s", msg);
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  3407
    }
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  3408
    return NULL;
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3409
  }
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3410
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3411
  // attach to the region
5532
34c4ef11dbed 6951686: Using large pages on Linux prevents zero based compressed oops
kvn
parents: 5413
diff changeset
  3412
  addr = (char*)shmat(shmid, req_addr, 0);
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3413
  int err = errno;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3414
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3415
  // Remove shmid. If shmat() is successful, the actual shared memory segment
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3416
  // will be deleted when it's detached by shmdt() or when the process
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3417
  // terminates. If shmat() is not successful this will remove the shared
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3418
  // segment immediately.
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3419
  shmctl(shmid, IPC_RMID, NULL);
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3420
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3421
  if ((intptr_t)addr == -1) {
26683
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  3422
    if (warn_on_failure) {
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  3423
      jio_snprintf(msg, sizeof(msg), "Failed to attach shared memory (errno = %d).", err);
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  3424
      warning("%s", msg);
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  3425
    }
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  3426
    return NULL;
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3427
  }
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3428
19546
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3429
  return addr;
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3430
}
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3431
26684
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
  3432
static void warn_on_large_pages_failure(char* req_addr, size_t bytes,
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
  3433
                                        int error) {
19546
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3434
  assert(error == ENOMEM, "Only expect to fail if no memory is available");
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3435
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3436
  bool warn_on_failure = UseLargePages &&
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3437
      (!FLAG_IS_DEFAULT(UseLargePages) ||
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3438
       !FLAG_IS_DEFAULT(UseHugeTLBFS) ||
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3439
       !FLAG_IS_DEFAULT(LargePageSizeInBytes));
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3440
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3441
  if (warn_on_failure) {
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3442
    char msg[128];
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3443
    jio_snprintf(msg, sizeof(msg), "Failed to reserve large pages memory req_addr: "
26683
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  3444
                 PTR_FORMAT " bytes: " SIZE_FORMAT " (errno = %d).", req_addr, bytes, error);
24424
2658d7834c6e 8037816: Fix for 8036122 breaks build with Xcode5/clang
drchase
parents: 24352
diff changeset
  3445
    warning("%s", msg);
19546
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3446
  }
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3447
}
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3448
26684
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
  3449
char* os::Linux::reserve_memory_special_huge_tlbfs_only(size_t bytes,
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
  3450
                                                        char* req_addr,
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
  3451
                                                        bool exec) {
19546
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3452
  assert(UseLargePages && UseHugeTLBFS, "only for Huge TLBFS large pages");
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3453
  assert(is_size_aligned(bytes, os::large_page_size()), "Unaligned size");
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3454
  assert(is_ptr_aligned(req_addr, os::large_page_size()), "Unaligned address");
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3455
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3456
  int prot = exec ? PROT_READ|PROT_WRITE|PROT_EXEC : PROT_READ|PROT_WRITE;
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3457
  char* addr = (char*)::mmap(req_addr, bytes, prot,
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3458
                             MAP_PRIVATE|MAP_ANONYMOUS|MAP_HUGETLB,
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3459
                             -1, 0);
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3460
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3461
  if (addr == MAP_FAILED) {
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3462
    warn_on_large_pages_failure(req_addr, bytes, errno);
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3463
    return NULL;
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3464
  }
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3465
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3466
  assert(is_ptr_aligned(addr, os::large_page_size()), "Must be");
15927
f256c20146f4 8008257: NMT: assert(new_rec->is_allocation_record()) failed when running with shared memory option
zgu
parents: 15926
diff changeset
  3467
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3468
  return addr;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3469
}
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3470
26684
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
  3471
char* os::Linux::reserve_memory_special_huge_tlbfs_mixed(size_t bytes,
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
  3472
                                                         size_t alignment,
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
  3473
                                                         char* req_addr,
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
  3474
                                                         bool exec) {
19546
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3475
  size_t large_page_size = os::large_page_size();
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3476
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3477
  assert(bytes >= large_page_size, "Shouldn't allocate large pages for small sizes");
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3478
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3479
  // Allocate small pages.
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3480
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3481
  char* start;
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3482
  if (req_addr != NULL) {
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3483
    assert(is_ptr_aligned(req_addr, alignment), "Must be");
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3484
    assert(is_size_aligned(bytes, alignment), "Must be");
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3485
    start = os::reserve_memory(bytes, req_addr);
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3486
    assert(start == NULL || start == req_addr, "Must be");
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3487
  } else {
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3488
    start = os::reserve_memory_aligned(bytes, alignment);
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3489
  }
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3490
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3491
  if (start == NULL) {
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3492
    return NULL;
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3493
  }
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3494
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3495
  assert(is_ptr_aligned(start, alignment), "Must be");
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3496
25946
1572c9f03fb9 8046598: Scalable Native memory tracking development
zgu
parents: 25503
diff changeset
  3497
  if (MemTracker::tracking_level() > NMT_minimal) {
1572c9f03fb9 8046598: Scalable Native memory tracking development
zgu
parents: 25503
diff changeset
  3498
    // os::reserve_memory_special will record this memory area.
1572c9f03fb9 8046598: Scalable Native memory tracking development
zgu
parents: 25503
diff changeset
  3499
    // Need to release it here to prevent overlapping reservations.
1572c9f03fb9 8046598: Scalable Native memory tracking development
zgu
parents: 25503
diff changeset
  3500
    Tracker tkr = MemTracker::get_virtual_memory_release_tracker();
1572c9f03fb9 8046598: Scalable Native memory tracking development
zgu
parents: 25503
diff changeset
  3501
    tkr.record((address)start, bytes);
1572c9f03fb9 8046598: Scalable Native memory tracking development
zgu
parents: 25503
diff changeset
  3502
  }
19546
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3503
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3504
  char* end = start + bytes;
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3505
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3506
  // Find the regions of the allocated chunk that can be promoted to large pages.
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3507
  char* lp_start = (char*)align_ptr_up(start, large_page_size);
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3508
  char* lp_end   = (char*)align_ptr_down(end, large_page_size);
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3509
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3510
  size_t lp_bytes = lp_end - lp_start;
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3511
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3512
  assert(is_size_aligned(lp_bytes, large_page_size), "Must be");
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3513
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3514
  if (lp_bytes == 0) {
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3515
    // The mapped region doesn't even span the start and the end of a large page.
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3516
    // Fall back to allocate a non-special area.
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3517
    ::munmap(start, end - start);
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3518
    return NULL;
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3519
  }
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3520
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3521
  int prot = exec ? PROT_READ|PROT_WRITE|PROT_EXEC : PROT_READ|PROT_WRITE;
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3522
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3523
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3524
  void* result;
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3525
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3526
  if (start != lp_start) {
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3527
    result = ::mmap(start, lp_start - start, prot,
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3528
                    MAP_PRIVATE|MAP_ANONYMOUS|MAP_FIXED,
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3529
                    -1, 0);
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3530
    if (result == MAP_FAILED) {
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3531
      ::munmap(lp_start, end - lp_start);
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3532
      return NULL;
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3533
    }
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3534
  }
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3535
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3536
  result = ::mmap(lp_start, lp_bytes, prot,
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3537
                  MAP_PRIVATE|MAP_ANONYMOUS|MAP_FIXED|MAP_HUGETLB,
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3538
                  -1, 0);
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3539
  if (result == MAP_FAILED) {
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3540
    warn_on_large_pages_failure(req_addr, bytes, errno);
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3541
    // If the mmap above fails, the large pages region will be unmapped and we
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3542
    // have regions before and after with small pages. Release these regions.
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3543
    //
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3544
    // |  mapped  |  unmapped  |  mapped  |
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3545
    // ^          ^            ^          ^
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3546
    // start      lp_start     lp_end     end
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3547
    //
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3548
    ::munmap(start, lp_start - start);
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3549
    ::munmap(lp_end, end - lp_end);
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3550
    return NULL;
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3551
  }
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3552
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3553
  if (lp_end != end) {
26683
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  3554
    result = ::mmap(lp_end, end - lp_end, prot,
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  3555
                    MAP_PRIVATE|MAP_ANONYMOUS|MAP_FIXED,
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  3556
                    -1, 0);
19546
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3557
    if (result == MAP_FAILED) {
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3558
      ::munmap(start, lp_end - start);
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3559
      return NULL;
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3560
    }
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3561
  }
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3562
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3563
  return start;
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3564
}
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3565
26684
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
  3566
char* os::Linux::reserve_memory_special_huge_tlbfs(size_t bytes,
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
  3567
                                                   size_t alignment,
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
  3568
                                                   char* req_addr,
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
  3569
                                                   bool exec) {
19546
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3570
  assert(UseLargePages && UseHugeTLBFS, "only for Huge TLBFS large pages");
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3571
  assert(is_ptr_aligned(req_addr, alignment), "Must be");
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3572
  assert(is_power_of_2(alignment), "Must be");
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3573
  assert(is_power_of_2(os::large_page_size()), "Must be");
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3574
  assert(bytes >= os::large_page_size(), "Shouldn't allocate large pages for small sizes");
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3575
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3576
  if (is_size_aligned(bytes, os::large_page_size()) && alignment <= os::large_page_size()) {
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3577
    return reserve_memory_special_huge_tlbfs_only(bytes, req_addr, exec);
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3578
  } else {
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3579
    return reserve_memory_special_huge_tlbfs_mixed(bytes, alignment, req_addr, exec);
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3580
  }
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3581
}
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3582
26684
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
  3583
char* os::reserve_memory_special(size_t bytes, size_t alignment,
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
  3584
                                 char* req_addr, bool exec) {
19546
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3585
  assert(UseLargePages, "only for large pages");
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3586
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3587
  char* addr;
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3588
  if (UseSHM) {
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3589
    addr = os::Linux::reserve_memory_special_shm(bytes, alignment, req_addr, exec);
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3590
  } else {
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3591
    assert(UseHugeTLBFS, "must be");
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3592
    addr = os::Linux::reserve_memory_special_huge_tlbfs(bytes, alignment, req_addr, exec);
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3593
  }
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3594
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3595
  if (addr != NULL) {
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3596
    if (UseNUMAInterleaving) {
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3597
      numa_make_global(addr, bytes);
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3598
    }
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3599
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3600
    // The memory is committed
25946
1572c9f03fb9 8046598: Scalable Native memory tracking development
zgu
parents: 25503
diff changeset
  3601
    MemTracker::record_virtual_memory_reserve_and_commit((address)addr, bytes, CALLER_PC);
19546
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3602
  }
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3603
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3604
  return addr;
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3605
}
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3606
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3607
bool os::Linux::release_memory_special_shm(char* base, size_t bytes) {
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3608
  // detaching the SHM segment will also delete it, see reserve_memory_special_shm()
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3609
  return shmdt(base) == 0;
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3610
}
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3611
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3612
bool os::Linux::release_memory_special_huge_tlbfs(char* base, size_t bytes) {
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3613
  return pd_release_memory(base, bytes);
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3614
}
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3615
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3616
bool os::release_memory_special(char* base, size_t bytes) {
25946
1572c9f03fb9 8046598: Scalable Native memory tracking development
zgu
parents: 25503
diff changeset
  3617
  bool res;
1572c9f03fb9 8046598: Scalable Native memory tracking development
zgu
parents: 25503
diff changeset
  3618
  if (MemTracker::tracking_level() > NMT_minimal) {
1572c9f03fb9 8046598: Scalable Native memory tracking development
zgu
parents: 25503
diff changeset
  3619
    Tracker tkr = MemTracker::get_virtual_memory_release_tracker();
1572c9f03fb9 8046598: Scalable Native memory tracking development
zgu
parents: 25503
diff changeset
  3620
    res = os::Linux::release_memory_special_impl(base, bytes);
1572c9f03fb9 8046598: Scalable Native memory tracking development
zgu
parents: 25503
diff changeset
  3621
    if (res) {
1572c9f03fb9 8046598: Scalable Native memory tracking development
zgu
parents: 25503
diff changeset
  3622
      tkr.record((address)base, bytes);
1572c9f03fb9 8046598: Scalable Native memory tracking development
zgu
parents: 25503
diff changeset
  3623
    }
1572c9f03fb9 8046598: Scalable Native memory tracking development
zgu
parents: 25503
diff changeset
  3624
1572c9f03fb9 8046598: Scalable Native memory tracking development
zgu
parents: 25503
diff changeset
  3625
  } else {
1572c9f03fb9 8046598: Scalable Native memory tracking development
zgu
parents: 25503
diff changeset
  3626
    res = os::Linux::release_memory_special_impl(base, bytes);
1572c9f03fb9 8046598: Scalable Native memory tracking development
zgu
parents: 25503
diff changeset
  3627
  }
1572c9f03fb9 8046598: Scalable Native memory tracking development
zgu
parents: 25503
diff changeset
  3628
  return res;
1572c9f03fb9 8046598: Scalable Native memory tracking development
zgu
parents: 25503
diff changeset
  3629
}
1572c9f03fb9 8046598: Scalable Native memory tracking development
zgu
parents: 25503
diff changeset
  3630
1572c9f03fb9 8046598: Scalable Native memory tracking development
zgu
parents: 25503
diff changeset
  3631
bool os::Linux::release_memory_special_impl(char* base, size_t bytes) {
19546
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3632
  assert(UseLargePages, "only for large pages");
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3633
  bool res;
25946
1572c9f03fb9 8046598: Scalable Native memory tracking development
zgu
parents: 25503
diff changeset
  3634
19546
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3635
  if (UseSHM) {
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3636
    res = os::Linux::release_memory_special_shm(base, bytes);
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3637
  } else {
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3638
    assert(UseHugeTLBFS, "must be");
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3639
    res = os::Linux::release_memory_special_huge_tlbfs(base, bytes);
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3640
  }
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3641
  return res;
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3642
}
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3643
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3644
size_t os::large_page_size() {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3645
  return _large_page_size;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3646
}
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3647
19546
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3648
// With SysV SHM the entire memory region must be allocated as shared
9335
7bdd2a3ab3d8 7034464: Support transparent large pages on Linux
iveresov
parents: 8476
diff changeset
  3649
// memory.
19546
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3650
// HugeTLBFS allows application to commit large page memory on demand.
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3651
// However, when committing memory with HugeTLBFS fails, the region
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3652
// that was supposed to be committed will lose the old reservation
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3653
// and allow other threads to steal that memory region. Because of this
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3654
// behavior we can't commit HugeTLBFS memory.
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3655
bool os::can_commit_large_page_memory() {
19546
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3656
  return UseTransparentHugePages;
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3657
}
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3658
252
050143a0dbfb 6642862: Code cache allocation fails with large pages after 6588638
jcoomes
parents: 235
diff changeset
  3659
bool os::can_execute_large_page_memory() {
19546
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  3660
  return UseTransparentHugePages || UseHugeTLBFS;
252
050143a0dbfb 6642862: Code cache allocation fails with large pages after 6588638
jcoomes
parents: 235
diff changeset
  3661
}
050143a0dbfb 6642862: Code cache allocation fails with large pages after 6588638
jcoomes
parents: 235
diff changeset
  3662
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3663
// Reserve memory at an arbitrary address, only if that area is
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3664
// available (and not reserved for something else).
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3665
13195
be27e1b6a4b9 6995781: Native Memory Tracking (Phase 1)
zgu
parents: 12735
diff changeset
  3666
char* os::pd_attempt_reserve_memory_at(size_t bytes, char* requested_addr) {
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3667
  const int max_tries = 10;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3668
  char* base[max_tries];
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3669
  size_t size[max_tries];
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3670
  const size_t gap = 0x000000;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3671
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3672
  // Assert only that the size is a multiple of the page size, since
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3673
  // that's all that mmap requires, and since that's all we really know
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3674
  // about at this low abstraction level.  If we need higher alignment,
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3675
  // we can either pass an alignment to this method or verify alignment
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3676
  // in one of the methods further up the call chain.  See bug 5044738.
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3677
  assert(bytes % os::vm_page_size() == 0, "reserving unexpected size block");
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3678
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3679
  // Repeatedly allocate blocks until the block is allocated at the
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3680
  // right spot. Give up after max_tries. Note that reserve_memory() will
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3681
  // automatically update _highest_vm_reserved_address if the call is
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3682
  // successful. The variable tracks the highest memory address every reserved
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3683
  // by JVM. It is used to detect heap-stack collision if running with
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3684
  // fixed-stack LinuxThreads. Because here we may attempt to reserve more
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3685
  // space than needed, it could confuse the collision detecting code. To
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3686
  // solve the problem, save current _highest_vm_reserved_address and
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3687
  // calculate the correct value before return.
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3688
  address old_highest = _highest_vm_reserved_address;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3689
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3690
  // Linux mmap allows caller to pass an address as hint; give it a try first,
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3691
  // if kernel honors the hint then we can return immediately.
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3692
  char * addr = anon_mmap(requested_addr, bytes, false);
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3693
  if (addr == requested_addr) {
26683
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  3694
    return requested_addr;
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3695
  }
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3696
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3697
  if (addr != NULL) {
26683
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  3698
    // mmap() is successful but it fails to reserve at the requested address
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  3699
    anon_munmap(addr, bytes);
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3700
  }
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3701
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3702
  int i;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3703
  for (i = 0; i < max_tries; ++i) {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3704
    base[i] = reserve_memory(bytes);
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3705
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3706
    if (base[i] != NULL) {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3707
      // Is this the block we wanted?
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3708
      if (base[i] == requested_addr) {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3709
        size[i] = bytes;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3710
        break;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3711
      }
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3712
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3713
      // Does this overlap the block we wanted? Give back the overlapped
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3714
      // parts and try again.
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3715
29580
a67a581cfe11 8073315: Enable gcc -Wtype-limits and fix upcoming issues.
goetz
parents: 29474
diff changeset
  3716
      ptrdiff_t top_overlap = requested_addr + (bytes + gap) - base[i];
a67a581cfe11 8073315: Enable gcc -Wtype-limits and fix upcoming issues.
goetz
parents: 29474
diff changeset
  3717
      if (top_overlap >= 0 && (size_t)top_overlap < bytes) {
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3718
        unmap_memory(base[i], top_overlap);
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3719
        base[i] += top_overlap;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3720
        size[i] = bytes - top_overlap;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3721
      } else {
29580
a67a581cfe11 8073315: Enable gcc -Wtype-limits and fix upcoming issues.
goetz
parents: 29474
diff changeset
  3722
        ptrdiff_t bottom_overlap = base[i] + bytes - requested_addr;
a67a581cfe11 8073315: Enable gcc -Wtype-limits and fix upcoming issues.
goetz
parents: 29474
diff changeset
  3723
        if (bottom_overlap >= 0 && (size_t)bottom_overlap < bytes) {
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3724
          unmap_memory(requested_addr, bottom_overlap);
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3725
          size[i] = bytes - bottom_overlap;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3726
        } else {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3727
          size[i] = bytes;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3728
        }
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3729
      }
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3730
    }
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3731
  }
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3732
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3733
  // Give back the unused reserved pieces.
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3734
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3735
  for (int j = 0; j < i; ++j) {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3736
    if (base[j] != NULL) {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3737
      unmap_memory(base[j], size[j]);
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3738
    }
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3739
  }
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3740
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3741
  if (i < max_tries) {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3742
    _highest_vm_reserved_address = MAX2(old_highest, (address)requested_addr + bytes);
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3743
    return requested_addr;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3744
  } else {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3745
    _highest_vm_reserved_address = old_highest;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3746
    return NULL;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3747
  }
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3748
}
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3749
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3750
size_t os::read(int fd, void *buf, unsigned int nBytes) {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3751
  return ::read(fd, buf, nBytes);
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3752
}
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3753
27562
47f369e3c69c 8049367: Modular Run-Time Images
chegar
parents: 27474
diff changeset
  3754
size_t os::read_at(int fd, void *buf, unsigned int nBytes, jlong offset) {
47f369e3c69c 8049367: Modular Run-Time Images
chegar
parents: 27474
diff changeset
  3755
  return ::pread(fd, buf, nBytes, offset);
47f369e3c69c 8049367: Modular Run-Time Images
chegar
parents: 27474
diff changeset
  3756
}
47f369e3c69c 8049367: Modular Run-Time Images
chegar
parents: 27474
diff changeset
  3757
22533
76088853a2eb 8028280: ParkEvent leak when running modified runThese which only loads classes
dsimms
parents: 22528
diff changeset
  3758
// Short sleep, direct OS call.
76088853a2eb 8028280: ParkEvent leak when running modified runThese which only loads classes
dsimms
parents: 22528
diff changeset
  3759
//
76088853a2eb 8028280: ParkEvent leak when running modified runThese which only loads classes
dsimms
parents: 22528
diff changeset
  3760
// Note: certain versions of Linux CFS scheduler (since 2.6.23) do not guarantee
76088853a2eb 8028280: ParkEvent leak when running modified runThese which only loads classes
dsimms
parents: 22528
diff changeset
  3761
// sched_yield(2) will actually give up the CPU:
76088853a2eb 8028280: ParkEvent leak when running modified runThese which only loads classes
dsimms
parents: 22528
diff changeset
  3762
//
76088853a2eb 8028280: ParkEvent leak when running modified runThese which only loads classes
dsimms
parents: 22528
diff changeset
  3763
//   * Alone on this pariticular CPU, keeps running.
76088853a2eb 8028280: ParkEvent leak when running modified runThese which only loads classes
dsimms
parents: 22528
diff changeset
  3764
//   * Before the introduction of "skip_buddy" with "compat_yield" disabled
76088853a2eb 8028280: ParkEvent leak when running modified runThese which only loads classes
dsimms
parents: 22528
diff changeset
  3765
//     (pre 2.6.39).
76088853a2eb 8028280: ParkEvent leak when running modified runThese which only loads classes
dsimms
parents: 22528
diff changeset
  3766
//
76088853a2eb 8028280: ParkEvent leak when running modified runThese which only loads classes
dsimms
parents: 22528
diff changeset
  3767
// So calling this with 0 is an alternative.
76088853a2eb 8028280: ParkEvent leak when running modified runThese which only loads classes
dsimms
parents: 22528
diff changeset
  3768
//
76088853a2eb 8028280: ParkEvent leak when running modified runThese which only loads classes
dsimms
parents: 22528
diff changeset
  3769
void os::naked_short_sleep(jlong ms) {
76088853a2eb 8028280: ParkEvent leak when running modified runThese which only loads classes
dsimms
parents: 22528
diff changeset
  3770
  struct timespec req;
76088853a2eb 8028280: ParkEvent leak when running modified runThese which only loads classes
dsimms
parents: 22528
diff changeset
  3771
76088853a2eb 8028280: ParkEvent leak when running modified runThese which only loads classes
dsimms
parents: 22528
diff changeset
  3772
  assert(ms < 1000, "Un-interruptable sleep, short time use only");
76088853a2eb 8028280: ParkEvent leak when running modified runThese which only loads classes
dsimms
parents: 22528
diff changeset
  3773
  req.tv_sec = 0;
76088853a2eb 8028280: ParkEvent leak when running modified runThese which only loads classes
dsimms
parents: 22528
diff changeset
  3774
  if (ms > 0) {
76088853a2eb 8028280: ParkEvent leak when running modified runThese which only loads classes
dsimms
parents: 22528
diff changeset
  3775
    req.tv_nsec = (ms % 1000) * 1000000;
26684
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
  3776
  } else {
22533
76088853a2eb 8028280: ParkEvent leak when running modified runThese which only loads classes
dsimms
parents: 22528
diff changeset
  3777
    req.tv_nsec = 1;
76088853a2eb 8028280: ParkEvent leak when running modified runThese which only loads classes
dsimms
parents: 22528
diff changeset
  3778
  }
76088853a2eb 8028280: ParkEvent leak when running modified runThese which only loads classes
dsimms
parents: 22528
diff changeset
  3779
76088853a2eb 8028280: ParkEvent leak when running modified runThese which only loads classes
dsimms
parents: 22528
diff changeset
  3780
  nanosleep(&req, NULL);
76088853a2eb 8028280: ParkEvent leak when running modified runThese which only loads classes
dsimms
parents: 22528
diff changeset
  3781
76088853a2eb 8028280: ParkEvent leak when running modified runThese which only loads classes
dsimms
parents: 22528
diff changeset
  3782
  return;
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3783
}
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3784
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3785
// Sleep forever; naked call to OS-specific sleep; use with CAUTION
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3786
void os::infinite_sleep() {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3787
  while (true) {    // sleep forever ...
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3788
    ::sleep(100);   // ... 100 seconds at a time
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3789
  }
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3790
}
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3791
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3792
// Used to convert frequent JVM_Yield() to nops
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3793
bool os::dont_yield() {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3794
  return DontYieldALot;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3795
}
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3796
25477
7dad9f95fd31 8047714: Fix for JDK-6546236 made Solaris os::yield() a no-op
fparain
parents: 25472
diff changeset
  3797
void os::naked_yield() {
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3798
  sched_yield();
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3799
}
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3800
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3801
////////////////////////////////////////////////////////////////////////////////
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3802
// thread priority support
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3803
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3804
// Note: Normal Linux applications are run with SCHED_OTHER policy. SCHED_OTHER
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3805
// only supports dynamic priority, static priority must be zero. For real-time
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3806
// applications, Linux supports SCHED_RR which allows static priority (1-99).
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3807
// However, for large multi-threaded applications, SCHED_RR is not only slower
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3808
// than SCHED_OTHER, but also very unstable (my volano tests hang hard 4 out
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3809
// of 5 runs - Sep 2005).
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3810
//
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3811
// The following code actually changes the niceness of kernel-thread/LWP. It
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3812
// has an assumption that setpriority() only modifies one kernel-thread/LWP,
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3813
// not the entire user process, and user level threads are 1:1 mapped to kernel
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3814
// threads. It has always been the case, but could change in the future. For
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3815
// this reason, the code should not be used as default (ThreadPriorityPolicy=0).
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3816
// It is only used when ThreadPriorityPolicy=1 and requires root privilege.
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3817
11601
f359304c1856 7082553: Interpret Thread.setPriority(Thread.MAX_PRIORITY) to mean FX60 on Solaris 10 and 11
phh
parents: 11483
diff changeset
  3818
int os::java_to_os_priority[CriticalPriority + 1] = {
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3819
  19,              // 0 Entry should never be used
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3820
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3821
   4,              // 1 MinPriority
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3822
   3,              // 2
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3823
   2,              // 3
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3824
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3825
   1,              // 4
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3826
   0,              // 5 NormPriority
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3827
  -1,              // 6
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3828
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3829
  -2,              // 7
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3830
  -3,              // 8
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3831
  -4,              // 9 NearMaxPriority
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3832
11601
f359304c1856 7082553: Interpret Thread.setPriority(Thread.MAX_PRIORITY) to mean FX60 on Solaris 10 and 11
phh
parents: 11483
diff changeset
  3833
  -5,              // 10 MaxPriority
f359304c1856 7082553: Interpret Thread.setPriority(Thread.MAX_PRIORITY) to mean FX60 on Solaris 10 and 11
phh
parents: 11483
diff changeset
  3834
f359304c1856 7082553: Interpret Thread.setPriority(Thread.MAX_PRIORITY) to mean FX60 on Solaris 10 and 11
phh
parents: 11483
diff changeset
  3835
  -5               // 11 CriticalPriority
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3836
};
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3837
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3838
static int prio_init() {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3839
  if (ThreadPriorityPolicy == 1) {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3840
    // Only root can raise thread priority. Don't allow ThreadPriorityPolicy=1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3841
    // if effective uid is not root. Perhaps, a more elegant way of doing
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3842
    // this is to test CAP_SYS_NICE capability, but that will require libcap.so
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3843
    if (geteuid() != 0) {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3844
      if (!FLAG_IS_DEFAULT(ThreadPriorityPolicy)) {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3845
        warning("-XX:ThreadPriorityPolicy requires root privilege on Linux");
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3846
      }
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3847
      ThreadPriorityPolicy = 0;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3848
    }
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3849
  }
11601
f359304c1856 7082553: Interpret Thread.setPriority(Thread.MAX_PRIORITY) to mean FX60 on Solaris 10 and 11
phh
parents: 11483
diff changeset
  3850
  if (UseCriticalJavaThreadPriority) {
f359304c1856 7082553: Interpret Thread.setPriority(Thread.MAX_PRIORITY) to mean FX60 on Solaris 10 and 11
phh
parents: 11483
diff changeset
  3851
    os::java_to_os_priority[MaxPriority] = os::java_to_os_priority[CriticalPriority];
f359304c1856 7082553: Interpret Thread.setPriority(Thread.MAX_PRIORITY) to mean FX60 on Solaris 10 and 11
phh
parents: 11483
diff changeset
  3852
  }
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3853
  return 0;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3854
}
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3855
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3856
OSReturn os::set_native_priority(Thread* thread, int newpri) {
25064
244218e6ec0a 8046758: cleanup non-indent white space issues prior to Contended Locking cleanup bucket
dcubed
parents: 24931
diff changeset
  3857
  if (!UseThreadPriorities || ThreadPriorityPolicy == 0) return OS_OK;
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3858
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3859
  int ret = setpriority(PRIO_PROCESS, thread->osthread()->thread_id(), newpri);
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3860
  return (ret == 0) ? OS_OK : OS_ERR;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3861
}
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3862
26684
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
  3863
OSReturn os::get_native_priority(const Thread* const thread,
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
  3864
                                 int *priority_ptr) {
25064
244218e6ec0a 8046758: cleanup non-indent white space issues prior to Contended Locking cleanup bucket
dcubed
parents: 24931
diff changeset
  3865
  if (!UseThreadPriorities || ThreadPriorityPolicy == 0) {
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3866
    *priority_ptr = java_to_os_priority[NormPriority];
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3867
    return OS_OK;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3868
  }
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3869
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3870
  errno = 0;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3871
  *priority_ptr = getpriority(PRIO_PROCESS, thread->osthread()->thread_id());
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3872
  return (*priority_ptr != -1 || errno == 0 ? OS_OK : OS_ERR);
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3873
}
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3874
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3875
// Hint to the underlying OS that a task switch would not be good.
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3876
// Void return because it's a hint and can fail.
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3877
void os::hint_no_preempt() {}
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3878
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3879
////////////////////////////////////////////////////////////////////////////////
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3880
// suspend/resume support
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3881
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3882
//  the low-level signal-based suspend/resume support is a remnant from the
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3883
//  old VM-suspension that used to be for java-suspension, safepoints etc,
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3884
//  within hotspot. Now there is a single use-case for this:
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3885
//    - calling get_thread_pc() on the VMThread by the flat-profiler task
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3886
//      that runs in the watcher thread.
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3887
//  The remaining code is greatly simplified from the more general suspension
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3888
//  code that used to be used.
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3889
//
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3890
//  The protocol is quite simple:
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3891
//  - suspend:
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3892
//      - sends a signal to the target thread
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3893
//      - polls the suspend state of the osthread using a yield loop
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3894
//      - target thread signal handler (SR_handler) sets suspend state
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3895
//        and blocks in sigsuspend until continued
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3896
//  - resume:
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3897
//      - sets target osthread state to continue
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3898
//      - sends signal to end the sigsuspend loop in the SR_handler
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3899
//
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3900
//  Note that the SR_lock plays no role in this suspend/resume protocol.
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3901
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3902
static void resume_clear_context(OSThread *osthread) {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3903
  osthread->set_ucontext(NULL);
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3904
  osthread->set_siginfo(NULL);
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3905
}
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3906
26684
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
  3907
static void suspend_save_context(OSThread *osthread, siginfo_t* siginfo,
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
  3908
                                 ucontext_t* context) {
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3909
  osthread->set_ucontext(context);
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3910
  osthread->set_siginfo(siginfo);
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3911
}
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3912
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3913
// Handler function invoked when a thread's execution is suspended or
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3914
// resumed. We have to be careful that only async-safe functions are
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3915
// called here (Note: most pthread functions are not async safe and
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3916
// should be avoided.)
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3917
//
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3918
// Note: sigwait() is a more natural fit than sigsuspend() from an
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3919
// interface point of view, but sigwait() prevents the signal hander
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3920
// from being run. libpthread would get very confused by not having
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3921
// its signal handlers run and prevents sigwait()'s use with the
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3922
// mutex granting granting signal.
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3923
//
18025
b7bcf7497f93 8005849: JEP 167: Event-Based JVM Tracing
sla
parents: 17854
diff changeset
  3924
// Currently only ever called on the VMThread and JavaThreads (PC sampling)
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3925
//
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3926
static void SR_handler(int sig, siginfo_t* siginfo, ucontext_t* context) {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3927
  // Save and restore errno to avoid confusing native code with EINTR
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3928
  // after sigsuspend.
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3929
  int old_errno = errno;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3930
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3931
  Thread* thread = Thread::current();
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3932
  OSThread* osthread = thread->osthread();
18025
b7bcf7497f93 8005849: JEP 167: Event-Based JVM Tracing
sla
parents: 17854
diff changeset
  3933
  assert(thread->is_VM_thread() || thread->is_Java_thread(), "Must be VMThread or JavaThread");
b7bcf7497f93 8005849: JEP 167: Event-Based JVM Tracing
sla
parents: 17854
diff changeset
  3934
b7bcf7497f93 8005849: JEP 167: Event-Based JVM Tracing
sla
parents: 17854
diff changeset
  3935
  os::SuspendResume::State current = osthread->sr.state();
b7bcf7497f93 8005849: JEP 167: Event-Based JVM Tracing
sla
parents: 17854
diff changeset
  3936
  if (current == os::SuspendResume::SR_SUSPEND_REQUEST) {
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3937
    suspend_save_context(osthread, siginfo, context);
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3938
18025
b7bcf7497f93 8005849: JEP 167: Event-Based JVM Tracing
sla
parents: 17854
diff changeset
  3939
    // attempt to switch the state, we assume we had a SUSPEND_REQUEST
b7bcf7497f93 8005849: JEP 167: Event-Based JVM Tracing
sla
parents: 17854
diff changeset
  3940
    os::SuspendResume::State state = osthread->sr.suspended();
b7bcf7497f93 8005849: JEP 167: Event-Based JVM Tracing
sla
parents: 17854
diff changeset
  3941
    if (state == os::SuspendResume::SR_SUSPENDED) {
b7bcf7497f93 8005849: JEP 167: Event-Based JVM Tracing
sla
parents: 17854
diff changeset
  3942
      sigset_t suspend_set;  // signals for sigsuspend()
b7bcf7497f93 8005849: JEP 167: Event-Based JVM Tracing
sla
parents: 17854
diff changeset
  3943
b7bcf7497f93 8005849: JEP 167: Event-Based JVM Tracing
sla
parents: 17854
diff changeset
  3944
      // get current set of blocked signals and unblock resume signal
b7bcf7497f93 8005849: JEP 167: Event-Based JVM Tracing
sla
parents: 17854
diff changeset
  3945
      pthread_sigmask(SIG_BLOCK, NULL, &suspend_set);
b7bcf7497f93 8005849: JEP 167: Event-Based JVM Tracing
sla
parents: 17854
diff changeset
  3946
      sigdelset(&suspend_set, SR_signum);
b7bcf7497f93 8005849: JEP 167: Event-Based JVM Tracing
sla
parents: 17854
diff changeset
  3947
b7bcf7497f93 8005849: JEP 167: Event-Based JVM Tracing
sla
parents: 17854
diff changeset
  3948
      sr_semaphore.signal();
b7bcf7497f93 8005849: JEP 167: Event-Based JVM Tracing
sla
parents: 17854
diff changeset
  3949
      // wait here until we are resumed
b7bcf7497f93 8005849: JEP 167: Event-Based JVM Tracing
sla
parents: 17854
diff changeset
  3950
      while (1) {
b7bcf7497f93 8005849: JEP 167: Event-Based JVM Tracing
sla
parents: 17854
diff changeset
  3951
        sigsuspend(&suspend_set);
b7bcf7497f93 8005849: JEP 167: Event-Based JVM Tracing
sla
parents: 17854
diff changeset
  3952
b7bcf7497f93 8005849: JEP 167: Event-Based JVM Tracing
sla
parents: 17854
diff changeset
  3953
        os::SuspendResume::State result = osthread->sr.running();
b7bcf7497f93 8005849: JEP 167: Event-Based JVM Tracing
sla
parents: 17854
diff changeset
  3954
        if (result == os::SuspendResume::SR_RUNNING) {
b7bcf7497f93 8005849: JEP 167: Event-Based JVM Tracing
sla
parents: 17854
diff changeset
  3955
          sr_semaphore.signal();
b7bcf7497f93 8005849: JEP 167: Event-Based JVM Tracing
sla
parents: 17854
diff changeset
  3956
          break;
b7bcf7497f93 8005849: JEP 167: Event-Based JVM Tracing
sla
parents: 17854
diff changeset
  3957
        }
b7bcf7497f93 8005849: JEP 167: Event-Based JVM Tracing
sla
parents: 17854
diff changeset
  3958
      }
b7bcf7497f93 8005849: JEP 167: Event-Based JVM Tracing
sla
parents: 17854
diff changeset
  3959
b7bcf7497f93 8005849: JEP 167: Event-Based JVM Tracing
sla
parents: 17854
diff changeset
  3960
    } else if (state == os::SuspendResume::SR_RUNNING) {
b7bcf7497f93 8005849: JEP 167: Event-Based JVM Tracing
sla
parents: 17854
diff changeset
  3961
      // request was cancelled, continue
b7bcf7497f93 8005849: JEP 167: Event-Based JVM Tracing
sla
parents: 17854
diff changeset
  3962
    } else {
b7bcf7497f93 8005849: JEP 167: Event-Based JVM Tracing
sla
parents: 17854
diff changeset
  3963
      ShouldNotReachHere();
b7bcf7497f93 8005849: JEP 167: Event-Based JVM Tracing
sla
parents: 17854
diff changeset
  3964
    }
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3965
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3966
    resume_clear_context(osthread);
18025
b7bcf7497f93 8005849: JEP 167: Event-Based JVM Tracing
sla
parents: 17854
diff changeset
  3967
  } else if (current == os::SuspendResume::SR_RUNNING) {
b7bcf7497f93 8005849: JEP 167: Event-Based JVM Tracing
sla
parents: 17854
diff changeset
  3968
    // request was cancelled, continue
b7bcf7497f93 8005849: JEP 167: Event-Based JVM Tracing
sla
parents: 17854
diff changeset
  3969
  } else if (current == os::SuspendResume::SR_WAKEUP_REQUEST) {
b7bcf7497f93 8005849: JEP 167: Event-Based JVM Tracing
sla
parents: 17854
diff changeset
  3970
    // ignore
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3971
  } else {
18025
b7bcf7497f93 8005849: JEP 167: Event-Based JVM Tracing
sla
parents: 17854
diff changeset
  3972
    // ignore
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3973
  }
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3974
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3975
  errno = old_errno;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3976
}
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3977
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3978
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3979
static int SR_initialize() {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3980
  struct sigaction act;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3981
  char *s;
26684
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
  3982
  // Get signal number to use for suspend/resume
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3983
  if ((s = ::getenv("_JAVA_SR_SIGNUM")) != 0) {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3984
    int sig = ::strtol(s, 0, 10);
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3985
    if (sig > 0 || sig < _NSIG) {
26683
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  3986
      SR_signum = sig;
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3987
    }
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3988
  }
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3989
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3990
  assert(SR_signum > SIGSEGV && SR_signum > SIGBUS,
26683
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  3991
         "SR_signum must be greater than max(SIGSEGV, SIGBUS), see 4355769");
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3992
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3993
  sigemptyset(&SR_sigset);
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3994
  sigaddset(&SR_sigset, SR_signum);
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3995
26684
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
  3996
  // Set up signal handler for suspend/resume
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3997
  act.sa_flags = SA_RESTART|SA_SIGINFO;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3998
  act.sa_handler = (void (*)(int)) SR_handler;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  3999
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4000
  // SR_signum is blocked by default.
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4001
  // 4528190 - We also need to block pthread restart signal (32 on all
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4002
  // supported Linux platforms). Note that LinuxThreads need to block
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4003
  // this signal for all threads to work properly. So we don't have
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4004
  // to use hard-coded signal number when setting up the mask.
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4005
  pthread_sigmask(SIG_BLOCK, NULL, &act.sa_mask);
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4006
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4007
  if (sigaction(SR_signum, &act, 0) == -1) {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4008
    return -1;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4009
  }
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4010
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4011
  // Save signal flag
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4012
  os::Linux::set_our_sigflags(SR_signum, act.sa_flags);
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4013
  return 0;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4014
}
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4015
18025
b7bcf7497f93 8005849: JEP 167: Event-Based JVM Tracing
sla
parents: 17854
diff changeset
  4016
static int sr_notify(OSThread* osthread) {
b7bcf7497f93 8005849: JEP 167: Event-Based JVM Tracing
sla
parents: 17854
diff changeset
  4017
  int status = pthread_kill(osthread->pthread_id(), SR_signum);
b7bcf7497f93 8005849: JEP 167: Event-Based JVM Tracing
sla
parents: 17854
diff changeset
  4018
  assert_status(status == 0, status, "pthread_kill");
b7bcf7497f93 8005849: JEP 167: Event-Based JVM Tracing
sla
parents: 17854
diff changeset
  4019
  return status;
b7bcf7497f93 8005849: JEP 167: Event-Based JVM Tracing
sla
parents: 17854
diff changeset
  4020
}
b7bcf7497f93 8005849: JEP 167: Event-Based JVM Tracing
sla
parents: 17854
diff changeset
  4021
b7bcf7497f93 8005849: JEP 167: Event-Based JVM Tracing
sla
parents: 17854
diff changeset
  4022
// "Randomly" selected value for how long we want to spin
b7bcf7497f93 8005849: JEP 167: Event-Based JVM Tracing
sla
parents: 17854
diff changeset
  4023
// before bailing out on suspending a thread, also how often
b7bcf7497f93 8005849: JEP 167: Event-Based JVM Tracing
sla
parents: 17854
diff changeset
  4024
// we send a signal to a thread we want to resume
b7bcf7497f93 8005849: JEP 167: Event-Based JVM Tracing
sla
parents: 17854
diff changeset
  4025
static const int RANDOMLY_LARGE_INTEGER = 1000000;
b7bcf7497f93 8005849: JEP 167: Event-Based JVM Tracing
sla
parents: 17854
diff changeset
  4026
static const int RANDOMLY_LARGE_INTEGER2 = 100;
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4027
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4028
// returns true on success and false on error - really an error is fatal
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4029
// but this seems the normal response to library errors
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4030
static bool do_suspend(OSThread* osthread) {
18025
b7bcf7497f93 8005849: JEP 167: Event-Based JVM Tracing
sla
parents: 17854
diff changeset
  4031
  assert(osthread->sr.is_running(), "thread should be running");
b7bcf7497f93 8005849: JEP 167: Event-Based JVM Tracing
sla
parents: 17854
diff changeset
  4032
  assert(!sr_semaphore.trywait(), "semaphore has invalid state");
b7bcf7497f93 8005849: JEP 167: Event-Based JVM Tracing
sla
parents: 17854
diff changeset
  4033
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4034
  // mark as suspended and send signal
18025
b7bcf7497f93 8005849: JEP 167: Event-Based JVM Tracing
sla
parents: 17854
diff changeset
  4035
  if (osthread->sr.request_suspend() != os::SuspendResume::SR_SUSPEND_REQUEST) {
b7bcf7497f93 8005849: JEP 167: Event-Based JVM Tracing
sla
parents: 17854
diff changeset
  4036
    // failed to switch, state wasn't running?
b7bcf7497f93 8005849: JEP 167: Event-Based JVM Tracing
sla
parents: 17854
diff changeset
  4037
    ShouldNotReachHere();
b7bcf7497f93 8005849: JEP 167: Event-Based JVM Tracing
sla
parents: 17854
diff changeset
  4038
    return false;
b7bcf7497f93 8005849: JEP 167: Event-Based JVM Tracing
sla
parents: 17854
diff changeset
  4039
  }
b7bcf7497f93 8005849: JEP 167: Event-Based JVM Tracing
sla
parents: 17854
diff changeset
  4040
b7bcf7497f93 8005849: JEP 167: Event-Based JVM Tracing
sla
parents: 17854
diff changeset
  4041
  if (sr_notify(osthread) != 0) {
b7bcf7497f93 8005849: JEP 167: Event-Based JVM Tracing
sla
parents: 17854
diff changeset
  4042
    ShouldNotReachHere();
b7bcf7497f93 8005849: JEP 167: Event-Based JVM Tracing
sla
parents: 17854
diff changeset
  4043
  }
b7bcf7497f93 8005849: JEP 167: Event-Based JVM Tracing
sla
parents: 17854
diff changeset
  4044
b7bcf7497f93 8005849: JEP 167: Event-Based JVM Tracing
sla
parents: 17854
diff changeset
  4045
  // managed to send the signal and switch to SUSPEND_REQUEST, now wait for SUSPENDED
b7bcf7497f93 8005849: JEP 167: Event-Based JVM Tracing
sla
parents: 17854
diff changeset
  4046
  while (true) {
b7bcf7497f93 8005849: JEP 167: Event-Based JVM Tracing
sla
parents: 17854
diff changeset
  4047
    if (sr_semaphore.timedwait(0, 2 * NANOSECS_PER_MILLISEC)) {
b7bcf7497f93 8005849: JEP 167: Event-Based JVM Tracing
sla
parents: 17854
diff changeset
  4048
      break;
b7bcf7497f93 8005849: JEP 167: Event-Based JVM Tracing
sla
parents: 17854
diff changeset
  4049
    } else {
b7bcf7497f93 8005849: JEP 167: Event-Based JVM Tracing
sla
parents: 17854
diff changeset
  4050
      // timeout
b7bcf7497f93 8005849: JEP 167: Event-Based JVM Tracing
sla
parents: 17854
diff changeset
  4051
      os::SuspendResume::State cancelled = osthread->sr.cancel_suspend();
b7bcf7497f93 8005849: JEP 167: Event-Based JVM Tracing
sla
parents: 17854
diff changeset
  4052
      if (cancelled == os::SuspendResume::SR_RUNNING) {
b7bcf7497f93 8005849: JEP 167: Event-Based JVM Tracing
sla
parents: 17854
diff changeset
  4053
        return false;
b7bcf7497f93 8005849: JEP 167: Event-Based JVM Tracing
sla
parents: 17854
diff changeset
  4054
      } else if (cancelled == os::SuspendResume::SR_SUSPENDED) {
b7bcf7497f93 8005849: JEP 167: Event-Based JVM Tracing
sla
parents: 17854
diff changeset
  4055
        // make sure that we consume the signal on the semaphore as well
b7bcf7497f93 8005849: JEP 167: Event-Based JVM Tracing
sla
parents: 17854
diff changeset
  4056
        sr_semaphore.wait();
b7bcf7497f93 8005849: JEP 167: Event-Based JVM Tracing
sla
parents: 17854
diff changeset
  4057
        break;
b7bcf7497f93 8005849: JEP 167: Event-Based JVM Tracing
sla
parents: 17854
diff changeset
  4058
      } else {
b7bcf7497f93 8005849: JEP 167: Event-Based JVM Tracing
sla
parents: 17854
diff changeset
  4059
        ShouldNotReachHere();
b7bcf7497f93 8005849: JEP 167: Event-Based JVM Tracing
sla
parents: 17854
diff changeset
  4060
        return false;
b7bcf7497f93 8005849: JEP 167: Event-Based JVM Tracing
sla
parents: 17854
diff changeset
  4061
      }
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4062
    }
18025
b7bcf7497f93 8005849: JEP 167: Event-Based JVM Tracing
sla
parents: 17854
diff changeset
  4063
  }
b7bcf7497f93 8005849: JEP 167: Event-Based JVM Tracing
sla
parents: 17854
diff changeset
  4064
b7bcf7497f93 8005849: JEP 167: Event-Based JVM Tracing
sla
parents: 17854
diff changeset
  4065
  guarantee(osthread->sr.is_suspended(), "Must be suspended");
b7bcf7497f93 8005849: JEP 167: Event-Based JVM Tracing
sla
parents: 17854
diff changeset
  4066
  return true;
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4067
}
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4068
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4069
static void do_resume(OSThread* osthread) {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4070
  assert(osthread->sr.is_suspended(), "thread should be suspended");
18025
b7bcf7497f93 8005849: JEP 167: Event-Based JVM Tracing
sla
parents: 17854
diff changeset
  4071
  assert(!sr_semaphore.trywait(), "invalid semaphore state");
b7bcf7497f93 8005849: JEP 167: Event-Based JVM Tracing
sla
parents: 17854
diff changeset
  4072
b7bcf7497f93 8005849: JEP 167: Event-Based JVM Tracing
sla
parents: 17854
diff changeset
  4073
  if (osthread->sr.request_wakeup() != os::SuspendResume::SR_WAKEUP_REQUEST) {
b7bcf7497f93 8005849: JEP 167: Event-Based JVM Tracing
sla
parents: 17854
diff changeset
  4074
    // failed to switch to WAKEUP_REQUEST
b7bcf7497f93 8005849: JEP 167: Event-Based JVM Tracing
sla
parents: 17854
diff changeset
  4075
    ShouldNotReachHere();
b7bcf7497f93 8005849: JEP 167: Event-Based JVM Tracing
sla
parents: 17854
diff changeset
  4076
    return;
b7bcf7497f93 8005849: JEP 167: Event-Based JVM Tracing
sla
parents: 17854
diff changeset
  4077
  }
b7bcf7497f93 8005849: JEP 167: Event-Based JVM Tracing
sla
parents: 17854
diff changeset
  4078
b7bcf7497f93 8005849: JEP 167: Event-Based JVM Tracing
sla
parents: 17854
diff changeset
  4079
  while (true) {
b7bcf7497f93 8005849: JEP 167: Event-Based JVM Tracing
sla
parents: 17854
diff changeset
  4080
    if (sr_notify(osthread) == 0) {
b7bcf7497f93 8005849: JEP 167: Event-Based JVM Tracing
sla
parents: 17854
diff changeset
  4081
      if (sr_semaphore.timedwait(0, 2 * NANOSECS_PER_MILLISEC)) {
b7bcf7497f93 8005849: JEP 167: Event-Based JVM Tracing
sla
parents: 17854
diff changeset
  4082
        if (osthread->sr.is_running()) {
b7bcf7497f93 8005849: JEP 167: Event-Based JVM Tracing
sla
parents: 17854
diff changeset
  4083
          return;
b7bcf7497f93 8005849: JEP 167: Event-Based JVM Tracing
sla
parents: 17854
diff changeset
  4084
        }
b7bcf7497f93 8005849: JEP 167: Event-Based JVM Tracing
sla
parents: 17854
diff changeset
  4085
      }
b7bcf7497f93 8005849: JEP 167: Event-Based JVM Tracing
sla
parents: 17854
diff changeset
  4086
    } else {
b7bcf7497f93 8005849: JEP 167: Event-Based JVM Tracing
sla
parents: 17854
diff changeset
  4087
      ShouldNotReachHere();
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4088
    }
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4089
  }
18025
b7bcf7497f93 8005849: JEP 167: Event-Based JVM Tracing
sla
parents: 17854
diff changeset
  4090
b7bcf7497f93 8005849: JEP 167: Event-Based JVM Tracing
sla
parents: 17854
diff changeset
  4091
  guarantee(osthread->sr.is_running(), "Must be running!");
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4092
}
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4093
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4094
///////////////////////////////////////////////////////////////////////////////////
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4095
// signal handling (except suspend/resume)
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4096
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4097
// This routine may be used by user applications as a "hook" to catch signals.
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4098
// The user-defined signal handler must pass unrecognized signals to this
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4099
// routine, and if it returns true (non-zero), then the signal handler must
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4100
// return immediately.  If the flag "abort_if_unrecognized" is true, then this
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4101
// routine will never retun false (zero), but instead will execute a VM panic
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4102
// routine kill the process.
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4103
//
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4104
// If this routine returns false, it is OK to call it again.  This allows
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4105
// the user-defined signal handler to perform checks either before or after
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4106
// the VM performs its own checks.  Naturally, the user code would be making
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4107
// a serious error if it tried to handle an exception (such as a null check
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4108
// or breakpoint) that the VM was generating for its own correct operation.
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4109
//
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4110
// This routine may recognize any of the following kinds of signals:
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4111
//    SIGBUS, SIGSEGV, SIGILL, SIGFPE, SIGQUIT, SIGPIPE, SIGXFSZ, SIGUSR1.
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4112
// It should be consulted by handlers for any of those signals.
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4113
//
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4114
// The caller of this routine must pass in the three arguments supplied
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4115
// to the function referred to in the "sa_sigaction" (not the "sa_handler")
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4116
// field of the structure passed to sigaction().  This routine assumes that
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4117
// the sa_flags field passed to sigaction() includes SA_SIGINFO and SA_RESTART.
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4118
//
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4119
// Note that the VM will print warnings if it detects conflicting signal
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4120
// handlers, unless invoked with the option "-XX:+AllowUserSignalHandlers".
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4121
//
26684
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
  4122
extern "C" JNIEXPORT int JVM_handle_linux_signal(int signo,
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
  4123
                                                 siginfo_t* siginfo,
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
  4124
                                                 void* ucontext,
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
  4125
                                                 int abort_if_unrecognized);
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4126
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4127
void signalHandler(int sig, siginfo_t* info, void* uc) {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4128
  assert(info != NULL && uc != NULL, "it must be old kernel");
15743
f708934a12e7 6749267: Signal handler should save/restore errno
hseigel
parents: 15475
diff changeset
  4129
  int orig_errno = errno;  // Preserve errno value over signal handler.
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4130
  JVM_handle_linux_signal(sig, info, uc, true);
15743
f708934a12e7 6749267: Signal handler should save/restore errno
hseigel
parents: 15475
diff changeset
  4131
  errno = orig_errno;
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4132
}
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4133
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4134
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4135
// This boolean allows users to forward their own non-matching signals
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4136
// to JVM_handle_linux_signal, harmlessly.
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4137
bool os::Linux::signal_handlers_are_installed = false;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4138
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4139
// For signal-chaining
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4140
struct sigaction os::Linux::sigact[MAXSIGNUM];
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4141
unsigned int os::Linux::sigs = 0;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4142
bool os::Linux::libjsig_is_loaded = false;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4143
typedef struct sigaction *(*get_signal_t)(int);
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4144
get_signal_t os::Linux::get_signal_action = NULL;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4145
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4146
struct sigaction* os::Linux::get_chained_signal_action(int sig) {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4147
  struct sigaction *actp = NULL;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4148
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4149
  if (libjsig_is_loaded) {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4150
    // Retrieve the old signal handler from libjsig
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4151
    actp = (*get_signal_action)(sig);
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4152
  }
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4153
  if (actp == NULL) {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4154
    // Retrieve the preinstalled signal handler from jvm
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4155
    actp = get_preinstalled_handler(sig);
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4156
  }
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4157
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4158
  return actp;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4159
}
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4160
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4161
static bool call_chained_handler(struct sigaction *actp, int sig,
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4162
                                 siginfo_t *siginfo, void *context) {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4163
  // Call the old signal handler
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4164
  if (actp->sa_handler == SIG_DFL) {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4165
    // It's more reasonable to let jvm treat it as an unexpected exception
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4166
    // instead of taking the default action.
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4167
    return false;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4168
  } else if (actp->sa_handler != SIG_IGN) {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4169
    if ((actp->sa_flags & SA_NODEFER) == 0) {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4170
      // automaticlly block the signal
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4171
      sigaddset(&(actp->sa_mask), sig);
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4172
    }
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4173
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4174
    sa_handler_t hand;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4175
    sa_sigaction_t sa;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4176
    bool siginfo_flag_set = (actp->sa_flags & SA_SIGINFO) != 0;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4177
    // retrieve the chained handler
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4178
    if (siginfo_flag_set) {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4179
      sa = actp->sa_sigaction;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4180
    } else {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4181
      hand = actp->sa_handler;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4182
    }
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4183
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4184
    if ((actp->sa_flags & SA_RESETHAND) != 0) {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4185
      actp->sa_handler = SIG_DFL;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4186
    }
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4187
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4188
    // try to honor the signal mask
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4189
    sigset_t oset;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4190
    pthread_sigmask(SIG_SETMASK, &(actp->sa_mask), &oset);
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4191
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4192
    // call into the chained handler
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4193
    if (siginfo_flag_set) {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4194
      (*sa)(sig, siginfo, context);
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4195
    } else {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4196
      (*hand)(sig);
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4197
    }
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4198
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4199
    // restore the signal mask
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4200
    pthread_sigmask(SIG_SETMASK, &oset, 0);
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4201
  }
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4202
  // Tell jvm's signal handler the signal is taken care of.
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4203
  return true;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4204
}
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4205
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4206
bool os::Linux::chained_handler(int sig, siginfo_t* siginfo, void* context) {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4207
  bool chained = false;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4208
  // signal-chaining
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4209
  if (UseSignalChaining) {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4210
    struct sigaction *actp = get_chained_signal_action(sig);
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4211
    if (actp != NULL) {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4212
      chained = call_chained_handler(actp, sig, siginfo, context);
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4213
    }
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4214
  }
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4215
  return chained;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4216
}
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4217
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4218
struct sigaction* os::Linux::get_preinstalled_handler(int sig) {
25064
244218e6ec0a 8046758: cleanup non-indent white space issues prior to Contended Locking cleanup bucket
dcubed
parents: 24931
diff changeset
  4219
  if ((((unsigned int)1 << sig) & sigs) != 0) {
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4220
    return &sigact[sig];
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4221
  }
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4222
  return NULL;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4223
}
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4224
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4225
void os::Linux::save_preinstalled_handler(int sig, struct sigaction& oldAct) {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4226
  assert(sig > 0 && sig < MAXSIGNUM, "vm signal out of expected range");
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4227
  sigact[sig] = oldAct;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4228
  sigs |= (unsigned int)1 << sig;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4229
}
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4230
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4231
// for diagnostic
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4232
int os::Linux::sigflags[MAXSIGNUM];
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4233
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4234
int os::Linux::get_our_sigflags(int sig) {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4235
  assert(sig > 0 && sig < MAXSIGNUM, "vm signal out of expected range");
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4236
  return sigflags[sig];
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4237
}
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4238
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4239
void os::Linux::set_our_sigflags(int sig, int flags) {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4240
  assert(sig > 0 && sig < MAXSIGNUM, "vm signal out of expected range");
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4241
  sigflags[sig] = flags;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4242
}
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4243
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4244
void os::Linux::set_signal_handler(int sig, bool set_installed) {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4245
  // Check for overwrite.
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4246
  struct sigaction oldAct;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4247
  sigaction(sig, (struct sigaction*)NULL, &oldAct);
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4248
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4249
  void* oldhand = oldAct.sa_sigaction
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4250
                ? CAST_FROM_FN_PTR(void*,  oldAct.sa_sigaction)
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4251
                : CAST_FROM_FN_PTR(void*,  oldAct.sa_handler);
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4252
  if (oldhand != CAST_FROM_FN_PTR(void*, SIG_DFL) &&
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4253
      oldhand != CAST_FROM_FN_PTR(void*, SIG_IGN) &&
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4254
      oldhand != CAST_FROM_FN_PTR(void*, (sa_sigaction_t)signalHandler)) {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4255
    if (AllowUserSignalHandlers || !set_installed) {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4256
      // Do not overwrite; user takes responsibility to forward to us.
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4257
      return;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4258
    } else if (UseSignalChaining) {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4259
      // save the old handler in jvm
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4260
      save_preinstalled_handler(sig, oldAct);
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4261
      // libjsig also interposes the sigaction() call below and saves the
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4262
      // old sigaction on it own.
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4263
    } else {
5403
6b0dd9c75dde 6888954: argument formatting for assert() and friends
jcoomes
parents: 5237
diff changeset
  4264
      fatal(err_msg("Encountered unexpected pre-existing sigaction handler "
6b0dd9c75dde 6888954: argument formatting for assert() and friends
jcoomes
parents: 5237
diff changeset
  4265
                    "%#lx for signal %d.", (long)oldhand, sig));
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4266
    }
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4267
  }
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4268
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4269
  struct sigaction sigAct;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4270
  sigfillset(&(sigAct.sa_mask));
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4271
  sigAct.sa_handler = SIG_DFL;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4272
  if (!set_installed) {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4273
    sigAct.sa_flags = SA_SIGINFO|SA_RESTART;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4274
  } else {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4275
    sigAct.sa_sigaction = signalHandler;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4276
    sigAct.sa_flags = SA_SIGINFO|SA_RESTART;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4277
  }
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4278
  // Save flags, which are set by ours
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4279
  assert(sig > 0 && sig < MAXSIGNUM, "vm signal out of expected range");
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4280
  sigflags[sig] = sigAct.sa_flags;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4281
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4282
  int ret = sigaction(sig, &sigAct, &oldAct);
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4283
  assert(ret == 0, "check");
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4284
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4285
  void* oldhand2  = oldAct.sa_sigaction
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4286
                  ? CAST_FROM_FN_PTR(void*, oldAct.sa_sigaction)
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4287
                  : CAST_FROM_FN_PTR(void*, oldAct.sa_handler);
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4288
  assert(oldhand2 == oldhand, "no concurrent signal handler installation");
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4289
}
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4290
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4291
// install signal handlers for signals that HotSpot needs to
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4292
// handle in order to support Java-level exception handling.
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4293
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4294
void os::Linux::install_signal_handlers() {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4295
  if (!signal_handlers_are_installed) {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4296
    signal_handlers_are_installed = true;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4297
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4298
    // signal-chaining
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4299
    typedef void (*signal_setting_t)();
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4300
    signal_setting_t begin_signal_setting = NULL;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4301
    signal_setting_t end_signal_setting = NULL;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4302
    begin_signal_setting = CAST_TO_FN_PTR(signal_setting_t,
26683
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  4303
                                          dlsym(RTLD_DEFAULT, "JVM_begin_signal_setting"));
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4304
    if (begin_signal_setting != NULL) {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4305
      end_signal_setting = CAST_TO_FN_PTR(signal_setting_t,
26683
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  4306
                                          dlsym(RTLD_DEFAULT, "JVM_end_signal_setting"));
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4307
      get_signal_action = CAST_TO_FN_PTR(get_signal_t,
26683
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  4308
                                         dlsym(RTLD_DEFAULT, "JVM_get_signal_action"));
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4309
      libjsig_is_loaded = true;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4310
      assert(UseSignalChaining, "should enable signal-chaining");
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4311
    }
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4312
    if (libjsig_is_loaded) {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4313
      // Tell libjsig jvm is setting signal handlers
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4314
      (*begin_signal_setting)();
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4315
    }
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4316
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4317
    set_signal_handler(SIGSEGV, true);
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4318
    set_signal_handler(SIGPIPE, true);
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4319
    set_signal_handler(SIGBUS, true);
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4320
    set_signal_handler(SIGILL, true);
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4321
    set_signal_handler(SIGFPE, true);
22848
c1a044cf0c07 8028470: PPC64 (part 214): linux: extend signal handler to catch SIGTRAP on ppc64.
goetz
parents: 22838
diff changeset
  4322
#if defined(PPC64)
c1a044cf0c07 8028470: PPC64 (part 214): linux: extend signal handler to catch SIGTRAP on ppc64.
goetz
parents: 22838
diff changeset
  4323
    set_signal_handler(SIGTRAP, true);
c1a044cf0c07 8028470: PPC64 (part 214): linux: extend signal handler to catch SIGTRAP on ppc64.
goetz
parents: 22838
diff changeset
  4324
#endif
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4325
    set_signal_handler(SIGXFSZ, true);
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4326
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4327
    if (libjsig_is_loaded) {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4328
      // Tell libjsig jvm finishes setting signal handlers
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4329
      (*end_signal_setting)();
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4330
    }
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4331
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4332
    // We don't activate signal checker if libjsig is in place, we trust ourselves
10561
bf51fe78a9ad 7051189: Need to suppress info message if -xcheck:jni used with libjsig.so
kevinw
parents: 10522
diff changeset
  4333
    // and if UserSignalHandler is installed all bets are off.
bf51fe78a9ad 7051189: Need to suppress info message if -xcheck:jni used with libjsig.so
kevinw
parents: 10522
diff changeset
  4334
    // Log that signal checking is off only if -verbose:jni is specified.
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4335
    if (CheckJNICalls) {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4336
      if (libjsig_is_loaded) {
10561
bf51fe78a9ad 7051189: Need to suppress info message if -xcheck:jni used with libjsig.so
kevinw
parents: 10522
diff changeset
  4337
        if (PrintJNIResolving) {
bf51fe78a9ad 7051189: Need to suppress info message if -xcheck:jni used with libjsig.so
kevinw
parents: 10522
diff changeset
  4338
          tty->print_cr("Info: libjsig is activated, all active signal checking is disabled");
bf51fe78a9ad 7051189: Need to suppress info message if -xcheck:jni used with libjsig.so
kevinw
parents: 10522
diff changeset
  4339
        }
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4340
        check_signals = false;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4341
      }
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4342
      if (AllowUserSignalHandlers) {
10561
bf51fe78a9ad 7051189: Need to suppress info message if -xcheck:jni used with libjsig.so
kevinw
parents: 10522
diff changeset
  4343
        if (PrintJNIResolving) {
bf51fe78a9ad 7051189: Need to suppress info message if -xcheck:jni used with libjsig.so
kevinw
parents: 10522
diff changeset
  4344
          tty->print_cr("Info: AllowUserSignalHandlers is activated, all active signal checking is disabled");
bf51fe78a9ad 7051189: Need to suppress info message if -xcheck:jni used with libjsig.so
kevinw
parents: 10522
diff changeset
  4345
        }
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4346
        check_signals = false;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4347
      }
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4348
    }
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4349
  }
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4350
}
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4351
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4352
// This is the fastest way to get thread cpu time on Linux.
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4353
// Returns cpu time (user+sys) for any thread, not only for current.
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4354
// POSIX compliant clocks are implemented in the kernels 2.6.16+.
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4355
// It might work on 2.6.10+ with a special kernel/glibc patch.
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4356
// For reference, please, see IEEE Std 1003.1-2004:
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4357
//   http://www.unix.org/single_unix_specification
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4358
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4359
jlong os::Linux::fast_thread_cpu_time(clockid_t clockid) {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4360
  struct timespec tp;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4361
  int rc = os::Linux::clock_gettime(clockid, &tp);
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4362
  assert(rc == 0, "clock_gettime is expected to return 0 code");
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4363
11251
e29da6b5622b 7117303: VM uses non-monotonic time source and complains that it is non-monotonic
johnc
parents: 11161
diff changeset
  4364
  return (tp.tv_sec * NANOSECS_PER_SEC) + tp.tv_nsec;
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4365
}
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4366
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4367
/////
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4368
// glibc on Linux platform uses non-documented flag
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4369
// to indicate, that some special sort of signal
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4370
// trampoline is used.
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4371
// We will never set this flag, and we should
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4372
// ignore this flag in our diagnostic
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4373
#ifdef SIGNIFICANT_SIGNAL_MASK
26684
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
  4374
  #undef SIGNIFICANT_SIGNAL_MASK
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4375
#endif
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4376
#define SIGNIFICANT_SIGNAL_MASK (~0x04000000)
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4377
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4378
static const char* get_signal_handler_name(address handler,
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4379
                                           char* buf, int buflen) {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4380
  int offset;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4381
  bool found = os::dll_address_to_library_name(handler, buf, buflen, &offset);
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4382
  if (found) {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4383
    // skip directory names
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4384
    const char *p1, *p2;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4385
    p1 = buf;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4386
    size_t len = strlen(os::file_separator());
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4387
    while ((p2 = strstr(p1, os::file_separator())) != NULL) p1 = p2 + len;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4388
    jio_snprintf(buf, buflen, "%s+0x%x", p1, offset);
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4389
  } else {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4390
    jio_snprintf(buf, buflen, PTR_FORMAT, handler);
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4391
  }
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4392
  return buf;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4393
}
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4394
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4395
static void print_signal_handler(outputStream* st, int sig,
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4396
                                 char* buf, size_t buflen) {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4397
  struct sigaction sa;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4398
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4399
  sigaction(sig, NULL, &sa);
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4400
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4401
  // See comment for SIGNIFICANT_SIGNAL_MASK define
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4402
  sa.sa_flags &= SIGNIFICANT_SIGNAL_MASK;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4403
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4404
  st->print("%s: ", os::exception_name(sig, buf, buflen));
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4405
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4406
  address handler = (sa.sa_flags & SA_SIGINFO)
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4407
    ? CAST_FROM_FN_PTR(address, sa.sa_sigaction)
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4408
    : CAST_FROM_FN_PTR(address, sa.sa_handler);
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4409
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4410
  if (handler == CAST_FROM_FN_PTR(address, SIG_DFL)) {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4411
    st->print("SIG_DFL");
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4412
  } else if (handler == CAST_FROM_FN_PTR(address, SIG_IGN)) {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4413
    st->print("SIG_IGN");
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4414
  } else {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4415
    st->print("[%s]", get_signal_handler_name(handler, buf, buflen));
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4416
  }
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4417
22826
3ee6886e718d 8020775: PPC64 (part 12): posix signal printing
goetz
parents: 22821
diff changeset
  4418
  st->print(", sa_mask[0]=");
3ee6886e718d 8020775: PPC64 (part 12): posix signal printing
goetz
parents: 22821
diff changeset
  4419
  os::Posix::print_signal_set_short(st, &sa.sa_mask);
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4420
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4421
  address rh = VMError::get_resetted_sighandler(sig);
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4422
  // May be, handler was resetted by VMError?
25064
244218e6ec0a 8046758: cleanup non-indent white space issues prior to Contended Locking cleanup bucket
dcubed
parents: 24931
diff changeset
  4423
  if (rh != NULL) {
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4424
    handler = rh;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4425
    sa.sa_flags = VMError::get_resetted_sigflags(sig) & SIGNIFICANT_SIGNAL_MASK;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4426
  }
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4427
22826
3ee6886e718d 8020775: PPC64 (part 12): posix signal printing
goetz
parents: 22821
diff changeset
  4428
  st->print(", sa_flags=");
3ee6886e718d 8020775: PPC64 (part 12): posix signal printing
goetz
parents: 22821
diff changeset
  4429
  os::Posix::print_sa_flags(st, sa.sa_flags);
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4430
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4431
  // Check: is it our handler?
25064
244218e6ec0a 8046758: cleanup non-indent white space issues prior to Contended Locking cleanup bucket
dcubed
parents: 24931
diff changeset
  4432
  if (handler == CAST_FROM_FN_PTR(address, (sa_sigaction_t)signalHandler) ||
26683
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  4433
      handler == CAST_FROM_FN_PTR(address, (sa_sigaction_t)SR_handler)) {
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4434
    // It is our signal handler
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4435
    // check for flags, reset system-used one!
25064
244218e6ec0a 8046758: cleanup non-indent white space issues prior to Contended Locking cleanup bucket
dcubed
parents: 24931
diff changeset
  4436
    if ((int)sa.sa_flags != os::Linux::get_our_sigflags(sig)) {
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4437
      st->print(
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4438
                ", flags was changed from " PTR32_FORMAT ", consider using jsig library",
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4439
                os::Linux::get_our_sigflags(sig));
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4440
    }
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4441
  }
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4442
  st->cr();
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4443
}
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4444
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4445
26684
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
  4446
#define DO_SIGNAL_CHECK(sig)                      \
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
  4447
  do {                                            \
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
  4448
    if (!sigismember(&check_signal_done, sig)) {  \
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
  4449
      os::Linux::check_signal_handler(sig);       \
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
  4450
    }                                             \
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
  4451
  } while (0)
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4452
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4453
// This method is a periodic task to check for misbehaving JNI applications
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4454
// under CheckJNI, we can add any periodic checks here
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4455
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4456
void os::run_periodic_checks() {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4457
  if (check_signals == false) return;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4458
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4459
  // SEGV and BUS if overridden could potentially prevent
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4460
  // generation of hs*.log in the event of a crash, debugging
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4461
  // such a case can be very challenging, so we absolutely
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4462
  // check the following for a good measure:
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4463
  DO_SIGNAL_CHECK(SIGSEGV);
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4464
  DO_SIGNAL_CHECK(SIGILL);
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4465
  DO_SIGNAL_CHECK(SIGFPE);
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4466
  DO_SIGNAL_CHECK(SIGBUS);
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4467
  DO_SIGNAL_CHECK(SIGPIPE);
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4468
  DO_SIGNAL_CHECK(SIGXFSZ);
22848
c1a044cf0c07 8028470: PPC64 (part 214): linux: extend signal handler to catch SIGTRAP on ppc64.
goetz
parents: 22838
diff changeset
  4469
#if defined(PPC64)
c1a044cf0c07 8028470: PPC64 (part 214): linux: extend signal handler to catch SIGTRAP on ppc64.
goetz
parents: 22838
diff changeset
  4470
  DO_SIGNAL_CHECK(SIGTRAP);
c1a044cf0c07 8028470: PPC64 (part 214): linux: extend signal handler to catch SIGTRAP on ppc64.
goetz
parents: 22838
diff changeset
  4471
#endif
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4472
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4473
  // ReduceSignalUsage allows the user to override these handlers
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4474
  // see comments at the very top and jvm_solaris.h
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4475
  if (!ReduceSignalUsage) {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4476
    DO_SIGNAL_CHECK(SHUTDOWN1_SIGNAL);
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4477
    DO_SIGNAL_CHECK(SHUTDOWN2_SIGNAL);
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4478
    DO_SIGNAL_CHECK(SHUTDOWN3_SIGNAL);
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4479
    DO_SIGNAL_CHECK(BREAK_SIGNAL);
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4480
  }
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4481
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4482
  DO_SIGNAL_CHECK(SR_signum);
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4483
  DO_SIGNAL_CHECK(INTERRUPT_SIGNAL);
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4484
}
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4485
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4486
typedef int (*os_sigaction_t)(int, const struct sigaction *, struct sigaction *);
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4487
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4488
static os_sigaction_t os_sigaction = NULL;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4489
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4490
void os::Linux::check_signal_handler(int sig) {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4491
  char buf[O_BUFLEN];
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4492
  address jvmHandler = NULL;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4493
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4494
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4495
  struct sigaction act;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4496
  if (os_sigaction == NULL) {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4497
    // only trust the default sigaction, in case it has been interposed
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4498
    os_sigaction = (os_sigaction_t)dlsym(RTLD_DEFAULT, "sigaction");
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4499
    if (os_sigaction == NULL) return;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4500
  }
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4501
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4502
  os_sigaction(sig, (struct sigaction*)NULL, &act);
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4503
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4504
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4505
  act.sa_flags &= SIGNIFICANT_SIGNAL_MASK;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4506
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4507
  address thisHandler = (act.sa_flags & SA_SIGINFO)
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4508
    ? CAST_FROM_FN_PTR(address, act.sa_sigaction)
25064
244218e6ec0a 8046758: cleanup non-indent white space issues prior to Contended Locking cleanup bucket
dcubed
parents: 24931
diff changeset
  4509
    : CAST_FROM_FN_PTR(address, act.sa_handler);
244218e6ec0a 8046758: cleanup non-indent white space issues prior to Contended Locking cleanup bucket
dcubed
parents: 24931
diff changeset
  4510
244218e6ec0a 8046758: cleanup non-indent white space issues prior to Contended Locking cleanup bucket
dcubed
parents: 24931
diff changeset
  4511
244218e6ec0a 8046758: cleanup non-indent white space issues prior to Contended Locking cleanup bucket
dcubed
parents: 24931
diff changeset
  4512
  switch (sig) {
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4513
  case SIGSEGV:
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4514
  case SIGBUS:
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4515
  case SIGFPE:
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4516
  case SIGPIPE:
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4517
  case SIGILL:
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4518
  case SIGXFSZ:
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4519
    jvmHandler = CAST_FROM_FN_PTR(address, (sa_sigaction_t)signalHandler);
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4520
    break;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4521
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4522
  case SHUTDOWN1_SIGNAL:
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4523
  case SHUTDOWN2_SIGNAL:
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4524
  case SHUTDOWN3_SIGNAL:
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4525
  case BREAK_SIGNAL:
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4526
    jvmHandler = (address)user_handler();
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4527
    break;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4528
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4529
  case INTERRUPT_SIGNAL:
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4530
    jvmHandler = CAST_FROM_FN_PTR(address, SIG_DFL);
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4531
    break;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4532
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4533
  default:
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4534
    if (sig == SR_signum) {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4535
      jvmHandler = CAST_FROM_FN_PTR(address, (sa_sigaction_t)SR_handler);
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4536
    } else {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4537
      return;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4538
    }
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4539
    break;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4540
  }
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4541
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4542
  if (thisHandler != jvmHandler) {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4543
    tty->print("Warning: %s handler ", exception_name(sig, buf, O_BUFLEN));
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4544
    tty->print("expected:%s", get_signal_handler_name(jvmHandler, buf, O_BUFLEN));
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4545
    tty->print_cr("  found:%s", get_signal_handler_name(thisHandler, buf, O_BUFLEN));
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4546
    // No need to check this sig any longer
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4547
    sigaddset(&check_signal_done, sig);
23444
b5457261694b 6536943: Bogus -Xcheck:jni warning for SIG_INT action for SIGINT in JVM started from non-interactive shell
minqi
parents: 23185
diff changeset
  4548
    // Running under non-interactive shell, SHUTDOWN2_SIGNAL will be reassigned SIG_IGN
b5457261694b 6536943: Bogus -Xcheck:jni warning for SIG_INT action for SIGINT in JVM started from non-interactive shell
minqi
parents: 23185
diff changeset
  4549
    if (sig == SHUTDOWN2_SIGNAL && !isatty(fileno(stdin))) {
b5457261694b 6536943: Bogus -Xcheck:jni warning for SIG_INT action for SIGINT in JVM started from non-interactive shell
minqi
parents: 23185
diff changeset
  4550
      tty->print_cr("Running in non-interactive shell, %s handler is replaced by shell",
b5457261694b 6536943: Bogus -Xcheck:jni warning for SIG_INT action for SIGINT in JVM started from non-interactive shell
minqi
parents: 23185
diff changeset
  4551
                    exception_name(sig, buf, O_BUFLEN));
b5457261694b 6536943: Bogus -Xcheck:jni warning for SIG_INT action for SIGINT in JVM started from non-interactive shell
minqi
parents: 23185
diff changeset
  4552
    }
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4553
  } else if(os::Linux::get_our_sigflags(sig) != 0 && (int)act.sa_flags != os::Linux::get_our_sigflags(sig)) {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4554
    tty->print("Warning: %s handler flags ", exception_name(sig, buf, O_BUFLEN));
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4555
    tty->print("expected:" PTR32_FORMAT, os::Linux::get_our_sigflags(sig));
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4556
    tty->print_cr("  found:" PTR32_FORMAT, act.sa_flags);
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4557
    // No need to check this sig any longer
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4558
    sigaddset(&check_signal_done, sig);
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4559
  }
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4560
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4561
  // Dump all the signal
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4562
  if (sigismember(&check_signal_done, sig)) {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4563
    print_signal_handlers(tty, buf, O_BUFLEN);
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4564
  }
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4565
}
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4566
26684
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
  4567
extern void report_error(char* file_name, int line_no, char* title,
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
  4568
                         char* format, ...);
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4569
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4570
extern bool signal_name(int signo, char* buf, size_t len);
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4571
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4572
const char* os::exception_name(int exception_code, char* buf, size_t size) {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4573
  if (0 < exception_code && exception_code <= SIGRTMAX) {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4574
    // signal
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4575
    if (!signal_name(exception_code, buf, size)) {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4576
      jio_snprintf(buf, size, "SIG%d", exception_code);
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4577
    }
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4578
    return buf;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4579
  } else {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4580
    return NULL;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4581
  }
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4582
}
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4583
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4584
// this is called _before_ the most of global arguments have been parsed
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4585
void os::init(void) {
26684
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
  4586
  char dummy;   // used to get a guess on initial stack address
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4587
//  first_hrtime = gethrtime();
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4588
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4589
  // With LinuxThreads the JavaMain thread pid (primordial thread)
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4590
  // is different than the pid of the java launcher thread.
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4591
  // So, on Linux, the launcher thread pid is passed to the VM
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4592
  // via the sun.java.launcher.pid property.
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4593
  // Use this property instead of getpid() if it was correctly passed.
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4594
  // See bug 6351349.
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4595
  pid_t java_launcher_pid = (pid_t) Arguments::sun_java_launcher_pid();
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4596
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4597
  _initial_pid = (java_launcher_pid > 0) ? java_launcher_pid : getpid();
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4598
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4599
  clock_tics_per_sec = sysconf(_SC_CLK_TCK);
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4600
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4601
  init_random(1234567);
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4602
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4603
  ThreadCritical::initialize();
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4604
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4605
  Linux::set_page_size(sysconf(_SC_PAGESIZE));
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4606
  if (Linux::page_size() == -1) {
5403
6b0dd9c75dde 6888954: argument formatting for assert() and friends
jcoomes
parents: 5237
diff changeset
  4607
    fatal(err_msg("os_linux.cpp: os::init: sysconf failed (%s)",
6b0dd9c75dde 6888954: argument formatting for assert() and friends
jcoomes
parents: 5237
diff changeset
  4608
                  strerror(errno)));
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4609
  }
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4610
  init_page_sizes((size_t) Linux::page_size());
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4611
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4612
  Linux::initialize_system_info();
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4613
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4614
  // main_thread points to the aboriginal thread
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4615
  Linux::_main_thread = pthread_self();
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4616
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4617
  Linux::clock_init();
21185
9d53434b1ef5 8027294: Prepare hotspot for non TOD based uptime counter
jbachorik
parents: 20408
diff changeset
  4618
  initial_time_count = javaTimeNanos();
19964
a3a04a9d29ac 6900441: PlatformEvent.park(millis) on Linux could still be affected by changes to the time-of-day clock
dholmes
parents: 19732
diff changeset
  4619
a3a04a9d29ac 6900441: PlatformEvent.park(millis) on Linux could still be affected by changes to the time-of-day clock
dholmes
parents: 19732
diff changeset
  4620
  // pthread_condattr initialization for monotonic clock
a3a04a9d29ac 6900441: PlatformEvent.park(millis) on Linux could still be affected by changes to the time-of-day clock
dholmes
parents: 19732
diff changeset
  4621
  int status;
a3a04a9d29ac 6900441: PlatformEvent.park(millis) on Linux could still be affected by changes to the time-of-day clock
dholmes
parents: 19732
diff changeset
  4622
  pthread_condattr_t* _condattr = os::Linux::condAttr();
a3a04a9d29ac 6900441: PlatformEvent.park(millis) on Linux could still be affected by changes to the time-of-day clock
dholmes
parents: 19732
diff changeset
  4623
  if ((status = pthread_condattr_init(_condattr)) != 0) {
a3a04a9d29ac 6900441: PlatformEvent.park(millis) on Linux could still be affected by changes to the time-of-day clock
dholmes
parents: 19732
diff changeset
  4624
    fatal(err_msg("pthread_condattr_init: %s", strerror(status)));
a3a04a9d29ac 6900441: PlatformEvent.park(millis) on Linux could still be affected by changes to the time-of-day clock
dholmes
parents: 19732
diff changeset
  4625
  }
a3a04a9d29ac 6900441: PlatformEvent.park(millis) on Linux could still be affected by changes to the time-of-day clock
dholmes
parents: 19732
diff changeset
  4626
  // Only set the clock if CLOCK_MONOTONIC is available
22891
1f5d1fff23fa 6546236: Thread interrupt() of Thread.sleep() can be lost on Solaris due to race with signal handler
fparain
parents: 22749
diff changeset
  4627
  if (os::supports_monotonic_clock()) {
19964
a3a04a9d29ac 6900441: PlatformEvent.park(millis) on Linux could still be affected by changes to the time-of-day clock
dholmes
parents: 19732
diff changeset
  4628
    if ((status = pthread_condattr_setclock(_condattr, CLOCK_MONOTONIC)) != 0) {
a3a04a9d29ac 6900441: PlatformEvent.park(millis) on Linux could still be affected by changes to the time-of-day clock
dholmes
parents: 19732
diff changeset
  4629
      if (status == EINVAL) {
a3a04a9d29ac 6900441: PlatformEvent.park(millis) on Linux could still be affected by changes to the time-of-day clock
dholmes
parents: 19732
diff changeset
  4630
        warning("Unable to use monotonic clock with relative timed-waits" \
a3a04a9d29ac 6900441: PlatformEvent.park(millis) on Linux could still be affected by changes to the time-of-day clock
dholmes
parents: 19732
diff changeset
  4631
                " - changes to the time-of-day clock may have adverse affects");
a3a04a9d29ac 6900441: PlatformEvent.park(millis) on Linux could still be affected by changes to the time-of-day clock
dholmes
parents: 19732
diff changeset
  4632
      } else {
a3a04a9d29ac 6900441: PlatformEvent.park(millis) on Linux could still be affected by changes to the time-of-day clock
dholmes
parents: 19732
diff changeset
  4633
        fatal(err_msg("pthread_condattr_setclock: %s", strerror(status)));
a3a04a9d29ac 6900441: PlatformEvent.park(millis) on Linux could still be affected by changes to the time-of-day clock
dholmes
parents: 19732
diff changeset
  4634
      }
a3a04a9d29ac 6900441: PlatformEvent.park(millis) on Linux could still be affected by changes to the time-of-day clock
dholmes
parents: 19732
diff changeset
  4635
    }
a3a04a9d29ac 6900441: PlatformEvent.park(millis) on Linux could still be affected by changes to the time-of-day clock
dholmes
parents: 19732
diff changeset
  4636
  }
a3a04a9d29ac 6900441: PlatformEvent.park(millis) on Linux could still be affected by changes to the time-of-day clock
dholmes
parents: 19732
diff changeset
  4637
  // else it defaults to CLOCK_REALTIME
a3a04a9d29ac 6900441: PlatformEvent.park(millis) on Linux could still be affected by changes to the time-of-day clock
dholmes
parents: 19732
diff changeset
  4638
17090
98a9d26f1ef1 8013398: Adjust number of stack guard pages on systems with large memory page size
vladidan
parents: 17083
diff changeset
  4639
  // If the pagesize of the VM is greater than 8K determine the appropriate
98a9d26f1ef1 8013398: Adjust number of stack guard pages on systems with large memory page size
vladidan
parents: 17083
diff changeset
  4640
  // number of initial guard pages.  The user can change this with the
98a9d26f1ef1 8013398: Adjust number of stack guard pages on systems with large memory page size
vladidan
parents: 17083
diff changeset
  4641
  // command line arguments, if needed.
98a9d26f1ef1 8013398: Adjust number of stack guard pages on systems with large memory page size
vladidan
parents: 17083
diff changeset
  4642
  if (vm_page_size() > (int)Linux::vm_default_page_size()) {
98a9d26f1ef1 8013398: Adjust number of stack guard pages on systems with large memory page size
vladidan
parents: 17083
diff changeset
  4643
    StackYellowPages = 1;
98a9d26f1ef1 8013398: Adjust number of stack guard pages on systems with large memory page size
vladidan
parents: 17083
diff changeset
  4644
    StackRedPages = 1;
98a9d26f1ef1 8013398: Adjust number of stack guard pages on systems with large memory page size
vladidan
parents: 17083
diff changeset
  4645
    StackShadowPages = round_to((StackShadowPages*Linux::vm_default_page_size()), vm_page_size()) / vm_page_size();
98a9d26f1ef1 8013398: Adjust number of stack guard pages on systems with large memory page size
vladidan
parents: 17083
diff changeset
  4646
  }
27164
6523fa019ffa 7102541: RFE: os::set_native_thread_name() cleanups
sla
parents: 27157
diff changeset
  4647
6523fa019ffa 7102541: RFE: os::set_native_thread_name() cleanups
sla
parents: 27157
diff changeset
  4648
  // retrieve entry point for pthread_setname_np
6523fa019ffa 7102541: RFE: os::set_native_thread_name() cleanups
sla
parents: 27157
diff changeset
  4649
  Linux::_pthread_setname_np =
6523fa019ffa 7102541: RFE: os::set_native_thread_name() cleanups
sla
parents: 27157
diff changeset
  4650
    (int(*)(pthread_t, const char*))dlsym(RTLD_DEFAULT, "pthread_setname_np");
6523fa019ffa 7102541: RFE: os::set_native_thread_name() cleanups
sla
parents: 27157
diff changeset
  4651
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4652
}
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4653
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4654
// To install functions for atexit system call
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4655
extern "C" {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4656
  static void perfMemory_exit_helper() {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4657
    perfMemory_exit();
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4658
  }
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4659
}
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4660
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4661
// this is called _after_ the global arguments have been parsed
26684
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
  4662
jint os::init_2(void) {
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4663
  Linux::fast_thread_clock_init();
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4664
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4665
  // Allocate a single page and mark it as readable for safepoint polling
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4666
  address polling_page = (address) ::mmap(NULL, Linux::page_size(), PROT_READ, MAP_PRIVATE|MAP_ANONYMOUS, -1, 0);
25064
244218e6ec0a 8046758: cleanup non-indent white space issues prior to Contended Locking cleanup bucket
dcubed
parents: 24931
diff changeset
  4667
  guarantee(polling_page != MAP_FAILED, "os::init_2: failed to allocate polling page");
244218e6ec0a 8046758: cleanup non-indent white space issues prior to Contended Locking cleanup bucket
dcubed
parents: 24931
diff changeset
  4668
244218e6ec0a 8046758: cleanup non-indent white space issues prior to Contended Locking cleanup bucket
dcubed
parents: 24931
diff changeset
  4669
  os::set_polling_page(polling_page);
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4670
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4671
#ifndef PRODUCT
26684
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
  4672
  if (Verbose && PrintMiscellaneous) {
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
  4673
    tty->print("[SafePoint Polling address: " INTPTR_FORMAT "]\n",
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
  4674
               (intptr_t)polling_page);
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
  4675
  }
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4676
#endif
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4677
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4678
  if (!UseMembar) {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4679
    address mem_serialize_page = (address) ::mmap(NULL, Linux::page_size(), PROT_READ | PROT_WRITE, MAP_PRIVATE|MAP_ANONYMOUS, -1, 0);
25064
244218e6ec0a 8046758: cleanup non-indent white space issues prior to Contended Locking cleanup bucket
dcubed
parents: 24931
diff changeset
  4680
    guarantee(mem_serialize_page != MAP_FAILED, "mmap Failed for memory serialize page");
244218e6ec0a 8046758: cleanup non-indent white space issues prior to Contended Locking cleanup bucket
dcubed
parents: 24931
diff changeset
  4681
    os::set_memory_serialize_page(mem_serialize_page);
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4682
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4683
#ifndef PRODUCT
26684
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
  4684
    if (Verbose && PrintMiscellaneous) {
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
  4685
      tty->print("[Memory Serialize  Page address: " INTPTR_FORMAT "]\n",
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
  4686
                 (intptr_t)mem_serialize_page);
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
  4687
    }
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4688
#endif
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4689
  }
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4690
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4691
  // initialize suspend/resume support - must do this before signal_sets_init()
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4692
  if (SR_initialize() != 0) {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4693
    perror("SR_initialize failed");
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4694
    return JNI_ERR;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4695
  }
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4696
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4697
  Linux::signal_sets_init();
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4698
  Linux::install_signal_handlers();
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4699
6964
6e45ffa3bccf 6983240: guarantee((Solaris::min_stack_allowed >= (StackYellowPages+StackRedPages...) wrong
coleenp
parents: 6962
diff changeset
  4700
  // Check minimum allowable stack size for thread creation and to initialize
6e45ffa3bccf 6983240: guarantee((Solaris::min_stack_allowed >= (StackYellowPages+StackRedPages...) wrong
coleenp
parents: 6962
diff changeset
  4701
  // the java system classes, including StackOverflowError - depends on page
6e45ffa3bccf 6983240: guarantee((Solaris::min_stack_allowed >= (StackYellowPages+StackRedPages...) wrong
coleenp
parents: 6962
diff changeset
  4702
  // size.  Add a page for compiler2 recursion in main thread.
6e45ffa3bccf 6983240: guarantee((Solaris::min_stack_allowed >= (StackYellowPages+StackRedPages...) wrong
coleenp
parents: 6962
diff changeset
  4703
  // Add in 2*BytesPerWord times page size to account for VM stack during
6e45ffa3bccf 6983240: guarantee((Solaris::min_stack_allowed >= (StackYellowPages+StackRedPages...) wrong
coleenp
parents: 6962
diff changeset
  4704
  // class initialization depending on 32 or 64 bit VM.
6e45ffa3bccf 6983240: guarantee((Solaris::min_stack_allowed >= (StackYellowPages+StackRedPages...) wrong
coleenp
parents: 6962
diff changeset
  4705
  os::Linux::min_stack_allowed = MAX2(os::Linux::min_stack_allowed,
26683
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  4706
                                      (size_t)(StackYellowPages+StackRedPages+StackShadowPages) * Linux::page_size() +
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  4707
                                      (2*BytesPerWord COMPILER2_PRESENT(+1)) * Linux::vm_default_page_size());
6964
6e45ffa3bccf 6983240: guarantee((Solaris::min_stack_allowed >= (StackYellowPages+StackRedPages...) wrong
coleenp
parents: 6962
diff changeset
  4708
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4709
  size_t threadStackSizeInBytes = ThreadStackSize * K;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4710
  if (threadStackSizeInBytes != 0 &&
6964
6e45ffa3bccf 6983240: guarantee((Solaris::min_stack_allowed >= (StackYellowPages+StackRedPages...) wrong
coleenp
parents: 6962
diff changeset
  4711
      threadStackSizeInBytes < os::Linux::min_stack_allowed) {
26683
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  4712
    tty->print_cr("\nThe stack size specified is too small, "
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  4713
                  "Specify at least %dk",
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  4714
                  os::Linux::min_stack_allowed/ K);
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  4715
    return JNI_ERR;
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4716
  }
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4717
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4718
  // Make the stack size a multiple of the page size so that
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4719
  // the yellow/red zones can be guarded.
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4720
  JavaThread::set_stack_size_at_create(round_to(threadStackSizeInBytes,
26683
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  4721
                                                vm_page_size()));
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4722
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4723
  Linux::capture_initial_stack(JavaThread::stack_size_at_create());
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4724
20279
7ffa08fef52a 8023956: Provide a work-around to broken Linux 32 bit "Exec Shield" using CS for NX emulation (crashing with SI_KERNEL)
dsimms
parents: 20005
diff changeset
  4725
#if defined(IA32)
7ffa08fef52a 8023956: Provide a work-around to broken Linux 32 bit "Exec Shield" using CS for NX emulation (crashing with SI_KERNEL)
dsimms
parents: 20005
diff changeset
  4726
  workaround_expand_exec_shield_cs_limit();
7ffa08fef52a 8023956: Provide a work-around to broken Linux 32 bit "Exec Shield" using CS for NX emulation (crashing with SI_KERNEL)
dsimms
parents: 20005
diff changeset
  4727
#endif
7ffa08fef52a 8023956: Provide a work-around to broken Linux 32 bit "Exec Shield" using CS for NX emulation (crashing with SI_KERNEL)
dsimms
parents: 20005
diff changeset
  4728
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4729
  Linux::libpthread_init();
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4730
  if (PrintMiscellaneous && (Verbose || WizardMode)) {
26683
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  4731
    tty->print_cr("[HotSpot is running with %s, %s(%s)]\n",
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  4732
                  Linux::glibc_version(), Linux::libpthread_version(),
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  4733
                  Linux::is_floating_stack() ? "floating stack" : "fixed stack");
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4734
  }
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4735
388
bcc631c5bbec 6684395: Port NUMA-aware allocator to linux
iveresov
parents: 252
diff changeset
  4736
  if (UseNUMA) {
1615
b46d9f19bde2 6779436: NUMA allocator: libnuma expects certain size of the buffer in numa_node_to_cpus()
iveresov
parents: 1388
diff changeset
  4737
    if (!Linux::libnuma_init()) {
b46d9f19bde2 6779436: NUMA allocator: libnuma expects certain size of the buffer in numa_node_to_cpus()
iveresov
parents: 1388
diff changeset
  4738
      UseNUMA = false;
b46d9f19bde2 6779436: NUMA allocator: libnuma expects certain size of the buffer in numa_node_to_cpus()
iveresov
parents: 1388
diff changeset
  4739
    } else {
b46d9f19bde2 6779436: NUMA allocator: libnuma expects certain size of the buffer in numa_node_to_cpus()
iveresov
parents: 1388
diff changeset
  4740
      if ((Linux::numa_max_node() < 1)) {
b46d9f19bde2 6779436: NUMA allocator: libnuma expects certain size of the buffer in numa_node_to_cpus()
iveresov
parents: 1388
diff changeset
  4741
        // There's only one node(they start from 0), disable NUMA.
b46d9f19bde2 6779436: NUMA allocator: libnuma expects certain size of the buffer in numa_node_to_cpus()
iveresov
parents: 1388
diff changeset
  4742
        UseNUMA = false;
b46d9f19bde2 6779436: NUMA allocator: libnuma expects certain size of the buffer in numa_node_to_cpus()
iveresov
parents: 1388
diff changeset
  4743
      }
b46d9f19bde2 6779436: NUMA allocator: libnuma expects certain size of the buffer in numa_node_to_cpus()
iveresov
parents: 1388
diff changeset
  4744
    }
19546
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  4745
    // With SHM and HugeTLBFS large pages we cannot uncommit a page, so there's no way
9341
347fa5cdbd39 7037939: NUMA: Disable adaptive resizing if SHM large pages are used
iveresov
parents: 9339
diff changeset
  4746
    // we can make the adaptive lgrp chunk resizing work. If the user specified
19546
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  4747
    // both UseNUMA and UseLargePages (or UseSHM/UseHugeTLBFS) on the command line - warn and
9341
347fa5cdbd39 7037939: NUMA: Disable adaptive resizing if SHM large pages are used
iveresov
parents: 9339
diff changeset
  4748
    // disable adaptive resizing.
19546
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  4749
    if (UseNUMA && UseLargePages && !can_commit_large_page_memory()) {
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  4750
      if (FLAG_IS_DEFAULT(UseNUMA)) {
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  4751
        UseNUMA = false;
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  4752
      } else {
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  4753
        if (FLAG_IS_DEFAULT(UseLargePages) &&
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  4754
            FLAG_IS_DEFAULT(UseSHM) &&
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  4755
            FLAG_IS_DEFAULT(UseHugeTLBFS)) {
9341
347fa5cdbd39 7037939: NUMA: Disable adaptive resizing if SHM large pages are used
iveresov
parents: 9339
diff changeset
  4756
          UseLargePages = false;
347fa5cdbd39 7037939: NUMA: Disable adaptive resizing if SHM large pages are used
iveresov
parents: 9339
diff changeset
  4757
        } else {
19546
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  4758
          warning("UseNUMA is not fully compatible with SHM/HugeTLBFS large pages, disabling adaptive resizing");
9341
347fa5cdbd39 7037939: NUMA: Disable adaptive resizing if SHM large pages are used
iveresov
parents: 9339
diff changeset
  4759
          UseAdaptiveSizePolicy = false;
347fa5cdbd39 7037939: NUMA: Disable adaptive resizing if SHM large pages are used
iveresov
parents: 9339
diff changeset
  4760
          UseAdaptiveNUMAChunkSizing = false;
347fa5cdbd39 7037939: NUMA: Disable adaptive resizing if SHM large pages are used
iveresov
parents: 9339
diff changeset
  4761
        }
347fa5cdbd39 7037939: NUMA: Disable adaptive resizing if SHM large pages are used
iveresov
parents: 9339
diff changeset
  4762
      }
347fa5cdbd39 7037939: NUMA: Disable adaptive resizing if SHM large pages are used
iveresov
parents: 9339
diff changeset
  4763
    }
1615
b46d9f19bde2 6779436: NUMA allocator: libnuma expects certain size of the buffer in numa_node_to_cpus()
iveresov
parents: 1388
diff changeset
  4764
    if (!UseNUMA && ForceNUMA) {
b46d9f19bde2 6779436: NUMA allocator: libnuma expects certain size of the buffer in numa_node_to_cpus()
iveresov
parents: 1388
diff changeset
  4765
      UseNUMA = true;
b46d9f19bde2 6779436: NUMA allocator: libnuma expects certain size of the buffer in numa_node_to_cpus()
iveresov
parents: 1388
diff changeset
  4766
    }
388
bcc631c5bbec 6684395: Port NUMA-aware allocator to linux
iveresov
parents: 252
diff changeset
  4767
  }
bcc631c5bbec 6684395: Port NUMA-aware allocator to linux
iveresov
parents: 252
diff changeset
  4768
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4769
  if (MaxFDLimit) {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4770
    // set the number of file descriptors to max. print out error
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4771
    // if getrlimit/setrlimit fails but continue regardless.
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4772
    struct rlimit nbr_files;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4773
    int status = getrlimit(RLIMIT_NOFILE, &nbr_files);
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4774
    if (status != 0) {
26684
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
  4775
      if (PrintMiscellaneous && (Verbose || WizardMode)) {
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4776
        perror("os::init_2 getrlimit failed");
26684
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
  4777
      }
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4778
    } else {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4779
      nbr_files.rlim_cur = nbr_files.rlim_max;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4780
      status = setrlimit(RLIMIT_NOFILE, &nbr_files);
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4781
      if (status != 0) {
26684
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
  4782
        if (PrintMiscellaneous && (Verbose || WizardMode)) {
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4783
          perror("os::init_2 setrlimit failed");
26684
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
  4784
        }
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4785
      }
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4786
    }
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4787
  }
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4788
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4789
  // Initialize lock used to serialize thread creation (see os::create_thread)
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4790
  Linux::set_createThread_lock(new Mutex(Mutex::leaf, "createThread_lock", false));
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4791
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4792
  // at-exit methods are called in the reverse order of their registration.
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4793
  // atexit functions are called on return from main or as a result of a
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4794
  // call to exit(3C). There can be only 32 of these functions registered
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4795
  // and atexit() does not set errno.
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4796
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4797
  if (PerfAllowAtExitRegistration) {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4798
    // only register atexit functions if PerfAllowAtExitRegistration is set.
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4799
    // atexit functions can be delayed until process exit time, which
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4800
    // can be problematic for embedded VM situations. Embedded VMs should
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4801
    // call DestroyJavaVM() to assure that VM resources are released.
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4802
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4803
    // note: perfMemory_exit_helper atexit function may be removed in
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4804
    // the future if the appropriate cleanup code can be added to the
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4805
    // VM_Exit VMOperation's doit method.
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4806
    if (atexit(perfMemory_exit_helper) != 0) {
22807
1cf02ef734e2 8016586: PPC64 (part 3): basic changes for PPC64
goetz
parents: 22806
diff changeset
  4807
      warning("os::init_2 atexit(perfMemory_exit_helper) failed");
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4808
    }
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4809
  }
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4810
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4811
  // initialize thread priority policy
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4812
  prio_init();
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4813
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4814
  return JNI_OK;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4815
}
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4816
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4817
// Mark the polling page as unreadable
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4818
void os::make_polling_page_unreadable(void) {
26684
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
  4819
  if (!guard_memory((char*)_polling_page, Linux::page_size())) {
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4820
    fatal("Could not disable polling page");
26684
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
  4821
  }
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
  4822
}
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4823
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4824
// Mark the polling page as readable
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4825
void os::make_polling_page_readable(void) {
25064
244218e6ec0a 8046758: cleanup non-indent white space issues prior to Contended Locking cleanup bucket
dcubed
parents: 24931
diff changeset
  4826
  if (!linux_mprotect((char *)_polling_page, Linux::page_size(), PROT_READ)) {
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4827
    fatal("Could not enable polling page");
823
9a5271881bc0 6716785: implicit null checks not triggering with CompressedOops
coleenp
parents: 781
diff changeset
  4828
  }
26684
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
  4829
}
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4830
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4831
int os::active_processor_count() {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4832
  // Linux doesn't yet have a (official) notion of processor sets,
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4833
  // so just return the number of online processors.
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4834
  int online_cpus = ::sysconf(_SC_NPROCESSORS_ONLN);
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4835
  assert(online_cpus > 0 && online_cpus <= processor_count(), "sanity check");
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4836
  return online_cpus;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4837
}
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4838
10739
91935236600e 7098194: integrate macosx-port changes
dcubed
parents: 10571
diff changeset
  4839
void os::set_native_thread_name(const char *name) {
27164
6523fa019ffa 7102541: RFE: os::set_native_thread_name() cleanups
sla
parents: 27157
diff changeset
  4840
  if (Linux::_pthread_setname_np) {
6523fa019ffa 7102541: RFE: os::set_native_thread_name() cleanups
sla
parents: 27157
diff changeset
  4841
    char buf [16]; // according to glibc manpage, 16 chars incl. '/0'
6523fa019ffa 7102541: RFE: os::set_native_thread_name() cleanups
sla
parents: 27157
diff changeset
  4842
    snprintf(buf, sizeof(buf), "%s", name);
6523fa019ffa 7102541: RFE: os::set_native_thread_name() cleanups
sla
parents: 27157
diff changeset
  4843
    buf[sizeof(buf) - 1] = '\0';
6523fa019ffa 7102541: RFE: os::set_native_thread_name() cleanups
sla
parents: 27157
diff changeset
  4844
    const int rc = Linux::_pthread_setname_np(pthread_self(), buf);
6523fa019ffa 7102541: RFE: os::set_native_thread_name() cleanups
sla
parents: 27157
diff changeset
  4845
    // ERANGE should not happen; all other errors should just be ignored.
6523fa019ffa 7102541: RFE: os::set_native_thread_name() cleanups
sla
parents: 27157
diff changeset
  4846
    assert(rc != ERANGE, "pthread_setname_np failed");
6523fa019ffa 7102541: RFE: os::set_native_thread_name() cleanups
sla
parents: 27157
diff changeset
  4847
  }
10739
91935236600e 7098194: integrate macosx-port changes
dcubed
parents: 10571
diff changeset
  4848
}
91935236600e 7098194: integrate macosx-port changes
dcubed
parents: 10571
diff changeset
  4849
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4850
bool os::distribute_processes(uint length, uint* distribution) {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4851
  // Not yet implemented.
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4852
  return false;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4853
}
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4854
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4855
bool os::bind_to_processor(uint processor_id) {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4856
  // Not yet implemented.
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4857
  return false;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4858
}
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4859
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4860
///
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4861
18025
b7bcf7497f93 8005849: JEP 167: Event-Based JVM Tracing
sla
parents: 17854
diff changeset
  4862
void os::SuspendedThreadTask::internal_do_task() {
b7bcf7497f93 8005849: JEP 167: Event-Based JVM Tracing
sla
parents: 17854
diff changeset
  4863
  if (do_suspend(_thread->osthread())) {
b7bcf7497f93 8005849: JEP 167: Event-Based JVM Tracing
sla
parents: 17854
diff changeset
  4864
    SuspendedThreadTaskContext context(_thread, _thread->osthread()->ucontext());
b7bcf7497f93 8005849: JEP 167: Event-Based JVM Tracing
sla
parents: 17854
diff changeset
  4865
    do_task(context);
b7bcf7497f93 8005849: JEP 167: Event-Based JVM Tracing
sla
parents: 17854
diff changeset
  4866
    do_resume(_thread->osthread());
b7bcf7497f93 8005849: JEP 167: Event-Based JVM Tracing
sla
parents: 17854
diff changeset
  4867
  }
b7bcf7497f93 8005849: JEP 167: Event-Based JVM Tracing
sla
parents: 17854
diff changeset
  4868
}
b7bcf7497f93 8005849: JEP 167: Event-Based JVM Tracing
sla
parents: 17854
diff changeset
  4869
b7bcf7497f93 8005849: JEP 167: Event-Based JVM Tracing
sla
parents: 17854
diff changeset
  4870
class PcFetcher : public os::SuspendedThreadTask {
26683
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  4871
 public:
18025
b7bcf7497f93 8005849: JEP 167: Event-Based JVM Tracing
sla
parents: 17854
diff changeset
  4872
  PcFetcher(Thread* thread) : os::SuspendedThreadTask(thread) {}
b7bcf7497f93 8005849: JEP 167: Event-Based JVM Tracing
sla
parents: 17854
diff changeset
  4873
  ExtendedPC result();
26683
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  4874
 protected:
18025
b7bcf7497f93 8005849: JEP 167: Event-Based JVM Tracing
sla
parents: 17854
diff changeset
  4875
  void do_task(const os::SuspendedThreadTaskContext& context);
26683
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  4876
 private:
18025
b7bcf7497f93 8005849: JEP 167: Event-Based JVM Tracing
sla
parents: 17854
diff changeset
  4877
  ExtendedPC _epc;
b7bcf7497f93 8005849: JEP 167: Event-Based JVM Tracing
sla
parents: 17854
diff changeset
  4878
};
b7bcf7497f93 8005849: JEP 167: Event-Based JVM Tracing
sla
parents: 17854
diff changeset
  4879
b7bcf7497f93 8005849: JEP 167: Event-Based JVM Tracing
sla
parents: 17854
diff changeset
  4880
ExtendedPC PcFetcher::result() {
b7bcf7497f93 8005849: JEP 167: Event-Based JVM Tracing
sla
parents: 17854
diff changeset
  4881
  guarantee(is_done(), "task is not done yet.");
b7bcf7497f93 8005849: JEP 167: Event-Based JVM Tracing
sla
parents: 17854
diff changeset
  4882
  return _epc;
b7bcf7497f93 8005849: JEP 167: Event-Based JVM Tracing
sla
parents: 17854
diff changeset
  4883
}
b7bcf7497f93 8005849: JEP 167: Event-Based JVM Tracing
sla
parents: 17854
diff changeset
  4884
b7bcf7497f93 8005849: JEP 167: Event-Based JVM Tracing
sla
parents: 17854
diff changeset
  4885
void PcFetcher::do_task(const os::SuspendedThreadTaskContext& context) {
b7bcf7497f93 8005849: JEP 167: Event-Based JVM Tracing
sla
parents: 17854
diff changeset
  4886
  Thread* thread = context.thread();
b7bcf7497f93 8005849: JEP 167: Event-Based JVM Tracing
sla
parents: 17854
diff changeset
  4887
  OSThread* osthread = thread->osthread();
b7bcf7497f93 8005849: JEP 167: Event-Based JVM Tracing
sla
parents: 17854
diff changeset
  4888
  if (osthread->ucontext() != NULL) {
b7bcf7497f93 8005849: JEP 167: Event-Based JVM Tracing
sla
parents: 17854
diff changeset
  4889
    _epc = os::Linux::ucontext_get_pc((ucontext_t *) context.ucontext());
b7bcf7497f93 8005849: JEP 167: Event-Based JVM Tracing
sla
parents: 17854
diff changeset
  4890
  } else {
b7bcf7497f93 8005849: JEP 167: Event-Based JVM Tracing
sla
parents: 17854
diff changeset
  4891
    // NULL context is unexpected, double-check this is the VMThread
b7bcf7497f93 8005849: JEP 167: Event-Based JVM Tracing
sla
parents: 17854
diff changeset
  4892
    guarantee(thread->is_VM_thread(), "can only be called for VMThread");
b7bcf7497f93 8005849: JEP 167: Event-Based JVM Tracing
sla
parents: 17854
diff changeset
  4893
  }
b7bcf7497f93 8005849: JEP 167: Event-Based JVM Tracing
sla
parents: 17854
diff changeset
  4894
}
b7bcf7497f93 8005849: JEP 167: Event-Based JVM Tracing
sla
parents: 17854
diff changeset
  4895
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4896
// Suspends the target using the signal mechanism and then grabs the PC before
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4897
// resuming the target. Used by the flat-profiler only
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4898
ExtendedPC os::get_thread_pc(Thread* thread) {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4899
  // Make sure that it is called by the watcher for the VMThread
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4900
  assert(Thread::current()->is_Watcher_thread(), "Must be watcher");
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4901
  assert(thread->is_VM_thread(), "Can only be called for VMThread");
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4902
18025
b7bcf7497f93 8005849: JEP 167: Event-Based JVM Tracing
sla
parents: 17854
diff changeset
  4903
  PcFetcher fetcher(thread);
b7bcf7497f93 8005849: JEP 167: Event-Based JVM Tracing
sla
parents: 17854
diff changeset
  4904
  fetcher.run();
b7bcf7497f93 8005849: JEP 167: Event-Based JVM Tracing
sla
parents: 17854
diff changeset
  4905
  return fetcher.result();
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4906
}
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4907
26684
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
  4908
int os::Linux::safe_cond_timedwait(pthread_cond_t *_cond,
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
  4909
                                   pthread_mutex_t *_mutex,
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
  4910
                                   const struct timespec *_abstime) {
26683
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  4911
  if (is_NPTL()) {
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  4912
    return pthread_cond_timedwait(_cond, _mutex, _abstime);
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  4913
  } else {
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  4914
    // 6292965: LinuxThreads pthread_cond_timedwait() resets FPU control
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  4915
    // word back to default 64bit precision if condvar is signaled. Java
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  4916
    // wants 53bit precision.  Save and restore current value.
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  4917
    int fpu = get_fpu_control_word();
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  4918
    int status = pthread_cond_timedwait(_cond, _mutex, _abstime);
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  4919
    set_fpu_control_word(fpu);
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  4920
    return status;
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  4921
  }
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4922
}
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4923
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4924
////////////////////////////////////////////////////////////////////////////////
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4925
// debug support
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4926
6176
4d9030fe341f 6953477: Increase portability and flexibility of building Hotspot
bobv
parents: 5922
diff changeset
  4927
bool os::find(address addr, outputStream* st) {
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4928
  Dl_info dlinfo;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4929
  memset(&dlinfo, 0, sizeof(dlinfo));
18683
a6418e038255 8015884: runThese crashed with SIGSEGV, hs_err has an error instead of stacktrace
dcubed
parents: 18086
diff changeset
  4930
  if (dladdr(addr, &dlinfo) != 0) {
6176
4d9030fe341f 6953477: Increase portability and flexibility of building Hotspot
bobv
parents: 5922
diff changeset
  4931
    st->print(PTR_FORMAT ": ", addr);
18683
a6418e038255 8015884: runThese crashed with SIGSEGV, hs_err has an error instead of stacktrace
dcubed
parents: 18086
diff changeset
  4932
    if (dlinfo.dli_sname != NULL && dlinfo.dli_saddr != NULL) {
6176
4d9030fe341f 6953477: Increase portability and flexibility of building Hotspot
bobv
parents: 5922
diff changeset
  4933
      st->print("%s+%#x", dlinfo.dli_sname,
26683
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  4934
                addr - (intptr_t)dlinfo.dli_saddr);
18683
a6418e038255 8015884: runThese crashed with SIGSEGV, hs_err has an error instead of stacktrace
dcubed
parents: 18086
diff changeset
  4935
    } else if (dlinfo.dli_fbase != NULL) {
6176
4d9030fe341f 6953477: Increase portability and flexibility of building Hotspot
bobv
parents: 5922
diff changeset
  4936
      st->print("<offset %#x>", addr - (intptr_t)dlinfo.dli_fbase);
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4937
    } else {
6176
4d9030fe341f 6953477: Increase portability and flexibility of building Hotspot
bobv
parents: 5922
diff changeset
  4938
      st->print("<absolute address>");
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4939
    }
18683
a6418e038255 8015884: runThese crashed with SIGSEGV, hs_err has an error instead of stacktrace
dcubed
parents: 18086
diff changeset
  4940
    if (dlinfo.dli_fname != NULL) {
6176
4d9030fe341f 6953477: Increase portability and flexibility of building Hotspot
bobv
parents: 5922
diff changeset
  4941
      st->print(" in %s", dlinfo.dli_fname);
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4942
    }
18683
a6418e038255 8015884: runThese crashed with SIGSEGV, hs_err has an error instead of stacktrace
dcubed
parents: 18086
diff changeset
  4943
    if (dlinfo.dli_fbase != NULL) {
6176
4d9030fe341f 6953477: Increase portability and flexibility of building Hotspot
bobv
parents: 5922
diff changeset
  4944
      st->print(" at " PTR_FORMAT, dlinfo.dli_fbase);
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4945
    }
6176
4d9030fe341f 6953477: Increase portability and flexibility of building Hotspot
bobv
parents: 5922
diff changeset
  4946
    st->cr();
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4947
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4948
    if (Verbose) {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4949
      // decode some bytes around the PC
16670
4af09aff4237 8003310: Enable -Wunused-function when compiling with gcc
mikael
parents: 16669
diff changeset
  4950
      address begin = clamp_address_in_page(addr-40, addr, os::vm_page_size());
4af09aff4237 8003310: Enable -Wunused-function when compiling with gcc
mikael
parents: 16669
diff changeset
  4951
      address end   = clamp_address_in_page(addr+40, addr, os::vm_page_size());
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4952
      address       lowest = (address) dlinfo.dli_sname;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4953
      if (!lowest)  lowest = (address) dlinfo.dli_fbase;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4954
      if (begin < lowest)  begin = lowest;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4955
      Dl_info dlinfo2;
18683
a6418e038255 8015884: runThese crashed with SIGSEGV, hs_err has an error instead of stacktrace
dcubed
parents: 18086
diff changeset
  4956
      if (dladdr(end, &dlinfo2) != 0 && dlinfo2.dli_saddr != dlinfo.dli_saddr
26684
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
  4957
          && end > dlinfo2.dli_saddr && dlinfo2.dli_saddr > begin) {
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4958
        end = (address) dlinfo2.dli_saddr;
26684
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
  4959
      }
6176
4d9030fe341f 6953477: Increase portability and flexibility of building Hotspot
bobv
parents: 5922
diff changeset
  4960
      Disassembler::decode(begin, end, st);
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4961
    }
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4962
    return true;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4963
  }
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4964
  return false;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4965
}
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4966
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4967
////////////////////////////////////////////////////////////////////////////////
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4968
// misc
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4969
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4970
// This does not do anything on Linux. This is basically a hook for being
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4971
// able to use structured exception handling (thread-local exception filters)
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4972
// on, e.g., Win32.
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4973
void
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4974
os::os_exception_wrapper(java_call_t f, JavaValue* value, methodHandle* method,
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4975
                         JavaCallArguments* args, Thread* thread) {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4976
  f(value, method, args, thread);
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4977
}
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4978
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4979
void os::print_statistics() {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4980
}
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4981
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4982
int os::message_box(const char* title, const char* message) {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4983
  int i;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4984
  fdStream err(defaultStream::error_fd());
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4985
  for (i = 0; i < 78; i++) err.print_raw("=");
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4986
  err.cr();
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4987
  err.print_raw_cr(title);
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4988
  for (i = 0; i < 78; i++) err.print_raw("-");
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4989
  err.cr();
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4990
  err.print_raw_cr(message);
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4991
  for (i = 0; i < 78; i++) err.print_raw("=");
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4992
  err.cr();
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4993
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4994
  char buf[16];
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4995
  // Prevent process from exiting upon "read error" without consuming all CPU
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4996
  while (::read(0, buf, sizeof(buf)) <= 0) { ::sleep(100); }
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4997
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4998
  return buf[0] == 'y' || buf[0] == 'Y';
489c9b5090e2 Initial load
duke
parents:
diff changeset
  4999
}
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5000
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5001
int os::stat(const char *path, struct stat *sbuf) {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5002
  char pathbuf[MAX_PATH];
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5003
  if (strlen(path) > MAX_PATH - 1) {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5004
    errno = ENAMETOOLONG;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5005
    return -1;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5006
  }
7405
e6fc8d3926f8 6348631: remove the use of the HPI library from Hotspot
ikrylov
parents: 7397
diff changeset
  5007
  os::native_path(strcpy(pathbuf, path));
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5008
  return ::stat(pathbuf, sbuf);
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5009
}
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5010
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5011
bool os::check_heap(bool force) {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5012
  return true;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5013
}
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5014
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5015
// Is a (classpath) directory empty?
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5016
bool os::dir_is_empty(const char* path) {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5017
  DIR *dir = NULL;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5018
  struct dirent *ptr;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5019
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5020
  dir = opendir(path);
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5021
  if (dir == NULL) return true;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5022
26684
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
  5023
  // Scan the directory
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5024
  bool result = true;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5025
  char buf[sizeof(struct dirent) + MAX_PATH];
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5026
  while (result && (ptr = ::readdir(dir)) != NULL) {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5027
    if (strcmp(ptr->d_name, ".") != 0 && strcmp(ptr->d_name, "..") != 0) {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5028
      result = false;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5029
    }
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5030
  }
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5031
  closedir(dir);
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5032
  return result;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5033
}
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5034
7405
e6fc8d3926f8 6348631: remove the use of the HPI library from Hotspot
ikrylov
parents: 7397
diff changeset
  5035
// This code originates from JDK's sysOpen and open64_w
e6fc8d3926f8 6348631: remove the use of the HPI library from Hotspot
ikrylov
parents: 7397
diff changeset
  5036
// from src/solaris/hpi/src/system_md.c
e6fc8d3926f8 6348631: remove the use of the HPI library from Hotspot
ikrylov
parents: 7397
diff changeset
  5037
e6fc8d3926f8 6348631: remove the use of the HPI library from Hotspot
ikrylov
parents: 7397
diff changeset
  5038
int os::open(const char *path, int oflag, int mode) {
e6fc8d3926f8 6348631: remove the use of the HPI library from Hotspot
ikrylov
parents: 7397
diff changeset
  5039
  if (strlen(path) > MAX_PATH - 1) {
e6fc8d3926f8 6348631: remove the use of the HPI library from Hotspot
ikrylov
parents: 7397
diff changeset
  5040
    errno = ENAMETOOLONG;
e6fc8d3926f8 6348631: remove the use of the HPI library from Hotspot
ikrylov
parents: 7397
diff changeset
  5041
    return -1;
e6fc8d3926f8 6348631: remove the use of the HPI library from Hotspot
ikrylov
parents: 7397
diff changeset
  5042
  }
27457
adbe834be3a0 8043780: Use open(O_CLOEXEC) instead of fcntl(FD_CLOEXEC)
martin
parents: 27400
diff changeset
  5043
adbe834be3a0 8043780: Use open(O_CLOEXEC) instead of fcntl(FD_CLOEXEC)
martin
parents: 27400
diff changeset
  5044
  // All file descriptors that are opened in the Java process and not
adbe834be3a0 8043780: Use open(O_CLOEXEC) instead of fcntl(FD_CLOEXEC)
martin
parents: 27400
diff changeset
  5045
  // specifically destined for a subprocess should have the close-on-exec
adbe834be3a0 8043780: Use open(O_CLOEXEC) instead of fcntl(FD_CLOEXEC)
martin
parents: 27400
diff changeset
  5046
  // flag set.  If we don't set it, then careless 3rd party native code
adbe834be3a0 8043780: Use open(O_CLOEXEC) instead of fcntl(FD_CLOEXEC)
martin
parents: 27400
diff changeset
  5047
  // might fork and exec without closing all appropriate file descriptors
adbe834be3a0 8043780: Use open(O_CLOEXEC) instead of fcntl(FD_CLOEXEC)
martin
parents: 27400
diff changeset
  5048
  // (e.g. as we do in closeDescriptors in UNIXProcess.c), and this in
adbe834be3a0 8043780: Use open(O_CLOEXEC) instead of fcntl(FD_CLOEXEC)
martin
parents: 27400
diff changeset
  5049
  // turn might:
adbe834be3a0 8043780: Use open(O_CLOEXEC) instead of fcntl(FD_CLOEXEC)
martin
parents: 27400
diff changeset
  5050
  //
adbe834be3a0 8043780: Use open(O_CLOEXEC) instead of fcntl(FD_CLOEXEC)
martin
parents: 27400
diff changeset
  5051
  // - cause end-of-file to fail to be detected on some file
adbe834be3a0 8043780: Use open(O_CLOEXEC) instead of fcntl(FD_CLOEXEC)
martin
parents: 27400
diff changeset
  5052
  //   descriptors, resulting in mysterious hangs, or
adbe834be3a0 8043780: Use open(O_CLOEXEC) instead of fcntl(FD_CLOEXEC)
martin
parents: 27400
diff changeset
  5053
  //
adbe834be3a0 8043780: Use open(O_CLOEXEC) instead of fcntl(FD_CLOEXEC)
martin
parents: 27400
diff changeset
  5054
  // - might cause an fopen in the subprocess to fail on a system
adbe834be3a0 8043780: Use open(O_CLOEXEC) instead of fcntl(FD_CLOEXEC)
martin
parents: 27400
diff changeset
  5055
  //   suffering from bug 1085341.
adbe834be3a0 8043780: Use open(O_CLOEXEC) instead of fcntl(FD_CLOEXEC)
martin
parents: 27400
diff changeset
  5056
  //
adbe834be3a0 8043780: Use open(O_CLOEXEC) instead of fcntl(FD_CLOEXEC)
martin
parents: 27400
diff changeset
  5057
  // (Yes, the default setting of the close-on-exec flag is a Unix
adbe834be3a0 8043780: Use open(O_CLOEXEC) instead of fcntl(FD_CLOEXEC)
martin
parents: 27400
diff changeset
  5058
  // design flaw)
adbe834be3a0 8043780: Use open(O_CLOEXEC) instead of fcntl(FD_CLOEXEC)
martin
parents: 27400
diff changeset
  5059
  //
adbe834be3a0 8043780: Use open(O_CLOEXEC) instead of fcntl(FD_CLOEXEC)
martin
parents: 27400
diff changeset
  5060
  // See:
adbe834be3a0 8043780: Use open(O_CLOEXEC) instead of fcntl(FD_CLOEXEC)
martin
parents: 27400
diff changeset
  5061
  // 1085341: 32-bit stdio routines should support file descriptors >255
adbe834be3a0 8043780: Use open(O_CLOEXEC) instead of fcntl(FD_CLOEXEC)
martin
parents: 27400
diff changeset
  5062
  // 4843136: (process) pipe file descriptor from Runtime.exec not being closed
adbe834be3a0 8043780: Use open(O_CLOEXEC) instead of fcntl(FD_CLOEXEC)
martin
parents: 27400
diff changeset
  5063
  // 6339493: (process) Runtime.exec does not close all file descriptors on Solaris 9
adbe834be3a0 8043780: Use open(O_CLOEXEC) instead of fcntl(FD_CLOEXEC)
martin
parents: 27400
diff changeset
  5064
  //
adbe834be3a0 8043780: Use open(O_CLOEXEC) instead of fcntl(FD_CLOEXEC)
martin
parents: 27400
diff changeset
  5065
  // Modern Linux kernels (after 2.6.23 2007) support O_CLOEXEC with open().
adbe834be3a0 8043780: Use open(O_CLOEXEC) instead of fcntl(FD_CLOEXEC)
martin
parents: 27400
diff changeset
  5066
  // O_CLOEXEC is preferable to using FD_CLOEXEC on an open file descriptor
adbe834be3a0 8043780: Use open(O_CLOEXEC) instead of fcntl(FD_CLOEXEC)
martin
parents: 27400
diff changeset
  5067
  // because it saves a system call and removes a small window where the flag
adbe834be3a0 8043780: Use open(O_CLOEXEC) instead of fcntl(FD_CLOEXEC)
martin
parents: 27400
diff changeset
  5068
  // is unset.  On ancient Linux kernels the O_CLOEXEC flag will be ignored
adbe834be3a0 8043780: Use open(O_CLOEXEC) instead of fcntl(FD_CLOEXEC)
martin
parents: 27400
diff changeset
  5069
  // and we fall back to using FD_CLOEXEC (see below).
adbe834be3a0 8043780: Use open(O_CLOEXEC) instead of fcntl(FD_CLOEXEC)
martin
parents: 27400
diff changeset
  5070
#ifdef O_CLOEXEC
adbe834be3a0 8043780: Use open(O_CLOEXEC) instead of fcntl(FD_CLOEXEC)
martin
parents: 27400
diff changeset
  5071
  oflag |= O_CLOEXEC;
adbe834be3a0 8043780: Use open(O_CLOEXEC) instead of fcntl(FD_CLOEXEC)
martin
parents: 27400
diff changeset
  5072
#endif
adbe834be3a0 8043780: Use open(O_CLOEXEC) instead of fcntl(FD_CLOEXEC)
martin
parents: 27400
diff changeset
  5073
adbe834be3a0 8043780: Use open(O_CLOEXEC) instead of fcntl(FD_CLOEXEC)
martin
parents: 27400
diff changeset
  5074
  int fd = ::open64(path, oflag, mode);
7405
e6fc8d3926f8 6348631: remove the use of the HPI library from Hotspot
ikrylov
parents: 7397
diff changeset
  5075
  if (fd == -1) return -1;
e6fc8d3926f8 6348631: remove the use of the HPI library from Hotspot
ikrylov
parents: 7397
diff changeset
  5076
e6fc8d3926f8 6348631: remove the use of the HPI library from Hotspot
ikrylov
parents: 7397
diff changeset
  5077
  //If the open succeeded, the file might still be a directory
e6fc8d3926f8 6348631: remove the use of the HPI library from Hotspot
ikrylov
parents: 7397
diff changeset
  5078
  {
e6fc8d3926f8 6348631: remove the use of the HPI library from Hotspot
ikrylov
parents: 7397
diff changeset
  5079
    struct stat64 buf64;
e6fc8d3926f8 6348631: remove the use of the HPI library from Hotspot
ikrylov
parents: 7397
diff changeset
  5080
    int ret = ::fstat64(fd, &buf64);
e6fc8d3926f8 6348631: remove the use of the HPI library from Hotspot
ikrylov
parents: 7397
diff changeset
  5081
    int st_mode = buf64.st_mode;
e6fc8d3926f8 6348631: remove the use of the HPI library from Hotspot
ikrylov
parents: 7397
diff changeset
  5082
e6fc8d3926f8 6348631: remove the use of the HPI library from Hotspot
ikrylov
parents: 7397
diff changeset
  5083
    if (ret != -1) {
e6fc8d3926f8 6348631: remove the use of the HPI library from Hotspot
ikrylov
parents: 7397
diff changeset
  5084
      if ((st_mode & S_IFMT) == S_IFDIR) {
e6fc8d3926f8 6348631: remove the use of the HPI library from Hotspot
ikrylov
parents: 7397
diff changeset
  5085
        errno = EISDIR;
e6fc8d3926f8 6348631: remove the use of the HPI library from Hotspot
ikrylov
parents: 7397
diff changeset
  5086
        ::close(fd);
e6fc8d3926f8 6348631: remove the use of the HPI library from Hotspot
ikrylov
parents: 7397
diff changeset
  5087
        return -1;
e6fc8d3926f8 6348631: remove the use of the HPI library from Hotspot
ikrylov
parents: 7397
diff changeset
  5088
      }
e6fc8d3926f8 6348631: remove the use of the HPI library from Hotspot
ikrylov
parents: 7397
diff changeset
  5089
    } else {
e6fc8d3926f8 6348631: remove the use of the HPI library from Hotspot
ikrylov
parents: 7397
diff changeset
  5090
      ::close(fd);
e6fc8d3926f8 6348631: remove the use of the HPI library from Hotspot
ikrylov
parents: 7397
diff changeset
  5091
      return -1;
e6fc8d3926f8 6348631: remove the use of the HPI library from Hotspot
ikrylov
parents: 7397
diff changeset
  5092
    }
e6fc8d3926f8 6348631: remove the use of the HPI library from Hotspot
ikrylov
parents: 7397
diff changeset
  5093
  }
e6fc8d3926f8 6348631: remove the use of the HPI library from Hotspot
ikrylov
parents: 7397
diff changeset
  5094
e6fc8d3926f8 6348631: remove the use of the HPI library from Hotspot
ikrylov
parents: 7397
diff changeset
  5095
#ifdef FD_CLOEXEC
27457
adbe834be3a0 8043780: Use open(O_CLOEXEC) instead of fcntl(FD_CLOEXEC)
martin
parents: 27400
diff changeset
  5096
  // Validate that the use of the O_CLOEXEC flag on open above worked.
adbe834be3a0 8043780: Use open(O_CLOEXEC) instead of fcntl(FD_CLOEXEC)
martin
parents: 27400
diff changeset
  5097
  // With recent kernels, we will perform this check exactly once.
adbe834be3a0 8043780: Use open(O_CLOEXEC) instead of fcntl(FD_CLOEXEC)
martin
parents: 27400
diff changeset
  5098
  static sig_atomic_t O_CLOEXEC_is_known_to_work = 0;
adbe834be3a0 8043780: Use open(O_CLOEXEC) instead of fcntl(FD_CLOEXEC)
martin
parents: 27400
diff changeset
  5099
  if (!O_CLOEXEC_is_known_to_work) {
26683
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  5100
    int flags = ::fcntl(fd, F_GETFD);
26684
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
  5101
    if (flags != -1) {
27457
adbe834be3a0 8043780: Use open(O_CLOEXEC) instead of fcntl(FD_CLOEXEC)
martin
parents: 27400
diff changeset
  5102
      if ((flags & FD_CLOEXEC) != 0)
adbe834be3a0 8043780: Use open(O_CLOEXEC) instead of fcntl(FD_CLOEXEC)
martin
parents: 27400
diff changeset
  5103
        O_CLOEXEC_is_known_to_work = 1;
adbe834be3a0 8043780: Use open(O_CLOEXEC) instead of fcntl(FD_CLOEXEC)
martin
parents: 27400
diff changeset
  5104
      else
adbe834be3a0 8043780: Use open(O_CLOEXEC) instead of fcntl(FD_CLOEXEC)
martin
parents: 27400
diff changeset
  5105
        ::fcntl(fd, F_SETFD, flags | FD_CLOEXEC);
26684
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
  5106
    }
26683
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  5107
  }
7405
e6fc8d3926f8 6348631: remove the use of the HPI library from Hotspot
ikrylov
parents: 7397
diff changeset
  5108
#endif
e6fc8d3926f8 6348631: remove the use of the HPI library from Hotspot
ikrylov
parents: 7397
diff changeset
  5109
e6fc8d3926f8 6348631: remove the use of the HPI library from Hotspot
ikrylov
parents: 7397
diff changeset
  5110
  return fd;
e6fc8d3926f8 6348631: remove the use of the HPI library from Hotspot
ikrylov
parents: 7397
diff changeset
  5111
}
e6fc8d3926f8 6348631: remove the use of the HPI library from Hotspot
ikrylov
parents: 7397
diff changeset
  5112
e6fc8d3926f8 6348631: remove the use of the HPI library from Hotspot
ikrylov
parents: 7397
diff changeset
  5113
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5114
// create binary file, rewriting existing file if required
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5115
int os::create_binary_file(const char* path, bool rewrite_existing) {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5116
  int oflags = O_WRONLY | O_CREAT;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5117
  if (!rewrite_existing) {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5118
    oflags |= O_EXCL;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5119
  }
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5120
  return ::open64(path, oflags, S_IREAD | S_IWRITE);
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5121
}
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5122
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5123
// return current position of file pointer
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5124
jlong os::current_file_offset(int fd) {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5125
  return (jlong)::lseek64(fd, (off64_t)0, SEEK_CUR);
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5126
}
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5127
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5128
// move file pointer to the specified offset
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5129
jlong os::seek_to_file_offset(int fd, jlong offset) {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5130
  return (jlong)::lseek64(fd, (off64_t)offset, SEEK_SET);
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5131
}
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5132
7405
e6fc8d3926f8 6348631: remove the use of the HPI library from Hotspot
ikrylov
parents: 7397
diff changeset
  5133
// This code originates from JDK's sysAvailable
e6fc8d3926f8 6348631: remove the use of the HPI library from Hotspot
ikrylov
parents: 7397
diff changeset
  5134
// from src/solaris/hpi/src/native_threads/src/sys_api_td.c
e6fc8d3926f8 6348631: remove the use of the HPI library from Hotspot
ikrylov
parents: 7397
diff changeset
  5135
e6fc8d3926f8 6348631: remove the use of the HPI library from Hotspot
ikrylov
parents: 7397
diff changeset
  5136
int os::available(int fd, jlong *bytes) {
e6fc8d3926f8 6348631: remove the use of the HPI library from Hotspot
ikrylov
parents: 7397
diff changeset
  5137
  jlong cur, end;
e6fc8d3926f8 6348631: remove the use of the HPI library from Hotspot
ikrylov
parents: 7397
diff changeset
  5138
  int mode;
e6fc8d3926f8 6348631: remove the use of the HPI library from Hotspot
ikrylov
parents: 7397
diff changeset
  5139
  struct stat64 buf64;
e6fc8d3926f8 6348631: remove the use of the HPI library from Hotspot
ikrylov
parents: 7397
diff changeset
  5140
e6fc8d3926f8 6348631: remove the use of the HPI library from Hotspot
ikrylov
parents: 7397
diff changeset
  5141
  if (::fstat64(fd, &buf64) >= 0) {
e6fc8d3926f8 6348631: remove the use of the HPI library from Hotspot
ikrylov
parents: 7397
diff changeset
  5142
    mode = buf64.st_mode;
e6fc8d3926f8 6348631: remove the use of the HPI library from Hotspot
ikrylov
parents: 7397
diff changeset
  5143
    if (S_ISCHR(mode) || S_ISFIFO(mode) || S_ISSOCK(mode)) {
26684
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
  5144
      // XXX: is the following call interruptible? If so, this might
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
  5145
      // need to go through the INTERRUPT_IO() wrapper as for other
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
  5146
      // blocking, interruptible calls in this file.
7405
e6fc8d3926f8 6348631: remove the use of the HPI library from Hotspot
ikrylov
parents: 7397
diff changeset
  5147
      int n;
e6fc8d3926f8 6348631: remove the use of the HPI library from Hotspot
ikrylov
parents: 7397
diff changeset
  5148
      if (::ioctl(fd, FIONREAD, &n) >= 0) {
e6fc8d3926f8 6348631: remove the use of the HPI library from Hotspot
ikrylov
parents: 7397
diff changeset
  5149
        *bytes = n;
e6fc8d3926f8 6348631: remove the use of the HPI library from Hotspot
ikrylov
parents: 7397
diff changeset
  5150
        return 1;
e6fc8d3926f8 6348631: remove the use of the HPI library from Hotspot
ikrylov
parents: 7397
diff changeset
  5151
      }
e6fc8d3926f8 6348631: remove the use of the HPI library from Hotspot
ikrylov
parents: 7397
diff changeset
  5152
    }
e6fc8d3926f8 6348631: remove the use of the HPI library from Hotspot
ikrylov
parents: 7397
diff changeset
  5153
  }
e6fc8d3926f8 6348631: remove the use of the HPI library from Hotspot
ikrylov
parents: 7397
diff changeset
  5154
  if ((cur = ::lseek64(fd, 0L, SEEK_CUR)) == -1) {
e6fc8d3926f8 6348631: remove the use of the HPI library from Hotspot
ikrylov
parents: 7397
diff changeset
  5155
    return 0;
e6fc8d3926f8 6348631: remove the use of the HPI library from Hotspot
ikrylov
parents: 7397
diff changeset
  5156
  } else if ((end = ::lseek64(fd, 0L, SEEK_END)) == -1) {
e6fc8d3926f8 6348631: remove the use of the HPI library from Hotspot
ikrylov
parents: 7397
diff changeset
  5157
    return 0;
e6fc8d3926f8 6348631: remove the use of the HPI library from Hotspot
ikrylov
parents: 7397
diff changeset
  5158
  } else if (::lseek64(fd, cur, SEEK_SET) == -1) {
e6fc8d3926f8 6348631: remove the use of the HPI library from Hotspot
ikrylov
parents: 7397
diff changeset
  5159
    return 0;
e6fc8d3926f8 6348631: remove the use of the HPI library from Hotspot
ikrylov
parents: 7397
diff changeset
  5160
  }
e6fc8d3926f8 6348631: remove the use of the HPI library from Hotspot
ikrylov
parents: 7397
diff changeset
  5161
  *bytes = end - cur;
e6fc8d3926f8 6348631: remove the use of the HPI library from Hotspot
ikrylov
parents: 7397
diff changeset
  5162
  return 1;
e6fc8d3926f8 6348631: remove the use of the HPI library from Hotspot
ikrylov
parents: 7397
diff changeset
  5163
}
e6fc8d3926f8 6348631: remove the use of the HPI library from Hotspot
ikrylov
parents: 7397
diff changeset
  5164
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5165
// Map a block of memory.
13195
be27e1b6a4b9 6995781: Native Memory Tracking (Phase 1)
zgu
parents: 12735
diff changeset
  5166
char* os::pd_map_memory(int fd, const char* file_name, size_t file_offset,
26683
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  5167
                        char *addr, size_t bytes, bool read_only,
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  5168
                        bool allow_exec) {
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5169
  int prot;
11967
ce179af268b1 7142641: -Xshared:on fails on ARM
dlong
parents: 11601
diff changeset
  5170
  int flags = MAP_PRIVATE;
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5171
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5172
  if (read_only) {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5173
    prot = PROT_READ;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5174
  } else {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5175
    prot = PROT_READ | PROT_WRITE;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5176
  }
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5177
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5178
  if (allow_exec) {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5179
    prot |= PROT_EXEC;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5180
  }
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5181
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5182
  if (addr != NULL) {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5183
    flags |= MAP_FIXED;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5184
  }
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5185
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5186
  char* mapped_address = (char*)mmap(addr, (size_t)bytes, prot, flags,
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5187
                                     fd, file_offset);
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5188
  if (mapped_address == MAP_FAILED) {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5189
    return NULL;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5190
  }
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5191
  return mapped_address;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5192
}
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5193
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5194
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5195
// Remap a block of memory.
13195
be27e1b6a4b9 6995781: Native Memory Tracking (Phase 1)
zgu
parents: 12735
diff changeset
  5196
char* os::pd_remap_memory(int fd, const char* file_name, size_t file_offset,
26683
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  5197
                          char *addr, size_t bytes, bool read_only,
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  5198
                          bool allow_exec) {
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5199
  // same as map_memory() on this OS
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5200
  return os::map_memory(fd, file_name, file_offset, addr, bytes, read_only,
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5201
                        allow_exec);
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5202
}
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5203
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5204
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5205
// Unmap a block of memory.
13195
be27e1b6a4b9 6995781: Native Memory Tracking (Phase 1)
zgu
parents: 12735
diff changeset
  5206
bool os::pd_unmap_memory(char* addr, size_t bytes) {
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5207
  return munmap(addr, bytes) == 0;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5208
}
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5209
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5210
static jlong slow_thread_cpu_time(Thread *thread, bool user_sys_cpu_time);
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5211
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5212
static clockid_t thread_cpu_clockid(Thread* thread) {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5213
  pthread_t tid = thread->osthread()->pthread_id();
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5214
  clockid_t clockid;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5215
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5216
  // Get thread clockid
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5217
  int rc = os::Linux::pthread_getcpuclockid(tid, &clockid);
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5218
  assert(rc == 0, "pthread_getcpuclockid is expected to return 0 code");
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5219
  return clockid;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5220
}
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5221
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5222
// current_thread_cpu_time(bool) and thread_cpu_time(Thread*, bool)
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5223
// are used by JVM M&M and JVMTI to get user+sys or user CPU time
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5224
// of a thread.
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5225
//
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5226
// current_thread_cpu_time() and thread_cpu_time(Thread*) returns
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5227
// the fast estimate available on the platform.
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5228
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5229
jlong os::current_thread_cpu_time() {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5230
  if (os::Linux::supports_fast_thread_cpu_time()) {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5231
    return os::Linux::fast_thread_cpu_time(CLOCK_THREAD_CPUTIME_ID);
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5232
  } else {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5233
    // return user + sys since the cost is the same
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5234
    return slow_thread_cpu_time(Thread::current(), true /* user + sys */);
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5235
  }
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5236
}
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5237
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5238
jlong os::thread_cpu_time(Thread* thread) {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5239
  // consistent with what current_thread_cpu_time() returns
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5240
  if (os::Linux::supports_fast_thread_cpu_time()) {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5241
    return os::Linux::fast_thread_cpu_time(thread_cpu_clockid(thread));
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5242
  } else {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5243
    return slow_thread_cpu_time(thread, true /* user + sys */);
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5244
  }
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5245
}
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5246
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5247
jlong os::current_thread_cpu_time(bool user_sys_cpu_time) {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5248
  if (user_sys_cpu_time && os::Linux::supports_fast_thread_cpu_time()) {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5249
    return os::Linux::fast_thread_cpu_time(CLOCK_THREAD_CPUTIME_ID);
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5250
  } else {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5251
    return slow_thread_cpu_time(Thread::current(), user_sys_cpu_time);
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5252
  }
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5253
}
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5254
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5255
jlong os::thread_cpu_time(Thread *thread, bool user_sys_cpu_time) {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5256
  if (user_sys_cpu_time && os::Linux::supports_fast_thread_cpu_time()) {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5257
    return os::Linux::fast_thread_cpu_time(thread_cpu_clockid(thread));
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5258
  } else {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5259
    return slow_thread_cpu_time(thread, user_sys_cpu_time);
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5260
  }
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5261
}
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5262
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5263
//  -1 on error.
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5264
static jlong slow_thread_cpu_time(Thread *thread, bool user_sys_cpu_time) {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5265
  pid_t  tid = thread->osthread()->thread_id();
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5266
  char *s;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5267
  char stat[2048];
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5268
  int statlen;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5269
  char proc_name[64];
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5270
  int count;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5271
  long sys_time, user_time;
6176
4d9030fe341f 6953477: Increase portability and flexibility of building Hotspot
bobv
parents: 5922
diff changeset
  5272
  char cdummy;
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5273
  int idummy;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5274
  long ldummy;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5275
  FILE *fp;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5276
24333
c7214442139d 8031126: java/lang/management/ThreadMXBean/ThreadUserTime.java fails intermittently
sla
parents: 23868
diff changeset
  5277
  snprintf(proc_name, 64, "/proc/self/task/%d/stat", tid);
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5278
  fp = fopen(proc_name, "r");
25064
244218e6ec0a 8046758: cleanup non-indent white space issues prior to Contended Locking cleanup bucket
dcubed
parents: 24931
diff changeset
  5279
  if (fp == NULL) return -1;
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5280
  statlen = fread(stat, 1, 2047, fp);
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5281
  stat[statlen] = '\0';
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5282
  fclose(fp);
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5283
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5284
  // Skip pid and the command string. Note that we could be dealing with
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5285
  // weird command names, e.g. user could decide to rename java launcher
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5286
  // to "java 1.4.2 :)", then the stat file would look like
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5287
  //                1234 (java 1.4.2 :)) R ... ...
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5288
  // We don't really need to know the command string, just find the last
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5289
  // occurrence of ")" and then start parsing from there. See bug 4726580.
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5290
  s = strrchr(stat, ')');
25064
244218e6ec0a 8046758: cleanup non-indent white space issues prior to Contended Locking cleanup bucket
dcubed
parents: 24931
diff changeset
  5291
  if (s == NULL) return -1;
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5292
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5293
  // Skip blank chars
27471
6e56277909f1 8062370: Various minor code improvements
goetz
parents: 27458
diff changeset
  5294
  do { s++; } while (s && isspace(*s));
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5295
6176
4d9030fe341f 6953477: Increase portability and flexibility of building Hotspot
bobv
parents: 5922
diff changeset
  5296
  count = sscanf(s,"%c %d %d %d %d %d %lu %lu %lu %lu %lu %lu %lu",
4d9030fe341f 6953477: Increase portability and flexibility of building Hotspot
bobv
parents: 5922
diff changeset
  5297
                 &cdummy, &idummy, &idummy, &idummy, &idummy, &idummy,
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5298
                 &ldummy, &ldummy, &ldummy, &ldummy, &ldummy,
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5299
                 &user_time, &sys_time);
25064
244218e6ec0a 8046758: cleanup non-indent white space issues prior to Contended Locking cleanup bucket
dcubed
parents: 24931
diff changeset
  5300
  if (count != 13) return -1;
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5301
  if (user_sys_cpu_time) {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5302
    return ((jlong)sys_time + (jlong)user_time) * (1000000000 / clock_tics_per_sec);
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5303
  } else {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5304
    return (jlong)user_time * (1000000000 / clock_tics_per_sec);
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5305
  }
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5306
}
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5307
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5308
void os::current_thread_cpu_time_info(jvmtiTimerInfo *info_ptr) {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5309
  info_ptr->max_value = ALL_64_BITS;       // will not wrap in less than 64 bits
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5310
  info_ptr->may_skip_backward = false;     // elapsed time not wall time
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5311
  info_ptr->may_skip_forward = false;      // elapsed time not wall time
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5312
  info_ptr->kind = JVMTI_TIMER_TOTAL_CPU;  // user+system time is returned
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5313
}
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5314
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5315
void os::thread_cpu_time_info(jvmtiTimerInfo *info_ptr) {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5316
  info_ptr->max_value = ALL_64_BITS;       // will not wrap in less than 64 bits
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5317
  info_ptr->may_skip_backward = false;     // elapsed time not wall time
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5318
  info_ptr->may_skip_forward = false;      // elapsed time not wall time
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5319
  info_ptr->kind = JVMTI_TIMER_TOTAL_CPU;  // user+system time is returned
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5320
}
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5321
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5322
bool os::is_thread_cpu_time_supported() {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5323
  return true;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5324
}
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5325
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5326
// System loadavg support.  Returns -1 if load average cannot be obtained.
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5327
// Linux doesn't yet have a (official) notion of processor sets,
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5328
// so just return the system wide load average.
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5329
int os::loadavg(double loadavg[], int nelem) {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5330
  return ::getloadavg(loadavg, nelem);
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5331
}
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5332
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5333
void os::pause() {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5334
  char filename[MAX_PATH];
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5335
  if (PauseAtStartupFile && PauseAtStartupFile[0]) {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5336
    jio_snprintf(filename, MAX_PATH, PauseAtStartupFile);
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5337
  } else {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5338
    jio_snprintf(filename, MAX_PATH, "./vm.paused.%d", current_process_id());
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5339
  }
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5340
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5341
  int fd = ::open(filename, O_WRONLY | O_CREAT | O_TRUNC, 0666);
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5342
  if (fd != -1) {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5343
    struct stat buf;
7405
e6fc8d3926f8 6348631: remove the use of the HPI library from Hotspot
ikrylov
parents: 7397
diff changeset
  5344
    ::close(fd);
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5345
    while (::stat(filename, &buf) == 0) {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5346
      (void)::poll(NULL, 0, 100);
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5347
    }
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5348
  } else {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5349
    jio_fprintf(stderr,
26683
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  5350
                "Could not open pause file '%s', continuing immediately.\n", filename);
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5351
  }
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5352
}
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5353
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5354
27458
eb5f1b4f01e1 8061552: Contended Locking speedup PlatformEvent unpark bucket
dcubed
parents: 27457
diff changeset
  5355
// Refer to the comments in os_solaris.cpp park-unpark. The next two
eb5f1b4f01e1 8061552: Contended Locking speedup PlatformEvent unpark bucket
dcubed
parents: 27457
diff changeset
  5356
// comment paragraphs are worth repeating here:
eb5f1b4f01e1 8061552: Contended Locking speedup PlatformEvent unpark bucket
dcubed
parents: 27457
diff changeset
  5357
//
eb5f1b4f01e1 8061552: Contended Locking speedup PlatformEvent unpark bucket
dcubed
parents: 27457
diff changeset
  5358
// Assumption:
eb5f1b4f01e1 8061552: Contended Locking speedup PlatformEvent unpark bucket
dcubed
parents: 27457
diff changeset
  5359
//    Only one parker can exist on an event, which is why we allocate
eb5f1b4f01e1 8061552: Contended Locking speedup PlatformEvent unpark bucket
dcubed
parents: 27457
diff changeset
  5360
//    them per-thread. Multiple unparkers can coexist.
eb5f1b4f01e1 8061552: Contended Locking speedup PlatformEvent unpark bucket
dcubed
parents: 27457
diff changeset
  5361
//
eb5f1b4f01e1 8061552: Contended Locking speedup PlatformEvent unpark bucket
dcubed
parents: 27457
diff changeset
  5362
// _Event serves as a restricted-range semaphore.
eb5f1b4f01e1 8061552: Contended Locking speedup PlatformEvent unpark bucket
dcubed
parents: 27457
diff changeset
  5363
//   -1 : thread is blocked, i.e. there is a waiter
eb5f1b4f01e1 8061552: Contended Locking speedup PlatformEvent unpark bucket
dcubed
parents: 27457
diff changeset
  5364
//    0 : neutral: thread is running or ready,
eb5f1b4f01e1 8061552: Contended Locking speedup PlatformEvent unpark bucket
dcubed
parents: 27457
diff changeset
  5365
//        could have been signaled after a wait started
eb5f1b4f01e1 8061552: Contended Locking speedup PlatformEvent unpark bucket
dcubed
parents: 27457
diff changeset
  5366
//    1 : signaled - thread is running or ready
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5367
//
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5368
// Beware -- Some versions of NPTL embody a flaw where pthread_cond_timedwait() can
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5369
// hang indefinitely.  For instance NPTL 0.60 on 2.4.21-4ELsmp is vulnerable.
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5370
// For specifics regarding the bug see GLIBC BUGID 261237 :
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5371
//    http://www.mail-archive.com/debian-glibc@lists.debian.org/msg10837.html.
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5372
// Briefly, pthread_cond_timedwait() calls with an expiry time that's not in the future
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5373
// will either hang or corrupt the condvar, resulting in subsequent hangs if the condvar
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5374
// is used.  (The simple C test-case provided in the GLIBC bug report manifests the
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5375
// hang).  The JVM is vulernable via sleep(), Object.wait(timo), LockSupport.parkNanos()
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5376
// and monitorenter when we're using 1-0 locking.  All those operations may result in
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5377
// calls to pthread_cond_timedwait().  Using LD_ASSUME_KERNEL to use an older version
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5378
// of libpthread avoids the problem, but isn't practical.
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5379
//
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5380
// Possible remedies:
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5381
//
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5382
// 1.   Establish a minimum relative wait time.  50 to 100 msecs seems to work.
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5383
//      This is palliative and probabilistic, however.  If the thread is preempted
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5384
//      between the call to compute_abstime() and pthread_cond_timedwait(), more
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5385
//      than the minimum period may have passed, and the abstime may be stale (in the
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5386
//      past) resultin in a hang.   Using this technique reduces the odds of a hang
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5387
//      but the JVM is still vulnerable, particularly on heavily loaded systems.
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5388
//
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5389
// 2.   Modify park-unpark to use per-thread (per ParkEvent) pipe-pairs instead
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5390
//      of the usual flag-condvar-mutex idiom.  The write side of the pipe is set
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5391
//      NDELAY. unpark() reduces to write(), park() reduces to read() and park(timo)
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5392
//      reduces to poll()+read().  This works well, but consumes 2 FDs per extant
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5393
//      thread.
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5394
//
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5395
// 3.   Embargo pthread_cond_timedwait() and implement a native "chron" thread
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5396
//      that manages timeouts.  We'd emulate pthread_cond_timedwait() by enqueuing
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5397
//      a timeout request to the chron thread and then blocking via pthread_cond_wait().
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5398
//      This also works well.  In fact it avoids kernel-level scalability impediments
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5399
//      on certain platforms that don't handle lots of active pthread_cond_timedwait()
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5400
//      timers in a graceful fashion.
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5401
//
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5402
// 4.   When the abstime value is in the past it appears that control returns
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5403
//      correctly from pthread_cond_timedwait(), but the condvar is left corrupt.
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5404
//      Subsequent timedwait/wait calls may hang indefinitely.  Given that, we
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5405
//      can avoid the problem by reinitializing the condvar -- by cond_destroy()
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5406
//      followed by cond_init() -- after all calls to pthread_cond_timedwait().
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5407
//      It may be possible to avoid reinitialization by checking the return
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5408
//      value from pthread_cond_timedwait().  In addition to reinitializing the
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5409
//      condvar we must establish the invariant that cond_signal() is only called
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5410
//      within critical sections protected by the adjunct mutex.  This prevents
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5411
//      cond_signal() from "seeing" a condvar that's in the midst of being
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5412
//      reinitialized or that is corrupt.  Sadly, this invariant obviates the
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5413
//      desirable signal-after-unlock optimization that avoids futile context switching.
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5414
//
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5415
//      I'm also concerned that some versions of NTPL might allocate an auxilliary
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5416
//      structure when a condvar is used or initialized.  cond_destroy()  would
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5417
//      release the helper structure.  Our reinitialize-after-timedwait fix
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5418
//      put excessive stress on malloc/free and locks protecting the c-heap.
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5419
//
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5420
// We currently use (4).  See the WorkAroundNTPLTimedWaitHang flag.
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5421
// It may be possible to refine (4) by checking the kernel and NTPL verisons
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5422
// and only enabling the work-around for vulnerable environments.
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5423
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5424
// utility to compute the abstime argument to timedwait:
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5425
// millis is the relative timeout time
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5426
// abstime will be the absolute timeout time
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5427
// TODO: replace compute_abstime() with unpackTime()
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5428
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5429
static struct timespec* compute_abstime(timespec* abstime, jlong millis) {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5430
  if (millis < 0)  millis = 0;
19964
a3a04a9d29ac 6900441: PlatformEvent.park(millis) on Linux could still be affected by changes to the time-of-day clock
dholmes
parents: 19732
diff changeset
  5431
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5432
  jlong seconds = millis / 1000;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5433
  millis %= 1000;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5434
  if (seconds > 50000000) { // see man cond_timedwait(3T)
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5435
    seconds = 50000000;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5436
  }
19964
a3a04a9d29ac 6900441: PlatformEvent.park(millis) on Linux could still be affected by changes to the time-of-day clock
dholmes
parents: 19732
diff changeset
  5437
22891
1f5d1fff23fa 6546236: Thread interrupt() of Thread.sleep() can be lost on Solaris due to race with signal handler
fparain
parents: 22749
diff changeset
  5438
  if (os::supports_monotonic_clock()) {
19964
a3a04a9d29ac 6900441: PlatformEvent.park(millis) on Linux could still be affected by changes to the time-of-day clock
dholmes
parents: 19732
diff changeset
  5439
    struct timespec now;
a3a04a9d29ac 6900441: PlatformEvent.park(millis) on Linux could still be affected by changes to the time-of-day clock
dholmes
parents: 19732
diff changeset
  5440
    int status = os::Linux::clock_gettime(CLOCK_MONOTONIC, &now);
a3a04a9d29ac 6900441: PlatformEvent.park(millis) on Linux could still be affected by changes to the time-of-day clock
dholmes
parents: 19732
diff changeset
  5441
    assert_status(status == 0, status, "clock_gettime");
a3a04a9d29ac 6900441: PlatformEvent.park(millis) on Linux could still be affected by changes to the time-of-day clock
dholmes
parents: 19732
diff changeset
  5442
    abstime->tv_sec = now.tv_sec  + seconds;
a3a04a9d29ac 6900441: PlatformEvent.park(millis) on Linux could still be affected by changes to the time-of-day clock
dholmes
parents: 19732
diff changeset
  5443
    long nanos = now.tv_nsec + millis * NANOSECS_PER_MILLISEC;
a3a04a9d29ac 6900441: PlatformEvent.park(millis) on Linux could still be affected by changes to the time-of-day clock
dholmes
parents: 19732
diff changeset
  5444
    if (nanos >= NANOSECS_PER_SEC) {
a3a04a9d29ac 6900441: PlatformEvent.park(millis) on Linux could still be affected by changes to the time-of-day clock
dholmes
parents: 19732
diff changeset
  5445
      abstime->tv_sec += 1;
a3a04a9d29ac 6900441: PlatformEvent.park(millis) on Linux could still be affected by changes to the time-of-day clock
dholmes
parents: 19732
diff changeset
  5446
      nanos -= NANOSECS_PER_SEC;
a3a04a9d29ac 6900441: PlatformEvent.park(millis) on Linux could still be affected by changes to the time-of-day clock
dholmes
parents: 19732
diff changeset
  5447
    }
a3a04a9d29ac 6900441: PlatformEvent.park(millis) on Linux could still be affected by changes to the time-of-day clock
dholmes
parents: 19732
diff changeset
  5448
    abstime->tv_nsec = nanos;
a3a04a9d29ac 6900441: PlatformEvent.park(millis) on Linux could still be affected by changes to the time-of-day clock
dholmes
parents: 19732
diff changeset
  5449
  } else {
a3a04a9d29ac 6900441: PlatformEvent.park(millis) on Linux could still be affected by changes to the time-of-day clock
dholmes
parents: 19732
diff changeset
  5450
    struct timeval now;
a3a04a9d29ac 6900441: PlatformEvent.park(millis) on Linux could still be affected by changes to the time-of-day clock
dholmes
parents: 19732
diff changeset
  5451
    int status = gettimeofday(&now, NULL);
a3a04a9d29ac 6900441: PlatformEvent.park(millis) on Linux could still be affected by changes to the time-of-day clock
dholmes
parents: 19732
diff changeset
  5452
    assert(status == 0, "gettimeofday");
a3a04a9d29ac 6900441: PlatformEvent.park(millis) on Linux could still be affected by changes to the time-of-day clock
dholmes
parents: 19732
diff changeset
  5453
    abstime->tv_sec = now.tv_sec  + seconds;
a3a04a9d29ac 6900441: PlatformEvent.park(millis) on Linux could still be affected by changes to the time-of-day clock
dholmes
parents: 19732
diff changeset
  5454
    long usec = now.tv_usec + millis * 1000;
a3a04a9d29ac 6900441: PlatformEvent.park(millis) on Linux could still be affected by changes to the time-of-day clock
dholmes
parents: 19732
diff changeset
  5455
    if (usec >= 1000000) {
a3a04a9d29ac 6900441: PlatformEvent.park(millis) on Linux could still be affected by changes to the time-of-day clock
dholmes
parents: 19732
diff changeset
  5456
      abstime->tv_sec += 1;
a3a04a9d29ac 6900441: PlatformEvent.park(millis) on Linux could still be affected by changes to the time-of-day clock
dholmes
parents: 19732
diff changeset
  5457
      usec -= 1000000;
a3a04a9d29ac 6900441: PlatformEvent.park(millis) on Linux could still be affected by changes to the time-of-day clock
dholmes
parents: 19732
diff changeset
  5458
    }
a3a04a9d29ac 6900441: PlatformEvent.park(millis) on Linux could still be affected by changes to the time-of-day clock
dholmes
parents: 19732
diff changeset
  5459
    abstime->tv_nsec = usec * 1000;
a3a04a9d29ac 6900441: PlatformEvent.park(millis) on Linux could still be affected by changes to the time-of-day clock
dholmes
parents: 19732
diff changeset
  5460
  }
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5461
  return abstime;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5462
}
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5463
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5464
void os::PlatformEvent::park() {       // AKA "down()"
27458
eb5f1b4f01e1 8061552: Contended Locking speedup PlatformEvent unpark bucket
dcubed
parents: 27457
diff changeset
  5465
  // Transitions for _Event:
eb5f1b4f01e1 8061552: Contended Locking speedup PlatformEvent unpark bucket
dcubed
parents: 27457
diff changeset
  5466
  //   -1 => -1 : illegal
eb5f1b4f01e1 8061552: Contended Locking speedup PlatformEvent unpark bucket
dcubed
parents: 27457
diff changeset
  5467
  //    1 =>  0 : pass - return immediately
eb5f1b4f01e1 8061552: Contended Locking speedup PlatformEvent unpark bucket
dcubed
parents: 27457
diff changeset
  5468
  //    0 => -1 : block; then set _Event to 0 before returning
eb5f1b4f01e1 8061552: Contended Locking speedup PlatformEvent unpark bucket
dcubed
parents: 27457
diff changeset
  5469
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5470
  // Invariant: Only the thread associated with the Event/PlatformEvent
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5471
  // may call park().
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5472
  // TODO: assert that _Assoc != NULL or _Assoc == Self
25472
381638db28e6 8047104: cleanup misc issues prior to Contended Locking reorder and cache
dcubed
parents: 25468
diff changeset
  5473
  assert(_nParked == 0, "invariant");
381638db28e6 8047104: cleanup misc issues prior to Contended Locking reorder and cache
dcubed
parents: 25468
diff changeset
  5474
25064
244218e6ec0a 8046758: cleanup non-indent white space issues prior to Contended Locking cleanup bucket
dcubed
parents: 24931
diff changeset
  5475
  int v;
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5476
  for (;;) {
26683
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  5477
    v = _Event;
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  5478
    if (Atomic::cmpxchg(v-1, &_Event, v) == v) break;
25064
244218e6ec0a 8046758: cleanup non-indent white space issues prior to Contended Locking cleanup bucket
dcubed
parents: 24931
diff changeset
  5479
  }
244218e6ec0a 8046758: cleanup non-indent white space issues prior to Contended Locking cleanup bucket
dcubed
parents: 24931
diff changeset
  5480
  guarantee(v >= 0, "invariant");
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5481
  if (v == 0) {
26683
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  5482
    // Do this the hard way by blocking ...
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  5483
    int status = pthread_mutex_lock(_mutex);
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  5484
    assert_status(status == 0, status, "mutex_lock");
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  5485
    guarantee(_nParked == 0, "invariant");
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  5486
    ++_nParked;
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  5487
    while (_Event < 0) {
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  5488
      status = pthread_cond_wait(_cond, _mutex);
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  5489
      // for some reason, under 2.7 lwp_cond_wait() may return ETIME ...
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  5490
      // Treat this the same as if the wait was interrupted
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  5491
      if (status == ETIME) { status = EINTR; }
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  5492
      assert_status(status == 0 || status == EINTR, status, "cond_wait");
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  5493
    }
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  5494
    --_nParked;
25064
244218e6ec0a 8046758: cleanup non-indent white space issues prior to Contended Locking cleanup bucket
dcubed
parents: 24931
diff changeset
  5495
244218e6ec0a 8046758: cleanup non-indent white space issues prior to Contended Locking cleanup bucket
dcubed
parents: 24931
diff changeset
  5496
    _Event = 0;
26683
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  5497
    status = pthread_mutex_unlock(_mutex);
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  5498
    assert_status(status == 0, status, "mutex_unlock");
15234
ff1f01be5fbd 8004902: correctness fixes motivated by contended locking work (6607129)
dcubed
parents: 15096
diff changeset
  5499
    // Paranoia to ensure our locked and lock-free paths interact
ff1f01be5fbd 8004902: correctness fixes motivated by contended locking work (6607129)
dcubed
parents: 15096
diff changeset
  5500
    // correctly with each other.
ff1f01be5fbd 8004902: correctness fixes motivated by contended locking work (6607129)
dcubed
parents: 15096
diff changeset
  5501
    OrderAccess::fence();
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5502
  }
25064
244218e6ec0a 8046758: cleanup non-indent white space issues prior to Contended Locking cleanup bucket
dcubed
parents: 24931
diff changeset
  5503
  guarantee(_Event >= 0, "invariant");
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5504
}
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5505
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5506
int os::PlatformEvent::park(jlong millis) {
27458
eb5f1b4f01e1 8061552: Contended Locking speedup PlatformEvent unpark bucket
dcubed
parents: 27457
diff changeset
  5507
  // Transitions for _Event:
eb5f1b4f01e1 8061552: Contended Locking speedup PlatformEvent unpark bucket
dcubed
parents: 27457
diff changeset
  5508
  //   -1 => -1 : illegal
eb5f1b4f01e1 8061552: Contended Locking speedup PlatformEvent unpark bucket
dcubed
parents: 27457
diff changeset
  5509
  //    1 =>  0 : pass - return immediately
eb5f1b4f01e1 8061552: Contended Locking speedup PlatformEvent unpark bucket
dcubed
parents: 27457
diff changeset
  5510
  //    0 => -1 : block; then set _Event to 0 before returning
eb5f1b4f01e1 8061552: Contended Locking speedup PlatformEvent unpark bucket
dcubed
parents: 27457
diff changeset
  5511
25064
244218e6ec0a 8046758: cleanup non-indent white space issues prior to Contended Locking cleanup bucket
dcubed
parents: 24931
diff changeset
  5512
  guarantee(_nParked == 0, "invariant");
244218e6ec0a 8046758: cleanup non-indent white space issues prior to Contended Locking cleanup bucket
dcubed
parents: 24931
diff changeset
  5513
244218e6ec0a 8046758: cleanup non-indent white space issues prior to Contended Locking cleanup bucket
dcubed
parents: 24931
diff changeset
  5514
  int v;
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5515
  for (;;) {
26683
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  5516
    v = _Event;
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  5517
    if (Atomic::cmpxchg(v-1, &_Event, v) == v) break;
25064
244218e6ec0a 8046758: cleanup non-indent white space issues prior to Contended Locking cleanup bucket
dcubed
parents: 24931
diff changeset
  5518
  }
244218e6ec0a 8046758: cleanup non-indent white space issues prior to Contended Locking cleanup bucket
dcubed
parents: 24931
diff changeset
  5519
  guarantee(v >= 0, "invariant");
244218e6ec0a 8046758: cleanup non-indent white space issues prior to Contended Locking cleanup bucket
dcubed
parents: 24931
diff changeset
  5520
  if (v != 0) return OS_OK;
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5521
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5522
  // We do this the hard way, by blocking the thread.
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5523
  // Consider enforcing a minimum timeout value.
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5524
  struct timespec abst;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5525
  compute_abstime(&abst, millis);
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5526
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5527
  int ret = OS_TIMEOUT;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5528
  int status = pthread_mutex_lock(_mutex);
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5529
  assert_status(status == 0, status, "mutex_lock");
25064
244218e6ec0a 8046758: cleanup non-indent white space issues prior to Contended Locking cleanup bucket
dcubed
parents: 24931
diff changeset
  5530
  guarantee(_nParked == 0, "invariant");
244218e6ec0a 8046758: cleanup non-indent white space issues prior to Contended Locking cleanup bucket
dcubed
parents: 24931
diff changeset
  5531
  ++_nParked;
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5532
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5533
  // Object.wait(timo) will return because of
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5534
  // (a) notification
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5535
  // (b) timeout
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5536
  // (c) thread.interrupt
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5537
  //
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5538
  // Thread.interrupt and object.notify{All} both call Event::set.
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5539
  // That is, we treat thread.interrupt as a special case of notification.
24931
4bba680186bd 8044339: Update FilterSpuriousWakeups documentation. Review "Solaris only" vm options descriptions
iignatyev
parents: 24424
diff changeset
  5540
  // We ignore spurious OS wakeups unless FilterSpuriousWakeups is false.
4bba680186bd 8044339: Update FilterSpuriousWakeups documentation. Review "Solaris only" vm options descriptions
iignatyev
parents: 24424
diff changeset
  5541
  // We assume all ETIME returns are valid.
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5542
  //
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5543
  // TODO: properly differentiate simultaneous notify+interrupt.
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5544
  // In that case, we should propagate the notify to another waiter.
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5545
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5546
  while (_Event < 0) {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5547
    status = os::Linux::safe_cond_timedwait(_cond, _mutex, &abst);
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5548
    if (status != 0 && WorkAroundNPTLTimedWaitHang) {
25064
244218e6ec0a 8046758: cleanup non-indent white space issues prior to Contended Locking cleanup bucket
dcubed
parents: 24931
diff changeset
  5549
      pthread_cond_destroy(_cond);
244218e6ec0a 8046758: cleanup non-indent white space issues prior to Contended Locking cleanup bucket
dcubed
parents: 24931
diff changeset
  5550
      pthread_cond_init(_cond, os::Linux::condAttr());
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5551
    }
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5552
    assert_status(status == 0 || status == EINTR ||
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5553
                  status == ETIME || status == ETIMEDOUT,
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5554
                  status, "cond_timedwait");
25064
244218e6ec0a 8046758: cleanup non-indent white space issues prior to Contended Locking cleanup bucket
dcubed
parents: 24931
diff changeset
  5555
    if (!FilterSpuriousWakeups) break;                 // previous semantics
244218e6ec0a 8046758: cleanup non-indent white space issues prior to Contended Locking cleanup bucket
dcubed
parents: 24931
diff changeset
  5556
    if (status == ETIME || status == ETIMEDOUT) break;
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5557
    // We consume and ignore EINTR and spurious wakeups.
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5558
  }
25064
244218e6ec0a 8046758: cleanup non-indent white space issues prior to Contended Locking cleanup bucket
dcubed
parents: 24931
diff changeset
  5559
  --_nParked;
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5560
  if (_Event >= 0) {
26683
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  5561
    ret = OS_OK;
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5562
  }
25064
244218e6ec0a 8046758: cleanup non-indent white space issues prior to Contended Locking cleanup bucket
dcubed
parents: 24931
diff changeset
  5563
  _Event = 0;
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5564
  status = pthread_mutex_unlock(_mutex);
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5565
  assert_status(status == 0, status, "mutex_unlock");
25064
244218e6ec0a 8046758: cleanup non-indent white space issues prior to Contended Locking cleanup bucket
dcubed
parents: 24931
diff changeset
  5566
  assert(_nParked == 0, "invariant");
15234
ff1f01be5fbd 8004902: correctness fixes motivated by contended locking work (6607129)
dcubed
parents: 15096
diff changeset
  5567
  // Paranoia to ensure our locked and lock-free paths interact
ff1f01be5fbd 8004902: correctness fixes motivated by contended locking work (6607129)
dcubed
parents: 15096
diff changeset
  5568
  // correctly with each other.
ff1f01be5fbd 8004902: correctness fixes motivated by contended locking work (6607129)
dcubed
parents: 15096
diff changeset
  5569
  OrderAccess::fence();
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5570
  return ret;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5571
}
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5572
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5573
void os::PlatformEvent::unpark() {
15234
ff1f01be5fbd 8004902: correctness fixes motivated by contended locking work (6607129)
dcubed
parents: 15096
diff changeset
  5574
  // Transitions for _Event:
27458
eb5f1b4f01e1 8061552: Contended Locking speedup PlatformEvent unpark bucket
dcubed
parents: 27457
diff changeset
  5575
  //    0 => 1 : just return
eb5f1b4f01e1 8061552: Contended Locking speedup PlatformEvent unpark bucket
dcubed
parents: 27457
diff changeset
  5576
  //    1 => 1 : just return
eb5f1b4f01e1 8061552: Contended Locking speedup PlatformEvent unpark bucket
dcubed
parents: 27457
diff changeset
  5577
  //   -1 => either 0 or 1; must signal target thread
eb5f1b4f01e1 8061552: Contended Locking speedup PlatformEvent unpark bucket
dcubed
parents: 27457
diff changeset
  5578
  //         That is, we can safely transition _Event from -1 to either
eb5f1b4f01e1 8061552: Contended Locking speedup PlatformEvent unpark bucket
dcubed
parents: 27457
diff changeset
  5579
  //         0 or 1.
15234
ff1f01be5fbd 8004902: correctness fixes motivated by contended locking work (6607129)
dcubed
parents: 15096
diff changeset
  5580
  // See also: "Semaphores in Plan 9" by Mullender & Cox
ff1f01be5fbd 8004902: correctness fixes motivated by contended locking work (6607129)
dcubed
parents: 15096
diff changeset
  5581
  //
ff1f01be5fbd 8004902: correctness fixes motivated by contended locking work (6607129)
dcubed
parents: 15096
diff changeset
  5582
  // Note: Forcing a transition from "-1" to "1" on an unpark() means
ff1f01be5fbd 8004902: correctness fixes motivated by contended locking work (6607129)
dcubed
parents: 15096
diff changeset
  5583
  // that it will take two back-to-back park() calls for the owning
ff1f01be5fbd 8004902: correctness fixes motivated by contended locking work (6607129)
dcubed
parents: 15096
diff changeset
  5584
  // thread to block. This has the benefit of forcing a spurious return
ff1f01be5fbd 8004902: correctness fixes motivated by contended locking work (6607129)
dcubed
parents: 15096
diff changeset
  5585
  // from the first park() call after an unpark() call which will help
ff1f01be5fbd 8004902: correctness fixes motivated by contended locking work (6607129)
dcubed
parents: 15096
diff changeset
  5586
  // shake out uses of park() and unpark() without condition variables.
ff1f01be5fbd 8004902: correctness fixes motivated by contended locking work (6607129)
dcubed
parents: 15096
diff changeset
  5587
ff1f01be5fbd 8004902: correctness fixes motivated by contended locking work (6607129)
dcubed
parents: 15096
diff changeset
  5588
  if (Atomic::xchg(1, &_Event) >= 0) return;
ff1f01be5fbd 8004902: correctness fixes motivated by contended locking work (6607129)
dcubed
parents: 15096
diff changeset
  5589
ff1f01be5fbd 8004902: correctness fixes motivated by contended locking work (6607129)
dcubed
parents: 15096
diff changeset
  5590
  // Wait for the thread associated with the event to vacate
ff1f01be5fbd 8004902: correctness fixes motivated by contended locking work (6607129)
dcubed
parents: 15096
diff changeset
  5591
  int status = pthread_mutex_lock(_mutex);
ff1f01be5fbd 8004902: correctness fixes motivated by contended locking work (6607129)
dcubed
parents: 15096
diff changeset
  5592
  assert_status(status == 0, status, "mutex_lock");
ff1f01be5fbd 8004902: correctness fixes motivated by contended locking work (6607129)
dcubed
parents: 15096
diff changeset
  5593
  int AnyWaiters = _nParked;
ff1f01be5fbd 8004902: correctness fixes motivated by contended locking work (6607129)
dcubed
parents: 15096
diff changeset
  5594
  assert(AnyWaiters == 0 || AnyWaiters == 1, "invariant");
ff1f01be5fbd 8004902: correctness fixes motivated by contended locking work (6607129)
dcubed
parents: 15096
diff changeset
  5595
  if (AnyWaiters != 0 && WorkAroundNPTLTimedWaitHang) {
ff1f01be5fbd 8004902: correctness fixes motivated by contended locking work (6607129)
dcubed
parents: 15096
diff changeset
  5596
    AnyWaiters = 0;
ff1f01be5fbd 8004902: correctness fixes motivated by contended locking work (6607129)
dcubed
parents: 15096
diff changeset
  5597
    pthread_cond_signal(_cond);
ff1f01be5fbd 8004902: correctness fixes motivated by contended locking work (6607129)
dcubed
parents: 15096
diff changeset
  5598
  }
ff1f01be5fbd 8004902: correctness fixes motivated by contended locking work (6607129)
dcubed
parents: 15096
diff changeset
  5599
  status = pthread_mutex_unlock(_mutex);
ff1f01be5fbd 8004902: correctness fixes motivated by contended locking work (6607129)
dcubed
parents: 15096
diff changeset
  5600
  assert_status(status == 0, status, "mutex_unlock");
ff1f01be5fbd 8004902: correctness fixes motivated by contended locking work (6607129)
dcubed
parents: 15096
diff changeset
  5601
  if (AnyWaiters != 0) {
27458
eb5f1b4f01e1 8061552: Contended Locking speedup PlatformEvent unpark bucket
dcubed
parents: 27457
diff changeset
  5602
    // Note that we signal() *after* dropping the lock for "immortal" Events.
eb5f1b4f01e1 8061552: Contended Locking speedup PlatformEvent unpark bucket
dcubed
parents: 27457
diff changeset
  5603
    // This is safe and avoids a common class of  futile wakeups.  In rare
eb5f1b4f01e1 8061552: Contended Locking speedup PlatformEvent unpark bucket
dcubed
parents: 27457
diff changeset
  5604
    // circumstances this can cause a thread to return prematurely from
eb5f1b4f01e1 8061552: Contended Locking speedup PlatformEvent unpark bucket
dcubed
parents: 27457
diff changeset
  5605
    // cond_{timed}wait() but the spurious wakeup is benign and the victim
eb5f1b4f01e1 8061552: Contended Locking speedup PlatformEvent unpark bucket
dcubed
parents: 27457
diff changeset
  5606
    // will simply re-test the condition and re-park itself.
eb5f1b4f01e1 8061552: Contended Locking speedup PlatformEvent unpark bucket
dcubed
parents: 27457
diff changeset
  5607
    // This provides particular benefit if the underlying platform does not
eb5f1b4f01e1 8061552: Contended Locking speedup PlatformEvent unpark bucket
dcubed
parents: 27457
diff changeset
  5608
    // provide wait morphing.
15234
ff1f01be5fbd 8004902: correctness fixes motivated by contended locking work (6607129)
dcubed
parents: 15096
diff changeset
  5609
    status = pthread_cond_signal(_cond);
ff1f01be5fbd 8004902: correctness fixes motivated by contended locking work (6607129)
dcubed
parents: 15096
diff changeset
  5610
    assert_status(status == 0, status, "cond_signal");
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5611
  }
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5612
}
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5613
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5614
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5615
// JSR166
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5616
// -------------------------------------------------------
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5617
26684
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
  5618
// The solaris and linux implementations of park/unpark are fairly
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
  5619
// conservative for now, but can be improved. They currently use a
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
  5620
// mutex/condvar pair, plus a a count.
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
  5621
// Park decrements count if > 0, else does a condvar wait.  Unpark
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
  5622
// sets count to 1 and signals condvar.  Only one thread ever waits
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
  5623
// on the condvar. Contention seen when trying to park implies that someone
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
  5624
// is unparking you, so don't wait. And spurious returns are fine, so there
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
  5625
// is no need to track notifications.
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
  5626
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
  5627
// This code is common to linux and solaris and will be moved to a
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
  5628
// common place in dolphin.
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
  5629
//
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
  5630
// The passed in time value is either a relative time in nanoseconds
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
  5631
// or an absolute time in milliseconds. Either way it has to be unpacked
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
  5632
// into suitable seconds and nanoseconds components and stored in the
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
  5633
// given timespec structure.
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
  5634
// Given time is a 64-bit value and the time_t used in the timespec is only
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
  5635
// a signed-32-bit value (except on 64-bit Linux) we have to watch for
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
  5636
// overflow if times way in the future are given. Further on Solaris versions
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
  5637
// prior to 10 there is a restriction (see cond_timedwait) that the specified
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
  5638
// number of seconds, in abstime, is less than current_time  + 100,000,000.
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
  5639
// As it will be 28 years before "now + 100000000" will overflow we can
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
  5640
// ignore overflow and just impose a hard-limit on seconds using the value
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
  5641
// of "now + 100,000,000". This places a limit on the timeout of about 3.17
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
  5642
// years from "now".
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5643
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5644
static void unpackTime(timespec* absTime, bool isAbsolute, jlong time) {
25064
244218e6ec0a 8046758: cleanup non-indent white space issues prior to Contended Locking cleanup bucket
dcubed
parents: 24931
diff changeset
  5645
  assert(time > 0, "convertTime");
19964
a3a04a9d29ac 6900441: PlatformEvent.park(millis) on Linux could still be affected by changes to the time-of-day clock
dholmes
parents: 19732
diff changeset
  5646
  time_t max_secs = 0;
a3a04a9d29ac 6900441: PlatformEvent.park(millis) on Linux could still be affected by changes to the time-of-day clock
dholmes
parents: 19732
diff changeset
  5647
22891
1f5d1fff23fa 6546236: Thread interrupt() of Thread.sleep() can be lost on Solaris due to race with signal handler
fparain
parents: 22749
diff changeset
  5648
  if (!os::supports_monotonic_clock() || isAbsolute) {
19964
a3a04a9d29ac 6900441: PlatformEvent.park(millis) on Linux could still be affected by changes to the time-of-day clock
dholmes
parents: 19732
diff changeset
  5649
    struct timeval now;
a3a04a9d29ac 6900441: PlatformEvent.park(millis) on Linux could still be affected by changes to the time-of-day clock
dholmes
parents: 19732
diff changeset
  5650
    int status = gettimeofday(&now, NULL);
a3a04a9d29ac 6900441: PlatformEvent.park(millis) on Linux could still be affected by changes to the time-of-day clock
dholmes
parents: 19732
diff changeset
  5651
    assert(status == 0, "gettimeofday");
a3a04a9d29ac 6900441: PlatformEvent.park(millis) on Linux could still be affected by changes to the time-of-day clock
dholmes
parents: 19732
diff changeset
  5652
a3a04a9d29ac 6900441: PlatformEvent.park(millis) on Linux could still be affected by changes to the time-of-day clock
dholmes
parents: 19732
diff changeset
  5653
    max_secs = now.tv_sec + MAX_SECS;
a3a04a9d29ac 6900441: PlatformEvent.park(millis) on Linux could still be affected by changes to the time-of-day clock
dholmes
parents: 19732
diff changeset
  5654
a3a04a9d29ac 6900441: PlatformEvent.park(millis) on Linux could still be affected by changes to the time-of-day clock
dholmes
parents: 19732
diff changeset
  5655
    if (isAbsolute) {
a3a04a9d29ac 6900441: PlatformEvent.park(millis) on Linux could still be affected by changes to the time-of-day clock
dholmes
parents: 19732
diff changeset
  5656
      jlong secs = time / 1000;
a3a04a9d29ac 6900441: PlatformEvent.park(millis) on Linux could still be affected by changes to the time-of-day clock
dholmes
parents: 19732
diff changeset
  5657
      if (secs > max_secs) {
a3a04a9d29ac 6900441: PlatformEvent.park(millis) on Linux could still be affected by changes to the time-of-day clock
dholmes
parents: 19732
diff changeset
  5658
        absTime->tv_sec = max_secs;
a3a04a9d29ac 6900441: PlatformEvent.park(millis) on Linux could still be affected by changes to the time-of-day clock
dholmes
parents: 19732
diff changeset
  5659
      } else {
a3a04a9d29ac 6900441: PlatformEvent.park(millis) on Linux could still be affected by changes to the time-of-day clock
dholmes
parents: 19732
diff changeset
  5660
        absTime->tv_sec = secs;
a3a04a9d29ac 6900441: PlatformEvent.park(millis) on Linux could still be affected by changes to the time-of-day clock
dholmes
parents: 19732
diff changeset
  5661
      }
a3a04a9d29ac 6900441: PlatformEvent.park(millis) on Linux could still be affected by changes to the time-of-day clock
dholmes
parents: 19732
diff changeset
  5662
      absTime->tv_nsec = (time % 1000) * NANOSECS_PER_MILLISEC;
a3a04a9d29ac 6900441: PlatformEvent.park(millis) on Linux could still be affected by changes to the time-of-day clock
dholmes
parents: 19732
diff changeset
  5663
    } else {
a3a04a9d29ac 6900441: PlatformEvent.park(millis) on Linux could still be affected by changes to the time-of-day clock
dholmes
parents: 19732
diff changeset
  5664
      jlong secs = time / NANOSECS_PER_SEC;
a3a04a9d29ac 6900441: PlatformEvent.park(millis) on Linux could still be affected by changes to the time-of-day clock
dholmes
parents: 19732
diff changeset
  5665
      if (secs >= MAX_SECS) {
a3a04a9d29ac 6900441: PlatformEvent.park(millis) on Linux could still be affected by changes to the time-of-day clock
dholmes
parents: 19732
diff changeset
  5666
        absTime->tv_sec = max_secs;
a3a04a9d29ac 6900441: PlatformEvent.park(millis) on Linux could still be affected by changes to the time-of-day clock
dholmes
parents: 19732
diff changeset
  5667
        absTime->tv_nsec = 0;
a3a04a9d29ac 6900441: PlatformEvent.park(millis) on Linux could still be affected by changes to the time-of-day clock
dholmes
parents: 19732
diff changeset
  5668
      } else {
a3a04a9d29ac 6900441: PlatformEvent.park(millis) on Linux could still be affected by changes to the time-of-day clock
dholmes
parents: 19732
diff changeset
  5669
        absTime->tv_sec = now.tv_sec + secs;
a3a04a9d29ac 6900441: PlatformEvent.park(millis) on Linux could still be affected by changes to the time-of-day clock
dholmes
parents: 19732
diff changeset
  5670
        absTime->tv_nsec = (time % NANOSECS_PER_SEC) + now.tv_usec*1000;
a3a04a9d29ac 6900441: PlatformEvent.park(millis) on Linux could still be affected by changes to the time-of-day clock
dholmes
parents: 19732
diff changeset
  5671
        if (absTime->tv_nsec >= NANOSECS_PER_SEC) {
a3a04a9d29ac 6900441: PlatformEvent.park(millis) on Linux could still be affected by changes to the time-of-day clock
dholmes
parents: 19732
diff changeset
  5672
          absTime->tv_nsec -= NANOSECS_PER_SEC;
a3a04a9d29ac 6900441: PlatformEvent.park(millis) on Linux could still be affected by changes to the time-of-day clock
dholmes
parents: 19732
diff changeset
  5673
          ++absTime->tv_sec; // note: this must be <= max_secs
a3a04a9d29ac 6900441: PlatformEvent.park(millis) on Linux could still be affected by changes to the time-of-day clock
dholmes
parents: 19732
diff changeset
  5674
        }
a3a04a9d29ac 6900441: PlatformEvent.park(millis) on Linux could still be affected by changes to the time-of-day clock
dholmes
parents: 19732
diff changeset
  5675
      }
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5676
    }
19964
a3a04a9d29ac 6900441: PlatformEvent.park(millis) on Linux could still be affected by changes to the time-of-day clock
dholmes
parents: 19732
diff changeset
  5677
  } else {
a3a04a9d29ac 6900441: PlatformEvent.park(millis) on Linux could still be affected by changes to the time-of-day clock
dholmes
parents: 19732
diff changeset
  5678
    // must be relative using monotonic clock
a3a04a9d29ac 6900441: PlatformEvent.park(millis) on Linux could still be affected by changes to the time-of-day clock
dholmes
parents: 19732
diff changeset
  5679
    struct timespec now;
a3a04a9d29ac 6900441: PlatformEvent.park(millis) on Linux could still be affected by changes to the time-of-day clock
dholmes
parents: 19732
diff changeset
  5680
    int status = os::Linux::clock_gettime(CLOCK_MONOTONIC, &now);
a3a04a9d29ac 6900441: PlatformEvent.park(millis) on Linux could still be affected by changes to the time-of-day clock
dholmes
parents: 19732
diff changeset
  5681
    assert_status(status == 0, status, "clock_gettime");
a3a04a9d29ac 6900441: PlatformEvent.park(millis) on Linux could still be affected by changes to the time-of-day clock
dholmes
parents: 19732
diff changeset
  5682
    max_secs = now.tv_sec + MAX_SECS;
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5683
    jlong secs = time / NANOSECS_PER_SEC;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5684
    if (secs >= MAX_SECS) {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5685
      absTime->tv_sec = max_secs;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5686
      absTime->tv_nsec = 0;
19964
a3a04a9d29ac 6900441: PlatformEvent.park(millis) on Linux could still be affected by changes to the time-of-day clock
dholmes
parents: 19732
diff changeset
  5687
    } else {
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5688
      absTime->tv_sec = now.tv_sec + secs;
19964
a3a04a9d29ac 6900441: PlatformEvent.park(millis) on Linux could still be affected by changes to the time-of-day clock
dholmes
parents: 19732
diff changeset
  5689
      absTime->tv_nsec = (time % NANOSECS_PER_SEC) + now.tv_nsec;
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5690
      if (absTime->tv_nsec >= NANOSECS_PER_SEC) {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5691
        absTime->tv_nsec -= NANOSECS_PER_SEC;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5692
        ++absTime->tv_sec; // note: this must be <= max_secs
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5693
      }
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5694
    }
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5695
  }
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5696
  assert(absTime->tv_sec >= 0, "tv_sec < 0");
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5697
  assert(absTime->tv_sec <= max_secs, "tv_sec > max_secs");
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5698
  assert(absTime->tv_nsec >= 0, "tv_nsec < 0");
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5699
  assert(absTime->tv_nsec < NANOSECS_PER_SEC, "tv_nsec >= nanos_per_sec");
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5700
}
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5701
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5702
void Parker::park(bool isAbsolute, jlong time) {
15234
ff1f01be5fbd 8004902: correctness fixes motivated by contended locking work (6607129)
dcubed
parents: 15096
diff changeset
  5703
  // Ideally we'd do something useful while spinning, such
ff1f01be5fbd 8004902: correctness fixes motivated by contended locking work (6607129)
dcubed
parents: 15096
diff changeset
  5704
  // as calling unpackTime().
ff1f01be5fbd 8004902: correctness fixes motivated by contended locking work (6607129)
dcubed
parents: 15096
diff changeset
  5705
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5706
  // Optional fast-path check:
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5707
  // Return immediately if a permit is available.
15234
ff1f01be5fbd 8004902: correctness fixes motivated by contended locking work (6607129)
dcubed
parents: 15096
diff changeset
  5708
  // We depend on Atomic::xchg() having full barrier semantics
ff1f01be5fbd 8004902: correctness fixes motivated by contended locking work (6607129)
dcubed
parents: 15096
diff changeset
  5709
  // since we are doing a lock-free update to _counter.
ff1f01be5fbd 8004902: correctness fixes motivated by contended locking work (6607129)
dcubed
parents: 15096
diff changeset
  5710
  if (Atomic::xchg(0, &_counter) > 0) return;
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5711
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5712
  Thread* thread = Thread::current();
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5713
  assert(thread->is_Java_thread(), "Must be JavaThread");
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5714
  JavaThread *jt = (JavaThread *)thread;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5715
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5716
  // Optional optimization -- avoid state transitions if there's an interrupt pending.
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5717
  // Check interrupt before trying to wait
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5718
  if (Thread::is_interrupted(thread, false)) {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5719
    return;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5720
  }
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5721
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5722
  // Next, demultiplex/decode time arguments
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5723
  timespec absTime;
25064
244218e6ec0a 8046758: cleanup non-indent white space issues prior to Contended Locking cleanup bucket
dcubed
parents: 24931
diff changeset
  5724
  if (time < 0 || (isAbsolute && time == 0)) { // don't wait at all
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5725
    return;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5726
  }
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5727
  if (time > 0) {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5728
    unpackTime(&absTime, isAbsolute, time);
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5729
  }
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5730
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5731
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5732
  // Enter safepoint region
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5733
  // Beware of deadlocks such as 6317397.
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5734
  // The per-thread Parker:: mutex is a classic leaf-lock.
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5735
  // In particular a thread must never block on the Threads_lock while
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5736
  // holding the Parker:: mutex.  If safepoints are pending both the
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5737
  // the ThreadBlockInVM() CTOR and DTOR may grab Threads_lock.
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5738
  ThreadBlockInVM tbivm(jt);
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5739
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5740
  // Don't wait if cannot get lock since interference arises from
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5741
  // unblocking.  Also. check interrupt before trying wait
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5742
  if (Thread::is_interrupted(thread, false) || pthread_mutex_trylock(_mutex) != 0) {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5743
    return;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5744
  }
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5745
25064
244218e6ec0a 8046758: cleanup non-indent white space issues prior to Contended Locking cleanup bucket
dcubed
parents: 24931
diff changeset
  5746
  int status;
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5747
  if (_counter > 0)  { // no wait needed
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5748
    _counter = 0;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5749
    status = pthread_mutex_unlock(_mutex);
25064
244218e6ec0a 8046758: cleanup non-indent white space issues prior to Contended Locking cleanup bucket
dcubed
parents: 24931
diff changeset
  5750
    assert(status == 0, "invariant");
15234
ff1f01be5fbd 8004902: correctness fixes motivated by contended locking work (6607129)
dcubed
parents: 15096
diff changeset
  5751
    // Paranoia to ensure our locked and lock-free paths interact
ff1f01be5fbd 8004902: correctness fixes motivated by contended locking work (6607129)
dcubed
parents: 15096
diff changeset
  5752
    // correctly with each other and Java-level accesses.
4487
de1359156181 6822370: ReentrantReadWriteLock: threads hung when there are no threads holding onto the lock (Netra x4450)
dholmes
parents: 4013
diff changeset
  5753
    OrderAccess::fence();
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5754
    return;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5755
  }
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5756
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5757
#ifdef ASSERT
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5758
  // Don't catch signals while blocked; let the running threads have the signals.
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5759
  // (This allows a debugger to break into the running thread.)
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5760
  sigset_t oldsigs;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5761
  sigset_t* allowdebug_blocked = os::Linux::allowdebug_blocked_signals();
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5762
  pthread_sigmask(SIG_BLOCK, allowdebug_blocked, &oldsigs);
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5763
#endif
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5764
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5765
  OSThreadWaitState osts(thread->osthread(), false /* not Object.wait() */);
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5766
  jt->set_suspend_equivalent();
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5767
  // cleared by handle_special_suspend_equivalent_condition() or java_suspend_self()
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5768
19964
a3a04a9d29ac 6900441: PlatformEvent.park(millis) on Linux could still be affected by changes to the time-of-day clock
dholmes
parents: 19732
diff changeset
  5769
  assert(_cur_index == -1, "invariant");
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5770
  if (time == 0) {
19964
a3a04a9d29ac 6900441: PlatformEvent.park(millis) on Linux could still be affected by changes to the time-of-day clock
dholmes
parents: 19732
diff changeset
  5771
    _cur_index = REL_INDEX; // arbitrary choice when not timed
25064
244218e6ec0a 8046758: cleanup non-indent white space issues prior to Contended Locking cleanup bucket
dcubed
parents: 24931
diff changeset
  5772
    status = pthread_cond_wait(&_cond[_cur_index], _mutex);
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5773
  } else {
19964
a3a04a9d29ac 6900441: PlatformEvent.park(millis) on Linux could still be affected by changes to the time-of-day clock
dholmes
parents: 19732
diff changeset
  5774
    _cur_index = isAbsolute ? ABS_INDEX : REL_INDEX;
25064
244218e6ec0a 8046758: cleanup non-indent white space issues prior to Contended Locking cleanup bucket
dcubed
parents: 24931
diff changeset
  5775
    status = os::Linux::safe_cond_timedwait(&_cond[_cur_index], _mutex, &absTime);
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5776
    if (status != 0 && WorkAroundNPTLTimedWaitHang) {
25064
244218e6ec0a 8046758: cleanup non-indent white space issues prior to Contended Locking cleanup bucket
dcubed
parents: 24931
diff changeset
  5777
      pthread_cond_destroy(&_cond[_cur_index]);
244218e6ec0a 8046758: cleanup non-indent white space issues prior to Contended Locking cleanup bucket
dcubed
parents: 24931
diff changeset
  5778
      pthread_cond_init(&_cond[_cur_index], isAbsolute ? NULL : os::Linux::condAttr());
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5779
    }
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5780
  }
19964
a3a04a9d29ac 6900441: PlatformEvent.park(millis) on Linux could still be affected by changes to the time-of-day clock
dholmes
parents: 19732
diff changeset
  5781
  _cur_index = -1;
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5782
  assert_status(status == 0 || status == EINTR ||
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5783
                status == ETIME || status == ETIMEDOUT,
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5784
                status, "cond_timedwait");
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5785
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5786
#ifdef ASSERT
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5787
  pthread_sigmask(SIG_SETMASK, &oldsigs, NULL);
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5788
#endif
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5789
25064
244218e6ec0a 8046758: cleanup non-indent white space issues prior to Contended Locking cleanup bucket
dcubed
parents: 24931
diff changeset
  5790
  _counter = 0;
244218e6ec0a 8046758: cleanup non-indent white space issues prior to Contended Locking cleanup bucket
dcubed
parents: 24931
diff changeset
  5791
  status = pthread_mutex_unlock(_mutex);
244218e6ec0a 8046758: cleanup non-indent white space issues prior to Contended Locking cleanup bucket
dcubed
parents: 24931
diff changeset
  5792
  assert_status(status == 0, status, "invariant");
15234
ff1f01be5fbd 8004902: correctness fixes motivated by contended locking work (6607129)
dcubed
parents: 15096
diff changeset
  5793
  // Paranoia to ensure our locked and lock-free paths interact
ff1f01be5fbd 8004902: correctness fixes motivated by contended locking work (6607129)
dcubed
parents: 15096
diff changeset
  5794
  // correctly with each other and Java-level accesses.
ff1f01be5fbd 8004902: correctness fixes motivated by contended locking work (6607129)
dcubed
parents: 15096
diff changeset
  5795
  OrderAccess::fence();
ff1f01be5fbd 8004902: correctness fixes motivated by contended locking work (6607129)
dcubed
parents: 15096
diff changeset
  5796
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5797
  // If externally suspended while waiting, re-suspend
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5798
  if (jt->handle_special_suspend_equivalent_condition()) {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5799
    jt->java_suspend_self();
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5800
  }
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5801
}
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5802
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5803
void Parker::unpark() {
25472
381638db28e6 8047104: cleanup misc issues prior to Contended Locking reorder and cache
dcubed
parents: 25468
diff changeset
  5804
  int status = pthread_mutex_lock(_mutex);
25064
244218e6ec0a 8046758: cleanup non-indent white space issues prior to Contended Locking cleanup bucket
dcubed
parents: 24931
diff changeset
  5805
  assert(status == 0, "invariant");
25472
381638db28e6 8047104: cleanup misc issues prior to Contended Locking reorder and cache
dcubed
parents: 25468
diff changeset
  5806
  const int s = _counter;
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5807
  _counter = 1;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5808
  if (s < 1) {
19964
a3a04a9d29ac 6900441: PlatformEvent.park(millis) on Linux could still be affected by changes to the time-of-day clock
dholmes
parents: 19732
diff changeset
  5809
    // thread might be parked
a3a04a9d29ac 6900441: PlatformEvent.park(millis) on Linux could still be affected by changes to the time-of-day clock
dholmes
parents: 19732
diff changeset
  5810
    if (_cur_index != -1) {
a3a04a9d29ac 6900441: PlatformEvent.park(millis) on Linux could still be affected by changes to the time-of-day clock
dholmes
parents: 19732
diff changeset
  5811
      // thread is definitely parked
a3a04a9d29ac 6900441: PlatformEvent.park(millis) on Linux could still be affected by changes to the time-of-day clock
dholmes
parents: 19732
diff changeset
  5812
      if (WorkAroundNPTLTimedWaitHang) {
26684
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
  5813
        status = pthread_cond_signal(&_cond[_cur_index]);
25064
244218e6ec0a 8046758: cleanup non-indent white space issues prior to Contended Locking cleanup bucket
dcubed
parents: 24931
diff changeset
  5814
        assert(status == 0, "invariant");
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5815
        status = pthread_mutex_unlock(_mutex);
25064
244218e6ec0a 8046758: cleanup non-indent white space issues prior to Contended Locking cleanup bucket
dcubed
parents: 24931
diff changeset
  5816
        assert(status == 0, "invariant");
19964
a3a04a9d29ac 6900441: PlatformEvent.park(millis) on Linux could still be affected by changes to the time-of-day clock
dholmes
parents: 19732
diff changeset
  5817
      } else {
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5818
        status = pthread_mutex_unlock(_mutex);
25064
244218e6ec0a 8046758: cleanup non-indent white space issues prior to Contended Locking cleanup bucket
dcubed
parents: 24931
diff changeset
  5819
        assert(status == 0, "invariant");
26684
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
  5820
        status = pthread_cond_signal(&_cond[_cur_index]);
25064
244218e6ec0a 8046758: cleanup non-indent white space issues prior to Contended Locking cleanup bucket
dcubed
parents: 24931
diff changeset
  5821
        assert(status == 0, "invariant");
19964
a3a04a9d29ac 6900441: PlatformEvent.park(millis) on Linux could still be affected by changes to the time-of-day clock
dholmes
parents: 19732
diff changeset
  5822
      }
a3a04a9d29ac 6900441: PlatformEvent.park(millis) on Linux could still be affected by changes to the time-of-day clock
dholmes
parents: 19732
diff changeset
  5823
    } else {
a3a04a9d29ac 6900441: PlatformEvent.park(millis) on Linux could still be affected by changes to the time-of-day clock
dholmes
parents: 19732
diff changeset
  5824
      pthread_mutex_unlock(_mutex);
25064
244218e6ec0a 8046758: cleanup non-indent white space issues prior to Contended Locking cleanup bucket
dcubed
parents: 24931
diff changeset
  5825
      assert(status == 0, "invariant");
19964
a3a04a9d29ac 6900441: PlatformEvent.park(millis) on Linux could still be affected by changes to the time-of-day clock
dholmes
parents: 19732
diff changeset
  5826
    }
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5827
  } else {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5828
    pthread_mutex_unlock(_mutex);
25064
244218e6ec0a 8046758: cleanup non-indent white space issues prior to Contended Locking cleanup bucket
dcubed
parents: 24931
diff changeset
  5829
    assert(status == 0, "invariant");
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5830
  }
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5831
}
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5832
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5833
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5834
extern char** environ;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5835
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5836
#ifndef __NR_fork
29180
50369728b00e 8064611: AARCH64: Changes to HotSpot shared code
aph
parents: 27474
diff changeset
  5837
  #define __NR_fork IA32_ONLY(2) IA64_ONLY(not defined) AMD64_ONLY(57) AARCH64_ONLY(1079)
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5838
#endif
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5839
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5840
#ifndef __NR_execve
29180
50369728b00e 8064611: AARCH64: Changes to HotSpot shared code
aph
parents: 27474
diff changeset
  5841
  #define __NR_execve IA32_ONLY(11) IA64_ONLY(1033) AMD64_ONLY(59) AARCH64_ONLY(221)
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5842
#endif
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5843
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5844
// Run the specified command in a separate process. Return its exit value,
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5845
// or -1 on failure (e.g. can't fork a new process).
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5846
// Unlike system(), this function can be called from signal handler. It
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5847
// doesn't block SIGINT et al.
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5848
int os::fork_and_exec(char* cmd) {
745
47129a5cacd3 6681796: hotspot build failure on gcc 4.2.x (ubuntu 8.04) w/ openjdk 6
xlu
parents: 388
diff changeset
  5849
  const char * argv[4] = {"sh", "-c", cmd, NULL};
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5850
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5851
  // fork() in LinuxThreads/NPTL is not async-safe. It needs to run
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5852
  // pthread_atfork handlers and reset pthread library. All we need is a
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5853
  // separate process to execve. Make a direct syscall to fork process.
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5854
  // On IA64 there's no fork syscall, we have to use fork() and hope for
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5855
  // the best...
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5856
  pid_t pid = NOT_IA64(syscall(__NR_fork);)
26683
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  5857
  IA64_ONLY(fork();)
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5858
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5859
  if (pid < 0) {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5860
    // fork failed
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5861
    return -1;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5862
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5863
  } else if (pid == 0) {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5864
    // child process
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5865
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5866
    // execve() in LinuxThreads will call pthread_kill_other_threads_np()
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5867
    // first to kill every thread on the thread list. Because this list is
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5868
    // not reset by fork() (see notes above), execve() will instead kill
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5869
    // every thread in the parent process. We know this is the only thread
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5870
    // in the new process, so make a system call directly.
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5871
    // IA64 should use normal execve() from glibc to match the glibc fork()
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5872
    // above.
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5873
    NOT_IA64(syscall(__NR_execve, "/bin/sh", argv, environ);)
745
47129a5cacd3 6681796: hotspot build failure on gcc 4.2.x (ubuntu 8.04) w/ openjdk 6
xlu
parents: 388
diff changeset
  5874
    IA64_ONLY(execve("/bin/sh", (char* const*)argv, environ);)
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5875
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5876
    // execve failed
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5877
    _exit(-1);
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5878
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5879
  } else  {
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5880
    // copied from J2SE ..._waitForProcessExit() in UNIXProcess_md.c; we don't
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5881
    // care about the actual exit code, for now.
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5882
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5883
    int status;
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5884
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5885
    // Wait for the child process to exit.  This returns immediately if
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5886
    // the child has already exited. */
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5887
    while (waitpid(pid, &status, 0) < 0) {
26683
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  5888
      switch (errno) {
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  5889
      case ECHILD: return 0;
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  5890
      case EINTR: break;
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  5891
      default: return -1;
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  5892
      }
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5893
    }
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5894
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5895
    if (WIFEXITED(status)) {
26683
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  5896
      // The child exited normally; get its exit code.
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  5897
      return WEXITSTATUS(status);
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5898
    } else if (WIFSIGNALED(status)) {
26683
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  5899
      // The child exited because of a signal
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  5900
      // The best value to return is 0x80 + signal number,
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  5901
      // because that is what all Unix shells do, and because
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  5902
      // it allows callers to distinguish between process exit and
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  5903
      // process death by signal.
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  5904
      return 0x80 + WTERMSIG(status);
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5905
    } else {
26683
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  5906
      // Unknown exit code; pass it through
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  5907
      return status;
1
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5908
    }
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5909
  }
489c9b5090e2 Initial load
duke
parents:
diff changeset
  5910
}
6176
4d9030fe341f 6953477: Increase portability and flexibility of building Hotspot
bobv
parents: 5922
diff changeset
  5911
4d9030fe341f 6953477: Increase portability and flexibility of building Hotspot
bobv
parents: 5922
diff changeset
  5912
// is_headless_jre()
4d9030fe341f 6953477: Increase portability and flexibility of building Hotspot
bobv
parents: 5922
diff changeset
  5913
//
11161
ec855b5a23c2 7110017: is_headless_jre should be updated to reflect the new location of awt toolkit libraries
dholmes
parents: 10739
diff changeset
  5914
// Test for the existence of xawt/libmawt.so or libawt_xawt.so
6176
4d9030fe341f 6953477: Increase portability and flexibility of building Hotspot
bobv
parents: 5922
diff changeset
  5915
// in order to report if we are running in a headless jre
4d9030fe341f 6953477: Increase portability and flexibility of building Hotspot
bobv
parents: 5922
diff changeset
  5916
//
11161
ec855b5a23c2 7110017: is_headless_jre should be updated to reflect the new location of awt toolkit libraries
dholmes
parents: 10739
diff changeset
  5917
// Since JDK8 xawt/libmawt.so was moved into the same directory
ec855b5a23c2 7110017: is_headless_jre should be updated to reflect the new location of awt toolkit libraries
dholmes
parents: 10739
diff changeset
  5918
// as libawt.so, and renamed libawt_xawt.so
ec855b5a23c2 7110017: is_headless_jre should be updated to reflect the new location of awt toolkit libraries
dholmes
parents: 10739
diff changeset
  5919
//
6176
4d9030fe341f 6953477: Increase portability and flexibility of building Hotspot
bobv
parents: 5922
diff changeset
  5920
bool os::is_headless_jre() {
26683
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  5921
  struct stat statbuf;
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  5922
  char buf[MAXPATHLEN];
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  5923
  char libmawtpath[MAXPATHLEN];
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  5924
  const char *xawtstr  = "/xawt/libmawt.so";
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  5925
  const char *new_xawtstr = "/libawt_xawt.so";
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  5926
  char *p;
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  5927
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  5928
  // Get path to libjvm.so
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  5929
  os::jvm_path(buf, sizeof(buf));
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  5930
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  5931
  // Get rid of libjvm.so
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  5932
  p = strrchr(buf, '/');
26684
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
  5933
  if (p == NULL) {
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
  5934
    return false;
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
  5935
  } else {
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
  5936
    *p = '\0';
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
  5937
  }
26683
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  5938
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  5939
  // Get rid of client or server
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  5940
  p = strrchr(buf, '/');
26684
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
  5941
  if (p == NULL) {
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
  5942
    return false;
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
  5943
  } else {
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
  5944
    *p = '\0';
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
  5945
  }
26683
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  5946
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  5947
  // check xawt/libmawt.so
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  5948
  strcpy(libmawtpath, buf);
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  5949
  strcat(libmawtpath, xawtstr);
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  5950
  if (::stat(libmawtpath, &statbuf) == 0) return false;
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  5951
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  5952
  // check libawt_xawt.so
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  5953
  strcpy(libmawtpath, buf);
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  5954
  strcat(libmawtpath, new_xawtstr);
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  5955
  if (::stat(libmawtpath, &statbuf) == 0) return false;
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  5956
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  5957
  return true;
6176
4d9030fe341f 6953477: Increase portability and flexibility of building Hotspot
bobv
parents: 5922
diff changeset
  5958
}
4d9030fe341f 6953477: Increase portability and flexibility of building Hotspot
bobv
parents: 5922
diff changeset
  5959
13198
271c557a7623 7129724: MAC: Core file location is wrong in crash report
mikael
parents: 13195
diff changeset
  5960
// Get the default path to the core file
271c557a7623 7129724: MAC: Core file location is wrong in crash report
mikael
parents: 13195
diff changeset
  5961
// Returns the length of the string
271c557a7623 7129724: MAC: Core file location is wrong in crash report
mikael
parents: 13195
diff changeset
  5962
int os::get_core_path(char* buffer, size_t bufferSize) {
28172
19ae5c844e75 8059586: hs_err report should treat redirected core pattern
dholmes
parents: 27926
diff changeset
  5963
  /*
19ae5c844e75 8059586: hs_err report should treat redirected core pattern
dholmes
parents: 27926
diff changeset
  5964
   * Max length of /proc/sys/kernel/core_pattern is 128 characters.
19ae5c844e75 8059586: hs_err report should treat redirected core pattern
dholmes
parents: 27926
diff changeset
  5965
   * See https://www.kernel.org/doc/Documentation/sysctl/kernel.txt
19ae5c844e75 8059586: hs_err report should treat redirected core pattern
dholmes
parents: 27926
diff changeset
  5966
   */
19ae5c844e75 8059586: hs_err report should treat redirected core pattern
dholmes
parents: 27926
diff changeset
  5967
  const int core_pattern_len = 129;
19ae5c844e75 8059586: hs_err report should treat redirected core pattern
dholmes
parents: 27926
diff changeset
  5968
  char core_pattern[core_pattern_len] = {0};
19ae5c844e75 8059586: hs_err report should treat redirected core pattern
dholmes
parents: 27926
diff changeset
  5969
19ae5c844e75 8059586: hs_err report should treat redirected core pattern
dholmes
parents: 27926
diff changeset
  5970
  int core_pattern_file = ::open("/proc/sys/kernel/core_pattern", O_RDONLY);
19ae5c844e75 8059586: hs_err report should treat redirected core pattern
dholmes
parents: 27926
diff changeset
  5971
  if (core_pattern_file != -1) {
19ae5c844e75 8059586: hs_err report should treat redirected core pattern
dholmes
parents: 27926
diff changeset
  5972
    ssize_t ret = ::read(core_pattern_file, core_pattern, core_pattern_len);
19ae5c844e75 8059586: hs_err report should treat redirected core pattern
dholmes
parents: 27926
diff changeset
  5973
    ::close(core_pattern_file);
19ae5c844e75 8059586: hs_err report should treat redirected core pattern
dholmes
parents: 27926
diff changeset
  5974
19ae5c844e75 8059586: hs_err report should treat redirected core pattern
dholmes
parents: 27926
diff changeset
  5975
    if (ret > 0) {
19ae5c844e75 8059586: hs_err report should treat redirected core pattern
dholmes
parents: 27926
diff changeset
  5976
      char *last_char = core_pattern + strlen(core_pattern) - 1;
19ae5c844e75 8059586: hs_err report should treat redirected core pattern
dholmes
parents: 27926
diff changeset
  5977
19ae5c844e75 8059586: hs_err report should treat redirected core pattern
dholmes
parents: 27926
diff changeset
  5978
      if (*last_char == '\n') {
19ae5c844e75 8059586: hs_err report should treat redirected core pattern
dholmes
parents: 27926
diff changeset
  5979
        *last_char = '\0';
19ae5c844e75 8059586: hs_err report should treat redirected core pattern
dholmes
parents: 27926
diff changeset
  5980
      }
19ae5c844e75 8059586: hs_err report should treat redirected core pattern
dholmes
parents: 27926
diff changeset
  5981
    }
19ae5c844e75 8059586: hs_err report should treat redirected core pattern
dholmes
parents: 27926
diff changeset
  5982
  }
19ae5c844e75 8059586: hs_err report should treat redirected core pattern
dholmes
parents: 27926
diff changeset
  5983
19ae5c844e75 8059586: hs_err report should treat redirected core pattern
dholmes
parents: 27926
diff changeset
  5984
  if (strlen(core_pattern) == 0) {
29580
a67a581cfe11 8073315: Enable gcc -Wtype-limits and fix upcoming issues.
goetz
parents: 29474
diff changeset
  5985
    return -1;
13198
271c557a7623 7129724: MAC: Core file location is wrong in crash report
mikael
parents: 13195
diff changeset
  5986
  }
271c557a7623 7129724: MAC: Core file location is wrong in crash report
mikael
parents: 13195
diff changeset
  5987
28172
19ae5c844e75 8059586: hs_err report should treat redirected core pattern
dholmes
parents: 27926
diff changeset
  5988
  char *pid_pos = strstr(core_pattern, "%p");
29580
a67a581cfe11 8073315: Enable gcc -Wtype-limits and fix upcoming issues.
goetz
parents: 29474
diff changeset
  5989
  int written;
28172
19ae5c844e75 8059586: hs_err report should treat redirected core pattern
dholmes
parents: 27926
diff changeset
  5990
19ae5c844e75 8059586: hs_err report should treat redirected core pattern
dholmes
parents: 27926
diff changeset
  5991
  if (core_pattern[0] == '/') {
19ae5c844e75 8059586: hs_err report should treat redirected core pattern
dholmes
parents: 27926
diff changeset
  5992
    written = jio_snprintf(buffer, bufferSize, core_pattern);
19ae5c844e75 8059586: hs_err report should treat redirected core pattern
dholmes
parents: 27926
diff changeset
  5993
  } else {
19ae5c844e75 8059586: hs_err report should treat redirected core pattern
dholmes
parents: 27926
diff changeset
  5994
    char cwd[PATH_MAX];
19ae5c844e75 8059586: hs_err report should treat redirected core pattern
dholmes
parents: 27926
diff changeset
  5995
19ae5c844e75 8059586: hs_err report should treat redirected core pattern
dholmes
parents: 27926
diff changeset
  5996
    const char* p = get_current_directory(cwd, PATH_MAX);
19ae5c844e75 8059586: hs_err report should treat redirected core pattern
dholmes
parents: 27926
diff changeset
  5997
    if (p == NULL) {
29580
a67a581cfe11 8073315: Enable gcc -Wtype-limits and fix upcoming issues.
goetz
parents: 29474
diff changeset
  5998
      return -1;
28172
19ae5c844e75 8059586: hs_err report should treat redirected core pattern
dholmes
parents: 27926
diff changeset
  5999
    }
19ae5c844e75 8059586: hs_err report should treat redirected core pattern
dholmes
parents: 27926
diff changeset
  6000
19ae5c844e75 8059586: hs_err report should treat redirected core pattern
dholmes
parents: 27926
diff changeset
  6001
    if (core_pattern[0] == '|') {
19ae5c844e75 8059586: hs_err report should treat redirected core pattern
dholmes
parents: 27926
diff changeset
  6002
      written = jio_snprintf(buffer, bufferSize,
19ae5c844e75 8059586: hs_err report should treat redirected core pattern
dholmes
parents: 27926
diff changeset
  6003
                        "\"%s\" (or dumping to %s/core.%d)",
19ae5c844e75 8059586: hs_err report should treat redirected core pattern
dholmes
parents: 27926
diff changeset
  6004
                                     &core_pattern[1], p, current_process_id());
19ae5c844e75 8059586: hs_err report should treat redirected core pattern
dholmes
parents: 27926
diff changeset
  6005
    } else {
19ae5c844e75 8059586: hs_err report should treat redirected core pattern
dholmes
parents: 27926
diff changeset
  6006
      written = jio_snprintf(buffer, bufferSize, "%s/%s", p, core_pattern);
19ae5c844e75 8059586: hs_err report should treat redirected core pattern
dholmes
parents: 27926
diff changeset
  6007
    }
19ae5c844e75 8059586: hs_err report should treat redirected core pattern
dholmes
parents: 27926
diff changeset
  6008
  }
19ae5c844e75 8059586: hs_err report should treat redirected core pattern
dholmes
parents: 27926
diff changeset
  6009
29580
a67a581cfe11 8073315: Enable gcc -Wtype-limits and fix upcoming issues.
goetz
parents: 29474
diff changeset
  6010
  if (written < 0) {
a67a581cfe11 8073315: Enable gcc -Wtype-limits and fix upcoming issues.
goetz
parents: 29474
diff changeset
  6011
    return -1;
a67a581cfe11 8073315: Enable gcc -Wtype-limits and fix upcoming issues.
goetz
parents: 29474
diff changeset
  6012
  }
a67a581cfe11 8073315: Enable gcc -Wtype-limits and fix upcoming issues.
goetz
parents: 29474
diff changeset
  6013
a67a581cfe11 8073315: Enable gcc -Wtype-limits and fix upcoming issues.
goetz
parents: 29474
diff changeset
  6014
  if (((size_t)written < bufferSize) && (pid_pos == NULL) && (core_pattern[0] != '|')) {
28172
19ae5c844e75 8059586: hs_err report should treat redirected core pattern
dholmes
parents: 27926
diff changeset
  6015
    int core_uses_pid_file = ::open("/proc/sys/kernel/core_uses_pid", O_RDONLY);
19ae5c844e75 8059586: hs_err report should treat redirected core pattern
dholmes
parents: 27926
diff changeset
  6016
19ae5c844e75 8059586: hs_err report should treat redirected core pattern
dholmes
parents: 27926
diff changeset
  6017
    if (core_uses_pid_file != -1) {
19ae5c844e75 8059586: hs_err report should treat redirected core pattern
dholmes
parents: 27926
diff changeset
  6018
      char core_uses_pid = 0;
19ae5c844e75 8059586: hs_err report should treat redirected core pattern
dholmes
parents: 27926
diff changeset
  6019
      ssize_t ret = ::read(core_uses_pid_file, &core_uses_pid, 1);
19ae5c844e75 8059586: hs_err report should treat redirected core pattern
dholmes
parents: 27926
diff changeset
  6020
      ::close(core_uses_pid_file);
19ae5c844e75 8059586: hs_err report should treat redirected core pattern
dholmes
parents: 27926
diff changeset
  6021
29580
a67a581cfe11 8073315: Enable gcc -Wtype-limits and fix upcoming issues.
goetz
parents: 29474
diff changeset
  6022
      if (core_uses_pid == '1') {
28172
19ae5c844e75 8059586: hs_err report should treat redirected core pattern
dholmes
parents: 27926
diff changeset
  6023
        jio_snprintf(buffer + written, bufferSize - written,
19ae5c844e75 8059586: hs_err report should treat redirected core pattern
dholmes
parents: 27926
diff changeset
  6024
                                          ".%d", current_process_id());
19ae5c844e75 8059586: hs_err report should treat redirected core pattern
dholmes
parents: 27926
diff changeset
  6025
      }
19ae5c844e75 8059586: hs_err report should treat redirected core pattern
dholmes
parents: 27926
diff changeset
  6026
    }
19ae5c844e75 8059586: hs_err report should treat redirected core pattern
dholmes
parents: 27926
diff changeset
  6027
  }
19ae5c844e75 8059586: hs_err report should treat redirected core pattern
dholmes
parents: 27926
diff changeset
  6028
13198
271c557a7623 7129724: MAC: Core file location is wrong in crash report
mikael
parents: 13195
diff changeset
  6029
  return strlen(buffer);
271c557a7623 7129724: MAC: Core file location is wrong in crash report
mikael
parents: 13195
diff changeset
  6030
}
10025
57fe03f10cf2 7061212: use o/s low memory notification in embedded builds
jcoomes
parents: 10023
diff changeset
  6031
19546
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  6032
/////////////// Unit tests ///////////////
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  6033
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  6034
#ifndef PRODUCT
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  6035
26684
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
  6036
#define test_log(...)              \
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
  6037
  do {                             \
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
  6038
    if (VerboseInternalVMTests) {  \
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
  6039
      tty->print_cr(__VA_ARGS__);  \
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
  6040
      tty->flush();                \
d1221849ea3d 8057109: manual cleanup of white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26683
diff changeset
  6041
    }                              \
19546
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  6042
  } while (false)
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  6043
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  6044
class TestReserveMemorySpecial : AllStatic {
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  6045
 public:
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  6046
  static void small_page_write(void* addr, size_t size) {
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  6047
    size_t page_size = os::vm_page_size();
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  6048
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  6049
    char* end = (char*)addr + size;
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  6050
    for (char* p = (char*)addr; p < end; p += page_size) {
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  6051
      *p = 1;
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  6052
    }
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  6053
  }
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  6054
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  6055
  static void test_reserve_memory_special_huge_tlbfs_only(size_t size) {
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  6056
    if (!UseHugeTLBFS) {
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  6057
      return;
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  6058
    }
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  6059
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  6060
    test_log("test_reserve_memory_special_huge_tlbfs_only(" SIZE_FORMAT ")", size);
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  6061
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  6062
    char* addr = os::Linux::reserve_memory_special_huge_tlbfs_only(size, NULL, false);
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  6063
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  6064
    if (addr != NULL) {
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  6065
      small_page_write(addr, size);
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  6066
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  6067
      os::Linux::release_memory_special_huge_tlbfs(addr, size);
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  6068
    }
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  6069
  }
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  6070
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  6071
  static void test_reserve_memory_special_huge_tlbfs_only() {
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  6072
    if (!UseHugeTLBFS) {
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  6073
      return;
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  6074
    }
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  6075
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  6076
    size_t lp = os::large_page_size();
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  6077
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  6078
    for (size_t size = lp; size <= lp * 10; size += lp) {
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  6079
      test_reserve_memory_special_huge_tlbfs_only(size);
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  6080
    }
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  6081
  }
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  6082
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  6083
  static void test_reserve_memory_special_huge_tlbfs_mixed(size_t size, size_t alignment) {
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  6084
    if (!UseHugeTLBFS) {
26683
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  6085
      return;
19546
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  6086
    }
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  6087
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  6088
    test_log("test_reserve_memory_special_huge_tlbfs_mixed(" SIZE_FORMAT ", " SIZE_FORMAT ")",
26683
a02753d5a0b2 8057107: cleanup indent white space issues prior to Contended Locking reorder and cache line bucket
dcubed
parents: 26135
diff changeset
  6089
             size, alignment);
19546
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  6090
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  6091
    assert(size >= os::large_page_size(), "Incorrect input to test");
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  6092
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  6093
    char* addr = os::Linux::reserve_memory_special_huge_tlbfs_mixed(size, alignment, NULL, false);
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  6094
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  6095
    if (addr != NULL) {
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  6096
      small_page_write(addr, size);
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  6097
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  6098
      os::Linux::release_memory_special_huge_tlbfs(addr, size);
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  6099
    }
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  6100
  }
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  6101
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  6102
  static void test_reserve_memory_special_huge_tlbfs_mixed_all_alignments(size_t size) {
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  6103
    size_t lp = os::large_page_size();
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  6104
    size_t ag = os::vm_allocation_granularity();
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  6105
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  6106
    for (size_t alignment = ag; is_size_aligned(size, alignment); alignment *= 2) {
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  6107
      test_reserve_memory_special_huge_tlbfs_mixed(size, alignment);
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  6108
    }
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  6109
  }
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  6110
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  6111
  static void test_reserve_memory_special_huge_tlbfs_mixed() {
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  6112
    size_t lp = os::large_page_size();
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  6113
    size_t ag = os::vm_allocation_granularity();
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  6114
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  6115
    test_reserve_memory_special_huge_tlbfs_mixed_all_alignments(lp);
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  6116
    test_reserve_memory_special_huge_tlbfs_mixed_all_alignments(lp + ag);
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  6117
    test_reserve_memory_special_huge_tlbfs_mixed_all_alignments(lp + lp / 2);
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  6118
    test_reserve_memory_special_huge_tlbfs_mixed_all_alignments(lp * 2);
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  6119
    test_reserve_memory_special_huge_tlbfs_mixed_all_alignments(lp * 2 + ag);
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  6120
    test_reserve_memory_special_huge_tlbfs_mixed_all_alignments(lp * 2 - ag);
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  6121
    test_reserve_memory_special_huge_tlbfs_mixed_all_alignments(lp * 2 + lp / 2);
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  6122
    test_reserve_memory_special_huge_tlbfs_mixed_all_alignments(lp * 10);
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  6123
    test_reserve_memory_special_huge_tlbfs_mixed_all_alignments(lp * 10 + lp / 2);
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  6124
  }
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  6125
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  6126
  static void test_reserve_memory_special_huge_tlbfs() {
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  6127
    if (!UseHugeTLBFS) {
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  6128
      return;
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  6129
    }
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  6130
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  6131
    test_reserve_memory_special_huge_tlbfs_only();
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  6132
    test_reserve_memory_special_huge_tlbfs_mixed();
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  6133
  }
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  6134
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  6135
  static void test_reserve_memory_special_shm(size_t size, size_t alignment) {
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  6136
    if (!UseSHM) {
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  6137
      return;
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  6138
    }
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  6139
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  6140
    test_log("test_reserve_memory_special_shm(" SIZE_FORMAT ", " SIZE_FORMAT ")", size, alignment);
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  6141
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  6142
    char* addr = os::Linux::reserve_memory_special_shm(size, alignment, NULL, false);
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  6143
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  6144
    if (addr != NULL) {
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  6145
      assert(is_ptr_aligned(addr, alignment), "Check");
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  6146
      assert(is_ptr_aligned(addr, os::large_page_size()), "Check");
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  6147
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  6148
      small_page_write(addr, size);
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  6149
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  6150
      os::Linux::release_memory_special_shm(addr, size);
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  6151
    }
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  6152
  }
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  6153
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  6154
  static void test_reserve_memory_special_shm() {
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  6155
    size_t lp = os::large_page_size();
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  6156
    size_t ag = os::vm_allocation_granularity();
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  6157
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  6158
    for (size_t size = ag; size < lp * 3; size += ag) {
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  6159
      for (size_t alignment = ag; is_size_aligned(size, alignment); alignment *= 2) {
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  6160
        test_reserve_memory_special_shm(size, alignment);
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  6161
      }
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  6162
    }
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  6163
  }
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  6164
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  6165
  static void test() {
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  6166
    test_reserve_memory_special_huge_tlbfs();
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  6167
    test_reserve_memory_special_shm();
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  6168
  }
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  6169
};
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  6170
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  6171
void TestReserveMemorySpecial_test() {
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  6172
  TestReserveMemorySpecial::test();
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  6173
}
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  6174
f6b7c9e96ea3 8007074: SIGSEGV at ParMarkBitMap::verify_clear()
stefank
parents: 18683
diff changeset
  6175
#endif