EventSource.WriteEventCore(Int32, Int32, EventSource+EventData*) Metoda

Definice

Důležité

Toto rozhraní API neodpovídá specifikaci CLS.

Vytvoří nové WriteEvent přetížení pomocí zadaného identifikátoru události a dat události.

protected:
 void WriteEventCore(int eventId, int eventDataCount, System::Diagnostics::Tracing::EventSource::EventData* data);
[System.CLSCompliant(false)]
[System.Security.SecurityCritical]
protected void WriteEventCore (int eventId, int eventDataCount, System.Diagnostics.Tracing.EventSource.EventData* data);
[System.CLSCompliant(false)]
protected void WriteEventCore (int eventId, int eventDataCount, System.Diagnostics.Tracing.EventSource.EventData* data);
[<System.CLSCompliant(false)>]
[<System.Security.SecurityCritical>]
member this.WriteEventCore : int * int * nativeptr<System.Diagnostics.Tracing.EventSource.EventData> -> unit
[<System.CLSCompliant(false)>]
member this.WriteEventCore : int * int * nativeptr<System.Diagnostics.Tracing.EventSource.EventData> -> unit

Parametry

eventId
Int32

Identifikátor události.

eventDataCount
Int32

Počet položek dat událostí.

data
EventSource.EventData

Struktura, která obsahuje data události.

Atributy

Poznámky

eventid by měla být větší než 0 nebo menší než 65535 nebo může v operaci dojít k chybám. Pokud dojde k chybám, můžete získat další informace o zdroji chyby kontrolou výstupního streamu ladicího programu, pokud máte k událostem spouštění procesu připojený ladicí program. Pokud máte naslouchací proces Trasování událostí pro Windows ve zdroji událostí, kde k chybě dochází, můžete také vyhledat chyby hlášené ve streamu událostí pro Windows.

Tato chráněná metoda umožňuje uživatelům definovat nová WriteEvent přetížení, která jsou rychlejší než poskytnutá přetížení. Vytvoření nového přetížení zahrnuje nebezpečný kód. Základním postupem je přiřaďte pole popisovačů dat událostí, které odpovídá počtu položek datové části. Pro každou položku datové části nastavte správnou velikost a hodnotu v poli dat události. Volání WriteEventCore s inicializovaným polem

Následující příklad ukazuje, jak přidat WriteEvent přetížení, které přijímá čtyři argumenty. Příkladem může být událost protokolování, která protokoluje řetězec a 3 celá čísla.

[Event(1)]
public void LogTime(string tag, int hour, int minute, int second)
{
    WriteEvent(1, tag, hour, minute, second);
}

Můžete to udělat bez volání WriteEventCore, ale bylo by to pomalejší, než je potřeba. Je to proto, že k určení, co dělat, používá pole a reflexe. Pokud je zaznamenáte vysokou rychlostí (> 1000 / s), může být vhodné vytvořit rychlý pomocník, jak je znázorněno v následujícím příkladu. Metoda zastíní existující WriteEvent. Původní kód volajícího (LogTime) se tedy ve skutečnosti nezmění, ale kompilátor jazyka C# použije specializovanější verzi, která bude rychlejší.

Pokud chcete zkompilovat nebezpečný kód, musíte zadat možnost kompilátoru /unsafe (možnosti kompilátoru jazyka C#).

class AnotherEventSource : EventSource {

    [NonEvent]
    public unsafe void WriteEvent(int eventId, string arg1, int arg2, int arg3, int arg4)
    {

        fixed (char* arg1Ptr = arg1)
        {
            EventData* dataDesc = stackalloc EventData[4];

            dataDesc[0].DataPointer = (IntPtr)arg1Ptr;
            dataDesc[0].Size = (arg1.Length + 1) * 2; // Size in bytes, including a null terminator.
            dataDesc[1].DataPointer = (IntPtr)(&arg2);
            dataDesc[1].Size = 4;
            dataDesc[2].DataPointer = (IntPtr)(&arg3);
            dataDesc[2].Size = 4;
            dataDesc[3].DataPointer = (IntPtr)(&arg4);
            dataDesc[3].Size = 4;

            WriteEventCore(eventId, 4, dataDesc);
        }
    }
}

Toto jsou očekávané velikosti a kódování dat pro standardní serializovatelné typy:

// bool arg
int temp = arg ? 1 : 0;
desc.DataPointer = (IntPtr)(&temp);
desc.Size = 4;

// byte arg
desc.DataPointer = (IntPtr)(&arg);
desc.Size = 1;

// sbyte arg
desc.DataPointer = (IntPtr)(&arg);
desc.Size = 1;

// char arg
desc.DataPointer = (IntPtr)(&arg);
desc.Size = 2;

// short arg
desc.DataPointer = (IntPtr)(&arg);
desc.Size = 2;

// ushort arg
desc.DataPointer = (IntPtr)(&arg);
desc.Size = 2;

// int arg
desc.DataPointer = (IntPtr)(&arg);
desc.Size = 4;

// uint arg
desc.DataPointer = (IntPtr)(&arg);
desc.Size = 4;

// long arg
desc.DataPointer = (IntPtr)(&arg);
desc.Size = 8;

// ulong arg
desc.DataPointer = (IntPtr)(&arg);
desc.Size = 8;

// float arg
desc.DataPointer = (IntPtr)(&arg);
desc.Size = 4;

// double arg
desc.DataPointer = (IntPtr)(&arg);
desc.Size = 8;

// decimal arg
desc.DataPointer = (IntPtr)(&arg);
desc.Size = 16;

// Guid arg
desc.DataPointer = (IntPtr)(&arg);
desc.Size = 16;

// IntPtr arg
desc.DataPointer = (IntPtr)(&arg);
desc.Size = IntPtr.Size;

// UIntPtr arg
desc.DataPointer = (IntPtr)(&arg);
desc.Size = UIntPtr.Size;

// DateTime arg
long fileTime = arg.ToUniversalTime() > new DateTime(1601, 1, 1) ? arg.ToFileTimeUtc() : 0;
desc.DataPointer = (IntPtr)(&fileTime);
desc.Size = 8;

// string arg
fixed(char* ptr = arg)
{
    desc.DataPointer = (IntPtr)ptr;
    // strings use 2 byte per char UTF16 encoding and a null terminator at the end
    // only strings without embedded null characters are supported
    desc.Size = (arg.Length + 1) * 2;
}

// byte[] arg
// This one is encoded using two adjacent EventData elements.
fixed(byte* ptr = arg)
{
    int length = arg.Length;
    desc[i].DataPointer = (IntPtr)(&length);
    desc[i].Size = 4;
    desc[i + 1].DataPointer = (IntPtr)ptr;
    desc[i + 1].Size = arg.Length;
}

// enums should be converted to their underlying type and then serialized
// as byte, short, or int.

Platí pro