]>
git.proxmox.com Git - ceph.git/blob - ceph/src/seastar/configure.py
3 # This file is open source software, licensed to you under the terms
4 # of the Apache License, Version 2.0 (the "License"). See the NOTICE file
5 # distributed with this work for additional information regarding copyright
6 # ownership. You may not use this file except in compliance with the License.
8 # You may obtain a copy of the License at
10 # http://www.apache.org/licenses/LICENSE-2.0
12 # Unless required by applicable law or agreed to in writing,
13 # software distributed under the License is distributed on an
14 # "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
15 # KIND, either express or implied. See the License for the
16 # specific language governing permissions and limitations
20 import distutils
.dir_util
27 tempfile
.tempdir
= "./build/tmp"
29 def add_tristate(arg_parser
, name
, dest
, help):
30 arg_parser
.add_argument('--enable-' + name
, dest
= dest
, action
= 'store_true', default
= None,
31 help = 'Enable ' + help)
32 arg_parser
.add_argument('--disable-' + name
, dest
= dest
, action
= 'store_false', default
= None,
33 help = 'Disable ' + help)
35 def try_compile(compiler
, source
= '', flags
= []):
36 return try_compile_and_link(compiler
, source
, flags
= flags
+ ['-c'])
38 def ensure_tmp_dir_exists():
39 if not os
.path
.exists(tempfile
.tempdir
):
40 os
.makedirs(tempfile
.tempdir
)
42 def try_compile_and_link(compiler
, source
= '', flags
= []):
43 ensure_tmp_dir_exists()
44 with tempfile
.NamedTemporaryFile() as sfile
:
45 ofile
= tempfile
.mktemp()
47 sfile
.file.write(bytes(source
, 'utf-8'))
49 # We can't write to /dev/null, since in some cases (-ftest-coverage) gcc will create an auxiliary
50 # output file based on the name of the output file, and "/dev/null.gcsa" is not a good name
51 return subprocess
.call([compiler
, '-x', 'c++', '-o', ofile
, sfile
.name
] + flags
,
52 stdout
= subprocess
.DEVNULL
,
53 stderr
= subprocess
.DEVNULL
) == 0
55 if os
.path
.exists(ofile
):
57 def dialect_supported(dialect
, compiler
='g++'):
58 return try_compile(compiler
=compiler
, source
='', flags
=['-std=' + dialect
])
60 arg_parser
= argparse
.ArgumentParser('Configure seastar')
61 arg_parser
.add_argument('--mode', action
='store', choices
=seastar_cmake
.SUPPORTED_MODES
+ ['all'], default
='all')
62 arg_parser
.add_argument('--cflags', action
= 'store', dest
= 'user_cflags', default
= '',
63 help = 'Extra flags for the C++ compiler')
64 arg_parser
.add_argument('--ldflags', action
= 'store', dest
= 'user_ldflags', default
= '',
65 help = 'Extra flags for the linker')
66 arg_parser
.add_argument('--optflags', action
= 'store', dest
= 'user_optflags', default
= '',
67 help = 'Extra optimization flags for the release mode')
68 arg_parser
.add_argument('--api-level', action
='store', dest
='api_level', default
='6',
69 help='Compatibility API level (6=latest)')
70 arg_parser
.add_argument('--compiler', action
= 'store', dest
= 'cxx', default
= 'g++',
71 help = 'C++ compiler path')
72 arg_parser
.add_argument('--c-compiler', action
='store', dest
='cc', default
='gcc',
73 help = 'C compiler path (for bundled libraries such as dpdk)')
74 arg_parser
.add_argument('--c++-dialect', action
='store', dest
='cpp_dialect', default
='',
75 help='C++ dialect to build with [default: %(default)s]')
76 arg_parser
.add_argument('--cook', action
='append', dest
='cook', default
=[],
77 help='Supply this dependency locally for development via `cmake-cooking` (can be repeated)')
78 arg_parser
.add_argument('--verbose', dest
='verbose', action
='store_true', help='Make configure output more verbose.')
83 help = 'DPDK support')
88 help = 'hwloc support')
91 name
= 'alloc-failure-injector',
92 dest
= 'alloc_failure_injection',
93 help = 'allocation failure injection')
96 name
= 'task-backtrace',
97 dest
= 'task_backtrace',
98 help = 'Collect backtrace at deferring points')
101 name
= 'unused-result-error',
102 dest
= "unused_result_error",
103 help = 'Make [[nodiscard]] violations an error')
106 name
= 'debug-shared-ptr',
107 dest
= "debug_shared_ptr",
108 help = 'Debug shared_ptr')
109 arg_parser
.add_argument('--allocator-page-size', dest
='alloc_page_size', type=int, help='override allocator page size')
110 arg_parser
.add_argument('--without-tests', dest
='exclude_tests', action
='store_true', help='Do not build tests by default')
111 arg_parser
.add_argument('--without-apps', dest
='exclude_apps', action
='store_true', help='Do not build applications by default')
112 arg_parser
.add_argument('--without-demos', dest
='exclude_demos', action
='store_true', help='Do not build demonstrations by default')
113 arg_parser
.add_argument('--split-dwarf', dest
='split_dwarf', action
='store_true', default
=False,
114 help='use of split dwarf (https://gcc.gnu.org/wiki/DebugFission) to speed up linking')
115 arg_parser
.add_argument('--heap-profiling', dest
='heap_profiling', action
='store_true', default
=False, help='Enable heap profiling')
116 arg_parser
.add_argument('--prefix', dest
='install_prefix', default
='/usr/local', help='Root installation path of Seastar files')
117 args
= arg_parser
.parse_args()
119 def identify_best_dialect(dialects
, compiler
):
120 """Returns the first C++ dialect accepted by the compiler in the sequence,
121 assuming the "best" dialects appear first.
123 If no dialects are accepted, the result is the last dialect in the sequence
124 (we assume that this error will be displayed to the user - during compile
125 time - in an informative way).
129 if dialect_supported(d
, compiler
):
134 if args
.cpp_dialect
== '':
135 cpp_dialects
= ['gnu++17', 'gnu++1z', 'gnu++14', 'gnu++1y']
136 args
.cpp_dialect
= identify_best_dialect(cpp_dialects
, compiler
=args
.cxx
)
138 def infer_dpdk_machine(user_cflags
):
139 """Infer the DPDK machine identifier (e.g., 'ivb') from the space-separated
140 string of user cflags by scraping the value of `-march` if it is present.
142 The default if no architecture is indicated is 'native'.
146 # `-march` may be repeated, and we want the last one.
147 # strip features, leave only the arch: armv8-a+crc+crypto -> armv8-a
148 for flag
in user_cflags
.split():
149 if flag
.startswith('-march'):
150 arch
= flag
[7:].split('+')[0]
156 'sandybridge': 'snb',
161 return MAPPING
.get(arch
, 'native')
163 MODES
= seastar_cmake
.SUPPORTED_MODES
if args
.mode
== 'all' else [args
.mode
]
166 tr
= seastar_cmake
.translate_arg
168 MODE_TO_CMAKE_BUILD_TYPE
= {'release' : 'RelWithDebInfo', 'debug' : 'Debug', 'dev' : 'Dev', 'sanitize' : 'Sanitize' }
170 def configure_mode(mode
):
171 BUILD_PATH
= seastar_cmake
.BUILD_PATHS
[mode
]
173 CFLAGS
= seastar_cmake
.convert_strings_to_cmake_list(
175 args
.user_optflags
if seastar_cmake
.is_release_mode(mode
) else '')
177 LDFLAGS
= seastar_cmake
.convert_strings_to_cmake_list(args
.user_ldflags
)
180 '-DCMAKE_BUILD_TYPE={}'.format(MODE_TO_CMAKE_BUILD_TYPE
[mode
]),
181 '-DCMAKE_C_COMPILER={}'.format(args
.cc
),
182 '-DCMAKE_CXX_COMPILER={}'.format(args
.cxx
),
183 '-DCMAKE_INSTALL_PREFIX={}'.format(args
.install_prefix
),
184 '-DSeastar_API_LEVEL={}'.format(args
.api_level
),
185 tr(args
.exclude_tests
, 'EXCLUDE_TESTS_FROM_ALL'),
186 tr(args
.exclude_apps
, 'EXCLUDE_APPS_FROM_ALL'),
187 tr(args
.exclude_demos
, 'EXCLUDE_DEMOS_FROM_ALL'),
188 tr(CFLAGS
, 'CXX_FLAGS'),
189 tr(LDFLAGS
, 'LD_FLAGS'),
190 tr(args
.cpp_dialect
, 'CXX_DIALECT'),
191 tr(args
.dpdk
, 'DPDK'),
192 tr(infer_dpdk_machine(args
.user_cflags
), 'DPDK_MACHINE'),
193 tr(args
.hwloc
, 'HWLOC', value_when_none
='yes'),
194 tr(args
.alloc_failure_injection
, 'ALLOC_FAILURE_INJECTION', value_when_none
='DEFAULT'),
195 tr(args
.task_backtrace
, 'TASK_BACKTRACE'),
196 tr(args
.alloc_page_size
, 'ALLOC_PAGE_SIZE'),
197 tr(args
.split_dwarf
, 'SPLIT_DWARF'),
198 tr(args
.heap_profiling
, 'HEAP_PROFILING'),
199 tr(args
.unused_result_error
, 'UNUSED_RESULT_ERROR'),
200 tr(args
.debug_shared_ptr
, 'DEBUG_SHARED_PTR', value_when_none
='default'),
203 ingredients_to_cook
= set(args
.cook
)
206 ingredients_to_cook
.add('dpdk')
208 # Generate a new build by pointing to the source directory.
209 if ingredients_to_cook
:
210 # We need to use cmake-cooking for some dependencies.
211 inclusion_arguments
= []
213 for ingredient
in ingredients_to_cook
:
214 inclusion_arguments
.extend(['-i', ingredient
])
216 ARGS
= seastar_cmake
.COOKING_BASIC_ARGS
+ inclusion_arguments
+ ['-d', BUILD_PATH
, '--']
217 dir = seastar_cmake
.ROOT_PATH
219 # When building without cooked dependencies, we can invoke cmake directly. We can't call
220 # cooking.sh, because without any -i parameters, it will try to build
222 ARGS
= ['cmake', '-G', 'Ninja', '../..']
224 ARGS
+= TRANSLATED_ARGS
226 print("Running CMake in '{}' ...".format(dir))
227 print(" \\\n ".join(ARGS
))
228 distutils
.dir_util
.mkpath(BUILD_PATH
)
229 subprocess
.check_call(ARGS
, shell
=False, cwd
=dir)