Thema: Delphi anderes Programm beenden

Einzelnen Beitrag anzeigen

Benutzerbild von Moombas
Moombas

Registriert seit: 22. Mär 2017
Ort: bei Flensburg
525 Beiträge
 
FreePascal / Lazarus
 
#33

AW: anderes Programm beenden

  Alt 21. Feb 2019, 10:25
Hallo zusammen,

ich hatte ein ähnliches Problem und mir den Codes aus Beitrag 7 (https://www.delphipraxis.net/272652-post7.html) "geklaut". Dieser hatte auch funktioniert, allerdings bekomme ich neuerdings eine Zugriffsverletzung im laufenden Programm bei
Delphi-Quellcode:
EnumWindows(@EnumWindowsProc, LPARAM(List));

//-->
function EnumWindowsProc(hWnd: HWND; lParam: LPARAM): BOOL; stdcall;
  begin
    TList(lParam).Add(Pointer(hWnd));
    Result := True;
  end;
Kann ich dabei den Grund irgendwie lokalisieren? Ich vermute das die Funktion hier irgendwie auf einen Fehler läuft.

Hier die einzelnen Codes von "mir":
Delphi-Quellcode:
//...global private
private
    { Private-Deklarationen }
    AppPID : DWORD;

//...Programm (als bestimmter Nutzer) starten
function TTools.CreateProcessAsLogon(const User, PW, Application, param, CmdLine: WideString): DWORD;
var
  s : WideString;
  si : TStartupInfoW;
  pif : TProcessInformation;
begin
  ZeroMemory(@si, sizeof(si));
  si.cb := sizeof(si);
  si.dwFlags := STARTF_USESHOWWINDOW;
  si.wShowWindow := 1;

  if CmdLine = 'then
    s := Application
  else
    s := Application + ' "' + CmdLine + '"';

  SetLastError(0);

  SI.cb := SizeOf(TStartupInfo);
  if CreateProcessWithLogonW(PWideChar(User), nil, PWideChar(PW), 0, nil, PWideChar(s), CREATE_DEFAULT_ERROR_MODE, nil, PChar(param), @si, @pif) then
  begin
    AppPID := PIf.dwProcessId;
    CloseHandle(PIf.hProcess);
    CloseHandle(PIf.hThread);
  end;

  Result := GetLastError;
end;

//...gestartetes Programm beenden
procedure TTools.EscapeClick(Sender: TObject);
  function EnumWindowsProc(hWnd: HWND; lParam: LPARAM): BOOL; stdcall;
  begin
    TList(lParam).Add(Pointer(hWnd));
    Result := True;
  end;

var
  List : TList;
  I, answer : Integer;
  ProcessId : DWORD;
  ThreadId : DWORD;
  ProcessHandle: THandle;
  ExitCode : DWORD;
begin
  if Instant.Enabled = true then
  begin
    answer := messagedlg('Wollen sie wirklich abbrechen?', mtConfirmation, [mbYes,mbNo], 0);
    if answer = mrYes then
    begin
      if AppPID <> 0 then
      begin
        List := TList.Create;
        try
          EnumWindows(@EnumWindowsProc, LPARAM(List)); //<---Hier kommt die Zugriffsverletzung
          for I := 0 to List.Count - 1 do
          begin
            ThreadId := GetWindowThreadProcessId(HWND(List.Items[I]), ProcessId);
            if ProcessId = AppPID then
            begin
              if IsWindow(HWND(List.Items[I])) then
              begin
                PostThreadMessage(ThreadId, WM_QUIT, 0, 0);
                ProcessHandle := OpenProcess(PROCESS_ALL_ACCESS, False, ProcessId);
                if ProcessHandle <> 0 then
                begin
                  GetExitCodeProcess(ProcessHandle, ExitCode);
                  TerminateProcess(ProcessHandle, ExitCode);
                  CloseHandle(ProcessHandle);
                end;
              end;
              Break;
            end;
          end;
        finally
          List.Free;
        end;
      end;
      //Log schreiben
      Logging(PfadP + Programs.items[Programs.itemindex] + ' wurde abgebrochen!');
      answer := messagedlg('Wollen sie die bisherigen Daten einlesen?', mtConfirmation, [mbYes,mbNo], 0);
      if answer = mrYes then
      begin
        FertigClick(Sender);
      end;
      AppPID := 0;
      Progress.Animate := False;
      Run.Enabled := False;
      Programs.Enabled := True;
      Data.Enabled := True;
      TxTLogs.Enabled := True;
      Escape.Enabled := False;
      LogL.Hide;
      LogA.Hide;
      Timer3.Enabled := False;
      Instant.Enabled := False;
      Kopieren.Enabled := True;
      FilialeC.Enabled := True;
      BezirkS.Enabled := True;
      FilialenPS.Enabled := True;
      Manuell.Enabled := True;
      Last.Enabled := True;
    end;
  end else
  begin
    Progress.Animate := False;
    Run.Enabled := False;
    Programs.Enabled := True;
    Data.Enabled := True;
    TxTLogs.Enabled := True;
    Escape.Enabled := False;
    LogL.Hide;
    LogA.Hide;
    Timer3.Enabled := False;
    Instant.Enabled := False;
    Kopieren.Enabled := True;
    FilialeC.Enabled := True;
    BezirkS.Enabled := True;
    FilialenPS.Enabled := True;
    Manuell.Enabled := True;
    Last.Enabled := True;
    Watch.Stop;
    watch.Destroy;
  end;
end;
Kann das durch meine Umstellung des Programms auf 64Bit kommen?
Edit: Wenn ich es als 32-Bit kompiliere funktioniert es einwandfrei. Wie kann ich den Teil für 64Bit ändern?
Der Weg ist das Ziel aber man sollte auf dem Weg niemals das Ziel aus den Augen verlieren.

Geändert von Moombas (21. Feb 2019 um 11:04 Uhr)
  Mit Zitat antworten Zitat