8

ブート時に起動される複数の VMWare Player マシンを備えた Windows 7 ボックスがあります。WMWare VIX とバッチ ファイルを使用して、次のように仮想マシンをシャットダウンします。

"C:\path\to\VMWare VIX\vmrun.exe" -T player stop "C:\path\to\machine.vmx" soft

私が達成したいのは、ホスト マシンがシャットダウンされたときにこれらのコマンドを実行して、各 VM を個別にシャットダウンする必要がないようにすることです。展開すると、[スタート] メニューからではなく、ACPI 電源ボタンを短く押すことでシャットダウンが開始される可能性があります。私が試した方法はうまくいきません(少なくとも十分ではありません):

  1. グループ ポリシー - 最も明白な方法ですが、Windows 7 では、シャットダウン スクリプトを「非同期で」実行するオプションがなくなりました。
    その結果、Windows は最初に開いているすべてのウィンドウを閉じるように指示し、VM は使用中であると応答し、[強制的に閉じる] ダイアログが表示されます。VMWare Player と他のすべてが閉じられた後でのみ、スクリプトが実行されますが、役に立ちません。
    これは変更できると思うかもしれませんが、「いいえ、申し訳ありません」という行に沿って公式のMSノートを見たのを覚えていると思います. しかし、リンクが見つかりません。

  2. 通常のシャットダウン ボタンの代わりに、すべての VM を閉じてからホストをデスクトップ ショートカットとしてシャットダウンする 1 つのバッチ ファイルを使用します。-動作します。それは、開発中に現在使用しているものです。
    ただし、ACPI 電源ボタンを使用すると、以前と同じ結果で通常のシャットダウンが開始されます。また、マシンの電源を毎日オン/オフするエンド ユーザーがモニターとマウスを使用する必要がない方がよいでしょう。
    現時点で私が探しているのは、物理的な電源ボタンを押したときに呼び出されるアクションを変更する方法です。Windows では、スリープ、休止状態、再起動などのいくつかの異なるアクションから選択できますが、それを「この .bat を実行する」に変更できますか? それとも、shutdown コマンドの動作を完全に変更しますか?

  3. プログラムでシャットダウン メッセージをインターセプトし、シャットダウンを中止し、バッチ ファイルを実行し、シャットダウンを再開します。ここ、 ここ 、ここなど、シャットダウンのインターセプトについていくつかの議論がありましたが、RubyまたはJavaを除くすべての言語で、この場合にそれを行うことができるかどうか、およびどのように行うことができるかを本当に理解するには、私はまだあまりにも無知です. 誰かが実際にこれを機能させる方法を明確にすることができれば (「強制終了」画面で動けなくなることなく)、あなたが提供する言語を試してみたいと思っています.

4

3 に答える 3

3

さて、私は自分に合った解決策を見つけました。AutoHotkey_L というツールと、AutoHotkey フォーラムのこれらの スレッドに従って作成されたスクリプト。

これは私が使用しているコードです。ドキュメントの AutoHotkey コマンドを読むことをお勧めします。コードが実際に何をしているのかを学びながらコードを微調整していますが、今のところこれで動作します。:)

#NoEnv
#Persistent
SendMode Input
SetWorkingDir %A_ScriptDir%
SetTimer, RunBeforeShutdown, Off

Gui,+LastFound
hwnd:=WinExist()
DllCall("ShutdownBlockReasonCreate","Uint",hwnd,"Str","")
DllCall("kernel32.dll\SetProcessShutdownParameters", UInt, 0x4FF, UInt, 0)
;puts us first in line for getting the shutdown call, i guess?
OnMessage(0x11, "WM_QUERYENDSESSION")
Return

WM_QUERYENDSESSION(wParam, lParam)
{
    ENDSESSION_Logoff = 2147483648
    If (lParam == ENDSESSION_Logoff) {
        global EventType = "Logoff"
    } Else {
        global EventType = "Shutdown"
        ;no way to distinguish between shutdown and restart
    }

    SetTimer, RunBeforeShutdown, On
    Return false
}

runBeforeShutdown:
    SetTimer, RunBeforeShutdown, Off
    Sleep, 1000
    SendInput, {ENTER}  ; gets us past the 'Force shudown' screen
    Sleep, 1000
    #SingleInstance, Force
    DllCall("ShutdownBlockReasonDestroy","Uint",hwnd)
    ; **** Your commands go here ****
    RunWait shutdown.bat
    ; ********

    If (EventType == "Logoff") {
        Shutdown, 0
    } Else {
        Shutdown, 1
    }
    Reload
Return

そのため、現在はログオフとシャットダウンのみを区別していますが、この投稿には HTML でシンプルな GUI があり、ユーザーは再起動や休止状態などを選択できます。

私の場合、VMware が実行されているかどうかに関係なく、シャットダウンを中断してバッチ ファイルを実行しても問題ありませんが、たとえば次のように条件を設定できます。

IfWinExist, ahk_class VMPlayerFrame {
    SetTimer, RunBeforeShutdown, On
    Return false
} Else { 
    Return true
}

このスクリプトでは、ホストの速度が非常に低下している (メモリ リーク) ため、スクリプトが閉じるのに間に合うように "強制シャットダウン" 画面が表示されないなどの問題が既に発生しています。また、最初の試行が失敗した場合に強制的にシャットダウンできるように、試行回数を追跡することでおそらく恩恵を受けるでしょう。

少なくとも今のところは十分です。結局のところ、自分のプロジェクトに仮想化は必要ないかもしれませんが、うまくいけば他の誰かを助けることができます. 代替ソリューションは引き続き大歓迎です。

于 2011-03-09T14:56:11.137 に答える
1

同じ問題に対するこの解決策を思いつきました: http://communities.vmware.com/thread/334740

「強制終了」を回避する秘訣は、最初にすべての VM を一時停止/停止してから、同じスクリプトでシャットダウンを再発行することです。それは私のために働くようです。

于 2011-11-02T09:04:23.660 に答える
0

Workstation には、「Workstation の終了後も VM を実行し続ける」という設定があります。VMware プレーヤーには同じオプションがありますか?

これが機能している様子:上記の設定を有効にします。ウィンドウが閉じ、VM は実行されたままになります。その後、シャットダウン プロセスは #1 からスクリプトに進むことができ、終了する前に VM をシャットダウン/一時停止する必要があります。

私自身はプレーヤー VM を持っていないので、これをテストすることはできませんが、役立つことを願っています。

于 2011-02-01T17:18:39.400 に答える