2010-12-19 18 views
4

Erstellen einer 32-Bit-Anwendung mit Delphi Ich habe keinen Zugriff auf alle Hives abhängig davon, ob die Anwendung auf einem Win32 oder Win64 Windows-Maschine ausgeführt wird. Hier ist ein Link für Standardzugriff: http://msdn.microsoft.com/en-us/library/aa390789(v=VS.85).aspxZugriff auf alle 3 Hives in der Registrierung

Ich möchte nur eine einzige Anwendung erstellen, und nicht eine separate Version für 32 & 64. Und ich möchte WMI verwenden und Abrufen von Informationen aus der 32-Bit-Registrierungsstruktur, die 64-Bit-Registrierungsstruktur und der WOW6432Node. Es gibt FLAGS zu setzen, aber ich kann nicht herausfinden, wie die Flags mit einem regulären WMI-Abfrage-Aufruf von meiner Delphi-Anwendung gesendet werden. Hier Informationen über das FLAGS: http://msdn.microsoft.com/en-us/library/aa393067(v=VS.85).aspx

GLibWmi & DelphiWmiCodeCreator exmple:

function GetWMIObject(const objectName: String): IDispatch; //create the Wmi instance 
var 
    chEaten: Integer; 
    BindCtx: IBindCtx; 
    Moniker: IMoniker; 
begin 
    OleCheck(CreateBindCtx(0, bindCtx)); 
    OleCheck(MkParseDisplayName(BindCtx, StringToOleStr(objectName), chEaten, Moniker)); 
    OleCheck(Moniker.BindToObject(BindCtx, nil, IDispatch, Result)); 
end; 

procedure GetWin32_StartupCommandInfo; 
var 
    objWMIService : OLEVariant; 
    colItems  : OLEVariant; 
    colItem  : OLEVariant; 
    oEnum   : IEnumvariant; 
    iValue  : LongWord; 
begin; 
    objWMIService := GetWMIObject('winmgmts:\\localhost\root\CIMV2'); 
    colItems  := objWMIService.ExecQuery('SELECT * FROM Win32_StartupCommand','WQL',0); 
    oEnum   := IUnknown(colItems._NewEnum) as IEnumVariant; 
    while oEnum.Next(1, colItem, iValue) = 0 do 
    begin 
    Writeln(''); 
    end; 
end; 

REVISED Code:

procedure GetWin32_StartupCommandInfo(aIDispatch: IDispatch); 
var 
    objWMIService : OLEVariant; 
    colItems  : OLEVariant; 
    colItem  : OLEVariant; 
    oEnum   : IEnumvariant; 
    iValue  : LongWord; 
begin; 
    objWMIService := aIDispatch; //GetWMIObject('winmgmts:\\localhost\root\CIMV2'); 
    colItems  := objWMIService.ExecQuery('SELECT * FROM Win32_StartupCommand','WQL',0); 
    oEnum   := IUnknown(colItems._NewEnum) as IEnumVariant; 
    while oEnum.Next(1, colItem, iValue) = 0 do 
    begin 
    with Form1.lst1 do begin 

     items.Add(Format('Caption="%s"; Location="%s"',[colItem.Caption,colItem.Location]));// String 
     {items.Add(Format('Command   %s',[colItem.Command]));// String 
     items.Add(Format('Description  %s',[colItem.Description]));// String 
     items.Add(Format('Location  %s',[colItem.Location]));// String 
     items.Add(Format('Name   %s',[colItem.Name]));// String 
     items.Add(Format('SettingID  %s',[colItem.SettingID]));// String 
     items.Add(Format('User   %s',[colItem.User]));// String 
     items.Add(Format('UserSID   %s',[colItem.UserSID]));// String 
     } 
     items.Add(''); 

    end; 
    end; 
end; 

function MyConnectWMI(wmiHost:string; var Services: ISWbemServices):Boolean; 
const 
    STR_CIM2_ROOT ='root\CIMV2'; 
    STR_EMPTY = ''; 
var 
    NVS: SWbemNamedValueSet; 
    providerArchitecture : OleVariant; 
    requiredArchitecture : OleVariant; 
    Locator : ISWbemLocator; //CoSWbemLocator; 
begin 
    try 
    providerArchitecture := 32; // or 64 
    requiredArchitecture := true; 

    NVS := CoSWbemNamedValueSet.Create(); 
    NVS.Add('__ProviderArchitecture', providerArchitecture , 0); 
    NVS.Add('__RequiredArchitecture', requiredArchitecture , 0); 
    // Create the Location object 
    Locator := CoSWbemLocator.Create(); 
    // Connect to the WMI service, with the root\cimv2 namespace 
    Services := Locator.ConnectServer(wmiHost, 
     STR_CIM2_ROOT, {user}STR_EMPTY, {password}STR_EMPTY, 
     STR_EMPTY,STR_EMPTY, 0, NVS); 

    Result := True; 
    except 
    Result := False; 
    end; 
