hotspot/src/share/vm/utilities/vmError.cpp
changeset 33105 294e48b4f704
parent 32583 e95e2cfc9cf5
child 33131 a8ad9de9e5a4
equal deleted inserted replaced
33104:a7c0f60a1294 33105:294e48b4f704
    69   "OS", "PROCESSOR_IDENTIFIER", "_ALT_JAVA_HOME_DIR",
    69   "OS", "PROCESSOR_IDENTIFIER", "_ALT_JAVA_HOME_DIR",
    70 
    70 
    71   (const char *)0
    71   (const char *)0
    72 };
    72 };
    73 
    73 
    74 // Fatal error handler for internal errors and crashes.
       
    75 //
       
    76 // The default behavior of fatal error handler is to print a brief message
       
    77 // to standard out (defaultStream::output_fd()), then save detailed information
       
    78 // into an error report file (hs_err_pid<pid>.log) and abort VM. If multiple
       
    79 // threads are having troubles at the same time, only one error is reported.
       
    80 // The thread that is reporting error will abort VM when it is done, all other
       
    81 // threads are blocked forever inside report_and_die().
       
    82 
       
    83 // Constructor for crashes
       
    84 VMError::VMError(Thread* thread, unsigned int sig, address pc, void* siginfo, void* context) {
       
    85     _thread = thread;
       
    86     _id = sig;
       
    87     _pc   = pc;
       
    88     _siginfo = siginfo;
       
    89     _context = context;
       
    90 
       
    91     _verbose = false;
       
    92     _current_step = 0;
       
    93     _current_step_info = NULL;
       
    94 
       
    95     _message = NULL;
       
    96     _detail_msg = NULL;
       
    97     _filename = NULL;
       
    98     _lineno = 0;
       
    99 
       
   100     _size = 0;
       
   101 }
       
   102 
       
   103 // Constructor for internal errors
       
   104 VMError::VMError(Thread* thread, const char* filename, int lineno,
       
   105                  const char* message, const char * detail_msg)
       
   106 {
       
   107   _thread = thread;
       
   108   _id = INTERNAL_ERROR;     // Value that's not an OS exception/signal
       
   109   _filename = filename;
       
   110   _lineno = lineno;
       
   111   _message = message;
       
   112   _detail_msg = detail_msg;
       
   113 
       
   114   _verbose = false;
       
   115   _current_step = 0;
       
   116   _current_step_info = NULL;
       
   117 
       
   118   _pc = NULL;
       
   119   _siginfo = NULL;
       
   120   _context = NULL;
       
   121 
       
   122   _size = 0;
       
   123 }
       
   124 
       
   125 // Constructor for OOM errors
       
   126 VMError::VMError(Thread* thread, const char* filename, int lineno, size_t size,
       
   127                  VMErrorType vm_err_type, const char* message) {
       
   128     _thread = thread;
       
   129     _id = vm_err_type; // Value that's not an OS exception/signal
       
   130     _filename = filename;
       
   131     _lineno = lineno;
       
   132     _message = message;
       
   133     _detail_msg = NULL;
       
   134 
       
   135     _verbose = false;
       
   136     _current_step = 0;
       
   137     _current_step_info = NULL;
       
   138 
       
   139     _pc = NULL;
       
   140     _siginfo = NULL;
       
   141     _context = NULL;
       
   142 
       
   143     _size = size;
       
   144 }
       
   145 
       
   146 
       
   147 // Constructor for non-fatal errors
       
   148 VMError::VMError(const char* message) {
       
   149     _thread = NULL;
       
   150     _id = INTERNAL_ERROR;     // Value that's not an OS exception/signal
       
   151     _filename = NULL;
       
   152     _lineno = 0;
       
   153     _message = message;
       
   154     _detail_msg = NULL;
       
   155 
       
   156     _verbose = false;
       
   157     _current_step = 0;
       
   158     _current_step_info = NULL;
       
   159 
       
   160     _pc = NULL;
       
   161     _siginfo = NULL;
       
   162     _context = NULL;
       
   163 
       
   164     _size = 0;
       
   165 }
       
   166 
       
   167 // -XX:OnError=<string>, where <string> can be a list of commands, separated
       
   168 // by ';'. "%p" is replaced by current process id (pid); "%%" is replaced by
       
   169 // a single "%". Some examples:
       
   170 //
       
   171 // -XX:OnError="pmap %p"                // show memory map
       
   172 // -XX:OnError="gcore %p; dbx - %p"     // dump core and launch debugger
       
   173 // -XX:OnError="cat hs_err_pid%p.log | mail my_email@sun.com"
       
   174 // -XX:OnError="kill -9 %p"             // ?#!@#
       
   175 
       
   176 // A simple parser for -XX:OnError, usage:
    74 // A simple parser for -XX:OnError, usage:
   177 //  ptr = OnError;
    75 //  ptr = OnError;
   178 //  while ((cmd = next_OnError_command(buffer, sizeof(buffer), &ptr) != NULL)
    76 //  while ((cmd = next_OnError_command(buffer, sizeof(buffer), &ptr) != NULL)
   179 //     ... ...
    77 //     ... ...
   180 static char* next_OnError_command(char* buf, int buflen, const char** ptr) {
    78 static char* next_OnError_command(char* buf, int buflen, const char** ptr) {
   193   Arguments::copy_expand_pid(cmd, cmdend - cmd, buf, buflen);
    91   Arguments::copy_expand_pid(cmd, cmdend - cmd, buf, buflen);
   194 
    92 
   195   *ptr = (*cmdend == '\0' ? cmdend : cmdend + 1);
    93   *ptr = (*cmdend == '\0' ? cmdend : cmdend + 1);
   196   return buf;
    94   return buf;
   197 }
    95 }
   198 
       
   199 
    96 
   200 static void print_bug_submit_message(outputStream *out, Thread *thread) {
    97 static void print_bug_submit_message(outputStream *out, Thread *thread) {
   201   if (out == NULL) return;
    98   if (out == NULL) return;
   202   out->print_raw_cr("# If you would like to submit a bug report, please visit:");
    99   out->print_raw_cr("# If you would like to submit a bug report, please visit:");
   203   out->print_raw   ("#   ");
   100   out->print_raw   ("#   ");
   220 void VMError::record_coredump_status(const char* message, bool status) {
   117 void VMError::record_coredump_status(const char* message, bool status) {
   221   coredump_status = status;
   118   coredump_status = status;
   222   strncpy(coredump_message, message, sizeof(coredump_message));
   119   strncpy(coredump_message, message, sizeof(coredump_message));
   223   coredump_message[sizeof(coredump_message)-1] = 0;
   120   coredump_message[sizeof(coredump_message)-1] = 0;
   224 }
   121 }
   225 
       
   226 
   122 
   227 // Return a string to describe the error
   123 // Return a string to describe the error
   228 char* VMError::error_string(char* buf, int buflen) {
   124 char* VMError::error_string(char* buf, int buflen) {
   229   char signame_buf[64];
   125   char signame_buf[64];
   230   const char *signame = os::exception_name(_id, signame_buf, sizeof(signame_buf));
   126   const char *signame = os::exception_name(_id, signame_buf, sizeof(signame_buf));
   241     int n = jio_snprintf(buf, buflen,
   137     int n = jio_snprintf(buf, buflen,
   242                          "Internal Error at %s:%d, pid=%d, tid=" UINTX_FORMAT,
   138                          "Internal Error at %s:%d, pid=%d, tid=" UINTX_FORMAT,
   243                          p ? p + 1 : _filename, _lineno,
   139                          p ? p + 1 : _filename, _lineno,
   244                          os::current_process_id(), os::current_thread_id());
   140                          os::current_process_id(), os::current_thread_id());
   245     if (n >= 0 && n < buflen && _message) {
   141     if (n >= 0 && n < buflen && _message) {
   246       if (_detail_msg) {
   142       if (strlen(_detail_msg) > 0) {
   247         jio_snprintf(buf + n, buflen - n, "%s%s: %s",
   143         jio_snprintf(buf + n, buflen - n, "%s%s: %s",
   248                      os::line_separator(), _message, _detail_msg);
   144         os::line_separator(), _message, _detail_msg);
   249       } else {
   145       } else {
   250         jio_snprintf(buf + n, buflen - n, "%sError: %s",
   146         jio_snprintf(buf + n, buflen - n, "%sError: %s",
   251                      os::line_separator(), _message);
   147                      os::line_separator(), _message);
   252       }
   148       }
   253     }
   149     }
   355 // when stack space is already low. Making things even worse is that there
   251 // when stack space is already low. Making things even worse is that there
   356 // could be nested report_and_die() calls on stack (see above). Only one
   252 // could be nested report_and_die() calls on stack (see above). Only one
   357 // thread can report error, so large buffers are statically allocated in data
   253 // thread can report error, so large buffers are statically allocated in data
   358 // segment.
   254 // segment.
   359 
   255 
   360 void VMError::report(outputStream* st) {
   256 int          VMError::_current_step;
       
   257 const char*  VMError::_current_step_info;
       
   258 
       
   259 void VMError::report(outputStream* st, bool _verbose) {
       
   260 
   361 # define BEGIN if (_current_step == 0) { _current_step = 1;
   261 # define BEGIN if (_current_step == 0) { _current_step = 1;
   362 # define STEP(n, s) } if (_current_step < n) { _current_step = n; _current_step_info = s;
   262 # define STEP(n, s) } if (_current_step < n) { _current_step = n; _current_step_info = s;
   363 # define END }
   263 # define END }
   364 
   264 
   365   // don't allocate large buffer on stack
   265   // don't allocate large buffer on stack
   427            st->print((_id == (int)OOM_MALLOC_ERROR) ? "(malloc) failed to allocate " :
   327            st->print((_id == (int)OOM_MALLOC_ERROR) ? "(malloc) failed to allocate " :
   428                                                  "(mmap) failed to map ");
   328                                                  "(mmap) failed to map ");
   429            jio_snprintf(buf, sizeof(buf), SIZE_FORMAT, _size);
   329            jio_snprintf(buf, sizeof(buf), SIZE_FORMAT, _size);
   430            st->print("%s", buf);
   330            st->print("%s", buf);
   431            st->print(" bytes");
   331            st->print(" bytes");
   432            if (_message != NULL) {
   332            if (strlen(_detail_msg) > 0) {
   433              st->print(" for ");
   333              st->print(" for ");
   434              st->print("%s", _message);
   334              st->print("%s", _detail_msg);
   435            }
   335            }
   436            st->cr();
   336            st->cr();
   437          } else {
   337          } else {
   438            if (_message != NULL) {
   338            if (strlen(_detail_msg) > 0) {
   439              st->print("# ");
   339              st->print("# ");
   440              st->print_cr("%s", _message);
   340              st->print_cr("%s", _detail_msg);
   441            }
   341            }
   442          }
   342          }
   443          // In error file give some solutions
   343          // In error file give some solutions
   444          if (_verbose) {
   344          if (_verbose) {
   445            print_oom_reasons(st);
   345            print_oom_reasons(st);
   491 
   391 
   492   STEP(80, "(printing error message)")
   392   STEP(80, "(printing error message)")
   493 
   393 
   494      if (should_report_bug(_id)) {  // already printed the message.
   394      if (should_report_bug(_id)) {  // already printed the message.
   495        // error message
   395        // error message
   496        if (_detail_msg) {
   396        if (strlen(_detail_msg) > 0) {
   497          st->print_cr("#  %s: %s", _message ? _message : "Error", _detail_msg);
   397          st->print_cr("#  %s: %s", _message ? _message : "Error", _detail_msg);
   498        } else if (_message) {
   398        } else if (_message) {
   499          st->print_cr("#  Error: %s", _message);
   399          st->print_cr("#  Error: %s", _message);
   500        }
   400        }
   501     }
   401      }
   502 
   402 
   503   STEP(90, "(printing Java version string)")
   403   STEP(90, "(printing Java version string)")
   504 
   404 
   505      // VM version
   405      // VM version
   506      st->print_cr("#");
   406      st->print_cr("#");
   894 # undef BEGIN
   794 # undef BEGIN
   895 # undef STEP
   795 # undef STEP
   896 # undef END
   796 # undef END
   897 }
   797 }
   898 
   798 
   899 VMError* volatile VMError::first_error = NULL;
       
   900 volatile jlong VMError::first_error_tid = -1;
   799 volatile jlong VMError::first_error_tid = -1;
   901 
   800 
   902 // An error could happen before tty is initialized or after it has been
   801 // An error could happen before tty is initialized or after it has been
   903 // destroyed. Here we use a very simple unbuffered fdStream for printing.
   802 // destroyed. Here we use a very simple unbuffered fdStream for printing.
   904 // Only out.print_raw() and out.print_raw_cr() should be used, as other
   803 // Only out.print_raw() and out.print_raw_cr() should be used, as other
   956    }
   855    }
   957 
   856 
   958   return fd;
   857   return fd;
   959 }
   858 }
   960 
   859 
   961 void VMError::report_and_die() {
   860 int         VMError::_id;
       
   861 const char* VMError::_message;
       
   862 char        VMError::_detail_msg[1024];
       
   863 Thread*     VMError::_thread;
       
   864 address     VMError::_pc;
       
   865 void*       VMError::_siginfo;
       
   866 void*       VMError::_context;
       
   867 const char* VMError::_filename;
       
   868 int         VMError::_lineno;
       
   869 size_t      VMError::_size;
       
   870 
       
   871 void VMError::report_and_die(Thread* thread, unsigned int sig, address pc, void* siginfo,
       
   872                              void* context, const char* detail_fmt, ...)
       
   873 {
       
   874   va_list detail_args;
       
   875   va_start(detail_args, detail_fmt);
       
   876   report_and_die(sig, NULL, detail_fmt, detail_args, thread, pc, siginfo, context, NULL, 0, 0);
       
   877   va_end(detail_args);
       
   878 }
       
   879 
       
   880 void VMError::report_and_die(Thread* thread, unsigned int sig, address pc, void* siginfo, void* context)
       
   881 {
       
   882   report_and_die(thread, sig, pc, siginfo, context, "%s", "");
       
   883 }
       
   884 
       
   885 void VMError::report_and_die(const char* message, const char* detail_fmt, ...)
       
   886 {
       
   887   va_list detail_args;
       
   888   va_start(detail_args, detail_fmt);
       
   889   report_and_die(INTERNAL_ERROR, message, detail_fmt, detail_args, NULL, NULL, NULL, NULL, NULL, 0, 0);
       
   890   va_end(detail_args);
       
   891 }
       
   892 
       
   893 void VMError::report_and_die(const char* message)
       
   894 {
       
   895   report_and_die(message, "%s", "");
       
   896 }
       
   897 
       
   898 void VMError::report_and_die(Thread* thread, const char* filename, int lineno, const char* message,
       
   899                              const char* detail_fmt, va_list detail_args)
       
   900 {
       
   901   report_and_die(INTERNAL_ERROR, message, detail_fmt, detail_args, thread, NULL, NULL, NULL, filename, lineno, 0);
       
   902 }
       
   903 
       
   904 void VMError::report_and_die(Thread* thread, const char* filename, int lineno, size_t size,
       
   905                              VMErrorType vm_err_type, const char* detail_fmt, va_list detail_args) {
       
   906   report_and_die(vm_err_type, NULL, detail_fmt, detail_args, thread, NULL, NULL, NULL, filename, lineno, size);
       
   907 }
       
   908 
       
   909 void VMError::report_and_die(int id, const char* message, const char* detail_fmt, va_list detail_args,
       
   910                              Thread* thread, address pc, void* siginfo, void* context, const char* filename,
       
   911                              int lineno, size_t size)
       
   912 {
   962   // Don't allocate large buffer on stack
   913   // Don't allocate large buffer on stack
   963   static char buffer[O_BUFLEN];
   914   static char buffer[O_BUFLEN];
   964 
   915 
   965   // How many errors occurred in error handler when reporting first_error.
   916   // How many errors occurred in error handler when reporting first_error.
   966   static int recursive_error_count;
   917   static int recursive_error_count;
   973 
   924 
   974   if (SuppressFatalErrorMessage) {
   925   if (SuppressFatalErrorMessage) {
   975       os::abort(CreateCoredumpOnCrash);
   926       os::abort(CreateCoredumpOnCrash);
   976   }
   927   }
   977   jlong mytid = os::current_thread_id();
   928   jlong mytid = os::current_thread_id();
   978   if (first_error == NULL &&
   929   if (first_error_tid == -1 &&
   979       Atomic::cmpxchg_ptr(this, &first_error, NULL) == NULL) {
   930       Atomic::cmpxchg(mytid, &first_error_tid, -1) == -1) {
       
   931 
       
   932     _id = id;
       
   933     _message = message;
       
   934     _thread = thread;
       
   935     _pc = pc;
       
   936     _siginfo = siginfo;
       
   937     _context = context;
       
   938     _filename = filename;
       
   939     _lineno = lineno;
       
   940     _size = size;
       
   941     jio_vsnprintf(_detail_msg, sizeof(_detail_msg), detail_fmt, detail_args);
   980 
   942 
   981     // first time
   943     // first time
   982     first_error_tid = mytid;
       
   983     set_error_reported();
   944     set_error_reported();
   984 
   945 
   985     if (ShowMessageBoxOnError || PauseAtExit) {
   946     if (ShowMessageBoxOnError || PauseAtExit) {
   986       show_message_box(buffer, sizeof(buffer));
   947       show_message_box(buffer, sizeof(buffer));
   987 
   948 
  1020         os::die();
   981         os::die();
  1021       }
   982       }
  1022 
   983 
  1023       jio_snprintf(buffer, sizeof(buffer),
   984       jio_snprintf(buffer, sizeof(buffer),
  1024                    "[error occurred during error reporting %s, id 0x%x]",
   985                    "[error occurred during error reporting %s, id 0x%x]",
  1025                    first_error ? first_error->_current_step_info : "",
   986                    _current_step_info, _id);
  1026                    _id);
       
  1027       if (log.is_open()) {
   987       if (log.is_open()) {
  1028         log.cr();
   988         log.cr();
  1029         log.print_raw_cr(buffer);
   989         log.print_raw_cr(buffer);
  1030         log.cr();
   990         log.cr();
  1031       } else {
   991       } else {
  1036     }
   996     }
  1037   }
   997   }
  1038 
   998 
  1039   // print to screen
   999   // print to screen
  1040   if (!out_done) {
  1000   if (!out_done) {
  1041     first_error->_verbose = false;
       
  1042 
       
  1043     staticBufferStream sbs(buffer, sizeof(buffer), &out);
  1001     staticBufferStream sbs(buffer, sizeof(buffer), &out);
  1044     first_error->report(&sbs);
  1002     report(&sbs, false);
  1045 
  1003 
  1046     out_done = true;
  1004     out_done = true;
  1047 
  1005 
  1048     first_error->_current_step = 0;         // reset current_step
  1006     _current_step = 0;
  1049     first_error->_current_step_info = "";   // reset current_step string
  1007     _current_step_info = "";
  1050   }
  1008   }
  1051 
  1009 
  1052   // print to error log file
  1010   // print to error log file
  1053   if (!log_done) {
  1011   if (!log_done) {
  1054     first_error->_verbose = true;
       
  1055 
       
  1056     // see if log file is already open
  1012     // see if log file is already open
  1057     if (!log.is_open()) {
  1013     if (!log.is_open()) {
  1058       // open log file
  1014       // open log file
  1059       int fd = prepare_log_file(ErrorFile, "hs_err_pid%p.log", buffer, sizeof(buffer));
  1015       int fd = prepare_log_file(ErrorFile, "hs_err_pid%p.log", buffer, sizeof(buffer));
  1060       if (fd != -1) {
  1016       if (fd != -1) {
  1070         transmit_report_done = true;
  1026         transmit_report_done = true;
  1071       }
  1027       }
  1072     }
  1028     }
  1073 
  1029 
  1074     staticBufferStream sbs(buffer, O_BUFLEN, &log);
  1030     staticBufferStream sbs(buffer, O_BUFLEN, &log);
  1075     first_error->report(&sbs);
  1031     report(&sbs, true);
  1076     first_error->_current_step = 0;         // reset current_step
  1032     _current_step = 0;
  1077     first_error->_current_step_info = "";   // reset current_step string
  1033     _current_step_info = "";
  1078 
  1034 
  1079     // Run error reporting to determine whether or not to report the crash.
  1035     // Run error reporting to determine whether or not to report the crash.
  1080     if (!transmit_report_done && should_report_bug(first_error->_id)) {
  1036     if (!transmit_report_done && should_report_bug(_id)) {
  1081       transmit_report_done = true;
  1037       transmit_report_done = true;
  1082       const int fd2 = ::dup(log.fd());
  1038       const int fd2 = ::dup(log.fd());
  1083       FILE* const hs_err = ::fdopen(fd2, "r");
  1039       FILE* const hs_err = ::fdopen(fd2, "r");
  1084       if (NULL != hs_err) {
  1040       if (NULL != hs_err) {
  1085         ErrorReporter er;
  1041         ErrorReporter er;
  1147         }
  1103         }
  1148       }
  1104       }
  1149     }
  1105     }
  1150   }
  1106   }
  1151 
  1107 
  1152   static bool skip_bug_url = !should_report_bug(first_error->_id);
  1108   static bool skip_bug_url = !should_report_bug(_id);
  1153   if (!skip_bug_url) {
  1109   if (!skip_bug_url) {
  1154     skip_bug_url = true;
  1110     skip_bug_url = true;
  1155 
  1111 
  1156     out.print_raw_cr("#");
  1112     out.print_raw_cr("#");
  1157     print_bug_submit_message(&out, _thread);
  1113     print_bug_submit_message(&out, _thread);
  1160   if (!UseOSErrorReporting) {
  1116   if (!UseOSErrorReporting) {
  1161     // os::abort() will call abort hooks, try it first.
  1117     // os::abort() will call abort hooks, try it first.
  1162     static bool skip_os_abort = false;
  1118     static bool skip_os_abort = false;
  1163     if (!skip_os_abort) {
  1119     if (!skip_os_abort) {
  1164       skip_os_abort = true;
  1120       skip_os_abort = true;
  1165       bool dump_core = should_report_bug(first_error->_id);
  1121       bool dump_core = should_report_bug(_id);
  1166       os::abort(dump_core && CreateCoredumpOnCrash, _siginfo, _context);
  1122       os::abort(dump_core && CreateCoredumpOnCrash, _siginfo, _context);
  1167     }
  1123     }
  1168 
  1124 
  1169     // if os::abort() doesn't abort, try os::die();
  1125     // if os::abort() doesn't abort, try os::die();
  1170     os::die();
  1126     os::die();
  1175  * OnOutOfMemoryError scripts/commands executed while VM is a safepoint - this
  1131  * OnOutOfMemoryError scripts/commands executed while VM is a safepoint - this
  1176  * ensures utilities such as jmap can observe the process is a consistent state.
  1132  * ensures utilities such as jmap can observe the process is a consistent state.
  1177  */
  1133  */
  1178 class VM_ReportJavaOutOfMemory : public VM_Operation {
  1134 class VM_ReportJavaOutOfMemory : public VM_Operation {
  1179  private:
  1135  private:
  1180   VMError *_err;
  1136   const char* _message;
  1181  public:
  1137  public:
  1182   VM_ReportJavaOutOfMemory(VMError *err) { _err = err; }
  1138   VM_ReportJavaOutOfMemory(const char* message) { _message = message; }
  1183   VMOp_Type type() const                 { return VMOp_ReportJavaOutOfMemory; }
  1139   VMOp_Type type() const                        { return VMOp_ReportJavaOutOfMemory; }
  1184   void doit();
  1140   void doit();
  1185 };
  1141 };
  1186 
  1142 
  1187 void VM_ReportJavaOutOfMemory::doit() {
  1143 void VM_ReportJavaOutOfMemory::doit() {
  1188   // Don't allocate large buffer on stack
  1144   // Don't allocate large buffer on stack
  1189   static char buffer[O_BUFLEN];
  1145   static char buffer[O_BUFLEN];
  1190 
  1146 
  1191   tty->print_cr("#");
  1147   tty->print_cr("#");
  1192   tty->print_cr("# java.lang.OutOfMemoryError: %s", _err->message());
  1148   tty->print_cr("# java.lang.OutOfMemoryError: %s", _message);
  1193   tty->print_cr("# -XX:OnOutOfMemoryError=\"%s\"", OnOutOfMemoryError);
  1149   tty->print_cr("# -XX:OnOutOfMemoryError=\"%s\"", OnOutOfMemoryError);
  1194 
  1150 
  1195   // make heap parsability
  1151   // make heap parsability
  1196   Universe::heap()->ensure_parsability(false);  // no need to retire TLABs
  1152   Universe::heap()->ensure_parsability(false);  // no need to retire TLABs
  1197 
  1153 
  1210       tty->print_cr("os::fork_and_exec failed: %s (%d)", strerror(errno), errno);
  1166       tty->print_cr("os::fork_and_exec failed: %s (%d)", strerror(errno), errno);
  1211     }
  1167     }
  1212   }
  1168   }
  1213 }
  1169 }
  1214 
  1170 
  1215 void VMError::report_java_out_of_memory() {
  1171 void VMError::report_java_out_of_memory(const char* message) {
  1216   if (OnOutOfMemoryError && OnOutOfMemoryError[0]) {
  1172   if (OnOutOfMemoryError && OnOutOfMemoryError[0]) {
  1217     MutexLocker ml(Heap_lock);
  1173     MutexLocker ml(Heap_lock);
  1218     VM_ReportJavaOutOfMemory op(this);
  1174     VM_ReportJavaOutOfMemory op(message);
  1219     VMThread::execute(&op);
  1175     VMThread::execute(&op);
  1220   }
  1176   }
  1221 }
  1177 }