Merge branch 'features/python' into develop

This commit is contained in:
Todd Gamblin 2014-11-03 14:20:37 -08:00
commit 488a6737b7
16 changed files with 552 additions and 248 deletions

420
lib/spack/env/cc vendored
View file

@ -1,140 +1,326 @@
#!/usr/bin/env python
import sys
if not sys.version_info[:2] >= (2,6):
sys.exit("Spack requires Python 2.6. Version was %s." % sys.version_info)
#!/bin/bash
##############################################################################
# Copyright (c) 2013, Lawrence Livermore National Security, LLC.
# Produced at the Lawrence Livermore National Laboratory.
#
# This file is part of Spack.
# Written by Todd Gamblin, tgamblin@llnl.gov, All rights reserved.
# LLNL-CODE-647188
#
# For details, see https://scalability-llnl.github.io/spack
# Please also see the LICENSE file for our notice and the LGPL.
#
# This program is free software; you can redistribute it and/or modify
# it under the terms of the GNU General Public License (as published by
# the Free Software Foundation) version 2.1 dated February 1999.
#
# This program is distributed in the hope that it will be useful, but
# WITHOUT ANY WARRANTY; without even the IMPLIED WARRANTY OF
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the terms and
# conditions of the GNU General Public License for more details.
#
# You should have received a copy of the GNU Lesser General Public License
# along with this program; if not, write to the Free Software Foundation,
# Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
##############################################################################
#
# Spack compiler wrapper script.
#
# Compiler commands go through this compiler wrapper in Spack builds.
# The compiler wrapper is a thin layer around the standard compilers.
# It enables several key pieces of functionality:
#
# 1. It allows Spack to swap compilers into and out of builds easily.
# 2. It adds several options to the compile line so that spack
# packages can find their dependencies at build time and run time:
# -I arguments for dependency /include directories.
# -L arguments for dependency /lib directories.
# -Wl,-rpath arguments for dependency /lib directories.
#
import os
import re
import subprocess
from contextlib import closing
# This is the list of environment variables that need to be set before
# the script runs. They are set by routines in spack.build_environment
# as part of spack.package.Package.do_install().
parameters="
SPACK_PREFIX
SPACK_ENV_PATH
SPACK_DEBUG_LOG_DIR
SPACK_COMPILER_SPEC
SPACK_SHORT_SPEC"
# Import spack parameters through the build environment.
spack_lib = os.environ.get("SPACK_LIB")
if not spack_lib:
print "Spack compiler must be run from spack!"
sys.exit(1)
# The compiler input variables are checked for sanity later:
# SPACK_CC, SPACK_CXX, SPACK_F77, SPACK_FC
# Debug flag is optional; set to true for debug logging:
# SPACK_DEBUG
# Test command is used to unit test the compiler script.
# SPACK_TEST_COMMAND
# Dependencies can be empty for pkgs with no deps:
# SPACK_DEPENDENCIES
# Grab a minimal set of spack packages
sys.path.append(spack_lib)
from spack.compilation import *
from external import argparse
import llnl.util.tty as tty
# die()
# Prints a message and exits with error 1.
function die {
echo "$@"
exit 1
}
spack_prefix = get_env_var("SPACK_PREFIX")
spack_debug = get_env_flag("SPACK_DEBUG")
spack_deps = get_path("SPACK_DEPENDENCIES")
spack_env_path = get_path("SPACK_ENV_PATH")
spack_debug_log_dir = get_env_var("SPACK_DEBUG_LOG_DIR")
spack_spec = get_env_var("SPACK_SPEC")
for param in $parameters; do
if [ -z "${!param}" ]; then
die "Spack compiler must be run from spack! Input $param was missing!"
fi
done
compiler_spec = get_env_var("SPACK_COMPILER_SPEC")
spack_cc = get_env_var("SPACK_CC", required=False)
spack_cxx = get_env_var("SPACK_CXX", required=False)
spack_f77 = get_env_var("SPACK_F77", required=False)
spack_fc = get_env_var("SPACK_FC", required=False)
#
# Figure out the type of compiler, the language, and the mode so that
# the compiler script knows what to do.
#
# Possible languages are C, C++, Fortran 77, and Fortran 90.
# 'command' is set based on the input command to $SPACK_[CC|CXX|F77|F90]
#
# 'mode' is set to one of:
# cc compile
# ld link
# ccld compile & link
# cpp preprocessor
# vcheck version check
#
command=$(basename "$0")
case "$command" in
cc|gcc|c89|c99|clang)
command="$SPACK_CC"
language="C"
;;
c++|CC|g++|clang++)
command="$SPACK_CXX"
language="C++"
;;
f77)
command="$SPACK_F77"
language="Fortran 77"
;;
fc|f90|f95)
command="$SPACK_FC"
language="Fortran 90"
;;
cpp)
mode=cpp
;;
ld)
mode=ld
;;
*)
die "Unkown compiler: $command"
;;
esac
# Figure out what type of operation we're doing
command = os.path.basename(sys.argv[0])
# Finish setting up the mode.
if [ -z "$mode" ]; then
mode=ccld
for arg in "$@"; do
if [ "$arg" = -v -o "$arg" = -V -o "$arg" = --version -o "$arg" = -dumpversion ]; then
mode=vcheck
break
elif [ "$arg" = -E ]; then
mode=cpp
break
elif [ "$arg" = -c ]; then
mode=cc
break
fi
done
fi
cpp, cc, ccld, ld, version_check = range(5)
# Dump the version and exist if we're in testing mode.
if [ "$SPACK_TEST_COMMAND" = "dump-mode" ]; then
echo "$mode"
exit
fi
if command == 'cpp':
mode = cpp
elif command == 'ld':
mode = ld
elif '-E' in sys.argv:
mode = cpp
elif '-c' in sys.argv:
mode = cc
else:
mode = ccld
# Check that at least one of the real commands was actually selected,
# otherwise we don't know what to execute.
if [ -z "$command" ]; then
die "ERROR: Compiler '$SPACK_COMPILER_SPEC' does not support compiling $language programs."
fi
# Save original command for debug logging
input_command="$@"
if command in ('cc', 'gcc', 'c89', 'c99', 'clang'):
command = spack_cc
language = "C"
elif command in ('c++', 'CC', 'g++', 'clang++'):
command = spack_cxx
language = "C++"
elif command in ('f77'):
command = spack_f77
language = "Fortran 77"
elif command in ('fc', 'f90', 'f95'):
command = spack_fc
language = "Fortran 90"
elif command in ('ld', 'cpp'):
pass # leave it the same. TODO: what's the right thing?
else:
raise Exception("Unknown compiler: %s" % command)
#
# Now do real parsing of the command line args, trying hard to keep
# non-rpath linker arguments in the proper order w.r.t. other command
# line arguments. This is important for things like groups.
#
includes=()
libraries=()
libs=()
rpaths=()
other_args=()
if command is None:
print "ERROR: Compiler '%s' does not support compiling %s programs." % (
compiler_spec, language)
sys.exit(1)
while [ -n "$1" ]; do
case "$1" in
-I*)
arg="${1#-I}"
if [ -z "$arg" ]; then shift; arg="$1"; fi
includes+=("$arg")
;;
-L*)
arg="${1#-L}"
if [ -z "$arg" ]; then shift; arg="$1"; fi
libraries+=("$arg")
;;
-l*)
arg="${1#-l}"
if [ -z "$arg" ]; then shift; arg="$1"; fi
libs+=("$arg")
;;
-Wl,*)
arg="${1#-Wl,}"
if [ -z "$arg" ]; then shift; arg="$1"; fi
if [[ "$arg" = -rpath=* ]]; then
rpaths+=("${arg#-rpath=}")
elif [[ "$arg" = -rpath ]]; then
shift; arg="$1"
if [[ "$arg" != -Wl,* ]]; then
die "-Wl,-rpath was not followed by -Wl,*"
fi
rpaths+=("${arg#-Wl,}")
else
other_args+=("-Wl,$arg")
fi
;;
-Xlinker,*)
arg="${1#-Xlinker,}"
if [ -z "$arg" ]; then shift; arg="$1"; fi
if [[ "$arg" = -rpath=* ]]; then
rpaths+=("${arg#-rpath=}")
elif [[ "$arg" = -rpath ]]; then
shift; arg="$1"
if [[ "$arg" != -Xlinker,* ]]; then
die "-Xlinker,-rpath was not followed by -Xlinker,*"
fi
rpaths+=("${arg#-Xlinker,}")
else
other_args+=("-Xlinker,$arg")
fi
;;
*)
other_args+=("$1")
;;
esac
shift
done
version_args = ['-V', '-v', '--version', '-dumpversion']
if any(arg in sys.argv for arg in version_args):
mode = version_check
# Dump parsed values for unit testing if asked for
if [ -n "$SPACK_TEST_COMMAND" ]; then
IFS=$'\n'
case "$SPACK_TEST_COMMAND" in
dump-includes) echo "${includes[*]}";;
dump-libraries) echo "${libraries[*]}";;
dump-libs) echo "${libs[*]}";;
dump-rpaths) echo "${rpaths[*]}";;
dump-other-args) echo "${other_args[*]}";;
dump-all)
echo "INCLUDES:"
echo "${includes[*]}"
echo
echo "LIBRARIES:"
echo "${libraries[*]}"
echo
echo "LIBS:"
echo "${libs[*]}"
echo
echo "RPATHS:"
echo "${rpaths[*]}"
echo
echo "ARGS:"
echo "${other_args[*]}"
;;
*)
echo "ERROR: Unknown test command"
exit 1 ;;
esac
exit
fi
# Parse out the includes, libs, etc. so we can adjust them if need be.
parser = argparse.ArgumentParser(add_help=False)
parser.add_argument("-I", action='append', default=[], dest='include_path')
parser.add_argument("-L", action='append', default=[], dest='lib_path')
parser.add_argument("-l", action='append', default=[], dest='libs')
# Read spack dependencies from the path environment variable
IFS=':' read -ra deps <<< "$SPACK_DEPENDENCIES"
for dep in "${deps[@]}"; do
if [ -d "$dep/include" ]; then
includes+=("$dep/include")
fi
options, other_args = parser.parse_known_args()
rpaths, other_args = parse_rpaths(other_args)
if [ -d "$dep/lib" ]; then
libraries+=("$dep/lib")
rpaths+=("$dep/lib")
fi
# Add dependencies' include and lib paths to our compiler flags.
def add_if_dir(path_list, directory, index=None):
if os.path.isdir(directory):
if index is None:
path_list.append(directory)
else:
path_list.insert(index, directory)
if [ -d "$dep/lib64" ]; then
libraries+=("$dep/lib64")
rpaths+=("$dep/lib64")
fi
done
for dep_dir in spack_deps:
add_if_dir(options.include_path, os.path.join(dep_dir, "include"))
add_if_dir(options.lib_path, os.path.join(dep_dir, "lib"))
add_if_dir(options.lib_path, os.path.join(dep_dir, "lib64"))
# Include all -L's and prefix/whatever dirs in rpath
for dir in "${libraries[@]}"; do
[ "$dir" != "." ] && rpaths+=("$dir")
done
rpaths+=("$SPACK_PREFIX/lib")
rpaths+=("$SPACK_PREFIX/lib64")
# Add our modified arguments to it.
arguments = ['-I%s' % path for path in options.include_path]
arguments += other_args
arguments += ['-L%s' % path for path in options.lib_path]
arguments += ['-l%s' % path for path in options.libs]
# Put the arguments together
args=()
for dir in "${includes[@]}"; do args+=("-I$dir"); done
args+=("${other_args[@]}")
for dir in "${libraries[@]}"; do args+=("-L$dir"); done
for lib in "${libs[@]}"; do args+=("-l$lib"); done
# Add rpaths to install dir and its dependencies. We add both lib and lib64
# here because we don't know which will be created.
rpaths.extend(options.lib_path)
rpaths.append('%s/lib' % spack_prefix)
rpaths.append('%s/lib64' % spack_prefix)
if mode == ccld:
arguments += ['-Wl,-rpath,%s' % p for p in rpaths]
elif mode == ld:
pairs = [('-rpath', '%s' % p) for p in rpaths]
arguments += [item for sublist in pairs for item in sublist]
if [ "$mode" = ccld ]; then
for dir in "${rpaths[@]}"; do args+=("-Wl,-rpath=$dir"); done
elif [ "$mode" = ld ]; then
for dir in "${rpaths[@]}"; do args+=("-rpath=$dir"); done
fi
# Unset some pesky environment variables
for var in ["LD_LIBRARY_PATH", "LD_RUN_PATH", "DYLD_LIBRARY_PATH"]:
if var in os.environ:
os.environ.pop(var)
#
# Unset pesky environment variables that could affect build sanity.
#
unset LD_LIBRARY_PATH
unset LD_RUN_PATH
unset DYLD_LIBRARY_PATH
# Ensure that the delegated command doesn't just call this script again.
remove_paths = ['.'] + spack_env_path
path = [p for p in get_path("PATH") if p not in remove_paths]
os.environ["PATH"] = ":".join(path)
#
# Filter '.' and Spack environment directories out of PATH so that
# this script doesn't just call itself
#
IFS=':' read -ra env_path <<< "$PATH"
IFS=':' read -ra spack_env_dirs <<< "$SPACK_ENV_PATH"
spack_env_dirs+=(".")
PATH=""
for dir in "${env_path[@]}"; do
remove=""
for rm_dir in "${spack_env_dirs[@]}"; do
if [ "$dir" = "$rm_dir" ]; then remove=True; fi
done
if [ -z "$remove" ]; then
if [ -z "$PATH" ]; then
PATH="$dir"
else
PATH="$PATH:$dir"
fi
fi
done
export PATH
full_command = [command] + arguments
full_command=("$command")
full_command+=("${args[@]}")
if spack_debug:
input_log = os.path.join(spack_debug_log_dir, 'spack-cc-%s.in.log' % spack_spec)
output_log = os.path.join(spack_debug_log_dir, 'spack-cc-%s.out.log' % spack_spec)
with closing(open(input_log, 'a')) as log:
args = [os.path.basename(sys.argv[0])] + sys.argv[1:]
log.write("%s\n" % " ".join(arg.replace(' ', r'\ ') for arg in args))
with closing(open(output_log, 'a')) as log:
log.write("%s\n" % " ".join(full_command))
#
# Write the input and output commands to debug logs if it's asked for.
#
if [ "$SPACK_DEBUG" = "TRUE" ]; then
input_log="$SPACK_DEBUG_LOG_DIR/spack-cc-$SPACK_SHORT_SPEC.in.log"
output_log="$SPACK_DEBUG_LOG_DIR/spack-cc-$SPACK_SHORT_SPEC.out.log"
echo "$input_command" >> $input_log
echo "$mode ${full_command[@]}" >> $output_log
fi
rcode = subprocess.call(full_command)
sys.exit(rcode)
exec "${full_command[@]}"

