mirror of https://lore.kernel.org/lkml/
 help / color / mirror / Atom feed
* [RFC PATCH v0 0/3] pghot: x86: IBS Memory Profiler for hot page promotion
@ 2026-09-24  6:22 Bharata B Rao
  2026-09-24  6:22 ` [RFC PATCH v0 1/3] x86/ibs: Move IBS caps definitions into its own header Bharata B Rao
                   ` (8 more replies)
  0 siblings, 9 replies; 10+ messages in thread
From: Bharata B Rao @ 2026-09-24  6:22 UTC (permalink / raw)
  To: linux-kernel, linux-mm
  Cc: tglx, mingo, bp, dave.hansen, x86, hpa, xin, luto, peterz,
	Jonathan.Cameron, gourry, rientjes, sj, weixugc, willy,
	ying.huang, ziy, dave, nifan.cxl, xuezhengchu, yiannis, akpm,
	david, byungchul, kinseyho, joshua.hahnjy, yuanchu, balbirs,
	shivankg, donettom, linyongting, Bharata B Rao

AMD Zen6 includes IBS Memory Profiler that is independent of the
primary IBS instance. This second, light-weight IBS instance can
be used exclusively for memory access profiling.

This patchset provides a driver for the same. Till now this driver
was being posted as part of pghot patchset [1] where IBS Memory
Profiler was used as an additional source for providing page hotness
information (hardware provided hints source - pghot-hwhints).

Since this driver is x86 specific and also to make review easier,
I am separating out the hardware-hints source into a patchset of
its own. This patchset depends on pghot infrastructure and hence
applies on top of the base pghot patchset. The small bits in the
patchset that modify the pghot documentation and pghot API itself
can be ignored here for the review purposes.

pghot in brief
==============
pghot is a proposed subsystem for hot page tracking and promotion. It
collects memory access information from multiple sources, classifies
hot pages resident in lower-tier memory, and promotes them to faster
tiers via a per-lower-tier-node kernel thread (kmigrated).

Goals of pghot:

- Unify hot page detection from multiple sources like hint faults,
  page table scans, hardware hints (AMD IBS).
- Decouple detection from migration.
- Centralize promotion logic via per-lower-tier-node kmigrated kernel
  thread.
- Move promotion rate-limiting and related logic used by numa_balancing=2
  (NUMAB2, the current NUMA balancing-based promotion) from the scheduler
  to pghot for broader reuse.

pghot provides an API (pghot_record_access()) that other
sub-systems/drivers can use to report memory access information
to pghot. IBS Memory Profiler is one such source or driver.

IBS Memory Profiler
===================
- Hardware samples an op every N core cycles or N dispatched ops,
  with a software-programmable period, so sampling overhead and
  coverage can be traded off at runtime.

- Each sample reports both the linear and the physical address of
  the accessed data, so the kernel gets the accessed PFN directly,
  without page-table scanning, hint faults or any address translation
  of its own.

- Samples include a data-source indication that identifies where the
  access was satisfied from (cache, DRAM, external memory etc). This
  lets software distinguish local DRAM traffic from CXL or other
  lower-tier accesses.

- Hardware filtering lets the profiler report only the accesses that
  matter for memory placement: L3-miss-only, a load-latency threshold,
  and exclusion by instruction-address bit 63 (i.e. user vs kernel).
  Filtered-out samples are discarded by hardware and never interrupt
  the kernel.

- The profiler raises its own interrupt, routed through a dedicated
  extended LVT offset that is distinct from the one used by the
  primary IBS instance. It can therefore be used by the kernel without
  interfering with existing IBS users such as perf.

Spec: "AMD64 Zen6 Instruction Based Sampling (IBS) Extensions and
Features", publication 69205 rev 1.00, section "IBS Memory Profiler".

Benchmarks summary
==================
All results are on 3-node tiered systems (DRAM top tier + CPU-less CXL
lower tier). Speedups below are normalized to the base kernel with no
tiering (NUMAB=0). Columns compare mainline hint-fault tiering
(base NUMAB=2) against HW-hint driven promotion via the AMD IBS
memory profiler (pghot-hwhints, NUMAB=0, no NUMA scanning). IBS sample
period is 10000 unless noted. Single run per config except llama.cpp
and microbench (avg of 3).

Benchmark      Metric (higher=better)   base-NUMAB2  pghot-hwhints
---------------------------------------------------------------------
NAS BT (MPI)   Mop/s total                  2.34x     2.15x
Graph500 BFS   harmonic-mean TEPS           2.34x     3.17x
llama.cpp      decode tok/s (tg128)         1.19x     1.22x
Redis+memtier  ops/sec                      1.04x     1.00x
ptr-chase      1/latency (p10k / p5008)     2.24x     1.49x / 3.48x
Microbench     completion time (1/t)        2.55x     2.22x
---------------------------------------------------------------------
(baseline = base kernel, no tiering = 1.00x; pghot-hwhints uses IBS, NUMAB=0)

