wbemprox: Create one processor object per package.

Signed-off-by: Hans Leidekker <hans@codeweavers.com>
Signed-off-by: Alexandre Julliard <julliard@winehq.org>
stable
Hans Leidekker 2019-01-25 10:44:14 +01:00 committed by Alexandre Julliard
parent f2e1c51422
commit cee8986529
2 changed files with 90 additions and 34 deletions

View File

@ -1365,38 +1365,47 @@ static UINT get_processor_count(void)
return info.NumberOfProcessors;
}
static UINT get_logical_processor_count( UINT *num_cores )
static UINT get_logical_processor_count( UINT *num_physical, UINT *num_packages )
{
SYSTEM_LOGICAL_PROCESSOR_INFORMATION *info;
UINT i, j, count = 0;
SYSTEM_LOGICAL_PROCESSOR_INFORMATION_EX *buf, *entry;
UINT core_relation_count = 0, package_relation_count = 0;
NTSTATUS status;
ULONG len;
ULONG len, offset = 0;
BOOL smt_enabled = FALSE;
DWORD all;
if (num_cores) *num_cores = get_processor_count();
status = NtQuerySystemInformation( SystemLogicalProcessorInformation, NULL, 0, &len );
if (num_packages) *num_packages = 1;
status = NtQuerySystemInformationEx( SystemLogicalProcessorInformationEx, &all, sizeof(all), NULL, 0, &len );
if (status != STATUS_INFO_LENGTH_MISMATCH) return get_processor_count();
if (!(info = heap_alloc( len ))) return get_processor_count();
status = NtQuerySystemInformation( SystemLogicalProcessorInformation, info, len, &len );
if (!(buf = heap_alloc( len ))) return get_processor_count();
status = NtQuerySystemInformationEx( SystemLogicalProcessorInformationEx, &all, sizeof(all), buf, len, NULL );
if (status != STATUS_SUCCESS)
{
heap_free( info );
heap_free( buf );
return get_processor_count();
}
if (num_cores) *num_cores = 0;
for (i = 0; i < len / sizeof(*info); i++)
while (offset < len)
{
if (info[i].Relationship == RelationProcessorCore)
entry = (SYSTEM_LOGICAL_PROCESSOR_INFORMATION_EX *)((char *)buf + offset);
if (entry->Relationship == RelationProcessorCore)
{
for (j = 0; j < sizeof(ULONG_PTR); j++) if (info[i].ProcessorMask & (1 << j)) count++;
core_relation_count++;
if (entry->u.Processor.Flags & LTP_PC_SMT) smt_enabled = TRUE;
}
else if (info[i].Relationship == RelationProcessorPackage && num_cores)
else if (entry->Relationship == RelationProcessorPackage)
{
for (j = 0; j < sizeof(ULONG_PTR); j++) if (info[i].ProcessorMask & (1 << j)) (*num_cores)++;
package_relation_count++;
}
offset += entry->Size;
}
heap_free( info );
return count;
heap_free( buf );
if (num_physical) *num_physical = core_relation_count;
if (num_packages) *num_packages = package_relation_count;
return smt_enabled ? core_relation_count * 2 : core_relation_count;
}
static UINT64 get_total_physical_memory(void)
@ -1460,8 +1469,7 @@ static enum fill_status fill_compsys( struct table *table, const struct expr *co
rec->manufacturer = compsys_manufacturerW;
rec->model = compsys_modelW;
rec->name = get_computername();
rec->num_logical_processors = get_logical_processor_count( NULL );
rec->num_processors = get_processor_count();
rec->num_logical_processors = get_logical_processor_count( NULL, &rec->num_processors );
rec->total_physical_memory = get_total_physical_memory();
rec->username = get_username();
if (!match_row( table, row, cond, &status )) free_row_values( table, row );
@ -2981,10 +2989,12 @@ static enum fill_status fill_processor( struct table *table, const struct expr *
static const WCHAR fmtW[] = {'C','P','U','%','u',0};
WCHAR caption[100], device_id[14], processor_id[17], manufacturer[13], name[49] = {0}, version[50];
struct record_processor *rec;
UINT i, offset = 0, num_rows = 0, num_cores, num_logical_processors, count = get_processor_count();
UINT i, offset = 0, num_rows = 0, num_logical, num_physical, num_packages;
enum fill_status status = FILL_STATUS_UNFILTERED;
if (!resize_table( table, count, sizeof(*rec) )) return FILL_STATUS_FAILED;
num_logical = get_logical_processor_count( &num_physical, &num_packages );
if (!resize_table( table, num_packages, sizeof(*rec) )) return FILL_STATUS_FAILED;
get_processor_caption( caption );
get_processor_id( processor_id );
@ -2992,10 +3002,7 @@ static enum fill_status fill_processor( struct table *table, const struct expr *
get_processor_name( name );
get_processor_version( version );
num_logical_processors = get_logical_processor_count( &num_cores ) / count;
num_cores /= count;
for (i = 0; i < count; i++)
for (i = 0; i < num_packages; i++)
{
rec = (struct record_processor *)(table->data + offset);
rec->addresswidth = get_osarchitecture() == os_32bitW ? 32 : 64;
@ -3012,8 +3019,8 @@ static enum fill_status fill_processor( struct table *table, const struct expr *
rec->manufacturer = heap_strdupW( manufacturer );
rec->maxclockspeed = get_processor_maxclockspeed( i );
rec->name = heap_strdupW( name );
rec->num_cores = num_cores;
rec->num_logical_processors = num_logical_processors;
rec->num_cores = num_physical / num_packages;
rec->num_logical_processors = num_logical / num_packages;
rec->processor_id = heap_strdupW( processor_id );
rec->processortype = 3; /* central processor */
rec->revision = get_processor_revision();

View File

@ -529,12 +529,16 @@ static void test_Win32_ComputerSystem( IWbemServices *services )
static const WCHAR modelW[] = {'M','o','d','e','l',0};
static const WCHAR nameW[] = {'N','a','m','e',0};
static const WCHAR usernameW[] = {'U','s','e','r','N','a','m','e',0};
static const WCHAR numprocessorsW[] =
{'N','u','m','b','e','r','O','f','P','r','o','c','e','s','s','o','r','s',0};
static const WCHAR numlogicalprocessorsW[] =
{'N','u','m','b','e','r','O','f','L','o','g','i','c','a','l','P','r','o','c','e','s','s','o','r','s',0};
static const WCHAR queryW[] =
{'S','E','L','E','C','T',' ','*',' ','F','R','O','M',' ','W','i','n','3','2','_',
'C','o','m','p','u','t','e','r','S','y','s','t','e','m',0};
BSTR wql = SysAllocString( wqlW ), query = SysAllocString( queryW );
IEnumWbemClassObject *result;
IWbemClassObject *service;
IWbemClassObject *obj;
VARIANT value;
CIMTYPE type;
HRESULT hr;
@ -565,17 +569,17 @@ static void test_Win32_ComputerSystem( IWbemServices *services )
goto out;
}
hr = IEnumWbemClassObject_Next( result, 10000, 1, &service, &count );
hr = IEnumWbemClassObject_Next( result, 10000, 1, &obj, &count );
ok( hr == S_OK, "got %08x\n", hr );
type = 0xdeadbeef;
VariantInit( &value );
hr = IWbemClassObject_Get( service, memorytypeW, 0, &value, &type, NULL );
hr = IWbemClassObject_Get( obj, memorytypeW, 0, &value, &type, NULL );
ok( hr == WBEM_E_NOT_FOUND, "got %08x\n", hr );
type = 0xdeadbeef;
VariantInit( &value );
hr = IWbemClassObject_Get( service, modelW, 0, &value, &type, NULL );
hr = IWbemClassObject_Get( obj, modelW, 0, &value, &type, NULL );
ok( hr == S_OK, "failed to get model %08x\n", hr );
ok( V_VT( &value ) == VT_BSTR, "unexpected variant type 0x%x\n", V_VT( &value ) );
ok( type == CIM_STRING, "unexpected type 0x%x\n", type );
@ -584,7 +588,7 @@ static void test_Win32_ComputerSystem( IWbemServices *services )
type = 0xdeadbeef;
VariantInit( &value );
hr = IWbemClassObject_Get( service, nameW, 0, &value, &type, NULL );
hr = IWbemClassObject_Get( obj, nameW, 0, &value, &type, NULL );
ok( hr == S_OK, "failed to get computer name %08x\n", hr );
ok( V_VT( &value ) == VT_BSTR, "unexpected variant type 0x%x\n", V_VT( &value ) );
ok( type == CIM_STRING, "unexpected type 0x%x\n", type );
@ -593,14 +597,33 @@ static void test_Win32_ComputerSystem( IWbemServices *services )
type = 0xdeadbeef;
VariantInit( &value );
hr = IWbemClassObject_Get( service, usernameW, 0, &value, &type, NULL );
hr = IWbemClassObject_Get( obj, numlogicalprocessorsW, 0, &value, &type, NULL );
ok( hr == S_OK || broken(hr == WBEM_E_NOT_FOUND) /* win2k3 */, "got %08x\n", hr );
if (hr == S_OK)
{
ok( V_VT( &value ) == VT_I4, "unexpected variant type 0x%x\n", V_VT( &value ) );
ok( type == CIM_UINT32, "unexpected type 0x%x\n", type );
trace( "numlogicalprocessors %u\n", V_I4( &value ) );
}
type = 0xdeadbeef;
VariantInit( &value );
hr = IWbemClassObject_Get( obj, numprocessorsW, 0, &value, &type, NULL );
ok( hr == S_OK, "got %08x\n", hr );
ok( V_VT( &value ) == VT_I4, "unexpected variant type 0x%x\n", V_VT( &value ) );
ok( type == CIM_UINT32, "unexpected type 0x%x\n", type );
trace( "numprocessors %u\n", V_I4( &value ) );
type = 0xdeadbeef;
VariantInit( &value );
hr = IWbemClassObject_Get( obj, usernameW, 0, &value, &type, NULL );
ok( hr == S_OK, "failed to get computer name %08x\n", hr );
ok( V_VT( &value ) == VT_BSTR, "unexpected variant type 0x%x\n", V_VT( &value ) );
ok( type == CIM_STRING, "unexpected type 0x%x\n", type );
ok( !lstrcmpiW( V_BSTR( &value ), username ), "got %s, expected %s\n", wine_dbgstr_w(V_BSTR(&value)), wine_dbgstr_w(username) );
VariantClear( &value );
IWbemClassObject_Release( service );
IWbemClassObject_Release( obj );
IEnumWbemClassObject_Release( result );
out:
SysFreeString( query );
@ -1563,6 +1586,10 @@ static void test_Win32_Processor( IWbemServices *services )
{'M','a','n','u','f','a','c','t','u','r','e','r',0};
static const WCHAR nameW[] =
{'N','a','m','e',0};
static const WCHAR numcoresW[] =
{'N','u','m','b','e','r','O','f','C','o','r','e','s',0};
static const WCHAR numlogicalprocessorsW[] =
{'N','u','m','b','e','r','O','f','L','o','g','i','c','a','l','P','r','o','c','e','s','s','o','r','s',0};
static const WCHAR processoridW[] =
{'P','r','o','c','e','s','s','o','r','I','d',0};
static const WCHAR revisionW[] =
@ -1665,6 +1692,28 @@ static void test_Win32_Processor( IWbemServices *services )
trace( "version %s\n", wine_dbgstr_w(V_BSTR( &val )) );
VariantClear( &val );
type = 0xdeadbeef;
VariantInit( &val );
hr = IWbemClassObject_Get( obj, numlogicalprocessorsW, 0, &val, &type, NULL );
ok( hr == S_OK || broken(hr == WBEM_E_NOT_FOUND) /* win2k3 */, "got %08x\n", hr );
if (hr == S_OK)
{
ok( V_VT( &val ) == VT_I4, "unexpected variant type 0x%x\n", V_VT( &val ) );
ok( type == CIM_UINT32, "unexpected type 0x%x\n", type );
trace( "numlogicalprocessors %u\n", V_I4( &val ) );
}
type = 0xdeadbeef;
VariantInit( &val );
hr = IWbemClassObject_Get( obj, numcoresW, 0, &val, &type, NULL );
ok( hr == S_OK || broken(hr == WBEM_E_NOT_FOUND) /* win2k3 */, "got %08x\n", hr );
if (hr == S_OK)
{
ok( V_VT( &val ) == VT_I4, "unexpected variant type 0x%x\n", V_VT( &val ) );
ok( type == CIM_UINT32, "unexpected type 0x%x\n", type );
trace( "numcores %u\n", V_I4( &val ) );
}
IWbemClassObject_Release( obj );
}