1317 lines
31 KiB
C
1317 lines
31 KiB
C
|
|
||
|
// This is a 64 bit aware debugger extension
|
||
|
#define KDEXT_64BIT
|
||
|
|
||
|
#include <windows.h>
|
||
|
#include <wdbgexts.h>
|
||
|
#include <stdio.h>
|
||
|
#include <stdlib.h>
|
||
|
#include <string.h>
|
||
|
|
||
|
#include "e100_equ.h"
|
||
|
#include "e100_557.h"
|
||
|
|
||
|
#include "mp_cmn.h"
|
||
|
|
||
|
#include "e100kd.h"
|
||
|
|
||
|
WINDBG_EXTENSION_APIS ExtensionApis;
|
||
|
EXT_API_VERSION ApiVersion = { 5, 0, EXT_API_VERSION_NUMBER64, 0};
|
||
|
|
||
|
|
||
|
USHORT SavedMajorVersion;
|
||
|
USHORT SavedMinorVersion;
|
||
|
BOOL ChkTarget; // is debuggee a CHK build?
|
||
|
|
||
|
typedef struct
|
||
|
{
|
||
|
char Name[16];
|
||
|
unsigned int Val;
|
||
|
} DBG_LEVEL;
|
||
|
|
||
|
DBG_LEVEL DbgLevel[] = {
|
||
|
{"ERROR", MP_ERROR},
|
||
|
{"WARN", MP_WARN},
|
||
|
{"TRACE", MP_TRACE},
|
||
|
{"INFO", MP_INFO},
|
||
|
{"LOUD", MP_LOUD}
|
||
|
};
|
||
|
|
||
|
typedef struct
|
||
|
{
|
||
|
char Name[32];
|
||
|
unsigned int Val;
|
||
|
|
||
|
} DBG_ADAPTER_FLAGS, DBG_FILTER;
|
||
|
|
||
|
DBG_ADAPTER_FLAGS DbgAdapterFlags[] = {
|
||
|
{"SCATTER_GATHER", fMP_ADAPTER_SCATTER_GATHER},
|
||
|
{"MAP_REGISTER", fMP_ADAPTER_MAP_REGISTER},
|
||
|
{"RECV_LOOKASIDE", fMP_ADAPTER_RECV_LOOKASIDE},
|
||
|
{"INTERRUPT_IN_USE", fMP_ADAPTER_INTERRUPT_IN_USE},
|
||
|
{"RESET_IN_PROGRESS", fMP_ADAPTER_RESET_IN_PROGRESS},
|
||
|
{"NO_CABLE", fMP_ADAPTER_NO_CABLE},
|
||
|
{"HARDWARE_ERROR", fMP_ADAPTER_HARDWARE_ERROR}
|
||
|
};
|
||
|
|
||
|
//
|
||
|
// Ndis Packet Filter Bits (OID_GEN_CURRENT_PACKET_FILTER).
|
||
|
//
|
||
|
#define NDIS_PACKET_TYPE_DIRECTED 0x00000001
|
||
|
#define NDIS_PACKET_TYPE_MULTICAST 0x00000002
|
||
|
#define NDIS_PACKET_TYPE_ALL_MULTICAST 0x00000004
|
||
|
#define NDIS_PACKET_TYPE_BROADCAST 0x00000008
|
||
|
#define NDIS_PACKET_TYPE_SOURCE_ROUTING 0x00000010
|
||
|
#define NDIS_PACKET_TYPE_PROMISCUOUS 0x00000020
|
||
|
#define NDIS_PACKET_TYPE_SMT 0x00000040
|
||
|
#define NDIS_PACKET_TYPE_ALL_LOCAL 0x00000080
|
||
|
#define NDIS_PACKET_TYPE_GROUP 0x00001000
|
||
|
#define NDIS_PACKET_TYPE_ALL_FUNCTIONAL 0x00002000
|
||
|
#define NDIS_PACKET_TYPE_FUNCTIONAL 0x00004000
|
||
|
#define NDIS_PACKET_TYPE_MAC_FRAME 0x00008000
|
||
|
|
||
|
|
||
|
DBG_FILTER DbgFilterTable[] = {
|
||
|
{"DIRECTED", NDIS_PACKET_TYPE_DIRECTED},
|
||
|
{"MULTICAST", NDIS_PACKET_TYPE_MULTICAST},
|
||
|
{"ALL_MULTICAST", NDIS_PACKET_TYPE_ALL_MULTICAST},
|
||
|
{"BROADCAST", NDIS_PACKET_TYPE_BROADCAST},
|
||
|
{"SOURCE_ROUTING", NDIS_PACKET_TYPE_SOURCE_ROUTING},
|
||
|
{"PROMISCUOUS", NDIS_PACKET_TYPE_PROMISCUOUS},
|
||
|
{"SMT", NDIS_PACKET_TYPE_SMT},
|
||
|
{"ALL_LOCAL", NDIS_PACKET_TYPE_ALL_LOCAL},
|
||
|
{"GROUP", NDIS_PACKET_TYPE_GROUP},
|
||
|
{"ALL_FUNCTIONAL", NDIS_PACKET_TYPE_ALL_FUNCTIONAL},
|
||
|
{"FUNCTIONAL", NDIS_PACKET_TYPE_FUNCTIONAL},
|
||
|
{"MAC_FRAME", NDIS_PACKET_TYPE_MAC_FRAME}
|
||
|
};
|
||
|
|
||
|
typedef struct
|
||
|
{
|
||
|
char Name[32];
|
||
|
USHORT Val;
|
||
|
} DBG_RFD_STATUS, DBG_RFD_COMMAND, DBG_USHORT_BITS, DBG_USHORT_VALUE;
|
||
|
|
||
|
typedef struct
|
||
|
{
|
||
|
char Name[32];
|
||
|
UCHAR Val;
|
||
|
} DBG_UCHAR_BITS, DBG_UCHAR_VALUE;
|
||
|
|
||
|
|
||
|
DBG_RFD_STATUS DbgRfdStatus[] = {
|
||
|
{"COMPLETE", RFD_STATUS_COMPLETE},
|
||
|
{"OK", RFD_STATUS_OK},
|
||
|
{"CRC_ERROR", RFD_CRC_ERROR},
|
||
|
{"ALIGNMENT_ERROR", RFD_ALIGNMENT_ERROR},
|
||
|
{"NO_RESOURCES", RFD_NO_RESOURCES},
|
||
|
{"DMA_OVERRUN", RFD_DMA_OVERRUN},
|
||
|
{"FRAME_TOO_SHORT", RFD_FRAME_TOO_SHORT},
|
||
|
{"RX_ERR", RFD_RX_ERR},
|
||
|
{"IA_MATCH", RFD_IA_MATCH},
|
||
|
{"RECEIVE_COLLISION", RFD_RECEIVE_COLLISION},
|
||
|
};
|
||
|
|
||
|
DBG_RFD_COMMAND DbgRfdCommand[] = {
|
||
|
{"EL", RFD_EL_BIT},
|
||
|
{"S", RFD_S_BIT},
|
||
|
{"H", RFD_H_BIT},
|
||
|
{"SF", RFD_SF_BIT}
|
||
|
};
|
||
|
|
||
|
DBG_USHORT_BITS DbgCbCommandBits[] = {
|
||
|
{"EL", CB_EL_BIT},
|
||
|
{"S", CB_S_BIT},
|
||
|
{"I", CB_I_BIT},
|
||
|
{"TX_SF", CB_TX_SF_BIT}
|
||
|
};
|
||
|
|
||
|
DBG_USHORT_VALUE DbgCbCommands[] = {
|
||
|
{"CB_NOP", CB_NOP},
|
||
|
{"CB_IA_ADDRESS", CB_IA_ADDRESS},
|
||
|
{"CB_CONFIGURE", CB_CONFIGURE},
|
||
|
{"CB_MULTICAST", CB_MULTICAST},
|
||
|
{"CB_TRANSMIT", CB_TRANSMIT},
|
||
|
{"CB_LOAD_MICROCODE", CB_LOAD_MICROCODE},
|
||
|
{"CB_DUMP", CB_DUMP},
|
||
|
{"CB_DIAGNOSE", CB_DIAGNOSE}
|
||
|
};
|
||
|
|
||
|
DBG_USHORT_VALUE DbgScbStatusRus[] = {
|
||
|
{"IDLE", SCB_RUS_IDLE},
|
||
|
{"SUSPEND", SCB_RUS_SUSPEND},
|
||
|
{"NO_RESOURCES", SCB_RUS_NO_RESOURCES},
|
||
|
{"READY", SCB_RUS_READY},
|
||
|
{"SUSP_NO_RBDS", SCB_RUS_SUSP_NO_RBDS},
|
||
|
{"NO_RBDS", SCB_RUS_NO_RBDS},
|
||
|
{"READY_NO_RBDS", SCB_RUS_READY_NO_RBDS},
|
||
|
};
|
||
|
|
||
|
DBG_USHORT_BITS DbgScbStatusBits[] = {
|
||
|
{"CX", SCB_STATUS_CX},
|
||
|
{"FR", SCB_STATUS_FR},
|
||
|
{"CNA", SCB_STATUS_CNA},
|
||
|
{"RNR", SCB_STATUS_RNR},
|
||
|
{"MDI", SCB_STATUS_MDI},
|
||
|
{"SWI", SCB_STATUS_SWI}
|
||
|
};
|
||
|
|
||
|
DBG_UCHAR_VALUE DbgScbCommandCuc[] = {
|
||
|
{"START", SCB_CUC_START},
|
||
|
{"RESUME", SCB_CUC_RESUME},
|
||
|
{"DUMP_ADDR", SCB_CUC_DUMP_ADDR},
|
||
|
{"DUMP_STAT", SCB_CUC_DUMP_STAT},
|
||
|
{"LOAD_BASE", SCB_CUC_LOAD_BASE},
|
||
|
{"DUMP_RST_STAT", SCB_CUC_DUMP_RST_STAT},
|
||
|
{"STATIC_RESUME", SCB_CUC_STATIC_RESUME}
|
||
|
};
|
||
|
|
||
|
|
||
|
DBG_UCHAR_VALUE DbgScbCommandRuc[] = {
|
||
|
{"START", SCB_RUC_START},
|
||
|
{"RESUME", SCB_RUC_RESUME},
|
||
|
{"ABORT", SCB_RUC_ABORT},
|
||
|
{"LOAD_HDS", SCB_RUC_LOAD_HDS},
|
||
|
{"LOAD_BASE", SCB_RUC_LOAD_BASE},
|
||
|
{"RBD_RESUME", SCB_RUC_RBD_RESUME}
|
||
|
};
|
||
|
|
||
|
VOID WinDbgExtensionDllInit(
|
||
|
PWINDBG_EXTENSION_APIS64 lpExtensionApis,
|
||
|
USHORT MajorVersion,
|
||
|
USHORT MinorVersion
|
||
|
)
|
||
|
{
|
||
|
ExtensionApis = *lpExtensionApis;
|
||
|
|
||
|
SavedMajorVersion = MajorVersion;
|
||
|
SavedMinorVersion = MinorVersion;
|
||
|
ChkTarget = SavedMajorVersion == 0x0c ? TRUE : FALSE;
|
||
|
}
|
||
|
|
||
|
LPEXT_API_VERSION ExtensionApiVersion(VOID)
|
||
|
{
|
||
|
return &ApiVersion;
|
||
|
}
|
||
|
|
||
|
VOID CheckVersion(VOID)
|
||
|
{
|
||
|
|
||
|
//
|
||
|
// for now don't bother to version check
|
||
|
//
|
||
|
return;
|
||
|
}
|
||
|
|
||
|
DECLARE_API( help )
|
||
|
{
|
||
|
int i;
|
||
|
|
||
|
dprintf("E100 extensions:\n");
|
||
|
|
||
|
dprintf(" dbglevel dump debug level\n");
|
||
|
dprintf(" mpadapter <MP_ADAPTER> <verbosity>> dump MP_ADAPTER block\n");
|
||
|
dprintf(" csr <CSRAddress> dump CSR block\n");
|
||
|
dprintf(" sendlist <CurrSendHead> <verbosity> dump send list\n");
|
||
|
dprintf(" mptcb <MP_TCB> dump MP_TCB block\n");
|
||
|
dprintf(" hwtcb <HW_TCB> dump HW_TCB block\n");
|
||
|
dprintf(" sendqueue <SendWaitQueue> dump queued send packets\n");
|
||
|
dprintf(" recvlist <RecvList> <verbosity> dump receive list\n");
|
||
|
dprintf(" mprfd <MP_RFD> dump MP_RFD block\n");
|
||
|
dprintf(" hwrfd <HW_RFD> dump HW_RFD block\n");
|
||
|
dprintf(" recvpendlist <RecvPendList> dump pending indicated rx packets\n");
|
||
|
}
|
||
|
|
||
|
|
||
|
DECLARE_API(dbglevel)
|
||
|
{
|
||
|
ULONG64 debugLevelPtr;
|
||
|
ULONG debugLevel, NewLevel;
|
||
|
ULONG64 Val;
|
||
|
|
||
|
int i;
|
||
|
ULONG Bytes;
|
||
|
|
||
|
debugLevelPtr = GetExpression("e100bnt5!MPDebugLevel");
|
||
|
|
||
|
if(debugLevelPtr == 0)
|
||
|
{
|
||
|
dprintf("Error retrieving address of MPDebugLevel\n");
|
||
|
dprintf("Target is %s\n", ChkTarget ? "Checked" : "Free");
|
||
|
}
|
||
|
|
||
|
dprintf("MPDebugLevel @ %p\n", debugLevelPtr);
|
||
|
|
||
|
debugLevel = GetUlongFromAddress(debugLevelPtr);
|
||
|
|
||
|
dprintf("Current MPDebugLevel = %d", debugLevel);
|
||
|
|
||
|
for(i = 0; i < sizeof(DbgLevel)/sizeof(DBG_LEVEL); i++)
|
||
|
{
|
||
|
if(debugLevel == DbgLevel[i].Val)
|
||
|
{
|
||
|
dprintf(" - %s", DbgLevel[i].Name);
|
||
|
break;
|
||
|
}
|
||
|
}
|
||
|
|
||
|
dprintf("\n");
|
||
|
|
||
|
dprintf("Available settings: ");
|
||
|
for(i = 0; i < sizeof(DbgLevel)/sizeof(DBG_LEVEL); i++)
|
||
|
{
|
||
|
if(debugLevel != DbgLevel[i].Val)
|
||
|
{
|
||
|
dprintf("%d-%s ", DbgLevel[i].Val, DbgLevel[i].Name);
|
||
|
}
|
||
|
}
|
||
|
|
||
|
dprintf("\n");
|
||
|
|
||
|
if(!*args)
|
||
|
{
|
||
|
return;
|
||
|
}
|
||
|
|
||
|
i = sscanf(args, "%lx", &NewLevel);
|
||
|
|
||
|
if(i == 1)
|
||
|
{
|
||
|
for(i = 0; i < sizeof(DbgLevel)/sizeof(DBG_LEVEL); i++)
|
||
|
{
|
||
|
if(NewLevel == DbgLevel[i].Val)
|
||
|
{
|
||
|
if(NewLevel != debugLevel)
|
||
|
{
|
||
|
dprintf("New MPDebugLevel = %d\n", NewLevel);
|
||
|
WriteMemory(debugLevelPtr, &NewLevel, sizeof(ULONG), &Bytes);
|
||
|
}
|
||
|
|
||
|
break;
|
||
|
}
|
||
|
}
|
||
|
}
|
||
|
}
|
||
|
|
||
|
DECLARE_API(version)
|
||
|
{
|
||
|
#if DBG
|
||
|
PCSTR kind = "Checked";
|
||
|
#else
|
||
|
PCSTR kind = "Free";
|
||
|
#endif
|
||
|
|
||
|
dprintf("%s E100 Extension dll on a %s system\n",
|
||
|
kind, ChkTarget? "Checked" : "Free");
|
||
|
|
||
|
}
|
||
|
|
||
|
#define MAX_FLAGS_PER_LINE 4
|
||
|
#define MAC_ADDRESS_LENGTH 6
|
||
|
|
||
|
DECLARE_API(mpadapter)
|
||
|
{
|
||
|
ULONG64 pAdapter;
|
||
|
|
||
|
int ArgCount = 0;
|
||
|
|
||
|
ULONG i, j;
|
||
|
ULONG Flags;
|
||
|
ULONG PacketFilter;
|
||
|
ULONG Off;
|
||
|
|
||
|
UCHAR MacAddress[MAC_ADDRESS_LENGTH];
|
||
|
UINT MCAddressCount;
|
||
|
PUCHAR pBuffer;
|
||
|
|
||
|
if(*args)
|
||
|
{
|
||
|
ArgCount = sscanf(args,"%I64lx",&pAdapter);
|
||
|
}
|
||
|
|
||
|
//check for arguments
|
||
|
if(ArgCount < 1)
|
||
|
{
|
||
|
dprintf("Usage: mpadapter <pointer to MP_ADAPTER>\n");
|
||
|
return ;
|
||
|
}
|
||
|
|
||
|
dprintf(" pAdapter %p : \n", pAdapter);
|
||
|
|
||
|
InitTypeRead(pAdapter, MP_ADAPTER);
|
||
|
|
||
|
dprintf(" AdapterHandle : %p\n", ReadField(AdapterHandle));
|
||
|
|
||
|
Flags = (ULONG) ReadField(Flags);
|
||
|
dprintf(" Flags : 0x%08x\n", Flags);
|
||
|
|
||
|
j = 0;
|
||
|
for(i = 0; i < sizeof(DbgAdapterFlags)/sizeof(DBG_ADAPTER_FLAGS); i++)
|
||
|
{
|
||
|
if(Flags & DbgAdapterFlags[i].Val)
|
||
|
{
|
||
|
if(j == 0)
|
||
|
{
|
||
|
dprintf(" ");
|
||
|
}
|
||
|
|
||
|
dprintf("%s", DbgAdapterFlags[i].Name);
|
||
|
|
||
|
j++;
|
||
|
|
||
|
if(j != MAX_FLAGS_PER_LINE)
|
||
|
{
|
||
|
dprintf(", ");
|
||
|
}
|
||
|
else
|
||
|
{
|
||
|
dprintf("\n");
|
||
|
j = 0;
|
||
|
}
|
||
|
}
|
||
|
}
|
||
|
|
||
|
if(j != 0)
|
||
|
{
|
||
|
dprintf("\n");
|
||
|
}
|
||
|
|
||
|
if(!GetFieldOffset("MP_ADAPTER", "PermanentAddress", &Off))
|
||
|
{
|
||
|
if(GetData(MacAddress, pAdapter+Off, MAC_ADDRESS_LENGTH, "PermanentAddress[]"))
|
||
|
{
|
||
|
dprintf(" Permanent address : %02x-%02x-%02x-%02x-%02x-%02x\n",
|
||
|
MacAddress[0], MacAddress[1],
|
||
|
MacAddress[2], MacAddress[3],
|
||
|
MacAddress[4], MacAddress[5]);
|
||
|
}
|
||
|
}
|
||
|
|
||
|
if((BOOLEAN) ReadField(OverrideAddress))
|
||
|
{
|
||
|
if(!GetFieldOffset("MP_ADAPTER", "CurrentAddress", &Off))
|
||
|
{
|
||
|
if(GetData(MacAddress, pAdapter+Off, MAC_ADDRESS_LENGTH, "CurrentAddress[]"))
|
||
|
{
|
||
|
dprintf(" Current address : %02x-%02x-%02x-%02x-%02x-%02x\n",
|
||
|
MacAddress[0], MacAddress[1],
|
||
|
MacAddress[2], MacAddress[3],
|
||
|
MacAddress[4], MacAddress[5]);
|
||
|
}
|
||
|
}
|
||
|
}
|
||
|
else
|
||
|
{
|
||
|
dprintf(" Current address : same as above\n");
|
||
|
}
|
||
|
|
||
|
dprintf("\n");
|
||
|
|
||
|
dprintf(" --- SEND ---\n");
|
||
|
dprintf(" CurrSendHead = %p , CurrSendTail = %p , nBusySend = %d\n",
|
||
|
ReadField(CurrSendHead), ReadField(CurrSendTail), (LONG)ReadField(nBusySend));
|
||
|
|
||
|
dprintf(" SendWaitQueue Head = %p, Tail = %p\n",
|
||
|
ReadField(SendWaitQueue.Head), ReadField(SendWaitQueue.Tail));
|
||
|
dprintf(" NumTcb = %d, RegNumTcb = %d, NumBuffers = %d\n",
|
||
|
(LONG)ReadField(NumTcb), (LONG)ReadField(RegNumTcb), (LONG)ReadField(NumBuffers));
|
||
|
dprintf(" MpTcbMem = %p\n", ReadField(MpTcbMem));
|
||
|
|
||
|
if(DBG_TEST_FLAG(Flags, fMP_ADAPTER_MAP_REGISTER))
|
||
|
{
|
||
|
dprintf(" CurrMapRegHead = %d, CurrMapRegTail = %d\n",
|
||
|
(UINT)ReadField(CurrMapRegHead), (UINT)ReadField(CurrMapRegTail));
|
||
|
}
|
||
|
|
||
|
dprintf(" TransmitIdle = %s, ResumeWait = %s\n",
|
||
|
(BOOLEAN)ReadField(TransmitIdle) ? "TRUE" : "FALSE",
|
||
|
(BOOLEAN)ReadField(ResumeWait) ? "TRUE" : "FALSE");
|
||
|
|
||
|
dprintf(" SendBufferPool = %p\n", ReadField(SendBufferPool));
|
||
|
|
||
|
dprintf("\n");
|
||
|
|
||
|
dprintf(" --- RECV ---\n");
|
||
|
|
||
|
if(!GetFieldOffset("MP_ADAPTER", "RecvList", &Off))
|
||
|
{
|
||
|
dprintf(" RecvList @ %p , nReadyRecv = %d\n",
|
||
|
pAdapter+Off, (LONG)ReadField(nReadyRecv));
|
||
|
}
|
||
|
|
||
|
if(!GetFieldOffset("MP_ADAPTER", "RecvPendList", &Off))
|
||
|
{
|
||
|
dprintf(" RecvPendList @ %p , RefCount = %d\n",
|
||
|
pAdapter+Off, (LONG)ReadField(RefCount));
|
||
|
}
|
||
|
|
||
|
dprintf(" NumRfd = %d, CurrNumRfd = %d , HwRfdSize = %d\n",
|
||
|
(LONG)ReadField(NumRfd), (LONG)ReadField(CurrNumRfd), (LONG)ReadField(HwRfdSize));
|
||
|
|
||
|
dprintf(" bAllocNewRfd = %s, RfdShrinkCount = %d\n",
|
||
|
(BOOLEAN)ReadField(bAllocNewRfd) ? "TRUE" : "FALSE",
|
||
|
(LONG)ReadField(RfdShrinkCount));
|
||
|
|
||
|
dprintf(" RecvPacketPool = %p , RecvBufferPool = %p\n",
|
||
|
ReadField(RecvPacketPool), ReadField(RecvBufferPool));
|
||
|
|
||
|
dprintf("\n");
|
||
|
|
||
|
PacketFilter = (ULONG)ReadField(PacketFilter);
|
||
|
dprintf(" PacketFilter : 0x%08x\n", PacketFilter);
|
||
|
|
||
|
j = 0;
|
||
|
for(i = 0; i < sizeof(DbgFilterTable)/sizeof(DBG_FILTER); i++)
|
||
|
{
|
||
|
if(PacketFilter & DbgFilterTable[i].Val)
|
||
|
{
|
||
|
if(j == 0)
|
||
|
{
|
||
|
dprintf(" ");
|
||
|
}
|
||
|
|
||
|
dprintf("%s", DbgFilterTable[i].Name);
|
||
|
|
||
|
j++;
|
||
|
|
||
|
if(j != MAX_FLAGS_PER_LINE)
|
||
|
{
|
||
|
dprintf(", ");
|
||
|
}
|
||
|
else
|
||
|
{
|
||
|
dprintf("\n");
|
||
|
j = 0;
|
||
|
}
|
||
|
}
|
||
|
}
|
||
|
|
||
|
if(j != 0)
|
||
|
{
|
||
|
dprintf("\n");
|
||
|
}
|
||
|
|
||
|
dprintf(" ulLookAhead=%d, usLinkSpeed=%d, usDuplexMode=%d\n",
|
||
|
(ULONG)ReadField(ulLookAhead), (USHORT)ReadField(usLinkSpeed),
|
||
|
(USHORT)ReadField(usDuplexMode));
|
||
|
|
||
|
dprintf("\n");
|
||
|
|
||
|
MCAddressCount = (UINT)ReadField(MCAddressCount);
|
||
|
dprintf(" MCAddressCount = %d\n", MCAddressCount);
|
||
|
|
||
|
pBuffer = malloc(MCAddressCount * MAC_ADDRESS_LENGTH);
|
||
|
if(pBuffer)
|
||
|
{
|
||
|
if(!GetFieldOffset("MP_ADAPTER", "MCList", &Off))
|
||
|
{
|
||
|
if(GetData(pBuffer, pAdapter+Off, MCAddressCount * MAC_ADDRESS_LENGTH, "MCList[]"))
|
||
|
{
|
||
|
for(i=0; i<MCAddressCount; i++)
|
||
|
{
|
||
|
j = i * MAC_ADDRESS_LENGTH;
|
||
|
dprintf(" (%d) = %02x-%02x-%02x-%02x-%02x-%02x\n",
|
||
|
i, pBuffer[j], pBuffer[j+1], pBuffer[j+2],
|
||
|
pBuffer[j+3], pBuffer[j+4], pBuffer[j+5]);
|
||
|
}
|
||
|
}
|
||
|
}
|
||
|
|
||
|
free(pBuffer);
|
||
|
}
|
||
|
else
|
||
|
{
|
||
|
|
||
|
}
|
||
|
|
||
|
|
||
|
dprintf("\n");
|
||
|
|
||
|
|
||
|
dprintf(" IoBaseAddress = 0x%x, IoRange = 0x%x, InterrupLevel = 0x%x, MemPhysAddress = 0x%x\n",
|
||
|
(ULONG)ReadField(IoBaseAddress), (ULONG)ReadField(IoRange),
|
||
|
(ULONG)ReadField(InterruptLevel), (ULONG)ReadField(MemPhysAddress.LowPart));
|
||
|
dprintf(" PortOffset = %p , CSRAddress = %p\n",
|
||
|
ReadField(PortOffset), ReadField(CSRAddress));
|
||
|
|
||
|
dprintf(" RevsionID = %d, SubVendorID = 0x%02x, SubSystemID = 0x%02x\n",
|
||
|
(UCHAR)ReadField(RevsionID), (USHORT)ReadField(SubVendorID),
|
||
|
(USHORT)ReadField(SubSystemID));
|
||
|
|
||
|
}
|
||
|
|
||
|
DECLARE_API(csr)
|
||
|
{
|
||
|
ULONG64 pHwCsr;
|
||
|
int ArgCount = 0;
|
||
|
|
||
|
UCHAR ucVal;
|
||
|
USHORT usVal;
|
||
|
|
||
|
ULONG i;
|
||
|
|
||
|
if(*args)
|
||
|
{
|
||
|
ArgCount = sscanf(args,"%I64lx", &pHwCsr);
|
||
|
}
|
||
|
|
||
|
//check for arguments
|
||
|
if(ArgCount < 1)
|
||
|
{
|
||
|
dprintf("Usage: csr <CSRAddress>\n");
|
||
|
return ;
|
||
|
}
|
||
|
|
||
|
dprintf(" pHwCsr %x : \n", pHwCsr);
|
||
|
|
||
|
InitTypeRead(pHwCsr, HW_CSR);
|
||
|
|
||
|
// ScbStatus
|
||
|
usVal = (USHORT)ReadField(ScbStatus);
|
||
|
dprintf(" ScbStatus - 0x%04x ", usVal);
|
||
|
|
||
|
dprintf("CUS-");
|
||
|
switch(usVal & SCB_CUS_MASK)
|
||
|
{
|
||
|
case SCB_CUS_IDLE:
|
||
|
dprintf("IDLE ");
|
||
|
break;
|
||
|
|
||
|
case SCB_CUS_SUSPEND:
|
||
|
dprintf("SUSPEND ");
|
||
|
break;
|
||
|
|
||
|
case SCB_CUS_ACTIVE:
|
||
|
dprintf("ACTIVE ");
|
||
|
break;
|
||
|
|
||
|
default:
|
||
|
dprintf("Reserved ");
|
||
|
}
|
||
|
|
||
|
for(i = 0; i < sizeof(DbgScbStatusRus)/sizeof(DBG_USHORT_VALUE); i++)
|
||
|
{
|
||
|
if((usVal & SCB_RUS_MASK) == DbgScbStatusRus[i].Val)
|
||
|
{
|
||
|
dprintf("RUS-%s ", DbgScbStatusRus[i].Name);
|
||
|
break;
|
||
|
}
|
||
|
}
|
||
|
|
||
|
dprintf("STAT-");
|
||
|
|
||
|
for(i = 0; i < sizeof(DbgScbStatusBits)/sizeof(DBG_USHORT_BITS); i++)
|
||
|
{
|
||
|
if(usVal & DbgScbStatusBits[i].Val)
|
||
|
{
|
||
|
dprintf("%s ", DbgScbStatusBits[i].Name);
|
||
|
}
|
||
|
}
|
||
|
|
||
|
dprintf("\n");
|
||
|
|
||
|
//ScbCommandLow
|
||
|
ucVal = (UCHAR)ReadField(ScbCommandLow);
|
||
|
dprintf(" ScbCommandLow - 0x%02x ", ucVal);
|
||
|
|
||
|
for(i = 0; i < sizeof(DbgScbCommandCuc)/sizeof(DBG_UCHAR_VALUE); i++)
|
||
|
{
|
||
|
if((ucVal & SCB_CUC_MASK) == DbgScbCommandCuc[i].Val)
|
||
|
{
|
||
|
dprintf("CUC-%s ", DbgScbCommandCuc[i].Name);
|
||
|
break;
|
||
|
}
|
||
|
}
|
||
|
|
||
|
for(i = 0; i < sizeof(DbgScbCommandRuc)/sizeof(DBG_UCHAR_VALUE); i++)
|
||
|
{
|
||
|
if((ucVal & SCB_RUC_MASK) == DbgScbCommandRuc[i].Val)
|
||
|
{
|
||
|
dprintf("RUC-%s ", DbgScbCommandRuc[i].Name);
|
||
|
break;
|
||
|
}
|
||
|
}
|
||
|
|
||
|
//ScbCommandHigh
|
||
|
ucVal = (UCHAR)ReadField(ScbCommandHigh);
|
||
|
dprintf(" ScbCommandHigh - 0x%02x ", ucVal);
|
||
|
if(ucVal & SCB_INT_MASK)
|
||
|
{
|
||
|
dprintf("INT_MASK ");
|
||
|
}
|
||
|
if(ucVal & SCB_SOFT_INT)
|
||
|
{
|
||
|
dprintf("SOFT_INT ");
|
||
|
}
|
||
|
|
||
|
dprintf("\n");
|
||
|
}
|
||
|
|
||
|
DECLARE_API(sendlist)
|
||
|
{
|
||
|
ULONG64 pMpTcb;
|
||
|
ULONG64 pFirstMpTcb;
|
||
|
|
||
|
int ArgCount = 0;
|
||
|
int Verbosity = 0;
|
||
|
int index = 0;
|
||
|
|
||
|
if(*args)
|
||
|
{
|
||
|
ArgCount = sscanf(args,"%I64lx %lx", &pMpTcb, &Verbosity);
|
||
|
}
|
||
|
|
||
|
//check for arguments
|
||
|
if(ArgCount < 1 || Verbosity > 1)
|
||
|
{
|
||
|
dprintf("Usage: sendlist <CurrSendHead> <verbosity>\n");
|
||
|
dprintf("1-Show HW_TCB info\n");
|
||
|
return ;
|
||
|
}
|
||
|
|
||
|
SIGN_EXTEND(pMpTcb);
|
||
|
|
||
|
pFirstMpTcb = pMpTcb;
|
||
|
|
||
|
do
|
||
|
{
|
||
|
dprintf(" (%d) pMpTcb %p : \n", index, pMpTcb);
|
||
|
|
||
|
PrintMpTcbDetails(pMpTcb, Verbosity);
|
||
|
|
||
|
if(GetFieldValue(pMpTcb, "MP_TCB", "Next", pMpTcb))
|
||
|
{
|
||
|
break;
|
||
|
}
|
||
|
|
||
|
index++;
|
||
|
|
||
|
if(CheckControlC())
|
||
|
{
|
||
|
dprintf("***Control-C***\n");
|
||
|
break;
|
||
|
}
|
||
|
|
||
|
} while(pMpTcb != pFirstMpTcb);
|
||
|
|
||
|
}
|
||
|
|
||
|
|
||
|
DECLARE_API(mptcb)
|
||
|
{
|
||
|
ULONG64 pMpTcb;
|
||
|
|
||
|
int ArgCount = 0;
|
||
|
|
||
|
if(*args)
|
||
|
{
|
||
|
ArgCount = sscanf(args,"%I64lx", &pMpTcb);
|
||
|
}
|
||
|
|
||
|
//check for arguments
|
||
|
if(ArgCount < 1)
|
||
|
{
|
||
|
dprintf("Usage: mptcb <MP_TCB>\n");
|
||
|
return ;
|
||
|
}
|
||
|
|
||
|
dprintf(" pMpTcb %p : \n", pMpTcb);
|
||
|
|
||
|
PrintMpTcbDetails(pMpTcb, 1);
|
||
|
|
||
|
}
|
||
|
|
||
|
DECLARE_API(hwtcb)
|
||
|
{
|
||
|
ULONG64 pHwTcb;
|
||
|
|
||
|
int ArgCount = 0;
|
||
|
|
||
|
if(*args)
|
||
|
{
|
||
|
ArgCount = sscanf(args,"%I64lx", &pHwTcb);
|
||
|
}
|
||
|
|
||
|
//check for arguments
|
||
|
if(ArgCount < 1)
|
||
|
{
|
||
|
dprintf("Usage: hwtcb <HW_TCB>\n");
|
||
|
return ;
|
||
|
}
|
||
|
|
||
|
dprintf(" pHwTcb %p : \n", pHwTcb);
|
||
|
|
||
|
PrintHwTcbDetails(pHwTcb);
|
||
|
}
|
||
|
|
||
|
void PrintMpTcbDetails(ULONG64 pMpTcb, int Verbosity)
|
||
|
{
|
||
|
ULONG Flags;
|
||
|
ULONG64 pMpTxBuf;
|
||
|
ULONG64 pHwTcb;
|
||
|
|
||
|
ULONG64 pVal;
|
||
|
ULONG ulVal;
|
||
|
USHORT usVal;
|
||
|
|
||
|
InitTypeRead(pMpTcb, MP_TCB);
|
||
|
|
||
|
dprintf(" Next %p", ReadField(Next));
|
||
|
|
||
|
Flags = (ULONG) ReadField(Flags);
|
||
|
dprintf(" , Flags - 0x%x", Flags);
|
||
|
if(Flags & fMP_TCB_IN_USE)
|
||
|
{
|
||
|
dprintf(" IN_USE");
|
||
|
}
|
||
|
if(Flags & fMP_TCB_USE_LOCAL_BUF)
|
||
|
{
|
||
|
dprintf(" USE_LOCAL_BUF");
|
||
|
}
|
||
|
if(Flags & fMP_TCB_MULTICAST)
|
||
|
{
|
||
|
dprintf(" MULTICAST");
|
||
|
}
|
||
|
|
||
|
dprintf("\n");
|
||
|
|
||
|
if(Flags & fMP_TCB_USE_LOCAL_BUF)
|
||
|
{
|
||
|
|
||
|
pMpTxBuf = ReadField(MpTxBuf);
|
||
|
dprintf(" MpTxBuf = %p", pMpTxBuf);
|
||
|
|
||
|
GetFieldValue(pMpTxBuf, "MP_TXBUF", "NdisBuffer", pVal);
|
||
|
dprintf(" - NdisBuffer = %p", pVal);
|
||
|
|
||
|
GetFieldValue(pMpTxBuf, "MP_TXBUF", "AllocSize", ulVal);
|
||
|
dprintf(" , AllocSize = %d", ulVal);
|
||
|
|
||
|
GetFieldValue(pMpTxBuf, "MP_TXBUF", "AllocVa", pVal);
|
||
|
dprintf(" , AllocVa = %p", pVal);
|
||
|
|
||
|
GetFieldValue(pMpTxBuf, "MP_TXBUF", "pBuffer", pVal);
|
||
|
dprintf(" , pBuffer = %p\n", pVal);
|
||
|
|
||
|
dprintf("\n");
|
||
|
}
|
||
|
|
||
|
if(Flags & fMP_TCB_IN_USE)
|
||
|
{
|
||
|
dprintf(" Packet = %p\n", ReadField(Packet));
|
||
|
|
||
|
pHwTcb = ReadField(HwTcb);
|
||
|
dprintf(" HwTcb = %p , HwTcbPhys = 0x%lx , PrevHwTcb = 0x%x\n",
|
||
|
pHwTcb, (ULONG)ReadField(HwTcbPhys), ReadField(PrevHwTcb));
|
||
|
|
||
|
dprintf(" HwTbd (First) = %p , HwTbdPhys = 0x%x\n",
|
||
|
ReadField(HwTbd), (ULONG)ReadField(HwTbdPhys));
|
||
|
|
||
|
dprintf(" PhysBufCount = %d, BufferCount = %d, FirstBuffer = %p , PacketLength = %d\n",
|
||
|
(ULONG)ReadField(PhysBufCount), (ULONG)ReadField(BufferCount),
|
||
|
ReadField(FirstBuffer), (ULONG)ReadField(PacketLength));
|
||
|
}
|
||
|
|
||
|
dprintf("\n");
|
||
|
|
||
|
if((Flags & fMP_TCB_IN_USE) && Verbosity == 1)
|
||
|
{
|
||
|
PrintHwTcbDetails(pHwTcb);
|
||
|
}
|
||
|
}
|
||
|
|
||
|
void PrintHwTcbDetails(ULONG64 pHwTcb)
|
||
|
{
|
||
|
USHORT HwCbStatus;
|
||
|
USHORT HwCbCommand;
|
||
|
|
||
|
ULONG i;
|
||
|
|
||
|
InitTypeRead(pHwTcb, HW_TCB);
|
||
|
|
||
|
HwCbStatus = (USHORT) ReadField(TxCbHeader.CbStatus);
|
||
|
HwCbCommand = (USHORT) ReadField(TxCbHeader.CbCommand);
|
||
|
|
||
|
dprintf(" TxCbHeader.CbStatus = 0x%04x ,", HwCbStatus);
|
||
|
if(HwCbStatus & CB_STATUS_COMPLETE)
|
||
|
{
|
||
|
dprintf(" COMPLETE");
|
||
|
}
|
||
|
if(HwCbStatus & CB_STATUS_OK)
|
||
|
{
|
||
|
dprintf(" OK");
|
||
|
}
|
||
|
if(HwCbStatus & CB_STATUS_UNDERRUN)
|
||
|
{
|
||
|
dprintf(" UNDERRUN");
|
||
|
}
|
||
|
|
||
|
dprintf("\n");
|
||
|
|
||
|
dprintf(" TxCbHeader.CbCommand = 0x%04x ", HwCbCommand);
|
||
|
for(i = 0; i < sizeof(DbgCbCommandBits)/sizeof(DBG_USHORT_BITS); i++)
|
||
|
{
|
||
|
if(HwCbCommand & DbgCbCommandBits[i].Val)
|
||
|
{
|
||
|
dprintf(", %s", DbgCbCommandBits[i].Name);
|
||
|
}
|
||
|
}
|
||
|
|
||
|
for(i = 0; i < sizeof(DbgCbCommands)/sizeof(DBG_USHORT_VALUE); i++)
|
||
|
{
|
||
|
if((HwCbCommand & CB_CMD_MASK) == DbgCbCommands[i].Val)
|
||
|
{
|
||
|
dprintf(", %s", DbgCbCommands[i].Name);
|
||
|
break;
|
||
|
}
|
||
|
}
|
||
|
|
||
|
if(i == sizeof(DbgCbCommands)/sizeof(DBG_USHORT_VALUE))
|
||
|
{
|
||
|
dprintf(", UNKNOWN COMMAND");
|
||
|
}
|
||
|
|
||
|
dprintf("\n");
|
||
|
|
||
|
dprintf(" TxCbHeader.CbLinkPointer = 0x%x\n", (ULONG)ReadField(TxCbHeader.CbLinkPointer));
|
||
|
|
||
|
if((HwCbCommand & CB_CMD_MASK) == CB_TRANSMIT)
|
||
|
{
|
||
|
dprintf(" TxCbTbdPointer = 0x%08x\n", (ULONG)ReadField(TxCbTbdPointer));
|
||
|
dprintf(" TxCbCount = %d, ", (USHORT)ReadField(TxCbCount));
|
||
|
dprintf("TxCbThreshold = %d, ", (UCHAR)ReadField(TxCbThreshold));
|
||
|
dprintf("TxCbTbdNumber = %d\n", (UCHAR)ReadField(TxCbTbdNumber));
|
||
|
}
|
||
|
}
|
||
|
|
||
|
DECLARE_API(sendqueue)
|
||
|
{
|
||
|
ULONG64 pEntry;
|
||
|
ULONG64 pPacket;
|
||
|
|
||
|
ULONG ulSize;
|
||
|
|
||
|
int ArgCount = 0;
|
||
|
int index = 0;
|
||
|
|
||
|
if(*args)
|
||
|
{
|
||
|
ArgCount = sscanf(args,"%I64lx", &pEntry);
|
||
|
}
|
||
|
|
||
|
//check for arguments
|
||
|
if(ArgCount < 1)
|
||
|
{
|
||
|
dprintf("Usage: sendqueue <SendWaitQueue address>\n");
|
||
|
return ;
|
||
|
}
|
||
|
|
||
|
SIGN_EXTEND(pEntry);
|
||
|
|
||
|
if(!(ulSize = GetTypeSize("NDIS_PACKET_PRIVATE")))
|
||
|
{
|
||
|
dprintf("Failed to get the type size of NDIS_PACKET_PRIVATE\n");
|
||
|
return;
|
||
|
}
|
||
|
|
||
|
dprintf("NDIS_PACKET_PRIVATE size is 0x%x\n", ulSize);
|
||
|
|
||
|
while(pEntry)
|
||
|
{
|
||
|
pPacket = pEntry - ulSize;
|
||
|
if(pPacket > pEntry)
|
||
|
{
|
||
|
dprintf("Invalid pEntry %p\n", pEntry);
|
||
|
break;
|
||
|
}
|
||
|
|
||
|
dprintf(" (%d) pEntry = %p, Pkt = %p\n", index, pEntry, pPacket);
|
||
|
|
||
|
if(ReadPtr(pEntry, &pEntry))
|
||
|
{
|
||
|
break;
|
||
|
}
|
||
|
|
||
|
index++;
|
||
|
|
||
|
if(CheckControlC())
|
||
|
{
|
||
|
dprintf("***Control-C***\n");
|
||
|
break;
|
||
|
}
|
||
|
}
|
||
|
}
|
||
|
|
||
|
DECLARE_API(recvlist)
|
||
|
{
|
||
|
ULONG64 pListHead;
|
||
|
ULONG64 pMpRfd;
|
||
|
ULONG64 pHwRfd;
|
||
|
|
||
|
int ArgCount = 0;
|
||
|
int Verbosity = 0;
|
||
|
int index = 0;
|
||
|
|
||
|
if(*args)
|
||
|
{
|
||
|
ArgCount = sscanf(args,"%I64lx %lx", &pListHead, &Verbosity);
|
||
|
}
|
||
|
|
||
|
//check for arguments
|
||
|
if(ArgCount < 1 || Verbosity > 1)
|
||
|
{
|
||
|
dprintf("Usage: recvlist <RecvList address> <verbosity>\n");
|
||
|
dprintf("1-Show HW_RFD info\n");
|
||
|
return ;
|
||
|
}
|
||
|
|
||
|
SIGN_EXTEND(pListHead);
|
||
|
|
||
|
if(GetFieldValue(pListHead, "LIST_ENTRY", "Flink", pMpRfd))
|
||
|
{
|
||
|
dprintf("Failed to get LIST_ENTRY Flink at %p\n", pListHead);
|
||
|
return;
|
||
|
}
|
||
|
|
||
|
while((pMpRfd != pListHead))
|
||
|
{
|
||
|
dprintf(" (%d) pMpRfd %p :\n", index, pMpRfd);
|
||
|
|
||
|
PrintMpRfdDetails(pMpRfd, Verbosity);
|
||
|
|
||
|
if(GetFieldValue(pMpRfd, "LIST_ENTRY", "Flink", pMpRfd))
|
||
|
{
|
||
|
dprintf("Failed to get LIST_ENTRY Flink at %p\n", pMpRfd);
|
||
|
break;
|
||
|
}
|
||
|
|
||
|
index++;
|
||
|
|
||
|
if(CheckControlC())
|
||
|
{
|
||
|
dprintf("***Control-C***\n");
|
||
|
break;
|
||
|
}
|
||
|
}
|
||
|
|
||
|
dprintf("RecvList has %d RFDs\n", index);
|
||
|
|
||
|
}
|
||
|
|
||
|
DECLARE_API(mprfd)
|
||
|
{
|
||
|
ULONG64 pMpRfd;
|
||
|
|
||
|
int ArgCount = 0;
|
||
|
|
||
|
if(*args)
|
||
|
{
|
||
|
ArgCount = sscanf(args,"%I64lx", &pMpRfd);
|
||
|
}
|
||
|
|
||
|
//check for arguments
|
||
|
if(ArgCount < 1)
|
||
|
{
|
||
|
dprintf("Usage: mprfd <MP_RFD>\n");
|
||
|
return ;
|
||
|
}
|
||
|
|
||
|
dprintf(" pMpRfd %p : \n", pMpRfd);
|
||
|
|
||
|
PrintMpRfdDetails(pMpRfd, 1);
|
||
|
}
|
||
|
|
||
|
DECLARE_API(hwrfd)
|
||
|
{
|
||
|
ULONG64 pHwRfd;
|
||
|
|
||
|
int ArgCount = 0;
|
||
|
|
||
|
if(*args)
|
||
|
{
|
||
|
ArgCount = sscanf(args,"%I64lx", &pHwRfd);
|
||
|
}
|
||
|
|
||
|
//check for arguments
|
||
|
if(ArgCount < 1)
|
||
|
{
|
||
|
dprintf("Usage: hwrfd <HW_RFD>\n");
|
||
|
return ;
|
||
|
}
|
||
|
|
||
|
dprintf(" pHwRfd = %p : \n", pHwRfd);
|
||
|
|
||
|
PrintHwRfdDetails(pHwRfd);
|
||
|
}
|
||
|
|
||
|
void PrintMpRfdDetails(ULONG64 pMpRfd, int Verbosity)
|
||
|
{
|
||
|
ULONG64 pHwRfd;
|
||
|
|
||
|
ULONG Flags;
|
||
|
|
||
|
InitTypeRead(pMpRfd, MP_RFD);
|
||
|
|
||
|
dprintf(" Flink %p", ReadField(List.Flink));
|
||
|
dprintf(" , Blink %p\n", ReadField(List.Blink));
|
||
|
|
||
|
pHwRfd = ReadField(HwRfd);
|
||
|
dprintf(" NdisPacket = %p , NdisBuffer = %p , HwRfd = %p\n",
|
||
|
ReadField(NdisPacket), ReadField(NdisBuffer), pHwRfd);
|
||
|
|
||
|
dprintf(" PacketSize = %d, ", (ULONG) ReadField(PacketSize));
|
||
|
|
||
|
Flags = (ULONG) ReadField(Flags);
|
||
|
dprintf("Flags 0x%x", Flags);
|
||
|
if(Flags & fMP_RFD_RECV_PEND)
|
||
|
{
|
||
|
dprintf(" RECV_PEND ");
|
||
|
}
|
||
|
if(Flags & fMP_RFD_ALLOC_PEND)
|
||
|
{
|
||
|
dprintf(" ALLOC_PEND ");
|
||
|
}
|
||
|
if(Flags & fMP_RFD_RECV_READY)
|
||
|
{
|
||
|
dprintf(" RECV_READY ");
|
||
|
}
|
||
|
if(Flags & fMP_RFD_RESOURCES)
|
||
|
{
|
||
|
dprintf(" RESOURCES ");
|
||
|
}
|
||
|
|
||
|
|
||
|
dprintf("\n");
|
||
|
|
||
|
if(Verbosity == 1)
|
||
|
{
|
||
|
PrintHwRfdDetails(pHwRfd);
|
||
|
}
|
||
|
}
|
||
|
|
||
|
void PrintHwRfdDetails(ULONG64 pHwRfd)
|
||
|
{
|
||
|
USHORT RfdStatus;
|
||
|
USHORT RfdCommand;
|
||
|
|
||
|
ULONG i;
|
||
|
|
||
|
InitTypeRead(pHwRfd, HW_RFD);
|
||
|
|
||
|
RfdStatus = (USHORT) ReadField(RfdCbHeader.CbStatus);
|
||
|
RfdCommand = (USHORT) ReadField(RfdCbHeader.CbCommand);
|
||
|
|
||
|
dprintf(" RfdCbHeader.CbStatus = 0x%04x", RfdStatus);
|
||
|
|
||
|
for(i = 0; i < sizeof(DbgRfdStatus)/sizeof(DBG_RFD_STATUS); i++)
|
||
|
{
|
||
|
if(RfdStatus & DbgRfdStatus[i].Val)
|
||
|
{
|
||
|
dprintf(", %s", DbgRfdStatus[i].Name);
|
||
|
}
|
||
|
}
|
||
|
|
||
|
dprintf("\n");
|
||
|
|
||
|
dprintf(" RfdCbHeader.CbCommand = %04x", RfdCommand);
|
||
|
for(i = 0; i < sizeof(DbgRfdCommand)/sizeof(DBG_RFD_COMMAND); i++)
|
||
|
{
|
||
|
if(RfdCommand & DbgRfdCommand[i].Val)
|
||
|
{
|
||
|
dprintf(", %s", DbgRfdCommand[i].Name);
|
||
|
}
|
||
|
}
|
||
|
|
||
|
dprintf("\n");
|
||
|
|
||
|
dprintf(" RfdCbHeader.CbLinkPointer = 0x%x\n", (ULONG)ReadField(RfdCbHeader.CbLinkPointer));
|
||
|
//dprintf(" RfdRbdPointer = 0x%x\n", (ULONG)ReadField(RfdRbdPointer));
|
||
|
dprintf(" RfdActualCount = %x , %d", (USHORT)ReadField(RfdActualCount), (USHORT)ReadField(RfdActualCount) & 0x3fff);
|
||
|
dprintf(", RfdSize = %d\n", (USHORT)ReadField(RfdSize));
|
||
|
}
|
||
|
|
||
|
DECLARE_API(recvpendlist)
|
||
|
{
|
||
|
ULONG64 pListHead;
|
||
|
ULONG64 pMpRfd;
|
||
|
ULONG64 pPacket;
|
||
|
|
||
|
int ArgCount = 0;
|
||
|
int index = 0;
|
||
|
|
||
|
if(*args)
|
||
|
{
|
||
|
ArgCount = sscanf(args,"%I64lx", &pListHead);
|
||
|
}
|
||
|
|
||
|
//check for arguments
|
||
|
if(ArgCount < 1)
|
||
|
{
|
||
|
dprintf("Usage: recvpendlist <RecvPendList address>\n");
|
||
|
return ;
|
||
|
}
|
||
|
|
||
|
SIGN_EXTEND(pListHead);
|
||
|
|
||
|
if(GetFieldValue(pListHead, "LIST_ENTRY", "Flink", pMpRfd))
|
||
|
{
|
||
|
dprintf("Failed to get LIST_ENTRY Flink at %p\n", pListHead);
|
||
|
return;
|
||
|
}
|
||
|
|
||
|
while(pMpRfd != pListHead)
|
||
|
{
|
||
|
dprintf(" (%d) pMpRfd %x :\n", index, pMpRfd);
|
||
|
|
||
|
PrintMpRfdDetails(pMpRfd, 0);
|
||
|
|
||
|
if(GetFieldValue(pMpRfd, "LIST_ENTRY", "Flink", pMpRfd))
|
||
|
{
|
||
|
dprintf("Failed to get LIST_ENTRY Flink at %p\n", pMpRfd);
|
||
|
break;
|
||
|
}
|
||
|
|
||
|
index++;
|
||
|
|
||
|
if(CheckControlC())
|
||
|
{
|
||
|
dprintf("***Control-C***\n");
|
||
|
break;
|
||
|
}
|
||
|
}
|
||
|
|
||
|
dprintf("RecvPendList has %d RFDs\n", index);
|
||
|
|
||
|
}
|
||
|
|
||
|
|
||
|
/**
|
||
|
Get 'size' bytes from the debuggee program at 'dwAddress' and place it
|
||
|
in our address space at 'ptr'. Use 'type' in an error printout if necessary
|
||
|
**/
|
||
|
BOOL GetData( IN LPVOID ptr, IN ULONG64 AddressPtr, IN ULONG size, IN PCSTR type )
|
||
|
{
|
||
|
BOOL b;
|
||
|
ULONG BytesRead;
|
||
|
ULONG count = size;
|
||
|
|
||
|
while(size > 0)
|
||
|
{
|
||
|
|
||
|
if(count >= 3000)
|
||
|
count = 3000;
|
||
|
|
||
|
b = ReadMemory(AddressPtr, ptr, count, &BytesRead );
|
||
|
|
||
|
if(!b || BytesRead != count)
|
||
|
{
|
||
|
dprintf( "Unable to read %u bytes at %X, for %s\n", size, AddressPtr, type );
|
||
|
return FALSE;
|
||
|
}
|
||
|
|
||
|
AddressPtr += count;
|
||
|
size -= count;
|
||
|
ptr = (LPVOID)((ULONG_PTR)ptr + count);
|
||
|
}
|
||
|
|
||
|
return TRUE;
|
||
|
}
|
||
|
|
||
|
/**
|
||
|
|
||
|
Routine to get offset and size of a "Field" of "Type" on a debugee machine. This uses
|
||
|
Ioctl call for type info.
|
||
|
Returns 0 on success, Ioctl error value otherwise.
|
||
|
|
||
|
**/
|
||
|
ULONG GetFieldOffsetAndSize(
|
||
|
IN LPSTR Type,
|
||
|
IN LPSTR Field,
|
||
|
OUT PULONG pOffset,
|
||
|
OUT PULONG pSize)
|
||
|
{
|
||
|
FIELD_INFO flds = {
|
||
|
Field, "", 0,
|
||
|
DBG_DUMP_FIELD_FULL_NAME | DBG_DUMP_FIELD_RETURN_ADDRESS | DBG_DUMP_FIELD_SIZE_IN_BITS,
|
||
|
0, NULL};
|
||
|
SYM_DUMP_PARAM Sym = {
|
||
|
sizeof (SYM_DUMP_PARAM), Type, DBG_DUMP_NO_PRINT, 0,
|
||
|
NULL, NULL, NULL, 1, &flds
|
||
|
};
|
||
|
ULONG Err, i=0;
|
||
|
LPSTR dot, last=Field;
|
||
|
|
||
|
Sym.nFields = 1;
|
||
|
Err = Ioctl( IG_DUMP_SYMBOL_INFO, &Sym, Sym.size );
|
||
|
*pOffset = (ULONG) (flds.address - Sym.addr);
|
||
|
*pSize = flds.size;
|
||
|
return Err;
|
||
|
}
|
||
|
|
||
|
ULONG GetUlongFromAddress (
|
||
|
ULONG64 Location)
|
||
|
{
|
||
|
ULONG Value;
|
||
|
ULONG result;
|
||
|
|
||
|
if((!ReadMemory(Location,&Value,sizeof(ULONG),&result)) ||
|
||
|
(result < sizeof(ULONG)))
|
||
|
{
|
||
|
dprintf("unable to read from %08x\n",Location);
|
||
|
return 0;
|
||
|
}
|
||
|
|
||
|
return Value;
|
||
|
}
|
||
|
|
||
|
ULONG64 GetPointerFromAddress(
|
||
|
ULONG64 Location)
|
||
|
{
|
||
|
ULONG64 Value;
|
||
|
ULONG result;
|
||
|
|
||
|
if(ReadPtr(Location,&Value))
|
||
|
{
|
||
|
dprintf("unable to read from %p\n",Location);
|
||
|
return 0;
|
||
|
}
|
||
|
|
||
|
return Value;
|
||
|
}
|
||
|
|
||
|
ULONG GetUlongValue (
|
||
|
PCHAR String)
|
||
|
{
|
||
|
ULONG64 Location;
|
||
|
ULONG Value;
|
||
|
ULONG result;
|
||
|
|
||
|
Location = GetExpression(String);
|
||
|
if(!Location)
|
||
|
{
|
||
|
dprintf("unable to get %s\n",String);
|
||
|
return 0;
|
||
|
}
|
||
|
|
||
|
return GetUlongFromAddress(Location);
|
||
|
}
|
||
|
|
||
|
ULONG64 GetPointerValue (
|
||
|
PCHAR String)
|
||
|
{
|
||
|
ULONG64 Location, Val=0;
|
||
|
|
||
|
Location = GetExpression(String);
|
||
|
if(!Location)
|
||
|
{
|
||
|
dprintf("unable to get %s\n",String);
|
||
|
return 0;
|
||
|
}
|
||
|
|
||
|
ReadPtr(Location, &Val);
|
||
|
|
||
|
return Val;
|
||
|
}
|
||
|
|
||
|
|