Delphi-PRAXiS

Delphi-PRAXiS (https://www.delphipraxis.net/forum.php)
-   Win32/Win64 API (native code) (https://www.delphipraxis.net/17-win32-win64-api-native-code/)
-   -   Ruhezustand / Hibernate unter Windows 7 und Windows HomeServer 2011 (https://www.delphipraxis.net/169775-ruhezustand-hibernate-unter-windows-7-und-windows-homeserver-2011-a.html)

Bambuti2000 10. Aug 2012 17:34

Ruhezustand / Hibernate unter Windows 7 und Windows HomeServer 2011
 
Hallo Leute,

bin jetzt schon seit zwei Tagen dran, und bekomme das Problem einfach nicht in den Griff.
Folgendes Problem (welches auch schon oft diskutiert wurde aber leider keine Lösung bringt) habe ich:
Vor dem Ruhezustand oder Standby soll noch ein Script ausgeführt werden, welches diverse andere Geräte im Netzwerk herunterfährt bzw. auch in Ruhezustand versetzt.
Unter Windows XP bekomme ich auch die BROADCAST_MESSAGE für die Anfrage zum Standby und kann soweit auch noch weiter aggieren, aber unter Windows 7 und HomeServer 2011 wird nur PBT_APMSUSPEND gesendet, und bevor ich das Abschalten des Systems (weder mit BROADCAST_QUERY_DENY noch mit ES_AWAYMODE_REQUIRED) verhindern kann ist es auch schon aus. Somit kann ich natürlich auch keine andern Programme oder Skripte mehr starten.

Ich hoffe dass das einigermassen verständlich klingt?!?!

Also, kurz ausgedrückt,
ich muss unter Windows 7 noch etwas starten bevor der Hibernate-/Suspend-Modus eintritt.
Da dies vermutlich nur geht, wenn ich den Vorgang für meine Ausführung unterbreche, benötige ichetwas um den Hibernate/Suspend abzubrechen bzw. pausieren zu lassen.

Damit ihr's testen könnt, hier mein Quelltext:
Delphi-Quellcode:
const
  ES_SYSTEM_REQUIRED  = DWORD($00000001);
  {$EXTERNALSYM ES_SYSTEM_REQUIRED}
  ES_DISPLAY_REQUIRED = DWORD($00000002);
  {$EXTERNALSYM ES_DISPLAY_REQUIRED}
  ES_USER_PRESENT     = DWORD($00000004);
  {$EXTERNALSYM ES_USER_PRESENT}
  ES_CONTINUOUS       = DWORD($80000000);
  {$EXTERNALSYM ES_CONTINUOUS}
  ES_AWAYMODE_REQUIRED = DWORD($00000040);
  {$EXTERNALSYM ES_AWAYMODE_REQUIRED}

type
  EXECUTION_STATE = DWORD;

function SetThreadExecutionState(esFlags: EXECUTION_STATE): EXECUTION_STATE; stdcall; external 'kernel32.dll';

procedure WndProc(var MyMessage: TMessage);
begin
  if (MyMessage.Msg = WM_POWERBROADCAST)
  or (MyMessage.Msg = WM_POWER) then
  begin
    {*** die ganzen MESSAGES hab ich mal zum Testen mit aufgenommen... ***}
    if (MyMessage.WParam = PBT_APMQUERYSUSPEND)
    or (MyMessage.WParam = PWR_SUSPENDREQUEST)
    or (MyMessage.WParam = PBT_APMQUERYSTANDBY)
    or (MyMessage.WParam = PBT_APMSUSPEND)
    or (MyMessage.WParam = PBT_APMSTANDBY)
    or (MyMessage.WParam = PBT_POWERSETTINGCHANGE)
    or (MyMessage.WParam = PBT_APMPOWERSTATUSCHANGE) then
    begin
      {*** hier würde ich gerne Pause machen ***}
      SetThreadExecutionState(ES_AWAYMODE_REQUIRED);
      MyMessage.Result := BROADCAST_QUERY_DENY;

      {*** das zuvor gewählte Programm wird ausgeführt, aber halt eben erst zu spät ***}
      {*** und der Standby wird einfach knallhart fortgesetzt ***}
      if (SelectEdt1.Text <> EmptyStr) then
        ShellExecute_AndWait(SelectEdt1.Text, SelectParamEdt1.Text);

      {*** nach erledigter Arbeit soll das System einfach da weitermachen, wo ich es unterbrochen habe ***}
      //MyMessage.Result := 1;
      //SetThreadExecutionState(ES_CONTINUOUS);
    end
    else
      if (MyMessage.WParam = PBT_APMRESUMECRITICAL)
      or (MyMessage.WParam = PBT_APMRESUMESUSPEND)
      or (MyMessage.WParam = PBT_APMRESUMESTANDBY)
      or (MyMessage.WParam = PBT_APMRESUMEAUTOMATIC) then
      begin
        {*** und hier wird ein anderes Programm beim RESUME ausgeführt, klappt prima ***}
        if (SelectEdt2.Text <> EmptyStr) then
          ShellExecute_AndWait(SelectEdt2.Text, SelectParamEdt2.Text);
      end;
    end;
  inherited WndProc(MyMessage);
end;

jfheins 10. Aug 2012 18:34

AW: Ruhezustand / Hibernate unter Windows 7 und Windows HomeServer 2011
 
Geht nicht.
Wie hier beschrieben: http://blogs.msdn.com/b/oldnewthing/...16/533250.aspx
Hast du ungefähr 2 Sekunden Zeit um etwas zu tun.
Früher (unter XP) war das mal anders, aber mit Vista kam die Philosophie
"Es wird gemacht was der User sagt, auch wenn die Programme rumjammern" zum tragen ;-)

hathor 10. Aug 2012 21:08

AW: Ruhezustand / Hibernate unter Windows 7 und Windows HomeServer 2011
 
ShutDownBlockReasonCreate

Info:
http://msdn.microsoft.com/en-us/libr...=vs.85%29.aspx
.
http://bartdesmet.net/blogs/bart/arc...n-C_2300_.aspx

Dalai 10. Aug 2012 21:53

AW: Ruhezustand / Hibernate unter Windows 7 und Windows HomeServer 2011
 
Ich empfehle einen anderen, einfacheren Weg: Gerät(e), die runtergefahren werden sollen, pingen in Intervallen die fraglichen anderen Geräte an und fahren sich bei Nichtreaktion selbst herunter, also genau umgekehrt wie du es bisher machst. Das funktioniert ganz brauchbar und sogar OS-übergreifend, erfordert natürlich ein paar Kenntnisse entweder im Schreiben von Skripten oder Programmieren (letzteres sollte ja kein Problem sein :lol:); es gibt bestimmt auch fertige Programme/Skripte für diese Variante (hab keines zur Hand, weil ich es nicht brauche).

MfG Dalai

hathor 11. Aug 2012 20:20

AW: Ruhezustand / Hibernate unter Windows 7 und Windows HomeServer 2011
 
Mehr Infos:

Shutdown Changes for Windows Vista
- differences between shutdown on Windows Vista and Windows XP
- gilt auch für WIN 7

http://msdn.microsoft.com/en-us/libr...=vs.85%29.aspx

Bambuti2000 13. Aug 2012 12:31

AW: Ruhezustand / Hibernate unter Windows 7 und Windows HomeServer 2011
 
Hi alle zusammen,

erstmal Danke für eure Antworten...

Geht nicht, gibt's nicht! Dachte ich bis jetzt immer, aber auch nach nun nochmals mehreren Tagen voll Tests und Recherchen, komme ich langsam an meine Grenzen und bin tief betroffen keine Lösung gefunden/geschaffen zu haben.

Leider kann "ShutDownBlockReasonCreate" wohl auch kaum auf ein "nicht Herunterfahren" reagieren und ist somit für Standby/Hibernate unpassend.

Ich werde wohl oder über die Variante von Dalai (nichts gegen die Idee, ich dachte nur ich könnte alles vom Server aus steuern) in Betracht ziehen.

Falls es allerdings doch jemandem gelingen sollte, wäre ich über eine kurze Info oder ein paar Tips nicht unerfreut.

Danke nochmals... :wink:

sansimarkus 14. Aug 2012 10:23

AW: Ruhezustand / Hibernate unter Windows 7 und Windows HomeServer 2011
 
Mit VisualStudio2012 und den KMDF-Templates kannst du dir (auch ohne große c++ Kenntnisse) einen Treiber kompilieren der Shutdown und Hibernate warten lässt. Das bringt dir beim Shutdown zwar nix wenn jemand auf "Sofort Herunterfahren" klickt, aber ansonsten kannst du damit genau das machen was du brauchst. In den Templates von den PnP-Treibern sind schon fertige Codesnippets dafür - ist nur ein wenig Sucharbeit. Der Haken dabei ist, dass du zum installieren des Treibers einmal in den Debug-modus von Windows musst sofern die Zielplatform Windows7/Server2008 64bit ist.


Edit: ansonsten ließe sich mit einem Treiber auch zwShutDownSystem und zwHibernateSystem aus der ntkernel.exe hooken - aber da kommts dann darauf an wie Schmerzbefreit du beim debugging bist, denn das ist ne haarige Angelegenheit, wie mit allen undokumentierten API Funktionen eben.


Edit2: und mal andersrum gedacht; warum nicht einfach die Taskleiste/Startmenü(=explorer) oder das Programm hooken, was den Shutdown-Befehl initial auslöst?

hathor 15. Aug 2012 07:17

AW: Ruhezustand / Hibernate unter Windows 7 und Windows HomeServer 2011
 
Don't Sleep ist ein kleines Programm, welches während der Laufzeit verhindert,
daß der PC in den Standby Modus oder Ruhezustand wechselt.
Aber nicht nur das, es wird ebenso das Abmelden am Computer verhindert,
sowie das Deaktivieren des Monitors, oder die Aktivierung des Bildschirmschoners.

"Don't Sleep" muss nicht installiert werden. Einfach am Desktop platzieren,
oder für portablen Einsatz auf den USB-Stick kopieren.

Info:
http://www.softwareok.de/?seite=Microsoft/DontSleep

Don't Sleep 2.81
DL:
http://www.softwareok.de/Download/DontSleep.zip
oder:
http://www.softwareok.de/?Download=D.../DontSleep.zip

Bambuti2000 28. Aug 2012 15:17

AW: Ruhezustand / Hibernate unter Windows 7 und Windows HomeServer 2011
 
Hi alle zusammen,

nur noch kurz zur Vervollständigung...

Don'tSleep funktioniert nicht ab Vista ==>

Ja, man könnte auch LightsOut hooken, aber ich wenn dann mal ein anderes Programm wird...

Ich hab jetzt die Netzwerk-Festplatte (mit integriertem Linux als BS) durch die Hintertüre modifiziert und einen Cron-Job laufen, der alle 15 Minuten prüft ob der Server noch erreichbar ist. Wenn nicht fährt die Platte in Standby. Funktioniert Spitze. Dank an Dalai.


Alle Zeitangaben in WEZ +1. Es ist jetzt 08:51 Uhr.

Powered by vBulletin® Copyright ©2000 - 2024, Jelsoft Enterprises Ltd.
LinkBacks Enabled by vBSEO © 2011, Crawlability, Inc.
Delphi-PRAXiS (c) 2002 - 2023 by Daniel R. Wolf, 2024 by Thomas Breitkreuz