TABLE OF CONTENTS
::pwtk::remote_wait
SYNOPSIS
proc ::pwtk::remote_wait {args} {
PURPOSE
Wait for all the specified remote processes to finish.
USAGE
remote_wait ?options?
EXAMPLES
remote_wait remote_wait -all remote_wait -ids LIST-OF-IDS remote_wait -hosts LIST-OF-HOSTS remote_wait -pattern PATTERN remote_wait -pids LIST-OF-PIDS
OPTIONS
- -all ... wait for all remote processes to finish (default)
- -pids LIST-OF-IDS ... wait for the remote processes specified with IDs to finish (PWTK assigns a unique ID to each background remote process)
- -pids LIST-OF-PIDS ... wait for the remote processes specified with PIDs to finish
- -hosts LIST-OF-HOSTS ... wait for remote processes that run at specified hosts to finish
- -pattern PATTERN ... wait for remote processes that match the pattern to finish
If ::pwtk::remote_wait is called without options, it defaults to -all, i.e., the command waits for all the remote background processes to finish.
Info about the PATTERN:
- PATTERN is a glob-style pattern.
- The remote processes are stored with 'hostname,index' keys.
- To specify all remote processes on a given host (say myhost), use: myhost,*
- To specify all remote processes with index=1, use: *,1
- To specify all remote processes with indices 1, 2, and 3, use: {*,[123]}
SOURCE
variable remote if { ! [info exists remote(ID)] } { # nothing to wait for; there are no remote background processes return } # default is -all ifset args -all # process options set options { {all "wait for all remote processes to finish"} {ids.arg {} "wait for remote processes specified with IDs to finish"} {pids.arg {} "wait for remote processes specified with PIDs to finish"} {hosts.arg {} "wait for remote processes at specified hosts to finish"} {pattern.arg {} "wait for remote processes that match the pattern to finish"} } set narg 0 set usage "?-all? ?-ids LIST-OF-IDS? ?-pids LIST-OF-PIDS? ?-hosts LIST-OF-HOSTS? ?-pattern PATTERN?" ::pwtk::parseOpt_ ::pwtk::checkOType_ -pids $opt(pids) {numberlist nonnegint} "list of positive integers" #set usage "Usage: ::pwtk::remote_wait \[options\]\n\nOptions are:" #array set opt [::cmdline::getoptions args $options $usage] #if { [llength $args] != 0 } { # ::pwtk::error [::cmdline::usage $options $usage] # ::error {} "from..." #} #::pwtk::checkOType_ -pids $opt(pids) {numberlist nonnegint} "list of positive integers" set pid_names "" set all_pid_names [array names remote PID,*] # -ids LIST-OF-IDS foreach id $opt(ids) { ifexist remote(ident,$id) { lappend pid_names PID,$remote(ident,$id) } } # -pids LIST-OF-PIDS foreach pid $opt(pids) { foreach pid_name $all_pid_names { if { $remote($pid_name) == $pid } { lappend pid_names $pid_name # N.B. do not use 'break' here -- it may happen we # have the same PID on different hosts (unlikely but # potentially possible) } } } # -pattern PATTERN if { $opt(pattern) ne "" } { append pid_names " [array names remote PID,$opt(pattern)]" } # -hosts LIST-OF-HOSTS if { $opt(hosts) ne "" } { foreach host $opt(hosts) { append pid_names " [array names remote PID,[rhostonly_ $host],*]" } } # -all if { $opt(all) } { set pid_names $all_pid_names } # gets idents & pids... lassign {} idents pids foreach ident [lmap pid_name [::pwtk::lunique $pid_names] {regsub PID, $pid_name {}}] { set id $remote(ID,$ident) if { [info exists remote(ident,$id)] } { lappend idents $ident lappend pids $remote(PID,$ident) } } # wait for PIDs to finish if { $pids ne {} } { print "Waiting for remote processes with PIDS $pids to finish...\n" } foreach ident $idents { remote_pidwait $remote(user_at_host,$ident) $remote(PID,$ident) set id $remote(ID,$ident) unset remote(ident,$id) ifnotexist first { puts ""; set first 1 } print "$remote(rsync) $remote(user_at_host,$ident):$remote(rdir,$ident)/$remote(log,$ident) ." rsync $remote(user_at_host,$ident):$remote(rdir,$ident)/$remote(log,$ident) . } if { $pids ne {} } { puts "" } }