windows 检测计划关闭

声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow 原文地址: http://stackoverflow.com/questions/6156216/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me): StackOverFlow

提示:将鼠标放在中文语句上可以显示对应的英文。显示中英文
时间:2020-09-09 08:24:36  来源:igfitidea点击:

Detecting a scheduled shutdown

windowswinapisystem-shutdown

提问by Ificator

I have a cmd script that will execute a set of patches, and it's designed to abort if a reboot is required to avoid patching issues. I'd also like to extend the script to abort if a reboot is scheduled (E.g. via the "shutdown" command) in order to avoid reboots mid patch if possible. Unfortunately I haven't managed to find a way to detect this apart from attempting to schedule another shutdown, which results in:

我有一个 cmd 脚本将执行一组补丁,如果需要重新启动以避免补丁问题,它被设计为中止。如果计划重新启动(例如通过“关闭”命令),我还想将脚本扩展为中止,以避免在可能的情况下在补丁中重新启动。不幸的是,除了尝试安排另一次关机之外,我还没有设法找到一种方法来检测这种情况,这会导致:

A system shutdown has already been scheduled.(1190)

已安排系统关闭。(1190)

While I could theoretically use this I don't think it would be good practice to scare logged in users every time I needed to check for a scheduled reboot. What I really need is a way to QUERY the state modified by the "shutdown" command.

虽然理论上我可以使用它,但我认为每次需要检查计划的重启时都吓唬登录用户并不是一个好习惯。我真正需要的是一种查询由“关闭”命令修改的状态的方法。

Is this possible? I'll be happy with really any solution that doesn't involve me having an application running permanently on the system to catch the shutdown events (which I don't think even get sent around until the shutdown is actually triggered)

这可能吗?我会对任何不涉及我在系统上永久运行应用程序以捕获关闭事件的解决方案感到满意(我认为在实际触发关闭之前甚至不会发送)

回答by Joseph

I have the same problem, I searched all over, but did not find anything useful.

我有同样的问题,我到处搜索,但没有找到任何有用的东西。

Eventually I just started messing around with different things I could think of. I can think of two workarounds for our problem.

最终,我开始胡思乱想我能想到的不同事情。对于我们的问题,我可以想到两种解决方法。

The event viewer can tell you that a shutdown has been scheduled, but not WHEN it was scheduled.

事件查看器可以告诉您已安排关机,但不会告诉您何时安排关机。

One idea is to query the event viewer for the most recent system shutdown, the most recent scheduled shutdown, and the most recent cancellation of a scheduled shutdown. If the scheduled shutdown is more recent than either the most recent cancellation or shutdown then there is one in progress. The Event IDs are: 1074 for a started scheduled shutdown, 1075 for a canceled scheduled shutdown, under Windows Logs/System 12 for system start up 13 for system shutdown (all under Windows Logs/System)

一种想法是在事件查看器中查询最近的系统关闭、最近的计划关闭和最近取消的计划关闭。如果预定的关闭比最近的取消或关闭更近,则有一个正在进行中。事件 ID 是: 1074 表示已启动的计划关闭,1075 表示取消的计划关闭,在 Windows 日志/系统下 12 表示系统启动 13 表示系统关闭(均在 Windows 日志/系统下)

I was too lazy to do this in a batch file, I know it is possible though.

我懒得在批处理文件中执行此操作,但我知道这是可能的。

So this is what I ended up doing: Rather than schedule a shutdown, just try to abort it. If no shutdown is in progress it will throw an error (Unable to abort the system shutdown because no shutdown was in progress.(1116)). Much better I think than freaking out a user by scheduling a shutdown.

所以这就是我最终要做的:与其安排关机,不如尝试中止它。如果没有进行关机,它会抛出一个错误(无法中止系统关机,因为没有关机正在进行。(1116))。我认为这比通过安排关机吓坏用户要好得多。

Here is a copy of the code I wrote for a simple auto shutdown script, it toggles between cancelling and starting a scheduled shutdown.

这是我为一个简单的自动关机脚本编写的代码副本,它在取消和开始计划关机之间切换。

@echo off
shutdown /a
if errorlevel 1 call:shutdown
goto end

:shutdown
    set /p choice=Shutdown in how many minutes? 
    set /a mod=60
    set /a mod*=%choice%
    shutdown /s /t %mod%

:end


EDIT- I am revisiting this answer as I have more info to add.

编辑- 我正在重新审视这个答案,因为我有更多信息要添加。

The Above solution will detect if a shutdown has been scheduled via the shutdown.exe command using the /t argument.

上述解决方案将使用 /t 参数通过 shutdown.exe 命令检测是否已安排关闭。

If you need to determine if Windows has schedule a shutdown (as it does automatically after some Windows Updates) then there is a registry entry that is set which you can query. The below is in PowerShell, but you can write a batch file to do the same.

如果您需要确定 Windows 是否安排了关机(就像它在某些 Windows 更新后自动执行的那样),那么可以设置一个注册表项供您查询。下面是在 PowerShell 中,但您可以编写一个批处理文件来执行相同的操作。

Test-Path 'HKLM:\SOFTWARE\Microsoft\Windows\CurrentVersion\Component Based Servicing\RebootPending'

Note:this will not return true if a reboot in scheduled using shutdown.exe, it will only return true if Windows says your computer need to be rebooted.

注意:如果使用shutdown.exe 计划重启,则不会返回true,只有当Windows 提示您的计算机需要重启时才会返回true。

回答by Marcelo

Another way to do this, if your script is setting the shutdown, is to save the %date% and %time% variables into global environments using setx command. Then you can check these variables on the next time that the script is called.

如果您的脚本正在设置关闭,另一种方法是使用 setx 命令将 %date% 和 %time% 变量保存到全局环境中。然后您可以在下次调用脚本时检查这些变量。

回答by Tu?n Tú Nguy?n

You can use:

您可以使用:

Shutdown /a "for aborting the scheduled"

Shutdown /a "用于中止预定"

then use shutdown again to create another schedule.

然后再次使用关闭来创建另一个计划。

回答by Adrian McCarthy

I suppose you could use the Task Scheduler APIto enumerate the scheduled tasks and see if any of them invoke shutdown.exe. But I"m not sure that's robust. There are probably multiple ways to schedule a shutdown.

我想您可以使用Task Scheduler API来枚举计划任务并查看它们中是否有任何调用 shutdown.exe。但我不确定这是否可靠。可能有多种方法可以安排关闭。

回答by Vagaus

Maybe you can try to initiate a shutdown by calling ExitWindowsExwith a large grace period and check for the return code ERROR_SHUTDOWN_IS_SCHEDULEDand call AbortSystemShutdownimmediately if ExitWindosEx return success (indicating you successfully scheduled a shutdown)

也许您可以尝试通过以较大的宽限期调用ExitWindowsEx并检查返回代码ERROR_SHUTDOWN_IS_SCHEDULED并在 ExitWindosEx 返回成功时立即调用AbortSystemShutdown来启动关机(表明您已成功安排关机)