|
| 1 | +# Stressapptest Validation |
| 2 | + |
| 3 | +This test validates system stability using [stressapptest](https://github.com/stressapptest/stressapptest). |
| 4 | + |
| 5 | +## Overview |
| 6 | + |
| 7 | +`stressapptest` is a stress-testing tool for CPU, memory, disk and networking, widely used in reliability testing for servers and embedded systems. |
| 8 | + |
| 9 | +This wrapper script adds: |
| 10 | + |
| 11 | +- **Cgroup-aware** memory sizing with safety guards |
| 12 | +- **Safe** and **Strict** modes |
| 13 | +- Post-run **dmesg** scanning (toggleable) |
| 14 | +- Auto detection for CPUs / memory / mounts / IP |
| 15 | +- Optional **auto** setup for disk and network tests |
| 16 | +- Looping with per-loop and aggregate **JSON** summaries |
| 17 | +- CPU pinning via **taskset** (if available) or **cpuset cgroups** (root, when supported) |
| 18 | + |
| 19 | +## Prerequisites |
| 20 | + |
| 21 | +- `stressapptest` must be installed and available in `PATH`. |
| 22 | + |
| 23 | +Optional tools (the wrapper works without them, but features degrade gracefully): |
| 24 | + |
| 25 | +- `taskset` (if present, used for CPU pinning) |
| 26 | +- Writable **cpuset** cgroups (kernel feature; used for pinning when `taskset` is absent) |
| 27 | +- `df` (for auto disk selection), `ip`/`hostname` (for auto network) |
| 28 | +- `getconf`/**`nproc`** (or `/proc/cpuinfo`) for CPU counting |
| 29 | + |
| 30 | +Build from source (typical host): |
| 31 | +```bash |
| 32 | +git clone https://github.com/stressapptest/stressapptest.git |
| 33 | +cd stressapptest |
| 34 | +./configure |
| 35 | +make |
| 36 | +sudo make install |
| 37 | + |
| 38 | +Yocto image: |
| 39 | + |
| 40 | +IMAGE_INSTALL:append = " stressapptest" |
| 41 | + |
| 42 | +Side-load: |
| 43 | + |
| 44 | +scp stressapptest user@target:/usr/local/bin/ |
| 45 | + |
| 46 | +Usage |
| 47 | + |
| 48 | +./run.sh [options] |
| 49 | + |
| 50 | +Options forwarded to stressapptest |
| 51 | + |
| 52 | +(These map 1:1 to stressapptest flags.) |
| 53 | + |
| 54 | +-M <MB> : Memory to test (default: auto; see memory sizing below) |
| 55 | + |
| 56 | +-s <seconds> : Duration (default: 300; safe mode: 120) |
| 57 | + |
| 58 | +-m <threads> : Memory copy threads (default: online CPUs; safe: ~half, up to 4) |
| 59 | + |
| 60 | +-W : More CPU-stressful memory copy |
| 61 | + |
| 62 | +-n <ipaddr> : Network client thread to <ipaddr> |
| 63 | + |
| 64 | +--listen : Listen thread (for networking) |
| 65 | + |
| 66 | +-f <filename> : Disk thread using <filename> |
| 67 | + |
| 68 | +-F : Use libc memcpy |
| 69 | + |
| 70 | +-l <logfile> : Log file (default: ./Stressapptest.log) |
| 71 | + |
| 72 | +-v <level> : Verbosity 0–20 (default: 8) |
| 73 | + |
| 74 | + |
| 75 | +Wrapper-specific options |
| 76 | + |
| 77 | +--safe : Conservative sizing and CPU subset |
| 78 | + |
| 79 | +--dry-run : Print the command that would run and exit |
| 80 | + |
| 81 | +--strict : Fail run if severe dmesg issues are detected |
| 82 | + |
| 83 | +--auto-net[=primary|loopback] : Start local listener and set -n automatically |
| 84 | +(default mode: primary; falls back to loopback if no primary IP) |
| 85 | + |
| 86 | +--auto-disk : Pick a writable mount and create a tempfile for -f |
| 87 | + |
| 88 | +--auto : Shorthand for --auto-net --auto-disk |
| 89 | + |
| 90 | + |
| 91 | +Memory sizing knobs (cgroup-aware) |
| 92 | + |
| 93 | +--mem-pct=<P> : Percent of available RAM to use (default 60; safe: 35) |
| 94 | + |
| 95 | +--mem-headroom-mb=<MB> : Keep this many MB free (default 256; safe: 512) |
| 96 | + |
| 97 | +--mem-cap-mb=<MB> : Hard upper cap on -M |
| 98 | + |
| 99 | +--require-mem-mb=<MB> : Refuse to run if computed target < MB |
| 100 | + |
| 101 | + |
| 102 | +Control & reporting |
| 103 | + |
| 104 | +--loops=<N> : Repeat test N times (default 1) |
| 105 | + |
| 106 | +--loop-delay=<S> : Sleep S seconds between loops (default 0) |
| 107 | + |
| 108 | +--json=<file> : Write line-delimited JSON per loop + final aggregate |
| 109 | + |
| 110 | + |
| 111 | +> You can also supply most of these via environment variables (e.g. SAFE=1, MEM_CAP_MB=256, JSON_OUT=summary.json, LOOPS=3). |
| 112 | + |
| 113 | + |
| 114 | + |
| 115 | +Examples |
| 116 | + |
| 117 | +Run for 60s using auto sizing: |
| 118 | + |
| 119 | +./run.sh -s 60 |
| 120 | + |
| 121 | +Safer profile (shorter, fewer threads, more headroom): |
| 122 | + |
| 123 | +./run.sh --safe |
| 124 | + |
| 125 | +Low-memory guard (refuse to run < 512 MB): |
| 126 | + |
| 127 | +./run.sh --require-mem-mb=512 |
| 128 | + |
| 129 | +Cap memory and add extra headroom: |
| 130 | + |
| 131 | +./run.sh --mem-cap-mb=256 --mem-headroom-mb=512 |
| 132 | + |
| 133 | +Multiple loops with JSON summary (and strict dmesg checks): |
| 134 | + |
| 135 | +./run.sh --loops=5 --loop-delay=10 --json=summary.json --strict |
| 136 | + |
| 137 | +Auto network + auto disk: |
| 138 | + |
| 139 | +./run.sh --auto |
| 140 | + |
| 141 | +Dry run (show exact command that would execute): |
| 142 | + |
| 143 | +./run.sh --dry-run |
| 144 | + |
| 145 | +CPU usage & pinning |
| 146 | + |
| 147 | +The wrapper starts one stressapptest process with -m <threads> (defaults to online CPUs). |
| 148 | +Those workers are threads—not separate processes—so ps typically shows a single process. |
| 149 | + |
| 150 | +Pinning behavior: |
| 151 | + |
| 152 | +1. If taskset exists → the process is pinned to the CPU list (logged as CPU pinning method: taskset (...)). |
| 153 | + |
| 154 | + |
| 155 | +2. Else, if cpuset cgroups are available (and writable) → the wrapper confines the process to that CPU list |
| 156 | +(logged as CPU pinning method: cgroup cpuset (...)). |
| 157 | + |
| 158 | + |
| 159 | +3. Else → runs unpinned (logged as CPU pinning method: none). |
| 160 | + |
| 161 | + |
| 162 | + |
| 163 | + |
| 164 | +How to verify |
| 165 | + |
| 166 | +Count threads: |
| 167 | + |
| 168 | +PID=$(pidof stressapptest) |
| 169 | +grep '^Threads:' /proc/$PID/status |
| 170 | +# or |
| 171 | +ls -1 /proc/$PID/task | wc -l |
| 172 | + |
| 173 | +See allowed CPUs: |
| 174 | + |
| 175 | +PID=$(pidof stressapptest) |
| 176 | +awk '/Cpus_allowed_list/ {print $2}' /proc/$PID/status |
| 177 | + |
| 178 | +Check cpuset cgroup (if used): |
| 179 | + |
| 180 | +cat /proc/$(pidof stressapptest)/cgroup |
| 181 | +# then inspect matching cpuset.cpus file under /sys/fs/cgroup/... |
| 182 | + |
| 183 | +Memory sizing (how it’s computed) |
| 184 | + |
| 185 | +1. Determine available memory (prefer cgroup limit/usage if present; otherwise MemAvailable). |
| 186 | + |
| 187 | + |
| 188 | +2. Take available * mem_pct (default 60%; --safe uses 35%). |
| 189 | + |
| 190 | + |
| 191 | +3. Reserve headroom (--mem-headroom-mb; default 256 MB; safe: 512 MB). |
| 192 | + |
| 193 | + |
| 194 | +4. Apply hard cap (--mem-cap-mb) if set. |
| 195 | + |
| 196 | + |
| 197 | +5. Clamp to sane floor (≥ 16 MB) and not above “available minus headroom”. |
| 198 | + |
| 199 | + |
| 200 | +6. If --require-mem-mb=N and computed < N, the run aborts. |
| 201 | + |
| 202 | + |
| 203 | +The final value is passed to stressapptest as -M. |
| 204 | + |
| 205 | +Output |
| 206 | + |
| 207 | +Result: ./Stressapptest.res → PASS or FAIL |
| 208 | + |
| 209 | +Log file: ./Stressapptest.log |
| 210 | + |
| 211 | +If --json is used: line-delimited JSON entries per loop and a final aggregate. |
| 212 | + |
| 213 | + |
| 214 | +Notes |
| 215 | + |
| 216 | +By default you’ll see one stressapptest process; workers are threads (use /proc/$PID/task to list them). |
| 217 | + |
| 218 | +Auto disk selection avoids RO/system mounts and picks the largest free writable mount for -f. |
| 219 | + |
| 220 | +Auto network starts a local listen thread and chooses a primary IP (falling back to loopback). |
| 221 | + |
| 222 | +--- |
| 223 | + |
| 224 | +License |
| 225 | + |
| 226 | +The test runner: BSD-3-Clause-Clear (Qualcomm Technologies, Inc. and/or its subsidiaries). |
| 227 | +stressapptest is licensed by its upstream author; see its repository for details. |
0 commit comments