static int drm_get_pci_id_for_fd(int fd, int *vendor_id, int *chip_id) { drmDevicePtr device; int ret; if (drmGetDevice(fd, &device) == 0) { if (device->bustype == DRM_BUS_PCI) { *vendor_id = device->deviceinfo.pci->vendor_id; *chip_id = device->deviceinfo.pci->device_id; ret = 1; } else { log_(_LOADER_WARNING, "MESA-LOADER: device is not located on the PCI bus\n"); ret = 0; } drmFreeDevice(&device); } else { log_(_LOADER_WARNING, "MESA-LOADER: failed to retrieve device information\n"); ret = 0; } return ret; }
int main(void) { drmDevicePtr *devices; drmDevicePtr device; int fd, ret, max_devices; printf("--- Checking the number of DRM device available ---\n"); max_devices = drmGetDevices2(0, NULL, 0); if (max_devices <= 0) { printf("drmGetDevices2() has not found any devices (errno=%d)\n", -max_devices); return 77; } printf("--- Devices reported %d ---\n", max_devices); devices = calloc(max_devices, sizeof(drmDevicePtr)); if (devices == NULL) { printf("Failed to allocate memory for the drmDevicePtr array\n"); return -1; } printf("--- Retrieving devices information (PCI device revision is ignored) ---\n"); ret = drmGetDevices2(0, devices, max_devices); if (ret < 0) { printf("drmGetDevices2() returned an error %d\n", ret); free(devices); return -1; } for (int i = 0; i < ret; i++) { print_device_info(devices[i], i, false); for (int j = 0; j < DRM_NODE_MAX; j++) { if (devices[i]->available_nodes & 1 << j) { printf("--- Opening device node %s ---\n", devices[i]->nodes[j]); fd = open(devices[i]->nodes[j], O_RDONLY | O_CLOEXEC, 0); if (fd < 0) { printf("Failed - %s (%d)\n", strerror(errno), errno); continue; } printf("--- Retrieving device info, for node %s ---\n", devices[i]->nodes[j]); if (drmGetDevice2(fd, DRM_DEVICE_GET_PCI_REVISION, &device) == 0) { print_device_info(device, i, true); drmFreeDevice(&device); } close(fd); } } } drmFreeDevices(devices, ret); free(devices); return 0; }
static char *drm_get_id_path_tag_for_fd(int fd) { drmDevicePtr device; char *tag; if (drmGetDevice(fd, &device) != 0) return NULL; tag = drm_construct_id_path_tag(device); drmFreeDevice(&device); return tag; }
int main(void) { drmDevicePtr *devices; drmDevicePtr device; int fd, ret, max_devices; max_devices = drmGetDevices(NULL, 0); if (max_devices <= 0) { printf("drmGetDevices() has returned %d\n", max_devices); return -1; } devices = calloc(max_devices, sizeof(drmDevicePtr)); if (devices == NULL) { printf("Failed to allocate memory for the drmDevicePtr array\n"); return -1; } ret = drmGetDevices(devices, max_devices); if (ret < 0) { printf("drmGetDevices() returned an error %d\n", ret); free(devices); return -1; } for (int i = 0; i < ret; i++) { print_device_info(devices[i], i); for (int j = 0; j < DRM_NODE_MAX; j++) { if (devices[i]->available_nodes & 1 << j) { printf("Opening device %d node %s\n", i, devices[i]->nodes[j]); fd = open(devices[i]->nodes[j], O_RDONLY | O_CLOEXEC, 0); if (fd < 0) { printf("Failed - %s (%d)\n", strerror(errno), errno); continue; } if (drmGetDevice(fd, &device) == 0) { print_device_info(device, i); drmFreeDevice(&device); } close(fd); } } } drmFreeDevices(devices, ret); free(devices); return 0; }
/* Find a match AMD device in PCI bus * Return the index of the device or -1 if not found */ static int amdgpu_find_device(uint8_t bus, uint16_t dev) { int i; drmDevicePtr device; for (i = 0; i < MAX_CARDS_SUPPORTED && drm_amdgpu[i] >= 0; i++) { if (drmGetDevice2(drm_amdgpu[i], DRM_DEVICE_GET_PCI_REVISION, &device) == 0) { if (device->bustype == DRM_BUS_PCI) if ((bus == 0xFF || device->businfo.pci->bus == bus) && device->deviceinfo.pci->device_id == dev) { drmFreeDevice(&device); return i; } drmFreeDevice(&device); } } return -1; }
/* Print AMD devices information */ static void amdgpu_print_devices() { int i; drmDevicePtr device; /* Open the first AMD devcie to print driver information. */ if (drm_amdgpu[0] >=0) { /* Display AMD driver version information.*/ drmVersionPtr retval = drmGetVersion(drm_amdgpu[0]); if (retval == NULL) { perror("Cannot get version for AMDGPU device"); return; } printf("Driver name: %s, Date: %s, Description: %s.\n", retval->name, retval->date, retval->desc); drmFreeVersion(retval); } /* Display information of AMD devices */ printf("Devices:\n"); for (i = 0; i < MAX_CARDS_SUPPORTED && drm_amdgpu[i] >=0; i++) if (drmGetDevice2(drm_amdgpu[i], DRM_DEVICE_GET_PCI_REVISION, &device) == 0) { if (device->bustype == DRM_BUS_PCI) { printf("PCI "); printf(" domain:%04x", device->businfo.pci->domain); printf(" bus:%02x", device->businfo.pci->bus); printf(" device:%02x", device->businfo.pci->dev); printf(" function:%01x", device->businfo.pci->func); printf(" vendor_id:%04x", device->deviceinfo.pci->vendor_id); printf(" device_id:%04x", device->deviceinfo.pci->device_id); printf(" subvendor_id:%04x", device->deviceinfo.pci->subvendor_id); printf(" subdevice_id:%04x", device->deviceinfo.pci->subdevice_id); printf(" revision_id:%02x", device->deviceinfo.pci->revision_id); printf("\n"); } drmFreeDevice(&device); } }
/* Helper function to do the ioctls needed for setup and init. */ static boolean do_winsys_init(struct amdgpu_winsys *ws, int fd) { struct amdgpu_buffer_size_alignments alignment_info = {}; struct amdgpu_heap_info vram, gtt; struct drm_amdgpu_info_hw_ip dma = {}, uvd = {}, vce = {}; uint32_t vce_version = 0, vce_feature = 0; int r, i, j; drmDevicePtr devinfo; /* Get PCI info. */ r = drmGetDevice(fd, &devinfo); if (r) { fprintf(stderr, "amdgpu: drmGetDevice failed.\n"); goto fail; } ws->info.pci_domain = devinfo->businfo.pci->domain; ws->info.pci_bus = devinfo->businfo.pci->bus; ws->info.pci_dev = devinfo->businfo.pci->dev; ws->info.pci_func = devinfo->businfo.pci->func; drmFreeDevice(&devinfo); /* Query hardware and driver information. */ r = amdgpu_query_gpu_info(ws->dev, &ws->amdinfo); if (r) { fprintf(stderr, "amdgpu: amdgpu_query_gpu_info failed.\n"); goto fail; } r = amdgpu_query_buffer_size_alignment(ws->dev, &alignment_info); if (r) { fprintf(stderr, "amdgpu: amdgpu_query_buffer_size_alignment failed.\n"); goto fail; } r = amdgpu_query_heap_info(ws->dev, AMDGPU_GEM_DOMAIN_VRAM, 0, &vram); if (r) { fprintf(stderr, "amdgpu: amdgpu_query_heap_info(vram) failed.\n"); goto fail; } r = amdgpu_query_heap_info(ws->dev, AMDGPU_GEM_DOMAIN_GTT, 0, >t); if (r) { fprintf(stderr, "amdgpu: amdgpu_query_heap_info(gtt) failed.\n"); goto fail; } r = amdgpu_query_hw_ip_info(ws->dev, AMDGPU_HW_IP_DMA, 0, &dma); if (r) { fprintf(stderr, "amdgpu: amdgpu_query_hw_ip_info(dma) failed.\n"); goto fail; } r = amdgpu_query_hw_ip_info(ws->dev, AMDGPU_HW_IP_UVD, 0, &uvd); if (r) { fprintf(stderr, "amdgpu: amdgpu_query_hw_ip_info(uvd) failed.\n"); goto fail; } r = amdgpu_query_hw_ip_info(ws->dev, AMDGPU_HW_IP_VCE, 0, &vce); if (r) { fprintf(stderr, "amdgpu: amdgpu_query_hw_ip_info(vce) failed.\n"); goto fail; } r = amdgpu_query_firmware_version(ws->dev, AMDGPU_INFO_FW_VCE, 0, 0, &vce_version, &vce_feature); if (r) { fprintf(stderr, "amdgpu: amdgpu_query_firmware_version(vce) failed.\n"); goto fail; } /* Set chip identification. */ ws->info.pci_id = ws->amdinfo.asic_id; /* TODO: is this correct? */ ws->info.vce_harvest_config = ws->amdinfo.vce_harvest_config; switch (ws->info.pci_id) { #define CHIPSET(pci_id, name, cfamily) case pci_id: ws->info.family = CHIP_##cfamily; break; #include "pci_ids/radeonsi_pci_ids.h" #undef CHIPSET default: fprintf(stderr, "amdgpu: Invalid PCI ID.\n"); goto fail; } if (ws->info.family >= CHIP_TONGA) ws->info.chip_class = VI; else if (ws->info.family >= CHIP_BONAIRE) ws->info.chip_class = CIK; else { fprintf(stderr, "amdgpu: Unknown family.\n"); goto fail; } /* LLVM 3.6.1 is required for VI. */ if (ws->info.chip_class >= VI && HAVE_LLVM == 0x0306 && MESA_LLVM_VERSION_PATCH < 1) { fprintf(stderr, "amdgpu: LLVM 3.6.1 is required, got LLVM %i.%i.%i\n", HAVE_LLVM >> 8, HAVE_LLVM & 255, MESA_LLVM_VERSION_PATCH); goto fail; }