View file

@ -48,12 +48,11 @@
# set_build_environment_variables and used to pass parameters to
# Spack's compiler wrappers.
#
SPACK_LIB = 'SPACK_LIB'
SPACK_ENV_PATH = 'SPACK_ENV_PATH'
SPACK_DEPENDENCIES = 'SPACK_DEPENDENCIES'
SPACK_PREFIX = 'SPACK_PREFIX'
SPACK_DEBUG = 'SPACK_DEBUG'
SPACK_SPEC = 'SPACK_SPEC'
SPACK_SHORT_SPEC = 'SPACK_SHORT_SPEC'
SPACK_DEBUG_LOG_DIR = 'SPACK_DEBUG_LOG_DIR'
@ -108,9 +107,6 @@ def set_compiler_environment_variables(pkg):
def set_build_environment_variables(pkg):
"""This ensures a clean install environment when we build packages.
"""
# This tells the compiler script where to find the Spack installation.
os.environ[SPACK_LIB] = spack.lib_path
# Add spack build environment path with compiler wrappers first in
# the path. We handle case sensitivity conflicts like "CC" and
# "cc" by putting one in the <build_env_path>/case-insensitive
@ -140,7 +136,7 @@ def set_build_environment_variables(pkg):
# Working directory for the spack command itself, for debug logs.
if spack.debug:
os.environ[SPACK_DEBUG] = "TRUE"
os.environ[SPACK_SPEC] = str(pkg.spec)
os.environ[SPACK_SHORT_SPEC] = pkg.spec.short_spec
os.environ[SPACK_DEBUG_LOG_DIR] = spack.spack_working_dir
# Add dependencies to CMAKE_PREFIX_PATH

