是否可以使用全局异常挂钩?

时间:2010-04-13 10:25:01

标签: delphi exception-handling

我的代码很好地涵盖了异常处理(try..except)。预计不会发生一些异常,并且会经常发生一些异常,这是预期的,也可以。现在我想为这段代码添加一些自动化测试。知道在执行期间发生了多少异常会很好,所以我稍后可以看到是否提出了预期的数字或发生了意外情况。我不想用调试代码混淆每个异常处理块,所以我的问题是:

有没有办法安装某种全局异常处理程序,它位于所有其他异常处理块之前?我正在寻找记录这些例外情况的中心位置。

感谢您的任何建议!

(如果这很重要:它是Delphi 2009)

4 个答案:

答案 0 :(得分:15)

您可以执行以下操作:

  • 保留System.RaiseExceptObjProc变量的值,该变量在普通的Delphi应用程序中指向SysUtils.RaiseExceptObject
  • 创建您自己的“RaiseExceptObject”proc并将其分配给RaiseExceptObjProc变量
  • 在你自己的“RaiseExceptObject”proc中你可以做你想做的事,然后调用保存的RaiseExceptObjProc值

有关详细信息,请参阅上面的变量和过程声明。

答案 1 :(得分:8)

我认为您可以使用AddVectoredExceptionHandler API函数。

以下是一个关于如何使用的小样本:

var
  f : TFileStream;

    function VectoredHandler(ExceptionInfo : PEXCEPTION_POINTERS): LongInt; stdcall;
    var 
      s : String;
    begin
      S := Format('Exception code %x address %p'#10#13, [ExceptionInfo^.ExceptionRecord^.ExceptionCode,
       ExceptionInfo^.ExceptionRecord^.ExceptionAddress]);
       f.WriteBuffer(PChar(s)^, Length(s) * sizeof(wchar));
       FlushFileBuffers(f.Handle);
      OutputDebugString(PChar(Format('ExceptionCode: %x', [ExceptionInfo^.ExceptionRecord^.ExceptionCode])));
      result := EXCEPTION_CONTINUE_SEARCH ;
    end;


    initialization
      AddVectoredExceptionHandler(0, VectoredHandler);

答案 2 :(得分:1)

您可以为madExcept添加一个自定义处理程序,这样可以让您获得完整的堆栈跟踪,但也可以继续。

答案 3 :(得分:0)

JCL有自己的异常对话框。只需将此对话框添加到项目中,它将处理所有意外的异常。位于此JCL文件夹中的详细信息:jcl \ experts \ debug。还有一些文本文件,它逐步描述了如何使用它。