Domanda

Voglio ottenere il numero di serie del disco rigido di avvio tramite una query WQL.

La partizione di avvio può essere recuperata utilizzando la seguente query:

SELECT * FROM Win32_DiskPartition where BootPartition=True

Il numero di serie è in Win32_DiskDrive:

SELECT DeviceID, SerialNumber FROM Win32_DiskDrive

Win32_DiskDriveToDiskPartition ha la mappatura di Win32_DiskDrive A Win32_DiskPartition.Sono mappati Win32_DiskDrive.DeviceID A Win32_DiskPartition.DeviceID In Win32_DiskDriveToDiskPartition

Come posso creare una query WQL che si unisce internamente Win32_DiskPartition E Win32_DiskDrive?Devo usare gli Associatori o funziona con INNER JOIN?

È stato utile?

Soluzione

WQL non supporta il file JOIN clausola.È necessario utilizzare il ASSOCIATORS OF dichiarazione come hai indovinato.Ecco un esempio in VBScript:

strComputer = "." 
Set oWMI = GetObject("winmgmts:\\" & strComputer & "\root\CIMV2") 

Set colPartitions = oWMI.ExecQuery( _
    "SELECT * FROM Win32_DiskPartition WHERE BootPartition=True") 

For Each oPartition in colPartitions 

    Set colDrives = oWMI.ExecQuery( _
        "ASSOCIATORS OF {Win32_DiskPartition.DeviceID='" _
        & oPartition.DeviceID & "'} WHERE ResultClass=Win32_DiskDrive")

    For Each oDrive in colDrives
        WScript.Echo oDrive.SerialNumber
    Next

Next

Si noti, tuttavia, che il Win32_DiskDrive.SerialNumber la proprietà non è disponibile prima di Windows Vista.Quindi, se vuoi che il tuo codice funzioni anche su versioni precedenti di Windows (ad es.Windows XP o Windows 2000) dovresti prendere in considerazione l'utilizzo di API diverse da WMI.


Modificare: (risposta al commento) Sì, puoi aggiungere un file nidificato ASSOCIATORS OF interrogare per ottenere il Win32_PhysicalMedia istanze corrispondenti a Win32_DiskDrive istanze;qualcosa come questo:

...
For Each oDrive in colDrives
    Set colMedia = oWMI.ExecQuery( _
        "ASSOCIATORS OF {Win32_DiskDrive.DeviceID='" _
        & oDrive.DeviceID & "'} WHERE ResultClass=Win32_PhysicalMedia")

    For Each oMedia in colMedia
        WScript.Echo oMedia.SerialNumber
    Next
Next

Non hai detto quale linguaggio stai utilizzando: immagino che in PowerShell o C# il tutto possa essere fatto in modo più elegante, ma VBScript è piuttosto dettagliato.

Altri suggerimenti

Ecco il codice C ++ che fa la stessa cosa del codice VBScript pubblicato da Helen.

// Obtain the initial locator to WMI
// ...
// Connect to WMI through the IWbemLocator::ConnectServer method
// ...
// Set security levels on the proxy
// ...

wchar_t wmihddsn[256];
    *wmihddsn=0;

hres = pSvc->ExecQuery(
    bstr_t("WQL"),
    bstr_t("SELECT * FROM Win32_DiskPartition WHERE BootPartition=True"),
    WBEM_FLAG_FORWARD_ONLY | WBEM_FLAG_RETURN_IMMEDIATELY, 
    NULL,
    &pEnumerator);

if(SUCCEEDED(hres) && pEnumerator) 
{
    // get the first Win32_DiskPartition
    HRESULT hr = pEnumerator->Next(WBEM_INFINITE, 1, &pclsObj, &uReturn);

    if(SUCCEEDED(hr) && 0 != uReturn)
    {
        VARIANT vtProp;
        wchar_t tmp[1024];
        char query[1024];

        // Get the value of the partition's DeviceID property
        hr = pclsObj->Get(L"DeviceID", 0, &vtProp, 0, 0);
        if(SUCCEEDED(hr))
        {
            if(vtProp.vt == VT_BSTR) {
                // wcout << " SerialNumber : " << vtProp.bstrVal << endl;
                wcscpy(tmp, vtProp.bstrVal);
            }
            VariantClear(&vtProp);


            // "join" Win32_DiskPartition to Win32_DiskDrive
            sprintf(query, 
                "ASSOCIATORS OF {Win32_DiskPartition.DeviceID='%s'} WHERE ResultClass=Win32_DiskDrive",
                NarrowWcharString(tmp));

            hres = pSvc->ExecQuery(
                bstr_t("WQL"),
                bstr_t(query),
                WBEM_FLAG_FORWARD_ONLY | WBEM_FLAG_RETURN_IMMEDIATELY, 
                NULL,
                &pEnumerator1);

            if(SUCCEEDED(hres) && pEnumerator1)
            {
                // get the first Win32_DiskDrive
                hr = pEnumerator1->Next(WBEM_INFINITE, 1, &pclsObj1, &uReturn);

                if(SUCCEEDED(hr) && 0 != uReturn)
                {
                    // Get the value of the disk-drive's DeviceID
                    hr = pclsObj1->Get(L"DeviceID", 0, &vtProp, 0, 0);
                    if(SUCCEEDED(hr))
                    {
                        if(vtProp.vt == VT_BSTR)
                        {
                            wcscpy(tmp, vtProp.bstrVal);
                        }
                        VariantClear(&vtProp);


                        // "join" Win32_DiskDrive to Win32_PhysicalMedia
                        sprintf(query,
                            "ASSOCIATORS OF {Win32_DiskDrive.DeviceID='%s'} WHERE ResultClass=Win32_PhysicalMedia",
                            NarrowWcharString(tmp));

                        hres = pSvc->ExecQuery(
                            bstr_t("WQL"),
                            bstr_t(query),
                            WBEM_FLAG_FORWARD_ONLY | WBEM_FLAG_RETURN_IMMEDIATELY, 
                            NULL,
                            &pEnumerator2);

                        if(SUCCEEDED(hres) && pEnumerator2)
                        {
                            // get the first Win32_PhysicalMedia
                            hr = pEnumerator2->Next(WBEM_INFINITE, 1, &pclsObj2, &uReturn);

                            if(SUCCEEDED(hr) && 0 != uReturn)
                            {
                                // get the PhysicalMedia's SerialNumber
                                hr = pclsObj2->Get(L"SerialNumber", 0, &vtProp, 0, 0);
                                if(SUCCEEDED(hr))
                                {
                                    if(vtProp.vt == VT_BSTR) 
                                    {
                                        // wcout << " SerialNumber : " << vtProp.bstrVal << endl;
                                        wcscpy(wmihddsn,vtProp.bstrVal);
                                    }
                                    VariantClear(&vtProp);
                                }

                            }

                            if(pclsObj2) pclsObj2->Release();
                        }
                        if(pEnumerator2) pEnumerator2->Release();

                    } // get disk-drive's DeviceID
                }

                if(pclsObj1) pclsObj1->Release();
            }
            if(pEnumerator1) pEnumerator1->Release();

        } // get partition's DeviceID
    }

    if(pclsObj) pclsObj->Release();
} // if succeeded first query
if(pEnumerator) pEnumerator->Release();

// ...
// cleanup
.

Autorizzato sotto: CC-BY-SA insieme a attribuzione
Non affiliato a StackOverflow
scroll top