Just a quick app to test and demonstrate how to get run times from a specific thread on FreeBSD.
58 lines
1.6 KiB
C++
58 lines
1.6 KiB
C++
/*
|
|
* SPDX-FileCopyrightText: 2025 Eilertsens Kodeknekkeri
|
|
* SPDX-FileCopyrightText: 2025 The FreeBSD Foundation
|
|
* SPDX-FileContributor: Harald Eilertsen <haraldei@anduin.net>
|
|
*
|
|
* SPDX-License-Identifier: BSD-2-Clause
|
|
*/
|
|
|
|
#include "helpers.hpp"
|
|
#include <cassert>
|
|
#include <iostream>
|
|
#include <sys/sysctl.h>
|
|
#include <sys/user.h>
|
|
#include <unistd.h>
|
|
|
|
void sysctl_cpu_time(pthread_t thread, struct timeval * utime, struct timeval * stime) {
|
|
int mib[] = { CTL_KERN, KERN_PROC, KERN_PROC_PID|KERN_PROC_INC_THREAD, getpid() };
|
|
|
|
auto miblen = sizeof mib / sizeof mib[0];
|
|
size_t bufsize = 0;
|
|
|
|
auto rc = sysctl(mib, miblen, nullptr, &bufsize, nullptr, 0);
|
|
// for some reason it seems sysctl sometimes return 0 (Ok) instead of ENOMEM when
|
|
// passed a nullptr as oldp. This is not according to documentation.
|
|
assert(rc == ENOMEM || rc == 0);
|
|
|
|
auto procinfo_buf = malloc(bufsize);
|
|
rc = sysctl(mib, 4U, procinfo_buf, &bufsize, nullptr, 0);
|
|
assert(rc == 0);
|
|
|
|
auto count = bufsize / sizeof(struct kinfo_proc);
|
|
|
|
#ifndef NDEBUG
|
|
std::cout << "[*] Received procinfo @ " << procinfo_buf
|
|
<< ", with " << count << " entries" << std::endl;
|
|
#endif
|
|
|
|
for (auto i = 0U; i < count; ++i) {
|
|
auto tinfo = (struct kinfo_proc *)procinfo_buf + i;
|
|
|
|
#ifndef NDEBUG
|
|
std::cout << "[*] " << i
|
|
<< ": tid = " << tinfo->ki_tid
|
|
<< ", runtime = " << tinfo->ki_runtime
|
|
<< ", user time = " << timeval_to_long(tinfo->ki_rusage.ru_utime)
|
|
<< ", sys time = " << timeval_to_long(tinfo->ki_rusage.ru_stime)
|
|
<< std::endl;
|
|
#endif
|
|
|
|
if (tinfo->ki_tid == ktid) {
|
|
*utime = tinfo->ki_rusage.ru_utime;
|
|
*stime = tinfo->ki_rusage.ru_stime;
|
|
break;
|
|
}
|
|
}
|
|
|
|
free(procinfo_buf);
|
|
}
|