.github,aya,test: clean up interface and script per review comments

- .github: Ensure we only download the debug package that matches the kernel we
  downloaded.
- aya: Constrain the breakpoint interface to only valid combinations of
  options.
- test: Document what the test is actually doing for future readers who might
  be unfamiliar with modprobe_path.
reviewable/pr1365/r7
Friday Ortiz 3 weeks ago committed by GitHub
parent 38e3f7fce2
commit 61e0aef8b6
No known key found for this signature in database
GPG Key ID: B5690EEEBB952194

@ -27,20 +27,22 @@ for VERSION in "${VERSIONS[@]}"; do
FILES+=("$match") FILES+=("$match")
# The debug package contains the actual System.map. Debian has transitioned # The debug package contains the actual System.map. Debian has transitioned
# between -dbg and -dbgsym suffixes, so try both. # between -dbg and -dbgsym suffixes, so match either for the specific kernel
DEBUG_REGEX_BASE="linux-image-${VERSION//./\\.}\\.[0-9]+(-[0-9]+)?(\+bpo|\+deb[0-9]+)?-cloud-${ARCHITECTURE}-" # we just selected.
debug_match="" kernel_basename=$(basename "$match")
for debug_suffix in dbg dbgsym; do kernel_prefix=${kernel_basename%%_*}
regex="${DEBUG_REGEX_BASE}${debug_suffix}_.*\\.deb" kernel_suffix=${kernel_basename#${kernel_prefix}_}
debug_match=$(printf '%s\n' "$URLS" | grep -E "$regex" | sort -V | tail -n1 || true) base_prefix=${kernel_prefix%-unsigned}
if [[ -n "$debug_match" ]]; then
break base_prefix_regex=$(printf '%s\n' "$base_prefix" | sed 's/[][(){}.^$*+?|\\-]/\\&/g')
fi kernel_suffix_regex=$(printf '%s\n' "$kernel_suffix" | sed 's/[][(){}.^$*+?|\\-]/\\&/g')
done
if [[ -z "$debug_match" ]]; then DEBUG_REGEX="${base_prefix_regex}-dbg(sym)?_${kernel_suffix_regex}"
printf 'Failed to locate debug package for VERSION=%s (tried dbg/dbgsym)\n' "$VERSION" >&2 debug_match=$(printf '%s\n' "$URLS" | grep -E "$DEBUG_REGEX" | sort -V | tail -n1) || {
printf 'Failed to locate debug package matching %s\n%s\nVERSION=%s\nREGEX=%s\n' \
"$kernel_basename" "$URLS" "$VERSION" "$DEBUG_REGEX" >&2
exit 1 exit 1
fi }
FILES+=("$debug_match") FILES+=("$debug_match")
done done

@ -236,10 +236,6 @@ pub enum ProgramError {
/// An error occurred while working with Netlink. /// An error occurred while working with Netlink.
#[error(transparent)] #[error(transparent)]
NetlinkError(#[from] NetlinkError), NetlinkError(#[from] NetlinkError),
/// The perf event breakpoint is underspecified
#[error("the breakpoint description is missing or incomplete")]
IncompleteBreakpoint,
} }
/// A [`Program`] file descriptor. /// A [`Program`] file descriptor.

@ -3,10 +3,8 @@
use std::os::fd::AsFd as _; use std::os::fd::AsFd as _;
use aya_obj::generated::{ use aya_obj::generated::{
HW_BREAKPOINT_EMPTY, HW_BREAKPOINT_INVALID, HW_BREAKPOINT_LEN_1, HW_BREAKPOINT_LEN_2, HW_BREAKPOINT_LEN_1, HW_BREAKPOINT_LEN_2, HW_BREAKPOINT_LEN_4, HW_BREAKPOINT_LEN_8,
HW_BREAKPOINT_LEN_3, HW_BREAKPOINT_LEN_4, HW_BREAKPOINT_LEN_5, HW_BREAKPOINT_LEN_6, bpf_link_type,
HW_BREAKPOINT_LEN_7, HW_BREAKPOINT_LEN_8, HW_BREAKPOINT_R, HW_BREAKPOINT_RW, HW_BREAKPOINT_W,
HW_BREAKPOINT_X, bpf_link_type,
bpf_prog_type::BPF_PROG_TYPE_PERF_EVENT, bpf_prog_type::BPF_PROG_TYPE_PERF_EVENT,
perf_hw_cache_id, perf_hw_cache_op_id, perf_hw_cache_op_result_id, perf_hw_id, perf_sw_ids, perf_hw_cache_id, perf_hw_cache_op_id, perf_hw_cache_op_result_id, perf_hw_id, perf_sw_ids,
perf_type_id, perf_type_id,
@ -21,7 +19,7 @@ use crate::{
FdLink, LinkError, ProgramData, ProgramError, ProgramType, impl_try_into_fdlink, FdLink, LinkError, ProgramData, ProgramError, ProgramType, impl_try_into_fdlink,
links::define_link_wrapper, links::define_link_wrapper,
load_program, load_program,
perf_attach::{PerfLinkIdInner, PerfLinkInner}, perf_attach::{PerfLinkIdInner, PerfLinkInner, perf_attach},
}, },
sys::{SyscallError, bpf_link_get_info_by_fd, perf_event_open}, sys::{SyscallError, bpf_link_get_info_by_fd, perf_event_open},
}; };
@ -62,16 +60,7 @@ pub enum PerfEventConfig {
}, },
/// A hardware breakpoint. /// A hardware breakpoint.
#[doc(alias = "PERF_TYPE_BREAKPOINT")] #[doc(alias = "PERF_TYPE_BREAKPOINT")]
Breakpoint { Breakpoint(BreakpointConfig),
/// The address to set the breakpoint on
address: u64,
/// The breakpoint size. For HwBreakpointX this must be sizeof(long). For
/// all other types it should be one of HwBreakpointLen1, HwBreakpointLen2,,
/// HwBreakpointLen4 or HwBreakpointLen8.
length: PerfBreakpointSize,
/// The breakpoint type, one of HW_BREAKPOINT_{R,W,RW,X}
type_: PerfBreakpointType,
},
/// The dynamic PMU (Performance Monitor Unit) event to report. /// The dynamic PMU (Performance Monitor Unit) event to report.
/// ///
/// Available PMU's may be found under `/sys/bus/event_source/devices`. /// Available PMU's may be found under `/sys/bus/event_source/devices`.
@ -290,38 +279,51 @@ impl HwCacheResult {
} }
} }
/// Type of hardware breakpoint, determines if we break on read, write, or execute. /// Type of hardware breakpoint, determines if we break on read, write, or
#[repr(u32)] /// execute, or if there should be no breakpoint on the given address.
#[derive(Debug, Clone, Copy)] #[derive(Debug, Clone, Copy)]
pub enum PerfBreakpointType { pub enum BreakpointConfig {
/// HW_BREAKPOINT_EMPTY /// HW_BREAKPOINT_EMPTY, no breakpoint.
#[doc(alias = "HW_BREAKPOINT_EMPTY")] #[doc(alias = "HW_BREAKPOINT_EMPTY")]
HwBreakpointEmpty = HW_BREAKPOINT_EMPTY, Empty {
/// HW_BREAKPOINT_R /// The size of the breakpoint being measured.
size: PerfBreakpointSize,
/// The address of the breakpoint.
address: u64,
},
/// HW_BREAKPOINT_R, count when we read the memory location.
#[doc(alias = "HW_BREAKPOINT_R")] #[doc(alias = "HW_BREAKPOINT_R")]
HwBreakpointR = HW_BREAKPOINT_R, Read {
/// HW_BREAKPOINT_W /// The size of the breakpoint being measured.
size: PerfBreakpointSize,
/// The address of the breakpoint.
address: u64,
},
/// HW_BREAKPOINT_W, count when we write the memory location.
#[doc(alias = "HW_BREAKPOINT_W")] #[doc(alias = "HW_BREAKPOINT_W")]
HwBreakpointW = HW_BREAKPOINT_W, Write {
/// HW_BREAKPOINT_RW /// The size of the breakpoint being measured.
size: PerfBreakpointSize,
/// The address of the breakpoint.
address: u64,
},
/// HW_BREAKPOINT_RW, count when we read or write the memory location.
#[doc(alias = "HW_BREAKPOINT_RW")] #[doc(alias = "HW_BREAKPOINT_RW")]
HwBreakpointRW = HW_BREAKPOINT_RW, ReadWrite {
/// HW_BREAKPOINT_X /// The size of the breakpoint being measured.
size: PerfBreakpointSize,
/// The address of the breakpoint.
address: u64,
},
/// HW_BREAKPOINT_X, count when we execute code at the memory location.
#[doc(alias = "HW_BREAKPOINT_X")] #[doc(alias = "HW_BREAKPOINT_X")]
HwBreakpointX = HW_BREAKPOINT_X, Execute {
/// HW_BREAKPOINT_INVALID /// The address of the breakpoint.
#[doc(alias = "HW_BREAKPOINT_INVALID")] address: u64,
HwBreakpointInvalid = HW_BREAKPOINT_INVALID, },
}
impl PerfBreakpointType {
pub(crate) const fn into_primitive(self) -> u32 {
const _: [(); 4] = [(); std::mem::size_of::<PerfBreakpointType>()];
self as u32
}
} }
/// The size of the breakpoint being measured /// The size of the breakpoint being observed in bytes.
#[repr(u64)] #[repr(u64)]
#[derive(Debug, Clone, Copy)] #[derive(Debug, Clone, Copy)]
pub enum PerfBreakpointSize { pub enum PerfBreakpointSize {
@ -331,21 +333,9 @@ pub enum PerfBreakpointSize {
/// HW_BREAKPOINT_LEN_2 /// HW_BREAKPOINT_LEN_2
#[doc(alias = "HW_BREAKPOINT_LEN_2")] #[doc(alias = "HW_BREAKPOINT_LEN_2")]
HwBreakpointLen2 = HW_BREAKPOINT_LEN_2 as u64, HwBreakpointLen2 = HW_BREAKPOINT_LEN_2 as u64,
/// HW_BREAKPOINT_LEN_3
#[doc(alias = "HW_BREAKPOINT_LEN_3")]
HwBreakpointLen3 = HW_BREAKPOINT_LEN_3 as u64,
/// HW_BREAKPOINT_LEN_4 /// HW_BREAKPOINT_LEN_4
#[doc(alias = "HW_BREAKPOINT_LEN_4")] #[doc(alias = "HW_BREAKPOINT_LEN_4")]
HwBreakpointLen4 = HW_BREAKPOINT_LEN_4 as u64, HwBreakpointLen4 = HW_BREAKPOINT_LEN_4 as u64,
/// HW_BREAKPOINT_LEN_5
#[doc(alias = "HW_BREAKPOINT_LEN_5")]
HwBreakpointLen5 = HW_BREAKPOINT_LEN_5 as u64,
/// HW_BREAKPOINT_LEN_6
#[doc(alias = "HW_BREAKPOINT_LEN_6")]
HwBreakpointLen6 = HW_BREAKPOINT_LEN_6 as u64,
/// HW_BREAKPOINT_LEN_7
#[doc(alias = "HW_BREAKPOINT_LEN_7")]
HwBreakpointLen7 = HW_BREAKPOINT_LEN_7 as u64,
/// HW_BREAKPOINT_LEN_8 /// HW_BREAKPOINT_LEN_8
#[doc(alias = "HW_BREAKPOINT_LEN_8")] #[doc(alias = "HW_BREAKPOINT_LEN_8")]
HwBreakpointLen8 = HW_BREAKPOINT_LEN_8 as u64, HwBreakpointLen8 = HW_BREAKPOINT_LEN_8 as u64,
@ -356,6 +346,16 @@ impl PerfBreakpointSize {
const _: [(); 8] = [(); std::mem::size_of::<PerfBreakpointSize>()]; const _: [(); 8] = [(); std::mem::size_of::<PerfBreakpointSize>()];
self as u64 self as u64
} }
pub(crate) const fn from_primitive(size: u64) -> Self {
match size {
n if n == Self::HwBreakpointLen1.into_primitive() => Self::HwBreakpointLen1,
n if n == Self::HwBreakpointLen2.into_primitive() => Self::HwBreakpointLen2,
n if n == Self::HwBreakpointLen4.into_primitive() => Self::HwBreakpointLen4,
n if n == Self::HwBreakpointLen8.into_primitive() => Self::HwBreakpointLen8,
_ => panic!("invalid hardware breakpoint size"),
}
}
} }
/// Sample Policy /// Sample Policy
@ -473,6 +473,7 @@ impl PerfEvent {
let prog_fd = self.fd()?; let prog_fd = self.fd()?;
let prog_fd = prog_fd.as_fd(); let prog_fd = prog_fd.as_fd();
let mut breakpoint = None;
let (perf_type, config) = match perf_config { let (perf_type, config) = match perf_config {
PerfEventConfig::Pmu { pmu_type, config } => (pmu_type, config), PerfEventConfig::Pmu { pmu_type, config } => (pmu_type, config),
PerfEventConfig::Hardware(hw_event) => ( PerfEventConfig::Hardware(hw_event) => (
@ -497,11 +498,10 @@ impl PerfEvent {
| (u64::from(result.into_primitive()) << 16), | (u64::from(result.into_primitive()) << 16),
), ),
PerfEventConfig::Raw { event_id } => (perf_type_id_to_u32(PERF_TYPE_RAW), event_id), PerfEventConfig::Raw { event_id } => (perf_type_id_to_u32(PERF_TYPE_RAW), event_id),
PerfEventConfig::Breakpoint { PerfEventConfig::Breakpoint(config) => {
address: _, breakpoint = Some(config);
length: _, (perf_type_id_to_u32(PERF_TYPE_BREAKPOINT), 0)
type_: _, }
} => (perf_type_id_to_u32(PERF_TYPE_BREAKPOINT), 0),
}; };
let (sample_period, sample_frequency) = match sample_policy { let (sample_period, sample_frequency) = match sample_policy {
SamplePolicy::Period(period) => (period, None), SamplePolicy::Period(period) => (period, None),
@ -521,18 +521,16 @@ impl PerfEvent {
cpu, cpu,
sample_period, sample_period,
sample_frequency, sample_frequency,
// wakeup=true for breakpoints, false for all other types
perf_type == perf_type_id_to_u32(PERF_TYPE_BREAKPOINT),
inherit, inherit,
0, 0,
Some(perf_config), breakpoint,
) )
.map_err(|io_error| SyscallError { .map_err(|io_error| SyscallError {
call: "perf_event_open", call: "perf_event_open",
io_error, io_error,
})?; })?;
let link = crate::programs::perf_attach(prog_fd, fd, None /* cookie */)?; let link = perf_attach(prog_fd, fd, None /* cookie */)?;
self.data.links.insert(PerfEventLink::new(link)) self.data.links.insert(PerfEventLink::new(link))
} }
} }