View file

@ -31,7 +31,7 @@
import spack.compilers
import spack.spec
import spack.config
from spack.compilation import get_path
from spack.util.environment import get_path
from spack.spec import CompilerSpec
description = "Manage compilers"

View file

@ -37,6 +37,10 @@ def setup_parser(subparser):
sp = subparser.add_subparsers(
metavar='SUBCOMMAND', dest='pkg_command')
add_parser = sp.add_parser('add', help=pkg_add.__doc__)
add_parser.add_argument('packages', nargs=argparse.REMAINDER,
help="Names of packages to add to git repo.")
list_parser = sp.add_parser('list', help=pkg_list.__doc__)
list_parser.add_argument('rev', default='HEAD', nargs='?',
help="Revision to list packages for.")
@ -79,6 +83,16 @@ def list_packages(rev):
return sorted(line[len(relpath):] for line in output.split('\n') if line)
def pkg_add(args):
for pkg_name in args.packages:
filename = spack.db.filename_for_package_name(pkg_name)
if not os.path.isfile(filename):
tty.die("No such package: %s. Path does not exist:" % pkg_name, filename)
git = get_git()
git('-C', spack.packages_path, 'add', filename)
def pkg_list(args):
"""List packages associated with a particular spack git revision."""
colify(list_packages(args.rev))
@ -117,7 +131,8 @@ def pkg_added(args):
def pkg(parser, args):
action = { 'diff' : pkg_diff,
action = { 'add' : pkg_add,
'diff' : pkg_diff,
'list' : pkg_list,
'removed' : pkg_removed,
'added' : pkg_added }

View file

@ -1,117 +0,0 @@
##############################################################################
# Copyright (c) 2013, Lawrence Livermore National Security, LLC.
# Produced at the Lawrence Livermore National Laboratory.
#
# This file is part of Spack.
# Written by Todd Gamblin, tgamblin@llnl.gov, All rights reserved.
# LLNL-CODE-647188
#
# For details, see https://scalability-llnl.github.io/spack
# Please also see the LICENSE file for our notice and the LGPL.
#
# This program is free software; you can redistribute it and/or modify
# it under the terms of the GNU General Public License (as published by
# the Free Software Foundation) version 2.1 dated February 1999.
#
# This program is distributed in the hope that it will be useful, but
# WITHOUT ANY WARRANTY; without even the IMPLIED WARRANTY OF
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the terms and
# conditions of the GNU General Public License for more details.
#
# You should have received a copy of the GNU Lesser General Public License
# along with this program; if not, write to the Free Software Foundation,
# Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
##############################################################################
"""\
The ``compilation`` module contains utility functions used by the compiler
wrapper script.
.. todo::
Think about moving this into the script to increase compilation
speed.
"""
import os
import sys
def get_env_var(name, required=True):
value = os.environ.get(name)
if required and value is None:
print "%s must be run from spack." % os.path.abspath(sys.argv[0])
sys.exit(1)
return value
def get_env_flag(name, required=False):
value = get_env_var(name, required)
if value:
return value.lower() == "true"
return False
def get_path(name):
path = os.environ.get(name, "").strip()
if path:
return path.split(":")
else:
return []
def parse_rpaths(arguments):
"""argparse, for all its features, cannot understand most compilers'
rpath arguments. This handles '-Wl,', '-Xlinker', and '-R'"""
def get_next(arg, args):
"""Get an expected next value of an iterator, or die if it's not there"""
try:
return next(args)
except StopIteration:
# quietly ignore -rpath and -Xlinker without args.
return None
other_args = []
def linker_args():
"""This generator function allows us to parse the linker args separately
from the compiler args, so that we can handle them more naturally.
"""
args = iter(arguments)
for arg in args:
if arg.startswith('-Wl,'):
sub_args = [sub for sub in arg.replace('-Wl,', '', 1).split(',')]
for arg in sub_args:
yield arg
elif arg == '-Xlinker':
target = get_next(arg, args)
if target is not None:
yield target
else:
other_args.append(arg)
# Extract all the possible ways rpath can appear in linker args, then
# append non-rpaths to other_args. This happens in-line as the linker
# args are extracted, so we preserve the original order of arguments.
# This is important for args like --whole-archive, --no-whole-archive,
# and others that tell the linker how to handle the next few libraries
# it encounters on the command line.
rpaths = []
largs = linker_args()
for arg in largs:
if arg == '-rpath':
target = get_next(arg, largs)
if target is not None:
rpaths.append(target)
elif arg.startswith('-R'):
target = arg.replace('-R', '', 1)
if not target:
target = get_next(arg, largs)
if target is None: break
if os.path.isdir(target):
rpaths.append(target)
else:
other_args.extend(['-Wl,' + arg, '-Wl,' + target])
else:
other_args.append('-Wl,' + arg)
return rpaths, other_args

View file

@ -35,8 +35,8 @@
import spack.spec
from spack.util.multiproc import parmap
from spack.util.executable import *
from spack.util.environment import get_path
from spack.version import Version
from spack.compilation import get_path
__all__ = ['Compiler', 'get_compiler_version']

View file

@ -40,7 +40,7 @@
from spack.compiler import Compiler
from spack.util.executable import which
from spack.util.naming import mod_to_class
from spack.compilation import get_path
from spack.util.environment import get_path
_imported_compilers_module = 'spack.compilers'
_required_instance_vars = ['cc', 'cxx', 'f77', 'fc']

View file

@ -53,7 +53,8 @@
'svn_fetch',
'hg_fetch',
'mirror',
'url_extrapolate']
'url_extrapolate',
'cc']
def list_tests():