end; 

procedure TForm1.btn1Click(Sender: TObject); 
var 
    aServices: ISWbemServices; 
begin 
    if MyConnectWMI('localhost', aServices) then 
    GetWin32_StartupCommandInfo(aServices); 
end; 

Antwort

2

Sie einen WMI-Moniker verwenden und soweit ich sehen kann, Sie können nicht die Optionen angeben, die Sie benötigen. Sie müssen stattdessen das SWbemLocator-Objekt verwenden, damit Sie den SWbemNamedValueSet als letzten Parameter übergeben können.

Es gibt eine ConnectWMI-Funktion in der Datei UProcedures.pas von GLibWMI. Es geht eine Null an den letzten Parm:

Services := Locator.ConnectServer(wmiHost, 
     STR_CIM2_ROOT, {user}STR_EMPTY, {password}STR_EMPTY, 
     STR_EMPTY,STR_EMPTY, 0, nil); 

Sie benötigen eine Alternative, um so etwas zu schaffen:

var 
    NVS: SWbemNamedValueSet; 
    providerArchitecture : OleVariant; 
    requiredArchitecture : OleVariant; 
///// 

    providerArchitecture := 32; // or 64 
    requiredArchitecture := true; 

    NVS := CoSWbemNamedValueSet.Create(); 
    NVS.Add('__ProviderArchitecture', providerArchitecture , 0); 
    NVS.Add('__RequiredArchitecture', requiredArchitecture , 0); 

    // Create the Location object 
    Locator := CoSWbemLocator.Create(); 
    // Connect to the WMI service, with the root\cimv2 namespace 
    Services := Locator.ConnectServer(wmiHost, 
     STR_CIM2_ROOT, {user}STR_EMPTY, {password}STR_EMPTY, 
     STR_EMPTY,STR_EMPTY, 0, NVS); 

, dass Sie eine ISWbemServices Schnittstelle erhalten wird, auf das Sie ExecQuery dann ausführen können.

Zugriff auf die Registry über StdRegProv -


procedure Get_RegistryValue(aIDispatch: IDispatch); 
var 
    objWMIService : OLEVariant; 

    strKeyPath : OLEVariant; 
    strValue : OLEVariant; 
    strOut : OLEVariant; 

    objStdRegProv : OLEVariant; 
begin; 
    objWMIService := aIDispatch; 

    objStdRegProv := objWMIService.Get('StdRegProv'); 

    strKeyPath := 'Software\Microsoft\Wbem\CIMOM'; 
    strValue := 'Logging'; 

    objStdRegProv.GetStringValue(HKEY_LOCAL_MACHINE, strKeyPath, strValue, strOut); 

    with Form1.lst1 do begin 
     items.Add(strOut); 
    end; 
    end; 
end; 


// connect to root\default instead of cimv2 
function MyConnectWMI(wmiHost:string; var Services: ISWbemServices):Boolean; 
const 
    STR_DEFAULT_ROOT = 'root\default' 
    STR_EMPTY = ''; 
var 
    NVS: SWbemNamedValueSet; 
    providerArchitecture : OleVariant; 
    requiredArchitecture : OleVariant; 
    Locator : ISWbemLocator; //CoSWbemLocator; 
begin 
    try 
    providerArchitecture := 32; // or 64 
    requiredArchitecture := true; 

    NVS := CoSWbemNamedValueSet.Create(); 
    NVS.Add('__ProviderArchitecture', providerArchitecture , 0); 
    NVS.Add('__RequiredArchitecture', requiredArchitecture , 0); 
    // Create the Location object 
    Locator := CoSWbemLocator.Create(); 
    // Connect to the WMI service, with the root\cimv2 namespace 
    Services := Locator.ConnectServer(wmiHost, 
     STR_DEFAULT_ROOT, {user}STR_EMPTY, {password}STR_EMPTY, 
     STR_EMPTY,STR_EMPTY, 0, NVS); 

    Result := True; 
    except 
    Result := False; 
    end; 
end; 
+0

habe ich es zu arbeiten, aber nur, wenn die providerArchitecture auf 64 gesetzt ist, wenn ich es auf 32 gesetzt habe ich bekommen einen EOleException Fehler: „Provider Load Fail“ . Ich benutze Win7 64Bit mit Delphi 2010. – Logman

+0

CHICK oben in meinem ursprünglichen Beitrag im Abschnitt ÜBERARBEITET. Der Code bricht ab, wenn "ExecQuery" ausgeführt wird und nicht wenn ich die Verbindung erstelle. – Logman

+0

Dies liegt an den Anbietern. Win32_StartupCommand wird vom Win32-Provider und nicht vom Registrierungsanbieter bereitgestellt. Diese Seite http://msdn.microsoft.com/en-us/library/aa394570%28v=VS.85%29.aspx listet die Anbieter auf. Der Registry-Provider erwähnt zwei Versionen auf 64-Bit-Plattformen. – vickd