Imported Upstream version 5.14.0.93

Former-commit-id: dda284b8de49fb65cd1a403db6a592e6c68a5e8c
This commit is contained in:
Xamarin Public Jenkins (auto-signing) 2018-05-23 09:42:45 +00:00
parent fb453ffa72
commit 300ff421ef
63 changed files with 880 additions and 65 deletions

View File

@ -116,6 +116,9 @@
/* Disable advanced SSA JIT optimizations */ /* Disable advanced SSA JIT optimizations */
#undef DISABLE_SSA #undef DISABLE_SSA
/* Do not create structured crash files during unmanaged crashes */
#undef DISABLE_STRUCTURED_CRASH
/* Disables the verifier */ /* Disables the verifier */
#undef DISABLE_VERIFIER #undef DISABLE_VERIFIER
@ -1182,6 +1185,9 @@
/* AOT cross offsets file */ /* AOT cross offsets file */
#undef MONO_OFFSETS_FILE #undef MONO_OFFSETS_FILE
/* Do not include names of unmanaged functions in the crash dump */
#undef MONO_PRIVATE_CRASHES
/* Reduce runtime requirements (and capabilities) */ /* Reduce runtime requirements (and capabilities) */
#undef MONO_SMALL_CONFIG #undef MONO_SMALL_CONFIG

View File

@ -1 +1 @@
fa303f4752344e66680344ff3fb9e799370ebf04 5df36bf6767b4dc7856dd80dcc0b9b48d09fea80

View File

@ -1 +1 @@
eeb04e9455d7e096619d07605df365016c14a883 5fc828dca3fdf41143cc1f3b6afabb8ebbc1ce43

View File

@ -271,6 +271,36 @@ This flag is mutually exlusive with
By default the mkbundle tool will download from a Mono server the By default the mkbundle tool will download from a Mono server the
target runtimes, you can specify a different server to provide target runtimes, you can specify a different server to provide
cross-compiled runtimes. cross-compiled runtimes.
.TP
.I "--mono-api-struct-path FILE"
FILE points to a file with the definition of the \fIBundleMonoAPI\fP structure which contains the
required pointers to various Mono API functions used throughout the generated code. This mechanism
is meant to be used by third parties which embed the Mono runtime and dynamically load and initialize
it as part of the application startup, in which case the Mono APIs will not be available for the shared
library loader and the bundle will fail to work (one example of such an embedding third party is
Xamarin.Android).
After providing the definition FILE, the embedder must call the \fIvoid initialize_mono_api (const BundleMonoAPI *info)\fP
function found in the generated code
.B before
calling \fIvoid mono_mkbundle_init ()\fP. The structure passed to \fIinitialize_mono_api\fP doesn't need
to be dynamically allocated as its contents is copied to the local structure in the generated code and no
pointer to the passed structure is retained or used after \fIinitialize_mono_api\fP returns.
The list of pointers is not documented here. Instead, please look at the \fIbundle-mono-api.inc\fP file
found in the mkbundle source directory in your Mono source tree (\fImcs/tools/mkbundle\fP) or in the Mono's
GitHub repository, https://github.com/mono/mono/blob/master/mcs/tools/mkbundle/bundle-mono-api.inc
Please note that your structure must match the one expected by your version of the Mono runtime.
The file must also define the \fImkbundle_log_error\fP function with the following signature:
.nf
static void mkbundle_log_error (const char *format, ...) {}
.fi
The function should implement logging API specific to the embedder.
.SH OLD EMBEDDING .SH OLD EMBEDDING
.PP .PP
The old embedding system compiles a small C stub that embeds the The old embedding system compiles a small C stub that embeds the

View File

@ -34,7 +34,7 @@ static class Consts
// Use these assembly version constants to make code more maintainable. // Use these assembly version constants to make code more maintainable.
// //
public const string MonoVersion = "5.14.0.88"; public const string MonoVersion = "5.14.0.93";
public const string MonoCompany = "Mono development team"; public const string MonoCompany = "Mono development team";
public const string MonoProduct = "Mono Common Language Infrastructure"; public const string MonoProduct = "Mono Common Language Infrastructure";
public const string MonoCopyright = "(c) Various Mono authors"; public const string MonoCopyright = "(c) Various Mono authors";

View File

@ -1046,6 +1046,10 @@ namespace System.Net.Sockets
sockares.EndPoint = remoteEP = sockares.socket.RemapIPEndPoint (ep); sockares.EndPoint = remoteEP = sockares.socket.RemapIPEndPoint (ep);
} }
if (!sockares.socket.CanTryAddressFamily(sockares.EndPoint.AddressFamily)) {
throw new ArgumentException(SR.net_invalidAddressList);
}
int error = 0; int error = 0;
if (sockares.socket.connect_in_progress) { if (sockares.socket.connect_in_progress) {

View File

@ -6,6 +6,8 @@ using System.Text;
using System.Runtime.CompilerServices; using System.Runtime.CompilerServices;
using System.Runtime.InteropServices; using System.Runtime.InteropServices;
using Mono;
namespace System.IO { namespace System.IO {
class LogcatTextWriter : TextWriter { class LogcatTextWriter : TextWriter {
@ -74,8 +76,8 @@ namespace System.IO {
} }
} }
fixed (byte *b_message = Encoding.UTF8.GetBytes(message + '\0')) { using (SafeStringMarshal str = new SafeStringMarshal(message)) {
Log (b_message); Log ((byte*) str.Value);
} }
} }
} }

View File

@ -1 +1 @@
4913525f963d43fade0e1932c0866bac8f140691 e0c31033cb234fbe245111fd514aa92d8fdf2932

View File

@ -1 +1 @@
9302768848b4854f4376a91c4929aafd6795061c 0918023fa07a69ea21bf62858b5e96077aa3691c

View File

@ -1 +1 @@
215528fef1993434fd461a57c3460f4a39899f1a 0f0a171716a2a2c26c59478c41d1810394a93ca6

View File

@ -1 +1 @@
1487b6dcbd5d53290d8bf88e9b9cbcc8d9210d29 b79a2601bb345aa58d09bd453fc59773b13e326c

View File

@ -1 +1 @@
cabe8b4cef9177c57763ca5b11abb0a1ce63d426 e8a3d67696f746c7f1053bee56d7678f26e7ad44

View File

@ -1 +1 @@
6c3985cf067e80c8f89524faba458cf7595582e1 2ab602ec65de544966c6b22e2cf6c2901778f977

View File

@ -1 +1 @@
4472801ac00c2194a791897985400daccecb1d4f 70e683ec01f53c43698314560eea4bb57c2aa44d

View File

@ -1 +1 @@
2458f1050f4d8332227229fda6ef12dc68c26268 dbf109dbc245a0e693d2ded6244fa5929d0055be

View File

@ -1 +1 @@
4913525f963d43fade0e1932c0866bac8f140691 e0c31033cb234fbe245111fd514aa92d8fdf2932

View File

@ -1 +1 @@
9302768848b4854f4376a91c4929aafd6795061c 0918023fa07a69ea21bf62858b5e96077aa3691c