130
lib/spack/spack/test/cc.py Normal file
View file

@ -0,0 +1,130 @@
##############################################################################
# Copyright (c) 2013, Lawrence Livermore National Security, LLC.
# Produced at the Lawrence Livermore National Laboratory.
#
# This file is part of Spack.
# Written by Todd Gamblin, tgamblin@llnl.gov, All rights reserved.
# LLNL-CODE-647188
#
# For details, see https://scalability-llnl.github.io/spack
# Please also see the LICENSE file for our notice and the LGPL.
#
# This program is free software; you can redistribute it and/or modify
# it under the terms of the GNU General Public License (as published by
# the Free Software Foundation) version 2.1 dated February 1999.
#
# This program is distributed in the hope that it will be useful, but
# WITHOUT ANY WARRANTY; without even the IMPLIED WARRANTY OF
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the terms and
# conditions of the GNU General Public License for more details.
#
# You should have received a copy of the GNU Lesser General Public License
# along with this program; if not, write to the Free Software Foundation,
# Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
##############################################################################
"""
This test checks that the Spack cc compiler wrapper is parsing
arguments correctly.
"""
import os
import unittest
from llnl.util.filesystem import *
import spack
from spack.util.executable import *
# Complicated compiler test command
test_command = [
'-I/test/include', '-L/test/lib', '-L/other/lib', '-I/other/include',
'arg1',
'-Wl,--start-group',
'arg2',
'-Wl,-rpath=/first/rpath', 'arg3', '-Wl,-rpath', '-Wl,/second/rpath',
'-llib1', '-llib2',
'arg4',
'-Wl,--end-group',
'-Xlinker,-rpath', '-Xlinker,/third/rpath', '-Xlinker,-rpath=/fourth/rpath',
'-llib3', '-llib4',
'arg5', 'arg6']
class CompilerTest(unittest.TestCase):
def setUp(self):
self.cc = Executable(join_path(spack.build_env_path, "cc"))
self.ld = Executable(join_path(spack.build_env_path, "ld"))
self.cpp = Executable(join_path(spack.build_env_path, "cpp"))
os.environ['SPACK_CC'] = "/bin/mycc"
os.environ['SPACK_PREFIX'] = "/usr"
os.environ['SPACK_ENV_PATH']="test"
os.environ['SPACK_DEBUG_LOG_DIR'] = "."
os.environ['SPACK_COMPILER_SPEC'] = "gcc@4.4.7"
os.environ['SPACK_SHORT_SPEC'] = "foo@1.2"
def check_cc(self, command, args, expected):
os.environ['SPACK_TEST_COMMAND'] = command
self.assertEqual(self.cc(*args, return_output=True).strip(), expected)
def check_ld(self, command, args, expected):
os.environ['SPACK_TEST_COMMAND'] = command
self.assertEqual(self.ld(*args, return_output=True).strip(), expected)
def check_cpp(self, command, args, expected):
os.environ['SPACK_TEST_COMMAND'] = command
self.assertEqual(self.cpp(*args, return_output=True).strip(), expected)
def test_vcheck_mode(self):
self.check_cc('dump-mode', ['-I/include', '--version'], "vcheck")
self.check_cc('dump-mode', ['-I/include', '-V'], "vcheck")
self.check_cc('dump-mode', ['-I/include', '-v'], "vcheck")
self.check_cc('dump-mode', ['-I/include', '-dumpversion'], "vcheck")
self.check_cc('dump-mode', ['-I/include', '--version', '-c'], "vcheck")
self.check_cc('dump-mode', ['-I/include', '-V', '-o', 'output'], "vcheck")
def test_cpp_mode(self):
self.check_cc('dump-mode', ['-E'], "cpp")
self.check_cpp('dump-mode', [], "cpp")
def test_ccld_mode(self):
self.check_cc('dump-mode', [], "ccld")
self.check_cc('dump-mode', ['foo.c', '-o', 'foo'], "ccld")
self.check_cc('dump-mode', ['foo.c', '-o', 'foo', '-Wl,-rpath=foo'], "ccld")
self.check_cc('dump-mode', ['foo.o', 'bar.o', 'baz.o', '-o', 'foo', '-Wl,-rpath=foo'], "ccld")
def test_ld_mode(self):
self.check_ld('dump-mode', [], "ld")
self.check_ld('dump-mode', ['foo.o', 'bar.o', 'baz.o', '-o', 'foo', '-Wl,-rpath=foo'], "ld")
def test_includes(self):
self.check_cc('dump-includes', test_command,
"\n".join(["/test/include", "/other/include"]))
def test_libraries(self):
self.check_cc('dump-libraries', test_command,
"\n".join(["/test/lib", "/other/lib"]))
def test_libs(self):
self.check_cc('dump-libs', test_command,
"\n".join(["lib1", "lib2", "lib3", "lib4"]))
def test_rpaths(self):
self.check_cc('dump-rpaths', test_command,
"\n".join(["/first/rpath", "/second/rpath", "/third/rpath", "/fourth/rpath"]))
def test_other_args(self):
self.check_cc('dump-other-args', test_command,
"\n".join(["arg1", "-Wl,--start-group", "arg2", "arg3", "arg4",
"-Wl,--end-group", "arg5", "arg6"]))

