diff --git a/bin/rivet-buildplugin.in b/bin/rivet-buildplugin.in old mode 100644 new mode 100755 --- a/bin/rivet-buildplugin.in +++ b/bin/rivet-buildplugin.in @@ -1,302 +1,302 @@ #!/usr/bin/env bash ## -*- sh -*- ## @configure_input@ ## Get program name PROG=$(basename $0) ## Default value for num_jobs is all available cores let num_jobs=$(getconf _NPROCESSORS_ONLN) function usage { cat <<-EOF $PROG: Compile a Rivet analysis plugin library from one or more sources Usage: $PROG [options] [libname] source1 [...] [compiler_flags] can be a path, provided the filename is of the form 'Rivet*.so' If is not specified, the default name is 'RivetAnalysis.so'. To make special build variations you can add appropriate compiler flags to the arguments and these will be passed directly to the compiler. For example, for a debug build of your plugin library, add '-g', and for a 32 bit build on a 64 bit system add '-m32'. Options: -h | --help: display this help message -j NUM number of parallel compile jobs [$num_jobs] -r | --with-root: add ROOT link options (requires root-config on system) -n | --cmd | --dry-run: just print the generated commands, do not execute -k | --keep: keep intermediate files -v | --verbose: write out debug info EOF } ################## ## Option handling # http://www.bahmanm.com/blogs/command-line-options-how-to-parse-in-bash-using-getopt ## Translate long options to short # https://stackoverflow.com/a/5255468 args=() for arg do case "$arg" in # translate our long options --help ) args+=("-h");; --with-root ) args+=("-r");; --cmd | --dry-run ) args+=("-n");; --keep ) args+=("-k");; --verbose ) args+=("-v");; # pass through anything else * ) args+=("$arg");; esac done ## Reset the translated args set -- "${args[@]}" ## Now we can process with getopt while getopts ":hj:rnkv" opt; do case $opt in h) usage; exit 0 ;; j) num_jobs=$OPTARG ;; r) with_root=yes ;; n) only_show=yes ;; k) keep_tmps=yes ;; v) debug=yes ;; \?) echo "Unknown option -$OPTARG" >&2; exit 1 ;; :) echo "Option -$OPTARG requires an argument" >&2; exit 1 ;; esac done ## Remove options shift $((OPTIND-1)) ## Check num_jobs is a number if [[ ! $num_jobs -eq $num_jobs ]]; then echo "Unknown argument to -j" >&2; exit 1 fi if [[ $num_jobs -lt 1 ]]; then echo "Number of jobs must be positive" >&2; exit 1 fi #echo "$with_root" #echo "$only_show" #echo "$@" ## Need some args left at this point if [[ $# -lt 1 ]]; then usage >&2 exit 1 fi ## Get and check the target library name libname="$1" match1=$(basename "$libname" | egrep '^.*\.so') match2=$(basename "$libname" | egrep '^Rivet.*\.so') if test -n "$match1"; then if test -z "$match2"; then echo "Library name '$libname' does not have the required 'Rivet*.so' name pattern" >&2 exit 1 fi ## If we're using the first arg as the library name, shift it off the positional list shift else if [[ -z $only_show ]]; then echo "Using default library name 'RivetAnalysis.so'" fi libname="RivetAnalysis.so" fi ## Again need some args left at this point if [[ $# -lt 1 ]]; then usage >&2 exit 1 fi ################## ## Now assemble the build flags ## These variables need to exist, may be used in later substitutions ## Note no use of $DESTDIR... we ignore it so that destdir can be used ## for temp installs later copied to / prefix="@prefix@" exec_prefix="@exec_prefix@" datarootdir="@datarootdir@" ## Work out shared library build flags by platform if [[ $(uname) == "Darwin" ]]; then ## Mac OS X shared_flags="-undefined dynamic_lookup -bundle" else ## Unix shared_flags="-shared -fPIC" fi ## Get Rivet system C++ compiler (fall back to $CXX and then g++ if needed) mycxx=g++ rivetcxx=$(which $(echo "@RIVETCXX@" | awk '{print $1}') 2> /dev/null) abscxx=$(which "$CXX" 2> /dev/null) if [[ -x "$rivetcxx" ]]; then mycxx="@CXX@" elif [[ -x "$abscxx" ]]; then mycxx="$CXX" fi ## Get Rivet system C++ compiler flags if [[ -n "@AM_CXXFLAGS@" ]]; then mycxxflags="@AM_CXXFLAGS@" fi if [[ -n "@RIVETCXXFLAGS@" ]]; then mycxxflags="$mycxxflags @RIVETCXXFLAGS@" fi ## Get Rivet system C preprocessor flags (duplicating that in rivet-config.in) if [[ -n "$RIVET_BUILDPLUGIN_BEFORE_INSTALL" ]]; then irivet="@top_srcdir@/include" else irivet="@includedir@" fi test -n "$irivet" && mycppflags="$mycppflags -I${irivet}" +iyoda="@YODAINCPATH@" +test -n "$iyoda" && mycppflags="$mycppflags -I${iyoda}" ihepmc="@HEPMCINCPATH@" test -n "$ihepmc" && mycppflags="$mycppflags -I${ihepmc}" -iyoda="@YODAINCPATH@" -test -n "$iyoda" && mycppflags="$mycppflags -I${iyoda}" ifastjet="@FASTJETINCPATH@" test -n "$ifastjet" && mycppflags="$mycppflags -I${ifastjet}" # igsl="@GSLINCPATH@" # test -n "$igsl" && mycppflags="$mycppflags -I${igsl}" # iboost="@BOOST_CPPFLAGS@" # test -n "$iboost" && mycppflags="$mycppflags ${iboost}" ## Get Rivet system linker flags (duplicating that in rivet-config.in) myldflags="" if [[ -n "$RIVET_BUILDPLUGIN_BEFORE_INSTALL" ]]; then lrivet="@top_builddir@/src/.libs" else lrivet="@libdir@" fi test -n "$lrivet" && myldflags="$myldflags -L${lrivet}" lhepmc="@HEPMCLIBPATH@" test -n "$lhepmc" && myldflags="$myldflags -L${lhepmc}" lyoda="@YODALIBPATH@" test -n "$lyoda" && myldflags="$myldflags -L${lyoda}" lfastjet="@FASTJETCONFIGLIBADD@" test -n "$lfastjet" && myldflags="$myldflags ${lfastjet}" ## Detect whether the linker accepts the --no-as-needed flag and prepend the linker flag with it if possible if (cd /tmp && echo -e 'int main() { return 0; }' > $$.cc; $mycxx -Wl,--no-as-needed $$.cc -o $$ 2> /dev/null); then myldflags="-Wl,--no-as-needed $myldflags" fi ## Get ROOT flags if needed if [[ -n $with_root ]]; then rootcxxflags=$(root-config --cflags 2> /dev/null) rootldflags=$(root-config --libs 2> /dev/null) fi ################## ## Assemble and run build machinery ## Split sources into buckets, one for each core let idx=1 sources="" for src in "$@" do if [[ -s "$src" ]]; then sources="$sources $src" buckets[$idx]="${buckets[$idx]} $src" let idx=(idx%$num_jobs)+1 else if [[ ${src:0:1} == "-" ]]; then ## Found a user option usercxxflags="$usercxxflags $src" else echo "Warning: $src not found" >&2 fi fi done ## May be less than num_jobs let num_buckets=${#buckets[@]} if [[ $num_buckets -lt 1 ]]; then echo "Error: no source files found" >&2 exit 2 fi ## Loop over buckets for idx in $(seq 1 $num_buckets); do # DO NOT SIMPLIFY, the OS X mktemp can't deal with suffixes directly tmpfile="$(mktemp tmp.XXXXXXXX)" mv "$tmpfile" "$tmpfile.cc" tmpfile="$tmpfile.cc" for i in $(echo ${buckets[$idx]}); do #< find the real way to do this! echo "#line 1 \"$i\"" >> "$tmpfile" cat "$i" >> "$tmpfile" done if [[ -s "$tmpfile" ]]; then srcnames[$idx]="$tmpfile" fi done objnames=("${srcnames[@]/.cc/.o}") if [[ -z "$debug" ]]; then silencer="@"; fi tmpmakefile=$(mktemp Makefile.tmp.XXXXXXXXXX) cat > "$tmpmakefile" <