在Windows中发送任意信号?

Linux支持使用kill -Command将一个任意的Posix-Signal(如SIGINTSIGTERM发送到一个进程。 虽然SIGINTSIGTERM只是无聊的旧方法,以友好或不那么友好的方式结束一个过程,但SIGQUIT意味着触发一个核心转储。 这可以用来触发正在运行的Java VM来打印出一个线程转储,包括所有正在运行的线程的堆栈跟踪 – 整洁! 在打印debugging信息之后,Java VM将继续执行之前的操作。 事实上,线程转储只是在另一个最大优先级的产生线程中发生。 (您可以使用kill -3 <VM-PID>自己尝试。

请注意,您也可以在sun.misc SignalHandler使用(不支持的!) SignalSignalHandler类来注册自己的信号处理程序,这样您就可以拥有各种各样的乐趣了。

但是,我还没有find一种方法发送信号到Windows进程。 信号由某些用户input创build:例如, Ctrl-C在两个平台上触发一个SIGINT 。 但是,似乎没有任何实用工具可以将信号手动发送到Windows上正在运行的但非交互式的进程。 显而易见的解决scheme是使用Cygwin kill可执行文件,但是当它可以使用适当的Windows API结束Windows进程时,我无法发送SIGBREAK (相当于SIGQUIT的Windows)。 实际上我认为它能够发送到Windows进程的唯一信号是SIGTERM

所以,长话短说,重复标题:如何在Windows中发送任意信号到进程?

如果你想要的是明确/程序化地杀死另一个程序/进程,在SysInternals的pstools中有一个名为“pskill”的小工具,其行为就像Unixen“kill”所能做的那样。

如果你想要别的东西,请继续阅读(虽然我可能在下面的一些细节上是错误的 – 从上次开发Windows程序到使用WinAPI和Charles Petzold出色的书籍“Programming for Windows” )。

在Windows上,您不能正确地获得“信号”,WinMain和WinProc从操作系统接收的函数是简单的消息 。 例如,当你点击一个窗口的“X”按钮时,Windows向该窗口的处理程序发送消息WM_CLOSE。 当窗口被删除但程序仍在运行时,它发送WM_DESTROY。 当它要离开主消息处理循环时,WinMain(而不是WinProc)接收WM_QUIT。 你的程序应该按照预期对所有这些进行响应 – 你可以通过在收到WM_CLOSE之后不做任何事情来开发一个“不可关闭”的应用程序。

当用户从Windows任务管理器中选择任务并单击“结束任务”时,操作系统将发送WM_CLOSE(另一个我不记得)。 如果你使用“结束进程”,但是,这个进程直接被杀死,没有消息发送过(来源: 旧的新事物

我记得有一种方法来获取另一个进程的HWND窗口,一旦你得到另一个进程可以通过函数PostMessage和DispatchMessage发送该窗口的消息。

Windows不是POSIX。 它没有信号。 控制台程序得到的唯一“信号”是调用SetConsoleCtrlHandler ,在这种情况下,可以通知用户已经按下Ctrl + C,Ctrl + Break,关闭控制台窗口,注销或关闭系统。

其他的一切都通过IPC来完成,通常是使用窗口消息或RPC。 查看Sun的文档,看看是否有办法在Windows JRE上进行问题的解答。

在Windows中,一切都围绕着Win32消息。 我不相信有一个命令行工具来做到这一点,但在C ++中,您可以使用FindWindow将任意消息发送到另一个Windows程序。 例如:

 #define WM_MYMSG ( WM_USER+0x100 ) HWND h = ::FindWindow(NULL,_T("Win32App")); if (h) { ::PostMessage(h, WM_MYMSG, 0, 0); } 

这也可以使用COM互操作在C#中完成。

您也可以使用jconsole查看所有正在运行的线程的堆栈跟踪。 这可以在Windows和任何其他支持Java的操作系统上运行。 jconsole也有很多其他很好的功能,内存图,CPU图等

它不回答你原来的问题,但希望可以让你得到相同的结果。

如果您不熟悉jconsole,请查看使用JConsole文档。

我只是想知道现在微软拥有的PsTools , SysInternals是否会帮助你。

Ruby在某种程度上能够(至少仿效)在Windows上的SIGINT SIGKILL等,并捕获这些消息。 可能要检查出来。

在Windows下,红宝石如何“发送信号SIGINT到该进程”,实际上是调用TerminateProcess或该PID上的等价物。

还有一个窗口等效的方法“捕捉CTRL + C”我想这是它在那里调用。