[bf13d27] | 1 | # |
---|
| 2 | # RTEMS Tools Project (http://www.rtems.org/) |
---|
| 3 | # Copyright 2010-2012 Chris Johns (chrisj@rtems.org) |
---|
| 4 | # All rights reserved. |
---|
| 5 | # |
---|
| 6 | # This file is part of the RTEMS Tools package in 'rtems-tools'. |
---|
| 7 | # |
---|
| 8 | # Permission to use, copy, modify, and/or distribute this software for any |
---|
| 9 | # purpose with or without fee is hereby granted, provided that the above |
---|
| 10 | # copyright notice and this permission notice appear in all copies. |
---|
| 11 | # |
---|
| 12 | # THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES |
---|
| 13 | # WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF |
---|
| 14 | # MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR |
---|
| 15 | # ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES |
---|
| 16 | # WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN |
---|
| 17 | # ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF |
---|
| 18 | # OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. |
---|
| 19 | |
---|
| 20 | # |
---|
| 21 | # Determine the defaults and load the specific file. |
---|
| 22 | # |
---|
| 23 | |
---|
| 24 | import glob |
---|
| 25 | import pprint |
---|
| 26 | import re |
---|
| 27 | import os |
---|
| 28 | |
---|
| 29 | import error |
---|
| 30 | import execute |
---|
[ab8319a] | 31 | import path |
---|
[bf13d27] | 32 | |
---|
[ba8a935] | 33 | basepath = 'sb' |
---|
[bf13d27] | 34 | |
---|
[ab8319a] | 35 | # |
---|
| 36 | # All paths in defaults must be Unix format. Do not store any Windows format |
---|
| 37 | # paths in the defaults. |
---|
| 38 | # |
---|
[8f84a6b] | 39 | # Every entry must describe the type of checking a host must pass. |
---|
| 40 | # |
---|
[ab8319a] | 41 | |
---|
[bf13d27] | 42 | defaults = { |
---|
| 43 | # Nothing |
---|
[8f84a6b] | 44 | 'nil': ('none', 'none', ''), |
---|
[bf13d27] | 45 | |
---|
| 46 | # Set to invalid values. |
---|
[8f84a6b] | 47 | '_bset': ('none', 'none', ''), |
---|
| 48 | 'name': ('none', 'none', ''), |
---|
| 49 | 'version': ('none', 'none', ''), |
---|
| 50 | 'release': ('none', 'none', ''), |
---|
| 51 | |
---|
| 52 | # GNU triples needed to build packages |
---|
| 53 | '_host': ('triplet', 'required', ''), |
---|
| 54 | '_build': ('triplet', 'required', '%{_host}'), |
---|
| 55 | '_target': ('none', 'optional', ''), |
---|
[bf13d27] | 56 | |
---|
| 57 | # Paths |
---|
[8f84a6b] | 58 | '_host_platform': ('none', 'none', '%{_host_cpu}-%{_host_vendor}-%{_host_os}%{?_gnu}'), |
---|
| 59 | '_build': ('none', 'none', '%{_host}'), |
---|
| 60 | '_arch': ('none', 'none', '%{_host_arch}'), |
---|
| 61 | '_sbdir': ('none', 'none', ''), |
---|
| 62 | '_topdir': ('dir', 'required', path.shell(os.getcwd())), |
---|
| 63 | '_configdir': ('dir', 'optional', '%{_topdir}/config:%{_sbdir}/config'), |
---|
| 64 | '_tardir': ('dir', 'optional', '%{_topdir}/tar'), |
---|
| 65 | '_sourcedir': ('dir', 'optional', '%{_topdir}/sources'), |
---|
[ec26725] | 66 | '_patchdir': ('dir', 'optional', '%{_topdir}/patches:%{_sbdir}/patches'), |
---|
[8f84a6b] | 67 | '_builddir': ('dir', 'optional', '%{_topdir}/build/%{name}-%{version}-%{release}'), |
---|
| 68 | '_docdir': ('dir', 'none', '%{_defaultdocdir}'), |
---|
| 69 | '_tmppath': ('dir', 'none', '%{_topdir}/build/tmp'), |
---|
| 70 | '_tmproot': ('dir', 'none', '%{_tmppath}/source-build-%(%{__id_u} -n)/%{_bset}'), |
---|
| 71 | 'buildroot:': ('dir', 'none', '%{_tmppath}/%{name}-root-%(%{__id_u} -n)'), |
---|
| 72 | '_datadir': ('dir', 'none', '%{_prefix}/share'), |
---|
| 73 | '_defaultdocdir': ('dir', 'none', '%{_prefix}/share/doc'), |
---|
| 74 | '_exeext': ('none', 'none', ''), |
---|
| 75 | '_exec_prefix': ('dir', 'none', '%{_prefix}'), |
---|
| 76 | '_bindir': ('dir', 'none', '%{_exec_prefix}/bin'), |
---|
| 77 | '_sbindir': ('dir', 'none', '%{_exec_prefix}/sbin'), |
---|
| 78 | '_libexecdir': ('dir', 'none', '%{_exec_prefix}/libexec'), |
---|
| 79 | '_datarootdir': ('dir', 'none', '%{_prefix}/share'), |
---|
| 80 | '_datadir': ('dir', 'none', '%{_datarootdir}'), |
---|
| 81 | '_sysconfdir': ('dir', 'none', '%{_prefix}/etc'), |
---|
| 82 | '_sharedstatedir': ('dir', 'none', '%{_prefix}/com'), |
---|
| 83 | '_localstatedir': ('dir', 'none', '%{prefix}/var'), |
---|
| 84 | '_includedir': ('dir', 'none', '%{_prefix}/include'), |
---|
| 85 | '_lib': ('dir', 'none', 'lib'), |
---|
| 86 | '_libdir': ('dir', 'none', '%{_exec_prefix}/%{_lib}'), |
---|
| 87 | '_libexecdir': ('dir', 'none', '%{_exec_prefix}/libexec'), |
---|
| 88 | '_mandir': ('dir', 'none', '%{_datarootdir}/man'), |
---|
| 89 | '_infodir': ('dir', 'none', '%{_datarootdir}/info'), |
---|
| 90 | '_localedir': ('dir', 'none', '%{_datarootdir}/locale'), |
---|
| 91 | '_localedir': ('dir', 'none', '%{_datadir}/locale'), |
---|
| 92 | '_localstatedir': ('dir', 'none', '%{_prefix}/var'), |
---|
| 93 | '_prefix': ('dir', 'none', '%{_usr}'), |
---|
| 94 | '_usr': ('dir', 'none', '/usr/local'), |
---|
| 95 | '_usrsrc': ('dir', 'none', '%{_usr}/src'), |
---|
| 96 | '_var': ('dir', 'none', '/usr/local/var'), |
---|
| 97 | '_varrun': ('dir', 'none', '%{_var}/run'), |
---|
[bf13d27] | 98 | |
---|
| 99 | # Defaults, override in platform specific modules. |
---|
[8f84a6b] | 100 | '___setup_shell': ('exe', 'required', '/bin/sh'), |
---|
| 101 | '__aclocal': ('exe', 'optional', 'aclocal'), |
---|
| 102 | '__ar': ('exe', 'required', 'ar'), |
---|
| 103 | '__arch_install_post': ('exe', 'none', '%{nil}'), |
---|
| 104 | '__as': ('exe', 'required', 'as'), |
---|
| 105 | '__autoconf': ('exe', 'required', 'autoconf'), |
---|
| 106 | '__autoheader': ('exe', 'required', 'autoheader'), |
---|
| 107 | '__automake': ('exe', 'required', 'automake'), |
---|
| 108 | '__awk': ('exe', 'required', 'awk'), |
---|
| 109 | '__bash': ('exe', 'optional', '/bin/bash'), |
---|
| 110 | '__bzip2': ('exe', 'required', '/usr/bin/bzip2'), |
---|
| 111 | '__cat': ('exe', 'required', '/bin/cat'), |
---|
| 112 | '__cc': ('exe', 'required', '/usr/bin/gcc'), |
---|
| 113 | '__chgrp': ('exe', 'required', '/usr/bin/chgrp'), |
---|
| 114 | '__chmod': ('exe', 'required', '/bin/chmod'), |
---|
| 115 | '__chown': ('exe', 'required', '/usr/sbin/chown'), |
---|
| 116 | '__cp': ('exe', 'required', '/bin/cp'), |
---|
| 117 | '__cpp': ('exe', 'none', '%{__cc} -E'), |
---|
| 118 | '__cxx': ('exe', 'required', '/usr/bin/g++'), |
---|
| 119 | '__grep': ('exe', 'required', '/usr/bin/grep'), |
---|
| 120 | '__gzip': ('exe', 'required', '/usr/bin/gzip'), |
---|
| 121 | '__id': ('exe', 'required', '/usr/bin/id'), |
---|
| 122 | '__id_u': ('exe', 'none', '%{__id} -u'), |
---|
| 123 | '__install': ('exe', 'required', '/usr/bin/install'), |
---|
| 124 | '__install_info': ('exe', 'optional', '/usr/bin/install-info'), |
---|
| 125 | '__ld': ('exe', 'required', '/usr/bin/ld'), |
---|
| 126 | '__ldconfig': ('exe', 'required', '/sbin/ldconfig'), |
---|
| 127 | '__ln_s': ('exe', 'none', 'ln -s'), |
---|
| 128 | '__make': ('exe', 'required', 'make'), |
---|
| 129 | '__mkdir': ('exe', 'required', '/bin/mkdir'), |
---|
| 130 | '__mkdir_p': ('exe', 'none', '/bin/mkdir -p'), |
---|
| 131 | '__mv': ('exe', 'required', '/bin/mv'), |
---|
| 132 | '__nm': ('exe', 'required', '/usr/bin/nm'), |
---|
[fc619d8] | 133 | '__objcopy': ('exe', 'optional', '/usr/bin//objcopy'), |
---|
| 134 | '__objdump': ('exe', 'optional', '/usr/bin/objdump'), |
---|
[8f84a6b] | 135 | '__patch': ('exe', 'required', '/usr/bin/patch'), |
---|
| 136 | '__perl': ('exe', 'optional', 'perl'), |
---|
| 137 | '__ranlib': ('exe', 'required', 'ranlib'), |
---|
| 138 | '__rm': ('exe', 'required', '/bin/rm'), |
---|
| 139 | '__sed': ('exe', 'required', '/usr/bin/sed'), |
---|
| 140 | '__setup_post': ('exe', 'none', '%{__chmod} -R a+rX,g-w,o-w .'), |
---|
| 141 | '__sh': ('exe', 'required', '/bin/sh'), |
---|
| 142 | '__tar': ('exe', 'required', '/usr/bin/tar'), |
---|
| 143 | '__tar_extract': ('exe', 'none', '%{__tar} -xvvf'), |
---|
| 144 | '__unzip': ('exe', 'required', '/usr/bin/unzip'), |
---|
| 145 | '__xz': ('exe', 'required', '/usr/bin/xz'), |
---|
[bf13d27] | 146 | |
---|
| 147 | # Shell Build Settings. |
---|
[8f84a6b] | 148 | '___build_args': ('none', 'none', '-e'), |
---|
| 149 | '___build_cmd': ('none', 'none', '%{?_sudo:%{_sudo} }%{?_remsh:%{_remsh} %{_remhost} }%{?_remsudo:%{_remsudo} }%{?_remchroot:%{_remchroot} %{_remroot} }%{___build_shell} %{___build_args}'), |
---|
| 150 | '___build_post': ('none', 'none', 'exit 0'), |
---|
[bf13d27] | 151 | |
---|
| 152 | # Prebuild set up script. |
---|
[8f84a6b] | 153 | '___build_pre': ('none', 'none', '''# ___build_pre in as set up in defaults.py |
---|
[bf13d27] | 154 | # Directories |
---|
[ba8a935] | 155 | SB_SOURCE_DIR="%{_sourcedir}" |
---|
| 156 | SB_BUILD_DIR="%{_builddir}" |
---|
| 157 | SB_OPT_FLAGS="%{optflags}" |
---|
| 158 | SB_ARCH="%{_arch}" |
---|
| 159 | SB_OS="%{_os}" |
---|
| 160 | export SB_SOURCE_DIR SB_BUILD_DIR SB_OPT_FLAGS SB_ARCH SB_OS |
---|
[bf13d27] | 161 | # Documentation |
---|
[ba8a935] | 162 | SB_DOC_DIR="%{_docdir}" |
---|
| 163 | export SB_DOC_DIR |
---|
[bf13d27] | 164 | # Packages |
---|
[ba8a935] | 165 | SB_PACKAGE_NAME="%{name}" |
---|
| 166 | SB_PACKAGE_VERSION="%{version}" |
---|
| 167 | SB_PACKAGE_RELEASE="%{release}" |
---|
| 168 | export SBPACKAGE_NAME SB_PACKAGE_VERSION SB_PACKAGE_RELEASE |
---|
[bf13d27] | 169 | # Build root directory |
---|
[ba8a935] | 170 | %{?buildroot:SB_BUILD_ROOT="%{buildroot}"} |
---|
| 171 | export SB_BUILD_ROOT |
---|
[bf13d27] | 172 | # The compiler flags |
---|
| 173 | %{?_targetcflags:CFLAGS_FOR_TARGET="%{_targetcflags}"} |
---|
| 174 | %{?_targetcxxflags:CXXFLAGS_FOR_TARGET="%{_targetcxxflags}"} |
---|
| 175 | export CFLAGS_FOR_TARGET |
---|
| 176 | # Default environment set up. |
---|
| 177 | LANG=C |
---|
| 178 | export LANG |
---|
| 179 | unset DISPLAY || : |
---|
| 180 | umask 022 |
---|
[8f84a6b] | 181 | cd "%{_builddir}"'''), |
---|
| 182 | '___build_shell': ('none', 'none', '%{?_buildshell:%{_buildshell}}%{!?_buildshell:/bin/sh}'), |
---|
| 183 | '___build_template': ('none', 'none', '''#!%{___build_shell} |
---|
[bf13d27] | 184 | %{___build_pre} |
---|
[8f84a6b] | 185 | %{nil}'''), |
---|
[bf13d27] | 186 | |
---|
| 187 | # Configure command |
---|
[8f84a6b] | 188 | 'configure': ('none', 'none', ''' |
---|
[bf13d27] | 189 | CFLAGS="${CFLAGS:-%optflags}" ; export CFLAGS ; |
---|
| 190 | CXXFLAGS="${CXXFLAGS:-%optflags}" ; export CXXFLAGS ; |
---|
| 191 | FFLAGS="${FFLAGS:-%optflags}" ; export FFLAGS ; |
---|
| 192 | ./configure --build=%{_build} --host=%{_host} \ |
---|
| 193 | --target=%{_target_platform} \ |
---|
| 194 | --program-prefix=%{?_program_prefix} \ |
---|
| 195 | --prefix=%{_prefix} \ |
---|
| 196 | --exec-prefix=%{_exec_prefix} \ |
---|
| 197 | --bindir=%{_bindir} \ |
---|
| 198 | --sbindir=%{_sbindir} \ |
---|
| 199 | --sysconfdir=%{_sysconfdir} \ |
---|
| 200 | --datadir=%{_datadir} \ |
---|
| 201 | --includedir=%{_includedir} \ |
---|
| 202 | --libdir=%{_libdir} \ |
---|
| 203 | --libexecdir=%{_libexecdir} \ |
---|
| 204 | --localstatedir=%{_localstatedir} \ |
---|
| 205 | --sharedstatedir=%{_sharedstatedir} \ |
---|
| 206 | --mandir=%{_mandir} \ |
---|
[8f84a6b] | 207 | --infodir=%{_infodir}''') |
---|
[bf13d27] | 208 | } |
---|
| 209 | |
---|
| 210 | class command_line: |
---|
| 211 | """Process the command line in a common way for all Tool Builder commands.""" |
---|
| 212 | |
---|
| 213 | _defaults = { 'params' : [], |
---|
| 214 | 'warn-all' : '0', |
---|
| 215 | 'quiet' : '0', |
---|
[864360e] | 216 | 'force' : '0', |
---|
[bf13d27] | 217 | 'trace' : '0', |
---|
| 218 | 'dry-run' : '0', |
---|
| 219 | 'no-clean' : '0', |
---|
| 220 | 'no-smp' : '0', |
---|
| 221 | 'rebuild' : '0' } |
---|
| 222 | |
---|
[ab8319a] | 223 | # |
---|
| 224 | # The define and if it is a path and needs conversion. |
---|
| 225 | # |
---|
| 226 | _long_opts = { '--prefix' : ('_prefix', True), |
---|
| 227 | '--prefixbase' : ('_prefixbase', True), |
---|
| 228 | '--topdir' : ('_topdir', True), |
---|
| 229 | '--configdir' : ('_configdir', True), |
---|
| 230 | '--builddir' : ('_builddir', True), |
---|
| 231 | '--sourcedir' : ('_sourcedir', True), |
---|
| 232 | '--tmppath' : ('_tmppath', True), |
---|
| 233 | '--log' : ('_logfile', False), |
---|
| 234 | '--url' : ('_url_base', False), |
---|
| 235 | '--targetcflags' : ('_targetcflags', False), |
---|
| 236 | '--targetcxxflags' : ('_targetcxxflags', False), |
---|
| 237 | '--libstdcxxflags' : ('_libstdcxxflags', False) } |
---|
[bf13d27] | 238 | |
---|
[864360e] | 239 | _long_true_opts = { '--force' : '_force', |
---|
| 240 | '--trace' : '_trace', |
---|
[bf13d27] | 241 | '--dry-run' : '_dry_run', |
---|
| 242 | '--warn-all' : '_warn_all', |
---|
| 243 | '--no-clean' : '_no_clean', |
---|
| 244 | '--no-smp' : '_no_smp', |
---|
| 245 | '--rebuild' : '_rebuild' } |
---|
| 246 | |
---|
| 247 | _target_triplets = { '--host' : '_host', |
---|
| 248 | '--build' : '_build', |
---|
| 249 | '--target' : '_target' } |
---|
| 250 | |
---|
| 251 | def _help(self): |
---|
| 252 | print '%s: [options] [args]' % (self.command_name) |
---|
[ba8a935] | 253 | print 'Source Builder, an RTEMS Tools Project (c) 2012 Chris Johns' |
---|
[bf13d27] | 254 | print 'Options and arguments:' |
---|
[864360e] | 255 | print '--force : Create directories that are not present' |
---|
[bf13d27] | 256 | print '--trace : Trace the execution (not current used)' |
---|
| 257 | print '--dry-run : Do everything but actually run the build' |
---|
| 258 | print '--warn-all : Generate warnings' |
---|
| 259 | print '--no-clean : Do not clean up the build tree' |
---|
| 260 | print '--no-smp : Run with 1 job and not as many as CPUs' |
---|
| 261 | print '--rebuild : Rebuild (not used)' |
---|
| 262 | print '--host : Set the host triplet' |
---|
| 263 | print '--build : Set the build triplet' |
---|
| 264 | print '--target : Set the target triplet' |
---|
| 265 | print '--prefix path : Tools build prefix, ie where they are installed' |
---|
| 266 | print '--prefixbase path : ' |
---|
| 267 | print '--topdir path : Top of the build tree, default is $PWD' |
---|
| 268 | print '--configdir path : Path to the configuration directory, default: ./config' |
---|
| 269 | print '--builddir path : Path to the build directory, default: ./build' |
---|
| 270 | print '--sourcedir path : Path to the source directory, default: ./source' |
---|
| 271 | print '--tmppath path : Path to the temp directory, default: ./tmp' |
---|
| 272 | print '--log file : Log file where all build out is written too' |
---|
| 273 | print '--url url : URL to look for source' |
---|
| 274 | print '--targetcflags flags : List of C flags for the target code' |
---|
| 275 | print '--targetcxxflags flags : List of C++ flags for the target code' |
---|
| 276 | print '--libstdcxxflags flags : List of C++ flags to build the target libstdc++ code' |
---|
| 277 | print '--with-<label> : Add the --with-<label> to the build' |
---|
| 278 | print '--without-<label> : Add the --without-<label> to the build' |
---|
[71b8893] | 279 | if self.optargs: |
---|
| 280 | for a in self.optargs: |
---|
| 281 | print '%-22s : %s' % (a, self.optargs[a]) |
---|
[bf13d27] | 282 | raise error.exit() |
---|
| 283 | |
---|
[71b8893] | 284 | def __init__(self, argv, optargs): |
---|
[ab8319a] | 285 | self.command_path = path.dirname(argv[0]) |
---|
[bf13d27] | 286 | if len(self.command_path) == 0: |
---|
| 287 | self.command_path = '.' |
---|
[ab8319a] | 288 | self.command_name = path.basename(argv[0]) |
---|
[bf13d27] | 289 | self.args = argv[1:] |
---|
[71b8893] | 290 | self.optargs = optargs |
---|
[bf13d27] | 291 | self.defaults = {} |
---|
| 292 | for to in command_line._long_true_opts: |
---|
[8f84a6b] | 293 | self.defaults[command_line._long_true_opts[to]] = ('none', 'none', '0') |
---|
| 294 | self.defaults['_sbdir'] = ('dir', 'required', path.shell(self.command_path)) |
---|
[bf13d27] | 295 | self._process() |
---|
| 296 | |
---|
| 297 | def __str__(self): |
---|
| 298 | def _dict(dd): |
---|
| 299 | s = '' |
---|
| 300 | ddl = dd.keys() |
---|
| 301 | ddl.sort() |
---|
| 302 | for d in ddl: |
---|
| 303 | s += ' ' + d + ': ' + str(dd[d]) + '\n' |
---|
| 304 | return s |
---|
| 305 | |
---|
| 306 | s = 'command: ' + self.command() + \ |
---|
| 307 | '\nargs: ' + str(self.args) + \ |
---|
| 308 | '\nopts:\n' + _dict(self.opts) |
---|
| 309 | |
---|
| 310 | return s |
---|
| 311 | |
---|
| 312 | def _process(self): |
---|
| 313 | |
---|
| 314 | def _process_lopt(opt, arg, long_opts, args, values = False): |
---|
| 315 | for lo in long_opts: |
---|
| 316 | if values and opt.startswith(lo): |
---|
| 317 | equals = opt.find('=') |
---|
| 318 | if equals < 0: |
---|
| 319 | if arg == len(args) - 1: |
---|
| 320 | raise error.general('missing option value: ' + lo) |
---|
| 321 | arg += 1 |
---|
| 322 | value = args[arg] |
---|
| 323 | else: |
---|
| 324 | value = opt[equals + 1:] |
---|
[4c32621] | 325 | if type(long_opts[lo]) is tuple: |
---|
| 326 | if long_opts[lo][1]: |
---|
| 327 | value = path.shell(value) |
---|
| 328 | macro = long_opts[lo][0] |
---|
| 329 | else: |
---|
| 330 | macro = long_opts[lo] |
---|
| 331 | return lo, macro, value, arg |
---|
[bf13d27] | 332 | elif opt == lo: |
---|
[4c32621] | 333 | return lo, long_opts[lo], True, arg |
---|
[bf13d27] | 334 | return None, None, None, arg |
---|
| 335 | |
---|
| 336 | self.opts = command_line._defaults |
---|
| 337 | i = 0 |
---|
| 338 | while i < len(self.args): |
---|
| 339 | a = self.args[i] |
---|
| 340 | if a.startswith('-'): |
---|
| 341 | if a.startswith('--'): |
---|
| 342 | if a.startswith('--warn-all'): |
---|
| 343 | self.opts['warn-all'] = True |
---|
| 344 | elif a == '--help': |
---|
| 345 | self._help() |
---|
| 346 | else: |
---|
| 347 | lo, macro, value, i = _process_lopt(a, i, |
---|
| 348 | command_line._long_true_opts, |
---|
| 349 | self.args) |
---|
| 350 | if lo: |
---|
[8f84a6b] | 351 | self.defaults[macro] = ('none', 'none', '1') |
---|
[bf13d27] | 352 | self.opts[lo[2:]] = '1' |
---|
| 353 | else: |
---|
| 354 | lo, macro, value, i = _process_lopt(a, i, |
---|
| 355 | command_line._long_opts, |
---|
| 356 | self.args, True) |
---|
| 357 | if lo: |
---|
[8f84a6b] | 358 | self.defaults[macro] = ('none', 'none', value) |
---|
[bf13d27] | 359 | self.opts[lo[2:]] = value |
---|
| 360 | else: |
---|
| 361 | # |
---|
| 362 | # The target triplet is 'cpu-vendor-os'. |
---|
| 363 | # |
---|
| 364 | lo, macro, value, i = _process_lopt(a, i, |
---|
| 365 | command_line._target_triplets, |
---|
| 366 | self.args, True) |
---|
| 367 | if lo: |
---|
| 368 | # |
---|
| 369 | # This is a target triplet. Run it past config.sub to make |
---|
| 370 | # make sure it is ok. |
---|
| 371 | # |
---|
| 372 | e = execute.capture_execution() |
---|
[ab8319a] | 373 | config_sub = path.join(self.command_path, |
---|
| 374 | basepath, 'config.sub') |
---|
[bf13d27] | 375 | exit_code, proc, output = e.shell(config_sub + ' ' + value) |
---|
| 376 | if exit_code == 0: |
---|
| 377 | value = output |
---|
[8f84a6b] | 378 | self.defaults[macro] = ('triplet', 'none', value) |
---|
[bf13d27] | 379 | self.opts[lo[2:]] = value |
---|
| 380 | _arch = macro + '_cpu' |
---|
| 381 | _vendor = macro + '_vendor' |
---|
| 382 | _os = macro + '_os' |
---|
| 383 | _arch_value = '' |
---|
| 384 | _vendor_value = '' |
---|
| 385 | _os_value = '' |
---|
| 386 | dash = value.find('-') |
---|
| 387 | if dash >= 0: |
---|
| 388 | _arch_value = value[:dash] |
---|
| 389 | value = value[dash + 1:] |
---|
| 390 | dash = value.find('-') |
---|
| 391 | if dash >= 0: |
---|
| 392 | _vendor_value = value[:dash] |
---|
| 393 | value = value[dash + 1:] |
---|
| 394 | if len(value): |
---|
| 395 | _os_value = value |
---|
[8f84a6b] | 396 | self.defaults[_arch] = ('none', 'none', _arch_value) |
---|
| 397 | self.defaults[_vendor] = ('none', 'none', _vendor_value) |
---|
| 398 | self.defaults[_os] = ('none', 'none', _os_value) |
---|
[71b8893] | 399 | if not lo and a not in self.optargs: |
---|
| 400 | raise error.general('invalid argument (try --help): %s' % (a)) |
---|
[bf13d27] | 401 | else: |
---|
[864360e] | 402 | if a == '-f': |
---|
| 403 | self.opts['force'] = '1' |
---|
| 404 | elif a == '-n': |
---|
[bf13d27] | 405 | self.opts['dry-run'] = '1' |
---|
| 406 | elif a == '-q': |
---|
| 407 | self.opts['quiet'] = '1' |
---|
| 408 | elif a == '-?': |
---|
| 409 | self._help() |
---|
[71b8893] | 410 | else: |
---|
| 411 | raise error.general('invalid argument (try --help): %s' % (a)) |
---|
[bf13d27] | 412 | else: |
---|
| 413 | self.opts['params'].append(a) |
---|
| 414 | i += 1 |
---|
| 415 | |
---|
| 416 | def _post_process(self, _defaults): |
---|
| 417 | if self.no_smp(): |
---|
[3cb08b5] | 418 | _defaults['_smp_mflags'] = ('none', 'none', _defaults['nil'][2]) |
---|
[8f84a6b] | 419 | if _defaults['_host'][2] == _defaults['nil'][2]: |
---|
[bf13d27] | 420 | raise error.general('host not set') |
---|
| 421 | return _defaults |
---|
| 422 | |
---|
| 423 | def expand(self, s, _defaults): |
---|
| 424 | """Simple basic expander of config file macros.""" |
---|
| 425 | mf = re.compile(r'%{[^}]+}') |
---|
| 426 | expanded = True |
---|
| 427 | while expanded: |
---|
| 428 | expanded = False |
---|
| 429 | for m in mf.findall(s): |
---|
| 430 | name = m[2:-1] |
---|
| 431 | if name in _defaults: |
---|
[8f84a6b] | 432 | s = s.replace(m, _defaults[name][2]) |
---|
[bf13d27] | 433 | expanded = True |
---|
| 434 | else: |
---|
| 435 | raise error.general('cannot process default macro: ' + m) |
---|
| 436 | return s |
---|
| 437 | |
---|
| 438 | def command(self): |
---|
[ab8319a] | 439 | return path.join(self.command_path, self.command_name) |
---|
[bf13d27] | 440 | |
---|
[864360e] | 441 | def force(self): |
---|
| 442 | return self.opts['force'] != '0' |
---|
| 443 | |
---|
[bf13d27] | 444 | def dry_run(self): |
---|
| 445 | return self.opts['dry-run'] != '0' |
---|
| 446 | |
---|
| 447 | def set_dry_run(self): |
---|
| 448 | self.opts['dry-run'] = '1' |
---|
| 449 | |
---|
| 450 | def quiet(self): |
---|
| 451 | return self.opts['quiet'] != '0' |
---|
| 452 | |
---|
| 453 | def trace(self): |
---|
| 454 | return self.opts['trace'] != '0' |
---|
| 455 | |
---|
| 456 | def warn_all(self): |
---|
| 457 | return self.opts['warn-all'] != '0' |
---|
| 458 | |
---|
| 459 | def no_clean(self): |
---|
| 460 | return self.opts['no-clean'] != '0' |
---|
| 461 | |
---|
| 462 | def no_smp(self): |
---|
| 463 | return self.opts['no-smp'] != '0' |
---|
| 464 | |
---|
| 465 | def rebuild(self): |
---|
| 466 | return self.opts['rebuild'] != '0' |
---|
| 467 | |
---|
| 468 | def params(self): |
---|
| 469 | return self.opts['params'] |
---|
| 470 | |
---|
[71b8893] | 471 | def get_arg(self, arg): |
---|
| 472 | if not arg in self.optargs: |
---|
| 473 | raise error.internal('bad arg: %s' % (arg)) |
---|
| 474 | for a in self.args: |
---|
| 475 | if a.startswith(arg): |
---|
| 476 | return a |
---|
| 477 | return None |
---|
| 478 | |
---|
[bf13d27] | 479 | def get_config_files(self, config): |
---|
[ab8319a] | 480 | # |
---|
| 481 | # Convert to shell paths and return shell paths. |
---|
| 482 | # |
---|
[8f84a6b] | 483 | # @fixme should this use a passed in set of defaults and not |
---|
| 484 | # not the initial set of values ? |
---|
| 485 | # |
---|
[ab8319a] | 486 | config = path.shell(config) |
---|
[71b8893] | 487 | if '*' in config or '?' in config: |
---|
| 488 | print config |
---|
[ab8319a] | 489 | configdir = path.dirname(config) |
---|
| 490 | configbase = path.basename(config) |
---|
[bf13d27] | 491 | if len(configbase) == 0: |
---|
| 492 | configbase = '*' |
---|
[71b8893] | 493 | if not configbase.endswith('.cfg'): |
---|
| 494 | configbase = configbase + '.cfg' |
---|
[bf13d27] | 495 | if len(configdir) == 0: |
---|
[8f84a6b] | 496 | configdir = self.expand(defaults['_configdir'][2], defaults) |
---|
[ab8319a] | 497 | configs = [] |
---|
[71b8893] | 498 | for cp in configdir.split(':'): |
---|
| 499 | hostconfigdir = path.host(cp) |
---|
| 500 | for f in glob.glob(os.path.join(hostconfigdir, configbase)): |
---|
| 501 | configs += path.shell(f) |
---|
[bf13d27] | 502 | else: |
---|
| 503 | configs = [config] |
---|
| 504 | return configs |
---|
| 505 | |
---|
| 506 | def config_files(self): |
---|
| 507 | configs = [] |
---|
| 508 | for config in self.opts['params']: |
---|
| 509 | configs.extend(self.get_config_files(config)) |
---|
| 510 | return configs |
---|
| 511 | |
---|
| 512 | def logfiles(self): |
---|
| 513 | if 'log' in self.opts: |
---|
| 514 | return self.opts['log'].split(',') |
---|
| 515 | return ['stdout'] |
---|
| 516 | |
---|
| 517 | def urls(self): |
---|
| 518 | if 'url' in self.opts: |
---|
| 519 | return self.opts['url'].split(',') |
---|
| 520 | return None |
---|
| 521 | |
---|
| 522 | def prefixbase(self): |
---|
| 523 | if 'prefixbase' in self.opts: |
---|
| 524 | return self.opts['prefixbase'] |
---|
| 525 | return None |
---|
| 526 | |
---|
[71b8893] | 527 | def load(args, optargs = None): |
---|
[bf13d27] | 528 | """ |
---|
| 529 | Copy the defaults, get the host specific values and merge them overriding |
---|
| 530 | any matching defaults, then create an options object to handle the command |
---|
| 531 | line merging in any command line overrides. Finally post process the |
---|
| 532 | command line. |
---|
| 533 | """ |
---|
| 534 | d = defaults |
---|
| 535 | overrides = None |
---|
| 536 | if os.name == 'nt': |
---|
| 537 | import windows |
---|
| 538 | overrides = windows.load() |
---|
| 539 | else: |
---|
| 540 | uname = os.uname() |
---|
| 541 | try: |
---|
| 542 | if uname[0] == 'Darwin': |
---|
| 543 | import darwin |
---|
| 544 | overrides = darwin.load() |
---|
| 545 | elif uname[0] == 'FreeBSD': |
---|
| 546 | import freebsd |
---|
| 547 | overrides = freebsd.load() |
---|
| 548 | elif uname[0] == 'Linux': |
---|
| 549 | import linux |
---|
| 550 | overrides = linux.load() |
---|
| 551 | except: |
---|
| 552 | pass |
---|
| 553 | if overrides is None: |
---|
| 554 | raise error.general('no hosts defaults found; please add') |
---|
| 555 | for k in overrides: |
---|
| 556 | d[k] = overrides[k] |
---|
[71b8893] | 557 | o = command_line(args, optargs) |
---|
[bf13d27] | 558 | for k in o.defaults: |
---|
| 559 | d[k] = o.defaults[k] |
---|
| 560 | d = o._post_process(d) |
---|
| 561 | return o, d |
---|
| 562 | |
---|
| 563 | if __name__ == '__main__': |
---|
| 564 | import sys |
---|
| 565 | try: |
---|
| 566 | _opts, _defaults = load(args = sys.argv) |
---|
| 567 | print _opts |
---|
| 568 | pprint.pprint(_defaults) |
---|
| 569 | except error.general, gerr: |
---|
| 570 | print gerr |
---|
| 571 | sys.exit(1) |
---|
| 572 | except error.internal, ierr: |
---|
| 573 | print ierr |
---|
| 574 | sys.exit(1) |
---|
| 575 | sys.exit(0) |
---|