Leaked source code of windows server 2003
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.
 
 
 
 
 
 

1937 lines
51 KiB

/*++
Copyright (c) 1990 Microsoft Corporation
Module Name:
inetdbg.c
Abstract:
This function contains the default ntsd debugger extensions
Author:
Mark Lucovsky (markl) 09-Apr-1991
Revision History:
--*/
#ifdef DBG
#undef DBG
#endif
#define dllexp
#define CALL_STACK_BUF_SIZE 1024
//
// To obtain the private & protected members of C++ class,
// let me fake the "private" keyword
//
# define private public
# define protected public
#define INCL_INETSRV_INCS
#include <tigris.hxx>
#include "smtpcli.h"
#include <ntsdexts.h>
#include "nntpdbgp.h"
extern "C" {
#if 0
void __cdecl main( void )
{
;
}
#endif
}
//
// Globals that we have to have because we included others' headers
//
CShareLockNH CNewsGroupCore::m_rglock[GROUP_LOCK_ARRAY_SIZE];
//DECLARE_DEBUG_PRINTS_OBJECT( );
NTSD_EXTENSION_APIS ExtensionApis;
HANDLE ExtensionCurrentProcess;
// globals
char g_szBuffer [1024]; // temp buffer for misc stuff
VOID
PrintUsage(
VOID
);
VOID
PrintSystemTime(
FILETIME* pftTime
);
VOID
PrintString(
LPSTR lp1,
LPSTR lp2
);
VOID
DbgPrintInstance(
NNTP_SERVER_INSTANCE* pInstance
);
VOID
DbgPrintNewstree(
CNewsTree* ptree,
DWORD nGroups
);
CNewsGroup*
DbgPrintNewsgroup(
CNewsGroup * pSrcGroup
);
CNNTPVRoot*
DbgPrintVRoot(
CNNTPVRoot *pDestGroup
);
VOID
DbgPrintVRootList(
CNNTPVRoot* pFirstVRoot,
DWORD nVRoots
);
VOID
DbgPrintDebugVRootList(
CNNTPVRoot* pFirstVRoot,
DWORD nVRoots
);
void
DbgPrintVRootTable(
CNNTPVRootTable * pVRTable
);
VOID
DbgDumpPool(
CSmtpClientPool* pSCPool
);
VOID
DbgDumpFeedBlock(
PFEED_BLOCK feedBlock
);
VOID
DbgDumpFeedList(
CFeedList* pSrcFeedList,
CFeedList* pDstFeedList
);
VOID
DbgDumpCPool(CPool* pCPool, DWORD dwSignature, LPCSTR symbol);
VOID
SkipArgument( LPSTR* ppArg )
{
// skip the arg and the spaces after
while( *(*ppArg) != ' ' ) (*ppArg)++;
while( *(*ppArg) == ' ' ) (*ppArg)++;
}
//
// Here and elsewhere we use "nntpsvc" prefix in GetExpression() calls.
//
#define DEBUG_PREFIX "&nntpsvc!"
#define DumpDword( symbol ) \
{ \
DWORD dw = GetExpression( DEBUG_PREFIX symbol ); \
DWORD dwValue = 0; \
\
if ( dw ) \
{ \
if ( ReadMemory( (LPVOID) dw, \
&dwValue, \
sizeof(dwValue), \
NULL )) \
{ \
dprintf( "\t" symbol " = %8d (0x%8lx)\n", \
dwValue, \
dwValue ); \
} \
} \
}
#define DumpCPool( symbol, signature ) \
{ \
DbgDumpCPool((CPool*)GetExpression(DEBUG_PREFIX symbol), signature, symbol ); \
}
//
// util functions
//
VOID
CopyUnicodeStringIntoAscii(
IN LPSTR AsciiString,
IN LPWSTR UnicodeString
)
{
while ( (*AsciiString++ = (CHAR)*UnicodeString++) != '\0');
} // CopyUnicodeStringIntoAscii
DECLARE_API( help )
{
INIT_API();
PrintUsage();
}
DECLARE_API( cpool )
{
CPool* pCPool;
INIT_API();
while (*lpArgumentString == ' ')
lpArgumentString++;
if ( !*lpArgumentString )
{
PrintUsage();
return;
}
//
// Get the address of the instance
//
pCPool = (CPool*)GetExpression( lpArgumentString );
if ( !pCPool )
{
dprintf( "nntpdbg: Unable to evaluate \"%s\"\n", lpArgumentString );
return;
}
DbgDumpCPool(pCPool, 0, NULL);
}
DECLARE_API( cpools )
{
INIT_API();
//
// Dump Nntpsvc cpools
//
dprintf("Nntpsvc Cpools:\n");
DumpCPool("CArticle__gArticlePool",ARTICLE_SIGNATURE);
DumpCPool("CCIOAllocator__IOPool",CIO_SIGNATURE) ;
DumpCPool("CFeed__gFeedPool",FEED_SIGNATURE) ;
DumpCPool("CChannel__gChannelPool",CHANNEL_SIGNATURE) ;
DumpCPool("CSessionSocket__gSocketAllocator",SESSION_SOCKET_SIGNATURE) ;
DumpCPool("CSessionState__gStatePool",SESSION_STATE_SIGNATURE) ;
DumpCPool("CXoverIndex__gCacheAllocator",1) ;
DumpCPool("CXoverIndex__gXoverIndexAllocator",1) ;
}
DECLARE_API( instance )
/*++
Routine Description:
This function is called as an NTSD extension to format and dump
an object attributes structure.
Arguments:
hCurrentProcess - Supplies a handle to the current process (at the
time the extension was called).
hCurrentThread - Supplies a handle to the current thread (at the
time the extension was called).
CurrentPc - Supplies the current pc at the time the extension is
called.
lpExtensionApis - Supplies the address of the functions callable
by this extension.
lpArgumentString - Supplies the asciiz string that describes the
ansi string to be dumped.
Return Value:
None.
--*/
{
NNTP_SERVER_INSTANCE *pSrcInst, *pDstInst;
DWORD cbInst = sizeof(NNTP_SERVER_INSTANCE);
INIT_API();
while (*lpArgumentString == ' ')
lpArgumentString++;
if ( !*lpArgumentString )
{
PrintUsage();
return;
}
//
// Get the address of the instance
//
pSrcInst = (NNTP_SERVER_INSTANCE*)GetExpression( lpArgumentString );
if ( !pSrcInst )
{
dprintf( "nntpdbg: Unable to evaluate \"%s\"\n", lpArgumentString );
return;
}
dprintf("Instance object is 0x%p\n", pSrcInst);
//
// Allocate memory in our address space so we can read data from the debuggee's address space
//
pDstInst = (NNTP_SERVER_INSTANCE*) DbgAlloc( cbInst );
if( !pDstInst )
{
dprintf( "nntpdbg: Unable to allocate memory \n");
return;
}
if( !ReadMemory( pSrcInst, pDstInst, cbInst, NULL ) )
{
dprintf("Could not get data at 0x%x\n", pSrcInst);
DbgFree( pDstInst );
return;
}
//
// Dump the the server instance
//
DbgPrintInstance( pDstInst );
DbgFree( pDstInst );
}
DECLARE_API( newstree )
/*++
Routine Description:
This function is called as an NTSD extension to format and dump
an object attributes structure.
Arguments:
hCurrentProcess - Supplies a handle to the current process (at the
time the extension was called).
hCurrentThread - Supplies a handle to the current thread (at the
time the extension was called).
CurrentPc - Supplies the current pc at the time the extension is
called.
lpExtensionApis - Supplies the address of the functions callable
by this extension.
lpArgumentString - Supplies the asciiz string that describes the
ansi string to be dumped.
Return Value:
None.
--*/
{
CNewsTree *pSrcTree, *pDstTree;
DWORD cbTree = sizeof(CNewsTree);
DWORD nGroups = 0;
INIT_API();
while (*lpArgumentString == ' ')
lpArgumentString++;
if ( !*lpArgumentString )
{
PrintUsage();
return;
}
//
// Get the address of the global newstree pointer
//
pSrcTree = (CNewsTree*)GetExpression( lpArgumentString );
if ( !pSrcTree )
{
dprintf( "nntpdbg: Unable to evaluate \"%s\"\n", lpArgumentString );
return;
}
// same as doing pSrcTree = *ppSrcTree !!
dprintf("Newstree object is 0x%p\n", pSrcTree);
SkipArgument( &lpArgumentString );
nGroups = atoi( lpArgumentString );
//
// Allocate memory in our address space so we can read data from the debuggee's address space
//
pDstTree = (CNewsTree*) DbgAlloc( cbTree );
if( !pDstTree )
{
dprintf( "nntpdbg: Unable to allocate memory \n");
return;
}
if( !ReadMemory( pSrcTree, pDstTree, cbTree, NULL ) )
{
dprintf("Could not get data at 0x%x\n", pSrcTree);
DbgFree( pDstTree );
return;
}
//
// Dump the newstree
//
DbgPrintNewstree( pDstTree, nGroups );
DbgFree( pDstTree );
}
DECLARE_API( vrootlist )
/*++
Routine Description:
This function is called as an NTSD extension to format and dump
an object attributes structure.
Arguments:
hCurrentProcess - Supplies a handle to the current process (at the
time the extension was called).
hCurrentThread - Supplies a handle to the current thread (at the
time the extension was called).
CurrentPc - Supplies the current pc at the time the extension is
called.
lpExtensionApis - Supplies the address of the functions callable
by this extension.
lpArgumentString - Supplies the asciiz string that describes the
ansi string to be dumped.
Return Value:
None.
--*/
{
CNNTPVRoot *pFirstVRoot;
DWORD nVRoots = 0;
INIT_API();
while (*lpArgumentString == ' ')
lpArgumentString++;
if ( !*lpArgumentString )
{
PrintUsage();
return;
}
//
// Get the address of the first vroot
//
pFirstVRoot = (CNNTPVRoot*)GetExpression( lpArgumentString );
if ( !pFirstVRoot )
{
dprintf( "nntpdbg: Unable to evaluate \"%s\"\n", lpArgumentString );
return;
}
SkipArgument( &lpArgumentString );
nVRoots = atoi( lpArgumentString );
//
// Dump the list
//
DbgPrintVRootList( pFirstVRoot, nVRoots );
}
DECLARE_API( newsgroup )
/*++
Routine Description:
This function is called as an NTSD extension to format and dump
an object attributes structure.
Arguments:
hCurrentProcess - Supplies a handle to the current process (at the
time the extension was called).
hCurrentThread - Supplies a handle to the current thread (at the
time the extension was called).
CurrentPc - Supplies the current pc at the time the extension is
called.
lpExtensionApis - Supplies the address of the functions callable
by this extension.
lpArgumentString - Supplies the asciiz string that describes the
ansi string to be dumped.
Return Value:
None.
--*/
{
CNewsGroup* pSrcGroup;
INIT_API();
while (*lpArgumentString == ' ')
lpArgumentString++;
if ( !*lpArgumentString )
{
PrintUsage();
return;
}
//
// Treat the argument as the address of a CNewsGroup struct
// NOTE: pSrcGroup is an address in the debuggee's address space !
//
pSrcGroup = (CNewsGroup*)GetExpression( lpArgumentString );
if ( !pSrcGroup )
{
dprintf( "nntpdbg: Unable to evaluate \"%s\"\n", lpArgumentString );
return;
}
//
// Dump the CNewsGroup object
//
DbgPrintNewsgroup( pSrcGroup );
}
DECLARE_API( vroot )
/*++
Routine Description:
This function is called as an NTSD extension to format and dump
an object attributes structure.
Arguments:
hCurrentProcess - Supplies a handle to the current process (at the
time the extension was called).
hCurrentThread - Supplies a handle to the current thread (at the
time the extension was called).
CurrentPc - Supplies the current pc at the time the extension is
called.
lpExtensionApis - Supplies the address of the functions callable
by this extension.
lpArgumentString - Supplies the asciiz string that describes the
ansi string to be dumped.
Return Value:
None.
--*/
{
CNNTPVRoot* pVroot = NULL;
INIT_API();
while (*lpArgumentString == ' ')
lpArgumentString++;
if ( !*lpArgumentString )
{
PrintUsage();
return;
}
//
// Treat the argument as the address of a CNNTPVRoot struct
// NOTE: pVroot is an address in the debuggee's address space !
//
pVroot = (CNNTPVRoot*)GetExpression( lpArgumentString );
if ( !pVroot )
{
dprintf( "nntpdbg: Unable to evaluate \"%s\"\n", lpArgumentString );
return;
}
//
// Dump the CNNTPVRoot object
//
DbgPrintVRoot( pVroot );
}
DECLARE_API( vrtable )
/*++
Routine Description:
This function is called as an NTSD extension to format and dump
an object attributes structure.
Arguments:
hCurrentProcess - Supplies a handle to the current process (at the
time the extension was called).
hCurrentThread - Supplies a handle to the current thread (at the
time the extension was called).
CurrentPc - Supplies the current pc at the time the extension is
called.
lpExtensionApis - Supplies the address of the functions callable
by this extension.
lpArgumentString - Supplies the asciiz string that describes the
ansi string to be dumped.
Return Value:
None.
--*/
{
CNNTPVRootTable* pVRTable = NULL;
INIT_API();
while (*lpArgumentString == ' ')
lpArgumentString++;
if ( !*lpArgumentString )
{
PrintUsage();
return;
}
//
// Treat the argument as the address of a CNNTPVRootTable struct
// NOTE: pVRTable is an address in the debuggee's address space !
//
pVRTable = (CNNTPVRootTable*)GetExpression( lpArgumentString );
if ( !pVRTable )
{
dprintf( "nntpdbg: Unable to evaluate \"%s\"\n", lpArgumentString );
return;
}
//
// Dump the CNNTPVRootTable object
//
DbgPrintVRootTable( pVRTable );
}
DECLARE_API( sockets )
/*++
Routine Description:
This function is called as an NTSD extension to format and dump
an object attributes structure.
Arguments:
hCurrentProcess - Supplies a handle to the current process (at the
time the extension was called).
hCurrentThread - Supplies a handle to the current thread (at the
time the extension was called).
CurrentPc - Supplies the current pc at the time the extension is
called.
lpExtensionApis - Supplies the address of the functions callable
by this extension.
lpArgumentString - Supplies the asciiz string that describes the
ansi string to be dumped.
Return Value:
None.
--*/
{
CSessionSocket *pSrcSocket, *pDstSocket;
DWORD cbSocket = sizeof(CSessionSocket);
INIT_API();
while (*lpArgumentString == ' ')
lpArgumentString++;
if ( !*lpArgumentString )
{
PrintUsage();
return;
}
//
// Get the address of the socket obj
//
pSrcSocket = (CSessionSocket*)GetExpression( lpArgumentString );
if ( !pSrcSocket )
{
dprintf( "nntpdbg: Unable to evaluate \"%s\"\n", lpArgumentString );
return;
}
dprintf("Socket object is 0x%p\n", pSrcSocket);
//
// Allocate memory in our address space so we can read data from the debuggee's address space
//
pDstSocket = (CSessionSocket*) DbgAlloc( cbSocket );
if( !pDstSocket )
{
dprintf( "nntpdbg: Unable to allocate memory \n");
return;
}
if( !ReadMemory( pSrcSocket, pDstSocket, cbSocket, NULL ) )
{
dprintf("Could not get data at 0x%x\n", pSrcSocket);
DbgFree( pDstSocket );
return;
}
//
// Dump the socket obj
//
dprintf(" ========== socket object =========== \n");
dprintf(" Prev = 0x%p Next = 0x%p \n", pDstSocket->m_pPrev, pDstSocket->m_pPrev);
dprintf(" Sink = 0x%p \n", pDstSocket->m_pSink );
dprintf(" Port = 0x%08lx \n", pDstSocket->m_nntpPort );
dprintf(" ClientContext = 0x%p \n", pDstSocket->m_context );
dprintf(" ========== socket object =========== \n");
DbgFree( pDstSocket );
}
DECLARE_API( smtp )
/*++
Routine Description:
This function is called as an NTSD extension to format and dump
an object attributes structure.
Arguments:
hCurrentProcess - Supplies a handle to the current process (at the
time the extension was called).
hCurrentThread - Supplies a handle to the current thread (at the
time the extension was called).
CurrentPc - Supplies the current pc at the time the extension is
called.
lpExtensionApis - Supplies the address of the functions callable
by this extension.
lpArgumentString - Supplies the asciiz string that describes the
ansi string to be dumped.
Return Value:
None.
--*/
{
CSmtpClientPool *pSrcSCPool, *pDstSCPool;
DWORD cbSCPool = sizeof(CSmtpClientPool);
INIT_API();
//
// Get the address of the global newstree pointer
//
pSrcSCPool = (CSmtpClientPool*)GetExpression( DEBUG_PREFIX "g_SCPool" );
if ( !pSrcSCPool )
{
dprintf( "nntpdbg: Unable to evaluate \"%s\"\n", DEBUG_PREFIX "g_SCPool" );
return;
}
//
// Allocate memory in our address space so we can read data from the debuggee's address space
//
pDstSCPool = (CSmtpClientPool*) DbgAlloc( cbSCPool );
if( !pDstSCPool )
{
dprintf( "nntpdbg: Unable to allocate memory \n");
return;
}
if( !ReadMemory( pSrcSCPool, pDstSCPool, cbSCPool, NULL ) )
{
dprintf("Could not get data at 0x%x\n", pSrcSCPool);
DbgFree( pDstSCPool );
return;
}
//
// Dump the smtp conx cache
//
DbgDumpPool( pDstSCPool );
DbgFree( pDstSCPool );
}
DECLARE_API( feedlist )
/*++
Routine Description:
This function is called as an NTSD extension to format and dump
an object attributes structure.
Arguments:
hCurrentProcess - Supplies a handle to the current process (at the
time the extension was called).
hCurrentThread - Supplies a handle to the current thread (at the
time the extension was called).
CurrentPc - Supplies the current pc at the time the extension is
called.
lpExtensionApis - Supplies the address of the functions callable
by this extension.
lpArgumentString - Supplies the asciiz string that describes the
ansi string to be dumped.
Return Value:
None.
--*/
{
CFeedList* pSrcFeedList;
CFeedList* pDstFeedList;
DWORD cbFeedList = sizeof(CFeedList);
INIT_API();
while (*lpArgumentString == ' ')
lpArgumentString++;
if ( !*lpArgumentString )
{
PrintUsage();
return;
}
//
// Get the ActiveFeeds global
//
pSrcFeedList = (CFeedList*)GetExpression( lpArgumentString );
if ( !pSrcFeedList )
{
dprintf( "nntpdbg: Unable to evaluate \"%s\"\n", lpArgumentString );
return;
}
pDstFeedList = (CFeedList*)DbgAlloc( cbFeedList );
if( !pDstFeedList )
{
dprintf("nntpdbg: Unable to allocate memory\n");
return;
}
//
// Dump the feedblock list
//
if( !ReadMemory( pSrcFeedList, pDstFeedList, cbFeedList, NULL ) )
{
dprintf("nntpdbg: Unable to read memory at 0x%p\n", pSrcFeedList );
DbgFree( pDstFeedList );
return;
}
DbgDumpFeedList( pSrcFeedList, pDstFeedList );
DbgFree( pDstFeedList );
}
DECLARE_API( feed )
/*++
Routine Description:
This function is called as an NTSD extension to format and dump
an object attributes structure.
Arguments:
hCurrentProcess - Supplies a handle to the current process (at the
time the extension was called).
hCurrentThread - Supplies a handle to the current thread (at the
time the extension was called).
CurrentPc - Supplies the current pc at the time the extension is
called.
lpExtensionApis - Supplies the address of the functions callable
by this extension.
lpArgumentString - Supplies the asciiz string that describes the
ansi string to be dumped.
Return Value:
None.
--*/
{
PFEED_BLOCK feedBlock;
INIT_API();
while (*lpArgumentString == ' ')
lpArgumentString++;
if ( !*lpArgumentString )
{
PrintUsage();
return;
}
//
// Treat the argument as the address of a FEED_BLOCK
//
feedBlock = (PFEED_BLOCK)GetExpression( lpArgumentString );
if ( !feedBlock )
{
dprintf( "nntpdbg: Unable to evaluate \"%s\"\n", lpArgumentString );
return;
}
DbgDumpFeedBlock( feedBlock );
}
DECLARE_API( rf )
/*++
Routine Description:
This function is called as an NTSD extension to format and dump
an object attributes structure.
Arguments:
hCurrentProcess - Supplies a handle to the current process (at the
time the extension was called).
hCurrentThread - Supplies a handle to the current thread (at the
time the extension was called).
CurrentPc - Supplies the current pc at the time the extension is
called.
lpExtensionApis - Supplies the address of the functions callable
by this extension.
lpArgumentString - Supplies the asciiz string that describes the
ansi string to be dumped.
Return Value:
None.
--*/
{
INIT_API();
PLONG pcCallStack = NULL;
LONG cCallStack = 0;
PVOID pvCallStack = NULL;
CHAR** ppchCallStack = NULL;
CHAR** ppchReal = NULL;
LPVOID lpvCallStack = NULL;
LPVOID lpvBuffer = NULL;
//
// Get the number of buffers
//
pcCallStack = (PLONG)GetExpression( "exstrace!g_iCallStack" );
if ( !pcCallStack )
{
dprintf( "nntpdbg: Unable to evaluate \"exstrace!g_cCallStack\"\n" );
return;
}
if ( !ReadMemory( pcCallStack, &cCallStack, sizeof(LONG), NULL ) ) {
dprintf( "nntpdbg: Could not read g_cCallStack\n" );
return;
}
//
// Get pointer to buffer
//
pvCallStack = (CHAR**)GetExpression( "exstrace!g_ppchCallStack" );
if ( !pvCallStack )
{
dprintf( "nntpdbg: Unable to evaluate \"exstrace!g_ppchCallStack\"\n" );
return;
}
if ( !ReadMemory( pvCallStack, &ppchCallStack, sizeof(CHAR**), NULL ) ) {
dprintf( "nntpdbg: Could not read g_ppchCallStack\n" );
return;
}
lpvCallStack = DbgAlloc( sizeof(CHAR*) * cCallStack );
if ( !lpvCallStack ) {
dprintf( "nntpdbg: Unable to allocate memory\n" );
return;
}
if ( !ReadMemory( ppchCallStack, lpvCallStack, sizeof(CHAR*)*cCallStack, NULL ) ) {
dprintf( "nntpdbg: Could not get data at 0x%x\n", ppchCallStack );
DbgFree( lpvCallStack );
return;
} else
ppchReal = (CHAR**)lpvCallStack;
lpvBuffer = DbgAlloc( CALL_STACK_BUF_SIZE );
if ( !lpvBuffer ) {
DbgFree( lpvCallStack );
dprintf( "nntpdbg: Unable to allocate memory\n" );
return;
}
for ( LONG i = 0; i < cCallStack; i++ ) {
if( ppchReal[i] ) {
if ( !ReadMemory( ppchReal[i], lpvBuffer, CALL_STACK_BUF_SIZE, NULL ) ) {
dprintf( "nntpdbg: Could not get data at 0x%x\n", ppchReal[i] );
DbgFree( lpvCallStack );
DbgFree( lpvBuffer );
return;
}
*(PBYTE(lpvBuffer)+CALL_STACK_BUF_SIZE-1) = 0;
dprintf("%s\n", (PCHAR)lpvBuffer );
}
}
DbgFree( lpvBuffer );
DbgFree( lpvCallStack );
}
VOID
PrintUsage(
VOID
)
{
dprintf("\n\nMicrosoft Internet News Server debugging extension, Version 2.0\n\n");
dprintf("!vroot <address> - Dump nntp virtual root\n");
dprintf("!vrtable <address> - Dump nntp virtual root table\n");
dprintf("!vrootlist <address> <n> - Dump the first <n> vroots in the table\n");
dprintf("!cpool <address> - Dump CPool at <address>\n");
dprintf("!cpools - Dump nntpsvc cpools\n");
dprintf("!instance <address> - Dump instance at <address> \n");
dprintf("!newstree <address> <n>- Dump first <n> newsgroups in newstree at <address> \n");
dprintf("!newsgroup <address> - Dump newsgroup at <address> \n");
dprintf("!sockets <address> - Dump socket at <address> \n");
dprintf("!smtp - Dump smtp conx cache \n");
dprintf("!feedlist <address> - Dump active feedblock list at <address> \n");
dprintf("!feed <address> - Dump feedblock at <address> \n");
dprintf("!rf - Dump all randfail call stacks \n" );
dprintf("!help - Usage \n\n");
}
VOID
DbgPrintInstance(
NNTP_SERVER_INSTANCE* pInst
)
/*++
Routine Description:
Dump the first n newsgroup objects in the newstree.
NOTE: Assumed that the pointer passed is in OUR address space
--*/
{
dprintf("\n\n======== Begin Instance dump =========\n");
if ( NNTP_SERVER_INSTANCE_SIGNATURE == pInst->m_signature ) {
switch( pInst->m_dwServerState ) {
case MD_SERVER_STATE_STARTED:
dprintf("Server state is started\n");
break;
case MD_SERVER_STATE_STARTING:
dprintf("Server state is starting\n");
break;
case MD_SERVER_STATE_STOPPING:
dprintf("Server state is stopping\n" );
break;
case MD_SERVER_STATE_STOPPED:
dprintf("Server state is stopped\n" );
break;
case MD_SERVER_STATE_PAUSING:
dprintf("Server state is pausing\n" );
break;
case MD_SERVER_STATE_PAUSED:
dprintf("Server state is paused\n" );
break;
case MD_SERVER_STATE_CONTINUING:
dprintf("Server state is continuing\n" );
break;
}
dprintf("Server has %d references\n", pInst->m_reference );
dprintf("Instance id is %d\n", pInst->QueryInstanceId() );
dprintf("Default port is %d\n", pInst->m_sDefaultPort );
pInst->m_fAddedToServerInstanceList ?
dprintf("Added to server instance list\n" ) :
dprintf("NOT added to server instance list\n" );
dprintf("It has %d connections now\n", pInst->m_dwCurrentConnections );
dprintf("Owning service is 0x%p\n", pInst->m_Service );
dprintf("Previous instance 0x%p\n",
CONTAINING_RECORD( pInst->m_InstanceListEntry.Flink,
IIS_SERVER_INSTANCE,
m_InstanceListEntry ) );
dprintf("Next instance 0x%p\n",
CONTAINING_RECORD( pInst->m_InstanceListEntry.Blink,
IIS_SERVER_INSTANCE,
m_InstanceListEntry ) );
pInst->m_ServiceStartCalled ?
dprintf("Start method called\n") :
dprintf("Start method NOT called\n" );
dprintf("Article table pointer 0x%p\n", pInst->m_pArticleTable );
dprintf("History table pointer 0x%p\n", pInst->m_pHistoryTable );
dprintf("Xover table pointer 0x%p\n", pInst->m_pXoverTable );
dprintf("Xover cache is 0x%p\n", pInst->m_pXCache );
dprintf("Expire object is 0x%p\n", pInst->m_pExpireObject );
dprintf("VRoot table is 0x%p\n", pInst->m_pVRootTable );
dprintf("Dirnot object is 0x%p\n", pInst->m_pDirNot );
dprintf("Server object is 0x%p\n", pInst->m_pNntpServerObject );
dprintf("Wrapper( for posting lib) is 0x%p\n", pInst->m_pInstanceWrapper );
dprintf("Wrapper( for newstree lib) is 0x%p\n", pInst->m_pInstanceWrapperEx );
dprintf("SEO router 0x%p\n", pInst->m_pSEORouter );
dprintf("Newstree is 0x%p\n", pInst->m_pTree );
pInst->m_fAllowClientPosts ?
dprintf("Server allows client posts\n") :
dprintf("Server doesn't allow client posts\n" );
pInst->m_fAllowFeedPosts ?
dprintf("Server allows feed posts\n" ) :
dprintf("Server doesn't allow feed posts\n" );
pInst->m_fAllowControlMessages ?
dprintf("Server allows control messages\n" ) :
dprintf("Server doesn't allow control messages\n" );
pInst->m_fNewnewsAllowed ?
dprintf("Newnews allowed\n" ) :
dprintf("Newnews not allowed\n" );
dprintf("Client post hard limit %d\n", pInst->m_cbHardLimit );
dprintf("Client post soft limit %d\n", pInst->m_cbSoftLimit );
dprintf("Feed hard limit %d\n", pInst->m_cbFeedHardLimit );
dprintf("Feed soft limit %d\n", pInst->m_cbFeedSoftLimit );
dprintf("SSL access params 0x%08lx\n", pInst->m_dwSslAccessPerms );
dprintf("SSLInfo object 0x%p\n", pInst->m_pSSLInfo );
dprintf("Rebuild object 0x%p\n", pInst->m_pRebuild );
dprintf("Last rebuild error %d\n", pInst->m_dwLastRebuildError );
dprintf("Socket list 0x%p\n", pInst->m_pInUseList );
dprintf("Active feed list 0x%p\n", pInst->m_pActiveFeeds );
dprintf("Passive feed list 0x%p\n", pInst->m_pPassiveFeeds );
} else {
dprintf("Instance signature bad\n" );
}
dprintf("\n\n======== End Instance dump =========\n\n");
}
VOID
DbgPrintNewstree(
CNewsTree* ptree,
DWORD nGroups
)
/*++
Routine Description:
Dump the first n newsgroup objects in the newstree.
NOTE: Assumed that the pointer passed is in OUR address space
--*/
{
CNewsGroup* pGroup;
dprintf("\n\n======== Newstree members =========\n");
dprintf(" Owning instance is 0x%p\n", ptree->m_pInstance );
dprintf(" StartSpecial is %d\n", ptree->m_idStartSpecial );
dprintf(" LastSpecial is %d\n", ptree->m_idLastSpecial );
dprintf(" idSlaveGroup is %d\n", ptree->m_idSlaveGroup );
dprintf(" idSpecialHigh is %d\n", ptree->m_idSpecialHigh );
dprintf(" idStart is %d\n", ptree->m_idStart );
dprintf(" idHigh is %d\n", ptree->m_idHigh );
dprintf(" First group is 0x%p\n", ptree->m_pFirst );
dprintf(" Last group is 0x%p\n", ptree->m_pLast );
dprintf(" Num groups is %d\n", ptree->m_cGroups );
dprintf(" VRoot table is 0x%p\n", ptree->m_pVRTable );
ptree->m_fStoppingTree ? dprintf( " Tree is being stopped\n" ) :
dprintf( " Tree is not being stopped\n" );
dprintf(" Group.lst object is 0x%p\n", ptree->m_pFixedPropsFile );
dprintf(" Groupvar.lst object is 0x%p\n", ptree->m_pVarPropsFile );
dprintf(" Server object is 0x%p\n", ptree->m_pServerObject );
ptree->m_fVRTableInit ? dprintf(" Vroot table initialized\n" ) :
dprintf(" Vroot table NOT initialized\n" );
if( nGroups )
{
dprintf("\n\n======== Begin Newstree dump =========\n");
for( pGroup = (CNewsGroup*)ptree->m_pFirst; pGroup && nGroups--; )
{
pGroup = DbgPrintNewsgroup( pGroup );
}
dprintf("\n\n======== End Newstree dump =========\n\n");
}
}
VOID
DbgPrintVRootList(
CNNTPVRoot* pFirstVRoot,
DWORD nVRoots
)
/*++
Routine Description:
Dump the first n newsgroup objects in the newstree.
NOTE: Assumed that the pointer passed is in OUR address space
--*/
{
CNNTPVRoot* pVRoot;
if( nVRoots )
{
dprintf("\n\n======== Begin virtual root list dump =========\n");
for( pVRoot = pFirstVRoot; pVRoot && nVRoots--; )
{
pVRoot = DbgPrintVRoot( pVRoot );
}
dprintf("\n\n======== End virtual root list dump =========\n\n");
}
}
VOID
PrintSystemTime(
FILETIME* pftTime
)
{
SYSTEMTIME st;
FileTimeToSystemTime( pftTime, &st );
dprintf(" %04d::%02d::%02d::::%02d::%02d::%02d\n", st.wYear, st.wMonth, st.wDay, st.wHour, st.wMinute, st.wSecond);
}
VOID
PrintString(
LPSTR lp1,
LPSTR lp2
)
{
move( g_szBuffer, lp2 );
dprintf( lp1, g_szBuffer );
}
CNewsGroup*
DbgPrintNewsgroup(
CNewsGroup * pSrcGroup
)
/*++
Routine Description:
Dump the newsgroup object at pGroup.
NOTE: Assumed that the pointer passed in is in the debuggee's address space
ie. we need to allocate memory and copy the data over into our address space !
Arguments:
Returns:
The next newsgroup pointer
--*/
{
CNewsGroup *pGroup, *pDstGroup;
char szNewsGroup [MAX_NEWSGROUP_NAME];
DWORD cbGroupName;
LPCSTR lpstrGroup;
DWORD cbPath, cbNewsGroup;
CNewsGroup* pGroupRet = NULL;
BOOL fActive = TRUE;
SYSTEMTIME sysTime;
//
// Allocate memory in our address space so we can read data from the debuggee's address space
//
cbNewsGroup = sizeof(CNewsGroup);
pDstGroup = (CNewsGroup*) DbgAlloc( cbNewsGroup );
if( !pDstGroup )
{
dprintf( "nntpdbg: Unable to allocate memory \n");
return NULL;
}
if( !ReadMemory( pSrcGroup, pDstGroup, cbNewsGroup, NULL ) )
{
dprintf("Could not get data at 0x%x\n", pSrcGroup);
goto DbgPrintNewsgroup_Exit;
}
// Now, we can use pGroup to access the members of the CNewsGroup object
pGroup = pDstGroup;
//
// Dump the newsgroup object
//
dprintf("\n\n======== Begin Newsgroup object =========\n\n");
//
// Check to see if group object is deallocated
//
fActive = ( pGroup->m_dwSignature == CNEWSGROUPCORE_SIGNATURE );
if ( fActive ) {
//
// dump newsgroup name
//
lpstrGroup = pGroup->m_pszGroupName;
cbGroupName = pGroup->m_cchGroupName; // it should have already included '\0'
if( ReadMemory( lpstrGroup, szNewsGroup, cbGroupName, NULL) ) {
dprintf("Newsgroup name is %s\n", szNewsGroup );
}
//
// Dump native name
//
lpstrGroup = pGroup->m_pszNativeName;
if ( lpstrGroup && ReadMemory( lpstrGroup, szNewsGroup, cbGroupName, NULL ) ) {
dprintf("Pretty name is %s\n", szNewsGroup );
} else {
dprintf("No native name\n" );
}
//
// Dump pretty name
//
lpstrGroup = pGroup->m_pszPrettyName;
cbGroupName = pGroup->m_cchPrettyName;
if ( lpstrGroup && ReadMemory( lpstrGroup, szNewsGroup, cbGroupName, NULL ) ) {
dprintf("Pretty name is %s\n", szNewsGroup );
} else {
dprintf("No pretty name\n" );
}
//
// Dump help text
//
lpstrGroup = pGroup->m_pszHelpText;
cbGroupName = pGroup->m_cchHelpText;
if ( lpstrGroup && ReadMemory( lpstrGroup, szNewsGroup, cbGroupName, NULL ) ) {
dprintf("Help text is %s\n", szNewsGroup );
} else {
dprintf("No help text\n" );
}
//
// Dump moderator
//
lpstrGroup = pGroup->m_pszModerator;
cbGroupName = pGroup->m_cchModerator;
if ( lpstrGroup && ReadMemory( lpstrGroup, szNewsGroup, cbGroupName, NULL ) ) {
dprintf("Moderator is %s\n", szNewsGroup );
} else {
dprintf("No moderator\n" );
}
//
// dump group privates
//
dprintf("Ref count is %d\n", pGroup->m_cRefs );
dprintf("Parent tree is 0x%p\n", pGroup->m_pNewsTree );
dprintf("Parent vroot is 0x%p\n", pGroup->m_pVRoot );
dprintf("Low watermark is %d\n", pGroup->m_iLowWatermark);
dprintf("High watermark is %d\n", pGroup->m_iHighWatermark);
dprintf("Article estimate is %d\n", pGroup->m_cMessages );
dprintf("Group id is %d\n", pGroup->m_dwGroupId );
pGroup->m_fReadOnly ? dprintf("Group is read only\n" ) : dprintf("Group is not read only\n" );
pGroup->m_fDeleted ? dprintf("Group is marked deleted\n") : dprintf("Group is NOT marked deleted\n");
FileTimeToSystemTime( &(pGroup->m_ftCreateDate), &sysTime );
dprintf("Group create time: %d/%d/%d - %d:%d:%d\n",
sysTime.wMonth,
sysTime.wDay,
sysTime.wYear,
sysTime.wHour,
sysTime.wMinute,
sysTime.wSecond );
dprintf("Cache hit is %d\n", pGroup->m_dwCacheHit );
pGroup->m_fAllowExpire ? dprintf( "Expire allowed\n" ) : dprintf( "Expire not allowed\n" );
pGroup->m_fAllowPost ? dprintf( "Post allowed\n" ) : dprintf( "Expire not allowed\n" );
pGroup->m_fDecorateVisited ? dprintf( "Decorate visited\n" ) : dprintf( "Decorate non-visited\n" );
dprintf("m_artXoverExpireLow is %d\n", pGroup->m_artXoverExpireLow);
dprintf("Prev group is 0x%p\n", pGroup->m_pPrev);
dprintf("Next group is 0x%p\n", pGroup->m_pNext);
pGroupRet = (CNewsGroup*)pGroup->m_pNext;
} else {
dprintf( "Newsgroup signature is bad\n" );
}
dprintf("\n======== End Newsgroup object =========\n");
DbgPrintNewsgroup_Exit:
DbgFreeEx( pDstGroup );
return pGroupRet;
}
CNNTPVRoot*
DbgPrintVRoot(
CNNTPVRoot * pVRoot
)
/*++
Routine Description:
Dump the vroot object at pVRoot
NOTE: Assumed that the pointer passed in is in the debuggee's address space
ie. we need to allocate memory and copy the data over into our address space !
Arguments:
Returns:
The next newsgroup pointer
--*/
{
CNNTPVRoot *pDestVRoot, *pMyVRoot;
DWORD cbVRoot;
CNNTPVRoot* pVRootRet = NULL;
BOOL fActive = FALSE;
//
// Allocate memory in our address space so we can read data from the debuggee's address space
//
cbVRoot = sizeof(CNNTPVRoot);
pDestVRoot = (CNNTPVRoot*) DbgAlloc( cbVRoot );
if( !pDestVRoot )
{
dprintf( "nntpdbg: Unable to allocate memory \n");
return NULL;
}
if( !ReadMemory( pVRoot, pDestVRoot, cbVRoot, NULL ) )
{
dprintf("Could not get data at 0x%x\n", pVRoot );
goto DbgPrintVRoot_Exit;
}
// Now, we can use pMyVRoot to access the members of the CNNTPVRoot object
pMyVRoot = pDestVRoot;
//
// Dump the vroot object
//
dprintf("\n\n======== Begin virtual root object =========\n\n");
//
// Check to see if group object is deallocated
//
fActive = ( pMyVRoot->m_dwSig == VROOT_GOOD_SIG );
if ( fActive ) {
//
// Dump reference
//
dprintf("Reference count is %d\n", pMyVRoot->m_cRefs );
dprintf("Next vroot is 0x%p\n", pMyVRoot->m_pNext );
pVRootRet = (CNNTPVRoot*)pMyVRoot->m_pNext;
dprintf("Prev vroot is 0x%p\n", pMyVRoot->m_pPrev );
pMyVRoot->m_fInit ? dprintf("Vroot is initialized\n") :
dprintf("Vroot is NOT initialized\n" );
dprintf("Vroot name is %s\n", pMyVRoot->m_szVRootName );
dprintf("Owning vroot table is 0x%p\n", pMyVRoot->m_pVRootTable );
pMyVRoot->m_fUpgrade ? dprintf("This is an upgraded vroot\n" ) :
dprintf("This is not an upgraded vroot\n" );
pMyVRoot->m_fIsIndexed ? dprintf("Content indexed\n" ) :
dprintf("Not content indexed\n" );
dprintf("Access bitmask is 0x%08lx\n", pMyVRoot->m_dwAccess );
dprintf("SSL access bitmask 0x%08lx\n", pMyVRoot->m_dwSSL );
dprintf("Metabase object 0x%p\n", pMyVRoot->m_pMB );
dprintf("Directory path %s\n", pMyVRoot->m_szDirectory );
dprintf("Prepare driver 0x%p\n", pMyVRoot->m_pDriverPrepare );
dprintf("Good driver 0x%p\n", pMyVRoot->m_pDriver );
switch( pMyVRoot->m_eLogonInfo ) {
case CNNTPVRoot::VROOT_LOGON_DEFAULT:
dprintf("This is a file system vroot\n");
break;
case CNNTPVRoot::VROOT_LOGON_UNC:
dprintf("This is a UNC vroot\n" );
break;
case CNNTPVRoot::VROOT_LOGON_EX:
dprintf("This is an exchange vroot\n" );
break;
}
switch( pMyVRoot->m_eState ) {
case CNNTPVRoot::VROOT_STATE_UNINIT:
dprintf("Vroot not inited\n" );
break;
case CNNTPVRoot::VROOT_STATE_CONNECTING:
dprintf("Vroot is connecting\n" );
break;
case CNNTPVRoot::VROOT_STATE_CONNECTED:
dprintf("Vroot is connected\n" );
break;
}
dprintf("VRoot Win32 Error %d\n", pMyVRoot->m_dwWin32Error );
dprintf("Impersonation token ( for UNC ): %d\n", pMyVRoot->m_hImpersonation );
pMyVRoot->m_bExpire ? dprintf("Vroot handles expire himself\n") :
dprintf("Protocol should help him expire\n" );
pMyVRoot->m_lDecCompleted == 0 ?
dprintf("Decorate newstree in progress\n") :
dprintf("Decorate newstree completed\n" );
#ifdef DEBUG
dprintf("Next vroot in debug list 0x%p\n",
CONTAINING_RECORD( pMyVRoot->m_DebugList.Flink,
CVRoot,
m_DebugList ) );
#endif
} else {
dprintf("Vroot signature bad\n" );
}
dprintf("\n======== End virtual root object =========\n");
DbgPrintVRoot_Exit:
DbgFreeEx( pDestVRoot );
return pVRootRet;
}
void
DbgPrintVRootTable(
CNNTPVRootTable * pVRTable
)
/*++
Routine Description:
Dump the vroot table object at pVRTable
NOTE: Assumed that the pointer passed in is in the debuggee's address space
ie. we need to allocate memory and copy the data over into our address space !
Arguments:
Returns:
The next newsgroup pointer
--*/
{
CNNTPVRootTable *pDestVRTable, *pMyVRTable;
DWORD cbVRTable;
CHAR szVRootPath[MAX_VROOT_PATH];
//
// Allocate memory in our address space so we can read data from the debuggee's address space
//
cbVRTable = sizeof(CNNTPVRootTable);
pDestVRTable = (CNNTPVRootTable*) DbgAlloc( cbVRTable );
if( !pDestVRTable )
{
dprintf( "nntpdbg: Unable to allocate memory \n");
return ;
}
if( !ReadMemory( pVRTable, pDestVRTable, cbVRTable, NULL ) )
{
dprintf("Could not get data at 0x%x\n", pVRTable );
goto DbgPrintVRootTable_Exit;
}
// Now, we can use pMyVRTable to access the members of the CNNTPVRoot object
pMyVRTable = pDestVRTable;
//
// Dump the vroot object
//
dprintf("\n\n======== Begin virtual root table object =========\n\n");
#ifdef DEBUG
if ( IsListEmpty( &pMyVRTable->impl.m_DebugListHead ) ) {
dprintf("Debug list is empty\n");
} else {
dprintf("First vroot in debug list 0x%p\n",
CONTAINING_RECORD( pMyVRTable->impl.m_DebugListHead.Flink,
CVRoot,
m_DebugList ) );
}
#endif
CopyUnicodeStringIntoAscii( szVRootPath, pMyVRTable->impl.m_wszRootPath );
dprintf("VRoot path is %s\n", szVRootPath );
pMyVRTable->impl.m_fInit ? dprintf("We have been initialized\n") :
dprintf("We are not initialized\n" );
pMyVRTable->impl.m_fShuttingDown ? dprintf("We are shutting down\n") :
dprintf("We are not shutting down\n" );
if ( pMyVRTable->impl.m_listVRoots.IsEmpty() ) {
dprintf("Table is empty\n" );
} else {
dprintf("The first vroot on table is 0x%p\n",
pMyVRTable->impl.m_listVRoots.m_pHead );
}
dprintf("Owning instance wrapper 0x%p\n", pMyVRTable->m_pInstWrapper );
dprintf("\n======== End virtual root table object =========\n");
DbgPrintVRootTable_Exit:
DbgFreeEx( pDestVRTable );
}
VOID
DbgDumpPool(
CSmtpClientPool* pSCPool
)
/*++
Routine Description:
Dump the smtp cached conx
NOTE: Assumed that the pointer passed is in OUR address space
--*/
{
DWORD cSlots = pSCPool->m_cSlots;
DWORD i;
BOOL* rgAvailList = NULL;
CSmtpClient** rgppSCList = NULL;
dprintf("\n======== Begin CSmtpClientPool dump =========\n\n");
dprintf("Number of slots is %d\n", cSlots);
DWORD cbAvailList = sizeof(BOOL)*cSlots;
DWORD cbSCList = sizeof(CSmtpClient*)*cSlots;
rgAvailList = (BOOL*)DbgAlloc( cbAvailList );
if( !rgAvailList || !ReadMemory( pSCPool->m_rgAvailList, rgAvailList, cbAvailList, NULL) )
{
dprintf("Failed to allocate or read memory\n");
goto DbgDumpPool_Exit;
}
rgppSCList = (CSmtpClient**)DbgAlloc( cbSCList );
if( !rgppSCList || !ReadMemory( pSCPool->m_rgpSCList, rgppSCList, cbSCList, NULL) )
{
dprintf("Failed to allocate or read memory\n");
goto DbgDumpPool_Exit;
}
// Dump the conx object pointers and avail status
for(i=0; i<cSlots; i++)
{
dprintf("Smtp conx object %d is 0x%p\n", i+1, rgppSCList [i]);
dprintf("Avail status is %d\n", rgAvailList [i]);
}
dprintf("\n======== End CSmtpClientPool dump =========\n");
DbgDumpPool_Exit:
DbgFreeEx( rgAvailList );
DbgFreeEx( rgppSCList );
}
VOID
DbgDumpFeedBlock(
PFEED_BLOCK feedBlock
)
/*++
Routine Description:
Dump the feedBlock passed in; validate signature
NOTE: Assumed that the pointer passed in is in the debuggee's address space
ie. we need to allocate memory and copy the data over into our address space !
Arguments:
Returns:
--*/
{
FEED_BLOCK feed;
// read memory from debuggee's address space
move( feed, feedBlock );
// validate signature
if( FEED_BLOCK_SIGN != feed.Signature )
{
dprintf("Invalid Feed block signature Expected: 0x%08lx Got: 0x%08lx \n", FEED_BLOCK_SIGN, feed.Signature );
return;
}
// ok, dump the feed block
dprintf("============ Begin feed block dump =============== \n");
dprintf("Number of feeds done so far is %d\n", feed.NumberOfFeeds);
dprintf("Number of failed connection attempts for Push feeds is %d\n", feed.cFailedAttempts);
dprintf("The last newsgroup spec Pulled is %d\n", feed.LastNewsgroupPulled);
dprintf("Resolved IP address is %d\n", feed.IPAddress);
dprintf("feedblock ListEntry Flink is 0x%p\n", feed.ListEntry.Flink);
dprintf("feedblock ListEntry Blink is 0x%p\n", feed.ListEntry.Blink);
dprintf("feed is in progress ? %d\n", feed.FeedsInProgress);
dprintf("Count of references to this block is %d\n", feed.ReferenceCount);
dprintf("Current State of this block is %d\n", feed.State);
dprintf("Should we delete this block when the references reach 0 ? %d\n", feed.MarkedForDelete);
dprintf("Pointer to a FEED_BLOCK that we are replaced by is 0x%p\n", feed.ReplacedBy);
dprintf("Pointer to a FEED_BLOCK we replace is 0x%p\n", feed.Replaces);
dprintf("Type of this feed (push/pull/passive) is %d\n", feed.FeedType);
//dprintf("Name of reg key this feed info is stored under 0x%p\n", feed.KeyName);
dprintf("The Queue used to record outgoing articles for this ACTIVE outgoing feed is 0x%p\n", feed.pFeedQueue);
dprintf("Unique id for this feed block is %d\n", feed.FeedId);
dprintf("Should we autocreate directories? %d\n", feed.AutoCreate);
dprintf("Minutes between feeds is %d\n", feed.FeedIntervalMinutes);
dprintf("Pull Request Time is");
PrintSystemTime( &feed.PullRequestTime );
FILETIME ft;
dprintf("Start Time is");
FILETIME_FROM_LI( &ft, &feed.StartTime );
PrintSystemTime( &ft );
dprintf("Next Active Time is");
FILETIME_FROM_LI( &ft, &feed.NextActiveTime);
PrintSystemTime( &ft );
PrintString("Name of the feed server is %s\n", feed.ServerName);
dprintf("Newsgroups to pull is 0x%p\n", feed.Newsgroups);
dprintf("Distributions is 0x%p\n", feed.Distribution);
dprintf("Flag indicating whether the feed is currently 'enabled' is %d\n", feed.fEnabled);
//PrintString("The name to be used in Path processing is %s\n", feed.UucpName);
PrintString("The directory where we are to store our temp files is %s\n", feed.FeedTempDirectory);
dprintf("Maximum number of consecutive failed connect attempts before\n");
dprintf("we disable the feed is %d\n", feed.MaxConnectAttempts);
dprintf("Number of sessions to create for outbound feeds is %d\n", feed.ConcurrentSessions);
dprintf("Type of security to have is %d\n", feed.SessionSecurityType);
dprintf("Authentication security is %d\n", feed.AuthenticationSecurity);
PrintString("User Account for clear text logons is %s\n", feed.NntpAccount);
PrintString("User Password for clear text logons is %s\n", feed.NntpPassword);
dprintf("Allow control messages on this feed ? %d\n", feed.fAllowControlMessages);
dprintf("============ End feed block dump =============== \n");
}
VOID
DbgDumpFeedList(
CFeedList* pSrcFeedList,
CFeedList* pDstFeedList
)
/*--
Arguments:
pSrcFeedList - pointer in debuggee's address space
pDstFeedList - pointer in OUR address space
--*/
{
LIST_ENTRY Entry;
PLIST_ENTRY listEntry;
PLIST_ENTRY SrclistEntry = (pDstFeedList->m_ListHead).Flink ;
listEntry = SrclistEntry;
DWORD offset = (DWORD)((DWORD_PTR)&((CFeedList*)0)->m_ListHead);
PLIST_ENTRY listEnd = (PLIST_ENTRY)((LPBYTE)pSrcFeedList+offset);
//dprintf("offset is %d listEnd is 0x%p\n", offset, listEnd);
while( listEntry != listEnd ) {
PFEED_BLOCK feedBlock = CONTAINING_RECORD( listEntry,
FEED_BLOCK,
ListEntry );
DbgDumpFeedBlock( feedBlock );
SrclistEntry = listEntry;
move( Entry, SrclistEntry );
listEntry = Entry.Flink ;
}
}
VOID
DbgDumpCPool(CPool* pCPool, DWORD dwSignature, LPCSTR szSymbol)
{
CPool* pPool = (CPool*)DbgAlloc( sizeof(CPool));
if ( pCPool && pPool )
{
if ( ReadMemory( (LPVOID) pCPool,
pPool,
sizeof(CPool),
NULL ))
{
dprintf( "%s at 0x%8lx, signature is 0x%.8x\n",
(szSymbol?szSymbol:"CPool"),
pCPool, pPool->m_dwSignature);
if( dwSignature != 0 && dwSignature != pPool->m_dwSignature ) {
dprintf(" *** signature mismatch\n" );
}
dprintf(" m_cMaxInstances = %d\n", pPool->m_cMaxInstances );
dprintf(" m_cInstanceSize = %d\n", pPool->m_cInstanceSize );
dprintf(" m_cNumberCommitted = %d\n", pPool->m_cNumberCommitted );
dprintf(" m_cNumberInUse = %d\n", pPool->m_cNumberInUse );
dprintf(" m_cNumberAvail = %d\n", pPool->m_cNumberAvail );
dprintf(" m_cFragmentInstances = %d\n", pPool->m_cFragmentInstances );
dprintf(" m_cFragments = %d\n", pPool->m_cFragments );
dprintf(" Fragments:\n");
for(int i=0; i<MAX_CPOOL_FRAGMENTS; i++) {
dprintf(" %p%s", pPool->m_pFragments[i], ((i+1)%4)==0?"\n":"" );
}
dprintf("=========================\n");
}
DbgFree( (PVOID)pPool );
}
}