in below/model/src/collector.rs [162:257]
fn collect_sample(logger: &slog::Logger, options: &CollectorOptions) -> Result<Sample> {
let mut reader = procfs::ProcReader::new();
// Take mutex, then take all values out of shared map and replace with default map
//
// NB: unconditionally drain the exit buffer otherwise we can leak the entries
let exit_pidmap = std::mem::take(
&mut *options
.exit_data
.lock()
.expect("tried to acquire poisoned lock"),
);
Ok(Sample {
cgroup: collect_cgroup_sample(
&cgroupfs::CgroupReader::new(options.cgroup_root.to_owned())?,
options.collect_io_stat,
logger,
&options.cgroup_re,
)?,
processes: merge_procfs_and_exit_data(
reader
.read_all_pids()?
.into_iter()
.map(|(k, v)| (k, v.into()))
.collect(),
exit_pidmap,
),
netstats: match procfs::NetReader::new().and_then(|v| v.read_netstat()) {
Ok(ns) => ns.into(),
Err(e) => {
error!(logger, "{:#}", e);
Default::default()
}
},
system: SystemSample {
stat: reader.read_stat()?.into(),
meminfo: reader.read_meminfo()?.into(),
vmstat: reader.read_vmstat()?.into(),
hostname: get_hostname()?,
kernel_version: match reader.read_kernel_version() {
Ok(k) => Some(k),
Err(e) => {
error!(logger, "{:#}", e);
None
}
},
os_release: match get_os_release() {
Ok(o) => Some(o),
Err(e) => {
error!(logger, "{:#}", e);
None
}
},
disks: if options.disable_disk_stat {
Default::default()
} else {
match reader.read_disk_stats_and_fsinfo() {
Ok(disks) => disks
.into_iter()
.filter(|(disk_name, disk_stat)| {
if disk_name.starts_with("ram") || disk_name.starts_with("loop") {
return false;
}
!is_all_zero_disk_stats(disk_stat)
})
.collect(),
Err(e) => {
error!(logger, "{:#}", e);
Default::default()
}
}
},
},
#[cfg(fbcode_build)]
gpus: {
if let Some(gpu_stats_receiver) = &options.gpu_stats_receiver {
// It is possible to receive no sample if the
// collector has not updated since the previous take
// or the collector encountered a recoverable error
// (e.g. timeout). The behavior for now is to store an
// empty map. Alternatively we could store the latest
// sample and read that, but then we have to decide how
// stale the data can be.
Some(
gpu_stats_receiver
.try_take()
.context("GPU stats collector had an error")?
.unwrap_or_default(),
)
} else {
None
}
},
})
}