@@ -2108,6 +2108,14 @@ static int eb_oa_config(struct i915_execbuffer *eb)
if (ret)
goto unlock;
+ /*
+ * If the perf stream was opened with hold preemption, flag the
+ * request properly so that the priority of the request is bumped once
+ * it reaches the execlist ports.
+ */
+ if (eb->i915->perf.oa.exclusive_stream->hold_preemption)
+ eb->request->flags |= I915_REQUEST_NOPREEMPT;
+
/*
* If the config hasn't changed, skip reconfiguring the HW (this is
* subject to a delay we want to avoid has much as possible).
@@ -1232,6 +1232,14 @@ struct i915_perf_stream {
*/
bool enabled;
+ /**
+ * @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.
+ */
+ bool hold_preemption;
+
/**
* @ops: The callbacks providing the implementation of this specific
* type of configured stream.
@@ -344,6 +344,8 @@ static const struct i915_oa_format gen8_plus_oa_formats[I915_OA_FORMAT_MAX] = {
* struct perf_open_properties - for validated properties given to open a stream
* @sample_flags: `DRM_I915_PERF_PROP_SAMPLE_*` properties are tracked as flags
* @single_context: Whether a single or all gpu contexts should be monitored
+ * @hold_preemption: Whether the preemption is disabled for the filtered
+ * context
* @ctx_handle: A gem ctx handle for use with @single_context
* @metrics_set: An ID for an OA unit metric set advertised via sysfs
* @oa_format: An OA unit HW report format
@@ -358,6 +360,7 @@ struct perf_open_properties {
u32 sample_flags;
u64 single_context:1;
+ u64 hold_preemption:1;
u64 ctx_handle;
/* OA sampling state */
@@ -2400,6 +2403,8 @@ static int i915_oa_stream_init(struct i915_perf_stream *stream,
stream->sample_flags |= SAMPLE_OA_REPORT;
stream->sample_size += format_size;
+ stream->hold_preemption = props->hold_preemption;
+
dev_priv->perf.oa.oa_buffer.format_size = format_size;
if (WARN_ON(dev_priv->perf.oa.oa_buffer.format_size == 0))
return -EINVAL;
@@ -2941,6 +2946,15 @@ i915_perf_open_ioctl_locked(struct drm_i915_private *dev_priv,
}
}
+ if (props->hold_preemption) {
+ if (!props->single_context) {
+ DRM_DEBUG("preemption disable with no context\n");
+ ret = -EINVAL;
+ goto err;
+ }
+ privileged_op = true;
+ }
+
/*
* On Haswell the OA unit supports clock gating off for a specific
* context and in this mode there's no visibility of metrics for the
@@ -2955,8 +2969,9 @@ i915_perf_open_ioctl_locked(struct drm_i915_private *dev_priv,
* MI_REPORT_PERF_COUNT commands and so consider it a privileged op to
* enable the OA unit by default.
*/
- if (IS_HASWELL(dev_priv) && specific_ctx)
+ if (IS_HASWELL(dev_priv) && specific_ctx && !props->hold_preemption) {
privileged_op = false;
+ }
/* Similar to perf's kernel.perf_paranoid_cpu sysctl option
* we check a dev.i915.perf_stream_paranoid sysctl option
@@ -2965,7 +2980,7 @@ i915_perf_open_ioctl_locked(struct drm_i915_private *dev_priv,
*/
if (privileged_op &&
i915_perf_stream_paranoid && !capable(CAP_SYS_ADMIN)) {
- DRM_DEBUG("Insufficient privileges to open system-wide i915 perf stream\n");
+ DRM_DEBUG("Insufficient privileges to open i915 perf stream\n");
ret = -EACCES;
goto err_ctx;
}
@@ -3162,6 +3177,9 @@ static int read_properties_unlocked(struct drm_i915_private *dev_priv,
props->oa_periodic = true;
props->oa_period_exponent = value;
break;
+ case DRM_I915_PERF_PROP_HOLD_PREEMPTION:
+ props->hold_preemption = !!value;
+ break;
case DRM_I915_PERF_PROP_MAX:
MISSING_CASE(id);
return -EINVAL;
@@ -3917,5 +3935,12 @@ void i915_perf_fini(struct drm_i915_private *dev_priv)
*/
int i915_perf_ioctl_version(void)
{
- return 1;
+ /* 1: initial version
+ *
+ * 2: Add DRM_I915_PERF_PROP_HOLD_PREEMPTION parameter to hold
+ * preemption on a particular context so that performance data is
+ * accessible from a delta of MI_RPC reports without looking at the
+ * OA buffer.
+ */
+ return 2;
}
@@ -1984,6 +1984,17 @@ enum drm_i915_perf_property_id {
*/
DRM_I915_PERF_PROP_OA_EXPONENT,
+ /**
+ * Specifying this property is only valid when specify a context to
+ * filter with DRM_I915_PERF_PROP_CTX_HANDLE. Specifying this property
+ * will hold preemption of the particular context we want to gather
+ * performance data about. The execbuf2 submissions must include a
+ * drm_i915_gem_execbuffer_ext_perf parameter for this to apply.
+ *
+ * This property is available in perf revision 2.
+ */
+ DRM_I915_PERF_PROP_HOLD_PREEMPTION,
+
DRM_I915_PERF_PROP_MAX /* non-ABI */
};