Commit 66665af2 by Christopher Cameron Committed by Commit Bot

macOS/ARM: Allow populating GPU based on AGXAccelerator

The existing scheme for populating GPU vendor and device IDs fails on macOS/ARM. If we find no PCI registry entries, look for a AGXAccelerator entry, and (partially) populate that. This is sufficient for Chrome to initialize hardware acceleration. It is unknown how this will interact with multiple GPUs, and this will likely need to be revisited. Bug: chromium:1110421 Change-Id: I08069d7aecf45c83a1d2827cfccc4733c1835994 Reviewed-on: https://chromium-review.googlesource.com/c/angle/angle/+/2324939Reviewed-by: 's avatarCorentin Wallez <cwallez@chromium.org> Reviewed-by: 's avatarGeoff Lang <geofflang@chromium.org> Reviewed-by: 's avatarLingfeng Yang <lfy@google.com> Commit-Queue: ccameron <ccameron@chromium.org>
parent f776eb9c
...@@ -77,40 +77,64 @@ bool GetEntryProperty(io_registry_entry_t entry, CFStringRef name, uint32_t *val ...@@ -77,40 +77,64 @@ bool GetEntryProperty(io_registry_entry_t entry, CFStringRef name, uint32_t *val
return true; return true;
} }
// Gathers the vendor and device IDs for the PCI GPUs // Gathers the vendor and device IDs for GPUs listed in the IORegistry.
bool GetPCIDevices(std::vector<GPUDeviceInfo> *devices) void GetIORegistryDevices(std::vector<GPUDeviceInfo> *devices)
{ {
constexpr uint32_t kNumServices = 2;
const char *kServiceNames[kNumServices] = {"IOPCIDevice", "AGXAccelerator"};
const bool kServiceIsVGA[kNumServices] = {true, false};
for (uint32_t i = 0; i < kNumServices; ++i)
{
// matchDictionary will be consumed by IOServiceGetMatchingServices, no need to release it. // matchDictionary will be consumed by IOServiceGetMatchingServices, no need to release it.
CFMutableDictionaryRef matchDictionary = IOServiceMatching("IOPCIDevice"); CFMutableDictionaryRef matchDictionary = IOServiceMatching(kServiceNames[i]);
io_iterator_t entryIterator; io_iterator_t entryIterator;
if (IOServiceGetMatchingServices(kIOMasterPortDefault, matchDictionary, &entryIterator) != if (IOServiceGetMatchingServices(kIOMasterPortDefault, matchDictionary, &entryIterator) !=
kIOReturnSuccess) kIOReturnSuccess)
{ {
return false; continue;
} }
io_registry_entry_t entry = IO_OBJECT_NULL; io_registry_entry_t entry = IO_OBJECT_NULL;
while ((entry = IOIteratorNext(entryIterator)) != IO_OBJECT_NULL) while ((entry = IOIteratorNext(entryIterator)) != IO_OBJECT_NULL)
{ {
constexpr uint32_t kClassCodeDisplayVGA = 0x30000; constexpr uint32_t kClassCodeDisplayVGA = 0x30000;
uint32_t classCode; uint32_t classCode;
GPUDeviceInfo info; GPUDeviceInfo info;
if (GetEntryProperty(entry, CFSTR("class-code"), &classCode) && // AGXAccelerator entries only provide a vendor ID.
classCode == kClassCodeDisplayVGA && if (!GetEntryProperty(entry, CFSTR("vendor-id"), &info.vendorId))
GetEntryProperty(entry, CFSTR("vendor-id"), &info.vendorId) &&
GetEntryProperty(entry, CFSTR("device-id"), &info.deviceId))
{ {
devices->push_back(info); continue;
} }
if (kServiceIsVGA[i])
{
if (!GetEntryProperty(entry, CFSTR("class-code"), &classCode))
{
continue;
}
if (classCode != kClassCodeDisplayVGA)
{
continue;
}
if (!GetEntryProperty(entry, CFSTR("device-id"), &info.deviceId))
{
continue;
}
}
devices->push_back(info);
IOObjectRelease(entry); IOObjectRelease(entry);
} }
IOObjectRelease(entryIterator); IOObjectRelease(entryIterator);
return true; // If any devices have been populated by IOPCIDevice, do not continue to AGXAccelerator.
if (!devices->empty())
{
break;
}
}
} }
void SetActiveGPUIndex(SystemInfo *info) void SetActiveGPUIndex(SystemInfo *info)
...@@ -217,11 +241,7 @@ bool GetSystemInfo(SystemInfo *info) ...@@ -217,11 +241,7 @@ bool GetSystemInfo(SystemInfo *info)
info->machineModelVersion = std::to_string(major) + "." + std::to_string(minor); info->machineModelVersion = std::to_string(major) + "." + std::to_string(minor);
} }
if (!GetPCIDevices(&(info->gpus))) GetIORegistryDevices(&info->gpus);
{
return false;
}
if (info->gpus.empty()) if (info->gpus.empty())
{ {
return false; return false;
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment