107 Commits

Author SHA1 Message Date
ba05c8aafc add __init__.py 2016-07-11 16:42:37 +02:00
9d1ab64720 do not repeat all that code 2016-07-11 16:32:00 +02:00
18349229ff trim 2016-07-11 16:29:14 +02:00
05f4ad9116 do not entangle tests 2016-07-11 16:20:44 +02:00
1aa7e1a4bd do not repeat tests 2016-07-11 16:18:25 +02:00
4d902ea85c add Miro's modifications for OpenBLAS detection 2016-07-11 16:14:44 +02:00
dfd6e41946 first print stdout, then stderr; fixes #174 2016-06-20 15:35:58 +02:00
7c5f82bc8a add GRASP 2016-06-15 22:16:21 +02:00
808d094420 update user faq 2016-05-28 18:08:56 +02:00
0f86f0bea9 update general doc 2016-05-28 18:06:50 +02:00
49d1652c98 update parts of doc 2016-05-28 18:03:22 +02:00
2dd36eb15d extend doc about testing 2016-05-28 17:46:18 +02:00
d08cd10e33 update documentation after change to yml 2016-05-28 17:46:03 +02:00
a9ceb81f39 update author info 2016-05-28 17:39:29 +02:00
9c9f001e57 s/yaml/master/ 2016-05-21 12:23:20 +02:00
be5d760555 add quotes 2016-05-21 01:41:02 +02:00
7a9af28fca fix BOOST_ARCHIVE_LOCATION 2016-05-21 01:32:22 +02:00
3200b0022d on linux try cmake 3.5.2 2016-05-20 23:05:46 +02:00
28547c43f7 more air 2016-05-20 22:39:40 +02:00
5a93ad7485 also fetch external/__init__.py 2016-05-20 22:15:38 +02:00
0a62067a6b Merge branch 'master' into yaml 2016-05-20 22:13:54 +02:00
f4889cf134 typo 2016-05-20 22:03:19 +02:00
8b055107ca fix boost test autocmake.yml files 2016-05-20 21:50:56 +02:00
0c42f1a9af another attempt to include python 2.7 and 3.5 2016-05-20 21:44:45 +02:00
5b04d7a8a4 if pyaml is not available, print a nice error message 2016-05-20 21:42:07 +02:00
6cf25bbd2b extend tests 2016-05-20 21:32:22 +02:00
24d235ac1a try to test python 2.7 and 3.5 2016-05-20 21:20:16 +02:00
ca8a86aa61 indicate that doc is outdated 2016-05-20 21:20:01 +02:00
42e5192dc9 fixes in boost.cmake 2016-05-20 21:16:01 +02:00
931ab9b444 allow flat_add to operate also on ints 2016-05-20 21:05:53 +02:00
8af4e033d9 convert boost tests to new form 2016-05-20 21:02:16 +02:00
bfeef557e7 convert python tests to new form 2016-05-20 20:58:43 +02:00
6896da511c restore a couple of tests 2016-05-20 20:55:10 +02:00
30ced00c4f restore tests on Python 2 2016-05-20 20:45:13 +02:00
37d430c0fd workaround for problem with trying to copy to existing dir 2016-05-20 20:43:08 +02:00
ee07ecb83e rm title 2016-05-20 17:41:24 +02:00
4d005acaa0 add logo 2016-05-20 17:40:45 +02:00
28582ceba7 reactivate test_cxx 2016-05-20 15:37:22 +02:00
939de1edb0 reactivate one real test 2016-05-20 15:35:13 +02:00
ed4dcbb138 s/cfg/yml/ 2016-05-20 15:02:49 +02:00
5d70c2f2cc more doc about stable/latest 2016-05-20 11:46:48 +02:00
23de8f4703 pep8 fix 2016-05-20 11:32:46 +02:00
d1545b9379 set version to 1.0.0-alpha-x 2016-05-20 11:30:54 +02:00
84b0e7c93c Merge branch 'master' into yaml 2016-05-20 11:29:18 +02:00
369e0a4937 s/org/io/ 2016-05-20 11:28:08 +02:00
648bc2c20d links to documentation 2016-05-20 11:27:56 +02:00
61ad3d7359 Merge branch 'stable-0.x'
Empty merge done with "-s ours". To avoid
branch renames to propagate to master source code.
2016-05-20 11:22:59 +02:00
a32c9d6f46 more descriptive warning 2016-05-20 00:45:35 +02:00
9531ac499e not every module has 'source:' 2016-05-20 00:44:48 +02:00
e2ae1fac50 Merge branch 'master' into yaml 2016-05-20 00:12:31 +02:00
5dc2bb2880 adapt url_root for fetch directives 2016-05-20 00:08:53 +02:00
d0dc52c7a9 convert boost module to yaml 2016-05-20 00:02:32 +02:00
51cdb55c53 convert more modules to yaml 2016-05-19 23:57:24 +02:00
ac03dc7998 convert math lib code to yaml 2016-05-19 23:52:48 +02:00
5b7ad87479 switch to .format() 2016-05-19 23:46:32 +02:00
0c6976a70d simplify 2016-05-19 23:39:13 +02:00
4eb5dee936 update googletest.cmake to yaml 2016-05-19 23:24:49 +02:00
d09aa22623 covert two modules to yaml 2016-05-19 23:22:28 +02:00
104f64cb1c convert ccache module to yml 2016-05-19 23:17:23 +02:00
83c0c3fabd fix progress bar 2016-05-19 23:14:17 +02:00
45fc08f37b Revert "testing interpolation"
This reverts commit 91c79f9d3c.
2016-05-19 23:10:37 +02:00
91c79f9d3c testing interpolation 2016-05-19 23:07:31 +02:00
ebc1ecc127 convert few modules to yaml 2016-05-19 23:03:00 +02:00
f447153eeb save work 2016-05-19 22:43:39 +02:00
90b89354db more work on parsing 2016-05-19 18:46:12 +02:00
24ff4c430e change to yaml format 2016-05-18 23:38:06 +02:00
bcafc815fc update authors list 2016-05-18 23:05:54 +02:00
d5e44a5bce rm redundant imports 2016-05-18 22:45:11 +02:00
e0b81c5516 reorg 2016-05-18 22:43:32 +02:00
0d500bc838 import datetime 2016-05-18 22:34:06 +02:00
88ddf9a1d1 oursource more functions 2016-05-18 22:30:47 +02:00
1b0f664735 trim text 2016-05-18 22:24:39 +02:00
8d7a0dc79c rm print 2016-05-18 22:24:32 +02:00
07d431607f improve test 2016-05-18 22:20:42 +02:00
f4112a758a simplify test 2016-05-18 22:18:10 +02:00
923116a113 more air 2016-05-18 22:15:49 +02:00
d7df341793 add test for parse_yaml 2016-05-18 22:12:37 +02:00
3565e2d885 pass argv 2016-05-18 22:12:22 +02:00
7def4fa318 helptext 2016-05-18 21:54:05 +02:00
c2fb14b22e restore --self 2016-05-18 21:48:08 +02:00
e36af9059b do not test update.py 2016-04-19 23:00:10 +02:00
2dff967497 fetch more files 2016-04-19 22:53:50 +02:00
f2ef8bf393 more structure 2016-04-19 22:52:39 +02:00
1a2bd4507b use copy.copy(l) instead of l.copy() 2016-04-19 22:27:27 +02:00
9e63f3e042 reactivate some tests 2016-04-19 22:23:27 +02:00
e2fee84581 pyaml is required 2016-04-19 22:20:16 +02:00
3a5192eed8 simplify pep8 testing 2016-04-19 22:19:18 +02:00
ffacd0378b rename 2016-04-19 22:10:14 +02:00
1543af1a3e reorg 2016-04-19 22:04:53 +02:00
653a4fafcb deactivate tests 2016-04-19 21:58:53 +02:00
cfb842e7bb point AUTOCMAKE_GITHUB_URL to yaml 2016-04-19 21:57:57 +02:00
cc6b374b93 less code repetition 2016-04-19 21:57:41 +02:00
2d858a2a5a absorb branch name in AUTOCMAKE_GITHUB_URL 2016-04-19 21:38:41 +02:00
4e0d0730d8 Merge branch 'master' into yaml 2016-04-19 12:30:51 +02:00
4e8a1dbac6 implement override 2016-04-18 17:31:50 +02:00
950ff76bd5 Merge branch 'master' into yaml 2016-04-18 17:00:50 +02:00
4a20af4af9 save work on migration to yaml 2016-04-18 17:00:18 +02:00
edf1245760 adapt example configuration file 2016-04-18 16:58:53 +02:00
e784ff88e0 go back to unordered dict parsing for simplicity
ordering is guaranteed by lists
2016-04-18 11:57:13 +02:00
806564e2e8 Merge branch 'master' into yaml 2016-04-18 11:53:44 +02:00
6926c30b3c extend interpolation to lists 2016-04-18 11:52:39 +02:00
69478cb27e Merge branch 'master' into yaml 2016-04-10 17:26:02 +02:00
4ef972dbd2 Merge branch 'master' into yaml 2016-03-29 07:03:27 +02:00
777a57908c add pyyaml 2016-03-19 17:51:39 +01:00
ae2863cf1b Merge branch 'master' into yaml 2016-03-19 17:50:55 +01:00
5615da7c78 do not hardcode file name 2016-03-19 17:46:50 +01:00
5be6e66038 preparing for yaml 2016-03-19 17:43:42 +01:00
96 changed files with 1423 additions and 936 deletions

2
.gitignore vendored
View File

