aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorMichał Górny <mgorny@gentoo.org>2021-11-07 21:11:52 +0000
committerJohn Baldwin <jhb@FreeBSD.org>2021-12-07 23:36:34 +0000
commit8099a354469a012512d9850302edaa0e27c75fd7 (patch)
tree20c48fc7b6311d47e4df38a63cde27a8130ede5d
parente9aeb50797fcaab1829ea626c1efd75de203a410 (diff)
downloadsrc-8099a354469a012512d9850302edaa0e27c75fd7.tar.gz
src-8099a354469a012512d9850302edaa0e27c75fd7.zip
libkvm: Fix kvm_getloadavg() on modern kernel vmcores
Fix kvm_getloadavg() to work correctly on vmcores for modern kernel versions. The kernels no longer include the `_fscale` symbol causing the kvm_nlist() invocation to fail. The code seemed to already assume that `_fscale` could be missing but the early kvm_nlist() result check has caused the function to fail if any symbol were missing. Modify it to only treat `_averunnable` as obligatory, and handle missing `_fscale` gracefully. Sponsored by: The FreeBSD Foundation Differential Revision: https://reviews.freebsd.org/D32884
-rw-r--r--lib/libkvm/kvm_getloadavg.c9
1 files changed, 4 insertions, 5 deletions
diff --git a/lib/libkvm/kvm_getloadavg.c b/lib/libkvm/kvm_getloadavg.c
index 0f2a5f69bcf0..f94b1d844663 100644
--- a/lib/libkvm/kvm_getloadavg.c
+++ b/lib/libkvm/kvm_getloadavg.c
@@ -62,7 +62,6 @@ int
kvm_getloadavg(kvm_t *kd, double loadavg[], int nelem)
{
struct loadavg loadinfo;
- struct nlist *p;
int fscale, i;
if (ISALIVE(kd))
@@ -74,10 +73,9 @@ kvm_getloadavg(kvm_t *kd, double loadavg[], int nelem)
return (-1);
}
- if (kvm_nlist(kd, nl) != 0) {
- for (p = nl; p->n_type != 0; ++p);
+ if (kvm_nlist(kd, nl) != 0 && nl[X_AVERUNNABLE].n_type == 0) {
_kvm_err(kd, kd->program,
- "%s: no such symbol", p->n_name);
+ "%s: no such symbol", nl[X_AVERUNNABLE].n_name);
return (-1);
}
@@ -92,7 +90,8 @@ kvm_getloadavg(kvm_t *kd, double loadavg[], int nelem)
* Old kernels have fscale separately; if not found assume
* running new format.
*/
- if (!KREAD(kd, nl[X_FSCALE].n_value, &fscale))
+ if (nl[X_FSCALE].n_type != 0 &&
+ !KREAD(kd, nl[X_FSCALE].n_value, &fscale))
loadinfo.fscale = fscale;
nelem = MIN(nelem, (int)(sizeof(loadinfo.ldavg) / sizeof(fixpt_t)));