"exe has encountered a problem and needs to close" message when exe is run. Runs OK on Dev machine
This is occurring on 2 machines that are both running Windows XP Pro SP3, yet it runs OK on my development machine within in or outside the Delphi IDE.
Running Windows XP Pro. Exe compiled under Delphi 2010.
When I run the exe I get the Windows Reporting error "Neopos.exe has encountered a problem and needs to close. We are sorry for the inconvenience"
I know it is happening somewhere in the form create of the main form.
Application.Initialize; //Runs this
Application.CreateForm(TfmMain, fmMain); //FAILS HERE
It does not get to: procedure TfmMain.FormCreate(Sender: TObject);
in the Main Form and I don't know how to track down this error and debug it.
What happens between: Application.CreateForm(TfmUDF, fmUDF);
AND procedure TfmMain.FormCreate(Sender: TObject)
in my ma开发者_StackOverflow社区in form.
How can I trace this to find out what the hell is causing the Windows Error.
Of course the Windows Error report contains a long listing of information. Where can I look in that to find the cause or at least a clue on the cause of the error.
This error has now stopped all development work (and ruined my weekend) so I urgently need to fix this.
The most straightforward route to take would be to include a product like MadExcept or JCL Debugger into your application, to get a full call stack (including line number) of the point of failure. We've rolled our own years ago, and it has been a tremendous help in situations like this.
One alternative, but lots more cumbersome, would be to generate a MAP file from your project, use MAP2DBG to generate a .MAP file, and use the Windows Debbuging Tools to get about the same information. This approach is a lot more hardcore, and only advisable if you really want to learn a lot about the internals of windows debugging (and enjoy working with arcane tools).
Another alternative would be to attach to the failing application from your development environment using Remote Debugging. Only applicable if you have a fair amount of control over the failing machines.
@user576639, here are some debugging ideas:
Look into the System's Event Viewer
If you got the exe has encountered a problem and needs to close
chances are you'll find something about it in the System's Event Viewer. That should be your first step.
Any special DLL's required?
- Do you need MIDAS.DLL?
- Are you using an database engine? Does it require some sort of client library?
I'm talking from experience here: My development machine obviously has all the libraries I might need. Most of my clients also have most of those libraries because they have my software installed. At times I put out small helping applications that don't go throw extensive testing and they fail to work on SOME machines but work fine on other machines. Why? I used TClientDataset and forgot to include MIDAS.DLL with the application; Or the application is trying to access a Firebird SQL server but the user doesn't have Firebird client library installed.
Printer driver issues
Boy I hate Delphi's printer handling. Also hate buggy printer drivers, haven't made up my mind about what's worst. If you have something on your main form that might be requesting information about the default Windows printer (example: an REPORT) give this a try: Install an sane/simple printer and set it as the default printer. If the user has Office 2007+ installed, set the "Microsoft XPS Document Writer" the default printer.
I have seen bad printer driver + delphi issues manifest themselves with the "exe needs to close" symptom.
Prepare an special build of your application
If you got this far without fixing your issue it's time to create an special build of your application that's capable of providing more information. First of all I'd try adding this to your DPR file; Don't know if this is still useful for Delphi 2010 but it did help me see some early exceptions with a Delphi 7 application:
function HandleUnhandledException:integer;stdcall;
begin
Result := 1; // 1 = EXCEPTION_EXECUTE_HANDLER
end;
// and then immediately after "begin" in your DPR file:
begin
SetUnhandledExceptionFilter(@HandleUnhandledException);
// ... the usual stuff goes here
end;
Add some ShowMessage-s to your Main Form's code, in your OnCreate handler (if you have one), in your Create constructor (again, if you have one). If you're adding an ShowMessage to your Create destructor, make sure it's after the "inherited" call. This will help pin-point how far the loading of the form goes before it fails.
If all else fails...
Create a new, blank form; Make it the new Main Form (so it's initialized before your former Main Form). Test it on the client's machine - does it show up? It most likely will, if it doesn't you've got some serious problems.
Start copying the components from the former main form to the new main form; Only the components need to be copied, not the code: Your error is probably caused by some component failing to initialize properly. Make sure no component has "Active=True"! Copy the components in small batches, test often. If you spot the component that causes your form not to load on the client's computer, tell us about it and we'll try to help.
If you manage to get all your components on the new form, write an OnCreate handler that sets Active := True for all the components that need that. Did that fix the issue?
If you got this far then all the components you used on your main form can load properly. The problem's related to YOUR CODE. Start copying all the code from your old main form to your new main form, in small bits, and test. You're bound to find the peace of code that causes your application to stop loading.
Use dependency walker to see if you're missing a required DLL.
You can use information from system reporting (your error and suggestion to send it ) with Error Report Grabber ( http://www.maxerist.net/main/soft-for-win/err-rep-grabber ). I developed this tool when I desperately needed to track a error that appeared very rarely so almost non-reproducible. It helped me to track the information from stack to find actual place in the code.
The tool works only on XP (MS removed this dialog in Win7 and probably Vista), but I see that your cases are XP so this can help.
UPDATE: if you're not familiar with assembler and everything, this can work like this. You should compile you program and don't change anything. Save the report on a bad machine, copy the file to your developer machine and open to view the contents. Look at the stack of your main thread in the report and find numbers more than $00400000, they're usually the addresses inside the procedures that called some other procedure and wait for return. In your developer machine, start the program and stop at any line, open CPU Window and on the main list with assembler instruction right-click and choose go to address, enter this address. You will see other assembler lines, but wrapped with pascal constructions you can probably recognize as yours
Thanks a lot for the help.
In the end I reverted to a recent backup and traced it down to a particular form. I did not actually find the error, which is a bit worrying, but in any case I am back up and running (phew!!)
I made the error to occur on my development machine also, when, and only when, I use my install program (Inno Setup) to compile a setup.exe and which installs the exe as well as installing postgreSQL. Seems really strange, as though there is a problem with the setup compiler. In any case I have not seen the error again. I guess it will remains a mystery, like women.
In Delphi withing debugging options select debug dcu's, this will allow you to debug into the Delphi source code for TForm and its descendants and you may be able to track down a more likely culprit.
Set a breakpoint on
Application.CreateForm(TfmMain, fmMain); //FAILS HERE
and then step into the code to see where the issue is.
精彩评论