Differences between dd /p and !dd?

Hi All,

For some background, I’m working on creating a driver for a prototype
PCI card and have been running into problems accessing the card’s memory
space. So to rule out the driver, I have been attempting to access the
card directly via windbg.

From windbg I can read the pci configuration space ok and it appears
correct. I see from this that BAR0 is setup correctly with a physical
address, (which I verified from pte! and does indeed map to the correct
virtual address space via MmMapIoSpace in the driver).

However, when my driver reads a 32 bit register:

reg = READ_REGISTER_ULONG((PULONG)((ULONG_PTR)DevExt->BAR0 + Register))

it sees 0xFFFFFFFF, which is incorrect.

So, I have been using both the !dd, dd, and dd /p[uc] commands to try
and read from BAR0. Here are some results:

0: kd> N 16
base is 16

//////////////////////////////////////////////////////////////////////////////////
// This should be read physical memory location
// - with the physical address supplied - from BAR0
// - according to my understanding of windbg help
//////////////////////////////////////////////////////////////////////////////////

0: kd> !dd [uc] -m fceffc00 L1

0 f000eef3 f000eef3 f000e2c3 f000eef3

10 f000eef3 f000ff54 f00006e1 f0000689

20 9fc0002f f000e987 f000eef3 f000eef3

30 f000eef3 f000eef3 f000ef57 e9f90000

40 c0001729 f000f84d f000f841 f00080b8

50 f000b30e 9fc00020 f000e82e f000efd2

60 f000e000 f000e6f2 9fc0002a f000ff53

70 f000ff53 f000f0a4 f000efc7 c0002790

//////////////////////////////////////////////////////////////////////////////////
// This should also be read physical memory (with the /p option) ???
//////////////////////////////////////////////////////////////////////////////////

0: kd> dd /p[uc] fceffc00 L1
fceffc00 ffffffff

//////////////////////////////////////////////////////////////////////////////////
// This should be a standard virtual address read
// - supplied with the virtual address obtained from MmMapIoSpace
//////////////////////////////////////////////////////////////////////////////////

0: kd> dd 0xF7E89C00 L1
// TARGET MACHINE HANGS FOREVER - SO DOES WINDBG!

Ok, so anyone want to point out to me what I’m missing - since 2
commands exist to read physical memory and each returns something
different? Also, any guess why a typical virtual memory read is
probably hanging the bus? (Again - this is prototype hardware, so any
info will help me in determining if its bad hw or if I’m out in left field).

Thanks in Advance!!!
-Mike

Michael Becker wrote:

For some background, I’m working on creating a driver for a prototype
PCI card and have been running into problems accessing the card’s
memory space. So to rule out the driver, I have been attempting to
access the card directly via windbg.
From windbg I can read the pci configuration space ok and it appears
correct. I see from this that BAR0 is setup correctly with a physical
address, (which I verified from pte! and does indeed map to the
correct virtual address space via MmMapIoSpace in the driver).

However, when my driver reads a 32 bit register:
reg = READ_REGISTER_ULONG((PULONG)((ULONG_PTR)DevExt->BAR0 +
Register))
it sees 0xFFFFFFFF, which is incorrect.

Have you scoped out your PCI card to make sure it is seeing the PCI read
cycles when you do this?

Where did you get BAR0? Did that come from the resources pumped into
StartDevice, passed through MmMapIoSpace? So, this is a normal WDM PNP
driver?

So, I have been using both the !dd, dd, and dd /p[uc] commands to try
and read from BAR0. Here are some results:

//////////////////////////////////////////////////////////////////////////////////

// This should be read physical memory location
// - with the physical address supplied - from BAR0
// - according to my understanding of windbg help
//////////////////////////////////////////////////////////////////////////////////

0: kd> !dd [uc] -m fceffc00 L1

0 f000eef3 f000eef3 f000e2c3 f000eef3

10 f000eef3 f000ff54 f00006e1 f0000689

20 9fc0002f f000e987 f000eef3 f000eef3

30 f000eef3 f000eef3 f000ef57 e9f90000

40 c0001729 f000f84d f000f841 f00080b8

50 f000b30e 9fc00020 f000e82e f000efd2

60 f000e000 f000e6f2 9fc0002a f000ff53

70 f000ff53 f000f0a4 f000efc7 c0002790

You aren’t dumping what you think you are dumping. This is physical
address 0: the real-mode interrupt table. Note how most of them point
in to the standard BIOS (F000:xxxx), and INT 10 points to the video BIOS
(C000:xxxx). From my experiments, it looks to me like the “-m” option
screws up the command line parser. Note how it has also ignored your
“L1”. I’m not sure “-m” makes sense with dd or !dd anyway. What do
you get with a simple “!dd fceffc00” ? I’ll bet it’s more ffffffff’s.

//////////////////////////////////////////////////////////////////////////////////

// This should be a standard virtual address read
// - supplied with the virtual address obtained from MmMapIoSpace
//////////////////////////////////////////////////////////////////////////////////

0: kd> dd 0xF7E89C00 L1
// TARGET MACHINE HANGS FOREVER - SO DOES WINDBG!

So, you dumped DevExt->BAR0, and it is F7E89C00?

Ok, so anyone want to point out to me what I’m missing - since 2
commands exist to read physical memory and each returns something
different? Also, any guess why a typical virtual memory read is
probably hanging the bus? (Again - this is prototype hardware, so any
info will help me in determining if its bad hw or if I’m out in left
field).

Well, the !dd command is screwed up, so it appears that all of the
physical address reads are reading the same thing: ffffffff. That often
signals a read cycle that was not claimed. I would begin to suspect
that the card isn’t responding. I think a few minutes with an
oscilloscope would be useful.


Tim Roberts, xxxxx@probo.com
Providenza & Boekelheide, Inc.

Tim and Jerry, thank you both very much for the replies, and for the
information regarding the “quirky” !dd command!

This is a prototype PCI board, so I had my suspicions regarding the
hardware, but couldn’t really push back on the hw designer until I could
resolve in my head just what Windbg was doing. Now that I have this
information, the hw engineer is admitting that there might be a problem
with the address timing, etc. and is looking into it. (To my dismay I
found these proto boards were never scoped or put on a bus analyzer to
check memory access before being dropped in my lap - *grumble*).

To wrap this thread up, let me answer the questions asked:

This is a standard WDM Pnp PCI driver.

The PCI config command register is set to 0x0157 - so MemSpaceEnable is
on - found out via the “!pci 0x101 …” Windbg command.

BAR0 came from both the above command run after the IRP_MJ_PNP,
IRP_MN_START_DEVICE IRP has completed, as well as from the resource list
obtained from Windows. (They of course match). (For the physical
address of BAR0).

The virtual BAR0 address was obtained from <virtual_address> =
MmMapIoSpace (<physical_address>, …).

After reading your responses, I am thinking that using the command “dd
<virtual_address>” where <virtual_address> maps to a PCI memory space
might not actually work right (due to caching, etc.), but the “dd /p[uc]
<physical_address>” is probably doing the right thing, just with broken
hardware.

Thanks again!
-Mike</physical_address></virtual_address></virtual_address></physical_address></virtual_address>