WMI Abfragen, variabel machen?

Für Fragen zur Programmiersprache auf welcher Lazarus aufbaut
Antworten
CeeJay D-Magic
Beiträge: 21
Registriert: Mi 8. Sep 2010, 08:55
OS, Lazarus, FPC: Windows 7 (Lazarus 0.9.31 r35701 FPC 2.6.1 x86_64-win64-win32/win64)
CPU-Target: 32Bit/64bit

WMI Abfragen, variabel machen?

Beitrag von CeeJay D-Magic »

Hallo Community!

Ich suche nach einer Möglichkeit WMI-abfragen einzusetzen ohne zu viel Code verwenden zu müssen.
Hier ein Teil des Codes den ich zurzeit einsetze:

Code: Alles auswählen

function GetWin32_OperatingSystemInfo: String;
const
  WbemUser            ='';
  WbemPassword        ='';
  WbemComputer        ='localhost';
  wbemFlagForwardOnly = $00000020;
var
  FSWbemLocator : OLEVariant;
  FWMIService   : OLEVariant;
  FWbemObjectSet: OLEVariant;
  FWbemObject   : Variant;
  oEnum         : IEnumvariant;
  sValue        : string;
begin;
  FSWbemLocator := CreateOleObject('WbemScripting.SWbemLocator');
  FWMIService   := FSWbemLocator.ConnectServer(WbemComputer, 'root\CIMV2', WbemUser, WbemPassword);
  FWbemObjectSet:= FWMIService.ExecQuery('SELECT * FROM Win32_OperatingSystem','WQL',wbemFlagForwardOnly);
  oEnum         := IUnknown(FWbemObjectSet._NewEnum) as IEnumVariant;
  while oEnum.Next(1, FWbemObject, nil) = 0 do
  begin
    result := '';
 
    sValue:= FWbemObject.Properties_.Item('BootDevice').Value;
    Result:=Format('BootDevice=%s',[sValue]);
    FWbemObject:=Unassigned;
  end;
Da dachte ich, statt haufenweise Anfragen mit dem oben gezeigten Statischen Code zu machen, den Code mit Variablen einzusetzen.
Dazu habe ich gedacht statt

Code: Alles auswählen

function GetWin32_OperatingSystemInfo: String;

Code: Alles auswählen

FWbemObjectSet:= FWMIService.ExecQuery('SELECT * FROM Win32_OperatingSystem','WQL',wbemFlagForwardOnly);
und

Code: Alles auswählen

sValue:= FWbemObject.Properties_.Item('BootDevice').Value;
als code zu verwenden, den auf

Code: Alles auswählen

function GetWin32_Info(classes: String; subclass: String): String;

Code: Alles auswählen

FWbemObjectSet:= FWMIService.ExecQuery(classes,'WQL',wbemFlagForwardOnly);

Code: Alles auswählen

sValue:= FWbemObject.Properties_.Item(subclass).Value;
zu ändern.

GetWin32_Info würde als Parameter den Inhalt zweier Edit.text boxen erhalten, auch mit dem selben Inhalt wie zuvor:
edit1.text = 'SELECT * FROM Win32_OperatingSystem'
edit2.text = 'BootDevice'
man könnte also manuell jede verfügbare Klasse oder unterklasse verwenden mit dem Code - aber irgendwas scheint da nicht zu funktionieren.

Kompiliert wird das ganze ohne Probleme, wenn dieser jedoch den Befehl ausführen soll gibt er mir nur ein

Code: Alles auswählen

EOleException Die Anfrage ist ung?ltig.  80041017
zurück.

Ich vermute das der Datentyp String nicht stimmt, was muss ich da stattdessen angeben?

Oder habe ich einen völligen Denkfehler und muss da komplett anders drangehen?

MfG,
Cee

CeeJay D-Magic
Beiträge: 21
Registriert: Mi 8. Sep 2010, 08:55
OS, Lazarus, FPC: Windows 7 (Lazarus 0.9.31 r35701 FPC 2.6.1 x86_64-win64-win32/win64)
CPU-Target: 32Bit/64bit

Re: WMI Abfragen, variabel machen?

Beitrag von CeeJay D-Magic »

Hm, weiß das wirklich keiner? :o

Vielleicht ergibt sich ja über das Wochenende noch was :)

CeeJay D-Magic
Beiträge: 21
Registriert: Mi 8. Sep 2010, 08:55
OS, Lazarus, FPC: Windows 7 (Lazarus 0.9.31 r35701 FPC 2.6.1 x86_64-win64-win32/win64)
CPU-Target: 32Bit/64bit

Re: WMI Abfragen, variabel machen?

Beitrag von CeeJay D-Magic »

Hat hier keiner auch nur im entferntesten eine Idee?

Benutzeravatar
theo
Beiträge: 10865
Registriert: Mo 11. Sep 2006, 19:01

Re: WMI Abfragen, variabel machen?

Beitrag von theo »

Hast du eine aktuelle Freepascal Version?

Hast du alle Beispiele mal durch? Geht nix?

http://lmgtfy.com/?q=WMIService+ExecQuery+Delphi" onclick="window.open(this.href);return false;

CeeJay D-Magic
Beiträge: 21
Registriert: Mi 8. Sep 2010, 08:55
OS, Lazarus, FPC: Windows 7 (Lazarus 0.9.31 r35701 FPC 2.6.1 x86_64-win64-win32/win64)
CPU-Target: 32Bit/64bit

Re: WMI Abfragen, variabel machen?

Beitrag von CeeJay D-Magic »

Danke theo! Dein Suchbeispiel hat mich auf etwas entscheidendes aufmerksam gemacht, und nachdem ich noch ein wenig rumprobiert habe, ging es!
1. Ist das der Datentyp WideString und
2. ist der konstant! - Da wäre ich im Leben nicht drauf gekommen... :o

Hier der geänderte Code:

Code: Alles auswählen

function GetWin32_Info_variable(const classes, subclass: Widestring; AStrings: TStrings): boolean;
const
  WbemUser            ='';
  WbemPassword        ='';
  WbemComputer        ='localhost';
  wbemFlagForwardOnly = $00000020;
var
  FSWbemLocator : OLEVariant;
  FWMIService   : OLEVariant;
  FWbemObjectSet: OLEVariant;
  FWbemObject   : Variant;
  oEnum         : IEnumvariant;
  sValue        : string;
begin;
  try
  FSWbemLocator := CreateOleObject('WbemScripting.SWbemLocator');
  FWMIService   := FSWbemLocator.ConnectServer(WbemComputer, 'root\CIMV2', WbemUser, WbemPassword);
  FWbemObjectSet:= FWMIService.ExecQuery(classes,'WQL',wbemFlagForwardOnly);
  oEnum         := IUnknown(FWbemObjectSet._NewEnum) as IEnumVariant;
  while oEnum.Next(1, FWbemObject, nil) = 0 do
  begin
    result := false;
    sValue:= FWbemObject.Properties_.Item(subclass).Value;
    AStrings.Add(Format(subclass+'=%s',[sValue]));// String
    FWbemObject:=Unassigned;
  end;
  except
    on E:EOleException do
       AStrings.Add(Format('EOleException %s %x', [E.Message,E.ErrorCode]));
    on E:Exception do
       writeln(E.Classname, ':', E.Message);
  end;
end;

Code: Alles auswählen

procedure TForm1.Button2Click(Sender: TObject);
begin
    GetWin32_Info_variable(Edit1.Text, Edit2.Text, Memo1.Lines);
end;
funzt wunderbar :D

Antworten