linux/drivers/gpu/drm
Tvrtko Ursulin b46a33e271 drm/i915/pmu: Expose a PMU interface for perf queries
From: Chris Wilson <chris@chris-wilson.co.uk>
From: Tvrtko Ursulin <tvrtko.ursulin@intel.com>
From: Dmitry Rogozhkin <dmitry.v.rogozhkin@intel.com>

The first goal is to be able to measure GPU (and invidual ring) busyness
without having to poll registers from userspace. (Which not only incurs
holding the forcewake lock indefinitely, perturbing the system, but also
runs the risk of hanging the machine.) As an alternative we can use the
perf event counter interface to sample the ring registers periodically
and send those results to userspace.

Functionality we are exporting to userspace is via the existing perf PMU
API and can be exercised via the existing tools. For example:

  perf stat -a -e i915/rcs0-busy/ -I 1000

Will print the render engine busynnes once per second. All the performance
counters can be enumerated (perf list) and have their unit of measure
correctly reported in sysfs.

v1-v2 (Chris Wilson):

v2: Use a common timer for the ring sampling.

v3: (Tvrtko Ursulin)
 * Decouple uAPI from i915 engine ids.
 * Complete uAPI defines.
 * Refactor some code to helpers for clarity.
 * Skip sampling disabled engines.
 * Expose counters in sysfs.
 * Pass in fake regs to avoid null ptr deref in perf core.
 * Convert to class/instance uAPI.
 * Use shared driver code for rc6 residency, power and frequency.

v4: (Dmitry Rogozhkin)
 * Register PMU with .task_ctx_nr=perf_invalid_context
 * Expose cpumask for the PMU with the single CPU in the mask
 * Properly support pmu->stop(): it should call pmu->read()
 * Properly support pmu->del(): it should call stop(event, PERF_EF_UPDATE)
 * Introduce refcounting of event subscriptions.
 * Make pmu.busy_stats a refcounter to avoid busy stats going away
   with some deleted event.
 * Expose cpumask for i915 PMU to avoid multiple events creation of
   the same type followed by counter aggregation by perf-stat.
 * Track CPUs getting online/offline to migrate perf context. If (likely)
   cpumask will initially set CPU0, CONFIG_BOOTPARAM_HOTPLUG_CPU0 will be
   needed to see effect of CPU status tracking.
 * End result is that only global events are supported and perf stat
   works correctly.
 * Deny perf driver level sampling - it is prohibited for uncore PMU.

v5: (Tvrtko Ursulin)

 * Don't hardcode number of engine samplers.
 * Rewrite event ref-counting for correctness and simplicity.
 * Store initial counter value when starting already enabled events
   to correctly report values to all listeners.
 * Fix RC6 residency readout.
 * Comments, GPL header.

v6:
 * Add missing entry to v4 changelog.
 * Fix accounting in CPU hotplug case by copying the approach from
   arch/x86/events/intel/cstate.c. (Dmitry Rogozhkin)

v7:
 * Log failure message only on failure.
 * Remove CPU hotplug notification state on unregister.

v8:
 * Fix error unwind on failed registration.
 * Checkpatch cleanup.

v9:
 * Drop the energy metric, it is available via intel_rapl_perf.
   (Ville Syrjälä)
 * Use HAS_RC6(p). (Chris Wilson)
 * Handle unsupported non-engine events. (Dmitry Rogozhkin)
 * Rebase for intel_rc6_residency_ns needing caller managed
   runtime pm.
 * Drop HAS_RC6 checks from the read callback since creating those
   events will be rejected at init time already.
 * Add counter units to sysfs so perf stat output is nicer.
 * Cleanup the attribute tables for brevity and readability.

v10:
 * Fixed queued accounting.

v11:
 * Move intel_engine_lookup_user to intel_engine_cs.c
 * Commit update. (Joonas Lahtinen)

v12:
 * More accurate sampling. (Chris Wilson)
 * Store and report frequency in MHz for better usability from
   perf stat.
 * Removed metrics: queued, interrupts, rc6 counters.
 * Sample engine busyness based on seqno difference only
   for less MMIO (and forcewake) on all platforms. (Chris Wilson)

