STRUCT I915_PERF_STREAM(9)

πŸ“¦ version 7.3.1, in nixpkgs unstable

πŸ’… struct i915_perf_stream(9) πŸ’…

okay so bestie, gather round, because this is the manual page for struct i915_perf_stream from the Kernel API Manual and it's literally the state for a single open stream FD. no cap, it's giving "main character energy" for your i915 performance streams. let's get into it ✨


🌟 NAME 🌟

struct i915_perf_stream β€” state for a single open stream FD


πŸ¦‹ SYNOPSIS πŸ¦‹

struct i915_perf_stream {
    struct i915_perf *perf;
    struct intel_uncore *uncore;
    struct intel_engine_cs *engine;
    struct mutex lock;
    u32 sample_flags;
    int sample_size;
    struct i915_gem_context *ctx;
    bool enabled;
    bool hold_preemption;
    const struct i915_perf_stream_ops *ops;
    struct i915_oa_config *oa_config;
    struct llist_head oa_config_bos;
    struct intel_context *pinned_ctx;
    u32 specific_ctx_id;
    u32 specific_ctx_id_mask;
    struct hrtimer poll_check_timer;
    wait_queue_head_t poll_wq;
    bool pollin;
    bool periodic;
    int period_exponent;
    struct {
      const struct i915_oa_format *format;
      struct i915_vma *vma;
      u8 *vaddr;
      u32 last_ctx_id;
      spinlock_t ptr_lock;
      u32 head;
      u32 tail;
    } oa_buffer;
    struct i915_vma *noa_wait;
    u64 poll_oa_period;
 };

🫢 THE MEMBERS (aka what's inside) 🫢

okay so this struct is packed with lore, let's go member by member, iykyk πŸ’–

  • perf β€” the i915_perf backpointer. it's literally pointing back home to its parent, iconic.
  • uncore β€” the mmio access path. that's how we talk to the hardware, slay.
  • engine β€” the Engine associated with this performance stream. it's the engine bestie, periodt.
  • lock β€” Lock associated with operations on stream. gotta keep things synchronized, no chaos allowed πŸ”’
  • sample_flags β€” Flags representing the DRM_I915_PERF_PROP_SAMPLE_* properties given when opening a stream, representing the contents of a single sample as read by userspace. so it's like the vibe check of what's in each sample, fr fr.
  • sample_size β€” Considering the configured contents of a sample combined with the required header size, this is the total size of a single sample record. it's giving "how big is one sample" energy.
  • ctx β€” NULL if measuring system-wide across all contexts or a specific context that is being monitored. so it's either everyone or one specific context, depending on the assignment πŸ’€
  • enabled β€” Whether the stream is currently enabled, considering whether the stream was opened in a disabled state and based on I915_PERF_IOCTL_ENABLE and I915_PERF_IOCTL_DISABLE calls. so it's tracking the on/off vibe based on those ioctls, got it ✨
  • hold_preemption β€” Whether preemption is put on hold for command submissions done on the ctx. This is useful for some drivers that cannot easily post process the OA buffer context to subtract delta of performance counters not associated with ctx. like, some drivers need this to do their math right, ngl.
  • ops β€” The callbacks providing the implementation of this specific type of configured stream. the function pointers that actually do the work, the real MVPs 🫢
  • oa_config β€” The OA configuration used by the stream. that's the config bestie.
  • oa_config_bos β€” A list of struct i915_oa_config_bo allocated lazily each time oa_config changes. lazy allocation, we love to see it πŸ’…
  • pinned_ctx β€” The OA context specific information. the context-specific lore for OA.
  • specific_ctx_id β€” The id of the specific context. literally just the id, no cap.
  • specific_ctx_id_mask β€” The mask used to masking specific_ctx_id bits. masking the bits, iconic behavior.
  • poll_check_timer β€” High resolution timer that will periodically check for data in the circular OA buffer for notifying userspace (e.g. during a read or poll). it's the timer that's like "hey bestie, data's ready" ⏰
  • poll_wq β€” The wait queue that hrtimer callback wakes when it sees data ready to read in the circular OA buffer. the wait queue gets woken up when there's tea to spill (data to read) 😭
  • pollin β€” Whether there is data available to read. yes or no, is there data? that's the question.
  • periodic β€” Whether periodic sampling is currently enabled. is the periodic sampling on or off, bestie?
  • period_exponent β€” The OA unit sampling frequency is derived from this. so the sampling frequency comes from this exponent, math girlies rise 🌸
  • oa_buffer β€” State of the OA buffer. this is a whole nested struct, let's break it down:
    • oa_buffer.ptr_lock β€” Locks reads and writes to all head/tail state. okay so consider: the head and tail pointer state needs to be read consistently from a hrtimer callback (atomic context) and read fop (user context) with tail pointer updates happening in atomic context and head updates in user context and the (unlikely) possibility of read errors needing to reset all head/tail state. it's giving "this lock is doing a lot of heavy lifting" energy.
Note: Contention/performance aren't currently a significant concern here considering the relatively low frequency of hrtimer callbacks (5ms period) and that reads typically only happen in response to a hrtimer event and likely complete before the next callback. so like, don't stress about performance here, it's chill.
Note: This lock is not held while reading and copying data to userspace so the value of head observed in htrimer callbacks won't represent any partial consumption of data. important distinction, bestie, the lock is not held during the actual reading/copying.
  • oa_buffer.head β€” Although we can always read back the head pointer register, we prefer to avoid trusting the HW state, just to avoid any risk that some hardware condition could * somehow bump the head pointer unpredictably and cause us to forward the wrong OA buffer data to userspace. so we don't trust the hardware, we track head ourselves, periodt. safety first πŸ’€
  • oa_buffer.tail β€” The last verified tail that can be read by userspace. the tail that's been verified as good to read, slay.
  • noa_wait β€” A batch buffer doing a wait on the GPU for the NOA logic to be reprogrammed. it's a batch buffer that's waiting on the GPU, the NOA logic is getting reprogrammed, iconic.
  • poll_oa_period β€” The period in nanoseconds at which the OA buffer should be checked for available data. so this is the nanosecond period for checking if there's data in the OA buffer, time is literally in nanoseconds, precise af ⏱️

πŸ‘‘ SEE ALSO πŸ‘‘

Kernel file ./drivers/gpu/drm/i915/i915_perf_types.h struct i915_perf_stream_ops(9), struct i915_oa_ops(9)

go read those too bestie, they're part of the lore πŸ¦‹


and that's the whole manual page, bestie! this came from ./drivers/gpu/drm/i915 and it's dated October 2026 β€” so it's literally from the future, we love a time-traveling manpage πŸŽ€βœ¨πŸ’– periodt! 🌈🫢

πŸ“¦ where this page comes from