【问题标题】:Abort entire application from thread in delphi从delphi中的线程中止整个应用程序
【发布时间】:2015-05-06 13:38:55
【问题描述】:

我的 delphi 应用程序有一个大问题。我正在开发一个使用外部安全的软件。我使用的 USB 设备必须连接到用户机器才能运行我的软件。如果用户有任何机会移除了这个加密狗,或者在没有它的情况下启动,应用程序应该警告用户并立即停止。 在创建应用程序时正在释放一个线程,用于检查安全设备。但是,当检查失败时,例如找不到设备,该线程没有杀死我的应用程序。我正在使用这样的东西:

    retCode := checkSecurity();
    if retCode = -1 then
    begin
        ShowMessage('Security device not found! Terminating immediately!');
        Application.Terminate;
    end;

这里的主要问题是Application.Terminate 并没有真正杀死应用程序。我在 SO 和其他地方读到 Terminate 发送一个优雅关闭的信号并等待其他线程(在我的情况下是应用程序的主线程)完成。我真的需要像上面提到的那样杀死应用程序,杀死所有线程并退出,如果可能的话,清理以避免内存泄漏,但如果没有,我很好。我正在使用 Delphi XE2,使用 Windows 8.1 进行开发。

有什么想法吗?

【问题讨论】:

  • "清理以避免内存泄漏" 这就是 Application.Terminate 以这种方式工作的原因 - 以确保事情得到清理。
  • 我正在开发的这个应用程序将被商业化,所以如果有人试图在没有安全设备的情况下使用该软件,我真的不介意留下一些剩菜,只要应用程序关闭
  • 突然关闭任何应用程序绝不是一个好主意。为什么?因为这样做甚至可能导致数据损坏。例如,让我们说在终止时您的应用程序正在向 disn 写入一些数据,而它只完成了一半。此时突然关闭它意味着一半应该写入的数据将永远消失。
  • 现在你说你不在乎当有人试图以不正当的方式使用你的应用程序时会导致什么。但是在多少情况下,您的应用程序可能会认为它以不正确的方式使用,但事实并非如此。例如,您可能有合法用户遇到 USB 控制器问题,因此您的应用程序可能会不时检测到您的安全设备被拔出。你真的想每次都为这样的用户造成 hasoc 吗?或者USB控制器可能由于省电(计算机进入睡眠模式)而断电的情况。
  • 仅供参考,Application.Terminate()WM_QUIT 消息发布到调用线程 的消息队列中,而主线程中的Application.Run() 在查找该消息时退出已收到。如果您在工作线程中调用Terminate()Run() 将永远不会收到消息。所以让工作线程改用PostThreadMessage(MainThreadID, WM_QUIT, 0, 0)。您还可以考虑在启动时在主线程中进行初始安全检查,然后再启动其他任何操作。如果检查失败则立即退出应用程序,否则完成启动并创建线程以进行后续检查。

标签: multithreading delphi


【解决方案1】:

您可以致电ExitProcess 强制立即终止。与Halt 相比,操作系统函数ExitProcess 执行的清理工作更少。

【讨论】:

  • ExitProcess 就像一个魅力!正如我所提到的,我的软件和金融安全是第一位的,稍后我将尝试改进泄漏。谢谢大卫!!!
  • 你不会泄露任何东西。操作系统会为您整理。
【解决方案2】:

要杀死一个应用程序,只需调用Halt。它是 DOS 时代的遗留物,适用于现代 Delphi 应用程序。它将调用所有单元中的所有“最终化”块,但不会更多。

【讨论】:

  • 使用 Halt 会引发异常 System Error Code 5: Access Denied
  • 这肯定是因为您的代码中的某些内容在终止时正在执行。使用调试器会告诉你它是什么。要么处理该代码引发错误的原因,要么完全绕过它。
【解决方案3】:

要从您可能使用的线程终止应用程序:

TThread.Queue(nil, 
  procedure
  begin
    Application.Terminate;
  end
);

这是跨平台的,和“几乎”一样

PostThreadMessage(MainThreadID, WM_QUIT, 0, 0)

假设 Application 对象尚未销毁并且您使用的是 Windows。

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 2017-06-28
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2011-07-14
    相关资源
    最近更新 更多