View file

@ -45,7 +45,6 @@ class PythonVersionTest(unittest.TestCase):
def spack_python_files(self):
# first file is the spack script.
yield spack.spack_file
yield os.path.join(spack.build_env_path, 'cc')
# Next files are all the source files and package files.
search_paths = [spack.lib_path, spack.var_path]

View file

@ -24,6 +24,15 @@
##############################################################################
import os
def get_path(name):
path = os.environ.get(name, "").strip()
if path:
return path.split(":")
else:
return []
def env_flag(name):
if name in os.environ:
return os.environ[name].lower() == "true"

View file

@ -0,0 +1,19 @@
from spack import *
class Bzip2(Package):
"""bzip2 is a freely available, patent free high-quality data
compressor. It typically compresses files to within 10% to 15%
of the best available techniques (the PPM family of statistical
compressors), whilst being around twice as fast at compression
and six times faster at decompression."""
homepage = "http://www.bzip.org"
url = "http://www.bzip.org/1.0.6/bzip2-1.0.6.tar.gz"
version('1.0.6', '00b516f4704d4a7cb50a1d97e6e8e15b')
def install(self, spec, prefix):
# No configure system -- have to filter the makefile for this package.
filter_file(r'CC=gcc', 'CC=cc', 'Makefile', string=True)
make()
make("install", "PREFIX=%s" % prefix)