View File

@ -1 +1 @@
215528fef1993434fd461a57c3460f4a39899f1a 0f0a171716a2a2c26c59478c41d1810394a93ca6

View File

@ -1 +1 @@
1487b6dcbd5d53290d8bf88e9b9cbcc8d9210d29 b79a2601bb345aa58d09bd453fc59773b13e326c

View File

@ -1 +1 @@
cabe8b4cef9177c57763ca5b11abb0a1ce63d426 e8a3d67696f746c7f1053bee56d7678f26e7ad44

View File

@ -1 +1 @@
6c3985cf067e80c8f89524faba458cf7595582e1 2ab602ec65de544966c6b22e2cf6c2901778f977

View File

@ -1 +1 @@
4472801ac00c2194a791897985400daccecb1d4f 70e683ec01f53c43698314560eea4bb57c2aa44d

View File

@ -1 +1 @@
2458f1050f4d8332227229fda6ef12dc68c26268 dbf109dbc245a0e693d2ded6244fa5929d0055be

View File

@ -1 +1 @@
4913525f963d43fade0e1932c0866bac8f140691 e0c31033cb234fbe245111fd514aa92d8fdf2932

View File

@ -1 +1 @@
9302768848b4854f4376a91c4929aafd6795061c 0918023fa07a69ea21bf62858b5e96077aa3691c

View File

@ -1 +1 @@
215528fef1993434fd461a57c3460f4a39899f1a 0f0a171716a2a2c26c59478c41d1810394a93ca6

View File

@ -1 +1 @@
1487b6dcbd5d53290d8bf88e9b9cbcc8d9210d29 b79a2601bb345aa58d09bd453fc59773b13e326c

View File

@ -1 +1 @@
cabe8b4cef9177c57763ca5b11abb0a1ce63d426 e8a3d67696f746c7f1053bee56d7678f26e7ad44

View File

@ -1 +1 @@
6c3985cf067e80c8f89524faba458cf7595582e1 2ab602ec65de544966c6b22e2cf6c2901778f977

View File

@ -1 +1 @@
4472801ac00c2194a791897985400daccecb1d4f 70e683ec01f53c43698314560eea4bb57c2aa44d

View File

@ -1 +1 @@
2458f1050f4d8332227229fda6ef12dc68c26268 dbf109dbc245a0e693d2ded6244fa5929d0055be

View File

@ -4,7 +4,7 @@ include ../../build/rules.make
PROGRAM = mkbundle.exe PROGRAM = mkbundle.exe
OTHER_RES = template.c template_z.c template_main.c OTHER_RES = template.c template_z.c template_main.c template_common.inc bundle-mono-api.inc
RESOURCE_FILES = $(OTHER_RES) RESOURCE_FILES = $(OTHER_RES)
@ -17,7 +17,7 @@ EXTRA_DISTFILES = $(RESOURCE_FILES)
include ../../build/executable.make include ../../build/executable.make
mkbundle.exe: $(RESOURCE_FILES) $(the_lib): $(RESOURCE_FILES)
test-simple: simple.exe test-simple: simple.exe
mono --debug $(the_lib) --simple simple.exe -o foo && ./foo mono --debug $(the_lib) --simple simple.exe -o foo && ./foo

View File

@ -0,0 +1,40 @@
/* -*- C -*- */
/*
* The structure below should contain pointers to all the Mono runtime functions used throughout ANY
* of the generated C code. The reason for this is to avoid symbol load failures when the generated
* bundle is used by a third party which embeds Mono and loads it dynamically (like
* Xamarin.Android). Third parties should provide their own version of the structure - compatible
* with this one. This is done this way so that we don't have to make the API here public in any way
* or form and thus maintain freedom to break it as we see needed.
*
* Whenever ANY change to this structure is made, the `init_default_mono_api_struct` and
* `validate_api_struct` functions found in `template_common.inc` MUST be updated.
*
* The `mkbundle_log_error` must be provided by the embedding third party in order to implement a
* logging method specific to that third party (e.g. Xamarin.Android cannot use `fprintf` since it
* won't show up in the logcat).
*/
typedef struct BundleMonoAPI
{
void (*mono_register_bundled_assemblies) (const MonoBundledAssembly **assemblies);
void (*mono_register_config_for_assembly) (const char* assembly_name, const char* config_xml);
void (*mono_jit_set_aot_mode) (int mode);
void (*mono_aot_register_module) (void* aot_info);
void (*mono_config_parse_memory) (const char *buffer);
void (*mono_register_machine_config) (const char *config_xml);
} BundleMonoAPI;
#ifdef USE_DEFAULT_MONO_API_STRUCT
#include <stdio.h>
#include <stdarg.h>
static void
mkbundle_log_error (const char *format, ...)
{
va_list ap;
va_start (ap, format);
vfprintf (stderr, format, ap);
va_end (ap);
}
#endif // USE_DEFAULT_MONO_API_STRUCT

View File

