mirror of https://github.com/tongzx/nt5src
You can not select more than 25 topics
Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
232 lines
5.1 KiB
232 lines
5.1 KiB
/*++
|
|
|
|
Copyright (c) 1998-2001 Microsoft Corporation
|
|
|
|
Module Name:
|
|
|
|
tracelog.cxx
|
|
|
|
Abstract:
|
|
|
|
This module implements a trace log.
|
|
|
|
A trace log is a fast, in-memory, thread safe activity log useful
|
|
for debugging certain classes of problems. They are especially useful
|
|
when debugging reference count bugs.
|
|
|
|
Author:
|
|
|
|
Keith Moore (keithmo) 10-Jun-1998
|
|
|
|
Revision History:
|
|
|
|
--*/
|
|
|
|
|
|
#include "precomp.h"
|
|
|
|
|
|
#if REFERENCE_DEBUG
|
|
|
|
|
|
//
|
|
// Environmental stuff.
|
|
//
|
|
|
|
#define MY_ALLOC_MEM(cb) \
|
|
(PVOID)UL_ALLOCATE_POOL( \
|
|
NonPagedPool, \
|
|
(ULONG)(cb), \
|
|
UL_DEBUG_POOL_TAG \
|
|
)
|
|
|
|
#define MY_FREE_MEM(ptr) \
|
|
UL_FREE_POOL( \
|
|
(PVOID)(ptr), \
|
|
UL_DEBUG_POOL_TAG \
|
|
)
|
|
|
|
#define MY_ASSERT(expr) ASSERT(expr)
|
|
|
|
|
|
/***************************************************************************++
|
|
|
|
Routine Description:
|
|
|
|
Creates a new (empty) trace log buffer.
|
|
|
|
Arguments:
|
|
|
|
LogSize - Supplies the number of entries in the log.
|
|
|
|
ExtraBytesInHeader - Supplies the number of extra bytes to include
|
|
in the log header. This is useful for adding application-specific
|
|
data to the log.
|
|
|
|
EntrySize - Supplies the size (in bytes) of each entry.
|
|
|
|
Return Value:
|
|
|
|
PTRACE_LOG - Pointer to the newly created log if successful,
|
|
NULL otherwise.
|
|
|
|
--***************************************************************************/
|
|
PTRACE_LOG
|
|
CreateTraceLog(
|
|
IN ULONG TypeSignature,
|
|
IN ULONG LogSize,
|
|
IN ULONG ExtraBytesInHeader,
|
|
IN ULONG EntrySize
|
|
)
|
|
{
|
|
ULONG totalSize;
|
|
PTRACE_LOG pLog;
|
|
|
|
//
|
|
// Sanity check the parameters.
|
|
//
|
|
|
|
MY_ASSERT( LogSize > 0 );
|
|
MY_ASSERT( EntrySize > 0 );
|
|
MY_ASSERT( ( EntrySize & 3 ) == 0 );
|
|
|
|
//
|
|
// Allocate & initialize the log structure.
|
|
//
|
|
|
|
totalSize = sizeof(*pLog) + ( LogSize * EntrySize ) + ExtraBytesInHeader;
|
|
MY_ASSERT( totalSize > 0 );
|
|
|
|
pLog = (PTRACE_LOG)MY_ALLOC_MEM( totalSize );
|
|
|
|
//
|
|
// Initialize it.
|
|
//
|
|
|
|
if (pLog != NULL)
|
|
{
|
|
RtlZeroMemory( pLog, totalSize );
|
|
|
|
pLog->Signature = TRACE_LOG_SIGNATURE;
|
|
pLog->TypeSignature = TypeSignature;
|
|
pLog->LogSize = LogSize;
|
|
pLog->NextEntry = -1;
|
|
pLog->EntrySize = EntrySize;
|
|
pLog->pLogBuffer = (PUCHAR)( pLog + 1 ) + ExtraBytesInHeader;
|
|
}
|
|
|
|
return pLog;
|
|
|
|
} // CreateTraceLog
|
|
|
|
|
|
/***************************************************************************++
|
|
|
|
Routine Description:
|
|
|
|
Destroys a trace log buffer created with CreateTraceLog().
|
|
|
|
Arguments:
|
|
|
|
pLog - Supplies the trace log buffer to destroy.
|
|
|
|
--***************************************************************************/
|
|
VOID
|
|
DestroyTraceLog(
|
|
IN PTRACE_LOG pLog
|
|
)
|
|
{
|
|
if (pLog != NULL)
|
|
{
|
|
MY_ASSERT( pLog->Signature == TRACE_LOG_SIGNATURE );
|
|
|
|
pLog->Signature = TRACE_LOG_SIGNATURE_X;
|
|
MY_FREE_MEM( pLog );
|
|
}
|
|
|
|
} // DestroyTraceLog
|
|
|
|
|
|
/***************************************************************************++
|
|
|
|
Routine Description:
|
|
|
|
Writes a new entry to the specified trace log.
|
|
|
|
Arguments:
|
|
|
|
pLog - Supplies the log to write to.
|
|
|
|
pEntry - Supplies a pointer to the data to write. This buffer is
|
|
assumed to be pLog->EntrySize bytes long.
|
|
|
|
Return Value:
|
|
|
|
LONGLONG - Index of the newly written entry within the tracelog
|
|
(used by the OwnerRef tracelog).
|
|
|
|
--***************************************************************************/
|
|
LONGLONG
|
|
WriteTraceLog(
|
|
IN PTRACE_LOG pLog,
|
|
IN PVOID pEntry
|
|
)
|
|
{
|
|
PUCHAR pTarget;
|
|
ULONGLONG index = -1;
|
|
|
|
if (pLog != NULL)
|
|
{
|
|
MY_ASSERT( pLog->Signature == TRACE_LOG_SIGNATURE );
|
|
MY_ASSERT( pEntry != NULL );
|
|
|
|
//
|
|
// Find the next slot, copy the entry to the slot.
|
|
//
|
|
|
|
index = (ULONGLONG) UlInterlockedIncrement64( &pLog->NextEntry );
|
|
|
|
pTarget = ( (index % pLog->LogSize) * pLog->EntrySize )
|
|
+ pLog->pLogBuffer;
|
|
|
|
RtlCopyMemory( pTarget, pEntry, pLog->EntrySize );
|
|
}
|
|
|
|
return index;
|
|
} // WriteTraceLog
|
|
|
|
|
|
/***************************************************************************++
|
|
|
|
Routine Description:
|
|
|
|
Resets the specified trace log such that the next entry written
|
|
will be placed at the beginning of the log.
|
|
|
|
Arguments:
|
|
|
|
pLog - Supplies the trace log to reset.
|
|
|
|
--***************************************************************************/
|
|
VOID
|
|
ResetTraceLog(
|
|
IN PTRACE_LOG pLog
|
|
)
|
|
{
|
|
if (pLog != NULL)
|
|
{
|
|
MY_ASSERT( pLog->Signature == TRACE_LOG_SIGNATURE );
|
|
|
|
RtlZeroMemory(
|
|
( pLog + 1 ),
|
|
pLog->LogSize * pLog->EntrySize
|
|
);
|
|
|
|
pLog->NextEntry = -1;
|
|
}
|
|
|
|
} // ResetTraceLog
|
|
|
|
|
|
#endif // REFERENCE_DEBUG
|
|
|