Einzelnen Beitrag anzeigen

Chewie

Registriert seit: 10. Jun 2002
Ort: Deidesheim
2.886 Beiträge
 
Turbo Delphi für Win32
 
#1

Nach Variablenaufruf wird Variableninhalt gelöscht

  Alt 10. Aug 2002, 17:04
Es gibt Tage, an denen zweifle ich an meinem Verstand...
Ich hab jetzt wieder ein ähnliches Problem wie das mit den Arrays (s.u.), aber diesmal hab ich nicht anstelle einer Variablen eine Zahl hingeschrieben.
Wieder einmal scheint ein Code zu funktionieren, solange, bis ich mir das Ergebnis testweise ausgegen will. Folgende Funnktion benutz ich:
Code:
[b]function[/b] GetThreadID(FileName: [b]String[/b]): DWord;
[b]var[/b]
  ToolHnd, MToolHnd: THandle;
  PE32: TProcessEntry32;
  ME32: TModuleEntry32;
  TE32: TThreadEntry32;
  PIDArray, ThreadArray: [b]Array[/b] [b]of[/b] Dword;
  a: Integer;
  PID: DWord;
[b]begin[/b]
  ToolHnd := CreateToolHelp32Snapshot(TH32CS_SNAPPROCESS [b]or[/b] TH32CS_SNAPTHREAD, 0); [i]//Handle auf Snapshot[/i]
  PE32.dwSize := SizeOf(ProcessEntry32);
  Process32First(ToolHnd, PE32); [i]//erster Prozess[/i]
  [b]if[/b] PE32.szExeFile = ExtractFileName(FileName) [b]then[/b]
  [b]begin[/b]
    SetLength(PIDArray, 1);
    PIDArray[0] := PE32.th32ProcessID;
  [b]end[/b];
  [b]while[/b] Process32Next(ToolHnd, PE32) [b]do[/b]
  [b]begin[/b]
    [b]if[/b] PE32.szExeFile = ExtractFileName(FileName) [b]then[/b]
    [b]begin[/b]
      SetLength(PIDArray, Length(PIDArray) + 1);
      PIDArray[Length(PIDARRAY) - 1] := PE32.th32ProcessID;
    [b]end[/b];
  [b]end[/b];
  [i]//ShowMessage(InttoStr(PIDArray[0]));
  { Jetzt sind alle PIDs der Prozesse, deren Dateinamen gleich dem gesuchten ist, gespeichert }
  { Jetzt wird für jeden Prozess anhand der Modulliste der vollständige Pfad ermittelt und so }
  { die endgültige, richtige ProcessID ermittelt.                                            }[/i]

  PID := 0;
  [b]for[/b] a := 0 [b]to[/b] Length(PIDArray) -1 [b]do[/b]
  [b]begin[/b]
    MToolHnd := CreateToolhelp32Snapshot(TH32CS_SNAPMODULE, PIDArray[a]); [i]//Modulliste des gewählten Prozesses[/i]
    Module32First(MToolhnd, ME32);
    [b]if[/b] ME32.szExePath = FileName [b]then[/b]
    [b]begin[/b]
      PID := ME32.th32ProcessID;
    [b]end[/b]
    [b]else[/b]
    [b]while[/b] Module32Next(MToolHnd, ME32) [b]do[/b]
    [b]begin[/b]
      [b]if[/b] ME32.szExePath = FileName [b]then[/b]
      [b]begin[/b]
        PID := ME32.th32ProcessID;
        break;
      [b]end[/b];
    [b]end[/b];
    CloseHandle(MToolHnd);
    [b]if[/b] PID <> 0 [b]then[/b] break;
  [b]end[/b];
  [i]//ShowMessage(InttoStr(PID));

  { Jetzt werden alle Threads des Prozesses ermittelt                                        }[/i]

  TE32.dwSize := SizeOf(ThreadEntry32);
  Thread32First(ToolHnd, TE32);
  [i]//Form1.Listbox1.Items.Add(InttoStr(TE32.th32OwnerProcessID) + 'Thread ' + InttoStr(TE32.th32ThreadID) + ' gehört zu Prozess ' + InttoStr(TE32.th32OwnerProcessID));[/i]
  [b]if[/b] TE32.th32OwnerProcessID = PID [b]then[/b]
  [b]begin[/b]
    SetLength(ThreadArray,1);
    ThreadArray[0] := TE32.th32ThreadID;
  [b]end[/b];
  [b]while[/b] Thread32Next(ToolHnd, TE32) [b]do[/b]
  [b]begin[/b]
    [i]//Form1.Listbox1.Items.Add(InttoStr(TE32.th32OwnerProcessID) + 'Thread ' + InttoStr(TE32.th32ThreadID) + ' gehört zu Prozess ' + InttoStr(TE32.th32OwnerProcessID));[/i]
    [b]if[/b] TE32.th32OwnerProcessID = PID [b]then[/b]
    [b]begin[/b]
      SetLength(ThreadArray,1);
      ThreadArray[0] := TE32.th32ThreadID;
    [b]end[/b];
  [b]end[/b];
  CloseHandle(ToolHnd);
  ShowMessage(InttoStr(ThreadArray[0]));
  Result := ThreadArray[0];
[b]end[/b];
Das blöde ist, dass ich leider nicht so ganz testen kann, ob sie funktioniert. Weil wenn ich gegen Ende der Funktion mir das Ergebnis ausgeben lasse, komme ich zu dem gewünschten Wert. Wenn ich mir aber den Rückgabewert der Funktion nach dem Aufruf ausgeben will, bekomme ich 0. Damit nicht genug, auch der ShowMessage-Aufruf in der Funktion liefert 0.
Doch es ist nicht nur bei der Thread-ID so. Auch die Prozess-ID ist bei mehrmaligem Ausgeben 0.
Deswegen kann ich nicht testen, ob die Funktion den richtigen Wert zurückliefert. Na ja, OK, ich könnt ihn in ne Datei schreiben, vielleicht würde das gehen. Aber trotzdem würd ich brennend gerne wissen, warum in aller welt sowas passiert. Ihr könnt die Funktion gern mal testen, sie liefert die ThreadID des ersten Threads der laufenden Anwendung, die per filename an die Funktion übergeben wurde. Vergleicht mal, was passiert, wenn ihr die Funnktion einnfach so aufruft und was passiert, wenn ihr den Rückgabewert euch anzeigen lasst. Würd mich wirklich interessieren, ob das Problem auch bei anderen auftaucht oder ob mein WinXP Schuld ist.

Nachtrag: Wenn ich die Funktion auf die eigene Anwendung anwende, scheint das Problem nicht aufzutauchen.
Martin Leim
Egal wie dumm man selbst ist, es gibt immer andere, die noch dümmer sind
  Mit Zitat antworten Zitat