#! /bin/sh
#
# Example script to create a series of calculations for varying lattice
# constant for fcc Al. 
# 
# We use the so called here-script mechanism to create the pipe input
# on the fly.
# This script works with bash at least. For other shells part of the syntax
# may be different. Consult your man pages.
# 
# We assume that the script is exectuted in a directory, where there is
# an inital calculation sub directory called SC containing a converged
# calculation of the same compound (fcc Al).
# 
########################################################################


# Always use fully qualified names, to assure proper program version.
# Store the exec names in variables, so we do not need to scan the script
# to replace the version later on.
FEDIT=fedit14.00-48-x86_64
FPLO=fplo14.00-48-x86_64


# Give all directories a name prefixed with the name of the parameter,
# which is running, followed by the parameter itself
prefix='a0='

# Remember the current directory.
# Be aware of the back quote syntax, on some unix systems you need a different 
# construct to cast the output of a command (pwd here) to a string.
ROOT=`pwd`


########################################################################
# some functions
usage() {
  echo "usage:  $1 [-r]  [-h[elp]]"
}

########################################################################

# Check the command line flags.
#
RUN_IT=0

while :
  do case $1 in
    -r) RUN_IT=1
        shift 1
        continue
        ;;
    -h*)
        usage `basename $0`
        exit 
        ;;
    -*) usage `basename $0`
        echo 'wrong options'
        exit
        ;;
    *)  break
        ;;
  esac
done


#
# security questions
#
if [ x$RUN_IT = x1 ]
then
    echo "Shall I run the jobs: [y/n]" ; read YN
    # The next test is a little trick to circumvent problems with
    # empty variable. We first form the concatenation x$YN, which
    # has the value of $YN prefixed with a single x.
    # Then we compare it with the teststring (y in our case) prefixed by x.
    # So, if $YN=y than also x$YN=xy. Disturbing?
    if [ "x$YN" != "xy" ] ; then
        echo "abort"
        exit
    else
        echo "Will run jobs now."
    fi
else
    echo "Shall I (re)create the input: [y/n]" ; read YN
    if [ "x$YN" != "xy" ] ; then
        echo "abort"
        exit
    else
        echo "Will (re)create input  now."
    fi
fi

########################################################################






# loop over the running parameter, in our case the lattice constant
for xx in 6.50 7.00 7.50 8.00 8.50
do

    # make sure we are in the root directory of our data directory tree
    cd $ROOT

    # create the directory name as described above (example 'a0=6.00')
    dir="$prefix$xx"


    # check, if input creation or job running shall take place
    if [ x$RUN_IT = x0 ] ; then
        # input creation branch

    
        # if the directory does not yet exist, create one
        if [ ! -d $dir ] 
        then
            mkdir $dir
            echo "directory $dir created"
            # copy the essential files from the inital calculation
            # which is assumed to be in the directory SC
            cp  ./SC/=.sym ./SC/=.dens $dir
            echo " =. files copied"
        else
            echo "directory $dir exists allready"
        fi


        # change into the directory of paramter $xx
        cd $dir

        # Now create the pipe file content, with the help of a here-script.
        # For the sake of book keeping we will save the pipe info into a file.
        # (One could equally pipe directly into fedit.)
    


        # The next command is the here-script ( <<EOF ), whose stdout is 
        # redirected ( > ) into the file ./=.pipe.
        # Every thing which comes between the <<EOF line and the line below,
        # starting with EOF, will go into ./=.pipe. The main advantage of this 
        # approach is, that we may use shell variable replacement 
        # (interpolation) to put the information of the running variable
        # $xx at the proper position
        cat <<EOF  > ./=.pipe
########################################################################
# this is the beginning of the pipe file

# go to symmetry menu
@+@
    # title
    @c@Al, a0-variation
    # enter spacegroup select box
    @s@
        # select space group
        @225@
        # leave selectbox
        @x@
    # structure type
    @t@
       # crystal
       @c@
       # leave select box
       @x@
    # lenth units
    @u@
        # bohr radii
        @b@
        # leave select box
        @x@
    # lattice constants; Here we put our running variable.
    # We enter as first lattice constant the value which is in $xx,
    # then we use the fedit-','-syntax to repeat the value
    @l@ $xx , ,
    # set axis angles
    @a@90.,,
    # setup Wyckoff positions
    # number is one in our case
    @n@1
    # Now, give list of ALL !!! Wyckoff positions.
    @1@ Al @ 0.,,
    #
    # NOW CALL UPDATE, NEVER FORGET THIS!!!
    #
    @+@
    # leave symmetry menu
    @x@
