STRUCT DRM_XE_WAIT_USER_FENCE(9)
π struct drm_xe_wait_user_fence β Kernel API Manual β¨
okay bestie, welcome to the <pink>Kernel API Manual</pink> π β today's main character is struct drm_xe_wait_user_fence, and honestly? she's the input of &DRM_IOCTL_XE_WAIT_USER_FENCE. iykyk. let's get into it π¦
πΈ NAME πΈ
struct drm_xe_wait_user_fence β the input of &DRM_IOCTL_XE_WAIT_USER_FENCE. that's her whole job, and she ate π
β¨ SYNOPSIS β¨
struct drm_xe_wait_user_fence {
__u64 extensions;
__u64 addr;
#define DRM_XE_UFENCE_WAIT_OP_EQ 0x0;
#define DRM_XE_UFENCE_WAIT_OP_NEQ 0x1;
#define DRM_XE_UFENCE_WAIT_OP_GT 0x2;
#define DRM_XE_UFENCE_WAIT_OP_GTE 0x3;
#define DRM_XE_UFENCE_WAIT_OP_LT 0x4;
#define DRM_XE_UFENCE_WAIT_OP_LTE 0x5;
__u16 op;
#define DRM_XE_UFENCE_WAIT_FLAG_ABSTIME (1 << 0);
__u16 flags;
__u32 pad;
__u64 value;
__u64 mask;
__s64 timeout;
__u32 exec_queue_id;
__u32 pad2;
__u64 reserved[2];
};
like, copy it exactly bestie, character for character, no edits, no "fixing" it π
π«Ά Members π«Ά
extensionsβ pointer to the first extension struct, if there is one. if any.addrβ the user pointer address to wait on. and it must be qword aligned, no cap πopβ the wait operation (aka type of comparison, we'll get to the menu of them)flagsβ wait flags π©padβ MBZ (must be zero, don't be weird about it)valueβ compare valuemaskβ comparison masktimeoutβ how long to wait before bailing, value in nanoseconds. okay so this one has lore:- without
DRM_XE_UFENCE_WAIT_FLAG_ABSTIMEset (that's relative timeout) it contains the timeout expressed in nanoseconds to wait, and the fence will expire atnow + timeout. - when
DRM_XE_UFENCE_WAIT_FLAG_ABSTIMEis set (that's absolute timeout) the wait will end attimeoutβ and it uses systemCLOCK_MONOTONICβ° - passing a negative
timeoutleads to a never ending wait. literally forever. π you have been warned. - on relative timeout this value is updated with the timeout left (for restarting the call in case of signal delivery). on absolute timeout this value stays intact (a restarted call still expires at the same point of time). iconic behaviour tbh β¨
- without
exec_queue_idβ theexec_queue_idreturned fromxe_exec_queue_create_ioctlpad2β MBZ (again: must be zero!!)reservedβ reserved π
π₯ Description π₯
so what does she do? she waits on a user fence β XE will wake-up on every HW engine interrupt in the instances list and check if the user fence is complete:
(*addr & MASK) OP (VALUE & MASK)
and then returns to user on user fence completion or timeout. slay π
the op can be any of these besties:
DRM_XE_UFENCE_WAIT_OP_EQDRM_XE_UFENCE_WAIT_OP_NEQDRM_XE_UFENCE_WAIT_OP_GTDRM_XE_UFENCE_WAIT_OP_GTEDRM_XE_UFENCE_WAIT_OP_LTDRM_XE_UFENCE_WAIT_OP_LTE
and the flags can be:
DRM_XE_UFENCE_WAIT_FLAG_ABSTIME
and the mask values can be, for example:
0xffuforu80xffffuforu160xffffffffuforu320xffffffffffffffffuforu64
match your mask to your width, periodt π
π SEE ALSO π
kernel file ./include/uapi/drm/xe_drm.h and then the whole friend group, no one left out:
Xe Device Block Diagram(9), Xe uAPI Overview(9), Xe IOCTL Extensions(9), struct drm_xe_user_extension(9), struct drm_xe_ext_set_property(9), struct drm_xe_engine_class_instance(9), struct drm_xe_engine(9), struct drm_xe_query_engines(9), enum drm_xe_memory_class(9), struct drm_xe_mem_region(9), struct drm_xe_query_mem_regions(9), struct drm_xe_query_config(9), struct drm_xe_gt(9), struct drm_xe_query_gt_list(9), struct drm_xe_query_topology_mask(9), struct drm_xe_query_engine_cycles(9), struct drm_xe_query_uc_fw_version(9), struct drm_xe_query_pxp_status(9), struct drm_xe_device_query(9), struct drm_xe_gem_create(9), struct drm_xe_gem_mmap_offset(9), struct drm_xe_vm_create(9), struct drm_xe_vm_destroy(9), struct drm_xe_vm_bind_op(9), struct drm_xe_vm_bind(9), struct drm_xe_vm_get_property(9), struct drm_xe_exec_queue_create(9), struct drm_xe_exec_queue_destroy(9), struct drm_xe_exec_queue_get_property(9), struct drm_xe_sync(9), struct drm_xe_exec(9), enum drm_xe_observation_type(9), enum drm_xe_observation_op(9), struct drm_xe_observation_param(9), enum drm_xe_observation_ioctls(9), enum drm_xe_oa_unit_type(9), struct drm_xe_oa_unit(9), struct drm_xe_query_oa_units(9), enum drm_xe_oa_format_type(9), enum drm_xe_oa_property_id(9), struct drm_xe_oa_config(9), struct drm_xe_oa_stream_status(9), struct drm_xe_oa_stream_info(9), enum drm_xe_pxp_session_type(9), enum drm_xe_eu_stall_property_id(9), struct drm_xe_query_eu_stall(9), struct drm_xe_madvise(9), struct drm_xe_mem_range_attr(9), struct drm_xe_vm_query_mem_range_attr(9), struct drm_xe_exec_queue_set_property(9), Xe DRM RAS(9), enum drm_xe_ras_error_severity(9), enum drm_xe_ras_error_component(9)
okay that's the whole page, you understood it, i'm obsessed π§π
this came out of./include/uapi/drmand it's datedOctober 2026, so yeah β that's the version and the date, noted and cited, we love a documented source π
stay hydrated and remember: pad and pad2 are MBZ. must. be. zero. π«Άβ¨
π¦ 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