@ -7,7 +7,7 @@ __pycache__/
test/*/CMakeLists.txt
test/*/build*/
test/*/cmake/update.py
test/*/cmake/lib/
test/*/cmake/autocmake/
test/*/cmake/downloaded/
test/*/setup

View File

@ -5,8 +5,9 @@ matrix:
include:
- os: linux
python: 2.7
compiler: gcc
env: SOURCES=ubuntu-toolchain-r-test
env: SOURCES=ubuntu-toolchain-r-test TEST_SCRIPT=test.py
addons:
apt:
sources:
@ -28,6 +29,46 @@ matrix:
# boost
- libboost-all-dev
- os: linux
python: 3.5
compiler: gcc
env: SOURCES=ubuntu-toolchain-r-test TEST_SCRIPT=test.py
addons:
apt:
sources:
- ubuntu-toolchain-r-test
packages:
# compilers
- g++
- gfortran
# math libraries
- libblas-dev
- liblapack-dev
- libatlas-base-dev
# mpi
- openmpi-bin
- libopenmpi-dev
# python library, development version
- libpython2.7
# boost
- libboost-all-dev
- os: linux
python: 3.5
compiler: gcc
env: SOURCES=ubuntu-toolchain-r-test TEST_SCRIPT=test_openblas.py
addons:
apt:
sources:
- ubuntu-toolchain-r-test
packages:
# compilers
- g++
- gfortran
- cmake
- libblas-dev
- libopenblas-dev
- os: osx
osx_image: xcode6.4
compiler: gcc
@ -40,20 +81,21 @@ install:
pip install virtualenv
elif [[ "${TRAVIS_OS_NAME}" == "linux" ]]; then
pip install --user virtualenv
curl https://cmake.org/files/v3.5/cmake-3.5.2-Linux-x86_64.tar.gz | tar xvz
export PATH=~/cmake-3.5.2-Linux-x86_64/bin:$PATH
export LD_LIBARY_PATH=~/cmake-3.5.2-Linux-x86_64/lib:$LD_LIBRARY_PATH
fi
- virtualenv venv
- source venv/bin/activate
- pip install pep8 pytest
- pip install -r requirements.txt
script:
# pep8 tests
- pep8 --ignore=E501 update.py
- pep8 --ignore=E501 test/test.py
- pep8 --ignore=E501 lib/config.py
- pep8 --ignore E501 update.py
- pep8 --ignore E501,E265 autocmake
# unit tests
- py.test -vv update.py
- py.test -vv test/test.py
- py.test -vv lib/config.py
- py.test -vv autocmake/*
- py.test -vv test/$TEST_SCRIPT
notifications:
email: false

View File

@ -7,7 +7,8 @@
- Miroslav Ilias (Windows, portability, earliest adopter testing and feedback, math library testing)
- Ivan Hrasko (Windows, Appveyor testing)
- Dan Jonsson (idea for configuration file approach)
- Dan Jonsson (idea for configuration file approach which preceded YAML solution)
- Roberto Di Remigio (design ideas and testing, OS X testing, Boost)
For a list of all the contributions see https://github.com/coderefinery/autocmake/contributors.
For a list of all the contributions,
see https://github.com/coderefinery/autocmake/contributors.

View File

@ -1,16 +1,21 @@
[![Build Status](https://travis-ci.org/coderefinery/autocmake.svg?branch=stable-0.x)](https://travis-ci.org/coderefinery/autocmake/builds)
[![Documentation Status](https://readthedocs.org/projects/autocmake/badge/?version=stable-0.x)](http://autocmake.readthedocs.org)
[![License](https://img.shields.io/badge/license-%20BSD--3-blue.svg)](../stable-0.x/LICENSE)
[![Build Status](https://travis-ci.org/coderefinery/autocmake.svg?branch=master)](https://travis-ci.org/coderefinery/autocmake/builds)
[![Documentation Status](https://readthedocs.org/projects/autocmake/badge/?version=latest)](http://autocmake.readthedocs.org)
[![License](https://img.shields.io/badge/license-%20BSD--3-blue.svg)](../master/LICENSE)
# Autocmake
![alt text](https://github.com/coderefinery/autocmake/raw/master/img/autocmake.png "Autocmake")
A CMake plugin composer.
Licensed under [BSD-3](../stable-0.x/LICENSE).
Licensed under [BSD-3](../master/LICENSE).
See http://autocmake.org.
### Projects using Autocmake
## Documentation
- [Latest stable code](http://autocmake.readthedocs.io/en/stable-0.x/) (stable-0.x branch)
- [Bleeding edge code](http://autocmake.readthedocs.io/en/latest/) (master branch)
## Projects using Autocmake
- [Numgrid](https://github.com/dftlibs/numgrid/)
- [XCint](https://github.com/dftlibs/xcint/)
@ -18,5 +23,6 @@ See http://autocmake.org.
- [mathlib-tester](https://github.com/miroi/mathlibs-tester)
- [Fortran Input Reader](https://github.com/miroi/fortran_input_reader)
- [PCMSolver](https://github.com/PCMSolver/pcmsolver)
- GRASP: General-purpose Relativistic Atomic Structure Program
If you use Autocmake, please link to your project via a pull request.

1
autocmake/__init__.py Normal file
View File

@ -0,0 +1 @@
__version__ = '1.0.0-alpha-x'

View File

@ -93,16 +93,21 @@ def run_cmake(command, build_path, default_build_path):
stdout_coded, stderr_coded = p.communicate()
stdout = stdout_coded.decode('UTF-8')
stderr = stderr_coded.decode('UTF-8')
# print cmake output to screen
print(stdout)
if stderr:
sys.stderr.write(stderr)
sys.exit(1)
# print cmake output to screen
print(stdout)
# write cmake output to file
with open('cmake_output', 'w') as f:
f.write(stdout)
# change directory and return
os.chdir(topdir)
if 'Configuring incomplete' in stdout:
# configuration was not successful
if (build_path == default_build_path):

0
autocmake/external/__init__.py vendored Normal file
View File

46
autocmake/extract.py Normal file
View File

@ -0,0 +1,46 @@
def extract_list(config, section):
from collections import Iterable
l = []
if 'modules' in config:
for module in config['modules']:
for k, v in module.items():
for x in v:
if section in x:
if isinstance(x[section], Iterable) and not isinstance(x[section], str):
for y in x[section]:
l.append(y)
else:
l.append(x[section])
return l
def to_d(l):
"""
Converts list of dicts to dict.
"""
_d = {}
for x in l:
for k, v in x.items():
_d[k] = v
return _d
def test_to_d():
l = [{'a': 'b'}, {'c': 'd'}]
d = {'a': 'b', 'c': 'd'}
assert to_d(l) == d
def to_l(x):
"""
Converts list of dicts to dict.
"""
if isinstance(x, str):
return [x]
else:
return x
def test_to_l():
assert to_l('foo') == ['foo']
assert to_l(['foo', 'bar']) == ['foo', 'bar']

176
autocmake/generate.py Normal file
View File

@ -0,0 +1,176 @@
def gen_cmake_command(config):
"""
Generate CMake command.
"""
from autocmake.extract import extract_list
s = []
s.append("\n\ndef gen_cmake_command(options, arguments):")
s.append(' """')
s.append(" Generate CMake command based on options and arguments.")
s.append(' """')
s.append(" command = []")
for env in config['export']:
s.append(' command.append({0})'.format(env))
s.append(" command.append(arguments['--cmake-executable'])")
for definition in config['define']:
s.append(' command.append({0})'.format(definition))
s.append(" command.append('-DCMAKE_BUILD_TYPE={0}'.format(arguments['--type']))")
s.append(" command.append('-G \"{0}\"'.format(arguments['--generator']))")
s.append(" if arguments['--cmake-options'] != \"''\":")
s.append(" command.append(arguments['--cmake-options'])")
s.append(" if arguments['--prefix']:")
s.append(" command.append('-DCMAKE_INSTALL_PREFIX=\"{0}\"'.format(arguments['--prefix']))")
s.append("\n return ' '.join(command)")
return '\n'.join(s)
def autogenerated_notice():
from datetime import date
from . import __version__
current_year = date.today().year
year_range = '2015-{0}'.format(current_year)
s = []
s.append('# This file is autogenerated by Autocmake v{0} http://autocmake.org'.format(__version__))
s.append('# Copyright (c) {0} by Radovan Bast, Jonas Juselius, and contributors.'.format(year_range))
return '\n'.join(s)
def gen_setup(config, relative_path, setup_script_name):
"""
Generate setup script.
"""
from autocmake.extract import extract_list
s = []
s.append('#!/usr/bin/env python')
s.append('\n{0}'.format(autogenerated_notice()))
s.append('\nimport os')
s.append('import sys')
s.append("\nsys.path.insert(0, '{0}')".format(relative_path))
s.append('from autocmake import configure')
s.append('from autocmake.external import docopt')
s.append('\n\noptions = """')
s.append('Usage:')
s.append(' ./{0} [options] [<builddir>]'.format(setup_script_name))
s.append(' ./{0} (-h | --help)'.format(setup_script_name))
s.append('\nOptions:')
options = []
for opt in config['docopt']:
first = opt.split()[0].strip()
rest = ' '.join(opt.split()[1:]).strip()
options.append([first, rest])
options.append(['--type=<TYPE>', 'Set the CMake build type (debug, release, or relwithdeb) [default: release].'])
options.append(['--generator=<STRING>', 'Set the CMake build system generator [default: Unix Makefiles].'])
options.append(['--show', 'Show CMake command and exit.'])
options.append(['--cmake-executable=<CMAKE_EXECUTABLE>', 'Set the CMake executable [default: cmake].'])
options.append(['--cmake-options=<STRING>', "Define options to CMake [default: '']."])
options.append(['--prefix=<PATH>', 'Set the install path for make install.'])
options.append(['<builddir>', 'Build directory.'])
options.append(['-h --help', 'Show this screen.'])
s.append(align_options(options))
s.append('"""')
s.append(gen_cmake_command(config))
s.append("\n")
s.append("# parse command line args")
s.append("try:")
s.append(" arguments = docopt.docopt(options, argv=None)")
s.append("except docopt.DocoptExit:")
s.append(r" sys.stderr.write('ERROR: bad input to {0}\n'.format(sys.argv[0]))")
s.append(" sys.stderr.write(options)")
s.append(" sys.exit(-1)")
s.append("\n")
s.append("# use extensions to validate/post-process args")
s.append("if configure.module_exists('extensions'):")
s.append(" import extensions")
s.append(" arguments = extensions.postprocess_args(sys.argv, arguments)")
s.append("\n")
s.append("root_directory = os.path.dirname(os.path.realpath(__file__))")
s.append("\n")
s.append("build_path = arguments['<builddir>']")
s.append("\n")
s.append("# create cmake command")
s.append("cmake_command = '{0} {1}'.format(gen_cmake_command(options, arguments), root_directory)")
s.append("\n")
s.append("# run cmake")
s.append("configure.configure(root_directory, build_path, cmake_command, arguments['--show'])")
return s
def gen_cmakelists(project_name, min_cmake_version, relative_path, modules):
"""
Generate CMakeLists.txt.
"""
import os
s = []
s.append(autogenerated_notice())
s.append('\n# set minimum cmake version')
s.append('cmake_minimum_required(VERSION {0} FATAL_ERROR)'.format(min_cmake_version))
s.append('\n# project name')
s.append('project({0})'.format(project_name))
s.append('\n# do not rebuild if rules (compiler flags) change')
s.append('set(CMAKE_SKIP_RULE_DEPENDENCY TRUE)')
s.append('\n# if CMAKE_BUILD_TYPE undefined, we set it to Debug')
s.append('if(NOT CMAKE_BUILD_TYPE)')
s.append(' set(CMAKE_BUILD_TYPE "Debug")')
s.append('endif()')
if len(modules) > 0:
s.append('\n# directories which hold included cmake modules')
module_paths = [module.path for module in modules]
module_paths.append('downloaded') # this is done to be able to find fetched modules when testing
module_paths = list(set(module_paths))
module_paths.sort() # we do this to always get the same order and to minimize diffs
for directory in module_paths:
rel_cmake_module_path = os.path.join(relative_path, directory)
# on windows cmake corrects this so we have to make it wrong again
rel_cmake_module_path = rel_cmake_module_path.replace('\\', '/')
s.append('set(CMAKE_MODULE_PATH ${{CMAKE_MODULE_PATH}} ${{PROJECT_SOURCE_DIR}}/{0})'.format(rel_cmake_module_path))
if len(modules) > 0:
s.append('\n# included cmake modules')
for module in modules:
s.append('include({0})'.format(os.path.splitext(module.name)[0]))
return s
def align_options(options):
"""
Indents flags and aligns help texts.
"""
l = 0
for opt in options:
if len(opt[0]) > l:
l = len(opt[0])
s = []
for opt in options:
s.append(' {0}{1} {2}'.format(opt[0], ' ' * (l - len(opt[0])), opt[1]))
return '\n'.join(s)

66
autocmake/interpolate.py Normal file
View File

@ -0,0 +1,66 @@
def replace(s, d):
from re import findall
if isinstance(s, str):
for var in findall(r"%\(([A-Za-z0-9_]*)\)", s):
s = s.replace("%({})".format(var), str(d[var]))
return s
def test_replace():
assert replace('hey %(foo) ho %(bar)',
{'foo': 'hey', 'bar': 'ho'}) == 'hey hey ho ho'
def interpolate(d, d_map):
from collections import Mapping, Iterable
from copy import copy
for k, v in d.items():
if isinstance(v, Mapping):
d[k] = interpolate(d[k], d_map)
elif isinstance(v, Iterable) and not isinstance(v, str):
l = []
for x in v:
if isinstance(x, Mapping):
l.append(interpolate(x, d_map))
else:
l.append(replace(x, d_map))
d[k] = copy(l)
else:
d[k] = replace(d[k], d_map)
return d
def test_interpolate():
d = {'foo': 'hey',
'bar': 'ho',
'one': 'hey %(foo) ho %(bar)',
'two': {'one': 'hey %(foo) ho %(bar)',
'two': 'raboof'}}
d_interpolated = {'foo': 'hey',
'bar': 'ho',
'one': 'hey hey ho ho',
'two': {'one': 'hey hey ho ho',
'two': 'raboof'}}
assert interpolate(d, d) == d_interpolated
def test_interpolate_int():
d = {'foo': 1,
'bar': 2,
'one': 'hey %(foo) ho %(bar)',
'two': {'one': 'hey %(foo) ho %(bar)',
'two': 'raboof'}}
d_interpolated = {'foo': 1,
'bar': 2,
'one': 'hey 1 ho 2',
'two': {'one': 'hey 1 ho 2',
'two': 'raboof'}}
assert interpolate(d, d) == d_interpolated
def test_interpolate_nested():
d2 = {'modules': [{'fc': [{'source': '%(url_root)fc_optional.cmake'}]}], 'url_root': 'downloaded/downloaded_'}
d2_interpolated = {'modules': [{'fc': [{'source': 'downloaded/downloaded_fc_optional.cmake'}]}], 'url_root': 'downloaded/downloaded_'}
assert interpolate(d2, d2) == d2_interpolated

132
autocmake/parse_rst.py Normal file
View File

@ -0,0 +1,132 @@
def parse_cmake_module(s_in, overrides={}):
import sys
from collections import Mapping, Iterable, defaultdict
from autocmake.parse_yaml import parse_yaml
# we do not use the nicer sys.version_info.major
# for compatibility with Python < 2.7
if sys.version_info[0] > 2:
from io import StringIO
else:
from StringIO import StringIO
parsed_config = defaultdict(lambda: None)
if 'autocmake.yml configuration::' not in s_in:
return parsed_config
s_out = []
is_rst_line = False
for line in s_in.split('\n'):
if is_rst_line:
if len(line) > 0:
if line[0] != '#':
is_rst_line = False
else:
is_rst_line = False
if is_rst_line:
s_out.append(line[2:])
if '#.rst:' in line:
is_rst_line = True
autocmake_entry = '\n'.join(s_out).split('autocmake.yml configuration::')[1]
autocmake_entry = autocmake_entry.replace('\n ', '\n')
buf = StringIO(autocmake_entry)
config = parse_yaml(buf, overrides)
for k, v in config.items():
if isinstance(v, Iterable) and not isinstance(v, str):
parsed_config[k] = [x for x in config[k]]
else:
parsed_config[k] = [config[k]]
return parsed_config
def test_parse_cmake_module():
s = r'''#.rst:
#
# Foo ...
#
# autocmake.yml configuration::
#
# docopt:
# - "--cxx=<CXX> C++ compiler [default: g++]."
# - "--extra-cxx-flags=<EXTRA_CXXFLAGS> Extra C++ compiler flags [default: '']."
# export: "'CXX={0}'.format(arguments['--cxx'])"
# define: "'-DEXTRA_CXXFLAGS=\"{0}\"'.format(arguments['--extra-cxx-flags'])"
enable_language(CXX)
if(NOT DEFINED CMAKE_C_COMPILER_ID)
message(FATAL_ERROR "CMAKE_C_COMPILER_ID variable is not defined!")
endif()'''
parsed_config = parse_cmake_module(s)
assert parsed_config['docopt'] == ["--cxx=<CXX> C++ compiler [default: g++].", "--extra-cxx-flags=<EXTRA_CXXFLAGS> Extra C++ compiler flags [default: '']."]
def test_parse_cmake_module_no_key():
s = '''#.rst:
#
# Foo ...
#
# Bar ...
enable_language(CXX)
if(NOT DEFINED CMAKE_C_COMPILER_ID)
message(FATAL_ERROR "CMAKE_C_COMPILER_ID variable is not defined!")
endif()'''
parsed_config = parse_cmake_module(s)
assert parsed_config['docopt'] is None
def test_parse_cmake_module_interpolate():
s = r'''#.rst:
#
# Foo ...
#
# autocmake.yml configuration::
#
# major: 1
# minor: 2
# patch: 3
# a: v%(major)
# b: v%(minor)
# c: v%(patch)
enable_language(CXX)'''
parsed_config = parse_cmake_module(s)
assert parsed_config['a'] == ['v1']
assert parsed_config['b'] == ['v2']
assert parsed_config['c'] == ['v3']
def test_parse_cmake_module_overrides():
s = r'''#.rst:
#
# Foo ...
#
# autocmake.yml configuration::
#
# major: 1
# minor: 2
# patch: 3
# a: v%(major)
# b: v%(minor)
# c: v%(patch)
enable_language(CXX)'''
parsed_config = parse_cmake_module(s, {'minor': 4})
assert parsed_config['a'] == ['v1']
assert parsed_config['b'] == ['v4']
assert parsed_config['c'] == ['v3']

30
autocmake/parse_yaml.py Normal file
View File

@ -0,0 +1,30 @@
def parse_yaml(stream, overrides={}):
import yaml
import sys
from autocmake.interpolate import interpolate
try:
config = yaml.load(stream, yaml.SafeLoader)
except yaml.YAMLError as exc:
print(exc)
sys.exit(-1)
for k in config:
if k in overrides:
config[k] = overrides[k]
config = interpolate(config, config)
return config
def test_parse_yaml():
text = """foo: bar
this: that
var: '%(foo)'
list:
- a: '%(foo)'
- b: '%(foo)'
- c: '%(foo)'"""
assert parse_yaml(text) == {'foo': 'bar', 'this': 'that', 'var': 'bar',
'list': [{'a': 'bar'}, {'b': 'bar'}, {'c': 'bar'}]}

View File

@ -60,9 +60,9 @@ author = u'Radovan Bast, Jonas Juselius, and contributors'
# built documents.
#
# The short X.Y version.
version = '0.5'
version = '1.0'
# The full version, including alpha/beta/rc tags.
release = '0.5.0'
release = '1.0.0-alpha-x'
# The language for content autogenerated by Sphinx. Refer to documentation
# for a list of supported languages.

View File

@ -9,12 +9,12 @@ This documentation is refreshed upon each push to the central repository.
The module reference documentation is generated from the module sources using
``#.rst:`` tags (compare for instance
http://autocmake.readthedocs.org/en/latest/module-reference.html#cc-cmake with
https://github.com/coderefinery/autocmake/blob/stable-0.x/modules/cc.cmake).
http://autocmake.readthedocs.io/en/latest/module-reference.html#cc-cmake with
https://github.com/coderefinery/autocmake/blob/master/modules/cc.cmake).
Please note that the lines following ``# autocmake.cfg configuration::`` are
understood by the ``update.py`` script to infer autocmake.cfg code from the
Please note that the lines following ``# autocmake.yml configuration::`` are
understood by the ``update.py`` script to infer autocmake.yml code from the
documentation. As an example consider
https://github.com/coderefinery/autocmake/blob/stable-0.x/modules/cc.cmake#L20-L25.
https://github.com/coderefinery/autocmake/blob/master/modules/cc.cmake#L20-L26.
Here, ``update.py`` will infer the configurations for ``docopt``, ``export``,
and ``define``.

View File

@ -5,12 +5,16 @@ Testing Autocmake
You will need to install `pytest <http://pytest.org/>`__.
Check also the `Travis <https://github.com/coderefinery/autocmake/blob/stable-0.x/.travis.yml>`__
Check also the `Travis <https://github.com/coderefinery/autocmake/blob/master/.travis.yml>`__
build and test recipe for other requirements.
Your contributions and changes should preserve the test set. You can run locally all tests with::
Your contributions and changes should preserve the test set and be PEP8 conform.
You can run locally all tests with::
$ py.test test/test.py
$ pep8 --ignore E501 update.py
$ pep8 --ignore E501,E265 autocmake
$ py.test -vv autocmake/*
$ py.test -vv test/test.py
You can also select individual tests, for example those with ``fc_blas`` string in the name::

View File

@ -12,48 +12,45 @@ infrastructure files which will be needed to build the project::
$ mkdir cmake # does not have to be called "cmake" - take the name you prefer
$ cd cmake
$ wget https://github.com/coderefinery/autocmake/raw/stable-0.x/update.py
$ wget https://github.com/coderefinery/autocmake/raw/master/update.py
$ python update.py --self
On the MS Windows system, you can use the PowerShell wget-replacement::
$ Invoke-WebRequest https://github.com/coderefinery/autocmake/raw/stable-0.x/update.py -OutFile update.py
$ Invoke-WebRequest https://github.com/coderefinery/autocmake/raw/master/update.py -OutFile update.py
This creates (or updates) the following files (an existing ``autocmake.cfg`` is
This creates (or updates) the following files (an existing ``autocmake.yml`` is
not overwritten by the script)::
cmake/
autocmake.cfg # edit this file
autocmake.yml # edit this file
update.py # no need to edit
lib/
config.py # no need to edit
docopt/
docopt.py # no need to edit
autocmake/ # no need to edit
... # no need to edit
Note that all other listed files are overwritten (use version control).
Note that ``update.py`` and files under ``autocmake/``
are overwritten (use version control).
Generating the CMake infrastructure
-----------------------------------
Now customize ``autocmake.cfg`` to your needs
(see :ref:`autocmake_cfg`)
Now customize ``autocmake.yml`` to your needs
(see :ref:`autocmake_yml`)
and then run the ``update.py`` script which
creates ``CMakeLists.txt`` and a setup script in the target path::
$ python update.py ..
The script also downloads external CMake modules specified in ``autocmake.cfg`` to a directory
The script also downloads external CMake modules specified in ``autocmake.yml`` to a directory
called ``downloaded/``::
cmake/
autocmake.cfg # edit this file
autocmake.yml # edit this file
update.py # no need to edit
lib/
config.py # no need to edit
docopt/
docopt.py # no need to edit
downloaded/ # contains CMake modules fetched from the web
autocmake/ # no need to edit
... # no need to edit
downloaded/ # contains CMake modules fetched from the web
Building the project

View File

@ -1,5 +1,5 @@
.. _autocmake_cfg:
.. _autocmake_yml:
Configuring autocmake.cfg
=========================
@ -13,38 +13,38 @@ below::
min_cmake_version: 2.8
[fc]
source: https://github.com/coderefinery/autocmake/raw/stable-0.x/modules/fc.cmake
source: https://github.com/coderefinery/autocmake/raw/master/modules/fc.cmake
[cc]
source: https://github.com/coderefinery/autocmake/raw/stable-0.x/modules/cc.cmake
source: https://github.com/coderefinery/autocmake/raw/master/modules/cc.cmake
[cxx]
source: https://github.com/coderefinery/autocmake/raw/stable-0.x/modules/cxx.cmake
source: https://github.com/coderefinery/autocmake/raw/master/modules/cxx.cmake
[flags]
source: https://github.com/coderefinery/autocmake/raw/stable-0.x/compilers/GNU.CXX.cmake
https://github.com/coderefinery/autocmake/raw/stable-0.x/compilers/Intel.CXX.cmake
source: https://github.com/coderefinery/autocmake/raw/master/compilers/GNU.CXX.cmake
https://github.com/coderefinery/autocmake/raw/master/compilers/Intel.CXX.cmake
[rpath]
source: custom/rpath.cmake
[definitions]
source: https://github.com/coderefinery/autocmake/raw/stable-0.x/modules/definitions.cmake
source: https://github.com/coderefinery/autocmake/raw/master/modules/definitions.cmake
[coverage]
source: https://github.com/coderefinery/autocmake/raw/stable-0.x/modules/code_coverage.cmake
source: https://github.com/coderefinery/autocmake/raw/master/modules/code_coverage.cmake
[safeguards]
source: https://github.com/coderefinery/autocmake/raw/stable-0.x/modules/safeguards.cmake
source: https://github.com/coderefinery/autocmake/raw/master/modules/safeguards.cmake
[default_build_paths]
source: https://github.com/coderefinery/autocmake/raw/stable-0.x/modules/default_build_paths.cmake
source: https://github.com/coderefinery/autocmake/raw/master/modules/default_build_paths.cmake
[src]
source: https://github.com/coderefinery/autocmake/raw/stable-0.x/modules/src.cmake
source: https://github.com/coderefinery/autocmake/raw/master/modules/src.cmake
[googletest]
source: https://github.com/coderefinery/autocmake/raw/stable-0.x/modules/googletest.cmake
source: https://github.com/coderefinery/autocmake/raw/master/modules/googletest.cmake
[custom]
source: custom/api.cmake
@ -71,13 +71,13 @@ The names of the other sections do not matter to Autocmake. You could name them
min_cmake_version: 2.8
[one]
source: https://github.com/coderefinery/autocmake/raw/stable-0.x/modules/fc.cmake
source: https://github.com/coderefinery/autocmake/raw/master/modules/fc.cmake
[two]
source: https://github.com/coderefinery/autocmake/raw/stable-0.x/modules/cc.cmake
source: https://github.com/coderefinery/autocmake/raw/master/modules/cc.cmake
[whatever]
source: https://github.com/coderefinery/autocmake/raw/stable-0.x/modules/cxx.cmake
source: https://github.com/coderefinery/autocmake/raw/master/modules/cxx.cmake
But it would not make much sense. It is better to choose names that are
meaningful to you.
@ -163,7 +163,7 @@ The preferred way to extend ``CMakeLists.txt`` is by editing ``autocmake.cfg``
and using the ``source`` option::
[fc]
source: https://github.com/coderefinery/autocmake/raw/stable-0.x/modules/fc.cmake
source: https://github.com/coderefinery/autocmake/raw/master/modules/fc.cmake
This will download ``fc.cmake`` and include it in ``CMakeLists.txt``.
@ -175,8 +175,8 @@ You can also include local CMake modules, e.g.::
It is also OK to include several modules at once::
[flags]
source: https://github.com/coderefinery/autocmake/raw/stable-0.x/compilers/GNU.CXX.cmake
https://github.com/coderefinery/autocmake/raw/stable-0.x/compilers/Intel.CXX.cmake
source: https://github.com/coderefinery/autocmake/raw/master/compilers/GNU.CXX.cmake
https://github.com/coderefinery/autocmake/raw/master/compilers/Intel.CXX.cmake
The modules will be included in the same order as they appear in ``autocmake.cfg``.
@ -187,7 +187,7 @@ Fetching files without including them in CMakeLists.txt
Sometimes you want to fetch a file without including it in ``CMakeLists.txt``.
This can be done with the ``fetch`` option. This is for instance done by the
``git_info.cmake`` module (see
https://github.com/coderefinery/autocmake/blob/stable-0.x/modules/git_info/git_info.cmake#L10-L11).
https://github.com/coderefinery/autocmake/blob/master/modules/git_info/git_info.cmake#L10-L11).
If ``fetch`` is invoked in ``autocmake.cfg``, then the fetched file is placed
under ``downloaded/``. If ``fetch`` is invoked from within a CMake module
@ -241,7 +241,7 @@ for many core modules which come with own options once you have sourced them.
The lines following ``# autocmake.cfg configuration::`` are
understood by the ``update.py`` script to infer ``autocmake.cfg`` code from the
documentation. As an example consider
https://github.com/coderefinery/autocmake/blob/stable-0.x/modules/cc.cmake#L20-L25.
https://github.com/coderefinery/autocmake/blob/master/modules/cc.cmake#L20-L25.
Here, ``update.py`` will infer the configurations for ``docopt``, ``export``,
and ``define``.
@ -251,6 +251,6 @@ Overriding documented configurations
Configurable documented defaults can be achieved using interpolations. See for
instance
https://github.com/coderefinery/autocmake/blob/stable-0.x/modules/boost/boost.cmake#L33-L36.
https://github.com/coderefinery/autocmake/blob/master/modules/boost/boost.cmake#L33-L36.
These can be modified within ``autocmake.cfg`` with a dictionary, e.g.:
https://github.com/coderefinery/autocmake/blob/stable-0.x/test/boost_libs/cmake/autocmake.cfg#L9
https://github.com/coderefinery/autocmake/blob/master/test/boost_libs/cmake/autocmake.cfg#L9

View File

@ -3,7 +3,7 @@
Customizing CMake modules
=========================
The ``update.py`` script assembles modules listed in ``autocmake.cfg`` into
The ``update.py`` script assembles modules listed in ``autocmake.yml`` into
``CMakeLists.txt``. Those that are fetched from the web are placed inside
``downloaded/``. You have several options to customize downloaded CMake
modules:
@ -22,7 +22,7 @@ Adapt local copies of CMake modules
A slightly better solution is to download the CMake modules that you wish you customize
to a separate directory (e.g. ``custom/``) and source the customized CMake
modules in ``autocmake.cfg``. Alternatively you can serve your custom modules
modules in ``autocmake.yml``. Alternatively you can serve your custom modules
from your own http server.
@ -34,19 +34,30 @@ the branched customized versions. This will make it easier for you
to stay up-to-date with upstream development.
Overriding defaults
Overriding settings
-------------------
Some modules use interpolations to set defaults, see for instance
https://github.com/coderefinery/autocmake/blob/stable-0.x/modules/boost/boost.cmake#L33-L36.
These can be modified within ``autocmake.cfg``, e.g.:
https://github.com/coderefinery/autocmake/blob/stable-0.x/test/boost_libs/cmake/autocmake.cfg#L9
If you source a module which contains directives such as
``define``,
``docopt``,
``export``, or
``fetch``, and you wish to modify those,
then you can override these settings in ``autocmake.yml``.
Settings in ``autocmake.yml`` take precedence over
settings imported by a sourced module.
As an example consider the Boost module which defines and uses
interpolation variables ``major``, ``minor``, and ``patch``, see
https://github.com/coderefinery/autocmake/blob/master/modules/boost/boost.cmake#L52-L54.
The recommended way to customize these is in ``autocmake.yml``, e.g.:
https://github.com/coderefinery/autocmake/blob/master/test/boost_libs/cmake/autocmake.yml#L12-L17.
Create own CMake modules
------------------------
Of course you can also create own modules and source them in ``autocmake.cfg``.
Of course you can also create own modules and source them in ``autocmake.yml``.
Contribute customizations to the "standard library"

View File

@ -4,7 +4,7 @@ Example Hello World project
===========================
This is a brief example for the busy and impatient programmer. For a longer
tour please see :ref:`autocmake_cfg`.
tour please see :ref:`autocmake_yml`.
We start with a mixed Fortran-C project with the following sources::
@ -25,7 +25,7 @@ Now we create ``cmake/`` and fetch ``update.py``::
$ mkdir cmake
$ cd cmake/
$ wget https://raw.githubusercontent.com/coderefinery/autocmake/stable-0.x/update.py
$ wget https://raw.githubusercontent.com/coderefinery/autocmake/master/update.py
$ python update.py --self
Now from top-level our file tree looks like this::
@ -50,13 +50,13 @@ Now we edit ``cmake/autocmake.cfg`` to look like this::
min_cmake_version: 2.8
[fc]
source: https://github.com/coderefinery/autocmake/raw/stable-0.x/modules/fc.cmake
source: https://github.com/coderefinery/autocmake/raw/master/modules/fc.cmake
[cc]
source: https://github.com/coderefinery/autocmake/raw/stable-0.x/modules/cc.cmake
source: https://github.com/coderefinery/autocmake/raw/master/modules/cc.cmake
[src]
source: https://github.com/coderefinery/autocmake/raw/stable-0.x/modules/src.cmake
source: https://github.com/coderefinery/autocmake/raw/master/modules/src.cmake
What we have specified here is the project name and that we wish Fortran and C
support. The ``src.cmake`` module tells CMake to include a ``src/CMakeLists.txt``.

View File

@ -107,7 +107,7 @@ overwritten at some point. A good standard is to organize your sources under
can include the latter in ``autocmake.cfg`` using::
[src]
source: https://github.com/coderefinery/autocmake/raw/stable-0.x/modules/src.cmake
source: https://github.com/coderefinery/autocmake/raw/master/modules/src.cmake
If you really don't like to do it this way, you can describe your sources and
targets in a custom module in a local file and include it like this::

View File

@ -21,7 +21,7 @@ rather fetch an older version, for example with the hash ``abcd123``. To
achieve this, instead of::
[foo]
source: https://github.com/coderefinery/autocmake/raw/stable-0.x/modules/foo.cmake
source: https://github.com/coderefinery/autocmake/raw/master/modules/foo.cmake
pin the version to ``abcd123`` (you do not need to specify the full Git hash, a unique
beginning will do)::

View File

@ -73,7 +73,7 @@ def main():
if s_out != '':
output.append('\n\n%s' % file_name)
output.append('-'*len(file_name))
output.append('`[Source code] <https://github.com/coderefinery/autocmake/blob/stable-0.x/modules/%s>`__' % full_file_name)
output.append('`[Source code] <https://github.com/coderefinery/autocmake/blob/master/modules/%s>`__' % full_file_name)
output.append(s_out)
with open(os.path.join(THIS_DIR, 'module-reference.rst'), 'w') as f:

View File

@ -7,9 +7,10 @@ Building libraries and executables from sources can be a complex task. Several
solutions exist to this problem: GNU Makefiles is the traditional approach.
Today, CMake is one of the trendier alternatives which can generate Makefiles
starting from a file called ``CMakeLists.txt``.
Autocmake composes CMake building blocks into a CMake project and generates
``CMakeLists.txt`` as well as a setup script, which serves as a front-end to
``CMakeLists.txt``. All this is done based on a lightweight ``autocmake.cfg``
``CMakeLists.txt``. All this is done based on a lightweight ``autocmake.yml``
file::
python update.py --self
@ -19,14 +20,14 @@ file::
| and updates the update.py script |
| |
v Developer maintaining
autocmake.cfg Autocmake
autocmake.yml Autocmake
| |
| python update.py .. |
| |
v v
CMakeLists.txt (and setup front-end)
| |
| python setup |
| python setup or ./setup |
| which invokes CMake |
v User of the code
Makefile (or something else) |
@ -37,7 +38,7 @@ file::
Build/install/test targets
Our main motivation to create Autocmake as a CMake framework library and
CMake module composer was to simplify CMake code transfer between codes. We got
CMake module composer is to simplify CMake code transfer between codes. We got
tired of manually diffing and copy-pasting boiler-plate CMake code and watching
it diverge while maintaining the CMake infrastructure in a growing number of
scientific projects which typically have very similar requirements:

View File

@ -3,9 +3,8 @@
Requirements and dependencies
=============================
Autocmake update and test scripts require Python 2.7 or higher. We try to also
support Python 3 (tested with Python 3.4). If the script fails with Python 3,
consider this a bug and please file an issue.
Autocmake update and test scripts require Python 2.7 or higher. We also
support Python 3 (we automatically test with 2.7 and 3.5).
The generated setup script runs with Python >= 2.6 (also tested with Python
3.4; probably also lower).
3.5).

View File

@ -1,7 +1,7 @@
Autocmake
=========
Autocmake (this documentation is outdated, see stable-0.x branch)
=================================================================
General

View File

@ -50,5 +50,8 @@ Like this::
$ python setup --cmake-options='"-DTHIS_OPTION=ON -DTHAT_OPTION=OFF"'
We use two sets of quotes because the shell swallows one set of them
before passing the arguments to Python. If you do not use two sets
of quotes then the setup command may end up incorrectly saved in `build/setup_command`.
before passing the arguments to Python. Yeah that's not nice, but nothing
we can do about it on the Python side.
If you do not use two sets
of quotes then the setup command may end up
incorrectly saved in `build/setup_command`.

View File

@ -1,7 +0,0 @@
# CMakeLists.txt and setup script will be generated from this file
# see: http://autocmake.readthedocs.org/en/latest/developers/configuration.html
# uncomment the following three lines and set the project name
# [project]
# name: myproject
# min_cmake_version: 2.8

7
example/autocmake.yml Normal file
View File

@ -0,0 +1,7 @@
# CMakeLists.txt and setup script will be generated from this file
# see: http://autocmake.readthedocs.io/en/latest/developers/configuration.html
# adapt the following lines and expand
name: myproject
min_cmake_version: 2.8

BIN
img/autocmake.png Normal file

Binary file not shown.

After

Width:  |  Height:  |  Size: 6.0 KiB

90
img/autocmake.svg Normal file
View File

@ -0,0 +1,90 @@
<?xml version="1.0" encoding="UTF-8" standalone="no"?>
<!-- Created with Inkscape (http://www.inkscape.org/) -->
<svg
xmlns:dc="http://purl.org/dc/elements/1.1/"
xmlns:cc="http://creativecommons.org/ns#"
xmlns:rdf="http://www.w3.org/1999/02/22-rdf-syntax-ns#"
xmlns:svg="http://www.w3.org/2000/svg"
xmlns="http://www.w3.org/2000/svg"
xmlns:sodipodi="http://sodipodi.sourceforge.net/DTD/sodipodi-0.dtd"
xmlns:inkscape="http://www.inkscape.org/namespaces/inkscape"
width="210mm"
height="297mm"
viewBox="0 0 744.09448819 1052.3622047"
id="svg2"
version="1.1"
inkscape:version="0.91 r13725"
sodipodi:docname="autocmake.svg">
<defs
id="defs4" />
<sodipodi:namedview
id="base"
pagecolor="#ffffff"
bordercolor="#666666"
borderopacity="1.0"
inkscape:pageopacity="0.0"
inkscape:pageshadow="2"
inkscape:zoom="0.49497475"
inkscape:cx="255.71429"
inkscape:cy="520"
inkscape:document-units="px"
inkscape:current-layer="layer1"
showgrid="false"
inkscape:window-width="1920"
inkscape:window-height="1001"
inkscape:window-x="0"
inkscape:window-y="27"
inkscape:window-maximized="1" />
<metadata
id="metadata7">
<rdf:RDF>
<cc:Work
rdf:about="">
<dc:format>image/svg+xml</dc:format>
<dc:type
rdf:resource="http://purl.org/dc/dcmitype/StillImage" />
<dc:title></dc:title>
</cc:Work>
</rdf:RDF>
</metadata>
<g
inkscape:label="Layer 1"
inkscape:groupmode="layer"
id="layer1">
<g
id="g3411">
<rect
y="326.18109"
x="72.047241"
height="400"
width="600"
id="rect3407"
style="fill:#0e4089;fill-opacity:1" />
<path
inkscape:connector-curvature="0"
id="path3401"
d="m 308.00113,650.73649 c 0,-0.42522 5.41704,-26.15959 12.03787,-57.1875 6.62083,-31.0279 12.97185,-60.80188 14.1134,-66.16438 l 2.07552,-9.75 15.3241,0 15.32411,0 0.19153,66.9375 0.19153,66.93751 -29.62903,0 c -19.84348,0 -29.62903,-0.25534 -29.62903,-0.77313 z m 71.0849,-51.16438 c -0.0908,-28.56562 -0.19938,-58.34999 -0.24129,-66.1875 -0.0419,-7.8375 0.0685,-14.67187 0.24533,-15.1875 0.24153,-0.70421 3.74313,-0.9375 14.07204,-0.9375 7.56277,0 13.90344,0.25313 14.09042,0.5625 0.33225,0.54975 29.7486,132.27474 29.7486,133.21275 0,0.26112 -12.99375,0.47476 -28.875,0.47476 l -28.875,0 -0.1651,-51.93751 z m 33.9151,-88.28869 0,-7.52381 -41.22185,0 -41.22186,0 -0.21564,6.9375 -0.21565,6.9375 -7.875,0 -7.875,0 -0.21565,-6.9375 -0.21564,-6.9375 -9.37402,0 -9.37401,0 0.21466,-7.3125 0.21466,-7.3125 76.5,0 76.5,0 0.21562,6.9375 c 0.1638,5.26821 -0.0165,6.9383 -0.75,6.94082 -5.8743,0.0202 -16.4307,0.58678 -16.74262,0.89865 -0.21953,0.21958 -0.55058,3.56584 -0.7356,7.43614 l -0.33638,7.03689 -8.63805,0.21131 -8.63797,0.2113 0,-7.5238 z m -36.7508,-29.8988 c -1.20169,-0.401 -1.01461,-80.3489 0.1883,-80.46723 2.44805,-0.24081 8.48431,0.23383 8.86144,0.6968 0.23316,0.28623 1.1451,4.40167 2.02652,9.14542 0.88143,4.74375 4.16729,22.41712 7.30192,39.27415 3.13463,16.85703 5.55114,30.79733 5.37002,30.97845 -0.38858,0.38858 -22.65342,0.73772 -23.7482,0.37241 z m -32.72028,-1.8842 c 0.24284,-0.96756 3.82423,-18.4238 7.95865,-38.79165 4.13442,-20.36785 7.70756,-37.63246 7.94032,-38.3658 0.34778,-1.09576 1.28287,-1.33336 5.24765,-1.33336 l 4.82446,0 0,40.125 0,40.125 -13.20631,0 -13.20631,0 0.44154,-1.75919 z"
style="fill:#ffffff" />
<rect
y="482.86636"
x="77.082703"
height="62.629459"
width="589.92908"
id="rect3409"
style="fill:#0e4089;fill-opacity:1" />
<text
sodipodi:linespacing="125%"
id="text3403"
y="531.68109"
x="192.04724"
style="font-style:normal;font-weight:normal;font-size:40px;line-height:125%;font-family:sans-serif;letter-spacing:0px;word-spacing:0px;fill:#ffffff;fill-opacity:1;stroke:none;stroke-width:1px;stroke-linecap:butt;stroke-linejoin:miter;stroke-opacity:1"
xml:space="preserve"><tspan
style="font-style:normal;font-variant:normal;font-weight:500;font-stretch:normal;font-family:'Pet Me 64';-inkscape-font-specification:'Pet Me 64 Medium';fill:#ffffff"
y="531.68109"
x="192.04724"
id="tspan3405"
sodipodi:role="line">Autocmake</tspan></text>
</g>
</g>
</svg>

After

Width:  |  Height:  |  Size: 4.3 KiB

View File

@ -5,11 +5,14 @@
# Autocmake update time.
# Note that the build-up commands are not Windows-compatible!
#
# Your autocmake.cfg should look like this::
# Your autocmake.yml should look like this::
#
# [boost]
# override: {'major': 1, 'minor': 59, 'patch': 0, 'components': 'chrono;timer;system'}
# source: https://github.com/coderefinery/autocmake/raw/stable-0.x/modules/boost/boost.cmake
# - boost:
# - major: 1
# - minor: 59
# - patch: 0
# - components: "chrono;timer;system"
# - source: "https://github.com/coderefinery/autocmake/raw/master/modules/boost/boost.cmake"
#
# Cross-dependencies between required components are not checked for.
# For example, Boost.Timer depends on Boost.Chrono and Boost.System thus you
@ -43,39 +46,41 @@
# MPI_FOUND
# BUILD_CUSTOM_BOOST
#
# autocmake.cfg configuration::
# autocmake.yml configuration::
#
# major=1
# minor=48
# patch=0
# components=''
# fetch: https://github.com/coderefinery/autocmake/raw/stable-0.x/modules/boost/boost_unpack.cmake
# https://github.com/coderefinery/autocmake/raw/stable-0.x/modules/boost/boost_userconfig.cmake
# https://github.com/coderefinery/autocmake/raw/stable-0.x/modules/boost/boost_configure.cmake
# https://github.com/coderefinery/autocmake/raw/stable-0.x/modules/boost/boost_build.cmake
# https://github.com/coderefinery/autocmake/raw/stable-0.x/modules/boost/boost_install.cmake
# https://github.com/coderefinery/autocmake/raw/stable-0.x/modules/boost/boost_headers.cmake
# https://github.com/coderefinery/autocmake/raw/stable-0.x/modules/boost/boost_cleanup.cmake
# http://sourceforge.net/projects/boost/files/boost/%(major)s.%(minor)s.%(patch)s/boost_%(major)s_%(minor)s_%(patch)s.zip
# docopt: --boost-headers=<BOOST_INCLUDEDIR> Include directories for Boost [default: ''].
# --boost-libraries=<BOOST_LIBRARYDIR> Library directories for Boost [default: ''].
# --build-boost=<FORCE_CUSTOM_BOOST> Deactivate Boost detection and build on-the-fly <ON/OFF> [default: OFF].
# define: '-DBOOST_INCLUDEDIR="{0}"'.format(arguments['--boost-headers'])
# '-DBOOST_LIBRARYDIR="{0}"'.format(arguments['--boost-libraries'])
# '-DFORCE_CUSTOM_BOOST="{0}"'.format(arguments['--build-boost'])
# '-DBOOST_MINIMUM_REQUIRED="%(major)s.%(minor)s.%(patch)s"'
# '-DBOOST_COMPONENTS_REQUIRED="%(components)s"'
# url_root: https://github.com/coderefinery/autocmake/raw/master/
# major: 1
# minor: 48
# patch: 0
# components: ""
# fetch:
# - "%(url_root)modules/boost/boost_unpack.cmake"
# - "%(url_root)modules/boost/boost_userconfig.cmake"
# - "%(url_root)modules/boost/boost_configure.cmake"
# - "%(url_root)modules/boost/boost_build.cmake"
# - "%(url_root)modules/boost/boost_install.cmake"
# - "%(url_root)modules/boost/boost_headers.cmake"
# - "%(url_root)modules/boost/boost_cleanup.cmake"
# - "http://sourceforge.net/projects/boost/files/boost/%(major).%(minor).%(patch)/boost_%(major)_%(minor)_%(patch).zip"
# docopt:
# - "--boost-headers=<BOOST_INCLUDEDIR> Include directories for Boost [default: '']."
# - "--boost-libraries=<BOOST_LIBRARYDIR> Library directories for Boost [default: '']."
# - "--build-boost=<FORCE_CUSTOM_BOOST> Deactivate Boost detection and build on-the-fly <ON/OFF> [default: OFF]."
# define:
# - "'-DBOOST_INCLUDEDIR=\"{0}\"'.format(arguments['--boost-headers'])"
# - "'-DBOOST_LIBRARYDIR=\"{0}\"'.format(arguments['--boost-libraries'])"
# - "'-DFORCE_CUSTOM_BOOST={0}'.format(arguments['--build-boost'])"
# - "'-DBOOST_MINIMUM_REQUIRED=\"%(major).%(minor).%(patch)\"'"
# - "'-DBOOST_COMPONENTS_REQUIRED=\"%(components)\"'"
# FIXME Maintainer should be able to choose between fail (end-user has to satisfy dependency
# on its own) and soft-fail (self-build of Boost)
# Underscore-separated version number
string(REGEX REPLACE "\\." "_" BOOSTVER ${BOOST_MINIMUM_REQUIRED})
# Where the Boost .zip archive is located
# CMAKE_CURRENT_LIST_DIR is undefined in CMake 2.8.2
# see https://public.kitware.com/Bug/print_bug_page.php?bug_id=11675
# workaround: create CMAKE_CURRENT_LIST_DIR
get_filename_component(CMAKE_CURRENT_LIST_DIR ${CMAKE_CURRENT_LIST_FILE} PATH)
set(BOOST_ARCHIVE_LOCATION ${CMAKE_CURRENT_LIST_DIR})
set(BOOST_ARCHIVE_LOCATION ${PROJECT_SOURCE_DIR}/cmake/downloaded)
set(BOOST_ARCHIVE boost_${BOOSTVER}.zip)
# FIXME These are possibly not always good settings

View File

@ -17,12 +17,13 @@
#
# CFLAGS
#
# autocmake.cfg configuration::
# autocmake.yml configuration::
#
# docopt: --cc=<CC> C compiler [default: gcc].
# --extra-cc-flags=<EXTRA_CFLAGS> Extra C compiler flags [default: ''].
# export: 'CC={0}'.format(arguments['--cc'])
# define: '-DEXTRA_CFLAGS="{0}"'.format(arguments['--extra-cc-flags'])
# docopt:
# - "--cc=<CC> C compiler [default: gcc]."
# - "--extra-cc-flags=<EXTRA_CFLAGS> Extra C compiler flags [default: '']."
# export: "'CC={0}'.format(arguments['--cc'])"
# define: "'-DEXTRA_CFLAGS=\"{0}\"'.format(arguments['--extra-cc-flags'])"
enable_language(C)

View File

@ -10,10 +10,10 @@
#
# CCACHE_FOUND
#
# autocmake.cfg configuration::
# autocmake.yml configuration::
#
# docopt: --ccache=<USE_CCACHE> Toggle use of ccache <ON/OFF> [default: ON].
# define: '-DUSE_CCACHE="{0}"'.format(arguments['--ccache'])
# docopt: "--ccache=<USE_CCACHE> Toggle use of ccache <ON/OFF> [default: ON]."
# define: "'-DUSE_CCACHE={0}'.format(arguments['--ccache'])"
if(USE_CCACHE)
find_program(CCACHE_FOUND ccache)

View File

@ -8,10 +8,10 @@
# CMAKE_C_FLAGS
# CMAKE_CXX_FLAGS
#
# autocmake.cfg configuration::
# autocmake.yml configuration::
#
# docopt: --coverage Enable code coverage [default: False].
# define: '-DENABLE_CODE_COVERAGE=%s' % arguments['--coverage']
# docopt: "--coverage Enable code coverage [default: False]."
# define: "'-DENABLE_CODE_COVERAGE={0}'.format(arguments['--coverage'])"
option(ENABLE_CODE_COVERAGE "Enable code coverage" OFF)

View File

@ -17,12 +17,13 @@
#
# CXXFLAGS
#
# autocmake.cfg configuration::
# autocmake.yml configuration::
#
# docopt: --cxx=<CXX> C++ compiler [default: g++].
# --extra-cxx-flags=<EXTRA_CXXFLAGS> Extra C++ compiler flags [default: ''].
# export: 'CXX={0}'.format(arguments['--cxx'])
# define: '-DEXTRA_CXXFLAGS="{0}"'.format(arguments['--extra-cxx-flags'])
# docopt:
# - "--cxx=<CXX> C++ compiler [default: g++]."
# - "--extra-cxx-flags=<EXTRA_CXXFLAGS> Extra C++ compiler flags [default: '']."
# export: "'CXX={0}'.format(arguments['--cxx'])"
# define: "'-DEXTRA_CXXFLAGS=\"{0}\"'.format(arguments['--extra-cxx-flags'])"
enable_language(CXX)

View File

@ -7,10 +7,10 @@
#
# PREPROCESSOR_DEFINITIONS
#
# autocmake.cfg configuration::
# autocmake.yml configuration::
#
# docopt: --add-definitions=<STRING> Add preprocesor definitions [default: ''].
# define: '-DPREPROCESSOR_DEFINITIONS="%s"' % arguments['--add-definitions']
# docopt: "--add-definitions=<STRING> Add preprocesor definitions [default: '']."
# define: "'-DPREPROCESSOR_DEFINITIONS=\"{0}\"'.format(arguments['--add-definitions'])"
if(NOT "${PREPROCESSOR_DEFINITIONS}" STREQUAL "")
add_definitions(${PREPROCESSOR_DEFINITIONS})

View File

@ -21,12 +21,13 @@
#
# FCFLAGS
#
# autocmake.cfg configuration::
# autocmake.yml configuration::
#
# docopt: --fc=<FC> Fortran compiler [default: gfortran].
# --extra-fc-flags=<EXTRA_FCFLAGS> Extra Fortran compiler flags [default: ''].
# export: 'FC={0}'.format(arguments['--fc'])
# define: '-DEXTRA_FCFLAGS="{0}"'.format(arguments['--extra-fc-flags'])
# docopt:
# - "--fc=<FC> Fortran compiler [default: gfortran]."
# - "--extra-fc-flags=<EXTRA_FCFLAGS> Extra Fortran compiler flags [default: '']."
# export: "'FC={0}'.format(arguments['--fc'])"
# define: "'-DEXTRA_FCFLAGS=\"{0}\"'.format(arguments['--extra-fc-flags'])"
enable_language(Fortran)

View File

@ -26,14 +26,16 @@
#
# FCFLAGS
#
# autocmake.cfg configuration::
# autocmake.yml configuration::
#
# docopt: --fc=<FC> Fortran compiler [default: gfortran].
# --extra-fc-flags=<EXTRA_FCFLAGS> Extra Fortran compiler flags [default: ''].
# --fc-support=<FC_SUPPORT> Toggle Fortran language support (ON/OFF) [default: ON].
# export: 'FC={0}'.format(arguments['--fc'])
# define: '-DEXTRA_FCFLAGS="{0}"'.format(arguments['--extra-fc-flags'])
# '-DENABLE_FC_SUPPORT="{0}"'.format(arguments['--fc-support'])
# docopt:
# - "--fc=<FC> Fortran compiler [default: gfortran]."
# - "--extra-fc-flags=<EXTRA_FCFLAGS> Extra Fortran compiler flags [default: '']."
# - "--fc-support=<FC_SUPPORT> Toggle Fortran language support (ON/OFF) [default: ON]."
# export: "'FC={0}'.format(arguments['--fc'])"
# define:
# - "'-DEXTRA_FCFLAGS=\"{0}\"'.format(arguments['--extra-fc-flags'])"
# - "'-DENABLE_FC_SUPPORT={0}'.format(arguments['--fc-support'])"
option(ENABLE_FC_SUPPORT "Enable Fortran language support" ON)

View File

@ -5,10 +5,12 @@
# Git repository version and status information
# to the program output.
#
# autocmake.cfg configuration::
# autocmake.yml configuration::
#
# fetch: https://github.com/coderefinery/autocmake/raw/stable-0.x/modules/git_info/git_info_sub.cmake
# https://github.com/coderefinery/autocmake/raw/stable-0.x/modules/git_info/git_info.h.in
# url_root: https://github.com/coderefinery/autocmake/raw/master/
# fetch:
# - "%(url_root)modules/git_info/git_info_sub.cmake"
# - "%(url_root)modules/git_info/git_info.h.in"
# CMAKE_CURRENT_LIST_DIR is undefined in CMake 2.8.2
# see https://public.kitware.com/Bug/print_bug_page.php?bug_id=11675

View File

@ -6,9 +6,9 @@
#
# GOOGLETEST_ROOT
#
# autocmake.cfg configuration::
# autocmake.yml configuration::
#
# define: '-DGOOGLETEST_ROOT=external/googletest/googletest'
# define: "'-DGOOGLETEST_ROOT=external/googletest/googletest'"
set(GOOGLETEST_ROOT external/googletest/googletest CACHE STRING "Google Test source root")

View File

@ -6,10 +6,10 @@
#
# CMAKE_Fortran_FLAGS
#
# autocmake.cfg configuration::
# autocmake.yml configuration::
#
# docopt: --int64 Enable 64bit integers [default: False].
# define: '-DENABLE_64BIT_INTEGERS=%s' % arguments['--int64']
# docopt: "--int64 Enable 64bit integers [default: False]."
# define: "'-DENABLE_64BIT_INTEGERS={0}'.format(arguments['--int64'])"
option(ENABLE_64BIT_INTEGERS "Enable 64-bit integers" OFF)

View File

@ -8,12 +8,14 @@
# ACCELERATE_LIBRARIES - describe me, uncached
# ACCELERATE_INCLUDE_DIR - describe me, uncached
#
# autocmake.cfg configuration::
# autocmake.yml configuration::
#
# docopt: --accelerate Find and link to ACCELERATE [default: False].
# define: '-DENABLE_ACCELERATE=%s' % arguments['--accelerate']
# fetch: https://github.com/coderefinery/autocmake/raw/stable-0.x/modules/find/find_libraries.cmake
# https://github.com/coderefinery/autocmake/raw/stable-0.x/modules/find/find_include_files.cmake
# url_root: https://github.com/coderefinery/autocmake/raw/master/
# docopt: "--accelerate Find and link to ACCELERATE [default: False]."
# define: "'-DENABLE_ACCELERATE={0}'.format(arguments['--accelerate'])"
# fetch:
# - "%(url_root)modules/find/find_libraries.cmake"
# - "%(url_root)modules/find/find_include_files.cmake"
option(ENABLE_ACCELERATE "Find and link to ACCELERATE" OFF)

View File

@ -8,10 +8,10 @@
# ACML_LIBRARIES
# ACML_INCLUDE_DIR
#
# autocmake.cfg configuration::
# autocmake.yml configuration::
#
# docopt: --acml Find and link to ACML [default: False].
# define: '-DENABLE_ACML=%s' % arguments['--acml']
# docopt: "--acml Find and link to ACML [default: False]."
# define: "'-DENABLE_ACML={0}'.format(arguments['--acml'])"
option(ENABLE_ACML "Find and link to ACML" OFF)

View File

@ -8,10 +8,10 @@
# ATLAS_LIBRARIES
# ATLAS_INCLUDE_DIR
#
# autocmake.cfg configuration::
# autocmake.yml configuration::
#
# docopt: --atlas Find and link to ATLAS [default: False].
# define: '-DENABLE_ATLAS=%s' % arguments['--atlas']
# docopt: "--atlas Find and link to ATLAS [default: False]."
# define: "'-DENABLE_ATLAS={0}'.format(arguments['--atlas'])"
option(ENABLE_ATLAS "Find and link to ATLAS" OFF)

View File

@ -8,10 +8,10 @@
# BLAS_LIBRARIES
# BLAS_INCLUDE_DIR
#
# autocmake.cfg configuration::
# autocmake.yml configuration::
#
# docopt: --blas Find and link to BLAS [default: False].
# define: '-DENABLE_BLAS=%s' % arguments['--blas']
# docopt: "--blas Find and link to BLAS [default: False]."
# define: "'-DENABLE_BLAS={0}'.format(arguments['--blas'])"
option(ENABLE_BLAS "Find and link to BLAS" OFF)

View File

@ -8,12 +8,14 @@
# CBLAS_LIBRARIES - describe me, uncached
# CBLAS_INCLUDE_DIR - describe me, uncached
#
# autocmake.cfg configuration::
# autocmake.yml configuration::
#
# docopt: --cblas Find and link to CBLAS [default: False].
# define: '-DENABLE_CBLAS=%s' % arguments['--cblas']
# fetch: https://github.com/coderefinery/autocmake/raw/stable-0.x/modules/find/find_libraries.cmake
# https://github.com/coderefinery/autocmake/raw/stable-0.x/modules/find/find_include_files.cmake
# url_root: https://github.com/coderefinery/autocmake/raw/master/
# docopt: "--cblas Find and link to CBLAS [default: False]."
# define: "'-DENABLE_CBLAS={0}'.format(arguments['--cblas'])"
# fetch:
# - "%(url_root)modules/find/find_libraries.cmake"
# - "%(url_root)modules/find/find_include_files.cmake"
option(ENABLE_CBLAS "Find and link to CBLAS" OFF)

View File

@ -8,10 +8,10 @@
# GOTO_LIBRARIES
# GOTO_INCLUDE_DIR
#
# autocmake.cfg configuration::
# autocmake.yml configuration::
#
# docopt: --goto Find and link to GOTO [default: False].
# define: '-DENABLE_GOTO=%s' % arguments['--goto']
# docopt: "--goto Find and link to GOTO [default: False]."
# define: "'-DENABLE_GOTO={0}'.format(arguments['--goto'])"
option(ENABLE_GOTO "Find and link to GOTO" OFF)

View File

@ -8,10 +8,10 @@
# LAPACK_LIBRARIES
# LAPACK_INCLUDE_DIR
#
# autocmake.cfg configuration::
# autocmake.yml configuration::
#
# docopt: --lapack Find and link to LAPACK [default: False].
# define: '-DENABLE_LAPACK=%s' % arguments['--lapack']
# docopt: "--lapack Find and link to LAPACK [default: False]."
# define: "'-DENABLE_LAPACK={0}'.format(arguments['--lapack'])"
option(ENABLE_LAPACK "Find and link to LAPACK" OFF)

View File

@ -8,12 +8,14 @@
# LAPACKE_LIBRARIES - describe me, uncached
# LAPACKE_INCLUDE_DIR - describe me, uncached
#
# autocmake.cfg configuration::
# autocmake.yml configuration::
#
# docopt: --lapacke Find and link to LAPACKE [default: False].
# define: '-DENABLE_LAPACKE=%s' % arguments['--lapacke']
# fetch: https://github.com/coderefinery/autocmake/raw/stable-0.x/modules/find/find_libraries.cmake
# https://github.com/coderefinery/autocmake/raw/stable-0.x/modules/find/find_include_files.cmake
# url_root: https://github.com/coderefinery/autocmake/raw/master/
# docopt: "--lapacke Find and link to LAPACKE [default: False]."
# define: "'-DENABLE_LAPACKE={0}'.format(arguments['--lapacke'])"
# fetch:
# - "%(url_root)modules/find/find_libraries.cmake"
# - "%(url_root)modules/find/find_include_files.cmake"
option(ENABLE_LAPACKE "Find and link to LAPACKE" OFF)

124
modules/math/openblas.cmake Normal file
View File

@ -0,0 +1,124 @@
# this file is adapted from https://github.com/BVLC/caffe/blob/master/cmake/Modules/FindOpenBLAS.cmake
# and reused by providing the corresponding copyright notice:
#
#
# COPYRIGHT
#
# All contributions by the University of California:
# Copyright (c) 2014, 2015, The Regents of the University of California (Regents)
# All rights reserved.
#
# All other contributions:
# Copyright (c) 2014, 2015, the respective contributors
# All rights reserved.
#
# Caffe uses a shared copyright model: each contributor holds copyright over
# their contributions to Caffe. The project versioning records all such
# contribution and copyright details. If a contributor wants to further mark
# their specific copyright on a particular contribution, they should indicate
# their copyright solely in the commit message of the change when it is
# committed.
#
# LICENSE
#
# Redistribution and use in source and binary forms, with or without
# modification, are permitted provided that the following conditions are met:
#
# 1. Redistributions of source code must retain the above copyright notice, this
# list of conditions and the following disclaimer.
# 2. Redistributions in binary form must reproduce the above copyright notice,
# this list of conditions and the following disclaimer in the documentation
# and/or other materials provided with the distribution.
#
# THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND
# ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
# WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
# DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR
# ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
# (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
# LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
# ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
# (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
# SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
#
#
#.rst:
#
# Find and link to OpenBLAS.
#
# Variables defined::
#
# OpenBLAS_FOUND
# OpenBLAS_LIB
# OpenBLAS_INCLUDE_DIR
#
# autocmake.yml configuration::
#
# docopt: "--openblas Find and link to OpenBLAS [default: False]."
# define: "'-DENABLE_OPENBLAS={0}'.format(arguments['--openblas'])"
option(ENABLE_OPENBLAS "Find and link to OpenBLAS" OFF)
if (ENABLE_OPENBLAS)
SET(Open_BLAS_INCLUDE_SEARCH_PATHS
/usr/include
/usr/include/openblas
/usr/include/openblas-base
/usr/local/include
/usr/local/include/openblas
/usr/local/include/openblas-base
/opt/OpenBLAS/include
$ENV{OpenBLAS_HOME}
$ENV{OpenBLAS_HOME}/include
)
SET(Open_BLAS_LIB_SEARCH_PATHS
/lib/
/lib/openblas-base
/lib64/
/usr/lib
/usr/lib/openblas-base
/usr/lib64
/usr/local/lib
/usr/local/lib64
/opt/OpenBLAS/lib
$ENV{OpenBLAS}cd
$ENV{OpenBLAS}/lib
$ENV{OpenBLAS_HOME}
$ENV{OpenBLAS_HOME}/lib
)
FIND_PATH(OpenBLAS_INCLUDE_DIR NAMES cblas.h PATHS ${Open_BLAS_INCLUDE_SEARCH_PATHS})
FIND_LIBRARY(OpenBLAS_LIB NAMES openblas PATHS ${Open_BLAS_LIB_SEARCH_PATHS})
SET(OpenBLAS_FOUND ON)
# Check include files
IF(NOT OpenBLAS_INCLUDE_DIR)
SET(OpenBLAS_FOUND OFF)
MESSAGE(STATUS "Could not find OpenBLAS include. Turning OpenBLAS_FOUND off")
ENDIF()
# Check libraries
IF(NOT OpenBLAS_LIB)
SET(OpenBLAS_FOUND OFF)
MESSAGE(STATUS "Could not find OpenBLAS lib. Turning OpenBLAS_FOUND off")
ENDIF()
IF (OpenBLAS_FOUND)
IF (NOT OpenBLAS_FIND_QUIETLY)
MESSAGE(STATUS "Found OpenBLAS libraries: ${OpenBLAS_LIB}")
MESSAGE(STATUS "Found OpenBLAS include: ${OpenBLAS_INCLUDE_DIR}")
ENDIF (NOT OpenBLAS_FIND_QUIETLY)
ELSE (OpenBLAS_FOUND)
IF (OpenBLAS_FIND_REQUIRED)
MESSAGE(FATAL_ERROR "Could not find OpenBLAS")
ENDIF (OpenBLAS_FIND_REQUIRED)
ENDIF (OpenBLAS_FOUND)
MARK_AS_ADVANCED(
OpenBLAS_INCLUDE_DIR
OpenBLAS_LIB
OpenBLAS
)
endif()

View File

@ -37,18 +37,20 @@
# MKL_ROOT
# MKLROOT
#
# autocmake.cfg configuration::
# autocmake.yml configuration::
#
# docopt: --blas=<BLAS> Detect and link BLAS library (auto or off) [default: auto].
# --lapack=<LAPACK> Detect and link LAPACK library (auto or off) [default: auto].
# --mkl=<MKL> Pass MKL flag to the Intel compiler and linker and skip BLAS/LAPACK detection (sequential, parallel, cluster, or off) [default: off].
# define: '-DENABLE_BLAS=%s' % arguments['--blas']
# '-DENABLE_LAPACK=%s' % arguments['--lapack']
# '-DMKL_FLAG=%s' % arguments['--mkl']
# '-DMATH_LIB_SEARCH_ORDER="MKL;ESSL;OPENBLAS;ATLAS;ACML;SYSTEM_NATIVE"'
# '-DBLAS_LANG=Fortran'
# '-DLAPACK_LANG=Fortran'
# warning: 'This module is deprecated and will be removed in future versions'
# docopt:
# - "--blas=<BLAS> Detect and link BLAS library (auto or off) [default: auto]."
# - "--lapack=<LAPACK> Detect and link LAPACK library (auto or off) [default: auto]."
# - "--mkl=<MKL> Pass MKL flag to the Intel compiler and linker and skip BLAS/LAPACK detection (sequential, parallel, cluster, or off) [default: off]."
# define:
# - "'-DENABLE_BLAS={0}'.format(arguments['--blas'])"
# - "'-DENABLE_LAPACK={0}'.format(arguments['--lapack'])"
# - "'-DMKL_FLAG={0}'.format(arguments['--mkl'])"
# - "'-DMATH_LIB_SEARCH_ORDER=\"MKL;ESSL;OPENBLAS;ATLAS;ACML;SYSTEM_NATIVE\"'"
# - "'-DBLAS_LANG=Fortran'"
# - "'-DLAPACK_LANG=Fortran'"
# warning: "the math_libs.cmake module is deprecated and will be removed in future versions"
#-------------------------------------------------------------------------------
# ENABLE_STATIC_LINKING

View File

@ -13,10 +13,10 @@
# CMAKE_C_FLAGS
# CMAKE_CXX_FLAGS
#
# autocmake.cfg configuration::
# autocmake.yml configuration::
#
# docopt: --mpi Enable MPI parallelization [default: False].
# define: '-DENABLE_MPI=%s' % arguments['--mpi']
# docopt: "--mpi Enable MPI parallelization [default: False]."
# define: "'-DENABLE_MPI={0}'.format(arguments['--mpi'])"
option(ENABLE_MPI "Enable MPI parallelization" OFF)

View File

@ -13,10 +13,10 @@
# CMAKE_C_FLAGS
# CMAKE_CXX_FLAGS
#
# autocmake.cfg configuration::
# autocmake.yml configuration::
#
# docopt: --omp Enable OpenMP parallelization [default: False].
# define: '-DENABLE_OPENMP=%s' % arguments['--omp']
# docopt: "--omp Enable OpenMP parallelization [default: False]."
# define: "'-DENABLE_OPENMP={0}'.format(arguments['--omp'])"
option(ENABLE_OPENMP "Enable OpenMP parallelization" OFF)

View File

@ -15,10 +15,10 @@
# PYTHON_VERSION_MINOR - Python minor version found e.g. 5
# PYTHON_VERSION_PATCH - Python patch version found e.g. 2
#
# autocmake.cfg configuration::
# autocmake.yml configuration::
#
# docopt: --python=<PYTHON_INTERPRETER> The Python interpreter (development version) to use. [default: ''].
# define: '-DPYTHON_INTERPRETER="%s"' % arguments['--python']
# docopt: "--python=<PYTHON_INTERPRETER> The Python interpreter (development version) to use. [default: '']."
# define: "'-DPYTHON_INTERPRETER=\"{0}\"'.format(arguments['--python'])"
if("${PYTHON_INTERPRETER}" STREQUAL "")
find_package(PythonInterp REQUIRED)

View File

@ -1,2 +1,3 @@
pep8
pytest
pyyaml

0
test/__init__.py Normal file
View File

View File

@ -1,16 +0,0 @@
[project]
name: example
min_cmake_version: 2.8
[cxx]
source: ../../../modules/cxx.cmake
[boost]
override: {'major': 1, 'minor': 48, 'patch': 0}
source: ../../../modules/boost/boost.cmake
[default_build_paths]
source: ../../../modules/default_build_paths.cmake
[src]
source: ../../../modules/src.cmake

View File

@ -0,0 +1,14 @@
name: example
min_cmake_version: 2.8
modules:
- cxx:
- source: ../../../modules/cxx.cmake
- boost:
- major: 1
- minor: 48
- patch: 0
- source: ../../../modules/boost/boost.cmake
- default_build_paths:
- source: ../../../modules/default_build_paths.cmake
- src:
- source: ../../../modules/src.cmake

View File

@ -1,25 +0,0 @@
[project]
name: example
min_cmake_version: 2.8
[cxx]
source: ../../../modules/cxx.cmake
[mpi]
source: ../../../modules/mpi.cmake
[python_interpreter]
source: ../../../modules/python_interpreter.cmake
[python_libs]
source: ../../../modules/python_libs.cmake
[boost]
override: {'major': 1, 'minor': 59, 'patch': 0, 'components': 'mpi;serialization;python'}
source: ../../../modules/boost/boost.cmake
[default_build_paths]
source: ../../../modules/default_build_paths.cmake
[src]
source: ../../../modules/src.cmake

View File

@ -0,0 +1,21 @@
name: example
min_cmake_version: 2.8
modules:
- cxx:
- source: ../../../modules/cxx.cmake
- mpi:
- source: ../../../modules/mpi.cmake
- python_interpreter:
- source: ../../../modules/python_interpreter.cmake
- python_libs:
- source: ../../../modules/python_libs.cmake
- boost:
- major: 1
- minor: 59
- patch: 0
- components: 'mpi;serialization;python'
- source: ../../../modules/boost/boost.cmake
- default_build_paths:
- source: ../../../modules/default_build_paths.cmake
- src:
- source: ../../../modules/src.cmake

View File

@ -1,12 +0,0 @@
[project]
name: example
min_cmake_version: 2.8
[cxx]
source: ../../../modules/cxx.cmake
[default_build_paths]
source: ../../../modules/default_build_paths.cmake
[src]
source: ../../../modules/src.cmake

View File

@ -0,0 +1,9 @@
name: example
min_cmake_version: 2.8
modules:
- cxx:
- source: ../../../modules/cxx.cmake
- default_build_paths:
- source: ../../../modules/default_build_paths.cmake
- src:
- source: ../../../modules/src.cmake

View File

@ -1,15 +0,0 @@
[project]
name: example
min_cmake_version: 2.8
[cxx]
source: ../../../modules/cxx.cmake
[math]
source: ../../../modules/math/accelerate.cmake
[default_build_paths]
source: ../../../modules/default_build_paths.cmake
[src]
source: ../../../modules/src.cmake

View File

@ -0,0 +1,11 @@
name: example
min_cmake_version: 2.8
modules:
- cxx:
- source: ../../../modules/cxx.cmake
- math:
- source: ../../../modules/math/accelerate.cmake
- default_build_paths:
- source: ../../../modules/default_build_paths.cmake
- src:
- source: ../../../modules/src.cmake

View File

@ -1,15 +0,0 @@
[project]
name: example
min_cmake_version: 2.8
[cxx]
source: ../../../modules/cxx.cmake
[math]
source: ../../../modules/math/cblas.cmake
[default_build_paths]
source: ../../../modules/default_build_paths.cmake
[src]
source: ../../../modules/src.cmake

View File

@ -0,0 +1,11 @@
name: example
min_cmake_version: 2.8
modules:
- cxx:
- source: ../../../modules/cxx.cmake
- math:
- source: ../../../modules/math/cblas.cmake
- default_build_paths:
- source: ../../../modules/default_build_paths.cmake
- src:
- source: ../../../modules/src.cmake

View File

@ -1,12 +0,0 @@
[project]
name: example
min_cmake_version: 2.8
[cxx]
source: ../../../modules/cxx.cmake
[default_build_paths]
source: ../../../modules/default_build_paths.cmake
[src]
source: ../../../modules/src.cmake

View File

@ -0,0 +1,9 @@
name: example
min_cmake_version: 2.8
modules:
- cxx:
- source: ../../../modules/cxx.cmake
- default_build_paths:
- source: ../../../modules/default_build_paths.cmake
- src:
- source: ../../../modules/src.cmake

View File

@ -1,12 +0,0 @@
[project]
name: example
min_cmake_version: 2.8
[fc]
source: ../../../modules/fc.cmake
[default_build_paths]
source: ../../../modules/default_build_paths.cmake
[src]
source: ../../../modules/src.cmake

View File

@ -0,0 +1,9 @@
name: example
min_cmake_version: 2.8
modules:
- fc:
- source: ../../../modules/fc.cmake
- default_build_paths:
- source: ../../../modules/default_build_paths.cmake
- src:
- source: ../../../modules/src.cmake

View File

@ -1,15 +0,0 @@
[project]
name: example
min_cmake_version: 2.8
[fc]
source: ../../../modules/fc.cmake
[math]
source: ../../../modules/math/blas.cmake
[default_build_paths]
source: ../../../modules/default_build_paths.cmake
[src]
source: ../../../modules/src.cmake

View File

@ -0,0 +1,11 @@
name: example
min_cmake_version: 2.8
modules:
- fc:
- source: ../../../modules/fc.cmake
- math:
- source: ../../../modules/math/blas.cmake
- default_build_paths:
- source: ../../../modules/default_build_paths.cmake
- src:
- source: ../../../modules/src.cmake

View File

@ -1,15 +0,0 @@
[project]
name: example
min_cmake_version: 2.8
[fc]
source: ../../../modules/fc.cmake
[default_build_paths]
source: ../../../modules/default_build_paths.cmake
[src]
source: ../../../modules/src.cmake
[git_info]
source: ../../../modules/git_info/git_info.cmake

View File

@ -0,0 +1,11 @@
name: example
min_cmake_version: 2.8
modules:
- fc:
- source: ../../../modules/fc.cmake
- default_build_paths:
- source: ../../../modules/default_build_paths.cmake
- src:
- source: ../../../modules/src.cmake
- git_info:
- source: ../../../modules/git_info/git_info.cmake

View File

@ -1,15 +0,0 @@
[project]
name: example
min_cmake_version: 2.8
[fc]
source: ../../../modules/fc.cmake
[int64]
source: ../../../modules/int64.cmake
[default_build_paths]
source: ../../../modules/default_build_paths.cmake
[src]
source: ../../../modules/src.cmake

View File

@ -0,0 +1,11 @@
name: example
min_cmake_version: 2.8
modules:
- fc:
- source: ../../../modules/fc.cmake
- int64:
- source: ../../../modules/int64.cmake
- default_build_paths:
- source: ../../../modules/default_build_paths.cmake
- src:
- source: ../../../modules/src.cmake

View File

@ -1,15 +0,0 @@
[project]
name: example
min_cmake_version: 2.8
[fc]
source: ../../../modules/fc.cmake
[math]
source: ../../../modules/math/lapack.cmake
[default_build_paths]
source: ../../../modules/default_build_paths.cmake
[src]
source: ../../../modules/src.cmake

View File

@ -0,0 +1,11 @@
name: example
min_cmake_version: 2.8
modules:
- fc:
- source: ../../../modules/fc.cmake
- math:
- source: ../../../modules/math/lapack.cmake
- default_build_paths:
- source: ../../../modules/default_build_paths.cmake
- src:
- source: ../../../modules/src.cmake

View File

@ -1,15 +0,0 @@
[project]
name: example
min_cmake_version: 2.8
[fc]
source: ../../../modules/fc.cmake
[omp]
source: ../../../modules/omp.cmake
[default_build_paths]
source: ../../../modules/default_build_paths.cmake
[src]
source: ../../../modules/src.cmake

View File

@ -0,0 +1,11 @@
name: example
min_cmake_version: 2.8
modules:
- fc:
- source: ../../../modules/fc.cmake
- omp:
- source: ../../../modules/omp.cmake
- default_build_paths:
- source: ../../../modules/default_build_paths.cmake
- src:
- source: ../../../modules/src.cmake

View File

@ -0,0 +1,11 @@
name: example
min_cmake_version: 2.8
modules:
- fc:
- source: ../../../modules/fc.cmake
- math:
- source: ../../../modules/math/openblas.cmake
- default_build_paths:
- source: ../../../modules/default_build_paths.cmake
- src:
- source: ../../../modules/src.cmake

View File

@ -0,0 +1,6 @@
if(OpenBLAS_FOUND)
add_executable(example example.f90)
target_link_libraries(example ${OpenBLAS_LIB})
else()
message(FATAL_ERROR "OpenBLAS library not found")
endif()

View File

@ -0,0 +1,45 @@
program example
implicit none
integer, parameter :: n = 10
integer :: i, j
logical :: test_ok
real(8), allocatable :: a(:, :)
real(8), allocatable :: b(:, :)
real(8), allocatable :: c(:, :)
allocate(a(n, n))
allocate(b(n, n))
allocate(c(n, n))
a = 1.0d0
b = 2.0d0
c = 0.0d0
call dgemm('n', 'n', n, n, n, 1.0d0, a, n, b, n, 0.0d0, c, n)
test_ok = .true.
do i = 1, n
do j = 1, n
if (dabs(c(i, j) - 20.0d0) > tiny(0.0d0)) then
print *, 'ERROR: element', i, j, 'is', c(i, j)
test_ok = .false.
end if
end do
end do
deallocate(a)
deallocate(b)
deallocate(c)
if (test_ok) then
print *, 'PASSED'
else
print *, 'FAILED'
end if
end program

View File

@ -1,15 +0,0 @@
[project]
name: example
min_cmake_version: 2.8
[cxx]
source: ../../../modules/cxx.cmake
[python_interpreter]
source: ../../../modules/python_interpreter.cmake
[default_build_paths]
source: ../../../modules/default_build_paths.cmake
[src]
source: ../../../modules/src.cmake

View File

@ -0,0 +1,13 @@
name: example
min_cmake_version: 2.8
modules:
- cxx:
- source: ../../../modules/cxx.cmake
- python_interpreter:
- source: ../../../modules/python_interpreter.cmake
- python_libs:
- source: ../../../modules/python_libs.cmake
- default_build_paths:
- source: ../../../modules/default_build_paths.cmake
- src:
- source: ../../../modules/src.cmake

View File

@ -1,15 +0,0 @@
[project]
name: example
min_cmake_version: 2.8
[cxx]
source: ../../../modules/cxx.cmake
[python_interpreter]
source: ../../../modules/python_interpreter.cmake
[default_build_paths]
source: ../../../modules/default_build_paths.cmake
[src]
source: ../../../modules/src.cmake

View File

@ -0,0 +1,11 @@
name: example
min_cmake_version: 2.8
modules:
- cxx:
- source: ../../../modules/cxx.cmake
- python_interpreter:
- source: ../../../modules/python_interpreter.cmake
- default_build_paths:
- source: ../../../modules/default_build_paths.cmake
- src:
- source: ../../../modules/src.cmake

View File

@ -1,18 +0,0 @@
[project]
name: example
min_cmake_version: 2.8
[cxx]
source: ../../../modules/cxx.cmake
[python_interpreter]
source: ../../../modules/python_interpreter.cmake
[python_libs]
source: ../../../modules/python_libs.cmake
[default_build_paths]
source: ../../../modules/default_build_paths.cmake
[src]
source: ../../../modules/src.cmake

View File

@ -0,0 +1,13 @@
name: example
min_cmake_version: 2.8
modules:
- cxx:
- source: ../../../modules/cxx.cmake
- python_interpreter:
- source: ../../../modules/python_interpreter.cmake
- python_libs:
- source: ../../../modules/python_libs.cmake
- default_build_paths:
- source: ../../../modules/default_build_paths.cmake
- src:
- source: ../../../modules/src.cmake

View File

@ -1,18 +0,0 @@
[project]
name: example
min_cmake_version: 2.8
[cxx]
source: ../../../modules/cxx.cmake
[python_interpreter]
source: ../../../modules/python_interpreter.cmake
[python_libs]
source: ../../../modules/python_libs.cmake
[default_build_paths]
source: ../../../modules/default_build_paths.cmake
[src]
source: ../../../modules/src.cmake

View File

@ -0,0 +1,13 @@
name: example
min_cmake_version: 2.8
modules:
- cxx:
- source: ../../../modules/cxx.cmake
- python_interpreter:
- source: ../../../modules/python_interpreter.cmake
- python_libs:
- source: ../../../modules/python_libs.cmake
- default_build_paths:
- source: ../../../modules/default_build_paths.cmake
- src:
- source: ../../../modules/src.cmake

View File

@ -15,9 +15,6 @@ skip_on_linux = pytest.mark.skipif('sys.platform == "linux2"', reason="not worki
skip_always = pytest.mark.skipif('1 == 1', reason="tests are broken")
# ------------------------------------------------------------------------------
def exe(command):
"""
Executes command and returns string representations of stdout and stderr captured from the console.
@ -41,8 +38,6 @@ def exe(command):
return stdout, stderr
# ------------------------------------------------------------------------------
def configure_build_and_exe(name, setup_command, launcher=None):
@ -51,15 +46,9 @@ def configure_build_and_exe(name, setup_command, launcher=None):
os.chdir(os.path.join(HERE, name, 'cmake'))
shutil.copy(os.path.join('..', '..', '..', 'update.py'), 'update.py')
dst_dir = 'lib'
if not os.path.exists(dst_dir):
os.makedirs(dst_dir)
shutil.copy(os.path.join('..', '..', '..', dst_dir, 'config.py'), dst_dir)
dst_dir = os.path.join('lib', 'docopt')
if not os.path.exists(dst_dir):
os.makedirs(dst_dir)
shutil.copy(os.path.join('..', '..', '..', dst_dir, 'docopt.py'), dst_dir)
if os.path.exists('autocmake'):
shutil.rmtree('autocmake')
shutil.copytree(os.path.join('..', '..', '..', 'autocmake'), 'autocmake')
stdout, stderr = exe('python update.py ..')
os.chdir(os.path.join(HERE, name))
@ -89,8 +78,6 @@ def configure_build_and_exe(name, setup_command, launcher=None):
assert 'PASSED' in stdout
# ------------------------------------------------------------------------------
def test_extra_cmake_options():
configure_build_and_exe('extra_cmake_options', 'python setup --cxx=g++ --cmake-options="-DENABLE_SOMETHING=OFF -DENABLE_FOO=ON"')

6
test/test_openblas.py Normal file
View File

@ -0,0 +1,6 @@
from .test import configure_build_and_exe, skip_on_osx
@skip_on_osx
def test_fc_openblas():
configure_build_and_exe('fc_openblas', 'python setup --fc=gfortran --openblas')

632
update.py
View File

@ -2,292 +2,75 @@
import os
import sys
import datetime
import ast
import collections
__version__ = '0.5.0'
# we do not use the nicer sys.version_info.major
# for compatibility with Python < 2.7
if sys.version_info[0] > 2:
from io import StringIO
from configparser import ConfigParser
import urllib.request
class URLopener(urllib.request.FancyURLopener):
def http_error_default(self, url, fp, errcode, errmsg, headers):
sys.stderr.write("ERROR: could not fetch {0}\n".format(url))
sys.exit(-1)
else:
from StringIO import StringIO
from ConfigParser import ConfigParser
import urllib
class URLopener(urllib.FancyURLopener):
def http_error_default(self, url, fp, errcode, errmsg, headers):
sys.stderr.write("ERROR: could not fetch {0}\n".format(url))
sys.exit(-1)
AUTOCMAKE_GITHUB_URL = 'https://github.com/coderefinery/autocmake'
# ------------------------------------------------------------------------------
AUTOCMAKE_GITHUB_URL = 'https://github.com/coderefinery/autocmake/raw/master/'
def fetch_url(src, dst):
"""
Fetch file from URL src and save it to dst.
"""
dirname = os.path.dirname(dst)
if dirname != '':
if not os.path.isdir(dirname):
os.makedirs(dirname)
opener = URLopener()
opener.retrieve(src, dst)
# ------------------------------------------------------------------------------
def check_for_yaml():
try:
import yaml
except:
sys.stderr.write("ERROR: you need to install the pyyaml package\n")
sys.exit(-1)
def print_progress_bar(text, done, total, width):
"""
Print progress bar.
"""
n = int(float(width) * float(done) / float(total))
sys.stdout.write("\r{0} [{1}{2}] ({3}/{4})".format(text, '#' * n, ' ' * (width - n), done, total))
sys.stdout.flush()
# ------------------------------------------------------------------------------
if total > 0:
n = int(float(width) * float(done) / float(total))
sys.stdout.write("\r{0} [{1}{2}] ({3}/{4})".format(text, '#' * n, ' ' * (width - n), done, total))
sys.stdout.flush()
def align_options(options):
"""
Indents flags and aligns help texts.
"""
l = 0
for opt in options:
if len(opt[0]) > l:
l = len(opt[0])
s = []
for opt in options:
s.append(' {0}{1} {2}'.format(opt[0], ' ' * (l - len(opt[0])), opt[1]))
return '\n'.join(s)
# ------------------------------------------------------------------------------
def flat_add(l, x):
if isinstance(x, int):
l.append(x)
return l
elif isinstance(x, str):
l.append(x)
return l
else:
return l + x
def gen_cmake_command(config):
"""
Generate CMake command.
"""
s = []
s.append("\n\ndef gen_cmake_command(options, arguments):")
s.append(' """')
s.append(" Generate CMake command based on options and arguments.")
s.append(' """')
s.append(" command = []")
# take care of environment variables
for section in config.sections():
if config.has_option(section, 'export'):
for env in config.get(section, 'export').split('\n'):
s.append(' command.append({0})'.format(env))
s.append(" command.append(arguments['--cmake-executable'])")
# take care of cmake definitions
for section in config.sections():
if config.has_option(section, 'define'):
for definition in config.get(section, 'define').split('\n'):
s.append(' command.append({0})'.format(definition))
s.append(" command.append('-DCMAKE_BUILD_TYPE={0}'.format(arguments['--type']))")
s.append(" command.append('-G \"{0}\"'.format(arguments['--generator']))")
s.append(" if arguments['--cmake-options'] != \"''\":")
s.append(" command.append(arguments['--cmake-options'])")
s.append(" if arguments['--prefix']:")
s.append(" command.append('-DCMAKE_INSTALL_PREFIX=\"{0}\"'.format(arguments['--prefix']))")
s.append("\n return ' '.join(command)")
return '\n'.join(s)
# ------------------------------------------------------------------------------
def autogenerated_notice():
current_year = datetime.date.today().year
year_range = '2015-{0}'.format(current_year)
s = []
s.append('# This file is autogenerated by Autocmake v{0} http://autocmake.org'.format(__version__))
s.append('# Copyright (c) {0} by Radovan Bast, Jonas Juselius, and contributors.'.format(year_range))
return '\n'.join(s)
# ------------------------------------------------------------------------------
def gen_setup(config, relative_path, setup_script_name):
"""
Generate setup script.
"""
s = []
s.append('#!/usr/bin/env python')
s.append('\n{0}'.format(autogenerated_notice()))
s.append('\nimport os')
s.append('import sys')
s.append("\nsys.path.insert(0, '{0}')".format(relative_path))
s.append("sys.path.insert(0, '{0}')".format(os.path.join(relative_path, 'lib')))
s.append("sys.path.insert(0, '{0}')".format(os.path.join(relative_path, 'lib', 'docopt')))
s.append('import config')
s.append('import docopt')
s.append('\n\noptions = """')
s.append('Usage:')
s.append(' ./{0} [options] [<builddir>]'.format(setup_script_name))
s.append(' ./{0} (-h | --help)'.format(setup_script_name))
s.append('\nOptions:')
options = []
for section in config.sections():
if config.has_option(section, 'docopt'):
for opt in config.get(section, 'docopt').split('\n'):
first = opt.split()[0].strip()
rest = ' '.join(opt.split()[1:]).strip()
options.append([first, rest])
options.append(['--type=<TYPE>', 'Set the CMake build type (debug, release, or relwithdeb) [default: release].'])
options.append(['--generator=<STRING>', 'Set the CMake build system generator [default: Unix Makefiles].'])
options.append(['--show', 'Show CMake command and exit.'])
options.append(['--cmake-executable=<CMAKE_EXECUTABLE>', 'Set the CMake executable [default: cmake].'])
options.append(['--cmake-options=<STRING>', "Define options to CMake [default: '']."])
options.append(['--prefix=<PATH>', 'Set the install path for make install.'])
options.append(['<builddir>', 'Build directory.'])
options.append(['-h --help', 'Show this screen.'])
s.append(align_options(options))
s.append('"""')
s.append(gen_cmake_command(config))
s.append("\n")
s.append("# parse command line args")
s.append("try:")
s.append(" arguments = docopt.docopt(options, argv=None)")
s.append("except docopt.DocoptExit:")
s.append(r" sys.stderr.write('ERROR: bad input to {0}\n'.format(sys.argv[0]))")
s.append(" sys.stderr.write(options)")
s.append(" sys.exit(-1)")
s.append("\n")
s.append("# use extensions to validate/post-process args")
s.append("if config.module_exists('extensions'):")
s.append(" import extensions")
s.append(" arguments = extensions.postprocess_args(sys.argv, arguments)")
s.append("\n")
s.append("root_directory = os.path.dirname(os.path.realpath(__file__))")
s.append("\n")
s.append("build_path = arguments['<builddir>']")
s.append("\n")
s.append("# create cmake command")
s.append("cmake_command = '{0} {1}'.format(gen_cmake_command(options, arguments), root_directory)")
s.append("\n")
s.append("# run cmake")
s.append("config.configure(root_directory, build_path, cmake_command, arguments['--show'])")
return s
# ------------------------------------------------------------------------------
def gen_cmakelists(project_name, min_cmake_version, relative_path, modules):
"""
Generate CMakeLists.txt.
"""
s = []
s.append(autogenerated_notice())
s.append('\n# set minimum cmake version')
s.append('cmake_minimum_required(VERSION {0} FATAL_ERROR)'.format(min_cmake_version))
s.append('\n# project name')
s.append('project({0})'.format(project_name))
s.append('\n# do not rebuild if rules (compiler flags) change')
s.append('set(CMAKE_SKIP_RULE_DEPENDENCY TRUE)')
s.append('\n# if CMAKE_BUILD_TYPE undefined, we set it to Debug')
s.append('if(NOT CMAKE_BUILD_TYPE)')
s.append(' set(CMAKE_BUILD_TYPE "Debug")')
s.append('endif()')
if len(modules) > 0:
s.append('\n# directories which hold included cmake modules')
module_paths = [module.path for module in modules]
module_paths.append('downloaded') # this is done to be able to find fetched modules when testing
module_paths = list(set(module_paths))
module_paths.sort() # we do this to always get the same order and to minimize diffs
for directory in module_paths:
rel_cmake_module_path = os.path.join(relative_path, directory)
# on windows cmake corrects this so we have to make it wrong again
rel_cmake_module_path = rel_cmake_module_path.replace('\\', '/')
s.append('set(CMAKE_MODULE_PATH ${{CMAKE_MODULE_PATH}} ${{PROJECT_SOURCE_DIR}}/{0})'.format(rel_cmake_module_path))
if len(modules) > 0:
s.append('\n# included cmake modules')
for module in modules:
s.append('include({0})'.format(os.path.splitext(module.name)[0]))
return s
# ------------------------------------------------------------------------------
def prepend_or_set(config, section, option, value, defaults):
"""
If option is already set, then value is prepended.
If option is not set, then it is created and set to value.
This is used to prepend options with values which come from the module documentation.
"""
if value:
if config.has_option(section, option):
value += '\n{0}'.format(config.get(section, option, 0, defaults))
config.set(section, option, value)
return config
# ------------------------------------------------------------------------------
def fetch_modules(config, relative_path):
def fetch_modules(config, relative_path, download_directory):
"""
Assemble modules which will
be included in CMakeLists.txt.
"""
from collections import Iterable, namedtuple, defaultdict
from autocmake.extract import extract_list, to_d, to_l
from autocmake.parse_rst import parse_cmake_module
download_directory = 'downloaded'
if not os.path.exists(download_directory):
os.makedirs(download_directory)
l = list(filter(lambda x: config.has_option(x, 'source'),
config.sections()))
n = len(l)
cleaned_config = defaultdict(lambda: [])
modules = []
Module = collections.namedtuple('Module', 'path name')
Module = namedtuple('Module', 'path name')
warnings = []
num_sources = len(extract_list(config, 'source'))
if n > 0: # otherwise division by zero in print_progress_bar
i = 0
print_progress_bar(text='- assembling modules:', done=0, total=n, width=30)
for section in config.sections():
if config.has_option(section, 'source'):
for src in config.get(section, 'source').split('\n'):
print_progress_bar(text='- assembling modules:',
done=0,
total=num_sources,
width=30)
i = 0
for t in config['modules']:
for k, v in t.items():
d = to_d(v)
for _k, _v in to_d(v).items():
cleaned_config[_k] = flat_add(cleaned_config[_k], _v)
# fetch sources and parse them
if 'source' in d:
for src in to_l(d['source']):
i += 1
# we download the file
module_name = os.path.basename(src)
if 'http' in src:
path = download_directory
@ -306,52 +89,104 @@ def fetch_modules(config, relative_path):
sys.stderr.write("ERROR: {0} does not exist\n".format(src))
sys.exit(-1)
if config.has_option(section, 'override'):
defaults = ast.literal_eval(config.get(section, 'override'))
else:
defaults = {}
# we infer config from the module documentation
# dictionary d overrides the configuration in the module documentation
# this allows to override interpolation inside the module
with open(file_name, 'r') as f:
parsed_config = parse_cmake_module(f.read(), defaults)
if parsed_config['warning']:
warnings.append('WARNING from {0}: {1}'.format(module_name, parsed_config['warning']))
config = prepend_or_set(config, section, 'docopt', parsed_config['docopt'], defaults)
config = prepend_or_set(config, section, 'define', parsed_config['define'], defaults)
config = prepend_or_set(config, section, 'export', parsed_config['export'], defaults)
if parsed_config['fetch']:
for src in parsed_config['fetch'].split('\n'):
dst = os.path.join(fetch_dst_directory, os.path.basename(src))
fetch_url(src, dst)
parsed_config = parse_cmake_module(f.read(), d)
for _k2, _v2 in parsed_config.items():
if _k2 not in to_d(v):
# we add to clean_config only if the entry does not exist
# in parent autocmake.yml already
# this allows to override
cleaned_config[_k2] = flat_add(cleaned_config[_k2], _v2)
modules.append(Module(path=path, name=name))
i += 1
print_progress_bar(
text='- assembling modules:',
done=i,
total=n,
width=30
)
if config.has_option(section, 'fetch'):
# when we fetch directly from autocmake.cfg
# we download into downloaded/
for src in config.get(section, 'fetch').split('\n'):
dst = os.path.join(download_directory, os.path.basename(src))
fetch_url(src, dst)
print('')
print_progress_bar(text='- assembling modules:',
done=i,
total=num_sources,
width=30)
if warnings != []:
print('- {0}'.format('\n- '.join(warnings)))
print('')
return modules
return modules, cleaned_config
# ------------------------------------------------------------------------------
def process_yaml(argv):
from autocmake.parse_yaml import parse_yaml
from autocmake.generate import gen_cmakelists, gen_setup
from autocmake.extract import extract_list
project_root = argv[1]
if not os.path.isdir(project_root):
sys.stderr.write("ERROR: {0} is not a directory\n".format(project_root))
sys.exit(-1)
# read config file
print('- parsing autocmake.yml')
with open('autocmake.yml', 'r') as stream:
config = parse_yaml(stream)
if 'name' in config:
project_name = config['name']
else:
sys.stderr.write("ERROR: you have to specify the project name in autocmake.yml\n")
sys.exit(-1)
if ' ' in project_name.rstrip():
sys.stderr.write("ERROR: project name contains a space\n")
sys.exit(-1)
if 'min_cmake_version' in config:
min_cmake_version = config['min_cmake_version']
else:
sys.stderr.write("ERROR: you have to specify min_cmake_version in autocmake.yml\n")
sys.exit(-1)
if 'setup_script' in config:
setup_script_name = config['setup_script']
else:
setup_script_name = 'setup'
# get relative path from setup script to this directory
relative_path = os.path.relpath(os.path.abspath('.'), project_root)
download_directory = 'downloaded'
if not os.path.exists(download_directory):
os.makedirs(download_directory)
# fetch modules from the web or from relative paths
modules, cleaned_config = fetch_modules(config, relative_path, download_directory)
# fetch files which are not parsed
for src in cleaned_config['fetch']:
dst = os.path.join(download_directory, os.path.basename(src))
fetch_url(src, dst)
# print warnings
for warning in cleaned_config['warning']:
print('- WARNING: {0}'.format(warning))
# create CMakeLists.txt
print('- generating CMakeLists.txt')
s = gen_cmakelists(project_name, min_cmake_version, relative_path, modules)
with open(os.path.join(project_root, 'CMakeLists.txt'), 'w') as f:
f.write('{0}\n'.format('\n'.join(s)))
# create setup script
print('- generating setup script')
s = gen_setup(cleaned_config, relative_path, setup_script_name)
file_path = os.path.join(project_root, setup_script_name)
with open(file_path, 'w') as f:
f.write('{0}\n'.format('\n'.join(s)))
if sys.platform != 'win32':
make_executable(file_path)
def main(argv):
"""
Main function.
"""
if len(argv) != 2:
sys.stderr.write("\nYou can update a project in two steps.\n\n")
sys.stderr.write("Step 1: Update or create infrastructure files\n")
@ -365,183 +200,84 @@ def main(argv):
if argv[1] in ['-h', '--help']:
print('Usage:')
print(' python update.py --self Update this script and fetch or update infrastructure files under lib/.')
print(' python update.py <builddir> (Re)generate CMakeLists.txt and setup script and fetch or update CMake modules.')
print(' python update.py (-h | --help) Show this help text.')
for t, h in [('python update.py --self',
'Update this script and fetch or update infrastructure files under autocmake/.'),
('python update.py <builddir>',
'(Re)generate CMakeLists.txt and setup script and fetch or update CMake modules.'),
('python update.py (-h | --help)',
'Show this help text.')]:
print(' {0:30} {1}'.format(t, h))
sys.exit(0)
if argv[1] == '--self':
# update self
if not os.path.isfile('autocmake.cfg'):
print('- fetching example autocmake.cfg')
if not os.path.isfile('autocmake.yml'):
print('- fetching example autocmake.yml')
fetch_url(
src='{0}/raw/stable-0.x/example/autocmake.cfg'.format(AUTOCMAKE_GITHUB_URL),
dst='autocmake.cfg'
src='{0}example/autocmake.yml'.format(AUTOCMAKE_GITHUB_URL),
dst='autocmake.yml'
)
if not os.path.isfile('.gitignore'):
print('- creating .gitignore')
with open('.gitignore', 'w') as f:
f.write('*.pyc\n')
print('- fetching lib/config.py')
fetch_url(
src='{0}/raw/stable-0.x/lib/config.py'.format(AUTOCMAKE_GITHUB_URL),
dst='lib/config.py'
)
print('- fetching lib/docopt/docopt.py')
fetch_url(
src='{0}/raw/stable-0.x/lib/docopt/docopt.py'.format(AUTOCMAKE_GITHUB_URL),
dst='lib/docopt/docopt.py'
)
print('- fetching update.py')
fetch_url(
src='{0}/raw/stable-0.x/update.py'.format(AUTOCMAKE_GITHUB_URL),
dst='update.py'
)
for f in ['autocmake/configure.py',
'autocmake/__init__.py',
'autocmake/external/docopt.py',
'autocmake/external/__init__.py',
'autocmake/generate.py',
'autocmake/extract.py',
'autocmake/interpolate.py',
'autocmake/parse_rst.py',
'autocmake/parse_yaml.py',
'update.py']:
print('- fetching {0}'.format(f))
fetch_url(
src='{0}{1}'.format(AUTOCMAKE_GITHUB_URL, f),
dst='{0}'.format(f)
)
sys.exit(0)
project_root = argv[1]
if not os.path.isdir(project_root):
sys.stderr.write("ERROR: {0} is not a directory\n".format(project_root))
sys.exit(-1)
# read config file
print('- parsing autocmake.cfg')
config = ConfigParser(dict_type=collections.OrderedDict)
config.read('autocmake.cfg')
if not config.has_option('project', 'name'):
sys.stderr.write("ERROR: you have to specify the project name\n")
sys.stderr.write(" in autocmake.cfg under [project]\n")
sys.exit(-1)
project_name = config.get('project', 'name')
if ' ' in project_name.rstrip():
sys.stderr.write("ERROR: project name contains a space\n")
sys.exit(-1)
if not config.has_option('project', 'min_cmake_version'):
sys.stderr.write("ERROR: you have to specify the min_cmake_version for CMake\n")
sys.stderr.write(" in autocmake.cfg under [project]\n")
sys.exit(-1)
min_cmake_version = config.get('project', 'min_cmake_version')
if config.has_option('project', 'setup_script'):
setup_script_name = config.get('project', 'setup_script')
else:
setup_script_name = 'setup'
# get relative path from setup script to this directory
relative_path = os.path.relpath(os.path.abspath('.'), project_root)
# fetch modules from the web or from relative paths
modules = fetch_modules(config, relative_path)
# create CMakeLists.txt
print('- generating CMakeLists.txt')
s = gen_cmakelists(project_name, min_cmake_version, relative_path, modules)
with open(os.path.join(project_root, 'CMakeLists.txt'), 'w') as f:
f.write('{0}\n'.format('\n'.join(s)))
# create setup script
print('- generating setup script')
s = gen_setup(config, relative_path, setup_script_name)
file_path = os.path.join(project_root, setup_script_name)
with open(file_path, 'w') as f:
f.write('{0}\n'.format('\n'.join(s)))
if sys.platform != 'win32':
make_executable(file_path)
# ------------------------------------------------------------------------------
process_yaml(argv)
# http://stackoverflow.com/a/30463972
def make_executable(path):
# http://stackoverflow.com/a/30463972
mode = os.stat(path).st_mode
mode |= (mode & 0o444) >> 2 # copy R bits to X
os.chmod(path, mode)
# ------------------------------------------------------------------------------
def fetch_url(src, dst):
"""
Fetch file from URL src and save it to dst.
"""
# we do not use the nicer sys.version_info.major
# for compatibility with Python < 2.7
if sys.version_info[0] > 2:
import urllib.request
def parse_cmake_module(s_in, defaults={}):
class URLopener(urllib.request.FancyURLopener):
def http_error_default(self, url, fp, errcode, errmsg, headers):
sys.stderr.write("ERROR: could not fetch {0}\n".format(url))
sys.exit(-1)
else:
import urllib
parsed_config = collections.defaultdict(lambda: None)
class URLopener(urllib.FancyURLopener):
def http_error_default(self, url, fp, errcode, errmsg, headers):
sys.stderr.write("ERROR: could not fetch {0}\n".format(url))
sys.exit(-1)
if 'autocmake.cfg configuration::' not in s_in:
return parsed_config
dirname = os.path.dirname(dst)
if dirname != '':
if not os.path.isdir(dirname):
os.makedirs(dirname)
s_out = []
is_rst_line = False
for line in s_in.split('\n'):
if is_rst_line:
if len(line) > 0:
if line[0] != '#':
is_rst_line = False
else:
is_rst_line = False
if is_rst_line:
s_out.append(line[2:])
if '#.rst:' in line:
is_rst_line = True
autocmake_entry = '\n'.join(s_out).split('autocmake.cfg configuration::')[1]
autocmake_entry = autocmake_entry.replace('\n ', '\n')
# we prepend a fake section heading so that we can parse it with configparser
autocmake_entry = '[foo]\n' + autocmake_entry
buf = StringIO(autocmake_entry)
config = ConfigParser(dict_type=collections.OrderedDict)
config.readfp(buf)
for section in config.sections():
for s in ['docopt', 'define', 'export', 'fetch', 'warning']:
if config.has_option(section, s):
parsed_config[s] = config.get(section, s, 0, defaults)
return parsed_config
# ------------------------------------------------------------------------------
def test_parse_cmake_module():
s = '''#.rst:
#
# Foo ...
#
# autocmake.cfg configuration::
#
# docopt: --cxx=<CXX> C++ compiler [default: g++].
# --extra-cxx-flags=<EXTRA_CXXFLAGS> Extra C++ compiler flags [default: ''].
# export: 'CXX={0}'.format(arguments['--cxx'])
# define: '-DEXTRA_CXXFLAGS="{0}"'.format(arguments['--extra-cxx-flags'])
enable_language(CXX)
if(NOT DEFINED CMAKE_C_COMPILER_ID)
message(FATAL_ERROR "CMAKE_C_COMPILER_ID variable is not defined!")
endif()'''
parsed_config = parse_cmake_module(s)
assert parsed_config['docopt'] == "--cxx=<CXX> C++ compiler [default: g++].\n--extra-cxx-flags=<EXTRA_CXXFLAGS> Extra C++ compiler flags [default: '']."
s = '''#.rst:
#
# Foo ...
#
# Bar ...
enable_language(CXX)
if(NOT DEFINED CMAKE_C_COMPILER_ID)
message(FATAL_ERROR "CMAKE_C_COMPILER_ID variable is not defined!")
endif()'''
parsed_config = parse_cmake_module(s)
assert parsed_config['docopt'] is None
# ------------------------------------------------------------------------------
opener = URLopener()
opener.retrieve(src, dst)
if __name__ == '__main__':
check_for_yaml()
main(sys.argv)