# back in main menu
# This was the symmetry setup, and now we follow our advise to create
# the default =.in input by using the REBUILD-action. 
# (The space before the 'e' opens the alternative menu bar.)
@ e@ 
# now we have the default input, and are still in the main menu

# Let us set the number of k-points to a non default value:
@k@ 16,,

# Let us set the xc-potential version now:
# first enter select box
@v@
    # select via search
    !Perdew Wang 92!
    # leave select box, go back to main menu
    @x@

#Let us set the relativistic mode:
@r@
    # Select by search, please note that the parentheses indicating the hotkey 
    # are not considered in search mode.
    # (Have a look at the select box interactively.)
    !scalar relativistic!
    # leave select box
    @x@



# Let us set some options:
# enter options menu
@-@
    # Good habit is to select all options explicitly
    # This includes the options, which are selected by default.

    # here an example for deselecting
    !PLOT_BASIS!-
    # here an example for selecting, 
    !NO_SYMMETRYTEST!+

    #leave menu
    @x@


# Let us select spin=1 explicitly:
@s@1

# Let us switch off inital polarization explicitly:
@i@f






# last action must be
@q@

# this is the end of the pipe file
########################################################################
EOF


        # Now execute fedit in pipe mode and use the information of the file
        # =.pipe just created in $dir.
        # We made sure that we are in $dir, since fedit shall act there!
        # We explicitely tell fedit to use the fplo executable stored in the 
        # variable $FPLO to have a well-defined state.

        $FEDIT -p $FPLO -pipe <./=.pipe 2>./+log 1>/dev/null

        # Check exit/return code of fedit, there must not be any command 
        # in between the check and the command, which produced it (fedit here).
        # The return code is stored in the variable $? in shell.
        # exit=1 means success
        if [ $? -ne 1 ]
        then
            cat<<EOF 
Content of log file:
------------------------------------------------------------------------
EOF

            cat ./+log
        
            cat <<EOF
------------------------------------------------------------------------
There was an error in the pipe input. Check logfile above or in $dir/+log.
Be aware that the line numbers refere to the file $dir/=.pipe!
EOF
            exit 2;
        fi

        # If we are here, the input was created in $dir according to our setup
        # Now we continue with the next parameter

        # change back to where we started
        cd $ROOT


        # end of input branch
        
    else

        # job-run branch
        
        # change into the directory of paramter $xx
        cd $dir

        echo "$FPLO running in  $dir ..."

        # now execute, whatever is nessecary to launch job in the current 
        # directory (name $dir)

        #START: example
        # We just run the jobs sequentially on a single machine
        # and redirect stdout to file out and stderr to /dev/null.
        # (In this way there will be no dangling output and the job could run
        # savely in background, which is not done in our example here.)

        # Furthermore, we use the +yes-file mechanism to avoid a crash
        # due to repeated inital polarization (spin split).
        # The "y" below enforces fplo to continue in such situation 
        # without a repeated split and  does nothing otherwise. See manual.

        echo "y" > ./+yes
        

        cat +yes | $FPLO 2>/dev/null > out
        
        #END:   example



        # change back to where we started
        cd $ROOT
    fi


# end of xx-loop
done

if [ x$RUN_IT = x1 ] ; then
    grepfplo -p 'a0=' -m EE | tee e
fi

# 
# After the input creation run we should have a directory structure like
#
# ./SC/
# ./a0=6.00/
# ./a0=6.50/
# ./a0=7.00/
# ./a0=7.50/
# ./a0=8.00/
# ./a0=8.50/
# ./script
#
# where every directory contains the same setup, except for the
# lattice constant.
# We may now perform converged calculations (option -r) in all directories.
# If we want to change, say, the number of k-points, we edit this number
# in the pipe-section above, re-run that script to change the input and 
# re-converge the calculations (option -r).
#