View file

@ -0,0 +1,16 @@
from spack import *
class Libffi(Package):
"""The libffi library provides a portable, high level programming
interface to various calling conventions. This allows a programmer
to call any function specified by a call interface description at
run time."""
homepage = "https://sourceware.org/libffi/"
url = "ftp://sourceware.org/pub/libffi/libffi-3.1.tar.gz"
version('3.1', 'f5898b29bbfd70502831a212d9249d10')
def install(self, spec, prefix):
configure("--prefix=%s" % prefix)
make()
make("install")

View file

@ -10,10 +10,14 @@ class Ncurses(Package):
homepage = "http://invisible-island.net/ncurses/ncurses.html"
version('5.9', '8cb9c412e5f2d96bc6f459aa8c6282a1',
url='http://invisible-island.net/datafiles/release/ncurses.tar.gz')
url='http://ftp.gnu.org/pub/gnu/ncurses/ncurses-5.9.tar.gz')
def install(self, spec, prefix):
configure("--prefix=%s" % prefix)
configure("--prefix=%s" % prefix,
"--with-shared",
"--enable-widec",
"--enable-pc-files",
"--without-ada")
make()
make("install")

View file

@ -0,0 +1,25 @@
from spack import *
class Python(Package):
"""The Python programming language."""
homepage = "http://www.python.org"
url = "http://www.python.org/ftp/python/2.7.8/Python-2.7.8.tar.xz"
version('2.7.8', 'd235bdfa75b8396942e360a70487ee00')
depends_on("openssl")
depends_on("bzip2")
depends_on("readline")
depends_on("ncurses")
depends_on("sqlite")
def install(self, spec, prefix):
# Need this to allow python build to find the Python installation.
env['PYTHONHOME'] = prefix
# Rest of install is pretty standard.
configure("--prefix=%s" % prefix,
"--with-threads",
"--enable-shared")
make()
make("install")

View file

@ -0,0 +1,21 @@
from spack import *
class Readline(Package):
"""The GNU Readline library provides a set of functions for use by
applications that allow users to edit command li nes as they
are typed in. Both Emacs and vi editing modes are
available. The Readline library includes additional functions
to maintain a list of previously-entered command lines, to
recall and perhaps reedit those lines, and perform csh-like
history expansion on previous commands. """
homepage = "http://cnswww.cns.cwru.edu/php/chet/readline/rltop.html"
url = "ftp://ftp.cwru.edu/pub/bash/readline-6.3.tar.gz"
version('6.3', '33c8fb279e981274f485fd91da77e94a')
depends_on("ncurses")
def install(self, spec, prefix):
configure("--prefix=%s" % prefix)
make("SHLIB_LIBS=-lncurses")
make("install")