News:

MASM32 SDK Description, downloads and other helpful links
MASM32.com New Forum Link
masmforum WebSite

Another HDD Activity Monitor

Started by Phoenix, March 26, 2006, 12:06:37 AM

Previous topic - Next topic

Phoenix

Based on MichaelW's HDD Activity Monitor code, i tried to find another way to show hdd activity without using pdh.dll-functions.

The attachment is another HDD Activity Monitor, based on DeviceIoControl from kernel32.dll using IOCTL_DISK_PERFORMANCE control code. It works on my WinXP Pro SP2-box and should also work on W2K boxes (the icons might look strange there, i was not able to test it yet).

ATA-, SATA and USB-Devices are monitored on my system in summary. Changes of USB-Devices caused problems (WM_DEVICECHANGE does not report DBT_DEVICEQUERYREMOVE/DBT_DEVICEREMOVEPENDING without a registration for device event notification) so the handles are retrieved in each timer procedure call as a workaround.

BTW, i needed to add four extra bytes to the DISK_PERFORMANCE struct, does somebody know the reason? http://msdn.microsoft.com/library/default.asp?url=/library/en-us/fileio/fs/disk_performance_str.asp

Regards, Phoenix

[attachment deleted by admin]

Mark Jones

Nice Phoenix! I just noticed that "DiskMon" from System Internals has a "minimize to tray icon" feature, but it's nowhere near as fast or nice as HDDMon. That said, thier "FileMon" product doesn't exactly sync with HDDMon - sometimes FileMon shows activity when HDDMon doesn't, and vice-versa. HDDMon seems to be showing writes which are reads according to FileMon.

Curious, would it be possible to log which applications or threads read or write in HDDMon?
"To deny our impulses... foolish; to revel in them, chaos." MCJ 2003.08

Phoenix

QuoteThat said, thier "FileMon" product doesn't exactly sync with HDDMon

Mark, it seems to me that DiskMon from System Internals logs requests for read/write operations, while HddMon ist reporting what has happend physically on the disk (MSDN: DeviceIoCcontrol: Number of Bytes written i. e.). This could possibly cause asynchronous behaviour (?)

AFAIK, DeviceIoControl has no options to trace applications or threads that cause disk activity.

MichaelW

Phoenix,

Nice work, I like the ability to differentiate between reads and writes.

After experimenting with your code the only reason I can see that the four fill bytes would be required is that the function is returning the 8-character Unicode string "PhysDisk" in the StorageManagerName member, and the terminating 00 word overflows the structure. I have no idea why appending a word to the end of the structure will not correct the problem.

For my version I am now using a timer period of 30ms. I tested shorter timer periods but the apparent disk activity decreased, I think because for the shorter disk activity periods the indicator "on" time was too short to be readily visible. Compared to your version mine shows considerably more disk activity. After changing the timer period for your code to 30ms, both versions show, as nearly as I can tell, the same level of disk activity.

Under Windows 2000 the icons work OK, but on my system they are sized for young eyeballs. When I was experimenting with icons I tried an animated icon that was modeled after the icon that ZoneAlarm displays when there is Internet activity. Basically, the ZoneAlarm icon is two stacks with up to 5 bars each, with green bars for IN and red bars for OUT, and with the number of bars in each stack indicating the level of activity. My icon used just a single stack of green bars, and I calculated the number of bars to display from the % Disk Time value. I eventually discarded the design when I had some (relatively minor) problems with the icons not displaying correctly in the notification area, even though they would display correctly elsewhere, coupled with severe flicker problems. On my system the ZoneAlarm icon has the problem with not displaying correctly, but not the flicker problem.

Quote from: Mark Jones on March 26, 2006, 03:02:10 AM
Curious, would it be possible to log which applications or threads read or write in HDDMon?

This occurred to me too as potentially useful information, but I could see no way to do it without some very low-level code.

eschew obfuscation

Phoenix

Michael,

thank you for your feedback.

Quotethe function is returning the 8-character Unicode string "PhysDisk" in the StorageManagerName member

On my box the function is returning "Partmgr" in the StorageManagerName member, which is a 7-character Unicode string, causing the same problem. However, the four extra bytes seem to be always set to zero. Perhaps the structure member "WCHAR StorageManagerName[8]" is wrong in MSDN and should be "WCHAR StorageManagerName[10]" according to this:

From http://www.osronline.com/ddkx/storage/k306_950y.htm

QuoteStorageManagerName
Contains an 8-character string that indicates which device driver provided the performance statistics. In Windows® 2000, this can be either "LogiDisk" for the driver logidisk.sys or "PhysDisk" for the driver physdisk.sys. These drivers collect performance statistics for devices and physical disks respectively. In Windows XP and later operating systems, this can be any of the following three strings: "FTDISK" for the driver ftdisk.sys, "DMIO" for the driver dmio.sys, or PARTMGR" for the driver partmgr.sys. These three drivers collect performance statistics for basic disk volumes, dynamic disk volumes, and physical disks respectively. Note that these strings are 8-character case-sensitive strings with blank fill. For example, in the case of the string "FTDISK", the StorageManagerName character array should contain two trailing blanks ("FTDISK<b><b>"), and in the case of the string "DMIO", the array should contain four trailing blanks ("DMIO<b><b><b><b>").

