1#! /bin/sh
2#
3comm=`echo "$0" | sed -e 's&^.*/&&g'`
4bootflag="-boots"
5cleanflag="-noclean"
6maxflag="-max"
7outflag="-out"
8niceflag="-nice"
9seedflag="-seed"
10stdopt="| jumble"
11
12cleanUp=1
13jumbles=10
14nice=10
15remaining=1
16saveOut=0
17seed="$$`date +%M%S`"
18
19#  The spaces in the echo and grep are required because of a "feature" that
20#  causes /bin/sh echo to consume ANY leading argument that begins with -n.
21
22while echo " $1" | grep "^ -" >/dev/null; do
23    if   test $# -lt 2;        then break
24    elif test $1 = $maxflag;   then jumbles=$2; shift; shift
25    elif test $1 = "-m";       then jumbles=$2; shift; shift
26    elif test $1 = $cleanflag; then cleanUp=0; shift
27    elif test $1 = "-c";       then cleanUp=0; shift
28    elif test $1 = $niceflag;  then nice=$2; shift; shift
29    elif test $1 = "-n";       then nice=$2; shift; shift
30    elif test $1 = $outflag;   then saveOut=1; shift
31    elif test $1 = "-o";       then saveOut=1; shift
32    elif test $1 = $seedflag;  then seed=$2; shift; shift
33    elif test $1 = "-s";       then seed=$2; shift; shift
34    elif test $1 = $bootflag;  then remaining=$2; shift; shift
35    elif test $1 = "-b";       then remaining=$2; shift; shift
36    elif test $1 = "-";        then shift; break
37    else echo "Bad flag:  $*"; while test $# -gt 0; do shift; done; break
38    fi
39done
40
41if test $# -eq 2; then
42    opts="$stdopt";
43elif test $# -eq 3; then
44    if test -n "$3"; then opts="$stdopt | $3"
45    else opts="$stdopt"
46    fi
47else
48    cleanprm="[$cleanflag]"
49    saveprm="[$saveflag]"
50    cntprm="[$bootflag nboot]"
51    maxprm="[$maxflag maxjumble]"
52    niceprm="[$niceflag nicevalue]"
53    seedprm="[$seedflag seed]"
54    optprm="[ "'"'"dnaml_opt1 [ | dnaml_opt2 [...]]"'"'" ]"
55    echo "
56Usage: $comm  $cntprm  $seedprm\\
57               $maxprm  $niceprm  $cleanprm  $saveprm\\
58               in_file  n_best  $optprm
59
60For the current bootstrap seed, the sequence input order is jumbled (up to
61maxjumble times) until the same best tree is found n_best times.  The output
62files are then reduced to a summary of the scores produced by jumbling, and one
63example of the best tree.  The number process is then repeated with new
64bootstrap seeds until nboot samples have been analyzed.
65
66Boot and jumble are included by the script and should not be specified by the
67user or in the data file.  Additional�fastDNAml program options are enclosed in
68quotes, and separated by vertical bars (|).
69
70Flags and parameters:
71
72    in_file -- name of the input data file
73    n_best -- input order is jumbled (up to maxjumble times) until same tree
74              is found n_best times
75    $bootflag nboot -- number of different bootstrap samples (Default=1)
76    $seedflag seed -- seed for first bootstrap (Default is based on the process
77                  ID and time of day)
78    $maxflag maxjumble -- maximum attempts at replicating inferred tree
79                      (Default=10)
80    $niceflag nicevalue -- run fastDNAml with specified nice value (Default=10)
81    $cleanflag -- inhibits cleanup of the files for the individual jumbles
82    $saveflag -- inhibits cleanup of the text output from fastDNAml
83"
84    exit
85fi
86
87if test $cleanUp -ne 0; then cleanflag=""; fi
88if test $saveOut -eq 0; then outflag=""; fi
89
90if   test -f "$1"; then
91    root=`echo "$1" | sed -e 's/\.phylip$//' -e 's/\.phy$//'`; in="$1"
92elif test -f "$1.phy"; then
93    root="$1"; in="$1.phy"
94elif test -f "$1.phylip"; then
95    root="$1"; in="$1.phylip"
96else
97    echo "$comm: Unable to find input file: $1"; exit
98fi
99
100seed=`echo $seed | awk '{printf("%09d",$1)}'`
101out=`echo "${root}_$seed" | sed -e 's&^.*/&&'`
102
103#  Check for reuse of same random seed:
104
105if test ! -f "$out.tree" -a ! -f "$out.out"; then
106
107#  Loop over jumble orders:
108
109    while
110        if test `ls -d $out.[0-9]* 2>/dev/null | wc -l` -gt 0; then
111            nJumble=`grep '^Ln Likelihood' $out.[0-9]* /dev/null | wc -l`
112            nBest=`grep '^Ln Likelihood' $out.[0-9]* /dev/null |
113                  sed -e 's/^.*:Ln Likelihood =\(.*\)$/\1/g' | sort -nr +0 |
114                  awk 'BEGIN{c=0} NR==1{b=$1-0.001} $1>=b{c++} END{print c}'`
115        else
116            nBest=0
117            nJumble=0
118        fi
119
120        test $nBest -lt $2 -a $nJumble -lt $jumbles
121    do
122        eval "bootstrap $seed < $in  $opts |
123              nice -$nice out.PID fastDNAml $out" >/dev/null || exit
124    done
125
126    if test $cleanUp -ne 0; then
127#
128#     clean_jumbles
129#
130#     Check for files
131
132        if test `ls -d $out.[0-9]* 2>/dev/null | wc -l` -eq 0; then
133            echo "$comm: No files found for $out"
134            exit
135        fi
136
137#     Find file suffix with the best score
138
139        pid=`grep '^Ln Likelihood' $out.[0-9]* /dev/null |
140            sed 's/^\(.*\):Ln Like.*=\(.*\)$/\2	\1/' |
141            sort -nr +0 | head -1 | sed -e 's/^[^	]*	//' -e 's/^.*\.//'`
142
143        if test -z "$pid"; then
144            echo "$comm: No likelihoods found for $out"
145            exit
146        fi
147
148#     Move output and treefile to new names
149
150        treenew="$out.tree"
151        treeold="treefile.$pid"
152        checkpt="checkpoint.$pid"
153
154        if   test -f "$treeold"; then  mv "$treeold" "$treenew"
155        elif test -f "$checkpt"; then  tail -1 "$checkpt" >"$treenew"
156        else echo "$comm: Cannot find tree file.  Bootstrap aborted."; exit
157        fi
158        rm -f  "$checkpt"
159
160        oldname="$out.$pid"
161        if test $saveOut -ne 0; then  mv  "$oldname"  "$out.out"
162        else rm -f "$oldname"
163        fi
164
165#     Remove other output, tree and checkpoint files:
166
167        if test `ls -d $out.[0-9]* 2>/dev/null | wc -l` -gt 0; then
168            pids=`grep '^Ln Likelihood' $out.[0-9]* /dev/null |
169                sed -e 's/^\(.*\):Ln Like.*$/\1/' -e 's/^.*\.//'`
170
171            for pid in $pids; do
172                rm -f  "$out.$pid"  "treefile.$pid"  "checkpoint.$pid"
173            done
174        fi
175
176#     End of clean_jumbles
177
178    fi
179    remaining=`expr $remaining - 1`
180fi
181
182#  Check number of replicates:
183
184if test $remaining -gt 0; then
185    $0 $bootflag $remaining $maxflag $jumbles $cleanflag $outflag $niceflag $nice "$@" &
186fi
187