@ -103,7 +103,8 @@ class MakeBundle {
"" ""
}; };
static string target_server = "https://download.mono-project.com/runtimes/raw/"; static string target_server = "https://download.mono-project.com/runtimes/raw/";
static string mono_api_struct_file;
static int Main (string [] args) static int Main (string [] args)
{ {
List<string> sources = new List<string> (); List<string> sources = new List<string> ();
@ -453,6 +454,13 @@ class MakeBundle {
aot_compile = true; aot_compile = true;
static_link = true; static_link = true;
break; break;
case "--mono-api-struct-path":
if (i+1 == top) {
Console.WriteLine ("Usage: --mono-api-struct-path <path/to/file>");
return 1;
}
mono_api_struct_file = args [++i];
break;
default: default:
sources.Add (args [i]); sources.Add (args [i]);
break; break;
@ -841,8 +849,6 @@ typedef struct {
const unsigned char *data; const unsigned char *data;
const unsigned int size; const unsigned int size;
} MonoBundledAssembly; } MonoBundledAssembly;
void mono_register_bundled_assemblies (const MonoBundledAssembly **assemblies);
void mono_register_config_for_assembly (const char* assembly_name, const char* config_xml);
"); ");
// These values are part of the public API, so they are expected not to change // These values are part of the public API, so they are expected not to change
@ -859,6 +865,20 @@ void mono_register_config_for_assembly (const char* assembly_name, cons
tc.WriteLine ("#include <mono/jit/jit.h>\n"); tc.WriteLine ("#include <mono/jit/jit.h>\n");
} }
Stream template_stream;
if (String.IsNullOrEmpty (mono_api_struct_file)) {
tc.WriteLine ("#define USE_DEFAULT_MONO_API_STRUCT");
template_stream = typeof (MakeBundle).Assembly.GetManifestResourceStream ("bundle-mono-api.inc");
} else {
template_stream = File.OpenRead (mono_api_struct_file);
}
StreamReader s;
using (s = new StreamReader (template_stream)) {
tc.Write (s.ReadToEnd ());
}
template_stream.Dispose ();
if (compress) { if (compress) {
tc.WriteLine ("typedef struct _compressed_data {"); tc.WriteLine ("typedef struct _compressed_data {");
tc.WriteLine ("\tMonoBundledAssembly assembly;"); tc.WriteLine ("\tMonoBundledAssembly assembly;");
@ -1008,6 +1028,12 @@ void mono_register_config_for_assembly (const char* assembly_name, cons
} }
tc.WriteLine ("\tNULL\n};\n"); tc.WriteLine ("\tNULL\n};\n");
// This must go before any attempt to access `mono_api`
using (template_stream = System.Reflection.Assembly.GetAssembly (typeof(MakeBundle)).GetManifestResourceStream ("template_common.inc")) {
using (s = new StreamReader (template_stream)) {
tc.Write (s.ReadToEnd ());
}
}
// AOT baked in plus loader // AOT baked in plus loader
foreach (string asm in aot_names){ foreach (string asm in aot_names){
@ -1016,7 +1042,7 @@ void mono_register_config_for_assembly (const char* assembly_name, cons
tc.WriteLine ("\nstatic void install_aot_modules (void) {\n"); tc.WriteLine ("\nstatic void install_aot_modules (void) {\n");
foreach (string asm in aot_names){ foreach (string asm in aot_names){
tc.WriteLine ("\tmono_aot_register_module (mono_aot_module_{0}_info);\n", asm); tc.WriteLine ("\tmono_api.mono_aot_register_module (mono_aot_module_{0}_info);\n", asm);
} }
string enum_aot_mode; string enum_aot_mode;
@ -1033,7 +1059,7 @@ void mono_register_config_for_assembly (const char* assembly_name, cons
default: default:
throw new Exception ("Unsupported AOT mode"); throw new Exception ("Unsupported AOT mode");
} }
tc.WriteLine ("\tmono_jit_set_aot_mode ({0});", enum_aot_mode); tc.WriteLine ("\tmono_api.mono_jit_set_aot_mode ({0});", enum_aot_mode);
tc.WriteLine ("\n}\n"); tc.WriteLine ("\n}\n");
@ -1048,12 +1074,12 @@ void mono_register_config_for_assembly (const char* assembly_name, cons
tc.WriteLine ("\nstatic void install_dll_config_files (void) {\n"); tc.WriteLine ("\nstatic void install_dll_config_files (void) {\n");
foreach (string[] ass in config_names){ foreach (string[] ass in config_names){
tc.WriteLine ("\tmono_register_config_for_assembly (\"{0}\", assembly_config_{1});\n", ass [0], ass [1]); tc.WriteLine ("\tmono_api.mono_register_config_for_assembly (\"{0}\", assembly_config_{1});\n", ass [0], ass [1]);
} }
if (config_file != null) if (config_file != null)
tc.WriteLine ("\tmono_config_parse_memory (&system_config);\n"); tc.WriteLine ("\tmono_api.mono_config_parse_memory (&system_config);\n");
if (machine_config_file != null) if (machine_config_file != null)
tc.WriteLine ("\tmono_register_machine_config (&machine_config);\n"); tc.WriteLine ("\tmono_api.mono_register_machine_config (&machine_config);\n");
tc.WriteLine ("}\n"); tc.WriteLine ("}\n");
if (config_dir != null) if (config_dir != null)
@ -1061,16 +1087,16 @@ void mono_register_config_for_assembly (const char* assembly_name, cons
else else
tc.WriteLine ("static const char *config_dir = NULL;"); tc.WriteLine ("static const char *config_dir = NULL;");
Stream template_stream;
if (compress) { if (compress) {
template_stream = System.Reflection.Assembly.GetAssembly (typeof(MakeBundle)).GetManifestResourceStream ("template_z.c"); template_stream = System.Reflection.Assembly.GetAssembly (typeof(MakeBundle)).GetManifestResourceStream ("template_z.c");
} else { } else {
template_stream = System.Reflection.Assembly.GetAssembly (typeof(MakeBundle)).GetManifestResourceStream ("template.c"); template_stream = System.Reflection.Assembly.GetAssembly (typeof(MakeBundle)).GetManifestResourceStream ("template.c");
} }
StreamReader s = new StreamReader (template_stream); using (s = new StreamReader (template_stream)) {
string template = s.ReadToEnd (); tc.Write (s.ReadToEnd ());
tc.Write (template); }
template_stream.Dispose ();
if (!nomain && custom_main == null) { if (!nomain && custom_main == null) {
Stream template_main_stream = System.Reflection.Assembly.GetAssembly (typeof(MakeBundle)).GetManifestResourceStream ("template_main.c"); Stream template_main_stream = System.Reflection.Assembly.GetAssembly (typeof(MakeBundle)).GetManifestResourceStream ("template_main.c");

View File

@ -1,7 +1,7 @@
void mono_mkbundle_init () void mono_mkbundle_init ()
{ {
install_dll_config_files (); install_dll_config_files ();
mono_register_bundled_assemblies(bundled); mono_api.mono_register_bundled_assemblies(bundled);
install_aot_modules (); install_aot_modules ();
} }

View File

@ -0,0 +1,61 @@
/* -*- C -*- */
#include <stdlib.h>
static BundleMonoAPI mono_api;
void initialize_mono_api (const BundleMonoAPI *info)
{
if (info == NULL) {
mkbundle_log_error ("mkbundle: missing Mono API info\n");
exit (1);
}
mono_api.mono_register_bundled_assemblies = info->mono_register_bundled_assemblies;
mono_api.mono_register_config_for_assembly = info->mono_register_config_for_assembly;
mono_api.mono_jit_set_aot_mode = info->mono_jit_set_aot_mode;
mono_api.mono_aot_register_module = info->mono_aot_register_module;
mono_api.mono_config_parse_memory = info->mono_config_parse_memory;
mono_api.mono_register_machine_config = info->mono_register_machine_config;
}
static int
validate_api_pointer (const char *name, void *ptr)
{
if (ptr != NULL)
return 0;
mkbundle_log_error ("mkbundle: Mono API pointer '%s' missing\n", name);
return 1;
}
static void
validate_api_struct ()
{
int missing = 0;
missing += validate_api_pointer ("mono_register_bundled_assemblies", mono_api.mono_register_bundled_assemblies);
missing += validate_api_pointer ("mono_register_config_for_assembly", mono_api.mono_register_config_for_assembly);
missing += validate_api_pointer ("mono_jit_set_aot_mode", mono_api.mono_jit_set_aot_mode);
missing += validate_api_pointer ("mono_aot_register_module", mono_api.mono_aot_register_module);
missing += validate_api_pointer ("mono_config_parse_memory", mono_api.mono_config_parse_memory);
missing += validate_api_pointer ("mono_register_machine_config", mono_api.mono_register_machine_config);
if (missing <= 0)
return;
mkbundle_log_error ("mkbundle: bundle not initialized properly, %d Mono API pointers are missing\n", missing);
exit (1);
}
static void
init_default_mono_api_struct ()
{
#ifdef USE_DEFAULT_MONO_API_STRUCT
mono_api.mono_register_bundled_assemblies = mono_register_bundled_assemblies;
mono_api.mono_register_config_for_assembly = mono_register_config_for_assembly;
mono_api.mono_jit_set_aot_mode = mono_jit_set_aot_mode;
mono_api.mono_aot_register_module = mono_aot_register_module;
mono_api.mono_config_parse_memory = mono_config_parse_memory;
mono_api.mono_register_machine_config = mono_register_machine_config;
#endif // USE_DEFAULT_MONO_API_STRUCT
}

View File

@ -48,6 +48,8 @@ void mono_mkbundle_init ()
Bytef *buffer; Bytef *buffer;
int nbundles; int nbundles;
init_default_mono_api_struct ();
validate_api_struct ();
install_dll_config_files (); install_dll_config_files ();
ptr = (CompressedAssembly **) compressed; ptr = (CompressedAssembly **) compressed;
@ -56,6 +58,12 @@ void mono_mkbundle_init ()
nbundles++; nbundles++;
bundled = (MonoBundledAssembly **) malloc (sizeof (MonoBundledAssembly *) * (nbundles + 1)); bundled = (MonoBundledAssembly **) malloc (sizeof (MonoBundledAssembly *) * (nbundles + 1));
if (bundled == NULL) {
// May fail...
mkbundle_log_error ("mkbundle: out of memory");
exit (1);
}
bundled_ptr = bundled; bundled_ptr = bundled;
ptr = (CompressedAssembly **) compressed; ptr = (CompressedAssembly **) compressed;
while (*ptr != NULL) { while (*ptr != NULL) {
@ -81,5 +89,5 @@ void mono_mkbundle_init ()
ptr++; ptr++;
} }
*bundled_ptr = NULL; *bundled_ptr = NULL;
mono_register_bundled_assemblies((const MonoBundledAssembly **) bundled); mono_api.mono_register_bundled_assemblies((const MonoBundledAssembly **) bundled);
} }

View File

@ -264,6 +264,7 @@
#define g_vasprintf monoeg_g_vasprintf #define g_vasprintf monoeg_g_vasprintf
#define g_win32_getlocale monoeg_g_win32_getlocale #define g_win32_getlocale monoeg_g_win32_getlocale
#define g_assertion_message monoeg_assertion_message #define g_assertion_message monoeg_assertion_message
#define g_get_assertion_message monoeg_get_assertion_message
#define g_malloc monoeg_malloc #define g_malloc monoeg_malloc
#define g_malloc0 monoeg_malloc0 #define g_malloc0 monoeg_malloc0
#define g_ptr_array_grow monoeg_ptr_array_grow #define g_ptr_array_grow monoeg_ptr_array_grow

View File

@ -584,6 +584,7 @@ GLogLevelFlags g_log_set_fatal_mask (const gchar *log_domain, GLogLevelFlags f
void g_logv (const gchar *log_domain, GLogLevelFlags log_level, const gchar *format, va_list args); void g_logv (const gchar *log_domain, GLogLevelFlags log_level, const gchar *format, va_list args);
void g_log (const gchar *log_domain, GLogLevelFlags log_level, const gchar *format, ...); void g_log (const gchar *log_domain, GLogLevelFlags log_level, const gchar *format, ...);
void g_assertion_message (const gchar *format, ...) G_GNUC_NORETURN; void g_assertion_message (const gchar *format, ...) G_GNUC_NORETURN;
const char * g_get_assertion_message (void);
#ifdef HAVE_C99_SUPPORT #ifdef HAVE_C99_SUPPORT
/* The for (;;) tells gc thats g_error () doesn't return, avoiding warnings */ /* The for (;;) tells gc thats g_error () doesn't return, avoiding warnings */

View File

@ -126,11 +126,22 @@ g_log (const gchar *log_domain, GLogLevelFlags log_level, const gchar *format, .
va_end (args); va_end (args);
} }
static char *failure_assertion = NULL;
const char *
g_get_assertion_message (void)
{
return failure_assertion;
}
void void
g_assertion_message (const gchar *format, ...) g_assertion_message (const gchar *format, ...)
{ {
va_list args; va_list args;
va_start (args, format);
g_vasprintf (&failure_assertion, format, args);
va_start (args, format); va_start (args, format);
g_logv (G_LOG_DOMAIN, G_LOG_LEVEL_ERROR, format, args); g_logv (G_LOG_DOMAIN, G_LOG_LEVEL_ERROR, format, args);
va_end (args); va_end (args);
@ -155,10 +166,57 @@ to_android_priority (GLogLevelFlags log_level)
return ANDROID_LOG_UNKNOWN; return ANDROID_LOG_UNKNOWN;
} }
#define LOG_MESSAGE_MAX_LEN 4096
static void
android_log_line (gint log_priority, const gchar *log_domain, gchar *log_message, gint log_len)
{
gchar log_buf [LOG_MESSAGE_MAX_LEN];
g_assert (log_len <= LOG_MESSAGE_MAX_LEN - 1);
/* If line is longer than LOG_MESSAGE_MAX_LEN - 1, then we simply cut it out. This is consistent with the previous behavior. */
strncpy (log_buf, log_message, log_len);
log_buf [log_len] = '\0';
__android_log_write (log_priority, log_domain, log_buf);
}
static void
android_log (gint log_priority, const gchar *log_domain, const gchar *log_message)
{
gint log_message_len, log_message_p_len;
gchar *log_message_p;
log_message_len = strlen (log_message);
if (log_message_len <= LOG_MESSAGE_MAX_LEN) {
__android_log_write (log_priority, log_domain, log_message);
return;
}
for (log_message_p = log_message; log_message_p < log_message + log_message_len;) {
gchar *p = strstr (log_message_p, "\n");
if (p == NULL) {
/* There is no more "\n". */
android_log_line (log_priority, log_domain, log_message_p, LOG_MESSAGE_MAX_LEN - 1);
break;
}
log_message_p_len = p - log_message_p;
if (log_message_p_len > LOG_MESSAGE_MAX_LEN - 1)
log_message_p_len = LOG_MESSAGE_MAX_LEN - 1;
android_log_line (log_priority, log_domain, log_message_p, log_message_p_len);
/* Set `log_message_p` to the character right after "\n" */
log_message_p = p + 1;
}
}
void void
g_log_default_handler (const gchar *log_domain, GLogLevelFlags log_level, const gchar *message, gpointer unused_data) g_log_default_handler (const gchar *log_domain, GLogLevelFlags log_level, const gchar *message, gpointer unused_data)
{ {
__android_log_write (to_android_priority (log_level), log_domain, message); android_log (to_android_priority (log_level), log_domain, message);
if (log_level & fatal) if (log_level & fatal)
abort (); abort ();
} }
@ -167,14 +225,14 @@ static void
default_stdout_handler (const gchar *message) default_stdout_handler (const gchar *message)
{ {
/* TODO: provide a proper app name */ /* TODO: provide a proper app name */
__android_log_write (ANDROID_LOG_ERROR, "mono", message); android_log (ANDROID_LOG_ERROR, "mono", message);
} }
static void static void
default_stderr_handler (const gchar *message) default_stderr_handler (const gchar *message)
{ {
/* TODO: provide a proper app name */ /* TODO: provide a proper app name */
__android_log_write (ANDROID_LOG_ERROR, "mono", message); android_log (ANDROID_LOG_ERROR, "mono", message);
} }

View File

@ -1 +1 @@
30544e52d5413d159ebfc887c18c8ca57dc512a2 eeede3fd1e7bbdb04ffb92845c9912d2b4def329

View File

@ -629,7 +629,9 @@ typedef struct {
gpointer (*create_delegate_trampoline) (MonoDomain *domain, MonoClass *klass); gpointer (*create_delegate_trampoline) (MonoDomain *domain, MonoClass *klass);
gpointer (*interp_get_remoting_invoke) (gpointer imethod, MonoError *error); gpointer (*interp_get_remoting_invoke) (gpointer imethod, MonoError *error);
GHashTable *(*get_weak_field_indexes) (MonoImage *image); GHashTable *(*get_weak_field_indexes) (MonoImage *image);
void (*runtime_telemetry_callback) (void); #ifdef TARGET_OSX
void (*install_state_summarizer) (void);
#endif
} MonoRuntimeCallbacks; } MonoRuntimeCallbacks;
typedef gboolean (*MonoInternalStackWalk) (MonoStackFrameInfo *frame, MonoContext *ctx, gpointer data); typedef gboolean (*MonoInternalStackWalk) (MonoStackFrameInfo *frame, MonoContext *ctx, gpointer data);
@ -647,6 +649,9 @@ typedef struct {
gboolean (*mono_above_abort_threshold) (void); gboolean (*mono_above_abort_threshold) (void);
void (*mono_clear_abort_threshold) (void); void (*mono_clear_abort_threshold) (void);
void (*mono_reraise_exception) (MonoException *ex); void (*mono_reraise_exception) (MonoException *ex);
#ifdef TARGET_OSX
void (*mono_summarize_stack) (MonoDomain *domain, MonoThreadSummary *out, MonoContext *crash_ctx);
#endif
} MonoRuntimeExceptionHandlingCallbacks; } MonoRuntimeExceptionHandlingCallbacks;
MONO_COLD void mono_set_pending_exception (MonoException *exc); MONO_COLD void mono_set_pending_exception (MonoException *exc);

View File

@ -295,4 +295,43 @@ mono_thread_internal_is_current (MonoInternalThread *internal);
gboolean gboolean
mono_threads_is_current_thread_in_protected_block (void); mono_threads_is_current_thread_in_protected_block (void);
#ifdef TARGET_OSX
#define MONO_MAX_SUMMARY_NAME_LEN 140
#define MONO_MAX_SUMMARY_THREADS 32
#define MONO_MAX_SUMMARY_FRAMES 40
typedef struct {
gboolean is_managed;
char str_descr [MONO_MAX_SUMMARY_NAME_LEN];
struct {
int token;
int il_offset;
int native_offset;
} managed_data;
struct {
intptr_t ip;
gboolean is_trampoline;
gboolean has_name;
} unmanaged_data;
} MonoFrameSummary;
typedef struct {
gboolean is_managed;
const char *name;
intptr_t managed_thread_ptr;
intptr_t info_addr;
intptr_t native_thread_id;
int num_managed_frames;
MonoFrameSummary managed_frames [MONO_MAX_SUMMARY_FRAMES];
int num_unmanaged_frames;
MonoFrameSummary unmanaged_frames [MONO_MAX_SUMMARY_FRAMES];
} MonoThreadSummary;
gboolean
mono_threads_summarize (MonoContext *ctx, gchar **out);
#endif
#endif /* _MONO_METADATA_THREADS_TYPES_H_ */ #endif /* _MONO_METADATA_THREADS_TYPES_H_ */

View File

@ -1 +1 @@
4221a74721ce7abdb902b7a2e9a0ebd03a18b626 2076561604c744a9962b1d7c8730136b7c0c977c

View File

@ -1 +1 @@
0af7d703a70750aa07b26a5dd0552e8bb896be00 40883bd5787aa951d2dd19ab3d388cf962220355

View File

@ -76,6 +76,10 @@
#include <mono/utils/mono-merp.h> #include <mono/utils/mono-merp.h>
#endif #endif
#ifndef HOST_WIN32
#include <mono/utils/mono-threads-debug.h>
#endif
#if defined(HOST_WATCHOS) #if defined(HOST_WATCHOS)
void void
@ -217,8 +221,18 @@ MONO_SIG_HANDLER_FUNC (static, sigterm_signal_handler)
MONO_SIG_HANDLER_INFO_TYPE *info = MONO_SIG_HANDLER_GET_INFO (); MONO_SIG_HANDLER_INFO_TYPE *info = MONO_SIG_HANDLER_GET_INFO ();
MONO_SIG_HANDLER_GET_CONTEXT; MONO_SIG_HANDLER_GET_CONTEXT;
if (mono_merp_enabled ()) // Note: this function only returns for a single thread
mono_handle_native_crash ("SIGTERM", ctx, info); // When it's invoked on other threads once the dump begins,
// those threads perform their dumps and then sleep until we
// die. The dump ends with the exit(1) below
MonoContext mctx;
gchar *output = NULL;
mono_sigctx_to_monoctx (ctx, &mctx);
if (!mono_threads_summarize (&mctx, &output))
g_assert_not_reached ();
// Only the dumping-supervisor thread exits mono_thread_summarize
MOSTLY_ASYNC_SAFE_PRINTF("Unhandled exception dump: \n######\n%s\n######\n", output);
mono_chain_signal (MONO_SIG_HANDLER_PARAMS); mono_chain_signal (MONO_SIG_HANDLER_PARAMS);
exit (1); exit (1);

View File

@ -1 +1 @@
52d96ac2667edf62d2f3cc4ba34f349b3d4fd8ab 13d84e99b840cfd0f64ad91c29a7fd2529ab3e67

View File

@ -1 +1 @@
#define FULL_VERSION "explicit/99fedb1" #define FULL_VERSION "explicit/0985509"

View File

@ -50,6 +50,8 @@ monoutils_sources = \
mono-log-darwin.c \ mono-log-darwin.c \
mono-merp.c \ mono-merp.c \
mono-merp.h \ mono-merp.h \
mono-state.h \
mono-state.c \
mono-internal-hash.c \ mono-internal-hash.c \
mono-internal-hash.h \ mono-internal-hash.h \
mono-io-portability.c \ mono-io-portability.c \

View File

@ -1 +1 @@
35bd901fd8fd0a57ad624389a8b542ac350a86c4 cd66bdf3ee839c1a783e27ecebc7733f76b9a4d9

View File

@ -445,8 +445,11 @@ mono_init_merp (const char *serviceName, const char *signal, pid_t crashed_pid,
} }
void void
mono_merp_invoke (pid_t crashed_pid, intptr_t thread_pointer, const char *signal) mono_merp_invoke (pid_t crashed_pid, intptr_t thread_pointer, const char *signal, const char *dump_file)
{ {
if (dump_file != NULL)
fprintf (stderr, "Crashing Dump File:\n####\n%s\n####\n", dump_file);
// This unique service name is used to communicate with merp over mach service ports // This unique service name is used to communicate with merp over mach service ports
char *serviceName = g_strdup_printf ("com.mono.merp.%.8x", crashed_pid); char *serviceName = g_strdup_printf ("com.mono.merp.%.8x", crashed_pid);

View File

@ -45,7 +45,7 @@ gboolean mono_merp_enabled (void);
* crash dump (leaving the caller to call exit), or terminates the runtime * crash dump (leaving the caller to call exit), or terminates the runtime
* when the registered telemetry application does not respond. * when the registered telemetry application does not respond.
*/ */
void mono_merp_invoke (pid_t crashed_pid, intptr_t thread_pointer, const char *signal); void mono_merp_invoke (pid_t crashed_pid, intptr_t thread_pointer, const char *signal, const char *dump_file);
#endif // TARGET_OSX #endif // TARGET_OSX

479
mono/utils/mono-state.c Normal file
View File

@ -0,0 +1,479 @@
/**
* \file
* Support for verbose unmanaged crash dumps
*
* Author:
* Alexander Kyte (alkyte@microsoft.com)
*
* (C) 2018 Microsoft, Inc.
*
*/
#include <config.h>
#include <glib.h>
#include <mono/utils/json.h>
#include <mono/utils/mono-state.h>
#include <mono/metadata/object-internals.h>
#ifdef TARGET_OSX
extern GCStats mono_gc_stats;
// For AOT mode
#include <mono/mini/mini-runtime.h>
#ifdef TARGET_OSX
#include <mach/mach.h>
#include <mach/task_info.h>
#endif
#define MONO_MAX_SUMMARY_LEN 900
static JsonWriter writer;
static GString static_gstr;
static char output_dump_str [MONO_MAX_SUMMARY_LEN];
static void mono_json_writer_init_static (void) {
static_gstr.len = 0;
static_gstr.allocated_len = MONO_MAX_SUMMARY_LEN;
static_gstr.str = output_dump_str;
memset (output_dump_str, 0, sizeof (output_dump_str));
writer.indent = 0;
writer.text = &static_gstr;
}
static void
mono_native_state_add_ctx (JsonWriter *writer, MonoContext *ctx)
{
// Context
mono_json_writer_indent (writer);
mono_json_writer_object_key(writer, "ctx");
mono_json_writer_object_begin(writer);
mono_json_writer_indent (writer);
mono_json_writer_object_key(writer, "IP");
mono_json_writer_printf (writer, "\"%p\",\n", (gpointer) MONO_CONTEXT_GET_IP (ctx));
mono_json_writer_indent (writer);
mono_json_writer_object_key(writer, "SP");
mono_json_writer_printf (writer, "\"%p\",\n", (gpointer) MONO_CONTEXT_GET_SP (ctx));
mono_json_writer_indent (writer);
mono_json_writer_object_key(writer, "BP");
mono_json_writer_printf (writer, "\"%p\"\n", (gpointer) MONO_CONTEXT_GET_BP (ctx));
mono_json_writer_indent_pop (writer);
mono_json_writer_indent (writer);
mono_json_writer_object_end (writer);
mono_json_writer_printf (writer, ",\n");
}
static void
mono_native_state_add_frame (JsonWriter *writer, MonoFrameSummary *frame)
{
mono_json_writer_indent (writer);
mono_json_writer_object_begin(writer);
if (frame->is_managed) {
mono_json_writer_indent (writer);
mono_json_writer_object_key(writer, "is_managed");
mono_json_writer_printf (writer, "\"%s\",\n", frame->is_managed ? "true" : "false");
}
if (frame->unmanaged_data.is_trampoline) {
mono_json_writer_indent (writer);
mono_json_writer_object_key(writer, "is_trampoline");
mono_json_writer_printf (writer, "\"true\",");
}
if (frame->is_managed) {
mono_json_writer_indent (writer);
mono_json_writer_object_key(writer, "assembly");
mono_json_writer_printf (writer, "\"%s\",\n", frame->str_descr);
mono_json_writer_indent (writer);
mono_json_writer_object_key(writer, "token");
mono_json_writer_printf (writer, "\"0x%05x\",\n", frame->managed_data.token);
mono_json_writer_indent (writer);
mono_json_writer_object_key(writer, "native_offset");
mono_json_writer_printf (writer, "\"0x%x\",\n", frame->managed_data.native_offset);
mono_json_writer_indent (writer);
mono_json_writer_object_key(writer, "il_offset");
mono_json_writer_printf (writer, "\"0x%05x\"\n", frame->managed_data.il_offset);
} else {
mono_json_writer_indent (writer);
mono_json_writer_object_key(writer, "native_address");
if (frame->unmanaged_data.ip)
mono_json_writer_printf (writer, "\"%p\"", (void *) frame->unmanaged_data.ip);
else
mono_json_writer_printf (writer, "\"outside mono-sgen\"");
if (frame->unmanaged_data.has_name) {
mono_json_writer_printf (writer, ",\n");
mono_json_writer_indent (writer);
mono_json_writer_object_key(writer, "unmanaged_name");
mono_json_writer_printf (writer, "\"%s\"\n", frame->str_descr);
} else {
mono_json_writer_printf (writer, "\n");
}
}
mono_json_writer_indent_pop (writer);
mono_json_writer_indent (writer);
mono_json_writer_object_end (writer);
}
static void
mono_native_state_add_frames (JsonWriter *writer, int num_frames, MonoFrameSummary *frames, const char *label)
{
mono_json_writer_indent (writer);
mono_json_writer_object_key(writer, label);
mono_json_writer_array_begin (writer);
mono_native_state_add_frame (writer, &frames [0]);
for (int i = 1; i < num_frames; ++i) {
mono_json_writer_printf (writer, ",\n");
mono_native_state_add_frame (writer, &frames [i]);
}
mono_json_writer_printf (writer, "\n");
mono_json_writer_indent_pop (writer);
mono_json_writer_indent (writer);
mono_json_writer_array_end (writer);
}
static void
mono_native_state_add_thread (JsonWriter *writer, MonoThreadSummary *thread, MonoContext *ctx)
{
static gboolean not_first_thread;
if (not_first_thread) {
mono_json_writer_printf (writer, ",\n");
} else {
not_first_thread = TRUE;
}
mono_json_writer_indent (writer);
mono_json_writer_object_begin(writer);
mono_json_writer_indent (writer);
mono_json_writer_object_key(writer, "is_managed");
mono_json_writer_printf (writer, "%s,\n", thread->is_managed ? "true" : "false");
mono_json_writer_indent (writer);
mono_json_writer_object_key(writer, "managed_thread_ptr");
mono_json_writer_printf (writer, "\"0x%x\",\n", (gpointer) thread->managed_thread_ptr);
mono_json_writer_indent (writer);
mono_json_writer_object_key(writer, "thread_info_addr");
mono_json_writer_printf (writer, "\"0x%x\",\n", (gpointer) thread->info_addr);
if (thread->name) {
mono_json_writer_indent (writer);
mono_json_writer_object_key(writer, "thread_name");
mono_json_writer_printf (writer, "\"%s\",\n", thread->name);
}
mono_json_writer_indent (writer);
mono_json_writer_object_key(writer, "native_thread_id");
mono_json_writer_printf (writer, "\"0x%x\",\n", (gpointer) thread->native_thread_id);
mono_native_state_add_ctx (writer, ctx);
if (thread->num_managed_frames > 0) {
mono_native_state_add_frames (writer, thread->num_managed_frames, thread->managed_frames, "managed_frames");
}
if (thread->num_unmanaged_frames > 0) {
if (thread->num_managed_frames > 0)
mono_json_writer_printf (writer, ",\n");
mono_native_state_add_frames (writer, thread->num_unmanaged_frames, thread->unmanaged_frames, "unmanaged_frames");
}
mono_json_writer_printf (writer, "\n");
mono_json_writer_indent (writer);
mono_json_writer_object_end (writer);
}
static void
mono_native_state_add_ee_info (JsonWriter *writer)
{
// FIXME: setup callbacks to enable
/*const char *aot_mode;*/
/*MonoAotMode mono_aot_mode = mono_jit_get_aot_mode ();*/
/*switch (mono_aot_mode) {*/
/*case MONO_AOT_MODE_NONE:*/
/*aot_mode = "none";*/
/*break;*/
/*case MONO_AOT_MODE_NORMAL:*/
/*aot_mode = "normal";*/
/*break;*/
/*case MONO_AOT_MODE_HYBRID:*/
/*aot_mode = "hybrid";*/
/*break;*/
/*case MONO_AOT_MODE_FULL:*/
/*aot_mode = "full";*/
/*break;*/
/*case MONO_AOT_MODE_LLVMONLY:*/
/*aot_mode = "llvmonly";*/
/*break;*/
/*case MONO_AOT_MODE_INTERP:*/
/*aot_mode = "interp";*/
/*break;*/
/*case MONO_AOT_MODE_INTERP_LLVMONLY:*/
/*aot_mode = "interp_llvmonly";*/
/*break;*/
/*default:*/
/*aot_mode = "error";*/
/*}*/
mono_json_writer_indent (writer);
mono_json_writer_object_key(writer, "execution_context");
mono_json_writer_object_begin(writer);
/*mono_json_writer_indent (writer);*/
/*mono_json_writer_object_key(writer, "aot_mode");*/
/*mono_json_writer_printf (writer, "\"%s\",\n", aot_mode);*/
/*mono_json_writer_indent (writer);*/
/*mono_json_writer_object_key(writer, "mono_use_llvm");*/
/*mono_json_writer_printf (writer, "\"%s\",\n", mono_use_llvm ? "true" : "false");*/
mono_json_writer_indent (writer);
mono_json_writer_object_key(writer, "coop-enabled");
mono_json_writer_printf (writer, "\"%s\"\n", mono_threads_are_safepoints_enabled () ? "true" : "false");
mono_json_writer_indent_pop (writer);
mono_json_writer_indent (writer);
mono_json_writer_object_end (writer);
mono_json_writer_printf (writer, ",\n");
}
// Taken from driver.c
#if defined(MONO_ARCH_ARCHITECTURE)
/* Redefine MONO_ARCHITECTURE to include more information */
#undef MONO_ARCHITECTURE
#define MONO_ARCHITECTURE MONO_ARCH_ARCHITECTURE
#endif
static void
mono_native_state_add_version (JsonWriter *writer)
{
mono_json_writer_indent (writer);
mono_json_writer_object_key(writer, "configuration");
mono_json_writer_object_begin(writer);
char *build = mono_get_runtime_callbacks ()->get_runtime_build_info ();
mono_json_writer_indent (writer);
mono_json_writer_object_key(writer, "version");
mono_json_writer_printf (writer, "\"%s\",\n", build);
mono_json_writer_indent (writer);
mono_json_writer_object_key(writer, "tlc");
#ifdef HAVE_KW_THREAD
mono_json_writer_printf (writer, "\"__thread\",\n");
#else
mono_json_writer_printf (writer, "\"normal\",\n");
#endif /* HAVE_KW_THREAD */
mono_json_writer_indent (writer);
mono_json_writer_object_key(writer, "sigsgev");
#ifdef MONO_ARCH_SIGSEGV_ON_ALTSTACK
mono_json_writer_printf (writer, "\"altstack\",\n");
#else
mono_json_writer_printf (writer, "\"normal\",\n");
#endif
mono_json_writer_indent (writer);
mono_json_writer_object_key(writer, "notifications");
#ifdef HAVE_EPOLL
mono_json_writer_printf (writer, "\"epoll\",\n");
#elif defined(HAVE_KQUEUE)
mono_json_writer_printf (writer, "\"kqueue\",\n");
#else
mono_json_writer_printf (writer, "\"thread+polling\",\n");
#endif
mono_json_writer_indent (writer);
mono_json_writer_object_key(writer, "architecture");
mono_json_writer_printf (writer, "\"%s\",\n", MONO_ARCHITECTURE);
mono_json_writer_indent (writer);
mono_json_writer_object_key(writer, "disabled_features");
mono_json_writer_printf (writer, "\"%s\",\n", DISABLED_FEATURES);
mono_json_writer_indent (writer);
mono_json_writer_object_key(writer, "smallconfig");
#ifdef MONO_SMALL_CONFIG
mono_json_writer_printf (writer, "\"enabled\",\n");
#else
mono_json_writer_printf (writer, "\"disabled\",\n");
#endif
mono_json_writer_indent (writer);
mono_json_writer_object_key(writer, "bigarrays");
#ifdef MONO_BIG_ARRAYS
mono_json_writer_printf (writer, "\"enabled\",\n");
#else
mono_json_writer_printf (writer, "\"disabled\",\n");
#endif
mono_json_writer_indent (writer);
mono_json_writer_object_key(writer, "softdebug");
#if !defined(DISABLE_SDB)
mono_json_writer_printf (writer, "\"enabled\",\n");
#else
mono_json_writer_printf (writer, "\"disabled\",\n");
#endif
mono_json_writer_indent (writer);
mono_json_writer_object_key(writer, "interpreter");
#ifndef DISABLE_INTERPRETER
mono_json_writer_printf (writer, "\"enabled\",\n");
#else
mono_json_writer_printf (writer, "\"disabled\",\n");
#endif
mono_json_writer_indent (writer);
mono_json_writer_object_key(writer, "llvm_support");
#ifdef MONO_ARCH_LLVM_SUPPORTED
#ifdef ENABLE_LLVM
mono_json_writer_printf (writer, "\"%s\"\n", LLVM_VERSION);
#else
mono_json_writer_printf (writer, "\"disabled\"\n");
#endif
#endif
mono_json_writer_indent_pop (writer);
mono_json_writer_indent (writer);
mono_json_writer_object_end (writer);
mono_json_writer_printf (writer, ",\n");
}
static void
mono_native_state_add_memory (JsonWriter *writer)
{
mono_json_writer_indent (writer);
mono_json_writer_object_key(writer, "memory");
mono_json_writer_object_begin(writer);
#ifdef TARGET_OSX
struct task_basic_info t_info;
memset (&t_info, 0, sizeof (t_info));
mach_msg_type_number_t t_info_count = TASK_BASIC_INFO_COUNT;
task_name_t task = mach_task_self ();
task_info(task, TASK_BASIC_INFO, (task_info_t) &t_info, &t_info_count);
mono_json_writer_indent (writer);
mono_json_writer_object_key(writer, "Resident Size");
mono_json_writer_printf (writer, "\"%lu\",\n", t_info.resident_size);
mono_json_writer_indent (writer);
mono_json_writer_object_key(writer, "Virtual Size");
mono_json_writer_printf (writer, "\"%lu\",\n", t_info.virtual_size);
#endif
GCStats stats;
memcpy (&stats, &mono_gc_stats, sizeof (GCStats));
mono_json_writer_indent (writer);
mono_json_writer_object_key(writer, "minor_gc_time");
mono_json_writer_printf (writer, "\"%lu\",\n", stats.minor_gc_time);
mono_json_writer_indent (writer);
mono_json_writer_object_key(writer, "major_gc_time");
mono_json_writer_printf (writer, "\"%lu\",\n", stats.major_gc_time);
mono_json_writer_indent (writer);
mono_json_writer_object_key(writer, "minor_gc_count");
mono_json_writer_printf (writer, "\"%lu\",\n", stats.minor_gc_count);
mono_json_writer_indent (writer);
mono_json_writer_object_key(writer, "major_gc_count");
mono_json_writer_printf (writer, "\"%lu\",\n", stats.major_gc_count);
mono_json_writer_indent (writer);
mono_json_writer_object_key(writer, "major_gc_time_concurrent");
mono_json_writer_printf (writer, "\"%lu\"\n", stats.major_gc_time_concurrent);
mono_json_writer_indent_pop (writer);
mono_json_writer_indent (writer);
mono_json_writer_object_end (writer);
mono_json_writer_printf (writer, ",\n");
}
static void
mono_native_state_add_prologue (JsonWriter *writer)
{
mono_json_writer_init (writer);
mono_json_writer_object_begin(writer);
mono_json_writer_indent (writer);
mono_json_writer_object_key(writer, "protocol_version");
mono_json_writer_printf (writer, "\"%s\",\n", MONO_NATIVE_STATE_PROTOCOL_VERSION);
mono_native_state_add_version (writer);
#ifndef MONO_PRIVATE_CRASHES
mono_native_state_add_ee_info (writer);
#endif
mono_native_state_add_memory (writer);
const char *assertion_msg = g_get_assertion_message ();
if (assertion_msg != NULL) {
mono_json_writer_indent (writer);
mono_json_writer_object_key(writer, "assertion_message");
char *pos;
if ((pos = strchr (assertion_msg, '\n')) != NULL)
*pos = '\0';
mono_json_writer_printf (writer, "\"%s\",\n", assertion_msg);
}
// Start threads array
mono_json_writer_indent (writer);
mono_json_writer_object_key(writer, "threads");
mono_json_writer_array_begin (writer);
}
static void
mono_native_state_add_epilogue (JsonWriter *writer)
{
mono_json_writer_indent_pop (writer);
mono_json_writer_printf (writer, "\n");
mono_json_writer_indent (writer);
mono_json_writer_array_end (writer);
mono_json_writer_indent_pop (writer);
mono_json_writer_indent (writer);
mono_json_writer_object_end (writer);
mono_json_writer_printf (writer, "\n");
}
void
mono_summarize_native_state_begin (void)
{
mono_json_writer_init_static ();
mono_native_state_add_prologue (&writer);
}
char *
mono_summarize_native_state_end (void)
{
mono_native_state_add_epilogue (&writer);
return writer.text->str;
}
void
mono_summarize_native_state_add_thread (MonoThreadSummary *thread, MonoContext *ctx)
{
mono_native_state_add_thread (&writer, thread, ctx);
}
#endif // TARGET_OSX

36
mono/utils/mono-state.h Normal file
View File

@ -0,0 +1,36 @@
/**
* \file
* Support for cooperative creation of unmanaged state dumps
*
* Author:
* Alexander Kyte (alkyte@microsoft.com)
*
* (C) 2018 Microsoft, Inc.
*
*/
#ifndef __MONO_UTILS_NATIVE_STATE__
#define __MONO_UTILS_NATIVE_STATE__
#ifdef TARGET_OSX
#include <mono/utils/mono-publib.h>
#include <mono/utils/mono-context.h>
#include <mono/metadata/threads-types.h>
#define MONO_NATIVE_STATE_PROTOCOL_VERSION "0.0.1"
MONO_BEGIN_DECLS
void
mono_summarize_native_state_begin (void);
char *
mono_summarize_native_state_end (void);
void
mono_summarize_native_state_add_thread (MonoThreadSummary *thread, MonoContext *ctx);
MONO_END_DECLS
#endif // TARGET_OSX
#endif // MONO_UTILS_NATIVE_STATE

Binary file not shown.

View File

@ -1 +1 @@
7718f3fa44677f27a38385291d1024f330626f0b 80d743d6111377b7ec2c45f8714f8a12bc4359b5

Binary file not shown.

View File

@ -1 +1 @@
0a2aaa9c3b319d85d75797276bb79dbb0bf9e295 1fc022089fba35a14e3acc1570832de14b8a3eb7

Binary file not shown.

View File

@ -1 +1 @@
abf511bb63f84f5f141c6b95f68851e63bda888a 0f600dd8a8aefd29bf4464227563f9c6c33f35d6

View File

@ -6,9 +6,9 @@
#, fuzzy #, fuzzy
msgid "" msgid ""
msgstr "" msgstr ""
"Project-Id-Version: mono 5.14.0.88\n" "Project-Id-Version: mono 5.14.0.93\n"
"Report-Msgid-Bugs-To: http://www.mono-project.com/Bugs\n" "Report-Msgid-Bugs-To: http://www.mono-project.com/Bugs\n"
"POT-Creation-Date: 2018-05-22 08:22+0000\n" "POT-Creation-Date: 2018-05-23 08:41+0000\n"
"PO-Revision-Date: YEAR-MO-DA HO:MI+ZONE\n" "PO-Revision-Date: YEAR-MO-DA HO:MI+ZONE\n"
"Last-Translator: FULL NAME <EMAIL@ADDRESS>\n" "Last-Translator: FULL NAME <EMAIL@ADDRESS>\n"
"Language-Team: LANGUAGE <LL@li.org>\n" "Language-Team: LANGUAGE <LL@li.org>\n"

Binary file not shown.

View File

@ -1 +1 @@
be2de23906ac7e2b3a64dab46113061b10a5b8ec 6c0693507274ad01db54288b85fc31df896fc51c