STRUCT DRM_I915_QUERY_MEMORY_REGIONS(9)
π struct drm_i915_query_memory_regions(9) π
okay so bestie, welcome to the Kernel API Manual β this page is literally all about struct drm_i915_query_memory_regions, and by the end you're gonna know it like the back of your hand. no cap. π¦
β¨ NAME β¨
struct drm_i915_query_memory_regions β yeah so the page header just gives you the struct name and dips, that's it, that's the whole NAME section π (there's genuinely no description tagline after the dash, so don't come for me)
β SYNOPSIS β
the whole shape of it, bestie, look:
struct drm_i915_query_memory_regions {
__u32 num_regions;
__u32 rsvd[3];
struct drm_i915_memory_region_info regions[];
};
like... three fields, one of them flexes an unsized array, we love a growable moment π
π Members π
num_regionsβ the number of supported regions. the headcount. how many besties are in this region group chat πrsvdβMBZ, which means Must Be Zero. do not touch. do not decorate. leave it at zero, periodt. π«Άregionsβ the actual tea β β info about each supported region, one struct per region.
πΈ Description πΈ
okay so here's the vibe: the region info query is how you get the driver to list every region it knows about. it does that by filling in an array of struct drm_i915_memory_region_info structures. that's it, that's the whole job. it's giving census, but for memory regions π§
and here's the literal example for getting the list of supported regions, i did not change a single character because this is sacred code:
struct drm_i915_query_memory_regions *info;
struct drm_i915_query_item item = {
.query_id = DRM_I915_QUERY_MEMORY_REGIONS;
};
struct drm_i915_query query = {
.num_items = 1,
.items_ptr = (uintptr_t)item,
};
int err, i;
// First query the size of the blob we need, this needs to be large
// enough to hold our array of regions. The kernel will fill out the
// item.length for us, which is the number of bytes we need.
err = ioctl(fd, DRM_IOCTL_I915_QUERY, query);
if (err) ...
info = calloc(1, item.length);
// Now that we allocated the required number of bytes, we call the ioctl
// again, this time with the data_ptr pointing to our newly allocated
// blob, which the kernel can then populate with the all the region info.
item.data_ptr = (uintptr_t)info,
err = ioctl(fd, DRM_IOCTL_I915_QUERY, query);
if (err) ...
// We can now access each region in the array
for (i = 0; i < info->num_regions; i++) {
struct drm_i915_memory_region_info mr = info->regions[i];
u16 class = mr.region.class;
u16 instance = mr.region.instance;
....
}
free(info);
the way this works is a two-pass situation, and honestly? iconic. π
- first
ioctl(fd, DRM_IOCTL_I915_QUERY, query)call β you're just asking "how many bytes do i need?" the kernel fills outitem.lengthfor you with the exact byte count. no guessing required, it literally tells you. π« - then
info = calloc(1, item.length);β allocate that many bytes, slay. - then you set
item.data_ptr = (uintptr_t)info,and hit the sameioctl(fd, DRM_IOCTL_I915_QUERY, query)again β this time the kernel populates your freshly allocated blob with all the region info. ate and left no crumbs π₯ - then you loop
for (i = 0; i < info->num_regions; i++), grab eachstruct drm_i915_memory_region_info mr = info->regions[i];, and readmr.region.classandmr.region.instanceinto youru16s. main character data extraction moment π - and obviously
free(info);β memory hygiene is self care, bestie, do not leak π«§
ngl bothioctlcalls checkif (err) ...β please actually handle your errors, i'm begging π the...is a placeholder, not a lifestyle.
π¦ SEE ALSO π¦
the whole friend group, in order, exactly as listed β go say hi to all of them:
- Kernel file
./tools/perf/trace/beauty/include/uapi/drm/i915_drm.h - uevents generated by i915 on its device node(9)
- struct
i915_user_extension(9) - enum
drm_i915_gem_engine_class(9) - struct
i915_engine_class_instance(9) perf_eventsexposed by i915 through/sys/bus/event_sources/drivers/i915(9)- struct
drm_i915_getparam(9) drm_i915_getparam_t(9)- struct
drm_i915_gem_mmap_offset(9) - struct
drm_i915_gem_set_domain(9) - struct
drm_i915_gem_exec_fence(9) - struct
drm_i915_gem_execbuffer_ext_timeline_fences(9) - struct
drm_i915_gem_execbuffer2(9) - struct
drm_i915_gem_caching(9) - struct
drm_i915_gem_context_create_ext(9) - struct
drm_i915_gem_context_param(9) - Virtual Engine uAPI(9)
- struct
i915_context_engines_parallel_submit(9) - Context Engine Map uAPI(9)
- struct
drm_i915_gem_context_create_ext_setparam(9) - struct
drm_i915_gem_vm_control(9) - struct
drm_i915_gem_userptr(9) - struct
drm_i915_perf_oa_config(9) - struct
drm_i915_query_item(9) - struct
drm_i915_query(9) - struct
drm_i915_query_topology_info(9) - Engine Discovery uAPI(9)
- struct
drm_i915_engine_info(9) - struct
drm_i915_query_engine_info(9) - struct
drm_i915_query_perf_config(9) - enum
drm_i915_gem_memory_class(9) - struct
drm_i915_gem_memory_class_instance(9) - struct
drm_i915_memory_region_info(9) - struct
drm_i915_query_guc_submission_version(9) - GuC HWCONFIG blob uAPI(9)
- struct
drm_i915_gem_create_ext(9) - struct
drm_i915_gem_create_ext_memory_regions(9) - struct
drm_i915_gem_create_ext_protected_content(9) - struct
drm_i915_gem_create_ext_set_pat(9)
ok and one last thing β the footer on this page shows the source as ./tools/perf/trace/beauty/incl... (yep, truncated like that in the original, not me being lazy π) and the date is October 2026. so that's the version deets, mwah, go query some regions bestie, you're gonna do amazing πβ¨π
π¦ where this page comes from
- nixpkgs unstable: linux-manual 7.3.1
- π girlified by deepseek-ai/DeepSeek-V4.1-Flash-1017 on : a language model's rewrite of the original, under its terms