summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--CMakeLists.txt4
-rw-r--r--clr.coreclr.props4
-rw-r--r--clr.defines.targets2
-rw-r--r--src/inc/clrconfigvalues.h4
-rw-r--r--src/inc/eventtracebase.h25
-rw-r--r--src/mscorlib/mscorlib.shared.sources.props1
-rw-r--r--src/mscorlib/src/System/Diagnostics/Eventing/EventSource.cs5
-rw-r--r--src/mscorlib/src/System/Diagnostics/Eventing/XplatEventLogger.cs141
-rw-r--r--src/pal/prebuilt/inc/clrallevents.h13
-rw-r--r--src/pal/prebuilt/inc/clrxplatevents.h7
-rw-r--r--src/pal/prebuilt/inc/etmdummy.h1
-rw-r--r--src/pal/src/eventprovider/lttng/eventprovdotnetruntime.cpp59
-rw-r--r--src/pal/src/eventprovider/lttng/tpdotnetruntime.h27
-rw-r--r--src/pal/tests/palsuite/eventprovider/clralltestevents.cpp7
-rw-r--r--src/vm/ClrEtwAll.man19
-rw-r--r--src/vm/ecalllist.h10
-rw-r--r--src/vm/eventtrace.cpp27
-rw-r--r--src/vm/eventtracepriv.h11
-rw-r--r--src/vm/mscorlib.cpp7
19 files changed, 361 insertions, 13 deletions
diff --git a/CMakeLists.txt b/CMakeLists.txt
index 2ac0ebb07a..2803728d33 100644
--- a/CMakeLists.txt
+++ b/CMakeLists.txt
@@ -221,6 +221,10 @@ if (WIN32 OR CLR_CMAKE_PLATFORM_LINUX)
add_definitions(-DFEATURE_EVENT_TRACE=1)
endif (WIN32 OR CLR_CMAKE_PLATFORM_LINUX)
+if (CLR_CMAKE_PLATFORM_LINUX)
+ add_definitions(-DFEATURE_EVENTSOURCE_XPLAT=1)
+endif (CLR_CMAKE_PLATFORM_LINUX)
+
if(CLR_CMAKE_PLATFORM_UNIX)
add_subdirectory(src/ToolBox/SOS/lldbplugin)
add_subdirectory(src/pal)
diff --git a/clr.coreclr.props b/clr.coreclr.props
index 819fd6f829..2373b7b5c3 100644
--- a/clr.coreclr.props
+++ b/clr.coreclr.props
@@ -94,6 +94,10 @@
<FeatureSvrGc Condition="'$(TargetArch)' != 'arm'">true</FeatureSvrGc>
</PropertyGroup>
+ <PropertyGroup Condition="'$(TargetsLinux)' == 'true'">
+ <FeatureXplatEventSource>true</FeatureXplatEventSource>
+ </PropertyGroup>
+
<PropertyGroup Condition="'$(TargetsUnix)' == 'true'">
<FeaturePal>true</FeaturePal>
diff --git a/clr.defines.targets b/clr.defines.targets
index 87ec8ace0a..879de92f84 100644
--- a/clr.defines.targets
+++ b/clr.defines.targets
@@ -37,6 +37,7 @@
<CDefines Condition="'$(FeatureDbgipcTransportVM)' == 'true'">$(CDefines);FEATURE_DBGIPC_TRANSPORT_VM</CDefines>
<CDefines Condition="'$(FeatureDbgPublish)' == 'true'">$(CDefines);FEATURE_DBG_PUBLISH</CDefines>
<CDefines Condition="'$(FeatureEventTrace)' == 'true'">$(CDefines);FEATURE_EVENT_TRACE</CDefines>
+ <CDefines Condition="'$(FeatureXplatEventSource)' == 'true'">$(CDefines);FEATURE_EVENTSOURCE_XPLAT</CDefines>
<CDefines Condition="'$(FeatureExceptionDispatchInfo)' == 'true'">$(CDefines);FEATURE_EXCEPTIONDISPATCHINFO</CDefines>
<CDefines Condition="'$(FeatureExceptionNotifications)' == 'true'">$(CDefines);FEATURE_EXCEPTION_NOTIFICATIONS</CDefines>
<CDefines Condition="'$(FeatureFrameworkInternal)' == 'true'">$(CDefines);FEATURE_FRAMEWORK_INTERNAL</CDefines>
@@ -190,6 +191,7 @@
<DefineConstants Condition="'$(FeatureNongenericCollections)' == 'true'">$(DefineConstants);FEATURE_NONGENERIC_COLLECTIONS</DefineConstants>
<DefineConstants Condition="'$(FeatureNormIdnaOnly)' == 'true'">$(DefineConstants);FEATURE_NORM_IDNA_ONLY</DefineConstants>
<DefineConstants Condition="'$(FeaturePal)' == 'true'">$(DefineConstants);FEATURE_PAL</DefineConstants>
+ <DefineConstants Condition="'$(FeatureXplatEventSource)' == 'true'">$(DefineConstants);FEATURE_EVENTSOURCE_XPLAT</DefineConstants>
<DefineConstants Condition="'$(FeaturePerfmon)' == 'true'">$(DefineConstants);FEATURE_PERFMON</DefineConstants>
<DefineConstants Condition="'$(FeaturePls)' == 'true'">$(DefineConstants);FEATURE_PLS</DefineConstants>
<DefineConstants Condition="'$(FeatureRandomizedStringHashing)' == 'true'">$(DefineConstants);FEATURE_RANDOMIZED_STRING_HASHING</DefineConstants>
diff --git a/src/inc/clrconfigvalues.h b/src/inc/clrconfigvalues.h
index 1b517fcefe..8f33e40c27 100644
--- a/src/inc/clrconfigvalues.h
+++ b/src/inc/clrconfigvalues.h
@@ -1010,9 +1010,9 @@ RETAIL_CONFIG_DWORD_INFO(EXTERNAL_ReadyToRun, W("ReadyToRun"), 1, "Enable/disabl
RETAIL_CONFIG_DWORD_INFO(EXTERNAL_ReadyToRun, W("ReadyToRun"), 0, "Enable/disable use of ReadyToRun native code") // Off by default for desktop
#endif
-#if defined(FEATURE_PAL) && defined(FEATURE_EVENT_TRACE)
+#if defined(FEATURE_EVENT_TRACE) || defined(FEATURE_EVENTSOURCE_XPLAT)
RETAIL_CONFIG_DWORD_INFO(EXTERNAL_EnableEventLog, W("EnableEventLog"), 0, "Enable/disable use of EnableEventLogging mechanism ") // Off by default
-#endif //defined(FEATURE_PAL) && defined(FEATURE_EVENT_TRACE)
+#endif //defined(FEATURE_EVENT_TRACE) || defined(FEATURE_EVENTSOURCE_XPLAT)
//
// Interop
diff --git a/src/inc/eventtracebase.h b/src/inc/eventtracebase.h
index 19d1994e24..13810b015e 100644
--- a/src/inc/eventtracebase.h
+++ b/src/inc/eventtracebase.h
@@ -227,6 +227,21 @@ extern BOOL g_fEEIJWStartup;
#define GetClrInstanceId() (static_cast<UINT16>(g_nClrInstanceId))
+#if defined(FEATURE_EVENT_TRACE) || defined(FEATURE_EVENTSOURCE_XPLAT)
+
+#include "clrconfig.h"
+ class XplatEventLogger
+{
+ public:
+ inline static BOOL IsEventLoggingEnabled()
+ {
+ static ConfigDWORD configEventLogging;
+ return configEventLogging.val(CLRConfig::EXTERNAL_EnableEventLog);
+ }
+};
+
+#endif //defined(FEATURE_EVENT_TRACE)
+
#if defined(FEATURE_EVENT_TRACE)
#ifndef FEATURE_PAL
@@ -283,16 +298,6 @@ extern "C" {
#elif defined(__LINUX__)
-#include "clrconfig.h"
- class XplatEventLogger
-{
- public:
- inline static BOOL IsEventLoggingEnabled()
- {
- static ConfigDWORD configEventLogging;
- return configEventLogging.val(CLRConfig::EXTERNAL_EnableEventLog);
- }
-};
#include "clrallevents.h"
#else
#error "A tracing System has not been enabled for this Platform"
diff --git a/src/mscorlib/mscorlib.shared.sources.props b/src/mscorlib/mscorlib.shared.sources.props
index 13f58e2fc0..f17226f4cb 100644
--- a/src/mscorlib/mscorlib.shared.sources.props
+++ b/src/mscorlib/mscorlib.shared.sources.props
@@ -989,6 +989,7 @@
<DiagnosticsSources Include="$(BclSourcesRoot)\System\Diagnostics\Eventing\EventDescriptor.cs" />
<DiagnosticsSources Include="$(BclSourcesRoot)\System\Diagnostics\Eventing\EventProvider.cs" />
<DiagnosticsSources Include="$(BclSourcesRoot)\System\Diagnostics\Eventing\EventSource.cs" />
+ <DiagnosticsSources Condition="'$(FeatureXplatEventSource)' == 'true'" Include="$(BclSourcesRoot)\System\Diagnostics\Eventing\XplatEventLogger.cs" />
<DiagnosticsSources Include="$(BclSourcesRoot)\System\Diagnostics\Eventing\EventSourceException.cs" />
<DiagnosticsSources Include="$(BclSourcesRoot)\System\Diagnostics\Eventing\FrameworkEventSource.cs" />
<DiagnosticsSources Include="$(BclSourcesRoot)\System\Diagnostics\Eventing\StubEnvironment.cs" />
diff --git a/src/mscorlib/src/System/Diagnostics/Eventing/EventSource.cs b/src/mscorlib/src/System/Diagnostics/Eventing/EventSource.cs
index ff5b8d5e39..1fc9a526cc 100644
--- a/src/mscorlib/src/System/Diagnostics/Eventing/EventSource.cs
+++ b/src/mscorlib/src/System/Diagnostics/Eventing/EventSource.cs
@@ -250,6 +250,11 @@ namespace System.Diagnostics.Tracing
/// </remarks>
public partial class EventSource : IDisposable
{
+
+#if FEATURE_EVENTSOURCE_XPLAT
+ private static readonly EventListener persistent_Xplat_Listener = XplatEventLogger.InitializePersistentListener();
+#endif //FEATURE_EVENTSOURCE_XPLAT
+
/// <summary>
/// The human-friendly name of the eventSource. It defaults to the simple name of the class
/// </summary>
diff --git a/src/mscorlib/src/System/Diagnostics/Eventing/XplatEventLogger.cs b/src/mscorlib/src/System/Diagnostics/Eventing/XplatEventLogger.cs
new file mode 100644
index 0000000000..94166f0412
--- /dev/null
+++ b/src/mscorlib/src/System/Diagnostics/Eventing/XplatEventLogger.cs
@@ -0,0 +1,141 @@
+using System;
+using System.Runtime.CompilerServices;
+using System.Collections.ObjectModel;
+using System.Collections.Generic;
+using System.Diagnostics;
+using System.Text;
+using System.Runtime.InteropServices;
+
+using Contract = System.Diagnostics.Contracts.Contract;
+
+#if FEATURE_EVENTSOURCE_XPLAT
+
+namespace System.Diagnostics.Tracing
+{
+
+ internal class XplatEventLogger : EventListener
+ {
+ public XplatEventLogger() {}
+
+ private static bool initializedPersistentListener = false;
+
+ [System.Security.SecuritySafeCritical]
+ public static EventListener InitializePersistentListener()
+ {
+ try{
+
+ if (!initializedPersistentListener && XplatEventLogger.IsEventSourceLoggingEnabled())
+ {
+ initializedPersistentListener = true;
+ return new XplatEventLogger();
+ }
+ }
+ catch(Exception){}
+
+ return null;
+ }
+
+ [DllImport(JitHelpers.QCall, CharSet = CharSet.Unicode)]
+ private static extern bool IsEventSourceLoggingEnabled();
+
+ [DllImport(JitHelpers.QCall, CharSet = CharSet.Unicode)]
+ private static extern void LogEventSource(int eventID, string eventName, string eventSourceName, string payload);
+
+ static List<char> escape_seq = new List<char> { '\b', '\f', '\n', '\r', '\t', '\"', '\\' };
+ static Dictionary<char, string> seq_mapping = new Dictionary<char, string>()
+ {
+ {'\b', "b"},
+ {'\f', "f"},
+ {'\n', "n"},
+ {'\r', "r"},
+ {'\t', "t"},
+ {'\"', "\\\""},
+ {'\\', "\\\\"}
+ };
+
+ private static void minimalJsonserializer(string payload, StringBuilder sb)
+ {
+ foreach( var elem in payload)
+ {
+ if (escape_seq.Contains(elem))
+ {
+ sb.Append("\\\\");
+ sb.Append(seq_mapping[elem]);
+ }
+ else
+ {
+ sb.Append(elem);
+ }
+ }
+ }
+
+ private static string Serialize(ReadOnlyCollection<string> payloadName, ReadOnlyCollection<object> payload, string sep = ", ")
+ {
+
+ if (payloadName == null || payload == null )
+ return String.Empty;
+
+ if (payloadName.Count == 0 || payload.Count == 0)
+ return String.Empty;
+
+ Contract.Assert(payloadName.Count == payload.Count);
+
+ var sb = StringBuilderCache.Acquire();
+
+ sb.Append('{');
+ for (int i = 0; i < payloadName.Count; i++)
+ {
+ var fieldstr = payloadName[i].ToString();
+
+ sb.Append("\\\"");
+ sb.Append(fieldstr);
+ sb.Append("\\\"");
+ sb.Append(':');
+
+ var valuestr = payload[i] as string;
+
+ if( valuestr != null)
+ {
+ sb.Append("\\\"");
+ minimalJsonserializer(valuestr,sb);
+ sb.Append("\\\"");
+ }
+ else
+ {
+ sb.Append(payload[i].ToString());
+ }
+
+ sb.Append(sep);
+
+ }
+
+ sb.Length -= sep.Length;
+ sb.Append('}');
+
+ return StringBuilderCache.GetStringAndRelease(sb);
+ }
+
+ internal protected override void OnEventSourceCreated(EventSource eventSource)
+ {
+ EnableEvents(eventSource, EventLevel.LogAlways, EventKeywords.All, null);
+ }
+
+ internal protected override void OnEventWritten(EventWrittenEventArgs eventData)
+ {
+ LogOnEventWritten(eventData);
+ }
+
+ [System.Security.SecuritySafeCritical]
+ private void LogOnEventWritten(EventWrittenEventArgs eventData)
+ {
+ string payload = "";
+ if (eventData.Payload != null)
+ {
+ payload = Serialize(eventData.PayloadNames, eventData.Payload);
+ }
+
+ LogEventSource( eventData.EventId, eventData.EventName,eventData.EventSource.Name,payload);
+ }
+ }
+}
+#endif //FEATURE_EVENTSOURCE_XPLAT
diff --git a/src/pal/prebuilt/inc/clrallevents.h b/src/pal/prebuilt/inc/clrallevents.h
index 8bcb8f713e..f56e3b0f4e 100644
--- a/src/pal/prebuilt/inc/clrallevents.h
+++ b/src/pal/prebuilt/inc/clrallevents.h
@@ -2246,6 +2246,19 @@ inline ULONG FireEtwCodeSymbols(
return FireEtXplatCodeSymbols(ModuleId,TotalChunks,ChunkNumber,ChunkLength,Chunk,ClrInstanceID);
}
+inline BOOL EventEnabledEventSource() {return XplatEventLogger::IsEventLoggingEnabled() && EventXplatEnabledEventSource();}
+
+inline ULONG FireEtwEventSource(
+ const signed int EventID,
+ PCWSTR EventName,
+ PCWSTR EventSourceName,
+ PCWSTR Payload
+)
+{
+ if (!EventEnabledEventSource()) {return ERROR_SUCCESS;}
+ return FireEtXplatEventSource(EventID,EventName,EventSourceName,Payload);
+}
+
inline BOOL EventEnabledCLRStackWalkDCStart() {return XplatEventLogger::IsEventLoggingEnabled() && EventXplatEnabledCLRStackWalkDCStart();}
inline ULONG FireEtwCLRStackWalkDCStart(
diff --git a/src/pal/prebuilt/inc/clrxplatevents.h b/src/pal/prebuilt/inc/clrxplatevents.h
index 52d35fc1d4..2e37485e49 100644
--- a/src/pal/prebuilt/inc/clrxplatevents.h
+++ b/src/pal/prebuilt/inc/clrxplatevents.h
@@ -1243,6 +1243,13 @@ extern "C" ULONG FireEtXplatCodeSymbols(
const BYTE* Chunk,
const unsigned short ClrInstanceID
);
+extern "C" BOOL EventXplatEnabledEventSource();
+extern "C" ULONG FireEtXplatEventSource(
+ const signed int EventID,
+ PCWSTR EventName,
+ PCWSTR EventSourceName,
+ PCWSTR Payload
+);
extern "C" BOOL EventXplatEnabledCLRStackWalkDCStart();
extern "C" ULONG FireEtXplatCLRStackWalkDCStart(
const unsigned short ClrInstanceID,
diff --git a/src/pal/prebuilt/inc/etmdummy.h b/src/pal/prebuilt/inc/etmdummy.h
index 97c592ed46..272bce78fa 100644
--- a/src/pal/prebuilt/inc/etmdummy.h
+++ b/src/pal/prebuilt/inc/etmdummy.h
@@ -177,6 +177,7 @@ This file is generated using the logic from <root>/src/inc/genXplatEtw.pl
#define FireEtwDebugExceptionProcessingStart() 0
#define FireEtwDebugExceptionProcessingEnd() 0
#define FireEtwCodeSymbols(ModuleId, TotalChunks, ChunkNumber, ChunkLength, Chunk, ClrInstanceID) 0
+#define FireEtwEventSource(EventID, EventName, EventSourceName, Payload) 0
#define FireEtwCLRStackWalkDCStart(ClrInstanceID, Reserved1, Reserved2, FrameCount, Stack) 0
#define FireEtwMethodDCStart(MethodID, ModuleID, MethodStartAddress, MethodSize, MethodToken, MethodFlags) 0
#define FireEtwMethodDCStart_V1(MethodID, ModuleID, MethodStartAddress, MethodSize, MethodToken, MethodFlags, ClrInstanceID) 0
diff --git a/src/pal/src/eventprovider/lttng/eventprovdotnetruntime.cpp b/src/pal/src/eventprovider/lttng/eventprovdotnetruntime.cpp
index 729053ebd8..1a0a25118b 100644
--- a/src/pal/src/eventprovider/lttng/eventprovdotnetruntime.cpp
+++ b/src/pal/src/eventprovider/lttng/eventprovdotnetruntime.cpp
@@ -5789,3 +5789,62 @@ extern "C" ULONG FireEtXplatCodeSymbols(
return Error;
}
+extern "C" BOOL EventXplatEnabledEventSource(){ return TRUE;}
+extern "C" ULONG FireEtXplatEventSource(
+ const signed int EventID,
+ PCWSTR EventName,
+ PCWSTR EventSourceName,
+ PCWSTR Payload
+)
+{
+ ULONG Error = ERROR_WRITE_FAULT;
+ if (!EventXplatEnabledEventSource()){ return ERROR_SUCCESS;};
+ INT EventName_path_size = -1;
+ INT EventName_full_name_path_size = WideCharToMultiByte( CP_ACP, 0, EventName, -1, NULL, 0, NULL, NULL );
+ CHAR* EventName_full_name=NULL;
+ INT EventSourceName_path_size = -1;
+ INT EventSourceName_full_name_path_size = WideCharToMultiByte( CP_ACP, 0, EventSourceName, -1, NULL, 0, NULL, NULL );
+ CHAR* EventSourceName_full_name=NULL;
+ INT Payload_path_size = -1;
+ INT Payload_full_name_path_size = WideCharToMultiByte( CP_ACP, 0, Payload, -1, NULL, 0, NULL, NULL );
+ CHAR* Payload_full_name=NULL;
+
+ EventName_full_name = (CHAR*)malloc(EventName_full_name_path_size*sizeof(CHAR));
+ _ASSERTE(EventName_full_name != NULL);
+ if(EventName_full_name == NULL){goto LExit;}
+
+ EventName_path_size = WideCharToMultiByte( CP_ACP, 0, EventName, -1, EventName_full_name, EventName_full_name_path_size, NULL, NULL );
+ _ASSERTE(EventName_path_size == EventName_full_name_path_size );
+ if( EventName_path_size == 0 ){ Error = ERROR_INVALID_PARAMETER; goto LExit;}
+ EventSourceName_full_name = (CHAR*)malloc(EventSourceName_full_name_path_size*sizeof(CHAR));
+ _ASSERTE(EventSourceName_full_name != NULL);
+ if(EventSourceName_full_name == NULL){goto LExit;}
+
+ EventSourceName_path_size = WideCharToMultiByte( CP_ACP, 0, EventSourceName, -1, EventSourceName_full_name, EventSourceName_full_name_path_size, NULL, NULL );
+ _ASSERTE(EventSourceName_path_size == EventSourceName_full_name_path_size );
+ if( EventSourceName_path_size == 0 ){ Error = ERROR_INVALID_PARAMETER; goto LExit;}
+ Payload_full_name = (CHAR*)malloc(Payload_full_name_path_size*sizeof(CHAR));
+ _ASSERTE(Payload_full_name != NULL);
+ if(Payload_full_name == NULL){goto LExit;}
+
+ Payload_path_size = WideCharToMultiByte( CP_ACP, 0, Payload, -1, Payload_full_name, Payload_full_name_path_size, NULL, NULL );
+ _ASSERTE(Payload_path_size == Payload_full_name_path_size );
+ if( Payload_path_size == 0 ){ Error = ERROR_INVALID_PARAMETER; goto LExit;}
+
+ tracepoint(
+ DotNETRuntime,
+ EventSource,
+ EventID,
+ EventName_full_name,
+ EventSourceName_full_name,
+ Payload_full_name
+ );
+
+ Error = ERROR_SUCCESS;
+LExit:
+ if (Payload_full_name != NULL) {free(Payload_full_name);}
+ if (EventSourceName_full_name != NULL) {free(EventSourceName_full_name);}
+ if (EventName_full_name != NULL) {free(EventName_full_name);}
+
+return Error;
+}
diff --git a/src/pal/src/eventprovider/lttng/tpdotnetruntime.h b/src/pal/src/eventprovider/lttng/tpdotnetruntime.h
index 0b3c8a7dbc..6e56d2e39b 100644
--- a/src/pal/src/eventprovider/lttng/tpdotnetruntime.h
+++ b/src/pal/src/eventprovider/lttng/tpdotnetruntime.h
@@ -26,6 +26,32 @@ This file is generated using the logic from <root>/src/inc/genXplatLttng.pl
#include <lttng/tracepoint.h>
+#define EventSource_TRACEPOINT_ARGS \
+TP_ARGS(\
+ const signed int ,EventID,\
+ const char* ,EventName,\
+ const char* ,EventSourceName,\
+ const char* ,Payload\
+)
+TRACEPOINT_EVENT_CLASS(
+ DotNETRuntime,
+ EventSource,
+ EventSource_TRACEPOINT_ARGS,
+ TP_FIELDS(
+ ctf_integer(signed int,EventID,EventID)
+ ctf_string(EventName,EventName)
+ ctf_string(EventSourceName,EventSourceName)
+ ctf_string(Payload,Payload)
+ )
+)
+#define EventSourceT_TRACEPOINT_INSTANCE(name) \
+TRACEPOINT_EVENT_INSTANCE(\
+ DotNETRuntime,\
+ EventSource ,\
+ name ,\
+ EventSource_TRACEPOINT_ARGS \
+)
+
#define StrongNameVerification_TRACEPOINT_ARGS \
TP_ARGS(\
const unsigned int ,VerificationFlags,\
@@ -3204,5 +3230,6 @@ T_TRACEPOINT_INSTANCE(DebugIPCEventEnd)
T_TRACEPOINT_INSTANCE(DebugExceptionProcessingStart)
T_TRACEPOINT_INSTANCE(DebugExceptionProcessingEnd)
CodeSymbolsT_TRACEPOINT_INSTANCE(CodeSymbols)
+EventSourceT_TRACEPOINT_INSTANCE(EventSource)
#endif /* LTTNG_CORECLR_HDotNETRuntime */
#include <lttng/tracepoint-event.h>
diff --git a/src/pal/tests/palsuite/eventprovider/clralltestevents.cpp b/src/pal/tests/palsuite/eventprovider/clralltestevents.cpp
index 0a572f1fd6..7f4adc0f93 100644
--- a/src/pal/tests/palsuite/eventprovider/clralltestevents.cpp
+++ b/src/pal/tests/palsuite/eventprovider/clralltestevents.cpp
@@ -1291,6 +1291,13 @@ win_UInt32,
win_Binary,
win_UInt16
);
+ EventXplatEnabledEventSource();
+Error |= FireEtXplatEventSource(
+win_Int32,
+W(" Testing UnicodeString "),
+W(" Testing UnicodeString "),
+W(" Testing UnicodeString ")
+);
EventXplatEnabledCLRStackWalkDCStart();
Error |= FireEtXplatCLRStackWalkDCStart(
win_UInt16,
diff --git a/src/vm/ClrEtwAll.man b/src/vm/ClrEtwAll.man
index ed9b25cd53..bbf4ce40fd 100644
--- a/src/vm/ClrEtwAll.man
+++ b/src/vm/ClrEtwAll.man
@@ -549,6 +549,21 @@
<!--Templates-->
<templates>
+ <template tid="EventSource">
+ <data name="EventID" inType="win:Int32" />
+ <data name="EventName" inType="win:UnicodeString" />
+ <data name="EventSourceName" inType="win:UnicodeString" />
+ <data name="Payload" inType="win:UnicodeString" />
+
+ <UserData>
+ <EventSource xmlns="myNs">
+ <EventID> %1 </EventID>
+ <EventName> %2 </EventName>
+ <EventSourceName> %3 </EventSourceName>
+ <Payload> %4 </Payload>
+ </EventSource>
+ </UserData>
+ </template>
<template tid="StrongNameVerification">
<data name="VerificationFlags" inType="win:UInt32" outType="win:HexInt32"/>
<data name="ErrorCode" inType="win:UInt32" outType="win:HexInt32"/>
@@ -3154,6 +3169,10 @@
keywords="CodeSymbolsKeyword" opcode="win:Start"
task="CodeSymbols"
symbol="CodeSymbols" message="$(string.RuntimePublisher.CodeSymbolsEventMessage)"/>
+
+ <event value="270" version="0" level="win:Informational" template="EventSource"
+ opcode="win:Start"
+ symbol="EventSource" />
</events>
</provider>
diff --git a/src/vm/ecalllist.h b/src/vm/ecalllist.h
index 0b0e45c194..26bc4b927b 100644
--- a/src/vm/ecalllist.h
+++ b/src/vm/ecalllist.h
@@ -2086,6 +2086,13 @@ FCFuncStart(gWindowsRuntimeBufferHelperFuncs)
FCFuncEnd()
#endif // ifdef FEATURE_COMINTEROP
+#if defined(FEATURE_EVENTSOURCE_XPLAT)
+FCFuncStart(gEventLogger)
+ QCFuncElement("IsEventSourceLoggingEnabled", XplatEventSourceLogger::IsEventSourceLoggingEnabled)
+ QCFuncElement("LogEventSource", XplatEventSourceLogger::LogEventSource)
+FCFuncEnd()
+#endif // defined(FEATURE_EVENTSOURCE_XPLAT)
+
#ifdef FEATURE_COMINTEROP
FCFuncStart(gRuntimeClassFuncs)
FCFuncElement("GetRedirectedGetHashCodeMD", ComObject::GetRedirectedGetHashCodeMD)
@@ -2479,6 +2486,9 @@ FCClassElement("WindowsRuntimeMetadata", "System.Runtime.InteropServices.Windows
#ifdef FEATURE_X509
FCClassElement("X509Utils", "System.Security.Cryptography.X509Certificates", gX509CertificateFuncs)
#endif // FEATURE_X509
+#if defined(FEATURE_EVENTSOURCE_XPLAT)
+FCClassElement("XplatEventLogger", "System.Diagnostics.Tracing", gEventLogger)
+#endif //defined(FEATURE_EVENTSOURCE_XPLAT)
#ifdef FEATURE_CAS_POLICY
FCClassElement("Zone", "System.Security.Policy", gCOMSecurityZone)
#endif // FEATURE_CAS_POLICY
diff --git a/src/vm/eventtrace.cpp b/src/vm/eventtrace.cpp
index 90dbf0bfc8..0e09665f0d 100644
--- a/src/vm/eventtrace.cpp
+++ b/src/vm/eventtrace.cpp
@@ -7390,4 +7390,31 @@ VOID ETW::EnumerationLog::EnumerationHelper(Module *moduleFilter, BaseDomain *do
}
}
+#if defined(FEATURE_EVENTSOURCE_XPLAT)
+
+void QCALLTYPE XplatEventSourceLogger::LogEventSource(__in_z int eventID, __in_z LPCWSTR eventName, __in_z LPCWSTR eventSourceName, __in_z LPCWSTR payload)
+{
+ QCALL_CONTRACT;
+
+ BEGIN_QCALL;
+ FireEtwEventSource(eventID, eventName, eventSourceName, payload);
+ END_QCALL;
+}
+
+BOOL QCALLTYPE XplatEventSourceLogger::IsEventSourceLoggingEnabled()
+{
+ QCALL_CONTRACT;
+
+ BOOL retVal = FALSE;
+
+ BEGIN_QCALL;
+ retVal = XplatEventLogger::IsEventLoggingEnabled();
+ END_QCALL;
+
+ return retVal;
+
+}
+
+#endif //defined(FEATURE_EVENTSOURCE_XPLAT)
+
#endif // !FEATURE_REDHAWK
diff --git a/src/vm/eventtracepriv.h b/src/vm/eventtracepriv.h
index 93c71b74e8..191f0d37b3 100644
--- a/src/vm/eventtracepriv.h
+++ b/src/vm/eventtracepriv.h
@@ -408,3 +408,14 @@ private:
#endif // __EVENTTRACEPRIV_H__
+
+#if defined(FEATURE_EVENTSOURCE_XPLAT)
+class XplatEventSourceLogger
+{
+public:
+ static void QCALLTYPE LogEventSource(__in_z int eventID, __in_z LPCWSTR eventName, __in_z LPCWSTR eventSourceName, __in_z LPCWSTR payload);
+
+ static BOOL QCALLTYPE IsEventSourceLoggingEnabled();
+};
+
+#endif //defined(FEATURE_EVENTSOURCE_XPLAT)
diff --git a/src/vm/mscorlib.cpp b/src/vm/mscorlib.cpp
index 4853991aea..d600f7c770 100644
--- a/src/vm/mscorlib.cpp
+++ b/src/vm/mscorlib.cpp
@@ -131,9 +131,14 @@
#include "windowsruntimebufferhelper.h"
#endif
-#endif // CROSSGEN_MSCORLIB
+#if defined(FEATURE_EVENTSOURCE_XPLAT)
+#define __EVENTTRACEPRIV_H__
+#include "eventtracepriv.h"
+#undef __EVENTTRACEPRIV_H__
+#endif //defined(FEATURE_EVENTSOURCE_XPLAT)
+#endif // CROSSGEN_MSCORLIB
#ifdef CROSSGEN_MSCORLIB