TerminateProcess vs Ctrl + C.

aro*_*101 6 windows console signals

我有一个控制台模式程序,它使用SQLite3来维护数据库文件.执行需要一段时间,但假设数据库写入发生,它应该在任何时候都是安全的取消.(这都是在Windows下)

从运行程序的角度来看,CtrlC在控制台中命中比让另一个程序调用TerminateProcess更安全吗?

我注意到如果调用TerminateProcess,我可以获得数据库损坏 - 我认为这是因为程序没有机会完成写入.我的猜测是CtrlC更好,因为程序得到一个信号并终止自己,而不是操作系统杀死它.

请注意,程序实际上并不处理信号(除非SQLite这样做); 我在谈论Win32可执行文件的内置默认机制来处理CtrlC信号.

澄清/简化问题 - 鉴于此写操作刚刚执行:

fwrite(buf, 1024*1024, 1, stream);
Run Code Online (Sandbox Code Playgroud)

在写这篇文章期间,TerminateProcess的行为会不同于CtrlC

aro*_*101 5

所有这些都是令人信服的论点,但唯一可以确定的方法是尝试它.所以我编写了一个简单的程序,分配1GB缓冲区,为其分配一些数据,然后使用单个fwrite()将其写入文件.我尝试了几种方法来使写入"损坏"数据(特别是我期待一个截断的文件):

  • 调用TerminateProcess(通过perl的kill函数和Win32 :: Process :: Kill)
  • CtrlC
  • 使用任务管理器的"结束进程"
  • 使用Process Explorer的"杀戮过程"

没有什么能阻止写入的每一种情况,文件大小正确并且具有正确的数据.虽然"杀戮"会立即发生,但这个过程会一直持续到写完为止.

似乎结论是TerminateProcess和CtrlCI/O观点之间没有区别- 一旦写入开始,它似乎保证完成(禁止断电).

  • 我怀疑 TerminateProcess 在执行系统调用时无法安全地杀死进程:该阶段的线程上下文在内核空间中,在那里强行杀死它可能会泄漏系统资源。操作系统可能为当前在内核空间中执行的所有进程线程安装钩子,当线程试图从系统调用返回时,这些线程会终止线程。 (2认同)