Headline: IBS/HW-hints recovers most of mainline NUMAB=2 on
bandwidth-heavy promotion (NAS BT 2.15x vs 2.34x, ~92% of NUMAB2
throughput) with zero hint faults or PTE scans; it beats NUMAB2 on
Graph500 (3.17x vs 2.34x, ~1/4 the promotions) and matches it on
llama decode. Coverage is the limiter on very large, uniformly hot
sets: Redis stays flat until sampling captures more of the hot set,
while pointer-chase at period=5008 reaches the lowest latency of the
set (3.48x vs NUMAB2 2.24x; DAMON 2.69x).

- NAS BT (MPI, Class D, 16 ranks): full footprint pre-staged on the
  CXL lower tier, then measured cold; isolates hot-page promotion.
- Graph500 (reference BFS, SCALE=28, edgefactor=16, 128 ranks):
  working set on the CXL node; figure of merit is harmonic-mean TEPS.
- llama.cpp (llama-bench, Mixtral-8x22B Q4_K_M): ~1/3 of the model
  demoted to CXL under memory pressure; decode (tg128) is tier-sensitive.
- Redis + memtier (~64 GB dataset, 62.2M x 1 KB keys): dataset
  migrated to CXL, GET-heavy traffic over 50% of the keyspace.
  IBS at period 10000 and 5008 both ~1.00x vs baseline (hot-set
  coverage ~10% of NUMAB2's ~40 GiB promotion).
- Microbenchmark: 64 threads, random 4K access over 8G on
  the CXL node; latency-bound.
- Pointer-chase (64 threads, 64 GiB buffer, 16 GiB hot, 240 s):
  latency-bound; NUMAB2 places the exact hot set. IBS period=10000
  under-promotes in 240 s; period=5008 promotes 12.0 GiB of the 16 GiB
  hot set and records the best latency (92 ns vs NUMAB2 143 ns,
  DAMON 119 ns).

Detailed per-benchmark tables (throughput/latency + vmstat and pghot
promotion counters) are posted as replies to this thread.

Test reports
============
Compile test matrix
-------------------
The series was compile-tested across the full range of relevant Kconfig
combinations on x86_64 (defconfig-based) and cross-compiled on arm64.
Combinations of PGHOT, PGHOT_PRECISE, NUMA_BALANCING,
NUMA_BALANCING_TIERING, NUMA_MIGRATION, HWMEM_PROFILER/AMD_IBS_MEMPROF,
DEBUG_FS, SYSCTL and PM/PM_SLEEP were verified, including pghot disabled,
pghot standalone (no NUMA balancing), NUMA balancing mode 1 and mode 2
(tiering), precise mode, the AMD IBS memory profiler (including with power
management and suspend/hibernation disabled), NUMA_MIGRATION=n, and pghot
with DEBUG_FS and/or SYSCTL disabled. Kconfig guards were confirmed
(NUMA_BALANCING_TIERING without PGHOT, and HWMEM_PROFILER without a
selecting driver, are dropped). Since PGHOT defaults to y when
NUMA_BALANCING is set and NUMA_BALANCING_TIERING defaults to y, an existing
config with NUMA_BALANCING=y but no pghot symbols resolves, via
olddefconfig, to PGHOT=y and NUMA_BALANCING_TIERING=y and builds cleanly,
while NUMA_BALANCING=n leaves PGHOT off. allnoconfig, tinyconfig,
allyesconfig and allmodconfig were also built. All configurations build with
no new warnings.

CPU hotplug stress testing
--------------------------
The IBS memory profiler's STARTING-phase cpuhp callbacks (arm IBS and
set up the APIC EILVT on startup; mask, disable and drain the per-CPU
sample ring on teardown) were stress tested against concurrent hotplug.

On an AMD Zen6 (256 CPUs, CXL lower tier) with PROVE_LOCKING, PROVE_RCU,
DEBUG_ATOMIC_SLEEP and SLUB_DEBUG_ON, the following ran concurrently for
20 minutes: IBS armed at the minimum sample period (5008) feeding a
node-bound memory workload; 8 parallel CPU offline/online loops plus
periodic mass offline of 96 CPUs at once; and continuous profiler
reconfiguration driving on_each_cpu() re-arm against the changing online
mask.

No oops, warning, lockdep/RCU splat or hung-task was seen. The profiler
kept sampling and pghot kept recording throughout, the per-CPU ring
dropped no samples even at ~2M samples/interval, and every CPU reliably
came back online with per-CPU state correctly reset.

Changes to the driver since it was posted last time with pghot
==============================================================
- Register IBS Memory Profiler cpuhp callbacks on CPUHP_AP_ONLINE_DYN
  instead of a dedicated CPUHP_AP_MM_AMD_IBS_MEMPROF_STARTING state.
  This elimiates the subtle races due to worker getting migrated
  to other CPU before teardown.
