162306a36Sopenharmony_ci#!/bin/bash 262306a36Sopenharmony_ci# SPDX-License-Identifier: GPL-2.0+ 362306a36Sopenharmony_ci# 462306a36Sopenharmony_ci# Alternate sleeping and spinning on randomly selected CPUs. The purpose 562306a36Sopenharmony_ci# of this script is to inflict random OS jitter on a concurrently running 662306a36Sopenharmony_ci# test. 762306a36Sopenharmony_ci# 862306a36Sopenharmony_ci# Usage: jitter.sh me jittering-path duration [ sleepmax [ spinmax ] ] 962306a36Sopenharmony_ci# 1062306a36Sopenharmony_ci# me: Random-number-generator seed salt. 1162306a36Sopenharmony_ci# duration: Time to run in seconds. 1262306a36Sopenharmony_ci# jittering-path: Path to file whose removal will stop this script. 1362306a36Sopenharmony_ci# sleepmax: Maximum microseconds to sleep, defaults to one second. 1462306a36Sopenharmony_ci# spinmax: Maximum microseconds to spin, defaults to one millisecond. 1562306a36Sopenharmony_ci# 1662306a36Sopenharmony_ci# Copyright (C) IBM Corporation, 2016 1762306a36Sopenharmony_ci# 1862306a36Sopenharmony_ci# Authors: Paul E. McKenney <paulmck@linux.ibm.com> 1962306a36Sopenharmony_ci 2062306a36Sopenharmony_cime=$(($1 * 1000)) 2162306a36Sopenharmony_cijittering=$2 2262306a36Sopenharmony_ciduration=$3 2362306a36Sopenharmony_cisleepmax=${4-1000000} 2462306a36Sopenharmony_cispinmax=${5-1000} 2562306a36Sopenharmony_ci 2662306a36Sopenharmony_cin=1 2762306a36Sopenharmony_ci 2862306a36Sopenharmony_cistarttime=`gawk 'BEGIN { print systime(); }' < /dev/null` 2962306a36Sopenharmony_ci 3062306a36Sopenharmony_cinohotplugcpus= 3162306a36Sopenharmony_cifor i in /sys/devices/system/cpu/cpu[0-9]* 3262306a36Sopenharmony_cido 3362306a36Sopenharmony_ci if test -f $i/online 3462306a36Sopenharmony_ci then 3562306a36Sopenharmony_ci : 3662306a36Sopenharmony_ci else 3762306a36Sopenharmony_ci curcpu=`echo $i | sed -e 's/^[^0-9]*//'` 3862306a36Sopenharmony_ci nohotplugcpus="$nohotplugcpus $curcpu" 3962306a36Sopenharmony_ci fi 4062306a36Sopenharmony_cidone 4162306a36Sopenharmony_ci 4262306a36Sopenharmony_ciwhile : 4362306a36Sopenharmony_cido 4462306a36Sopenharmony_ci # Check for done. 4562306a36Sopenharmony_ci t=`gawk -v s=$starttime 'BEGIN { print systime() - s; }' < /dev/null` 4662306a36Sopenharmony_ci if test "$t" -gt "$duration" 4762306a36Sopenharmony_ci then 4862306a36Sopenharmony_ci exit 0; 4962306a36Sopenharmony_ci fi 5062306a36Sopenharmony_ci 5162306a36Sopenharmony_ci # Check for stop request. 5262306a36Sopenharmony_ci if ! test -f "$jittering" 5362306a36Sopenharmony_ci then 5462306a36Sopenharmony_ci exit 1; 5562306a36Sopenharmony_ci fi 5662306a36Sopenharmony_ci 5762306a36Sopenharmony_ci # Set affinity to randomly selected online CPU 5862306a36Sopenharmony_ci if cpus=`grep 1 /sys/devices/system/cpu/*/online 2>&1 | 5962306a36Sopenharmony_ci sed -e 's,/[^/]*$,,' -e 's/^[^0-9]*//'` 6062306a36Sopenharmony_ci then 6162306a36Sopenharmony_ci : 6262306a36Sopenharmony_ci else 6362306a36Sopenharmony_ci cpus= 6462306a36Sopenharmony_ci fi 6562306a36Sopenharmony_ci # Do not leave out non-hot-pluggable CPUs 6662306a36Sopenharmony_ci cpus="$cpus $nohotplugcpus" 6762306a36Sopenharmony_ci 6862306a36Sopenharmony_ci cpumask=`awk -v cpus="$cpus" -v me=$me -v n=$n 'BEGIN { 6962306a36Sopenharmony_ci srand(n + me + systime()); 7062306a36Sopenharmony_ci ncpus = split(cpus, ca); 7162306a36Sopenharmony_ci print ca[int(rand() * ncpus + 1)]; 7262306a36Sopenharmony_ci }' < /dev/null` 7362306a36Sopenharmony_ci n=$(($n+1)) 7462306a36Sopenharmony_ci if ! taskset -c -p $cpumask $$ > /dev/null 2>&1 7562306a36Sopenharmony_ci then 7662306a36Sopenharmony_ci echo taskset failure: '"taskset -c -p ' $cpumask $$ '"' 7762306a36Sopenharmony_ci exit 1 7862306a36Sopenharmony_ci fi 7962306a36Sopenharmony_ci 8062306a36Sopenharmony_ci # Sleep a random duration 8162306a36Sopenharmony_ci sleeptime=`awk -v me=$me -v n=$n -v sleepmax=$sleepmax 'BEGIN { 8262306a36Sopenharmony_ci srand(n + me + systime()); 8362306a36Sopenharmony_ci printf("%06d", int(rand() * sleepmax)); 8462306a36Sopenharmony_ci }' < /dev/null` 8562306a36Sopenharmony_ci n=$(($n+1)) 8662306a36Sopenharmony_ci sleep .$sleeptime 8762306a36Sopenharmony_ci 8862306a36Sopenharmony_ci # Spin a random duration 8962306a36Sopenharmony_ci limit=`awk -v me=$me -v n=$n -v spinmax=$spinmax 'BEGIN { 9062306a36Sopenharmony_ci srand(n + me + systime()); 9162306a36Sopenharmony_ci printf("%06d", int(rand() * spinmax)); 9262306a36Sopenharmony_ci }' < /dev/null` 9362306a36Sopenharmony_ci n=$(($n+1)) 9462306a36Sopenharmony_ci for i in {1..$limit} 9562306a36Sopenharmony_ci do 9662306a36Sopenharmony_ci echo > /dev/null 9762306a36Sopenharmony_ci done 9862306a36Sopenharmony_cidone 9962306a36Sopenharmony_ci 10062306a36Sopenharmony_ciexit 1 101