如何在Windows XP注销之前运行我的程序?

9

我正在寻找一个“RunOnceEx”的反向版本。

RunOnceEx会在用户的桌面和任务栏启动之前运行某些程序。登录进程在runonceex完成之前不会继续进行。

我想要做完全相同的事情,但是在用户注销时。

当她/他注销时,所有正在运行的程序都会关闭,只留下shell(桌面和任务栏),然后“我希望我的程序将在此时执行”,最后注销。

我认为这是可能的,因为“mobsync.exe”正在这样做。但我找不到在哪里以及如何做到这一点。


我想要一种“可编程”的方式——即在安装期间或应用程序中设置它的选项。组策略很好,但它并不能满足要求。微软是否将“mobsync.exe”硬编码了? - Dennis C
1
如@VonC所说,只需添加一些注册表条目。那有多难! - TFD
你是在寻找C/C++或.NET的解决方案吗?此外,mobsync.exe是微软程序,很可能像你拒绝的所有答案一样使用注册表项。 - John Bellone
7个回答

7

警告,如此处所述,gpedit.msc将允许您为所有用户配置注销脚本。

如果您只需要该脚本适用于一个用户,则需要直接在注册表中声明它,同时在HKCUHKLM中进行声明。


4
要仅为当前用户运行此操作,您可以使用WMI在关机/注销发生时获取信息。
您可以编写一个小的C#(或任何其他可以使用WMI的语言)应用程序或vbs脚本来监听Win32_ComputerShutdownEvent WMI事件。
这里有一个示例C#应用程序,在这个问题中可以找到:Get Log off event from system

3
如果您想要在注销时运行程序以执行代码,则应挂钩 WM_QUERYENDSESSION 消息并查找值为 ENDSESSION_LOGOFF(0x80000000)的 lParam 值。
测试此 lParam 值非常重要,因为其他值表示“强制关闭”,即您的进程可能会在允许运行代码之前被终止。实际上,大多数关机/会话结束消息仅旨在提供最后一分钟的清理代码运行的机会,并不安全,因为响应长时间运行的操作;但是这种特定组合应该是可以的。
注意:我从未尝试过在响应 WM_QUERYENDSESSION 消息时实际运行单独的进程。窗口管理器可能会像在关机期间那样拒绝此操作。尝试并查看吧。
如果您处于 .NET 环境中(您没有指定),则更快的方法是向 Microsoft.Win32.SystemEvents.SessionEnding 事件添加事件处理程序。

3

我在Google的第一个搜索结果中找到了以下内容:

要执行程序,您可以创建一个脚本来运行它,并使用组策略来强制执行它。 在组策略编辑器中,导航到用户配置-->Windows设置-->脚本(登录/注销)

在此处查看更多信息


由于我在stackoverflow提问,而不是Superuser,所以我正在寻找关于编程的解决方案。 - Dennis C

1
你需要的是GINA的实现。您可以在WlxIsLogoffOk函数中运行自定义命令,该函数在用户启动注销时调用。
一旦创建了正确的GINA dll,您就可以在此处注册它:HKEY_LOCAL_MACHINE\SOFTWARE\Microsoft\Windows NT\CurrentVersion\Winlogon\@GinaDLL 这是一个可能适合您需求的实现(它提供了一个注销注册表键,您可以在其中指定您的命令): http://wwwthep.physik.uni-mainz.de/~frink/newgina_pre09/readme.html

1
+1,因为这是一个合法的答案,但我认为为了实现这个人想要完成的目标而实现一个GINA dll是过于复杂了。 - Christopher Tarquini

1

正如VonC和TFD所提到的,组策略编辑器只是操作注册表的另一种方式。

只需使用gpedit进行更改(在用户配置文件 - Windows设置 - 脚本中),然后查看注册表中的[HKEY_CURRENT_USER\Software\Policies\Microsoft\Windows\System\Scripts],以了解如何直接进行更改。

此外,在我的电脑(挂在域中)上有一个隐藏的文件夹C:\WINDOWS\System32\GroupPolicy,其中包含用户和计算机的子文件夹。两者都有名为Shutdown和Startup的其他子文件夹。也许您也可以使用这些文件夹。


0
如果您需要为单个(或任何)用户创建一个简单且可用的应用程序,可以使用C++或C#等语言编写一个简单的应用程序。
最简单的方法是在托盘中使用C#(只需将托盘组件添加到窗体中),并为FormClosing事件注册事件处理程序。代码如下:
    private void Form1_FormClosing(object sender, FormClosingEventArgs e)
    {
        if (e.CloseReason != CloseReason.UserClosing)
        {
            // It's not the user closing the application,
            // Let's do whatever you want here, for example starting a process
            Process notePad = new Process();

            notePad.StartInfo.FileName   = "notepad.exe";
            notePad.StartInfo.Arguments = "ProcessStart.cs";

            notePad.Start();
        }
    }

所以你的应用程序将在Windows启动时或用户登录时开始运行。它会等待(只使用少量内存),并在系统关闭、用户注销等情况下执行某些操作(通过检查上方的“CloseReason”)。


网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接