- Make SPSC tail handling symmetric by using smp_store_release().
- Mark the clearing of mprof_work_pending with WRITE_ONCE() in
  mprof_work_handler() and x86_amd_ibs_mprof_offline(), so every
  access to the flag is uniformly annotated.
- Take cpus_read_lock() across mprof_publish(). This keeps the online
  set stable so on_each_cpu() cannot race a CPU's ONLINE arm path.
- Drain the per-CPU sample workers before free_percpu(mprof_s) on the init
  error path.
- Add dram accesses stats for far memory accesses too.
- Made reading of data2 optional to L1 and L2 hit.
- Protect debugfs and sysfs readers in ibs-mprof.c with mutex.
- Validate memprofiler EILVT offset at once during init time.
- Ensure the period reads back what is written into the HW IbsMemOpCnt
  - Minimum value changed from 5000 to 5008 to make it 16-bytes aligned
- Reject over-sized writes to IBS Memory Profiler's debugfs tunables.
- Change ibs_mprof_enabled to static definition.
- Include linux/string_choices.h explicitly in mprof for str_enabled_disabled().
- Handle failure path in mprof driver init proper rollback.
- Added suspend/resume support so that EILVT/IBS is properly configured
  for CPU0 post resume.
- Gated mprof init with X86_FEATURE_IBS check so that the driver
  refuses to move further on non-AMD platforms.

Dependencies
============
- [1] pghot patchset:
  https://lore.kernel.org/linux-mm/20260728054356.291998-1-bharata@amd.com/

- IBS Memory Profiler depends on the patchset that increases the
  number of APIC EILVT registers:
  https://lore.kernel.org/lkml/cover.1788425679.git.naveen@kernel.org/

- Full tree with all dependencies included:
  https://github.com/AMDESE/linux-mm/tree/bharata/pghot-mprof-rfcv0

AI assistance was taken to run and summarize the benchmark results,
to run compile test matrix and CPU hotplug stress tests.

Bharata B Rao (3):
  x86/ibs: Move IBS caps definitions into its own header
  x86/mm/ibs: In-kernel driver for AMD IBS Memory Profiler
  x86/mm/ibs: Add runtime controls for IBS memprofiler

 .../admin-guide/kernel-parameters.txt         |   5 +
 Documentation/admin-guide/mm/pghot.rst        |  89 ++
 arch/x86/Kconfig                              |  16 +
 arch/x86/entry/entry_fred.c                   |   1 +
 arch/x86/include/asm/hardirq.h                |   3 +
 arch/x86/include/asm/ibs-caps.h               |  93 ++
 arch/x86/include/asm/ibs-mprof.h              |  61 ++
 arch/x86/include/asm/idtentry.h               |   6 +
 arch/x86/include/asm/irq_vectors.h            |   4 +-
 arch/x86/include/asm/msr-index.h              |   8 +
 arch/x86/include/asm/perf_event.h             |  81 +-
 arch/x86/kernel/idt.c                         |   3 +
 arch/x86/kernel/irq.c                         |   3 +
 arch/x86/mm/Makefile                          |   1 +
 arch/x86/mm/ibs-mprof.c                       | 867 ++++++++++++++++++
 include/linux/vm_event_item.h                 |   8 +
 mm/Kconfig                                    |   9 +
 mm/vmstat.c                                   |   8 +
 18 files changed, 1185 insertions(+), 81 deletions(-)
 create mode 100644 arch/x86/include/asm/ibs-caps.h
 create mode 100644 arch/x86/include/asm/ibs-mprof.h
 create mode 100644 arch/x86/mm/ibs-mprof.c

-- 
2.34.1

^ permalink raw reply	[flat|nested] 10+ messages in thread

end of thread, other threads:[~2026-09-24  6:37 UTC | newest]

Thread overview: 10+ messages (download: mbox.gz / follow: Atom feed)
-- links below jump to the message on this page --
2026-09-24  6:22 [RFC PATCH v0 0/3] pghot: x86: IBS Memory Profiler for hot page promotion Bharata B Rao
2026-09-24  6:22 ` [RFC PATCH v0 1/3] x86/ibs: Move IBS caps definitions into its own header Bharata B Rao
2026-09-24  6:22 ` [RFC PATCH v0 2/3] x86/mm/ibs: In-kernel driver for AMD IBS Memory Profiler Bharata B Rao
2026-09-24  6:22 ` [RFC PATCH v0 3/3] x86/mm/ibs: Add runtime controls for IBS memprofiler Bharata B Rao
2026-09-24  6:26 ` [RFC PATCH v0 0/3] pghot: x86: IBS Memory Profiler for hot page promotion Bharata B Rao
2026-09-24  6:27 ` Bharata B Rao
2026-09-24  6:31 ` Bharata B Rao
2026-09-24  6:33 ` Bharata B Rao
2026-09-24  6:35 ` Bharata B Rao
2026-09-24  6:37 ` Bharata B Rao

This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox

all inboxes | Powered by JetHome®