So, at least one WCHAR for the terminating 00 is missing in the structure, but two WCHARs are needed...(Size=88 bytes => DWORD alignment?)

Quoteboth versions show, as nearly as I can tell, the same level of disk activity.

DeviceIoControl / IOCTL_DISK_PERFORMANCE seem to collect the data for the PhysicalDisk performance object (pdh.dll), your results may comfirm this.

QuoteCurious, would it be possible to log which applications or threads read or write in HDDMon?
This occurred to me too as potentially useful information, but I could see no way to do it without some very low-level code

There is an interesting topic on MSDN about tracing disk I/0 events using StartTrace function from Advapi32.dll:
http://windowssdk.msdn.microsoft.com/library/default.asp?url=/library/en-us/etw/etw/i_o_events.asp

QuoteYou can use the ThreadId members of EVENT_TRACE_HEADER to identify the thread that requested the IO operation. If you also collect process and thread events, you can trace disk IO operations to a process.

QuoteUnder Windows 2000 the icons work OK, but on my system they are sized for young eyeballs.

Well, the design of these icons took more time than the coding itself... i have done at least five different sets but none of them is really satisfying. I think using something like the ZoneAlarm icon is a very good idea, but unfortunately i'm really no good designer... perhaps somebody has some good icons for this purpose?

MichaelW

After building a test app with the Microsoft Visual C++ Toolkit 2003 it looks like the compiler is adding a 4-byte pad to the end of the structure. I'm guessing that this has nothing to do with alignment, it's just Microsoft silently hiding a mistake :toothy



[attachment deleted by admin]
eschew obfuscation

PBrennick

On my machine I have been watching the HDD LED and your red light and the two seem to be perfectly in sync.

Paul
The GeneSys Project is available from:
The Repository or My crappy website

Phoenix

Michael,

... a very strage strategy to hide an error, but Microsoft is always good for a surprise  :bdg

Well, i have tested HddMon on my office W2K box, and i needed a magnifying glass to see the icons... The attached file is HddMon with another set of icons (handmade, tested with W2K and XP) and some minor modifications in the Timer proc.

Phoenix

[attachment deleted by admin]

MichaelW

Thanks Phoenix,

Under Windows 2000 the new icons look great in Explorer, but in the notification area the diagonal edges are visibly jagged, and irregular.

BTW, the code to restore the foreground window does not work (this should have been obvious to me), and making it work would involve too much monkey motion, so I just eliminated it from my version.

eschew obfuscation

Mark Jones

Great work. Here's a RadASM project file and some alternate icons. Not as pretty but can't miss 'em.

[attachment deleted by admin]
"To deny our impulses... foolish; to revel in them, chaos." MCJ 2003.08

Emperor

Works great on my computer :bg

Just love the icons!

Phoenix

MichaelW,

Thanks! Only the rw.ico has a 32X32 and a 16x16 icon, the others are 16x16 only... so they look jagged, i should add 32x32 icons to the others too. BTW, what exactly does not work? I can see nothing wrong with restoring the foreground window code....

Mark,

Thank you for your icons! I'm just working on a similar set based on these icons.

Emperor,

thank you for your feedback. Works on XP or W2K?

MichaelW

As I stated, the icons look great everywhere but the notification area, and I think you made good choices on the design. Now that I look at the na icon in an icon editor, I see that the colors are irregular, and this might contribute to what I am seeing, but I think the real problem is something in the way Windows 2000 handles the notification area.

On my Windows 2000 system, the first SetForegroundWindow works, so the menu closes properly when you open it and then click somewhere else, but the second SetForegroundWindow fails when you do this.

And I think this behavior should be the same on Windows XP:

MSDN: SetForegroundWindow


          Invoke GetForegroundWindow
          push   eax
          Invoke SetForegroundWindow, hWin

          Invoke GetCursorPos,addr pt
          Invoke TrackPopupMenu, hPopupMenu, TPM_RIGHTALIGN,
            pt.x, pt.y, NULL, hWin, NULL

          pop    eax
          Invoke SetForegroundWindow, eax
          .IF eax == 0
            MsgBox 0,"SetForegroundWindow failed",0,0
          .ENDIF

eschew obfuscation

PBrennick

Phoenix,
Looks great on my XP box!

Michael,
What means 'notification area?'

Paul
The GeneSys Project is available from:
The Repository or My crappy website

MichaelW

Hi Paul,

taskbar notification area, AKA system tray

eschew obfuscation