From a003944d0fa3fa28c2c6c63a907c939ffdc7a5e9 Mon Sep 17 00:00:00 2001 From: Aleksey Kliger Date: Fri, 12 Mar 2021 17:02:15 -0500 Subject: [PATCH 01/55] XXX wip hot reload component - doesn't build - Mar 12 --- src/mono/mono/CMakeLists.txt | 6 ++ src/mono/mono/component/CMakeLists.txt | 17 ++++ src/mono/mono/component/component.h | 16 ++++ src/mono/mono/component/hot_reload.c | 45 ++++++++++ src/mono/mono/component/hot_reload.h | 18 ++++ src/mono/mono/metadata/CMakeLists.txt | 2 + src/mono/mono/metadata/components.c | 100 +++++++++++++++++++++++ src/mono/mono/metadata/components.h | 25 ++++++ src/mono/mono/metadata/hot_reload-stub.c | 31 +++++++ src/mono/mono/utils/mono-compiler.h | 12 +++ 10 files changed, 272 insertions(+) create mode 100644 src/mono/mono/component/CMakeLists.txt create mode 100644 src/mono/mono/component/component.h create mode 100644 src/mono/mono/component/hot_reload.c create mode 100644 src/mono/mono/component/hot_reload.h create mode 100644 src/mono/mono/metadata/components.c create mode 100644 src/mono/mono/metadata/components.h create mode 100644 src/mono/mono/metadata/hot_reload-stub.c diff --git a/src/mono/mono/CMakeLists.txt b/src/mono/mono/CMakeLists.txt index 817a804b68752c..4a935062fe4ea6 100644 --- a/src/mono/mono/CMakeLists.txt +++ b/src/mono/mono/CMakeLists.txt @@ -8,6 +8,12 @@ if(ENABLE_PERFTRACING) ) endif(ENABLE_PERFTRACING) +if(NOT STATIC_COMPONENTS) + list(APPEND subdirs + component + ) +endif() + foreach(dir ${subdirs}) add_subdirectory(${dir}) endforeach() diff --git a/src/mono/mono/component/CMakeLists.txt b/src/mono/mono/component/CMakeLists.txt new file mode 100644 index 00000000000000..bfc008267d9cfc --- /dev/null +++ b/src/mono/mono/component/CMakeLists.txt @@ -0,0 +1,17 @@ + +set(component_sources_base + component.h + ) + +set(hot_reload_sources_base + ${component_source_base} + hot-reload.c + hot-reload.h + ) + + +if(NOT STATIC_COMPONENTS) + add_library(mono-component-hot_reload SHARED "${hot_reload_sources}") + target_link_libraries(mono-component-hot_reload monosgen-shared) + install(TARGETS mono-component_hot_reload LIBRARY) +endif() diff --git a/src/mono/mono/component/component.h b/src/mono/mono/component/component.h new file mode 100644 index 00000000000000..71d27ea1bbe0ef --- /dev/null +++ b/src/mono/mono/component/component.h @@ -0,0 +1,16 @@ +// Licensed to the .NET Foundation under one or more agreements. +// The .NET Foundation licenses this file to you under the MIT license. +// + +#ifndef _MONO_COMPONENT_COMPONENT_H +#define _MONO_COMPONENT_COMPONENT_H + +typedef struct _MonoComponent MonoComponent; + +typedef void (*MonoComponent_CleanupFn) (MonoComponent *self); + +struct _MonoComponent { + MonoComponent_CleanupFn cleanup; +}; + +#endif/*_MONO_COMPONENT_COMPONENT_H*/ diff --git a/src/mono/mono/component/hot_reload.c b/src/mono/mono/component/hot_reload.c new file mode 100644 index 00000000000000..0f988265ed1210 --- /dev/null +++ b/src/mono/mono/component/hot_reload.c @@ -0,0 +1,45 @@ +// Licensed to the .NET Foundation under one or more agreements. +// The .NET Foundation licenses this file to you under the MIT license. +// + +#include +#include + +#include + +#include + +MONO_COMPONENT_EXPORT_ENTRYPOINT +MonoComponentHotReload * +mono_component_hot_reload_init (void); + +static void +hot_reload_cleanup (void); + +static void +hot_reload_apply_changes (MonoImage *base_image, gconstpointer dmeta, uint32_t dmeta_len, gconstpointer dil, uint32_t dil_len, MonoError *error); + +static MonoComponentHotReload fn_table = { + { &hot_reload_cleanup }, + &hot_reload_apply_changes, +}; + +MonoComponentHotReload * +mono_component_hot_reload_init (void); +{ + /* TODO: initialize things */ + + return &fn_table; +} + +static +hot_reload_cleanup (void) +{ + static gboolean cleaned = FALSE; + if (cleaned) + return; + + /* TODO: implement me */ + + cleaned = TRUE; +} diff --git a/src/mono/mono/component/hot_reload.h b/src/mono/mono/component/hot_reload.h new file mode 100644 index 00000000000000..e97fcfc942bf2e --- /dev/null +++ b/src/mono/mono/component/hot_reload.h @@ -0,0 +1,18 @@ +// Licensed to the .NET Foundation under one or more agreements. +// The .NET Foundation licenses this file to you under the MIT license. +// + +#ifndef _MONO_COMPONENT_HOT_RELOAD_H +#define _MONO_COMPONENT_HOT_RELOAD_H + +#include +#include "mono/metadata/object-forward.h" +#include "mono/utils/mono-error.h" +#include "mono/component/component.h" + +typedef struct _MonoComponentHotReload { + MonoComponent component; + void (*apply_changes) (MonoImage *base_image, gconstpointer dmeta, uint32_t dmeta_len, gconstpointer dil, uint32_t dil_len, MonoError *error); +} + +#endif/*_MONO_COMPONENT_HOT_RELOAD_H*/ diff --git a/src/mono/mono/metadata/CMakeLists.txt b/src/mono/mono/metadata/CMakeLists.txt index 4b56d07c440560..1b7ba75f6b0e44 100644 --- a/src/mono/mono/metadata/CMakeLists.txt +++ b/src/mono/mono/metadata/CMakeLists.txt @@ -71,6 +71,8 @@ set(metadata_common_sources class-setup-vtable.c cominterop.c cominterop.h + components.h + components.c coree.c coree.h coree-internals.h diff --git a/src/mono/mono/metadata/components.c b/src/mono/mono/metadata/components.c new file mode 100644 index 00000000000000..4ed2257e207a4b --- /dev/null +++ b/src/mono/mono/metadata/components.c @@ -0,0 +1,100 @@ +// Licensed to the .NET Foundation under one or more agreements. +// The .NET Foundation licenses this file to you under the MIT license. +// + +#include +#include +#include "mono/component/component.h" +#include "mono/component/hot_reload.h" +#include "mono/metadata/components.h" +#include "mono/utils/mono-dl.h" + +typedef MonoComponent * (*MonoComponentInitFn) (void); + +/* List of MonoDl* for each loaded component */ +static GSList *loaded_components; + +/* One static per component */ +static MonoComponentHotReload *hot_reload; + +static MonoComponentInitFn +get_component (const char *component_name, MonoDl **component_lib); + +void +mono_components_init (void) +{ +#ifdef STATIC_LINK_COMPONENTS + /* directly call each components init function */ + hot_reload = mono_component_hot_reload_init (); +#else + /* call get_component for each component and init it or its stubs and add it to loaded_components */ + MonoDl *lib = NULL; + + /* Repeat for each component */ + hot_reload = (MonoComponentHotReload*)get_component ("hot_reload", &lib); + if (hot_reload) { + loaded_components = g_slist_prepend (loaded_components, lib); + } else { + hot_reload = mono_component_hot_reload_stub_init (); + } + +#endif +} + + +void +mono_components_cleanup (void) +{ + /* call each components cleanup fn */ + if (hot_reload) { + hot_reload->component.cleanup (); + hot_reload = NULL; + } +#ifndef STATIC_LINK_COMPONENTS + for (GSList *p = loaded_components; p != NULL; p = p->next) { + mono_dl_close ((MonoDl*)p->data); + } +#endif +} + +static char* +component_library_name (const char *component) +{ + return g_strdup_printf ("mono-component-%s%s", component, MONO_SOLIB_EXT); +} + +static char* +component_init_name (const char *component) +{ + return g_strdup_printf ("mono_component_%s_init", component_name); +} + +MonoComponentInitFn +get_component (const char *component_name, MonoDl **lib_out) +{ + char *component_lib = component_library_name (component_name); + char *error_msg = NULL; + MonoComponentInitFn result = NULL; + MonoDl *lib = mono_dl_open (component_lib, MONO_DL_EAGER, &error_msg); + if (!lib) { + mono_trace (G_LOG_LEVEL_DEBUG, MONO_TRACE_DLLIMPORT, "Component %s not found: %s", component_name, error_msg); + g_free (error_msg); + g_free (component_lib); + goto done; + } + + char *comoponent_init = component_init_name (component_name); + gpointer sym = NULL; + error_msg = mono_dl_sym (lib, component_init, &sym); + if (error_msg) { + mono_trace (G_LOG_LEVEL_DEBUG, MONO_TRACE_DLLIMPORT, "Component %s library does not have symbol %s: %s", component_name, component_init, error_msg); + g_free (error_msg); + g_free (component_init); + goto done; + } + + result = sym; + *lib_out = lib; +done: + return result; +} diff --git a/src/mono/mono/metadata/components.h b/src/mono/mono/metadata/components.h new file mode 100644 index 00000000000000..8d3f6abff10008 --- /dev/null +++ b/src/mono/mono/metadata/components.h @@ -0,0 +1,25 @@ +// Licensed to the .NET Foundation under one or more agreements. +// The .NET Foundation licenses this file to you under the MIT license. +// + +#ifndef _MONO_METADATA_COMPONENTS_H +#define _MONO_METADATA_COMPONENTS_H + +#include +#include + +void +mono_components_init (void); + +void +mono_components_cleanup (void); + +/* Declare each component's getter function here */ +MonoComponentHotReload * +mono_component_hot_reload (void); + +/* Declare each copomnents stub init function here */ +MonoComponentHotReload * +mono_component_hot_reload_stub_init (void); + +#endif/*_MONO_METADATA_COMPONENTS_H*/ diff --git a/src/mono/mono/metadata/hot_reload-stub.c b/src/mono/mono/metadata/hot_reload-stub.c new file mode 100644 index 00000000000000..4a44062ee63e38 --- /dev/null +++ b/src/mono/mono/metadata/hot_reload-stub.c @@ -0,0 +1,31 @@ +// Licensed to the .NET Foundation under one or more agreements. +// The .NET Foundation licenses this file to you under the MIT license. +// + +#include +#include +#include "mono/component/component.h" +#include "mono/component/hot_reload.h" +#include "mono/utils/mono-error-internals.h" + +static MonoComponentHotReload fn_table = { + { &hot_reload_stub_cleanup }, + &hot_reload_stub_apply_changes, +}; + +MonoComponentHotReload * +mono_component_hot_reload_stub_init (void) +{ + return &fn_table; +} + +void +hot_reload_stub_cleanup (void) +{ +} + +void +hot_reload_stub_apply_changes (MonoImage *base_image, gconstpointer dmeta, uint32_t dmeta_len, gconstpointer dil, uint32_t dil_len, MonoError *error) +{ + mono_error_set_not_supported (error, "Hot reload not supported in this runtime."); +} diff --git a/src/mono/mono/utils/mono-compiler.h b/src/mono/mono/utils/mono-compiler.h index 4f6043e3349d22..71d5c60c70d35a 100644 --- a/src/mono/mono/utils/mono-compiler.h +++ b/src/mono/mono/utils/mono-compiler.h @@ -81,6 +81,18 @@ typedef ptrdiff_t ssize_t; /* Used to mark internal functions used by the CoreFX PAL library */ #define MONO_PAL_API MONO_API +/* Mono components */ + +/* User to mark internal functions used by dynamically linked runtime components */ +#define MONO_COMPONENT_API MONO_API + +#ifdef COMPILING_COMPONENT_DYNAMIC +#define MONO_COMPONENT_EXPORT_ENTRYPOINT MONO_EXTERN_C MONO_API_EXPORT +#else +#define MONO_COMPONENT_EXPORT_ENTRYPOINT /* empty */ +#endif + + #ifdef __GNUC__ #define MONO_ALWAYS_INLINE __attribute__ ((__always_inline__)) #elif defined(_MSC_VER) From 4af68816a101ecdb0685c67aeb9977af01990f10 Mon Sep 17 00:00:00 2001 From: Aleksey Kliger Date: Thu, 18 Mar 2021 16:45:28 -0400 Subject: [PATCH 02/55] XXX - wip hot reload component - checkpoint - it builds - Mar 18 static linking not done yet. no idea if it runs. the component dylibs aren't copied from obj/ to bin/ --- src/mono/mono/CMakeLists.txt | 6 ------ src/mono/mono/component/CMakeLists.txt | 11 +++++++---- src/mono/mono/component/hot_reload.c | 16 +++++++++++----- src/mono/mono/component/hot_reload.h | 2 +- src/mono/mono/metadata/CMakeLists.txt | 6 +++++- src/mono/mono/metadata/components.c | 9 +++++---- src/mono/mono/metadata/components.h | 2 +- src/mono/mono/metadata/hot_reload-stub.c | 9 ++++++++- src/mono/mono/mini/CMakeLists.txt | 2 ++ 9 files changed, 40 insertions(+), 23 deletions(-) diff --git a/src/mono/mono/CMakeLists.txt b/src/mono/mono/CMakeLists.txt index 4a935062fe4ea6..817a804b68752c 100644 --- a/src/mono/mono/CMakeLists.txt +++ b/src/mono/mono/CMakeLists.txt @@ -8,12 +8,6 @@ if(ENABLE_PERFTRACING) ) endif(ENABLE_PERFTRACING) -if(NOT STATIC_COMPONENTS) - list(APPEND subdirs - component - ) -endif() - foreach(dir ${subdirs}) add_subdirectory(${dir}) endforeach() diff --git a/src/mono/mono/component/CMakeLists.txt b/src/mono/mono/component/CMakeLists.txt index bfc008267d9cfc..9ec869c3734106 100644 --- a/src/mono/mono/component/CMakeLists.txt +++ b/src/mono/mono/component/CMakeLists.txt @@ -5,13 +5,16 @@ set(component_sources_base set(hot_reload_sources_base ${component_source_base} - hot-reload.c - hot-reload.h + hot_reload.c + hot_reload.h ) +addprefix(hot_reload_sources ../component "${hot_reload_sources_base}") + +add_library(hot_reload-objects OBJECT "${hot_reload_sources}") if(NOT STATIC_COMPONENTS) - add_library(mono-component-hot_reload SHARED "${hot_reload_sources}") + add_library(mono-component-hot_reload SHARED $) target_link_libraries(mono-component-hot_reload monosgen-shared) - install(TARGETS mono-component_hot_reload LIBRARY) + install(TARGETS mono-component-hot_reload LIBRARY) endif() diff --git a/src/mono/mono/component/hot_reload.c b/src/mono/mono/component/hot_reload.c index 0f988265ed1210..eca3e7a6a6eacf 100644 --- a/src/mono/mono/component/hot_reload.c +++ b/src/mono/mono/component/hot_reload.c @@ -5,7 +5,7 @@ #include #include -#include +#include #include @@ -14,7 +14,7 @@ MonoComponentHotReload * mono_component_hot_reload_init (void); static void -hot_reload_cleanup (void); +hot_reload_cleanup (MonoComponent *self); static void hot_reload_apply_changes (MonoImage *base_image, gconstpointer dmeta, uint32_t dmeta_len, gconstpointer dil, uint32_t dil_len, MonoError *error); @@ -25,15 +25,15 @@ static MonoComponentHotReload fn_table = { }; MonoComponentHotReload * -mono_component_hot_reload_init (void); +mono_component_hot_reload_init (void) { /* TODO: initialize things */ return &fn_table; } -static -hot_reload_cleanup (void) +static void +hot_reload_cleanup (MonoComponent *self) { static gboolean cleaned = FALSE; if (cleaned) @@ -43,3 +43,9 @@ hot_reload_cleanup (void) cleaned = TRUE; } + +static void +hot_reload_apply_changes (MonoImage *base_image, gconstpointer dmeta, uint32_t dmeta_len, gconstpointer dil, uint32_t dil_len, MonoError *error) +{ + printf ("it worked!\n"); +} diff --git a/src/mono/mono/component/hot_reload.h b/src/mono/mono/component/hot_reload.h index e97fcfc942bf2e..97f56b6b05cd99 100644 --- a/src/mono/mono/component/hot_reload.h +++ b/src/mono/mono/component/hot_reload.h @@ -13,6 +13,6 @@ typedef struct _MonoComponentHotReload { MonoComponent component; void (*apply_changes) (MonoImage *base_image, gconstpointer dmeta, uint32_t dmeta_len, gconstpointer dil, uint32_t dil_len, MonoError *error); -} +} MonoComponentHotReload; #endif/*_MONO_COMPONENT_HOT_RELOAD_H*/ diff --git a/src/mono/mono/metadata/CMakeLists.txt b/src/mono/mono/metadata/CMakeLists.txt index 1b7ba75f6b0e44..4890c7c46b7843 100644 --- a/src/mono/mono/metadata/CMakeLists.txt +++ b/src/mono/mono/metadata/CMakeLists.txt @@ -52,6 +52,10 @@ else() set(metadata_platform_sources ${metadata_unix_sources}) endif() +set(component_stub_sources + hot_reload-stub.c +) + set(metadata_common_sources appdomain.c domain.c @@ -236,7 +240,7 @@ set(reloc_libdir "${CMAKE_INSTALL_LIBDIR}") set_source_files_properties(../metadata/mono-config-dirs.c PROPERTIES COMPILE_DEFINITIONS "MONO_BINDIR=\"${bindir}\";MONO_ASSEMBLIES=\"${assembliesdir}\";MONO_CFG_DIR=\"${confdir}\";MONO_RELOC_LIBDIR=\"../${reloc_libdir}\"") -addprefix(metadata_sources ../metadata/ "${metadata_platform_sources};${metadata_common_sources};${metadata_gc_dependent_sources};${metadata_sgen_sources};${ilgen_sources}") +addprefix(metadata_sources ../metadata/ "${metadata_platform_sources};${metadata_common_sources};${metadata_gc_dependent_sources};${metadata_sgen_sources};${ilgen_sources};${component_stub_sources}") set(metadata_public_headers_base appdomain.h diff --git a/src/mono/mono/metadata/components.c b/src/mono/mono/metadata/components.c index 4ed2257e207a4b..fad54c5ab8b8ac 100644 --- a/src/mono/mono/metadata/components.c +++ b/src/mono/mono/metadata/components.c @@ -8,6 +8,7 @@ #include "mono/component/hot_reload.h" #include "mono/metadata/components.h" #include "mono/utils/mono-dl.h" +#include "mono/utils/mono-logger-internals.h" typedef MonoComponent * (*MonoComponentInitFn) (void); @@ -47,7 +48,7 @@ mono_components_cleanup (void) { /* call each components cleanup fn */ if (hot_reload) { - hot_reload->component.cleanup (); + hot_reload->component.cleanup (&hot_reload->component); hot_reload = NULL; } #ifndef STATIC_LINK_COMPONENTS @@ -66,7 +67,7 @@ component_library_name (const char *component) static char* component_init_name (const char *component) { - return g_strdup_printf ("mono_component_%s_init", component_name); + return g_strdup_printf ("mono_component_%s_init", component); } MonoComponentInitFn @@ -83,9 +84,9 @@ get_component (const char *component_name, MonoDl **lib_out) goto done; } - char *comoponent_init = component_init_name (component_name); + char *component_init = component_init_name (component_name); gpointer sym = NULL; - error_msg = mono_dl_sym (lib, component_init, &sym); + error_msg = mono_dl_symbol (lib, component_init, &sym); if (error_msg) { mono_trace (G_LOG_LEVEL_DEBUG, MONO_TRACE_DLLIMPORT, "Component %s library does not have symbol %s: %s", component_name, component_init, error_msg); g_free (error_msg); diff --git a/src/mono/mono/metadata/components.h b/src/mono/mono/metadata/components.h index 8d3f6abff10008..8e0ec94984b96d 100644 --- a/src/mono/mono/metadata/components.h +++ b/src/mono/mono/metadata/components.h @@ -6,7 +6,7 @@ #define _MONO_METADATA_COMPONENTS_H #include -#include +#include void mono_components_init (void); diff --git a/src/mono/mono/metadata/hot_reload-stub.c b/src/mono/mono/metadata/hot_reload-stub.c index 4a44062ee63e38..c1bdc871309937 100644 --- a/src/mono/mono/metadata/hot_reload-stub.c +++ b/src/mono/mono/metadata/hot_reload-stub.c @@ -6,8 +6,15 @@ #include #include "mono/component/component.h" #include "mono/component/hot_reload.h" +#include "mono/metadata/components.h" #include "mono/utils/mono-error-internals.h" +static void +hot_reload_stub_cleanup (MonoComponent *self); + +static void +hot_reload_stub_apply_changes (MonoImage *base_image, gconstpointer dmeta, uint32_t dmeta_len, gconstpointer dil, uint32_t dil_len, MonoError *error); + static MonoComponentHotReload fn_table = { { &hot_reload_stub_cleanup }, &hot_reload_stub_apply_changes, @@ -20,7 +27,7 @@ mono_component_hot_reload_stub_init (void) } void -hot_reload_stub_cleanup (void) +hot_reload_stub_cleanup (MonoComponent *self) { } diff --git a/src/mono/mono/mini/CMakeLists.txt b/src/mono/mono/mini/CMakeLists.txt index 6e5c37ba16b352..a75df7c5b2db0b 100644 --- a/src/mono/mono/mini/CMakeLists.txt +++ b/src/mono/mono/mini/CMakeLists.txt @@ -29,6 +29,7 @@ include(../sgen/CMakeLists.txt) if(INTERNAL_ZLIB) # TODO: hook up HAVE_SYS_ZLIB instead include(../zlib/CMakeLists.txt) endif() +include(../component/CMakeLists.txt) if(ENABLE_PERFTRACING) @@ -404,3 +405,4 @@ if(NOT DISABLE_EXECUTABLES) endif() install(TARGETS mono-sgen RUNTIME) endif() + From 1dc389d0db4f5398558756d4d5b1e7f2eaab5dd0 Mon Sep 17 00:00:00 2001 From: Aleksey Kliger Date: Fri, 19 Mar 2021 11:13:27 -0400 Subject: [PATCH 03/55] actually export the entrypoint from the components --- src/mono/mono/component/CMakeLists.txt | 4 ++++ 1 file changed, 4 insertions(+) diff --git a/src/mono/mono/component/CMakeLists.txt b/src/mono/mono/component/CMakeLists.txt index 9ec869c3734106..6d3be82ba4aed4 100644 --- a/src/mono/mono/component/CMakeLists.txt +++ b/src/mono/mono/component/CMakeLists.txt @@ -13,6 +13,10 @@ addprefix(hot_reload_sources ../component "${hot_reload_sources_base}") add_library(hot_reload-objects OBJECT "${hot_reload_sources}") +if (NOT STATIC_COMPONENTS) + target_compile_definitions (hot_reload-objects PRIVATE -DCOMPILING_COMPONENT_DYNAMIC) +endif() + if(NOT STATIC_COMPONENTS) add_library(mono-component-hot_reload SHARED $) target_link_libraries(mono-component-hot_reload monosgen-shared) From 5a9069f35eeb12e95b6696890fdda7b89f0889bb Mon Sep 17 00:00:00 2001 From: Aleksey Kliger Date: Fri, 19 Mar 2021 14:13:18 -0400 Subject: [PATCH 04/55] wip - make mono/component cmake more uniform --- src/mono/mono/component/CMakeLists.txt | 34 ++++++++++++++++++-------- 1 file changed, 24 insertions(+), 10 deletions(-) diff --git a/src/mono/mono/component/CMakeLists.txt b/src/mono/mono/component/CMakeLists.txt index 6d3be82ba4aed4..b85a5b49178959 100644 --- a/src/mono/mono/component/CMakeLists.txt +++ b/src/mono/mono/component/CMakeLists.txt @@ -1,24 +1,38 @@ + +# a list of every component, add a new component here +set(components + hot_reload + #component_two, etc... + ) + +# the generic components source files set(component_sources_base component.h ) -set(hot_reload_sources_base +# the sources for each individiable component +# define a new component_name-sources_base list for each component + +set(hot_reload-sources_base ${component_source_base} hot_reload.c hot_reload.h ) -addprefix(hot_reload_sources ../component "${hot_reload_sources_base}") +# from here down, all the components are treated in the same way -add_library(hot_reload-objects OBJECT "${hot_reload_sources}") +# define a component_name-objects oject target with the relative source file names +foreach (component IN LISTS components) + addprefix("${component}-sources" ../component "${${component}-sources_base}") + add_library("${component}-objects" OBJECT "${${component}-sources}") +endforeach() if (NOT STATIC_COMPONENTS) - target_compile_definitions (hot_reload-objects PRIVATE -DCOMPILING_COMPONENT_DYNAMIC) -endif() - -if(NOT STATIC_COMPONENTS) - add_library(mono-component-hot_reload SHARED $) - target_link_libraries(mono-component-hot_reload monosgen-shared) - install(TARGETS mono-component-hot_reload LIBRARY) + foreach (component IN LISTS components) + target_compile_definitions ("${component}-objects" PRIVATE -DCOMPILING_COMPONENT_DYNAMIC) + add_library("mono-component-${component}" SHARED $) + target_link_libraries("mono-component-${component}" monosgen-shared) + install(TARGETS "mono-component-${component}" LIBRARY) + endforeach() endif() From e9b865bd42879e75076cabc244b9a1faf92f2b7f Mon Sep 17 00:00:00 2001 From: Aleksey Kliger Date: Fri, 19 Mar 2021 14:13:44 -0400 Subject: [PATCH 05/55] wip - mono.proj copy (dynamic) components to artifacts/bin --- src/mono/mono.proj | 9 +++++++++ 1 file changed, 9 insertions(+) diff --git a/src/mono/mono.proj b/src/mono/mono.proj index c41d29595c8c62..de3e08ffb5f349 100644 --- a/src/mono/mono.proj +++ b/src/mono/mono.proj @@ -624,12 +624,17 @@ + <_MonoRuntimeComponentsFilePath Include="$([System.IO.Directory]::GetParent($(_MonoRuntimeFilePath)))\libmono-component-*" Condition="Exists($(_MonoRuntimeFilePath))" /> <_MonoRuntimeArtifacts Include="$(_MonoRuntimeFilePath)"> $(RuntimeBinDir)$(MonoFileName) <_MonoRuntimeArtifacts Include="$(_MonoRuntimeStaticFilePath)"> $(RuntimeBinDir)$(MonoStaticFileName) + + <_MonoRuntimeArtifacts Include="@(_MonoRuntimeComponentsFilePath)"> + $(RuntimeBinDir)%(_MonoRuntimeComponentsFilePath.Filename)%(_MonoRuntimeComponentsFilePath.Extension) + <_MonoRuntimeArtifacts Include="$(_MonoAotCrossFilePath)"> $(RuntimeBinDir)cross\$(PackageRID)\mono-aot-cross$(ExeExt) @@ -672,6 +677,10 @@ $(_IcuLibdir)\*.dat" /> + + + + Date: Fri, 19 Mar 2021 16:11:28 -0400 Subject: [PATCH 06/55] wip - mono.proj - fixup component rpaths libmonosgen-2.0.dylib -> libcoreclr.dylib --- src/mono/mono.proj | 3 +++ 1 file changed, 3 insertions(+) diff --git a/src/mono/mono.proj b/src/mono/mono.proj index de3e08ffb5f349..e3bcefaeb2abe7 100644 --- a/src/mono/mono.proj +++ b/src/mono/mono.proj @@ -702,6 +702,9 @@ Condition="'$(MonoGenerateOffsetsOSGroups)' == '' and ('$(TargetsMacCatalyst)' == 'true' or '$(TargetsiOS)' == 'true' or '$(TargetstvOS)' == 'true' or '$(TargetsAndroid)' == 'true' or '$(TargetsBrowser)' == 'true')"/> + + + From dc56cb364c7e5d4490ef965ee7c95d1f934e9a89 Mon Sep 17 00:00:00 2001 From: Aleksey Kliger Date: Fri, 19 Mar 2021 16:12:27 -0400 Subject: [PATCH 07/55] wip - metadata - call mono_components_init from mono_metadata_init --- src/mono/mono/metadata/metadata.c | 23 +++++++++++++++++++++++ 1 file changed, 23 insertions(+) diff --git a/src/mono/mono/metadata/metadata.c b/src/mono/mono/metadata/metadata.c index e18a6f4ec8b8cc..4369c38078afc2 100644 --- a/src/mono/mono/metadata/metadata.c +++ b/src/mono/mono/metadata/metadata.c @@ -30,6 +30,7 @@ #include "debug-helpers.h" #include "abi-details.h" #include "cominterop.h" +#include "components.h" #include #include #include @@ -2029,11 +2030,33 @@ mono_metadata_init (void) for (i = 0; i < NBUILTIN_TYPES (); ++i) g_hash_table_insert (type_cache, (gpointer) &builtin_types [i], (gpointer) &builtin_types [i]); + mono_components_init (); + #ifdef ENABLE_METADATA_UPDATE mono_metadata_update_init (); #endif } +/** + * mono_metadata_cleanup: + * + * Free all resources used by this module. + * This is a Mono runtime internal function. + */ +void +mono_metadata_cleanup (void) +{ +#ifdef ENABLE_METADATA_UPDATE + mono_metadata_update_cleanup (); +#endif + mono_components_cleanup (); + g_hash_table_destroy (type_cache); + type_cache = NULL; + g_ptr_array_free (image_sets, TRUE); + image_sets = NULL; + mono_os_mutex_destroy (&image_sets_mutex); +} + /** * mono_metadata_parse_type: * \param m metadata context From 768da985a8e86fca08995dd7be6ee20c890a9274 Mon Sep 17 00:00:00 2001 From: Aleksey Kliger Date: Fri, 19 Mar 2021 16:13:00 -0400 Subject: [PATCH 08/55] wip - components - big component loading hack - code runs now the component loading hack is to look for the components in the directory of the executable app. This works for self-contained apps, but is wrong when libmonosgen-2.0 is loaded by a host application. We need to somehow find out either from the host or from the system where that library _is_ and to load the components from the same directory --- src/mono/mono/component/hot_reload.c | 5 +- src/mono/mono/metadata/components.c | 85 +++++++++++++++++++++++----- 2 files changed, 74 insertions(+), 16 deletions(-) diff --git a/src/mono/mono/component/hot_reload.c b/src/mono/mono/component/hot_reload.c index eca3e7a6a6eacf..3ef36ccd36a9cb 100644 --- a/src/mono/mono/component/hot_reload.c +++ b/src/mono/mono/component/hot_reload.c @@ -28,6 +28,8 @@ MonoComponentHotReload * mono_component_hot_reload_init (void) { /* TODO: initialize things */ + + fprintf (stderr, "hot reload initialized\n"); return &fn_table; } @@ -40,6 +42,7 @@ hot_reload_cleanup (MonoComponent *self) return; /* TODO: implement me */ + fprintf (stderr, "hot reload cleaned up\n"); cleaned = TRUE; } @@ -47,5 +50,5 @@ hot_reload_cleanup (MonoComponent *self) static void hot_reload_apply_changes (MonoImage *base_image, gconstpointer dmeta, uint32_t dmeta_len, gconstpointer dil, uint32_t dil_len, MonoError *error) { - printf ("it worked!\n"); + fprintf (stderr, "it worked!\n"); } diff --git a/src/mono/mono/metadata/components.c b/src/mono/mono/metadata/components.c index fad54c5ab8b8ac..f11cac32a286e9 100644 --- a/src/mono/mono/metadata/components.c +++ b/src/mono/mono/metadata/components.c @@ -6,9 +6,11 @@ #include #include "mono/component/component.h" #include "mono/component/hot_reload.h" +#include "mono/metadata/class-internals.h" #include "mono/metadata/components.h" #include "mono/utils/mono-dl.h" #include "mono/utils/mono-logger-internals.h" +#include "mono/utils/mono-path.h" typedef MonoComponent * (*MonoComponentInitFn) (void); @@ -18,7 +20,7 @@ static GSList *loaded_components; /* One static per component */ static MonoComponentHotReload *hot_reload; -static MonoComponentInitFn +static MonoComponent* get_component (const char *component_name, MonoDl **component_lib); void @@ -59,9 +61,9 @@ mono_components_cleanup (void) } static char* -component_library_name (const char *component) +component_library_base_name (const char *component) { - return g_strdup_printf ("mono-component-%s%s", component, MONO_SOLIB_EXT); + return g_strdup_printf ("mono-component-%s", component); } static char* @@ -70,23 +72,67 @@ component_init_name (const char *component) return g_strdup_printf ("mono_component_%s_init", component); } -MonoComponentInitFn -get_component (const char *component_name, MonoDl **lib_out) +static char * +components_dir (void) +{ + static char *dir = NULL; + if (!dir) { + /* FIXME: this is right for self-contained apps, but if we're + * started by a host, the components are next to + * libmonosgen-2.0.so, not next to the host app. + */ + char buf[4096]; + if (mono_dl_get_executable_path (buf, sizeof(buf)) != -1) { + char *resolvedname = mono_path_resolve_symlinks (buf); + dir = g_path_get_dirname (resolvedname); + g_free (resolvedname); + } + } + return dir; +} + +static MonoDl* +try_load (const char* dir, const char *component_name, const char* component_base_lib) +{ + MonoDl *lib = NULL; + void *iter = NULL; + char *path = NULL; + while ((path = mono_dl_build_path (dir, component_base_lib, &iter)) && !lib) { + char *error_msg = NULL; + lib = mono_dl_open (path, MONO_DL_EAGER, &error_msg); + if (!lib) { + mono_trace (G_LOG_LEVEL_DEBUG, MONO_TRACE_DLLIMPORT, "Component %s not found: %s", component_name, error_msg); + g_free (error_msg); + continue; + } + } + if (lib) + mono_trace (G_LOG_LEVEL_DEBUG, MONO_TRACE_DLLIMPORT, "Component %s found at %s", component_name, path); + g_free (path); + return lib; +} + +static MonoComponentInitFn +load_component (const char *component_name, MonoDl **lib_out) { - char *component_lib = component_library_name (component_name); - char *error_msg = NULL; + char *component_base_lib = component_library_base_name (component_name); MonoComponentInitFn result = NULL; - MonoDl *lib = mono_dl_open (component_lib, MONO_DL_EAGER, &error_msg); - if (!lib) { - mono_trace (G_LOG_LEVEL_DEBUG, MONO_TRACE_DLLIMPORT, "Component %s not found: %s", component_name, error_msg); - g_free (error_msg); - g_free (component_lib); + + /* FIXME: just copy what mono_profiler_load does, assuming it works */ + + /* FIXME: do I need to provide a path? */ + MonoDl *lib = NULL; + lib = try_load (components_dir (), component_name, component_base_lib); + if (!lib) + lib = try_load (NULL, component_name, component_base_lib); + + g_free (component_base_lib); + if (!lib) goto done; - } char *component_init = component_init_name (component_name); gpointer sym = NULL; - error_msg = mono_dl_symbol (lib, component_init, &sym); + char *error_msg = mono_dl_symbol (lib, component_init, &sym); if (error_msg) { mono_trace (G_LOG_LEVEL_DEBUG, MONO_TRACE_DLLIMPORT, "Component %s library does not have symbol %s: %s", component_name, component_init, error_msg); g_free (error_msg); @@ -94,8 +140,17 @@ get_component (const char *component_name, MonoDl **lib_out) goto done; } - result = sym; + result = (MonoComponentInitFn)sym; *lib_out = lib; done: return result; } + +MonoComponent* +get_component (const char *component_name, MonoDl **lib_out) +{ + MonoComponentInitFn initfn = load_component (component_name, lib_out); + if (!initfn) + return NULL; + return initfn(); +} From 64e6c6efbf95f3e7464e1bf8c1c911fbc0933330 Mon Sep 17 00:00:00 2001 From: Aleksey Kliger Date: Fri, 19 Mar 2021 18:06:55 -0400 Subject: [PATCH 09/55] wip - initial skeleton of component design document --- docs/design/mono/components.md | 1 + 1 file changed, 1 insertion(+) diff --git a/docs/design/mono/components.md b/docs/design/mono/components.md index 2dc982dbeaaf1a..5231d6f1bfa633 100644 --- a/docs/design/mono/components.md +++ b/docs/design/mono/components.md @@ -278,3 +278,4 @@ In each runtime pack we include: - An MSBuild targets file that defines targets to copy a specified set of components to the app publish folder (if components are dynamic); or to link the runtime together with stubs and a set of enabled components (if components are static) ** TODO ** Write this up in more detail + From 0db7d16bc3f07a3918afc776d393d20f7a0b607e Mon Sep 17 00:00:00 2001 From: Aleksey Kliger Date: Mon, 22 Mar 2021 11:03:11 -0400 Subject: [PATCH 10/55] update doc --- docs/design/mono/components.md | 1 - 1 file changed, 1 deletion(-) diff --git a/docs/design/mono/components.md b/docs/design/mono/components.md index 5231d6f1bfa633..2dc982dbeaaf1a 100644 --- a/docs/design/mono/components.md +++ b/docs/design/mono/components.md @@ -278,4 +278,3 @@ In each runtime pack we include: - An MSBuild targets file that defines targets to copy a specified set of components to the app publish folder (if components are dynamic); or to link the runtime together with stubs and a set of enabled components (if components are static) ** TODO ** Write this up in more detail - From a7c8b97d1e3aae3b6890020f3aec0515033f31c6 Mon Sep 17 00:00:00 2001 From: Aleksey Kliger Date: Mon, 22 Mar 2021 17:00:32 -0400 Subject: [PATCH 11/55] wip - add support for STATIC_COMPONENTS - seems to work Right now this doesn't include support for disabling individual components --- src/mono/cmake/config.h.in | 2 + src/mono/cmake/options.cmake | 2 + src/mono/mono.proj | 16 +++++++- src/mono/mono/component/CMakeLists.txt | 10 +++++ src/mono/mono/component/hot_reload.c | 2 + src/mono/mono/component/hot_reload.h | 7 ++++ src/mono/mono/metadata/components.c | 56 +++++++++++++++++++------- src/mono/mono/mini/CMakeLists.txt | 9 ++++- 8 files changed, 87 insertions(+), 17 deletions(-) diff --git a/src/mono/cmake/config.h.in b/src/mono/cmake/config.h.in index 259fff72457acd..28ce48b806531d 100644 --- a/src/mono/cmake/config.h.in +++ b/src/mono/cmake/config.h.in @@ -1058,3 +1058,5 @@ #endif +/* Enable static linking of mono runtime components */ +#cmakedefine STATIC_COMPONENTS diff --git a/src/mono/cmake/options.cmake b/src/mono/cmake/options.cmake index 56da20953393db..b18f3aa4b1aaf4 100644 --- a/src/mono/cmake/options.cmake +++ b/src/mono/cmake/options.cmake @@ -53,6 +53,7 @@ option (ENABLE_CHECKED_BUILD_THREAD "Enable runtime history of per-thread coop s option (ENABLE_CHECKED_BUILD_METADATA "Enable runtime checks of mempool references between metadata images (must set env var MONO_CHECK_MODE=metadata)") option (ENABLE_METADATA_UPDATE "Enable runtime support for metadata updates") option (ENABLE_MSCORDBI "Generate mscordbi to support icordbg interface") +option (STATIC_COMPONENTS "Compile mono runtime components as static (not dynamic) libraries") set (GC_SUSPEND "default" CACHE STRING "GC suspend method (default, preemptive, coop, hybrid)") set (CHECKED_BUILD "" CACHE STRING "Set ENABLE_CHECKED_BUILD_ options at once. Comma-separated list of lowercase ENABLE_CHECKED_BUILD_ options ie. 'gc,threads,private_types' etc.") @@ -60,3 +61,4 @@ set (ENABLE_MINIMAL "" CACHE STRING "Set many DISABLE_ options at once. Comma-se set (AOT_TARGET_TRIPLE "" CACHE STRING "Target triple for AOT cross compiler") set (AOT_OFFSETS_FILE "" CACHE STRING "Offsets file for AOT cross compiler") set (LLVM_PREFIX "" CACHE STRING "Enable LLVM support with LLVM installed at .") + diff --git a/src/mono/mono.proj b/src/mono/mono.proj index e3bcefaeb2abe7..1cc1df277f19cd 100644 --- a/src/mono/mono.proj +++ b/src/mono/mono.proj @@ -37,6 +37,9 @@ libmonosgen-2.0.a $(CoreClrFileName) libmonosgen-2.0.a + .dylib + .dll + .so $(Configuration) $(Configuration) $([MSBuild]::NormalizeDirectory('$(ArtifactsDir)', 'tests', 'coreclr', '$(TargetOS).$(Platform).$(CoreClrTestConfig)', 'Tests', 'Core_Root')) @@ -74,6 +77,12 @@ hybrid + + + + false + + @@ -396,6 +405,11 @@ <_MonoCMakeArgs Include="-DENABLE_MSCORDBI=1" /> + + + <_MonoCMakeArgs Include="-DSTATIC_COMPONENTS=1" /> + + <_MonoCFLAGSOption>-DCMAKE_C_FLAGS="@(_MonoCPPFLAGS, ' ') @(_MonoCFLAGS, ' ')" <_MonoCXXFLAGSOption>-DCMAKE_CXX_FLAGS="@(_MonoCPPFLAGS, ' ') @(_MonoCXXFLAGS, ' ')" @@ -704,7 +718,7 @@ - + diff --git a/src/mono/mono/component/CMakeLists.txt b/src/mono/mono/component/CMakeLists.txt index b85a5b49178959..40492a56d4b471 100644 --- a/src/mono/mono/component/CMakeLists.txt +++ b/src/mono/mono/component/CMakeLists.txt @@ -35,4 +35,14 @@ if (NOT STATIC_COMPONENTS) target_link_libraries("mono-component-${component}" monosgen-shared) install(TARGETS "mono-component-${component}" LIBRARY) endforeach() +else() + foreach (component IN LISTS components) + add_library("mono-component-${component}-static" STATIC $) + install(TARGETS "mono-component-${component}-static" LIBRARY) + endforeach() + # define a singlee components_static_objects target for mini if building a shared libmono with static-linked components + add_library (components_static_objects OBJECT) + foreach (component IN LISTS components) + target_sources (components_static_objects PRIVATE ${${component}-sources}) + endforeach() endif() diff --git a/src/mono/mono/component/hot_reload.c b/src/mono/mono/component/hot_reload.c index 3ef36ccd36a9cb..8a70eb62ba68f9 100644 --- a/src/mono/mono/component/hot_reload.c +++ b/src/mono/mono/component/hot_reload.c @@ -9,9 +9,11 @@ #include +#ifndef STATIC_COMPONENTS MONO_COMPONENT_EXPORT_ENTRYPOINT MonoComponentHotReload * mono_component_hot_reload_init (void); +#endif static void hot_reload_cleanup (MonoComponent *self); diff --git a/src/mono/mono/component/hot_reload.h b/src/mono/mono/component/hot_reload.h index 97f56b6b05cd99..eb56b51006d12a 100644 --- a/src/mono/mono/component/hot_reload.h +++ b/src/mono/mono/component/hot_reload.h @@ -8,6 +8,7 @@ #include #include "mono/metadata/object-forward.h" #include "mono/utils/mono-error.h" +#include "mono/utils/mono-compiler.h" #include "mono/component/component.h" typedef struct _MonoComponentHotReload { @@ -15,4 +16,10 @@ typedef struct _MonoComponentHotReload { void (*apply_changes) (MonoImage *base_image, gconstpointer dmeta, uint32_t dmeta_len, gconstpointer dil, uint32_t dil_len, MonoError *error); } MonoComponentHotReload; +#ifdef STATIC_COMPONENTS +MONO_COMPONENT_EXPORT_ENTRYPOINT +MonoComponentHotReload * +mono_component_hot_reload_init (void); +#endif + #endif/*_MONO_COMPONENT_HOT_RELOAD_H*/ diff --git a/src/mono/mono/metadata/components.c b/src/mono/mono/metadata/components.c index f11cac32a286e9..3aae8f67d4ee28 100644 --- a/src/mono/mono/metadata/components.c +++ b/src/mono/mono/metadata/components.c @@ -14,20 +14,36 @@ typedef MonoComponent * (*MonoComponentInitFn) (void); +#ifndef STATIC_COMPONENTS /* List of MonoDl* for each loaded component */ static GSList *loaded_components; +#endif /* One static per component */ static MonoComponentHotReload *hot_reload; +#ifndef STATIC_COMPONENTS static MonoComponent* get_component (const char *component_name, MonoDl **component_lib); +#endif void mono_components_init (void) { -#ifdef STATIC_LINK_COMPONENTS +#ifdef STATIC_COMPONENTS /* directly call each components init function */ + /* TODO: support disabled components. + * + * The issue here is that we need to do static linking, so if we don't + * directly reference mono_component__init anywhere (ie + * if we dlsym from RTLD_DEFAULT) the static linking of the final + * binary won't actually include that symbol (unless we play + * platform-specific linker tricks). + * + * So maybe we will need some API hook so that embedders need to call + * to pass us the address of each component that isn't disabled. + * + */ hot_reload = mono_component_hot_reload_init (); #else /* call get_component for each component and init it or its stubs and add it to loaded_components */ @@ -53,7 +69,7 @@ mono_components_cleanup (void) hot_reload->component.cleanup (&hot_reload->component); hot_reload = NULL; } -#ifndef STATIC_LINK_COMPONENTS +#ifndef STATIC_COMPONENTS for (GSList *p = loaded_components; p != NULL; p = p->next) { mono_dl_close ((MonoDl*)p->data); } @@ -61,15 +77,32 @@ mono_components_cleanup (void) } static char* -component_library_base_name (const char *component) +component_init_name (const char *component) { - return g_strdup_printf ("mono-component-%s", component); + return g_strdup_printf ("mono_component_%s_init", component); +} + +static gpointer +load_component_entrypoint (MonoDl *lib, const char *component_name) +{ + char *component_init = component_init_name (component_name); + gpointer sym = NULL; + char *error_msg = mono_dl_symbol (lib, component_init, &sym); + if (error_msg) { + mono_trace (G_LOG_LEVEL_DEBUG, MONO_TRACE_DLLIMPORT, "Component %s library does not have symbol %s: %s", component_name, component_init, error_msg); + g_free (error_msg); + g_free (component_init); + return NULL; + } + g_free (component_init); + return sym; } +#ifndef STATIC_COMPONENTS static char* -component_init_name (const char *component) +component_library_base_name (const char *component) { - return g_strdup_printf ("mono_component_%s_init", component); + return g_strdup_printf ("mono-component-%s", component); } static char * @@ -130,15 +163,7 @@ load_component (const char *component_name, MonoDl **lib_out) if (!lib) goto done; - char *component_init = component_init_name (component_name); - gpointer sym = NULL; - char *error_msg = mono_dl_symbol (lib, component_init, &sym); - if (error_msg) { - mono_trace (G_LOG_LEVEL_DEBUG, MONO_TRACE_DLLIMPORT, "Component %s library does not have symbol %s: %s", component_name, component_init, error_msg); - g_free (error_msg); - g_free (component_init); - goto done; - } + gpointer sym = load_component_entrypoint (lib, component_name); result = (MonoComponentInitFn)sym; *lib_out = lib; @@ -154,3 +179,4 @@ get_component (const char *component_name, MonoDl **lib_out) return NULL; return initfn(); } +#endif diff --git a/src/mono/mono/mini/CMakeLists.txt b/src/mono/mono/mini/CMakeLists.txt index a75df7c5b2db0b..9ddf90ba07dfc6 100644 --- a/src/mono/mono/mini/CMakeLists.txt +++ b/src/mono/mono/mini/CMakeLists.txt @@ -324,7 +324,6 @@ set(OS_LIBS bcrypt.lib Mswsock.lib ws2_32.lib psapi.lib version.lib advapi32.lib set(mini_sources "${mini_sources};${PROJECT_BINARY_DIR}/../../NativeVersion.rc") # this is generated by GenerateMonoVersionFile in mono.proj endif() - add_library(monosgen-objects OBJECT "${eglib_sources};${metadata_sources};${utils_sources};${sgen_sources};${icu_shim_sources};${eventpipe_sources};${mini_sources};${zlib_sources}") add_library(monosgen-static STATIC $) set_target_properties(monosgen-static PROPERTIES OUTPUT_NAME monosgen-2.0) @@ -355,6 +354,11 @@ if(NOT DISABLE_SHARED_LIBS) if(TARGET_DARWIN) set_property(TARGET monosgen-shared APPEND_STRING PROPERTY LINK_FLAGS " -Wl,-compatibility_version -Wl,2.0 -Wl,-current_version -Wl,2.0") endif() + if (STATIC_COMPONENTS) + # if components are built statically, but we're building a shared lib mono, + # link them into the library + target_link_libraries (monosgen-shared components_static_objects) + endif() install(TARGETS monosgen-shared LIBRARY) endif() @@ -400,6 +404,9 @@ if(NOT DISABLE_EXECUTABLES) endif() add_executable(mono-sgen "${sgen_sources}") target_link_libraries(mono-sgen monosgen-static ${OS_LIBS} ${ICONV_LIB} ${LLVM_LIBS} ${ICU_LIBS}) + if (STATIC_COMPONENTS) + target_link_libraries(mono-sgen components_static_objects) + endif() if(ICU_LDFLAGS) set_property(TARGET mono-sgen APPEND_STRING PROPERTY LINK_FLAGS " ${ICU_LDFLAGS}") endif() From 4d4289b816ce12ea5f0b131d2797e4cc1497a50e Mon Sep 17 00:00:00 2001 From: Aleksey Kliger Date: Tue, 23 Mar 2021 10:23:31 -0400 Subject: [PATCH 12/55] wip - fix dynamic components install_name_tool stuff --- src/mono/mono.proj | 18 ++++++++++-------- 1 file changed, 10 insertions(+), 8 deletions(-) diff --git a/src/mono/mono.proj b/src/mono/mono.proj index 1cc1df277f19cd..c252e200075440 100644 --- a/src/mono/mono.proj +++ b/src/mono/mono.proj @@ -40,6 +40,8 @@ .dylib .dll .so + .lib + .a $(Configuration) $(Configuration) $([MSBuild]::NormalizeDirectory('$(ArtifactsDir)', 'tests', 'coreclr', '$(TargetOS).$(Platform).$(CoreClrTestConfig)', 'Tests', 'Core_Root')) @@ -638,7 +640,8 @@ - <_MonoRuntimeComponentsFilePath Include="$([System.IO.Directory]::GetParent($(_MonoRuntimeFilePath)))\libmono-component-*" Condition="Exists($(_MonoRuntimeFilePath))" /> + <_MonoRuntimeComponentsStaticFilePath Include="$([System.IO.Directory]::GetParent($(_MonoRuntimeFilePath)))\libmono-component-*$(StaticNativeLibrarySuffix)" Condition="Exists($(_MonoRuntimeFilePath))" /> + <_MonoRuntimeComponentsSharedFilePath Include="$([System.IO.Directory]::GetParent($(_MonoRuntimeFilePath)))\libmono-component-*$(SharedNativeLibrarySuffix)" Condition="Exists($(_MonoRuntimeFilePath))" /> <_MonoRuntimeArtifacts Include="$(_MonoRuntimeFilePath)"> $(RuntimeBinDir)$(MonoFileName) @@ -646,8 +649,11 @@ $(RuntimeBinDir)$(MonoStaticFileName) - <_MonoRuntimeArtifacts Include="@(_MonoRuntimeComponentsFilePath)"> - $(RuntimeBinDir)%(_MonoRuntimeComponentsFilePath.Filename)%(_MonoRuntimeComponentsFilePath.Extension) + <_MonoRuntimeArtifacts Include="@(_MonoRuntimeComponentsStaticFilePath)"> + $(RuntimeBinDir)%(_MonoRuntimeComponentsStaticFilePath.Filename)%(_MonoRuntimeComponentsStaticFilePath.Extension) + + <_MonoRuntimeArtifacts Include="@(_MonoRuntimeComponentsSharedFilePath)"> + $(RuntimeBinDir)%(_MonoRuntimeComponentsSharedFilePath.Filename)%(_MonoRuntimeComponentsSharedFilePath.Extension) <_MonoRuntimeArtifacts Include="$(_MonoAotCrossFilePath)"> $(RuntimeBinDir)cross\$(PackageRID)\mono-aot-cross$(ExeExt) @@ -691,10 +697,6 @@ $(_IcuLibdir)\*.dat" /> - - - - - + From c3eaebcac9f8d8285be0015813be2f8fd6f2456f Mon Sep 17 00:00:00 2001 From: Aleksey Kliger Date: Tue, 23 Mar 2021 16:15:50 -0400 Subject: [PATCH 13/55] wip - put stubs in the component directory For the static components scenario, build .a files for components and component stubs and leave it to the final link step to pick what to link. Also in the static components scenario, the stub implements a normal (ie mono_component__init) entrypoint. The advantage is that the embedder/workload doesn't need to write any code (just pick libraries to link) and the runtime can do direct calls to the component init functions avoiding having to use linker flags to ensure that component entrypoints are in the final linked artifact. --- src/mono/mono/component/CMakeLists.txt | 51 +++++++++++++++---- .../{metadata => component}/hot_reload-stub.c | 11 ++++ src/mono/mono/metadata/CMakeLists.txt | 6 +-- src/mono/mono/mini/CMakeLists.txt | 5 ++ 4 files changed, 57 insertions(+), 16 deletions(-) rename src/mono/mono/{metadata => component}/hot_reload-stub.c (82%) diff --git a/src/mono/mono/component/CMakeLists.txt b/src/mono/mono/component/CMakeLists.txt index 40492a56d4b471..4bfe9f8df49358 100644 --- a/src/mono/mono/component/CMakeLists.txt +++ b/src/mono/mono/component/CMakeLists.txt @@ -6,43 +6,72 @@ set(components #component_two, etc... ) -# the generic components source files -set(component_sources_base - component.h - ) - -# the sources for each individiable component -# define a new component_name-sources_base list for each component - +# the sources for each individiable component define a new +# component_name-sources_base list for each component, and a +# component_name-stub-sources_base list for the component stub. set(hot_reload-sources_base - ${component_source_base} hot_reload.c hot_reload.h ) +set(hot_reload-stub-sources_base + hot_reload-stub.c + ) # from here down, all the components are treated in the same way -# define a component_name-objects oject target with the relative source file names +# a generic component interface that all components implement +add_library(component_base INTERFACE) +target_sources(component_base INTERFACE + ../component/component.h + ) + + +# define a component_name-objects and component_name-stub-objects object +# targets with the relative source file names foreach (component IN LISTS components) addprefix("${component}-sources" ../component "${${component}-sources_base}") add_library("${component}-objects" OBJECT "${${component}-sources}") + target_link_libraries("${component}-objects" component_base) + addprefix("${component}-stub-sources" ../component "${${component}-stub-sources_base}") + add_library("${component}-stub-objects" OBJECT "${${component}-stub-sources}") + target_link_libraries("${component}-stub-objects" component_base) endforeach() if (NOT STATIC_COMPONENTS) + # define a shared library for each component foreach (component IN LISTS components) target_compile_definitions ("${component}-objects" PRIVATE -DCOMPILING_COMPONENT_DYNAMIC) add_library("mono-component-${component}" SHARED $) target_link_libraries("mono-component-${component}" monosgen-shared) install(TARGETS "mono-component-${component}" LIBRARY) endforeach() + + # define a single components_stubs_objects target that will be linked into + # the runtime to be used as fallbacks if the dynamic components are not + # available + add_library (components_stubs_objects OBJECT) + foreach (component IN LISTS components) + target_sources (components_stubs_objects PRIVATE ${${component}-stub-sources}) + endforeach() + target_link_libraries(components_stubs_objects component_base) + else() + + #define a static library for each component and component stub foreach (component IN LISTS components) add_library("mono-component-${component}-static" STATIC $) install(TARGETS "mono-component-${component}-static" LIBRARY) endforeach() - # define a singlee components_static_objects target for mini if building a shared libmono with static-linked components + foreach (component IN LISTS components) + add_library("mono-component-${component}-stub-static" STATIC $) + install(TARGETS "mono-component-${component}-stub-static" LIBRARY) + endforeach() + + # define a single components_static_objects target for mini if building a shared libmono with static-linked components add_library (components_static_objects OBJECT) foreach (component IN LISTS components) target_sources (components_static_objects PRIVATE ${${component}-sources}) endforeach() + target_link_libraries(components_static_objects component_base) + endif() diff --git a/src/mono/mono/metadata/hot_reload-stub.c b/src/mono/mono/component/hot_reload-stub.c similarity index 82% rename from src/mono/mono/metadata/hot_reload-stub.c rename to src/mono/mono/component/hot_reload-stub.c index c1bdc871309937..35c066f3394533 100644 --- a/src/mono/mono/metadata/hot_reload-stub.c +++ b/src/mono/mono/component/hot_reload-stub.c @@ -7,6 +7,7 @@ #include "mono/component/component.h" #include "mono/component/hot_reload.h" #include "mono/metadata/components.h" +#include "mono/utils/mono-compiler.h" #include "mono/utils/mono-error-internals.h" static void @@ -20,6 +21,15 @@ static MonoComponentHotReload fn_table = { &hot_reload_stub_apply_changes, }; +#ifdef STATIC_COMPONENTS +MONO_COMPONENT_EXPORT_ENTRYPOINT +MonoComponentHotReload * +mono_component_hot_reload_init (void) +{ + return mono_component_hot_reload_stub_init (); +} +#endif + MonoComponentHotReload * mono_component_hot_reload_stub_init (void) { @@ -36,3 +46,4 @@ hot_reload_stub_apply_changes (MonoImage *base_image, gconstpointer dmeta, uint3 { mono_error_set_not_supported (error, "Hot reload not supported in this runtime."); } + diff --git a/src/mono/mono/metadata/CMakeLists.txt b/src/mono/mono/metadata/CMakeLists.txt index 4890c7c46b7843..1b7ba75f6b0e44 100644 --- a/src/mono/mono/metadata/CMakeLists.txt +++ b/src/mono/mono/metadata/CMakeLists.txt @@ -52,10 +52,6 @@ else() set(metadata_platform_sources ${metadata_unix_sources}) endif() -set(component_stub_sources - hot_reload-stub.c -) - set(metadata_common_sources appdomain.c domain.c @@ -240,7 +236,7 @@ set(reloc_libdir "${CMAKE_INSTALL_LIBDIR}") set_source_files_properties(../metadata/mono-config-dirs.c PROPERTIES COMPILE_DEFINITIONS "MONO_BINDIR=\"${bindir}\";MONO_ASSEMBLIES=\"${assembliesdir}\";MONO_CFG_DIR=\"${confdir}\";MONO_RELOC_LIBDIR=\"../${reloc_libdir}\"") -addprefix(metadata_sources ../metadata/ "${metadata_platform_sources};${metadata_common_sources};${metadata_gc_dependent_sources};${metadata_sgen_sources};${ilgen_sources};${component_stub_sources}") +addprefix(metadata_sources ../metadata/ "${metadata_platform_sources};${metadata_common_sources};${metadata_gc_dependent_sources};${metadata_sgen_sources};${ilgen_sources}") set(metadata_public_headers_base appdomain.h diff --git a/src/mono/mono/mini/CMakeLists.txt b/src/mono/mono/mini/CMakeLists.txt index 9ddf90ba07dfc6..77fd31293170a8 100644 --- a/src/mono/mono/mini/CMakeLists.txt +++ b/src/mono/mono/mini/CMakeLists.txt @@ -358,6 +358,9 @@ if(NOT DISABLE_SHARED_LIBS) # if components are built statically, but we're building a shared lib mono, # link them into the library target_link_libraries (monosgen-shared components_static_objects) + else() + # if components are built dynamically, link the fallback stubs into the runtime + target_link_libraries (monosgen-shared components_stubs_objects) endif() install(TARGETS monosgen-shared LIBRARY) endif() @@ -406,6 +409,8 @@ if(NOT DISABLE_EXECUTABLES) target_link_libraries(mono-sgen monosgen-static ${OS_LIBS} ${ICONV_LIB} ${LLVM_LIBS} ${ICU_LIBS}) if (STATIC_COMPONENTS) target_link_libraries(mono-sgen components_static_objects) + else() + target_link_libraries(mono-sgen components_stubs_objects) endif() if(ICU_LDFLAGS) set_property(TARGET mono-sgen APPEND_STRING PROPERTY LINK_FLAGS " ${ICU_LDFLAGS}") From 109b339fe691acd46da0fff6e17e895f118308f2 Mon Sep 17 00:00:00 2001 From: Aleksey Kliger Date: Wed, 24 Mar 2021 11:58:19 -0400 Subject: [PATCH 14/55] wip - default to static components on ios/tvos device and on wasm --- src/mono/mono.proj | 3 +++ src/mono/mono/component/CMakeLists.txt | 8 +++++++- 2 files changed, 10 insertions(+), 1 deletion(-) diff --git a/src/mono/mono.proj b/src/mono/mono.proj index c252e200075440..e49863e0b96cb4 100644 --- a/src/mono/mono.proj +++ b/src/mono/mono.proj @@ -81,6 +81,9 @@ + true + true + true false diff --git a/src/mono/mono/component/CMakeLists.txt b/src/mono/mono/component/CMakeLists.txt index 4bfe9f8df49358..2d7af6a7ed4ff0 100644 --- a/src/mono/mono/component/CMakeLists.txt +++ b/src/mono/mono/component/CMakeLists.txt @@ -42,7 +42,13 @@ if (NOT STATIC_COMPONENTS) foreach (component IN LISTS components) target_compile_definitions ("${component}-objects" PRIVATE -DCOMPILING_COMPONENT_DYNAMIC) add_library("mono-component-${component}" SHARED $) - target_link_libraries("mono-component-${component}" monosgen-shared) + if (NOT DISABLE_SHARED_LIBS) + target_link_libraries("mono-component-${component}" monosgen-shared) + # If we disable shared libs, but build dynamic components we would need + # to enable allowing undefined symbols here (presumably to be resolved + # from the mono-sgen executable. But that's not a configuration we + # should need in dotnet/runtime. + endif() install(TARGETS "mono-component-${component}" LIBRARY) endforeach() From d26ed44b03b9a125652d86d3e4523eca4f6ae90d Mon Sep 17 00:00:00 2001 From: Aleksey Kliger Date: Wed, 24 Mar 2021 13:09:18 -0400 Subject: [PATCH 15/55] Add eglib_objects cmake object target for eglib Link it into monosgen-shard and monosgen-static. This is needed by the "mono components" prototype https://github.com/dotnet/runtime/pull/49913 so that each dynamic component could statically link its own version of eglib operations (and we will do followup work to move the ones that use global state, like the logging operations, to be in one place only) --- src/mono/mono/eglib/CMakeLists.txt | 2 ++ src/mono/mono/mini/CMakeLists.txt | 4 +++- 2 files changed, 5 insertions(+), 1 deletion(-) diff --git a/src/mono/mono/eglib/CMakeLists.txt b/src/mono/mono/eglib/CMakeLists.txt index 520359c38e1ea8..d8b7d01a1e4bf7 100644 --- a/src/mono/mono/eglib/CMakeLists.txt +++ b/src/mono/mono/eglib/CMakeLists.txt @@ -45,3 +45,5 @@ set(eglib_common_sources unicode-data.h) addprefix(eglib_sources ../eglib/ "${eglib_platform_sources};${eglib_common_sources}") + +add_library(eglib_objects OBJECT "${eglib_sources}") diff --git a/src/mono/mono/mini/CMakeLists.txt b/src/mono/mono/mini/CMakeLists.txt index 77fd31293170a8..6fc8b4b1e769d8 100644 --- a/src/mono/mono/mini/CMakeLists.txt +++ b/src/mono/mono/mini/CMakeLists.txt @@ -324,9 +324,10 @@ set(OS_LIBS bcrypt.lib Mswsock.lib ws2_32.lib psapi.lib version.lib advapi32.lib set(mini_sources "${mini_sources};${PROJECT_BINARY_DIR}/../../NativeVersion.rc") # this is generated by GenerateMonoVersionFile in mono.proj endif() -add_library(monosgen-objects OBJECT "${eglib_sources};${metadata_sources};${utils_sources};${sgen_sources};${icu_shim_sources};${eventpipe_sources};${mini_sources};${zlib_sources}") +add_library(monosgen-objects OBJECT "${metadata_sources};${utils_sources};${sgen_sources};${icu_shim_sources};${eventpipe_sources};${mini_sources};${zlib_sources}") add_library(monosgen-static STATIC $) set_target_properties(monosgen-static PROPERTIES OUTPUT_NAME monosgen-2.0) +target_link_libraries(monosgen-static eglib_objects) if(NOT DISABLE_LIBS) install(TARGETS monosgen-static LIBRARY) install(FILES ${metadata_public_headers} @@ -338,6 +339,7 @@ if(NOT DISABLE_LIBS) endif() if(NOT DISABLE_SHARED_LIBS) add_library(monosgen-shared SHARED $ ) + target_link_libraries(monosgen-shared eglib_objects) set_target_properties(monosgen-shared PROPERTIES OUTPUT_NAME monosgen-2.0) if(TARGET_WIN32) # on Windows the import library for the shared monosgen-2.0 library will have the same name as the static library (monosgen-2.0.lib), From b1414bbbead16b756211ce14dfdceef5c0e857b7 Mon Sep 17 00:00:00 2001 From: Aleksey Kliger Date: Wed, 24 Mar 2021 21:24:18 -0400 Subject: [PATCH 16/55] wip - static link eglib_objects into dynamic components --- src/mono/mono/component/CMakeLists.txt | 6 ++++++ 1 file changed, 6 insertions(+) diff --git a/src/mono/mono/component/CMakeLists.txt b/src/mono/mono/component/CMakeLists.txt index 2d7af6a7ed4ff0..1f1fb6bca54b29 100644 --- a/src/mono/mono/component/CMakeLists.txt +++ b/src/mono/mono/component/CMakeLists.txt @@ -43,6 +43,12 @@ if (NOT STATIC_COMPONENTS) target_compile_definitions ("${component}-objects" PRIVATE -DCOMPILING_COMPONENT_DYNAMIC) add_library("mono-component-${component}" SHARED $) if (NOT DISABLE_SHARED_LIBS) + # each shared library component gets its own copy for eglib + # + # FIXME: this is bad for things like the g_log_set_default_handler/g_logv + # which use global state - we should move those functions into + # monosgen-shared and get them via dynamic linking. + target_link_libraries("mono-component-${component}" eglib_objects) target_link_libraries("mono-component-${component}" monosgen-shared) # If we disable shared libs, but build dynamic components we would need # to enable allowing undefined symbols here (presumably to be resolved From 812067b5c016d072b58e0b6de4d8f54ef5fa060c Mon Sep 17 00:00:00 2001 From: lateralusX Date: Thu, 25 Mar 2021 12:22:03 +0100 Subject: [PATCH 17/55] Convert EventPipe/DiagnosticsServer into components. --- src/mono/mono/component/CMakeLists.txt | 41 ++++++++- .../mono/component/diagnostics_server-stub.c | 69 ++++++++++++++ src/mono/mono/component/diagnostics_server.c | 38 ++++++++ src/mono/mono/component/diagnostics_server.h | 24 +++++ src/mono/mono/component/event_pipe-stub.c | 92 +++++++++++++++++++ src/mono/mono/component/event_pipe.c | 37 ++++++++ src/mono/mono/component/event_pipe.h | 23 +++++ src/mono/mono/metadata/appdomain.c | 9 +- src/mono/mono/metadata/components.c | 64 ++++++++----- src/mono/mono/metadata/components.h | 31 ++++++- src/mono/mono/mini/CMakeLists.txt | 17 +--- src/mono/mono/mini/mini-runtime.c | 16 ++-- 12 files changed, 400 insertions(+), 61 deletions(-) create mode 100644 src/mono/mono/component/diagnostics_server-stub.c create mode 100644 src/mono/mono/component/diagnostics_server.c create mode 100644 src/mono/mono/component/diagnostics_server.h create mode 100644 src/mono/mono/component/event_pipe-stub.c create mode 100644 src/mono/mono/component/event_pipe.c create mode 100644 src/mono/mono/component/event_pipe.h diff --git a/src/mono/mono/component/CMakeLists.txt b/src/mono/mono/component/CMakeLists.txt index 1f1fb6bca54b29..51935f62140023 100644 --- a/src/mono/mono/component/CMakeLists.txt +++ b/src/mono/mono/component/CMakeLists.txt @@ -1,14 +1,14 @@ -# a list of every component, add a new component here -set(components - hot_reload - #component_two, etc... - ) +# a list of every component. +set(components "") # the sources for each individiable component define a new # component_name-sources_base list for each component, and a # component_name-stub-sources_base list for the component stub. +list(APPEND components + hot_reload +) set(hot_reload-sources_base hot_reload.c hot_reload.h @@ -17,6 +17,37 @@ set(hot_reload-stub-sources_base hot_reload-stub.c ) +if(ENABLE_PERFTRACING) + + list(APPEND components + event_pipe + ) + + set (SHARED_EVENTPIPE_INCLUDE_PATH "../../../native/") + set (SHARED_EVENTPIPE_SOURCE_PATH "../../../native/eventpipe/") + set (MONO_EVENTPIPE_SHIM_SOURCE_PATH "../eventpipe/") + + include(${MONO_EVENTPIPE_SHIM_SOURCE_PATH}/CMakeLists.txt) + + include_directories( + ${SHARED_EVENTPIPE_INCLUDE_PATH} + ${MONO_EVENTPIPE_SHIM_SOURCE_PATH} + ) + + set(event_pipe-sources_base + ${eventpipe_sources} + event_pipe.c + event_pipe.h + diagnostics_server.c + diagnostics_server.h + ) + set(event_pipe-stub-sources_base + event_pipe-stub.c + diagnostics_server-stub.c + ) + +endif(ENABLE_PERFTRACING) + # from here down, all the components are treated in the same way # a generic component interface that all components implement diff --git a/src/mono/mono/component/diagnostics_server-stub.c b/src/mono/mono/component/diagnostics_server-stub.c new file mode 100644 index 00000000000000..842a68cd5fe3a3 --- /dev/null +++ b/src/mono/mono/component/diagnostics_server-stub.c @@ -0,0 +1,69 @@ +// Licensed to the .NET Foundation under one or more agreements. +// The .NET Foundation licenses this file to you under the MIT license. +// + +#include +#include "mono/component/diagnostics_server.h" + +static void +diagnostics_server_stub_cleanup (MonoComponent *self); + +static void +diagnostics_server_stub_ds_server_init (void); + +static void +diagnostics_server_stub_ds_server_shutdown (void); + +static void +diagnostics_server_stub_ds_server_pause_for_diagnostics_monitor (void); + +static void +diagnostics_server_stub_ds_server_disable (void); + +static MonoComponentDiagnosticsServer fn_table = { + { &diagnostics_server_stub_cleanup }, + &diagnostics_server_stub_ds_server_init, + &diagnostics_server_stub_ds_server_shutdown, + &diagnostics_server_stub_ds_server_pause_for_diagnostics_monitor, + &diagnostics_server_stub_ds_server_disable +}; + +#ifdef STATIC_COMPONENTS +MONO_COMPONENT_EXPORT_ENTRYPOINT +MonoComponentDiagnosticsServer * +mono_component_diagnostics_server_init (void) +{ + return mono_component_diagnostics_server_stub_init (); +} +#endif + +MonoComponentDiagnosticsServer * +mono_component_diagnostics_server_stub_init (void) +{ + return &fn_table; +} + +static void +diagnostics_server_stub_cleanup (MonoComponent *self) +{ +} + +static void +diagnostics_server_stub_ds_server_init (void) +{ +} + +static void +diagnostics_server_stub_ds_server_shutdown (void) +{ +} + +static void +diagnostics_server_stub_ds_server_pause_for_diagnostics_monitor (void) +{ +} + +static void +diagnostics_server_stub_ds_server_disable (void) +{ +} diff --git a/src/mono/mono/component/diagnostics_server.c b/src/mono/mono/component/diagnostics_server.c new file mode 100644 index 00000000000000..239576b4667bd0 --- /dev/null +++ b/src/mono/mono/component/diagnostics_server.c @@ -0,0 +1,38 @@ +// Licensed to the .NET Foundation under one or more agreements. +// The .NET Foundation licenses this file to you under the MIT license. +// + +#include +#include +#include +#include +#include + +#ifndef STATIC_COMPONENTS +MONO_COMPONENT_EXPORT_ENTRYPOINT +MonoComponentDiagnosticsServer * +mono_component_diagnostics_server_init (void); +#endif + +static void +diagnostics_server_cleanup (MonoComponent *self); + +static MonoComponentDiagnosticsServer fn_table = { + { &diagnostics_server_cleanup }, + &ds_server_init, + &ds_server_shutdown, + &ds_server_pause_for_diagnostics_monitor, + &ds_server_disable +}; + +static void +diagnostics_server_cleanup (MonoComponent *self) +{ + return; +} + +MonoComponentDiagnosticsServer * +mono_component_diagnostics_server_init (void) +{ + return &fn_table; +} diff --git a/src/mono/mono/component/diagnostics_server.h b/src/mono/mono/component/diagnostics_server.h new file mode 100644 index 00000000000000..40edf4e4279bf0 --- /dev/null +++ b/src/mono/mono/component/diagnostics_server.h @@ -0,0 +1,24 @@ +// Licensed to the .NET Foundation under one or more agreements. +// The .NET Foundation licenses this file to you under the MIT license. +// + +#ifndef _MONO_COMPONENT_DIAGNOSTICS_SERVER_H +#define _MONO_COMPONENT_DIAGNOSTICS_SERVER_H + +#include "mono/component/component.h" + +typedef struct _MonoComponentDiagnosticsServer { + MonoComponent component; + void (*ds_server_init) (void); + void (*ds_server_shutdown) (void); + void (*ds_server_pause_for_diagnostics_monitor) (void); + void (*ds_server_disable) (void); +} MonoComponentDiagnosticsServer; + +#ifdef STATIC_COMPONENTS +MONO_COMPONENT_EXPORT_ENTRYPOINT +MonoComponentDiagnosticsServer * +mono_component_diagnostics_server_init (void); +#endif + +#endif /*_MONO_COMPONENT_DIAGNOSTICS_SERVER_H*/ diff --git a/src/mono/mono/component/event_pipe-stub.c b/src/mono/mono/component/event_pipe-stub.c new file mode 100644 index 00000000000000..2329fa58828f09 --- /dev/null +++ b/src/mono/mono/component/event_pipe-stub.c @@ -0,0 +1,92 @@ +// Licensed to the .NET Foundation under one or more agreements. +// The .NET Foundation licenses this file to you under the MIT license. +// + +#include +#include "mono/component/event_pipe.h" + +static void +event_pipe_stub_cleanup (MonoComponent *self); + +static void +event_pipe_stub_ep_init (void); + +static void +event_pipe_stub_ep_finish_init (void); + +static void +event_pipe_stub_ep_shutdown (void); + +static void +event_pipe_stub_ds_server_init (void); + +static void +event_pipe_stub_ds_server_shutdown (void); + +static void +event_pipe_stub_ds_server_pause_for_diagnostics_monitor (void); + +static void +event_pipe_stub_ds_server_disable (void); + +static MonoComponentEventPipe fn_table = { + { &event_pipe_stub_cleanup }, + &event_pipe_stub_ep_init, + &event_pipe_stub_ep_finish_init, + &event_pipe_stub_ep_shutdown +}; + +#ifdef STATIC_COMPONENTS +MONO_COMPONENT_EXPORT_ENTRYPOINT +MonoComponentEventpipe * +mono_component_event_pipe_init (void) +{ + return mono_component_event_pipe_stub_init (); +} +#endif + +MonoComponentEventPipe * +mono_component_event_pipe_stub_init (void) +{ + return &fn_table; +} + +static void +event_pipe_stub_cleanup (MonoComponent *self) +{ +} + +static void +event_pipe_stub_ep_init (void) +{ +} + +static void +event_pipe_stub_ep_finish_init (void) +{ +} + +static void +event_pipe_stub_ep_shutdown (void) +{ +} + +static void +event_pipe_stub_ds_server_init (void) +{ +} + +static void +event_pipe_stub_ds_server_shutdown (void) +{ +} + +static void +event_pipe_stub_ds_server_pause_for_diagnostics_monitor (void) +{ +} + +static void +event_pipe_stub_ds_server_disable (void) +{ +} diff --git a/src/mono/mono/component/event_pipe.c b/src/mono/mono/component/event_pipe.c new file mode 100644 index 00000000000000..d638fb2d37b1ae --- /dev/null +++ b/src/mono/mono/component/event_pipe.c @@ -0,0 +1,37 @@ +// Licensed to the .NET Foundation under one or more agreements. +// The .NET Foundation licenses this file to you under the MIT license. +// + +#include +#include +#include +#include +#include + +#ifndef STATIC_COMPONENTS +MONO_COMPONENT_EXPORT_ENTRYPOINT +MonoComponentEventPipe * +mono_component_event_pipe_init (void); +#endif + +static void +event_pipe_cleanup (MonoComponent *self); + +static MonoComponentEventPipe fn_table = { + { &event_pipe_cleanup }, + &ep_init, + &ep_finish_init, + &ep_shutdown +}; + +static void +event_pipe_cleanup (MonoComponent *self) +{ + return; +} + +MonoComponentEventPipe * +mono_component_event_pipe_init (void) +{ + return &fn_table; +} diff --git a/src/mono/mono/component/event_pipe.h b/src/mono/mono/component/event_pipe.h new file mode 100644 index 00000000000000..9bfb1056edcb0c --- /dev/null +++ b/src/mono/mono/component/event_pipe.h @@ -0,0 +1,23 @@ +// Licensed to the .NET Foundation under one or more agreements. +// The .NET Foundation licenses this file to you under the MIT license. +// + +#ifndef _MONO_COMPONENT_EVENT_PIPE_H +#define _MONO_COMPONENT_EVENT_PIPE_H + +#include "mono/component/component.h" + +typedef struct _MonoComponentEventPipe { + MonoComponent component; + void (*ep_init) (void); + void (*ep_finish_init) (void); + void (*ep_shutdown) (void); +} MonoComponentEventPipe; + +#ifdef STATIC_COMPONENTS +MONO_COMPONENT_EXPORT_ENTRYPOINT +MonoComponentEventPipe * +mono_component_event_pipe_init (void); +#endif + +#endif /*_MONO_COMPONENT_EVENT_PIPE_H*/ diff --git a/src/mono/mono/metadata/appdomain.c b/src/mono/mono/metadata/appdomain.c index 6426bc8729a168..f3462d1462e39d 100644 --- a/src/mono/mono/metadata/appdomain.c +++ b/src/mono/mono/metadata/appdomain.c @@ -69,10 +69,7 @@ #include #include #include - -#ifdef ENABLE_PERFTRACING -#include -#endif +#include #ifdef HOST_WIN32 #include @@ -282,8 +279,8 @@ mono_runtime_init_checked (MonoDomain *domain, MonoThreadStartCB start_cb, MonoT mono_thread_internal_attach (domain); #if defined(ENABLE_PERFTRACING) && !defined(DISABLE_EVENTPIPE) - ds_server_init (); - ds_server_pause_for_diagnostics_monitor (); + mono_component_diagnostics_server ()->ds_server_init (); + mono_component_diagnostics_server ()->ds_server_pause_for_diagnostics_monitor (); #endif mono_type_initialization_init (); diff --git a/src/mono/mono/metadata/components.c b/src/mono/mono/metadata/components.c index 3aae8f67d4ee28..df1c13f93939c4 100644 --- a/src/mono/mono/metadata/components.c +++ b/src/mono/mono/metadata/components.c @@ -6,6 +6,8 @@ #include #include "mono/component/component.h" #include "mono/component/hot_reload.h" +#include "mono/component/event_pipe.h" +#include "mono/component/diagnostics_server.h" #include "mono/metadata/class-internals.h" #include "mono/metadata/components.h" #include "mono/utils/mono-dl.h" @@ -14,13 +16,34 @@ typedef MonoComponent * (*MonoComponentInitFn) (void); -#ifndef STATIC_COMPONENTS -/* List of MonoDl* for each loaded component */ -static GSList *loaded_components; +typedef struct _MonoComponentEntry { + const char *name; + MonoComponentInitFn init; + MonoComponent **component; + MonoDl *lib; +} MonoComponentEntry; + +#ifdef STATIC_COMPONENTS +#define COMPONENT_INIT_FUNC(name) (MonoComponentInitFn) mono_component_ ## name ## _init +#else +#define COMPONENT_INIT_FUNC(name) (MonoComponentInitFn) mono_component_ ## name ## _stub_init #endif -/* One static per component */ -static MonoComponentHotReload *hot_reload; +MonoComponentHotReload *hot_reload = NULL; +MonoComponentEventPipe *event_pipe = NULL; +MonoComponentEventPipe *diagnostics_server = NULL; + +// DiagnosticsServer component currently hosted by EventPipe module. +#define HOT_RELOAD_MODULE_NAME "hot_reload" +#define EVENT_PIPE_MODULE_NAME "event_pipe" +#define DIAGNOSTICS_SERVER_MODULE_NAME EVENT_PIPE_MODULE_NAME + +/* One per component */ +MonoComponentEntry components[] = { + { HOT_RELOAD_MODULE_NAME, COMPONENT_INIT_FUNC (hot_reload), (MonoComponent**)&hot_reload, NULL }, + { EVENT_PIPE_MODULE_NAME, COMPONENT_INIT_FUNC (event_pipe), (MonoComponent**)&event_pipe, NULL }, + { DIAGNOSTICS_SERVER_MODULE_NAME, COMPONENT_INIT_FUNC (diagnostics_server), (MonoComponent**)&diagnostics_server, NULL } +}; #ifndef STATIC_COMPONENTS static MonoComponent* @@ -44,36 +67,31 @@ mono_components_init (void) * to pass us the address of each component that isn't disabled. * */ - hot_reload = mono_component_hot_reload_init (); + for (int i = 0; i < G_N_ELEMENTS (components); ++i) + *components [i].component = components [i].init (); #else - /* call get_component for each component and init it or its stubs and add it to loaded_components */ + /* call get_component for each component and init it or its stubs and add it to loaded_components */ MonoDl *lib = NULL; - /* Repeat for each component */ - hot_reload = (MonoComponentHotReload*)get_component ("hot_reload", &lib); - if (hot_reload) { - loaded_components = g_slist_prepend (loaded_components, lib); - } else { - hot_reload = mono_component_hot_reload_stub_init (); + for (int i = 0; i < G_N_ELEMENTS (components); ++i) { + *components [i].component = get_component (components [i].name, &lib); + components [i].lib = lib; + if (!*components [i].component) + *components [i].component = components [i].init (); } - #endif } - void mono_components_cleanup (void) { /* call each components cleanup fn */ - if (hot_reload) { - hot_reload->component.cleanup (&hot_reload->component); - hot_reload = NULL; + for (int i = 0; i < G_N_ELEMENTS (components); ++i) { + if (*components [i].component) + (*components [i].component)->cleanup (*components [i].component); + if (components [i].lib) + mono_dl_close (components [i].lib); } -#ifndef STATIC_COMPONENTS - for (GSList *p = loaded_components; p != NULL; p = p->next) { - mono_dl_close ((MonoDl*)p->data); - } -#endif } static char* diff --git a/src/mono/mono/metadata/components.h b/src/mono/mono/metadata/components.h index 8e0ec94984b96d..03d50fdfc0a948 100644 --- a/src/mono/mono/metadata/components.h +++ b/src/mono/mono/metadata/components.h @@ -7,6 +7,8 @@ #include #include +#include +#include void mono_components_init (void); @@ -15,11 +17,38 @@ void mono_components_cleanup (void); /* Declare each component's getter function here */ +static inline MonoComponentHotReload * -mono_component_hot_reload (void); +mono_component_hot_reload (void) +{ + extern MonoComponentHotReload *hot_reload; + return hot_reload; +} + +static inline +MonoComponentEventPipe * +mono_component_event_pipe (void) +{ + extern MonoComponentEventPipe *event_pipe; + return event_pipe; +} + +static inline +MonoComponentDiagnosticsServer * +mono_component_diagnostics_server (void) +{ + extern MonoComponentDiagnosticsServer *diagnostics_server; + return diagnostics_server; +} /* Declare each copomnents stub init function here */ MonoComponentHotReload * mono_component_hot_reload_stub_init (void); +MonoComponentEventPipe * +mono_component_event_pipe_stub_init (void); + +MonoComponentDiagnosticsServer * +mono_component_diagnostics_server_stub_init (void); + #endif/*_MONO_METADATA_COMPONENTS_H*/ diff --git a/src/mono/mono/mini/CMakeLists.txt b/src/mono/mono/mini/CMakeLists.txt index 6fc8b4b1e769d8..c3da713698791d 100644 --- a/src/mono/mono/mini/CMakeLists.txt +++ b/src/mono/mono/mini/CMakeLists.txt @@ -31,21 +31,6 @@ if(INTERNAL_ZLIB) # TODO: hook up HAVE_SYS_ZLIB instead endif() include(../component/CMakeLists.txt) -if(ENABLE_PERFTRACING) - - set (SHARED_EVENTPIPE_INCLUDE_PATH "../../../native/") - set (SHARED_EVENTPIPE_SOURCE_PATH "../../../native/eventpipe/") - set (MONO_EVENTPIPE_SHIM_SOURCE_PATH "../eventpipe/") - - include(${MONO_EVENTPIPE_SHIM_SOURCE_PATH}/CMakeLists.txt) - - include_directories( - ${SHARED_EVENTPIPE_INCLUDE_PATH} - ${MONO_EVENTPIPE_SHIM_SOURCE_PATH} - ) - -endif(ENABLE_PERFTRACING) - if(HOST_WIN32) # /OPT:ICF merges idential functions breaking mono_lookup_icall_symbol () add_link_options(/OPT:NOICF) @@ -324,7 +309,7 @@ set(OS_LIBS bcrypt.lib Mswsock.lib ws2_32.lib psapi.lib version.lib advapi32.lib set(mini_sources "${mini_sources};${PROJECT_BINARY_DIR}/../../NativeVersion.rc") # this is generated by GenerateMonoVersionFile in mono.proj endif() -add_library(monosgen-objects OBJECT "${metadata_sources};${utils_sources};${sgen_sources};${icu_shim_sources};${eventpipe_sources};${mini_sources};${zlib_sources}") +add_library(monosgen-objects OBJECT "${eglib_sources};${metadata_sources};${utils_sources};${sgen_sources};${icu_shim_sources};${mini_sources};${zlib_sources}") add_library(monosgen-static STATIC $) set_target_properties(monosgen-static PROPERTIES OUTPUT_NAME monosgen-2.0) target_link_libraries(monosgen-static eglib_objects) diff --git a/src/mono/mono/mini/mini-runtime.c b/src/mono/mono/mini/mini-runtime.c index f1c43bcabaea95..dca4243cb0e418 100644 --- a/src/mono/mono/mini/mini-runtime.c +++ b/src/mono/mono/mini/mini-runtime.c @@ -71,11 +71,7 @@ #include #include #include - -#ifdef ENABLE_PERFTRACING -#include -#include -#endif +#include #include "mini.h" #include "seq-points.h" @@ -4430,9 +4426,9 @@ mini_init (const char *filename, const char *runtime_version) #if defined(ENABLE_PERFTRACING) && !defined(DISABLE_EVENTPIPE) if (mono_compile_aot) - ds_server_disable (); + mono_component_diagnostics_server ()->ds_server_disable (); - ep_init (); + mono_component_event_pipe ()->ep_init (); #endif if (mono_aot_only) { @@ -4501,7 +4497,7 @@ mini_init (const char *filename, const char *runtime_version) mono_threads_set_runtime_startup_finished (); #if defined(ENABLE_PERFTRACING) && !defined(DISABLE_EVENTPIPE) - ep_finish_init (); + mono_component_event_pipe ()->ep_finish_init (); #endif #ifdef ENABLE_EXPERIMENT_TIERED @@ -4884,8 +4880,8 @@ mini_cleanup (MonoDomain *domain) mono_jit_dump_cleanup (); mini_get_interp_callbacks ()->cleanup (); #if defined(ENABLE_PERFTRACING) && !defined(DISABLE_EVENTPIPE) - ep_shutdown (); - ds_server_shutdown (); + mono_component_event_pipe ()->ep_shutdown (); + mono_component_diagnostics_server ()->ds_server_shutdown (); #endif } From bbb9c9232018ac08108a5a1365acd943c8861aac Mon Sep 17 00:00:00 2001 From: lateralusX Date: Fri, 26 Mar 2021 16:09:30 +0100 Subject: [PATCH 18/55] Use EventPipe component API from runtime. --- .../mono/component/diagnostics_server-stub.c | 31 +- src/mono/mono/component/diagnostics_server.c | 3 + src/mono/mono/component/diagnostics_server.h | 10 +- src/mono/mono/component/event_pipe-stub.c | 219 +- src/mono/mono/component/event_pipe.c | 223 ++- src/mono/mono/component/event_pipe.h | 136 +- src/mono/mono/eventpipe/ep-rt-config-mono.h | 1 - src/mono/mono/eventpipe/ep-rt-mono.c | 1757 ++++++++++++----- src/mono/mono/eventpipe/ep-rt-mono.h | 325 +-- src/mono/mono/metadata/appdomain.c | 4 +- src/mono/mono/metadata/components.c | 11 +- src/mono/mono/metadata/components.h | 4 + .../mono/metadata/environment-internals.h | 4 +- src/mono/mono/metadata/icall-eventpipe.c | 310 +-- src/mono/mono/metadata/object-internals.h | 2 +- src/mono/mono/mini/mini-runtime.c | 10 +- src/mono/mono/utils/mono-proclib.h | 2 +- src/mono/mono/utils/mono-threads.h | 5 +- src/native/eventpipe/CMakeLists.txt | 2 + .../eventpipe/ep-ipc-pal-types-forward.h | 22 + src/native/eventpipe/ep-ipc-pal-types.h | 15 +- src/native/eventpipe/ep-types-forward.h | 205 ++ src/native/eventpipe/ep-types.h | 198 +- 23 files changed, 2109 insertions(+), 1390 deletions(-) create mode 100644 src/native/eventpipe/ep-ipc-pal-types-forward.h create mode 100644 src/native/eventpipe/ep-types-forward.h diff --git a/src/mono/mono/component/diagnostics_server-stub.c b/src/mono/mono/component/diagnostics_server-stub.c index 842a68cd5fe3a3..e9c04c204e8247 100644 --- a/src/mono/mono/component/diagnostics_server-stub.c +++ b/src/mono/mono/component/diagnostics_server-stub.c @@ -3,29 +3,35 @@ // #include + +#ifdef ENABLE_PERFTRACING #include "mono/component/diagnostics_server.h" +/* + * Forward declares of all static functions. + */ + static void diagnostics_server_stub_cleanup (MonoComponent *self); static void -diagnostics_server_stub_ds_server_init (void); +diagnostics_server_stub_init (void); static void -diagnostics_server_stub_ds_server_shutdown (void); +diagnostics_server_stub_shutdown (void); static void -diagnostics_server_stub_ds_server_pause_for_diagnostics_monitor (void); +diagnostics_server_stub_pause_for_diagnostics_monitor (void); static void -diagnostics_server_stub_ds_server_disable (void); +diagnostics_server_stub_disable (void); static MonoComponentDiagnosticsServer fn_table = { { &diagnostics_server_stub_cleanup }, - &diagnostics_server_stub_ds_server_init, - &diagnostics_server_stub_ds_server_shutdown, - &diagnostics_server_stub_ds_server_pause_for_diagnostics_monitor, - &diagnostics_server_stub_ds_server_disable + &diagnostics_server_stub_init, + &diagnostics_server_stub_shutdown, + &diagnostics_server_stub_pause_for_diagnostics_monitor, + &diagnostics_server_stub_disable }; #ifdef STATIC_COMPONENTS @@ -49,21 +55,22 @@ diagnostics_server_stub_cleanup (MonoComponent *self) } static void -diagnostics_server_stub_ds_server_init (void) +diagnostics_server_stub_init (void) { } static void -diagnostics_server_stub_ds_server_shutdown (void) +diagnostics_server_stub_shutdown (void) { } static void -diagnostics_server_stub_ds_server_pause_for_diagnostics_monitor (void) +diagnostics_server_stub_pause_for_diagnostics_monitor (void) { } static void -diagnostics_server_stub_ds_server_disable (void) +diagnostics_server_stub_disable (void) { } +#endif /* ENABLE_PERFTRACING */ diff --git a/src/mono/mono/component/diagnostics_server.c b/src/mono/mono/component/diagnostics_server.c index 239576b4667bd0..82ee17b6466e7a 100644 --- a/src/mono/mono/component/diagnostics_server.c +++ b/src/mono/mono/component/diagnostics_server.c @@ -3,6 +3,8 @@ // #include + +#ifdef ENABLE_PERFTRACING #include #include #include @@ -36,3 +38,4 @@ mono_component_diagnostics_server_init (void) { return &fn_table; } +#endif /* ENABLE_PERFTRACING */ diff --git a/src/mono/mono/component/diagnostics_server.h b/src/mono/mono/component/diagnostics_server.h index 40edf4e4279bf0..89aeef9f2b02ba 100644 --- a/src/mono/mono/component/diagnostics_server.h +++ b/src/mono/mono/component/diagnostics_server.h @@ -5,14 +5,15 @@ #ifndef _MONO_COMPONENT_DIAGNOSTICS_SERVER_H #define _MONO_COMPONENT_DIAGNOSTICS_SERVER_H +#ifdef ENABLE_PERFTRACING #include "mono/component/component.h" typedef struct _MonoComponentDiagnosticsServer { MonoComponent component; - void (*ds_server_init) (void); - void (*ds_server_shutdown) (void); - void (*ds_server_pause_for_diagnostics_monitor) (void); - void (*ds_server_disable) (void); + void (*init) (void); + void (*shutdown) (void); + void (*pause_for_diagnostics_monitor) (void); + void (*disable) (void); } MonoComponentDiagnosticsServer; #ifdef STATIC_COMPONENTS @@ -21,4 +22,5 @@ MonoComponentDiagnosticsServer * mono_component_diagnostics_server_init (void); #endif +#endif /* ENABLE_PERFTRACING */ #endif /*_MONO_COMPONENT_DIAGNOSTICS_SERVER_H*/ diff --git a/src/mono/mono/component/event_pipe-stub.c b/src/mono/mono/component/event_pipe-stub.c index 2329fa58828f09..bc634afd56c92a 100644 --- a/src/mono/mono/component/event_pipe-stub.c +++ b/src/mono/mono/component/event_pipe-stub.c @@ -3,90 +3,251 @@ // #include + +#ifdef ENABLE_PERFTRACING #include "mono/component/event_pipe.h" +static EventPipeSessionID _dummy_session_id; + +static uint8_t _max_event_pipe_type_size [256]; + +/* + * Forward declares of all static functions. + */ + static void event_pipe_stub_cleanup (MonoComponent *self); static void -event_pipe_stub_ep_init (void); +event_pipe_stub_init (void); static void -event_pipe_stub_ep_finish_init (void); +event_pipe_stub_finish_init (void); static void -event_pipe_stub_ep_shutdown (void); +event_pipe_stub_shutdown (void); + +static EventPipeSessionID +event_pipe_stub_enable ( + const ep_char8_t *output_path, + uint32_t circular_buffer_size_in_mb, + const EventPipeProviderConfigurationNative *providers, + uint32_t providers_len, + EventPipeSessionType session_type, + EventPipeSerializationFormat format, + bool rundown_requested, + IpcStream *stream, + EventPipeSessionSynchronousCallback sync_callback); static void -event_pipe_stub_ds_server_init (void); +event_pipe_stub_disable (EventPipeSessionID id); + +static bool +event_pipe_stub_get_next_event ( + EventPipeSessionID session_id, + EventPipeEventInstanceData *instance); + +static EventPipeWaitHandle +event_pipe_stub_get_wait_handle (EventPipeSessionID session_id); static void -event_pipe_stub_ds_server_shutdown (void); +event_pipe_stub_start_streaming (EventPipeSessionID session_id); static void -event_pipe_stub_ds_server_pause_for_diagnostics_monitor (void); +event_pipe_stub_write_event_2 ( + EventPipeEvent *ep_event, + EventData *event_data, + uint32_t event_data_len, + const uint8_t *activity_id, + const uint8_t *related_activity_id); + +static EventPipeProvider * +event_pipe_stub_create_provider ( + const ep_char8_t *provider_name, + EventPipeCallback callback_func, + EventPipeCallbackDataFree callback_data_free_func, + void *callback_data); static void -event_pipe_stub_ds_server_disable (void); +event_pipe_stub_delete_provider (EventPipeProvider *provider); + +static EventPipeProvider * +event_pipe_stub_get_provider (const ep_char8_t *provider_name); + +static EventPipeEvent * +event_pipe_stub_provider_add_event ( + EventPipeProvider *provider, + uint32_t event_id, + uint64_t keywords, + uint32_t event_version, + EventPipeEventLevel level, + bool need_stack, + const uint8_t *metadata, + uint32_t metadata_len); + +static bool +event_pipe_stub_get_session_info ( + EventPipeSessionID session_id, + EventPipeSessionInfo *instance); + +static bool +event_pipe_stub_thread_ctrl_activity_id ( + EventPipeActivityControlCode activity_control_code, + uint8_t *activity_id, + uint32_t activity_id_len); static MonoComponentEventPipe fn_table = { { &event_pipe_stub_cleanup }, - &event_pipe_stub_ep_init, - &event_pipe_stub_ep_finish_init, - &event_pipe_stub_ep_shutdown + &event_pipe_stub_init, + &event_pipe_stub_finish_init, + &event_pipe_stub_shutdown, + &event_pipe_stub_enable, + &event_pipe_stub_disable, + &event_pipe_stub_get_next_event, + &event_pipe_stub_get_wait_handle, + &event_pipe_stub_start_streaming, + event_pipe_stub_write_event_2, + event_pipe_stub_create_provider, + event_pipe_stub_delete_provider, + event_pipe_stub_get_provider, + event_pipe_stub_provider_add_event, + event_pipe_stub_get_session_info, + event_pipe_stub_thread_ctrl_activity_id }; -#ifdef STATIC_COMPONENTS -MONO_COMPONENT_EXPORT_ENTRYPOINT -MonoComponentEventpipe * -mono_component_event_pipe_init (void) +static void +event_pipe_stub_cleanup (MonoComponent *self) { - return mono_component_event_pipe_stub_init (); } -#endif -MonoComponentEventPipe * -mono_component_event_pipe_stub_init (void) +static void +event_pipe_stub_init (void) { - return &fn_table; } static void -event_pipe_stub_cleanup (MonoComponent *self) +event_pipe_stub_finish_init (void) { } static void -event_pipe_stub_ep_init (void) +event_pipe_stub_shutdown (void) { } -static void -event_pipe_stub_ep_finish_init (void) +static EventPipeSessionID +event_pipe_stub_enable ( + const ep_char8_t *output_path, + uint32_t circular_buffer_size_in_mb, + const EventPipeProviderConfigurationNative *providers, + uint32_t providers_len, + EventPipeSessionType session_type, + EventPipeSerializationFormat format, + bool rundown_requested, + IpcStream *stream, + EventPipeSessionSynchronousCallback sync_callback) { + return (EventPipeSessionID)&_dummy_session_id; } static void -event_pipe_stub_ep_shutdown (void) +event_pipe_stub_disable (EventPipeSessionID id) { } -static void -event_pipe_stub_ds_server_init (void) +static bool +event_pipe_stub_get_next_event ( + EventPipeSessionID session_id, + EventPipeEventInstanceData *instance) +{ + return false; +} + +static EventPipeWaitHandle +event_pipe_stub_get_wait_handle (EventPipeSessionID session_id) { + return (EventPipeWaitHandle)NULL; } static void -event_pipe_stub_ds_server_shutdown (void) +event_pipe_stub_start_streaming (EventPipeSessionID session_id) { } static void -event_pipe_stub_ds_server_pause_for_diagnostics_monitor (void) +event_pipe_stub_write_event_2 ( + EventPipeEvent *ep_event, + EventData *event_data, + uint32_t event_data_len, + const uint8_t *activity_id, + const uint8_t *related_activity_id) { } +static EventPipeProvider * +event_pipe_stub_create_provider ( + const ep_char8_t *provider_name, + EventPipeCallback callback_func, + EventPipeCallbackDataFree callback_data_free_func, + void *callback_data) +{ + return (EventPipeProvider *)_max_event_pipe_type_size; +} + static void -event_pipe_stub_ds_server_disable (void) +event_pipe_stub_delete_provider (EventPipeProvider *provider) +{ +} + +static EventPipeProvider * +event_pipe_stub_get_provider (const ep_char8_t *provider_name) +{ + return NULL; +} + +static EventPipeEvent * +event_pipe_stub_provider_add_event ( + EventPipeProvider *provider, + uint32_t event_id, + uint64_t keywords, + uint32_t event_version, + EventPipeEventLevel level, + bool need_stack, + const uint8_t *metadata, + uint32_t metadata_len) +{ + return (EventPipeEvent *)_max_event_pipe_type_size; +} + +static bool +event_pipe_stub_get_session_info ( + EventPipeSessionID session_id, + EventPipeSessionInfo *instance) +{ + return false; +} + +static bool +event_pipe_stub_thread_ctrl_activity_id ( + EventPipeActivityControlCode activity_control_code, + uint8_t *activity_id, + uint32_t activity_id_len) { + return false; +} + +#ifdef STATIC_COMPONENTS +MONO_COMPONENT_EXPORT_ENTRYPOINT +MonoComponentEventpipe * +mono_component_event_pipe_init (void) +{ + return mono_component_event_pipe_stub_init (); +} +#endif + +MonoComponentEventPipe * +mono_component_event_pipe_stub_init (void) +{ + return &fn_table; } +#endif /* ENABLE_PERFTRACING */ diff --git a/src/mono/mono/component/event_pipe.c b/src/mono/mono/component/event_pipe.c index d638fb2d37b1ae..8d409a89c2bdaa 100644 --- a/src/mono/mono/component/event_pipe.c +++ b/src/mono/mono/component/event_pipe.c @@ -3,25 +3,92 @@ // #include + +#ifdef ENABLE_PERFTRACING #include #include #include #include +#include +#include +#include -#ifndef STATIC_COMPONENTS -MONO_COMPONENT_EXPORT_ENTRYPOINT -MonoComponentEventPipe * -mono_component_event_pipe_init (void); -#endif +struct _EventPipeProviderConfigurationNative { + gunichar2 *provider_name; + uint64_t keywords; + uint32_t logging_level; + gunichar2 *filter_data; +}; + +struct _EventPipeSessionInfo { + int64_t starttime_as_utc_filetime; + int64_t start_timestamp; + int64_t timestamp_frequency; +}; + +struct _EventPipeEventInstanceData { + intptr_t provider_id; + uint32_t event_id; + uint32_t thread_id; + int64_t timestamp; + uint8_t activity_id [EP_ACTIVITY_ID_SIZE]; + uint8_t related_activity_id [EP_ACTIVITY_ID_SIZE]; + const uint8_t *payload; + uint32_t payload_len; +}; + +/* + * Forward declares of all static functions. + */ static void event_pipe_cleanup (MonoComponent *self); +static EventPipeSessionID +event_pipe_enable ( + const ep_char8_t *output_path, + uint32_t circular_buffer_size_in_mb, + const EventPipeProviderConfigurationNative *providers, + uint32_t providers_len, + EventPipeSessionType session_type, + EventPipeSerializationFormat format, + bool rundown_requested, + IpcStream *stream, + EventPipeSessionSynchronousCallback sync_callback); + +static bool +event_pipe_get_next_event ( + EventPipeSessionID session_id, + EventPipeEventInstanceData *instance); + +static bool +event_pipe_get_session_info ( + EventPipeSessionID session_id, + EventPipeSessionInfo *instance); + +static bool +event_pipe_thread_ctrl_activity_id( + EventPipeActivityControlCode activity_control_code, + uint8_t *activity_id, + uint32_t activity_id_len); + static MonoComponentEventPipe fn_table = { { &event_pipe_cleanup }, &ep_init, &ep_finish_init, - &ep_shutdown + &ep_shutdown, + &event_pipe_enable, + &ep_disable, + &event_pipe_get_next_event, + &ep_get_wait_handle, + &ep_start_streaming, + &ep_write_event_2, + &ep_create_provider, + &ep_delete_provider, + &ep_get_provider, + &ep_provider_add_event, + &event_pipe_get_session_info, + &event_pipe_thread_ctrl_activity_id }; static void @@ -30,8 +97,152 @@ event_pipe_cleanup (MonoComponent *self) return; } +static EventPipeSessionID +event_pipe_enable ( + const ep_char8_t *output_path, + uint32_t circular_buffer_size_in_mb, + const EventPipeProviderConfigurationNative *providers, + uint32_t providers_len, + EventPipeSessionType session_type, + EventPipeSerializationFormat format, + bool rundown_requested, + IpcStream *stream, + EventPipeSessionSynchronousCallback sync_callback) +{ + ERROR_DECL (error); + EventPipeSessionID session_id = 0; + + EventPipeProviderConfiguration *config_providers = g_new0 (EventPipeProviderConfiguration, providers_len); + + if (config_providers) { + for (int i = 0; i < providers_len; ++i) { + ep_provider_config_init ( + &config_providers[i], + providers[i].provider_name ? mono_utf16_to_utf8 (providers[i].provider_name, g_utf16_len (providers[i].provider_name), error) : NULL, + providers [i].keywords, + (EventPipeEventLevel)providers [i].logging_level, + providers[i].filter_data ? mono_utf16_to_utf8 (providers[i].filter_data, g_utf16_len (providers[i].filter_data), error) : NULL); + } + } + + session_id = ep_enable ( + output_path, + circular_buffer_size_in_mb, + config_providers, + providers_len, + session_type, + format, + rundown_requested, + stream, + sync_callback); + + if (config_providers) { + for (int i = 0; i < providers_len; ++i) { + ep_provider_config_fini (&config_providers[i]); + g_free ((ep_char8_t *)ep_provider_config_get_provider_name (&config_providers[i])); + g_free ((ep_char8_t *)ep_provider_config_get_filter_data (&config_providers[i])); + } + } + + return session_id; +} + +static bool +event_pipe_get_next_event ( + EventPipeSessionID session_id, + EventPipeEventInstanceData *instance) +{ + EP_ASSERT (instance != NULL); + + EventPipeEventInstance *const next_instance = ep_get_next_event (session_id); + EventPipeEventInstanceData *const data = (EventPipeEventInstanceData *)instance; + if (next_instance && data) { + const EventPipeEvent *const ep_event = ep_event_instance_get_ep_event (next_instance); + if (ep_event) { + data->provider_id = (intptr_t)ep_event_get_provider (ep_event); + data->event_id = ep_event_get_event_id (ep_event); + } + data->thread_id = ep_event_instance_get_thread_id (next_instance); + data->timestamp = ep_event_instance_get_timestamp (next_instance); + memcpy (&data->activity_id, ep_event_instance_get_activity_id_cref (next_instance), EP_ACTIVITY_ID_SIZE); + memcpy (&data->related_activity_id, ep_event_instance_get_related_activity_id_cref (next_instance), EP_ACTIVITY_ID_SIZE); + data->payload = ep_event_instance_get_data (next_instance); + data->payload_len = ep_event_instance_get_data_len (next_instance); + } + + return next_instance != NULL; +} + +static bool +event_pipe_thread_ctrl_activity_id ( + EventPipeActivityControlCode activity_control_code, + uint8_t *activity_id, + uint32_t activity_id_len) +{ + bool result = true; + ep_rt_thread_activity_id_handle_t activity_id_handle = ep_thread_get_activity_id_handle (); + + if (activity_id_handle == NULL) + return false; + + uint8_t current_activity_id [EP_ACTIVITY_ID_SIZE]; + switch (activity_control_code) { + case EP_ACTIVITY_CONTROL_GET_ID: + ep_thread_get_activity_id (activity_id_handle, activity_id, EP_ACTIVITY_ID_SIZE); + break; + case EP_ACTIVITY_CONTROL_SET_ID: + ep_thread_set_activity_id (activity_id_handle, activity_id, EP_ACTIVITY_ID_SIZE); + break; + case EP_ACTIVITY_CONTROL_CREATE_ID: + ep_thread_create_activity_id (activity_id, EP_ACTIVITY_ID_SIZE); + break; + case EP_ACTIVITY_CONTROL_GET_SET_ID: + ep_thread_get_activity_id (activity_id_handle, current_activity_id, EP_ACTIVITY_ID_SIZE); + ep_thread_set_activity_id (activity_id_handle, activity_id, EP_ACTIVITY_ID_SIZE); + memcpy (activity_id, current_activity_id, EP_ACTIVITY_ID_SIZE); + break; + case EP_ACTIVITY_CONTROL_CREATE_SET_ID: + ep_thread_get_activity_id (activity_id_handle, activity_id, EP_ACTIVITY_ID_SIZE); + ep_thread_create_activity_id (current_activity_id, EP_ACTIVITY_ID_SIZE); + ep_thread_set_activity_id (activity_id_handle, current_activity_id, EP_ACTIVITY_ID_SIZE); + break; + default: + result = false; + break; + } + + return result; +} + +static bool +event_pipe_get_session_info ( + EventPipeSessionID session_id, + EventPipeSessionInfo *instance) +{ + bool result = false; + if (instance) { + EventPipeSession *session = ep_get_session ((EventPipeSessionID)session_id); + if (session) { + instance->starttime_as_utc_filetime = ep_session_get_session_start_time (session); + instance->start_timestamp = ep_session_get_session_start_timestamp (session); + instance->timestamp_frequency = ep_perf_frequency_query (); + result = true; + } + } + + return result; +} + +#ifndef STATIC_COMPONENTS +MONO_COMPONENT_EXPORT_ENTRYPOINT +MonoComponentEventPipe * +mono_component_event_pipe_init (void); +#endif + MonoComponentEventPipe * mono_component_event_pipe_init (void) { return &fn_table; } + +#endif /* ENABLE_PERFTRACING */ diff --git a/src/mono/mono/component/event_pipe.h b/src/mono/mono/component/event_pipe.h index 9bfb1056edcb0c..c0bf25309d39ff 100644 --- a/src/mono/mono/component/event_pipe.h +++ b/src/mono/mono/component/event_pipe.h @@ -5,13 +5,140 @@ #ifndef _MONO_COMPONENT_EVENT_PIPE_H #define _MONO_COMPONENT_EVENT_PIPE_H -#include "mono/component/component.h" +#ifdef ENABLE_PERFTRACING + +#include + +#include +#include + +typedef enum _EventPipeActivityControlCode { + EP_ACTIVITY_CONTROL_GET_ID = 1, + EP_ACTIVITY_CONTROL_SET_ID = 2, + EP_ACTIVITY_CONTROL_CREATE_ID = 3, + EP_ACTIVITY_CONTROL_GET_SET_ID = 4, + EP_ACTIVITY_CONTROL_CREATE_SET_ID = 5 +} EventPipeActivityControlCode; + +typedef struct _EventPipeProviderConfigurationNative EventPipeProviderConfigurationNative; +typedef struct _EventPipeEventInstanceData EventPipeEventInstanceData; +typedef struct _EventPipeSessionInfo EventPipeSessionInfo; + +/* + * EventPipe. + */ + +typedef void +(*event_pipe_component_init_func) (void); + +typedef void +(*event_pipe_component_finish_init_func) (void); + +typedef void +(*event_pipe_component_shutdown_func) (void); + +typedef EventPipeSessionID +(*event_pipe_component_enable_func) ( + const ep_char8_t *output_path, + uint32_t circular_buffer_size_in_mb, + const EventPipeProviderConfigurationNative *providers, + uint32_t providers_len, + EventPipeSessionType session_type, + EventPipeSerializationFormat format, + bool rundown_requested, + IpcStream *stream, + EventPipeSessionSynchronousCallback sync_callback); + +typedef void +(*event_pipe_component_disable_func) (EventPipeSessionID id); + +typedef bool +(*event_pipe_component_get_next_event_func) ( + EventPipeSessionID session_id, + EventPipeEventInstanceData *instance); + +typedef EventPipeWaitHandle +(*event_pipe_component_get_wait_handle_func) (EventPipeSessionID session_id); + +typedef void +(*event_pipe_component_start_streaming_func) (EventPipeSessionID session_id); + +typedef void +(*event_pipe_component_write_event_2_func) ( + EventPipeEvent *ep_event, + EventData *event_data, + uint32_t event_data_len, + const uint8_t *activity_id, + const uint8_t *related_activity_id); + +/* + * EventPipeProvider. + */ + +typedef EventPipeProvider * +(*event_pipe_component_create_provider_func) ( + const ep_char8_t *provider_name, + EventPipeCallback callback_func, + EventPipeCallbackDataFree callback_data_free_func, + void *callback_data); + +typedef void +(*event_pipe_component_delete_provider_func) (EventPipeProvider *provider); + +typedef EventPipeProvider * +(*event_pipe_component_get_provider_func) (const ep_char8_t *provider_name); + +typedef EventPipeEvent * +(*event_pipe_component_provider_add_event_func) ( + EventPipeProvider *provider, + uint32_t event_id, + uint64_t keywords, + uint32_t event_version, + EventPipeEventLevel level, + bool need_stack, + const uint8_t *metadata, + uint32_t metadata_len); + +/* + * EventPipeSession. + */ + +typedef bool +(*event_pipe_component_get_session_info_func) ( + EventPipeSessionID session_id, + EventPipeSessionInfo *instance); + +/* + * EventPipeThread. + */ + +typedef bool +(*event_pipe_component_thread_ctrl_activity_id_func)( + EventPipeActivityControlCode activity_control_code, + uint8_t *activity_id, + uint32_t activity_id_len); + +/* + * MonoComponentEventPipe function table. + */ typedef struct _MonoComponentEventPipe { MonoComponent component; - void (*ep_init) (void); - void (*ep_finish_init) (void); - void (*ep_shutdown) (void); + event_pipe_component_init_func init; + event_pipe_component_finish_init_func finish_init; + event_pipe_component_shutdown_func shutdown; + event_pipe_component_enable_func enable; + event_pipe_component_disable_func disable; + event_pipe_component_get_next_event_func get_next_event; + event_pipe_component_get_wait_handle_func get_wait_handle; + event_pipe_component_start_streaming_func start_streaming; + event_pipe_component_write_event_2_func write_event_2; + event_pipe_component_create_provider_func create_provider; + event_pipe_component_delete_provider_func delete_provider; + event_pipe_component_get_provider_func get_provider; + event_pipe_component_provider_add_event_func provider_add_event; + event_pipe_component_get_session_info_func get_session_info; + event_pipe_component_thread_ctrl_activity_id_func thread_ctrl_activity_id; } MonoComponentEventPipe; #ifdef STATIC_COMPONENTS @@ -20,4 +147,5 @@ MonoComponentEventPipe * mono_component_event_pipe_init (void); #endif +#endif /* ENABLE_PERFTRACING */ #endif /*_MONO_COMPONENT_EVENT_PIPE_H*/ diff --git a/src/mono/mono/eventpipe/ep-rt-config-mono.h b/src/mono/mono/eventpipe/ep-rt-config-mono.h index ec3ceb9f4aba01..7b08ff795f3909 100644 --- a/src/mono/mono/eventpipe/ep-rt-config-mono.h +++ b/src/mono/mono/eventpipe/ep-rt-config-mono.h @@ -1,7 +1,6 @@ #ifndef __EVENTPIPE_RT_CONFIG_MONO_H__ #define __EVENTPIPE_RT_CONFIG_MONO_H__ -#define EP_RT_MONO_USE_STATIC_RUNTIME #define EP_THREAD_INCLUDE_ACTIVITY_ID #endif /* __EVENTPIPE_RT_CONFIG_MONO_H__ */ diff --git a/src/mono/mono/eventpipe/ep-rt-mono.c b/src/mono/mono/eventpipe/ep-rt-mono.c index 3cc88969dda0f1..b6e878aae95f6e 100644 --- a/src/mono/mono/eventpipe/ep-rt-mono.c +++ b/src/mono/mono/eventpipe/ep-rt-mono.c @@ -6,297 +6,142 @@ #include #include #include -#include + #include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include #include +// EventPipe rt init state. +gboolean _ep_rt_mono_initialized; + +// EventPipe TLS key. +MonoNativeTlsKey _ep_rt_mono_thread_holder_tls_id; + +// Random byte provider. +gpointer _ep_rt_mono_rand_provider; + +// EventPipe global config lock. ep_rt_spin_lock_handle_t _ep_rt_mono_config_lock = {0}; -EventPipeMonoFuncTable _ep_rt_mono_func_table = {0}; +// OS cmd line. mono_lazy_init_t _ep_rt_mono_os_cmd_line_init = MONO_LAZY_INIT_STATUS_NOT_INITIALIZED; char *_ep_rt_mono_os_cmd_line = NULL; +// Managed cmd line. mono_lazy_init_t _ep_rt_mono_managed_cmd_line_init = MONO_LAZY_INIT_STATUS_NOT_INITIALIZED; char *_ep_rt_mono_managed_cmd_line = NULL; -#ifdef HOST_WIN32 -int64_t -ep_rt_mono_perf_counter_query (void) -{ - LARGE_INTEGER value; - if (QueryPerformanceCounter (&value)) - return (int64_t)value.QuadPart; - else - return 0; -} - -int64_t -ep_rt_mono_perf_frequency_query (void) -{ - LARGE_INTEGER value; - if (QueryPerformanceFrequency (&value)) - return (int64_t)value.QuadPart; - else - return 0; -} - -void -ep_rt_mono_system_time_get (EventPipeSystemTime *system_time) -{ - SYSTEMTIME value; - GetSystemTime (&value); +// Sample profiler. +static GArray * _ep_rt_mono_sampled_thread_callstacks = NULL; +static uint32_t _ep_rt_mono_max_sampled_thread_count = 32; - EP_ASSERT (system_time != NULL); - ep_system_time_set ( - system_time, - value.wYear, - value.wMonth, - value.wDayOfWeek, - value.wDay, - value.wHour, - value.wMinute, - value.wSecond, - value.wMilliseconds); -} - -int64_t -ep_rt_mono_system_timestamp_get (void) -{ - FILETIME value; - GetSystemTimeAsFileTime (&value); - return (int64_t)((((uint64_t)value.dwHighDateTime) << 32) | (uint64_t)value.dwLowDateTime); -} -#else -#include -#include -#include -#include - -#if HAVE_SYS_TIME_H -#include -#endif // HAVE_SYS_TIME_H - -#if HAVE_MACH_ABSOLUTE_TIME -#include -static mono_lazy_init_t _ep_rt_mono_time_base_info_init = MONO_LAZY_INIT_STATUS_NOT_INITIALIZED; -static mach_timebase_info_data_t _ep_rt_mono_time_base_info = {0}; -#endif - -#ifdef HAVE_LOCALTIME_R -#define HAVE_GMTIME_R 1 -#endif - -static const int64_t SECS_BETWEEN_1601_AND_1970_EPOCHS = 11644473600LL; -static const int64_t SECS_TO_100NS = 10000000; -static const int64_t SECS_TO_NS = 1000000000; -static const int64_t MSECS_TO_MIS = 1000; - -/* clock_gettime () is found by configure on Apple builds, but its only present from ios 10, macos 10.12, tvos 10 and watchos 3 */ -#if defined (HAVE_CLOCK_MONOTONIC) && (defined(TARGET_IOS) || defined(TARGET_OSX) || defined(TARGET_WATCHOS) || defined(TARGET_TVOS)) -#undef HAVE_CLOCK_MONOTONIC -#endif - -#ifndef HAVE_CLOCK_MONOTONIC -static const int64_t MISECS_TO_NS = 1000; -#endif - -static -void -time_base_info_lazy_init (void); - -static -int64_t -system_time_to_int64 ( - time_t sec, - long nsec); - -#if HAVE_MACH_ABSOLUTE_TIME -static -void -time_base_info_lazy_init (void) -{ - kern_return_t result = mach_timebase_info (&_ep_rt_mono_time_base_info); - if (result != KERN_SUCCESS) - memset (&_ep_rt_mono_time_base_info, 0, sizeof (_ep_rt_mono_time_base_info)); -} -#endif - -int64_t -ep_rt_mono_perf_counter_query (void) -{ -#if HAVE_MACH_ABSOLUTE_TIME - return (int64_t)mach_absolute_time (); -#elif HAVE_CLOCK_MONOTONIC - struct timespec ts; - int result = clock_gettime (CLOCK_MONOTONIC, &ts); - if (result == 0) - return ((int64_t)(ts.tv_sec) * (int64_t)(SECS_TO_NS)) + (int64_t)(ts.tv_nsec); -#else - #error "ep_rt_mono_perf_counter_get requires either mach_absolute_time () or clock_gettime (CLOCK_MONOTONIC) to be supported." -#endif - return 0; -} - -int64_t -ep_rt_mono_perf_frequency_query (void) -{ -#if HAVE_MACH_ABSOLUTE_TIME - // (numer / denom) gives you the nanoseconds per tick, so the below code - // computes the number of ticks per second. We explicitly do the multiplication - // first in order to help minimize the error that is produced by integer division. - mono_lazy_initialize (&_ep_rt_mono_time_base_info_init, time_base_info_lazy_init); - if (_ep_rt_mono_time_base_info.denom == 0 || _ep_rt_mono_time_base_info.numer == 0) - return 0; - return ((int64_t)(SECS_TO_NS) * (int64_t)(_ep_rt_mono_time_base_info.denom)) / (int64_t)(_ep_rt_mono_time_base_info.numer); -#elif HAVE_CLOCK_MONOTONIC - // clock_gettime () returns a result in terms of nanoseconds rather than a count. This - // means that we need to either always scale the result by the actual resolution (to - // get a count) or we need to say the resolution is in terms of nanoseconds. We prefer - // the latter since it allows the highest throughput and should minimize error propagated - // to the user. - return (int64_t)(SECS_TO_NS); -#else - #error "ep_rt_mono_perf_frequency_query requires either mach_absolute_time () or clock_gettime (CLOCK_MONOTONIC) to be supported." -#endif - return 0; -} - -void -ep_rt_mono_system_time_get (EventPipeSystemTime *system_time) -{ - time_t tt; -#if HAVE_GMTIME_R - struct tm ut; -#endif /* HAVE_GMTIME_R */ - struct tm *ut_ptr; - struct timeval time_val; - int timeofday_retval; - - EP_ASSERT (system_time != NULL); - - tt = time (NULL); - - /* We can't get millisecond resolution from time (), so we get it from gettimeofday () */ - timeofday_retval = gettimeofday (&time_val, NULL); - -#if HAVE_GMTIME_R - ut_ptr = &ut; - if (gmtime_r (&tt, ut_ptr) == NULL) -#else /* HAVE_GMTIME_R */ - if ((ut_ptr = gmtime (&tt)) == NULL) -#endif /* HAVE_GMTIME_R */ - g_assert_not_reached (); - - uint16_t milliseconds = 0; - if (timeofday_retval != -1) { - int old_seconds; - int new_seconds; - - milliseconds = time_val.tv_usec / MSECS_TO_MIS; - - old_seconds = ut_ptr->tm_sec; - new_seconds = time_val.tv_sec % 60; - - /* just in case we reached the next second in the interval between time () and gettimeofday () */ - if (old_seconds != new_seconds) - milliseconds = 999; - } - - ep_system_time_set ( - system_time, - 1900 + ut_ptr->tm_year, - ut_ptr->tm_mon + 1, - ut_ptr->tm_wday, - ut_ptr->tm_mday, - ut_ptr->tm_hour, - ut_ptr->tm_min, - ut_ptr->tm_sec, - milliseconds); -} - -static -inline -int64_t -system_time_to_int64 ( - time_t sec, - long nsec) -{ - return ((int64_t)sec + SECS_BETWEEN_1601_AND_1970_EPOCHS) * SECS_TO_100NS + (nsec / 100); -} +// Rundown events. +EventPipeProvider *EventPipeProviderDotNETRuntimeRundown = NULL; +EventPipeEvent *EventPipeEventMethodDCEndVerbose_V1 = NULL; +EventPipeEvent *EventPipeEventDCEndInit_V1 = NULL; +EventPipeEvent *EventPipeEventDCEndComplete_V1 = NULL; +EventPipeEvent *EventPipeEventMethodDCEndILToNativeMap = NULL; +EventPipeEvent *EventPipeEventDomainModuleDCEnd_V1 = NULL; +EventPipeEvent *EventPipeEventModuleDCEnd_V2 = NULL; +EventPipeEvent *EventPipeEventAssemblyDCEnd_V1 = NULL; +EventPipeEvent *EventPipeEventAppDomainDCEnd_V1 = NULL; +EventPipeEvent *EventPipeEventRuntimeInformationDCStart = NULL; -int64_t -ep_rt_mono_system_timestamp_get (void) -{ -#if HAVE_CLOCK_MONOTONIC - struct timespec time; - if (clock_gettime (CLOCK_REALTIME, &time) == 0) - return system_time_to_int64 (time.tv_sec, time.tv_nsec); -#else - struct timeval time; - if (gettimeofday (&time, NULL) == 0) - return system_time_to_int64 (time.tv_sec, time.tv_usec * MISECS_TO_NS); -#endif - else - return system_time_to_int64 (0, 0); -} -#endif +// Rundown types. +typedef +bool +(*ep_rt_mono_fire_method_rundown_events_func)( + const uint64_t method_id, + const uint64_t module_id, + const uint64_t method_start_address, + const uint32_t method_size, + const uint32_t method_token, + const uint32_t method_flags, + const ep_char8_t *method_namespace, + const ep_char8_t *method_name, + const ep_char8_t *method_signature, + const uint16_t count_of_map_entries, + const uint32_t *il_offsets, + const uint32_t *native_offsets, + void *user_data); -#ifndef HOST_WIN32 -#if defined(__APPLE__) -#if defined (TARGET_OSX) -G_BEGIN_DECLS -gchar ***_NSGetEnviron(void); -G_END_DECLS -#define environ (*_NSGetEnviron()) -#else -static char *_ep_rt_mono_environ[1] = { NULL }; -#define environ _ep_rt_mono_environ -#endif /* defined (TARGET_OSX) */ -#else -G_BEGIN_DECLS -extern char **environ; -G_END_DECLS -#endif /* defined (__APPLE__) */ -#endif /* !defined (HOST_WIN32) */ +typedef +bool +(*ep_rt_mono_fire_assembly_rundown_events_func)( + const uint64_t domain_id, + const uint64_t assembly_id, + const uint32_t assembly_flags, + const uint32_t binding_id, + const ep_char8_t *assembly_name, + const uint64_t module_id, + const uint32_t module_flags, + const uint32_t reserved_flags, + const ep_char8_t *module_il_path, + const ep_char8_t *module_native_path, + const uint8_t *managed_pdb_signature, + const uint32_t managed_pdb_age, + const ep_char8_t *managed_pdb_build_path, + const uint8_t *native_pdb_signature, + const uint32_t native_pdb_age, + const ep_char8_t *native_pdb_build_path, + void *user_data); -void -ep_rt_mono_os_environment_get_utf16 (ep_rt_env_array_utf16_t *env_array) -{ - EP_ASSERT (env_array != NULL); -#ifdef HOST_WIN32 - LPWSTR envs = GetEnvironmentStringsW (); - if (envs) { - LPWSTR next = envs; - while (*next) { - ep_rt_env_array_utf16_append (env_array, ep_rt_utf16_string_dup (next)); - next += ep_rt_utf16_string_len (next) + 1; - } - FreeEnvironmentStringsW (envs); - } -#else - gchar **next = NULL; - for (next = environ; *next != NULL; ++next) - ep_rt_env_array_utf16_append (env_array, ep_rt_utf8_to_utf16_string (*next, -1)); -#endif -} +typedef +bool +(*ep_rt_mono_fire_domain_rundown_events_func)( + const uint64_t domain_id, + const uint32_t domain_flags, + const ep_char8_t *domain_name, + const uint32_t domain_index, + void *user_data); + +typedef struct _EventPipeFireMethodEventsData{ + MonoDomain *domain; + uint8_t *buffer; + size_t buffer_size; + ep_rt_mono_fire_method_rundown_events_func method_events_func; +} EventPipeFireMethodEventsData; + +typedef struct _EventPipeSampleProfileData { + EventPipeStackContents stack_contents; + uint64_t thread_id; + uintptr_t thread_ip; + uint32_t payload_data; +} EventPipeSampleProfileData; // Rundown flags. #define RUNTIME_SKU_CORECLR 0x2 +#define METHOD_FLAGS_DYNAMIC_METHOD 0x1 +#define METHOD_FLAGS_GENERIC_METHOD 0x2 +#define METHOD_FLAGS_SHARED_GENERIC_METHOD 0x4 +#define METHOD_FLAGS_JITTED_METHOD 0x8 +#define METHOD_FLAGS_JITTED_HELPER_METHOD 0x10 -// Rundown events. -EventPipeProvider *EventPipeProviderDotNETRuntimeRundown = NULL; -EventPipeEvent *EventPipeEventMethodDCEndVerbose_V1 = NULL; -EventPipeEvent *EventPipeEventDCEndInit_V1 = NULL; -EventPipeEvent *EventPipeEventDCEndComplete_V1 = NULL; -EventPipeEvent *EventPipeEventMethodDCEndILToNativeMap = NULL; -EventPipeEvent *EventPipeEventDomainModuleDCEnd_V1 = NULL; -EventPipeEvent *EventPipeEventModuleDCEnd_V2 = NULL; -EventPipeEvent *EventPipeEventAssemblyDCEnd_V1 = NULL; -EventPipeEvent *EventPipeEventAppDomainDCEnd_V1 = NULL; -EventPipeEvent *EventPipeEventRuntimeInformationDCStart = NULL; +#define MODULE_FLAGS_NATIVE_MODULE 0x2 +#define MODULE_FLAGS_DYNAMIC_MODULE 0x4 +#define MODULE_FLAGS_MANIFEST_MODULE 0x8 + +#define ASSEMBLY_FLAGS_DYNAMIC_ASSEMBLY 0x2 +#define ASSEMBLY_FLAGS_NATIVE_ASSEMBLY 0x4 +#define ASSEMBLY_FLAGS_COLLECTIBLE_ASSEMBLY 0x8 + +#define DOMAIN_FLAGS_DEFAULT_DOMAIN 0x1 +#define DOMAIN_FLAGS_EXECUTABLE_DOMAIN 0x2 /* - * Forward declares of all static rundown functions. + * Forward declares of all static functions. */ static @@ -517,6 +362,53 @@ static void init_dotnet_runtime_rundown (void); +static +void +eventpipe_fire_method_events ( + MonoJitInfo *ji, + MonoMethod *method, + EventPipeFireMethodEventsData *events_data); + +static +void +eventpipe_fire_method_events_func ( + MonoJitInfo *ji, + void *user_data); + +static +void +eventpipe_fire_assembly_events ( + MonoDomain *domain, + MonoAssembly *assembly, + ep_rt_mono_fire_assembly_rundown_events_func assembly_events_func); + +static +gboolean +eventpipe_execute_rundown ( + ep_rt_mono_fire_domain_rundown_events_func domain_events_func, + ep_rt_mono_fire_assembly_rundown_events_func assembly_events_func, + ep_rt_mono_fire_method_rundown_events_func methods_events_func); + +static +gboolean +eventpipe_walk_managed_stack_for_thread_func ( + MonoStackFrameInfo *frame, + MonoContext *ctx, + void *data); + +static +gboolean +eventpipe_sample_profiler_walk_managed_stack_for_thread_func ( + MonoStackFrameInfo *frame, + MonoContext *ctx, + void *data); + +static +void +profiler_eventpipe_thread_exited ( + MonoProfiler *prof, + uintptr_t tid); + static inline uint16_t @@ -913,7 +805,203 @@ write_event_method_dc_end_verbose_v1 ( ep_raise_error_if_nok (success); - ep_write_event (EventPipeEventMethodDCEndVerbose_V1, buffer, (uint32_t)offset, activity_id, related_activity_id); + ep_write_event (EventPipeEventMethodDCEndVerbose_V1, buffer, (uint32_t)offset, activity_id, related_activity_id); + +ep_on_exit: + if (!fixed_buffer) + ep_rt_byte_array_free (buffer); + return success; + +ep_on_error: + EP_ASSERT (!success); + ep_exit_error_handler (); +} + +static +bool +write_event_module_dc_end_v2 ( + const uint64_t module_id, + const uint64_t assembly_id, + const uint32_t module_flags, + const uint32_t reserved_1, + const ep_char8_t *module_il_path, + const ep_char8_t *module_native_path, + const uint16_t clr_instance_id, + const uint8_t *managed_pdb_signature, + const uint32_t managed_pdb_age, + const ep_char8_t *managed_pdb_build_path, + const uint8_t *native_pdb_signature, + const uint32_t native_pdb_age, + const ep_char8_t *native_pdb_build_path, + const uint8_t *activity_id, + const uint8_t *related_activity_id) +{ + EP_ASSERT (EventPipeEventModuleDCEnd_V2 != NULL); + + if (!ep_event_is_enabled (EventPipeEventModuleDCEnd_V2)) + return true; + + uint8_t stack_buffer [290]; + uint8_t *buffer = stack_buffer; + size_t offset = 0; + size_t size = sizeof (stack_buffer); + bool fixed_buffer = true; + bool success = true; + + success &= write_buffer_uint64_t (&module_id, &buffer, &offset, &size, &fixed_buffer); + success &= write_buffer_uint64_t (&assembly_id, &buffer, &offset, &size, &fixed_buffer); + success &= write_buffer_uint32_t (&module_flags, &buffer, &offset, &size, &fixed_buffer); + success &= write_buffer_uint32_t (&reserved_1, &buffer, &offset, &size, &fixed_buffer); + success &= write_buffer_string_utf8_t (module_il_path, &buffer, &offset, &size, &fixed_buffer); + success &= write_buffer_string_utf8_t (module_native_path, &buffer, &offset, &size, &fixed_buffer); + success &= write_buffer_uint16_t (&clr_instance_id, &buffer, &offset, &size, &fixed_buffer); + success &= write_buffer_guid_t (managed_pdb_signature, &buffer, &offset, &size, &fixed_buffer); + success &= write_buffer_uint32_t (&managed_pdb_age, &buffer, &offset, &size, &fixed_buffer); + success &= write_buffer_string_utf8_t (managed_pdb_build_path, &buffer, &offset, &size, &fixed_buffer); + success &= write_buffer_guid_t (native_pdb_signature, &buffer, &offset, &size, &fixed_buffer); + success &= write_buffer_uint32_t (&native_pdb_age, &buffer, &offset, &size, &fixed_buffer); + success &= write_buffer_string_utf8_t (native_pdb_build_path, &buffer, &offset, &size, &fixed_buffer); + + ep_raise_error_if_nok (success); + + ep_write_event (EventPipeEventModuleDCEnd_V2, buffer, (uint32_t)offset, activity_id, related_activity_id); + +ep_on_exit: + if (!fixed_buffer) + ep_rt_byte_array_free (buffer); + return success; + +ep_on_error: + EP_ASSERT (!success); + ep_exit_error_handler (); +} + +static +bool +write_event_domain_module_dc_end_v1 ( + const uint64_t module_id, + const uint64_t assembly_id, + const uint64_t domain_id, + const uint32_t module_flags, + const uint32_t reserved_1, + const ep_char8_t *module_il_path, + const ep_char8_t *module_native_path, + const uint16_t clr_instance_id, + const uint8_t *activity_id, + const uint8_t *related_activity_id) +{ + EP_ASSERT (EventPipeEventDomainModuleDCEnd_V1 != NULL); + + if (!ep_event_is_enabled (EventPipeEventDomainModuleDCEnd_V1)) + return true; + + uint8_t stack_buffer [162]; + uint8_t *buffer = stack_buffer; + size_t offset = 0; + size_t size = sizeof (stack_buffer); + bool fixed_buffer = true; + bool success = true; + + success &= write_buffer_uint64_t (&module_id, &buffer, &offset, &size, &fixed_buffer); + success &= write_buffer_uint64_t (&assembly_id, &buffer, &offset, &size, &fixed_buffer); + success &= write_buffer_uint64_t (&domain_id, &buffer, &offset, &size, &fixed_buffer); + success &= write_buffer_uint32_t (&module_flags, &buffer, &offset, &size, &fixed_buffer); + success &= write_buffer_uint32_t (&reserved_1, &buffer, &offset, &size, &fixed_buffer); + success &= write_buffer_string_utf8_t (module_il_path, &buffer, &offset, &size, &fixed_buffer); + success &= write_buffer_string_utf8_t (module_native_path, &buffer, &offset, &size, &fixed_buffer); + success &= write_buffer_uint16_t (&clr_instance_id, &buffer, &offset, &size, &fixed_buffer); + + ep_raise_error_if_nok (success); + + ep_write_event (EventPipeEventDomainModuleDCEnd_V1, buffer, (uint32_t)offset, activity_id, related_activity_id); + +ep_on_exit: + if (!fixed_buffer) + ep_rt_byte_array_free (buffer); + return success; + +ep_on_error: + EP_ASSERT (!success); + ep_exit_error_handler (); +} + +static +bool +write_event_assembly_dc_end_v1 ( + const uint64_t assembly_id, + const uint64_t domain_id, + const uint64_t binding_id, + const uint32_t assembly_flags, + const ep_char8_t *fully_qualified_name, + const uint16_t clr_instance_id, + const uint8_t *activity_id, + const uint8_t *related_activity_id) +{ + EP_ASSERT (EventPipeEventAssemblyDCEnd_V1 != NULL); + + if (!ep_event_is_enabled (EventPipeEventAssemblyDCEnd_V1)) + return true; + + uint8_t stack_buffer [94]; + uint8_t *buffer = stack_buffer; + size_t offset = 0; + size_t size = sizeof (stack_buffer); + bool fixed_buffer = true; + bool success = true; + + success &= write_buffer_uint64_t (&assembly_id, &buffer, &offset, &size, &fixed_buffer); + success &= write_buffer_uint64_t (&domain_id, &buffer, &offset, &size, &fixed_buffer); + success &= write_buffer_uint64_t (&binding_id, &buffer, &offset, &size, &fixed_buffer); + success &= write_buffer_uint32_t (&assembly_flags, &buffer, &offset, &size, &fixed_buffer); + success &= write_buffer_string_utf8_t (fully_qualified_name, &buffer, &offset, &size, &fixed_buffer); + success &= write_buffer_uint16_t (&clr_instance_id, &buffer, &offset, &size, &fixed_buffer); + + ep_raise_error_if_nok (success); + + ep_write_event (EventPipeEventAssemblyDCEnd_V1, buffer, (uint32_t)offset, activity_id, related_activity_id); + +ep_on_exit: + if (!fixed_buffer) + ep_rt_byte_array_free (buffer); + return success; + +ep_on_error: + EP_ASSERT (!success); + ep_exit_error_handler (); +} + +static +bool +write_event_domain_dc_end_v1 ( + const uint64_t domain_id, + const uint32_t domain_flags, + const ep_char8_t *domain_name, + const uint32_t domain_index, + const uint16_t clr_instance_id, + const uint8_t *activity_id, + const uint8_t *related_activity_id) +{ + EP_ASSERT (EventPipeEventAppDomainDCEnd_V1 != NULL); + + if (!ep_event_is_enabled (EventPipeEventAppDomainDCEnd_V1)) + return true; + + uint8_t stack_buffer [82]; + uint8_t *buffer = stack_buffer; + size_t offset = 0; + size_t size = sizeof (stack_buffer); + bool fixed_buffer = true; + bool success = true; + + success &= write_buffer_uint64_t (&domain_id, &buffer, &offset, &size, &fixed_buffer); + success &= write_buffer_uint32_t (&domain_flags, &buffer, &offset, &size, &fixed_buffer); + success &= write_buffer_string_utf8_t (domain_name, &buffer, &offset, &size, &fixed_buffer); + success &= write_buffer_uint32_t (&domain_index, &buffer, &offset, &size, &fixed_buffer); + success &= write_buffer_uint16_t (&clr_instance_id, &buffer, &offset, &size, &fixed_buffer); + + ep_raise_error_if_nok (success); + + ep_write_event (EventPipeEventAppDomainDCEnd_V1, buffer, (uint32_t)offset, activity_id, related_activity_id); ep_on_exit: if (!fixed_buffer) @@ -925,362 +1013,821 @@ write_event_method_dc_end_verbose_v1 ( ep_exit_error_handler (); } +// Mapping FireEtw* CoreClr functions. +#define FireEtwRuntimeInformationDCStart(...) write_runtime_info_dc_start(__VA_ARGS__,NULL,NULL) +#define FireEtwDCEndInit_V1(...) write_event_dc_end_init_v1(__VA_ARGS__,NULL,NULL) +#define FireEtwMethodDCEndILToNativeMap(...) write_event_method_dc_end_il_to_native_map(__VA_ARGS__,NULL,NULL) +#define FireEtwMethodDCEndVerbose_V1(...) write_event_method_dc_end_verbose_v1(__VA_ARGS__,NULL,NULL) +#define FireEtwModuleDCEnd_V2(...) write_event_module_dc_end_v2(__VA_ARGS__,NULL,NULL) +#define FireEtwDomainModuleDCEnd_V1(...) write_event_domain_module_dc_end_v1(__VA_ARGS__,NULL,NULL) +#define FireEtwAssemblyDCEnd_V1(...) write_event_assembly_dc_end_v1(__VA_ARGS__,NULL,NULL) +#define FireEtwAppDomainDCEnd_V1(...) write_event_domain_dc_end_v1(__VA_ARGS__,NULL,NULL) +#define FireEtwDCEndComplete_V1(...) write_event_dc_end_complete_v1(__VA_ARGS__,NULL,NULL) + static bool -write_event_module_dc_end_v2 ( +fire_method_rundown_events_func ( + const uint64_t method_id, const uint64_t module_id, + const uint64_t method_start_address, + const uint32_t method_size, + const uint32_t method_token, + const uint32_t method_flags, + const ep_char8_t *method_namespace, + const ep_char8_t *method_name, + const ep_char8_t *method_signature, + const uint16_t count_of_map_entries, + const uint32_t *il_offsets, + const uint32_t *native_offsets, + void *user_data) +{ + FireEtwMethodDCEndILToNativeMap ( + method_id, + 0, + 0, + count_of_map_entries, + il_offsets, + native_offsets, + clr_instance_get_id ()); + + FireEtwMethodDCEndVerbose_V1 ( + method_id, + module_id, + method_start_address, + method_size, + method_token, + method_flags, + method_namespace, + method_name, + method_signature, + clr_instance_get_id ()); + + return true; +} + +static +bool +fire_assembly_rundown_events_func ( + const uint64_t domain_id, const uint64_t assembly_id, + const uint32_t assembly_flags, + const uint32_t binding_id, + const ep_char8_t *assembly_name, + const uint64_t module_id, const uint32_t module_flags, - const uint32_t reserved_1, + const uint32_t reserved_flags, const ep_char8_t *module_il_path, const ep_char8_t *module_native_path, - const uint16_t clr_instance_id, const uint8_t *managed_pdb_signature, const uint32_t managed_pdb_age, const ep_char8_t *managed_pdb_build_path, const uint8_t *native_pdb_signature, const uint32_t native_pdb_age, const ep_char8_t *native_pdb_build_path, - const uint8_t *activity_id, - const uint8_t *related_activity_id) + void *user_data) { - EP_ASSERT (EventPipeEventModuleDCEnd_V2 != NULL); + FireEtwModuleDCEnd_V2 ( + module_id, + assembly_id, + module_flags, + reserved_flags, + module_il_path, + module_native_path, + clr_instance_get_id (), + managed_pdb_signature, + managed_pdb_age, + managed_pdb_build_path, + native_pdb_signature, + native_pdb_age, + native_pdb_build_path); - if (!ep_event_is_enabled (EventPipeEventModuleDCEnd_V2)) - return true; + FireEtwDomainModuleDCEnd_V1 ( + module_id, + assembly_id, + domain_id, + module_flags, + reserved_flags, + module_il_path, + module_native_path, + clr_instance_get_id ()); - uint8_t stack_buffer [290]; - uint8_t *buffer = stack_buffer; - size_t offset = 0; - size_t size = sizeof (stack_buffer); - bool fixed_buffer = true; - bool success = true; + FireEtwAssemblyDCEnd_V1 ( + assembly_id, + domain_id, + binding_id, + assembly_flags, + assembly_name, + clr_instance_get_id ()); - success &= write_buffer_uint64_t (&module_id, &buffer, &offset, &size, &fixed_buffer); - success &= write_buffer_uint64_t (&assembly_id, &buffer, &offset, &size, &fixed_buffer); - success &= write_buffer_uint32_t (&module_flags, &buffer, &offset, &size, &fixed_buffer); - success &= write_buffer_uint32_t (&reserved_1, &buffer, &offset, &size, &fixed_buffer); - success &= write_buffer_string_utf8_t (module_il_path, &buffer, &offset, &size, &fixed_buffer); - success &= write_buffer_string_utf8_t (module_native_path, &buffer, &offset, &size, &fixed_buffer); - success &= write_buffer_uint16_t (&clr_instance_id, &buffer, &offset, &size, &fixed_buffer); - success &= write_buffer_guid_t (managed_pdb_signature, &buffer, &offset, &size, &fixed_buffer); - success &= write_buffer_uint32_t (&managed_pdb_age, &buffer, &offset, &size, &fixed_buffer); - success &= write_buffer_string_utf8_t (managed_pdb_build_path, &buffer, &offset, &size, &fixed_buffer); - success &= write_buffer_guid_t (native_pdb_signature, &buffer, &offset, &size, &fixed_buffer); - success &= write_buffer_uint32_t (&native_pdb_age, &buffer, &offset, &size, &fixed_buffer); - success &= write_buffer_string_utf8_t (native_pdb_build_path, &buffer, &offset, &size, &fixed_buffer); + return true; +} - ep_raise_error_if_nok (success); +static +bool +fire_domain_rundown_events_func ( + const uint64_t domain_id, + const uint32_t domain_flags, + const ep_char8_t *domain_name, + const uint32_t domain_index, + void *user_data) +{ + return FireEtwAppDomainDCEnd_V1 ( + domain_id, + domain_flags, + domain_name, + domain_index, + clr_instance_get_id ()); +} - ep_write_event (EventPipeEventModuleDCEnd_V2, buffer, (uint32_t)offset, activity_id, related_activity_id); +static +void +init_dotnet_runtime_rundown (void) +{ + //TODO: Add callback method to enable/disable more native events getting into EventPipe (when enabled). + EP_ASSERT (EventPipeProviderDotNETRuntimeRundown == NULL); + EventPipeProviderDotNETRuntimeRundown = ep_create_provider (ep_config_get_rundown_provider_name_utf8 (), NULL, NULL, NULL); -ep_on_exit: - if (!fixed_buffer) - ep_rt_byte_array_free (buffer); - return success; + EP_ASSERT (EventPipeEventMethodDCEndVerbose_V1 == NULL); + EventPipeEventMethodDCEndVerbose_V1 = ep_provider_add_event (EventPipeProviderDotNETRuntimeRundown, 144, 48, 1, EP_EVENT_LEVEL_INFORMATIONAL, true, NULL, 0); -ep_on_error: - EP_ASSERT (!success); - ep_exit_error_handler (); + EP_ASSERT (EventPipeEventDCEndComplete_V1 == NULL); + EventPipeEventDCEndComplete_V1 = ep_provider_add_event (EventPipeProviderDotNETRuntimeRundown, 146, 131128, 1, EP_EVENT_LEVEL_INFORMATIONAL, true, NULL, 0); + + EP_ASSERT (EventPipeEventDCEndInit_V1 == NULL); + EventPipeEventDCEndInit_V1 = ep_provider_add_event (EventPipeProviderDotNETRuntimeRundown, 148, 131128, 1, EP_EVENT_LEVEL_INFORMATIONAL, true, NULL, 0); + + EP_ASSERT (EventPipeEventMethodDCEndILToNativeMap == NULL); + EventPipeEventMethodDCEndILToNativeMap = ep_provider_add_event (EventPipeProviderDotNETRuntimeRundown, 150, 131072, 0, EP_EVENT_LEVEL_VERBOSE, true, NULL, 0); + + EP_ASSERT (EventPipeEventDomainModuleDCEnd_V1 == NULL); + EventPipeEventDomainModuleDCEnd_V1 = ep_provider_add_event (EventPipeProviderDotNETRuntimeRundown, 152, 8, 1, EP_EVENT_LEVEL_INFORMATIONAL, true, NULL, 0); + + EP_ASSERT (EventPipeEventModuleDCEnd_V2 == NULL); + EventPipeEventModuleDCEnd_V2 = ep_provider_add_event (EventPipeProviderDotNETRuntimeRundown, 154, 536870920, 2, EP_EVENT_LEVEL_INFORMATIONAL, true, NULL, 0); + + EP_ASSERT (EventPipeEventAssemblyDCEnd_V1 == NULL); + EventPipeEventAssemblyDCEnd_V1 = ep_provider_add_event (EventPipeProviderDotNETRuntimeRundown, 156, 8, 1, EP_EVENT_LEVEL_INFORMATIONAL, true, NULL, 0); + + EP_ASSERT (EventPipeEventAppDomainDCEnd_V1 == NULL); + EventPipeEventAppDomainDCEnd_V1 = ep_provider_add_event (EventPipeProviderDotNETRuntimeRundown, 158, 8, 1, EP_EVENT_LEVEL_INFORMATIONAL, true, NULL, 0); + + EP_ASSERT (EventPipeEventRuntimeInformationDCStart == NULL); + EventPipeEventRuntimeInformationDCStart = ep_provider_add_event (EventPipeProviderDotNETRuntimeRundown, 187, 0, 0, EP_EVENT_LEVEL_INFORMATIONAL, true, NULL, 0); } static -bool -write_event_domain_module_dc_end_v1 ( - const uint64_t module_id, - const uint64_t assembly_id, - const uint64_t domain_id, - const uint32_t module_flags, - const uint32_t reserved_1, - const ep_char8_t *module_il_path, - const ep_char8_t *module_native_path, - const uint16_t clr_instance_id, - const uint8_t *activity_id, - const uint8_t *related_activity_id) +void +eventpipe_fire_method_events ( + MonoJitInfo *ji, + MonoMethod *method, + EventPipeFireMethodEventsData *events_data) { - EP_ASSERT (EventPipeEventDomainModuleDCEnd_V1 != NULL); + EP_ASSERT (ji != NULL); + EP_ASSERT (events_data->domain != NULL); + EP_ASSERT (events_data->method_events_func != NULL); + + uint64_t method_id = 0; + uint64_t module_id = 0; + uint64_t method_code_start = (uint64_t)ji->code_start; + uint32_t method_code_size = (uint32_t)ji->code_size; + uint32_t method_token = 0; + uint32_t method_flags = 0; + uint8_t kind = MONO_CLASS_DEF; + char *method_namespace = NULL; + const char *method_name = NULL; + char *method_signature = NULL; + + //TODO: Optimize string formatting into functions accepting GString to reduce heap alloc. + + if (method) { + method_id = (uint64_t)method; + method_token = method->token; + + if (mono_jit_info_get_generic_sharing_context (ji)) + method_flags |= METHOD_FLAGS_SHARED_GENERIC_METHOD; + + if (method->dynamic) + method_flags |= METHOD_FLAGS_DYNAMIC_METHOD; + + if (!ji->from_aot && !ji->from_llvm) { + method_flags |= METHOD_FLAGS_JITTED_METHOD; + if (method->wrapper_type != MONO_WRAPPER_NONE) + method_flags |= METHOD_FLAGS_JITTED_HELPER_METHOD; + } - if (!ep_event_is_enabled (EventPipeEventDomainModuleDCEnd_V1)) - return true; + if (method->is_generic || method->is_inflated) + method_flags |= METHOD_FLAGS_GENERIC_METHOD; - uint8_t stack_buffer [162]; - uint8_t *buffer = stack_buffer; - size_t offset = 0; - size_t size = sizeof (stack_buffer); - bool fixed_buffer = true; - bool success = true; + method_name = method->name; + method_signature = mono_signature_full_name (method->signature); - success &= write_buffer_uint64_t (&module_id, &buffer, &offset, &size, &fixed_buffer); - success &= write_buffer_uint64_t (&assembly_id, &buffer, &offset, &size, &fixed_buffer); - success &= write_buffer_uint64_t (&domain_id, &buffer, &offset, &size, &fixed_buffer); - success &= write_buffer_uint32_t (&module_flags, &buffer, &offset, &size, &fixed_buffer); - success &= write_buffer_uint32_t (&reserved_1, &buffer, &offset, &size, &fixed_buffer); - success &= write_buffer_string_utf8_t (module_il_path, &buffer, &offset, &size, &fixed_buffer); - success &= write_buffer_string_utf8_t (module_native_path, &buffer, &offset, &size, &fixed_buffer); - success &= write_buffer_uint16_t (&clr_instance_id, &buffer, &offset, &size, &fixed_buffer); + if (method->klass) { + module_id = (uint64_t)m_class_get_image (method->klass); + kind = m_class_get_class_kind (method->klass); + if (kind == MONO_CLASS_GTD || kind == MONO_CLASS_GINST) + method_flags |= METHOD_FLAGS_GENERIC_METHOD; + method_namespace = mono_type_get_name_full (m_class_get_byval_arg (method->klass), MONO_TYPE_NAME_FORMAT_IL); + } + } + + uint16_t offset_entries = 0; + uint32_t *il_offsets = NULL; + uint32_t *native_offsets = NULL; + + MonoDebugMethodJitInfo *debug_info = method ? mono_debug_find_method (method, events_data->domain) : NULL; + if (debug_info) { + offset_entries = debug_info->num_line_numbers; + size_t needed_size = (offset_entries * sizeof (uint32_t) * 2); + if (!events_data->buffer || needed_size > events_data->buffer_size) { + g_free (events_data->buffer); + events_data->buffer_size = (size_t)(needed_size * 1.5); + events_data->buffer = g_new (uint8_t, events_data->buffer_size); + } + + if (events_data->buffer) { + il_offsets = (uint32_t*)events_data->buffer; + native_offsets = il_offsets + offset_entries; + + for (int offset_count = 0; offset_count < offset_entries; ++offset_count) { + il_offsets [offset_count] = debug_info->line_numbers [offset_count].il_offset; + native_offsets [offset_count] = debug_info->line_numbers [offset_count].native_offset; + } + } + + mono_debug_free_method_jit_info (debug_info); + } + + if (events_data->buffer && !il_offsets && !native_offsets) { + // No IL offset -> Native offset mapping available. Put all code on IL offset 0. + EP_ASSERT (events_data->buffer_size >= sizeof (uint32_t) * 2); + offset_entries = 1; + il_offsets = (uint32_t*)events_data->buffer; + native_offsets = il_offsets + offset_entries; + il_offsets [0] = 0; + native_offsets [0] = (uint32_t)ji->code_size; + } + + events_data->method_events_func ( + method_id, + module_id, + method_code_start, + method_code_size, + method_token, + method_flags, + (ep_char8_t *)method_namespace, + (ep_char8_t *)method_name, + (ep_char8_t *)method_signature, + offset_entries, + il_offsets, + native_offsets, + NULL); + + g_free (method_namespace); + g_free (method_signature); +} + +static +void +eventpipe_fire_method_events_func ( + MonoJitInfo *ji, + void *user_data) +{ + EventPipeFireMethodEventsData *events_data = (EventPipeFireMethodEventsData *)user_data; + EP_ASSERT (events_data != NULL); + + if (ji && !ji->is_trampoline && !ji->async) { + MonoMethod *method = jinfo_get_method (ji); + if (method && !m_method_is_wrapper (method)) + eventpipe_fire_method_events (ji, method, events_data); + } +} + +static +void +eventpipe_fire_assembly_events ( + MonoDomain *domain, + MonoAssembly *assembly, + ep_rt_mono_fire_assembly_rundown_events_func assembly_events_func) +{ + EP_ASSERT (domain != NULL); + EP_ASSERT (assembly != NULL); + EP_ASSERT (assembly_events_func != NULL); + + uint64_t domain_id = (uint64_t)domain; + uint64_t module_id = (uint64_t)assembly->image; + uint64_t assembly_id = (uint64_t)assembly; + + // TODO: Extract all module IL/Native paths and pdb metadata when available. + const char *module_il_path = ""; + const char *module_il_pdb_path = ""; + const char *module_native_path = ""; + const char *module_native_pdb_path = ""; + uint8_t signature [EP_GUID_SIZE] = { 0 }; + uint32_t module_il_pdb_age = 0; + uint32_t module_native_pdb_age = 0; + + uint32_t reserved_flags = 0; + uint64_t binding_id = 0; + + // Native methods are part of JIT table and already emitted. + // TODO: FireEtwMethodDCEndVerbose_V1_or_V2 for all native methods in module as well? + + // Netcore has a 1:1 between assemblies and modules, so its always a manifest module. + uint32_t module_flags = MODULE_FLAGS_MANIFEST_MODULE; + if (assembly->image) { + if (assembly->image->dynamic) + module_flags |= MODULE_FLAGS_DYNAMIC_MODULE; + if (assembly->image->aot_module) + module_flags |= MODULE_FLAGS_NATIVE_MODULE; + + module_il_path = assembly->image->filename ? assembly->image->filename : ""; + } + + uint32_t assembly_flags = 0; + if (assembly->dynamic) + assembly_flags |= ASSEMBLY_FLAGS_DYNAMIC_ASSEMBLY; + + if (assembly->image && assembly->image->aot_module) { + assembly_flags |= ASSEMBLY_FLAGS_NATIVE_ASSEMBLY; + } + + char *assembly_name = mono_stringify_assembly_name (&assembly->aname); + + assembly_events_func ( + domain_id, + assembly_id, + assembly_flags, + binding_id, + (const ep_char8_t*)assembly_name, + module_id, + module_flags, + reserved_flags, + (const ep_char8_t *)module_il_path, + (const ep_char8_t *)module_native_path, + signature, + module_il_pdb_age, + (const ep_char8_t *)module_il_pdb_path, + signature, + module_native_pdb_age, + (const ep_char8_t *)module_native_pdb_path, + NULL); + + g_free (assembly_name); +} - ep_raise_error_if_nok (success); +static +gboolean +eventpipe_execute_rundown ( + ep_rt_mono_fire_domain_rundown_events_func domain_events_func, + ep_rt_mono_fire_assembly_rundown_events_func assembly_events_func, + ep_rt_mono_fire_method_rundown_events_func method_events_func) +{ + EP_ASSERT (domain_events_func != NULL); + EP_ASSERT (assembly_events_func != NULL); + EP_ASSERT (method_events_func != NULL); + + // Under netcore we only have root domain. + MonoDomain *root_domain = mono_get_root_domain (); + if (root_domain) { + uint64_t domain_id = (uint64_t)root_domain; + + // Iterate all functions in use (both JIT and AOT). + EventPipeFireMethodEventsData events_data; + events_data.domain = root_domain; + events_data.buffer_size = 1024 * sizeof(uint32_t); + events_data.buffer = g_new (uint8_t, events_data.buffer_size); + events_data.method_events_func = method_events_func; + mono_jit_info_table_foreach_internal (root_domain, eventpipe_fire_method_events_func, &events_data); + g_free (events_data.buffer); + + // Iterate all assemblies in domain. + GPtrArray *assemblies = mono_domain_get_assemblies (root_domain); + if (assemblies) { + for (int i = 0; i < assemblies->len; ++i) { + MonoAssembly *assembly = (MonoAssembly *)g_ptr_array_index (assemblies, i); + if (assembly) + eventpipe_fire_assembly_events (root_domain, assembly, assembly_events_func); + } + g_ptr_array_free (assemblies, TRUE); + } - ep_write_event (EventPipeEventDomainModuleDCEnd_V1, buffer, (uint32_t)offset, activity_id, related_activity_id); + uint32_t domain_flags = DOMAIN_FLAGS_DEFAULT_DOMAIN | DOMAIN_FLAGS_EXECUTABLE_DOMAIN; + const char *domain_name = root_domain->friendly_name ? root_domain->friendly_name : ""; + uint32_t domain_index = 1; -ep_on_exit: - if (!fixed_buffer) - ep_rt_byte_array_free (buffer); - return success; + domain_events_func ( + domain_id, + domain_flags, + (const ep_char8_t *)domain_name, + domain_index, + NULL); + } -ep_on_error: - EP_ASSERT (!success); - ep_exit_error_handler (); + return TRUE; } static -bool -write_event_assembly_dc_end_v1 ( - const uint64_t assembly_id, - const uint64_t domain_id, - const uint64_t binding_id, - const uint32_t assembly_flags, - const ep_char8_t *fully_qualified_name, - const uint16_t clr_instance_id, - const uint8_t *activity_id, - const uint8_t *related_activity_id) +gboolean +eventpipe_walk_managed_stack_for_thread_func ( + MonoStackFrameInfo *frame, + MonoContext *ctx, + void *data) { - EP_ASSERT (EventPipeEventAssemblyDCEnd_V1 != NULL); + EP_ASSERT (frame != NULL); + EP_ASSERT (data != NULL); + + switch (frame->type) { + case FRAME_TYPE_DEBUGGER_INVOKE: + case FRAME_TYPE_MANAGED_TO_NATIVE: + case FRAME_TYPE_TRAMPOLINE: + case FRAME_TYPE_INTERP_TO_MANAGED: + case FRAME_TYPE_INTERP_TO_MANAGED_WITH_CTX: + return FALSE; + case FRAME_TYPE_MANAGED: + case FRAME_TYPE_INTERP: + if (!frame->ji) + return FALSE; + MonoMethod *method = frame->ji->async ? NULL : frame->actual_method; + if (method && !m_method_is_wrapper (method)) + ep_stack_contents_append ((EventPipeStackContents *)data, (uintptr_t)((uint8_t*)frame->ji->code_start + frame->native_offset), method); + return ep_stack_contents_get_length ((EventPipeStackContents *)data) >= EP_MAX_STACK_DEPTH; + default: + EP_UNREACHABLE ("eventpipe_walk_managed_stack_for_thread_func"); + return FALSE; + } +} - if (!ep_event_is_enabled (EventPipeEventAssemblyDCEnd_V1)) - return true; +static +gboolean +eventpipe_sample_profiler_walk_managed_stack_for_thread_func ( + MonoStackFrameInfo *frame, + MonoContext *ctx, + void *data) +{ + EP_ASSERT (frame != NULL); + EP_ASSERT (data != NULL); - uint8_t stack_buffer [94]; - uint8_t *buffer = stack_buffer; - size_t offset = 0; - size_t size = sizeof (stack_buffer); - bool fixed_buffer = true; - bool success = true; + EventPipeSampleProfileData *sample_data = (EventPipeSampleProfileData *)data; - success &= write_buffer_uint64_t (&assembly_id, &buffer, &offset, &size, &fixed_buffer); - success &= write_buffer_uint64_t (&domain_id, &buffer, &offset, &size, &fixed_buffer); - success &= write_buffer_uint64_t (&binding_id, &buffer, &offset, &size, &fixed_buffer); - success &= write_buffer_uint32_t (&assembly_flags, &buffer, &offset, &size, &fixed_buffer); - success &= write_buffer_string_utf8_t (fully_qualified_name, &buffer, &offset, &size, &fixed_buffer); - success &= write_buffer_uint16_t (&clr_instance_id, &buffer, &offset, &size, &fixed_buffer); + if (sample_data->payload_data == EP_SAMPLE_PROFILER_SAMPLE_TYPE_ERROR) { + if (frame->type == FRAME_TYPE_MANAGED_TO_NATIVE) + sample_data->payload_data = EP_SAMPLE_PROFILER_SAMPLE_TYPE_EXTERNAL; + else + sample_data->payload_data = EP_SAMPLE_PROFILER_SAMPLE_TYPE_MANAGED; + } - ep_raise_error_if_nok (success); + return eventpipe_walk_managed_stack_for_thread_func (frame, ctx, &sample_data->stack_contents); +} - ep_write_event (EventPipeEventAssemblyDCEnd_V1, buffer, (uint32_t)offset, activity_id, related_activity_id); +static +void +profiler_eventpipe_thread_exited ( + MonoProfiler *prof, + uintptr_t tid) +{ + if (_ep_rt_mono_initialized) { + EventPipeThreadHolder *thread_holder = (EventPipeThreadHolder *)mono_native_tls_get_value (_ep_rt_mono_thread_holder_tls_id); + if (thread_holder) + thread_holder_free_func (thread_holder); + mono_native_tls_set_value (_ep_rt_mono_thread_holder_tls_id, NULL); + } +} -ep_on_exit: - if (!fixed_buffer) - ep_rt_byte_array_free (buffer); - return success; +void +ep_rt_mono_init (void) +{ + mono_native_tls_alloc (&_ep_rt_mono_thread_holder_tls_id, NULL); -ep_on_error: - EP_ASSERT (!success); - ep_exit_error_handler (); + mono_100ns_ticks (); + mono_rand_open (); + _ep_rt_mono_rand_provider = mono_rand_init (NULL, 0); + + _ep_rt_mono_initialized = TRUE; + + MonoProfilerHandle profiler = mono_profiler_create (NULL); + mono_profiler_set_thread_stopped_callback (profiler, profiler_eventpipe_thread_exited); } -static -bool -write_event_domain_dc_end_v1 ( - const uint64_t domain_id, - const uint32_t domain_flags, - const ep_char8_t *domain_name, - const uint32_t domain_index, - const uint16_t clr_instance_id, - const uint8_t *activity_id, - const uint8_t *related_activity_id) +void +ep_rt_mono_fini (void) { - EP_ASSERT (EventPipeEventAppDomainDCEnd_V1 != NULL); + if (_ep_rt_mono_sampled_thread_callstacks) + g_array_free (_ep_rt_mono_sampled_thread_callstacks, TRUE); - if (!ep_event_is_enabled (EventPipeEventAppDomainDCEnd_V1)) - return true; + if (_ep_rt_mono_initialized) + mono_rand_close (_ep_rt_mono_rand_provider); - uint8_t stack_buffer [82]; - uint8_t *buffer = stack_buffer; - size_t offset = 0; - size_t size = sizeof (stack_buffer); - bool fixed_buffer = true; - bool success = true; + _ep_rt_mono_sampled_thread_callstacks = NULL; + _ep_rt_mono_rand_provider = NULL; + _ep_rt_mono_initialized = FALSE; +} - success &= write_buffer_uint64_t (&domain_id, &buffer, &offset, &size, &fixed_buffer); - success &= write_buffer_uint32_t (&domain_flags, &buffer, &offset, &size, &fixed_buffer); - success &= write_buffer_string_utf8_t (domain_name, &buffer, &offset, &size, &fixed_buffer); - success &= write_buffer_uint32_t (&domain_index, &buffer, &offset, &size, &fixed_buffer); - success &= write_buffer_uint16_t (&clr_instance_id, &buffer, &offset, &size, &fixed_buffer); +bool +ep_rt_mono_rand_try_get_bytes ( + uint8_t *buffer, + size_t buffer_size) +{ + EP_ASSERT (_ep_rt_mono_rand_provider != NULL); - ep_raise_error_if_nok (success); + ERROR_DECL (error); + return mono_rand_try_get_bytes (&_ep_rt_mono_rand_provider, (guchar *)buffer, (gssize)buffer_size, error); +} - ep_write_event (EventPipeEventAppDomainDCEnd_V1, buffer, (uint32_t)offset, activity_id, related_activity_id); +EventPipeThread * +ep_rt_mono_thread_get_or_create (void) +{ + EventPipeThreadHolder *thread_holder = (EventPipeThreadHolder *)mono_native_tls_get_value (_ep_rt_mono_thread_holder_tls_id); + if (!thread_holder) { + thread_holder = thread_holder_alloc_func (); + mono_native_tls_set_value (_ep_rt_mono_thread_holder_tls_id, thread_holder); + } + return ep_thread_holder_get_thread (thread_holder); +} -ep_on_exit: - if (!fixed_buffer) - ep_rt_byte_array_free (buffer); - return success; +void * +ep_rt_mono_thread_attach (bool background_thread) +{ + MonoThread *thread = NULL; + + // NOTE, under netcore, only root domain exists. + if (!mono_thread_current ()) { + thread = mono_thread_internal_attach (mono_get_root_domain ()); + if (background_thread && thread) { + mono_thread_set_state (thread, ThreadState_Background); + mono_thread_info_set_flags (MONO_THREAD_INFO_FLAGS_NO_SAMPLE); + } + } -ep_on_error: - EP_ASSERT (!success); - ep_exit_error_handler (); + return thread; } -// Mapping FireEtw* CoreClr functions. -#define FireEtwRuntimeInformationDCStart(...) write_runtime_info_dc_start(__VA_ARGS__,NULL,NULL) -#define FireEtwDCEndInit_V1(...) write_event_dc_end_init_v1(__VA_ARGS__,NULL,NULL) -#define FireEtwMethodDCEndILToNativeMap(...) write_event_method_dc_end_il_to_native_map(__VA_ARGS__,NULL,NULL) -#define FireEtwMethodDCEndVerbose_V1(...) write_event_method_dc_end_verbose_v1(__VA_ARGS__,NULL,NULL) -#define FireEtwModuleDCEnd_V2(...) write_event_module_dc_end_v2(__VA_ARGS__,NULL,NULL) -#define FireEtwDomainModuleDCEnd_V1(...) write_event_domain_module_dc_end_v1(__VA_ARGS__,NULL,NULL) -#define FireEtwAssemblyDCEnd_V1(...) write_event_assembly_dc_end_v1(__VA_ARGS__,NULL,NULL) -#define FireEtwAppDomainDCEnd_V1(...) write_event_domain_dc_end_v1(__VA_ARGS__,NULL,NULL) -#define FireEtwDCEndComplete_V1(...) write_event_dc_end_complete_v1(__VA_ARGS__,NULL,NULL) +void +ep_rt_mono_thread_detach (void) +{ + MonoThread *current_thread = mono_thread_current (); + if (current_thread) + mono_thread_internal_detach (current_thread); +} -static -bool -fire_method_rundown_events_func ( - const uint64_t method_id, - const uint64_t module_id, - const uint64_t method_start_address, - const uint32_t method_size, - const uint32_t method_token, - const uint32_t method_flags, - const ep_char8_t *method_namespace, - const ep_char8_t *method_name, - const ep_char8_t *method_signature, - const uint16_t count_of_map_entries, - const uint32_t *il_offsets, - const uint32_t *native_offsets, - void *user_data) +#ifdef HOST_WIN32 +int64_t +ep_rt_mono_perf_counter_query (void) { - FireEtwMethodDCEndILToNativeMap ( - method_id, - 0, - 0, - count_of_map_entries, - il_offsets, - native_offsets, - clr_instance_get_id ()); + LARGE_INTEGER value; + if (QueryPerformanceCounter (&value)) + return (int64_t)value.QuadPart; + else + return 0; +} - FireEtwMethodDCEndVerbose_V1 ( - method_id, - module_id, - method_start_address, - method_size, - method_token, - method_flags, - method_namespace, - method_name, - method_signature, - clr_instance_get_id ()); +int64_t +ep_rt_mono_perf_frequency_query (void) +{ + LARGE_INTEGER value; + if (QueryPerformanceFrequency (&value)) + return (int64_t)value.QuadPart; + else + return 0; +} - return true; +void +ep_rt_mono_system_time_get (EventPipeSystemTime *system_time) +{ + SYSTEMTIME value; + GetSystemTime (&value); + + EP_ASSERT (system_time != NULL); + ep_system_time_set ( + system_time, + value.wYear, + value.wMonth, + value.wDayOfWeek, + value.wDay, + value.wHour, + value.wMinute, + value.wSecond, + value.wMilliseconds); } -static -bool -fire_assembly_rundown_events_func ( - const uint64_t domain_id, - const uint64_t assembly_id, - const uint32_t assembly_flags, - const uint32_t binding_id, - const ep_char8_t *assembly_name, - const uint64_t module_id, - const uint32_t module_flags, - const uint32_t reserved_flags, - const ep_char8_t *module_il_path, - const ep_char8_t *module_native_path, - const uint8_t *managed_pdb_signature, - const uint32_t managed_pdb_age, - const ep_char8_t *managed_pdb_build_path, - const uint8_t *native_pdb_signature, - const uint32_t native_pdb_age, - const ep_char8_t *native_pdb_build_path, - void *user_data) +int64_t +ep_rt_mono_system_timestamp_get (void) { - FireEtwModuleDCEnd_V2 ( - module_id, - assembly_id, - module_flags, - reserved_flags, - module_il_path, - module_native_path, - clr_instance_get_id (), - managed_pdb_signature, - managed_pdb_age, - managed_pdb_build_path, - native_pdb_signature, - native_pdb_age, - native_pdb_build_path); + FILETIME value; + GetSystemTimeAsFileTime (&value); + return (int64_t)((((uint64_t)value.dwHighDateTime) << 32) | (uint64_t)value.dwLowDateTime); +} +#else +#include +#include +#include +#include + +#if HAVE_SYS_TIME_H +#include +#endif // HAVE_SYS_TIME_H + +#if HAVE_MACH_ABSOLUTE_TIME +#include +static mono_lazy_init_t _ep_rt_mono_time_base_info_init = MONO_LAZY_INIT_STATUS_NOT_INITIALIZED; +static mach_timebase_info_data_t _ep_rt_mono_time_base_info = {0}; +#endif + +#ifdef HAVE_LOCALTIME_R +#define HAVE_GMTIME_R 1 +#endif + +static const int64_t SECS_BETWEEN_1601_AND_1970_EPOCHS = 11644473600LL; +static const int64_t SECS_TO_100NS = 10000000; +static const int64_t SECS_TO_NS = 1000000000; +static const int64_t MSECS_TO_MIS = 1000; + +/* clock_gettime () is found by configure on Apple builds, but its only present from ios 10, macos 10.12, tvos 10 and watchos 3 */ +#if defined (HAVE_CLOCK_MONOTONIC) && (defined(TARGET_IOS) || defined(TARGET_OSX) || defined(TARGET_WATCHOS) || defined(TARGET_TVOS)) +#undef HAVE_CLOCK_MONOTONIC +#endif - FireEtwDomainModuleDCEnd_V1 ( - module_id, - assembly_id, - domain_id, - module_flags, - reserved_flags, - module_il_path, - module_native_path, - clr_instance_get_id ()); +#ifndef HAVE_CLOCK_MONOTONIC +static const int64_t MISECS_TO_NS = 1000; +#endif - FireEtwAssemblyDCEnd_V1 ( - assembly_id, - domain_id, - binding_id, - assembly_flags, - assembly_name, - clr_instance_get_id ()); +static +void +time_base_info_lazy_init (void); - return true; -} +static +int64_t +system_time_to_int64 ( + time_t sec, + long nsec); +#if HAVE_MACH_ABSOLUTE_TIME static -bool -fire_domain_rundown_events_func ( - const uint64_t domain_id, - const uint32_t domain_flags, - const ep_char8_t *domain_name, - const uint32_t domain_index, - void *user_data) +void +time_base_info_lazy_init (void) { - return FireEtwAppDomainDCEnd_V1 ( - domain_id, - domain_flags, - domain_name, - domain_index, - clr_instance_get_id ()); + kern_return_t result = mach_timebase_info (&_ep_rt_mono_time_base_info); + if (result != KERN_SUCCESS) + memset (&_ep_rt_mono_time_base_info, 0, sizeof (_ep_rt_mono_time_base_info)); +} +#endif + +int64_t +ep_rt_mono_perf_counter_query (void) +{ +#if HAVE_MACH_ABSOLUTE_TIME + return (int64_t)mach_absolute_time (); +#elif HAVE_CLOCK_MONOTONIC + struct timespec ts; + int result = clock_gettime (CLOCK_MONOTONIC, &ts); + if (result == 0) + return ((int64_t)(ts.tv_sec) * (int64_t)(SECS_TO_NS)) + (int64_t)(ts.tv_nsec); +#else + #error "ep_rt_mono_perf_counter_get requires either mach_absolute_time () or clock_gettime (CLOCK_MONOTONIC) to be supported." +#endif + return 0; +} + +int64_t +ep_rt_mono_perf_frequency_query (void) +{ +#if HAVE_MACH_ABSOLUTE_TIME + // (numer / denom) gives you the nanoseconds per tick, so the below code + // computes the number of ticks per second. We explicitly do the multiplication + // first in order to help minimize the error that is produced by integer division. + mono_lazy_initialize (&_ep_rt_mono_time_base_info_init, time_base_info_lazy_init); + if (_ep_rt_mono_time_base_info.denom == 0 || _ep_rt_mono_time_base_info.numer == 0) + return 0; + return ((int64_t)(SECS_TO_NS) * (int64_t)(_ep_rt_mono_time_base_info.denom)) / (int64_t)(_ep_rt_mono_time_base_info.numer); +#elif HAVE_CLOCK_MONOTONIC + // clock_gettime () returns a result in terms of nanoseconds rather than a count. This + // means that we need to either always scale the result by the actual resolution (to + // get a count) or we need to say the resolution is in terms of nanoseconds. We prefer + // the latter since it allows the highest throughput and should minimize error propagated + // to the user. + return (int64_t)(SECS_TO_NS); +#else + #error "ep_rt_mono_perf_frequency_query requires either mach_absolute_time () or clock_gettime (CLOCK_MONOTONIC) to be supported." +#endif + return 0; } -static void -init_dotnet_runtime_rundown (void) +ep_rt_mono_system_time_get (EventPipeSystemTime *system_time) { - //TODO: Add callback method to enable/disable more native events getting into EventPipe (when enabled). - EP_ASSERT (EventPipeProviderDotNETRuntimeRundown == NULL); - EventPipeProviderDotNETRuntimeRundown = ep_create_provider (ep_config_get_rundown_provider_name_utf8 (), NULL, NULL, NULL); + time_t tt; +#if HAVE_GMTIME_R + struct tm ut; +#endif /* HAVE_GMTIME_R */ + struct tm *ut_ptr; + struct timeval time_val; + int timeofday_retval; - EP_ASSERT (EventPipeEventMethodDCEndVerbose_V1 == NULL); - EventPipeEventMethodDCEndVerbose_V1 = ep_provider_add_event (EventPipeProviderDotNETRuntimeRundown, 144, 48, 1, EP_EVENT_LEVEL_INFORMATIONAL, true, NULL, 0); + EP_ASSERT (system_time != NULL); - EP_ASSERT (EventPipeEventDCEndComplete_V1 == NULL); - EventPipeEventDCEndComplete_V1 = ep_provider_add_event (EventPipeProviderDotNETRuntimeRundown, 146, 131128, 1, EP_EVENT_LEVEL_INFORMATIONAL, true, NULL, 0); + tt = time (NULL); - EP_ASSERT (EventPipeEventDCEndInit_V1 == NULL); - EventPipeEventDCEndInit_V1 = ep_provider_add_event (EventPipeProviderDotNETRuntimeRundown, 148, 131128, 1, EP_EVENT_LEVEL_INFORMATIONAL, true, NULL, 0); + /* We can't get millisecond resolution from time (), so we get it from gettimeofday () */ + timeofday_retval = gettimeofday (&time_val, NULL); - EP_ASSERT (EventPipeEventMethodDCEndILToNativeMap == NULL); - EventPipeEventMethodDCEndILToNativeMap = ep_provider_add_event (EventPipeProviderDotNETRuntimeRundown, 150, 131072, 0, EP_EVENT_LEVEL_VERBOSE, true, NULL, 0); +#if HAVE_GMTIME_R + ut_ptr = &ut; + if (gmtime_r (&tt, ut_ptr) == NULL) +#else /* HAVE_GMTIME_R */ + if ((ut_ptr = gmtime (&tt)) == NULL) +#endif /* HAVE_GMTIME_R */ + EP_UNREACHABLE (); - EP_ASSERT (EventPipeEventDomainModuleDCEnd_V1 == NULL); - EventPipeEventDomainModuleDCEnd_V1 = ep_provider_add_event (EventPipeProviderDotNETRuntimeRundown, 152, 8, 1, EP_EVENT_LEVEL_INFORMATIONAL, true, NULL, 0); + uint16_t milliseconds = 0; + if (timeofday_retval != -1) { + int old_seconds; + int new_seconds; - EP_ASSERT (EventPipeEventModuleDCEnd_V2 == NULL); - EventPipeEventModuleDCEnd_V2 = ep_provider_add_event (EventPipeProviderDotNETRuntimeRundown, 154, 536870920, 2, EP_EVENT_LEVEL_INFORMATIONAL, true, NULL, 0); + milliseconds = time_val.tv_usec / MSECS_TO_MIS; - EP_ASSERT (EventPipeEventAssemblyDCEnd_V1 == NULL); - EventPipeEventAssemblyDCEnd_V1 = ep_provider_add_event (EventPipeProviderDotNETRuntimeRundown, 156, 8, 1, EP_EVENT_LEVEL_INFORMATIONAL, true, NULL, 0); + old_seconds = ut_ptr->tm_sec; + new_seconds = time_val.tv_sec % 60; - EP_ASSERT (EventPipeEventAppDomainDCEnd_V1 == NULL); - EventPipeEventAppDomainDCEnd_V1 = ep_provider_add_event (EventPipeProviderDotNETRuntimeRundown, 158, 8, 1, EP_EVENT_LEVEL_INFORMATIONAL, true, NULL, 0); + /* just in case we reached the next second in the interval between time () and gettimeofday () */ + if (old_seconds != new_seconds) + milliseconds = 999; + } - EP_ASSERT (EventPipeEventRuntimeInformationDCStart == NULL); - EventPipeEventRuntimeInformationDCStart = ep_provider_add_event (EventPipeProviderDotNETRuntimeRundown, 187, 0, 0, EP_EVENT_LEVEL_INFORMATIONAL, true, NULL, 0); + ep_system_time_set ( + system_time, + 1900 + ut_ptr->tm_year, + ut_ptr->tm_mon + 1, + ut_ptr->tm_wday, + ut_ptr->tm_mday, + ut_ptr->tm_hour, + ut_ptr->tm_min, + ut_ptr->tm_sec, + milliseconds); +} + +static +inline +int64_t +system_time_to_int64 ( + time_t sec, + long nsec) +{ + return ((int64_t)sec + SECS_BETWEEN_1601_AND_1970_EPOCHS) * SECS_TO_100NS + (nsec / 100); +} + +int64_t +ep_rt_mono_system_timestamp_get (void) +{ +#if HAVE_CLOCK_MONOTONIC + struct timespec time; + if (clock_gettime (CLOCK_REALTIME, &time) == 0) + return system_time_to_int64 (time.tv_sec, time.tv_nsec); +#else + struct timeval time; + if (gettimeofday (&time, NULL) == 0) + return system_time_to_int64 (time.tv_sec, time.tv_usec * MISECS_TO_NS); +#endif + else + return system_time_to_int64 (0, 0); +} +#endif + +#ifndef HOST_WIN32 +#if defined(__APPLE__) +#if defined (TARGET_OSX) +G_BEGIN_DECLS +gchar ***_NSGetEnviron(void); +G_END_DECLS +#define environ (*_NSGetEnviron()) +#else +static char *_ep_rt_mono_environ[1] = { NULL }; +#define environ _ep_rt_mono_environ +#endif /* defined (TARGET_OSX) */ +#else +G_BEGIN_DECLS +extern char **environ; +G_END_DECLS +#endif /* defined (__APPLE__) */ +#endif /* !defined (HOST_WIN32) */ + +void +ep_rt_mono_os_environment_get_utf16 (ep_rt_env_array_utf16_t *env_array) +{ + EP_ASSERT (env_array != NULL); +#ifdef HOST_WIN32 + LPWSTR envs = GetEnvironmentStringsW (); + if (envs) { + LPWSTR next = envs; + while (*next) { + ep_rt_env_array_utf16_append (env_array, ep_rt_utf16_string_dup (next)); + next += ep_rt_utf16_string_len (next) + 1; + } + FreeEnvironmentStringsW (envs); + } +#else + gchar **next = NULL; + for (next = environ; *next != NULL; ++next) + ep_rt_env_array_utf16_append (env_array, ep_rt_utf8_to_utf16_string (*next, -1)); +#endif } void @@ -1299,6 +1846,121 @@ ep_rt_mono_fini_providers_and_events (void) // ep_delete_provider (EventPipeProviderDotNETRuntimeRundown); } +bool +ep_rt_mono_walk_managed_stack_for_thread ( + ep_rt_thread_handle_t thread, + EventPipeStackContents *stack_contents) +{ + EP_ASSERT (thread != NULL && stack_contents != NULL); + + if (thread == ep_rt_thread_get_handle ()) + mono_get_eh_callbacks ()->mono_walk_stack_with_ctx (eventpipe_walk_managed_stack_for_thread_func, NULL, MONO_UNWIND_SIGNAL_SAFE, stack_contents); + else + mono_get_eh_callbacks ()->mono_walk_stack_with_state (eventpipe_walk_managed_stack_for_thread_func, mono_thread_info_get_suspend_state (thread), MONO_UNWIND_SIGNAL_SAFE, stack_contents); + + return true; +} + +bool +ep_rt_mono_method_get_simple_assembly_name ( + ep_rt_method_desc_t *method, + ep_char8_t *name, + size_t name_len) +{ + EP_ASSERT (method != NULL); + EP_ASSERT (name != NULL); + + MonoClass *method_class = mono_method_get_class (method); + MonoImage *method_image = method_class ? mono_class_get_image (method_class) : NULL; + const ep_char8_t *assembly_name = method_image ? mono_image_get_name (method_image) : NULL; + + if (!assembly_name) + return false; + + g_strlcpy (name, assembly_name, name_len); + return true; +} + +bool +ep_rt_mono_method_get_full_name ( + ep_rt_method_desc_t *method, + ep_char8_t *name, + size_t name_len) +{ + EP_ASSERT (method != NULL); + EP_ASSERT (name != NULL); + + char *full_method_name = mono_method_get_name_full (method, TRUE, TRUE, MONO_TYPE_NAME_FORMAT_IL); + if (!full_method_name) + return false; + + g_strlcpy (name, full_method_name, name_len); + + g_free (full_method_name); + return true; +} + +bool +ep_rt_mono_sample_profiler_write_sampling_event_for_threads ( + ep_rt_thread_handle_t sampling_thread, + EventPipeEvent *sampling_event) +{ + // Follows CoreClr implementation of sample profiler. Generic invasive/expensive way to do CPU sample profiling relying on STW and stackwalks. + // TODO: Investigate alternatives on platforms supporting Signals/SuspendThread (see Mono profiler) or CPU PMU's (see ETW/perf_event_open). + + // Sample profiler only runs on one thread, no need to synchorinize. + if (!_ep_rt_mono_sampled_thread_callstacks) + _ep_rt_mono_sampled_thread_callstacks = g_array_sized_new (FALSE, FALSE, sizeof (EventPipeSampleProfileData), _ep_rt_mono_max_sampled_thread_count); + + // Make sure there is room based on previous max number of sampled threads. + // NOTE, there is a chance there are more threads than max, if that's the case we will + // miss those threads in this sample, but will be included in next when max has been adjusted. + g_array_set_size (_ep_rt_mono_sampled_thread_callstacks, _ep_rt_mono_max_sampled_thread_count); + + uint32_t filtered_thread_count = 0; + uint32_t sampled_thread_count = 0; + + mono_stop_world (MONO_THREAD_INFO_FLAGS_NO_GC | MONO_THREAD_INFO_FLAGS_NO_SAMPLE); + + // Record all info needed in sample events while runtime is suspended, must be async safe. + FOREACH_THREAD_SAFE_EXCLUDE (thread_info, MONO_THREAD_INFO_FLAGS_NO_GC | MONO_THREAD_INFO_FLAGS_NO_SAMPLE) { + if (!mono_thread_info_is_running (thread_info)) { + MonoThreadUnwindState *thread_state = mono_thread_info_get_suspend_state (thread_info); + if (thread_state->valid) { + if (sampled_thread_count < _ep_rt_mono_max_sampled_thread_count) { + EventPipeSampleProfileData *data = &g_array_index (_ep_rt_mono_sampled_thread_callstacks, EventPipeSampleProfileData, sampled_thread_count); + data->thread_id = ep_rt_thread_id_t_to_uint64_t (mono_thread_info_get_tid (thread_info)); + data->thread_ip = (uintptr_t)MONO_CONTEXT_GET_IP (&thread_state->ctx); + data->payload_data = EP_SAMPLE_PROFILER_SAMPLE_TYPE_ERROR; + ep_stack_contents_reset (&data->stack_contents); + mono_get_eh_callbacks ()->mono_walk_stack_with_state (eventpipe_sample_profiler_walk_managed_stack_for_thread_func, thread_state, MONO_UNWIND_SIGNAL_SAFE, data); + sampled_thread_count++; + } + } + } + filtered_thread_count++; + } FOREACH_THREAD_SAFE_END + + mono_restart_world (MONO_THREAD_INFO_FLAGS_NO_GC | MONO_THREAD_INFO_FLAGS_NO_SAMPLE); + + // Fire sample event for threads. Must be done after runtime is resumed since it's not async safe. + // Since we can't keep thread info around after runtime as been suspended, use an empty + // adapter instance and only set recorded tid as parameter inside adapter. + THREAD_INFO_TYPE adapter = { 0 }; + for (uint32_t i = 0; i < sampled_thread_count; ++i) { + EventPipeSampleProfileData *data = &g_array_index (_ep_rt_mono_sampled_thread_callstacks, EventPipeSampleProfileData, i); + if (data->payload_data != EP_SAMPLE_PROFILER_SAMPLE_TYPE_ERROR && ep_stack_contents_get_length(&data->stack_contents) > 0) { + mono_thread_info_set_tid (&adapter, ep_rt_uint64_t_to_thread_id_t (data->thread_id)); + ep_write_sample_profile_event (sampling_thread, sampling_event, &adapter, &data->stack_contents, (uint8_t *)&data->payload_data, sizeof (data->payload_data)); + } + } + + // Current thread count will be our next maximum sampled threads. + _ep_rt_mono_max_sampled_thread_count = filtered_thread_count; + + return true; +} + void ep_rt_mono_execute_rundown (void) { @@ -1331,8 +1993,7 @@ ep_rt_mono_execute_rundown (void) FireEtwDCEndInit_V1 (clr_instance_get_id ()); - EP_ASSERT (_ep_rt_mono_func_table.ep_rt_mono_execute_rundown != NULL); - _ep_rt_mono_func_table.ep_rt_mono_execute_rundown ( + eventpipe_execute_rundown ( fire_domain_rundown_events_func, fire_assembly_rundown_events_func, fire_method_rundown_events_func); diff --git a/src/mono/mono/eventpipe/ep-rt-mono.h b/src/mono/mono/eventpipe/ep-rt-mono.h index e8590d9bbdafbb..7fcb97bff999eb 100644 --- a/src/mono/mono/eventpipe/ep-rt-mono.h +++ b/src/mono/mono/eventpipe/ep-rt-mono.h @@ -10,6 +10,7 @@ #include #include #include + #include #include #include @@ -17,11 +18,11 @@ #include #include #include +#include +#include #include #include #include -#include -#include #undef EP_ARRAY_SIZE #define EP_ARRAY_SIZE(expr) G_N_ELEMENTS(expr) @@ -347,129 +348,6 @@ prefix_name ## _rt_ ## type_name ## _ ## func_name #define EP_RT_DEFINE_HASH_MAP_ITERATOR(hash_map_name, hash_map_type, iterator_type, key_type, value_type) \ EP_RT_DEFINE_HASH_MAP_ITERATOR_PREFIX(ep, hash_map_name, hash_map_type, iterator_type, key_type, value_type) -// Rundown callbacks. -typedef -bool -(*ep_rt_mono_fire_method_rundown_events_func)( - const uint64_t method_id, - const uint64_t module_id, - const uint64_t method_start_address, - const uint32_t method_size, - const uint32_t method_token, - const uint32_t method_flags, - const ep_char8_t *method_namespace, - const ep_char8_t *method_name, - const ep_char8_t *method_signature, - const uint16_t count_of_map_entries, - const uint32_t *il_offsets, - const uint32_t *native_offsets, - void *user_data); - -typedef -bool -(*ep_rt_mono_fire_assembly_rundown_events_func)( - const uint64_t domain_id, - const uint64_t assembly_id, - const uint32_t assembly_flags, - const uint32_t binding_id, - const ep_char8_t *assembly_name, - const uint64_t module_id, - const uint32_t module_flags, - const uint32_t reserved_flags, - const ep_char8_t *module_il_path, - const ep_char8_t *module_native_path, - const uint8_t *managed_pdb_signature, - const uint32_t managed_pdb_age, - const ep_char8_t *managed_pdb_build_path, - const uint8_t *native_pdb_signature, - const uint32_t native_pdb_age, - const ep_char8_t *native_pdb_build_path, - void *user_data); - -typedef -bool -(*ep_rt_mono_fire_domain_rundown_events_func)( - const uint64_t domain_id, - const uint32_t domain_flags, - const ep_char8_t *domain_name, - const uint32_t domain_index, - void *user_data); - -typedef EventPipeThreadHolder * (*ep_rt_thread_holder_alloc_func)(void); -typedef void (*ep_rt_thread_holder_free_func)(EventPipeThreadHolder *thread_holder); - -typedef int (*ep_rt_mono_cpu_count_func)(void); -typedef int (*ep_rt_mono_process_current_pid_func)(void); -typedef MonoNativeThreadId (*ep_rt_mono_native_thread_id_get_func)(void); -typedef gboolean (*ep_rt_mono_native_thread_id_equals_func)(MonoNativeThreadId, MonoNativeThreadId); -typedef gboolean (*ep_rt_mono_runtime_is_shutting_down_func)(void); -typedef gboolean (*ep_rt_mono_rand_try_get_bytes_func)(guchar *buffer, gssize buffer_size, MonoError *error); -typedef EventPipeThread * (*ep_rt_mono_thread_get_func)(void); -typedef EventPipeThread * (*ep_rt_mono_thread_get_or_create_func)(void); -typedef void (*ep_rt_mono_thread_exited_func)(void); -typedef gint (*ep_rt_mono_thread_info_sleep_func)(guint32 ms, gboolean *alerted); -typedef gboolean (*ep_rt_mono_thread_info_yield_func)(void); -typedef gpointer (*ep_rt_mono_w32file_create_func)(const gunichar2 *name, guint32 fileaccess, guint32 sharemode, guint32 createmode, guint32 attrs); -typedef gboolean (*ep_rt_mono_w32file_write_func)(gpointer handle, gconstpointer buffer, guint32 numbytes, guint32 *byteswritten, gint32 *win32error); -typedef gboolean (*ep_rt_mono_w32file_close_func)(gpointer handle); -typedef gpointer (*ep_rt_mono_w32event_create_func)(gboolean manual, gboolean initial); -typedef gboolean (*ep_rt_mono_w32event_close_func)(gpointer handle); -typedef void (*ep_rt_mono_w32event_set_func)(gpointer handle); -typedef MonoW32HandleWaitRet (*ep_rt_mono_w32handle_wait_one_func)(gpointer handle, guint32 timeout, gboolean alertable); -typedef void* (*ep_rt_mono_valloc_func)(void *addr, size_t length, int flags, MonoMemAccountType type); -typedef int (*ep_rt_mono_vfree_func)(void *addr, size_t length, MonoMemAccountType type); -typedef int (*ep_rt_mono_valloc_granule_func)(void); -typedef gboolean (*ep_rt_mono_thread_platform_create_thread_func)(ep_rt_thread_start_func thread_func, gpointer thread_data, gsize * const stack_size, ep_rt_thread_id_t *thread_id); -typedef gpointer (*ep_rt_mono_thread_attach_func)(gboolean); -typedef void (*ep_rt_mono_thread_detach_func)(void); -typedef char* (*ep_rt_mono_get_os_cmd_line_func)(void); -typedef char* (*ep_rt_mono_get_managed_cmd_line_func)(void); -typedef gboolean (*ep_rt_mono_execute_rundown_func)(ep_rt_mono_fire_domain_rundown_events_func domain_events_func, ep_rt_mono_fire_assembly_rundown_events_func assembly_events_func, ep_rt_mono_fire_method_rundown_events_func methods_events_func); -typedef gboolean (*ep_rt_mono_walk_managed_stack_for_thread_func)(ep_rt_thread_handle_t thread, EventPipeStackContents *stack_contents); -typedef gboolean (*ep_rt_mono_sample_profiler_write_sampling_event_for_threads_func)(ep_rt_thread_handle_t sampling_thread, EventPipeEvent *sampling_event); -typedef gboolean (*ep_rt_mono_method_get_simple_assembly_name_func)(ep_rt_method_desc_t *method, ep_char8_t *name, size_t name_len); -typedef gboolean (*ep_rt_mono_method_get_full_name_func)(ep_rt_method_desc_t *method, ep_char8_t *name, size_t name_len); - -typedef struct _EventPipeMonoFuncTable { - ep_rt_mono_process_current_pid_func ep_rt_mono_process_current_pid; - ep_rt_mono_cpu_count_func ep_rt_mono_cpu_count; - ep_rt_mono_native_thread_id_get_func ep_rt_mono_native_thread_id_get; - ep_rt_mono_native_thread_id_equals_func ep_rt_mono_native_thread_id_equals; - ep_rt_mono_runtime_is_shutting_down_func ep_rt_mono_runtime_is_shutting_down; - ep_rt_mono_rand_try_get_bytes_func ep_rt_mono_rand_try_get_bytes; - ep_rt_mono_thread_get_func ep_rt_mono_thread_get; - ep_rt_mono_thread_get_or_create_func ep_rt_mono_thread_get_or_create; - ep_rt_mono_thread_exited_func ep_rt_mono_thread_exited; - ep_rt_mono_thread_info_sleep_func ep_rt_mono_thread_info_sleep; - ep_rt_mono_thread_info_yield_func ep_rt_mono_thread_info_yield; - ep_rt_mono_w32file_create_func ep_rt_mono_w32file_create; - ep_rt_mono_w32file_write_func ep_rt_mono_w32file_write; - ep_rt_mono_w32file_close_func ep_rt_mono_w32file_close; - ep_rt_mono_w32event_create_func ep_rt_mono_w32event_create; - ep_rt_mono_w32event_close_func ep_rt_mono_w32event_close; - ep_rt_mono_w32event_set_func ep_rt_mono_w32event_set; - ep_rt_mono_w32handle_wait_one_func ep_rt_mono_w32hadle_wait_one; - ep_rt_mono_valloc_func ep_rt_mono_valloc; - ep_rt_mono_vfree_func ep_rt_mono_vfree; - ep_rt_mono_valloc_granule_func ep_rt_mono_valloc_granule; - ep_rt_mono_thread_platform_create_thread_func ep_rt_mono_thread_platform_create_thread; - ep_rt_mono_thread_attach_func ep_rt_mono_thread_attach; - ep_rt_mono_thread_detach_func ep_rt_mono_thread_detach; - ep_rt_mono_get_os_cmd_line_func ep_rt_mono_get_os_cmd_line; - ep_rt_mono_get_managed_cmd_line_func ep_rt_mono_get_managed_cmd_line; - ep_rt_mono_execute_rundown_func ep_rt_mono_execute_rundown; - ep_rt_mono_walk_managed_stack_for_thread_func ep_rt_mono_walk_managed_stack_for_thread; - ep_rt_mono_sample_profiler_write_sampling_event_for_threads_func ep_rt_mono_sample_profiler_write_sampling_event_for_threads; - ep_rt_mono_method_get_simple_assembly_name_func ep_rt_mono_method_get_simple_assembly_name; - ep_rt_mono_method_get_full_name_func ep_rt_mono_method_get_full_name; -} EventPipeMonoFuncTable; - -int64_t -ep_rt_mono_perf_counter_query (void); - -int64_t -ep_rt_mono_perf_frequency_query (void); - void ep_rt_mono_system_time_get (EventPipeSystemTime *system_time); @@ -485,28 +363,37 @@ ep_rt_mono_init_providers_and_events (void); void ep_rt_mono_fini_providers_and_events (void); +bool +ep_rt_mono_walk_managed_stack_for_thread ( + ep_rt_thread_handle_t thread, + EventPipeStackContents *stack_contents); + +bool +ep_rt_mono_method_get_simple_assembly_name ( + ep_rt_method_desc_t *method, + ep_char8_t *name, + size_t name_len); + +bool +ep_rt_mono_method_get_full_name ( + ep_rt_method_desc_t *method, + ep_char8_t *name, + size_t name_len); + +bool +ep_rt_mono_sample_profiler_write_sampling_event_for_threads ( + ep_rt_thread_handle_t sampling_thread, + EventPipeEvent *sampling_event); + void ep_rt_mono_execute_rundown (void); -static -inline -EventPipeMonoFuncTable * -ep_rt_mono_func_table_get (void) -{ - extern EventPipeMonoFuncTable _ep_rt_mono_func_table; - return &_ep_rt_mono_func_table; -} - static inline char * os_command_line_get (void) { -#ifdef EP_RT_MONO_USE_STATIC_RUNTIME return mono_get_os_cmd_line (); -#else - return ep_rt_mono_func_table_get ()->ep_rt_mono_get_os_cmd_line (); -#endif } static @@ -550,11 +437,7 @@ inline char * managed_command_line_get (void) { -#ifdef EP_RT_MONO_USE_STATIC_RUNTIME return mono_runtime_get_managed_cmd_line (); -#else - return ep_rt_mono_func_table_get ()->ep_rt_mono_get_managed_cmd_line (); -#endif } static @@ -602,17 +485,6 @@ ep_rt_mono_config_lock_get (void) return &_ep_rt_mono_config_lock; } -MONO_PROFILER_API -void -mono_eventpipe_init ( - EventPipeMonoFuncTable *table, - ep_rt_thread_holder_alloc_func thread_holder_alloc_func, - ep_rt_thread_holder_free_func thread_holder_free_func); - -MONO_PROFILER_API -void -mono_eventpipe_fini (void); - /* * Helpers */ @@ -644,11 +516,7 @@ inline MonoNativeThreadId ep_rt_mono_native_thread_id_get (void) { -#ifdef EP_RT_MONO_USE_STATIC_RUNTIME return mono_native_thread_id_get (); -#else - return ep_rt_mono_func_table_get ()->ep_rt_mono_native_thread_id_get (); -#endif } static @@ -656,27 +524,7 @@ inline gboolean ep_rt_mono_native_thread_id_equals (MonoNativeThreadId id1, MonoNativeThreadId id2) { -#ifdef EP_RT_MONO_USE_STATIC_RUNTIME return mono_native_thread_id_equals (id1, id2); -#else - return ep_rt_mono_func_table_get ()->ep_rt_mono_native_thread_id_equals (id1, id2); -#endif -} - -static -inline -gboolean -ep_rt_mono_rand_try_get_bytes (guchar *buffer, gssize buffer_size, MonoError *error) -{ - return ep_rt_mono_func_table_get ()->ep_rt_mono_rand_try_get_bytes (buffer, buffer_size, error); -} - -static -inline -void -ep_rt_mono_thread_exited (void) -{ - ep_rt_mono_func_table_get ()->ep_rt_mono_thread_exited (); } static @@ -684,11 +532,8 @@ inline gpointer ep_rt_mono_w32file_create (const gunichar2 *name, guint32 fileaccess, guint32 sharemode, guint32 createmode, guint32 attrs) { -#ifdef EP_RT_MONO_USE_STATIC_RUNTIME + //TODO, replace with low level PAL implementation. return mono_w32file_create (name, fileaccess, sharemode, createmode, attrs); -#else - return ep_rt_mono_func_table_get ()->ep_rt_mono_w32file_create (name, fileaccess, sharemode, createmode, attrs); -#endif } static @@ -696,11 +541,8 @@ inline gboolean ep_rt_mono_w32file_write (gpointer handle, gconstpointer buffer, guint32 numbytes, guint32 *byteswritten, gint32 *win32error) { -#ifdef EP_RT_MONO_USE_STATIC_RUNTIME + //TODO, replace with low level PAL implementation. return mono_w32file_write (handle, buffer, numbytes, byteswritten, win32error); -#else - return ep_rt_mono_func_table_get ()->ep_rt_mono_w32file_write (handle, buffer, numbytes, byteswritten, win32error); -#endif } static @@ -708,11 +550,8 @@ inline gboolean ep_rt_mono_w32file_close (gpointer handle) { -#ifdef EP_RT_MONO_USE_STATIC_RUNTIME + //TODO, replace with low level PAL implementation. return mono_w32file_close (handle); -#else - return ep_rt_mono_func_table_get ()->ep_rt_mono_w32file_close (handle); -#endif } static @@ -720,7 +559,8 @@ inline void ep_rt_mono_thread_setup (bool background_thread) { - ep_rt_mono_func_table_get ()->ep_rt_mono_thread_attach (background_thread); + extern void * ep_rt_mono_thread_attach (bool background_thread); + ep_rt_mono_thread_attach (background_thread); } static @@ -728,7 +568,8 @@ inline void ep_rt_mono_thread_teardown (void) { - ep_rt_mono_func_table_get ()->ep_rt_mono_thread_detach (); + extern void ep_rt_mono_thread_detach (void); + ep_rt_mono_thread_detach (); } /* @@ -803,7 +644,9 @@ inline void ep_rt_init (void) { - mono_eventpipe_init (ep_rt_mono_func_table_get (), thread_holder_alloc_func, thread_holder_free_func); + extern void ep_rt_mono_init (void); + ep_rt_mono_init (); + ep_rt_spin_lock_alloc (ep_rt_mono_config_lock_get ()); } @@ -816,7 +659,9 @@ ep_rt_shutdown (void) mono_lazy_cleanup (os_command_line_get_init (), os_command_line_lazy_clean); ep_rt_spin_lock_free (ep_rt_mono_config_lock_get ()); - mono_eventpipe_fini (); + + extern void ep_rt_mono_fini (void); + ep_rt_mono_fini (); } static @@ -860,7 +705,7 @@ ep_rt_walk_managed_stack_for_thread ( ep_rt_thread_handle_t thread, EventPipeStackContents *stack_contents) { - return (ep_rt_mono_func_table_get ()->ep_rt_mono_walk_managed_stack_for_thread (thread, stack_contents) == TRUE) ? true : false; + return ep_rt_mono_walk_managed_stack_for_thread (thread, stack_contents); } static @@ -871,7 +716,7 @@ ep_rt_method_get_simple_assembly_name ( ep_char8_t *name, size_t name_len) { - return (ep_rt_mono_func_table_get ()->ep_rt_mono_method_get_simple_assembly_name (method, name, name_len) == TRUE) ? true : false; + return ep_rt_mono_method_get_simple_assembly_name (method, name, name_len); } static @@ -882,7 +727,7 @@ ep_rt_method_get_full_name ( ep_char8_t *name, size_t name_len) { - return (ep_rt_mono_func_table_get ()->ep_rt_mono_method_get_full_name (method, name, name_len) == TRUE) ? true : false; + return ep_rt_mono_method_get_full_name (method, name, name_len); } static @@ -1089,7 +934,7 @@ static void ep_rt_sample_profiler_write_sampling_event_for_threads (ep_rt_thread_handle_t sampling_thread, EventPipeEvent *sampling_event) { - ep_rt_mono_func_table_get ()->ep_rt_mono_sample_profiler_write_sampling_event_for_threads (sampling_thread, sampling_event); + ep_rt_mono_sample_profiler_write_sampling_event_for_threads (sampling_thread, sampling_event); } static @@ -1196,12 +1041,9 @@ ep_rt_wait_event_alloc ( bool manual, bool initial) { + //TODO, replace with low level PAL implementation. EP_ASSERT (wait_event != NULL); -#ifdef EP_RT_MONO_USE_STATIC_RUNTIME wait_event->event = mono_w32event_create (manual, initial); -#else - wait_event->event = ep_rt_mono_func_table_get ()->ep_rt_mono_w32event_create (manual, initial); -#endif } static @@ -1209,12 +1051,9 @@ inline void ep_rt_wait_event_free (ep_rt_wait_event_handle_t *wait_event) { + //TODO, replace with low level PAL implementation. if (wait_event != NULL && wait_event->event != NULL) { -#ifdef EP_RT_MONO_USE_STATIC_RUNTIME mono_w32event_close (wait_event->event); -#else - ep_rt_mono_func_table_get ()->ep_rt_mono_w32event_close (wait_event->event); -#endif wait_event->event = NULL; } } @@ -1224,12 +1063,9 @@ inline bool ep_rt_wait_event_set (ep_rt_wait_event_handle_t *wait_event) { + //TODO, replace with low level PAL implementation. EP_ASSERT (wait_event != NULL && wait_event->event != NULL); -#ifdef EP_RT_MONO_USE_STATIC_RUNTIME mono_w32event_set (wait_event->event); -#else - ep_rt_mono_func_table_get ()->ep_rt_mono_w32event_set (wait_event->event); -#endif return true; } @@ -1241,12 +1077,9 @@ ep_rt_wait_event_wait ( uint32_t timeout, bool alertable) { + //TODO, replace with low level PAL implementation. EP_ASSERT (wait_event != NULL && wait_event->event != NULL); -#ifdef EP_RT_MONO_USE_STATIC_RUNTIME return (int32_t)mono_w32handle_wait_one (wait_event->event, timeout, alertable); -#else - return (int32_t)ep_rt_mono_func_table_get ()->ep_rt_mono_w32hadle_wait_one (wait_event->event, timeout, alertable); -#endif } static @@ -1290,11 +1123,7 @@ inline bool ep_rt_process_detach (void) { -#ifdef EP_RT_MONO_USE_STATIC_RUNTIME return (mono_runtime_is_shutting_down () == TRUE) ? true : false; -#else - return (ep_rt_mono_func_table_get ()->ep_rt_mono_runtime_is_shutting_down () == TRUE) ? true : false; -#endif } static @@ -1315,8 +1144,8 @@ ep_rt_create_activity_id ( EP_ASSERT (activity_id != NULL); EP_ASSERT (activity_id_len == EP_ACTIVITY_ID_SIZE); - ERROR_DECL (error); - ep_rt_mono_rand_try_get_bytes ((guchar *)activity_id, EP_ACTIVITY_ID_SIZE, error); + extern bool ep_rt_mono_rand_try_get_bytes (uint8_t *buffer,size_t buffer_size); + ep_rt_mono_rand_try_get_bytes ((guchar *)activity_id, EP_ACTIVITY_ID_SIZE); const uint16_t version_mask = 0xF000; const uint16_t random_guid_version = 0x4000; @@ -1347,7 +1176,7 @@ inline bool ep_rt_is_running (void) { - return ep_rt_process_detach (); + return !ep_rt_process_detach (); } static @@ -1431,11 +1260,7 @@ ep_rt_thread_create ( thread_params->thread_params.thread_func = thread_func; thread_params->thread_params.thread_params = params; thread_params->background_thread = true; -#ifdef EP_RT_MONO_USE_STATIC_RUNTIME return (mono_thread_platform_create_thread (ep_rt_thread_mono_start_func, thread_params, NULL, (ep_rt_thread_id_t *)id) == TRUE) ? true : false; -#else - return (ep_rt_mono_func_table_get ()->ep_rt_mono_thread_platform_create_thread (ep_rt_thread_mono_start_func, thread_params, NULL, (ep_rt_thread_id_t *)id) == TRUE) ? true : false; -#endif } return false; @@ -1454,11 +1279,7 @@ inline uint32_t ep_rt_current_process_get_id (void) { -#ifdef EP_RT_MONO_USE_STATIC_RUNTIME return (uint32_t)mono_process_current_pid (); -#else - return (uint32_t)ep_rt_mono_func_table_get ()->ep_rt_mono_process_current_pid (); -#endif } static @@ -1474,11 +1295,7 @@ inline uint32_t ep_rt_processors_get_count (void) { -#ifdef EP_RT_MONO_USE_STATIC_RUNTIME return (uint32_t)mono_cpu_count (); -#else - return (uint32_t)ep_rt_mono_func_table_get ()->ep_rt_mono_cpu_count (); -#endif } static @@ -1486,11 +1303,7 @@ inline ep_rt_thread_id_t ep_rt_current_thread_get_id (void) { -#ifdef EP_RT_MONO_USE_STATIC_RUNTIME return mono_native_thread_id_get (); -#else - return ep_rt_mono_func_table_get ()->ep_rt_mono_native_thread_id_get (); -#endif } static @@ -1498,6 +1311,7 @@ inline int64_t ep_rt_perf_counter_query (void) { + extern int64_t ep_rt_mono_perf_counter_query (void); return ep_rt_mono_perf_counter_query (); } @@ -1506,6 +1320,7 @@ inline int64_t ep_rt_perf_frequency_query (void) { + extern int64_t ep_rt_mono_perf_frequency_query (void); return ep_rt_mono_perf_frequency_query (); } @@ -1530,11 +1345,7 @@ inline int32_t ep_rt_system_get_alloc_granularity (void) { -#ifdef EP_RT_MONO_USE_STATIC_RUNTIME return (int32_t)mono_valloc_granule (); -#else - return (int32_t)ep_rt_mono_func_table_get ()->ep_rt_mono_valloc_granule (); -#endif } static @@ -1602,11 +1413,8 @@ inline uint8_t * ep_rt_valloc0 (size_t buffer_size) { -#ifdef EP_RT_MONO_USE_STATIC_RUNTIME uint8_t *buffer = (uint8_t *)mono_valloc (NULL, buffer_size, MONO_MMAP_READ | MONO_MMAP_WRITE, MONO_MEM_ACCOUNT_PROFILER); -#else - uint8_t *buffer = (uint8_t *)ep_rt_mono_func_table_get ()->ep_rt_mono_valloc (NULL, buffer_size, MONO_MMAP_READ | MONO_MMAP_WRITE, MONO_MEM_ACCOUNT_PROFILER); -#endif + if (buffer) memset (buffer, 0, buffer_size); return buffer; @@ -1620,11 +1428,7 @@ ep_rt_vfree ( size_t buffer_size) { if (buffer) -#ifdef EP_RT_MONO_USE_STATIC_RUNTIME mono_vfree (buffer, buffer_size, MONO_MEM_ACCOUNT_PROFILER); -#else - ep_rt_mono_func_table_get ()->ep_rt_mono_vfree (buffer, buffer_size, MONO_MEM_ACCOUNT_PROFILER); -#endif } static @@ -2001,13 +1805,9 @@ inline EventPipeThread * ep_rt_thread_get (void) { -#ifdef EP_RT_MONO_USE_STATIC_RUNTIME - extern MonoNativeTlsKey ep_rt_mono_thread_holder_tls_id; - EventPipeThreadHolder *thread_holder = (EventPipeThreadHolder *)mono_native_tls_get_value (ep_rt_mono_thread_holder_tls_id); + extern MonoNativeTlsKey _ep_rt_mono_thread_holder_tls_id; + EventPipeThreadHolder *thread_holder = (EventPipeThreadHolder *)mono_native_tls_get_value (_ep_rt_mono_thread_holder_tls_id); return thread_holder ? ep_thread_holder_get_thread (thread_holder) : NULL; -#else - return ep_rt_mono_func_table_get ()->ep_rt_mono_thread_get (); -#endif } static @@ -2016,8 +1816,10 @@ EventPipeThread * ep_rt_thread_get_or_create (void) { EventPipeThread *thread = ep_rt_thread_get (); - if (!thread) - thread = ep_rt_mono_func_table_get ()->ep_rt_mono_thread_get_or_create (); + if (!thread) { + extern EventPipeThread * ep_rt_mono_thread_get_or_create (void); + thread = ep_rt_mono_thread_get_or_create (); + } return thread; } @@ -2114,17 +1916,10 @@ int32_t ep_rt_mono_thread_sleep (uint32_t ms, bool alertable) { gboolean alerted = false; -#ifdef EP_RT_MONO_USE_STATIC_RUNTIME if (alertable) return (int32_t)mono_thread_info_sleep (ms, &alerted); else return (int32_t)mono_thread_info_sleep (ms, NULL); -#else - if (alertable) - return (int32_t)ep_rt_mono_func_table_get ()->ep_rt_mono_thread_info_sleep (ms, &alerted); - else - return (int32_t)ep_rt_mono_func_table_get ()->ep_rt_mono_thread_info_sleep (ms, NULL); -#endif } static @@ -2132,11 +1927,7 @@ inline bool ep_rt_mono_thread_yield (void) { -#ifdef EP_RT_MONO_USE_STATIC_RUNTIME return (mono_thread_info_yield () == TRUE) ? true : false; -#else - return (ep_rt_mono_func_table_get ()->ep_rt_mono_thread_info_yield () == TRUE) ? true : false; -#endif } // See src/coreclr/vm/spinlock.h for details. diff --git a/src/mono/mono/metadata/appdomain.c b/src/mono/mono/metadata/appdomain.c index f3462d1462e39d..26e2f52da4f79b 100644 --- a/src/mono/mono/metadata/appdomain.c +++ b/src/mono/mono/metadata/appdomain.c @@ -279,8 +279,8 @@ mono_runtime_init_checked (MonoDomain *domain, MonoThreadStartCB start_cb, MonoT mono_thread_internal_attach (domain); #if defined(ENABLE_PERFTRACING) && !defined(DISABLE_EVENTPIPE) - mono_component_diagnostics_server ()->ds_server_init (); - mono_component_diagnostics_server ()->ds_server_pause_for_diagnostics_monitor (); + mono_component_diagnostics_server ()->init (); + mono_component_diagnostics_server ()->pause_for_diagnostics_monitor (); #endif mono_type_initialization_init (); diff --git a/src/mono/mono/metadata/components.c b/src/mono/mono/metadata/components.c index df1c13f93939c4..f8a0f5dc32c8ff 100644 --- a/src/mono/mono/metadata/components.c +++ b/src/mono/mono/metadata/components.c @@ -29,20 +29,25 @@ typedef struct _MonoComponentEntry { #define COMPONENT_INIT_FUNC(name) (MonoComponentInitFn) mono_component_ ## name ## _stub_init #endif +#define HOT_RELOAD_MODULE_NAME "hot_reload" MonoComponentHotReload *hot_reload = NULL; + +#ifdef ENABLE_PERFTRACING MonoComponentEventPipe *event_pipe = NULL; -MonoComponentEventPipe *diagnostics_server = NULL; +MonoComponentDiagnosticsServer *diagnostics_server = NULL; // DiagnosticsServer component currently hosted by EventPipe module. -#define HOT_RELOAD_MODULE_NAME "hot_reload" #define EVENT_PIPE_MODULE_NAME "event_pipe" #define DIAGNOSTICS_SERVER_MODULE_NAME EVENT_PIPE_MODULE_NAME +#endif /* One per component */ MonoComponentEntry components[] = { { HOT_RELOAD_MODULE_NAME, COMPONENT_INIT_FUNC (hot_reload), (MonoComponent**)&hot_reload, NULL }, +#ifdef ENABLE_PERFTRACING { EVENT_PIPE_MODULE_NAME, COMPONENT_INIT_FUNC (event_pipe), (MonoComponent**)&event_pipe, NULL }, - { DIAGNOSTICS_SERVER_MODULE_NAME, COMPONENT_INIT_FUNC (diagnostics_server), (MonoComponent**)&diagnostics_server, NULL } + { DIAGNOSTICS_SERVER_MODULE_NAME, COMPONENT_INIT_FUNC (diagnostics_server), (MonoComponent**)&diagnostics_server, NULL }, +#endif }; #ifndef STATIC_COMPONENTS diff --git a/src/mono/mono/metadata/components.h b/src/mono/mono/metadata/components.h index 03d50fdfc0a948..9b59803098c1b8 100644 --- a/src/mono/mono/metadata/components.h +++ b/src/mono/mono/metadata/components.h @@ -25,6 +25,7 @@ mono_component_hot_reload (void) return hot_reload; } +#ifdef ENABLE_PERFTRACING static inline MonoComponentEventPipe * mono_component_event_pipe (void) @@ -40,15 +41,18 @@ mono_component_diagnostics_server (void) extern MonoComponentDiagnosticsServer *diagnostics_server; return diagnostics_server; } +#endif /* Declare each copomnents stub init function here */ MonoComponentHotReload * mono_component_hot_reload_stub_init (void); +#ifdef ENABLE_PERFTRACING MonoComponentEventPipe * mono_component_event_pipe_stub_init (void); MonoComponentDiagnosticsServer * mono_component_diagnostics_server_stub_init (void); +#endif #endif/*_MONO_METADATA_COMPONENTS_H*/ diff --git a/src/mono/mono/metadata/environment-internals.h b/src/mono/mono/metadata/environment-internals.h index cfd13afc4d53b6..510f4222c90ede 100644 --- a/src/mono/mono/metadata/environment-internals.h +++ b/src/mono/mono/metadata/environment-internals.h @@ -7,10 +7,12 @@ #ifndef _MONO_METADATA_ENVIRONMENT_INTERNALS_H_ #define _MONO_METADATA_ENVIRONMENT_INTERNALS_H_ +#include + void mono_set_os_args (int argc, char **argv); -char * +MONO_COMPONENT_API char * mono_get_os_cmd_line (void); #endif /* _MONO_METADATA_ENVIRONMENT_INTERNALS_H_ */ diff --git a/src/mono/mono/metadata/icall-eventpipe.c b/src/mono/mono/metadata/icall-eventpipe.c index c8ab05a558af30..ad1ae17253daaa 100644 --- a/src/mono/mono/metadata/icall-eventpipe.c +++ b/src/mono/mono/metadata/icall-eventpipe.c @@ -1,206 +1,15 @@ #include #include #include - #include #if defined(ENABLE_PERFTRACING) && !defined(DISABLE_EVENTPIPE) -#include -#include -#include -#include -#include - -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include - -// Rundown flags. -#define METHOD_FLAGS_DYNAMIC_METHOD 0x1 -#define METHOD_FLAGS_GENERIC_METHOD 0x2 -#define METHOD_FLAGS_SHARED_GENERIC_METHOD 0x4 -#define METHOD_FLAGS_JITTED_METHOD 0x8 -#define METHOD_FLAGS_JITTED_HELPER_METHOD 0x10 - -#define MODULE_FLAGS_NATIVE_MODULE 0x2 -#define MODULE_FLAGS_DYNAMIC_MODULE 0x4 -#define MODULE_FLAGS_MANIFEST_MODULE 0x8 - -#define ASSEMBLY_FLAGS_DYNAMIC_ASSEMBLY 0x2 -#define ASSEMBLY_FLAGS_NATIVE_ASSEMBLY 0x4 -#define ASSEMBLY_FLAGS_COLLECTIBLE_ASSEMBLY 0x8 - -#define DOMAIN_FLAGS_DEFAULT_DOMAIN 0x1 -#define DOMAIN_FLAGS_EXECUTABLE_DOMAIN 0x2 - -typedef enum _EventPipeActivityControlCode { - EP_ACTIVITY_CONTROL_GET_ID = 1, - EP_ACTIVITY_CONTROL_SET_ID = 2, - EP_ACTIVITY_CONTROL_CREATE_ID = 3, - EP_ACTIVITY_CONTROL_GET_SET_ID = 4, - EP_ACTIVITY_CONTROL_CREATE_SET_ID = 5 -} EventPipeActivityControlCode; - -typedef struct _EventPipeProviderConfigurationNative { - gunichar2 *provider_name; - uint64_t keywords; - uint32_t logging_level; - gunichar2 *filter_data; -} EventPipeProviderConfigurationNative; - -typedef struct _EventPipeSessionInfo { - int64_t starttime_as_utc_filetime; - int64_t start_timestamp; - int64_t timestamp_frequency; -} EventPipeSessionInfo; - -typedef struct _EventPipeEventInstanceData { - intptr_t provider_id; - uint32_t event_id; - uint32_t thread_id; - int64_t timestamp; - uint8_t activity_id [EP_ACTIVITY_ID_SIZE]; - uint8_t related_activity_id [EP_ACTIVITY_ID_SIZE]; - const uint8_t *payload; - uint32_t payload_len; -} EventPipeEventInstanceData; - -typedef struct _EventPipeFireMethodEventsData{ - MonoDomain *domain; - uint8_t *buffer; - size_t buffer_size; - ep_rt_mono_fire_method_rundown_events_func method_events_func; -} EventPipeFireMethodEventsData; - -typedef struct _EventPipeSampleProfileData { - EventPipeStackContents stack_contents; - uint64_t thread_id; - uintptr_t thread_ip; - uint32_t payload_data; -} EventPipeSampleProfileData; - -gboolean ep_rt_mono_initialized; -MonoNativeTlsKey ep_rt_mono_thread_holder_tls_id; -gpointer ep_rt_mono_rand_provider; - -static ep_rt_thread_holder_alloc_func thread_holder_alloc_callback_func; -static ep_rt_thread_holder_free_func thread_holder_free_callback_func; - -static GArray * _ep_rt_mono_sampled_thread_callstacks = NULL; -static uint32_t _ep_rt_mono_max_sampled_thread_count = 32; +#include /* * Forward declares of all static functions. */ -static -gboolean -rand_try_get_bytes_func ( - guchar *buffer, - gssize buffer_size, - MonoError *error); - -static -EventPipeThread * -eventpipe_thread_get (void); - -static -EventPipeThread * -eventpipe_thread_get_or_create (void); - -static -void -eventpipe_thread_exited (void); - -static -void -profiler_eventpipe_thread_exited ( - MonoProfiler *prof, - uintptr_t tid); - -static -gpointer -eventpipe_thread_attach (gboolean background_thread); - -static -void -eventpipe_thread_detach (void); - -static -void -eventpipe_fire_method_events ( - MonoJitInfo *ji, - MonoMethod *method, - EventPipeFireMethodEventsData *events_data); - -static -void -eventpipe_fire_method_events_func ( - MonoJitInfo *ji, - gpointer user_data); - -static -void -eventpipe_fire_assembly_events ( - MonoDomain *domain, - MonoAssembly *assembly, - ep_rt_mono_fire_assembly_rundown_events_func assembly_events_func); - -static -gboolean -eventpipe_execute_rundown ( - ep_rt_mono_fire_domain_rundown_events_func domain_events_func, - ep_rt_mono_fire_assembly_rundown_events_func assembly_events_func, - ep_rt_mono_fire_method_rundown_events_func methods_events_func); - -static -gboolean -eventpipe_walk_managed_stack_for_thread_func ( - MonoStackFrameInfo *frame, - MonoContext *ctx, - gpointer data); - -static -gboolean -eventpipe_walk_managed_stack_for_thread ( - ep_rt_thread_handle_t thread, - EventPipeStackContents *stack_contents); - -static -gboolean -eventpipe_sample_profiler_walk_managed_stack_for_thread_func ( - MonoStackFrameInfo *frame, - MonoContext *ctx, - gpointer data); - -static -gboolean -eventpipe_sample_profiler_write_sampling_event_for_threads ( - ep_rt_thread_handle_t sampling_thread, - EventPipeEvent *sampling_event); - -static -gboolean -eventpipe_method_get_simple_assembly_name ( - ep_rt_method_desc_t *method, - ep_char8_t *name, - size_t name_len); - -static -gboolean -evetpipe_method_get_full_name ( - ep_rt_method_desc_t *method, - ep_char8_t *name, - size_t name_len); - static void delegate_callback_data_free_func ( @@ -857,11 +666,11 @@ ves_icall_System_Diagnostics_Tracing_EventPipeInternal_CreateProvider ( char *provider_name_utf8 = mono_string_handle_to_utf8 (provider_name, error); if (is_ok (error) && provider_name_utf8) { - provider = ep_create_provider (provider_name_utf8, delegate_callback_func, delegate_callback_data_free_func, callback_data); + provider = mono_component_event_pipe ()->create_provider (provider_name_utf8, delegate_callback_func, delegate_callback_data_free_func, callback_data); } g_free (provider_name_utf8); - return provider; + return (gconstpointer)provider; } intptr_t @@ -877,7 +686,7 @@ ves_icall_System_Diagnostics_Tracing_EventPipeInternal_DefineEvent ( g_assert (provider_handle != 0); EventPipeProvider *provider = (EventPipeProvider *)provider_handle; - EventPipeEvent *ep_event = ep_provider_add_event (provider, event_id, (uint64_t)keywords, event_version, (EventPipeEventLevel)level, /* needStack = */ true, metadata, metadata_len); + EventPipeEvent *ep_event = mono_component_event_pipe ()->provider_add_event (provider, event_id, (uint64_t)keywords, event_version, (EventPipeEventLevel)level, /* needStack = */ true, metadata, metadata_len); g_assert (ep_event != NULL); return (intptr_t)ep_event; @@ -886,15 +695,14 @@ ves_icall_System_Diagnostics_Tracing_EventPipeInternal_DefineEvent ( void ves_icall_System_Diagnostics_Tracing_EventPipeInternal_DeleteProvider (intptr_t provider_handle) { - if (provider_handle) { - ep_delete_provider ((EventPipeProvider *)provider_handle); - } + if (provider_handle) + mono_component_event_pipe ()->delete_provider ((EventPipeProvider *)provider_handle); } void ves_icall_System_Diagnostics_Tracing_EventPipeInternal_Disable (uint64_t session_id) { - ep_disable (session_id); + mono_component_event_pipe ()->disable (session_id); } uint64_t @@ -915,42 +723,21 @@ ves_icall_System_Diagnostics_Tracing_EventPipeInternal_Enable ( if (output_file) output_file_utf8 = mono_utf16_to_utf8 (output_file, g_utf16_len (output_file), error); - EventPipeProviderConfigurationNative *native_config_providers = (EventPipeProviderConfigurationNative *)providers; - EventPipeProviderConfiguration *config_providers = g_new0 (EventPipeProviderConfiguration, providers_len); - - if (config_providers) { - for (int i = 0; i < providers_len; ++i) { - ep_provider_config_init ( - &config_providers[i], - native_config_providers[i].provider_name ? mono_utf16_to_utf8 (native_config_providers[i].provider_name, g_utf16_len (native_config_providers[i].provider_name), error) : NULL, - native_config_providers [i].keywords, - (EventPipeEventLevel)native_config_providers [i].logging_level, - native_config_providers[i].filter_data ? mono_utf16_to_utf8 (native_config_providers[i].filter_data, g_utf16_len (native_config_providers[i].filter_data), error) : NULL); - } - } - - session_id = ep_enable ( + session_id = mono_component_event_pipe ()->enable ( output_file_utf8, circular_buffer_size_mb, - config_providers, + (EventPipeProviderConfigurationNative *)providers, providers_len, output_file != NULL ? EP_SESSION_TYPE_FILE : EP_SESSION_TYPE_LISTENER, (EventPipeSerializationFormat)format, true, NULL, NULL); - ep_start_streaming (session_id); - if (config_providers) { - for (int i = 0; i < providers_len; ++i) { - ep_provider_config_fini (&config_providers[i]); - g_free ((ep_char8_t *)ep_provider_config_get_provider_name (&config_providers[i])); - g_free ((ep_char8_t *)ep_provider_config_get_filter_data (&config_providers[i])); - } - } + mono_component_event_pipe ()->start_streaming (session_id); g_free (output_file_utf8); - return session_id; + return (uint64_t)session_id; } int32_t @@ -958,40 +745,7 @@ ves_icall_System_Diagnostics_Tracing_EventPipeInternal_EventActivityIdControl ( uint32_t control_code, /* GUID * */uint8_t *activity_id) { - int32_t result = 0; - ep_rt_thread_activity_id_handle_t activity_id_handle = ep_thread_get_activity_id_handle (); - - if (activity_id_handle == NULL) - return 1; - - uint8_t current_activity_id [EP_ACTIVITY_ID_SIZE]; - EventPipeActivityControlCode activity_control_code = (EventPipeActivityControlCode)control_code; - switch (activity_control_code) { - case EP_ACTIVITY_CONTROL_GET_ID: - ep_thread_get_activity_id (activity_id_handle, activity_id, EP_ACTIVITY_ID_SIZE); - break; - case EP_ACTIVITY_CONTROL_SET_ID: - ep_thread_set_activity_id (activity_id_handle, activity_id, EP_ACTIVITY_ID_SIZE); - break; - case EP_ACTIVITY_CONTROL_CREATE_ID: - ep_thread_create_activity_id (activity_id, EP_ACTIVITY_ID_SIZE); - break; - case EP_ACTIVITY_CONTROL_GET_SET_ID: - ep_thread_get_activity_id (activity_id_handle, current_activity_id, EP_ACTIVITY_ID_SIZE); - ep_thread_set_activity_id (activity_id_handle, activity_id, EP_ACTIVITY_ID_SIZE); - memcpy (activity_id, current_activity_id, EP_ACTIVITY_ID_SIZE); - break; - case EP_ACTIVITY_CONTROL_CREATE_SET_ID: - ep_thread_get_activity_id (activity_id_handle, activity_id, EP_ACTIVITY_ID_SIZE); - ep_thread_create_activity_id (current_activity_id, EP_ACTIVITY_ID_SIZE); - ep_thread_set_activity_id (activity_id_handle, current_activity_id, EP_ACTIVITY_ID_SIZE); - break; - default: - result = 1; - break; - } - - return result; + return mono_component_event_pipe ()->thread_ctrl_activity_id ((EventPipeActivityControlCode)control_code, activity_id, EP_ACTIVITY_ID_SIZE) ? 0 : 1; } MonoBoolean @@ -999,25 +753,7 @@ ves_icall_System_Diagnostics_Tracing_EventPipeInternal_GetNextEvent ( uint64_t session_id, /* EventPipeEventInstanceData * */void *instance) { - g_assert (instance != NULL); - - EventPipeEventInstance *const next_instance = ep_get_next_event (session_id); - EventPipeEventInstanceData *const data = (EventPipeEventInstanceData *)instance; - if (next_instance && data) { - const EventPipeEvent *const ep_event = ep_event_instance_get_ep_event (next_instance); - if (ep_event) { - data->provider_id = (intptr_t)ep_event_get_provider (ep_event); - data->event_id = ep_event_get_event_id (ep_event); - } - data->thread_id = ep_event_instance_get_thread_id (next_instance); - data->timestamp = ep_event_instance_get_timestamp (next_instance); - memcpy (&data->activity_id, ep_event_instance_get_activity_id_cref (next_instance), EP_ACTIVITY_ID_SIZE); - memcpy (&data->related_activity_id, ep_event_instance_get_related_activity_id_cref (next_instance), EP_ACTIVITY_ID_SIZE); - data->payload = ep_event_instance_get_data (next_instance); - data->payload_len = ep_event_instance_get_data_len (next_instance); - } - - return next_instance != NULL; + return mono_component_event_pipe ()->get_next_event ((EventPipeSessionID)session_id, (EventPipeEventInstanceData *)instance) ? TRUE : FALSE; } intptr_t @@ -1029,7 +765,7 @@ ves_icall_System_Diagnostics_Tracing_EventPipeInternal_GetProvider (const gunich if (provider_name) { provider_name_utf8 = mono_utf16_to_utf8 (provider_name, g_utf16_len (provider_name), error); - provider = ep_get_provider (provider_name_utf8); + provider = mono_component_event_pipe()->get_provider (provider_name_utf8); } g_free (provider_name_utf8); @@ -1041,25 +777,13 @@ ves_icall_System_Diagnostics_Tracing_EventPipeInternal_GetSessionInfo ( uint64_t session_id, /* EventPipeSessionInfo * */void *session_info) { - bool result = false; - if (session_info) { - EventPipeSession *session = ep_get_session ((EventPipeSessionID)session_id); - if (session) { - EventPipeSessionInfo *instance = (EventPipeSessionInfo *)session_info; - instance->starttime_as_utc_filetime = ep_session_get_session_start_time (session); - instance->start_timestamp = ep_session_get_session_start_timestamp (session); - instance->timestamp_frequency = ep_perf_frequency_query (); - result = true; - } - } - - return result; + return mono_component_event_pipe()->get_session_info (session_id, (EventPipeSessionInfo *)session_info) ? TRUE : FALSE; } intptr_t ves_icall_System_Diagnostics_Tracing_EventPipeInternal_GetWaitHandle (uint64_t session_id) { - return (intptr_t)ep_get_wait_handle (session_id); + return (intptr_t) mono_component_event_pipe()->get_wait_handle ((EventPipeSessionID)session_id); } void @@ -1072,7 +796,7 @@ ves_icall_System_Diagnostics_Tracing_EventPipeInternal_WriteEventData ( { g_assert (event_handle); EventPipeEvent *ep_event = (EventPipeEvent *)event_handle; - ep_write_event_2 (ep_event, (EventData *)event_data, event_data_len, activity_id, related_activity_id); + mono_component_event_pipe()->write_event_2 (ep_event, (EventData *)event_data, event_data_len, activity_id, related_activity_id); } #else /* ENABLE_PERFTRACING */ diff --git a/src/mono/mono/metadata/object-internals.h b/src/mono/mono/metadata/object-internals.h index c92ea7bcf43d62..8ba20f76b8d037 100644 --- a/src/mono/mono/metadata/object-internals.h +++ b/src/mono/mono/metadata/object-internals.h @@ -2070,7 +2070,7 @@ mono_gc_wbarrier_value_copy_internal (void* dest, const void* src, int count, Mo void mono_gc_wbarrier_object_copy_internal (MonoObject* obj, MonoObject *src); -char * +MONO_COMPONENT_API char * mono_runtime_get_managed_cmd_line (void); char * diff --git a/src/mono/mono/mini/mini-runtime.c b/src/mono/mono/mini/mini-runtime.c index dca4243cb0e418..0d74d9506b6435 100644 --- a/src/mono/mono/mini/mini-runtime.c +++ b/src/mono/mono/mini/mini-runtime.c @@ -4426,9 +4426,9 @@ mini_init (const char *filename, const char *runtime_version) #if defined(ENABLE_PERFTRACING) && !defined(DISABLE_EVENTPIPE) if (mono_compile_aot) - mono_component_diagnostics_server ()->ds_server_disable (); + mono_component_diagnostics_server ()->disable (); - mono_component_event_pipe ()->ep_init (); + mono_component_event_pipe ()->init (); #endif if (mono_aot_only) { @@ -4497,7 +4497,7 @@ mini_init (const char *filename, const char *runtime_version) mono_threads_set_runtime_startup_finished (); #if defined(ENABLE_PERFTRACING) && !defined(DISABLE_EVENTPIPE) - mono_component_event_pipe ()->ep_finish_init (); + mono_component_event_pipe ()->finish_init (); #endif #ifdef ENABLE_EXPERIMENT_TIERED @@ -4880,8 +4880,8 @@ mini_cleanup (MonoDomain *domain) mono_jit_dump_cleanup (); mini_get_interp_callbacks ()->cleanup (); #if defined(ENABLE_PERFTRACING) && !defined(DISABLE_EVENTPIPE) - mono_component_event_pipe ()->ep_shutdown (); - mono_component_diagnostics_server ()->ds_server_shutdown (); + mono_component_event_pipe ()->shutdown (); + mono_component_diagnostics_server ()->shutdown (); #endif } diff --git a/src/mono/mono/utils/mono-proclib.h b/src/mono/mono/utils/mono-proclib.h index 01c93526c124b5..6b653bd7ff27e9 100644 --- a/src/mono/mono/utils/mono-proclib.h +++ b/src/mono/mono/utils/mono-proclib.h @@ -70,7 +70,7 @@ char* mono_process_get_name (gpointer pid, char *buf, int len); gint64 mono_process_get_data (gpointer pid, MonoProcessData data); gint64 mono_process_get_data_with_error (gpointer pid, MonoProcessData data, MonoProcessError *error); -int mono_process_current_pid (void); +MONO_COMPONENT_API int mono_process_current_pid (void); MONO_API int mono_cpu_count (void); gint64 mono_cpu_get_data (int cpu_id, MonoCpuData data, MonoProcessError *error); diff --git a/src/mono/mono/utils/mono-threads.h b/src/mono/mono/utils/mono-threads.h index 8d08f10fe5baf0..bb1ce35d825d88 100644 --- a/src/mono/mono/utils/mono-threads.h +++ b/src/mono/mono/utils/mono-threads.h @@ -23,6 +23,7 @@ #include #include #include +#include #include #include @@ -506,7 +507,7 @@ mono_thread_info_get_stack_bounds (guint8 **staddr, size_t *stsize); MONO_API gboolean mono_thread_info_yield (void); -gint +MONO_COMPONENT_API gint mono_thread_info_sleep (guint32 ms, gboolean *alerted); gint @@ -624,7 +625,7 @@ gint mono_threads_suspend_get_suspend_signal (void); gint mono_threads_suspend_get_restart_signal (void); gint mono_threads_suspend_get_abort_signal (void); -gboolean +MONO_COMPONENT_API gboolean mono_thread_platform_create_thread (MonoThreadStart thread_fn, gpointer thread_data, gsize* const stack_size, MonoNativeThreadId *tid); diff --git a/src/native/eventpipe/CMakeLists.txt b/src/native/eventpipe/CMakeLists.txt index 07acdcf6800029..c320b615fc410e 100644 --- a/src/native/eventpipe/CMakeLists.txt +++ b/src/native/eventpipe/CMakeLists.txt @@ -41,6 +41,7 @@ if(ENABLE_PERFTRACING OR FEATURE_PERFTRACING) ep-file.h ep-getter-setter.h ep-ipc-pal-types.h + ep-ipc-pal-types-forward.h ep-ipc-stream.h ep-json-file.h ep-metadata-generator.h @@ -56,6 +57,7 @@ if(ENABLE_PERFTRACING OR FEATURE_PERFTRACING) ep-stream.h ep-thread.h ep-types.h + ep-types-forward.h ) list(APPEND SHARED_DIAGNOSTIC_SERVER_SOURCES diff --git a/src/native/eventpipe/ep-ipc-pal-types-forward.h b/src/native/eventpipe/ep-ipc-pal-types-forward.h new file mode 100644 index 00000000000000..2c890cce81a772 --- /dev/null +++ b/src/native/eventpipe/ep-ipc-pal-types-forward.h @@ -0,0 +1,22 @@ +#ifndef __EVENTPIPE_IPC_PAL_TYPES_FORWARD_H__ +#define __EVENTPIPE_IPC_PAL_TYPES_FORWARD_H__ + +#ifdef ENABLE_PERFTRACING + +#include +#include +#ifndef __cplusplus +#include +#endif // __cplusplus + +typedef char ep_char8_t; + +/* + * IPC Stream Structs. + */ + +typedef struct _IpcStream IpcStream; +typedef struct _IpcStreamVtable IpcStreamVtable; + +#endif /* ENABLE_PERFTRACING */ +#endif /* __EVENTPIPE_IPC_PAL_TYPES_FORWARD_H__ */ diff --git a/src/native/eventpipe/ep-ipc-pal-types.h b/src/native/eventpipe/ep-ipc-pal-types.h index ac2f3d0c5bd678..a353b8a3c104c8 100644 --- a/src/native/eventpipe/ep-ipc-pal-types.h +++ b/src/native/eventpipe/ep-ipc-pal-types.h @@ -9,20 +9,7 @@ #endif #include "ep-getter-setter.h" -#include -#include -#ifndef __cplusplus -#include -#endif // __cplusplus - -typedef char ep_char8_t; - -/* - * IPC Stream Structs. - */ - -typedef struct _IpcStream IpcStream; -typedef struct _IpcStreamVtable IpcStreamVtable; +#include "ep-ipc-pal-types-forward.h" #endif /* ENABLE_PERFTRACING */ #endif /* __EVENTPIPE_IPC_PAL_TYPES_H__ */ diff --git a/src/native/eventpipe/ep-types-forward.h b/src/native/eventpipe/ep-types-forward.h new file mode 100644 index 00000000000000..75976bcdec1a7e --- /dev/null +++ b/src/native/eventpipe/ep-types-forward.h @@ -0,0 +1,205 @@ +#ifndef __EVENTPIPE_TYPES_FORWARD_H__ +#define __EVENTPIPE_TYPES_FORWARD_H__ + +#ifdef ENABLE_PERFTRACING + +/* + * EventPipe Structs. + */ + +typedef struct _EventData EventData; +typedef struct _EventFilterDescriptor EventFilterDescriptor; +typedef struct _EventPipeBuffer EventPipeBuffer; +typedef struct _EventPipeBufferList EventPipeBufferList; +typedef struct _EventPipeBufferManager EventPipeBufferManager; +typedef struct _EventPipeBlock EventPipeBlock; +typedef struct _EventPipeBlockVtable EventPipeBlockVtable; +typedef struct _EventPipeConfiguration EventPipeConfiguration; +typedef struct _EventPipeEvent EventPipeEvent; +typedef struct _EventPipeEventBlockBase EventPipeEventBlockBase; +typedef struct _EventPipeEventBlock EventPipeEventBlock; +typedef struct _EventPipeEventHeader EventPipeEventHeader; +typedef struct _EventPipeEventInstance EventPipeEventInstance; +typedef struct _EventPipeEventMetadataEvent EventPipeEventMetadataEvent; +typedef struct _EventPipeEventPayload EventPipeEventPayload; +typedef struct _EventPipeEventSource EventPipeEventSource; +typedef struct _EventPipeFile EventPipeFile; +typedef struct _EventPipeJsonFile EventPipeJsonFile; +typedef struct _EventPipeMetadataBlock EventPipeMetadataBlock; +typedef struct _EventPipeParameterDesc EventPipeParameterDesc; +typedef struct _EventPipeProvider EventPipeProvider; +typedef struct _EventPipeProviderCallbackData EventPipeProviderCallbackData; +typedef struct _EventPipeProviderCallbackDataQueue EventPipeProviderCallbackDataQueue; +typedef struct _EventPipeProviderConfiguration EventPipeProviderConfiguration; +typedef struct _EventPipeSession EventPipeSession; +typedef struct _EventPipeSessionProvider EventPipeSessionProvider; +typedef struct _EventPipeSessionProviderList EventPipeSessionProviderList; +typedef struct _EventPipeSequencePoint EventPipeSequencePoint; +typedef struct _EventPipeSequencePointBlock EventPipeSequencePointBlock; +typedef struct _EventPipeStackBlock EventPipeStackBlock; +typedef struct _EventPipeStackContents EventPipeStackContents; +typedef struct _EventPipeSystemTime EventPipeSystemTime; +typedef struct _EventPipeThread EventPipeThread; +typedef struct _EventPipeThreadHolder EventPipeThreadHolder; +typedef struct _EventPipeThreadSessionState EventPipeThreadSessionState; +typedef struct _FastSerializableObject FastSerializableObject; +typedef struct _FastSerializableObjectVtable FastSerializableObjectVtable; +typedef struct _FastSerializer FastSerializer; +typedef struct _FileStream FileStream; +typedef struct _FileStreamWriter FileStreamWriter; +typedef struct _IpcStreamWriter IpcStreamWriter; +typedef struct _StackHashEntry StackHashEntry; +typedef struct _StackHashKey StackHashKey; +typedef struct _StreamWriter StreamWriter; +typedef struct _StreamWriterVtable StreamWriterVtable; + +#define EP_MAX_NUMBER_OF_SESSIONS 64 + +#define EP_GUID_SIZE 16 + +#define EP_ACTIVITY_ID_SIZE EP_GUID_SIZE + +#define EP_MAX_STACK_DEPTH 100 + +/* + * EventPipe Enums. + */ + +typedef enum { + EP_BUFFER_STATE_WRITABLE = 0, + EP_BUFFER_STATE_READ_ONLY = 1 +} EventPipeBufferState; + +typedef enum { + EP_EVENT_LEVEL_LOGALWAYS, + EP_EVENT_LEVEL_CRITICAL, + EP_EVENT_LEVEL_ERROR, + EP_EVENT_LEVEL_WARNING, + EP_EVENT_LEVEL_INFORMATIONAL, + EP_EVENT_LEVEL_VERBOSE +} EventPipeEventLevel; + +typedef enum { + EP_FILE_FLUSH_FLAGS_EVENT_BLOCK = 1, + EP_FILE_FLUSH_FLAGS_METADATA_BLOCK = 2, + EP_FILE_FLUSH_FLAGS_STACK_BLOCK = 4, + EP_FILE_FLUSH_FLAGS_ALL_BLOCKS = EP_FILE_FLUSH_FLAGS_EVENT_BLOCK | EP_FILE_FLUSH_FLAGS_METADATA_BLOCK | EP_FILE_FLUSH_FLAGS_STACK_BLOCK +} EventPipeFileFlushFlags; + +// Represents the type of an event parameter. +// This enum is derived from the managed TypeCode type, though +// not all of these values are available in TypeCode. +// For example, Guid does not exist in TypeCode. +// Keep this in sync with COR_PRF_EVENTPIPE_PARAM_TYPE defined in +// corprof.idl +typedef enum { + EP_PARAMETER_TYPE_EMPTY = 0, // Null reference + EP_PARAMETER_TYPE_OBJECT = 1, // Instance that isn't a value + EP_PARAMETER_TYPE_DB_NULL = 2, // Database null value + EP_PARAMETER_TYPE_BOOLEAN = 3, // Boolean + EP_PARAMETER_TYPE_CHAR = 4, // Unicode character + EP_PARAMETER_TYPE_SBYTE = 5, // Signed 8-bit integer + EP_PARAMETER_TYPE_BYTE = 6, // Unsigned 8-bit integer + EP_PARAMETER_TYPE_INT16 = 7, // Signed 16-bit integer + EP_PARAMETER_TYPE_UINT16 = 8, // Unsigned 16-bit integer + EP_PARAMETER_TYPE_INT32 = 9, // Signed 32-bit integer + EP_PARAMETER_TYPE_UINT32 = 10, // Unsigned 32-bit integer + EP_PARAMETER_TYPE_INT64 = 11, // Signed 64-bit integer + EP_PARAMETER_TYPE_UINT64 = 12, // Unsigned 64-bit integer + EP_PARAMETER_TYPE_SINGLE = 13, // IEEE 32-bit float + EP_PARAMETER_TYPE_DOUBLE = 14, // IEEE 64-bit double + EP_PARAMETER_TYPE_DECIMAL = 15, // Decimal + EP_PARAMETER_TYPE_DATE_TIME = 16, // DateTime + EP_PARAMETER_TYPE_GUID = 17, // Guid + EP_PARAMETER_TYPE_STRING = 18, // Unicode character string + EP_PARAMETER_TYPE_ARRAY = 19 // Indicates the type is an arbitrary sized array +} EventPipeParameterType; + +typedef enum { + EP_METADATA_TAG_OPCODE = 1, + EP_METADATA_TAG_PARAMETER_PAYLOAD = 2 +} EventPipeMetadataTag; + +typedef enum { + EP_SAMPLE_PROFILER_SAMPLE_TYPE_ERROR = 0, + EP_SAMPLE_PROFILER_SAMPLE_TYPE_EXTERNAL = 1, + EP_SAMPLE_PROFILER_SAMPLE_TYPE_MANAGED = 2 +} EventPipeSampleProfilerSampleType; + +typedef enum { + // Default format used in .Net Core 2.0-3.0 Preview 6 + // TBD - it may remain the default format .Net Core 3.0 when + // used with private EventPipe managed API via reflection. + // This format had limited official exposure in documented + // end-user RTM scenarios, but it is supported by PerfView, + // TraceEvent, and was used by AI profiler. + EP_SERIALIZATION_FORMAT_NETPERF_V3, + // Default format we plan to use in .Net Core 3 Preview7+ + // for most if not all scenarios. + EP_SERIALIZATION_FORMAT_NETTRACE_V4, + EP_SERIALIZATION_FORMAT_COUNT +} EventPipeSerializationFormat; + +typedef enum { + EP_SESSION_TYPE_FILE, + EP_SESSION_TYPE_LISTENER, + EP_SESSION_TYPE_IPCSTREAM, + EP_SESSION_TYPE_SYNCHRONOUS +} EventPipeSessionType ; + +typedef enum { + EP_STATE_NOT_INITIALIZED, + EP_STATE_INITIALIZED, + EP_STATE_SHUTTING_DOWN +} EventPipeState; + +typedef enum { + EP_THREAD_TYPE_SERVER, + EP_THREAD_TYPE_SESSION, + EP_THREAD_TYPE_SAMPLING +} EventPipeThreadType; + +/* + * EventPipe Basic Types. + */ + +typedef intptr_t EventPipeWaitHandle; +typedef uint64_t EventPipeSessionID; +typedef unsigned short ep_char16_t; +typedef int64_t ep_timestamp_t; +typedef int64_t ep_system_timestamp_t; + +/* + * EventPipe Callbacks. + */ + +// Define the event pipe callback to match the ETW callback signature. +typedef void (*EventPipeCallback)( + const uint8_t *source_id, + unsigned long is_enabled, + uint8_t level, + uint64_t match_any_keywords, + uint64_t match_all_keywords, + EventFilterDescriptor *filter_data, + void *callback_data); + +typedef void (*EventPipeCallbackDataFree)( + EventPipeCallback callback, + void *callback_data); + +typedef void (*EventPipeSessionSynchronousCallback)( + EventPipeProvider *provider, + uint32_t event_id, + uint32_t event_version, + uint32_t metadata_blob_len, + const uint8_t *metadata_blob, + uint32_t event_data_len, + const uint8_t *event_data, + const uint8_t *activity_id, + const uint8_t *related_activity_id, + /*ep_rt_thread_handle_t*/ void *event_thread, + uint32_t stack_frames_len, + uintptr_t *stack_frames); + +#endif /* ENABLE_PERFTRACING */ +#endif /* __EVENTPIPE_TYPES_FORWARD_H__ */ diff --git a/src/native/eventpipe/ep-types.h b/src/native/eventpipe/ep-types.h index 0c91757fcfbe95..22ad3a749bf865 100644 --- a/src/native/eventpipe/ep-types.h +++ b/src/native/eventpipe/ep-types.h @@ -10,206 +10,10 @@ #endif #include "ep-getter-setter.h" -/* - * EventPipe Structs. - */ - -typedef struct _EventData EventData; -typedef struct _EventFilterDescriptor EventFilterDescriptor; -typedef struct _EventPipeBuffer EventPipeBuffer; -typedef struct _EventPipeBufferList EventPipeBufferList; -typedef struct _EventPipeBufferManager EventPipeBufferManager; -typedef struct _EventPipeBlock EventPipeBlock; -typedef struct _EventPipeBlockVtable EventPipeBlockVtable; -typedef struct _EventPipeConfiguration EventPipeConfiguration; -typedef struct _EventPipeEvent EventPipeEvent; -typedef struct _EventPipeEventBlockBase EventPipeEventBlockBase; -typedef struct _EventPipeEventBlock EventPipeEventBlock; -typedef struct _EventPipeEventHeader EventPipeEventHeader; -typedef struct _EventPipeEventInstance EventPipeEventInstance; -typedef struct _EventPipeEventMetadataEvent EventPipeEventMetadataEvent; -typedef struct _EventPipeEventPayload EventPipeEventPayload; -typedef struct _EventPipeEventSource EventPipeEventSource; -typedef struct _EventPipeFile EventPipeFile; -typedef struct _EventPipeJsonFile EventPipeJsonFile; -typedef struct _EventPipeMetadataBlock EventPipeMetadataBlock; -typedef struct _EventPipeParameterDesc EventPipeParameterDesc; -typedef struct _EventPipeProvider EventPipeProvider; -typedef struct _EventPipeProviderCallbackData EventPipeProviderCallbackData; -typedef struct _EventPipeProviderCallbackDataQueue EventPipeProviderCallbackDataQueue; -typedef struct _EventPipeProviderConfiguration EventPipeProviderConfiguration; -typedef struct _EventPipeSession EventPipeSession; -typedef struct _EventPipeSessionProvider EventPipeSessionProvider; -typedef struct _EventPipeSessionProviderList EventPipeSessionProviderList; -typedef struct _EventPipeSequencePoint EventPipeSequencePoint; -typedef struct _EventPipeSequencePointBlock EventPipeSequencePointBlock; -typedef struct _EventPipeStackBlock EventPipeStackBlock; -typedef struct _EventPipeStackContents EventPipeStackContents; -typedef struct _EventPipeSystemTime EventPipeSystemTime; -typedef struct _EventPipeThread EventPipeThread; -typedef struct _EventPipeThreadHolder EventPipeThreadHolder; -typedef struct _EventPipeThreadSessionState EventPipeThreadSessionState; -typedef struct _FastSerializableObject FastSerializableObject; -typedef struct _FastSerializableObjectVtable FastSerializableObjectVtable; -typedef struct _FastSerializer FastSerializer; -typedef struct _FileStream FileStream; -typedef struct _FileStreamWriter FileStreamWriter; -typedef struct _IpcStreamWriter IpcStreamWriter; -typedef struct _StackHashEntry StackHashEntry; -typedef struct _StackHashKey StackHashKey; -typedef struct _StreamWriter StreamWriter; -typedef struct _StreamWriterVtable StreamWriterVtable; - -#define EP_MAX_NUMBER_OF_SESSIONS 64 - -#define EP_GUID_SIZE 16 - -#define EP_ACTIVITY_ID_SIZE EP_GUID_SIZE - -#define EP_MAX_STACK_DEPTH 100 - -/* - * EventPipe Enums. - */ - -typedef enum { - EP_BUFFER_STATE_WRITABLE = 0, - EP_BUFFER_STATE_READ_ONLY = 1 -} EventPipeBufferState; - -typedef enum { - EP_EVENT_LEVEL_LOGALWAYS, - EP_EVENT_LEVEL_CRITICAL, - EP_EVENT_LEVEL_ERROR, - EP_EVENT_LEVEL_WARNING, - EP_EVENT_LEVEL_INFORMATIONAL, - EP_EVENT_LEVEL_VERBOSE -} EventPipeEventLevel; - -typedef enum { - EP_FILE_FLUSH_FLAGS_EVENT_BLOCK = 1, - EP_FILE_FLUSH_FLAGS_METADATA_BLOCK = 2, - EP_FILE_FLUSH_FLAGS_STACK_BLOCK = 4, - EP_FILE_FLUSH_FLAGS_ALL_BLOCKS = EP_FILE_FLUSH_FLAGS_EVENT_BLOCK | EP_FILE_FLUSH_FLAGS_METADATA_BLOCK | EP_FILE_FLUSH_FLAGS_STACK_BLOCK -} EventPipeFileFlushFlags; - -// Represents the type of an event parameter. -// This enum is derived from the managed TypeCode type, though -// not all of these values are available in TypeCode. -// For example, Guid does not exist in TypeCode. -// Keep this in sync with COR_PRF_EVENTPIPE_PARAM_TYPE defined in -// corprof.idl -typedef enum { - EP_PARAMETER_TYPE_EMPTY = 0, // Null reference - EP_PARAMETER_TYPE_OBJECT = 1, // Instance that isn't a value - EP_PARAMETER_TYPE_DB_NULL = 2, // Database null value - EP_PARAMETER_TYPE_BOOLEAN = 3, // Boolean - EP_PARAMETER_TYPE_CHAR = 4, // Unicode character - EP_PARAMETER_TYPE_SBYTE = 5, // Signed 8-bit integer - EP_PARAMETER_TYPE_BYTE = 6, // Unsigned 8-bit integer - EP_PARAMETER_TYPE_INT16 = 7, // Signed 16-bit integer - EP_PARAMETER_TYPE_UINT16 = 8, // Unsigned 16-bit integer - EP_PARAMETER_TYPE_INT32 = 9, // Signed 32-bit integer - EP_PARAMETER_TYPE_UINT32 = 10, // Unsigned 32-bit integer - EP_PARAMETER_TYPE_INT64 = 11, // Signed 64-bit integer - EP_PARAMETER_TYPE_UINT64 = 12, // Unsigned 64-bit integer - EP_PARAMETER_TYPE_SINGLE = 13, // IEEE 32-bit float - EP_PARAMETER_TYPE_DOUBLE = 14, // IEEE 64-bit double - EP_PARAMETER_TYPE_DECIMAL = 15, // Decimal - EP_PARAMETER_TYPE_DATE_TIME = 16, // DateTime - EP_PARAMETER_TYPE_GUID = 17, // Guid - EP_PARAMETER_TYPE_STRING = 18, // Unicode character string - EP_PARAMETER_TYPE_ARRAY = 19 // Indicates the type is an arbitrary sized array -} EventPipeParameterType; - -typedef enum { - EP_METADATA_TAG_OPCODE = 1, - EP_METADATA_TAG_PARAMETER_PAYLOAD = 2 -} EventPipeMetadataTag; - -typedef enum { - EP_SAMPLE_PROFILER_SAMPLE_TYPE_ERROR = 0, - EP_SAMPLE_PROFILER_SAMPLE_TYPE_EXTERNAL = 1, - EP_SAMPLE_PROFILER_SAMPLE_TYPE_MANAGED = 2 -} EventPipeSampleProfilerSampleType; - -typedef enum { - // Default format used in .Net Core 2.0-3.0 Preview 6 - // TBD - it may remain the default format .Net Core 3.0 when - // used with private EventPipe managed API via reflection. - // This format had limited official exposure in documented - // end-user RTM scenarios, but it is supported by PerfView, - // TraceEvent, and was used by AI profiler. - EP_SERIALIZATION_FORMAT_NETPERF_V3, - // Default format we plan to use in .Net Core 3 Preview7+ - // for most if not all scenarios. - EP_SERIALIZATION_FORMAT_NETTRACE_V4, - EP_SERIALIZATION_FORMAT_COUNT -} EventPipeSerializationFormat; - -typedef enum { - EP_SESSION_TYPE_FILE, - EP_SESSION_TYPE_LISTENER, - EP_SESSION_TYPE_IPCSTREAM, - EP_SESSION_TYPE_SYNCHRONOUS -} EventPipeSessionType ; - -typedef enum { - EP_STATE_NOT_INITIALIZED, - EP_STATE_INITIALIZED, - EP_STATE_SHUTTING_DOWN -} EventPipeState; - -typedef enum { - EP_THREAD_TYPE_SERVER, - EP_THREAD_TYPE_SESSION, - EP_THREAD_TYPE_SAMPLING -} EventPipeThreadType; - -/* - * EventPipe Basic Types. - */ - -typedef intptr_t EventPipeWaitHandle; -typedef uint64_t EventPipeSessionID; -typedef unsigned short ep_char16_t; -typedef int64_t ep_timestamp_t; -typedef int64_t ep_system_timestamp_t; +#include "ep-types-forward.h" #include "ep-rt-types.h" -/* - * EventPipe Callbacks. - */ - -// Define the event pipe callback to match the ETW callback signature. -typedef void (*EventPipeCallback)( - const uint8_t *source_id, - unsigned long is_enabled, - uint8_t level, - uint64_t match_any_keywords, - uint64_t match_all_keywords, - EventFilterDescriptor *filter_data, - void *callback_data); - -typedef void (*EventPipeCallbackDataFree)( - EventPipeCallback callback, - void *callback_data); - -typedef void (*EventPipeSessionSynchronousCallback)( - EventPipeProvider *provider, - uint32_t event_id, - uint32_t event_version, - uint32_t metadata_blob_len, - const uint8_t *metadata_blob, - uint32_t event_data_len, - const uint8_t *event_data, - const uint8_t *activity_id, - const uint8_t *related_activity_id, - ep_rt_thread_handle_t event_thread, - uint32_t stack_frames_len, - uintptr_t *stack_frames); - /* * EventFilterDescriptor. */ From 93143721c75744a60e1e52ded205af94d898abb5 Mon Sep 17 00:00:00 2001 From: lateralusX Date: Mon, 29 Mar 2021 14:24:03 +0200 Subject: [PATCH 19/55] Export needed Mono API's used by component. --- src/mono/mono/metadata/class-internals.h | 2 ++ src/mono/mono/metadata/gc-internals.h | 5 +++-- src/mono/mono/metadata/object-internals.h | 2 ++ src/mono/mono/metadata/threads-types.h | 2 +- src/mono/mono/metadata/w32event.h | 4 ++++ src/mono/mono/metadata/w32file.h | 3 +++ src/mono/mono/metadata/w32handle.h | 2 ++ src/mono/mono/utils/mono-compiler.h | 2 ++ src/mono/mono/utils/mono-rand.h | 4 ++++ src/mono/mono/utils/mono-threads.h | 5 ++++- src/mono/mono/utils/mono-time.h | 2 +- 11 files changed, 28 insertions(+), 5 deletions(-) diff --git a/src/mono/mono/metadata/class-internals.h b/src/mono/mono/metadata/class-internals.h index 233e4ecc9b655e..2889d03722304e 100644 --- a/src/mono/mono/metadata/class-internals.h +++ b/src/mono/mono/metadata/class-internals.h @@ -16,6 +16,7 @@ #include "mono/sgen/gc-internal-agnostic.h" #include "mono/utils/mono-error-internals.h" #include "mono/utils/mono-memory-model.h" +#include "mono/utils/mono-compiler.h" #define MONO_CLASS_IS_ARRAY(c) (m_class_get_rank (c)) @@ -1126,6 +1127,7 @@ mono_identifier_escape_type_name_chars (const char* identifier); char* mono_type_get_full_name (MonoClass *klass); +MONO_COMPONENT_API char * mono_method_get_name_full (MonoMethod *method, gboolean signature, gboolean ret, MonoTypeNameFormat format); diff --git a/src/mono/mono/metadata/gc-internals.h b/src/mono/mono/metadata/gc-internals.h index f52deb7dbda4d8..34203f25357957 100644 --- a/src/mono/mono/metadata/gc-internals.h +++ b/src/mono/mono/metadata/gc-internals.h @@ -18,6 +18,7 @@ #include #include #include +#include /* Register a memory area as a conservatively scanned GC root */ #define MONO_GC_REGISTER_ROOT_PINNING(x,src,key,msg) mono_gc_register_root ((char*)&(x), sizeof(x), MONO_GC_DESCRIPTOR_NULL, (src), (key), (msg)) @@ -426,7 +427,7 @@ extern gchar **mono_do_not_finalize_class_names; * Unified runtime stop/restart world, SGEN Only. * Will take and release the LOCK_GC. */ -void mono_stop_world (MonoThreadInfoFlags flags); -void mono_restart_world (MonoThreadInfoFlags flags); +MONO_COMPONENT_API void mono_stop_world (MonoThreadInfoFlags flags); +MONO_COMPONENT_API void mono_restart_world (MonoThreadInfoFlags flags); #endif /* __MONO_METADATA_GC_INTERNAL_H__ */ diff --git a/src/mono/mono/metadata/object-internals.h b/src/mono/mono/metadata/object-internals.h index 8ba20f76b8d037..49af8f525f91e7 100644 --- a/src/mono/mono/metadata/object-internals.h +++ b/src/mono/mono/metadata/object-internals.h @@ -691,6 +691,7 @@ mono_get_runtime_callbacks (void); void mono_install_eh_callbacks (MonoRuntimeExceptionHandlingCallbacks *cbs); +MONO_COMPONENT_API MonoRuntimeExceptionHandlingCallbacks * mono_get_eh_callbacks (void); @@ -1795,6 +1796,7 @@ mono_string_from_utf32_checked (const mono_unichar4 *data, MonoError *error); char* mono_ldstr_utf8 (MonoImage *image, guint32 idx, MonoError *error); +MONO_COMPONENT_API char* mono_utf16_to_utf8 (const mono_unichar2 *s, gsize slength, MonoError *error); diff --git a/src/mono/mono/metadata/threads-types.h b/src/mono/mono/metadata/threads-types.h index b9c963721d58e2..e3869ca5b5fdd5 100644 --- a/src/mono/mono/metadata/threads-types.h +++ b/src/mono/mono/metadata/threads-types.h @@ -207,7 +207,7 @@ void mono_thread_internal_unhandled_exception (MonoObject* exc); void mono_alloc_special_static_data_free (GHashTable *special_static_fields); -void mono_thread_set_state (MonoInternalThread *thread, MonoThreadState state); +MONO_COMPONENT_API void mono_thread_set_state (MonoInternalThread *thread, MonoThreadState state); void mono_thread_clr_state (MonoInternalThread *thread, MonoThreadState state); gboolean mono_thread_test_state (MonoInternalThread *thread, MonoThreadState test); gboolean mono_thread_test_and_set_state (MonoInternalThread *thread, MonoThreadState test, MonoThreadState set); diff --git a/src/mono/mono/metadata/w32event.h b/src/mono/mono/metadata/w32event.h index 74a045cc4dd0db..8f88ce09450239 100644 --- a/src/mono/mono/metadata/w32event.h +++ b/src/mono/mono/metadata/w32event.h @@ -12,16 +12,20 @@ #include "object-internals.h" #include "w32handle.h" #include +#include void mono_w32event_init (void); +MONO_COMPONENT_API gpointer mono_w32event_create (gboolean manual, gboolean initial); +MONO_COMPONENT_API gboolean mono_w32event_close (gpointer handle); +MONO_COMPONENT_API void mono_w32event_set (gpointer handle); diff --git a/src/mono/mono/metadata/w32file.h b/src/mono/mono/metadata/w32file.h index 2700933c98bc38..86e1c05f397e1a 100644 --- a/src/mono/mono/metadata/w32file.h +++ b/src/mono/mono/metadata/w32file.h @@ -142,12 +142,15 @@ typedef struct { void mono_w32file_init (void); +MONO_COMPONENT_API gpointer mono_w32file_create(const gunichar2 *name, guint32 fileaccess, guint32 sharemode, guint32 createmode, guint32 attrs); +MONO_COMPONENT_API gboolean mono_w32file_close (gpointer handle); +MONO_COMPONENT_API gboolean mono_w32file_write (gpointer handle, gconstpointer buffer, guint32 numbytes, guint32 *byteswritten, gint32 *win32error); diff --git a/src/mono/mono/metadata/w32handle.h b/src/mono/mono/metadata/w32handle.h index c985e793232fb6..6ec82b812e0772 100644 --- a/src/mono/mono/metadata/w32handle.h +++ b/src/mono/mono/metadata/w32handle.h @@ -16,6 +16,7 @@ #include "mono/utils/mono-coop-mutex.h" #include "mono/utils/mono-error.h" +#include #define MONO_W32HANDLE_MAXIMUM_WAIT_OBJECTS 64 #define MONO_INFINITE_WAIT ((guint32) 0xFFFFFFFF) @@ -136,6 +137,7 @@ mono_w32handle_lock (MonoW32Handle *handle_data); void mono_w32handle_unlock (MonoW32Handle *handle_data); +MONO_COMPONENT_API MonoW32HandleWaitRet mono_w32handle_wait_one (gpointer handle, guint32 timeout, gboolean alertable); diff --git a/src/mono/mono/utils/mono-compiler.h b/src/mono/mono/utils/mono-compiler.h index 71d5c60c70d35a..4f9f87239fc7f6 100644 --- a/src/mono/mono/utils/mono-compiler.h +++ b/src/mono/mono/utils/mono-compiler.h @@ -14,6 +14,8 @@ #include #endif +#include + #ifdef __GNUC__ #define MONO_ATTR_USED __attribute__ ((__used__)) #else diff --git a/src/mono/mono/utils/mono-rand.h b/src/mono/mono/utils/mono-rand.h index 2f3b6aaa36cff3..4ce397aa8e4f75 100644 --- a/src/mono/mono/utils/mono-rand.h +++ b/src/mono/mono/utils/mono-rand.h @@ -10,18 +10,22 @@ #include "mono-compiler.h" #include "mono-error.h" +MONO_COMPONENT_API gboolean mono_rand_open (void); +MONO_COMPONENT_API gpointer mono_rand_init (const guchar *seed, gssize seed_size); +MONO_COMPONENT_API gboolean mono_rand_try_get_bytes (gpointer *handle, guchar *buffer, gssize buffer_size, MonoError *error); gboolean mono_rand_try_get_uint32 (gpointer *handle, guint32 *val, guint32 min, guint32 max, MonoError *error); +MONO_COMPONENT_API void mono_rand_close (gpointer handle); diff --git a/src/mono/mono/utils/mono-threads.h b/src/mono/mono/utils/mono-threads.h index bb1ce35d825d88..a6b1b2544a4462 100644 --- a/src/mono/mono/utils/mono-threads.h +++ b/src/mono/mono/utils/mono-threads.h @@ -452,6 +452,7 @@ mono_thread_info_unset_internal_thread_gchandle (THREAD_INFO_TYPE *info); gboolean mono_thread_info_is_exiting (void); +MONO_COMPONENT_API #ifdef HOST_WIN32 G_EXTERN_C // due to THREAD_INFO_TYPE varying #endif @@ -471,6 +472,7 @@ mono_thread_info_current_unchecked (void); MONO_API int mono_thread_info_get_small_id (void); +MONO_COMPONENT_API MonoLinkedListSet* mono_thread_info_list_head (void); @@ -764,6 +766,7 @@ gboolean mono_threads_transition_peek_blocking_suspend_requested (THREAD_INFO_TY void mono_threads_transition_begin_no_safepoints (THREAD_INFO_TYPE* info, const char *func); void mono_threads_transition_end_no_safepoints (THREAD_INFO_TYPE* info, const char *func); +MONO_COMPONENT_API G_EXTERN_C // due to THREAD_INFO_TYPE varying MonoThreadUnwindState* mono_thread_info_get_suspend_state (THREAD_INFO_TYPE *info); @@ -774,7 +777,7 @@ mono_threads_enter_gc_unsafe_region_cookie (void); void mono_thread_info_wait_for_resume (THREAD_INFO_TYPE *info); /* Advanced suspend API, used for suspending multiple threads as once. */ G_EXTERN_C // due to THREAD_INFO_TYPE varying -gboolean mono_thread_info_is_running (THREAD_INFO_TYPE *info); +MONO_COMPONENT_API gboolean mono_thread_info_is_running (THREAD_INFO_TYPE *info); gboolean mono_thread_info_is_live (THREAD_INFO_TYPE *info); G_EXTERN_C // due to THREAD_INFO_TYPE varying int mono_thread_info_suspend_count (THREAD_INFO_TYPE *info); diff --git a/src/mono/mono/utils/mono-time.h b/src/mono/mono/utils/mono-time.h index 921efbbc61a95c..874a4677c693ac 100644 --- a/src/mono/mono/utils/mono-time.h +++ b/src/mono/mono/utils/mono-time.h @@ -20,7 +20,7 @@ gint64 mono_msec_boottime (void); gint64 mono_msec_ticks (void); /* Returns the number of 100ns ticks from unspecified time: this should be monotonic */ -gint64 mono_100ns_ticks (void); +MONO_COMPONENT_API gint64 mono_100ns_ticks (void); /* Returns the number of 100ns ticks since 1/1/1601, UTC timezone */ gint64 mono_100ns_datetime (void); From fad70f71957799d85a47f681411812900298d2ee Mon Sep 17 00:00:00 2001 From: lateralusX Date: Mon, 29 Mar 2021 14:25:32 +0200 Subject: [PATCH 20/55] Correctly export/import symbols on Windows. --- src/mono/CMakeLists.txt | 1 - src/mono/mono/component/CMakeLists.txt | 4 +--- src/mono/mono/mini/CMakeLists.txt | 19 +++++++++++++++---- 3 files changed, 16 insertions(+), 8 deletions(-) diff --git a/src/mono/CMakeLists.txt b/src/mono/CMakeLists.txt index 1437fc59feb482..4f5678898cb182 100644 --- a/src/mono/CMakeLists.txt +++ b/src/mono/CMakeLists.txt @@ -106,7 +106,6 @@ if(DISABLE_INTERPRETER) endif() add_definitions(-DHAVE_CONFIG_H) -add_definitions(-DMONO_DLL_EXPORT) if(GCC) add_definitions(-g) # TODO: should this really be on by default? diff --git a/src/mono/mono/component/CMakeLists.txt b/src/mono/mono/component/CMakeLists.txt index 51935f62140023..eec30ea93cf3ad 100644 --- a/src/mono/mono/component/CMakeLists.txt +++ b/src/mono/mono/component/CMakeLists.txt @@ -1,5 +1,3 @@ - - # a list of every component. set(components "") @@ -71,7 +69,7 @@ endforeach() if (NOT STATIC_COMPONENTS) # define a shared library for each component foreach (component IN LISTS components) - target_compile_definitions ("${component}-objects" PRIVATE -DCOMPILING_COMPONENT_DYNAMIC) + target_compile_definitions ("${component}-objects" PRIVATE -DCOMPILING_COMPONENT_DYNAMIC;-DMONO_DLL_IMPORT) add_library("mono-component-${component}" SHARED $) if (NOT DISABLE_SHARED_LIBS) # each shared library component gets its own copy for eglib diff --git a/src/mono/mono/mini/CMakeLists.txt b/src/mono/mono/mini/CMakeLists.txt index c3da713698791d..4a0051a16dc4b1 100644 --- a/src/mono/mono/mini/CMakeLists.txt +++ b/src/mono/mono/mini/CMakeLists.txt @@ -228,8 +228,6 @@ set(windows_sources mini-windows.c mini-windows-tls-callback.c mini-windows.h - mini-windows-dllmain.c - # mini-windows-dlldac.c ) set(posix_sources @@ -309,10 +307,13 @@ set(OS_LIBS bcrypt.lib Mswsock.lib ws2_32.lib psapi.lib version.lib advapi32.lib set(mini_sources "${mini_sources};${PROJECT_BINARY_DIR}/../../NativeVersion.rc") # this is generated by GenerateMonoVersionFile in mono.proj endif() -add_library(monosgen-objects OBJECT "${eglib_sources};${metadata_sources};${utils_sources};${sgen_sources};${icu_shim_sources};${mini_sources};${zlib_sources}") +set(monosgen-sources "${metadata_sources};${utils_sources};${sgen_sources};${icu_shim_sources};${mini_sources};${zlib_sources}") + +add_library(monosgen-objects OBJECT "${monosgen-sources}") add_library(monosgen-static STATIC $) set_target_properties(monosgen-static PROPERTIES OUTPUT_NAME monosgen-2.0) target_link_libraries(monosgen-static eglib_objects) + if(NOT DISABLE_LIBS) install(TARGETS monosgen-static LIBRARY) install(FILES ${metadata_public_headers} @@ -323,7 +324,12 @@ if(NOT DISABLE_LIBS) DESTINATION ${CMAKE_INSTALL_INCLUDEDIR}/mono-2.0/mono/jit) endif() if(NOT DISABLE_SHARED_LIBS) - add_library(monosgen-shared SHARED $ ) + if(HOST_WIN32) + add_library(monosgen-shared SHARED "mini-windows-dllmain.c;${monosgen-sources}") + target_compile_definitions(monosgen-shared PRIVATE -DMONO_DLL_EXPORT) + else() + add_library(monosgen-shared SHARED $ ) + endif() target_link_libraries(monosgen-shared eglib_objects) set_target_properties(monosgen-shared PROPERTIES OUTPUT_NAME monosgen-2.0) if(TARGET_WIN32) @@ -350,6 +356,11 @@ if(NOT DISABLE_SHARED_LIBS) target_link_libraries (monosgen-shared components_stubs_objects) endif() install(TARGETS monosgen-shared LIBRARY) + if(HOST_WIN32) + add_library(monosgen-shared-dac SHARED "mini-windows-dlldac.c") + set_target_properties(monosgen-shared-dac PROPERTIES OUTPUT_NAME monosgen-2.0-dac) + install(TARGETS monosgen-shared-dac LIBRARY) + endif() endif() find_package(Python3 COMPONENTS Interpreter) From 31d1cd40b117fe3007ee53be73d0bc00ec0f9230 Mon Sep 17 00:00:00 2001 From: lateralusX Date: Mon, 29 Mar 2021 16:46:28 +0200 Subject: [PATCH 21/55] Resolve components_dir based on coreclr location. --- src/mono/mono/metadata/components.c | 7 ++----- 1 file changed, 2 insertions(+), 5 deletions(-) diff --git a/src/mono/mono/metadata/components.c b/src/mono/mono/metadata/components.c index f8a0f5dc32c8ff..e8cab3ccee1ab8 100644 --- a/src/mono/mono/metadata/components.c +++ b/src/mono/mono/metadata/components.c @@ -4,6 +4,7 @@ #include #include +#include #include "mono/component/component.h" #include "mono/component/hot_reload.h" #include "mono/component/event_pipe.h" @@ -133,12 +134,8 @@ components_dir (void) { static char *dir = NULL; if (!dir) { - /* FIXME: this is right for self-contained apps, but if we're - * started by a host, the components are next to - * libmonosgen-2.0.so, not next to the host app. - */ char buf[4096]; - if (mono_dl_get_executable_path (buf, sizeof(buf)) != -1) { + if (g_module_address ((void *)components_dir, buf, sizeof (buf), NULL, NULL, 0, NULL)) { char *resolvedname = mono_path_resolve_symlinks (buf); dir = g_path_get_dirname (resolvedname); g_free (resolvedname); From 3f87923e1f5b37bef93abe584a34009b2ced7960 Mon Sep 17 00:00:00 2001 From: lateralusX Date: Mon, 29 Mar 2021 18:12:07 +0200 Subject: [PATCH 22/55] Keep eventpipe/diagnostic server sources separated until added to component. --- src/mono/mono/component/CMakeLists.txt | 1 + src/mono/mono/eventpipe/CMakeLists.txt | 40 +++++++++++++++++++++++--- src/native/eventpipe/ds-ipc.c | 2 +- src/native/eventpipe/ds-rt-config.h | 6 ++-- src/native/eventpipe/ds-server.c | 2 +- 5 files changed, 42 insertions(+), 9 deletions(-) diff --git a/src/mono/mono/component/CMakeLists.txt b/src/mono/mono/component/CMakeLists.txt index eec30ea93cf3ad..5eacecc299e174 100644 --- a/src/mono/mono/component/CMakeLists.txt +++ b/src/mono/mono/component/CMakeLists.txt @@ -34,6 +34,7 @@ if(ENABLE_PERFTRACING) set(event_pipe-sources_base ${eventpipe_sources} + ${diagnostic_server_sources} event_pipe.c event_pipe.h diagnostics_server.c diff --git a/src/mono/mono/eventpipe/CMakeLists.txt b/src/mono/mono/eventpipe/CMakeLists.txt index 7dad16975afdc6..f7ee1e3c0bdde2 100644 --- a/src/mono/mono/eventpipe/CMakeLists.txt +++ b/src/mono/mono/eventpipe/CMakeLists.txt @@ -1,33 +1,56 @@ if(ENABLE_PERFTRACING) if (FEATURE_PERFTRACING_PAL_TCP) - add_definitions(-DFEATURE_PERFTRACING_PAL_TCP) + add_definitions(-DENABLE_PERFTRACING_PAL_TCP) endif (FEATURE_PERFTRACING_PAL_TCP) + if (FEATURE_PERFTRACING_DISABLE_LISTEN_PORTS) + add_definitions(-DENABLE_PERFTRACING_DISABLE_LISTEN_PORTS) + endif (FEATURE_PERFTRACING_DISABLE_LISTEN_PORTS) + + if (FEATURE_PERFTRACING_DISABLE_CONNECT_PORTS) + add_definitions(-DENABLE_PERFTRACING_DISABLE_CONNECT_PORTS) + endif (FEATURE_PERFTRACING_DISABLE_CONNECT_PORTS) + include (${SHARED_EVENTPIPE_SOURCE_PATH}CMakeLists.txt) set(MONO_EVENTPIPE_SHIM_SOURCES "") set(MONO_EVENTPIPE_SHIM_HEADERS "") + set(MONO_DIAGNOSTIC_SERVER_SHIM_SOURCES "") + set(MONO_DIAGNOSTIC_SERVER_SHIM_HEADERS "") + list(APPEND MONO_EVENTPIPE_SHIM_SOURCES - ds-rt-mono.c ep-rt-mono.c ) + list(APPEND MONO_DIAGNOSTIC_SERVER_SHIM_SOURCES + ds-rt-mono.c + ) + list(APPEND MONO_EVENTPIPE_SHIM_HEADERS - ds-rt-mono.h - ds-rt-types-mono.h ep-rt-config-mono.h ep-rt-mono.h ep-rt-types-mono.h ) + list(APPEND MONO_DIAGNOSTIC_SERVER_SHIM_HEADERS + ds-rt-mono.h + ds-rt-types-mono.h + ) + set(shared_eventpipe_sources_base "") set(mono_eventpipe_shim_sources_base "") + set(shared_diagnostic_server_sources_base "") + set(mono_diagnostic_server_shim_sources_base "") + list(APPEND shared_eventpipe_sources_base ${SHARED_EVENTPIPE_SOURCES} ${SHARED_EVENTPIPE_HEADERS} + ) + + list(APPEND shared_diagnostic_server_sources_base ${SHARED_DIAGNOSTIC_SERVER_SOURCES} ${SHARED_DIAGNOSTIC_SERVER_HEADERS} ${SHARED_DIAGNOSTIC_SERVER_PAL_SOURCES} @@ -39,10 +62,19 @@ if(ENABLE_PERFTRACING) ${MONO_EVENTPIPE_SHIM_HEADERS} ) + list(APPEND mono_diagnostic_server_shim_sources_base + ${MONO_DIAGNOSTIC_SERVER_SHIM_SOURCES} + ${MONO_DIAGNOSTIC_SERVER_SHIM_HEADERS} + ) + addprefix(shared_eventpipe_sources_base ${SHARED_EVENTPIPE_SOURCE_PATH} "${shared_eventpipe_sources_base}") addprefix(mono_eventpipe_shim_sources_base ${MONO_EVENTPIPE_SHIM_SOURCE_PATH} "${mono_eventpipe_shim_sources_base}") + addprefix(shared_diagnostic_server_sources_base ${SHARED_EVENTPIPE_SOURCE_PATH} "${shared_diagnostic_server_sources_base}") + addprefix(mono_diagnostic_server_shim_sources_base ${MONO_EVENTPIPE_SHIM_SOURCE_PATH} "${mono_diagnostic_server_shim_sources_base}") + set(eventpipe_sources ${shared_eventpipe_sources_base} ${mono_eventpipe_shim_sources_base}) + set(diagnostic_server_sources ${shared_diagnostic_server_sources_base} ${mono_diagnostic_server_shim_sources_base}) set_source_files_properties(${SHARED_EVENTPIPE_SOURCE_PATH}/ep-sources.c PROPERTIES COMPILE_DEFINITIONS EP_FORCE_INCLUDE_SOURCE_FILES) set_source_files_properties(${SHARED_EVENTPIPE_SOURCE_PATH}/ds-sources.c PROPERTIES COMPILE_DEFINITIONS DS_FORCE_INCLUDE_SOURCE_FILES) diff --git a/src/native/eventpipe/ds-ipc.c b/src/native/eventpipe/ds-ipc.c index 8493eeab058246..2aa1ca2cb76c07 100644 --- a/src/native/eventpipe/ds-ipc.c +++ b/src/native/eventpipe/ds-ipc.c @@ -164,7 +164,7 @@ ipc_stream_factory_build_and_add_port ( bool result = false; DiagnosticsIpc *ipc = NULL; -#ifndef DS_IPC_PAL_TCP +#ifndef DS_IPC_DISABLE_LISTEN_PORTS if (!default_port && builder->type == DS_PORT_TYPE_LISTEN) { // Ignore listen type (see conversation in https://github.com/dotnet/runtime/pull/40499 for details) DS_LOG_INFO_0 ("ipc_stream_factory_build_and_add_port - Ignoring LISTEN port configuration"); diff --git a/src/native/eventpipe/ds-rt-config.h b/src/native/eventpipe/ds-rt-config.h index 678ee18de2bde9..cb84d7d31afd1b 100644 --- a/src/native/eventpipe/ds-rt-config.h +++ b/src/native/eventpipe/ds-rt-config.h @@ -11,7 +11,7 @@ #define DS_INCLUDE_SOURCE_FILES #endif -#ifdef FEATURE_PERFTRACING_PAL_TCP +#ifdef ENABLE_PERFTRACING_PAL_TCP #define DS_IPC_PAL_TCP #else #ifndef HOST_WIN32 @@ -21,11 +21,11 @@ #endif #endif -#ifdef FEATURE_PERFTRACING_DISABLE_CONNECT_PORTS +#ifdef ENABLE_PERFTRACING_DISABLE_CONNECT_PORTS #define DS_IPC_DISABLE_CONNECT_PORTS #endif -#ifdef FEATURE_PERFTRACING_DISABLE_LISTEN_PORTS +#ifdef ENABLE_PERFTRACING_DISABLE_LISTEN_PORTS #define DS_IPC_DISABLE_LISTEN_PORTS #endif diff --git a/src/native/eventpipe/ds-server.c b/src/native/eventpipe/ds-server.c index 7f9c6866e0341c..dfce6d6860464e 100644 --- a/src/native/eventpipe/ds-server.c +++ b/src/native/eventpipe/ds-server.c @@ -116,7 +116,7 @@ EP_RT_DEFINE_THREAD_FUNC (server_thread) EP_ASSERT (server_volatile_load_shutting_down_state () || ds_ipc_stream_factory_has_active_ports ()); if (!ds_ipc_stream_factory_has_active_ports ()) { -#ifndef DS_IPC_PAL_TCP +#ifndef DS_IPC_DISABLE_LISTEN_PORTS DS_LOG_ERROR_0 ("Diagnostics IPC listener was undefined"); #endif return 1; From a698804497e52c9bcd929eec500c83c664f6d02b Mon Sep 17 00:00:00 2001 From: lateralusX Date: Tue, 30 Mar 2021 11:20:16 +0200 Subject: [PATCH 23/55] Enable Diagnostics TCP PAL for iOS and Android. --- src/mono/mono.proj | 6 +++++- 1 file changed, 5 insertions(+), 1 deletion(-) diff --git a/src/mono/mono.proj b/src/mono/mono.proj index e49863e0b96cb4..8d5a7c2b8a02eb 100644 --- a/src/mono/mono.proj +++ b/src/mono/mono.proj @@ -363,7 +363,6 @@ <_MonoCMakeArgs Include="-DENABLE_MINIMAL=ssa,portability,logging" /> <_MonoCMakeArgs Include="-DENABLE_SIGALTSTACK=1"/> <_MonoCMakeArgs Include="-DDISABLE_CRASH_REPORTING=1"/> - <_MonoCMakeArgs Include="-DENABLE_PERFTRACING=0"/> <_MonoCFLAGS Condition="'$(Platform)' == 'arm'" Include="-march=armv7-a" /> <_MonoCFLAGS Condition="'$(Platform)' == 'arm'" Include="-mtune=cortex-a8" /> @@ -410,6 +409,11 @@ <_MonoCMakeArgs Include="-DENABLE_MSCORDBI=1" /> + + <_MonoCMakeArgs Include="-DFEATURE_PERFTRACING_PAL_TCP=1"/> + <_MonoCMakeArgs Include="-DFEATURE_PERFTRACING_DISABLE_LISTEN_PORTS=1"/> + + <_MonoCMakeArgs Include="-DSTATIC_COMPONENTS=1" /> From aa535720605e93ef59a252ec432c8cb62213cf66 Mon Sep 17 00:00:00 2001 From: lateralusX Date: Tue, 30 Mar 2021 13:28:21 +0200 Subject: [PATCH 24/55] EventPipe/DiagnosticServer as static components. --- src/mono/mono/component/CMakeLists.txt | 16 +++++----- .../mono/component/diagnostics_server-stub.c | 31 ++++++++++--------- src/mono/mono/component/diagnostics_server.h | 1 + src/mono/mono/component/event_pipe-stub.c | 3 +- src/mono/mono/component/event_pipe.h | 1 + src/mono/mono/mini/CMakeLists.txt | 8 ++--- 6 files changed, 32 insertions(+), 28 deletions(-) diff --git a/src/mono/mono/component/CMakeLists.txt b/src/mono/mono/component/CMakeLists.txt index 5eacecc299e174..6e432fd44b31cf 100644 --- a/src/mono/mono/component/CMakeLists.txt +++ b/src/mono/mono/component/CMakeLists.txt @@ -88,14 +88,14 @@ if (NOT STATIC_COMPONENTS) install(TARGETS "mono-component-${component}" LIBRARY) endforeach() - # define a single components_stubs_objects target that will be linked into + # define a single static library mono-components-stubs-static that will be linked into # the runtime to be used as fallbacks if the dynamic components are not # available - add_library (components_stubs_objects OBJECT) + add_library ("mono-components-stubs-static" STATIC) foreach (component IN LISTS components) - target_sources (components_stubs_objects PRIVATE ${${component}-stub-sources}) + target_sources ("mono-components-stubs-static" PRIVATE $) endforeach() - target_link_libraries(components_stubs_objects component_base) + target_link_libraries("mono-components-stubs-static" component_base) else() @@ -109,11 +109,11 @@ else() install(TARGETS "mono-component-${component}-stub-static" LIBRARY) endforeach() - # define a single components_static_objects target for mini if building a shared libmono with static-linked components - add_library (components_static_objects OBJECT) + # define a single static library mono-components-static for mini if building a shared libmono with static-linked components + add_library ("mono-components-static" STATIC) foreach (component IN LISTS components) - target_sources (components_static_objects PRIVATE ${${component}-sources}) + target_sources ("mono-components-static" PRIVATE $) endforeach() - target_link_libraries(components_static_objects component_base) + target_link_libraries("mono-components-static" component_base) endif() diff --git a/src/mono/mono/component/diagnostics_server-stub.c b/src/mono/mono/component/diagnostics_server-stub.c index e9c04c204e8247..e625943aad86dc 100644 --- a/src/mono/mono/component/diagnostics_server-stub.c +++ b/src/mono/mono/component/diagnostics_server-stub.c @@ -6,6 +6,7 @@ #ifdef ENABLE_PERFTRACING #include "mono/component/diagnostics_server.h" +#include "mono/metadata/components.h" /* * Forward declares of all static functions. @@ -34,21 +35,6 @@ static MonoComponentDiagnosticsServer fn_table = { &diagnostics_server_stub_disable }; -#ifdef STATIC_COMPONENTS -MONO_COMPONENT_EXPORT_ENTRYPOINT -MonoComponentDiagnosticsServer * -mono_component_diagnostics_server_init (void) -{ - return mono_component_diagnostics_server_stub_init (); -} -#endif - -MonoComponentDiagnosticsServer * -mono_component_diagnostics_server_stub_init (void) -{ - return &fn_table; -} - static void diagnostics_server_stub_cleanup (MonoComponent *self) { @@ -73,4 +59,19 @@ static void diagnostics_server_stub_disable (void) { } + +#ifdef STATIC_COMPONENTS +MONO_COMPONENT_EXPORT_ENTRYPOINT +MonoComponentDiagnosticsServer * +mono_component_diagnostics_server_init (void) +{ + return mono_component_diagnostics_server_stub_init (); +} +#endif + +MonoComponentDiagnosticsServer * +mono_component_diagnostics_server_stub_init (void) +{ + return &fn_table; +} #endif /* ENABLE_PERFTRACING */ diff --git a/src/mono/mono/component/diagnostics_server.h b/src/mono/mono/component/diagnostics_server.h index 89aeef9f2b02ba..5f5a41a23576c7 100644 --- a/src/mono/mono/component/diagnostics_server.h +++ b/src/mono/mono/component/diagnostics_server.h @@ -7,6 +7,7 @@ #ifdef ENABLE_PERFTRACING #include "mono/component/component.h" +#include "mono/utils/mono-compiler.h" typedef struct _MonoComponentDiagnosticsServer { MonoComponent component; diff --git a/src/mono/mono/component/event_pipe-stub.c b/src/mono/mono/component/event_pipe-stub.c index bc634afd56c92a..1384dfde362be6 100644 --- a/src/mono/mono/component/event_pipe-stub.c +++ b/src/mono/mono/component/event_pipe-stub.c @@ -6,6 +6,7 @@ #ifdef ENABLE_PERFTRACING #include "mono/component/event_pipe.h" +#include "mono/metadata/components.h" static EventPipeSessionID _dummy_session_id; @@ -238,7 +239,7 @@ event_pipe_stub_thread_ctrl_activity_id ( #ifdef STATIC_COMPONENTS MONO_COMPONENT_EXPORT_ENTRYPOINT -MonoComponentEventpipe * +MonoComponentEventPipe * mono_component_event_pipe_init (void) { return mono_component_event_pipe_stub_init (); diff --git a/src/mono/mono/component/event_pipe.h b/src/mono/mono/component/event_pipe.h index c0bf25309d39ff..11b81a53857da0 100644 --- a/src/mono/mono/component/event_pipe.h +++ b/src/mono/mono/component/event_pipe.h @@ -8,6 +8,7 @@ #ifdef ENABLE_PERFTRACING #include +#include "mono/utils/mono-compiler.h" #include #include diff --git a/src/mono/mono/mini/CMakeLists.txt b/src/mono/mono/mini/CMakeLists.txt index 4a0051a16dc4b1..e22132de22b845 100644 --- a/src/mono/mono/mini/CMakeLists.txt +++ b/src/mono/mono/mini/CMakeLists.txt @@ -350,10 +350,10 @@ if(NOT DISABLE_SHARED_LIBS) if (STATIC_COMPONENTS) # if components are built statically, but we're building a shared lib mono, # link them into the library - target_link_libraries (monosgen-shared components_static_objects) + target_link_libraries (monosgen-shared "mono-components-static") else() # if components are built dynamically, link the fallback stubs into the runtime - target_link_libraries (monosgen-shared components_stubs_objects) + target_link_libraries (monosgen-shared "mono-components-stubs-static") endif() install(TARGETS monosgen-shared LIBRARY) if(HOST_WIN32) @@ -406,9 +406,9 @@ if(NOT DISABLE_EXECUTABLES) add_executable(mono-sgen "${sgen_sources}") target_link_libraries(mono-sgen monosgen-static ${OS_LIBS} ${ICONV_LIB} ${LLVM_LIBS} ${ICU_LIBS}) if (STATIC_COMPONENTS) - target_link_libraries(mono-sgen components_static_objects) + target_link_libraries(mono-sgen "mono-components-static") else() - target_link_libraries(mono-sgen components_stubs_objects) + target_link_libraries(mono-sgen "mono-components-stubs-static") endif() if(ICU_LDFLAGS) set_property(TARGET mono-sgen APPEND_STRING PROPERTY LINK_FLAGS " ${ICU_LDFLAGS}") From 63ea63a8587854ab054e260a46984cd4da9bf80f Mon Sep 17 00:00:00 2001 From: lateralusX Date: Tue, 30 Mar 2021 16:58:38 +0200 Subject: [PATCH 25/55] Fix EventPipe tests after switching to component based arch. --- src/mono/mono/component/CMakeLists.txt | 8 ++- src/mono/mono/eventpipe/ep-rt-mono.c | 19 ++++--- src/mono/mono/eventpipe/ep-rt-mono.h | 52 ++++--------------- src/mono/mono/eventpipe/test/CMakeLists.txt | 9 ++-- .../eventpipe/test/ep-buffer-manager-tests.c | 2 +- src/mono/mono/eventpipe/test/ep-setup-tests.c | 2 + src/mono/mono/eventpipe/test/ep-tests-debug.h | 3 ++ .../mono/eventpipe/test/ep-thread-tests.c | 2 + src/mono/mono/mini/CMakeLists.txt | 2 +- 9 files changed, 44 insertions(+), 55 deletions(-) diff --git a/src/mono/mono/component/CMakeLists.txt b/src/mono/mono/component/CMakeLists.txt index 6e432fd44b31cf..263addd50eba3d 100644 --- a/src/mono/mono/component/CMakeLists.txt +++ b/src/mono/mono/component/CMakeLists.txt @@ -70,8 +70,12 @@ endforeach() if (NOT STATIC_COMPONENTS) # define a shared library for each component foreach (component IN LISTS components) - target_compile_definitions ("${component}-objects" PRIVATE -DCOMPILING_COMPONENT_DYNAMIC;-DMONO_DLL_IMPORT) - add_library("mono-component-${component}" SHARED $) + if(HOST_WIN32) + add_library("mono-component-${component}" SHARED "${${component}-sources}") + else() + add_library("mono-component-${component}" SHARED $) + endif() + target_compile_definitions ("mono-component-${component}" PRIVATE -DCOMPILING_COMPONENT_DYNAMIC;-DMONO_DLL_IMPORT) if (NOT DISABLE_SHARED_LIBS) # each shared library component gets its own copy for eglib # diff --git a/src/mono/mono/eventpipe/ep-rt-mono.c b/src/mono/mono/eventpipe/ep-rt-mono.c index b6e878aae95f6e..bda75e3076bd84 100644 --- a/src/mono/mono/eventpipe/ep-rt-mono.c +++ b/src/mono/mono/eventpipe/ep-rt-mono.c @@ -1485,12 +1485,8 @@ profiler_eventpipe_thread_exited ( MonoProfiler *prof, uintptr_t tid) { - if (_ep_rt_mono_initialized) { - EventPipeThreadHolder *thread_holder = (EventPipeThreadHolder *)mono_native_tls_get_value (_ep_rt_mono_thread_holder_tls_id); - if (thread_holder) - thread_holder_free_func (thread_holder); - mono_native_tls_set_value (_ep_rt_mono_thread_holder_tls_id, NULL); - } + void ep_rt_mono_thread_exited (void); + ep_rt_mono_thread_exited (); } void @@ -1569,6 +1565,17 @@ ep_rt_mono_thread_detach (void) mono_thread_internal_detach (current_thread); } +void +ep_rt_mono_thread_exited (void) +{ + if (_ep_rt_mono_initialized) { + EventPipeThreadHolder *thread_holder = (EventPipeThreadHolder *)mono_native_tls_get_value (_ep_rt_mono_thread_holder_tls_id); + if (thread_holder) + thread_holder_free_func (thread_holder); + mono_native_tls_set_value (_ep_rt_mono_thread_holder_tls_id, NULL); + } +} + #ifdef HOST_WIN32 int64_t ep_rt_mono_perf_counter_query (void) diff --git a/src/mono/mono/eventpipe/ep-rt-mono.h b/src/mono/mono/eventpipe/ep-rt-mono.h index 7fcb97bff999eb..f8947083dfba91 100644 --- a/src/mono/mono/eventpipe/ep-rt-mono.h +++ b/src/mono/mono/eventpipe/ep-rt-mono.h @@ -348,46 +348,6 @@ prefix_name ## _rt_ ## type_name ## _ ## func_name #define EP_RT_DEFINE_HASH_MAP_ITERATOR(hash_map_name, hash_map_type, iterator_type, key_type, value_type) \ EP_RT_DEFINE_HASH_MAP_ITERATOR_PREFIX(ep, hash_map_name, hash_map_type, iterator_type, key_type, value_type) -void -ep_rt_mono_system_time_get (EventPipeSystemTime *system_time); - -int64_t -ep_rt_mono_system_timestamp_get (void); - -void -ep_rt_mono_os_environment_get_utf16 (ep_rt_env_array_utf16_t *env_array); - -void -ep_rt_mono_init_providers_and_events (void); - -void -ep_rt_mono_fini_providers_and_events (void); - -bool -ep_rt_mono_walk_managed_stack_for_thread ( - ep_rt_thread_handle_t thread, - EventPipeStackContents *stack_contents); - -bool -ep_rt_mono_method_get_simple_assembly_name ( - ep_rt_method_desc_t *method, - ep_char8_t *name, - size_t name_len); - -bool -ep_rt_mono_method_get_full_name ( - ep_rt_method_desc_t *method, - ep_char8_t *name, - size_t name_len); - -bool -ep_rt_mono_sample_profiler_write_sampling_event_for_threads ( - ep_rt_thread_handle_t sampling_thread, - EventPipeEvent *sampling_event); - -void -ep_rt_mono_execute_rundown (void); - static inline char * @@ -705,6 +665,7 @@ ep_rt_walk_managed_stack_for_thread ( ep_rt_thread_handle_t thread, EventPipeStackContents *stack_contents) { + extern bool ep_rt_mono_walk_managed_stack_for_thread (ep_rt_thread_handle_t thread, EventPipeStackContents *stack_contents); return ep_rt_mono_walk_managed_stack_for_thread (thread, stack_contents); } @@ -716,6 +677,7 @@ ep_rt_method_get_simple_assembly_name ( ep_char8_t *name, size_t name_len) { + extern bool ep_rt_mono_method_get_simple_assembly_name (ep_rt_method_desc_t *method, ep_char8_t *name, size_t name_len); return ep_rt_mono_method_get_simple_assembly_name (method, name, name_len); } @@ -727,6 +689,7 @@ ep_rt_method_get_full_name ( ep_char8_t *name, size_t name_len) { + extern bool ep_rt_mono_method_get_full_name (ep_rt_method_desc_t *method, ep_char8_t *name, size_t name_len); return ep_rt_mono_method_get_full_name (method, name, name_len); } @@ -743,6 +706,7 @@ inline void ep_rt_init_providers_and_events (void) { + extern void ep_rt_mono_init_providers_and_events (void); ep_rt_mono_init_providers_and_events (); } @@ -934,6 +898,7 @@ static void ep_rt_sample_profiler_write_sampling_event_for_threads (ep_rt_thread_handle_t sampling_thread, EventPipeEvent *sampling_event) { + extern bool ep_rt_mono_sample_profiler_write_sampling_event_for_threads (ep_rt_thread_handle_t sampling_thread, EventPipeEvent *sampling_event); ep_rt_mono_sample_profiler_write_sampling_event_for_threads (sampling_thread, sampling_event); } @@ -1186,8 +1151,10 @@ ep_rt_execute_rundown (void) { if (ep_rt_config_value_get_rundown () > 0) { // Ask the runtime to emit rundown events. - if (/*is_running &&*/ !ep_rt_process_shutdown ()) + if (/*is_running &&*/ !ep_rt_process_shutdown ()) { + extern void ep_rt_mono_execute_rundown (void); ep_rt_mono_execute_rundown (); + } } } @@ -1329,6 +1296,7 @@ inline void ep_rt_system_time_get (EventPipeSystemTime *system_time) { + extern void ep_rt_mono_system_time_get (EventPipeSystemTime *system_time); ep_rt_mono_system_time_get (system_time); } @@ -1337,6 +1305,7 @@ inline int64_t ep_rt_system_timestamp_get (void) { + extern int64_t ep_rt_mono_system_timestamp_get (void); return ep_rt_mono_system_timestamp_get (); } @@ -1467,6 +1436,7 @@ inline void ep_rt_os_environment_get_utf16 (ep_rt_env_array_utf16_t *env_array) { + extern void ep_rt_mono_os_environment_get_utf16 (ep_rt_env_array_utf16_t *env_array); ep_rt_mono_os_environment_get_utf16 (env_array); } diff --git a/src/mono/mono/eventpipe/test/CMakeLists.txt b/src/mono/mono/eventpipe/test/CMakeLists.txt index f0f5612ecd07c5..1d1c64a6edd9ae 100644 --- a/src/mono/mono/eventpipe/test/CMakeLists.txt +++ b/src/mono/mono/eventpipe/test/CMakeLists.txt @@ -1,6 +1,7 @@ if(ENABLE_PERFTRACING) - if(ENABLE_EVENTPIPE_TEST AND (NOT DISABLE_LIBS) AND (NOT DISABLE_EXECUTABLES)) + # TODO: Add support for dynamic components once package/deploy have been resolved. + if(ENABLE_EVENTPIPE_TEST AND STATIC_COMPONENTS AND (NOT DISABLE_LIBS) AND (NOT DISABLE_EXECUTABLES)) set(EVENTPIPE_TEST_SOURCES "") set(EVENTPIPE_TEST_HEADERS "") @@ -55,13 +56,13 @@ if(ENABLE_PERFTRACING) set(CMAKE_SKIP_RPATH 1) add_executable(ep-test ${EVENTPIPE_TEST_SOURCES} ${EVENTPIPE_TEST_HEADERS}) - target_link_libraries(ep-test monosgen-static ${OS_LIBS} ${ICONV_LIB} ${LLVM_LIBS} ${ICU_LIBS}) + target_link_libraries(ep-test monosgen-static "mono-components-static" ${OS_LIBS} ${ICONV_LIB} ${LLVM_LIBS} ${ICU_LIBS}) if(ICU_LDFLAGS) set_target_properties(ep-test PROPERTIES LINK_FLAGS ${ICU_LDFLAGS}) endif() install(TARGETS ep-test RUNTIME) - else(ENABLE_EVENTPIPE_TEST AND (NOT DISABLE_LIBS) AND (NOT DISABLE_EXECUTABLES)) + else(ENABLE_EVENTPIPE_TEST AND STATIC_COMPONENTS AND (NOT DISABLE_LIBS) AND (NOT DISABLE_EXECUTABLES)) message(VERBOSE "Skip building native EventPipe library test runner.") - endif(ENABLE_EVENTPIPE_TEST AND (NOT DISABLE_LIBS) AND (NOT DISABLE_EXECUTABLES)) + endif(ENABLE_EVENTPIPE_TEST AND STATIC_COMPONENTS AND (NOT DISABLE_LIBS) AND (NOT DISABLE_EXECUTABLES)) endif(ENABLE_PERFTRACING) diff --git a/src/mono/mono/eventpipe/test/ep-buffer-manager-tests.c b/src/mono/mono/eventpipe/test/ep-buffer-manager-tests.c index 35f38084b0ba68..0c74b6c094bc10 100644 --- a/src/mono/mono/eventpipe/test/ep-buffer-manager-tests.c +++ b/src/mono/mono/eventpipe/test/ep-buffer-manager-tests.c @@ -581,11 +581,11 @@ test_buffer_manager_perf (void) static RESULT test_buffer_manager_teardown (void) { +#ifdef _CRTDBG_MAP_ALLOC // Need to emulate a thread exit to make sure TLS gets cleaned up for current thread // or we will get memory leaks reported. ep_rt_mono_thread_exited (); -#ifdef _CRTDBG_MAP_ALLOC _CrtMemCheckpoint (&eventpipe_memory_end_snapshot); if ( _CrtMemDifference( &eventpipe_memory_diff_snapshot, &eventpipe_memory_start_snapshot, &eventpipe_memory_end_snapshot) ) { _CrtMemDumpStatistics( &eventpipe_memory_diff_snapshot ); diff --git a/src/mono/mono/eventpipe/test/ep-setup-tests.c b/src/mono/mono/eventpipe/test/ep-setup-tests.c index 30743664ac6c7f..6bb24553e7f356 100644 --- a/src/mono/mono/eventpipe/test/ep-setup-tests.c +++ b/src/mono/mono/eventpipe/test/ep-setup-tests.c @@ -12,6 +12,8 @@ test_setup (void) if (core_root) { mono_set_assemblies_path (core_root); g_free (core_root); + } else { + mono_set_assemblies_path ("."); } eventpipe_test_domain = mono_jit_init_version_for_test_only ("eventpipe-tests", "v4.0.30319"); diff --git a/src/mono/mono/eventpipe/test/ep-tests-debug.h b/src/mono/mono/eventpipe/test/ep-tests-debug.h index e86795ea3ff5fe..75b4cc5ae087a5 100644 --- a/src/mono/mono/eventpipe/test/ep-tests-debug.h +++ b/src/mono/mono/eventpipe/test/ep-tests-debug.h @@ -5,4 +5,7 @@ #include #include +// Private function only used by EventPipe tests. +extern void ep_rt_mono_thread_exited (void); + #endif /* __EVENTPIPE_TESTS_DEBUG_H__ */ diff --git a/src/mono/mono/eventpipe/test/ep-thread-tests.c b/src/mono/mono/eventpipe/test/ep-thread-tests.c index 1ffe239b47c3dd..c0ae56dfe862cc 100644 --- a/src/mono/mono/eventpipe/test/ep-thread-tests.c +++ b/src/mono/mono/eventpipe/test/ep-thread-tests.c @@ -126,9 +126,11 @@ test_get_or_create_thread (void) test_location = 4; +#ifdef _CRTDBG_MAP_ALLOC // Need to emulate a thread exit to make sure TLS gets cleaned up for current thread // or we will get memory leaks reported. ep_rt_mono_thread_exited (); +#endif thread = ep_thread_get (); if (thread) { diff --git a/src/mono/mono/mini/CMakeLists.txt b/src/mono/mono/mini/CMakeLists.txt index e22132de22b845..6dc8b13e88ec21 100644 --- a/src/mono/mono/mini/CMakeLists.txt +++ b/src/mono/mono/mini/CMakeLists.txt @@ -326,10 +326,10 @@ endif() if(NOT DISABLE_SHARED_LIBS) if(HOST_WIN32) add_library(monosgen-shared SHARED "mini-windows-dllmain.c;${monosgen-sources}") - target_compile_definitions(monosgen-shared PRIVATE -DMONO_DLL_EXPORT) else() add_library(monosgen-shared SHARED $ ) endif() + target_compile_definitions(monosgen-shared PRIVATE -DMONO_DLL_EXPORT) target_link_libraries(monosgen-shared eglib_objects) set_target_properties(monosgen-shared PROPERTIES OUTPUT_NAME monosgen-2.0) if(TARGET_WIN32) From 997f30fa1e53786123394b5f0e35988c29e3e0c4 Mon Sep 17 00:00:00 2001 From: lateralusX Date: Tue, 30 Mar 2021 18:09:51 +0200 Subject: [PATCH 26/55] Fix memory leak in EventPipe buffer manager. --- src/native/eventpipe/ep-buffer-manager.c | 1 + 1 file changed, 1 insertion(+) diff --git a/src/native/eventpipe/ep-buffer-manager.c b/src/native/eventpipe/ep-buffer-manager.c index bcab43e1d34480..5b7c0592caf1b3 100644 --- a/src/native/eventpipe/ep-buffer-manager.c +++ b/src/native/eventpipe/ep-buffer-manager.c @@ -1371,6 +1371,7 @@ ep_buffer_manager_write_all_buffers_to_file_v4 ( } ep_on_exit: + ep_rt_thread_session_state_array_fini(&session_states_to_delete); return; ep_on_error: ep_exit_error_handler (); From a3844c1beeda50e2f54014cb7ea5d840b6268fb0 Mon Sep 17 00:00:00 2001 From: lateralusX Date: Wed, 31 Mar 2021 13:03:14 +0200 Subject: [PATCH 27/55] Fix osx builds. --- src/mono/mono.proj | 6 +- src/mono/mono/component/CMakeLists.txt | 2 +- .../mono/component/diagnostics_server-stub.c | 10 ++- src/mono/mono/component/diagnostics_server.h | 7 +- src/mono/mono/eventpipe/ep-rt-mono.c | 75 ++++++++++++++++++- src/mono/mono/mini/CMakeLists.txt | 5 +- src/mono/mono/utils/atomic.h | 2 +- 7 files changed, 95 insertions(+), 12 deletions(-) diff --git a/src/mono/mono.proj b/src/mono/mono.proj index 8d5a7c2b8a02eb..6298182b14b18f 100644 --- a/src/mono/mono.proj +++ b/src/mono/mono.proj @@ -724,10 +724,14 @@ SkipUnchangedFiles="true" Condition="'$(MonoGenerateOffsetsOSGroups)' == '' and ('$(TargetsMacCatalyst)' == 'true' or '$(TargetsiOS)' == 'true' or '$(TargetstvOS)' == 'true' or '$(TargetsAndroid)' == 'true' or '$(TargetsBrowser)' == 'true')"/> + + <_MonoRuntimeComponentsSharedArtifacts Include="$(RuntimeBinDir)libmono-component-*$(SharedNativeLibrarySuffix)" /> + + - + diff --git a/src/mono/mono/component/CMakeLists.txt b/src/mono/mono/component/CMakeLists.txt index 263addd50eba3d..995f1b0552a2f3 100644 --- a/src/mono/mono/component/CMakeLists.txt +++ b/src/mono/mono/component/CMakeLists.txt @@ -72,10 +72,10 @@ if (NOT STATIC_COMPONENTS) foreach (component IN LISTS components) if(HOST_WIN32) add_library("mono-component-${component}" SHARED "${${component}-sources}") + target_compile_definitions ("mono-component-${component}" PRIVATE -DCOMPILING_COMPONENT_DYNAMIC;-DMONO_DLL_IMPORT) else() add_library("mono-component-${component}" SHARED $) endif() - target_compile_definitions ("mono-component-${component}" PRIVATE -DCOMPILING_COMPONENT_DYNAMIC;-DMONO_DLL_IMPORT) if (NOT DISABLE_SHARED_LIBS) # each shared library component gets its own copy for eglib # diff --git a/src/mono/mono/component/diagnostics_server-stub.c b/src/mono/mono/component/diagnostics_server-stub.c index e625943aad86dc..08bec21ef28e89 100644 --- a/src/mono/mono/component/diagnostics_server-stub.c +++ b/src/mono/mono/component/diagnostics_server-stub.c @@ -15,10 +15,10 @@ static void diagnostics_server_stub_cleanup (MonoComponent *self); -static void +static bool diagnostics_server_stub_init (void); -static void +static bool diagnostics_server_stub_shutdown (void); static void @@ -40,14 +40,16 @@ diagnostics_server_stub_cleanup (MonoComponent *self) { } -static void +static bool diagnostics_server_stub_init (void) { + return true; } -static void +static bool diagnostics_server_stub_shutdown (void) { + return true; } static void diff --git a/src/mono/mono/component/diagnostics_server.h b/src/mono/mono/component/diagnostics_server.h index 5f5a41a23576c7..67ee2ff4618149 100644 --- a/src/mono/mono/component/diagnostics_server.h +++ b/src/mono/mono/component/diagnostics_server.h @@ -9,10 +9,13 @@ #include "mono/component/component.h" #include "mono/utils/mono-compiler.h" +#include +#include + typedef struct _MonoComponentDiagnosticsServer { MonoComponent component; - void (*init) (void); - void (*shutdown) (void); + bool (*init) (void); + bool (*shutdown) (void); void (*pause_for_diagnostics_monitor) (void); void (*disable) (void); } MonoComponentDiagnosticsServer; diff --git a/src/mono/mono/eventpipe/ep-rt-mono.c b/src/mono/mono/eventpipe/ep-rt-mono.c index bda75e3076bd84..a3e7d9d076468e 100644 --- a/src/mono/mono/eventpipe/ep-rt-mono.c +++ b/src/mono/mono/eventpipe/ep-rt-mono.c @@ -409,6 +409,79 @@ profiler_eventpipe_thread_exited ( MonoProfiler *prof, uintptr_t tid); +/* + * Forward declares of all private functions (accessed using extern in ep-rt-mono.h). + */ + +void +ep_rt_mono_init (void); + +void +ep_rt_mono_fini (void); + +bool +ep_rt_mono_rand_try_get_bytes ( + uint8_t *buffer, + size_t buffer_size); + +EventPipeThread * +ep_rt_mono_thread_get_or_create (void); + +void * +ep_rt_mono_thread_attach (bool background_thread); + +void +ep_rt_mono_thread_detach (void); + +void +ep_rt_mono_thread_exited (void); + +int64_t +ep_rt_mono_perf_counter_query (void); + +int64_t +ep_rt_mono_perf_frequency_query (void); + +void +ep_rt_mono_system_time_get (EventPipeSystemTime *system_time); + +int64_t +ep_rt_mono_system_timestamp_get (void); + +void +ep_rt_mono_os_environment_get_utf16 (ep_rt_env_array_utf16_t *env_array); + +void +ep_rt_mono_init_providers_and_events (void); + +void +ep_rt_mono_fini_providers_and_events (void); + +bool +ep_rt_mono_sample_profiler_write_sampling_event_for_threads ( + ep_rt_thread_handle_t sampling_thread, + EventPipeEvent *sampling_event); + +void +ep_rt_mono_execute_rundown (void); + +bool +ep_rt_mono_walk_managed_stack_for_thread ( + ep_rt_thread_handle_t thread, + EventPipeStackContents *stack_contents); + +bool +ep_rt_mono_method_get_simple_assembly_name ( + ep_rt_method_desc_t *method, + ep_char8_t *name, + size_t name_len); + +bool +ep_rt_mono_method_get_full_name ( + ep_rt_method_desc_t *method, + ep_char8_t *name, + size_t name_len); + static inline uint16_t @@ -1953,7 +2026,7 @@ ep_rt_mono_sample_profiler_write_sampling_event_for_threads ( // Fire sample event for threads. Must be done after runtime is resumed since it's not async safe. // Since we can't keep thread info around after runtime as been suspended, use an empty // adapter instance and only set recorded tid as parameter inside adapter. - THREAD_INFO_TYPE adapter = { 0 }; + THREAD_INFO_TYPE adapter = { { 0 } }; for (uint32_t i = 0; i < sampled_thread_count; ++i) { EventPipeSampleProfileData *data = &g_array_index (_ep_rt_mono_sampled_thread_callstacks, EventPipeSampleProfileData, i); if (data->payload_data != EP_SAMPLE_PROFILER_SAMPLE_TYPE_ERROR && ep_stack_contents_get_length(&data->stack_contents) > 0) { diff --git a/src/mono/mono/mini/CMakeLists.txt b/src/mono/mono/mini/CMakeLists.txt index 6dc8b13e88ec21..2cb6dfef550fc0 100644 --- a/src/mono/mono/mini/CMakeLists.txt +++ b/src/mono/mono/mini/CMakeLists.txt @@ -326,10 +326,11 @@ endif() if(NOT DISABLE_SHARED_LIBS) if(HOST_WIN32) add_library(monosgen-shared SHARED "mini-windows-dllmain.c;${monosgen-sources}") + target_compile_definitions(monosgen-shared PRIVATE -DMONO_DLL_EXPORT) else() - add_library(monosgen-shared SHARED $ ) + add_library(monosgen-shared SHARED $) + target_compile_definitions(monosgen-objects PRIVATE -DMONO_DLL_EXPORT) endif() - target_compile_definitions(monosgen-shared PRIVATE -DMONO_DLL_EXPORT) target_link_libraries(monosgen-shared eglib_objects) set_target_properties(monosgen-shared PROPERTIES OUTPUT_NAME monosgen-2.0) if(TARGET_WIN32) diff --git a/src/mono/mono/utils/atomic.h b/src/mono/mono/utils/atomic.h index 4b46122c518656..5ba7bd2c2a0861 100755 --- a/src/mono/mono/utils/atomic.h +++ b/src/mono/mono/utils/atomic.h @@ -373,7 +373,7 @@ static inline gint64 mono_atomic_load_i64(volatile gint64 *src) #else /* Implement 64-bit cas by hand or emulate it. */ -extern gint64 mono_atomic_cas_i64(volatile gint64 *dest, gint64 exch, gint64 comp); +MONO_COMPONENT_API gint64 mono_atomic_cas_i64(volatile gint64 *dest, gint64 exch, gint64 comp); /* Implement all other 64-bit atomics in terms of a specialized CAS * in this case, since chances are that the other 64-bit atomic From b933f9c7fc834177ebd7be9bff7249cb6fbdbca2 Mon Sep 17 00:00:00 2001 From: lateralusX Date: Wed, 31 Mar 2021 15:12:38 +0200 Subject: [PATCH 28/55] Fix iOS builds. --- src/mono/mono.proj | 2 ++ src/mono/mono/component/CMakeLists.txt | 4 ++-- src/mono/mono/mini/CMakeLists.txt | 8 ++++---- src/mono/mono/utils/mono-threads.h | 1 - 4 files changed, 8 insertions(+), 7 deletions(-) diff --git a/src/mono/mono.proj b/src/mono/mono.proj index 6298182b14b18f..45124f731dd0a3 100644 --- a/src/mono/mono.proj +++ b/src/mono/mono.proj @@ -81,6 +81,7 @@ + true true true true @@ -569,6 +570,7 @@ + diff --git a/src/mono/mono/component/CMakeLists.txt b/src/mono/mono/component/CMakeLists.txt index 995f1b0552a2f3..441d75ebbdf088 100644 --- a/src/mono/mono/component/CMakeLists.txt +++ b/src/mono/mono/component/CMakeLists.txt @@ -82,8 +82,8 @@ if (NOT STATIC_COMPONENTS) # FIXME: this is bad for things like the g_log_set_default_handler/g_logv # which use global state - we should move those functions into # monosgen-shared and get them via dynamic linking. - target_link_libraries("mono-component-${component}" eglib_objects) - target_link_libraries("mono-component-${component}" monosgen-shared) + target_link_libraries("mono-component-${component}" PRIVATE eglib_objects) + target_link_libraries("mono-component-${component}" PRIVATE monosgen-shared) # If we disable shared libs, but build dynamic components we would need # to enable allowing undefined symbols here (presumably to be resolved # from the mono-sgen executable. But that's not a configuration we diff --git a/src/mono/mono/mini/CMakeLists.txt b/src/mono/mono/mini/CMakeLists.txt index 2cb6dfef550fc0..0018629ee1fc3c 100644 --- a/src/mono/mono/mini/CMakeLists.txt +++ b/src/mono/mono/mini/CMakeLists.txt @@ -331,14 +331,14 @@ if(NOT DISABLE_SHARED_LIBS) add_library(monosgen-shared SHARED $) target_compile_definitions(monosgen-objects PRIVATE -DMONO_DLL_EXPORT) endif() - target_link_libraries(monosgen-shared eglib_objects) + target_link_libraries(monosgen-shared PRIVATE eglib_objects) set_target_properties(monosgen-shared PROPERTIES OUTPUT_NAME monosgen-2.0) if(TARGET_WIN32) # on Windows the import library for the shared monosgen-2.0 library will have the same name as the static library (monosgen-2.0.lib), # to avoid a conflict we rename the import library with the .import.lib suffix set_target_properties(monosgen-shared PROPERTIES IMPORT_SUFFIX ".import.lib") endif() - target_link_libraries(monosgen-shared ${OS_LIBS} ${ICONV_LIB} ${LLVM_LIBS} ${ICU_LIBS}) + target_link_libraries(monosgen-shared PRIVATE ${OS_LIBS} ${ICONV_LIB} ${LLVM_LIBS} ${ICU_LIBS}) if(ICU_LDFLAGS) set_property(TARGET monosgen-shared APPEND_STRING PROPERTY LINK_FLAGS " ${ICU_LDFLAGS}") endif() @@ -351,10 +351,10 @@ if(NOT DISABLE_SHARED_LIBS) if (STATIC_COMPONENTS) # if components are built statically, but we're building a shared lib mono, # link them into the library - target_link_libraries (monosgen-shared "mono-components-static") + target_link_libraries (monosgen-shared PRIVATE "mono-components-static") else() # if components are built dynamically, link the fallback stubs into the runtime - target_link_libraries (monosgen-shared "mono-components-stubs-static") + target_link_libraries (monosgen-shared PRIVATE "mono-components-stubs-static") endif() install(TARGETS monosgen-shared LIBRARY) if(HOST_WIN32) diff --git a/src/mono/mono/utils/mono-threads.h b/src/mono/mono/utils/mono-threads.h index a6b1b2544a4462..edb857d9fcc044 100644 --- a/src/mono/mono/utils/mono-threads.h +++ b/src/mono/mono/utils/mono-threads.h @@ -767,7 +767,6 @@ void mono_threads_transition_begin_no_safepoints (THREAD_INFO_TYPE* info, const void mono_threads_transition_end_no_safepoints (THREAD_INFO_TYPE* info, const char *func); MONO_COMPONENT_API -G_EXTERN_C // due to THREAD_INFO_TYPE varying MonoThreadUnwindState* mono_thread_info_get_suspend_state (THREAD_INFO_TYPE *info); gpointer From d9b55a6ac4d72a9edf3fba1281332cb8f1157e14 Mon Sep 17 00:00:00 2001 From: lateralusX Date: Wed, 31 Mar 2021 16:32:06 +0200 Subject: [PATCH 29/55] Fix some warnings. --- src/mono/mono/eventpipe/test/ep-buffer-manager-tests.c | 3 ++- src/mono/mono/eventpipe/test/ep-tests-debug.h | 3 --- src/mono/mono/eventpipe/test/ep-tests.c | 1 + src/mono/mono/eventpipe/test/ep-thread-tests.c | 4 ++-- src/mono/mono/metadata/native-library.c | 4 ++-- src/mono/mono/utils/mono-threads.h | 4 ---- 6 files changed, 7 insertions(+), 12 deletions(-) diff --git a/src/mono/mono/eventpipe/test/ep-buffer-manager-tests.c b/src/mono/mono/eventpipe/test/ep-buffer-manager-tests.c index 0c74b6c094bc10..3a13b05911e8de 100644 --- a/src/mono/mono/eventpipe/test/ep-buffer-manager-tests.c +++ b/src/mono/mono/eventpipe/test/ep-buffer-manager-tests.c @@ -333,7 +333,7 @@ test_buffer_manager_read_event (void) test_location = 5; - ep_raise_error_if_nok (ep_event_instance_get_thread_id (ep_event_instance) == ep_rt_current_thread_get_id ()); + ep_raise_error_if_nok (ep_event_instance_get_thread_id (ep_event_instance) == ep_rt_thread_id_t_to_uint64_t (ep_rt_current_thread_get_id ())); ep_on_exit: buffer_manager_fini (buffer_manager,thread, session, provider, ep_event); @@ -584,6 +584,7 @@ test_buffer_manager_teardown (void) #ifdef _CRTDBG_MAP_ALLOC // Need to emulate a thread exit to make sure TLS gets cleaned up for current thread // or we will get memory leaks reported. + extern void ep_rt_mono_thread_exited (void); ep_rt_mono_thread_exited (); _CrtMemCheckpoint (&eventpipe_memory_end_snapshot); diff --git a/src/mono/mono/eventpipe/test/ep-tests-debug.h b/src/mono/mono/eventpipe/test/ep-tests-debug.h index 75b4cc5ae087a5..e86795ea3ff5fe 100644 --- a/src/mono/mono/eventpipe/test/ep-tests-debug.h +++ b/src/mono/mono/eventpipe/test/ep-tests-debug.h @@ -5,7 +5,4 @@ #include #include -// Private function only used by EventPipe tests. -extern void ep_rt_mono_thread_exited (void); - #endif /* __EVENTPIPE_TESTS_DEBUG_H__ */ diff --git a/src/mono/mono/eventpipe/test/ep-tests.c b/src/mono/mono/eventpipe/test/ep-tests.c index 34179b61642b8b..b0e7803924551d 100644 --- a/src/mono/mono/eventpipe/test/ep-tests.c +++ b/src/mono/mono/eventpipe/test/ep-tests.c @@ -1256,6 +1256,7 @@ test_eventpipe_mem_checkpoint (void) #ifdef _CRTDBG_MAP_ALLOC // Need to emulate a thread exit to make sure TLS gets cleaned up for current thread // or we will get memory leaks reported. + extern void ep_rt_mono_thread_exited (void); ep_rt_mono_thread_exited (); _CrtMemCheckpoint (&eventpipe_memory_end_snapshot); diff --git a/src/mono/mono/eventpipe/test/ep-thread-tests.c b/src/mono/mono/eventpipe/test/ep-thread-tests.c index c0ae56dfe862cc..2eb85ff976c2da 100644 --- a/src/mono/mono/eventpipe/test/ep-thread-tests.c +++ b/src/mono/mono/eventpipe/test/ep-thread-tests.c @@ -126,11 +126,10 @@ test_get_or_create_thread (void) test_location = 4; -#ifdef _CRTDBG_MAP_ALLOC // Need to emulate a thread exit to make sure TLS gets cleaned up for current thread // or we will get memory leaks reported. + extern void ep_rt_mono_thread_exited (void); ep_rt_mono_thread_exited (); -#endif thread = ep_thread_get (); if (thread) { @@ -201,6 +200,7 @@ test_thread_activity_id (void) // Need to emulate a thread exit to make sure TLS gets cleaned up for current thread // or we will get memory leaks reported. + extern void ep_rt_mono_thread_exited (void); ep_rt_mono_thread_exited (); thread = ep_thread_get (); diff --git a/src/mono/mono/metadata/native-library.c b/src/mono/mono/metadata/native-library.c index 13c0cf562d5ca5..e70f24f7cc480d 100644 --- a/src/mono/mono/metadata/native-library.c +++ b/src/mono/mono/metadata/native-library.c @@ -1224,7 +1224,7 @@ ves_icall_System_Runtime_InteropServices_NativeLibrary_FreeLib (gpointer lib, Mo g_hash_table_add (native_library_module_blocklist, module); mono_dl_close (module); } else { - MonoDl raw_module = { 0 }; + MonoDl raw_module = { { 0 } }; raw_module.handle = lib; mono_dl_close (&raw_module); } @@ -1255,7 +1255,7 @@ ves_icall_System_Runtime_InteropServices_NativeLibrary_GetSymbol (gpointer lib, if (!symbol) mono_error_set_generic_error (error, "System", "EntryPointNotFoundException", "%s: %s", module->full_name, symbol_name); } else { - MonoDl raw_module = { 0 }; + MonoDl raw_module = { { 0 } }; raw_module.handle = lib; mono_dl_symbol (&raw_module, symbol_name, &symbol); if (!symbol) diff --git a/src/mono/mono/utils/mono-threads.h b/src/mono/mono/utils/mono-threads.h index edb857d9fcc044..c0cd48216528b3 100644 --- a/src/mono/mono/utils/mono-threads.h +++ b/src/mono/mono/utils/mono-threads.h @@ -453,9 +453,6 @@ gboolean mono_thread_info_is_exiting (void); MONO_COMPONENT_API -#ifdef HOST_WIN32 -G_EXTERN_C // due to THREAD_INFO_TYPE varying -#endif THREAD_INFO_TYPE * mono_thread_info_current (void); @@ -775,7 +772,6 @@ mono_threads_enter_gc_unsafe_region_cookie (void); void mono_thread_info_wait_for_resume (THREAD_INFO_TYPE *info); /* Advanced suspend API, used for suspending multiple threads as once. */ -G_EXTERN_C // due to THREAD_INFO_TYPE varying MONO_COMPONENT_API gboolean mono_thread_info_is_running (THREAD_INFO_TYPE *info); gboolean mono_thread_info_is_live (THREAD_INFO_TYPE *info); G_EXTERN_C // due to THREAD_INFO_TYPE varying From 84c5704fdc13e1f295f1603bf5d56bfdf5c43964 Mon Sep 17 00:00:00 2001 From: lateralusX Date: Thu, 1 Apr 2021 15:15:12 +0200 Subject: [PATCH 30/55] Add support to disable components. --- src/mono/CMakeLists.txt | 8 +++ src/mono/cmake/config.h.in | 6 +-- src/mono/mono.proj | 7 ++- src/mono/mono/component/CMakeLists.txt | 60 ++++++++++++--------- src/mono/mono/eventpipe/test/CMakeLists.txt | 6 +-- src/mono/mono/mini/CMakeLists.txt | 29 +++++----- 6 files changed, 67 insertions(+), 49 deletions(-) diff --git a/src/mono/CMakeLists.txt b/src/mono/CMakeLists.txt index 4f5678898cb182..4cbabf0e0842d4 100644 --- a/src/mono/CMakeLists.txt +++ b/src/mono/CMakeLists.txt @@ -651,6 +651,14 @@ if (CMAKE_BUILD_TYPE STREQUAL "Debug") endif() ### End of debug build checks +###################################### +# COMPONENT BUILD CHECKS +###################################### +if(DISABLE_COMPONENTS AND NOT STATIC_COMPONENTS) + set(STATIC_COMPONENTS 1) +endif() +### End of component build checks + ###################################### # OTHER CHECKS ###################################### diff --git a/src/mono/cmake/config.h.in b/src/mono/cmake/config.h.in index 28ce48b806531d..b466563394a041 100644 --- a/src/mono/cmake/config.h.in +++ b/src/mono/cmake/config.h.in @@ -1052,11 +1052,11 @@ /* Enable runtime support for metadata updates */ #cmakedefine ENABLE_METADATA_UPDATE 1 +/* Enable static linking of mono runtime components */ +#cmakedefine STATIC_COMPONENTS + #if defined(ENABLE_LLVM) && defined(HOST_WIN32) && defined(TARGET_WIN32) && (!defined(TARGET_AMD64) || !defined(_MSC_VER)) #error LLVM for host=Windows and target=Windows is only supported on x64 MSVC build. #endif #endif - -/* Enable static linking of mono runtime components */ -#cmakedefine STATIC_COMPONENTS diff --git a/src/mono/mono.proj b/src/mono/mono.proj index 45124f731dd0a3..60dc97a094bfe0 100644 --- a/src/mono/mono.proj +++ b/src/mono/mono.proj @@ -81,7 +81,6 @@ - true true true true @@ -570,7 +569,7 @@ - + @@ -659,10 +658,10 @@ <_MonoRuntimeArtifacts Include="@(_MonoRuntimeComponentsStaticFilePath)"> - $(RuntimeBinDir)%(_MonoRuntimeComponentsStaticFilePath.Filename)%(_MonoRuntimeComponentsStaticFilePath.Extension) + $(RuntimeBinDir)%(_MonoRuntimeComponentsStaticFilePath.Filename)%(_MonoRuntimeComponentsStaticFilePath.Extension) <_MonoRuntimeArtifacts Include="@(_MonoRuntimeComponentsSharedFilePath)"> - $(RuntimeBinDir)%(_MonoRuntimeComponentsSharedFilePath.Filename)%(_MonoRuntimeComponentsSharedFilePath.Extension) + $(RuntimeBinDir)%(_MonoRuntimeComponentsSharedFilePath.Filename)%(_MonoRuntimeComponentsSharedFilePath.Extension) <_MonoRuntimeArtifacts Include="$(_MonoAotCrossFilePath)"> $(RuntimeBinDir)cross\$(PackageRID)\mono-aot-cross$(ExeExt) diff --git a/src/mono/mono/component/CMakeLists.txt b/src/mono/mono/component/CMakeLists.txt index 441d75ebbdf088..5a46948a073906 100644 --- a/src/mono/mono/component/CMakeLists.txt +++ b/src/mono/mono/component/CMakeLists.txt @@ -21,9 +21,9 @@ if(ENABLE_PERFTRACING) event_pipe ) - set (SHARED_EVENTPIPE_INCLUDE_PATH "../../../native/") - set (SHARED_EVENTPIPE_SOURCE_PATH "../../../native/eventpipe/") - set (MONO_EVENTPIPE_SHIM_SOURCE_PATH "../eventpipe/") + set(SHARED_EVENTPIPE_INCLUDE_PATH "../../../native/") + set(SHARED_EVENTPIPE_SOURCE_PATH "../../../native/eventpipe/") + set(MONO_EVENTPIPE_SHIM_SOURCE_PATH "../eventpipe/") include(${MONO_EVENTPIPE_SHIM_SOURCE_PATH}/CMakeLists.txt) @@ -53,30 +53,35 @@ endif(ENABLE_PERFTRACING) add_library(component_base INTERFACE) target_sources(component_base INTERFACE ../component/component.h - ) +) +if(DISABLE_COMPONENTS OR (NOT STATIC_COMPONENTS AND HOST_WIN32)) + set(DISABLE_COMPONENT_OBJECTS 1) +endif() # define a component_name-objects and component_name-stub-objects object # targets with the relative source file names -foreach (component IN LISTS components) +foreach(component IN LISTS components) addprefix("${component}-sources" ../component "${${component}-sources_base}") - add_library("${component}-objects" OBJECT "${${component}-sources}") - target_link_libraries("${component}-objects" component_base) + if(NOT DISABLE_COMPONENT_OBJECTS) + add_library("${component}-objects" OBJECT "${${component}-sources}") + target_link_libraries("${component}-objects" component_base) + endif() addprefix("${component}-stub-sources" ../component "${${component}-stub-sources_base}") add_library("${component}-stub-objects" OBJECT "${${component}-stub-sources}") target_link_libraries("${component}-stub-objects" component_base) endforeach() -if (NOT STATIC_COMPONENTS) +if(NOT DISABLE_COMPONENTS AND NOT STATIC_COMPONENTS) # define a shared library for each component - foreach (component IN LISTS components) + foreach(component IN LISTS components) if(HOST_WIN32) add_library("mono-component-${component}" SHARED "${${component}-sources}") - target_compile_definitions ("mono-component-${component}" PRIVATE -DCOMPILING_COMPONENT_DYNAMIC;-DMONO_DLL_IMPORT) + target_compile_definitions("mono-component-${component}" PRIVATE -DCOMPILING_COMPONENT_DYNAMIC;-DMONO_DLL_IMPORT) else() add_library("mono-component-${component}" SHARED $) endif() - if (NOT DISABLE_SHARED_LIBS) + if(NOT DISABLE_SHARED_LIBS) # each shared library component gets its own copy for eglib # # FIXME: this is bad for things like the g_log_set_default_handler/g_logv @@ -89,35 +94,38 @@ if (NOT STATIC_COMPONENTS) # from the mono-sgen executable. But that's not a configuration we # should need in dotnet/runtime. endif() + target_link_libraries("mono-component-${component}" PRIVATE ${OS_LIBS}) install(TARGETS "mono-component-${component}" LIBRARY) endforeach() - # define a single static library mono-components-stubs-static that will be linked into - # the runtime to be used as fallbacks if the dynamic components are not - # available - add_library ("mono-components-stubs-static" STATIC) - foreach (component IN LISTS components) - target_sources ("mono-components-stubs-static" PRIVATE $) - endforeach() - target_link_libraries("mono-components-stubs-static" component_base) - -else() +elseif(NOT DISABLE_COMPONENTS AND STATIC_COMPONENTS) #define a static library for each component and component stub - foreach (component IN LISTS components) + foreach(component IN LISTS components) add_library("mono-component-${component}-static" STATIC $) install(TARGETS "mono-component-${component}-static" LIBRARY) endforeach() - foreach (component IN LISTS components) + foreach(component IN LISTS components) add_library("mono-component-${component}-stub-static" STATIC $) install(TARGETS "mono-component-${component}-stub-static" LIBRARY) endforeach() # define a single static library mono-components-static for mini if building a shared libmono with static-linked components - add_library ("mono-components-static" STATIC) - foreach (component IN LISTS components) - target_sources ("mono-components-static" PRIVATE $) + add_library("mono-components-static" STATIC) + foreach(component IN LISTS components) + target_sources("mono-components-static" PRIVATE $) endforeach() target_link_libraries("mono-components-static" component_base) endif() + +if(DISABLE_COMPONENTS OR NOT STATIC_COMPONENTS) + # define a single static library mono-components-stubs-static that will be linked into + # the runtime to be used as fallbacks if the dynamic components are not + # available or when only static component stubs are requested. + add_library("mono-components-stubs-static" STATIC) + foreach(component IN LISTS components) + target_sources("mono-components-stubs-static" PRIVATE $) + endforeach() + target_link_libraries("mono-components-stubs-static" component_base) +endif() diff --git a/src/mono/mono/eventpipe/test/CMakeLists.txt b/src/mono/mono/eventpipe/test/CMakeLists.txt index 1d1c64a6edd9ae..574cd28f7c42f3 100644 --- a/src/mono/mono/eventpipe/test/CMakeLists.txt +++ b/src/mono/mono/eventpipe/test/CMakeLists.txt @@ -1,7 +1,7 @@ if(ENABLE_PERFTRACING) # TODO: Add support for dynamic components once package/deploy have been resolved. - if(ENABLE_EVENTPIPE_TEST AND STATIC_COMPONENTS AND (NOT DISABLE_LIBS) AND (NOT DISABLE_EXECUTABLES)) + if(ENABLE_EVENTPIPE_TEST AND STATIC_COMPONENTS AND (NOT DISABLE_COMPONENTS) AND (NOT DISABLE_LIBS) AND (NOT DISABLE_EXECUTABLES)) set(EVENTPIPE_TEST_SOURCES "") set(EVENTPIPE_TEST_HEADERS "") @@ -61,8 +61,8 @@ if(ENABLE_PERFTRACING) set_target_properties(ep-test PROPERTIES LINK_FLAGS ${ICU_LDFLAGS}) endif() install(TARGETS ep-test RUNTIME) - else(ENABLE_EVENTPIPE_TEST AND STATIC_COMPONENTS AND (NOT DISABLE_LIBS) AND (NOT DISABLE_EXECUTABLES)) + else(ENABLE_EVENTPIPE_TEST AND STATIC_COMPONENTS AND (NOT DISABLE_COMPONENTS) AND (NOT DISABLE_LIBS) AND (NOT DISABLE_EXECUTABLES)) message(VERBOSE "Skip building native EventPipe library test runner.") - endif(ENABLE_EVENTPIPE_TEST AND STATIC_COMPONENTS AND (NOT DISABLE_LIBS) AND (NOT DISABLE_EXECUTABLES)) + endif(ENABLE_EVENTPIPE_TEST AND STATIC_COMPONENTS AND (NOT DISABLE_COMPONENTS) AND (NOT DISABLE_LIBS) AND (NOT DISABLE_EXECUTABLES)) endif(ENABLE_PERFTRACING) diff --git a/src/mono/mono/mini/CMakeLists.txt b/src/mono/mono/mini/CMakeLists.txt index 0018629ee1fc3c..ab055d461835b4 100644 --- a/src/mono/mono/mini/CMakeLists.txt +++ b/src/mono/mono/mini/CMakeLists.txt @@ -19,6 +19,18 @@ include_directories( ${PROJECT_SOURCE_DIR}/../eglib ${PROJECT_SOURCE_DIR}/../sgen) +if(HOST_DARWIN) +set(OS_LIBS "-framework CoreFoundation" "-framework Foundation") +elseif(HOST_IOS) +set(OS_LIBS "-framework CoreFoundation" "-lobjc" "-lc++") +elseif(HOST_ANDROID) +set(OS_LIBS m dl log) +elseif(HOST_LINUX) +set(OS_LIBS pthread m dl) +elseif(HOST_WIN32) +set(OS_LIBS bcrypt.lib Mswsock.lib ws2_32.lib psapi.lib version.lib advapi32.lib winmm.lib kernel32.lib) +endif() + # # SUBDIRS # @@ -294,16 +306,7 @@ if(LLVM_LIBDIR) link_directories(${LLVM_LIBDIR}) endif() -if(HOST_DARWIN) -set(OS_LIBS "-framework CoreFoundation" "-framework Foundation") -elseif(HOST_IOS) -set(OS_LIBS "-framework CoreFoundation" "-lobjc" "-lc++") -elseif(HOST_ANDROID) -set(OS_LIBS m dl log) -elseif(HOST_LINUX) -set(OS_LIBS pthread m dl) -elseif(HOST_WIN32) -set(OS_LIBS bcrypt.lib Mswsock.lib ws2_32.lib psapi.lib version.lib advapi32.lib winmm.lib kernel32.lib) +if(HOST_WIN32) set(mini_sources "${mini_sources};${PROJECT_BINARY_DIR}/../../NativeVersion.rc") # this is generated by GenerateMonoVersionFile in mono.proj endif() @@ -348,12 +351,12 @@ if(NOT DISABLE_SHARED_LIBS) if(TARGET_DARWIN) set_property(TARGET monosgen-shared APPEND_STRING PROPERTY LINK_FLAGS " -Wl,-compatibility_version -Wl,2.0 -Wl,-current_version -Wl,2.0") endif() - if (STATIC_COMPONENTS) + if (NOT DISABLE_COMPONENTS AND STATIC_COMPONENTS) # if components are built statically, but we're building a shared lib mono, # link them into the library target_link_libraries (monosgen-shared PRIVATE "mono-components-static") else() - # if components are built dynamically, link the fallback stubs into the runtime + # if components are built dynamically or disabled, link the fallback stubs into the runtime target_link_libraries (monosgen-shared PRIVATE "mono-components-stubs-static") endif() install(TARGETS monosgen-shared LIBRARY) @@ -406,7 +409,7 @@ if(NOT DISABLE_EXECUTABLES) endif() add_executable(mono-sgen "${sgen_sources}") target_link_libraries(mono-sgen monosgen-static ${OS_LIBS} ${ICONV_LIB} ${LLVM_LIBS} ${ICU_LIBS}) - if (STATIC_COMPONENTS) + if (NOT DISABLE_COMPONENTS AND STATIC_COMPONENTS) target_link_libraries(mono-sgen "mono-components-static") else() target_link_libraries(mono-sgen "mono-components-stubs-static") From 8e28f27020389aa1a41817d4a0c0982b044c94a9 Mon Sep 17 00:00:00 2001 From: lateralusX Date: Thu, 1 Apr 2021 15:16:50 +0200 Subject: [PATCH 31/55] Quite hot_reload component. --- src/mono/mono/component/hot_reload.c | 9 ++------- 1 file changed, 2 insertions(+), 7 deletions(-) diff --git a/src/mono/mono/component/hot_reload.c b/src/mono/mono/component/hot_reload.c index 8a70eb62ba68f9..5476fd0150db2c 100644 --- a/src/mono/mono/component/hot_reload.c +++ b/src/mono/mono/component/hot_reload.c @@ -29,10 +29,7 @@ static MonoComponentHotReload fn_table = { MonoComponentHotReload * mono_component_hot_reload_init (void) { - /* TODO: initialize things */ - - fprintf (stderr, "hot reload initialized\n"); - + /* TODO: implement me */ return &fn_table; } @@ -44,13 +41,11 @@ hot_reload_cleanup (MonoComponent *self) return; /* TODO: implement me */ - fprintf (stderr, "hot reload cleaned up\n"); - cleaned = TRUE; } static void hot_reload_apply_changes (MonoImage *base_image, gconstpointer dmeta, uint32_t dmeta_len, gconstpointer dil, uint32_t dil_len, MonoError *error) { - fprintf (stderr, "it worked!\n"); + /* TODO: implement me */ } From 850367b78f3fcd3d9cbca2841b71a61d3c473734 Mon Sep 17 00:00:00 2001 From: lateralusX Date: Thu, 1 Apr 2021 16:47:30 +0200 Subject: [PATCH 32/55] Build shared mono runtime using final library name. --- src/mono/CMakeLists.txt | 4 +++ src/mono/mono.proj | 44 +++++++++++++++---------------- src/mono/mono/mini/CMakeLists.txt | 8 +++--- 3 files changed, 29 insertions(+), 27 deletions(-) diff --git a/src/mono/CMakeLists.txt b/src/mono/CMakeLists.txt index 4cbabf0e0842d4..cff8015614a26b 100644 --- a/src/mono/CMakeLists.txt +++ b/src/mono/CMakeLists.txt @@ -11,6 +11,10 @@ set(CMAKE_CXX_FLAGS_CHECKED "") set(CMAKE_EXE_LINKER_FLAGS_CHECKED "") set(CMAKE_SHARED_LINKER_FLAGS_CHECKED "") +if(NOT MONO_LIB_NAME) + set(MONO_LIB_NAME "monosgen-2.0") +endif() + include(GNUInstallDirs) include(CheckIncludeFile) include(CheckFunctionExists) diff --git a/src/mono/mono.proj b/src/mono/mono.proj index 60dc97a094bfe0..c8bd5b7f5c3868 100644 --- a/src/mono/mono.proj +++ b/src/mono/mono.proj @@ -28,15 +28,19 @@ \" python3 python - coreclr.dll - libcoreclr.dylib - libcoreclr.dylib - libcoreclr.so - libmonosgen-2.0.dylib - libmonosgen-2.0.so - libmonosgen-2.0.a + coreclr + monosgen-2.0 + $(CoreClrLibName).dll + lib$(CoreClrLibName).dylib + lib$(CoreClrLibName).dylib + lib$(CoreClrLibName).so + lib$(MonoLibName).dylib + lib$(MonoLibName).so + lib$(MonoLibName).a + $(MonoLibName) + $(CoreClrLibName) $(CoreClrFileName) - libmonosgen-2.0.a + lib$(MonoLibName).a .dylib .dll .so @@ -204,6 +208,7 @@ <_MonoCMakeArgs Condition="'$(CMakeArgs)' != ''" Include="$(CMakeArgs)"/> <_MonoCMakeArgs Condition="'$(MonoEnableLLVM)' == 'true'" Include="-DLLVM_PREFIX=$(MonoLLVMDir.TrimEnd('\/'))" /> <_MonoCMakeArgs Include="-DGC_SUSPEND=$(MonoThreadSuspend)" /> + <_MonoCMakeArgs Include="-DMONO_LIB_NAME=$(MonoCMakeLibName)" /> @@ -631,14 +636,14 @@ - <_MonoRuntimeFilePath Condition="'$(TargetsWindows)' == 'true'">$(MonoObjDir)out\bin\monosgen-2.0.dll - <_MonoRuntimeFilePath Condition="'$(TargetsOSX)' == 'true'">$(MonoObjDir)out\lib\libmonosgen-2.0.dylib - <_MonoRuntimeFilePath Condition="'$(TargetsMacCatalyst)' == 'true'">$(MonoObjDir)out\lib\libmonosgen-2.0.dylib - <_MonoRuntimeFilePath Condition="'$(TargetsiOS)' == 'true'">$(MonoObjDir)out\lib\libmonosgen-2.0.dylib - <_MonoRuntimeFilePath Condition="'$(TargetstvOS)' == 'true'">$(MonoObjDir)out\lib\libmonosgen-2.0.dylib - <_MonoRuntimeFilePath Condition="'$(TargetsBrowser)' == 'true'">$(MonoObjDir)out\lib\libmonosgen-2.0.a - <_MonoRuntimeFilePath Condition="'$(_MonoRuntimeFilePath)' == ''">$(MonoObjDir)out\lib\libmonosgen-2.0.so - <_MonoRuntimeStaticFilePath Condition="'$(TargetsMacCatalyst)' == 'true' or '$(TargetsiOS)' == 'true' or '$(TargetstvOS)' == 'true' or '$(TargetsAndroid)' == 'true'">$(MonoObjDir)out\lib\libmonosgen-2.0.a + <_MonoRuntimeFilePath Condition="'$(TargetsWindows)' == 'true'">$(MonoObjDir)out\bin\$(MonoCMakeLibName).dll + <_MonoRuntimeFilePath Condition="'$(TargetsOSX)' == 'true'">$(MonoObjDir)out\lib\lib$(MonoCMakeLibName).dylib + <_MonoRuntimeFilePath Condition="'$(TargetsMacCatalyst)' == 'true'">$(MonoObjDir)out\lib\lib$(MonoCMakeLibName).dylib + <_MonoRuntimeFilePath Condition="'$(TargetsiOS)' == 'true'">$(MonoObjDir)out\lib\lib$(MonoCMakeLibName).dylib + <_MonoRuntimeFilePath Condition="'$(TargetstvOS)' == 'true'">$(MonoObjDir)out\lib\lib$(MonoCMakeLibName).dylib + <_MonoRuntimeFilePath Condition="'$(TargetsBrowser)' == 'true'">$(MonoObjDir)out\lib\lib$(MonoCMakeLibName).a + <_MonoRuntimeFilePath Condition="'$(_MonoRuntimeFilePath)' == ''">$(MonoObjDir)out\lib\lib$(MonoCMakeLibName).so + <_MonoRuntimeStaticFilePath Condition="'$(TargetsMacCatalyst)' == 'true' or '$(TargetsiOS)' == 'true' or '$(TargetstvOS)' == 'true' or '$(TargetsAndroid)' == 'true'">$(MonoObjDir)out\lib\lib$(MonoCMakeLibName).a <_MonoIncludeInterpStaticFiles Condition="'$(TargetsBrowser)' == 'true'">true <_MonoIncludeIcuFiles Condition="'$(TargetsiOS)' == 'true' or '$(TargetstvOS)' == 'true'">true @@ -725,14 +730,7 @@ SkipUnchangedFiles="true" Condition="'$(MonoGenerateOffsetsOSGroups)' == '' and ('$(TargetsMacCatalyst)' == 'true' or '$(TargetsiOS)' == 'true' or '$(TargetstvOS)' == 'true' or '$(TargetsAndroid)' == 'true' or '$(TargetsBrowser)' == 'true')"/> - - <_MonoRuntimeComponentsSharedArtifacts Include="$(RuntimeBinDir)libmono-component-*$(SharedNativeLibrarySuffix)" /> - - - - - diff --git a/src/mono/mono/mini/CMakeLists.txt b/src/mono/mono/mini/CMakeLists.txt index ab055d461835b4..41fde405eb496d 100644 --- a/src/mono/mono/mini/CMakeLists.txt +++ b/src/mono/mono/mini/CMakeLists.txt @@ -314,7 +314,7 @@ set(monosgen-sources "${metadata_sources};${utils_sources};${sgen_sources};${icu add_library(monosgen-objects OBJECT "${monosgen-sources}") add_library(monosgen-static STATIC $) -set_target_properties(monosgen-static PROPERTIES OUTPUT_NAME monosgen-2.0) +set_target_properties(monosgen-static PROPERTIES OUTPUT_NAME ${MONO_LIB_NAME}) target_link_libraries(monosgen-static eglib_objects) if(NOT DISABLE_LIBS) @@ -335,9 +335,9 @@ if(NOT DISABLE_SHARED_LIBS) target_compile_definitions(monosgen-objects PRIVATE -DMONO_DLL_EXPORT) endif() target_link_libraries(monosgen-shared PRIVATE eglib_objects) - set_target_properties(monosgen-shared PROPERTIES OUTPUT_NAME monosgen-2.0) + set_target_properties(monosgen-shared PROPERTIES OUTPUT_NAME ${MONO_LIB_NAME}) if(TARGET_WIN32) - # on Windows the import library for the shared monosgen-2.0 library will have the same name as the static library (monosgen-2.0.lib), + # on Windows the import library for the shared mono library will have the same name as the static library, # to avoid a conflict we rename the import library with the .import.lib suffix set_target_properties(monosgen-shared PROPERTIES IMPORT_SUFFIX ".import.lib") endif() @@ -362,7 +362,7 @@ if(NOT DISABLE_SHARED_LIBS) install(TARGETS monosgen-shared LIBRARY) if(HOST_WIN32) add_library(monosgen-shared-dac SHARED "mini-windows-dlldac.c") - set_target_properties(monosgen-shared-dac PROPERTIES OUTPUT_NAME monosgen-2.0-dac) + set_target_properties(monosgen-shared-dac PROPERTIES OUTPUT_NAME ${MONO_LIB_NAME}-dac) install(TARGETS monosgen-shared-dac LIBRARY) endif() endif() From bcbe7bc73a2014c839771afc106ea6abf05295af Mon Sep 17 00:00:00 2001 From: lateralusX Date: Thu, 1 Apr 2021 16:48:03 +0200 Subject: [PATCH 33/55] Fix multiple components hosted by same shared library. --- src/mono/mono/metadata/components.c | 56 +++++++++++++++-------------- 1 file changed, 30 insertions(+), 26 deletions(-) diff --git a/src/mono/mono/metadata/components.c b/src/mono/mono/metadata/components.c index e8cab3ccee1ab8..c7edd28ef9547c 100644 --- a/src/mono/mono/metadata/components.c +++ b/src/mono/mono/metadata/components.c @@ -18,6 +18,7 @@ typedef MonoComponent * (*MonoComponentInitFn) (void); typedef struct _MonoComponentEntry { + const char *lib_name; const char *name; MonoComponentInitFn init; MonoComponent **component; @@ -30,30 +31,33 @@ typedef struct _MonoComponentEntry { #define COMPONENT_INIT_FUNC(name) (MonoComponentInitFn) mono_component_ ## name ## _stub_init #endif -#define HOT_RELOAD_MODULE_NAME "hot_reload" +#define HOT_RELOAD_LIBRARY_NAME "hot_reload" +#define HOT_RELOAD_COMPONENT_NAME HOT_RELOAD_LIBRARY_NAME MonoComponentHotReload *hot_reload = NULL; #ifdef ENABLE_PERFTRACING MonoComponentEventPipe *event_pipe = NULL; MonoComponentDiagnosticsServer *diagnostics_server = NULL; -// DiagnosticsServer component currently hosted by EventPipe module. -#define EVENT_PIPE_MODULE_NAME "event_pipe" -#define DIAGNOSTICS_SERVER_MODULE_NAME EVENT_PIPE_MODULE_NAME +// DiagnosticsServer component currently hosted by EventPipe library. +#define EVENT_PIPE_LIBRARY_NAME "event_pipe" +#define DIAGNOSTICS_SERVER_LIBRARY_NAME EVENT_PIPE_LIBRARY_NAME +#define EVENT_PIPE_COMPONENT_NAME "event_pipe" +#define DIAGNOSTICS_SERVER_COMPONENT_NAME "diagnostics_server" #endif /* One per component */ MonoComponentEntry components[] = { - { HOT_RELOAD_MODULE_NAME, COMPONENT_INIT_FUNC (hot_reload), (MonoComponent**)&hot_reload, NULL }, + { HOT_RELOAD_LIBRARY_NAME, HOT_RELOAD_COMPONENT_NAME, COMPONENT_INIT_FUNC (hot_reload), (MonoComponent**)&hot_reload, NULL }, #ifdef ENABLE_PERFTRACING - { EVENT_PIPE_MODULE_NAME, COMPONENT_INIT_FUNC (event_pipe), (MonoComponent**)&event_pipe, NULL }, - { DIAGNOSTICS_SERVER_MODULE_NAME, COMPONENT_INIT_FUNC (diagnostics_server), (MonoComponent**)&diagnostics_server, NULL }, + { EVENT_PIPE_LIBRARY_NAME, EVENT_PIPE_COMPONENT_NAME, COMPONENT_INIT_FUNC (event_pipe), (MonoComponent**)&event_pipe, NULL }, + { DIAGNOSTICS_SERVER_LIBRARY_NAME, DIAGNOSTICS_SERVER_COMPONENT_NAME, COMPONENT_INIT_FUNC (diagnostics_server), (MonoComponent**)&diagnostics_server, NULL }, #endif }; #ifndef STATIC_COMPONENTS static MonoComponent* -get_component (const char *component_name, MonoDl **component_lib); +get_component (const MonoComponentEntry *component, MonoDl **component_lib); #endif void @@ -80,7 +84,7 @@ mono_components_init (void) MonoDl *lib = NULL; for (int i = 0; i < G_N_ELEMENTS (components); ++i) { - *components [i].component = get_component (components [i].name, &lib); + *components [i].component = get_component (&components [i], &lib); components [i].lib = lib; if (!*components [i].component) *components [i].component = components [i].init (); @@ -101,19 +105,19 @@ mono_components_cleanup (void) } static char* -component_init_name (const char *component) +component_init_name (const MonoComponentEntry *component) { - return g_strdup_printf ("mono_component_%s_init", component); + return g_strdup_printf ("mono_component_%s_init", component->name); } static gpointer -load_component_entrypoint (MonoDl *lib, const char *component_name) +load_component_entrypoint (MonoDl *lib, const MonoComponentEntry *component) { - char *component_init = component_init_name (component_name); + char *component_init = component_init_name (component); gpointer sym = NULL; char *error_msg = mono_dl_symbol (lib, component_init, &sym); if (error_msg) { - mono_trace (G_LOG_LEVEL_DEBUG, MONO_TRACE_DLLIMPORT, "Component %s library does not have symbol %s: %s", component_name, component_init, error_msg); + mono_trace (G_LOG_LEVEL_DEBUG, MONO_TRACE_DLLIMPORT, "Component %s library does not have symbol %s: %s", component->name, component_init, error_msg); g_free (error_msg); g_free (component_init); return NULL; @@ -124,9 +128,9 @@ load_component_entrypoint (MonoDl *lib, const char *component_name) #ifndef STATIC_COMPONENTS static char* -component_library_base_name (const char *component) +component_library_base_name (const MonoComponentEntry *component) { - return g_strdup_printf ("mono-component-%s", component); + return g_strdup_printf ("mono-component-%s", component->lib_name); } static char * @@ -145,7 +149,7 @@ components_dir (void) } static MonoDl* -try_load (const char* dir, const char *component_name, const char* component_base_lib) +try_load (const char* dir, const MonoComponentEntry *component, const char* component_base_lib) { MonoDl *lib = NULL; void *iter = NULL; @@ -154,36 +158,36 @@ try_load (const char* dir, const char *component_name, const char* component_bas char *error_msg = NULL; lib = mono_dl_open (path, MONO_DL_EAGER, &error_msg); if (!lib) { - mono_trace (G_LOG_LEVEL_DEBUG, MONO_TRACE_DLLIMPORT, "Component %s not found: %s", component_name, error_msg); + mono_trace (G_LOG_LEVEL_DEBUG, MONO_TRACE_DLLIMPORT, "Component %s not found: %s", component->name, error_msg); g_free (error_msg); continue; } } if (lib) - mono_trace (G_LOG_LEVEL_DEBUG, MONO_TRACE_DLLIMPORT, "Component %s found at %s", component_name, path); + mono_trace (G_LOG_LEVEL_DEBUG, MONO_TRACE_DLLIMPORT, "Component %s found at %s", component->name, path); g_free (path); return lib; } static MonoComponentInitFn -load_component (const char *component_name, MonoDl **lib_out) +load_component (const MonoComponentEntry *component, MonoDl **lib_out) { - char *component_base_lib = component_library_base_name (component_name); + char *component_base_lib = component_library_base_name (component); MonoComponentInitFn result = NULL; /* FIXME: just copy what mono_profiler_load does, assuming it works */ /* FIXME: do I need to provide a path? */ MonoDl *lib = NULL; - lib = try_load (components_dir (), component_name, component_base_lib); + lib = try_load (components_dir (), component, component_base_lib); if (!lib) - lib = try_load (NULL, component_name, component_base_lib); + lib = try_load (NULL, component, component_base_lib); g_free (component_base_lib); if (!lib) goto done; - gpointer sym = load_component_entrypoint (lib, component_name); + gpointer sym = load_component_entrypoint (lib, component); result = (MonoComponentInitFn)sym; *lib_out = lib; @@ -192,9 +196,9 @@ load_component (const char *component_name, MonoDl **lib_out) } MonoComponent* -get_component (const char *component_name, MonoDl **lib_out) +get_component (const MonoComponentEntry *component, MonoDl **lib_out) { - MonoComponentInitFn initfn = load_component (component_name, lib_out); + MonoComponentInitFn initfn = load_component (component, lib_out); if (!initfn) return NULL; return initfn(); From 73738a8e8e97255553654002685a76cc572dfd06 Mon Sep 17 00:00:00 2001 From: lateralusX Date: Tue, 6 Apr 2021 16:45:28 +0200 Subject: [PATCH 34/55] Use static components and disable TCP/IP. --- src/mono/mono.proj | 8 +++++--- 1 file changed, 5 insertions(+), 3 deletions(-) diff --git a/src/mono/mono.proj b/src/mono/mono.proj index c8bd5b7f5c3868..890d6cc56392d0 100644 --- a/src/mono/mono.proj +++ b/src/mono/mono.proj @@ -89,7 +89,8 @@ true true - false + + true @@ -414,10 +415,11 @@ <_MonoCMakeArgs Include="-DENABLE_MSCORDBI=1" /> - + + From dd59777c41ff4d1ea3f916b7b41b34b7acce1d57 Mon Sep 17 00:00:00 2001 From: lateralusX Date: Wed, 7 Apr 2021 10:55:28 +0200 Subject: [PATCH 35/55] Cleanup after rebase/merge. --- src/mono/mono/eventpipe/ep-rt-mono.c | 4 +- src/mono/mono/metadata/icall-eventpipe.c | 572 ---------------------- src/mono/mono/metadata/jit-info.h | 4 +- src/mono/mono/metadata/loader-internals.h | 2 +- src/mono/mono/metadata/metadata.c | 20 - 5 files changed, 5 insertions(+), 597 deletions(-) diff --git a/src/mono/mono/eventpipe/ep-rt-mono.c b/src/mono/mono/eventpipe/ep-rt-mono.c index a3e7d9d076468e..103dbd842ce93f 100644 --- a/src/mono/mono/eventpipe/ep-rt-mono.c +++ b/src/mono/mono/eventpipe/ep-rt-mono.c @@ -1470,11 +1470,11 @@ eventpipe_execute_rundown ( events_data.buffer_size = 1024 * sizeof(uint32_t); events_data.buffer = g_new (uint8_t, events_data.buffer_size); events_data.method_events_func = method_events_func; - mono_jit_info_table_foreach_internal (root_domain, eventpipe_fire_method_events_func, &events_data); + mono_jit_info_table_foreach_internal (eventpipe_fire_method_events_func, &events_data); g_free (events_data.buffer); // Iterate all assemblies in domain. - GPtrArray *assemblies = mono_domain_get_assemblies (root_domain); + GPtrArray *assemblies = mono_alc_get_all_loaded_assemblies (); if (assemblies) { for (int i = 0; i < assemblies->len; ++i) { MonoAssembly *assembly = (MonoAssembly *)g_ptr_array_index (assemblies, i); diff --git a/src/mono/mono/metadata/icall-eventpipe.c b/src/mono/mono/metadata/icall-eventpipe.c index ad1ae17253daaa..53755c6b2f0277 100644 --- a/src/mono/mono/metadata/icall-eventpipe.c +++ b/src/mono/mono/metadata/icall-eventpipe.c @@ -27,578 +27,6 @@ delegate_callback_func ( EventFilterDescriptor *filter_data, void *callback_context); -static -gboolean -rand_try_get_bytes_func ( - guchar *buffer, - gssize buffer_size, - MonoError *error) -{ - g_assert (ep_rt_mono_rand_provider != NULL); - return mono_rand_try_get_bytes (&ep_rt_mono_rand_provider, buffer, buffer_size, error); -} - -static -EventPipeThread * -eventpipe_thread_get (void) -{ - EventPipeThreadHolder *thread_holder = (EventPipeThreadHolder *)mono_native_tls_get_value (ep_rt_mono_thread_holder_tls_id); - return thread_holder ? ep_thread_holder_get_thread (thread_holder) : NULL; -} - -static -EventPipeThread * -eventpipe_thread_get_or_create (void) -{ - EventPipeThreadHolder *thread_holder = (EventPipeThreadHolder *)mono_native_tls_get_value (ep_rt_mono_thread_holder_tls_id); - if (!thread_holder && thread_holder_alloc_callback_func) { - thread_holder = thread_holder_alloc_callback_func (); - mono_native_tls_set_value (ep_rt_mono_thread_holder_tls_id, thread_holder); - } - return ep_thread_holder_get_thread (thread_holder); -} - -static -void -eventpipe_thread_exited (void) -{ - if (ep_rt_mono_initialized) { - EventPipeThreadHolder *thread_holder = (EventPipeThreadHolder *)mono_native_tls_get_value (ep_rt_mono_thread_holder_tls_id); - if (thread_holder && thread_holder_free_callback_func) - thread_holder_free_callback_func (thread_holder); - mono_native_tls_set_value (ep_rt_mono_thread_holder_tls_id, NULL); - } -} - -static -void -profiler_eventpipe_thread_exited ( - MonoProfiler *prof, - uintptr_t tid) -{ - eventpipe_thread_exited (); -} - -static -gpointer -eventpipe_thread_attach (gboolean background_thread) -{ - MonoThread *thread = NULL; - - // NOTE, under netcore, only root domain exists. - if (!mono_thread_current ()) { - thread = mono_thread_internal_attach (mono_get_root_domain ()); - if (background_thread && thread) { - mono_thread_set_state (thread, ThreadState_Background); - mono_thread_info_set_flags (MONO_THREAD_INFO_FLAGS_NO_SAMPLE); - } - } - - return thread; -} - -static -void -eventpipe_thread_detach (void) -{ - MonoThread *current_thread = mono_thread_current (); - if (current_thread) - mono_thread_internal_detach (current_thread); -} - -static -void -eventpipe_fire_method_events ( - MonoJitInfo *ji, - MonoMethod *method, - EventPipeFireMethodEventsData *events_data) -{ - g_assert_checked (ji != NULL); - g_assert_checked (events_data->domain != NULL); - g_assert_checked (events_data->method_events_func != NULL); - - uint64_t method_id = 0; - uint64_t module_id = 0; - uint64_t method_code_start = (uint64_t)ji->code_start; - uint32_t method_code_size = (uint32_t)ji->code_size; - uint32_t method_token = 0; - uint32_t method_flags = 0; - uint8_t kind = MONO_CLASS_DEF; - char *method_namespace = NULL; - const char *method_name = NULL; - char *method_signature = NULL; - - //TODO: Optimize string formatting into functions accepting GString to reduce heap alloc. - - if (method) { - method_id = (uint64_t)method; - method_token = method->token; - - if (mono_jit_info_get_generic_sharing_context (ji)) - method_flags |= METHOD_FLAGS_SHARED_GENERIC_METHOD; - - if (method->dynamic) - method_flags |= METHOD_FLAGS_DYNAMIC_METHOD; - - if (!ji->from_aot && !ji->from_llvm) { - method_flags |= METHOD_FLAGS_JITTED_METHOD; - if (method->wrapper_type != MONO_WRAPPER_NONE) - method_flags |= METHOD_FLAGS_JITTED_HELPER_METHOD; - } - - if (method->is_generic || method->is_inflated) - method_flags |= METHOD_FLAGS_GENERIC_METHOD; - - method_name = method->name; - method_signature = mono_signature_full_name (method->signature); - - if (method->klass) { - module_id = (uint64_t)m_class_get_image (method->klass); - kind = m_class_get_class_kind (method->klass); - if (kind == MONO_CLASS_GTD || kind == MONO_CLASS_GINST) - method_flags |= METHOD_FLAGS_GENERIC_METHOD; - method_namespace = mono_type_get_name_full (m_class_get_byval_arg (method->klass), MONO_TYPE_NAME_FORMAT_IL); - } - } - - uint16_t offset_entries = 0; - uint32_t *il_offsets = NULL; - uint32_t *native_offsets = NULL; - - MonoDebugMethodJitInfo *debug_info = method ? mono_debug_find_method (method, events_data->domain) : NULL; - if (debug_info) { - offset_entries = debug_info->num_line_numbers; - size_t needed_size = (offset_entries * sizeof (uint32_t) * 2); - if (!events_data->buffer || needed_size > events_data->buffer_size) { - g_free (events_data->buffer); - events_data->buffer_size = (size_t)(needed_size * 1.5); - events_data->buffer = g_new (uint8_t, events_data->buffer_size); - } - - if (events_data->buffer) { - il_offsets = (uint32_t*)events_data->buffer; - native_offsets = il_offsets + offset_entries; - - for (int offset_count = 0; offset_count < offset_entries; ++offset_count) { - il_offsets [offset_count] = debug_info->line_numbers [offset_count].il_offset; - native_offsets [offset_count] = debug_info->line_numbers [offset_count].native_offset; - } - } - - mono_debug_free_method_jit_info (debug_info); - } - - if (events_data->buffer && !il_offsets && !native_offsets) { - // No IL offset -> Native offset mapping available. Put all code on IL offset 0. - g_assert_checked (events_data->buffer_size >= sizeof (uint32_t) * 2); - offset_entries = 1; - il_offsets = (uint32_t*)events_data->buffer; - native_offsets = il_offsets + offset_entries; - il_offsets [0] = 0; - native_offsets [0] = (uint32_t)ji->code_size; - } - - events_data->method_events_func ( - method_id, - module_id, - method_code_start, - method_code_size, - method_token, - method_flags, - (ep_char8_t *)method_namespace, - (ep_char8_t *)method_name, - (ep_char8_t *)method_signature, - offset_entries, - il_offsets, - native_offsets, - NULL); - - g_free (method_namespace); - g_free (method_signature); -} - -static -void -eventpipe_fire_method_events_func ( - MonoJitInfo *ji, - gpointer user_data) -{ - EventPipeFireMethodEventsData *events_data = (EventPipeFireMethodEventsData *)user_data; - g_assert_checked (events_data != NULL); - - if (ji && !ji->is_trampoline && !ji->async) { - MonoMethod *method = jinfo_get_method (ji); - if (method && !m_method_is_wrapper (method)) - eventpipe_fire_method_events (ji, method, events_data); - } -} - -static -void -eventpipe_fire_assembly_events ( - MonoDomain *domain, - MonoAssembly *assembly, - ep_rt_mono_fire_assembly_rundown_events_func assembly_events_func) -{ - g_assert_checked (domain != NULL); - g_assert_checked (assembly != NULL); - g_assert_checked (assembly_events_func != NULL); - - uint64_t domain_id = (uint64_t)domain; - uint64_t module_id = (uint64_t)assembly->image; - uint64_t assembly_id = (uint64_t)assembly; - - // TODO: Extract all module IL/Native paths and pdb metadata when available. - const char *module_il_path = ""; - const char *module_il_pdb_path = ""; - const char *module_native_path = ""; - const char *module_native_pdb_path = ""; - uint8_t signature [EP_GUID_SIZE] = { 0 }; - uint32_t module_il_pdb_age = 0; - uint32_t module_native_pdb_age = 0; - - uint32_t reserved_flags = 0; - uint64_t binding_id = 0; - - // Native methods are part of JIT table and already emitted. - // TODO: FireEtwMethodDCEndVerbose_V1_or_V2 for all native methods in module as well? - - // Netcore has a 1:1 between assemblies and modules, so its always a manifest module. - uint32_t module_flags = MODULE_FLAGS_MANIFEST_MODULE; - if (assembly->image) { - if (assembly->image->dynamic) - module_flags |= MODULE_FLAGS_DYNAMIC_MODULE; - if (assembly->image->aot_module) - module_flags |= MODULE_FLAGS_NATIVE_MODULE; - - module_il_path = assembly->image->filename ? assembly->image->filename : ""; - } - - uint32_t assembly_flags = 0; - if (assembly->dynamic) - assembly_flags |= ASSEMBLY_FLAGS_DYNAMIC_ASSEMBLY; - - if (assembly->image && assembly->image->aot_module) { - assembly_flags |= ASSEMBLY_FLAGS_NATIVE_ASSEMBLY; - } - - char *assembly_name = mono_stringify_assembly_name (&assembly->aname); - - assembly_events_func ( - domain_id, - assembly_id, - assembly_flags, - binding_id, - (const ep_char8_t*)assembly_name, - module_id, - module_flags, - reserved_flags, - (const ep_char8_t *)module_il_path, - (const ep_char8_t *)module_native_path, - signature, - module_il_pdb_age, - (const ep_char8_t *)module_il_pdb_path, - signature, - module_native_pdb_age, - (const ep_char8_t *)module_native_pdb_path, - NULL); - - g_free (assembly_name); -} - -static -gboolean -eventpipe_execute_rundown ( - ep_rt_mono_fire_domain_rundown_events_func domain_events_func, - ep_rt_mono_fire_assembly_rundown_events_func assembly_events_func, - ep_rt_mono_fire_method_rundown_events_func method_events_func) -{ - g_assert_checked (domain_events_func != NULL); - g_assert_checked (assembly_events_func != NULL); - g_assert_checked (method_events_func != NULL); - - // Under netcore we only have root domain. - MonoDomain *root_domain = mono_get_root_domain (); - if (root_domain) { - uint64_t domain_id = (uint64_t)root_domain; - - // Iterate all functions in use (both JIT and AOT). - EventPipeFireMethodEventsData events_data; - events_data.domain = root_domain; - events_data.buffer_size = 1024 * sizeof(uint32_t); - events_data.buffer = g_new (uint8_t, events_data.buffer_size); - events_data.method_events_func = method_events_func; - mono_jit_info_table_foreach_internal (eventpipe_fire_method_events_func, &events_data); - g_free (events_data.buffer); - - // Iterate all assemblies in domain. - GPtrArray *assemblies = mono_alc_get_all_loaded_assemblies (); - if (assemblies) { - for (int i = 0; i < assemblies->len; ++i) { - MonoAssembly *assembly = (MonoAssembly *)g_ptr_array_index (assemblies, i); - if (assembly) - eventpipe_fire_assembly_events (root_domain, assembly, assembly_events_func); - } - g_ptr_array_free (assemblies, TRUE); - } - - uint32_t domain_flags = DOMAIN_FLAGS_DEFAULT_DOMAIN | DOMAIN_FLAGS_EXECUTABLE_DOMAIN; - const char *domain_name = root_domain->friendly_name ? root_domain->friendly_name : ""; - uint32_t domain_index = 1; - - domain_events_func ( - domain_id, - domain_flags, - (const ep_char8_t *)domain_name, - domain_index, - NULL); - } - - return TRUE; -} - -static -gboolean -eventpipe_walk_managed_stack_for_thread_func ( - MonoStackFrameInfo *frame, - MonoContext *ctx, - gpointer data) -{ - g_assert_checked (frame != NULL); - g_assert_checked (data != NULL); - - switch (frame->type) { - case FRAME_TYPE_DEBUGGER_INVOKE: - case FRAME_TYPE_MANAGED_TO_NATIVE: - case FRAME_TYPE_TRAMPOLINE: - case FRAME_TYPE_INTERP_TO_MANAGED: - case FRAME_TYPE_INTERP_TO_MANAGED_WITH_CTX: - return FALSE; - case FRAME_TYPE_MANAGED: - case FRAME_TYPE_INTERP: - if (!frame->ji) - return FALSE; - MonoMethod *method = frame->ji->async ? NULL : frame->actual_method; - if (method && !m_method_is_wrapper (method)) - ep_stack_contents_append ((EventPipeStackContents *)data, (uintptr_t)((uint8_t*)frame->ji->code_start + frame->native_offset), method); - return ep_stack_contents_get_length ((EventPipeStackContents *)data) >= EP_MAX_STACK_DEPTH; - default: - g_assert_not_reached (); - return FALSE; - } -} - -static -gboolean -eventpipe_walk_managed_stack_for_thread ( - ep_rt_thread_handle_t thread, - EventPipeStackContents *stack_contents) -{ - g_assert (thread != NULL && stack_contents != NULL); - - if (thread == ep_rt_thread_get_handle ()) - mono_get_eh_callbacks ()->mono_walk_stack_with_ctx (eventpipe_walk_managed_stack_for_thread_func, NULL, MONO_UNWIND_SIGNAL_SAFE, stack_contents); - else - mono_get_eh_callbacks ()->mono_walk_stack_with_state (eventpipe_walk_managed_stack_for_thread_func, mono_thread_info_get_suspend_state (thread), MONO_UNWIND_SIGNAL_SAFE, stack_contents); - - return TRUE; -} - -static -gboolean -eventpipe_sample_profiler_walk_managed_stack_for_thread_func ( - MonoStackFrameInfo *frame, - MonoContext *ctx, - gpointer data) -{ - g_assert_checked (frame != NULL); - g_assert_checked (data != NULL); - - EventPipeSampleProfileData *sample_data = (EventPipeSampleProfileData *)data; - - if (sample_data->payload_data == EP_SAMPLE_PROFILER_SAMPLE_TYPE_ERROR) { - if (frame->type == FRAME_TYPE_MANAGED_TO_NATIVE) - sample_data->payload_data = EP_SAMPLE_PROFILER_SAMPLE_TYPE_EXTERNAL; - else - sample_data->payload_data = EP_SAMPLE_PROFILER_SAMPLE_TYPE_MANAGED; - } - - return eventpipe_walk_managed_stack_for_thread_func (frame, ctx, &sample_data->stack_contents); -} - -static -gboolean -eventpipe_sample_profiler_write_sampling_event_for_threads ( - ep_rt_thread_handle_t sampling_thread, - EventPipeEvent *sampling_event) -{ - // Follows CoreClr implementation of sample profiler. Generic invasive/expensive way to do CPU sample profiling relying on STW and stackwalks. - // TODO: Investigate alternatives on platforms supporting Signals/SuspendThread (see Mono profiler) or CPU PMU's (see ETW/perf_event_open). - - // Sample profiler only runs on one thread, no need to synchorinize. - if (!_ep_rt_mono_sampled_thread_callstacks) - _ep_rt_mono_sampled_thread_callstacks = g_array_sized_new (FALSE, FALSE, sizeof (EventPipeSampleProfileData), _ep_rt_mono_max_sampled_thread_count); - - // Make sure there is room based on previous max number of sampled threads. - // NOTE, there is a chance there are more threads than max, if that's the case we will - // miss those threads in this sample, but will be included in next when max has been adjusted. - g_array_set_size (_ep_rt_mono_sampled_thread_callstacks, _ep_rt_mono_max_sampled_thread_count); - - uint32_t filtered_thread_count = 0; - uint32_t sampled_thread_count = 0; - - mono_stop_world (MONO_THREAD_INFO_FLAGS_NO_GC | MONO_THREAD_INFO_FLAGS_NO_SAMPLE); - - // Record all info needed in sample events while runtime is suspended, must be async safe. - FOREACH_THREAD_SAFE_EXCLUDE (thread_info, MONO_THREAD_INFO_FLAGS_NO_GC | MONO_THREAD_INFO_FLAGS_NO_SAMPLE) { - if (!mono_thread_info_is_running (thread_info)) { - MonoThreadUnwindState *thread_state = mono_thread_info_get_suspend_state (thread_info); - if (thread_state->valid) { - if (sampled_thread_count < _ep_rt_mono_max_sampled_thread_count) { - EventPipeSampleProfileData *data = &g_array_index (_ep_rt_mono_sampled_thread_callstacks, EventPipeSampleProfileData, sampled_thread_count); - data->thread_id = ep_rt_thread_id_t_to_uint64_t (mono_thread_info_get_tid (thread_info)); - data->thread_ip = (uintptr_t)MONO_CONTEXT_GET_IP (&thread_state->ctx); - data->payload_data = EP_SAMPLE_PROFILER_SAMPLE_TYPE_ERROR; - ep_stack_contents_reset (&data->stack_contents); - mono_get_eh_callbacks ()->mono_walk_stack_with_state (eventpipe_sample_profiler_walk_managed_stack_for_thread_func, thread_state, MONO_UNWIND_SIGNAL_SAFE, data); - sampled_thread_count++; - } - } - } - filtered_thread_count++; - } FOREACH_THREAD_SAFE_END - - mono_restart_world (MONO_THREAD_INFO_FLAGS_NO_GC | MONO_THREAD_INFO_FLAGS_NO_SAMPLE); - - // Fire sample event for threads. Must be done after runtime is resumed since it's not async safe. - // Since we can't keep thread info around after runtime as been suspended, use an empty - // adapter instance and only set recorded tid as parameter inside adapter. - THREAD_INFO_TYPE adapter = { 0 }; - for (uint32_t i = 0; i < sampled_thread_count; ++i) { - EventPipeSampleProfileData *data = &g_array_index (_ep_rt_mono_sampled_thread_callstacks, EventPipeSampleProfileData, i); - if (data->payload_data != EP_SAMPLE_PROFILER_SAMPLE_TYPE_ERROR && ep_stack_contents_get_length(&data->stack_contents) > 0) { - mono_thread_info_set_tid (&adapter, ep_rt_uint64_t_to_thread_id_t (data->thread_id)); - ep_write_sample_profile_event (sampling_thread, sampling_event, &adapter, &data->stack_contents, (uint8_t *)&data->payload_data, sizeof (data->payload_data)); - } - } - - // Current thread count will be our next maximum sampled threads. - _ep_rt_mono_max_sampled_thread_count = filtered_thread_count; - - return TRUE; -} - -static -gboolean -eventpipe_method_get_simple_assembly_name ( - ep_rt_method_desc_t *method, - ep_char8_t *name, - size_t name_len) -{ - g_assert_checked (method != NULL); - g_assert_checked (name != NULL); - - MonoClass *method_class = mono_method_get_class (method); - MonoImage *method_image = method_class ? mono_class_get_image (method_class) : NULL; - const ep_char8_t *assembly_name = method_image ? mono_image_get_name (method_image) : NULL; - - if (!assembly_name) - return FALSE; - - g_strlcpy (name, assembly_name, name_len); - return TRUE; -} - -static -gboolean -evetpipe_method_get_full_name ( - ep_rt_method_desc_t *method, - ep_char8_t *name, - size_t name_len) -{ - g_assert_checked (method != NULL); - g_assert_checked (name != NULL); - - char *full_method_name = mono_method_get_name_full (method, TRUE, TRUE, MONO_TYPE_NAME_FORMAT_IL); - if (!full_method_name) - return FALSE; - - g_strlcpy (name, full_method_name, name_len); - - g_free (full_method_name); - return TRUE; -} - -void -mono_eventpipe_init ( - EventPipeMonoFuncTable *table, - ep_rt_thread_holder_alloc_func thread_holder_alloc_func, - ep_rt_thread_holder_free_func thread_holder_free_func) -{ - if (table != NULL) { - table->ep_rt_mono_cpu_count = mono_cpu_count; - table->ep_rt_mono_process_current_pid = mono_process_current_pid; - table->ep_rt_mono_native_thread_id_get = mono_native_thread_id_get; - table->ep_rt_mono_native_thread_id_equals = mono_native_thread_id_equals; - table->ep_rt_mono_runtime_is_shutting_down = mono_runtime_is_shutting_down; - table->ep_rt_mono_rand_try_get_bytes = rand_try_get_bytes_func; - table->ep_rt_mono_thread_get = eventpipe_thread_get; - table->ep_rt_mono_thread_get_or_create = eventpipe_thread_get_or_create; - table->ep_rt_mono_thread_exited = eventpipe_thread_exited; - table->ep_rt_mono_thread_info_sleep = mono_thread_info_sleep; - table->ep_rt_mono_thread_info_yield = mono_thread_info_yield; - table->ep_rt_mono_w32file_close = mono_w32file_close; - table->ep_rt_mono_w32file_create = mono_w32file_create; - table->ep_rt_mono_w32file_write = mono_w32file_write; - table->ep_rt_mono_w32event_create = mono_w32event_create; - table->ep_rt_mono_w32event_close = mono_w32event_close; - table->ep_rt_mono_w32event_set = mono_w32event_set; - table->ep_rt_mono_w32hadle_wait_one = mono_w32handle_wait_one; - table->ep_rt_mono_valloc = mono_valloc; - table->ep_rt_mono_vfree = mono_vfree; - table->ep_rt_mono_valloc_granule = mono_valloc_granule; - table->ep_rt_mono_thread_platform_create_thread = mono_thread_platform_create_thread; - table->ep_rt_mono_thread_attach = eventpipe_thread_attach; - table->ep_rt_mono_thread_detach = eventpipe_thread_detach; - table->ep_rt_mono_get_os_cmd_line = mono_get_os_cmd_line; - table->ep_rt_mono_get_managed_cmd_line = mono_runtime_get_managed_cmd_line; - table->ep_rt_mono_execute_rundown = eventpipe_execute_rundown; - table->ep_rt_mono_walk_managed_stack_for_thread = eventpipe_walk_managed_stack_for_thread; - table->ep_rt_mono_sample_profiler_write_sampling_event_for_threads = eventpipe_sample_profiler_write_sampling_event_for_threads; - table->ep_rt_mono_method_get_simple_assembly_name = eventpipe_method_get_simple_assembly_name; - table->ep_rt_mono_method_get_full_name = evetpipe_method_get_full_name; - } - - thread_holder_alloc_callback_func = thread_holder_alloc_func; - thread_holder_free_callback_func = thread_holder_free_func; - mono_native_tls_alloc (&ep_rt_mono_thread_holder_tls_id, NULL); - - mono_100ns_ticks (); - mono_rand_open (); - ep_rt_mono_rand_provider = mono_rand_init (NULL, 0); - - ep_rt_mono_initialized = TRUE; - - MonoProfilerHandle profiler = mono_profiler_create (NULL); - mono_profiler_set_thread_stopped_callback (profiler, profiler_eventpipe_thread_exited); -} - -void -mono_eventpipe_fini (void) -{ - if (_ep_rt_mono_sampled_thread_callstacks) - g_array_free (_ep_rt_mono_sampled_thread_callstacks, TRUE); - - if (ep_rt_mono_initialized) - mono_rand_close (ep_rt_mono_rand_provider); - - _ep_rt_mono_sampled_thread_callstacks = NULL; - ep_rt_mono_rand_provider = NULL; - thread_holder_alloc_callback_func = NULL; - thread_holder_free_callback_func = NULL; - ep_rt_mono_initialized = FALSE; -} - static void delegate_callback_data_free_func ( diff --git a/src/mono/mono/metadata/jit-info.h b/src/mono/mono/metadata/jit-info.h index dabb36af8bf3e1..ec41b61c0b3417 100644 --- a/src/mono/mono/metadata/jit-info.h +++ b/src/mono/mono/metadata/jit-info.h @@ -260,7 +260,7 @@ mono_jit_info_add_aot_module (MonoImage *image, gpointer start, gpointer end); MonoGenericJitInfo* mono_jit_info_get_generic_jit_info (MonoJitInfo *ji); -MonoGenericSharingContext* +MONO_COMPONENT_API MonoGenericSharingContext* mono_jit_info_get_generic_sharing_context (MonoJitInfo *ji); void @@ -289,7 +289,7 @@ MonoJitInfo* mono_jit_info_table_find_internal (gpointer addr, gboolean try_aot, typedef void (*MonoJitInfoFunc) (MonoJitInfo *ji, gpointer user_data); -void +MONO_COMPONENT_API void mono_jit_info_table_foreach_internal (MonoJitInfoFunc func, gpointer user_data); void diff --git a/src/mono/mono/metadata/loader-internals.h b/src/mono/mono/metadata/loader-internals.h index ec6eb8f80cdf3b..af4ff2e4865685 100644 --- a/src/mono/mono/metadata/loader-internals.h +++ b/src/mono/mono/metadata/loader-internals.h @@ -278,7 +278,7 @@ mono_alc_add_assembly (MonoAssemblyLoadContext *alc, MonoAssembly *ass); MonoAssembly* mono_alc_find_assembly (MonoAssemblyLoadContext *alc, MonoAssemblyName *aname); -GPtrArray* +MONO_COMPONENT_API GPtrArray* mono_alc_get_all_loaded_assemblies (void); MONO_API void diff --git a/src/mono/mono/metadata/metadata.c b/src/mono/mono/metadata/metadata.c index 4369c38078afc2..0d9c7dcfe048bb 100644 --- a/src/mono/mono/metadata/metadata.c +++ b/src/mono/mono/metadata/metadata.c @@ -2037,26 +2037,6 @@ mono_metadata_init (void) #endif } -/** - * mono_metadata_cleanup: - * - * Free all resources used by this module. - * This is a Mono runtime internal function. - */ -void -mono_metadata_cleanup (void) -{ -#ifdef ENABLE_METADATA_UPDATE - mono_metadata_update_cleanup (); -#endif - mono_components_cleanup (); - g_hash_table_destroy (type_cache); - type_cache = NULL; - g_ptr_array_free (image_sets, TRUE); - image_sets = NULL; - mono_os_mutex_destroy (&image_sets_mutex); -} - /** * mono_metadata_parse_type: * \param m metadata context From e730fdd328f4fe49909c1ffc99536a54da23ab7d Mon Sep 17 00:00:00 2001 From: lateralusX Date: Wed, 7 Apr 2021 11:12:45 +0200 Subject: [PATCH 36/55] Removed components.md. --- docs/design/mono/components.md | 1 + 1 file changed, 1 insertion(+) diff --git a/docs/design/mono/components.md b/docs/design/mono/components.md index 2dc982dbeaaf1a..5231d6f1bfa633 100644 --- a/docs/design/mono/components.md +++ b/docs/design/mono/components.md @@ -278,3 +278,4 @@ In each runtime pack we include: - An MSBuild targets file that defines targets to copy a specified set of components to the app publish folder (if components are dynamic); or to link the runtime together with stubs and a set of enabled components (if components are static) ** TODO ** Write this up in more detail + From be1778a7fa7919486fcb416f6de36fcc32ee6184 Mon Sep 17 00:00:00 2001 From: lateralusX Date: Thu, 8 Apr 2021 09:11:39 +0200 Subject: [PATCH 37/55] Only build mono dac shared library on Windows x64 and don't install. --- src/mono/mono/mini/CMakeLists.txt | 3 +-- 1 file changed, 1 insertion(+), 2 deletions(-) diff --git a/src/mono/mono/mini/CMakeLists.txt b/src/mono/mono/mini/CMakeLists.txt index 41fde405eb496d..3625053879ac77 100644 --- a/src/mono/mono/mini/CMakeLists.txt +++ b/src/mono/mono/mini/CMakeLists.txt @@ -360,10 +360,9 @@ if(NOT DISABLE_SHARED_LIBS) target_link_libraries (monosgen-shared PRIVATE "mono-components-stubs-static") endif() install(TARGETS monosgen-shared LIBRARY) - if(HOST_WIN32) + if(HOST_WIN32 AND TARGET_AMD64) add_library(monosgen-shared-dac SHARED "mini-windows-dlldac.c") set_target_properties(monosgen-shared-dac PROPERTIES OUTPUT_NAME ${MONO_LIB_NAME}-dac) - install(TARGETS monosgen-shared-dac LIBRARY) endif() endif() From 853dd855b4e6b5cb923ca4ed3079c999266f3546 Mon Sep 17 00:00:00 2001 From: lateralusX Date: Thu, 8 Apr 2021 10:03:40 +0200 Subject: [PATCH 38/55] Split static and shared lib names. --- src/mono/CMakeLists.txt | 4 ++++ src/mono/mono.proj | 29 +++++++++++++++-------------- src/mono/mono/mini/CMakeLists.txt | 4 ++-- 3 files changed, 21 insertions(+), 16 deletions(-) diff --git a/src/mono/CMakeLists.txt b/src/mono/CMakeLists.txt index cff8015614a26b..0ac0e24574af2c 100644 --- a/src/mono/CMakeLists.txt +++ b/src/mono/CMakeLists.txt @@ -15,6 +15,10 @@ if(NOT MONO_LIB_NAME) set(MONO_LIB_NAME "monosgen-2.0") endif() +if(NOT MONO_SHARED_LIB_NAME) + set(MONO_SHARED_LIB_NAME "$(MONO_LIB_NAME)") +endif() + include(GNUInstallDirs) include(CheckIncludeFile) include(CheckFunctionExists) diff --git a/src/mono/mono.proj b/src/mono/mono.proj index 890d6cc56392d0..09d6a662da8e14 100644 --- a/src/mono/mono.proj +++ b/src/mono/mono.proj @@ -29,16 +29,16 @@ python3 python coreclr - monosgen-2.0 $(CoreClrLibName).dll lib$(CoreClrLibName).dylib lib$(CoreClrLibName).dylib lib$(CoreClrLibName).so - lib$(MonoLibName).dylib - lib$(MonoLibName).so + monosgen-2.0 + $(MonoLibName) + $(CoreClrLibName) + lib$(MonoSharedLibName).dylib + lib$(MonoSharedLibName).so lib$(MonoLibName).a - $(MonoLibName) - $(CoreClrLibName) $(CoreClrFileName) lib$(MonoLibName).a .dylib @@ -209,7 +209,8 @@ <_MonoCMakeArgs Condition="'$(CMakeArgs)' != ''" Include="$(CMakeArgs)"/> <_MonoCMakeArgs Condition="'$(MonoEnableLLVM)' == 'true'" Include="-DLLVM_PREFIX=$(MonoLLVMDir.TrimEnd('\/'))" /> <_MonoCMakeArgs Include="-DGC_SUSPEND=$(MonoThreadSuspend)" /> - <_MonoCMakeArgs Include="-DMONO_LIB_NAME=$(MonoCMakeLibName)" /> + <_MonoCMakeArgs Include="-DMONO_LIB_NAME=$(MonoLibName)" /> + <_MonoCMakeArgs Include="-DMONO_SHARED_LIB_NAME=$(MonoSharedLibName)" /> @@ -638,14 +639,14 @@ - <_MonoRuntimeFilePath Condition="'$(TargetsWindows)' == 'true'">$(MonoObjDir)out\bin\$(MonoCMakeLibName).dll - <_MonoRuntimeFilePath Condition="'$(TargetsOSX)' == 'true'">$(MonoObjDir)out\lib\lib$(MonoCMakeLibName).dylib - <_MonoRuntimeFilePath Condition="'$(TargetsMacCatalyst)' == 'true'">$(MonoObjDir)out\lib\lib$(MonoCMakeLibName).dylib - <_MonoRuntimeFilePath Condition="'$(TargetsiOS)' == 'true'">$(MonoObjDir)out\lib\lib$(MonoCMakeLibName).dylib - <_MonoRuntimeFilePath Condition="'$(TargetstvOS)' == 'true'">$(MonoObjDir)out\lib\lib$(MonoCMakeLibName).dylib - <_MonoRuntimeFilePath Condition="'$(TargetsBrowser)' == 'true'">$(MonoObjDir)out\lib\lib$(MonoCMakeLibName).a - <_MonoRuntimeFilePath Condition="'$(_MonoRuntimeFilePath)' == ''">$(MonoObjDir)out\lib\lib$(MonoCMakeLibName).so - <_MonoRuntimeStaticFilePath Condition="'$(TargetsMacCatalyst)' == 'true' or '$(TargetsiOS)' == 'true' or '$(TargetstvOS)' == 'true' or '$(TargetsAndroid)' == 'true'">$(MonoObjDir)out\lib\lib$(MonoCMakeLibName).a + <_MonoRuntimeFilePath Condition="'$(TargetsWindows)' == 'true'">$(MonoObjDir)out\bin\$(MonoSharedLibName).dll + <_MonoRuntimeFilePath Condition="'$(TargetsOSX)' == 'true'">$(MonoObjDir)out\lib\lib$(MonoSharedLibName).dylib + <_MonoRuntimeFilePath Condition="'$(TargetsMacCatalyst)' == 'true'">$(MonoObjDir)out\lib\lib$(MonoSharedLibName).dylib + <_MonoRuntimeFilePath Condition="'$(TargetsiOS)' == 'true'">$(MonoObjDir)out\lib\lib$(MonoSharedLibName).dylib + <_MonoRuntimeFilePath Condition="'$(TargetstvOS)' == 'true'">$(MonoObjDir)out\lib\lib$(MonoSharedLibName).dylib + <_MonoRuntimeFilePath Condition="'$(TargetsBrowser)' == 'true'">$(MonoObjDir)out\lib\lib$(MonoLibName).a + <_MonoRuntimeFilePath Condition="'$(_MonoRuntimeFilePath)' == ''">$(MonoObjDir)out\lib\lib$(MonoSharedLibName).so + <_MonoRuntimeStaticFilePath Condition="'$(TargetsMacCatalyst)' == 'true' or '$(TargetsiOS)' == 'true' or '$(TargetstvOS)' == 'true' or '$(TargetsAndroid)' == 'true'">$(MonoObjDir)out\lib\lib$(MonoLibName).a <_MonoIncludeInterpStaticFiles Condition="'$(TargetsBrowser)' == 'true'">true <_MonoIncludeIcuFiles Condition="'$(TargetsiOS)' == 'true' or '$(TargetstvOS)' == 'true'">true diff --git a/src/mono/mono/mini/CMakeLists.txt b/src/mono/mono/mini/CMakeLists.txt index 3625053879ac77..ce7ba612f9db38 100644 --- a/src/mono/mono/mini/CMakeLists.txt +++ b/src/mono/mono/mini/CMakeLists.txt @@ -335,7 +335,7 @@ if(NOT DISABLE_SHARED_LIBS) target_compile_definitions(monosgen-objects PRIVATE -DMONO_DLL_EXPORT) endif() target_link_libraries(monosgen-shared PRIVATE eglib_objects) - set_target_properties(monosgen-shared PROPERTIES OUTPUT_NAME ${MONO_LIB_NAME}) + set_target_properties(monosgen-shared PROPERTIES OUTPUT_NAME ${MONO_SHARED_LIB_NAME}) if(TARGET_WIN32) # on Windows the import library for the shared mono library will have the same name as the static library, # to avoid a conflict we rename the import library with the .import.lib suffix @@ -362,7 +362,7 @@ if(NOT DISABLE_SHARED_LIBS) install(TARGETS monosgen-shared LIBRARY) if(HOST_WIN32 AND TARGET_AMD64) add_library(monosgen-shared-dac SHARED "mini-windows-dlldac.c") - set_target_properties(monosgen-shared-dac PROPERTIES OUTPUT_NAME ${MONO_LIB_NAME}-dac) + set_target_properties(monosgen-shared-dac PROPERTIES OUTPUT_NAME ${MONO_SHARED_LIB_NAME}-dac) endif() endif() From e9238e3d92a718cd47620f6d6284a19870b283a8 Mon Sep 17 00:00:00 2001 From: lateralusX Date: Thu, 8 Apr 2021 10:04:17 +0200 Subject: [PATCH 39/55] Add component artifacts to installer pkg. --- .../Microsoft.NETCore.App/Directory.Build.props | 16 ++++++++++++++++ 1 file changed, 16 insertions(+) diff --git a/src/installer/pkg/sfx/Microsoft.NETCore.App/Directory.Build.props b/src/installer/pkg/sfx/Microsoft.NETCore.App/Directory.Build.props index 506d9bd5320f54..cb4a88dd8a95f9 100644 --- a/src/installer/pkg/sfx/Microsoft.NETCore.App/Directory.Build.props +++ b/src/installer/pkg/sfx/Microsoft.NETCore.App/Directory.Build.props @@ -169,6 +169,7 @@ + @@ -176,6 +177,21 @@ + + + + + + + + + + + + + + + From cf6710ee780342ce565c48720749384add763ce8 Mon Sep 17 00:00:00 2001 From: lateralusX Date: Thu, 8 Apr 2021 20:40:50 +0200 Subject: [PATCH 40/55] Make owning_thread_id a little less racy on EP_CHECKED_BUILD. --- src/mono/mono/eventpipe/ep-rt-mono.h | 42 ++++++++++++++++++---- src/mono/mono/eventpipe/ep-rt-types-mono.h | 3 +- 2 files changed, 36 insertions(+), 9 deletions(-) diff --git a/src/mono/mono/eventpipe/ep-rt-mono.h b/src/mono/mono/eventpipe/ep-rt-mono.h index f8947083dfba91..50d288f8674e93 100644 --- a/src/mono/mono/eventpipe/ep-rt-mono.h +++ b/src/mono/mono/eventpipe/ep-rt-mono.h @@ -1480,13 +1480,43 @@ ep_rt_lock_requires_lock_not_held (const ep_rt_lock_handle_t *lock) * SpinLock. */ +#ifdef EP_CHECKED_BUILD +static +inline +void +ep_rt_spin_lock_set_owning_thread_id ( + ep_rt_spin_lock_handle_t *spin_lock, + MonoNativeThreadId thread_id) +{ + if (sizeof (spin_lock->owning_thread_id) == sizeof (uint32_t)) + ep_rt_volatile_store_uint32_t ((uint32_t *)&spin_lock->owning_thread_id, MONO_NATIVE_THREAD_ID_TO_UINT (thread_id)); + else if (sizeof (spin_lock->owning_thread_id) == sizeof (uint64_t)) + ep_rt_volatile_store_uint64_t ((uint64_t *)&spin_lock->owning_thread_id, MONO_NATIVE_THREAD_ID_TO_UINT (thread_id)); + else + spin_lock->owning_thread_id = thread_id; +} + +static +inline +MonoNativeThreadId +ep_rt_spin_lock_get_owning_thread_id (const ep_rt_spin_lock_handle_t *spin_lock) +{ + if (sizeof (spin_lock->owning_thread_id) == sizeof (uint32_t)) + return MONO_UINT_TO_NATIVE_THREAD_ID (ep_rt_volatile_load_uint32_t ((const uint32_t *)&spin_lock->owning_thread_id)); + else if (sizeof (spin_lock->owning_thread_id) == sizeof (uint64_t)) + return MONO_UINT_TO_NATIVE_THREAD_ID (ep_rt_volatile_load_uint64_t ((const uint64_t *)&spin_lock->owning_thread_id)); + else + return spin_lock->owning_thread_id; +} +#endif + static inline void ep_rt_spin_lock_alloc (ep_rt_spin_lock_handle_t *spin_lock) { #ifdef EP_CHECKED_BUILD - spin_lock->lock_is_held = false; + ep_rt_spin_lock_set_owning_thread_id (spin_lock, MONO_UINT_TO_NATIVE_THREAD_ID (0)); #endif spin_lock->lock = g_new0 (MonoCoopMutex, 1); if (spin_lock->lock) @@ -1513,8 +1543,7 @@ ep_rt_spin_lock_aquire (ep_rt_spin_lock_handle_t *spin_lock) if (spin_lock && spin_lock->lock) { mono_coop_mutex_lock (spin_lock->lock); #ifdef EP_CHECKED_BUILD - spin_lock->owning_thread_id = ep_rt_mono_native_thread_id_get (); - spin_lock->lock_is_held = true; + ep_rt_spin_lock_set_owning_thread_id (spin_lock, ep_rt_mono_native_thread_id_get ()); #endif } return true; @@ -1527,8 +1556,7 @@ ep_rt_spin_lock_release (ep_rt_spin_lock_handle_t *spin_lock) { if (spin_lock && spin_lock->lock) { #ifdef EP_CHECKED_BUILD - spin_lock->lock_is_held = false; - spin_lock->owning_thread_id = MONO_UINT_TO_NATIVE_THREAD_ID (0); + ep_rt_spin_lock_set_owning_thread_id (spin_lock, MONO_UINT_TO_NATIVE_THREAD_ID (0)); #endif mono_coop_mutex_unlock (spin_lock->lock); } @@ -1541,7 +1569,7 @@ inline void ep_rt_spin_lock_requires_lock_held (const ep_rt_spin_lock_handle_t *spin_lock) { - g_assert (spin_lock->lock_is_held && ep_rt_mono_native_thread_id_equals (spin_lock->owning_thread_id, ep_rt_mono_native_thread_id_get ())); + g_assert (ep_rt_mono_native_thread_id_equals (ep_rt_spin_lock_get_owning_thread_id (spin_lock), ep_rt_mono_native_thread_id_get ())); } static @@ -1549,7 +1577,7 @@ inline void ep_rt_spin_lock_requires_lock_not_held (const ep_rt_spin_lock_handle_t *spin_lock) { - g_assert (!spin_lock->lock_is_held || (spin_lock->lock_is_held && !ep_rt_mono_native_thread_id_equals (spin_lock->owning_thread_id, ep_rt_mono_native_thread_id_get ()))); + g_assert (!ep_rt_mono_native_thread_id_equals (ep_rt_spin_lock_get_owning_thread_id (spin_lock), ep_rt_mono_native_thread_id_get ())); } #endif diff --git a/src/mono/mono/eventpipe/ep-rt-types-mono.h b/src/mono/mono/eventpipe/ep-rt-types-mono.h index 484ee34d8c3a02..ef248e56af8b1e 100644 --- a/src/mono/mono/eventpipe/ep-rt-types-mono.h +++ b/src/mono/mono/eventpipe/ep-rt-types-mono.h @@ -68,8 +68,7 @@ struct _rt_mono_event_internal_t { struct _rt_mono_lock_internal_t { MonoCoopMutex *lock; #ifdef EP_CHECKED_BUILD - MonoNativeThreadId owning_thread_id; - bool lock_is_held; + volatile MonoNativeThreadId owning_thread_id; #endif }; From 7eba3c41691f32dddcebcce21d8ec530207a5f26 Mon Sep 17 00:00:00 2001 From: lateralusX Date: Thu, 8 Apr 2021 20:47:43 +0200 Subject: [PATCH 41/55] Emit EEStartupStart event on Mono runtime. --- src/mono/mono/component/event_pipe-stub.c | 25 +++++--- src/mono/mono/component/event_pipe.c | 41 ++++++------ src/mono/mono/component/event_pipe.h | 8 +++ src/mono/mono/eventpipe/ep-rt-mono.c | 77 ++++++++++++++++++++++- src/mono/mono/eventpipe/ep-rt-mono.h | 7 +++ src/mono/mono/metadata/appdomain.c | 1 + 6 files changed, 129 insertions(+), 30 deletions(-) diff --git a/src/mono/mono/component/event_pipe-stub.c b/src/mono/mono/component/event_pipe-stub.c index 1384dfde362be6..02ec77ace64d78 100644 --- a/src/mono/mono/component/event_pipe-stub.c +++ b/src/mono/mono/component/event_pipe-stub.c @@ -97,6 +97,10 @@ event_pipe_stub_thread_ctrl_activity_id ( uint8_t *activity_id, uint32_t activity_id_len); +static bool +event_pipe_stub_write_event_ee_startup_start (void); + + static MonoComponentEventPipe fn_table = { { &event_pipe_stub_cleanup }, &event_pipe_stub_init, @@ -107,13 +111,14 @@ static MonoComponentEventPipe fn_table = { &event_pipe_stub_get_next_event, &event_pipe_stub_get_wait_handle, &event_pipe_stub_start_streaming, - event_pipe_stub_write_event_2, - event_pipe_stub_create_provider, - event_pipe_stub_delete_provider, - event_pipe_stub_get_provider, - event_pipe_stub_provider_add_event, - event_pipe_stub_get_session_info, - event_pipe_stub_thread_ctrl_activity_id + &event_pipe_stub_write_event_2, + &event_pipe_stub_create_provider, + &event_pipe_stub_delete_provider, + &event_pipe_stub_get_provider, + &event_pipe_stub_provider_add_event, + &event_pipe_stub_get_session_info, + &event_pipe_stub_thread_ctrl_activity_id, + &event_pipe_stub_write_event_ee_startup_start }; static void @@ -237,6 +242,12 @@ event_pipe_stub_thread_ctrl_activity_id ( return false; } +static bool +event_pipe_stub_write_event_ee_startup_start (void) +{ + return true; +} + #ifdef STATIC_COMPONENTS MONO_COMPONENT_EXPORT_ENTRYPOINT MonoComponentEventPipe * diff --git a/src/mono/mono/component/event_pipe.c b/src/mono/mono/component/event_pipe.c index 8d409a89c2bdaa..19b48f251680e3 100644 --- a/src/mono/mono/component/event_pipe.c +++ b/src/mono/mono/component/event_pipe.c @@ -88,7 +88,8 @@ static MonoComponentEventPipe fn_table = { &ep_get_provider, &ep_provider_add_event, &event_pipe_get_session_info, - &event_pipe_thread_ctrl_activity_id + &event_pipe_thread_ctrl_activity_id, + &ep_rt_mono_write_event_ee_startup_start }; static void @@ -173,6 +174,25 @@ event_pipe_get_next_event ( return next_instance != NULL; } +static bool +event_pipe_get_session_info ( + EventPipeSessionID session_id, + EventPipeSessionInfo *instance) +{ + bool result = false; + if (instance) { + EventPipeSession *session = ep_get_session ((EventPipeSessionID)session_id); + if (session) { + instance->starttime_as_utc_filetime = ep_session_get_session_start_time (session); + instance->start_timestamp = ep_session_get_session_start_timestamp (session); + instance->timestamp_frequency = ep_perf_frequency_query (); + result = true; + } + } + + return result; +} + static bool event_pipe_thread_ctrl_activity_id ( EventPipeActivityControlCode activity_control_code, @@ -214,25 +234,6 @@ event_pipe_thread_ctrl_activity_id ( return result; } -static bool -event_pipe_get_session_info ( - EventPipeSessionID session_id, - EventPipeSessionInfo *instance) -{ - bool result = false; - if (instance) { - EventPipeSession *session = ep_get_session ((EventPipeSessionID)session_id); - if (session) { - instance->starttime_as_utc_filetime = ep_session_get_session_start_time (session); - instance->start_timestamp = ep_session_get_session_start_timestamp (session); - instance->timestamp_frequency = ep_perf_frequency_query (); - result = true; - } - } - - return result; -} - #ifndef STATIC_COMPONENTS MONO_COMPONENT_EXPORT_ENTRYPOINT MonoComponentEventPipe * diff --git a/src/mono/mono/component/event_pipe.h b/src/mono/mono/component/event_pipe.h index 11b81a53857da0..1fb5f6fd02006a 100644 --- a/src/mono/mono/component/event_pipe.h +++ b/src/mono/mono/component/event_pipe.h @@ -119,6 +119,13 @@ typedef bool uint8_t *activity_id, uint32_t activity_id_len); +/* + * EventPipe Native Events. + */ + +typedef bool +(*event_pipe_component_write_event_ee_startup_start)(void); + /* * MonoComponentEventPipe function table. */ @@ -140,6 +147,7 @@ typedef struct _MonoComponentEventPipe { event_pipe_component_provider_add_event_func provider_add_event; event_pipe_component_get_session_info_func get_session_info; event_pipe_component_thread_ctrl_activity_id_func thread_ctrl_activity_id; + event_pipe_component_write_event_ee_startup_start write_event_ee_startup_start; } MonoComponentEventPipe; #ifdef STATIC_COMPONENTS diff --git a/src/mono/mono/eventpipe/ep-rt-mono.c b/src/mono/mono/eventpipe/ep-rt-mono.c index 103dbd842ce93f..7c677639b085a4 100644 --- a/src/mono/mono/eventpipe/ep-rt-mono.c +++ b/src/mono/mono/eventpipe/ep-rt-mono.c @@ -59,6 +59,10 @@ EventPipeEvent *EventPipeEventAssemblyDCEnd_V1 = NULL; EventPipeEvent *EventPipeEventAppDomainDCEnd_V1 = NULL; EventPipeEvent *EventPipeEventRuntimeInformationDCStart = NULL; +// Runtime private events. +EventPipeProvider *EventPipeProviderDotNETRuntimePrivate = NULL; +EventPipeEvent *EventPipeEventEEStartupStart_V1 = NULL; + // Rundown types. typedef bool @@ -362,6 +366,17 @@ static void init_dotnet_runtime_rundown (void); +static +bool +write_event_ee_startup_start_v1 ( + const uint16_t clr_instance_id, + const uint8_t *activity_id, + const uint8_t *related_activity_id); + +static +void +init_dotnet_runtime_private (void); + static void eventpipe_fire_method_events ( @@ -462,9 +477,6 @@ ep_rt_mono_sample_profiler_write_sampling_event_for_threads ( ep_rt_thread_handle_t sampling_thread, EventPipeEvent *sampling_event); -void -ep_rt_mono_execute_rundown (void); - bool ep_rt_mono_walk_managed_stack_for_thread ( ep_rt_thread_handle_t thread, @@ -482,6 +494,9 @@ ep_rt_mono_method_get_full_name ( ep_char8_t *name, size_t name_len); +void +ep_rt_mono_execute_rundown (void); + static inline uint16_t @@ -1086,6 +1101,41 @@ write_event_domain_dc_end_v1 ( ep_exit_error_handler (); } +static +bool +write_event_ee_startup_start_v1 ( + const uint16_t clr_instance_id, + const uint8_t *activity_id, + const uint8_t *related_activity_id) +{ + EP_ASSERT (EventPipeEventEEStartupStart_V1 != NULL); + + if (!ep_event_is_enabled (EventPipeEventEEStartupStart_V1)) + return true; + + uint8_t stack_buffer [32]; + uint8_t *buffer = stack_buffer; + size_t offset = 0; + size_t size = sizeof (stack_buffer); + bool fixed_buffer = true; + bool success = true; + + success &= write_buffer_uint16_t (&clr_instance_id, &buffer, &offset, &size, &fixed_buffer); + + ep_raise_error_if_nok (success); + + ep_write_event (EventPipeEventEEStartupStart_V1, buffer, (uint32_t)offset, activity_id, related_activity_id); + +ep_on_exit: + if (!fixed_buffer) + ep_rt_byte_array_free (buffer); + return success; + +ep_on_error: + EP_ASSERT (!success); + ep_exit_error_handler (); +} + // Mapping FireEtw* CoreClr functions. #define FireEtwRuntimeInformationDCStart(...) write_runtime_info_dc_start(__VA_ARGS__,NULL,NULL) #define FireEtwDCEndInit_V1(...) write_event_dc_end_init_v1(__VA_ARGS__,NULL,NULL) @@ -1096,6 +1146,7 @@ write_event_domain_dc_end_v1 ( #define FireEtwAssemblyDCEnd_V1(...) write_event_assembly_dc_end_v1(__VA_ARGS__,NULL,NULL) #define FireEtwAppDomainDCEnd_V1(...) write_event_domain_dc_end_v1(__VA_ARGS__,NULL,NULL) #define FireEtwDCEndComplete_V1(...) write_event_dc_end_complete_v1(__VA_ARGS__,NULL,NULL) +#define FireEtwEEStartupStart_V1(...) write_event_ee_startup_start_v1(__VA_ARGS__,NULL,NULL) static bool @@ -1248,6 +1299,18 @@ init_dotnet_runtime_rundown (void) EventPipeEventRuntimeInformationDCStart = ep_provider_add_event (EventPipeProviderDotNETRuntimeRundown, 187, 0, 0, EP_EVENT_LEVEL_INFORMATIONAL, true, NULL, 0); } +static +void +init_dotnet_runtime_private (void) +{ + //TODO: Add callback method to enable/disable more native events getting into EventPipe (when enabled). + EP_ASSERT (EventPipeProviderDotNETRuntimePrivate == NULL); + EventPipeProviderDotNETRuntimePrivate = ep_create_provider (ep_config_get_private_provider_name_utf8 (), NULL, NULL, NULL); + + EP_ASSERT (EventPipeEventEEStartupStart_V1 == NULL); + EventPipeEventEEStartupStart_V1 = ep_provider_add_event (EventPipeProviderDotNETRuntimePrivate, 80, 2147483648, 1, EP_EVENT_LEVEL_INFORMATIONAL, true, NULL, 0); +} + static void eventpipe_fire_method_events ( @@ -1914,6 +1977,7 @@ void ep_rt_mono_init_providers_and_events (void) { init_dotnet_runtime_rundown (); + init_dotnet_runtime_private (); } void @@ -1923,6 +1987,7 @@ ep_rt_mono_fini_providers_and_events (void) // Deallocating providers/events here might cause AV if a WriteEvent // was to occur. Thus, we are not doing this cleanup. + // ep_delete_provider (EventPipeProviderDotNETRuntimePrivate); // ep_delete_provider (EventPipeProviderDotNETRuntimeRundown); } @@ -2081,6 +2146,12 @@ ep_rt_mono_execute_rundown (void) FireEtwDCEndComplete_V1 (clr_instance_get_id ()); } +bool +ep_rt_mono_write_event_ee_startup_start (void) +{ + return FireEtwEEStartupStart_V1 (clr_instance_get_id ()); +} + #endif /* ENABLE_PERFTRACING */ MONO_EMPTY_SOURCE_FILE(eventpipe_rt_mono); diff --git a/src/mono/mono/eventpipe/ep-rt-mono.h b/src/mono/mono/eventpipe/ep-rt-mono.h index 50d288f8674e93..fd8c94cd766cb7 100644 --- a/src/mono/mono/eventpipe/ep-rt-mono.h +++ b/src/mono/mono/eventpipe/ep-rt-mono.h @@ -2106,5 +2106,12 @@ ep_rt_volatile_store_ptr_without_barrier ( *ptr = value; } +/* + * EventPipe Native Events. + */ + +bool +ep_rt_mono_write_event_ee_startup_start (void); + #endif /* ENABLE_PERFTRACING */ #endif /* __EVENTPIPE_RT_MONO_H__ */ diff --git a/src/mono/mono/metadata/appdomain.c b/src/mono/mono/metadata/appdomain.c index 26e2f52da4f79b..2f6a7f8faef0b6 100644 --- a/src/mono/mono/metadata/appdomain.c +++ b/src/mono/mono/metadata/appdomain.c @@ -281,6 +281,7 @@ mono_runtime_init_checked (MonoDomain *domain, MonoThreadStartCB start_cb, MonoT #if defined(ENABLE_PERFTRACING) && !defined(DISABLE_EVENTPIPE) mono_component_diagnostics_server ()->init (); mono_component_diagnostics_server ()->pause_for_diagnostics_monitor (); + mono_component_event_pipe ()->write_event_ee_startup_start (); #endif mono_type_initialization_init (); From b74160cdeafdcf855e56647ee522fb0509ec78b8 Mon Sep 17 00:00:00 2001 From: lateralusX Date: Fri, 9 Apr 2021 15:05:03 +0200 Subject: [PATCH 42/55] Fix DISABLE_COMPONENTS to included needed stubs in monosgen-2.0 static lib. --- src/mono/mono/CMakeLists.txt | 6 -- src/mono/mono/component/CMakeLists.txt | 87 ++++++++++--------- .../mono/component/diagnostics_server-stub.c | 3 - src/mono/mono/component/diagnostics_server.c | 3 - src/mono/mono/component/diagnostics_server.h | 6 +- src/mono/mono/component/event_pipe-stub.c | 3 - src/mono/mono/component/event_pipe.c | 4 - src/mono/mono/component/event_pipe.h | 7 +- src/mono/mono/eventpipe/test/CMakeLists.txt | 31 +------ src/mono/mono/metadata/appdomain.c | 3 +- src/mono/mono/metadata/components.c | 4 - src/mono/mono/metadata/components.h | 4 - src/mono/mono/mini/CMakeLists.txt | 39 ++++++--- src/mono/mono/mini/mini-runtime.c | 6 -- 14 files changed, 82 insertions(+), 124 deletions(-) diff --git a/src/mono/mono/CMakeLists.txt b/src/mono/mono/CMakeLists.txt index 817a804b68752c..897a1886ac74b8 100644 --- a/src/mono/mono/CMakeLists.txt +++ b/src/mono/mono/CMakeLists.txt @@ -2,12 +2,6 @@ project(mono) set(subdirs mini profiler) -if(ENABLE_PERFTRACING) - list(APPEND subdirs - eventpipe/test - ) -endif(ENABLE_PERFTRACING) - foreach(dir ${subdirs}) add_subdirectory(${dir}) endforeach() diff --git a/src/mono/mono/component/CMakeLists.txt b/src/mono/mono/component/CMakeLists.txt index 5a46948a073906..b1880e243b8b6f 100644 --- a/src/mono/mono/component/CMakeLists.txt +++ b/src/mono/mono/component/CMakeLists.txt @@ -4,6 +4,8 @@ set(components "") # the sources for each individiable component define a new # component_name-sources_base list for each component, and a # component_name-stub-sources_base list for the component stub. + +# hot_reload list(APPEND components hot_reload ) @@ -15,37 +17,34 @@ set(hot_reload-stub-sources_base hot_reload-stub.c ) -if(ENABLE_PERFTRACING) - - list(APPEND components - event_pipe - ) - - set(SHARED_EVENTPIPE_INCLUDE_PATH "../../../native/") - set(SHARED_EVENTPIPE_SOURCE_PATH "../../../native/eventpipe/") - set(MONO_EVENTPIPE_SHIM_SOURCE_PATH "../eventpipe/") +# event_pipe/diagnostics_server +list(APPEND components + event_pipe +) - include(${MONO_EVENTPIPE_SHIM_SOURCE_PATH}/CMakeLists.txt) +set(SHARED_EVENTPIPE_INCLUDE_PATH "../../../native/") +set(SHARED_EVENTPIPE_SOURCE_PATH "../../../native/eventpipe/") +set(MONO_EVENTPIPE_SHIM_SOURCE_PATH "../eventpipe/") - include_directories( - ${SHARED_EVENTPIPE_INCLUDE_PATH} - ${MONO_EVENTPIPE_SHIM_SOURCE_PATH} - ) +include(${MONO_EVENTPIPE_SHIM_SOURCE_PATH}/CMakeLists.txt) - set(event_pipe-sources_base - ${eventpipe_sources} - ${diagnostic_server_sources} - event_pipe.c - event_pipe.h - diagnostics_server.c - diagnostics_server.h - ) - set(event_pipe-stub-sources_base - event_pipe-stub.c - diagnostics_server-stub.c - ) +include_directories( + ${SHARED_EVENTPIPE_INCLUDE_PATH} + ${MONO_EVENTPIPE_SHIM_SOURCE_PATH} +) -endif(ENABLE_PERFTRACING) +set(event_pipe-sources_base + ${eventpipe_sources} + ${diagnostic_server_sources} + event_pipe.c + event_pipe.h + diagnostics_server.c + diagnostics_server.h + ) +set(event_pipe-stub-sources_base + event_pipe-stub.c + diagnostics_server-stub.c + ) # from here down, all the components are treated in the same way @@ -81,18 +80,18 @@ if(NOT DISABLE_COMPONENTS AND NOT STATIC_COMPONENTS) else() add_library("mono-component-${component}" SHARED $) endif() + # each shared library component gets its own copy for eglib + # + # FIXME: this is bad for things like the g_log_set_default_handler/g_logv + # which use global state - we should move those functions into + # monosgen-shared and get them via dynamic linking. + target_sources("mono-component-${component}" PRIVATE $) if(NOT DISABLE_SHARED_LIBS) - # each shared library component gets its own copy for eglib - # - # FIXME: this is bad for things like the g_log_set_default_handler/g_logv - # which use global state - we should move those functions into - # monosgen-shared and get them via dynamic linking. - target_link_libraries("mono-component-${component}" PRIVATE eglib_objects) - target_link_libraries("mono-component-${component}" PRIVATE monosgen-shared) # If we disable shared libs, but build dynamic components we would need # to enable allowing undefined symbols here (presumably to be resolved - # from the mono-sgen executable. But that's not a configuration we + # from the mono-sgen executable. But that's not a configuration we # should need in dotnet/runtime. + target_link_libraries("mono-component-${component}" PRIVATE monosgen-shared) endif() target_link_libraries("mono-component-${component}" PRIVATE ${OS_LIBS}) install(TARGETS "mono-component-${component}" LIBRARY) @@ -110,22 +109,24 @@ elseif(NOT DISABLE_COMPONENTS AND STATIC_COMPONENTS) install(TARGETS "mono-component-${component}-stub-static" LIBRARY) endforeach() - # define a single static library mono-components-static for mini if building a shared libmono with static-linked components - add_library("mono-components-static" STATIC) + # define a list of mono-components objects for mini if building a shared libmono with static-linked components + set(mono-components-objects "") foreach(component IN LISTS components) - target_sources("mono-components-static" PRIVATE $) + list(APPEND mono-components-objects $) endforeach() - target_link_libraries("mono-components-static" component_base) endif() if(DISABLE_COMPONENTS OR NOT STATIC_COMPONENTS) - # define a single static library mono-components-stubs-static that will be linked into + # define a list of mono-components-stubs objects that will be linked into # the runtime to be used as fallbacks if the dynamic components are not # available or when only static component stubs are requested. - add_library("mono-components-stubs-static" STATIC) + set(mono-components-stub-objects "") foreach(component IN LISTS components) - target_sources("mono-components-stubs-static" PRIVATE $) + list(APPEND mono-components-stub-objects $) endforeach() - target_link_libraries("mono-components-stubs-static" component_base) endif() + +# component tests +set(MONO_EVENTPIPE_TEST_SOURCE_PATH "${MONO_EVENTPIPE_SHIM_SOURCE_PATH}/test") +include(${MONO_EVENTPIPE_TEST_SOURCE_PATH}/CMakeLists.txt) diff --git a/src/mono/mono/component/diagnostics_server-stub.c b/src/mono/mono/component/diagnostics_server-stub.c index 08bec21ef28e89..73b257bc82a6f3 100644 --- a/src/mono/mono/component/diagnostics_server-stub.c +++ b/src/mono/mono/component/diagnostics_server-stub.c @@ -3,8 +3,6 @@ // #include - -#ifdef ENABLE_PERFTRACING #include "mono/component/diagnostics_server.h" #include "mono/metadata/components.h" @@ -76,4 +74,3 @@ mono_component_diagnostics_server_stub_init (void) { return &fn_table; } -#endif /* ENABLE_PERFTRACING */ diff --git a/src/mono/mono/component/diagnostics_server.c b/src/mono/mono/component/diagnostics_server.c index 82ee17b6466e7a..239576b4667bd0 100644 --- a/src/mono/mono/component/diagnostics_server.c +++ b/src/mono/mono/component/diagnostics_server.c @@ -3,8 +3,6 @@ // #include - -#ifdef ENABLE_PERFTRACING #include #include #include @@ -38,4 +36,3 @@ mono_component_diagnostics_server_init (void) { return &fn_table; } -#endif /* ENABLE_PERFTRACING */ diff --git a/src/mono/mono/component/diagnostics_server.h b/src/mono/mono/component/diagnostics_server.h index 67ee2ff4618149..cbc32eb9192d1a 100644 --- a/src/mono/mono/component/diagnostics_server.h +++ b/src/mono/mono/component/diagnostics_server.h @@ -5,10 +5,13 @@ #ifndef _MONO_COMPONENT_DIAGNOSTICS_SERVER_H #define _MONO_COMPONENT_DIAGNOSTICS_SERVER_H -#ifdef ENABLE_PERFTRACING #include "mono/component/component.h" #include "mono/utils/mono-compiler.h" +#ifndef ENABLE_PERFTRACING +#define ENABLE_PERFTRACING +#endif + #include #include @@ -26,5 +29,4 @@ MonoComponentDiagnosticsServer * mono_component_diagnostics_server_init (void); #endif -#endif /* ENABLE_PERFTRACING */ #endif /*_MONO_COMPONENT_DIAGNOSTICS_SERVER_H*/ diff --git a/src/mono/mono/component/event_pipe-stub.c b/src/mono/mono/component/event_pipe-stub.c index 02ec77ace64d78..4cad9dccd78ada 100644 --- a/src/mono/mono/component/event_pipe-stub.c +++ b/src/mono/mono/component/event_pipe-stub.c @@ -3,8 +3,6 @@ // #include - -#ifdef ENABLE_PERFTRACING #include "mono/component/event_pipe.h" #include "mono/metadata/components.h" @@ -262,4 +260,3 @@ mono_component_event_pipe_stub_init (void) { return &fn_table; } -#endif /* ENABLE_PERFTRACING */ diff --git a/src/mono/mono/component/event_pipe.c b/src/mono/mono/component/event_pipe.c index 19b48f251680e3..49dd05e06fe149 100644 --- a/src/mono/mono/component/event_pipe.c +++ b/src/mono/mono/component/event_pipe.c @@ -3,8 +3,6 @@ // #include - -#ifdef ENABLE_PERFTRACING #include #include #include @@ -245,5 +243,3 @@ mono_component_event_pipe_init (void) { return &fn_table; } - -#endif /* ENABLE_PERFTRACING */ diff --git a/src/mono/mono/component/event_pipe.h b/src/mono/mono/component/event_pipe.h index 1fb5f6fd02006a..201696c9c07100 100644 --- a/src/mono/mono/component/event_pipe.h +++ b/src/mono/mono/component/event_pipe.h @@ -5,11 +5,13 @@ #ifndef _MONO_COMPONENT_EVENT_PIPE_H #define _MONO_COMPONENT_EVENT_PIPE_H -#ifdef ENABLE_PERFTRACING - #include #include "mono/utils/mono-compiler.h" +#ifndef ENABLE_PERFTRACING +#define ENABLE_PERFTRACING +#endif + #include #include @@ -156,5 +158,4 @@ MonoComponentEventPipe * mono_component_event_pipe_init (void); #endif -#endif /* ENABLE_PERFTRACING */ #endif /*_MONO_COMPONENT_EVENT_PIPE_H*/ diff --git a/src/mono/mono/eventpipe/test/CMakeLists.txt b/src/mono/mono/eventpipe/test/CMakeLists.txt index 574cd28f7c42f3..65784b823c4960 100644 --- a/src/mono/mono/eventpipe/test/CMakeLists.txt +++ b/src/mono/mono/eventpipe/test/CMakeLists.txt @@ -27,36 +27,13 @@ if(ENABLE_PERFTRACING) ep-tests-debug.h ) - include_directories( - ${PROJECT_SOURCE_DIR}/../../native/ - ${PROJECT_SOURCE_DIR}/.. - ${PROJECT_SOURCE_DIR} - ${PROJECT_SOURCE_DIR}/eglib - ${PROJECT_BINARY_DIR}/.. - ${PROJECT_BINARY_DIR}/eglib - ) - - if(HAVE_SYS_ICU) - if(ICU_LIBDIR) - set(ICU_LDFLAGS "-L${ICU_LIBDIR}") - endif() - endif() - - if(HOST_DARWIN) - set(OS_LIBS "-framework CoreFoundation" "-framework Foundation") - elseif(HOST_IOS) - set(OS_LIBS "-framework CoreFoundation" "-lobjc" "-lc++") - elseif(HOST_ANDROID) - set(OS_LIBS m dl log) - elseif(HOST_LINUX) - set(OS_LIBS pthread m dl) - elseif(HOST_WIN32) - set(OS_LIBS bcrypt.lib ws2_32.lib version.lib winmm.lib) - endif() + addprefix(EVENTPIPE_TEST_SOURCES ${MONO_EVENTPIPE_TEST_SOURCE_PATH} "${EVENTPIPE_TEST_SOURCES}") + addprefix(EVENTPIPE_TEST_HEADERS ${MONO_EVENTPIPE_TEST_SOURCE_PATH} "${EVENTPIPE_TEST_HEADERS}") set(CMAKE_SKIP_RPATH 1) add_executable(ep-test ${EVENTPIPE_TEST_SOURCES} ${EVENTPIPE_TEST_HEADERS}) - target_link_libraries(ep-test monosgen-static "mono-components-static" ${OS_LIBS} ${ICONV_LIB} ${LLVM_LIBS} ${ICU_LIBS}) + target_sources(ep-test PRIVATE "${mono-components-objects}") + target_link_libraries(ep-test monosgen-static ${OS_LIBS} ${ICONV_LIB} ${LLVM_LIBS} ${ICU_LIBS}) if(ICU_LDFLAGS) set_target_properties(ep-test PROPERTIES LINK_FLAGS ${ICU_LDFLAGS}) endif() diff --git a/src/mono/mono/metadata/appdomain.c b/src/mono/mono/metadata/appdomain.c index 2f6a7f8faef0b6..9626f3a91e57c3 100644 --- a/src/mono/mono/metadata/appdomain.c +++ b/src/mono/mono/metadata/appdomain.c @@ -278,11 +278,10 @@ mono_runtime_init_checked (MonoDomain *domain, MonoThreadStartCB start_cb, MonoT mono_thread_internal_attach (domain); -#if defined(ENABLE_PERFTRACING) && !defined(DISABLE_EVENTPIPE) mono_component_diagnostics_server ()->init (); mono_component_diagnostics_server ()->pause_for_diagnostics_monitor (); + mono_component_event_pipe ()->write_event_ee_startup_start (); -#endif mono_type_initialization_init (); diff --git a/src/mono/mono/metadata/components.c b/src/mono/mono/metadata/components.c index c7edd28ef9547c..8e3bea3fd837bb 100644 --- a/src/mono/mono/metadata/components.c +++ b/src/mono/mono/metadata/components.c @@ -35,7 +35,6 @@ typedef struct _MonoComponentEntry { #define HOT_RELOAD_COMPONENT_NAME HOT_RELOAD_LIBRARY_NAME MonoComponentHotReload *hot_reload = NULL; -#ifdef ENABLE_PERFTRACING MonoComponentEventPipe *event_pipe = NULL; MonoComponentDiagnosticsServer *diagnostics_server = NULL; @@ -44,15 +43,12 @@ MonoComponentDiagnosticsServer *diagnostics_server = NULL; #define DIAGNOSTICS_SERVER_LIBRARY_NAME EVENT_PIPE_LIBRARY_NAME #define EVENT_PIPE_COMPONENT_NAME "event_pipe" #define DIAGNOSTICS_SERVER_COMPONENT_NAME "diagnostics_server" -#endif /* One per component */ MonoComponentEntry components[] = { { HOT_RELOAD_LIBRARY_NAME, HOT_RELOAD_COMPONENT_NAME, COMPONENT_INIT_FUNC (hot_reload), (MonoComponent**)&hot_reload, NULL }, -#ifdef ENABLE_PERFTRACING { EVENT_PIPE_LIBRARY_NAME, EVENT_PIPE_COMPONENT_NAME, COMPONENT_INIT_FUNC (event_pipe), (MonoComponent**)&event_pipe, NULL }, { DIAGNOSTICS_SERVER_LIBRARY_NAME, DIAGNOSTICS_SERVER_COMPONENT_NAME, COMPONENT_INIT_FUNC (diagnostics_server), (MonoComponent**)&diagnostics_server, NULL }, -#endif }; #ifndef STATIC_COMPONENTS diff --git a/src/mono/mono/metadata/components.h b/src/mono/mono/metadata/components.h index 9b59803098c1b8..03d50fdfc0a948 100644 --- a/src/mono/mono/metadata/components.h +++ b/src/mono/mono/metadata/components.h @@ -25,7 +25,6 @@ mono_component_hot_reload (void) return hot_reload; } -#ifdef ENABLE_PERFTRACING static inline MonoComponentEventPipe * mono_component_event_pipe (void) @@ -41,18 +40,15 @@ mono_component_diagnostics_server (void) extern MonoComponentDiagnosticsServer *diagnostics_server; return diagnostics_server; } -#endif /* Declare each copomnents stub init function here */ MonoComponentHotReload * mono_component_hot_reload_stub_init (void); -#ifdef ENABLE_PERFTRACING MonoComponentEventPipe * mono_component_event_pipe_stub_init (void); MonoComponentDiagnosticsServer * mono_component_diagnostics_server_stub_init (void); -#endif #endif/*_MONO_METADATA_COMPONENTS_H*/ diff --git a/src/mono/mono/mini/CMakeLists.txt b/src/mono/mono/mini/CMakeLists.txt index ce7ba612f9db38..e0722381fa6011 100644 --- a/src/mono/mono/mini/CMakeLists.txt +++ b/src/mono/mono/mini/CMakeLists.txt @@ -313,9 +313,13 @@ endif() set(monosgen-sources "${metadata_sources};${utils_sources};${sgen_sources};${icu_shim_sources};${mini_sources};${zlib_sources}") add_library(monosgen-objects OBJECT "${monosgen-sources}") -add_library(monosgen-static STATIC $) +add_library(monosgen-static STATIC $;$) set_target_properties(monosgen-static PROPERTIES OUTPUT_NAME ${MONO_LIB_NAME}) -target_link_libraries(monosgen-static eglib_objects) + +if(DISABLE_COMPONENTS) + # add component fallback stubs into static mono library when components have been disabled. + target_sources(monosgen-static PRIVATE "${mono-components-stub-objects}") +endif() if(NOT DISABLE_LIBS) install(TARGETS monosgen-static LIBRARY) @@ -334,7 +338,7 @@ if(NOT DISABLE_SHARED_LIBS) add_library(monosgen-shared SHARED $) target_compile_definitions(monosgen-objects PRIVATE -DMONO_DLL_EXPORT) endif() - target_link_libraries(monosgen-shared PRIVATE eglib_objects) + target_sources(monosgen-shared PRIVATE $) set_target_properties(monosgen-shared PROPERTIES OUTPUT_NAME ${MONO_SHARED_LIB_NAME}) if(TARGET_WIN32) # on Windows the import library for the shared mono library will have the same name as the static library, @@ -351,13 +355,16 @@ if(NOT DISABLE_SHARED_LIBS) if(TARGET_DARWIN) set_property(TARGET monosgen-shared APPEND_STRING PROPERTY LINK_FLAGS " -Wl,-compatibility_version -Wl,2.0 -Wl,-current_version -Wl,2.0") endif() - if (NOT DISABLE_COMPONENTS AND STATIC_COMPONENTS) + if(NOT DISABLE_COMPONENTS AND STATIC_COMPONENTS) # if components are built statically, but we're building a shared lib mono, # link them into the library - target_link_libraries (monosgen-shared PRIVATE "mono-components-static") - else() - # if components are built dynamically or disabled, link the fallback stubs into the runtime - target_link_libraries (monosgen-shared PRIVATE "mono-components-stubs-static") + target_sources(monosgen-shared PRIVATE "${mono-components-objects}") + elseif(NOT DISABLE_COMPONENTS AND NOT STATIC_COMPONENTS) + # if components are built dynamically, link the fallback stubs into the runtime + target_sources(monosgen-shared PRIVATE "${mono-components-stub-objects}") + elseif(DISABLE_COMPONENTS) + # if components are disabled, link the fallback stubs into the runtime + target_sources(monosgen-shared PRIVATE "${mono-components-stub-objects}") endif() install(TARGETS monosgen-shared LIBRARY) if(HOST_WIN32 AND TARGET_AMD64) @@ -407,15 +414,19 @@ if(NOT DISABLE_EXECUTABLES) set(sgen_sources "${sgen_sources};${PROJECT_BINARY_DIR}/../../NativeVersion.rc") endif() add_executable(mono-sgen "${sgen_sources}") - target_link_libraries(mono-sgen monosgen-static ${OS_LIBS} ${ICONV_LIB} ${LLVM_LIBS} ${ICU_LIBS}) - if (NOT DISABLE_COMPONENTS AND STATIC_COMPONENTS) - target_link_libraries(mono-sgen "mono-components-static") - else() - target_link_libraries(mono-sgen "mono-components-stubs-static") + target_link_libraries(mono-sgen PRIVATE monosgen-static ${OS_LIBS} ${ICONV_LIB} ${LLVM_LIBS} ${ICU_LIBS}) + if(NOT DISABLE_COMPONENTS AND STATIC_COMPONENTS) + # if components are built statically, link them into runtime. + target_sources(mono-sgen PRIVATE "${mono-components-objects}") + elseif(NOT DISABLE_COMPONENTS AND NOT STATIC_COMPONENTS) + # if components are built dynamically, link the fallback stubs into the runtime + target_sources(mono-sgen PRIVATE "${mono-components-stub-objects}") + elseif(DISABLE_COMPONENTS) + # if components are disabled, link the fallback stubs into the runtime + # fallback stubs already provided in monosgen-static when components are disabled endif() if(ICU_LDFLAGS) set_property(TARGET mono-sgen APPEND_STRING PROPERTY LINK_FLAGS " ${ICU_LDFLAGS}") endif() install(TARGETS mono-sgen RUNTIME) endif() - diff --git a/src/mono/mono/mini/mini-runtime.c b/src/mono/mono/mini/mini-runtime.c index 0d74d9506b6435..0dc726c4b530e5 100644 --- a/src/mono/mono/mini/mini-runtime.c +++ b/src/mono/mono/mini/mini-runtime.c @@ -4424,12 +4424,10 @@ mini_init (const char *filename, const char *runtime_version) else domain = mono_init_from_assembly (filename, filename); -#if defined(ENABLE_PERFTRACING) && !defined(DISABLE_EVENTPIPE) if (mono_compile_aot) mono_component_diagnostics_server ()->disable (); mono_component_event_pipe ()->init (); -#endif if (mono_aot_only) { /* This helps catch code allocation requests */ @@ -4496,9 +4494,7 @@ mini_init (const char *filename, const char *runtime_version) #endif mono_threads_set_runtime_startup_finished (); -#if defined(ENABLE_PERFTRACING) && !defined(DISABLE_EVENTPIPE) mono_component_event_pipe ()->finish_init (); -#endif #ifdef ENABLE_EXPERIMENT_TIERED if (!mono_compile_aot) { @@ -4879,10 +4875,8 @@ mini_cleanup (MonoDomain *domain) jit_stats_cleanup (); mono_jit_dump_cleanup (); mini_get_interp_callbacks ()->cleanup (); -#if defined(ENABLE_PERFTRACING) && !defined(DISABLE_EVENTPIPE) mono_component_event_pipe ()->shutdown (); mono_component_diagnostics_server ()->shutdown (); -#endif } void From 773315f9181a488af10499e7a537cde37c23a546 Mon Sep 17 00:00:00 2001 From: lateralusX Date: Fri, 9 Apr 2021 15:48:12 +0200 Subject: [PATCH 43/55] Switch WebAssembly over to DISABLE_COMPONENTS (eventpipe and hot-reload). --- src/mono/mono.proj | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/src/mono/mono.proj b/src/mono/mono.proj index 09d6a662da8e14..515dcfe7ccd847 100644 --- a/src/mono/mono.proj +++ b/src/mono/mono.proj @@ -293,10 +293,11 @@ <_MonoMinimal Condition="'$(Configuration)' == 'Release' and '$(MonoEnableAssertMessages)' != 'true'">$(_MonoMinimal),assert_messages - <_MonoCMakeArgs Include="-DENABLE_MINIMAL=jit,portability,sgen_major_marksweep_conc,sgen_split_nursery,sgen_gc_bridge,sgen_toggleref,sgen_debug_helpers,sgen_binary_protocol,logging,shared_perfcounters,interpreter,threads,eventpipe,qcalls$(_MonoMinimal)"/> + <_MonoCMakeArgs Include="-DENABLE_MINIMAL=jit,portability,sgen_major_marksweep_conc,sgen_split_nursery,sgen_gc_bridge,sgen_toggleref,sgen_debug_helpers,sgen_binary_protocol,logging,shared_perfcounters,interpreter,threads,qcalls$(_MonoMinimal)"/> <_MonoCMakeArgs Include="-DENABLE_INTERP_LIB=1"/> <_MonoCMakeArgs Include="-DDISABLE_ICALL_TABLES=1"/> <_MonoCMakeArgs Include="-DDISABLE_CRASH_REPORTING=1"/> + <_MonoCMakeArgs Include="-DDISABLE_COMPONENTS=1"/> <_MonoCMakeArgs Include="-DENABLE_ICALL_EXPORT=1"/> <_MonoCMakeArgs Include="-DENABLE_LAZY_GC_THREAD_CREATION=1"/> <_MonoCMakeArgs Include="-DENABLE_LLVM_RUNTIME=1"/> From 95e5a361f85207896073c3ff226e07ac486aa3a6 Mon Sep 17 00:00:00 2001 From: lateralusX Date: Tue, 13 Apr 2021 14:47:57 +0200 Subject: [PATCH 44/55] Add component link support in Android/iOS AppBuilder --- .../AndroidAppBuilder/AndroidAppBuilder.cs | 6 +++ src/tasks/AndroidAppBuilder/ApkBuilder.cs | 48 +++++++++++++++++- src/tasks/AppleAppBuilder/AppleAppBuilder.cs | 7 ++- src/tasks/AppleAppBuilder/Xcode.cs | 50 ++++++++++++++++++- 4 files changed, 107 insertions(+), 4 deletions(-) diff --git a/src/tasks/AndroidAppBuilder/AndroidAppBuilder.cs b/src/tasks/AndroidAppBuilder/AndroidAppBuilder.cs index af036e41e27375..7667f0ae6fe8e4 100644 --- a/src/tasks/AndroidAppBuilder/AndroidAppBuilder.cs +++ b/src/tasks/AndroidAppBuilder/AndroidAppBuilder.cs @@ -33,6 +33,11 @@ public class AndroidAppBuilderTask : Task /// public bool ForceAOT { get; set; } + /// + /// List of components to static link, if available + /// + public string? StaticLinkedComponentNames { get; set; } = ""!; + [Required] public string RuntimeIdentifier { get; set; } = ""!; @@ -90,6 +95,7 @@ public override bool Execute() apkBuilder.KeyStorePath = KeyStorePath; apkBuilder.ForceInterpreter = ForceInterpreter; apkBuilder.ForceAOT = ForceAOT; + apkBuilder.StaticLinkedComponentNames = StaticLinkedComponentNames; apkBuilder.Assemblies = Assemblies; (ApkBundlePath, ApkPackageId) = apkBuilder.BuildApk(abi, MainLibraryFileName, MonoRuntimeHeaders); diff --git a/src/tasks/AndroidAppBuilder/ApkBuilder.cs b/src/tasks/AndroidAppBuilder/ApkBuilder.cs index 0ce54fd15c1d6d..fc887ff17af430 100644 --- a/src/tasks/AndroidAppBuilder/ApkBuilder.cs +++ b/src/tasks/AndroidAppBuilder/ApkBuilder.cs @@ -24,6 +24,7 @@ public class ApkBuilder public string? KeyStorePath { get; set; } public bool ForceInterpreter { get; set; } public bool ForceAOT { get; set; } + public string? StaticLinkedComponentNames { get; set; } public ITaskItem[] Assemblies { get; set; } = Array.Empty(); public (string apk, string packageId) BuildApk( @@ -171,6 +172,7 @@ public class ApkBuilder // 1. Build libmonodroid.so` via cmake + string nativeLibraries = ""; string monoRuntimeLib = Path.Combine(AppDir, "libmonosgen-2.0.a"); if (!File.Exists(monoRuntimeLib)) { @@ -178,7 +180,49 @@ public class ApkBuilder } else { - monoRuntimeLib = $" {monoRuntimeLib}{Environment.NewLine}"; + nativeLibraries = $" {monoRuntimeLib}{Environment.NewLine}"; + } + + string[] staticComponentStubLibs = Directory.GetFiles(AppDir, "libmono-component-*-stub-static.a"); + bool staticLinkAllComponents = false; + string[] componentNames = Array.Empty(); + + if (!string.IsNullOrEmpty(StaticLinkedComponentNames) && StaticLinkedComponentNames.Equals("*", StringComparison.OrdinalIgnoreCase)) + staticLinkAllComponents = true; + else if (!string.IsNullOrEmpty(StaticLinkedComponentNames)) + componentNames = StaticLinkedComponentNames.Split(";"); + + // by default, component stubs will be linked and depending on how mono runtime has been build, + // stubs can disable or dynamic load components. + foreach (string staticComponentStubLib in staticComponentStubLibs) + { + string componentLibToLink = staticComponentStubLib; + if (staticLinkAllComponents) + { + // static link component. + componentLibToLink = componentLibToLink.Replace("-stub-static.a", "-static.a", StringComparison.OrdinalIgnoreCase); + } + else + { + foreach (string componentName in componentNames) + { + if (componentLibToLink.Contains(componentName, StringComparison.OrdinalIgnoreCase)) + { + // static link component. + componentLibToLink = componentLibToLink.Replace("-stub-static.a", "-static.a", StringComparison.OrdinalIgnoreCase); + break; + } + } + } + + // if lib doesn't exist (primarly due to runtime build without static lib support), fallback linking stub lib. + if (!File.Exists(componentLibToLink)) + { + Utils.LogInfo($"\nCouldn't find static component library: {componentLibToLink}, linking static component stub library: {staticComponentStubLib}.\n"); + componentLibToLink = staticComponentStubLib; + } + + nativeLibraries += $" {componentLibToLink}{Environment.NewLine}"; } string aotSources = ""; @@ -190,7 +234,7 @@ public class ApkBuilder string cmakeLists = Utils.GetEmbeddedResource("CMakeLists-android.txt") .Replace("%MonoInclude%", monoRuntimeHeaders) - .Replace("%NativeLibrariesToLink%", monoRuntimeLib) + .Replace("%NativeLibrariesToLink%", nativeLibraries) .Replace("%AotSources%", aotSources) .Replace("%AotModulesSource%", string.IsNullOrEmpty(aotSources) ? "" : "modules.c"); diff --git a/src/tasks/AppleAppBuilder/AppleAppBuilder.cs b/src/tasks/AppleAppBuilder/AppleAppBuilder.cs index 6affce39e30f5b..85efde52b045fa 100644 --- a/src/tasks/AppleAppBuilder/AppleAppBuilder.cs +++ b/src/tasks/AppleAppBuilder/AppleAppBuilder.cs @@ -126,6 +126,11 @@ public string TargetOS /// public bool ForceAOT { get; set; } + /// + /// List of components to static link, if available + /// + public string? StaticLinkedComponentNames { get; set; } = ""!; + /// /// Forces the runtime to use the invariant mode /// @@ -199,7 +204,7 @@ public override bool Execute() generator.EnableRuntimeLogging = EnableRuntimeLogging; XcodeProjectPath = generator.GenerateXCode(ProjectName, MainLibraryFileName, assemblerFiles, - AppDir, binDir, MonoRuntimeHeaders, !isDevice, UseConsoleUITemplate, ForceAOT, ForceInterpreter, InvariantGlobalization, Optimized, NativeMainSource); + AppDir, binDir, MonoRuntimeHeaders, !isDevice, UseConsoleUITemplate, ForceAOT, ForceInterpreter, InvariantGlobalization, Optimized, StaticLinkedComponentNames, NativeMainSource); if (BuildAppBundle) { diff --git a/src/tasks/AppleAppBuilder/Xcode.cs b/src/tasks/AppleAppBuilder/Xcode.cs index 442eb539af38b2..90bf0ff56ab2aa 100644 --- a/src/tasks/AppleAppBuilder/Xcode.cs +++ b/src/tasks/AppleAppBuilder/Xcode.cs @@ -53,6 +53,7 @@ public string GenerateXCode( bool forceInterpreter, bool invariantGlobalization, bool stripDebugSymbols, + string? staticLinkedComponentNames=null, string? nativeMainSource = null) { // bundle everything as resources excluding native files @@ -102,11 +103,58 @@ public string GenerateXCode( .Replace("%MonoInclude%", monoInclude) .Replace("%HardenedRuntime%", hardenedRuntime ? "TRUE" : "FALSE"); + string toLink = ""; + + string[] allComponentLibs = Directory.GetFiles(workspace, "libmono-component-*-static.a"); + string[] staticComponentStubLibs = Directory.GetFiles(workspace, "libmono-component-*-stub-static.a"); + bool staticLinkAllComponents = false; + string[] componentNames = Array.Empty(); + + if (!string.IsNullOrEmpty(staticLinkedComponentNames) && staticLinkedComponentNames.Equals("*", StringComparison.OrdinalIgnoreCase)) + staticLinkAllComponents = true; + else if (!string.IsNullOrEmpty(staticLinkedComponentNames)) + componentNames = staticLinkedComponentNames.Split(";"); + + // by default, component stubs will be linked and depending on how mono runtime has been build, + // stubs can disable or dynamic load components. + foreach (string staticComponentStubLib in staticComponentStubLibs) + { + string componentLibToLink = staticComponentStubLib; + if (staticLinkAllComponents) + { + // static link component. + componentLibToLink = componentLibToLink.Replace("-stub-static.a", "-static.a", StringComparison.OrdinalIgnoreCase); + } + else + { + foreach (string componentName in componentNames) + { + if (componentLibToLink.Contains(componentName, StringComparison.OrdinalIgnoreCase)) + { + // static link component. + componentLibToLink = componentLibToLink.Replace("-stub-static.a", "-static.a", StringComparison.OrdinalIgnoreCase); + break; + } + } + } + + // if lib doesn't exist (primarly due to runtime build without static lib support), fallback linking stub lib. + if (!File.Exists(componentLibToLink)) + { + Utils.LogInfo($"\nCouldn't find static component library: {componentLibToLink}, linking static component stub library: {staticComponentStubLib}.\n"); + componentLibToLink = staticComponentStubLib; + } + + toLink += $" \"-force_load {componentLibToLink}\"{Environment.NewLine}"; + } string[] dylibs = Directory.GetFiles(workspace, "*.dylib"); - string toLink = ""; foreach (string lib in Directory.GetFiles(workspace, "*.a")) { + // all component libs already added to linker. + if (allComponentLibs.Any(lib.Contains)) + continue; + string libName = Path.GetFileNameWithoutExtension(lib); // libmono must always be statically linked, for other librarires we can use dylibs bool dylibExists = libName != "libmonosgen-2.0" && dylibs.Any(dylib => Path.GetFileName(dylib) == libName + ".dylib"); From f79ae260f08bec21fd62e0eaab88023047ae93fa Mon Sep 17 00:00:00 2001 From: lateralusX Date: Tue, 13 Apr 2021 16:16:03 +0200 Subject: [PATCH 45/55] Add ability to disable link of static components into shared runtime lib. --- src/mono/CMakeLists.txt | 4 ++++ src/mono/mono/component/CMakeLists.txt | 17 ++++++++--------- src/mono/mono/mini/CMakeLists.txt | 12 ++++++++++-- 3 files changed, 22 insertions(+), 11 deletions(-) diff --git a/src/mono/CMakeLists.txt b/src/mono/CMakeLists.txt index 0ac0e24574af2c..fcb13923813afe 100644 --- a/src/mono/CMakeLists.txt +++ b/src/mono/CMakeLists.txt @@ -665,6 +665,10 @@ endif() if(DISABLE_COMPONENTS AND NOT STATIC_COMPONENTS) set(STATIC_COMPONENTS 1) endif() + +if(DISABLE_LINK_STATIC_COMPONENTS AND NOT STATIC_COMPONENTS) + set(STATIC_COMPONENTS 1) +endif() ### End of component build checks ###################################### diff --git a/src/mono/mono/component/CMakeLists.txt b/src/mono/mono/component/CMakeLists.txt index b1880e243b8b6f..367663d6fec35c 100644 --- a/src/mono/mono/component/CMakeLists.txt +++ b/src/mono/mono/component/CMakeLists.txt @@ -117,15 +117,14 @@ elseif(NOT DISABLE_COMPONENTS AND STATIC_COMPONENTS) endif() -if(DISABLE_COMPONENTS OR NOT STATIC_COMPONENTS) - # define a list of mono-components-stubs objects that will be linked into - # the runtime to be used as fallbacks if the dynamic components are not - # available or when only static component stubs are requested. - set(mono-components-stub-objects "") - foreach(component IN LISTS components) - list(APPEND mono-components-stub-objects $) - endforeach() -endif() +# define a list of mono-components-stubs objects that will be linked into +# the runtime to be used as fallbacks if the dynamic components are not +# available or when only static component stubs are requested. +set(mono-components-stub-objects "") +foreach(component IN LISTS components) + list(APPEND mono-components-stub-objects $) +endforeach() + # component tests set(MONO_EVENTPIPE_TEST_SOURCE_PATH "${MONO_EVENTPIPE_SHIM_SOURCE_PATH}/test") diff --git a/src/mono/mono/mini/CMakeLists.txt b/src/mono/mono/mini/CMakeLists.txt index e0722381fa6011..8fbc1af6141fa1 100644 --- a/src/mono/mono/mini/CMakeLists.txt +++ b/src/mono/mono/mini/CMakeLists.txt @@ -355,10 +355,14 @@ if(NOT DISABLE_SHARED_LIBS) if(TARGET_DARWIN) set_property(TARGET monosgen-shared APPEND_STRING PROPERTY LINK_FLAGS " -Wl,-compatibility_version -Wl,2.0 -Wl,-current_version -Wl,2.0") endif() - if(NOT DISABLE_COMPONENTS AND STATIC_COMPONENTS) + if(NOT DISABLE_COMPONENTS AND STATIC_COMPONENTS AND NOT DISABLE_LINK_STATIC_COMPONENTS) # if components are built statically, but we're building a shared lib mono, # link them into the library target_sources(monosgen-shared PRIVATE "${mono-components-objects}") + elseif(NOT DISABLE_COMPONENTS AND STATIC_COMPONENTS AND DISABLE_LINK_STATIC_COMPONENTS) + # if components are built statically, we're building a shared lib mono, but we shouldn't link components + # link the fallback stubs into the runtime + target_sources(monosgen-shared PRIVATE "${mono-components-stub-objects}") elseif(NOT DISABLE_COMPONENTS AND NOT STATIC_COMPONENTS) # if components are built dynamically, link the fallback stubs into the runtime target_sources(monosgen-shared PRIVATE "${mono-components-stub-objects}") @@ -415,9 +419,13 @@ if(NOT DISABLE_EXECUTABLES) endif() add_executable(mono-sgen "${sgen_sources}") target_link_libraries(mono-sgen PRIVATE monosgen-static ${OS_LIBS} ${ICONV_LIB} ${LLVM_LIBS} ${ICU_LIBS}) - if(NOT DISABLE_COMPONENTS AND STATIC_COMPONENTS) + if(NOT DISABLE_COMPONENTS AND STATIC_COMPONENTS AND NOT DISABLE_LINK_STATIC_COMPONENTS) # if components are built statically, link them into runtime. target_sources(mono-sgen PRIVATE "${mono-components-objects}") + elseif(NOT DISABLE_COMPONENTS AND STATIC_COMPONENTS AND DISABLE_LINK_STATIC_COMPONENTS) + # if components are built statically, but we shouldn't link components + # link the fallback stubs into the runtime + target_sources(mono-sgen PRIVATE "${mono-components-stub-objects}") elseif(NOT DISABLE_COMPONENTS AND NOT STATIC_COMPONENTS) # if components are built dynamically, link the fallback stubs into the runtime target_sources(mono-sgen PRIVATE "${mono-components-stub-objects}") From 45c96d59458613321000cfed98840908e7ae4d7f Mon Sep 17 00:00:00 2001 From: lateralusX Date: Tue, 13 Apr 2021 16:17:37 +0200 Subject: [PATCH 46/55] Enable diagnostics server TCP PAL for iOS and Android. --- src/mono/mono.proj | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/src/mono/mono.proj b/src/mono/mono.proj index 515dcfe7ccd847..1355059712799a 100644 --- a/src/mono/mono.proj +++ b/src/mono/mono.proj @@ -417,11 +417,11 @@ <_MonoCMakeArgs Include="-DENABLE_MSCORDBI=1" /> - - + <_MonoCMakeArgs Include="-DISABLE_LINK_STATIC_COMPONENTS=1" /> + From 1891d94ec5d827796700efd33ec5c48ff7dff3b4 Mon Sep 17 00:00:00 2001 From: lateralusX Date: Wed, 14 Apr 2021 11:20:52 +0200 Subject: [PATCH 47/55] Remove ep->ds dependecy using callback. --- src/mono/mono/component/event_pipe.h | 6 +++--- src/native/eventpipe/ds-ipc.c | 5 +++++ src/native/eventpipe/ep-types-forward.h | 2 ++ src/native/eventpipe/ep.c | 11 +++++++++-- src/native/eventpipe/ep.h | 7 +++++++ 5 files changed, 26 insertions(+), 5 deletions(-) diff --git a/src/mono/mono/component/event_pipe.h b/src/mono/mono/component/event_pipe.h index 201696c9c07100..e9c8c39aec99f3 100644 --- a/src/mono/mono/component/event_pipe.h +++ b/src/mono/mono/component/event_pipe.h @@ -125,8 +125,8 @@ typedef bool * EventPipe Native Events. */ -typedef bool -(*event_pipe_component_write_event_ee_startup_start)(void); +typedef void +(*event_pipe_component_write_event_ee_startup_start_func)(void); /* * MonoComponentEventPipe function table. @@ -149,7 +149,7 @@ typedef struct _MonoComponentEventPipe { event_pipe_component_provider_add_event_func provider_add_event; event_pipe_component_get_session_info_func get_session_info; event_pipe_component_thread_ctrl_activity_id_func thread_ctrl_activity_id; - event_pipe_component_write_event_ee_startup_start write_event_ee_startup_start; + event_pipe_component_write_event_ee_startup_start_func write_event_ee_startup_start; } MonoComponentEventPipe; #ifdef STATIC_COMPONENTS diff --git a/src/native/eventpipe/ds-ipc.c b/src/native/eventpipe/ds-ipc.c index 2aa1ca2cb76c07..a8b12b1e980f16 100644 --- a/src/native/eventpipe/ds-ipc.c +++ b/src/native/eventpipe/ds-ipc.c @@ -7,6 +7,7 @@ #define DS_IMPL_IPC_PAL_GETTER_SETTER #include "ds-ipc.h" #include "ds-protocol.h" +#include "ep.h" #include "ds-rt.h" /* @@ -238,6 +239,8 @@ ipc_log_poll_handles (ds_rt_ipc_poll_handle_array_t *ipc_poll_handles) bool ds_ipc_stream_factory_init (void) { + ep_ipc_stream_factory_callback_set (ds_ipc_stream_factory_any_suspended_ports); + ds_rt_port_array_alloc (&_ds_port_array); return ds_rt_port_array_is_valid (&_ds_port_array); } @@ -255,6 +258,8 @@ ds_ipc_stream_factory_fini (void) } ds_rt_port_array_free (&_ds_port_array);*/ + + ep_ipc_stream_factory_callback_set (NULL); } bool diff --git a/src/native/eventpipe/ep-types-forward.h b/src/native/eventpipe/ep-types-forward.h index 75976bcdec1a7e..c6954d632961cd 100644 --- a/src/native/eventpipe/ep-types-forward.h +++ b/src/native/eventpipe/ep-types-forward.h @@ -201,5 +201,7 @@ typedef void (*EventPipeSessionSynchronousCallback)( uint32_t stack_frames_len, uintptr_t *stack_frames); +typedef bool (*EventPipeIpcStreamFactorySuspendedPortsCallback)(void); + #endif /* ENABLE_PERFTRACING */ #endif /* __EVENTPIPE_TYPES_FORWARD_H__ */ diff --git a/src/native/eventpipe/ep.c b/src/native/eventpipe/ep.c index 5517c7d98fcc75..9552dd59eb11a3 100644 --- a/src/native/eventpipe/ep.c +++ b/src/native/eventpipe/ep.c @@ -20,6 +20,8 @@ static bool _ep_can_start_threads = false; static ep_rt_session_id_array_t _ep_deferred_enable_session_ids = { 0 }; static ep_rt_session_id_array_t _ep_deferred_disable_session_ids = { 0 }; +static EventPipeIpcStreamFactorySuspendedPortsCallback _ep_ipc_stream_factory_suspended_ports_callback = NULL; + /* * Forward declares of all static functions. */ @@ -842,8 +844,7 @@ static bool ipc_stream_factory_any_suspended_ports (void) { - extern bool ds_ipc_stream_factory_any_suspended_ports (void); - return ds_ipc_stream_factory_any_suspended_ports (); + return _ep_ipc_stream_factory_suspended_ports_callback ? _ep_ipc_stream_factory_suspended_ports_callback () : false; } #ifdef EP_CHECKED_BUILD @@ -1523,6 +1524,12 @@ ep_system_time_set ( system_time->milliseconds = milliseconds; } +void +ep_ipc_stream_factory_callback_set (EventPipeIpcStreamFactorySuspendedPortsCallback suspended_ports_callback) +{ + _ep_ipc_stream_factory_suspended_ports_callback = suspended_ports_callback; +} + #endif /* !defined(EP_INCLUDE_SOURCE_FILES) || defined(EP_FORCE_INCLUDE_SOURCE_FILES) */ #endif /* ENABLE_PERFTRACING */ diff --git a/src/native/eventpipe/ep.h b/src/native/eventpipe/ep.h index cfb99aa9d65a92..fb2dafd246924c 100644 --- a/src/native/eventpipe/ep.h +++ b/src/native/eventpipe/ep.h @@ -337,6 +337,13 @@ ep_system_time_get (EventPipeSystemTime *system_time) ep_rt_system_time_get (system_time); } +/* + * EventPipeIpcStreamFactoryCallback. + */ + +void +ep_ipc_stream_factory_callback_set (EventPipeIpcStreamFactorySuspendedPortsCallback suspended_ports_callback); + #else /* ENABLE_PERFTRACING */ static From 6b88bfacb22e4ca1814a082e5990a57385b29e6d Mon Sep 17 00:00:00 2001 From: lateralusX Date: Wed, 14 Apr 2021 11:36:12 +0200 Subject: [PATCH 48/55] Bundle DiagnosticsServer/EventPipe in diagnostics_tracing component. --- .../Microsoft.NETCore.App/Directory.Build.props | 14 +++++++------- src/mono/mono/component/CMakeLists.txt | 8 ++++---- src/mono/mono/metadata/components.c | 9 ++++----- 3 files changed, 15 insertions(+), 16 deletions(-) diff --git a/src/installer/pkg/sfx/Microsoft.NETCore.App/Directory.Build.props b/src/installer/pkg/sfx/Microsoft.NETCore.App/Directory.Build.props index cb4a88dd8a95f9..5d22c457f23f8a 100644 --- a/src/installer/pkg/sfx/Microsoft.NETCore.App/Directory.Build.props +++ b/src/installer/pkg/sfx/Microsoft.NETCore.App/Directory.Build.props @@ -178,13 +178,13 @@ - - - - - - - + + + + + + + diff --git a/src/mono/mono/component/CMakeLists.txt b/src/mono/mono/component/CMakeLists.txt index 367663d6fec35c..276be1a596dce0 100644 --- a/src/mono/mono/component/CMakeLists.txt +++ b/src/mono/mono/component/CMakeLists.txt @@ -17,9 +17,9 @@ set(hot_reload-stub-sources_base hot_reload-stub.c ) -# event_pipe/diagnostics_server +# diagnostics_tracing (event_pipe/diagnostics_server) list(APPEND components - event_pipe + diagnostics_tracing ) set(SHARED_EVENTPIPE_INCLUDE_PATH "../../../native/") @@ -33,7 +33,7 @@ include_directories( ${MONO_EVENTPIPE_SHIM_SOURCE_PATH} ) -set(event_pipe-sources_base +set(diagnostics_tracing-sources_base ${eventpipe_sources} ${diagnostic_server_sources} event_pipe.c @@ -41,7 +41,7 @@ set(event_pipe-sources_base diagnostics_server.c diagnostics_server.h ) -set(event_pipe-stub-sources_base +set(diagnostics_tracing-stub-sources_base event_pipe-stub.c diagnostics_server-stub.c ) diff --git a/src/mono/mono/metadata/components.c b/src/mono/mono/metadata/components.c index 8e3bea3fd837bb..85708f78b3f8e2 100644 --- a/src/mono/mono/metadata/components.c +++ b/src/mono/mono/metadata/components.c @@ -38,17 +38,16 @@ MonoComponentHotReload *hot_reload = NULL; MonoComponentEventPipe *event_pipe = NULL; MonoComponentDiagnosticsServer *diagnostics_server = NULL; -// DiagnosticsServer component currently hosted by EventPipe library. -#define EVENT_PIPE_LIBRARY_NAME "event_pipe" -#define DIAGNOSTICS_SERVER_LIBRARY_NAME EVENT_PIPE_LIBRARY_NAME +// DiagnosticsServer/EventPipe components currently hosted by diagnostics_tracing library. +#define DIAGNOSTICS_TRACING_LIBRARY_NAME "diagnostics_tracing" #define EVENT_PIPE_COMPONENT_NAME "event_pipe" #define DIAGNOSTICS_SERVER_COMPONENT_NAME "diagnostics_server" /* One per component */ MonoComponentEntry components[] = { { HOT_RELOAD_LIBRARY_NAME, HOT_RELOAD_COMPONENT_NAME, COMPONENT_INIT_FUNC (hot_reload), (MonoComponent**)&hot_reload, NULL }, - { EVENT_PIPE_LIBRARY_NAME, EVENT_PIPE_COMPONENT_NAME, COMPONENT_INIT_FUNC (event_pipe), (MonoComponent**)&event_pipe, NULL }, - { DIAGNOSTICS_SERVER_LIBRARY_NAME, DIAGNOSTICS_SERVER_COMPONENT_NAME, COMPONENT_INIT_FUNC (diagnostics_server), (MonoComponent**)&diagnostics_server, NULL }, + { DIAGNOSTICS_TRACING_LIBRARY_NAME, EVENT_PIPE_COMPONENT_NAME, COMPONENT_INIT_FUNC (event_pipe), (MonoComponent**)&event_pipe, NULL }, + { DIAGNOSTICS_TRACING_LIBRARY_NAME, DIAGNOSTICS_SERVER_COMPONENT_NAME, COMPONENT_INIT_FUNC (diagnostics_server), (MonoComponent**)&diagnostics_server, NULL }, }; #ifndef STATIC_COMPONENTS From 3213dec4f94657d3f5cdc2e0672d3db2c47be1d8 Mon Sep 17 00:00:00 2001 From: lateralusX Date: Thu, 15 Apr 2021 12:48:40 +0200 Subject: [PATCH 49/55] Fix warning. --- src/mono/mono/component/event_pipe.h | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/mono/mono/component/event_pipe.h b/src/mono/mono/component/event_pipe.h index e9c8c39aec99f3..76ac80d9f484f1 100644 --- a/src/mono/mono/component/event_pipe.h +++ b/src/mono/mono/component/event_pipe.h @@ -125,7 +125,7 @@ typedef bool * EventPipe Native Events. */ -typedef void +typedef bool (*event_pipe_component_write_event_ee_startup_start_func)(void); /* From 0c8347715bc4983d31cfe3c0cb09fa35d4e2ec72 Mon Sep 17 00:00:00 2001 From: lateralusX Date: Thu, 15 Apr 2021 12:49:17 +0200 Subject: [PATCH 50/55] Fix linking of none stub components on Android. --- src/tasks/AndroidAppBuilder/ApkBuilder.cs | 7 ++++++- 1 file changed, 6 insertions(+), 1 deletion(-) diff --git a/src/tasks/AndroidAppBuilder/ApkBuilder.cs b/src/tasks/AndroidAppBuilder/ApkBuilder.cs index fc887ff17af430..67e5cd7c6a5c2c 100644 --- a/src/tasks/AndroidAppBuilder/ApkBuilder.cs +++ b/src/tasks/AndroidAppBuilder/ApkBuilder.cs @@ -180,7 +180,7 @@ public class ApkBuilder } else { - nativeLibraries = $" {monoRuntimeLib}{Environment.NewLine}"; + nativeLibraries += $"{monoRuntimeLib}{Environment.NewLine}"; } string[] staticComponentStubLibs = Directory.GetFiles(AppDir, "libmono-component-*-stub-static.a"); @@ -225,6 +225,11 @@ public class ApkBuilder nativeLibraries += $" {componentLibToLink}{Environment.NewLine}"; } + // There's a circular dependecy between static mono runtime lib and static component libraries. + // Adding mono runtime lib before and after component libs will resolve issues with undefined symbols + // due to circular dependecy. + nativeLibraries += $" {monoRuntimeLib}{Environment.NewLine}"; + string aotSources = ""; foreach (string asm in assemblerFiles) { From 65cdb359149350894587477cc4f7b85400c093d5 Mon Sep 17 00:00:00 2001 From: lateralusX Date: Thu, 15 Apr 2021 13:58:03 +0200 Subject: [PATCH 51/55] Remove changes done to components.md. --- docs/design/mono/components.md | 1 - 1 file changed, 1 deletion(-) diff --git a/docs/design/mono/components.md b/docs/design/mono/components.md index 5231d6f1bfa633..2dc982dbeaaf1a 100644 --- a/docs/design/mono/components.md +++ b/docs/design/mono/components.md @@ -278,4 +278,3 @@ In each runtime pack we include: - An MSBuild targets file that defines targets to copy a specified set of components to the app publish folder (if components are dynamic); or to link the runtime together with stubs and a set of enabled components (if components are static) ** TODO ** Write this up in more detail - From f15dc9b212935ef0bf6f1835af191536b62868b6 Mon Sep 17 00:00:00 2001 From: lateralusX Date: Fri, 16 Apr 2021 12:16:12 +0200 Subject: [PATCH 52/55] Review feedback. --- src/mono/mono.proj | 62 +++++++------------ src/mono/mono/component/component.h | 12 +++- .../mono/component/diagnostics_server-stub.c | 11 ++-- src/mono/mono/component/diagnostics_server.c | 12 ++-- src/mono/mono/component/event_pipe-stub.c | 11 ++-- src/mono/mono/component/event_pipe.c | 12 ++-- src/mono/mono/component/hot_reload-stub.c | 11 ++-- src/mono/mono/component/hot_reload.c | 17 ++--- src/mono/mono/metadata/components.c | 13 +--- src/mono/mono/metadata/components.h | 3 - src/mono/mono/utils/mono-compiler.h | 2 +- 11 files changed, 74 insertions(+), 92 deletions(-) diff --git a/src/mono/mono.proj b/src/mono/mono.proj index 1355059712799a..48f27121ae5e04 100644 --- a/src/mono/mono.proj +++ b/src/mono/mono.proj @@ -19,33 +19,24 @@ .cmd .sh .exe - .dll - .dylib - .dylib - .so - lib - lib + lib + .dylib + .dll + .so + .lib + .a \" python3 python coreclr - $(CoreClrLibName).dll - lib$(CoreClrLibName).dylib - lib$(CoreClrLibName).dylib - lib$(CoreClrLibName).so + $(LibPrefix)$(CoreClrLibName)$(SharedLibExt) monosgen-2.0 $(MonoLibName) $(CoreClrLibName) - lib$(MonoSharedLibName).dylib - lib$(MonoSharedLibName).so - lib$(MonoLibName).a - $(CoreClrFileName) - lib$(MonoLibName).a - .dylib - .dll - .so - .lib - .a + $(LibPrefix)$(MonoSharedLibName)$(SharedLibExt) + $(LibPrefix)$(MonoLibName)$(StaticLibExt) + $(MonoStaticLibFileName) + $(MonoSharedLibFileName) $(Configuration) $(Configuration) $([MSBuild]::NormalizeDirectory('$(ArtifactsDir)', 'tests', 'coreclr', '$(TargetOS).$(Platform).$(CoreClrTestConfig)', 'Tests', 'Core_Root')) @@ -420,7 +411,7 @@ <_MonoCMakeArgs Include="-DFEATURE_PERFTRACING_PAL_TCP=1"/> <_MonoCMakeArgs Include="-DFEATURE_PERFTRACING_DISABLE_LISTEN_PORTS=1"/> - <_MonoCMakeArgs Include="-DISABLE_LINK_STATIC_COMPONENTS=1" /> + <_MonoCMakeArgs Include="-DDISABLE_LINK_STATIC_COMPONENTS=1" /> @@ -640,14 +631,9 @@ - <_MonoRuntimeFilePath Condition="'$(TargetsWindows)' == 'true'">$(MonoObjDir)out\bin\$(MonoSharedLibName).dll - <_MonoRuntimeFilePath Condition="'$(TargetsOSX)' == 'true'">$(MonoObjDir)out\lib\lib$(MonoSharedLibName).dylib - <_MonoRuntimeFilePath Condition="'$(TargetsMacCatalyst)' == 'true'">$(MonoObjDir)out\lib\lib$(MonoSharedLibName).dylib - <_MonoRuntimeFilePath Condition="'$(TargetsiOS)' == 'true'">$(MonoObjDir)out\lib\lib$(MonoSharedLibName).dylib - <_MonoRuntimeFilePath Condition="'$(TargetstvOS)' == 'true'">$(MonoObjDir)out\lib\lib$(MonoSharedLibName).dylib - <_MonoRuntimeFilePath Condition="'$(TargetsBrowser)' == 'true'">$(MonoObjDir)out\lib\lib$(MonoLibName).a - <_MonoRuntimeFilePath Condition="'$(_MonoRuntimeFilePath)' == ''">$(MonoObjDir)out\lib\lib$(MonoSharedLibName).so - <_MonoRuntimeStaticFilePath Condition="'$(TargetsMacCatalyst)' == 'true' or '$(TargetsiOS)' == 'true' or '$(TargetstvOS)' == 'true' or '$(TargetsAndroid)' == 'true'">$(MonoObjDir)out\lib\lib$(MonoLibName).a + <_MonoRuntimeFilePath Condition="'$(TargetsWindows)' == 'true'">$(MonoObjDir)out\bin\$(MonoFileName) + <_MonoRuntimeFilePath Condition="'$(_MonoRuntimeFilePath)' == ''">$(MonoObjDir)out\lib\$(MonoFileName) + <_MonoRuntimeStaticFilePath>$(MonoObjDir)out\lib\$(MonoStaticLibFileName) <_MonoIncludeInterpStaticFiles Condition="'$(TargetsBrowser)' == 'true'">true <_MonoIncludeIcuFiles Condition="'$(TargetsiOS)' == 'true' or '$(TargetstvOS)' == 'true'">true @@ -657,13 +643,13 @@ - <_MonoRuntimeComponentsStaticFilePath Include="$([System.IO.Directory]::GetParent($(_MonoRuntimeFilePath)))\libmono-component-*$(StaticNativeLibrarySuffix)" Condition="Exists($(_MonoRuntimeFilePath))" /> - <_MonoRuntimeComponentsSharedFilePath Include="$([System.IO.Directory]::GetParent($(_MonoRuntimeFilePath)))\libmono-component-*$(SharedNativeLibrarySuffix)" Condition="Exists($(_MonoRuntimeFilePath))" /> - <_MonoRuntimeArtifacts Include="$(_MonoRuntimeFilePath)"> + <_MonoRuntimeComponentsStaticFilePath Include="$([System.IO.Directory]::GetParent($(_MonoRuntimeFilePath)))\libmono-component-*$(StaticLibExt)" Condition="Exists($(_MonoRuntimeFilePath))" /> + <_MonoRuntimeComponentsSharedFilePath Include="$([System.IO.Directory]::GetParent($(_MonoRuntimeFilePath)))\libmono-component-*$(SharedLibExt)" Condition="Exists($(_MonoRuntimeFilePath))" /> + <_MonoRuntimeArtifacts Include="$(_MonoRuntimeFilePath)" Condition="Exists($(_MonoRuntimeFilePath))"> $(RuntimeBinDir)$(MonoFileName) - <_MonoRuntimeArtifacts Include="$(_MonoRuntimeStaticFilePath)"> - $(RuntimeBinDir)$(MonoStaticFileName) + <_MonoRuntimeArtifacts Include="$(_MonoRuntimeStaticFilePath)" Condition="Exists($(_MonoRuntimeStaticFilePath))"> + $(RuntimeBinDir)$(MonoStaticLibFileName) <_MonoRuntimeArtifacts Include="@(_MonoRuntimeComponentsStaticFilePath)"> @@ -700,11 +686,11 @@ <_MonoRuntimeArtifacts Condition="'$(TargetsBrowser)' == 'true' and '$(BuildMonoAOTCrossCompilerOnly)' != 'true'" Include="$(MonoObjDir)out\lib\libmono-profiler-aot.a"> $(RuntimeBinDir)libmono-profiler-aot.a - <_MonoICorDebugArtifacts Condition="'$(MonoMsCorDbi)' == 'true'" Include="$(MonoObjDir)out\lib\$(LibPrefix)dbgshim$(LibExt)"> - $(RuntimeBinDir)$(LibPrefix)dbgshim$(LibExt) + <_MonoICorDebugArtifacts Condition="'$(MonoMsCorDbi)' == 'true'" Include="$(MonoObjDir)out\lib\$(LibPrefix)dbgshim$(SharedLibExt)"> + $(RuntimeBinDir)$(LibPrefix)dbgshim$(SharedLibExt) - <_MonoICorDebugArtifacts Condition="'$(MonoMsCorDbi)' == 'true'" Include="$(MonoObjDir)out\lib\$(LibPrefix)mscordbi$(LibExt)"> - $(RuntimeBinDir)$(LibPrefix)mscordbi$(LibExt) + <_MonoICorDebugArtifacts Condition="'$(MonoMsCorDbi)' == 'true'" Include="$(MonoObjDir)out\lib\$(LibPrefix)mscordbi$(SharedLibExt)"> + $(RuntimeBinDir)$(LibPrefix)mscordbi$(SharedLibExt) <_IcuArtifacts Condition="'$(_MonoIncludeIcuFiles)' == 'true'" diff --git a/src/mono/mono/component/component.h b/src/mono/mono/component/component.h index 71d27ea1bbe0ef..300e09753f6a44 100644 --- a/src/mono/mono/component/component.h +++ b/src/mono/mono/component/component.h @@ -5,12 +5,20 @@ #ifndef _MONO_COMPONENT_COMPONENT_H #define _MONO_COMPONENT_COMPONENT_H +#include +#ifndef __cplusplus +#include +#endif // __cplusplus + +#define MONO_COMPONENT_ITF_VERSION 1 + typedef struct _MonoComponent MonoComponent; -typedef void (*MonoComponent_CleanupFn) (MonoComponent *self); +typedef bool (*MonoComponent_AvailableFn) (void); struct _MonoComponent { - MonoComponent_CleanupFn cleanup; + intptr_t itf_version; + MonoComponent_AvailableFn available; }; #endif/*_MONO_COMPONENT_COMPONENT_H*/ diff --git a/src/mono/mono/component/diagnostics_server-stub.c b/src/mono/mono/component/diagnostics_server-stub.c index 73b257bc82a6f3..0a8f6649cda25a 100644 --- a/src/mono/mono/component/diagnostics_server-stub.c +++ b/src/mono/mono/component/diagnostics_server-stub.c @@ -10,8 +10,8 @@ * Forward declares of all static functions. */ -static void -diagnostics_server_stub_cleanup (MonoComponent *self); +static bool +diagnostics_server_stub_available (void); static bool diagnostics_server_stub_init (void); @@ -26,16 +26,17 @@ static void diagnostics_server_stub_disable (void); static MonoComponentDiagnosticsServer fn_table = { - { &diagnostics_server_stub_cleanup }, + { MONO_COMPONENT_ITF_VERSION, &diagnostics_server_stub_available }, &diagnostics_server_stub_init, &diagnostics_server_stub_shutdown, &diagnostics_server_stub_pause_for_diagnostics_monitor, &diagnostics_server_stub_disable }; -static void -diagnostics_server_stub_cleanup (MonoComponent *self) +static bool +diagnostics_server_stub_available (void) { + return false; } static bool diff --git a/src/mono/mono/component/diagnostics_server.c b/src/mono/mono/component/diagnostics_server.c index 239576b4667bd0..c03b1296038d9d 100644 --- a/src/mono/mono/component/diagnostics_server.c +++ b/src/mono/mono/component/diagnostics_server.c @@ -14,21 +14,21 @@ MonoComponentDiagnosticsServer * mono_component_diagnostics_server_init (void); #endif -static void -diagnostics_server_cleanup (MonoComponent *self); +static bool +diagnostics_server_available (void); static MonoComponentDiagnosticsServer fn_table = { - { &diagnostics_server_cleanup }, + { MONO_COMPONENT_ITF_VERSION, &diagnostics_server_available }, &ds_server_init, &ds_server_shutdown, &ds_server_pause_for_diagnostics_monitor, &ds_server_disable }; -static void -diagnostics_server_cleanup (MonoComponent *self) +static bool +diagnostics_server_available (void) { - return; + return true; } MonoComponentDiagnosticsServer * diff --git a/src/mono/mono/component/event_pipe-stub.c b/src/mono/mono/component/event_pipe-stub.c index 4cad9dccd78ada..ce008d05b4f297 100644 --- a/src/mono/mono/component/event_pipe-stub.c +++ b/src/mono/mono/component/event_pipe-stub.c @@ -14,8 +14,8 @@ static uint8_t _max_event_pipe_type_size [256]; * Forward declares of all static functions. */ -static void -event_pipe_stub_cleanup (MonoComponent *self); +static bool +event_pipe_stub_available (void); static void event_pipe_stub_init (void); @@ -100,7 +100,7 @@ event_pipe_stub_write_event_ee_startup_start (void); static MonoComponentEventPipe fn_table = { - { &event_pipe_stub_cleanup }, + { MONO_COMPONENT_ITF_VERSION, &event_pipe_stub_available }, &event_pipe_stub_init, &event_pipe_stub_finish_init, &event_pipe_stub_shutdown, @@ -119,9 +119,10 @@ static MonoComponentEventPipe fn_table = { &event_pipe_stub_write_event_ee_startup_start }; -static void -event_pipe_stub_cleanup (MonoComponent *self) +static bool +event_pipe_stub_available (void) { + return false; } static void diff --git a/src/mono/mono/component/event_pipe.c b/src/mono/mono/component/event_pipe.c index 49dd05e06fe149..74588de587e84b 100644 --- a/src/mono/mono/component/event_pipe.c +++ b/src/mono/mono/component/event_pipe.c @@ -39,8 +39,8 @@ struct _EventPipeEventInstanceData { * Forward declares of all static functions. */ -static void -event_pipe_cleanup (MonoComponent *self); +static bool +event_pipe_available (void); static EventPipeSessionID event_pipe_enable ( @@ -71,7 +71,7 @@ event_pipe_thread_ctrl_activity_id( uint32_t activity_id_len); static MonoComponentEventPipe fn_table = { - { &event_pipe_cleanup }, + { MONO_COMPONENT_ITF_VERSION, &event_pipe_available }, &ep_init, &ep_finish_init, &ep_shutdown, @@ -90,10 +90,10 @@ static MonoComponentEventPipe fn_table = { &ep_rt_mono_write_event_ee_startup_start }; -static void -event_pipe_cleanup (MonoComponent *self) +static bool +event_pipe_available (void) { - return; + return true; } static EventPipeSessionID diff --git a/src/mono/mono/component/hot_reload-stub.c b/src/mono/mono/component/hot_reload-stub.c index 35c066f3394533..7f1fdd20f03c20 100644 --- a/src/mono/mono/component/hot_reload-stub.c +++ b/src/mono/mono/component/hot_reload-stub.c @@ -10,14 +10,14 @@ #include "mono/utils/mono-compiler.h" #include "mono/utils/mono-error-internals.h" -static void -hot_reload_stub_cleanup (MonoComponent *self); +static bool +hot_reload_stub_available (void); static void hot_reload_stub_apply_changes (MonoImage *base_image, gconstpointer dmeta, uint32_t dmeta_len, gconstpointer dil, uint32_t dil_len, MonoError *error); static MonoComponentHotReload fn_table = { - { &hot_reload_stub_cleanup }, + { MONO_COMPONENT_ITF_VERSION, &hot_reload_stub_available }, &hot_reload_stub_apply_changes, }; @@ -36,9 +36,10 @@ mono_component_hot_reload_stub_init (void) return &fn_table; } -void -hot_reload_stub_cleanup (MonoComponent *self) +bool +hot_reload_stub_available (void) { + return false; } void diff --git a/src/mono/mono/component/hot_reload.c b/src/mono/mono/component/hot_reload.c index 5476fd0150db2c..2963eb6648914e 100644 --- a/src/mono/mono/component/hot_reload.c +++ b/src/mono/mono/component/hot_reload.c @@ -15,14 +15,14 @@ MonoComponentHotReload * mono_component_hot_reload_init (void); #endif -static void -hot_reload_cleanup (MonoComponent *self); +static bool +hot_reload_available (void); static void hot_reload_apply_changes (MonoImage *base_image, gconstpointer dmeta, uint32_t dmeta_len, gconstpointer dil, uint32_t dil_len, MonoError *error); static MonoComponentHotReload fn_table = { - { &hot_reload_cleanup }, + { MONO_COMPONENT_ITF_VERSION, &hot_reload_available }, &hot_reload_apply_changes, }; @@ -33,15 +33,10 @@ mono_component_hot_reload_init (void) return &fn_table; } -static void -hot_reload_cleanup (MonoComponent *self) +static bool +hot_reload_available (void) { - static gboolean cleaned = FALSE; - if (cleaned) - return; - - /* TODO: implement me */ - cleaned = TRUE; + return true; } static void diff --git a/src/mono/mono/metadata/components.c b/src/mono/mono/metadata/components.c index 85708f78b3f8e2..6301566d6c45bb 100644 --- a/src/mono/mono/metadata/components.c +++ b/src/mono/mono/metadata/components.c @@ -85,17 +85,10 @@ mono_components_init (void) *components [i].component = components [i].init (); } #endif -} - -void -mono_components_cleanup (void) -{ - /* call each components cleanup fn */ + /* validate components interface version */ for (int i = 0; i < G_N_ELEMENTS (components); ++i) { - if (*components [i].component) - (*components [i].component)->cleanup (*components [i].component); - if (components [i].lib) - mono_dl_close (components [i].lib); + guint64 version = (guint64)(*components [i].component)->itf_version; + g_assertf (version == MONO_COMPONENT_ITF_VERSION, "%s component returned unexpected interface version (expected %" PRIu64 " got %" PRIu64 ")", components [i].name, (guint64)MONO_COMPONENT_ITF_VERSION, version); } } diff --git a/src/mono/mono/metadata/components.h b/src/mono/mono/metadata/components.h index 03d50fdfc0a948..2fd82eaf97e398 100644 --- a/src/mono/mono/metadata/components.h +++ b/src/mono/mono/metadata/components.h @@ -13,9 +13,6 @@ void mono_components_init (void); -void -mono_components_cleanup (void); - /* Declare each component's getter function here */ static inline MonoComponentHotReload * diff --git a/src/mono/mono/utils/mono-compiler.h b/src/mono/mono/utils/mono-compiler.h index 4f9f87239fc7f6..f5f8b860ca0cd9 100644 --- a/src/mono/mono/utils/mono-compiler.h +++ b/src/mono/mono/utils/mono-compiler.h @@ -85,7 +85,7 @@ typedef ptrdiff_t ssize_t; /* Mono components */ -/* User to mark internal functions used by dynamically linked runtime components */ +/* Used to mark internal functions used by dynamically linked runtime components */ #define MONO_COMPONENT_API MONO_API #ifdef COMPILING_COMPONENT_DYNAMIC From 28606d8209644e285d746da2c1e2014cb64246ed Mon Sep 17 00:00:00 2001 From: lateralusX Date: Fri, 16 Apr 2021 13:00:41 +0200 Subject: [PATCH 53/55] Fix none Windows build error. --- src/mono/mono/component/component.h | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/mono/mono/component/component.h b/src/mono/mono/component/component.h index 300e09753f6a44..afc15a118739a0 100644 --- a/src/mono/mono/component/component.h +++ b/src/mono/mono/component/component.h @@ -5,7 +5,7 @@ #ifndef _MONO_COMPONENT_COMPONENT_H #define _MONO_COMPONENT_COMPONENT_H -#include +#include #ifndef __cplusplus #include #endif // __cplusplus From 58a349c6293dfb1b7deb98f276ee435806c2ae74 Mon Sep 17 00:00:00 2001 From: lateralusX Date: Fri, 16 Apr 2021 14:45:25 +0200 Subject: [PATCH 54/55] Only include lib once in runtime artifacts when not building shared library --- src/mono/mono.proj | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/mono/mono.proj b/src/mono/mono.proj index 48f27121ae5e04..0ad59ae65ac200 100644 --- a/src/mono/mono.proj +++ b/src/mono/mono.proj @@ -648,7 +648,7 @@ <_MonoRuntimeArtifacts Include="$(_MonoRuntimeFilePath)" Condition="Exists($(_MonoRuntimeFilePath))"> $(RuntimeBinDir)$(MonoFileName) - <_MonoRuntimeArtifacts Include="$(_MonoRuntimeStaticFilePath)" Condition="Exists($(_MonoRuntimeStaticFilePath))"> + <_MonoRuntimeArtifacts Include="$(_MonoRuntimeStaticFilePath)" Condition="Exists($(_MonoRuntimeStaticFilePath)) and '$(_MonoRuntimeStaticFilePath)' != '$(_MonoRuntimeFilePath)'"> $(RuntimeBinDir)$(MonoStaticLibFileName) From 277159c8c98a42248eded63b688af3b6c28630b4 Mon Sep 17 00:00:00 2001 From: lateralusX Date: Fri, 16 Apr 2021 16:03:31 +0200 Subject: [PATCH 55/55] Only install static libraries on platforms currently shipping them. --- src/mono/mono.proj | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/mono/mono.proj b/src/mono/mono.proj index 0ad59ae65ac200..c9b3f7e36ad228 100644 --- a/src/mono/mono.proj +++ b/src/mono/mono.proj @@ -633,7 +633,7 @@ <_MonoRuntimeFilePath Condition="'$(TargetsWindows)' == 'true'">$(MonoObjDir)out\bin\$(MonoFileName) <_MonoRuntimeFilePath Condition="'$(_MonoRuntimeFilePath)' == ''">$(MonoObjDir)out\lib\$(MonoFileName) - <_MonoRuntimeStaticFilePath>$(MonoObjDir)out\lib\$(MonoStaticLibFileName) + <_MonoRuntimeStaticFilePath Condition="'$(TargetsMacCatalyst)' == 'true' or '$(TargetsiOS)' == 'true' or '$(TargetstvOS)' == 'true' or '$(TargetsAndroid)' == 'true'">$(MonoObjDir)out\lib\$(MonoStaticLibFileName) <_MonoIncludeInterpStaticFiles Condition="'$(TargetsBrowser)' == 'true'">true <_MonoIncludeIcuFiles Condition="'$(TargetsiOS)' == 'true' or '$(TargetstvOS)' == 'true'">true