1######################################################################## 2# # 3# This software is part of the ast package # 4# Copyright (c) 1982-2010 AT&T Intellectual Property # 5# and is licensed under the # 6# Common Public License, Version 1.0 # 7# by AT&T Intellectual Property # 8# # 9# A copy of the License is available at # 10# http://www.opensource.org/licenses/cpl1.0.txt # 11# (with md5 checksum 059e8cd6165cb4c31e351f2b69388fd9) # 12# # 13# Information and Software Systems Research # 14# AT&T Research # 15# Florham Park NJ # 16# # 17# David Korn <dgk@research.att.com> # 18# # 19######################################################################## 20function err_exit 21{ 22 print -u2 -n "\t" 23 print -u2 -r ${Command}[$1]: "${@:2}" 24 (( Errors+=1 )) 25} 26 27alias err_exit='err_exit $LINENO' 28 29float DELAY=${1:-0.2} 30integer FOREGROUND=10 BACKGROUND=2 Errors=0 31 32s=$($SHELL -c ' 33integer i foreground=0 background=0 34float delay='$DELAY' d=0 s=0 35 36set --errexit 37 38trap "(( background++ ))" CHLD 39 40(( d = delay )) 41for ((i = 0; i < '$BACKGROUND'; i++)) 42do sleep $d & 43 (( d *= 4 )) 44 (( s += d )) 45done 46for ((i = 0; i < '$FOREGROUND'; i++)) 47do (( foreground++ )) 48 sleep $delay 49 (( s -= delay )) 50 $SHELL -c : > /dev/null # foreground does not generate SIGCHLD 51done 52if (( (s += delay) < 1 )) 53then (( s = 1 )) 54fi 55sleep $s 56wait 57print foreground=$foreground background=$background 58') || err_exit "test loop failed" 59 60eval $s 61 62(( foreground == FOREGROUND )) || err_exit "expected '$FOREGROUND foreground' -- got '$foreground' (DELAY=$DELAY)" 63(( background == BACKGROUND )) || err_exit "expected '$BACKGROUND background' -- got '$background' (DELAY=$DELAY)" 64 65set --noerrexit 66 67if [[ ${.sh.version} == Version?*([[:upper:]])J* ]] 68then 69 70 jobmax=4 71 got=$($SHELL -c ' 72 JOBMAX='$jobmax' JOBCOUNT=$(('$jobmax'*2)) 73 integer running=0 maxrunning=0 74 trap "((running--))" CHLD 75 for ((i=0; i<JOBCOUNT; i++)) 76 do sleep 1 & 77 if ((++running > maxrunning)) 78 then ((maxrunning=running)) 79 fi 80 done 81 wait 82 print running=$running maxrunning=$maxrunning 83 ') 84 exp='running=0 maxrunning='$jobmax 85 [[ $got == $exp ]] || err_exit "SIGCHLD trap queueing failed -- expected '$exp', got '$got'" 86 87 got=$($SHELL -c ' 88 typeset -A proc 89 90 trap " 91 print \${proc[\$!].name} \${proc[\$!].status} \$? 92 unset proc[\$!] 93 " CHLD 94 95 { sleep 3; print a; exit 1; } & 96 proc[$!]=( name=a status=1 ) 97 98 { sleep 2; print b; exit 2; } & 99 proc[$!]=( name=b status=2 ) 100 101 { sleep 1; print c; exit 3; } & 102 proc[$!]=( name=c status=3 ) 103 104 while (( ${#proc[@]} )) 105 do sleep -s 106 done 107 ') 108 exp='c\nc 3 3\nb\nb 2 2\na\na 1 1' 109 [[ $got == $exp ]] || err_exit "SIGCHLD trap queueing failed -- expected $(printf %q "$exp"), got $(printf %q "$got")" 110 111fi 112 113{ 114got=$( ( sleep 1;print $'\n') | $SHELL -c 'function handler { : ;} 115 trap handler CHLD; sleep .3 & IFS= read; print good') 116} 2> /dev/null 117[[ $got == good ]] || err_exit 'SIGCLD handler effects read behavior' 118 119set -- $( 120 ( 121 $SHELL -xc $' 122 trap \'wait $!; print $! $?\' CHLD 123 { sleep 0.1; exit 9; } & 124 print $! 125 sleep 0.5 126 ' 127 ) 2>/dev/null; print $? 128) 129if (( $# != 4 )) 130then err_exit "CHLD trap failed -- expected 4 args, got $#" 131elif (( $4 != 0 )) 132then err_exit "CHLD trap failed -- exit code $4" 133elif (( $1 != $2 )) 134then err_exit "child pid mismatch -- got '$1' != '$2'" 135elif (( $3 != 9 )) 136then err_exit "child status mismatch -- expected '9', got '$3'" 137fi 138 139exit $((Errors)) 140