我有一个德尔福服务应用程序。 Indy TCP 服务器和许多客户端(最多 50 个)、到 Firebird 的 ADO 连接和简单的网络交换。应用程序在下一个事件(例如)中随机崩溃(可能在 7 天后工作,可能是 1 小时):
文件: rollcontrol.exe, 文件: 1.1.20.2, 文件: 0x60acd5f2
文件名: ntdll.dll, 文件名: 6.3.9600.19678, 文件名: 0x5e82c0f7
错误信息: 0xc0000005
错误信息:0x00058def
Идентификатор сбойного процесса: 0x4178
or:
版本: rollcontrol.exe, 版本: 1.1.1.9, 版本: 0x607b239c
文件名: msvcrt.dll,地址:7.0.9600.16384,地址:0x52158ff5
错误信息: 0xc0000005
错误信息:0x00009e80
应用程序中的所有作业都在 anonimius 线程或 tcp/ip 连接线程中进行。每个线程中的所有代码都在 try except 语句中执行。没有内存泄漏或线程数增加。服务线程的主要代码很简单:
procedure TRollControl_Svc.ServiceExecute(Sender: TService);
begin
while not Terminated do
try
ServiceThread.ProcessRequests(False);
ServiceThread.Sleep(100);
except
on e : exception do LogException('ServiceExecute', E);
end;
end;
我如何处理此异常并防止应用程序崩溃?如何用两行简单的代码使服务线程崩溃?
Thanks
UPDATE:数据库连接示例:
function TRollControl_Svc.GetNodeIdByIP(ip: string): integer;
Var
SQLConnection : TADOConnection;
SQLQuery : TADOQuery;
Thread : TThread;
fResult : integer;
begin
fResult := 0;
try
Thread := nil;
Thread := TThread.CreateAnonymousThread(
procedure
begin
try
SQLConnection := nil;
SQLQuery := nil;
CoInitialize(nil);
SQLConnection := TADOConnection.Create(nil);
SQLConnection.ConnectionString := 'Provider=MSDASQL.1;Password=' + Psw + ';Persist Security Info=True;User ID=' + Usr + ';Data Source=' + Srv ;
SQLConnection.LoginPrompt := false;
SQLQuery := TADOQuery.Create(nil);
SQLQuery.Connection := SQLConnection;
SQLQuery.LockType := ltReadOnly;
try SQLConnection.Open; except SQLConnection.Open; end;
SQLConnection.BeginTrans;
SQLQuery.Close;
SQLQuery.SQL.Text := 'select nodes.* from nodes where nodes.ip = :ip';
SQLQuery.Parameters.ParamByName('ip').Value := ip;
try SQLQuery.Open; except SQLQuery.Open; end;
if SQLQuery.IsEmpty then exit;
fResult := SQLQuery.FieldByName('ID').AsInteger;
if SQLConnection.InTransaction then
SQLConnection.CommitTrans;
finally
TryFree(SQLQuery);
TryFree(SQLConnection);
CoUninitialize;
end;
end
);
Thread.FreeOnTerminate := false;
Thread.Start;
Thread.WaitFor;
finally
TryFree(Thread);
end;
result := fResult;
end;
错误处理
这不是导致您的问题的答案,但我认为评论中可能不清楚。
在支持结构化异常处理的语言中,当事情不起作用时,该语言为程序员提供了优雅地失败的机会。这不是你使用它的方式。从您的示例匿名线程中您可以得到:
try SQLConnection.Open; except SQLConnection.Open; end;
因此,您被告知无法建立连接,并且您没有对这种情况做出响应,而是继续尝试再次连接。连接无法工作的原因有很多,其中一些是暂时的,因此尝试可能会稍后才能工作,但如果您只是在没有任何暂停的情况下再次尝试,那么预计它会再次失败似乎是合理的。
捕获错误显然很重要,但您必须有适当的故障路径。
我无法知道这是否与实际出现的问题有关。
本文内容由网友自发贡献,版权归原作者所有,本站不承担相应法律责任。如您发现有涉嫌抄袭侵权的内容,请联系:hwhale#tublm.com(使用前将#替换为@)