@ -5,6 +5,7 @@ use std::{
}; };
use aya_obj::generated::{ use aya_obj::generated::{
HW_BREAKPOINT_EMPTY, HW_BREAKPOINT_R, HW_BREAKPOINT_RW, HW_BREAKPOINT_W, HW_BREAKPOINT_X,
PERF_FLAG_FD_CLOEXEC, perf_event_attr, PERF_FLAG_FD_CLOEXEC, perf_event_attr,
perf_event_sample_format::PERF_SAMPLE_RAW, perf_event_sample_format::PERF_SAMPLE_RAW,
perf_sw_ids::PERF_COUNT_SW_BPF_OUTPUT, perf_sw_ids::PERF_COUNT_SW_BPF_OUTPUT,
@ -13,7 +14,7 @@ use aya_obj::generated::{
use libc::pid_t; use libc::pid_t;
use super::{PerfEventIoctlRequest, Syscall, syscall}; use super::{PerfEventIoctlRequest, Syscall, syscall};
use crate::programs::perf_event::PerfEventConfig; use crate::programs::perf_event::{BreakpointConfig, PerfBreakpointSize};
#[expect(clippy::too_many_arguments)] #[expect(clippy::too_many_arguments)]
pub(crate) fn perf_event_open( pub(crate) fn perf_event_open(
@ -23,10 +24,9 @@ pub(crate) fn perf_event_open(
cpu: c_int, cpu: c_int,
sample_period: u64, sample_period: u64,
sample_frequency: Option<u64>, sample_frequency: Option<u64>,
wakeup: bool,
inherit: bool, inherit: bool,
flags: u32, flags: u32,
perf_config: Option<PerfEventConfig>, breakpoint: Option<BreakpointConfig>,
) -> io::Result<crate::MockableFd> { ) -> io::Result<crate::MockableFd> {
let mut attr = unsafe { mem::zeroed::<perf_event_attr>() }; let mut attr = unsafe { mem::zeroed::<perf_event_attr>() };
@ -35,7 +35,6 @@ pub(crate) fn perf_event_open(
attr.type_ = perf_type; attr.type_ = perf_type;
attr.sample_type = PERF_SAMPLE_RAW as u64; attr.sample_type = PERF_SAMPLE_RAW as u64;
attr.set_inherit(if inherit { 1 } else { 0 }); attr.set_inherit(if inherit { 1 } else { 0 });
attr.__bindgen_anon_2.wakeup_events = u32::from(wakeup);
if let Some(frequency) = sample_frequency { if let Some(frequency) = sample_frequency {
attr.set_freq(1); attr.set_freq(1);
@ -44,16 +43,25 @@ pub(crate) fn perf_event_open(
attr.__bindgen_anon_1.sample_period = sample_period; attr.__bindgen_anon_1.sample_period = sample_period;
} }
if let Some(PerfEventConfig::Breakpoint { if let Some(bp) = breakpoint {
let (type_, length, address) = match bp {
BreakpointConfig::Empty { size, address } => (HW_BREAKPOINT_EMPTY, size, address),
BreakpointConfig::Read { size, address } => (HW_BREAKPOINT_R, size, address),
BreakpointConfig::Write { size, address } => (HW_BREAKPOINT_W, size, address),
BreakpointConfig::ReadWrite { size, address } => (HW_BREAKPOINT_RW, size, address),
BreakpointConfig::Execute { address } => (
HW_BREAKPOINT_X,
PerfBreakpointSize::from_primitive(std::mem::size_of::<libc::c_long>() as u64),
address, address,
length, ),
type_, };
}) = perf_config attr.bp_type = type_;
{
attr.bp_type = type_.into_primitive();
attr.__bindgen_anon_3.bp_addr = address; attr.__bindgen_anon_3.bp_addr = address;
attr.__bindgen_anon_4.bp_len = length.into_primitive(); attr.__bindgen_anon_4.bp_len = length.into_primitive();
attr.set_precise_ip(2); attr.set_precise_ip(2);
attr.__bindgen_anon_2.wakeup_events = u32::from(true);
} else {
attr.__bindgen_anon_2.wakeup_events = u32::from(false);
} }
perf_event_sys(attr, pid, cpu, flags) perf_event_sys(attr, pid, cpu, flags)
@ -68,7 +76,6 @@ pub(crate) fn perf_event_open_bpf(cpu: c_int) -> io::Result<crate::MockableFd> {
1, 1,
None, None,
true, true,
false,
PERF_FLAG_FD_CLOEXEC, PERF_FLAG_FD_CLOEXEC,
None, None,
) )

@ -7,10 +7,7 @@ use aya::{
Ebpf, Ebpf,
programs::{ programs::{
PerfEventScope, SamplePolicy, PerfEventScope, SamplePolicy,
perf_event::{ perf_event::{BreakpointConfig, PerfBreakpointSize::HwBreakpointLen1, PerfEventConfig},
PerfBreakpointSize::HwBreakpointLen1, PerfBreakpointType::HwBreakpointRW,
PerfEventConfig,
},
}, },
util::online_cpus, util::online_cpus,
}; };
@ -72,6 +69,10 @@ fn find_kallsyms_symbol(sym: &str) -> Option<u64> {
#[test_log::test] #[test_log::test]
fn perf_event_bp() { fn perf_event_bp() {
let mut bpf = Ebpf::load(crate::PERF_EVENT_BP).unwrap(); let mut bpf = Ebpf::load(crate::PERF_EVENT_BP).unwrap();
// Search for the address of modprobe_path. Prefer to grab it directly from
// kallsyms, but if it's not there we can grab it from System.map and apply
// the kaslr offset.
let attach_addr = if let Some(addr) = find_kallsyms_symbol("modprobe_path") { let attach_addr = if let Some(addr) = find_kallsyms_symbol("modprobe_path") {
addr addr
} else { } else {
@ -91,15 +92,13 @@ fn perf_event_bp() {
.unwrap(); .unwrap();
prog.load().unwrap(); prog.load().unwrap();
// attach hardware breakpoint to modprobe_path global
for cpu in online_cpus().unwrap() { for cpu in online_cpus().unwrap() {
info!("attaching to cpu {cpu}"); info!("attaching to cpu {cpu}");
prog.attach( prog.attach(
PerfEventConfig::Breakpoint { PerfEventConfig::Breakpoint(BreakpointConfig::ReadWrite {
address: attach_addr, address: attach_addr,
length: HwBreakpointLen1, size: HwBreakpointLen1,
type_: HwBreakpointRW, }),
},
PerfEventScope::AllProcessesOneCpu { cpu }, PerfEventScope::AllProcessesOneCpu { cpu },
SamplePolicy::Period(1), SamplePolicy::Period(1),
true, true,
@ -107,10 +106,14 @@ fn perf_event_bp() {
.unwrap(); .unwrap();
} }
// trigger hardware breakpoint by reading modprobe_path via procfs // Trigger the hardware breakpoint by reading /proc/sys/kernel/modprobe, the
let _ = fs::read_to_string("/proc/sys/kernel/modprobe"); // sysctl connected to modprobe_path.
//
// See: https://elixir.bootlin.com/linux/v6.1.155/source/kernel/sysctl.c#L1770
fs::read_to_string("/proc/sys/kernel/modprobe").expect("failed to read modprobe");
// assert that the map contains an entry for this process // Assert that the map contains an entry for this process, and that we read
// the address we expected to.
let map: aya::maps::HashMap<_, u32, u64> = let map: aya::maps::HashMap<_, u32, u64> =
aya::maps::HashMap::try_from(bpf.map_mut("READERS").unwrap()).unwrap(); aya::maps::HashMap::try_from(bpf.map_mut("READERS").unwrap()).unwrap();
let tgid = std::process::id(); let tgid = std::process::id();

@ -5299,6 +5299,54 @@ pub fn aya::programs::perf_attach::PerfLinkId::borrow_mut(&mut self) -> &mut T
impl<T> core::convert::From<T> for aya::programs::perf_attach::PerfLinkId impl<T> core::convert::From<T> for aya::programs::perf_attach::PerfLinkId
pub fn aya::programs::perf_attach::PerfLinkId::from(t: T) -> T pub fn aya::programs::perf_attach::PerfLinkId::from(t: T) -> T
pub mod aya::programs::perf_event pub mod aya::programs::perf_event
pub enum aya::programs::perf_event::BreakpointConfig
pub aya::programs::perf_event::BreakpointConfig::Empty
pub aya::programs::perf_event::BreakpointConfig::Empty::address: u64
pub aya::programs::perf_event::BreakpointConfig::Empty::size: aya::programs::perf_event::PerfBreakpointSize
pub aya::programs::perf_event::BreakpointConfig::Execute
pub aya::programs::perf_event::BreakpointConfig::Execute::address: u64
pub aya::programs::perf_event::BreakpointConfig::Read
pub aya::programs::perf_event::BreakpointConfig::Read::address: u64
pub aya::programs::perf_event::BreakpointConfig::Read::size: aya::programs::perf_event::PerfBreakpointSize
pub aya::programs::perf_event::BreakpointConfig::ReadWrite
pub aya::programs::perf_event::BreakpointConfig::ReadWrite::address: u64
pub aya::programs::perf_event::BreakpointConfig::ReadWrite::size: aya::programs::perf_event::PerfBreakpointSize
pub aya::programs::perf_event::BreakpointConfig::Write
pub aya::programs::perf_event::BreakpointConfig::Write::address: u64
pub aya::programs::perf_event::BreakpointConfig::Write::size: aya::programs::perf_event::PerfBreakpointSize
impl core::clone::Clone for aya::programs::perf_event::BreakpointConfig
pub fn aya::programs::perf_event::BreakpointConfig::clone(&self) -> aya::programs::perf_event::BreakpointConfig
impl core::fmt::Debug for aya::programs::perf_event::BreakpointConfig
pub fn aya::programs::perf_event::BreakpointConfig::fmt(&self, f: &mut core::fmt::Formatter<'_>) -> core::fmt::Result
impl core::marker::Copy for aya::programs::perf_event::BreakpointConfig
impl core::marker::Freeze for aya::programs::perf_event::BreakpointConfig
impl core::marker::Send for aya::programs::perf_event::BreakpointConfig
impl core::marker::Sync for aya::programs::perf_event::BreakpointConfig
impl core::marker::Unpin for aya::programs::perf_event::BreakpointConfig
impl core::panic::unwind_safe::RefUnwindSafe for aya::programs::perf_event::BreakpointConfig
impl core::panic::unwind_safe::UnwindSafe for aya::programs::perf_event::BreakpointConfig
impl<T, U> core::convert::Into<U> for aya::programs::perf_event::BreakpointConfig where U: core::convert::From<T>
pub fn aya::programs::perf_event::BreakpointConfig::into(self) -> U
impl<T, U> core::convert::TryFrom<U> for aya::programs::perf_event::BreakpointConfig where U: core::convert::Into<T>
pub type aya::programs::perf_event::BreakpointConfig::Error = core::convert::Infallible
pub fn aya::programs::perf_event::BreakpointConfig::try_from(value: U) -> core::result::Result<T, <T as core::convert::TryFrom<U>>::Error>
impl<T, U> core::convert::TryInto<U> for aya::programs::perf_event::BreakpointConfig where U: core::convert::TryFrom<T>
pub type aya::programs::perf_event::BreakpointConfig::Error = <U as core::convert::TryFrom<T>>::Error
pub fn aya::programs::perf_event::BreakpointConfig::try_into(self) -> core::result::Result<U, <U as core::convert::TryFrom<T>>::Error>
impl<T> alloc::borrow::ToOwned for aya::programs::perf_event::BreakpointConfig where T: core::clone::Clone
pub type aya::programs::perf_event::BreakpointConfig::Owned = T
pub fn aya::programs::perf_event::BreakpointConfig::clone_into(&self, target: &mut T)
pub fn aya::programs::perf_event::BreakpointConfig::to_owned(&self) -> T
impl<T> core::any::Any for aya::programs::perf_event::BreakpointConfig where T: 'static + ?core::marker::Sized
pub fn aya::programs::perf_event::BreakpointConfig::type_id(&self) -> core::any::TypeId
impl<T> core::borrow::Borrow<T> for aya::programs::perf_event::BreakpointConfig where T: ?core::marker::Sized
pub fn aya::programs::perf_event::BreakpointConfig::borrow(&self) -> &T
impl<T> core::borrow::BorrowMut<T> for aya::programs::perf_event::BreakpointConfig where T: ?core::marker::Sized
pub fn aya::programs::perf_event::BreakpointConfig::borrow_mut(&mut self) -> &mut T
impl<T> core::clone::CloneToUninit for aya::programs::perf_event::BreakpointConfig where T: core::clone::Clone
pub unsafe fn aya::programs::perf_event::BreakpointConfig::clone_to_uninit(&self, dest: *mut u8)
impl<T> core::convert::From<T> for aya::programs::perf_event::BreakpointConfig
pub fn aya::programs::perf_event::BreakpointConfig::from(t: T) -> T
#[repr(u32)] pub enum aya::programs::perf_event::HardwareEvent #[repr(u32)] pub enum aya::programs::perf_event::HardwareEvent
pub aya::programs::perf_event::HardwareEvent::BranchInstructions = 4 pub aya::programs::perf_event::HardwareEvent::BranchInstructions = 4
pub aya::programs::perf_event::HardwareEvent::BranchMisses = 5 pub aya::programs::perf_event::HardwareEvent::BranchMisses = 5
@ -5460,11 +5508,7 @@ pub fn aya::programs::perf_event::HwCacheResult::from(t: T) -> T
#[repr(u64)] pub enum aya::programs::perf_event::PerfBreakpointSize #[repr(u64)] pub enum aya::programs::perf_event::PerfBreakpointSize
pub aya::programs::perf_event::PerfBreakpointSize::HwBreakpointLen1 = 1 pub aya::programs::perf_event::PerfBreakpointSize::HwBreakpointLen1 = 1
pub aya::programs::perf_event::PerfBreakpointSize::HwBreakpointLen2 = 2 pub aya::programs::perf_event::PerfBreakpointSize::HwBreakpointLen2 = 2
pub aya::programs::perf_event::PerfBreakpointSize::HwBreakpointLen3 = 3
pub aya::programs::perf_event::PerfBreakpointSize::HwBreakpointLen4 = 4 pub aya::programs::perf_event::PerfBreakpointSize::HwBreakpointLen4 = 4
pub aya::programs::perf_event::PerfBreakpointSize::HwBreakpointLen5 = 5
pub aya::programs::perf_event::PerfBreakpointSize::HwBreakpointLen6 = 6
pub aya::programs::perf_event::PerfBreakpointSize::HwBreakpointLen7 = 7
pub aya::programs::perf_event::PerfBreakpointSize::HwBreakpointLen8 = 8 pub aya::programs::perf_event::PerfBreakpointSize::HwBreakpointLen8 = 8
impl core::clone::Clone for aya::programs::perf_event::PerfBreakpointSize impl core::clone::Clone for aya::programs::perf_event::PerfBreakpointSize
pub fn aya::programs::perf_event::PerfBreakpointSize::clone(&self) -> aya::programs::perf_event::PerfBreakpointSize pub fn aya::programs::perf_event::PerfBreakpointSize::clone(&self) -> aya::programs::perf_event::PerfBreakpointSize
@ -5499,51 +5543,8 @@ impl<T> core::clone::CloneToUninit for aya::programs::perf_event::PerfBreakpoint
pub unsafe fn aya::programs::perf_event::PerfBreakpointSize::clone_to_uninit(&self, dest: *mut u8) pub unsafe fn aya::programs::perf_event::PerfBreakpointSize::clone_to_uninit(&self, dest: *mut u8)
impl<T> core::convert::From<T> for aya::programs::perf_event::PerfBreakpointSize impl<T> core::convert::From<T> for aya::programs::perf_event::PerfBreakpointSize
pub fn aya::programs::perf_event::PerfBreakpointSize::from(t: T) -> T pub fn aya::programs::perf_event::PerfBreakpointSize::from(t: T) -> T
#[repr(u32)] pub enum aya::programs::perf_event::PerfBreakpointType
pub aya::programs::perf_event::PerfBreakpointType::HwBreakpointEmpty = 0
pub aya::programs::perf_event::PerfBreakpointType::HwBreakpointInvalid = 7
pub aya::programs::perf_event::PerfBreakpointType::HwBreakpointR = 1
pub aya::programs::perf_event::PerfBreakpointType::HwBreakpointRW = 3
pub aya::programs::perf_event::PerfBreakpointType::HwBreakpointW = 2
pub aya::programs::perf_event::PerfBreakpointType::HwBreakpointX = 4
impl core::clone::Clone for aya::programs::perf_event::PerfBreakpointType
pub fn aya::programs::perf_event::PerfBreakpointType::clone(&self) -> aya::programs::perf_event::PerfBreakpointType
impl core::fmt::Debug for aya::programs::perf_event::PerfBreakpointType
pub fn aya::programs::perf_event::PerfBreakpointType::fmt(&self, f: &mut core::fmt::Formatter<'_>) -> core::fmt::Result
impl core::marker::Copy for aya::programs::perf_event::PerfBreakpointType
impl core::marker::Freeze for aya::programs::perf_event::PerfBreakpointType
impl core::marker::Send for aya::programs::perf_event::PerfBreakpointType
impl core::marker::Sync for aya::programs::perf_event::PerfBreakpointType
impl core::marker::Unpin for aya::programs::perf_event::PerfBreakpointType
impl core::panic::unwind_safe::RefUnwindSafe for aya::programs::perf_event::PerfBreakpointType
impl core::panic::unwind_safe::UnwindSafe for aya::programs::perf_event::PerfBreakpointType
impl<T, U> core::convert::Into<U> for aya::programs::perf_event::PerfBreakpointType where U: core::convert::From<T>
pub fn aya::programs::perf_event::PerfBreakpointType::into(self) -> U
impl<T, U> core::convert::TryFrom<U> for aya::programs::perf_event::PerfBreakpointType where U: core::convert::Into<T>
pub type aya::programs::perf_event::PerfBreakpointType::Error = core::convert::Infallible
pub fn aya::programs::perf_event::PerfBreakpointType::try_from(value: U) -> core::result::Result<T, <T as core::convert::TryFrom<U>>::Error>
impl<T, U> core::convert::TryInto<U> for aya::programs::perf_event::PerfBreakpointType where U: core::convert::TryFrom<T>
pub type aya::programs::perf_event::PerfBreakpointType::Error = <U as core::convert::TryFrom<T>>::Error
pub fn aya::programs::perf_event::PerfBreakpointType::try_into(self) -> core::result::Result<U, <U as core::convert::TryFrom<T>>::Error>
impl<T> alloc::borrow::ToOwned for aya::programs::perf_event::PerfBreakpointType where T: core::clone::Clone
pub type aya::programs::perf_event::PerfBreakpointType::Owned = T
pub fn aya::programs::perf_event::PerfBreakpointType::clone_into(&self, target: &mut T)
pub fn aya::programs::perf_event::PerfBreakpointType::to_owned(&self) -> T
impl<T> core::any::Any for aya::programs::perf_event::PerfBreakpointType where T: 'static + ?core::marker::Sized
pub fn aya::programs::perf_event::PerfBreakpointType::type_id(&self) -> core::any::TypeId
impl<T> core::borrow::Borrow<T> for aya::programs::perf_event::PerfBreakpointType where T: ?core::marker::Sized
pub fn aya::programs::perf_event::PerfBreakpointType::borrow(&self) -> &T
impl<T> core::borrow::BorrowMut<T> for aya::programs::perf_event::PerfBreakpointType where T: ?core::marker::Sized
pub fn aya::programs::perf_event::PerfBreakpointType::borrow_mut(&mut self) -> &mut T
impl<T> core::clone::CloneToUninit for aya::programs::perf_event::PerfBreakpointType where T: core::clone::Clone
pub unsafe fn aya::programs::perf_event::PerfBreakpointType::clone_to_uninit(&self, dest: *mut u8)
impl<T> core::convert::From<T> for aya::programs::perf_event::PerfBreakpointType
pub fn aya::programs::perf_event::PerfBreakpointType::from(t: T) -> T
pub enum aya::programs::perf_event::PerfEventConfig pub enum aya::programs::perf_event::PerfEventConfig
pub aya::programs::perf_event::PerfEventConfig::Breakpoint pub aya::programs::perf_event::PerfEventConfig::Breakpoint(aya::programs::perf_event::BreakpointConfig)
pub aya::programs::perf_event::PerfEventConfig::Breakpoint::address: u64
pub aya::programs::perf_event::PerfEventConfig::Breakpoint::length: aya::programs::perf_event::PerfBreakpointSize
pub aya::programs::perf_event::PerfEventConfig::Breakpoint::type_: aya::programs::perf_event::PerfBreakpointType
pub aya::programs::perf_event::PerfEventConfig::Hardware(aya::programs::perf_event::HardwareEvent) pub aya::programs::perf_event::PerfEventConfig::Hardware(aya::programs::perf_event::HardwareEvent)
pub aya::programs::perf_event::PerfEventConfig::HwCache pub aya::programs::perf_event::PerfEventConfig::HwCache
pub aya::programs::perf_event::PerfEventConfig::HwCache::event: aya::programs::perf_event::HwCacheEvent pub aya::programs::perf_event::PerfEventConfig::HwCache::event: aya::programs::perf_event::HwCacheEvent
@ -8297,7 +8298,6 @@ pub aya::programs::ProgramError::AttachCookieNotSupported
pub aya::programs::ProgramError::Btf(aya_obj::btf::btf::BtfError) pub aya::programs::ProgramError::Btf(aya_obj::btf::btf::BtfError)
pub aya::programs::ProgramError::ExtensionError(aya::programs::extension::ExtensionError) pub aya::programs::ProgramError::ExtensionError(aya::programs::extension::ExtensionError)
pub aya::programs::ProgramError::IOError(std::io::error::Error) pub aya::programs::ProgramError::IOError(std::io::error::Error)
pub aya::programs::ProgramError::IncompleteBreakpoint
pub aya::programs::ProgramError::InvalidName pub aya::programs::ProgramError::InvalidName
pub aya::programs::ProgramError::InvalidName::name: alloc::string::String pub aya::programs::ProgramError::InvalidName::name: alloc::string::String
pub aya::programs::ProgramError::KProbeError(aya::programs::kprobe::KProbeError) pub aya::programs::ProgramError::KProbeError(aya::programs::kprobe::KProbeError)

Loading…
Cancel
Save