/*
 * Contributed by Stephane Eranian <eranian@gmail.com>
 *
 * Permission is hereby granted, free of charge, to any person obtaining a copy
 * of this software and associated documentation files (the "Software"), to deal
 * in the Software without restriction, including without limitation the rights
 * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies
 * of the Software, and to permit persons to whom the Software is furnished to do so,
 * subject to the following conditions:
 *
 * The above copyright notice and this permission notice shall be included in all
 * copies or substantial portions of the Software.
 *
 * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED,
 * INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A
 * PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT
 * HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF
 * CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE
 * OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
 *
 * This file is part of libpfm, a performance monitoring support library for
 * applications on Linux.
 *
 *
 * PMU: intel_spr (Intel SapphireRapid)
 * Based on Intel JSON event table version   : 1.11
 * Based on Intel JSON event table pusblised : 02/09/2023
 */

static const intel_x86_umask_t spr_amx_ops_retired[]={
  { .uname   = "BF16",
    .udesc   = "AMX retired arithmetic BF16 operations.",
    .ucode   = 0x0200ull,
    .uflags  = INTEL_X86_NCOMBO,
  },
  { .uname   = "INT8",
    .udesc   = "AMX retired arithmetic integer 8-bit operations.",
    .ucode   = 0x0100ull,
    .uflags  = INTEL_X86_NCOMBO,
  },
};

static const intel_x86_umask_t intel_spr_ocr[]={
  { .uname   = "DEMAND_CODE_RD_ANY_RESPONSE",
    .udesc   = "Counts demand instruction fetches and L1 instruction cache prefetches that have any type of response.",
    .ucode   = 0x1000400ull,
    .uflags  = INTEL_X86_NCOMBO,
  },
  { .uname   = "DEMAND_CODE_RD_DRAM",
    .udesc   = "Counts demand instruction fetches and L1 instruction cache prefetches that were supplied by DRAM.",
    .ucode   = 0x73c00000400ull,
    .uflags  = INTEL_X86_NCOMBO,
  },
  { .uname   = "DEMAND_CODE_RD_L3_HIT",
    .udesc   = "Counts demand instruction fetches and L1 instruction cache prefetches that hit in the L3 or were snooped from another core's caches on the same socket.",
    .ucode   = 0x3f803c000400ull,
    .uflags  = INTEL_X86_NCOMBO,
  },
  { .uname   = "DEMAND_CODE_RD_L3_HIT_SNOOP_HITM",
    .udesc   = "Counts demand instruction fetches and L1 instruction cache prefetches that resulted in a snoop hit a modified line in another core's caches which forwarded the data.",
    .ucode   = 0x10003c000400ull,
    .uflags  = INTEL_X86_NCOMBO,
  },
  { .uname   = "DEMAND_CODE_RD_L3_MISS",
    .udesc   = "Counts demand instruction fetches and L1 instruction cache prefetches that were not supplied by the local socket's L1, L2, or L3 caches.",
    .ucode   = 0x3fbfc0000400ull,
    .uflags  = INTEL_X86_NCOMBO,
  },
  { .uname   = "DEMAND_CODE_RD_LOCAL_DRAM",
    .udesc   = "Counts demand instruction fetches and L1 instruction cache prefetches that were supplied by DRAM attached to this socket, unless in Sub NUMA Cluster(SNC) Mode.  In SNC Mode counts only those DRAM accesses that are controlled by the close SNC Cluster.",
    .ucode   = 0x10400000400ull,
    .uflags  = INTEL_X86_NCOMBO,
  },
  { .uname   = "DEMAND_CODE_RD_SNC_CACHE_HITM",
    .udesc   = "Counts demand instruction fetches and L1 instruction cache prefetches that hit a modified line in a distant L3 Cache or were snooped from a distant core's L1/L2 caches on this socket when the system is in SNC (sub-NUMA cluster) mode.",
    .ucode   = 0x100800000400ull,
    .uflags  = INTEL_X86_NCOMBO,
  },
  { .uname   = "DEMAND_CODE_RD_SNC_CACHE_HIT_WITH_FWD",
    .udesc   = "Counts demand instruction fetches and L1 instruction cache prefetches that either hit a non-modified line in a distant L3 Cache or were snooped from a distant core's L1/L2 caches on this socket when the system is in SNC (sub-NUMA cluster) mode.",
    .ucode   = 0x80800000400ull,
    .uflags  = INTEL_X86_NCOMBO,
  },
  { .uname   = "DEMAND_CODE_RD_SNC_DRAM",
    .udesc   = "Counts demand instruction fetches and L1 instruction cache prefetches that were supplied by DRAM on a distant memory controller of this socket when the system is in SNC (sub-NUMA cluster) mode.",
    .ucode   = 0x70800000400ull,
    .uflags  = INTEL_X86_NCOMBO,
  },
  { .uname   = "DEMAND_DATA_RD_ANY_RESPONSE",
    .udesc   = "Counts demand data reads that have any type of response.",
    .ucode   = 0x1000100ull,
    .uflags  = INTEL_X86_NCOMBO,
  },
  { .uname   = "DEMAND_DATA_RD_DRAM",
    .udesc   = "Counts demand data reads that were supplied by DRAM.",
    .ucode   = 0x73c00000100ull,
    .uflags  = INTEL_X86_NCOMBO,
  },
  { .uname   = "DEMAND_DATA_RD_L3_HIT",
    .udesc   = "Counts demand data reads that hit in the L3 or were snooped from another core's caches on the same socket.",
    .ucode   = 0x3f803c000100ull,
    .uflags  = INTEL_X86_NCOMBO,
  },
  { .uname   = "DEMAND_DATA_RD_L3_HIT_SNOOP_HITM",
    .udesc   = "Counts demand data reads that resulted in a snoop hit a modified line in another core's caches which forwarded the data.",
    .ucode   = 0x10003c000100ull,
    .uflags  = INTEL_X86_NCOMBO,
  },
  { .uname   = "DEMAND_DATA_RD_L3_HIT_SNOOP_HIT_NO_FWD",
    .udesc   = "Counts demand data reads that resulted in a snoop that hit in another core, which did not forward the data.",
    .ucode   = 0x4003c000100ull,
    .uflags  = INTEL_X86_NCOMBO,
  },
  { .uname   = "DEMAND_DATA_RD_L3_HIT_SNOOP_HIT_WITH_FWD",
    .udesc   = "Counts demand data reads that resulted in a snoop hit in another core's caches which forwarded the unmodified data to the requesting core.",
    .ucode   = 0x8003c000100ull,
    .uflags  = INTEL_X86_NCOMBO,
  },
  { .uname   = "DEMAND_DATA_RD_L3_MISS",
    .udesc   = "Counts demand data reads that were not supplied by the local socket's L1, L2, or L3 caches.",
    .ucode   = 0x3fbfc0000100ull,
    .uflags  = INTEL_X86_NCOMBO,
  },
  { .uname   = "DEMAND_DATA_RD_LOCAL_DRAM",
    .udesc   = "Counts demand data reads that were supplied by DRAM attached to this socket, unless in Sub NUMA Cluster(SNC) Mode.  In SNC Mode counts only those DRAM accesses that are controlled by the close SNC Cluster.",
    .ucode   = 0x10400000100ull,
    .uflags  = INTEL_X86_NCOMBO,
  },
  { .uname   = "DEMAND_DATA_RD_REMOTE_CACHE_SNOOP_HITM",
    .udesc   = "Counts demand data reads that were supplied by a cache on a remote socket where a snoop hit a modified line in another core's caches which forwarded the data.",
    .ucode   = 0x103000000100ull,
    .uflags  = INTEL_X86_NCOMBO,
  },
  { .uname   = "DEMAND_DATA_RD_REMOTE_CACHE_SNOOP_HIT_WITH_FWD",
    .udesc   = "Counts demand data reads that were supplied by a cache on a remote socket where a snoop hit in another core's caches which forwarded the unmodified data to the requesting core.",
    .ucode   = 0x83000000100ull,
    .uflags  = INTEL_X86_NCOMBO,
  },
  { .uname   = "DEMAND_DATA_RD_REMOTE_DRAM",
    .udesc   = "Counts demand data reads that were supplied by DRAM attached to another socket.",
    .ucode   = 0x73000000100ull,
    .uflags  = INTEL_X86_NCOMBO,
  },
  { .uname   = "DEMAND_DATA_RD_REMOTE_PMM",
    .udesc   = "Counts demand data reads that were supplied by PMM attached to another socket.",
    .ucode   = 0x70300000100ull,
    .uflags  = INTEL_X86_NCOMBO,
  },
  { .uname   = "DEMAND_DATA_RD_SNC_CACHE_HITM",
    .udesc   = "Counts demand data reads that hit a modified line in a distant L3 Cache or were snooped from a distant core's L1/L2 caches on this socket when the system is in SNC (sub-NUMA cluster) mode.",
    .ucode   = 0x100800000100ull,
    .uflags  = INTEL_X86_NCOMBO,
  },
  { .uname   = "DEMAND_DATA_RD_SNC_CACHE_HIT_WITH_FWD",
    .udesc   = "Counts demand data reads that either hit a non-modified line in a distant L3 Cache or were snooped from a distant core's L1/L2 caches on this socket when the system is in SNC (sub-NUMA cluster) mode.",
    .ucode   = 0x80800000100ull,
    .uflags  = INTEL_X86_NCOMBO,
  },
  { .uname   = "DEMAND_DATA_RD_SNC_DRAM",
    .udesc   = "Counts demand data reads that were supplied by DRAM on a distant memory controller of this socket when the system is in SNC (sub-NUMA cluster) mode.",
    .ucode   = 0x70800000100ull,
    .uflags  = INTEL_X86_NCOMBO,
  },
  { .uname   = "DEMAND_RFO_ANY_RESPONSE",
    .udesc   = "Counts demand reads for ownership (RFO) requests and software prefetches for exclusive ownership (PREFETCHW) that have any type of response.",
    .ucode   = 0x3f3ffc000200ull,
    .uflags  = INTEL_X86_NCOMBO,
  },
  { .uname   = "DEMAND_RFO_DRAM",
    .udesc   = "Counts demand reads for ownership (RFO) requests and software prefetches for exclusive ownership (PREFETCHW) that were supplied by DRAM.",
    .ucode   = 0x73c00000200ull,
    .uflags  = INTEL_X86_NCOMBO,
  },
  { .uname   = "DEMAND_RFO_L3_HIT",
    .udesc   = "Counts demand reads for ownership (RFO) requests and software prefetches for exclusive ownership (PREFETCHW) that hit in the L3 or were snooped from another core's caches on the same socket.",
    .ucode   = 0x3f803c000200ull,
    .uflags  = INTEL_X86_NCOMBO,
  },
  { .uname   = "DEMAND_RFO_L3_HIT_SNOOP_HITM",
    .udesc   = "Counts demand reads for ownership (RFO) requests and software prefetches for exclusive ownership (PREFETCHW) that resulted in a snoop hit a modified line in another core's caches which forwarded the data.",
    .ucode   = 0x10003c000200ull,
    .uflags  = INTEL_X86_NCOMBO,
  },
  { .uname   = "DEMAND_RFO_L3_MISS",
    .udesc   = "Counts demand reads for ownership (RFO) requests and software prefetches for exclusive ownership (PREFETCHW) that were not supplied by the local socket's L1, L2, or L3 caches.",
    .ucode   = 0x3f3fc0000200ull,
    .uflags  = INTEL_X86_NCOMBO,
  },
  { .uname   = "DEMAND_RFO_LOCAL_DRAM",
    .udesc   = "Counts demand reads for ownership (RFO) requests and software prefetches for exclusive ownership (PREFETCHW) that were supplied by DRAM attached to this socket, unless in Sub NUMA Cluster(SNC) Mode.  In SNC Mode counts only those DRAM accesses that are controlled by the close SNC Cluster.",
    .ucode   = 0x10400000200ull,
    .uflags  = INTEL_X86_NCOMBO,
  },
  { .uname   = "DEMAND_RFO_SNC_CACHE_HITM",
    .udesc   = "Counts demand reads for ownership (RFO) requests and software prefetches for exclusive ownership (PREFETCHW) that hit a modified line in a distant L3 Cache or were snooped from a distant core's L1/L2 caches on this socket when the system is in SNC (sub-NUMA cluster) mode.",
    .ucode   = 0x100800000200ull,
    .uflags  = INTEL_X86_NCOMBO,
  },
  { .uname   = "DEMAND_RFO_SNC_CACHE_HIT_WITH_FWD",
    .udesc   = "Counts demand reads for ownership (RFO) requests and software prefetches for exclusive ownership (PREFETCHW) that either hit a non-modified line in a distant L3 Cache or were snooped from a distant core's L1/L2 caches on this socket when the system is in SNC (sub-NUMA cluster) mode.",
    .ucode   = 0x80800000200ull,
    .uflags  = INTEL_X86_NCOMBO,
  },
  { .uname   = "DEMAND_RFO_SNC_DRAM",
    .udesc   = "Counts demand reads for ownership (RFO) requests and software prefetches for exclusive ownership (PREFETCHW) that were supplied by DRAM on a distant memory controller of this socket when the system is in SNC (sub-NUMA cluster) mode.",
    .ucode   = 0x70800000200ull,
    .uflags  = INTEL_X86_NCOMBO,
  },
  { .uname   = "HWPF_L1D_ANY_RESPONSE",
    .udesc   = "Counts data load hardware prefetch requests to the L1 data cache that have any type of response.",
    .ucode   = 0x1040000ull,
    .uflags  = INTEL_X86_NCOMBO,
  },
  { .uname   = "HWPF_L2_ANY_RESPONSE",
    .udesc   = "Counts hardware prefetches (which bring data to L2) that have any type of response.",
    .ucode   = 0x1007000ull,
    .uflags  = INTEL_X86_NCOMBO,
  },
  { .uname   = "HWPF_L3_ANY_RESPONSE",
    .udesc   = "Counts hardware prefetches to the L3 only that have any type of response.",
    .ucode   = 0x1238000ull,
    .uflags  = INTEL_X86_NCOMBO,
  },
  { .uname   = "HWPF_L3_L3_HIT",
    .udesc   = "Counts hardware prefetches to the L3 only that hit in the L3 or were snooped from another core's caches on the same socket.",
    .ucode   = 0x8008238000ull,
    .uflags  = INTEL_X86_NCOMBO,
  },
  { .uname   = "HWPF_L3_L3_MISS",
    .udesc   = "Counts hardware prefetches to the L3 only that missed the local socket's L1, L2, and L3 caches.",
    .ucode   = 0x9400238000ull,
    .uflags  = INTEL_X86_NCOMBO,
  },
  { .uname   = "HWPF_L3_L3_MISS_LOCAL",
    .udesc   = "Counts hardware prefetches to the L3 only that were not supplied by the local socket's L1, L2, or L3 caches and the cacheline is homed locally.",
    .ucode   = 0x8400238000ull,
    .uflags  = INTEL_X86_NCOMBO,
  },
  { .uname   = "HWPF_L3_REMOTE",
    .udesc   = "Counts hardware prefetches to the L3 only that were not supplied by the local socket's L1, L2, or L3 caches and the cacheline was homed in a remote socket.",
    .ucode   = 0x9000238000ull,
    .uflags  = INTEL_X86_NCOMBO,
  },
  { .uname   = "MODIFIED_WRITE_ANY_RESPONSE",
    .udesc   = "Counts writebacks of modified cachelines and streaming stores that have any type of response.",
    .ucode   = 0x1080800ull,
    .uflags  = INTEL_X86_NCOMBO,
  },
  { .uname   = "READS_TO_CORE_ANY_RESPONSE",
    .udesc   = "Counts all (cacheable) data read, code read and RFO requests including demands and prefetches to the core caches (L1 or L2) that have any type of response.",
    .ucode   = 0x3f3ffc447700ull,
    .uflags  = INTEL_X86_NCOMBO,
  },
  { .uname   = "READS_TO_CORE_DRAM",
    .udesc   = "Counts all (cacheable) data read, code read and RFO requests including demands and prefetches to the core caches (L1 or L2) that were supplied by DRAM.",
    .ucode   = 0x73c00447700ull,
    .uflags  = INTEL_X86_NCOMBO,
  },
  { .uname   = "READS_TO_CORE_L3_HIT",
    .udesc   = "Counts all (cacheable) data read, code read and RFO requests including demands and prefetches to the core caches (L1 or L2) that hit in the L3 or were snooped from another core's caches on the same socket.",
    .ucode   = 0x3f003c447700ull,
    .uflags  = INTEL_X86_NCOMBO,
  },
  { .uname   = "READS_TO_CORE_L3_HIT_SNOOP_HITM",
    .udesc   = "Counts all (cacheable) data read, code read and RFO requests including demands and prefetches to the core caches (L1 or L2) that resulted in a snoop hit a modified line in another core's caches which forwarded the data.",
    .ucode   = 0x10003c447700ull,
    .uflags  = INTEL_X86_NCOMBO,
  },
  { .uname   = "READS_TO_CORE_L3_HIT_SNOOP_HIT_NO_FWD",
    .udesc   = "Counts all (cacheable) data read, code read and RFO requests including demands and prefetches to the core caches (L1 or L2) that resulted in a snoop that hit in another core, which did not forward the data.",
    .ucode   = 0x4003c447700ull,
    .uflags  = INTEL_X86_NCOMBO,
  },
  { .uname   = "READS_TO_CORE_L3_HIT_SNOOP_HIT_WITH_FWD",
    .udesc   = "Counts all (cacheable) data read, code read and RFO requests including demands and prefetches to the core caches (L1 or L2) that resulted in a snoop hit in another core's caches which forwarded the unmodified data to the requesting core.",
    .ucode   = 0x8003c447700ull,
    .uflags  = INTEL_X86_NCOMBO,
  },
  { .uname   = "READS_TO_CORE_L3_MISS",
    .udesc   = "Counts all (cacheable) data read, code read and RFO requests including demands and prefetches to the core caches (L1 or L2) that were not supplied by the local socket's L1, L2, or L3 caches.",
    .ucode   = 0x3f3fc0447700ull,
    .uflags  = INTEL_X86_NCOMBO,
  },
  { .uname   = "READS_TO_CORE_L3_MISS_LOCAL",
    .udesc   = "Counts all (cacheable) data read, code read and RFO requests including demands and prefetches to the core caches (L1 or L2) that were not supplied by the local socket's L1, L2, or L3 caches and the cacheline is homed locally.",
    .ucode   = 0x3f04c0447700ull,
    .uflags  = INTEL_X86_NCOMBO,
  },
  { .uname   = "READS_TO_CORE_L3_MISS_LOCAL_SOCKET",
    .udesc   = "Counts all (cacheable) data read, code read and RFO requests including demands and prefetches to the core caches (L1 or L2) that missed the L3 Cache and were supplied by the local socket (DRAM or PMM), whether or not in Sub NUMA Cluster(SNC) Mode.  In SNC Mode counts PMM or DRAM accesses that are controlled by the close or distant SNC Cluster.  It does not count misses to the L3 which go to Local CXL Type 2 Memory or Local Non DRAM.",
    .ucode   = 0x70cc0447700ull,
    .uflags  = INTEL_X86_NCOMBO,
  },
  { .uname   = "READS_TO_CORE_LOCAL_DRAM",
    .udesc   = "Counts all (cacheable) data read, code read and RFO requests including demands and prefetches to the core caches (L1 or L2) that were supplied by DRAM attached to this socket, unless in Sub NUMA Cluster(SNC) Mode.  In SNC Mode counts only those DRAM accesses that are controlled by the close SNC Cluster.",
    .ucode   = 0x10400447700ull,
    .uflags  = INTEL_X86_NCOMBO,
  },
  { .uname   = "READS_TO_CORE_LOCAL_SOCKET_DRAM",
    .udesc   = "Counts all (cacheable) data read, code read and RFO requests including demands and prefetches to the core caches (L1 or L2) that were supplied by DRAM attached to this socket, whether or not in Sub NUMA Cluster(SNC) Mode.  In SNC Mode counts DRAM accesses that are controlled by the close or distant SNC Cluster.",
    .ucode   = 0x70c00447700ull,
    .uflags  = INTEL_X86_NCOMBO,
  },
  { .uname   = "READS_TO_CORE_LOCAL_SOCKET_PMM",
    .udesc   = "Counts all (cacheable) data read, code read and RFO requests including demands and prefetches to the core caches (L1 or L2) that were supplied by PMM attached to this socket, whether or not in Sub NUMA Cluster(SNC) Mode.  In SNC Mode counts PMM accesses that are controlled by the close or distant SNC Cluster.",
    .ucode   = 0x700c0447700ull,
    .uflags  = INTEL_X86_NCOMBO,
  },
  { .uname   = "READS_TO_CORE_REMOTE",
    .udesc   = "Counts all (cacheable) data read, code read and RFO requests including demands and prefetches to the core caches (L1 or L2) that were not supplied by the local socket's L1, L2, or L3 caches and were supplied by a remote socket.",
    .ucode   = 0x3f3300447700ull,
    .uflags  = INTEL_X86_NCOMBO,
  },
  { .uname   = "READS_TO_CORE_REMOTE_CACHE_SNOOP_FWD",
    .udesc   = "Counts all (cacheable) data read, code read and RFO requests including demands and prefetches to the core caches (L1 or L2) that were supplied by a cache on a remote socket where a snoop was sent and data was returned (Modified or Not Modified).",
    .ucode   = 0x183000447700ull,
    .uflags  = INTEL_X86_NCOMBO,
  },
  { .uname   = "READS_TO_CORE_REMOTE_CACHE_SNOOP_HITM",
    .udesc   = "Counts all (cacheable) data read, code read and RFO requests including demands and prefetches to the core caches (L1 or L2) that were supplied by a cache on a remote socket where a snoop hit a modified line in another core's caches which forwarded the data.",
    .ucode   = 0x103000447700ull,
    .uflags  = INTEL_X86_NCOMBO,
  },
  { .uname   = "READS_TO_CORE_REMOTE_CACHE_SNOOP_HIT_WITH_FWD",
    .udesc   = "Counts all (cacheable) data read, code read and RFO requests including demands and prefetches to the core caches (L1 or L2) that were supplied by a cache on a remote socket where a snoop hit in another core's caches which forwarded the unmodified data to the requesting core.",
    .ucode   = 0x83000447700ull,
    .uflags  = INTEL_X86_NCOMBO,
  },
  { .uname   = "READS_TO_CORE_REMOTE_DRAM",
    .udesc   = "Counts all (cacheable) data read, code read and RFO requests including demands and prefetches to the core caches (L1 or L2) that were supplied by DRAM attached to another socket.",
    .ucode   = 0x73000447700ull,
    .uflags  = INTEL_X86_NCOMBO,
  },
  { .uname   = "READS_TO_CORE_REMOTE_MEMORY",
    .udesc   = "Counts all (cacheable) data read, code read and RFO requests including demands and prefetches to the core caches (L1 or L2) that were supplied by DRAM or PMM attached to another socket.",
    .ucode   = 0x73300447700ull,
    .uflags  = INTEL_X86_NCOMBO,
  },
  { .uname   = "READS_TO_CORE_REMOTE_PMM",
    .udesc   = "Counts all (cacheable) data read, code read and RFO requests including demands and prefetches to the core caches (L1 or L2) that were supplied by PMM attached to another socket.",
    .ucode   = 0x70300447700ull,
    .uflags  = INTEL_X86_NCOMBO,
  },
  { .uname   = "READS_TO_CORE_SNC_CACHE_HITM",
    .udesc   = "Counts all (cacheable) data read, code read and RFO requests including demands and prefetches to the core caches (L1 or L2) that hit a modified line in a distant L3 Cache or were snooped from a distant core's L1/L2 caches on this socket when the system is in SNC (sub-NUMA cluster) mode.",
    .ucode   = 0x100800447700ull,
    .uflags  = INTEL_X86_NCOMBO,
  },
  { .uname   = "READS_TO_CORE_SNC_CACHE_HIT_WITH_FWD",
    .udesc   = "Counts all (cacheable) data read, code read and RFO requests including demands and prefetches to the core caches (L1 or L2) that either hit a non-modified line in a distant L3 Cache or were snooped from a distant core's L1/L2 caches on this socket when the system is in SNC (sub-NUMA cluster) mode.",
    .ucode   = 0x80800447700ull,
    .uflags  = INTEL_X86_NCOMBO,
  },
  { .uname   = "READS_TO_CORE_SNC_DRAM",
    .udesc   = "Counts all (cacheable) data read, code read and RFO requests including demands and prefetches to the core caches (L1 or L2) that were supplied by DRAM on a distant memory controller of this socket when the system is in SNC (sub-NUMA cluster) mode.",
    .ucode   = 0x70800447700ull,
    .uflags  = INTEL_X86_NCOMBO,
  },
  { .uname   = "RFO_TO_CORE_L3_HIT_M",
    .udesc   = "Counts demand reads for ownership (RFO), hardware prefetch RFOs (which bring data to L2), and software prefetches for exclusive ownership (PREFETCHW) that hit to a (M)odified cacheline in the L3 or snoop filter.",
    .ucode   = 0x1f8004002200ull,
    .uflags  = INTEL_X86_NCOMBO,
  },
  { .uname   = "STREAMING_WR_ANY_RESPONSE",
    .udesc   = "Counts streaming stores that have any type of response.",
    .ucode   = 0x1080000ull,
    .uflags  = INTEL_X86_NCOMBO,
  },
  { .uname   = "STREAMING_WR_L3_HIT",
    .udesc   = "Counts streaming stores that hit in the L3 or were snooped from another core's caches on the same socket.",
    .ucode   = 0x8008080000ull,
    .uflags  = INTEL_X86_NCOMBO,
  },
  { .uname   = "STREAMING_WR_L3_MISS",
    .udesc   = "Counts streaming stores that missed the local socket's L1, L2, and L3 caches.",
    .ucode   = 0x9400080000ull,
    .uflags  = INTEL_X86_NCOMBO,
  },
  { .uname   = "STREAMING_WR_L3_MISS_LOCAL",
    .udesc   = "Counts streaming stores that were not supplied by the local socket's L1, L2, or L3 caches and the cacheline is homed locally.",
    .ucode   = 0x8400080000ull,
    .uflags  = INTEL_X86_NCOMBO,
  },
  { .uname   = "WRITE_ESTIMATE_MEMORY",
    .udesc   = "Counts Demand RFOs, ItoM's, PREFECTHW's, Hardware RFO Prefetches to the L1/L2 and Streaming stores that likely resulted in a store to Memory (DRAM or PMM)",
    .ucode   = 0xfbff8082200ull,
    .uflags  = INTEL_X86_NCOMBO,
  },
};



static const intel_x86_umask_t intel_spr_int_vec_retired[]={
  { .uname   = "128BIT",
    .udesc   = "TBD",
    .ucode   = 0x1300ull,
    .uflags  = INTEL_X86_NCOMBO,
  },
  { .uname   = "256BIT",
    .udesc   = "TBD",
    .ucode   = 0xac00ull,
    .uflags  = INTEL_X86_NCOMBO,
  },
  { .uname   = "ADD_128",
    .udesc   = "integer ADD, SUB, SAD 128-bit vector instructions.",
    .ucode   = 0x0300ull,
    .uflags  = INTEL_X86_NCOMBO,
  },
  { .uname   = "ADD_256",
    .udesc   = "integer ADD, SUB, SAD 256-bit vector instructions.",
    .ucode   = 0x0c00ull,
    .uflags  = INTEL_X86_NCOMBO,
  },
  { .uname   = "MUL_256",
    .udesc   = "TBD",
    .ucode   = 0x8000ull,
    .uflags  = INTEL_X86_NCOMBO,
  },
  { .uname   = "SHUFFLES",
    .udesc   = "TBD",
    .ucode   = 0x4000ull,
    .uflags  = INTEL_X86_NCOMBO,
  },
  { .uname   = "VNNI_128",
    .udesc   = "TBD",
    .ucode   = 0x1000ull,
    .uflags  = INTEL_X86_NCOMBO,
  },
  { .uname   = "VNNI_256",
    .udesc   = "TBD",
    .ucode   = 0x2000ull,
    .uflags  = INTEL_X86_NCOMBO,
  },
};

static const intel_x86_umask_t intel_spr_mem_uop_retired[]={
  { .uname   = "ANY",
    .udesc   = "Retired memory uops for any access",
    .ucode   = 0x0300ull,
    .uflags  = INTEL_X86_DFL,
  },
};

static const intel_x86_umask_t intel_spr_misc2_retired[]={
  { .uname   = "LFENCE",
    .udesc   = "TBD",
    .ucode   = 0x2000ull,
    .uflags  = INTEL_X86_DFL,
  },
};

static const intel_x86_umask_t intel_spr_mem_load_misc_retired[]={
  { .uname   = "UC",
    .udesc   = "Retired instructions with at least 1 uncacheable load or lock.",
    .ucode   = 0x0400ull,
    .uflags  = INTEL_X86_PEBS | INTEL_X86_DFL,
  },
};

static const intel_x86_umask_t intel_spr_mem_load_l3_miss_retired[]={
  { .uname   = "LOCAL_DRAM",
    .udesc   = "Retired load instructions which data sources missed L3 but serviced from local dram",
    .ucode   = 0x0100ull,
    .uflags  = INTEL_X86_NCOMBO,
  },
  { .uname   = "REMOTE_DRAM",
    .udesc   = "TBD",
    .ucode   = 0x0200ull,
    .uflags  = INTEL_X86_NCOMBO,
  },
  { .uname   = "REMOTE_FWD",
    .udesc   = "Retired load instructions whose data sources was forwarded from a remote cache",
    .ucode   = 0x0800ull,
    .uflags  = INTEL_X86_NCOMBO,
  },
  { .uname   = "REMOTE_HITM",
    .udesc   = "TBD",
    .ucode   = 0x0400ull,
    .uflags  = INTEL_X86_NCOMBO,
  },
  { .uname   = "REMOTE_PMM",
    .udesc   = "Retired load instructions with remote Intel Optane DC persistent memory as the data source where the data request missed all caches.",
    .ucode   = 0x1000ull,
    .uflags  = INTEL_X86_NCOMBO,
  },
};

static const intel_x86_umask_t intel_spr_mem_load_l3_hit_retired[]={
  { .uname   = "XSNP_FWD",
    .udesc   = "Retired load instructions whose data sources were HitM responses from shared L3",
    .ucode   = 0x0400ull,
    .uflags  = INTEL_X86_NCOMBO | INTEL_X86_PEBS,
  },
  { .uname   = "XSNP_MISS",
    .udesc   = "Retired load instructions whose data sources were L3 hit and cross-core snoop missed in on-pkg core cache.",
    .ucode   = 0x0100ull,
    .uflags  = INTEL_X86_NCOMBO | INTEL_X86_PEBS,
  },
  { .uname   = "XSNP_NONE",
    .udesc   = "Retired load instructions whose data sources were hits in L3 without snoops required",
    .ucode   = 0x0800ull,
    .uflags  = INTEL_X86_NCOMBO | INTEL_X86_PEBS,
  },
  { .uname   = "XSNP_NO_FWD",
    .udesc   = "Retired load instructions whose data sources were L3 and cross-core snoop hits in on-pkg core cache",
    .ucode   = 0x0200ull,
    .uflags  = INTEL_X86_NCOMBO | INTEL_X86_PEBS,
  },
};

static const intel_x86_umask_t intel_spr_mem_load_retired[]={
  { .uname   = "FB_HIT",
    .udesc   = "Number of completed demand load requests that missed the L1, but hit the FB(fill buffer), because a preceding miss to the same cacheline initiated the line to be brought into L1, but data is not yet ready in L1.",
    .ucode   = 0x4000ull,
    .uflags  = INTEL_X86_NCOMBO | INTEL_X86_PEBS,
  },
  { .uname   = "L1_HIT",
    .udesc   = "Retired load instructions with L1 cache hits as data sources",
    .ucode   = 0x0100ull,
    .uflags  = INTEL_X86_NCOMBO | INTEL_X86_PEBS,
  },
  { .uname   = "L1_MISS",
    .udesc   = "Retired load instructions missed L1 cache as data sources",
    .ucode   = 0x0800ull,
    .uflags  = INTEL_X86_NCOMBO | INTEL_X86_PEBS,
  },
  { .uname   = "L2_HIT",
    .udesc   = "Retired load instructions with L2 cache hits as data sources",
    .ucode   = 0x0200ull,
    .uflags  = INTEL_X86_NCOMBO | INTEL_X86_PEBS,
  },
  { .uname   = "L2_MISS",
    .udesc   = "Retired load instructions missed L2 cache as data sources",
    .ucode   = 0x1000ull,
    .uflags  = INTEL_X86_NCOMBO | INTEL_X86_PEBS,
  },
  { .uname   = "L3_HIT",
    .udesc   = "Retired load instructions with L3 cache hits as data sources",
    .ucode   = 0x0400ull,
    .uflags  = INTEL_X86_NCOMBO | INTEL_X86_PEBS,
  },
  { .uname   = "L3_MISS",
    .udesc   = "Retired load instructions missed L3 cache as data sources",
    .ucode   = 0x2000ull,
    .uflags  = INTEL_X86_NCOMBO | INTEL_X86_PEBS,
  },
  { .uname   = "LOCAL_PMM",
    .udesc   = "Retired load instructions with local Intel Optane DC persistent memory as the data source where the data request missed all caches.",
    .ucode   = 0x8000ull,
    .uflags  = INTEL_X86_NCOMBO,
  },
};

static const intel_x86_umask_t intel_spr_mem_inst_retired[]={
  { .uname   = "ALL_LOADS",
    .udesc   = "All retired load instructions.",
    .ucode   = 0x8100ull,
    .uflags  = INTEL_X86_NCOMBO | INTEL_X86_PEBS,
  },
  { .uname   = "ALL_STORES",
    .udesc   = "All retired store instructions.",
    .ucode   = 0x8200ull,
    .uflags  = INTEL_X86_NCOMBO | INTEL_X86_PEBS,
  },
  { .uname   = "ANY",
    .udesc   = "All retired memory instructions.",
    .ucode   = 0x8300ull,
    .uflags  = INTEL_X86_NCOMBO | INTEL_X86_PEBS |INTEL_X86_DFL,
  },
  { .uname   = "LOCK_LOADS",
    .udesc   = "Retired load instructions with locked access.",
    .ucode   = 0x2100ull,
    .uflags  = INTEL_X86_NCOMBO | INTEL_X86_PEBS,
  },
  { .uname   = "SPLIT_LOADS",
    .udesc   = "Retired load instructions that split across a cacheline boundary.",
    .ucode   = 0x4100ull,
    .uflags  = INTEL_X86_NCOMBO | INTEL_X86_PEBS,
  },
  { .uname   = "SPLIT_STORES",
    .udesc   = "Retired store instructions that split across a cacheline boundary.",
    .ucode   = 0x4200ull,
    .uflags  = INTEL_X86_NCOMBO | INTEL_X86_PEBS,
  },
  { .uname   = "STLB_MISS_LOADS",
    .udesc   = "Retired load instructions that miss the STLB.",
    .ucode   = 0x1100ull,
    .uflags  = INTEL_X86_NCOMBO | INTEL_X86_PEBS,
  },
  { .uname   = "STLB_MISS_STORES",
    .udesc   = "Retired store instructions that miss the STLB.",
    .ucode   = 0x1200ull,
    .uflags  = INTEL_X86_NCOMBO | INTEL_X86_PEBS,
  },
};

static const intel_x86_umask_t intel_spr_fp_arith_inst_retired2[]={
  { .uname   = "128B_PACKED_HALF",
    .udesc   = "TBD",
    .ucode   = 0x0400ull,
    .uflags  = INTEL_X86_NCOMBO,
  },
  { .uname   = "256B_PACKED_HALF",
    .udesc   = "TBD",
    .ucode   = 0x0800ull,
    .uflags  = INTEL_X86_NCOMBO,
  },
  { .uname   = "512B_PACKED_HALF",
    .udesc   = "TBD",
    .ucode   = 0x1000ull,
    .uflags  = INTEL_X86_NCOMBO,
  },
  { .uname   = "COMPLEX_SCALAR_HALF",
    .udesc   = "TBD",
    .ucode   = 0x0200ull,
    .uflags  = INTEL_X86_NCOMBO,
  },
  { .uname   = "SCALAR",
    .udesc   = "Number of all Scalar Half-Precision FP arithmetic instructions(1) retired - regular and complex.",
    .ucode   = 0x0300ull,
    .uflags  = INTEL_X86_NCOMBO,
  },
  { .uname   = "SCALAR_HALF",
    .udesc   = "TBD",
    .ucode   = 0x0100ull,
    .uflags  = INTEL_X86_NCOMBO,
  },
  { .uname   = "VECTOR",
    .udesc   = "Number of all Vector (also called packed) Half-Precision FP arithmetic instructions(1) retired.",
    .ucode   = 0x1c00ull,
    .uflags  = INTEL_X86_NCOMBO,
  },
};

static const intel_x86_umask_t intel_spr_mem_trans_retired[]={
  { .uname  = "LOAD_LATENCY",
    .udesc  = "Memory load instructions retired above programmed clocks, minimum threshold value is 3 (Precise Event and ldlat required)",
    .ucode  = 0x100,
    .uflags = INTEL_X86_NCOMBO | INTEL_X86_PEBS | INTEL_X86_LDLAT,
  },
  { .uname   = "STORE_SAMPLE",
    .udesc   = "Retired instructions with at least 1 store uop. This PEBS event is the trigger for stores sampled by the PEBS Store Facility.",
    .ucode   = 0x0200ull,
    .uflags  = INTEL_X86_NCOMBO | INTEL_X86_PEBS,
  },
};

static const intel_x86_umask_t intel_spr_misc_retired[]={
  { .uname   = "LBR_INSERTS",
    .udesc   = "Increments whenever there is an update to the LBR array.",
    .ucode   = 0x2000ull,
    .uflags  = INTEL_X86_DFL,
  },
};

static const intel_x86_umask_t intel_spr_rtm_retired[]={
  { .uname   = "ABORTED",
    .udesc   = "Number of times an RTM execution aborted.",
    .ucode   = 0x0400ull,
    .uflags  = INTEL_X86_NCOMBO,
  },
  { .uname   = "ABORTED_EVENTS",
    .udesc   = "Number of times an RTM execution aborted due to none of the previous 4 categories (e.g. interrupt)",
    .ucode   = 0x8000ull,
    .uflags  = INTEL_X86_NCOMBO,
  },
  { .uname   = "ABORTED_MEM",
    .udesc   = "Number of times an RTM execution aborted due to various memory events (e.g. read/write capacity and conflicts)",
    .ucode   = 0x0800ull,
    .uflags  = INTEL_X86_NCOMBO,
  },
  { .uname   = "ABORTED_MEMTYPE",
    .udesc   = "Number of times an RTM execution aborted due to incompatible memory type",
    .ucode   = 0x4000ull,
    .uflags  = INTEL_X86_NCOMBO,
  },
  { .uname   = "ABORTED_UNFRIENDLY",
    .udesc   = "Number of times an RTM execution aborted due to HLE-unfriendly instructions",
    .ucode   = 0x2000ull,
    .uflags  = INTEL_X86_NCOMBO,
  },
  { .uname   = "COMMIT",
    .udesc   = "Number of times an RTM execution successfully committed",
    .ucode   = 0x0200ull,
    .uflags  = INTEL_X86_NCOMBO,
  },
  { .uname   = "START",
    .udesc   = "Number of times an RTM execution started.",
    .ucode   = 0x0100ull,
    .uflags  = INTEL_X86_NCOMBO,
  },
};

static const intel_x86_umask_t intel_spr_fp_arith_inst_retired[]={
  { .uname   = "128B_PACKED_DOUBLE",
    .udesc   = "Counts number of SSE/AVX computational 128-bit packed double precision floating-point instructions retired; some instructions will count twice as noted below.  Each count represents 2 computation operations, one for each element.  Applies to SSE* and AVX* packed double precision floating-point instructions: ADD SUB HADD HSUB SUBADD MUL DIV MIN MAX SQRT DPP FM(N)ADD/SUB.  DPP and FM(N)ADD/SUB instructions count twice as they perform 2 calculations per element.",
    .ucode   = 0x0400ull,
    .uflags  = INTEL_X86_NCOMBO,
  },
  { .uname   = "128B_PACKED_SINGLE",
    .udesc   = "Number of SSE/AVX computational 128-bit packed single precision floating-point instructions retired; some instructions will count twice as noted below.  Each count represents 4 computation operations, one for each element.  Applies to SSE* and AVX* packed single precision floating-point instructions: ADD SUB MUL DIV MIN MAX RCP14 RSQRT14 SQRT DPP FM(N)ADD/SUB.  DPP and FM(N)ADD/SUB instructions count twice as they perform 2 calculations per element.",
    .ucode   = 0x0800ull,
    .uflags  = INTEL_X86_NCOMBO,
  },
  { .uname   = "256B_PACKED_DOUBLE",
    .udesc   = "Counts number of SSE/AVX computational 256-bit packed double precision floating-point instructions retired; some instructions will count twice as noted below.  Each count represents 4 computation operations, one for each element.  Applies to SSE* and AVX* packed double precision floating-point instructions: ADD SUB HADD HSUB SUBADD MUL DIV MIN MAX SQRT FM(N)ADD/SUB.  FM(N)ADD/SUB instructions count twice as they perform 2 calculations per element.",
    .ucode   = 0x1000ull,
    .uflags  = INTEL_X86_NCOMBO,
  },
  { .uname   = "256B_PACKED_SINGLE",
    .udesc   = "Counts number of SSE/AVX computational 256-bit packed single precision floating-point instructions retired; some instructions will count twice as noted below.  Each count represents 8 computation operations, one for each element.  Applies to SSE* and AVX* packed single precision floating-point instructions: ADD SUB HADD HSUB SUBADD MUL DIV MIN MAX SQRT RSQRT RCP DPP FM(N)ADD/SUB.  DPP and FM(N)ADD/SUB instructions count twice as they perform 2 calculations per element.",
    .ucode   = 0x2000ull,
    .uflags  = INTEL_X86_NCOMBO,
  },
  { .uname   = "4_FLOPS",
    .udesc   = "Number of SSE/AVX computational 128-bit packed single and 256-bit packed double precision FP instructions retired; some instructions will count twice as noted below.  Each count represents 2 or/and 4 computation operations, 1 for each element.  Applies to SSE* and AVX* packed single precision and packed double precision FP instructions: ADD SUB HADD HSUB SUBADD MUL DIV MIN MAX RCP14 RSQRT14 SQRT DPP FM(N)ADD/SUB.  DPP and FM(N)ADD/SUB count twice as they perform 2 calculations per element.",
    .ucode   = 0x1800ull,
    .uflags  = INTEL_X86_NCOMBO,
  },
  { .uname   = "512B_PACKED_DOUBLE",
    .udesc   = "Counts number of SSE/AVX computational 512-bit packed double precision floating-point instructions retired; some instructions will count twice as noted below.  Each count represents 8 computation operations, one for each element.  Applies to SSE* and AVX* packed double precision floating-point instructions: ADD SUB MUL DIV MIN MAX SQRT RSQRT14 RCP14 FM(N)ADD/SUB. FM(N)ADD/SUB instructions count twice as they perform 2 calculations per element.",
    .ucode   = 0x4000ull,
    .uflags  = INTEL_X86_NCOMBO,
  },
  { .uname   = "512B_PACKED_SINGLE",
    .udesc   = "Counts number of SSE/AVX computational 512-bit packed single precision floating-point instructions retired; some instructions will count twice as noted below.  Each count represents 16 computation operations, one for each element.  Applies to SSE* and AVX* packed single precision floating-point instructions: ADD SUB MUL DIV MIN MAX SQRT RSQRT14 RCP14 FM(N)ADD/SUB. FM(N)ADD/SUB instructions count twice as they perform 2 calculations per element.",
    .ucode   = 0x8000ull,
    .uflags  = INTEL_X86_NCOMBO,
  },
  { .uname   = "8_FLOPS",
    .udesc   = "Number of SSE/AVX computational 256-bit packed single precision and 512-bit packed double precision  FP instructions retired; some instructions will count twice as noted below.  Each count represents 8 computation operations, 1 for each element.  Applies to SSE* and AVX* packed single precision and double precision FP instructions: ADD SUB HADD HSUB SUBADD MUL DIV MIN MAX SQRT RSQRT RSQRT14 RCP RCP14 DPP FM(N)ADD/SUB.  DPP and FM(N)ADD/SUB count twice as they perform 2 calculations per element.",
    .ucode   = 0x6000ull,
    .uflags  = INTEL_X86_NCOMBO,
  },
  { .uname   = "SCALAR",
    .udesc   = "Number of SSE/AVX computational scalar floating-point instructions retired; some instructions will count twice as noted below.  Applies to SSE* and AVX* scalar, double and single precision floating-point: ADD SUB MUL DIV MIN MAX RCP14 RSQRT14 RANGE SQRT DPP FM(N)ADD/SUB.  DPP and FM(N)ADD/SUB instructions count twice as they perform multiple calculations per element.",
    .ucode   = 0x0300ull,
    .uflags  = INTEL_X86_NCOMBO,
  },
  { .uname   = "SCALAR_DOUBLE",
    .udesc   = "Counts number of SSE/AVX computational scalar double precision floating-point instructions retired; some instructions will count twice as noted below.  Each count represents 1 computational operation. Applies to SSE* and AVX* scalar double precision floating-point instructions: ADD SUB MUL DIV MIN MAX SQRT FM(N)ADD/SUB.  FM(N)ADD/SUB instructions count twice as they perform 2 calculations per element.",
    .ucode   = 0x0100ull,
    .uflags  = INTEL_X86_NCOMBO,
  },
  { .uname   = "SCALAR_SINGLE",
    .udesc   = "Counts number of SSE/AVX computational scalar single precision floating-point instructions retired; some instructions will count twice as noted below.  Each count represents 1 computational operation. Applies to SSE* and AVX* scalar single precision floating-point instructions: ADD SUB MUL DIV MIN MAX SQRT RSQRT RCP FM(N)ADD/SUB.  FM(N)ADD/SUB instructions count twice as they perform 2 calculations per element.",
    .ucode   = 0x0200ull,
    .uflags  = INTEL_X86_NCOMBO,
  },
  { .uname   = "VECTOR",
    .udesc   = "Number of any Vector retired FP arithmetic instructions",
    .ucode   = 0xfc00ull,
    .uflags  = INTEL_X86_NCOMBO,
  },
};

static const intel_x86_umask_t intel_spr_frontend_retired[]={
  { .uname   = "ANY_DSB_MISS",
    .udesc   = "Retired Instructions who experienced DSB miss.",
    .ucode   = 0x0100ull,
    .uflags  = INTEL_X86_NCOMBO | INTEL_X86_PEBS,
  },
  { .uname   = "DSB_MISS",
    .udesc   = "Retired Instructions who experienced a critical DSB miss.",
    .ucode   = 0x1100ull,
    .uflags  = INTEL_X86_NCOMBO | INTEL_X86_PEBS,
  },
  { .uname   = "ITLB_MISS",
    .udesc   = "Retired Instructions who experienced iTLB true miss.",
    .ucode   = 0x1400ull,
    .uflags  = INTEL_X86_NCOMBO | INTEL_X86_PEBS,
  },
  { .uname   = "L1I_MISS",
    .udesc   = "Retired Instructions who experienced Instruction L1 Cache true miss.",
    .ucode   = 0x1200ull,
    .uflags  = INTEL_X86_NCOMBO | INTEL_X86_PEBS,
  },
  { .uname   = "L2_MISS",
    .udesc   = "Retired Instructions who experienced Instruction L2 Cache true miss.",
    .ucode   = 0x1300ull,
    .uflags  = INTEL_X86_NCOMBO | INTEL_X86_PEBS,
  },
  { .uname   = "LATENCY_GE_1",
    .udesc   = "Retired instructions after front-end starvation of at least 1 cycle",
    .ucode   = 0x60010600ull,
    .uflags  = INTEL_X86_NCOMBO | INTEL_X86_FETHR | INTEL_X86_PEBS,
    .modhw   = _INTEL_X86_ATTR_FETHR,
  },
  { .uname   = "LATENCY_GE_128",
    .udesc   = "Retired instructions that are fetched after an interval where the front-end delivered no uops for a period of 128 cycles which was not interrupted by a back-end stall.",
    .ucode   = 0x60800600ull,
    .uflags  = INTEL_X86_NCOMBO | INTEL_X86_FETHR | INTEL_X86_PEBS,
    .modhw   = _INTEL_X86_ATTR_FETHR,
  },
  { .uname   = "LATENCY_GE_16",
    .udesc   = "Retired instructions that are fetched after an interval where the front-end delivered no uops for a period of 16 cycles which was not interrupted by a back-end stall.",
    .ucode   = 0x60100600ull,
    .uflags  = INTEL_X86_NCOMBO | INTEL_X86_FETHR | INTEL_X86_PEBS,
    .modhw   = _INTEL_X86_ATTR_FETHR,
  },
  { .uname   = "LATENCY_GE_2",
    .udesc   = "Retired instructions after front-end starvation of at least 2 cycles",
    .ucode   = 0x60020600ull,
    .uflags  = INTEL_X86_NCOMBO | INTEL_X86_FETHR | INTEL_X86_PEBS,
    .modhw   = _INTEL_X86_ATTR_FETHR,
  },
  { .uname   = "LATENCY_GE_256",
    .udesc   = "Retired instructions that are fetched after an interval where the front-end delivered no uops for a period of 256 cycles which was not interrupted by a back-end stall.",
    .ucode   = 0x61000600ull,
    .uflags  = INTEL_X86_NCOMBO | INTEL_X86_FETHR | INTEL_X86_PEBS,
    .modhw   = _INTEL_X86_ATTR_FETHR,
  },
  { .uname   = "LATENCY_GE_2_BUBBLES_GE_1",
    .udesc   = "Retired instructions that are fetched after an interval where the front-end had at least 1 bubble-slot for a period of 2 cycles which was not interrupted by a back-end stall.",
    .ucode   = 0x10020600ull,
    .uflags  = INTEL_X86_NCOMBO | INTEL_X86_FETHR | INTEL_X86_PEBS,
    .modhw   = _INTEL_X86_ATTR_FETHR,
  },
  { .uname   = "LATENCY_GE_32",
    .udesc   = "Retired instructions that are fetched after an interval where the front-end delivered no uops for a period of 32 cycles which was not interrupted by a back-end stall.",
    .ucode   = 0x60200600ull,
    .uflags  = INTEL_X86_NCOMBO | INTEL_X86_FETHR | INTEL_X86_PEBS,
    .modhw   = _INTEL_X86_ATTR_FETHR,
  },
  { .uname   = "LATENCY_GE_4",
    .udesc   = "Retired instructions that are fetched after an interval where the front-end delivered no uops for a period of 4 cycles which was not interrupted by a back-end stall.",
    .ucode   = 0x60040600ull,
    .uflags  = INTEL_X86_NCOMBO | INTEL_X86_FETHR | INTEL_X86_PEBS,
    .modhw   = _INTEL_X86_ATTR_FETHR,
  },
  { .uname   = "LATENCY_GE_512",
    .udesc   = "Retired instructions that are fetched after an interval where the front-end delivered no uops for a period of 512 cycles which was not interrupted by a back-end stall.",
    .ucode   = 0x62000600ull,
    .uflags  = INTEL_X86_NCOMBO | INTEL_X86_FETHR | INTEL_X86_PEBS,
    .modhw   = _INTEL_X86_ATTR_FETHR,
  },
  { .uname   = "LATENCY_GE_64",
    .udesc   = "Retired instructions that are fetched after an interval where the front-end delivered no uops for a period of 64 cycles which was not interrupted by a back-end stall.",
    .ucode   = 0x60400600ull,
    .uflags  = INTEL_X86_NCOMBO | INTEL_X86_FETHR | INTEL_X86_PEBS,
    .modhw   = _INTEL_X86_ATTR_FETHR,
  },
  { .uname   = "LATENCY_GE_8",
    .udesc   = "Retired instructions that are fetched after an interval where the front-end delivered no uops for a period of 8 cycles which was not interrupted by a back-end stall.",
    .ucode   = 0x60080600ull,
    .uflags  = INTEL_X86_NCOMBO | INTEL_X86_FETHR | INTEL_X86_PEBS,
    .modhw   = _INTEL_X86_ATTR_FETHR,
  },
  { .uname   = "MS_FLOWS",
    .udesc   = "TBD",
    .ucode   = 0x0800ull,
    .uflags  = INTEL_X86_NCOMBO | INTEL_X86_PEBS,
  },
  { .uname   = "STLB_MISS",
    .udesc   = "Retired Instructions who experienced STLB (2nd level TLB) true miss.",
    .ucode   = 0x1500ull,
    .uflags  = INTEL_X86_NCOMBO | INTEL_X86_PEBS,
  },
  { .uname   = "UNKNOWN_BRANCH",
    .udesc   = "TBD",
    .ucode   = 0x1700ull,
    .uflags  = INTEL_X86_NCOMBO | INTEL_X86_PEBS,
  },
};

static const intel_x86_umask_t intel_spr_br_misp_retired[]={
  { .uname   = "ALL_BRANCHES",
    .udesc   = "All mispredicted branch instructions retired.",
    .ucode   = 0x0000ull,
    .uflags  = INTEL_X86_NCOMBO | INTEL_X86_PEBS | INTEL_X86_DFL,
  },
  { .uname   = "COND",
    .udesc   = "Mispredicted conditional branch instructions retired.",
    .ucode   = 0x1100ull,
    .uflags  = INTEL_X86_NCOMBO | INTEL_X86_PEBS,
  },
  { .uname   = "COND_NTAKEN",
    .udesc   = "Mispredicted non-taken conditional branch instructions retired.",
    .ucode   = 0x1000ull,
    .uflags  = INTEL_X86_NCOMBO | INTEL_X86_PEBS,
  },
  { .uname   = "COND_TAKEN",
    .udesc   = "Number of branch instructions retired that were mispredicted and taken.",
    .ucode   = 0x0100ull,
    .uflags  = INTEL_X86_NCOMBO | INTEL_X86_PEBS,
  },
  { .uname   = "INDIRECT",
    .udesc   = "Miss-predicted near indirect branch instructions retired (excluding returns)",
    .ucode   = 0x8000ull,
    .uflags  = INTEL_X86_NCOMBO | INTEL_X86_PEBS,
  },
  { .uname   = "INDIRECT_CALL",
    .udesc   = "Mispredicted indirect CALL retired.",
    .ucode   = 0x0200ull,
    .uflags  = INTEL_X86_NCOMBO | INTEL_X86_PEBS,
  },
  { .uname   = "NEAR_TAKEN",
    .udesc   = "Number of near branch instructions retired that were mispredicted and taken.",
    .ucode   = 0x2000ull,
    .uflags  = INTEL_X86_NCOMBO | INTEL_X86_PEBS,
  },
  { .uname   = "RET",
    .udesc   = "This event counts the number of mispredicted ret instructions retired. Non PEBS",
    .ucode   = 0x0800ull,
    .uflags  = INTEL_X86_NCOMBO | INTEL_X86_PEBS,
  },
};

static const intel_x86_umask_t intel_spr_br_inst_retired[]={
  { .uname   = "ALL_BRANCHES",
    .udesc   = "All branch instructions retired.",
    .ucode   = 0x0000ull,
    .uflags  = INTEL_X86_NCOMBO | INTEL_X86_PEBS | INTEL_X86_DFL,
  },
  { .uname   = "COND",
    .udesc   = "Conditional branch instructions retired.",
    .ucode   = 0x1100ull,
    .uflags  = INTEL_X86_NCOMBO | INTEL_X86_PEBS,
  },
  { .uname   = "COND_NTAKEN",
    .udesc   = "Not taken branch instructions retired.",
    .ucode   = 0x1000ull,
    .uflags  = INTEL_X86_NCOMBO | INTEL_X86_PEBS,
  },
  { .uname   = "COND_TAKEN",
    .udesc   = "Taken conditional branch instructions retired.",
    .ucode   = 0x0100ull,
    .uflags  = INTEL_X86_NCOMBO | INTEL_X86_PEBS,
  },
  { .uname   = "FAR_BRANCH",
    .udesc   = "Far branch instructions retired.",
    .ucode   = 0x4000ull,
    .uflags  = INTEL_X86_NCOMBO | INTEL_X86_PEBS,
  },
  { .uname   = "INDIRECT",
    .udesc   = "Indirect near branch instructions retired (excluding returns)",
    .ucode   = 0x8000ull,
    .uflags  = INTEL_X86_NCOMBO | INTEL_X86_PEBS,
  },
  { .uname   = "NEAR_CALL",
    .udesc   = "Direct and indirect near call instructions retired.",
    .ucode   = 0x0200ull,
    .uflags  = INTEL_X86_NCOMBO | INTEL_X86_PEBS,
  },
  { .uname   = "NEAR_RETURN",
    .udesc   = "Return instructions retired.",
    .ucode   = 0x0800ull,
    .uflags  = INTEL_X86_NCOMBO | INTEL_X86_PEBS,
  },
  { .uname   = "NEAR_TAKEN",
    .udesc   = "Taken branch instructions retired.",
    .ucode   = 0x2000ull,
    .uflags  = INTEL_X86_NCOMBO | INTEL_X86_PEBS,
  },
};

static const intel_x86_umask_t intel_spr_machine_clears[]={
  { .uname   = "COUNT",
    .udesc   = "Number of machine clears (nukes) of any type.",
    .ucode   = 0x0100ull | (0x1 << INTEL_X86_CMASK_BIT) | (0x1 << INTEL_X86_EDGE_BIT),
    .uflags  = INTEL_X86_NCOMBO,
    .modhw   = _INTEL_X86_ATTR_C | _INTEL_X86_ATTR_E,
  },
  { .uname   = "MEMORY_ORDERING",
    .udesc   = "Number of machine clears due to memory ordering conflicts.",
    .ucode   = 0x0200ull,
    .uflags  = INTEL_X86_NCOMBO,
  },
  { .uname   = "SMC",
    .udesc   = "Self-modifying code (SMC) detected.",
    .ucode   = 0x0400ull,
    .uflags  = INTEL_X86_NCOMBO,
  },
};

static const intel_x86_umask_t intel_spr_uops_retired[]={
  { .uname   = "CYCLES",
    .udesc   = "Cycles with retired uop(s).",
    .ucode   = 0x0200ull | (0x1 << INTEL_X86_CMASK_BIT),
    .uflags  = INTEL_X86_NCOMBO,
    .modhw   = _INTEL_X86_ATTR_C,
  },
  { .uname   = "HEAVY",
    .udesc   = "TBD",
    .ucode   = 0x0100ull,
    .uflags  = INTEL_X86_NCOMBO,
  },
  { .uname   = "MS",
    .udesc   = "TBD",
    .ucode   = 0x0800ull,
    .uflags  = INTEL_X86_NCOMBO,
  },
  { .uname   = "SLOTS",
    .udesc   = "Retirement slots used.",
    .ucode   = 0x0200ull,
    .uflags  = INTEL_X86_NCOMBO,
  },
  { .uname   = "STALLS",
    .udesc   = "Cycles without actually retired uops.",
    .ucode   = 0x0200ull | (0x1 << INTEL_X86_INV_BIT) | (0x1 << INTEL_X86_CMASK_BIT),
    .uflags  = INTEL_X86_NCOMBO,
    .modhw   = _INTEL_X86_ATTR_I | _INTEL_X86_ATTR_C,
  },
  { .uname   = "STALL_CYCLES",
    .uequiv  = "STALLS",
    .udesc   = "Cycles without actually retired uops.",
    .ucode   = 0x0200ull | (0x1 << INTEL_X86_INV_BIT) | (0x1 << INTEL_X86_CMASK_BIT),
    .uflags  = INTEL_X86_NCOMBO,
    .modhw   = _INTEL_X86_ATTR_I | _INTEL_X86_ATTR_C,
  },
};

static const intel_x86_umask_t intel_spr_assists[]={
  { .uname   = "ANY",
    .udesc   = "Number of occurrences where a microcode assist is invoked by hardware.",
    .ucode   = 0x1b00ull,
    .uflags  = INTEL_X86_NCOMBO,
  },
  { .uname   = "FP",
    .udesc   = "Counts all microcode FP assists.",
    .ucode   = 0x0200ull,
    .uflags  = INTEL_X86_NCOMBO,
  },
  { .uname   = "PAGE_FAULT",
    .udesc   = "TBD",
    .ucode   = 0x0800ull,
    .uflags  = INTEL_X86_NCOMBO,
  },
  { .uname   = "SSE_AVX_MIX",
    .udesc   = "TBD",
    .ucode   = 0x1000ull,
    .uflags  = INTEL_X86_NCOMBO,
  },
};

static const intel_x86_umask_t intel_spr_exe[]={
  { .uname   = "AMX_BUSY",
    .udesc   = "Counts the cycles where the AMX (Advance Matrix Extension) unit is busy performing an operation.",
    .ucode   = 0x0200ull,
    .uflags  = INTEL_X86_DFL,
  },
};

static const intel_x86_umask_t intel_spr_fp_arith_dispatched[]={
  { .uname   = "PORT_0",
    .udesc   = "TBD",
    .ucode   = 0x0100ull,
    .uflags  = INTEL_X86_NCOMBO,
  },
  { .uname   = "PORT_1",
    .udesc   = "TBD",
    .ucode   = 0x0200ull,
    .uflags  = INTEL_X86_NCOMBO,
  },
  { .uname   = "PORT_5",
    .udesc   = "TBD",
    .ucode   = 0x0400ull,
    .uflags  = INTEL_X86_NCOMBO,
  },
};

static const intel_x86_umask_t intel_spr_uops_dispatched[]={
  { .uname   = "PORT_0",
    .udesc   = "Uops executed on port 0",
    .ucode   = 0x0100ull,
    .uflags  = INTEL_X86_NCOMBO,
  },
  { .uname   = "PORT_1",
    .udesc   = "Uops executed on port 1",
    .ucode   = 0x0200ull,
    .uflags  = INTEL_X86_NCOMBO,
  },
  { .uname   = "PORT_2_3_10",
    .udesc   = "Uops executed on ports 2, 3 and 10",
    .ucode   = 0x0400ull,
    .uflags  = INTEL_X86_NCOMBO,
  },
  { .uname   = "PORT_4_9",
    .udesc   = "Uops executed on ports 4 and 9",
    .ucode   = 0x1000ull,
    .uflags  = INTEL_X86_NCOMBO,
  },
  { .uname   = "PORT_5_11",
    .udesc   = "Uops executed on ports 5 and 11",
    .ucode   = 0x2000ull,
    .uflags  = INTEL_X86_NCOMBO,
  },
  { .uname   = "PORT_6",
    .udesc   = "Uops executed on port 6",
    .ucode   = 0x4000ull,
    .uflags  = INTEL_X86_NCOMBO,
  },
  { .uname   = "PORT_7_8",
    .udesc   = "Uops executed on ports 7 and 8",
    .ucode   = 0x8000ull,
    .uflags  = INTEL_X86_NCOMBO,
  },
};

static const intel_x86_umask_t intel_spr_uops_executed[]={
  { .uname   = "CORE",
    .udesc   = "Number of uops executed on the core.",
    .ucode   = 0x0200ull,
    .uflags  = INTEL_X86_NCOMBO,
  },
  { .uname   = "CORE_CYCLES_GE_1",
    .udesc   = "Cycles at least 1 micro-op is executed from any thread on physical core.",
    .ucode   = 0x0200ull | (0x1 << INTEL_X86_CMASK_BIT),
    .uflags  = INTEL_X86_NCOMBO,
    .modhw   = _INTEL_X86_ATTR_C,
  },
  { .uname   = "CORE_CYCLES_GE_2",
    .udesc   = "Cycles at least 2 micro-op is executed from any thread on physical core.",
    .ucode   = 0x0200ull | (0x2 << INTEL_X86_CMASK_BIT),
    .uflags  = INTEL_X86_NCOMBO,
    .modhw   = _INTEL_X86_ATTR_C,
  },
  { .uname   = "CORE_CYCLES_GE_3",
    .udesc   = "Cycles at least 3 micro-op is executed from any thread on physical core.",
    .ucode   = 0x0200ull | (0x3 << INTEL_X86_CMASK_BIT),
    .uflags  = INTEL_X86_NCOMBO,
    .modhw   = _INTEL_X86_ATTR_C,
  },
  { .uname   = "CORE_CYCLES_GE_4",
    .udesc   = "Cycles at least 4 micro-op is executed from any thread on physical core.",
    .ucode   = 0x0200ull | (0x4 << INTEL_X86_CMASK_BIT),
    .uflags  = INTEL_X86_NCOMBO,
    .modhw   = _INTEL_X86_ATTR_C,
  },
  { .uname   = "CYCLES_GE_1",
    .udesc   = "Cycles where at least 1 uop was executed per-thread",
    .ucode   = 0x0100ull | (0x1 << INTEL_X86_CMASK_BIT),
    .uflags  = INTEL_X86_NCOMBO,
    .modhw   = _INTEL_X86_ATTR_C,
  },
  { .uname   = "CYCLES_GE_2",
    .udesc   = "Cycles where at least 2 uops were executed per-thread",
    .ucode   = 0x0100ull | (0x2 << INTEL_X86_CMASK_BIT),
    .uflags  = INTEL_X86_NCOMBO,
    .modhw   = _INTEL_X86_ATTR_C,
  },
  { .uname   = "CYCLES_GE_3",
    .udesc   = "Cycles where at least 3 uops were executed per-thread",
    .ucode   = 0x0100ull | (0x3 << INTEL_X86_CMASK_BIT),
    .uflags  = INTEL_X86_NCOMBO,
    .modhw   = _INTEL_X86_ATTR_C,
  },
  { .uname   = "CYCLES_GE_4",
    .udesc   = "Cycles where at least 4 uops were executed per-thread",
    .ucode   = 0x0100ull | (0x4 << INTEL_X86_CMASK_BIT),
    .uflags  = INTEL_X86_NCOMBO,
    .modhw   = _INTEL_X86_ATTR_C,
  },
  { .uname   = "STALLS",
    .udesc   = "Counts number of cycles no uops were dispatched to be executed on this thread.",
    .ucode   = 0x0100ull | (0x1 << INTEL_X86_INV_BIT) | (0x1 << INTEL_X86_CMASK_BIT),
    .uflags  = INTEL_X86_NCOMBO,
    .modhw   = _INTEL_X86_ATTR_I | _INTEL_X86_ATTR_C,
  },
  { .uname   = "STALL_CYCLES",
    .uequiv  = "STALLS",
    .udesc   = "Counts number of cycles no uops were dispatched to be executed on this thread.",
    .ucode   = 0x0100ull | (0x1 << INTEL_X86_INV_BIT) | (0x1 << INTEL_X86_CMASK_BIT),
    .uflags  = INTEL_X86_NCOMBO,
    .modhw   = _INTEL_X86_ATTR_I | _INTEL_X86_ATTR_C,
  },
  { .uname   = "THREAD",
    .udesc   = "Counts the number of uops to be executed per-thread each cycle.",
    .ucode   = 0x0100ull,
    .uflags  = INTEL_X86_NCOMBO,
  },
  { .uname   = "X87",
    .udesc   = "Counts the number of x87 uops dispatched.",
    .ucode   = 0x1000ull,
    .uflags  = INTEL_X86_NCOMBO,
  },
};

static const intel_x86_umask_t intel_spr_arith[]={
  { .uname   = "DIVIDER_ACTIVE",
    .uequiv  = "DIV_ACTIVE",
    .udesc   = "Cycles when divide unit is busy executing divide or square root operations.",
    .ucode   = 0x0900ull | (0x1 << INTEL_X86_CMASK_BIT),
    .uflags  = INTEL_X86_NCOMBO,
    .modhw   = _INTEL_X86_ATTR_C,
  },
  { .uname   = "DIV_ACTIVE",
    .udesc   = "Cycles when divide unit is busy executing divide or square root operations.",
    .ucode   = 0x0900ull | (0x1 << INTEL_X86_CMASK_BIT),
    .uflags  = INTEL_X86_NCOMBO,
    .modhw   = _INTEL_X86_ATTR_C,
  },
  { .uname   = "FPDIV_ACTIVE",
    .udesc   = "TBD",
    .ucode   = 0x0100ull | (0x1 << INTEL_X86_CMASK_BIT),
    .uflags  = INTEL_X86_NCOMBO,
    .modhw   = _INTEL_X86_ATTR_C,
  },
  { .uname   = "FP_DIVIDER_ACTIVE",
    .uequiv  = "FPDIV_ACTIVE",
    .udesc   = "TBD",
    .ucode   = 0x0100ull | (0x1 << INTEL_X86_CMASK_BIT),
    .uflags  = INTEL_X86_NCOMBO,
    .modhw   = _INTEL_X86_ATTR_C,
  },
  { .uname   = "IDIV_ACTIVE",
    .udesc   = "This event counts the cycles the integer divider is busy.",
    .ucode   = 0x0800ull,
    .uflags  = INTEL_X86_NCOMBO,
  },
  { .uname   = "INT_DIVIDER_ACTIVE",
    .uequiv  = "IDIV_ACTIVE",
    .udesc   = "This event counts the cycles the integer divider is busy.",
    .ucode   = 0x0800ull,
    .uflags  = INTEL_X86_NCOMBO,
  },
};

static const intel_x86_umask_t intel_spr_uops_issued[]={
  { .uname   = "ANY",
    .udesc   = "Uops that RAT issues to RS",
    .ucode   = 0x0100ull,
    .uflags  = INTEL_X86_DFL,
  },
};

static const intel_x86_umask_t intel_spr_int_misc[]={
  { .uname   = "CLEARS_COUNT",
    .udesc   = "Clears speculative count",
    .ucode   = 0x0100ull | (0x1 << INTEL_X86_CMASK_BIT) | (0x1 << INTEL_X86_EDGE_BIT),
    .uflags  = INTEL_X86_NCOMBO,
    .modhw   = _INTEL_X86_ATTR_C | _INTEL_X86_ATTR_E,
  },
  { .uname   = "CLEAR_RESTEER_CYCLES",
    .udesc   = "Counts cycles after recovery from a branch misprediction or machine clear till the first uop is issued from the resteered path.",
    .ucode   = 0x8000ull,
    .uflags  = INTEL_X86_NCOMBO,
  },
  { .uname   = "MBA_STALLS",
    .udesc   = "TBD",
    .ucode   = 0x2000ull,
    .uflags  = INTEL_X86_NCOMBO,
  },
  { .uname   = "RECOVERY_CYCLES",
    .udesc   = "Core cycles the allocator was stalled due to recovery from earlier clear event for this thread",
    .ucode   = 0x0100ull,
    .uflags  = INTEL_X86_NCOMBO,
  },
  { .uname   = "UNKNOWN_BRANCH_CYCLES",
    .udesc   = "TBD",
    .ucode   = 0x0700ull,
    .uflags  = INTEL_X86_NCOMBO,
  },
  { .uname   = "UOP_DROPPING",
    .udesc   = "TMA slots where uops got dropped",
    .ucode   = 0x1000ull,
    .uflags  = INTEL_X86_NCOMBO,
  },
};

static const intel_x86_umask_t intel_spr_lsd[]={
  { .uname   = "CYCLES_ACTIVE",
    .udesc   = "Cycles Uops delivered by the LSD, but didn't come from the decoder.",
    .ucode   = 0x0100ull | (0x1 << INTEL_X86_CMASK_BIT),
    .uflags  = INTEL_X86_NCOMBO,
    .modhw   = _INTEL_X86_ATTR_C,
  },
  { .uname   = "CYCLES_OK",
    .udesc   = "Cycles optimal number of Uops delivered by the LSD, but did not come from the decoder.",
    .ucode   = 0x0100ull | (0x6 << INTEL_X86_CMASK_BIT),
    .uflags  = INTEL_X86_NCOMBO,
    .modhw   = _INTEL_X86_ATTR_C,
  },
  { .uname   = "UOPS",
    .udesc   = "Number of Uops delivered by the LSD.",
    .ucode   = 0x0100ull,
    .uflags  = INTEL_X86_NCOMBO,
  },
};

static const intel_x86_umask_t intel_spr_exe_activity[]={
  { .uname   = "1_PORTS_UTIL",
    .udesc   = "Cycles total of 1 uop is executed on all ports and Reservation Station was not empty.",
    .ucode   = 0x0200ull,
    .uflags  = INTEL_X86_NCOMBO,
  },
  { .uname   = "2_PORTS_UTIL",
    .udesc   = "Cycles total of 2 uops are executed on all ports and Reservation Station was not empty.",
    .ucode   = 0x0400ull,
    .uflags  = INTEL_X86_NCOMBO,
  },
  { .uname   = "3_PORTS_UTIL",
    .udesc   = "Cycles total of 3 uops are executed on all ports and Reservation Station was not empty.",
    .ucode   = 0x0800ull,
    .uflags  = INTEL_X86_NCOMBO,
  },
  { .uname   = "4_PORTS_UTIL",
    .udesc   = "Cycles total of 4 uops are executed on all ports and Reservation Station was not empty.",
    .ucode   = 0x1000ull,
    .uflags  = INTEL_X86_NCOMBO,
  },
  { .uname   = "BOUND_ON_LOADS",
    .udesc   = "Execution stalls while memory subsystem has an outstanding load.",
    .ucode   = 0x2100ull | (0x5 << INTEL_X86_CMASK_BIT),
    .uflags  = INTEL_X86_NCOMBO,
    .modhw   = _INTEL_X86_ATTR_C,
  },
  { .uname   = "BOUND_ON_STORES",
    .udesc   = "Cycles where the Store Buffer was full and no loads caused an execution stall.",
    .ucode   = 0x4000ull | (0x2 << INTEL_X86_CMASK_BIT),
    .uflags  = INTEL_X86_NCOMBO,
    .modhw   = _INTEL_X86_ATTR_C,
  },
};

static const intel_x86_umask_t intel_spr_rs[]={
  { .uname   = "EMPTY",
    .udesc   = "Cycles when Reservation Station (RS) is empty for the thread.",
    .ucode   = 0x0700ull,
    .uflags  = INTEL_X86_NCOMBO,
  },
  { .uname   = "EMPTY_COUNT",
    .udesc   = "Counts end of periods where the Reservation Station (RS) was empty.",
    .ucode   = 0x0700ull | (0x1 << INTEL_X86_INV_BIT) | (0x1 << INTEL_X86_CMASK_BIT) | (0x1 << INTEL_X86_EDGE_BIT),
    .uflags  = INTEL_X86_NCOMBO,
    .modhw   = _INTEL_X86_ATTR_I | _INTEL_X86_ATTR_C | _INTEL_X86_ATTR_E,
  },
};

static const intel_x86_umask_t intel_spr_cycle_activity[]={
  { .uname   = "CYCLES_L1D_MISS",
    .udesc   = "Cycles while L1 cache miss demand load is outstanding.",
    .ucode   = 0x0800ull | (0x8 << INTEL_X86_CMASK_BIT),
    .uflags  = INTEL_X86_NCOMBO,
    .modhw   = _INTEL_X86_ATTR_C,
  },
  { .uname   = "CYCLES_L2_MISS",
    .udesc   = "Cycles while L2 cache miss demand load is outstanding.",
    .ucode   = 0x0100ull | (0x1 << INTEL_X86_CMASK_BIT),
    .uflags  = INTEL_X86_NCOMBO,
    .modhw   = _INTEL_X86_ATTR_C,
  },
  { .uname   = "CYCLES_MEM_ANY",
    .udesc   = "Cycles while memory subsystem has an outstanding load.",
    .ucode   = 0x1000ull | (0x10 << INTEL_X86_CMASK_BIT),
    .uflags  = INTEL_X86_NCOMBO,
    .modhw   = _INTEL_X86_ATTR_C,
  },
  { .uname   = "STALLS_L1D_MISS",
    .udesc   = "Execution stalls while L1 cache miss demand load is outstanding.",
    .ucode   = 0x0c00ull | (0xc << INTEL_X86_CMASK_BIT),
    .uflags  = INTEL_X86_NCOMBO,
    .modhw   = _INTEL_X86_ATTR_C,
  },
  { .uname   = "STALLS_L2_MISS",
    .udesc   = "Execution stalls while L2 cache miss demand load is outstanding.",
    .ucode   = 0x0500ull | (0x5 << INTEL_X86_CMASK_BIT),
    .uflags  = INTEL_X86_NCOMBO,
    .modhw   = _INTEL_X86_ATTR_C,
  },
  { .uname   = "STALLS_L3_MISS",
    .udesc   = "Execution stalls while L3 cache miss demand load is outstanding.",
    .ucode   = 0x0600ull | (0x6 << INTEL_X86_CMASK_BIT),
    .uflags  = INTEL_X86_NCOMBO,
    .modhw   = _INTEL_X86_ATTR_C,
  },
  { .uname   = "STALLS_TOTAL",
    .udesc   = "Total execution stalls.",
    .ucode   = 0x0400ull | (0x4 << INTEL_X86_CMASK_BIT),
    .uflags  = INTEL_X86_NCOMBO,
    .modhw   = _INTEL_X86_ATTR_C,
  },
};

static const intel_x86_umask_t intel_spr_resource_stalls[]={
  { .uname   = "SB",
    .udesc   = "Cycles stalled due to no store buffers available. (not including draining form sync).",
    .ucode   = 0x0800ull,
    .uflags  = INTEL_X86_NCOMBO,
  },
  { .uname   = "SCOREBOARD",
    .udesc   = "Counts cycles where the pipeline is stalled due to serializing operations.",
    .ucode   = 0x0200ull,
    .uflags  = INTEL_X86_NCOMBO,
  },
};

static const intel_x86_umask_t intel_spr_idq_uops_not_delivered[]={
  { .uname   = "CORE",
    .udesc   = "Uops not delivered by IDQ when backend of the machine is not stalled",
    .ucode   = 0x0100ull,
    .uflags  = INTEL_X86_NCOMBO,
  },
  { .uname   = "CYCLES_0_UOPS_DELIV_CORE",
    .udesc   = "Cycles when no uops are not delivered by the IDQ when backend of the machine is not stalled",
    .ucode   = 0x0100ull | (0x6 << INTEL_X86_CMASK_BIT),
    .uflags  = INTEL_X86_NCOMBO,
    .modhw   = _INTEL_X86_ATTR_C,
  },
  { .uname   = "CYCLES_FE_WAS_OK",
    .udesc   = "Cycles when optimal number of uops was delivered to the back-end when the back-end is not stalled",
    .ucode   = 0x0100ull | (0x1 << INTEL_X86_INV_BIT) | (0x1 << INTEL_X86_CMASK_BIT),
    .uflags  = INTEL_X86_NCOMBO,
    .modhw   = _INTEL_X86_ATTR_I | _INTEL_X86_ATTR_C,
  },
};

static const intel_x86_umask_t intel_spr_decode[]={
  { .uname   = "LCP",
    .udesc   = "Stalls caused by changing prefix length of the instruction.",
    .ucode   = 0x0100ull,
    .uflags  = INTEL_X86_NCOMBO,
  },
  { .uname   = "MS_BUSY",
    .udesc   = "Cycles the Microcode Sequencer is busy.",
    .ucode   = 0x0200ull,
    .uflags  = INTEL_X86_NCOMBO,
 },
};

static const intel_x86_umask_t intel_spr_icache_tag[]={
  { .uname   = "STALLS",
    .udesc   = "Cycles where a code fetch is stalled due to L1 instruction cache tag miss.",
    .ucode   = 0x0400ull,
    .uflags  = INTEL_X86_DFL,
  },
};

static const intel_x86_umask_t intel_spr_icache_data[]={
  { .uname   = "STALLS",
    .udesc   = "Cycles where a code fetch is stalled due to L1 instruction cache miss.",
    .ucode   = 0x0400ull,
    .uflags  = INTEL_X86_DFL,
  },
};

static const intel_x86_umask_t intel_spr_idq[]={
  { .uname   = "DSB_CYCLES_ANY",
    .udesc   = "Cycles Decode Stream Buffer (DSB) is delivering any Uop",
    .ucode   = 0x0800ull | (0x1 << INTEL_X86_CMASK_BIT),
    .uflags  = INTEL_X86_NCOMBO,
    .modhw   = _INTEL_X86_ATTR_C,
  },
  { .uname   = "DSB_CYCLES_OK",
    .udesc   = "Cycles DSB is delivering optimal number of Uops",
    .ucode   = 0x0800ull | (0x6 << INTEL_X86_CMASK_BIT),
    .uflags  = INTEL_X86_NCOMBO,
    .modhw   = _INTEL_X86_ATTR_C,
  },
  { .uname   = "DSB_UOPS",
    .udesc   = "Uops delivered to Instruction Decode Queue (IDQ) from the Decode Stream Buffer (DSB) path",
    .ucode   = 0x0800ull,
    .uflags  = INTEL_X86_NCOMBO,
  },
  { .uname   = "MITE_CYCLES_ANY",
    .udesc   = "Cycles MITE is delivering any Uop",
    .ucode   = 0x0400ull | (0x1 << INTEL_X86_CMASK_BIT),
    .uflags  = INTEL_X86_NCOMBO,
    .modhw   = _INTEL_X86_ATTR_C,
  },
  { .uname   = "MITE_CYCLES_OK",
    .udesc   = "Cycles MITE is delivering optimal number of Uops",
    .ucode   = 0x0400ull | (0x6 << INTEL_X86_CMASK_BIT),
    .uflags  = INTEL_X86_NCOMBO,
    .modhw   = _INTEL_X86_ATTR_C,
  },
  { .uname   = "MITE_UOPS",
    .udesc   = "Uops delivered to Instruction Decode Queue (IDQ) from MITE path",
    .ucode   = 0x0400ull,
    .uflags  = INTEL_X86_NCOMBO,
  },
  { .uname   = "MS_CYCLES_ANY",
    .udesc   = "Cycles when uops are being delivered to IDQ while MS is busy",
    .ucode   = 0x2000ull | (0x1 << INTEL_X86_CMASK_BIT),
    .uflags  = INTEL_X86_NCOMBO,
    .modhw   = _INTEL_X86_ATTR_C,
  },
  { .uname   = "MS_SWITCHES",
    .udesc   = "Number of switches from DSB or MITE to the MS",
    .ucode   = 0x2000ull | (0x1 << INTEL_X86_CMASK_BIT) | (0x1 << INTEL_X86_EDGE_BIT),
    .uflags  = INTEL_X86_NCOMBO,
    .modhw   = _INTEL_X86_ATTR_C | _INTEL_X86_ATTR_E,
  },
  { .uname   = "MS_UOPS",
    .udesc   = "Uops delivered to IDQ while MS is busy",
    .ucode   = 0x2000ull,
    .uflags  = INTEL_X86_NCOMBO,
  },
};

static const intel_x86_umask_t intel_spr_uops_decoded[]={
  { .uname   = "DEC0_UOPS",
    .udesc   = "TBD",
    .ucode   = 0x0100ull,
    .uflags  = INTEL_X86_DFL,
  },
};

static const intel_x86_umask_t intel_spr_inst_decoded[]={
  { .uname   = "DECODERS",
    .udesc   = "Instruction decoders utilized in a cycle",
    .ucode   = 0x0100ull,
    .uflags  = INTEL_X86_DFL,
  },
};

static const intel_x86_umask_t intel_spr_dsb2mite_switches[]={
  { .uname   = "PENALTY_CYCLES",
    .udesc   = "DSB-to-MITE switch true penalty cycles.",
    .ucode   = 0x0200ull,
    .uflags  = INTEL_X86_DFL,
  },
};

static const intel_x86_umask_t intel_spr_tx_mem[]={
  { .uname   = "ABORT_CAPACITY_READ",
    .udesc   = "Speculatively counts the number of TSX aborts due to a data capacity limitation for transactional reads",
    .ucode   = 0x8000ull,
    .uflags  = INTEL_X86_NCOMBO,
  },
  { .uname   = "ABORT_CAPACITY_WRITE",
    .udesc   = "Speculatively counts the number of TSX aborts due to a data capacity limitation for transactional writes.",
    .ucode   = 0x0200ull,
    .uflags  = INTEL_X86_NCOMBO,
  },
  { .uname   = "ABORT_CONFLICT",
    .udesc   = "Number of times a transactional abort was signaled due to a data conflict on a transactionally accessed address",
    .ucode   = 0x0100ull,
    .uflags  = INTEL_X86_NCOMBO,
  },
};

static const intel_x86_umask_t intel_spr_l1d[]={
  { .uname   = "REPLACEMENT",
    .udesc   = "Counts the number of cache lines replaced in L1 data cache.",
    .ucode   = 0x0100ull,
    .uflags  = INTEL_X86_DFL,
  },
};

static const intel_x86_umask_t intel_spr_load_hit_prefetch[]={
  { .uname   = "SWPF",
    .udesc   = "Counts the number of demand load dispatches that hit L1D fill buffer (FB) allocated for software prefetch.",
    .ucode   = 0x0100ull,
    .uflags  = INTEL_X86_DFL,
  },
};

static const intel_x86_umask_t intel_spr_l1d_pend_miss[]={
  { .uname   = "FB_FULL",
    .udesc   = "Number of cycles a demand request has waited due to L1D Fill Buffer (FB) unavailability.",
    .ucode   = 0x0200ull,
    .uflags  = INTEL_X86_NCOMBO,
  },
  { .uname   = "FB_FULL_PERIODS",
    .udesc   = "Number of phases a demand request has waited due to L1D Fill Buffer (FB) unavailability.",
    .ucode   = 0x0200ull | (0x1 << INTEL_X86_CMASK_BIT) | (0x1 << INTEL_X86_EDGE_BIT),
    .uflags  = INTEL_X86_NCOMBO,
    .modhw   = _INTEL_X86_ATTR_C | _INTEL_X86_ATTR_E,
  },
  { .uname   = "L2_STALL",
    .uequiv  = "L2_STALLS",
    .udesc   = "Number of cycles a demand request has waited due to L1D due to lack of L2 resources.",
    .ucode   = 0x0400ull,
    .uflags  = INTEL_X86_NCOMBO,
  },
  { .uname   = "L2_STALLS",
    .udesc   = "Number of cycles a demand request has waited due to L1D due to lack of L2 resources.",
    .ucode   = 0x0400ull,
    .uflags  = INTEL_X86_NCOMBO,
  },
  { .uname   = "PENDING",
    .udesc   = "Number of L1D misses that are outstanding",
    .ucode   = 0x0100ull,
    .uflags  = INTEL_X86_NCOMBO,
  },
  { .uname   = "PENDING_CYCLES",
    .udesc   = "Cycles with L1D load Misses outstanding.",
    .ucode   = 0x0100ull | (0x1 << INTEL_X86_CMASK_BIT),
    .uflags  = INTEL_X86_NCOMBO,
    .modhw   = _INTEL_X86_ATTR_C,
  },
};

static const intel_x86_umask_t intel_spr_memory_activity[]={
  { .uname   = "CYCLES_L1D_MISS",
    .udesc   = "Cycles while L1 cache miss demand load is outstanding.",
    .ucode   = 0x0200ull | (0x2 << INTEL_X86_CMASK_BIT),
    .uflags  = INTEL_X86_NCOMBO,
    .modhw   = _INTEL_X86_ATTR_C,
  },
  { .uname   = "STALLS_L1D_MISS",
    .udesc   = "Execution stalls while L1 cache miss demand load is outstanding.",
    .ucode   = 0x0300ull | (0x3 << INTEL_X86_CMASK_BIT),
    .uflags  = INTEL_X86_NCOMBO,
    .modhw   = _INTEL_X86_ATTR_C,
  },
  { .uname   = "STALLS_L2_MISS",
    .udesc   = "TBD",
    .ucode   = 0x0500ull | (0x5 << INTEL_X86_CMASK_BIT),
    .uflags  = INTEL_X86_NCOMBO,
    .modhw   = _INTEL_X86_ATTR_C,
  },
  { .uname   = "STALLS_L3_MISS",
    .udesc   = "TBD",
    .ucode   = 0x0900ull | (0x9 << INTEL_X86_CMASK_BIT),
    .uflags  = INTEL_X86_NCOMBO,
    .modhw   = _INTEL_X86_ATTR_C,
  },
};

static const intel_x86_umask_t intel_spr_mem_store_retired[]={
  { .uname   = "L2_HIT",
    .udesc   = "TBD",
    .ucode   = 0x0100ull,
    .uflags  = INTEL_X86_DFL,
  },
};

static const intel_x86_umask_t intel_spr_mem_load_completed[]={
  { .uname   = "L1_MISS_ANY",
    .udesc   = "Completed demand load uops that miss the L1 d-cache.",
    .ucode   = 0xfd00ull,
    .uflags  = INTEL_X86_DFL,
  },
};

static const intel_x86_umask_t spr_sq_misc[]={
  { .uname   = "BUS_LOCK",
    .udesc   = "Counts bus locks, accounts for cache line split locks and UC locks.",
    .ucode   = 0x1000ull,
    .uflags  = INTEL_X86_DFL,
  },
};

static const intel_x86_umask_t intel_spr_sw_prefetch_access[]={
  { .uname   = "NTA",
    .udesc   = "Number of PREFETCHNTA instructions executed.",
    .ucode   = 0x0100ull,
    .uflags  = INTEL_X86_NCOMBO,
  },
  { .uname   = "PREFETCHW",
    .udesc   = "Number of PREFETCHW instructions executed.",
    .ucode   = 0x0800ull,
    .uflags  = INTEL_X86_NCOMBO,
  },
  { .uname   = "T0",
    .udesc   = "Number of PREFETCHT0 instructions executed.",
    .ucode   = 0x0200ull,
    .uflags  = INTEL_X86_NCOMBO,
  },
  { .uname   = "T1_T2",
    .udesc   = "Number of PREFETCHT1 or PREFETCHT2 instructions executed.",
    .ucode   = 0x0400ull,
    .uflags  = INTEL_X86_NCOMBO,
  },
};

static const intel_x86_umask_t intel_spr_longest_lat_cache[]={
  { .uname   = "MISS",
    .udesc   = "Core-originated cacheable requests that missed L3  (Except hardware prefetches to the L3)",
    .ucode   = 0x4100ull,
    .uflags  = INTEL_X86_DFL,
  },
  { .uname   = "REFERENCE",
    .udesc   = "Core-originated cacheable requests that refer to L3 (Except hardware prefetches to the L3)",
    .ucode   = 0x4f00ull,
    .uflags  = INTEL_X86_NCOMBO,
  },
};

static const intel_x86_umask_t intel_spr_xq[]={
  { .uname   = "FULL_CYCLES",
    .udesc   = "TBD",
    .ucode   = 0x0100ull | (0x1 << INTEL_X86_CMASK_BIT),
    .uflags  = INTEL_X86_DFL,
    .modhw   = _INTEL_X86_ATTR_C,
  },
};

static const intel_x86_umask_t intel_spr_l2_lines_out[]={
  { .uname   = "NON_SILENT",
    .udesc   = "TBD",
    .ucode   = 0x0200ull,
    .uflags  = INTEL_X86_NCOMBO,
  },
  { .uname   = "SILENT",
    .udesc   = "Non-modified cache lines that are silently dropped by L2 cache when triggered by an L2 cache fill.",
    .ucode   = 0x0100ull,
    .uflags  = INTEL_X86_NCOMBO,
  },
  { .uname   = "USELESS_HWPF",
    .udesc   = "Cache lines that have been L2 hardware prefetched but not used by demand accesses",
    .ucode   = 0x0400ull,
    .uflags  = INTEL_X86_NCOMBO,
  },
};

static const intel_x86_umask_t intel_spr_l2_lines_in[]={
  { .uname   = "ALL",
    .udesc   = "L2 cache lines filling L2",
    .ucode   = 0x1f00ull,
    .uflags  = INTEL_X86_DFL,
  },
};

static const intel_x86_umask_t intel_spr_l2_rqsts[]={
  { .uname   = "ALL_CODE_RD",
    .udesc   = "L2 code requests",
    .ucode   = 0xe400ull,
    .uflags  = INTEL_X86_NCOMBO,
  },
  { .uname   = "ALL_DEMAND_DATA_RD",
    .udesc   = "Demand Data Read requests",
    .ucode   = 0xe100ull,
    .uflags  = INTEL_X86_NCOMBO,
  },
  { .uname   = "ALL_DEMAND_MISS",
    .udesc   = "Demand requests that miss L2 cache",
    .ucode   = 0x2700ull,
    .uflags  = INTEL_X86_NCOMBO,
  },
  { .uname   = "ALL_DEMAND_REFERENCES",
    .udesc   = "Demand requests to L2 cache",
    .ucode   = 0xe700ull,
    .uflags  = INTEL_X86_NCOMBO,
  },
  { .uname   = "ALL_RFO",
    .udesc   = "RFO requests to L2 cache",
    .ucode   = 0xe200ull,
    .uflags  = INTEL_X86_NCOMBO,
  },
  { .uname   = "CODE_RD_HIT",
    .udesc   = "L2 cache hits when fetching instructions, code reads.",
    .ucode   = 0xc400ull,
    .uflags  = INTEL_X86_NCOMBO,
  },
  { .uname   = "CODE_RD_MISS",
    .udesc   = "L2 cache misses when fetching instructions",
    .ucode   = 0x2400ull,
    .uflags  = INTEL_X86_NCOMBO,
  },
  { .uname   = "DEMAND_DATA_RD_HIT",
    .udesc   = "Demand Data Read requests that hit L2 cache",
    .ucode   = 0xc100ull,
    .uflags  = INTEL_X86_NCOMBO,
  },
  { .uname   = "DEMAND_DATA_RD_MISS",
    .udesc   = "Demand Data Read miss L2, no rejects",
    .ucode   = 0x2100ull,
    .uflags  = INTEL_X86_NCOMBO,
  },
  { .uname   = "RFO_HIT",
    .udesc   = "RFO requests that hit L2 cache",
    .ucode   = 0xc200ull,
    .uflags  = INTEL_X86_NCOMBO,
  },
  { .uname   = "RFO_MISS",
    .udesc   = "RFO requests that miss L2 cache",
    .ucode   = 0x2200ull,
    .uflags  = INTEL_X86_NCOMBO,
  },
  { .uname   = "SWPF_HIT",
    .udesc   = "SW prefetch requests that hit L2 cache.",
    .ucode   = 0xc800ull,
    .uflags  = INTEL_X86_NCOMBO,
  },
  { .uname   = "SWPF_MISS",
    .udesc   = "SW prefetch requests that miss L2 cache.",
    .ucode   = 0x2800ull,
    .uflags  = INTEL_X86_NCOMBO,
  },
};

static const intel_x86_umask_t intel_spr_offcore_requests[]={
  { .uname   = "ALL_REQUESTS",
    .udesc   = "TBD",
    .ucode   = 0x8000ull,
    .uflags  = INTEL_X86_NCOMBO,
  },
  { .uname   = "DATA_RD",
    .udesc   = "Demand and prefetch data reads",
    .ucode   = 0x0800ull,
    .uflags  = INTEL_X86_NCOMBO,
  },
  { .uname   = "DEMAND_DATA_RD",
    .udesc   = "Demand Data Read requests sent to uncore",
    .ucode   = 0x0100ull,
    .uflags  = INTEL_X86_NCOMBO,
  },
};

static const intel_x86_umask_t intel_spr_offcore_requests_outstanding[]={
  { .uname   = "ALL_DATA_RD",
    .uequiv  = "DATA_RD",
    .udesc   = "TBD",
    .ucode   = 0x0800ull,
    .uflags  = INTEL_X86_NCOMBO,
  },
  { .uname   = "CYCLES_WITH_DATA_RD",
    .udesc   = "TBD",
    .ucode   = 0x0800ull | (0x1 << INTEL_X86_CMASK_BIT),
    .uflags  = INTEL_X86_NCOMBO,
    .modhw   = _INTEL_X86_ATTR_C,
  },
  { .uname   = "CYCLES_WITH_DEMAND_RFO",
    .udesc   = "TBD",
    .ucode   = 0x0400ull | (0x1 << INTEL_X86_CMASK_BIT),
    .uflags  = INTEL_X86_NCOMBO,
    .modhw   = _INTEL_X86_ATTR_C,
  },
  { .uname   = "DATA_RD",
    .udesc   = "TBD",
    .ucode   = 0x0800ull,
    .uflags  = INTEL_X86_NCOMBO,
  },
};

static const intel_x86_umask_t intel_spr_dtlb_store_misses[]={
  { .uname   = "STLB_HIT",
    .udesc   = "Stores that miss the DTLB and hit the STLB.",
    .ucode   = 0x2000ull,
    .uflags  = INTEL_X86_NCOMBO,
  },
  { .uname   = "WALK_ACTIVE",
    .udesc   = "Cycles when at least one PMH is busy with a page walk for a store.",
    .ucode   = 0x1000ull | (0x1 << INTEL_X86_CMASK_BIT),
    .uflags  = INTEL_X86_NCOMBO,
    .modhw   = _INTEL_X86_ATTR_C,
  },
  { .uname   = "WALK_COMPLETED",
    .udesc   = "Store misses in all TLB levels causes a page walk that completes. (All page sizes)",
    .ucode   = 0x0e00ull,
    .uflags  = INTEL_X86_NCOMBO,
  },
  { .uname   = "WALK_COMPLETED_1G",
    .udesc   = "Page walks completed due to a demand data store to a 1G page.",
    .ucode   = 0x0800ull,
    .uflags  = INTEL_X86_NCOMBO,
  },
  { .uname   = "WALK_COMPLETED_2M_4M",
    .udesc   = "Page walks completed due to a demand data store to a 2M/4M page.",
    .ucode   = 0x0400ull,
    .uflags  = INTEL_X86_NCOMBO,
  },
  { .uname   = "WALK_COMPLETED_4K",
    .udesc   = "Page walks completed due to a demand data store to a 4K page.",
    .ucode   = 0x0200ull,
    .uflags  = INTEL_X86_NCOMBO,
  },
  { .uname   = "WALK_PENDING",
    .udesc   = "Number of page walks outstanding for a store in the PMH each cycle.",
    .ucode   = 0x1000ull,
    .uflags  = INTEL_X86_NCOMBO,
  },
};

static const intel_x86_umask_t intel_spr_dtlb_load_misses[]={
  { .uname   = "STLB_HIT",
    .udesc   = "Loads that miss the DTLB and hit the STLB.",
    .ucode   = 0x2000ull,
    .uflags  = INTEL_X86_NCOMBO,
  },
  { .uname   = "WALK_ACTIVE",
    .udesc   = "Cycles when at least one PMH is busy with a page walk for a demand load.",
    .ucode   = 0x1000ull | (0x1 << INTEL_X86_CMASK_BIT),
    .uflags  = INTEL_X86_NCOMBO,
    .modhw   = _INTEL_X86_ATTR_C,
  },
  { .uname   = "WALK_COMPLETED",
    .udesc   = "Load miss in all TLB levels causes a page walk that completes. (All page sizes)",
    .ucode   = 0x0e00ull,
    .uflags  = INTEL_X86_NCOMBO,
  },
  { .uname   = "WALK_COMPLETED_1G",
    .udesc   = "Page walks completed due to a demand data load to a 1G page.",
    .ucode   = 0x0800ull,
    .uflags  = INTEL_X86_NCOMBO,
  },
  { .uname   = "WALK_COMPLETED_2M_4M",
    .udesc   = "Page walks completed due to a demand data load to a 2M/4M page.",
    .ucode   = 0x0400ull,
    .uflags  = INTEL_X86_NCOMBO,
  },
  { .uname   = "WALK_COMPLETED_4K",
    .udesc   = "Page walks completed due to a demand data load to a 4K page.",
    .ucode   = 0x0200ull,
    .uflags  = INTEL_X86_NCOMBO,
  },
  { .uname   = "WALK_PENDING",
    .udesc   = "Number of page walks outstanding for a demand load in the PMH each cycle.",
    .ucode   = 0x1000ull,
    .uflags  = INTEL_X86_NCOMBO,
  },
};

static const intel_x86_umask_t intel_spr_itlb_misses[]={
  { .uname   = "STLB_HIT",
    .udesc   = "Instruction fetch requests that miss the ITLB and hit the STLB.",
    .ucode   = 0x2000ull,
    .uflags  = INTEL_X86_NCOMBO,
  },
  { .uname   = "WALK_ACTIVE",
    .udesc   = "Cycles when at least one PMH is busy with a page walk for code (instruction fetch) request.",
    .ucode   = 0x1000ull | (0x1 << INTEL_X86_CMASK_BIT),
    .uflags  = INTEL_X86_NCOMBO,
    .modhw   = _INTEL_X86_ATTR_C,
  },
  { .uname   = "WALK_COMPLETED",
    .udesc   = "Code miss in all TLB levels causes a page walk that completes. (All page sizes)",
    .ucode   = 0x0e00ull,
    .uflags  = INTEL_X86_NCOMBO,
  },
  { .uname   = "WALK_COMPLETED_2M_4M",
    .udesc   = "Code miss in all TLB levels causes a page walk that completes. (2M/4M)",
    .ucode   = 0x0400ull,
    .uflags  = INTEL_X86_NCOMBO,
  },
  { .uname   = "WALK_COMPLETED_4K",
    .udesc   = "Code miss in all TLB levels causes a page walk that completes. (4K)",
    .ucode   = 0x0200ull,
    .uflags  = INTEL_X86_NCOMBO,
  },
  { .uname   = "WALK_PENDING",
    .udesc   = "Number of page walks outstanding for an outstanding code request in the PMH each cycle.",
    .ucode   = 0x1000ull,
    .uflags  = INTEL_X86_NCOMBO,
  },
};

static const intel_x86_umask_t intel_spr_ld_blocks[]={
  { .uname   = "ADDRESS_ALIAS",
    .udesc   = "False dependencies in MOB due to partial compare on address.",
    .ucode   = 0x0400ull,
    .uflags  = INTEL_X86_NCOMBO,
  },
  { .uname   = "NO_SR",
    .udesc   = "The number of times that split load operations are temporarily blocked because all resources for handling the split accesses are in use.",
    .ucode   = 0x8800ull,
    .uflags  = INTEL_X86_NCOMBO,
  },
  { .uname   = "STORE_FORWARD",
    .udesc   = "Loads blocked due to overlapping with a preceding store that cannot be forwarded.",
    .ucode   = 0x8200ull,
    .uflags  = INTEL_X86_NCOMBO,
  },
};

static const intel_x86_umask_t intel_spr_topdown[]={
  { .uname   = "BACKEND_BOUND_SLOTS",
    .udesc   = "TMA slots where no uops were being issued due to lack of back-end resources.",
    .ucode   = 0x0200ull,
    .uflags  = INTEL_X86_NCOMBO,
  },
  { .uname   = "BAD_SPEC_SLOTS",
    .udesc   = "TMA slots wasted due to incorrect speculations.",
    .ucode   = 0x0400ull,
    .uflags  = INTEL_X86_NCOMBO,
  },
  { .uname   = "BR_MISPREDICT_SLOTS",
    .udesc   = "TMA slots wasted due to incorrect speculation by branch mispredictions",
    .ucode   = 0x0800ull,
    .uflags  = INTEL_X86_NCOMBO,
  },
  { .uname   = "MEMORY_BOUND_SLOTS",
    .udesc   = "TBD",
    .ucode   = 0x1000ull,
    .uflags  = INTEL_X86_NCOMBO,
  },
  { .uname   = "SLOTS",
    .udesc   = "TMA slots available for an unhalted logical processor. Fixed counter - architectural event",
    .ucode   = 0x0400ull,
    .uflags  = INTEL_X86_NCOMBO,
  },
  { .uname   = "SLOTS_P",
    .udesc   = "TMA slots available for an unhalted logical processor. General counter - architectural event",
    .ucode   = 0x01a4ull,
    .uflags  = INTEL_X86_NCOMBO | INTEL_X86_CODE_OVERRIDE,
  },
};

static const intel_x86_umask_t intel_spr_cpu_clk_unhalted[]={
  { .uname   = "C01",
    .udesc   = "Core clocks when the thread is in the C0.1 light-weight slower wakeup time but more power saving optimized state.",
    .ucode   = 0x10ecull,
    .uflags  = INTEL_X86_NCOMBO | INTEL_X86_CODE_OVERRIDE,
  },
  { .uname   = "C02",
    .udesc   = "Core clocks when the thread is in the C0.2 light-weight faster wakeup time but less power saving optimized state.",
    .ucode   = 0x20ecull,
    .uflags  = INTEL_X86_NCOMBO | INTEL_X86_CODE_OVERRIDE,
  },
  { .uname   = "C0_WAIT",
    .udesc   = "Core clocks when the thread is in the C0.1 or C0.2 or running a PAUSE in C0 ACPI state.",
    .ucode   = 0x70ecull,
    .uflags  = INTEL_X86_NCOMBO | INTEL_X86_CODE_OVERRIDE,
  },
  { .uname   = "DISTRIBUTED",
    .udesc   = "Cycle counts are evenly distributed between active threads in the Core.",
    .ucode   = 0x02ecull,
    .uflags  = INTEL_X86_NCOMBO | INTEL_X86_CODE_OVERRIDE,
  },
  { .uname   = "ONE_THREAD_ACTIVE",
    .udesc   = "Core crystal clock cycles when this thread is unhalted and the other thread is halted.",
    .ucode   = 0x0200ull,
    .uflags  = INTEL_X86_NCOMBO,
  },
  { .uname   = "PAUSE",
    .udesc   = "TBD",
    .ucode   = 0x40ecull,
    .uflags  = INTEL_X86_NCOMBO | INTEL_X86_CODE_OVERRIDE,
  },
  { .uname   = "PAUSE_INST",
    .udesc   = "TBD",
    .ucode   = 0x40ecull | (0x1 << INTEL_X86_CMASK_BIT) | (0x1 << INTEL_X86_EDGE_BIT),
    .uflags  = INTEL_X86_NCOMBO | INTEL_X86_CODE_OVERRIDE,
    .modhw   = _INTEL_X86_ATTR_C | _INTEL_X86_ATTR_E,
  },
  { .uname   = "REF_DISTRIBUTED",
    .udesc   = "Core crystal clock cycles. Cycle counts are evenly distributed between active threads in the Core.",
    .ucode   = 0x0800ull,
    .uflags  = INTEL_X86_NCOMBO,
  },
  { .uname   = "REF_TSC",
    .udesc   = "Reference cycles when the core is not in halt state (Fixed Counter 2).",
    .ucode   = 0x0300ull,
    .uflags  = INTEL_X86_NCOMBO | INTEL_X86_CODE_OVERRIDE,
  },
  { .uname   = "REF_TSC_P",
    .udesc   = "Reference cycles when the core is not in halt state (Programmable Counter).",
    .ucode   = 0x0100ull,
    .uflags  = INTEL_X86_NCOMBO,
  },
  { .uname   = "THREAD",
    .udesc   = "Core cycles when the thread is not in halt state",
    .ucode   = 0x0200ull,
    .uflags  = INTEL_X86_NCOMBO | INTEL_X86_CODE_OVERRIDE, /* fixed counter encoding */
  },
  { .uname   = "THREAD_P",
    .udesc   = "Thread cycles when thread is not in halt state",
    .ucode   = 0x0000ull,
    .uflags  = INTEL_X86_NCOMBO,
  },
};

static const intel_x86_umask_t intel_spr_inst_retired[]={
  { .uname   = "ANY",
    .udesc   = "Number of instructions retired. Fixed Counter - architectural event (c, e, i, intx, intxcp modifiers not available)",
    .ucode   = 0x0100ull,
    .ucntmsk = 0x100000000ull,
    .uflags  = INTEL_X86_NCOMBO | INTEL_X86_PEBS | INTEL_X86_DFL,
    /*
     * because this encoding is for a fixed counter, not all modifiers are available. Given that we do not have per umask modmsk, we use
     * the hardcoded modifiers field instead. We mark all unavailable modifiers as set (to 0) so the user cannot modify them
     */
    .modhw   = _INTEL_X86_ATTR_INTX | _INTEL_X86_ATTR_INTXCP | _INTEL_X86_ATTR_C | _INTEL_X86_ATTR_I | _INTEL_X86_ATTR_E,
  },
  { .uname   = "STALL_CYCLES",
    .udesc   = "Cycles without actually retired instructions.",
    .ucode   = 0x0100ull | (0x1 << INTEL_X86_INV_BIT) | (0x1 << INTEL_X86_CMASK_BIT),
    .uflags  = INTEL_X86_NCOMBO,
    .modhw   = _INTEL_X86_ATTR_I | _INTEL_X86_ATTR_C,
  },
  { .uname   = "ANY_P",
    .udesc   = "Number of instructions retired. General Counter - architectural event",
    .ucode   = 0x0000ull,
    .uflags  = INTEL_X86_NCOMBO,
  },
  { .uname   = "MACRO_FUSED",
    .udesc   = "TBD",
    .ucode   = 0x1000ull,
    .uflags  = INTEL_X86_NCOMBO,
  },
  { .uname   = "NOP",
    .udesc   = "Number of all retired NOP instructions.",
    .ucode   = 0x0200ull,
    .uflags  = INTEL_X86_NCOMBO,
  },
  { .uname   = "PREC_DIST",
    .udesc   = "Precise instruction retired with PEBS precise-distribution",
    .ucode   = 0x0100ull,
    .ucntmsk = 0x100000000ull,
    .uflags  = INTEL_X86_NCOMBO | INTEL_X86_CODE_OVERRIDE | INTEL_X86_FIXED | INTEL_X86_PEBS,
    /*
     * because this encoding is for a fixed counter, not all modifiers are available. Given that we do not have per umask modmsk, we use
     * the hardcoded modifiers field instead. We mark all unavailable modifiers as set (to 0) so the user cannot modify them
     */
    .modhw   = _INTEL_X86_ATTR_INTX | _INTEL_X86_ATTR_INTXCP | _INTEL_X86_ATTR_C | _INTEL_X86_ATTR_I,
},
  { .uname   = "REP_ITERATION",
    .udesc   = "Iterations of Repeat string retired instructions.",
    .ucode   = 0x0800ull,
    .uflags  = INTEL_X86_NCOMBO,
  },
};

static const intel_x86_entry_t intel_spr_pe[]={
  { .name   = "UNHALTED_CORE_CYCLES",
    .desc   = "Count core clock cycles whenever the clock signal on the specific core is running (not halted)",
    .modmsk = INTEL_V2_ATTRS,
    .cntmsk = 0x20000000full,
    .code = 0x3c,
  },
  { .name   = "UNHALTED_REFERENCE_CYCLES",
    .desc   = "Unhalted reference cycles",
    .modmsk = INTEL_FIXED3_ATTRS,
    .cntmsk = 0x400000000ull,
    .code = 0x0300, /* pseudo encoding */
    .flags = INTEL_X86_FIXED,
  },
  { .name   = "INSTRUCTION_RETIRED",
    .desc   = "Number of instructions at retirement",
    .modmsk = INTEL_V2_ATTRS,
    .cntmsk = 0x1000000ffull,
    .code = 0xc0,
  },
  { .name   = "INSTRUCTIONS_RETIRED",
    .desc   = "Number of instructions at retirement",
    .modmsk = INTEL_V2_ATTRS,
    .equiv = "INSTRUCTION_RETIRED",
    .cntmsk = 0x1000000ffull,
    .code = 0xc0,
  },
  { .name   = "AMX_OPS_RETIRED",
    .desc   = "Advance Matrix Extension (AMX) operations retired",
    .code   = 0x00ce,
    .modmsk = INTEL_V5_ATTRS,
    .cntmsk = 0x1ull,
    .ngrp   = 1,
    .flags  = 0,
    .numasks= LIBPFM_ARRAY_SIZE(spr_amx_ops_retired),
    .umasks = spr_amx_ops_retired,
  },
  { .name   = "INT_VEC_RETIRED",
    .desc   = "integer ADD, SUB, SAD 128-bit vector instructions.",
    .code   = 0x00e7,
    .modmsk = INTEL_V5_ATTRS,
    .cntmsk = 0xffull,
    .ngrp   = 1,
    .flags  = 0,
    .numasks= LIBPFM_ARRAY_SIZE(intel_spr_int_vec_retired),
    .umasks = intel_spr_int_vec_retired,
  },
  { .name   = "MEM_UOP_RETIRED",
    .desc   = "Retired memory uops for any access",
    .code   = 0x00e5,
    .modmsk = INTEL_V5_ATTRS,
    .cntmsk = 0xffull,
    .ngrp   = 1,
    .flags  = 0,
    .numasks= LIBPFM_ARRAY_SIZE(intel_spr_mem_uop_retired),
    .umasks = intel_spr_mem_uop_retired,
  },
  { .name   = "MISC2_RETIRED",
    .desc   = "TBD",
    .code   = 0x00e0,
    .modmsk = INTEL_V5_ATTRS,
    .cntmsk = 0xffull,
    .ngrp   = 1,
    .flags  = 0,
    .numasks= LIBPFM_ARRAY_SIZE(intel_spr_misc2_retired),
    .umasks = intel_spr_misc2_retired,
  },
  { .name   = "MEM_LOAD_MISC_RETIRED",
    .desc   = "Retired instructions with at least 1 uncacheable load or lock.",
    .code   = 0x00d4,
    .modmsk = INTEL_V5_ATTRS,
    .cntmsk = 0xfull,
    .ngrp   = 1,
    .flags  = INTEL_X86_PEBS,
    .numasks= LIBPFM_ARRAY_SIZE(intel_spr_mem_load_misc_retired),
    .umasks = intel_spr_mem_load_misc_retired,
  },
  { .name   = "MEM_LOAD_L3_MISS_RETIRED",
    .desc   = "Retired load instructions which data sources missed L3 but serviced from local dram",
    .code   = 0x00d3,
    .modmsk = INTEL_V5_ATTRS,
    .cntmsk = 0xfull,
    .ngrp   = 1,
    .flags  = 0,
    .numasks= LIBPFM_ARRAY_SIZE(intel_spr_mem_load_l3_miss_retired),
    .umasks = intel_spr_mem_load_l3_miss_retired,
  },
  { .name   = "MEM_LOAD_L3_HIT_RETIRED",
    .desc   = "Retired load instructions whose data sources were L3 hit and cross-core snoop missed in on-pkg core cache.",
    .code   = 0x00d2,
    .modmsk = INTEL_V5_ATTRS,
    .cntmsk = 0xfull,
    .ngrp   = 1,
    .flags  = INTEL_X86_PEBS,
    .numasks= LIBPFM_ARRAY_SIZE(intel_spr_mem_load_l3_hit_retired),
    .umasks = intel_spr_mem_load_l3_hit_retired,
  },
  { .name   = "MEM_LOAD_RETIRED",
    .desc   = "Retired load instructions with L1 cache hits as data sources",
    .code   = 0x00d1,
    .modmsk = INTEL_V5_ATTRS,
    .cntmsk = 0xfull,
    .ngrp   = 1,
    .flags  = INTEL_X86_PEBS,
    .numasks= LIBPFM_ARRAY_SIZE(intel_spr_mem_load_retired),
    .umasks = intel_spr_mem_load_retired,
  },
  { .name   = "MEM_INST_RETIRED",
    .desc   = "Retired load instructions that miss the STLB.",
    .code   = 0x00d0,
    .modmsk = INTEL_V5_ATTRS,
    .cntmsk = 0xfull,
    .ngrp   = 1,
    .flags  = INTEL_X86_PEBS,
    .numasks= LIBPFM_ARRAY_SIZE(intel_spr_mem_inst_retired),
    .umasks = intel_spr_mem_inst_retired,
  },
  { .name   = "FP_ARITH_INST_RETIRED2",
    .desc   = "TBD",
    .code   = 0x00cf,
    .modmsk = INTEL_V5_ATTRS,
    .cntmsk = 0xffull,
    .ngrp   = 1,
    .flags  = 0,
    .numasks= LIBPFM_ARRAY_SIZE(intel_spr_fp_arith_inst_retired2),
    .umasks = intel_spr_fp_arith_inst_retired2,
  },
  { .name   = "MEM_TRANS_RETIRED",
    .desc   = "Counts randomly selected loads when the latency from first dispatch to completion is greater than 128 cycles.",
    .code   = 0x01cd,
    .modmsk = INTEL_V5_ATTRS | _INTEL_X86_ATTR_LDLAT,
    .cntmsk = 0xfeull,
    .ngrp   = 1,
    .flags  = INTEL_X86_PEBS,
    .numasks= LIBPFM_ARRAY_SIZE(intel_spr_mem_trans_retired),
    .umasks = intel_spr_mem_trans_retired,
  },
  { .name   = "MISC_RETIRED",
    .desc   = "Increments whenever there is an update to the LBR array.",
    .code   = 0x00cc,
    .modmsk = INTEL_V5_ATTRS,
    .cntmsk = 0xffull,
    .ngrp   = 1,
    .flags  = 0,
    .numasks= LIBPFM_ARRAY_SIZE(intel_spr_misc_retired),
    .umasks = intel_spr_misc_retired,
  },
  { .name   = "RTM_RETIRED",
    .desc   = "Number of times an RTM execution started.",
    .code   = 0x00c9,
    .modmsk = INTEL_V5_ATTRS,
    .cntmsk = 0xffull,
    .ngrp   = 1,
    .flags  = 0,
    .numasks= LIBPFM_ARRAY_SIZE(intel_spr_rtm_retired),
    .umasks = intel_spr_rtm_retired,
  },
  { .name   = "SQ_MISC",
    .desc   = "Counts bus locks, accounts for cache line split locks and UC locks.",
    .code   = 0x002c,
    .modmsk = INTEL_V5_ATTRS,
    .cntmsk = 0xfull,
    .ngrp   = 1,
    .flags  = INTEL_X86_SPEC,
    .numasks= LIBPFM_ARRAY_SIZE(spr_sq_misc),
    .umasks = spr_sq_misc,
  },
  { .name   = "FP_ARITH_INST_RETIRED",
    .desc   = "Counts number of SSE/AVX computational scalar double precision floating-point instructions retired; some instructions will count twice as noted below.  Each count represents 1 computational operation. Applies to SSE* and AVX* scalar double precision floating-point instructions: ADD SUB MUL DIV MIN MAX SQRT FM(N)ADD/SUB.  FM(N)ADD/SUB instructions count twice as they perform 2 calculations per element.",
    .code   = 0x00c7,
    .modmsk = INTEL_V5_ATTRS,
    .cntmsk = 0xffull,
    .ngrp   = 1,
    .flags  = 0,
    .numasks= LIBPFM_ARRAY_SIZE(intel_spr_fp_arith_inst_retired),
    .umasks = intel_spr_fp_arith_inst_retired,
  },
  { .name   = "FRONTEND_RETIRED",
    .desc   = "Retired Instructions who experienced a critical DSB miss.",
    .code   = 0x01c6,
    .modmsk = INTEL_SKL_FE_ATTRS,
    .cntmsk = 0xffull,
    .ngrp   = 1,
    .flags  = INTEL_X86_FRONTEND | INTEL_X86_PEBS,
    .numasks= LIBPFM_ARRAY_SIZE(intel_spr_frontend_retired),
    .umasks = intel_spr_frontend_retired,
  },
  { .name   = "BR_MISP_RETIRED",
    .desc   = "Mispredicted branch instructions retired.",
    .code   = 0x00c5,
    .modmsk = INTEL_V5_ATTRS,
    .cntmsk = 0xffull,
    .ngrp   = 1,
    .flags  = INTEL_X86_PEBS,
    .numasks= LIBPFM_ARRAY_SIZE(intel_spr_br_misp_retired),
    .umasks = intel_spr_br_misp_retired,
  },
  { .name   = "BR_INST_RETIRED",
    .desc   = "Branch instructions retired.",
    .code   = 0x00c4,
    .modmsk = INTEL_V5_ATTRS,
    .cntmsk = 0xffull,
    .ngrp   = 1,
    .flags  = INTEL_X86_PEBS,
    .numasks= LIBPFM_ARRAY_SIZE(intel_spr_br_inst_retired),
    .umasks = intel_spr_br_inst_retired,
  },
  { .name   = "MACHINE_CLEARS",
    .desc   = "Number of machine clears (nukes) of any type.",
    .code   = 0x00c3,
    .modmsk = INTEL_V5_ATTRS,
    .cntmsk = 0xffull,
    .ngrp   = 1,
    .flags  = INTEL_X86_SPEC,
    .numasks= LIBPFM_ARRAY_SIZE(intel_spr_machine_clears),
    .umasks = intel_spr_machine_clears,
  },
  { .name   = "UOPS_RETIRED",
    .desc   = "Retired uops.",
    .code   = 0x00c2,
    .modmsk = INTEL_V5_ATTRS,
    .cntmsk = 0xffull,
    .ngrp   = 1,
    .flags  = 0,
    .numasks= LIBPFM_ARRAY_SIZE(intel_spr_uops_retired),
    .umasks = intel_spr_uops_retired,
  },
  { .name   = "ASSISTS",
    .desc   = "Counts all microcode FP assists.",
    .code   = 0x00c1,
    .modmsk = INTEL_V5_ATTRS,
    .cntmsk = 0xffull,
    .ngrp   = 1,
    .flags  = INTEL_X86_SPEC,
    .numasks= LIBPFM_ARRAY_SIZE(intel_spr_assists),
    .umasks = intel_spr_assists,
  },
  { .name   = "EXE",
    .desc   = "Excution cycles.",
    .code   = 0x02b7,
    .modmsk = INTEL_V5_ATTRS,
    .cntmsk = 0xffull,
    .ngrp   = 1,
    .flags  = INTEL_X86_NHM_OFFCORE,
    .numasks= LIBPFM_ARRAY_SIZE(intel_spr_exe),
    .umasks = intel_spr_exe,
  },
  { .name   = "FP_ARITH_DISPATCHED",
    .desc   = "TBD",
    .code   = 0x00b3,
    .modmsk = INTEL_V5_ATTRS,
    .cntmsk = 0xffull,
    .ngrp   = 1,
    .flags  = 0,
    .numasks= LIBPFM_ARRAY_SIZE(intel_spr_fp_arith_dispatched),
    .umasks = intel_spr_fp_arith_dispatched,
  },
  { .name   = "UOPS_DISPATCHED",
    .desc   = "Uops dispatched.",
    .code   = 0x00b2,
    .modmsk = INTEL_V5_ATTRS,
    .cntmsk = 0xffull,
    .ngrp   = 1,
    .flags  = INTEL_X86_SPEC,
    .numasks= LIBPFM_ARRAY_SIZE(intel_spr_uops_dispatched),
    .umasks = intel_spr_uops_dispatched,
  },
  { .name   = "UOPS_EXECUTED",
    .desc   = "Uops executed.",
    .code   = 0x00b1,
    .modmsk = INTEL_V5_ATTRS,
    .cntmsk = 0xffull,
    .ngrp   = 1,
    .flags  = INTEL_X86_SPEC,
    .numasks= LIBPFM_ARRAY_SIZE(intel_spr_uops_executed),
    .umasks = intel_spr_uops_executed,
  },
  { .name   = "ARITH",
    .desc   = "Arithmetic operations.",
    .code   = 0x00b0,
    .modmsk = INTEL_V5_ATTRS,
    .cntmsk = 0xffull,
    .ngrp   = 1,
    .flags  = INTEL_X86_SPEC,
    .numasks= LIBPFM_ARRAY_SIZE(intel_spr_arith),
    .umasks = intel_spr_arith,
  },
  { .name   = "UOPS_ISSUED",
    .desc   = "Uops issued.",
    .code   = 0x00ae,
    .modmsk = INTEL_V5_ATTRS,
    .cntmsk = 0xffull,
    .ngrp   = 1,
    .flags  = INTEL_X86_SPEC,
    .numasks= LIBPFM_ARRAY_SIZE(intel_spr_uops_issued),
    .umasks = intel_spr_uops_issued,
  },
  { .name   = "INT_MISC",
    .desc   = "Miscellaneous interruptions.",
    .code   = 0x00ad,
    .modmsk = INTEL_V5_ATTRS,
    .cntmsk = 0xffull,
    .ngrp   = 1,
    .flags  = INTEL_X86_SPEC,
    .numasks= LIBPFM_ARRAY_SIZE(intel_spr_int_misc),
    .umasks = intel_spr_int_misc,
  },
  { .name   = "LSD",
    .desc   = "LSD (Loop Stream Detector) operations.",
    .code   = 0x00a8,
    .modmsk = INTEL_V5_ATTRS,
    .cntmsk = 0xffull,
    .ngrp   = 1,
    .flags  = INTEL_X86_SPEC,
    .numasks= LIBPFM_ARRAY_SIZE(intel_spr_lsd),
    .umasks = intel_spr_lsd,
  },
  { .name   = "EXE_ACTIVITY",
    .desc   = "Execution activity.",
    .code   = 0x00a6,
    .modmsk = INTEL_V5_ATTRS,
    .cntmsk = 0xffull,
    .ngrp   = 1,
    .flags  = INTEL_X86_SPEC,
    .numasks= LIBPFM_ARRAY_SIZE(intel_spr_exe_activity),
    .umasks = intel_spr_exe_activity,
  },
  { .name   = "RS",
    .desc   = "Reservation Station (RS) activity.",
    .code   = 0x00a5,
    .modmsk = INTEL_V5_ATTRS,
    .cntmsk = 0xffull,
    .ngrp   = 1,
    .flags  = INTEL_X86_SPEC,
    .numasks= LIBPFM_ARRAY_SIZE(intel_spr_rs),
    .umasks = intel_spr_rs,
  },
  { .name   = "CYCLE_ACTIVITY",
    .desc   = "Stalled cycles.",
    .code   = 0x00a3,
    .modmsk = INTEL_V5_ATTRS,
    .cntmsk = 0xfull,
    .ngrp   = 1,
    .flags  = INTEL_X86_SPEC,
    .numasks= LIBPFM_ARRAY_SIZE(intel_spr_cycle_activity),
    .umasks = intel_spr_cycle_activity,
  },
  { .name   = "RESOURCE_STALLS",
    .desc   = "Cycles where Allocation is stalled due to Resource Related reasons.",
    .code   = 0x00a2,
    .modmsk = INTEL_V5_ATTRS,
    .cntmsk = 0xffull,
    .ngrp   = 1,
    .flags  = INTEL_X86_SPEC,
    .numasks= LIBPFM_ARRAY_SIZE(intel_spr_resource_stalls),
    .umasks = intel_spr_resource_stalls,
  },
  { .name   = "IDQ_UOPS_NOT_DELIVERED",
    .desc   = "Uops not delivered.",
    .code   = 0x009c,
    .modmsk = INTEL_V5_ATTRS,
    .cntmsk = 0xffull,
    .ngrp   = 1,
    .flags  = INTEL_X86_SPEC,
    .numasks= LIBPFM_ARRAY_SIZE(intel_spr_idq_uops_not_delivered),
    .umasks = intel_spr_idq_uops_not_delivered,
  },
  { .name   = "DECODE",
    .desc   = "Decoder activity.",
    .code   = 0x0087,
    .modmsk = INTEL_V5_ATTRS,
    .cntmsk = 0xfull,
    .ngrp   = 1,
    .flags  = INTEL_X86_SPEC,
    .numasks= LIBPFM_ARRAY_SIZE(intel_spr_decode),
    .umasks = intel_spr_decode,
  },
  { .name   = "ICACHE_TAG",
    .desc   = "Instruction cache tagging.",
    .code   = 0x0083,
    .modmsk = INTEL_V5_ATTRS,
    .cntmsk = 0xfull,
    .ngrp   = 1,
    .flags  = INTEL_X86_SPEC,
    .numasks= LIBPFM_ARRAY_SIZE(intel_spr_icache_tag),
    .umasks = intel_spr_icache_tag,
  },
  { .name   = "ICACHE_DATA",
    .desc   = "Instruction cache.",
    .code   = 0x0080,
    .modmsk = INTEL_V5_ATTRS,
    .cntmsk = 0xfull,
    .ngrp   = 1,
    .flags  = INTEL_X86_SPEC,
    .numasks= LIBPFM_ARRAY_SIZE(intel_spr_icache_data),
    .umasks = intel_spr_icache_data,
  },
  { .name   = "IDQ",
    .desc   = "IDQ (Instruction Decoded Queue) operations.",
    .code   = 0x0079,
    .modmsk = INTEL_V5_ATTRS,
    .cntmsk = 0xfull,
    .ngrp   = 1,
    .flags  = INTEL_X86_SPEC,
    .numasks= LIBPFM_ARRAY_SIZE(intel_spr_idq),
    .umasks = intel_spr_idq,
  },
  { .name   = "UOPS_DECODED",
    .desc   = "Uops decoded.",
    .code   = 0x0076,
    .modmsk = INTEL_V5_ATTRS,
    .cntmsk = 0xfull,
    .ngrp   = 1,
    .flags  = INTEL_X86_SPEC,
    .numasks= LIBPFM_ARRAY_SIZE(intel_spr_uops_decoded),
    .umasks = intel_spr_uops_decoded,
  },
  { .name   = "INST_DECODED",
    .desc   = "Instruction decoded.",
    .code   = 0x0075,
    .modmsk = INTEL_V5_ATTRS,
    .cntmsk = 0xfull,
    .ngrp   = 1,
    .flags  = INTEL_X86_SPEC,
    .numasks= LIBPFM_ARRAY_SIZE(intel_spr_inst_decoded),
    .umasks = intel_spr_inst_decoded,
  },
  { .name   = "DSB2MITE_SWITCHES",
    .desc   = "DSB to MITE switches.",
    .code   = 0x0061,
    .modmsk = INTEL_V5_ATTRS,
    .cntmsk = 0xfull,
    .ngrp   = 1,
    .flags  = INTEL_X86_SPEC,
    .numasks= LIBPFM_ARRAY_SIZE(intel_spr_dsb2mite_switches),
    .umasks = intel_spr_dsb2mite_switches,
  },
  { .name   = "TX_MEM",
    .desc   = "Transactional memory.",
    .code   = 0x0054,
    .modmsk = INTEL_V5_ATTRS,
    .cntmsk = 0xfull,
    .ngrp   = 1,
    .flags  = INTEL_X86_SPEC,
    .numasks= LIBPFM_ARRAY_SIZE(intel_spr_tx_mem),
    .umasks = intel_spr_tx_mem,
  },
  { .name   = "L1D",
    .desc   = "L1D cache.",
    .code   = 0x0051,
    .modmsk = INTEL_V5_ATTRS,
    .cntmsk = 0xfull,
    .ngrp   = 1,
    .flags  = 0,
    .numasks= LIBPFM_ARRAY_SIZE(intel_spr_l1d),
    .umasks = intel_spr_l1d,
  },
  { .name   = "LOAD_HIT_PREFETCH",
    .desc   = "Load dispatches.",
    .code   = 0x004c,
    .modmsk = INTEL_V5_ATTRS,
    .cntmsk = 0xfull,
    .ngrp   = 1,
    .flags  = 0,
    .numasks= LIBPFM_ARRAY_SIZE(intel_spr_load_hit_prefetch),
    .umasks = intel_spr_load_hit_prefetch,
  },
  { .name   = "L1D_PEND_MISS",
    .desc   = "L1D pending misses.",
    .code   = 0x0048,
    .modmsk = INTEL_V5_ATTRS,
    .cntmsk = 0xfull,
    .ngrp   = 1,
    .flags  = 0,
    .numasks= LIBPFM_ARRAY_SIZE(intel_spr_l1d_pend_miss),
    .umasks = intel_spr_l1d_pend_miss,
  },
  { .name   = "MEMORY_ACTIVITY",
    .desc   = "Memory activity.",
    .code   = 0x0047,
    .modmsk = INTEL_V5_ATTRS,
    .cntmsk = 0xfull,
    .ngrp   = 1,
    .flags  = 0,
    .numasks= LIBPFM_ARRAY_SIZE(intel_spr_memory_activity),
    .umasks = intel_spr_memory_activity,
  },
  { .name   = "MEM_STORE_RETIRED",
    .desc   = "TBD",
    .code   = 0x0044,
    .modmsk = INTEL_V5_ATTRS,
    .cntmsk = 0xfull,
    .ngrp   = 1,
    .flags  = 0,
    .numasks= LIBPFM_ARRAY_SIZE(intel_spr_mem_store_retired),
    .umasks = intel_spr_mem_store_retired,
  },
  { .name   = "MEM_LOAD_COMPLETED",
    .desc   = "Completed demand load.",
    .code   = 0x0043,
    .modmsk = INTEL_V5_ATTRS,
    .cntmsk = 0xfull,
    .ngrp   = 1,
    .flags  = INTEL_X86_SPEC,
    .numasks= LIBPFM_ARRAY_SIZE(intel_spr_mem_load_completed),
    .umasks = intel_spr_mem_load_completed,
  },
  { .name   = "SW_PREFETCH_ACCESS",
    .desc   = "Software prefetches.",
    .code   = 0x0040,
    .modmsk = INTEL_V5_ATTRS,
    .cntmsk = 0xfull,
    .ngrp   = 1,
    .flags  = INTEL_X86_SPEC,
    .numasks= LIBPFM_ARRAY_SIZE(intel_spr_sw_prefetch_access),
    .umasks = intel_spr_sw_prefetch_access,
  },
  { .name   = "LONGEST_LAT_CACHE",
    .desc   = "L3 cache.",
    .code   = 0x002e,
    .modmsk = INTEL_V5_ATTRS,
    .cntmsk = 0xffull,
    .ngrp   = 1,
    .flags  = INTEL_X86_SPEC,
    .numasks= LIBPFM_ARRAY_SIZE(intel_spr_longest_lat_cache),
    .umasks = intel_spr_longest_lat_cache,
  },
  { .name   = "XQ",
    .desc   = "TBD",
    .code   = 0x002d,
    .modmsk = INTEL_V5_ATTRS,
    .cntmsk = 0xfull,
    .ngrp   = 1,
    .flags  = 0,
    .numasks= LIBPFM_ARRAY_SIZE(intel_spr_xq),
    .umasks = intel_spr_xq,
  },
  { .name   = "L2_LINES_OUT",
    .desc   = "L2 lines evicted.",
    .code   = 0x0026,
    .modmsk = INTEL_V5_ATTRS,
    .cntmsk = 0xfull,
    .ngrp   = 1,
    .flags  = INTEL_X86_SPEC,
    .numasks= LIBPFM_ARRAY_SIZE(intel_spr_l2_lines_out),
    .umasks = intel_spr_l2_lines_out,
  },
  { .name   = "L2_LINES_IN",
    .desc   = "L2 lines allocated.",
    .code   = 0x0025,
    .modmsk = INTEL_V5_ATTRS,
    .cntmsk = 0xfull,
    .ngrp   = 1,
    .flags  = INTEL_X86_SPEC,
    .numasks= LIBPFM_ARRAY_SIZE(intel_spr_l2_lines_in),
    .umasks = intel_spr_l2_lines_in,
  },
  { .name   = "L2_RQSTS",
    .desc   = "L2 requests.",
    .code   = 0x0024,
    .modmsk = INTEL_V5_ATTRS,
    .cntmsk = 0xfull,
    .ngrp   = 1,
    .flags  = INTEL_X86_SPEC,
    .numasks= LIBPFM_ARRAY_SIZE(intel_spr_l2_rqsts),
    .umasks = intel_spr_l2_rqsts,
  },
  { .name   = "OFFCORE_REQUESTS",
    .desc   = "Offcore requests.",
    .code   = 0x0021,
    .modmsk = INTEL_V5_ATTRS,
    .cntmsk = 0xfull,
    .ngrp   = 1,
    .flags  = INTEL_X86_SPEC,
    .numasks= LIBPFM_ARRAY_SIZE(intel_spr_offcore_requests),
    .umasks = intel_spr_offcore_requests,
  },
  { .name   = "OFFCORE_REQUESTS_OUTSTANDING",
    .desc   = "Outstanding offcore requests.",
    .code   = 0x0020,
    .modmsk = INTEL_V5_ATTRS,
    .cntmsk = 0xfull,
    .ngrp   = 1,
    .flags  = INTEL_X86_SPEC,
    .numasks= LIBPFM_ARRAY_SIZE(intel_spr_offcore_requests_outstanding),
    .umasks = intel_spr_offcore_requests_outstanding,
  },
  { .name   = "DTLB_STORE_MISSES",
    .desc   = "Data TLB store misses.",
    .code   = 0x0013,
    .modmsk = INTEL_V5_ATTRS,
    .cntmsk = 0xfull,
    .ngrp   = 1,
    .flags  = INTEL_X86_SPEC,
    .numasks= LIBPFM_ARRAY_SIZE(intel_spr_dtlb_store_misses),
    .umasks = intel_spr_dtlb_store_misses,
  },
  { .name   = "DTLB_LOAD_MISSES",
    .desc   = "Data TLB load misses.",
    .code   = 0x0012,
    .modmsk = INTEL_V5_ATTRS,
    .cntmsk = 0xfull,
    .ngrp   = 1,
    .flags  = INTEL_X86_SPEC,
    .numasks= LIBPFM_ARRAY_SIZE(intel_spr_dtlb_load_misses),
    .umasks = intel_spr_dtlb_load_misses,
  },
  { .name   = "ITLB_MISSES",
    .desc   = "Instruction TLB misses.",
    .code   = 0x0011,
    .modmsk = INTEL_V5_ATTRS,
    .cntmsk = 0xfull,
    .ngrp   = 1,
    .flags  = INTEL_X86_SPEC,
    .numasks= LIBPFM_ARRAY_SIZE(intel_spr_itlb_misses),
    .umasks = intel_spr_itlb_misses,
  },
  { .name   = "LD_BLOCKS",
    .desc   = "Blocking loads.",
    .code   = 0x0003,
    .modmsk = INTEL_V5_ATTRS,
    .cntmsk = 0xfull,
    .ngrp   = 1,
    .flags  = INTEL_X86_SPEC,
    .numasks= LIBPFM_ARRAY_SIZE(intel_spr_ld_blocks),
    .umasks = intel_spr_ld_blocks,
  },
  { .name   = "TOPDOWN",
    .desc   = "Topdown events.",
    .cntmsk = 0x800000000ull,
    .modmsk = INTEL_V5_ATTRS,
    .ngrp   = 1,
    .flags  = INTEL_X86_SPEC,
    .numasks= LIBPFM_ARRAY_SIZE(intel_spr_topdown),
    .umasks = intel_spr_topdown,
  },
  { .name   = "CPU_CLK_UNHALTED",
    .desc   = "Cycles in unhalted state.",
    .code   = 0x003c,
    .modmsk = INTEL_V5_ATTRS,
    .cntmsk = 0x1ull,
    .ngrp   = 1,
    .flags  = INTEL_X86_SPEC,
    .numasks= LIBPFM_ARRAY_SIZE(intel_spr_cpu_clk_unhalted),
    .umasks = intel_spr_cpu_clk_unhalted,
  },
  { .name   = "INST_RETIRED",
    .desc   = "Number of instructions retired.",
    .code   = 0x00c0,
    .modmsk = INTEL_V5_ATTRS,
    .cntmsk = 0x1ull,
    .ngrp   = 1,
    .flags  = INTEL_X86_PEBS,
    .numasks= LIBPFM_ARRAY_SIZE(intel_spr_inst_retired),
    .umasks = intel_spr_inst_retired,
  },
  { .name   = "OCR",
    .desc   = "Counts demand data reads that have any type of response.",
    .code   = 0x012a,
    .modmsk = INTEL_V5_ATTRS,
    .cntmsk = 0xfull,
    .ngrp   = 1,
    .flags  = INTEL_X86_SPEC | INTEL_X86_NHM_OFFCORE,
    .numasks= LIBPFM_ARRAY_SIZE(intel_spr_ocr),
    .umasks = intel_spr_ocr,
  },
  { .name   = "OFFCORE_RESPONSE_0",
    .desc   = "Offcore response event",
    .code   = 0x012a,
    .modmsk = INTEL_V5_ATTRS,
    .cntmsk = 0xfull,
    .ngrp   = 1,
    .equiv  = "OCR",
    .flags  = INTEL_X86_SPEC | INTEL_X86_NHM_OFFCORE,
    .numasks= LIBPFM_ARRAY_SIZE(intel_spr_ocr),
    .umasks = intel_spr_ocr,
  },
  { .name   = "OFFCORE_RESPONSE_1",
    .desc   = "Offcore response event",
    .code   = 0x012b,
    .modmsk = INTEL_V5_ATTRS,
    .cntmsk = 0xfull,
    .ngrp   = 1,
    .equiv  = "OCR",
    .flags  = INTEL_X86_SPEC | INTEL_X86_NHM_OFFCORE,
    .numasks= LIBPFM_ARRAY_SIZE(intel_spr_ocr),
    .umasks = intel_spr_ocr,
  },
};
