#! /bin/bash # # epix: wrapper script for ePiX # # Options: --help for usage, --version for version and license # # Compiler flags may be specified on the command line or in the config # file ~/.epixrc. The script attempts to deal intelligently with missing # or multiple extensions. If the input file has a recognized extension, # there's no issue. If only the root name is given, the script # searches for completions in the order of preference dictated by the # variable EPIX_EXTENSIONS. A warning is issued for multiple matches. # # Copyright (C) 2001, 2002, 2003, 2004, 2005, 2006, 2007 # Andrew D. Hwang # . "@pkglibdir@/epix-lib.sh" EPIX_CONFIG_FILE="$HOME/.epixrc" # Search these extensions in order of preference EPIX_EXTENSIONS="xp flx cc c C cpp" # or NULL EPIX_DOT_EXT=".${EPIX_EXTENSIONS// /|.}" # for usage message # Default inc/lib directories and compiler DEFAULT_INC="-I@includedir@" DEFAULT_LIB="-L@pkglibdir@" COMPILER="@RUNTIME_COMPILER@" # Use default library unless we're called by version number LIBS="-lm" POSTLIBS="-lepix" EPIX_SRC_EXT=cc declare EPIX_MYINCLUDES declare EPIX_MYLIBDIRS declare EPIX_MYLIBS declare EPIX_MYWARNS declare EPIX_MYFLAGS declare -a EPIX_FILE_LIST declare -a TEMPFILES trap '[ -n "${TEMPFILES[*]}" ] && rm -f "${TEMPFILES[@]}"' 0 1 2 3 7 10 13 15 function epix_help() { cat <<"HELP" Options: -h, --help Show this message and exit -V, --version Show version and exit -v, --verbose Show success/failure messages --gpl Show license -o, --output Specify output file name (ONLY for use with a single input file) --pst Write output file using PSTricks macros --tikz Write output file using tikz macros --eepic Write output file using eepic macros -I Append include directory -L Append library directory -l Link against lib --no-defaults Do not use default include/library directories or libraries -cc, --compiler) Specify the compiler (e.g., gcc) All other options are passed to the compiler. Valid options, one per line, may be placed in $HOME/.epixrc. HELP ePiX_bugreport } # End of epix_help # Parse command line/config file for compiler flags/options function epix_parse_options { while [ "$1" != "${1#-}" ]; do case "$1" in -I) if [ $# -lt 2 ]; then ePiX_die "Missing argument to \"$1\" option"; fi EPIX_MYINCLUDES="$EPIX_MYINCLUDES -I$2"; shift 2; continue ;; -L) if [ $# -lt 2 ]; then ePiX_die "Missing argument to \"$1\" option"; fi EPIX_MYLIBDIRS="$EPIX_MYLIBDIRS -L$2"; shift 2; continue ;; -l) if [ $# -lt 2 ]; then ePiX_die "Missing argument to \"$1\" option"; fi EPIX_MYLIBS="$EPIX_MYLIBS -l$2"; shift 2; continue ;; -W) if [ $# -lt 2 ]; then ePiX_die "Missing argument to \"$1\" option"; fi EPIX_MYWARNS="$EPIX_MYWARNS -W$2"; shift 2; continue ;; -I*) EPIX_MYINCLUDES="$EPIX_MYINCLUDES $1"; shift; continue ;; -L*) EPIX_MYLIBDIRS="$EPIX_MYLIBDIRS $1"; shift; continue ;; -l*) EPIX_MYLIBS="$EPIX_MYLIBS $1"; shift; continue ;; -W*) EPIX_MYWARNS="$EPIX_MYWARNS $1"; shift; continue ;; -i*|-u|-x) if [ $# -lt 2 ]; then ePiX_die "Missing argument to \"$1\" option"; fi EPIX_MYFLAGS="$EPIX_MYFLAGS $1 $2"; shift 2; continue ;; -b) ePiX_warn "Skipping option \"$1 $2\"" shift 2; continue ;; -o|--output) if [ $# -lt 2 ]; then ePiX_die "Missing argument to \"$1\" option"; fi EPIX_OUTFILE="$2" EPIX_OUTROOT="${EPIX_OUTFILE%%.eepic}" shift 2; continue ;; --pst) EPIX_MYFLAGS="$EPIX_MYFLAGS -DEPIX_FMT_PSTRICKS" shift; continue ;; --tikz) EPIX_MYFLAGS="$EPIX_MYFLAGS -DEPIX_FMT_TIKZ" shift; continue ;; --eepic) EPIX_MYFLAGS="$EPIX_MYFLAGS -DEPIX_FMT_EEPIC" shift; continue ;; # Deliberately undocumented -q|--quiet) EPIX_STDOUT="$SYSTEM_DEVNULL" EPIX_STDERR="$SYSTEM_DEVNULL" shift; continue ;; -v|--verbose) if [ -z "$2" ]; then echo "Please use -V for version" exit 0 fi EPIX_STDOUT="$SYSTEM_STDOUT" EPIX_STDERR="$SYSTEM_STDERR" shift; continue ;; -vv) echo "Discontinued option -vv; please use -v for verbose output" exit 0 ;; -h|--help) ePiX_usage epix $EPIX_DOT_EXT epix_help exit 0 ;; -V|--version|--gpl) ePiX_version epix ePiX_license exit 0 ;; --no-defaults) POSTLIBS= DEFAULT_INC= DEFAULT_LIB= shift; continue ;; -cc|--compiler) if [ $# -lt 2 ]; then ePiX_die "Missing argument to \"$1\" option"; fi COMPILER=$2 COMP_NAME=$(basename "$COMPILER") if [ "${COMP_NAME: -2}" = cc ]; then EPIX_SRC_EXT=c; fi shift 2; continue ;; *) EPIX_MYFLAGS="$EPIX_MYFLAGS $1"; shift; continue ;; esac done # Assume remaining parameters are input files EPIX_FILE_LIST=("$@") } # End of epix_parse_options # Compile specified files to eepic function epix_compile_files { if [ -z "$1" ]; then ePiX_die "No input file specified" fi mkdir "$EPIX_TEMPDIR" || ePiX_die "Can't create \"${EPIX_TEMPDIR}\"" # file counts local processed=0 local success=0 local failure=0 for EPIX_INFILE in "${EPIX_FILE_LIST[@]}"; do # sets EPIX_INROOT, EPIX_SUFFIX, EPIX_NOTFOUND, touches EPIX_LOGFILE epix_parse_filename "$EPIX_INFILE" "$EPIX_EXTENSIONS" let processed=processed+1 if [ "$EPIX_NOTFOUND" = "yes" ]; then ePiX_fail && continue; fi : ${EPIX_OUTROOT:=$EPIX_INROOT} EPIX_OUTFILE="$EPIX_OUTROOT".eepic { TEMP_BIN="$EPIX_INROOT" && touch "${EPIX_TEMPDIR}/$TEMP_BIN" && TEMPFILES=("{TEMPFILES[@]}" "${EPIX_TEMPDIR}/$TEMP_BIN") ; } || { ePiX_fail "Couldn't create \"$EPIX_TEMPDIR/$TEMP_BIN\"" && continue;} # Create symlink to input file with appropriate extension for compiler TEMP_INPUT="${TEMP_BIN}-tmp.$EPIX_SRC_EXT" TEMPFILES=("{TEMPFILES[@]}" "${EPIX_TEMPDIR}/$TEMP_INPUT") { cd ${EPIX_TEMPDIR} && \ ln -s "../$EPIX_INFILE" "$TEMP_INPUT" && cd .. ; } || { ePiX_fail "Couldn't create \"${EPIX_TEMPDIR}/$TEMP_INPUT\"" && \ continue; } # Log message, and compile executable TMP_CMD=($COMPILER "${EPIX_TEMPDIR}/${TEMP_INPUT}" $EPIX_MYWARNS \ -o "${EPIX_TEMPDIR}/${TEMP_BIN}" \ $EPIX_MYFLAGS $EPIX_MYINCLUDES $DEFAULT_INC $EPIX_MYLIBDIRS \ $DEFAULT_LIB $LIBS $EPIX_MYLIBS $POSTLIBS) ePiX_command "${TMP_CMD[@]}" # Write eepic file if [ -x "$EPIX_TEMPDIR/$TEMP_BIN" ]; then echo "%% Generated from $EPIX_INFILE on $(date) by" \ > "$EPIX_OUTFILE" ePiX_msg "Writing eepic file: ./$EPIX_TEMPDIR/$TEMP_BIN > $EPIX_OUTFILE" ./$EPIX_TEMPDIR/"$TEMP_BIN" >> "$EPIX_OUTFILE" if [ $? -ne 0 ]; then ePiX_warn "Could not create $EPIX_OUTFILE" let failure=failure+1 else let success=success+1 fi else ePiX_warn "Compilation of $EPIX_INFILE failed" let failure=failure+1 fi # Clean up; for multiple input files, clear output name rm -f "$EPIX_TEMPDIR/$TEMP_BIN" "$EPIX_TEMPDIR/$TEMP_INPUT" if [ "$EPIX_OUTROOT" = "$EPIX_INROOT" ]; then unset EPIX_OUTROOT; fi echo -e "\nTranscript written on $EPIX_LOGFILE" > "$EPIX_STDOUT" done # for EPIX_INFILE in $INFILE_LIST if [ $processed -gt 1 ]; then echo "$processed files processed: $success successfully, $failure failed" > "$EPIX_STDERR" fi if [ -d "$EPIX_TEMPDIR" ]; then rm -Rf "$EPIX_TEMPDIR"; fi } # end of epix_compile_files ## Script proper starts here ## if [ $# -eq 0 ]; then ePiX_usage epix $EPIX_DOT_EXT epix_help exit 0 fi # Read options from the config file, if any if [ -f "$EPIX_CONFIG_FILE" ]; then cat "$EPIX_CONFIG_FILE" | grep -v "#" | \ while read line; do epix_parse_options "$line" done fi # Command line options override config file options epix_parse_options "$@" # Suppress all warnings if none are requested if [ "$EPIX_MYWARNS" = "" ]; then EPIX_MYWARNS="-w"; fi # Remaining option(s) assumed to be input file(s) epix_compile_files "${EPIX_FILE_LIST[@]}" exit 0