[SlimDX] Unable to handle crashes

Started by
3 comments, last by Monza 14 years, 1 month ago
I'm using DirectX 9 with Slimdx. I have problems about deploying my project. The main problem is that application crashes on some computers due to their graphic devices. For example, I installed my application to my friend's computer and it crashed on startup. It is an old computer with Geforce 6600GT adapter. I got error message by using Debugging Tools for Windows (it is really hard to get errors for managed code). The error was about device.GetTransform function and not detailed. So I installed all development staffs including visual studio, directx sdk ... on his computer to get exact error. The error said something like that: "Get functions can't be used with pure device." What? where this comes from? I used exactly same device type on my computer without any error. I have 8600M GT. So when I commented out pure device flag, application worked on my friend's computer. After that I installed this application to an academician' s computer in my school. It crashed on that computer, too without pure device flag. I couldn't find a chance to examine this error. I think the more important problem is that my device creation code is missing something very important. I'm using this device creation code. I converted it from a C++ code.

                direct3D = new Direct3D();
                presentParams = new PresentParameters();
                int AdapterToUse = 0;
                DeviceType devtype = DeviceType.Hardware;
                Size clientSize = childForm.ClientSize;
                presentParams.BackBufferWidth = clientSize.Width;
                presentParams.BackBufferHeight = clientSize.Height;
                presentParams.DeviceWindowHandle = childForm.Handle;
                presentParams.Windowed = true;
                presentParams.SwapEffect = SwapEffect.Discard;
                presentParams.EnableAutoDepthStencil = false;
                presentParams.PresentationInterval = PresentInterval.Default;

                DisplayMode mode = direct3D.GetAdapterDisplayMode(AdapterToUse);
                Format fmtBackbuffer = mode.Format;
                Format[] Depths = { Format.D32, Format.D24X8, Format.D24S8, Format.D24X4S4, Format.D16, Format.D15S1 };
                Format DepthSelected = Format.Unknown;
                Boolean r = false;

                for (int i = 0; i < Depths.Length; i++)
                {
                    r = direct3D.CheckDeviceFormat(AdapterToUse, devtype, mode.Format, Usage.DepthStencil, ResourceType.Surface, Depths);
                    if (r == false)
                    {
                        continue;
                    }


                    r = direct3D.CheckDepthStencilMatch(AdapterToUse, devtype, mode.Format, fmtBackbuffer, Depths);
                    if (r == false)
                    {

                        continue;
                    }

                    DepthSelected = Depths;
                    break;
                }

                if (DepthSelected != Format.Unknown)
                {
                    presentParams.EnableAutoDepthStencil = true;
                    presentParams.AutoDepthStencilFormat = DepthSelected;
                }


                Capabilities hardware = direct3D.GetDeviceCaps(AdapterToUse, devtype);
                if ((hardware.VertexShaderVersion >= new Version(1, 1)) && (hardware.PixelShaderVersion >= new Version(1, 1)))
                {
                    CreateFlags flags = CreateFlags.SoftwareVertexProcessing;

                    if ((hardware.DeviceCaps & DeviceCaps.HWTransformAndLight) != 0)
                        flags = CreateFlags.HardwareVertexProcessing;

                   //if this line is commented out, application works on 6600GT
                    if ((hardware.DeviceCaps & DeviceCaps.PureDevice) != 0)
                        flags |= CreateFlags.PureDevice;

                    device = new Device(direct3D, AdapterToUse, devtype, childForm.Handle, flags | CreateFlags.Multithreaded, presentParams);
                }
                else
                {
                    device = new Device(direct3D, AdapterToUse, DeviceType.Reference, childForm.Handle, CreateFlags.SoftwareVertexProcessing | CreateFlags.Multithreaded, presentParams);
                }



I'm using a try catch block for this code but it doesn't help because application crashes after device creation. This problem caused me to think of some questions: - To prevent crashes what should I check on device creation code? - What is the easiest way debugging directx applications or getting errors on other computers? [Edited by - Mesut on March 5, 2010 1:16:39 PM]
------------------------------Mesut
Advertisement
CheckDeviceFormat returns a hresult not a boolean.
it returns D3D_OK == S_OK == 0 upon success (eg false upon success if casted to a boolean)
Hi,

it is fact that you cannot use Get* functions (D3D-functions starting with "Get")with pure device. So you shouldn't try to create such a device if you plan to use Get* functions.
It is written in the Direct3D documentation.

However, why the program works on your computer and not on the others may be driver related or perhaps your computer doesn't expose the pure device cap (which sounds unlikely).

Anyhow, the program works correctly on the other computers and it doesn't work correctly on yours. Using DirectX debug dlls usually gives information about the correctness of your code.

Good luck!
First thanks for your answers.

Quote:Original post by marius1930
CheckDeviceFormat returns a hresult not a boolean.
it returns D3D_OK == S_OK == 0 upon success (eg false upon success if casted to a boolean)


For SlimDX return value is boolean. In SlimDX documentation it says for the return value: "true if the format is compatible with the specified device; otherwise, false.".

Quote:Original post by kauna
Anyhow, the program works correctly on the other computers and it doesn't work correctly on yours. Using DirectX debug dlls usually gives information about the correctness of your code.


I will give directx debug dlls a try. But I have to prevent crashing by checking every possibilties on device creation. And if there is a problem application should give an error and terminate. So I think I don't check everything on device creation. In c++ we can check device creation result by using this line:
if( FAILED( g_pD3D->CreateDevice( D3DADAPTER_DEFAULT, D3DDEVTYPE_HAL, hWnd,									D3DCREATE_SOFTWARE_VERTEXPROCESSING,									&d3dpp, &d3dDevice ) ) )	return E_FAIL;


I can't browse slimdx source code right now because google project server is down. Does SlimDX throws an error on device creation failure or we only need to check is device null?

------------------------------Mesut
I also started to get a device crash on some NVIDIA computers with the SLIMDX GETTRANSFORM function.

Never found out what was causing the problem. Only happened with some transformations and it was hard to reproduce the error.

I bypassed the GETTRANSFORM command by storing the matrix locally when I did the original SETTRANSFORM

This topic is closed to new replies.

Advertisement