Syntax error while using End of Message (EOM) inside a while loop in ubuntu shell script
I have a code containing a command where the user is prompted to select an option from those shown in the menu. This needs to be repeatedly executed for several times, hence I have used the while loop. Now, I have used EOM (End of message) method to give input when prompted. While using I have noticed that this method yeilds the follwoing error when executed. I have narrowed down the bug to this part of the code (line 80 to 83) and am not able to get pass this.
Please help me resolve this.
The lines where the error is ocuring:
TEMP="q"
gmx_mpi make_ndx -f pull_sim.gro -o index.ndx <<EOM
$TEMP
EOM
Error:
./Run_Pull_Code.sh: 105: Syntax error: end of file unexpected (expecting "done")
Kindly find the full following code (refer to lines 80 to 83 here):
#!/bin/sh
# The above comment sets the sh file to execute as an interpreter (Line by line)
# Finding the current working directory
BASEDIR=$(pwd)
echo "I am currently in the following directory:"
echo "$BASEDIR"
echo " "
##########################################################################################
# Setting the pulling code positions and decrements (All in nm)
##########################################################################################
DECREMENT=0.5 #Steps in nm
RANGE=1 #From the highest to the lowest position
MID_POS=9.327 #Observing the highest water molecule (O atom) of the water surface
INIT_POS=$( echo "$MID_POS + $RANGE" | bc -l) # Initial position
LAST_POS=$( echo "$MID_POS - $RANGE" | bc -l) # Final position
CURR_POS=$INIT_POS # Assigning the Initial position as the current position
LOOP_CNT=0
while [ 1 -eq "$(echo "${LAST_POS} <= ${CURR_POS}" | bc)" ]
do
# increment the value
LOOP_CNT=$( echo "$LOOP_CNT + 1" | bc -l)
DISTANCE=$CURR_POS
# Setting the loop number (X) as the pull code number for simulation (X)
SIM_CNT=$LOOP_CNT
# Making the directories (1) X_Pull (2) X_Pull/Making
DIR_NAME_MAIN=$SIM_CNT"_Pull"
mkdir $DIR_NAME_MAIN
DIR_NAME_MAKING=$SIM_CNT"_Pull/Making"
mkdir $DIR_NAME_MAKING
echo " "
echo "I have made the directories."
echo " "
# Copying the files from prerequisites folder to the newly created folder
cp Prerequisites/Avo_decanol.pdb Prerequisites/water_box.pdb $DIR_NAME_MAKING
cp Prerequisites/simulation_file.mdp Prerequisites/topol.top $DIR_NAME_MAIN
##########################################################################################
# Making the simulation box "pull_sim.gro"
##########################################################################################
cd $DIR_NAME_MAKING
#(1) Fix the distance of the decanol from the water surface and make the only decanol box with the same dimension as that of the water box
DISTANCE=9.5
gmx_mpi editconf -f Avo_decanol.pdb -o Dec_box.pdb -center 2.5 2.5 $DISTANCE -box 5 5 12
#(2) CREATING CONSTANT HEADER AND ENDER cat files in PDB format
#The first 4 lines of any PDB file contains the information of the box size and the name, etc.
#Just copy the four lines into a separate HEADER PDB file by the following command.
sed -n '1,4p' Dec_box.pdb > HEADER.pdb
#The last 2 lines are also common to all PDB files, hence copy these to a ENDER PDB file by the following command.
sed -n '38,39p' Dec_box.pdb > ENDER.pdb
#(3) Separate the decanol atom properties from its PDB file (line 5 to 37) by the follwing command
sed -n '5,37p' Dec_box.pdb > file_1.pdb
#(4) Separate the water atom properties from its PDB file (line 5 to 15004) by the follwing command
sed -n '5,15004p' water_box.pdb > file_2.pdb
#(5) Now connect all the above files with the water surface PDB file in the following sequence:
cat HEADER.pdb file_1.pdb file_2.pdb ENDER.pdb > pull_sim.pdb
#(6) Rearrange all the number of atoms in the pull_sim.pdb and convert it into a GRO file, pull_sim.gro file.
gmx_mpi editconf -f pull_sim.pdb -o pull_sim.gro -center 2.5 2.5 6.0 -box 5.0 5.0 12.0 -resnr 1
# Copying the recently made pull_sim.gro file from making folder to the previous folder
cd ../
cp Making/pull_sim.gro ./
echo " "
echo "The pull box has been created."
echo " "
##########################################################################################
# Starting the simulation
##########################################################################################
# (1) Making index file
TEMP="q"
gmx_mpi make_ndx -f pull_sim.gro -o index.ndx <<EOM
$TEMP
EOM
# (2) Creating tpr file from grompp module
gmx_mpi grompp -f simulation_file.mdp -p topol.top -c pull_sim.gro -n index.ndx -maxwarn 0 -o nvt.tpr
# Clearing all the contents
clear
echo " "
echo "#####################*********** Pull Simulation: $LOOP_CNT ***********#####################"
echo " "
# (3) mdrun
gmx_mpi mdrun -v -deffnm nvt -nb gpu -pme gpu -pmefft gpu -bonded gpu
# Moving back to the main folder
cd ../
# Decrementing the distance for the next loop
CURR_POS=$( echo "$CURR_POS - $DECREMENT" | bc -l)
done
#clear
echo " "
echo "Complete"
echo " "
Heredocs cannot be indented like the rest of the script (unless you use -EOM
but then you can only indent with tabs). After all, the purpose of the heredoc is to allow you to write something that will appear as is. This means that the EOM
cannot be like this:
while something;
do
command <<EOM
Hello!
EOM
done
Instead, the EOM
(or any other marked you use) needs to be the only thing on the line, so no whitespace or anything else before or after it. Like this:
while something;
do
command <<EOM
Hello!
EOM
done
Also, note that because of the reasons mentioned above, the leading whitespace will also be included, so that this:
c=0;
while [ $c -eq 0 ];
do
cat <<EOM
Hello!
EOM
let c++
done
Would print:
$ foo.sh
Hello!
While this:
c=0;
while [ $c -eq 0 ];
do
cat <<EOM
Hello!
EOM
let c++
done
Would print:
$ foo.sh
Hello!
Finally, when running your script, I get a different error:
$ foo.sh
I am currently in the following directory:
/home/terdon/foo
/home/terdon/scripts/foo.sh: line 108: warning: here-document at line 84 delimited by end-of-file (wanted `EOM')
/home/terdon/scripts/foo.sh: line 109: syntax error: unexpected end of file
This will be because I am not giving the same input data and, since you were not ending the EOM correctly, your data was probably being processed by the script and that's why you saw a different error. I expect my fix will get rid of it though, as it let me run your script through to the end on my machine.