1#!/bin/sh 2# usage: . cpuset_funcs.sh 3# functions for cpuset test 4 5################################################################################ 6## ## 7## Copyright (c) 2009 FUJITSU LIMITED ## 8## ## 9## This program is free software; you can redistribute it and#or modify ## 10## it under the terms of the GNU General Public License as published by ## 11## the Free Software Foundation; either version 2 of the License, or ## 12## (at your option) any later version. ## 13## ## 14## This program is distributed in the hope that it will be useful, but ## 15## WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY ## 16## or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License ## 17## for more details. ## 18## ## 19## You should have received a copy of the GNU General Public License ## 20## along with this program; if not, write to the Free Software ## 21## Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA ## 22## ## 23## Author: Miao Xie <miaox@cn.fujitsu.com> ## 24## ## 25################################################################################ 26 27. test.sh 28 29NR_CPUS=`tst_ncpus` 30if [ -f "/sys/devices/system/node/has_high_memory" ]; then 31 N_NODES="`cat /sys/devices/system/node/has_high_memory`" 32else 33 N_NODES="`cat /sys/devices/system/node/has_normal_memory`" 34fi 35N_NODES=${N_NODES#*-*} 36N_NODES=$(($N_NODES + 1)) 37 38CPUSET="/dev/cpuset" 39CPUSET_TMP="/tmp/cpuset_tmp" 40 41HOTPLUG_CPU="1" 42 43cpuset_log() 44{ 45 tst_resm TINFO "$*" 46} 47 48# cpuset_log_error <error_file> 49cpuset_log_error() 50{ 51 local error_message= 52 53 while read error_message 54 do 55 cpuset_log "$error_message" 56 done < "$1" 57} 58 59version_check() 60{ 61 if tst_kvcmp -lt "2.6.28"; then 62 tst_brkm TCONF "kernel is below 2.6.28" 63 fi 64} 65 66ncpus_check() 67{ 68 if [ $NR_CPUS -lt $1 ]; then 69 tst_brkm TCONF "The total of CPUs is less than $1" 70 fi 71} 72 73nnodes_check() 74{ 75 if [ $N_NODES -lt $1 ]; then 76 tst_brkm TCONF "The total of nodes is less than $1" 77 fi 78} 79 80user_check() 81{ 82 if [ $(id -u) != 0 ]; then 83 tst_brkm TCONF "Test must be run as root" 84 fi 85} 86 87cpuset_check() 88{ 89 if [ -f /proc/cgroups ]; then 90 CPUSET_CONTROLLER=`grep -w cpuset /proc/cgroups | cut -f1` 91 CPUSET_CONTROLLER_VALUE=`grep -w cpuset /proc/cgroups | cut -f4` 92 93 if [ "$CPUSET_CONTROLLER" = "cpuset" ] && [ "$CPUSET_CONTROLLER_VALUE" = "1" ] 94 then 95 return 0 96 fi 97 fi 98 99 tst_brkm TCONF "Cpuset is not supported" 100} 101 102# optional parameters (pass both or none of them): 103# $1 - required number of cpus (default 2) 104# $2 - required number of memory nodes (default 2) 105check() 106{ 107 user_check 108 109 cpuset_check 110 111 version_check 112 113 ncpus_check ${1:-2} 114 115 nnodes_check ${2:-2} 116 117} 118 119# Create /dev/cpuset & mount the cgroup file system with cpuset 120# clean any group created eralier (if any) 121setup() 122{ 123 if [ -e "$CPUSET" ] 124 then 125 tst_resm TWARN "$CPUSET already exist.. overwriting" 126 cleanup || tst_brkm TFAIL "Can't cleanup... Exiting" 127 fi 128 129 mkdir -p "$CPUSET_TMP" 130 mkdir "$CPUSET" 131 mount -t cgroup -o cpuset cpuset "$CPUSET" 2> /dev/null 132 if [ $? -ne 0 ]; then 133 cleanup 134 tst_brkm TFAIL "Could not mount cgroup filesystem with"\ 135 " cpuset on $CPUSET..Exiting test" 136 fi 137} 138 139# Write the cleanup function 140cleanup() 141{ 142 grep "$CPUSET" /proc/mounts >/dev/null 2>&1 || { 143 rm -rf "$CPUSET" >/dev/null 2>&1 144 return 0 145 } 146 147 find "$CPUSET" -type d | sort | sed -n '2,$p' | tac | while read subdir 148 do 149 while read pid 150 do 151 /bin/kill -9 $pid > /dev/null 2>&1 152 if [ $? -ne 0 ]; then 153 tst_brkm TFAIL "Couldn't kill task - "\ 154 "$pid in the cpuset" 155 fi 156 done < "$subdir/tasks" 157 rmdir "$subdir" 158 if [ $? -ne 0 ]; then 159 tst_brkm TFAIL "Couldn't remove subdir - " 160 "$subdir in the cpuset" 161 fi 162 done 163 164 umount "$CPUSET" 165 if [ $? -ne 0 ]; then 166 tst_brkm TFAIL "Couldn't umount cgroup filesystem with"\ 167 " cpuset on $CPUSET..Exiting test" 168 fi 169 rmdir "$CPUSET" > /dev/null 2>&1 170 rm -rf "$CPUSET_TMP" > /dev/null 2>&1 171} 172 173# set the cpuset's parameter 174# cpuset_set <cpusetpath> <cpus> <mems> <load_balance> 175cpuset_set() 176{ 177 local path="$1" 178 mkdir -p "$path" 179 if [ $? -ne 0 ]; then 180 return 1 181 fi 182 183 local cpus="$2" 184 local mems="$3" 185 local load_balance="$4" 186 187 if [ "$path" != "$CPUSET" ]; then 188 if [ "$cpus" != "-" ]; then 189 /bin/echo $cpus > $path/cpuset.cpus 190 if [ $? -ne 0 ]; then 191 return 1 192 fi 193 fi 194 195 /bin/echo $mems > $path/cpuset.mems 196 if [ $? -ne 0 ]; then 197 return 1 198 fi 199 fi 200 201 /bin/echo $load_balance > $path/cpuset.sched_load_balance 202 if [ $? -ne 0 ]; then 203 return 1 204 fi 205} 206 207# cpu_hotplug cpu_id offline/online 208cpu_hotplug() 209{ 210 if [ "$2" = "online" ]; then 211 /bin/echo 1 > "/sys/devices/system/cpu/cpu$1/online" 212 if [ $? -ne 0 ]; then 213 return 1 214 fi 215 elif [ "$2" = "offline" ]; then 216 /bin/echo 0 > "/sys/devices/system/cpu/cpu$1/online" 217 if [ $? -ne 0 ]; then 218 return 1 219 fi 220 fi 221} 222 223# setup_test_environment <online | offline> 224# online - online a CPU in testing, so we must offline a CPU first 225# offline - offline a CPU in testing, we needn't do anything 226setup_test_environment() 227{ 228 if [ "$1" = "online" ]; then 229 cpu_hotplug $HOTPLUG_CPU offline 230 if [ $? -ne 0 ]; then 231 return 1 232 fi 233 fi 234} 235 236cpu_hotplug_cleanup() 237{ 238 local cpus_array="$(seq -s' ' 1 $((NR_CPUS-1)))" 239 local cpuid= 240 for cpuid in $cpus_array 241 do 242 local file="/sys/devices/system/cpu/cpu$cpuid/online" 243 local offline="$(cat $file)" 244 if [ $offline -eq 0 ]; then 245 cpu_hotplug $cpuid "online" 246 fi 247 done 248} 249 250