v13:
 * Comment spelling, use mul_u32_u32 to work around potential GCC
   issue and somne code alignment changes. (Chris Wilson)

v14:
 * Rebase.

v15:
 * Rebase for RPS refactoring.

v16:
 * Use the dynamic slot in the CPU hotplug state machine so that we are
   free to setup our state as multi-instance. Previously we were re-using
   the CPUHP_AP_PERF_X86_UNCORE_ONLINE slot which is neither used as
   multi-instance, nor owned by our driver to start with.
 * Register the CPU hotplug handlers after the PMU, otherwise the callback
   will get called before the PMU is initialized which can end up in
   perf_pmu_migrate_context with an un-initialized base.
 * Added workaround for a probable bug in cpuhp core.

v17:
 * Remove workaround for the cpuhp bug.

v18:
 * Rebase for drm_i915_gem_engine_class getting upstream before us.

v19:
 * Rebase. (trivial)

Signed-off-by: Chris Wilson <chris@chris-wilson.co.uk>
Signed-off-by: Tvrtko Ursulin <tvrtko.ursulin@intel.com>
Signed-off-by: Dmitry Rogozhkin <dmitry.v.rogozhkin@intel.com>
Cc: Tvrtko Ursulin <tvrtko.ursulin@intel.com>
Cc: Chris Wilson <chris@chris-wilson.co.uk>
Cc: Dmitry Rogozhkin <dmitry.v.rogozhkin@intel.com>
Cc: Peter Zijlstra <peterz@infradead.org>
Reviewed-by: Chris Wilson <chris@chris-wilson.co.uk>
Signed-off-by: Tvrtko Ursulin <tvrtko.ursulin@intel.com>
Link: https://patchwork.freedesktop.org/patch/msgid/20171121181852.16128-2-tvrtko.ursulin@linux.intel.com
2017-11-22 11:24:57 +00:00
..
amd Merge branch 'linus-4.14-rc4-acp-prereq' of git://people.freedesktop.org/~agd5f/linux into drm-next 2017-11-14 05:53:39 +10:00
arc drm/arc: Use drm_gem_fb_create() 2017-09-02 14:23:06 +02:00
arm drm/arm/mali: Use drm_gem_fb_create() 2017-08-27 19:29:46 +02:00
armada drm/armada: Replace drm_framebuffer_reference/unreference() with _get/put() 2017-10-16 15:02:44 -04:00
ast drm: Pass struct drm_file * to __drm_mode_object_find [v2] 2017-10-12 10:03:04 +10:00
atmel-hlcdc drm/atmel-hlcdc: Use drm_gem_fb_create() 2017-08-27 19:30:15 +02:00
bochs drm: Pass struct drm_file * to __drm_mode_object_find [v2] 2017-10-12 10:03:04 +10:00
bridge drm/bridge: adv7511: Fix a use after free 2017-10-18 09:38:43 +05:30
cirrus drm: Pass struct drm_file * to __drm_mode_object_find [v2] 2017-10-12 10:03:04 +10:00
etnaviv drm/etnaviv: short-circuit perfmon ioctls 2017-10-22 18:41:56 +02:00
exynos - Improved HDMI and Mixer drivers 2017-11-14 14:12:43 +10:00
fsl-dcu drm/fsl-dcu: Use drm_gem_fb_create() 2017-10-01 17:00:20 +02:00
gma500 drm/gma500: use ARRAY_SIZE 2017-10-16 11:29:05 +02:00
hisilicon drm/hisilicon: Ensure LDI regs are properly configured. 2017-11-01 10:36:50 +08:00
i2c drm: i2c: tda998x: constify i2c_device_id 2017-08-22 08:33:44 +02:00
i810 drm/pci: Deprecate drm_pci_init/exit completely 2017-06-20 10:41:03 +02:00
i915 drm/i915/pmu: Expose a PMU interface for perf queries 2017-11-22 11:24:57 +00:00
imx Merge tag 'drm-misc-next-2017-09-20' of git://anongit.freedesktop.org/git/drm-misc into drm-next 2017-09-28 05:46:15 +10:00
lib mm: treewide: remove GFP_TEMPORARY allocation flag 2017-09-13 18:53:16 -07:00
mediatek drm/mediatek: hdmi: clean up drm_bridge_add call 2017-08-21 08:49:24 +05:30
meson drm/meson: Use drm_gem_fb_create() 2017-10-01 17:01:39 +02:00
mga Merge airlied/drm-next into drm-misc-next 2017-07-26 13:43:33 +02:00
mgag200 drm: Pass struct drm_file * to __drm_mode_object_find [v2] 2017-10-12 10:03:04 +10:00
msm Linux 4.14-rc7 2017-11-02 12:40:41 +10:00
mxsfb drm/mxsfb: Use drm_gem_fb_create() and drm_gem_fb_prepare_fb() 2017-10-01 17:02:20 +02:00
nouveau drm/nouveau/bios/timing: mark expected switch fall-throughs 2017-11-03 09:12:10 +10:00
omapdrm omapdrm: omapdss_hdmi_ops: add lost_hotplug op 2017-10-12 10:49:14 +03:00
panel drm/panel: simple: add Toshiba LT089AC19000 2017-10-19 11:48:44 +02:00
pl111 drm/pl111: Add handling of Versatile platforms 2017-09-10 23:58:42 +02:00
qxl qxl: alloc & use shadow for dumb buffers 2017-10-23 08:23:11 +02:00
r128 drm/pci: Deprecate drm_pci_init/exit completely 2017-06-20 10:41:03 +02:00
radeon Merge tag 'drm-amdkfd-next-2017-11-02' of git://people.freedesktop.org/~gabbayo/linux into drm-next 2017-11-03 05:12:24 +10:00
rcar-du drm/rcar-du: Use drm_gem_fb_create() 2017-10-01 17:02:53 +02:00
rockchip Driver Changes: 2017-11-14 05:29:34 +10:00
savage drm/pci: Deprecate drm_pci_init/exit completely 2017-06-20 10:41:03 +02:00
selftests mm: treewide: remove GFP_TEMPORARY allocation flag 2017-09-13 18:53:16 -07:00
shmobile drm/shmobile: Use drm_gem_fb_create() 2017-10-01 17:03:22 +02:00
sis drm/pci: Deprecate drm_pci_init/exit completely 2017-06-20 10:41:03 +02:00
sti drm/sti: Use drm_gem_fb_create() 2017-08-27 19:30:49 +02:00
stm drm/stm: ltdc: remove bridge from driver internal structure 2017-10-10 11:32:48 +02:00
sun4i drm/sun4i: Add support for A20 display pipeline components 2017-10-17 19:49:17 +02:00
tdfx drm/pci: Deprecate drm_pci_init/exit completely 2017-06-20 10:41:03 +02:00
tegra drm/tegra: hdmi: Add cec-notifier support 2017-10-20 14:19:54 +02:00
tilcdc tilcdc changes for v4.15 2017-10-17 10:13:47 +10:00
tinydrm drm/tinydrm: Remove explicit .best_encoder assignment 2017-10-13 17:34:51 +02:00
ttm drm/ttm: Downgrade pr_err to pr_debug for memory allocation failures 2017-11-04 09:48:28 -04:00
tve200 drm/tve200: Use drm_gem_fb_create() and drm_gem_fb_prepare_fb() 2017-10-01 17:04:36 +02:00
udl Merge tag 'drm-misc-next-2017-10-20' of git://anongit.freedesktop.org/drm/drm-misc into drm-next 2017-10-24 16:51:05 +10:00
vc4 drm/vc4: Fix wrong printk format in vc4_bo_stats_debugfs() 2017-11-03 10:15:42 -07:00
vgem drm/vgem: switch to drm_*_get(), drm_*_put() helpers 2017-08-11 11:41:43 -04:00
via drm/via: use ARRAY_SIZE 2017-10-16 11:29:28 +02:00
virtio Merge airlied/drm-next into drm-misc-next 2017-10-03 11:09:16 +02:00
vmwgfx drm: Reorganize drm_pending_event to support future event types [v2] 2017-10-21 07:23:40 +10:00
zte drm/zte: Use drm_gem_fb_create() 2017-08-27 19:31:06 +02:00
ati_pcigart.c
drm_agpsupport.c drm/agpsupport: Remove extra blank line 2017-09-20 09:54:19 -07:00
drm_atomic_helper.c Merge tag 'drm-misc-next-2017-10-20' of git://anongit.freedesktop.org/drm/drm-misc into drm-next 2017-10-24 16:51:05 +10:00
drm_atomic.c drm: Reorganize drm_pending_event to support future event types [v2] 2017-10-21 07:23:40 +10:00
drm_auth.c drm: Check mode object lease status in all master ioctl paths [v4] 2017-10-25 16:31:30 +10:00
drm_blend.c mm: treewide: remove GFP_TEMPORARY allocation flag 2017-09-13 18:53:16 -07:00
drm_bridge.c drm/bridge: change return type of drm_bridge_add function 2017-08-21 08:51:53 +05:30
drm_bufs.c switch compat_drm_mapbufs() to drm_ioctl_kernel() 2017-07-04 13:16:26 -04:00
drm_cache.c
drm_color_mgmt.c drm: Pass struct drm_file * to __drm_mode_object_find [v2] 2017-10-12 10:03:04 +10:00
drm_connector.c drm: Pass struct drm_file * to __drm_mode_object_find [v2] 2017-10-12 10:03:04 +10:00
drm_context.c
drm_crtc_helper_internal.h drm: Add drm_{crtc/encoder/connector}_mode_valid() 2017-05-30 08:37:24 +02:00
drm_crtc_helper.c drm: Replace kzalloc with kcalloc 2017-10-13 15:49:03 -04:00
drm_crtc_internal.h drm: Pass struct drm_file * to __drm_mode_object_find [v2] 2017-10-12 10:03:04 +10:00
drm_crtc.c drm: Pass struct drm_file * to __drm_mode_object_find [v2] 2017-10-12 10:03:04 +10:00
drm_debugfs_crc.c drm/atomic: Prepare drm_modeset_lock infrastructure for interruptible waiting, v2. 2017-09-13 09:50:52 +02:00
drm_debugfs.c
drm_dma.c
drm_dp_aux_dev.c drm_dp_aux_dev: switch to read_iter/write_iter 2017-07-08 20:51:46 -04:00
drm_dp_dual_mode_helper.c drm: Add retries for lspcon mode detection 2017-10-13 12:13:54 +03:00
drm_dp_helper.c drm/dp: WARN about invalid/unknown link rates and bw codes 2017-10-11 18:41:44 +03:00
drm_dp_mst_topology.c drm/dp/mst: Sideband message transaction to power up/down nodes 2017-09-11 16:03:57 +03:00
drm_drv.c drm: Add new LEASE debug level 2017-10-25 16:31:29 +10:00
drm_dumb_buffers.c drm/dumb-buffers: Add defaults for .dumb_map_offset and .dumb_destroy 2017-07-29 13:51:44 +02:00
drm_edid_load.c drm: add backwards compatibility support for drm_kms_helper.edid_firmware 2017-09-19 18:11:45 +03:00
drm_edid.c drm: handle override and firmware EDID at drm_do_get_edid() level 2017-09-19 17:49:25 +03:00
drm_encoder_slave.c
drm_encoder.c drm: Check mode object lease status in all master ioctl paths [v4] 2017-10-25 16:31:30 +10:00
drm_fb_cma_helper.c drm/fb-cma-helper: Remove unused functions 2017-10-01 17:05:39 +02:00
drm_fb_helper.c drm: Replace kzalloc with kcalloc 2017-10-13 15:49:03 -04:00
drm_file.c drm: Document device unplug infrastructure 2017-08-11 10:48:03 +02:00
drm_flip_work.c
drm_fourcc.c
drm_framebuffer.c drm/mode_object: fix documentation for object lookups. 2017-11-10 13:50:47 +10:00
drm_gem_cma_helper.c drm/gem-cma-helper: Change the level of the allocation failure message 2017-10-16 15:19:57 +02:00
drm_gem_framebuffer_helper.c drm/gem-fb-helper: Improve documentation 2017-10-08 15:02:51 +02:00
drm_gem.c drm: fix typo in drm_gem_get_pages() comment 2017-10-04 18:04:28 +02:00
drm_global.c
drm_hashtab.c
drm_info.c
drm_internal.h drm: Add CRTC_GET_SEQUENCE and CRTC_QUEUE_SEQUENCE ioctls [v3] 2017-10-23 11:15:03 +10:00
drm_ioc32.c Merge airlied/drm-next into drm-misc-next 2017-07-26 13:43:33 +02:00
drm_ioctl.c drm: Add four ioctls for managing drm mode object leases [v7] 2017-10-25 16:31:30 +10:00
drm_irq.c drm/doc: Polish irq helper documentation 2017-06-01 08:02:14 +02:00
drm_kms_helper_common.c drm: add backwards compatibility support for drm_kms_helper.edid_firmware 2017-09-19 18:11:45 +03:00
drm_lease.c drm: Add four ioctls for managing drm mode object leases [v7] 2017-10-25 16:31:30 +10:00
drm_legacy.h switch compat_drm_mapbufs() to drm_ioctl_kernel() 2017-07-04 13:16:26 -04:00
drm_lock.c
drm_memory.c
drm_mipi_dsi.c drm: Convert to using %pOF instead of full_name 2017-07-26 13:45:06 +02:00
drm_mm.c lib/interval_tree: fast overlap detection 2017-09-08 18:26:49 -07:00
drm_mode_config.c drm: Check mode object lease status in all master ioctl paths [v4] 2017-10-25 16:31:30 +10:00
drm_mode_object.c drm/mode_object: fix documentation for object lookups. 2017-11-10 13:50:47 +10:00
drm_modes.c drm/modes: Fix drm_mode_is_420_only() comment 2017-07-31 14:23:30 +02:00
drm_modeset_helper.c drm: Plumb modifiers through plane init 2017-08-01 17:50:06 +01:00
drm_modeset_lock.c drm: Require __GFP_NOFAIL for the legacy drm_modeset_lock_all 2017-10-31 17:36:46 +01:00
drm_of.c drm/drm_of: Move drm_of_panel_bridge_remove_function into header. 2017-10-13 16:59:36 +02:00
drm_panel.c
drm_pci.c drm/core: clean up references to drm_dev_unref() 2017-09-27 10:53:12 +02:00
drm_plane_helper.c drm: Replace kzalloc with kcalloc 2017-10-13 15:49:03 -04:00
drm_plane.c drm: Check mode object lease status in all master ioctl paths [v4] 2017-10-25 16:31:30 +10:00
drm_prime.c drm/core: clean up references to drm_dev_unref() 2017-09-27 10:53:12 +02:00
drm_print.c
drm_probe_helper.c drm: Pass struct drm_file * to __drm_mode_object_find [v2] 2017-10-12 10:03:04 +10:00
drm_property.c drm: Pass struct drm_file * to __drm_mode_object_find [v2] 2017-10-12 10:03:04 +10:00
drm_rect.c drm: Add DRM_MODE_ROTATE_ and DRM_MODE_REFLECT_ to UAPI 2017-05-22 09:49:48 +02:00
drm_scatter.c
drm_scdc_helper.c Merge tag 'drm-misc-next-2017-09-20' of git://anongit.freedesktop.org/git/drm-misc into drm-next 2017-09-28 05:46:15 +10:00
drm_simple_kms_helper.c drm: Plumb modifiers through plane init 2017-08-01 17:50:06 +01:00
drm_syncobj.c Merge tag 'drm-misc-next-2017-10-16' of git://anongit.freedesktop.org/drm/drm-misc into drm-next 2017-10-17 10:10:17 +10:00
drm_sysfs.c
drm_trace_points.c
drm_trace.h drm: Use correct path to trace include 2017-09-05 11:11:18 +02:00
drm_vblank.c drm/vblank: Tune drm_crtc_accurate_vblank_count() WARN down to a debug 2017-11-07 21:07:02 +02:00
drm_vm.c Merge branch 'x86-mm-for-linus' of git://git.kernel.org/pub/scm/linux/kernel/git/tip/tip 2017-09-04 12:21:28 -07:00
drm_vma_manager.c lib/interval_tree: fast overlap detection 2017-09-08 18:26:49 -07:00
Kconfig Merge branch 'drm-next-4.15' of git://people.freedesktop.org/~agd5f/linux into drm-next 2017-09-28 08:37:02 +10:00
Makefile drm: Add drm_object lease infrastructure [v5] 2017-10-25 16:31:29 +10:00