-
December 14th, 2009, 03:18 AM
#1
Direct Hardware Access???
I really have no idea where to put this but since I'm using VC++98 and dealing with WinXP I chose here . I know the simple answer is no :/ ..... But is there a way.... any way to get direct hardware access in windows? This is so I can read video memory. (It would be a bonus to write it as well but I can live without that).
What I'm doing atm is: 1) capturing the the screen (BitBlt()), 2) Converting the image to greyscale, 3) Sobel edge detection and 4) drawing the buffer to my app window. 5) Repeat
I'm trying to eliminate the biggest bottleneck... As you can see from the benchmarked 1 minute runs below is (drum roll please)
Code:
Iter/min Iter/sec Sec/Iteration
1100 18.33333333 0.054545455 -- BitBlt()
10100 168.3333333 0.005940594 --RGB->G
3650 60.83333333 0.016438356 --Sobel
6300 105 0.00952381 --OGL calls to draw buffer
I was like :OOOOOOOOO. That is completely ridiculous. I just started SSE stuff. I'm sure I can get 40k+ iterations/min (probably >50k) copying the screen to memory if I had direct access to read the video memory. That alone would bring my ~11.5fps to ~30+fps. It shocked me that copying the screen takes more time then edge detection!
I'll take any option that allows me to run this while running windows. I essentially have one monitor as the desktop that I work on. And the other monitor runs this app. Did I overlook some OGL function that would help me? I'll take that as an option (although it'll pale in comparison to SSE memcpy)..... it seems like just about anything is better than BitBlt.
Thanks for your help
-
December 14th, 2009, 03:32 AM
#2
Re: Direct Hardware Access???
OpenGL and DirectX have direct access. Maybe you should take a look at one of them.
-
December 14th, 2009, 06:25 AM
#3
Re: Direct Hardware Access???
One of my weaknesses is my memory. I'm sure I did look at OGL but I don't thin k I found anything that could copy the desktop window..... I think I found something that could capture an app window. I'll look again.
-
December 15th, 2009, 07:12 AM
#4
Re: Direct Hardware Access???
DirectX might make it give more performance, but there is no direct hardware access. The Surface pointer that you get with DirectX is the same as what kernel driver get.
Regards,
Ramkrishna Pawar
-
December 15th, 2009, 12:09 PM
#5
Re: Direct Hardware Access???
The fastest way to do something is, obviously, to not do it at all
Who paints the screen that you want to capture? Could you get your data from them directly, bypassing the access to you hardware?
Vlad - MS MVP [2007 - 2012] - www.FeinSoftware.com
Convenience and productivity tools for Microsoft Visual Studio:
FeinWindows - replacement windows manager for Visual Studio, and more...
-
December 15th, 2009, 12:37 PM
#6
Re: Direct Hardware Access???
Windows exported direct screen memory pointers until Windows 3.1. The issue is that there is no "video memory" direct access with "enhanced mode" (Microsoft term) or what is now commonly called "virtual mode". There is a translation layer in Windows (HAL) that talks to the hardware and that is the only thing that can actually access the video buffer at B800:0000 (originally exported as a universal constant pointer _B8000).
Now if you have a dirty DOS program that directly accesses the video memory, Windows will intercept that and paint it in a window. You can easily get a handle to the window (take a look at the console routines) and read everything pasted there. That is once removed, but that is the best you can safely do. If you are really desparate, most video drivers have a back door for testing that allows access to the video memory, but you need to get that info from the manufacturer.
DirectX accesses the extended memory on a video device, but I believe the video memory for acual painting (what is called the Primary Buffer) is blocked for user access.
-
December 15th, 2009, 02:04 PM
#7
Re: Direct Hardware Access???
Originally Posted by egawtry
DirectX accesses the extended memory on a video device, but I believe the video memory for acual painting (what is called the Primary Buffer) is blocked for user access.
This is correct and one of the main differences between Win9x and NT-based systems (like XP). For compatibility reasons, Win9x allowed video memory access, but NT did not because of security and stability reasons.
-
December 15th, 2009, 02:26 PM
#8
Re: Direct Hardware Access???
Originally Posted by Skizmo
OpenGL and DirectX have direct access. Maybe you should take a look at one of them.
Amazingly OpenGL glReadPixels is slower. I only benchmarked the whole loop not that call so it is possible ReadPixels is faster but I need to make a RC switch and that might be slowing me down. Brought me down to about 6.5 fps.
Originally Posted by VladimirF
.... Who paints the screen that you want to capture? Could you get your data from them directly, bypassing the access to you hardware?
The OS (Windows XP Home) paints the screen . I'm doing a full screen capture.
---------------------------------------------------------------------------
@Krishnaa & Skizmo: I'm not too familiar with DX as I always thought it better to work with things that are not OS specific. I'll take a look into it over the next few days.
@egawtry: Thanks for sharing your knowledge. It's been many many years since I did assembly with DOS. IDK id it's possible to have resolutions as large as my screen though in a console app (1200x800). I'm going to try out the backdoor root through the drivers.... hopefully one (or two) manufacturers I have video cards for will be nice and help out. Although if the DX route works out I may not choose that route as that will get me to about 24 fps if it's comparable to OGL write speeds..... well I may not pursue it until I get to the next step in this little project
Thanks guys for your help
-
December 15th, 2009, 02:46 PM
#9
Re: Direct Hardware Access???
Originally Posted by robione
I'm trying to eliminate the biggest bottleneck... As you can see from the benchmarked 1 minute runs below is (drum roll please)
Before posting any timing data, you need to specify the compiler, compiler version, and compiler options used to build the test.
If you are timing an unoptimized, "debug" build, then those numbers you're showing are meaningless. Only release, optimized builds are valid in timing tests.
Regards,
Paul McKenzie
-
December 16th, 2009, 06:50 PM
#10
Re: Direct Hardware Access???
I understand your point Paul but given the timing data I don't think one could argue too much that the bottleneck is reading the screen data. The difference in timing compared to the rest of the loop is just too great.
That being said those times were from debug builds because at the time I had not coded in a way to view the iterations/unit time while the program was running. I basically ran the debugger to the cursor and looked at the 'count' variable. I just wrapped the timing code around whichever part I was measuring. It basically is
Code:
while(!WM_QUIT) {
time_i = time_f;
//Stuff above loop
while(time_f - time_i < 60000) {
//Code to measure
inc count
update time_f
}
//Stuff below loop
}
Since this thread began I have coded in the ability to display the timing during execution. The release build times are:
Code:
Iter/min Iterations/sec Sec/Iter
1160 19.33333333 0.051724138 --BitBlt
11400 190 0.005263158 --RGB->G
4380 73 0.01369863 --Sobel
7700 128.3333333 0.007792208 --OpenGL
The improvements to RGB->G conversion and Sobel are not from changing build types. They are both coded in assembly. The improvements came from changing a loop instruction to the dec/cmp/jnz equivalent in the greyscale conversion. For Sobel it was simply doing less math and optimizing the algorithm. The BitBlt improvement..... there really isn't one as I rounded down to 1100. I the original was ~1140. All the numbers posted are towards the slower times... but a fast time for BitBlt is like 1180. Not much of a difference.
I'm using multimedia timers with 1msec resolution for timing.
CPU: Intel Atom N270 1.6GHz Single core
GFX: Intel 945 Express Chipset
Compiler: VC++ 98 SP5 w/ Processor Pack
Compiler options: /nologo /ML /W3 /GX /O2 /D "WIN32" /D "NDEBUG" /D "_WINDOWS" /D "_MBCS" /Fp"Release/edge.pch" /Yu"stdafx.h" /Fo"Release/" /Fd"Release/" /FD /c
And the DirectX route seems to be no better than OGL. As I was downloading the DX SDK I read an article here (http://www.codeproject.com/KB/dialog/screencap.aspx) that explained how to do screen captures using three methods (Win API, DX and, via WMEncoder). Apparently BitBlt wins the battle :/
-
December 16th, 2009, 06:59 PM
#11
Re: Direct Hardware Access???
Originally Posted by robione
Apparently BitBlt wins the battle :/
The issue with this is that BitBlt depends solely on the device context you're writing to. Since you are writing to the screen, BitBlt is highly dependent on the video hardware being used, video driver, etc.
Regards,
Paul McKenzie
Posting Permissions
- You may not post new threads
- You may not post replies
- You may not post attachments
- You may not edit your posts
-
Forum Rules
|
Click Here to Expand Forum to Full Width
|