==> tests/cpuuse.c <==1/* cpuuse.rs's meter_counts_this_threads_cpu_and_memory. */
2#include "mesh/check.h"
3#include "mesh/cpuuse.h"
4
5#include <pthread.h>
6#include <time.h>
7
8static double ms_since(const struct timespec *t0) {
9 struct timespec t;
10 clock_gettime(CLOCK_MONOTONIC, &t);
11 return (double)(t.tv_sec - t0->tv_sec) * 1e3 + (double)(t.tv_nsec - t0->tv_nsec) / 1e6;
12}
13
14static void *lane(void *arg) {
15 (void)arg;
16 mesh_meter m;
17 mesh_meter_start(&m, 31);
18 uint64_t cpu, rss;
19 uint32_t units;
20 mesh_slot_use_get(&mesh_cpuuse_slots[31], &cpu, &rss, &units);
21 CHECK_U(units, 1);
22 /* 30 ms of this thread's CPU (the Rust spins 30 ms of wall time, which a
23 * loaded machine may not turn into 20 ms of CPU); at most 10 s of wall. */
24 struct timespec t0;
25 clock_gettime(CLOCK_MONOTONIC, &t0);
26 uint64_t c0 = mesh_thread_cpu_ns();
27 volatile uint64_t x = 0;
28 while (mesh_thread_cpu_ns() - c0 < 30000000u && ms_since(&t0) < 10000) x = x * 31 + 7;
29 mesh_meter_tick(&m, 1u << 20);
30 mesh_slot_use_get(&mesh_cpuuse_slots[31], &cpu, &rss, &units);
31 CHECK(cpu >= 20000000);
32 CHECK_U(rss, 1u << 20);
33 CHECK_U(units, 1);
34 mesh_meter_tick(&m, 3u << 20);
35 mesh_slot_use_get(&mesh_cpuuse_slots[31], &cpu, &rss, &units);
36 CHECK_U(rss, 3u << 20);
37 mesh_meter_end(&m);
38 return NULL;
39}
40
41int main(void) {
42 pthread_t t;
43 pthread_create(&t, NULL, lane, NULL);
44 pthread_join(t, NULL);
45 uint64_t cpu, rss;
46 uint32_t units;
47 mesh_slot_use_get(&mesh_cpuuse_slots[31], &cpu, &rss, &units);
48 CHECK(cpu < 200000000);
49 CHECK_U(rss, 0);
50 CHECK_U(units, 0);
51 return mesh_check_done();
52}