From 2949a35176664d147e2a77e583f504772727143c Mon Sep 17 00:00:00 2001 From: Bo Peng Date: Sun, 13 Aug 2006 16:07:17 +0000 Subject: [PATCH] Add scons build system. * INSTALL.scons: instruction * development/scons/*: scons build system, qt frontend only * development/ChangeLog, status.14x, ChangeLog: bookkeeping git-svn-id: svn://svn.lyx.org/lyx/lyx-devel/branches/BRANCH_1_4_X@14650 a592a061-630c-0410-9148-cb99ea01b6c8 --- ChangeLog | 4 + INSTALL.scons | 351 +++++ development/ChangeLog | 4 + development/scons/SConstruct | 2072 ++++++++++++++++++++++++ development/scons/scons_manifest.py | 2248 +++++++++++++++++++++++++++ development/scons/scons_utils.py | 669 ++++++++ status.14x | 2 + 7 files changed, 5350 insertions(+) create mode 100644 INSTALL.scons create mode 100644 development/scons/SConstruct create mode 100644 development/scons/scons_manifest.py create mode 100644 development/scons/scons_utils.py diff --git a/ChangeLog b/ChangeLog index 6b5172eea8..20b9d1885e 100644 --- a/ChangeLog +++ b/ChangeLog @@ -1,3 +1,7 @@ +2006-08-13 Bo Peng + + * INSTALL.scons: instructions of the new scons build system. + 2006-07-13 Jean-Marc Lasgouttes * status.14x: diff --git a/INSTALL.scons b/INSTALL.scons new file mode 100644 index 0000000000..5c097c491e --- /dev/null +++ b/INSTALL.scons @@ -0,0 +1,351 @@ +========================= +Building LyX with SCons +========================= + +Aug, 2006 + + +The GNU Build System (autoconf, automake and make) has been used to build +and distribute lyx. These de facto *nix tools are readily available and +widely supported on the *nix systems, but not so under windows. They are +not necessarily easy to use and maintain (at least to non-m4 experts) +either. Because of these, a scons (http://www.scons.org) build system has +been set up as an alternative way to build lyx. As of writing, this system +only supports the qt frontends. + +This file is organized as follows: +1. General usage of scons +2. *nix systems (Linux, Solaris and Mac OSX) +3. Windows/mingw +4. Windows/cygwin +5. Windows/msvc +6. Tips and hints +7. Troubleshooting + + +1. General usage of scons +========================= + +Prerequisites: +-------------- + +* Python: + Python >= 1.5.2 is required to run scons, but Python >= 2.3 is used by + lyx itself so the newer version is needed. Python is widely + available on non-windows systems. Windows users can download and install + python from http://www.python.org. + +* SCons: + scons >= 0.96.92 is needed. You can either use a full system-wide scons + distribution or a light-weight one (called scons-local) installed along + with the lyx source tree. Both variants of scons are freely available + from http://www.scons.org. Note that LyX source may ship with scons-base + in the near future. + +* Other libraries: + These include zlib (required), qt3 (required), gettext + (optional), boost (optional), aspell (optional) and Aiksaurus + (optional). Please refer to the system-specific sections regarding the + availability and installation of them. + + +Start scons: +------------ + +The scons system resides under development/scons. You can invoke it from +either development/scons by, for example: + > cd development/scons + > scons qt_dir=d:/qt3 -j3 lyx +or from top source directory by: + > scons -f development/scons/SConstruct all + +There are three types of command line options: + * key=value are user options. They are used to tell scons which + frontend to use, whether or not use included boost libraries etc. + You can use 'scons -h' to list all of the options. + * parameters start with - or -- are scons options. Useful ones include + -j3 (with three threads) and --config=force (force reconfiguration). + * others options are targets, which are lyx objects to build. + + +User Options: +------------- + +Here I only list important options that you will likely use. Full option +list with detailed description and default value can be displayed using +command 'scons -h'. + +Components to use/build: + + * frontend=qt2: qt2 is the default, and there is no other choice + * mode=debug/release: lyx will be built under the debug or release + directory, with different default build options. + * boost=included/system/auto: whether or not use included boost, system + boost, or try to detect system boost first. Note that boost=included + is safer if system boost has a different version from the included + one. + * gettext=included/system/auto + * nls=yes/no whether or not enable natural language support. + * spell=aspell/pspell/ispell/auto: spell engine + + +Paths: Most of them will be probed if not specified. + + * qt_dir: top level directory of qt (with at least subdirectory bin + containing commands uic and moc) + * qt_lib_path: path to the qt library, use only if there is no + $qt_dir/lib + * qt_inc_path: path to qt include directory, use only if there is no + $qt_dir/include + * extra_inc_path, extra_inc_path1, extra_lib_path, extra_lib_path1: + additional paths to other libraries + * extra_bin_path: a convenient way to add an extra path to $PATH + + +Convenience options: + + * fast_start=yes/no: if true, bypass initial configuration step and use + existing src/config.h + * load_option=yes/no/opt1,opt2/-opt1,opt2: if true, load previously saved + command line options so you can run 'scons install' directly after a + long 'scons all' building command. You can load selected options using + load_option=opt1,opt2,... or exclude options using the - version of it. + * rebuild=target1,target2... By default, scons will exam all components + when you build lyx. You can free scons from some hard work and save + yourself some time by telling scons to rebuild only specified + component(s). rebuild=no, none, yes or all can be used as well. + * log_file: a log file of executed commands, default to scons_lyx.log + + +Installation options: + + * prefix: directory where lyx will be installed + * exec_dir: directory where lyx binaries will be installed. + Default to $prefix/bin + * dest_dir: if specified, install to this directory instead of $prefix. + * version_suffix=yes/no/something : if specified, this suffix will be + appended to the user data directory. + + +Compiler choice and flags: + * use_vc: use msvc instead of mingw g++ under windows + * optimization: optimization flag to use (e.g. -O2) + * CC, LINK, CPP, CXX, CCFLAGS, LINKFLAGS etc: compiler commands and + flags. Setting CCFLAGS etc will replace default flags. These variables + can be set as environment variables as well. + + +Targets: +-------- + +You can specify one or more of the following targets: + + Static libraries (names correspond to their directories): + boost, intl, support, mathed, insets, frontends, graphics, + controllers, client, qt2, lyxbase + Programs: + tex2lyx, client, lyx, all = tex2lyx + client + lyx + Installation: + po, install = all + po + Misc: + msvs_projects + +Your built targets are put into $build_dir, which is debug (mode=debug), +release (mode=release) or any name specified via build_dir=name. The +directory structure is: + $build_dir + - common: most of the intermediate files, mostly object files + - libs: all static libraries + - qt2: lyx executable built with the qt frontend + - executables: lyxclient, tex2lyx, lyx + +MSVS projects will be put to development/scons (and you should invoke +scons from there for this target). + + +A typical working sequence: +--------------------------- + + > cd development/scons + > scons qt_dir=/path/to/qt3 + (build lyx, and all needed libraries...) + > scons all -j3 + (build lyx, client and tex2lyx, options like qt_dir will be carried + over here) + > scons rebuild=lyxbase + (working on lyx_main.C, so only need to rebuild lyxbase) + > scons + (build again, only lyxbase will be rebuilt) + > scons fast_start=no --config=force + (need to regenerate src/config.h) + > scons prefix=/usr/site dest_dir=/install/dir + (lyx is built for /usr/site, but install to /install/dir) + + +2. *nix systems (Linux, Solaris and Mac OSX) +============================================ + +Proper use of extra_inc_path, qt_dir etc should solve most of the +problems. + + +3. Windows/mingw +================ + + * install mingw with the following packages: + binutils-2.16.91-...tar.gz + gcc-core-3.4.5-...tar.gz + gcc-g++-3.4.5-...tar.gz + mingw-runtime-3.9.tar.gz + mingw-utils-0.3.tar.gz + MSYS-1.0.11-...exe + msysDTK-1.0.1.exe + w32api-3.6.tar.gz + + * install the latest Qt official "open source" binary package for + Windows/Mingw (required) + + * install mingw/zlib (required): + Download zlib binaries and developer files (zlib-1.2.3-bin.zip and + zlib-1.2.3-lib.zip) from http://gnuwin32.sourceforge.net/packages/zlib.htm . + + * install iconv (optional): + Download libiconv from http://gnuwin32.sourceforge.net/packages/libiconv.htm + The complete package (without source) is recommended. + + You may also try the windows binary (libiconv-x.x.x.bin.woe32.zip) of + iconv from one of the GNU mirrors listed in http://www.gnu.org/prep/ftp.html. + + * install gettext (optional): + Download gettext from http://gnuwin32.sourceforge.net/packages/gettext.htm + The complete package (without source) is recommended. + + You may also try the windows binary (gettext-runtime-x.x.x.bin.woe32.zip + and gettext-tools-x.x.x.bin.woe32.zip) from one of the GNU mirrors + (e.g. http://mirrors.usc.edu/pub/gnu/gettext/). + + * install aspell (optional): + LyX uses aspell 0.60.4 and there is no, as of now, official windows + version. If you do not want to compile aspell from source by yourself, + your best bet is using Abdel's lyx 1.5.0svn experimental package located + at http://wiki.lyx.org/Windows/LyX150Experimental. The link to his + pre-built aspell package is http://younes.a.free.fr/Lyx-15-experimental + + * install aiksaurus (optional): + Try to build aiksaurus from source (both mingw or msvc should work), + or look for pre-built package from the lyx 1.5.0svn experimental page. + + * Open a mingw xterm, and start scons as usual. + +Note: gettext, iconv and zlib are usually decompressed to c:/mingw so no +extra_inc_path etc is needed. + + +4. Windows/cygwin +================= + +LyX should be easy to compile, but you must use the most recent cygwin +dll (version 1.5.20-1 as of July 2006) because the qt3 library in the +cygwin distribution does not work with previous versions due to broken +threading support. + +To build lyx for cygwin, you should + + * install (using the cygwin setup program) at least the following + packages and all other packages pulled in by dependencies: + + aspell gzip libiconv qt3-bin + aspell-dev jpeg libpng qt3-devel + gcc libintl libpng2 + gettext libintl1 jpeg + gettext-devel libintl2 python + + * install aiksaurus (http://aiksaurus.sourceforge.net/, optional): + There is no cygwin package for aiksaurus, so you should build it from + source. However, aiksaurus builds smoothly on cygwin. + + * run scons as you would do under linux. + +Note: cygwin/qt does not follow the usual $qt_dir/include, $qt_dir/bin, +$qt_dir/lib directory structure. For example, cygwin/qt3 uses directories +/usr/include/qt3, /usr/lib/qt3/bin and /usr/lib/qt3/lib. If these +directories can not be detected automatically, use options, for example, + qt_dir=/usr/lib/qt3 qt_inc_path=/usr/include/qt3 + + +5. Windows/msvc +=============== + +To build lyx with msvc, you should + + * install msvc + It is recommended that you use MSVC2005 Express edition which is + freely available from microsoft. + + * get windows platform SDK + Please follow the link in the MSVC webpage to download and configure. + It is important that you add SDK paths to %INCLUDE% and %LIB% in, e.g., + C:\Program Files\Microsoft Visual Studio 8\Common7\Tools\vsvars32.bat. + If you plan to use the MSVS IDE, you should also update the Visual C++ + directories in VCProjectEngine.dll.express.config, as suggested in + http://msdn.microsoft.com/vstudio/express/visualc/usingpsdk/. + + * build qt3 + - download qt3 source from trolltech (not the binary version, which + only works with mingw) + - get q../free patch for qt3 + - compile qt3 as instructed + + * download and install the official zlib library from www.zlib.org. + + * optionally install iconv, gettext, aspell, aiksaurus following + the mingw instructions. + + * start from msvc command prompt, use the use_vc option to build lyx. + You may need to use extra_inc_path etc to point to zlib paths. + + * you can use the msvs_projects target to obtain msvc project files + for each lyx component. + - go to development/scons (important) + - run + > scons [other options] msvs_projects + Note that + - The resulting project files will use scons to build lyx + - All command line options, including rebuild, can be used as usual + (when msvs invoke scons). + - To use the msvc debugger, you have to use mode=debug (default). + + +6. Tips and hints +================= + + * Using external boost libraries (install boost libraries and use + option boost=system) can speed up scons' starting time a lot, since + the boost headers will then be considered as system headers and will + not be included in the dependency tree. + + +7. Troubleshooting +================== + +When you get an error: + +Q. Some path is not found. +A, Try options such as extra_inc_path, extra_lib_path. + +Q. A test fails (failed to find zlib etc). +A. Have a look at config.log. + +Q. I get a linking error. +A. Get the command sequence from scons_lyx.log and see what could + have gone wrong. You usually only need to tweak the last linking + command. + +Q. Still can not figure it out. +A. Send an email to lyx-devel mailing list. + +Q. Feeling too impatient/adventurous to wait for list response. +A. Read SConstruct and SConscript and see what went wrong. Trust me, they + are much easier to decipher than the autoconf/m4 files. + + diff --git a/development/ChangeLog b/development/ChangeLog index e64f2dade0..0bcf7771d4 100644 --- a/development/ChangeLog +++ b/development/ChangeLog @@ -1,3 +1,7 @@ +2006-08-13 Bo Peng + + * scons/*: add scons build system + 2006-08-13 Michael Gerz * tools/mkdoclinks.sh: diff --git a/development/scons/SConstruct b/development/scons/SConstruct new file mode 100644 index 0000000000..3c4aacfd1f --- /dev/null +++ b/development/scons/SConstruct @@ -0,0 +1,2072 @@ +# vi:filetype=python:expandtab:tabstop=4:shiftwidth=4 +# +# file SConstruct +# +# This file is part of LyX, the document processor. +# Licence details can be found in the file COPYING. +# +# \author Bo Peng +# Full author contact details are available in file CREDITS. +# +# This is a scons based building system for lyx, please refer +# to INSTALL.scons for detailed instructions. +# + +import os, sys, copy, cPickle, glob + +# scons_utils.py defines a few utility function +sys.path.append('config') +import scons_utils as utils +# import all file lists +from scons_manifest import * + +#---------------------------------------------------------- +# Required runtime environment +#---------------------------------------------------------- + +# scons asks for 1.5.2, lyx requires 2.3 +EnsurePythonVersion(2, 3) +# Please use at least 0.96.92 (not 0.96.1) +EnsureSConsVersion(0, 96) +# also check for minor version number for scons 0.96 +from SCons import __version__ +version = map(int, __version__.split('.')) +if version[0] == 0 and version[1] == 96 and version[2] < 92: + print "Scons >= 0.96.92 is required." + Exit(1) + +# determine where I am ... +# +# called as 'cd development/scons; scons' +if os.path.isfile('SConstruct'): + top_src_dir = '../..' + scons_dir = '.' +# called as 'scons -f development/scons/SConstruct' +else: + top_src_dir = '.' + scons_dir = 'development/scons' + + +#---------------------------------------------------------- +# Global definitions +#---------------------------------------------------------- + +# some global settings +# +package_version = '1.4.3svn' +boost_version = '1_32' + +devel_version = True +default_build_mode = 'debug' + +package = 'lyx' +package_bugreport = 'lyx-devel@lists.lyx.org' +package_name = 'LyX' +package_tarname = 'lyx' +package_string = '%s %s' % (package_name, package_version) + +# various cache/log files +default_log_file = 'scons_lyx.log' +env_cache_file = 'env.cache' + + +#---------------------------------------------------------- +# platform dependent settings +#---------------------------------------------------------- + +if os.name == 'nt': + platform_name = 'win32' + default_frontend = 'qt2' + default_prefix = 'c:/program files/lyx' + default_with_x = False + default_packaging_method = 'windows' +elif os.name == 'posix' and sys.platform != 'cygwin': + platform_name = sys.platform + default_frontend = 'qt2' + default_prefix = '/usr/local' + default_with_x = True + default_packaging_method = 'posix' +elif os.name == 'posix' and sys.platform == 'cygwin': + platform_name = 'cygwin' + default_frontend = 'qt2' + default_prefix = '/usr' + default_with_x = True + default_packaging_method = 'posix' +elif os.name == 'darwin': + platform_name = 'macosx' + default_frontend = 'qt2' + # FIXME: macOSX default prefix? + default_prefix = '.' + default_with_x = False + default_packaging_method = 'macosx' +else: # unsupported system, assume posix behavior + platform_name = 'others' + default_frontend = 'qt2' + default_prefix = '.' + default_with_x = True + default_packaging_method = 'posix' + +#--------------------------------------------------------- +# Handling options +#---------------------------------------------------------- +# +# You can set perminant default values in config.py +if os.path.isfile('config.py'): + print "Getting options from config.py..." + print open('config.py').read() + +opts = Options(['config.py']) +opts.AddOptions( + # frontend + EnumOption('frontend', 'Main GUI', default_frontend, + allowed_values = ('qt2') ), + # debug or release build + EnumOption('mode', 'Building method', default_build_mode, + allowed_values = ('debug', 'release') ), + # boost libraries + EnumOption('boost', + 'Use included, system boost library, or try sytem boost first.', + 'auto', allowed_values = ( + 'auto', # detect boost, if not found, use included + 'included', # always use included boost + 'system', # always use system boost, fail if can not find + ) ), + # + EnumOption('gettext', + 'Use included, system gettext library, or try sytem gettext first', + 'auto', allowed_values = ( + 'auto', # detect gettext, if not found, use included + 'included', # always use included gettext + 'system', # always use system gettext, fail if can not find + ) ), + # + EnumOption('spell', 'Choose spell checker to use.', 'auto', + allowed_values = ('aspell', 'pspell', 'ispell', 'auto', 'no') ), + # packaging method + EnumOption('packaging', 'Packaging method to use.', default_packaging_method, + allowed_values = ('windows', 'posix', 'macosx')), + # + BoolOption('fast_start', 'Whether or not use cached tests and keep current config.h', True), + # No precompiled header support (too troublesome to make it work for msvc) + # BoolOption('pch', 'Whether or not use pch', False), + # enable assertion, (config.h has ENABLE_ASSERTIOS + BoolOption('assertions', 'Use assertions', True), + # enable warning, (config.h has WITH_WARNINGS) + # default to False since MSVC does not have #warning + BoolOption('warnings', 'Use warnings', False), + # config.h define _GLIBCXX_CONCEPT_CHECKS + # Note: for earlier version of gcc (3.3) define _GLIBCPP_CONCEPT_CHECKS + BoolOption('concept_checks', 'Enable concept checks', True), + # + BoolOption('nls', 'Whether or not use native language support', True), + # + BoolOption('profiling', 'Whether or not enable profiling', False), + # config.h define _GLIBCXX_DEBUG and _GLIBCXX_DEBUG_PEDANTIC + BoolOption('stdlib_debug', 'Whether or not turn on stdlib debug', False), + # using x11? + BoolOption('X11', 'Use x11 windows system', default_with_x), + # use MS VC++ to build lyx + BoolOption('use_vc', 'Use MS VC++ to build lyx (cl.exe will be probed)', None), + # + PathOption('qt_dir', 'Path to qt directory', None), + # + PathOption('qt_inc_path', 'Path to qt include directory', None), + # + PathOption('qt_lib_path', 'Path to qt library directory', None), + # extra include and libpath + PathOption('extra_inc_path', 'Extra include path', None), + # + PathOption('extra_lib_path', 'Extra library path', None), + # + PathOption('extra_bin_path', 'A convenient way to add a path to $PATH', None), + # + PathOption('extra_inc_path1', 'Extra include path', None), + # + PathOption('extra_lib_path1', 'Extra library path', None), + # rebuild only specifed, comma separated targets + ('rebuild', '''rebuild only specifed, comma separated targets. + yes or all (default): rebuild everything + no or none: rebuild nothing (usually used for installation) + comp1,comp2,...: rebuild specified targets''', None), + # can be set to a non-existing directory + ('prefix', 'install architecture-independent files in PREFIX', default_prefix), + # build directory, will use $mode if not set + ('build_dir', 'Build directory', None), + # version suffix + ('version_suffix', 'install lyx as lyx-suffix', None), + # how to load options + ('load_option', '''load option from previous scons run. option can be + yes (default): load all options + no: do not load any option + opt1,opt2: load specified options + -opt1,opt2: load all options other than specified ones''', 'yes'), + # + ('optimization', 'optimization CCFLAGS option.', None), + # + PathOption('exec_prefix', 'install architecture-independent executable files in PREFIX', None), + # log file + ('logfile', 'save commands (not outputs) to logfile', default_log_file), + # provided for backward compatibility + ('dest_dir', 'install to DESTDIR. (Provided for backward compatibility only)', None), + # environment variable can be set as options. + ('DESTDIR', 'install to DESTDIR', None), + ('CC', 'replace default $CC', None), + ('LINK', 'replace default $LINK', None), + ('CPP', 'replace default $CPP', None), + ('CXX', 'replace default $CXX', None), + ('CXXCPP', 'replace default $CXXCPP', None), + ('CCFLAGS', 'replace default $CCFLAGS', None), + ('CPPFLAGS', 'replace default $CPPFLAGS', None), + ('LINKFLAGS', 'replace default $LINKFLAGS', None), +) + +# allowed options +all_options = [x.key for x in opts.options] + +# copied from SCons/Options/BoolOption.py +# We need to use them before a boolean ARGUMENTS option is available +# in env as bool. +true_strings = ('y', 'yes', 'true', 't', '1', 'on' , 'all' ) +false_strings = ('n', 'no', 'false', 'f', '0', 'off', 'none') + +# whether or not use current config.h, and cached tests +# +# if fast_start=yes (default), load variables from env_cache_file +if (not ARGUMENTS.has_key('fast_start') or \ + ARGUMENTS['fast_start'] in true_strings) \ + and os.path.isfile(env_cache_file): + fast_start = True + cache_file = open(env_cache_file) + env_cache = cPickle.load(cache_file) + cache_file.close() + print '------------ fast_start mode --------------------' + print ' Use cached test results and current config.h' + print ' use fast_start=no to override' + print +else: + fast_start = False + env_cache = {} + +# if load_option=yes (default), load saved comand line options +# +# This option can take value yes/no/opt1,opt2/-opt1,opt2 +# and tries to be clever in choosing options to load +if (not ARGUMENTS.has_key('load_option') or \ + ARGUMENTS['load_option'] not in false_strings) \ + and os.path.isfile(env_cache_file): + cache_file = open(env_cache_file) + opt_cache = cPickle.load(cache_file)['arg_cache'] + cache_file.close() + # import cached options, but we should ignore qt_dir when frontend changes + if ARGUMENTS.has_key('frontend') and opt_cache.has_key('frontend') \ + and ARGUMENTS['frontend'] != opt_cache['frontend'] \ + and opt_cache.has_key('qt_dir'): + opt_cache.pop('qt_dir') + # some options will require full rebuild + # these are in general things that will change config.h + for arg in ['version_suffix', 'nls', 'boost', 'spell']: + if ARGUMENTS.has_key(arg) and ((not opt_cache.has_key(arg)) or \ + ARGUMENTS[arg] != opt_cache[arg]): + if fast_start: + print " ** fast_start is disabled because of the change of option", arg + print + fast_start = False + # and we do not cache some options (dest_dir is obsolete) + for arg in ['fast_start', 'load_option', 'dest_dir']: + if opt_cache.has_key(arg): + opt_cache.pop(arg) + # remove obsolete cached keys (well, SConstruct is evolving. :-) + for arg in opt_cache.keys(): + if arg not in all_options: + print 'Option %s is obsolete, do not load it' % arg + opt_cache.pop(arg) + # now, if load_option=opt1,opt2 or -opt1,opt2 + if ARGUMENTS.has_key('load_option') and \ + ARGUMENTS['load_option'] not in true_strings + false_strings: + # if -opt1,opt2 is specified, do not load these options + if ARGUMENTS['load_option'][0] == '-': + for arg in ARGUMENTS['load_option'][1:].split(','): + if opt_cache.has_key(arg): + opt_cache.pop(arg) + # if opt1,opt2 is specified, only load specified options + else: + args = ARGUMENTS['load_option'].split(',') + for arg in opt_cache.keys(): + if arg not in args: + opt_cache.pop(arg) + # now restore options as if entered from command line + for key in opt_cache.keys(): + if not ARGUMENTS.has_key(key): + ARGUMENTS[key] = opt_cache[key] + print "Restoring cached option %s=%s" % (key, ARGUMENTS[key]) + print + +# check if there is unused (or misspelled) argument +for arg in ARGUMENTS.keys(): + if arg not in all_options: + import textwrap + print "Unknown option '%s'... exiting." % arg + print + print "Available options are (check 'scons -help' for details):" + print ' ' + '\n '.join(textwrap.wrap(', '.join(all_options))) + Exit(1) + +# save arguments +env_cache['arg_cache'] = ARGUMENTS + + +#--------------------------------------------------------- +# Setting up environment +#--------------------------------------------------------- + +# I do not really like ENV=os.environ, but you may add it +# here if you experience some environment related problem +env = Environment(options = opts) + +# set individual variables since I do not really like ENV = os.environ +env['ENV']['PATH'] = os.environ.get('PATH') +env['ENV']['HOME'] = os.environ.get('HOME') +# these are defined for MSVC +env['ENV']['LIB'] = os.environ.get('LIB') +env['ENV']['INCLUDE'] = os.environ.get('INCLUDE') + +# for simplicity, use var instead of env[var] +frontend = env['frontend'] +prefix = env['prefix'] +mode = env['mode'] + +if platform_name == 'win32': + if env.has_key('use_vc'): + use_vc = env['use_vc'] + if WhereIs('cl.exe') is None: + print "cl.exe is not found. Are you using the MSVC environment?" + Exit(2) + elif WhereIs('cl.exe') is not None: + use_vc = True + else: + use_vc = False +else: + use_vc = False + +# lyx will be built to $build/build_dir so it is possible +# to build multiple build_dirs using the same source +# $mode can be debug or release +if env.has_key('build_dir') and env['build_dir'] is not None: + # create the directory if needed + if not os.path.isdir(env['build_dir']): + try: + os.makedirs(env['build_dir']) + except: + pass + if not os.path.isdir(env['build_dir']): + print 'Can not create directory', env['build_dir'] + Exit(3) + env['BUILDDIR'] = env['build_dir'] +else: + # Determine the name of the build $mode + env['BUILDDIR'] = '#' + mode + +# all built libraries will go to build_dir/libs +# (This is different from the make file approach) +env['LOCALLIBPATH'] = '$BUILDDIR/libs' +env.AppendUnique(LIBPATH = ['$LOCALLIBPATH']) + + +# Here is a summary of variables defined in env +# 1. defined options +# 2. undefined options with a non-None default value +# 3. compiler commands and flags like CCFLAGS. +# MSGFMT used to process po files +# 4. Variables that will be used to replace variables in some_file.in +# src/support/package.C.in: +# TOP_SRCDIR, LOCALEDIR, LYX_DIR, PROGRAM_SUFFIX +# lib/lyx2lyx/lyx2lyx_version.py.in +# PACKAGE_VERSION +# src/version.C.in +# PACKAGE_VERSION, VERSION_INFO + +# full path name is used to build msvs project files +# and to replace TOP_SRCDIR in package.C +env['TOP_SRCDIR'] = Dir(top_src_dir).abspath +# needed by src/version.C.in => src/version.C +env['PACKAGE_VERSION'] = package_version + +# determine share_dir etc +packaging_method = env.get('packaging') +if packaging_method == 'windows': + share_dir = 'Resources' + man_dir = 'Resources/man/man1' + locale_dir = 'Resources/locale' + default_prefix = 'c:/program files/lyx' +else: + share_dir = 'share/lyx' + man_dir = 'man/man1' + locale_dir = 'share/locale' + default_prefix = '/usr/local/' + +# install to default_prefix by default +# program suffix: can be yes, or a string +if env.has_key('version_suffix'): + if env['version_suffix'] in true_strings: + program_suffix = package_version + elif env['version_suffix'] in false_strings: + program_suffix = '' + else: + program_suffix = env['version_suffix'] +else: + program_suffix = '' +# used by package.C.in +env['PROGRAM_SUFFIX'] = program_suffix + +# whether or not add suffix to file and directory names +add_suffix = packaging_method != 'windows' +# LYX_DIR are different (used in package.C.in) +if add_suffix: + env['LYX_DIR'] = Dir(os.path.join(prefix, share_dir + program_suffix)).abspath +else: + env['LYX_DIR'] = Dir(os.path.join(prefix, share_dir)).abspath +# we need absolute path for package.C +env['LOCALEDIR'] = Dir(os.path.join(prefix, locale_dir)).abspath + + +#--------------------------------------------------------- +# Setting building environment (Tools, compiler flags etc) +#--------------------------------------------------------- + +# Since Tool('mingw') will reset CCFLAGS etc, this should be +# done before getEnvVariable +if platform_name == 'win32': + if use_vc: + env.Tool('msvc') + env.Tool('mslink') + else: + env.Tool('mingw') + env.AppendUnique(CPPPATH = ['#c:/MinGW/include']) + +# we differentiate between hard-coded options and default options +# hard-coded options are required and will always be there +# default options can be replaced by enviromental variables or command line options +CCFLAGS_required = [] +LINKFLAGS_required = [] +CCFLAGS_default = [] + +# under windows, scons is confused by .C/.c and uses gcc instead of +# g++. I am forcing the use of g++ here. This is expected to change +# after lyx renames all .C files to .cpp +# +# save the old c compiler and CCFLAGS (used by libintl) +C_COMPILER = env.subst('$CC') +C_CCFLAGS = env.subst('$CCFLAGS').split() +# if we use ms vc, the commands are fine (cl.exe and link.exe) +if use_vc: + # /TP treat all source code as C++ + # C4819: The file contains a character that cannot be represented + # in the current code page (number) + # C4996: foo was decleared deprecated + CCFLAGS_required.extend(['/TP', '/EHsc']) + CCFLAGS_default.extend(['/wd4819', '/wd4996', '/nologo']) +else: + if env.has_key('CXX') and env['CXX']: + env['CC'] = env.subst('$CXX') + env['LINK'] = env.subst('$CXX') + else: + env['CC'] = 'g++' + env['LINK'] = 'g++' + +# for debug/release mode +if env.has_key('optimization') and env['optimization'] is not None: + # if user supplies optimization flags, use it anyway + CCFLAGS_required.extend(env['optimization'].split()) + # and do not use default + set_default_optimization_flags = False +else: + set_default_optimization_flags = True + +if mode == 'debug': + if use_vc: + CCFLAGS_required.append('/Zi') + LINKFLAGS_required.extend(['/debug', '/map']) + else: + CCFLAGS_required.append('-g') + CCFLAGS_default.append('-O') +elif mode == 'release' and set_default_optimization_flags: + if use_vc: + CCFLAGS_default.append('/O2') + else: + CCFLAGS_default.append('-O2') + +# msvc uses separate tools for profiling +if env.has_key('profiling') and env['profiling']: + if use_vc: + print 'Visual C++ does not use profiling options' + else: + CCFLAGS_required.append('-pg') + LINKFLAGS_required.append('-pg') + +if env.has_key('warnings') and env['warnings']: + if use_vc: + CCFLAGS_default.append('/W2') + else: + # Note: autotools detect gxx version and pass -W for 3.x + # and -Wextra for other versions of gcc + CCFLAGS_default.append('-Wall') + +# Now, set the variables as follows: +# 1. if command line option exists: replace default +# 2. then if s envronment variable exists: replace default +# 3. set variable to required + default +def setEnvVariable(env, name, required = None, default = None, split = True): + ''' env: environment to set variable + name: variable + required: hardcoded options + default: default options that can be replaced by command line or + environment variables + split: whether or not split obtained variable like '-02 -g' + ''' + # first try command line argument (override environment settings) + if ARGUMENTS.has_key(name): + default = ARGUMENTS[name] + if split: + default = default.split() + # then use environment default + elif os.environ.has_key(name): + print "Acquiring varaible %s from system environment: %s" % (name, os.environ[name]) + default = os.environ[name] + if split: + default = default.split() + # set variable + if required is not None: + env[name] = required + if default is not None: + if env.has_key(name) and env[name] != default: + env[name] += default + else: + env[name] = default + +setEnvVariable(env, 'DESTDIR', split=False) +setEnvVariable(env, 'CC') +setEnvVariable(env, 'LINK') +setEnvVariable(env, 'CPP') +setEnvVariable(env, 'CXX') +setEnvVariable(env, 'CXXCPP') +setEnvVariable(env, 'CCFLAGS', CCFLAGS_required, CCFLAGS_default) +setEnvVariable(env, 'CXXFLAGS') +setEnvVariable(env, 'CPPFLAGS') +setEnvVariable(env, 'LINKFLAGS', LINKFLAGS_required) + +# if DESTDIR is not set... +if env.has_key('dest_dir'): + print "This option is obsolete. Please use DESTDIR instead." + env['DESTDIR'] = env['dest_dir'] + + +#--------------------------------------------------------- +# Frontend related variables (QTDIR etc) +#--------------------------------------------------------- + +if env.has_key('qt_dir') and env['qt_dir']: + env['QTDIR'] = env['qt_dir'] +elif os.path.isdir(os.environ.get('QTDIR', '/usr/lib/qt-3.3')): + env['QTDIR'] = os.environ.get('QTDIR', '/usr/lib/qt-3.3') + +# if there is a valid QTDIR, set path for lib and bin directories +if env.has_key('QTDIR'): + # add path to the qt tools + if os.path.isdir(os.path.join(env['QTDIR'], 'lib')): + env.AppendUnique(LIBPATH = [os.path.join(env['QTDIR'], 'lib')]) + # set environment so that moc etc can be found even if its path is not set properly + if os.path.isdir(os.path.join(env['QTDIR'], 'bin')): + os.environ['PATH'] += os.pathsep + os.path.join(env['QTDIR'], 'bin') + env.PrependENVPath('PATH', os.path.join(env['QTDIR'], 'bin')) + +# frontend name is qt2, but we are looking for qt3 libs +frontend_lib = 'qt3' +if env.has_key('qt_lib_path') and env['qt_lib_path']: + qt_lib_path = env.subst('$qt_lib_path') +elif env.has_key('QTDIR') and os.path.isdir(os.path.join(env.subst('$QTDIR'), 'lib')): + qt_lib_path = env.subst('$QTDIR/lib') +# this is the path for cygwin. +elif os.path.isdir(os.path.join('/usr/lib/', frontend_lib, 'lib')): + qt_lib_path = '/usr/lib/%s/lib' % frontend_lib +else: + print "Qt library directory is not found. Please specify it using qt_lib_path" + Exit(1) +env.AppendUnique(LIBPATH = [qt_lib_path]) +# qt4 seems to be using pkg_config +env.PrependENVPath('PKG_CONFIG_PATH', qt_lib_path) + +if env.has_key('qt_inc_path') and env['qt_inc_path']: + qt_inc_path = env['qt_inc_path'] +elif env.has_key('QTDIR') and os.path.isdir(os.path.join(env.subst('$QTDIR'), 'include')): + qt_inc_path = '$QTDIR/include' +# this is the path for cygwin. +elif os.path.isdir('/usr/include/' + frontend_lib): + qt_inc_path = '/usr/include/' + frontend_lib +else: + print "Qt include directory not found. Please specify it using qt_inc_path" + Exit(1) +# Note that this CPPPATH is for testing only +# it will be removed before calling SConscript +env['CPPPATH'] = [qt_inc_path] + +# +# extra_inc_path and extra_lib_path +# +extra_inc_paths = [] +if env.has_key('extra_inc_path') and env['extra_inc_path']: + extra_inc_paths.append(env['extra_inc_path']) +if env.has_key('extra_lib_path') and env['extra_lib_path']: + env.AppendUnique(LIBPATH = [env['extra_lib_path']]) +if env.has_key('extra_inc_path1') and env['extra_inc_path1']: + extra_inc_paths.append(env['extra_inc_path1']) +if env.has_key('extra_lib_path1') and env['extra_lib_path1']: + env.AppendUnique(LIBPATH = [env['extra_lib_path1']]) +if env.has_key('extra_bin_path') and env['extra_bin_path']: + # only the first one is needed (a scons bug?) + os.environ['PATH'] += os.pathsep + env['extra_bin_path'] + env.PrependENVPath('PATH', env['extra_bin_path']) +# extra_inc_paths will be used later by intlenv etc +env.AppendUnique(CPPPATH = extra_inc_paths) + + +#---------------------------------------------------------- +# Autoconf business +#---------------------------------------------------------- + +conf = Configure(env, + custom_tests = { + 'CheckPkgConfig' : utils.checkPkgConfig, + 'CheckPackage' : utils.checkPackage, + 'CheckMkdirOneArg' : utils.checkMkdirOneArg, + 'CheckSelectArgType' : utils.checkSelectArgType, + 'CheckBoostLibraries' : utils.checkBoostLibraries, + 'CheckCommand' : utils.checkCommand, + 'CheckCXXGlobalCstd' : utils.checkCXXGlobalCstd, + 'CheckLC_MESSAGES' : utils.checkLC_MESSAGES, + 'CheckIconvConst' : utils.checkIconvConst, + } +) + +# pkg-config? (if not, we use hard-coded options) +if not fast_start: + if conf.CheckPkgConfig('0.15.0'): + env['HAS_PKG_CONFIG'] = True + else: + print 'pkg-config >= 0.1.50 is not found' + env['HAS_PKG_CONFIG'] = False + env_cache['HAS_PKG_CONFIG'] = env['HAS_PKG_CONFIG'] +else: + env['HAS_PKG_CONFIG'] = env_cache['HAS_PKG_CONFIG'] + +# zlib? This is required. (fast_start assumes the existance of zlib) +if not fast_start: + if (not use_vc and not conf.CheckLibWithHeader('z', 'zlib.h', 'C')) \ + or (use_vc and not conf.CheckLibWithHeader('zdll', 'zlib.h', 'C')): + print 'Did not find zdll.lib or zlib.h, exiting!' + Exit(1) + +# qt libraries? +if not fast_start: + # + # qt3 does not use pkg_config + if frontend == 'qt2': + if not conf.CheckLibWithHeader('qt-mt', 'qapp.h', 'c++', 'QApplication qapp();'): + print 'Did not find qt libraries, exiting!' + Exit(1) + +# now, if msvc2005 is used, we will need that QT_LIB_PATH/QT_LIB.manifest file +if use_vc: + if mode == 'debug': + manifest = os.path.join(qt_lib_path, 'QtGuid4.dll.manifest') + else: + manifest = os.path.join(qt_lib_path, 'QtGui4.dll.manifest') + if os.path.isfile(manifest): + env['LINKCOM'] = [env['LINKCOM'], 'mt.exe /MANIFEST %s /outputresource:$TARGET;1' % manifest] + +# check socket libs +if not fast_start: + socket_libs = [] + if conf.CheckLib('socket'): + socket_libs.append('socket') + # nsl is the network services library and provides a + # transport-level interface to networking services. + if conf.CheckLib('nsl'): + socket_libs.append('nsl') + env_cache['SOCKET_LIBS'] = socket_libs +else: + socket_libs = env_cache['SOCKET_LIBS'] + +# check available boost libs (since lyx1.4 does not use iostream) +boost_libs = [] +for lib in ['signals', 'regex', 'filesystem', 'iostreams']: + if os.path.isdir(os.path.join(top_src_dir, 'boost', 'libs', lib)): + boost_libs.append(lib) + +if not fast_start: + # check boost libraries + boost_opt = ARGUMENTS.get('boost', 'auto') + # check for system boost + lib_paths = env['LIBPATH'] + ['/usr/lib', '/usr/local/lib'] + inc_paths = env['CPPPATH'] + ['/usr/include', '/usr/local/include'] + # default to $BUILDDIR/libs (use None since this path will be added anyway) + boost_libpath = None + # here I assume that all libraries are in the same directory + if boost_opt == 'included': + boost_libraries = ['included_boost_%s' % x for x in boost_libs] + included_boost = True + env['BOOST_INC_PATH'] = '$TOP_SRCDIR/boost' + elif boost_opt == 'auto': + res = conf.CheckBoostLibraries(boost_libs, lib_paths, inc_paths, boost_version, mode == 'debug') + # if not found, use local boost + if res[0] is None: + boost_libraries = ['included_boost_%s' % x for x in boost_libs] + included_boost = True + env['BOOST_INC_PATH'] = '$TOP_SRCDIR/boost' + else: + included_boost = False + (boost_libraries, boost_libpath, env['BOOST_INC_PATH']) = res + elif boost_opt == 'system': + res = conf.CheckBoostLibraries(boost_libs, lib_paths, inc_paths, boost_version, mode == 'debug') + if res[0] is None: + print "Can not find system boost libraries with version %s " % boost_version + print "Please supply a path through extra_lib_path and try again." + print "Or use boost=included to use included boost libraries." + Exit(2) + else: + included_boost = False + (boost_libraries, boost_libpath, env['BOOST_INC_PATH']) = res + env_cache['BOOST_LIBRARIES'] = boost_libraries + env_cache['INCLUDED_BOOST'] = included_boost + env_cache['BOOST_INC_PATH'] = env['BOOST_INC_PATH'] + env_cache['BOOST_LIBPATH'] = boost_libpath +else: + boost_libraries = env_cache['BOOST_LIBRARIES'] + included_boost = env_cache['INCLUDED_BOOST'] + env['BOOST_INC_PATH'] = env_cache['BOOST_INC_PATH'] + boost_libpath = env_cache['BOOST_LIBPATH'] + +if boost_libpath is not None: + env.AppendUnique(LIBPATH = [boost_libpath]) + + +env['ENABLE_NLS'] = env['nls'] + +if not fast_start: + if not env['ENABLE_NLS']: + intl_libs = [] + included_gettext = False + else: + # check gettext libraries + gettext_opt = ARGUMENTS.get('gettext', 'auto') + # check for system gettext + succ = False + if gettext_opt in ['auto', 'system']: + if conf.CheckLib('intl'): + included_gettext = False + intl_libs = ['intl'] + succ = True + else: # no found + if gettext_opt == 'system': + print "Can not find system gettext library" + print "Please supply a path through extra_lib_path and try again." + print "Or use gettext=included to use included gettext libraries." + Exit(2) + # now, auto and succ = false, or gettext=included + if not succ: + # we do not need to set LIBPATH now. + included_gettext = True + intl_libs = ['included_intl'] + env_cache['INCLUDED_GETTEXT'] = included_gettext + env_cache['INTL_LIBS'] = intl_libs +else: + included_gettext = env_cache['INCLUDED_GETTEXT'] + intl_libs = env_cache['INTL_LIBS'] + +# +# check for msgfmt command +if not fast_start: + env['MSGFMT'] = conf.CheckCommand('msgfmt') + env_cache['MSGFMT'] = env['MSGFMT'] +else: + env['MSGFMT'] = env_cache['MSGFMT'] + +# check uic and moc commands for qt frontends +if not fast_start: + if frontend[:2] == 'qt' and (conf.CheckCommand('uic') == None \ + or conf.CheckCommand('moc') == None): + print 'uic or moc command is not found for frontend', frontend + Exit(1) + +# +# Customized builders +# +# install customized builders +env['BUILDERS']['substFile'] = Builder(action = utils.env_subst) + + +#---------------------------------------------------------- +# Generating config.h +#---------------------------------------------------------- +aspell_lib = 'aspell' +# assume that we use aspell, aspelld compiled for msvc +if platform_name == 'win32' and mode == 'debug' and use_vc: + aspell_lib = 'aspelld' + +# check the existence of config.h +config_h = os.path.join(env.Dir('$BUILDDIR/common').path, 'config.h') +boost_config_h = os.path.join(env.Dir('$BUILDDIR/boost').path, 'config.h') +if not fast_start or not os.path.isfile(boost_config_h) \ + or not os.path.isfile(config_h): + # + print "Creating %s..." % boost_config_h + # + utils.createConfigFile(conf, + config_file = boost_config_h, + config_pre = '''/* boost/config.h. Generated by SCons. */ + +/* -*- C++ -*- */ +/* +* \file config.h +* This file is part of LyX, the document processor. +* Licence details can be found in the file COPYING. +* +* This is the compilation configuration file for LyX. +* It was generated by scon. +* You might want to change some of the defaults if something goes wrong +* during the compilation. +*/ + +#ifndef _BOOST_CONFIG_H +#define _BOOST_CONFIG_H +''', + headers = [ + ('ostream', 'HAVE_OSTREAM', 'cxx'), + ('locale', 'HAVE_LOCALE', 'cxx'), + ('sstream', 'HAVE_SSTREAM', 'cxx'), + #('newapis.h', 'HAVE_NEWAPIS_H', 'c'), + ], + custom_tests = [ + (env.has_key('assertions') and env['assertions'], + 'ENABLE_ASSERTIONS', + 'Define if you want assertions to be enabled in the code' + ), + ], + config_post = ''' + +#if defined(HAVE_OSTREAM) && defined(HAVE_LOCALE) && defined(HAVE_SSTREAM) +# define USE_BOOST_FORMAT 1 +#else +# define USE_BOOST_FORMAT 0 +#endif + +#if !defined(ENABLE_ASSERTIONS) +# define BOOST_DISABLE_ASSERTS 1 +#endif +#define BOOST_ENABLE_ASSERT_HANDLER 1 + +#define BOOST_DISABLE_THREADS 1 +#define BOOST_NO_WREGEX 1 +#define BOOST_NO_WSTRING 1 + +#ifdef __CYGWIN__ +# define BOOST_POSIX 1 +#endif + +#define BOOST_ALL_NO_LIB 1 + +#if defined(HAVE_NEWAPIS_H) +# define WANT_GETFILEATTRIBUTESEX_WRAPPER 1 +#endif + +#endif +''' + ) + # + print "\nGenerating %s..." % config_h + + # AIKSAURUS_H_LOCATION + if (conf.CheckCXXHeader("Aiksaurus.h")): + aik_location = '' + elif (conf.CheckCXXHeader("Aiksaurus/Aiksaurus.h")): + aik_location = '' + else: + aik_location = '' + + # determine headers to use + spell_opt = ARGUMENTS.get('spell', 'auto') + env['USE_ASPELL'] = False + env['USE_PSPELL'] = False + env['USE_ISPELL'] = False + if spell_opt in ['auto', 'aspell'] and conf.CheckLib(aspell_lib): + spell_engine = 'USE_ASPELL' + elif spell_opt in ['auto', 'pspell'] and conf.CheckLib('pspell'): + spell_engine = 'USE_PSPELL' + elif spell_opt in ['auto', 'ispell'] and conf.CheckLib('ispell'): + spell_engine = 'USE_ISPELL' + else: + spell_engine = None + + if spell_engine is not None: + env[spell_engine] = True + else: + if spell_opt == 'auto': + print "Warning: Can not locate any spell checker" + elif spell_opt != 'no': + print "Warning: Can not locate specified spell checker:", spell_opt + Exit(1) + + # check arg types of select function + (select_arg1, select_arg234, select_arg5) = conf.CheckSelectArgType() + + # + # create config.h + result = utils.createConfigFile(conf, + config_file = config_h, + config_pre = '''/* config.h. Generated by SCons. */ + +/* -*- C++ -*- */ +/* +* \file config.h +* This file is part of LyX, the document processor. +* Licence details can be found in the file COPYING. +* +* This is the compilation configuration file for LyX. +* It was generated by scon. +* You might want to change some of the defaults if something goes wrong +* during the compilation. +*/ + +#ifndef _CONFIG_H +#define _CONFIG_H +''', + headers = [ + ('io.h', 'HAVE_IO_H', 'c'), + ('limits.h', 'HAVE_LIMITS_H', 'c'), + ('locale.h', 'HAVE_LOCALE_H', 'c'), + ('process.h', 'HAVE_PROCESS_H', 'c'), + ('stdlib.h', 'HAVE_STDLIB_H', 'c'), + ('sys/stat.h', 'HAVE_SYS_STAT_H', 'c'), + ('sys/time.h', 'HAVE_SYS_TIME_H', 'c'), + ('sys/types.h', 'HAVE_SYS_TYPES_H', 'c'), + ('sys/utime.h', 'HAVE_SYS_UTIME_H', 'c'), + ('sys/socket.h', 'HAVE_SYS_SOCKET_H', 'c'), + ('unistd.h', 'HAVE_UNISTD_H', 'c'), + ('utime.h', 'HAVE_UTIME_H', 'c'), + ('direct.h', 'HAVE_DIRECT_H', 'c'), + ('istream', 'HAVE_ISTREAM', 'cxx'), + ('ios', 'HAVE_IOS', 'cxx'), + ], + functions = [ + ('open', 'HAVE_OPEN', None), + ('close', 'HAVE_CLOSE', None), + ('popen', 'HAVE_POPEN', None), + ('pclose', 'HAVE_PCLOSE', None), + ('_open', 'HAVE__OPEN', None), + ('_close', 'HAVE__CLOSE', None), + ('_popen', 'HAVE__POPEN', None), + ('_pclose', 'HAVE__PCLOSE', None), + ('getpid', 'HAVE_GETPID', None), + ('_getpid', 'HAVE__GETPID', None), + ('mkdir', 'HAVE_MKDIR', None), + ('_mkdir', 'HAVE__MKDIR', None), + ('mktemp', 'HAVE_MKTEMP', None), + ('mkstemp', 'HAVE_MKSTEMP', None), + ('strerror', 'HAVE_STRERROR', None), + ('count', 'HAVE_STD_COUNT', ''' +#include +int count() +{ + char a[] = "hello"; + return std::count(a, a+5, 'l'); +} +'''), + ('getcwd', 'HAVE_GETCWD', None), + ('setenv', 'HAVE_SETENV', None), + ('putenv', 'HAVE_PUTENV', None), + ('fcntl', 'HAVE_FCNTL', None), + ], + types = [ + ('std::istreambuf_iterator', 'HAVE_DECL_ISTREAMBUF_ITERATOR', + '#include \n#include ') + ], + libs = [ + ('gdi32', 'HAVE_LIBGDI32'), + (('iconv', 'libiconv'), 'HAVE_ICONV', 'ICONV_LIB'), + (('Aiksaurus', 'libAiksaurus'), 'HAVE_LIBAIKSAURUS', 'AIKSAURUS_LIB'), + ], + custom_tests = [ + (conf.CheckType('pid_t', includes='#include '), + 'HAVE_PID_T', + 'Define is sys/types.h does not have pid_t', + '', + '#define pid_t int', + ), + (conf.CheckCXXGlobalCstd(), + 'CXX_GLOBAL_CSTD', + 'Define if your C++ compiler puts C library functions in the global namespace' + ), + (conf.CheckMkdirOneArg(), + 'MKDIR_TAKES_ONE_ARG', + 'Define if mkdir takes only one argument.' + ), + (conf.CheckLC_MESSAGES(), + 'HAVE_LC_MESSAGES', + 'Define if your file defines LC_MESSAGES.' + ), + (devel_version, 'DEVEL_VERSION', 'Whether or not a development version'), + (env['nls'], + 'ENABLE_NLS', + "Define to 1 if translation of program messages to the user's native anguage is requested.", + ), + (env['nls'] and not included_gettext, + 'HAVE_GETTEXT', + 'Define to 1 if using system gettext library' + ), + (env.has_key('warnings') and env['warnings'], + 'WITH_WARNINGS', + 'Define this if you want to see the warning directives put here and there by the developpers to get attention' + ), + (env.has_key('concept_checks') and env['concept_checks'], + '_GLIBCXX_CONCEPT_CHECKS', + 'libstdc++ concept checking' + ), + (env.has_key('stdlib_debug') and env['stdlib_debug'], + '_GLIBCXX_DEBUG', + 'libstdc++ debug mode' + ), + (env.has_key('stdlib_debug') and env['stdlib_debug'], + '_GLIBCXX_DEBUG_PEDANTIC', + 'libstdc++ pedantic debug mode' + ), + (os.name != 'nt', 'BOOST_POSIX', + 'Indicates to boost which API to use (posix or windows).' + ), + (spell_engine is not None, spell_engine, + 'Spell engine to use' + ), + ], + extra_items = [ + ('#define PACKAGE "%s%s"' % (package, program_suffix), + 'Name of package'), + ('#define PACKAGE_BUGREPORT "%s"' % package_bugreport, + 'Define to the address where bug reports for this package should be sent.'), + ('#define PACKAGE_NAME "%s"' % package_name, + 'Define to the full name of this package.'), + ('#define PACKAGE_STRING "%s"' % package_string, + 'Define to the full name and version of this package.'), + ('#define PACKAGE_TARNAME "%s"' % package_tarname, + 'Define to the one symbol short name of this package.'), + ('#define PACKAGE_VERSION "%s"' % package_version, + 'Define to the version of this package.'), + ('#define BOOST_ALL_NO_LIB 1', + 'disable automatic linking of boost libraries.'), + ('#define USE_%s_PACKAGING 1' % packaging_method.upper(), + 'Packaging method'), + ('#define AIKSAURUS_H_LOCATION ' + aik_location, + 'Aiksaurus include file'), + ('#define SELECT_TYPE_ARG1 %s' % select_arg1, + "Define to the type of arg 1 for `select'."), + ('#define SELECT_TYPE_ARG234 %s' % select_arg234, + "Define to the type of arg 2, 3, 4 for `select'."), + ('#define SELECT_TYPE_ARG5 %s' % select_arg5, + "Define to the type of arg 5 for `select'."), + ], + config_post = '''/************************************************************ +** You should not need to change anything beyond this point */ + +#ifndef HAVE_STRERROR +#if defined(__cplusplus) +extern "C" +#endif +char * strerror(int n); +#endif + +#ifdef HAVE_MKSTEMP +#ifndef HAVE_DECL_MKSTEMP +#if defined(__cplusplus) +extern "C" +#endif +int mkstemp(char*); +#endif +#endif + +#include <../boost/config.h> + +#endif +''' + ) + + # these keys are needed in env + for key in ['USE_ASPELL', 'USE_PSPELL', 'USE_ISPELL', 'HAVE_FCNTL',\ + 'HAVE_ICONV', 'HAVE_LIBGDI32', 'HAVE_LIBAIKSAURUS', + 'ICONV_LIB', 'AIKSAURUS_LIB']: + # USE_ASPELL etc does not go through result + if result.has_key(key): + env[key] = result[key] + env_cache[key] = env[key] + + # + # if nls=yes and gettext=included, create intl/config.h + # intl/libintl.h etc + # + intl_config_h = os.path.join(env.Dir('$BUILDDIR/intl').path, 'config.h') + if env['nls'] and included_gettext: + # + print "Creating %s..." % intl_config_h + # + # create intl/config.h + result = utils.createConfigFile(conf, + config_file = intl_config_h, + config_pre = '''/* intl/config.h. Generated by SCons. */ + +/* -*- C++ -*- */ +/* +* \file config.h +* This file is part of LyX, the document processor. +* Licence details can be found in the file COPYING. +* +* This is the compilation configuration file for LyX. +* It was generated by scon. +* You might want to change some of the defaults if something goes wrong +* during the compilation. +*/ + +#ifndef _CONFIG_H +#define _CONFIG_H +''', + headers = [ + ('unistd.h', 'HAVE_UNISTD_H', 'c'), + ('inttypes.h', 'HAVE_INTTYPES_H', 'c'), + ('string.h', 'HAVE_STRING_H', 'c'), + ('strings.h', 'HAVE_STRINGS_H', 'c'), + ('argz.h', 'HAVE_ARGZ_H', 'c'), + ('limits.h', 'HAVE_LIMITS_H', 'c'), + ('alloca.h', 'HAVE_ALLOCA_H', 'c'), + ('stddef.h', 'HAVE_STDDEF_H', 'c'), + ('stdint.h', 'HAVE_STDINT_H', 'c'), + ('sys/param.h', 'HAVE_SYS_PARAM_H', 'c'), + ], + functions = [ + ('getcwd', 'HAVE_GETCWD', None), + ('stpcpy', 'HAVE_STPCPY', None), + ('strcasecmp', 'HAVE_STRCASECMP', None), + ('strdup', 'HAVE_STRDUP', None), + ('strtoul', 'HAVE_STRTOUL', None), + ('alloca', 'HAVE_ALLOCA', None), + ('__fsetlocking', 'HAVE___FSETLOCKING', None), + ('mempcpy', 'HAVE_MEMPCPY', None), + ('__argz_count', 'HAVE___ARGZ_COUNT', None), + ('__argz_next', 'HAVE___ARGZ_NEXT', None), + ('__argz_stringify', 'HAVE___ARGZ_STRINGIFY', None), + ('setlocale', 'HAVE_SETLOCALE', None), + ('tsearch', 'HAVE_TSEARCH', None), + ('getegid', 'HAVE_GETEGID', None), + ('getgid', 'HAVE_GETGID', None), + ('getuid', 'HAVE_GETUID', None), + ('wcslen', 'HAVE_WCSLEN', None), + ('asprintf', 'HAVE_ASPRINTF', None), + ('wprintf', 'HAVE_WPRINTF', None), + ('snprintf', 'HAVE_SNPRINTF', None), + ('printf', 'HAVE_POSIX_PRINTF', None), + ('fcntl', 'HAVE_FCNTL', None), + ], + types = [ + ('intmax_t', 'HAVE_INTMAX_T', None), + ('long double', 'HAVE_LONG_DOUBLE', None), + ('long long', 'HAVE_LONG_LONG', None), + ('wchar_t', 'HAVE_WCHAR_T', None), + ('wint_t', 'HAVE_WINT_T', None), + ('uintmax_t', 'HAVE_INTTYPES_H_WITH_UINTMAX', '#include '), + ('uintmax_t', 'HAVE_STDINT_H_WITH_UINTMAX', '#include '), + ], + libs = [ + (('iconv', 'libiconv'), 'HAVE_ICONV', 'ICONV_LIB'), + ('c', 'HAVE_LIBC'), + ], + custom_tests = [ + (conf.CheckLC_MESSAGES(), + 'HAVE_LC_MESSAGES', + 'Define if your file defines LC_MESSAGES.' + ), + (conf.CheckIconvConst(), + 'ICONV_CONST', + 'Define as const if the declaration of iconv() needs const.', + '#define ICONV_CONST', + '#define ICONV_CONST const', + ), + (conf.CheckType('intmax_t', includes='#include ') or \ + conf.CheckType('intmax_t', includes='#include '), + 'HAVE_INTMAX_T', + "Define to 1 if you have the `intmax_t' type." + ), + (env.has_key('nls') and env['nls'], + 'ENABLE_NLS', + "Define to 1 if translation of program messages to the user's native anguage is requested.", + ), + ], + config_post = '#endif' + ) + + # these keys are needed in env + for key in ['HAVE_ASPRINTF', 'HAVE_WPRINTF', 'HAVE_SNPRINTF', \ + 'HAVE_POSIX_PRINTF', 'HAVE_ICONV', 'HAVE_LIBC']: + # USE_ASPELL etc does not go through result + if result.has_key(key): + env[key] = result[key] + env_cache[key] = env[key] + +else: + # + # this comes as a big surprise, without this line + # (doing nothing obvious), adding fast_start=yes + # to a build with fast_start=no will result in a rebuild + # Note that the exact header file to check does not matter + conf.CheckCHeader('io.h') + # only a few variables need to be rescanned + for key in ['USE_ASPELL', 'USE_PSPELL', 'USE_ISPELL', 'HAVE_FCNTL',\ + 'HAVE_ICONV', 'HAVE_LIBGDI32', 'HAVE_LIBAIKSAURUS', + 'ICONV_LIB', 'AIKSAURUS_LIB']: + env[key] = env_cache[key] + # + # nls related keys + if env['nls'] and included_gettext: + # only a few variables need to be rescanned + for key in ['HAVE_ASPRINTF', 'HAVE_WPRINTF', 'HAVE_SNPRINTF', \ + 'HAVE_POSIX_PRINTF', 'HAVE_ICONV', 'HAVE_LIBC']: + env[key] = env_cache[key] + +# this looks misplaced, but intl/libintl.h is needed by src/message.C +if env['nls'] and included_gettext: + # libgnuintl.h.in => libintl.h + env.substFile('$BUILDDIR/intl/libintl.h', '$TOP_SRCDIR/intl/libgnuintl.h.in') + env.Command('$BUILDDIR/intl/libgnuintl.h', '$BUILDDIR/intl/libintl.h', + [Copy('$TARGET', '$SOURCE')]) + +# +# Finish auto-configuration +env = conf.Finish() + +#---------------------------------------------------------- +# Now set up our build process accordingly +#---------------------------------------------------------- + +# +# QT_LIB +# +# NOTE: Tool('qt') or Tool('qt4') will be loaded later +# in their respective directory and specialized env. +if frontend == 'qt2': + # note: env.Tool('qt') my set QT_LIB to qt + qt_libs = ['qt-mt'] + frontend_libs = ['qt-mt'] + + +if platform_name in ['win32', 'cygwin']: + # the final link step needs stdc++ to succeed under mingw + # FIXME: shouldn't g++ automatically link to stdc++? + if use_vc: + system_libs = ['shlwapi', 'shell32', 'advapi32', 'zdll'] + else: + system_libs = ['shlwapi', 'stdc++', 'z'] +elif platform_name == 'cygwin' and env['X11']: + system_libs = ['GL', 'Xmu', 'Xi', 'Xrender', 'Xrandr', 'Xcursor', + 'Xft', 'freetype', 'fontconfig', 'Xext', 'X11', 'SM', 'ICE', 'resolv', + 'pthread', 'z'] +else: + system_libs = ['z'] + +libs = [ + ('HAVE_ICONV', env['ICONV_LIB']), + ('HAVE_LIBGDI32', 'gdi32'), + ('HAVE_LIBAIKSAURUS', env['AIKSAURUS_LIB']), + ('USE_ASPELL', aspell_lib), + ('USE_ISPELL', 'ispell'), + ('USE_PSPELL', 'pspell'), +] + +for lib in libs: + if env[lib[0]]: + system_libs.append(lib[1]) + +# +# Build parameters CPPPATH etc +# +if env['X11']: + env.AppendUnique(LIBPATH = ['/usr/X11R6/lib']) + +# +# boost: for boost header files +# BUILDDIR/common: for config.h +# TOP_SRCDIR/src: for support/* etc +# +env['CPPPATH'] += ['$BUILDDIR/common', '$TOP_SRCDIR/src'] +# +# Separating boost directories from CPPPATH stops scons from building +# the dependency tree for boost header files, and effectively reduce +# the null build time of lyx from 29s to 16s. Since lyx may tweak local +# boost headers, this is only done for system boost headers. +if included_boost: + env.AppendUnique(CPPPATH = ['$BOOST_INC_PATH']) +else: + if use_vc: + env.PrependUnique(CCFLAGS = ['/I$BOOST_INC_PATH']) + else: + env.PrependUnique(CCFLAGS = ['-I$BOOST_INC_PATH']) + +# for intl/config.h, intl/libintl.h and intl/libgnuintl.h +if env['nls'] and included_gettext: + env['CPPPATH'].append('$BUILDDIR/intl') +# +# QT_INC_PATH is not needed for *every* source file +env['CPPPATH'].remove(qt_inc_path) + +# +# A Link script for cygwin see +# http://www.cygwin.com/ml/cygwin/2004-09/msg01101.html +# http://www.cygwin.com/ml/cygwin-apps/2004-09/msg00309.html +# for details +# +if platform_name == 'cygwin': + ld_script_path = '/usr/lib/qt3/mkspecs/cygwin-g++' + ld_script = utils.installCygwinLDScript(ld_script_path) + env.AppendUnique(LINKFLAGS = ['-Wl,--enable-runtime-pseudo-reloc', + '-Wl,--script,%s' % ld_script, '-Wl,-s']) + +# +# Report results +# +# fill in the version info +env['VERSION_INFO'] = '''Configuration + Host type: %s + Special build flags: %s + C Compiler: %s + C Compiler flags: %s %s + C++ Compiler: %s + C++ Compiler LyX flags: %s + C++ Compiler flags: %s %s + Linker flags: %s + Linker user flags: %s +Build info: + Builing directory: %s + Local library directory: %s + Libraries paths: %s + Boost libraries: %s + Frontend libraries: %s + System libraries: %s + include search path: %s +Frontend: + Frontend: %s + Packaging: %s + LyX dir: %s + LyX files dir: %s +''' % (platform_name, + env.subst('$CCFLAGS'), env.subst('$CC'), + env.subst('$CPPFLAGS'), env.subst('$CFLAGS'), + env.subst('$CXX'), env.subst('$CXXFLAGS'), + env.subst('$CPPFLAGS'), env.subst('$CXXFLAGS'), + env.subst('$LINKFLAGS'), env.subst('$LINKFLAGS'), + env.subst('$BUILDDIR'), env.subst('$LOCALLIBPATH'), + str(env['LIBPATH']), str(boost_libraries), + str(frontend_libs), str(system_libs), str(env['CPPPATH']), + frontend, packaging_method, + prefix, env['LYX_DIR']) + +if frontend == 'qt2': + env['VERSION_INFO'] += ''' include dir: %s + library dir: %s + X11: %s +''' % (qt_inc_path, qt_lib_path, env['X11']) + +if not fast_start: + print env['VERSION_INFO'] + +# +# Mingw command line may be too short for our link usage, +# Here we use a trick from scons wiki +# http://www.scons.org/cgi-sys/cgiwrap/scons/moin.cgi/LongCmdLinesOnWin32 +# +# I also would like to add logging (commands only) capacity to the +# spawn system. +logfile = env.get('logfile', default_log_file) +if logfile != '' or platform_name == 'win32': + import time + utils.setLoggedSpawn(env, logfile, longarg = (platform_name == 'win32'), + info = '''# This is a log of commands used by scons to build lyx +# Time: %s +# Command: %s +# Info: %s +''' % (time.asctime(), ' '.join(sys.argv), + env['VERSION_INFO'].replace('\n','\n# ')) ) + + +# Cleanup stuff +# +# -h will print out help info +Help(opts.GenerateHelpText(env)) + +# save environment settings (for fast_start option) +cache_file = open(env_cache_file, 'w') +cPickle.dump(env_cache, cache_file) +cache_file.close() + + +#---------------------------------------------------------- +# Start building +#---------------------------------------------------------- +# this has been the source of problems on some platforms... +# I find that I need to supply it with full path name +env.SConsignFile(os.path.join(Dir(env['BUILDDIR']).abspath, '.sconsign')) +# this usage needs further investigation. +#env.CacheDir('%s/Cache/%s' % (env['BUILDDIR'], frontend)) + +print "Building all targets recursively" + +if env.has_key('rebuild'): + rebuild_targets = env['rebuild'].split(',') + if 'none' in rebuild_targets or 'no' in rebuild_targets: + rebuild_targets = [] + elif 'all' in rebuild_targets or 'yes' in rebuild_targets: + # None: let scons decide which components to build + # Forcing all components to be rebuilt is in theory not necessary + rebuild_targets = None +else: + rebuild_targets = None + +def libExists(libname): + ''' Check whether or not lib $LOCALLIBNAME/libname already exists''' + return os.path.isfile(File(env.subst('$LOCALLIBPATH/${LIBPREFIX}%s$LIBSUFFIX'%libname)).abspath) + +def appExists(apppath, appname): + ''' Check whether or not application already exists''' + return os.path.isfile(File(env.subst('$BUILDDIR/common/%s/${PROGPREFIX}%s$PROGSUFFIX' % (apppath, appname))).abspath) + +targets = BUILD_TARGETS +# msvc need to pass full target name, so I have to look for path/lyx etc +build_lyx = targets == [] or True in ['lyx' in x for x in targets] \ + or 'install' in targets or 'all' in targets +build_boost = (included_boost and not libExists('boost_regex')) or 'boost' in targets +build_intl = (included_gettext and not libExists('included_intl')) or 'intl' in targets +build_support = build_lyx or True in [x in targets for x in ['support', 'client', 'tex2lyx']] +build_mathed = build_lyx or 'mathed' in targets +build_insets = build_lyx or 'insets' in targets +build_frontends = build_lyx or 'frontends' in targets +build_graphics = build_lyx or 'graphics' in targets +build_controllers = build_lyx or 'controllers' in targets +build_client = True in ['client' in x for x in targets] \ + or 'install' in targets or 'all' in targets +build_tex2lyx = True in ['tex2lyx' in x for x in targets] \ + or 'install' in targets or 'all' in targets +build_lyxbase = build_lyx or 'lyxbase' in targets +build_po = 'po' in targets or 'install' in targets or 'all' in targets +build_qt2 = (build_lyx and frontend == 'qt2') or 'qt2' in targets +build_msvs_projects = use_vc and 'msvs_projects' in targets + + +# now, if rebuild_targets is specified, do not rebuild some targets +if rebuild_targets is not None: + # + def ifBuildLib(name, libname, old_value): + # explicitly asked to rebuild + if name in rebuild_targets: + return True + # else if not rebuild, and if the library already exists + elif libExists(libname): + return False + # do not change the original value + else: + return old_value + build_boost = ifBuildLib('boost', 'included_boost_filesystem', build_boost) + build_intl = ifBuildLib('intl', 'included_intl', build_intl) + build_support = ifBuildLib('support', 'support', build_support) + build_mathed = ifBuildLib('mathed', 'mathed', build_mathed) + build_insets = ifBuildLib('insets', 'insets', build_insets) + build_frontends = ifBuildLib('frontends', 'frontends', build_frontends) + build_graphics = ifBuildLib('graphics', 'graphics', build_graphics) + build_controllers = ifBuildLib('controllers', 'controllers', build_controllers) + build_lyxbase = ifBuildLib('lyxbase', 'lyxbase_pre', build_lyxbase) + build_qt2 = ifBuildLib('qt2', 'qt2', build_qt2) + # + def ifBuildApp(name, appname, old_value): + # explicitly asked to rebuild + if name in rebuild_targets: + return True + # else if not rebuild, and if the library already exists + elif appExists(name, appname): + return False + # do not change the original value + else: + return old_value + build_tex2lyx = ifBuildApp('tex2lyx', 'tex2lyx', build_tex2lyx) + build_client = ifBuildApp('client', 'lyxclient', build_client) + +# sync frontend and frontend +if build_qt2: + frontend = 'qt2' + +if build_boost: + # + # boost libraries + # + # special builddir + env.BuildDir('$BUILDDIR/boost', '$TOP_SRCDIR/boost/libs', duplicate = 0) + + boostenv = env.Copy() + # + # boost use its own config.h + boostenv['CPPPATH'] = ['$TOP_SRCDIR/boost', '$BUILDDIR/boost'] + extra_inc_paths + boostenv.AppendUnique(CCFLAGS = ['-DBOOST_USER_CONFIG=""']) + + for lib in boost_libs: + print 'Processing files in boost/libs/%s/src...' % lib + boostlib = boostenv.StaticLibrary( + target = '$LOCALLIBPATH/included_boost_%s' % lib, + source = ['$BUILDDIR/boost/%s/src/%s' % (lib, x) for x in eval('boost_libs_%s_src_files' % lib)] + ) + Alias('boost', boostlib) + + +if build_intl: + # + # intl + # + intlenv = env.Copy() + + print "Processing files in intl..." + + env.BuildDir('$BUILDDIR/intl', '$TOP_SRCDIR/intl', duplicate = 0) + + # we need the original C compiler for these files + intlenv['CC'] = C_COMPILER + intlenv['CCFLAGS'] = C_CCFLAGS + if use_vc: + intlenv.Append(CCFLAGS=['/Dinline#', '/D__attribute__(x)#', '/Duintmax_t=UINT_MAX']) + # intl does not use global config.h + intlenv['CPPPATH'] = ['$BUILDDIR/intl'] + extra_inc_paths + + intlenv.Append(CCFLAGS = [ + r'-DLOCALEDIR=\"' + env['LOCALEDIR'].replace('\\', '\\\\') + r'\"', + r'-DLOCALE_ALIAS_PATH=\"' + env['LOCALEDIR'].replace('\\', '\\\\') + r'\"', + r'-DLIBDIR=\"' + env['TOP_SRCDIR'].replace('\\', '\\\\') + r'/lib\"', + '-DIN_LIBINTL', + '-DENABLE_RELOCATABLE=1', + '-DIN_LIBRARY', + r'-DINSTALLDIR=\"' + prefix.replace('\\', '\\\\') + r'/lib\"', + '-DNO_XMALLOC', + '-Dset_relocation_prefix=libintl_set_relocation_prefix', + '-Drelocate=libintl_relocate', + '-DDEPENDS_ON_LIBICONV=1', + '-DHAVE_CONFIG_H' + ] + ) + + intl = intlenv.StaticLibrary( + target = '$LOCALLIBPATH/included_intl', + LIBS = ['c'], + source = ['$BUILDDIR/intl/%s' % x for x in intl_files] + ) + Alias('intl', intl) + + +# +# Now, src code under src/ +# +env.BuildDir('$BUILDDIR/common', '$TOP_SRCDIR/src', duplicate = 0) + + +if build_support: + # + # src/support + # + print "Processing files in src/support..." + + env.substFile('$BUILDDIR/common/support/package.C', '$TOP_SRCDIR/src/support/package.C.in') + + support = env.StaticLibrary( + target = '$LOCALLIBPATH/support', + source = ['$BUILDDIR/common/support/%s' % x for x in src_support_files] + ) + Alias('support', support) + + +if build_mathed: + # + # src/mathed + # + print "Processing files in src/mathed..." + # + mathed = env.StaticLibrary( + target = '$LOCALLIBPATH/mathed', + source = ['$BUILDDIR/common/mathed/%s' % x for x in src_mathed_files] + ) + Alias('mathed', mathed) + + +if build_insets: + # + # src/insets + # + print "Processing files in src/insets..." + # + insets = env.StaticLibrary( + target = '$LOCALLIBPATH/insets', + source = ['$BUILDDIR/common/insets/%s' % x for x in src_insets_files] + ) + Alias('insets', insets) + + +if build_frontends: + # + # src/frontends + # + print "Processing files in src/frontends..." + + frontends = env.StaticLibrary( + target = '$LOCALLIBPATH/frontends', + source = ['$BUILDDIR/common/frontends/%s' % x for x in src_frontends_files] + ) + Alias('frontends', frontends) + + +if build_graphics: + # + # src/graphics + # + print "Processing files in src/graphics..." + + graphics = env.StaticLibrary( + target = '$LOCALLIBPATH/graphics', + source = ['$BUILDDIR/common/graphics/%s' % x for x in src_graphics_files] + ) + Alias('graphics', graphics) + + +if build_controllers: + # + # src/frontends/controllers + # + print "Processing files in src/frontends/controllers..." + + controllers = env.StaticLibrary( + target = '$LOCALLIBPATH/controllers', + source = ['$BUILDDIR/common/frontends/controllers/%s' % x for x in src_frontends_controllers_files] + ) + Alias('controllers', controllers) + + +# +# src/frontend/qt3/4 +# +if build_qt2: + env.BuildDir('$BUILDDIR/$frontend', '$TOP_SRCDIR/src/frontend/$frontend', duplicate = 0) + + print "Processing files in src/frontends/qt2..." + + qt2env = env.Copy() + # disable auto scan to speed up non build time + qt2env['QT_AUTOSCAN'] = 0 + qt2env['QT_MOCHPREFIX'] = '' + + # load qt2 tools + qt2env.Tool('qt') + + qt2env.AppendUnique(CPPPATH = [ + '$BUILDDIR/common', + '$BUILDDIR/common/images', + '$BUILDDIR/common/frontends', + '$BUILDDIR/common/frontends/qt2', + '$BUILDDIR/common/frontends/controllers', + qt_inc_path] + ) + + qt2_moc_files = ["$BUILDDIR/common/frontends/qt2/%s" % x for x in src_frontends_qt2_moc_files] + + # manually moc and uic files for better performance + qt2_moced_files = [qt2env.Moc(x.replace('.C', '_moc.cpp'), x.replace('.C', '.h')) for x in qt2_moc_files] + + qt2_uiced_files = [qt2env.Uic('$BUILDDIR/common/frontends/qt2/ui/'+x) for x in \ + src_frontends_qt2_ui_files] + + qt2_uiced_cc_files = [] + for x in qt2_uiced_files: + qt2_uiced_cc_files.extend(x[1:]) + + qt2 = qt2env.StaticLibrary( + target = '$LOCALLIBPATH/qt2', + source = ['$BUILDDIR/common/frontends/qt2/%s' % x for x in src_frontends_qt2_files] \ + + qt2_moced_files + qt2_uiced_cc_files + ) + Alias('qt2', qt2) + + +if build_client: + # + # src/client + # + env.BuildDir('$BUILDDIR/common', '$TOP_SRCDIR/src', duplicate = 0) + + print "Processing files in src/client..." + + if env['HAVE_FCNTL']: + client = env.Program( + target = '$BUILDDIR/common/client/lyxclient', + LIBS = ['support'] + intl_libs + system_libs + + socket_libs + boost_libraries, + source = ['$BUILDDIR/common/client/%s' % x for x in src_client_files] + ) + Alias('client', env.Command(os.path.join('$BUILDDIR', os.path.split(str(client[0]))[1]), + client, [Copy('$TARGET', '$SOURCE')])) + else: + client = None + Alias('client', client) +else: + if env['HAVE_FCNTL']: + # define client even if lyxclient is not built with rebuild=no + client = [env.subst('$BUILDDIR/common/client/${PROGPREFIX}lyxclient$PROGSUFFIX')] + else: + client = None + + +if build_tex2lyx: + # + # tex2lyx + # + print "Processing files in src/tex2lyx..." + + tex2lyx_env = env.Copy() + # + tex2lyx_env.Prepend(CPPPATH = ['$BUILDDIR/common/tex2lyx']) + tex2lyx_env.AppendUnique(LIBPATH = ['#$LOCALLIBPATH']) + + for file in ['FloatList.C', 'Floating.C', 'counters.C', 'lyxlayout.h', 'lyxlayout.C', + 'lyxtextclass.h', 'lyxtextclass.C', 'lyxlex.C', 'lyxlex_pimpl.C']: + env.Command('$BUILDDIR/common/tex2lyx/'+file, '$TOP_SRCDIR/src/'+file, + [Copy('$TARGET', '$SOURCE')]) + + tex2lyx = tex2lyx_env.Program( + target = '$BUILDDIR/common/tex2lyx/tex2lyx', + LIBS = ['support'] + boost_libraries + system_libs, + source = ['$BUILDDIR/common/tex2lyx/%s' % x for x in src_tex2lyx_files] + ) + Alias('tex2lyx', env.Command(os.path.join('$BUILDDIR', os.path.split(str(tex2lyx[0]))[1]), + tex2lyx, [Copy('$TARGET', '$SOURCE')])) + Alias('tex2lyx', tex2lyx) +else: + # define tex2lyx even if tex2lyx is not built with rebuild=no + tex2lyx = [env.subst('$BUILDDIR/common/tex2lyx/${PROGPREFIX}tex2lyx$PROGSUFFIX')] + + +if build_lyxbase: + # + # src/ + # + print "Processing files in src..." + + env.substFile('$BUILDDIR/common/version.C', '$TOP_SRCDIR/src/version.C.in') + + if env.has_key('USE_ASPELL') and env['USE_ASPELL']: + src_post_files.append('aspell.C') + elif env.has_key('USE_PSPELL') and env['USE_PSPELL']: + src_post_files.append('pspell.C') + elif env.has_key('USE_ISPELL') and env['USE_ISPELL']: + src_post_files.append('ispell.C') + + # msvc requires at least one source file with main() + # so I exclude main.C from lyxbase + lyxbase_pre = env.StaticLibrary( + target = '$LOCALLIBPATH/lyxbase_pre', + source = ['$BUILDDIR/common/%s' % x for x in src_pre_files] + ) + lyxbase_post = env.StaticLibrary( + target = '$LOCALLIBPATH/lyxbase_post', + source = ["$BUILDDIR/common/%s" % x for x in src_post_files] + ) + Alias('lyxbase', lyxbase_pre) + Alias('lyxbase', lyxbase_post) + + +if build_lyx: + # + # Build lyx with given frontend + # + lyx = env.Program( + target = '$BUILDDIR/$frontend/lyx', + source = ['$BUILDDIR/common/main.C'], + LIBS = [ + 'lyxbase_pre', + 'mathed', + 'insets', + 'frontends', + frontend, + 'controllers', + 'graphics', + 'support', + 'lyxbase_post', + ] + + boost_libraries + + frontend_libs + + intl_libs + + socket_libs + + system_libs + ) + # [/path/to/lyx.ext] => lyx-qt3.ext + target_name = os.path.split(str(lyx[0]))[1].replace('lyx', 'lyx-%s' % frontend) + Alias('lyx', env.Command(os.path.join('$BUILDDIR', target_name), lyx, + [Copy('$TARGET', '$SOURCE')])) + Alias('lyx', lyx) +else: + # define lyx even if lyx is not built with rebuild=no + lyx = [env.subst('$BUILDDIR/$frontend/${PROGPREFIX}lyx$PROGSUFFIX')] + + +if build_msvs_projects: + def build_project(target, full_target = None, + src = [], inc = [], res = [], rebuildTargetOnly = True): + ''' build mavs project files + target: alias (correspond to directory name) + full_target: full path/filename of the target + src: source files + inc: include files + res: resource files + rebuildTargetOnly: whether or not only rebuild this target + + For non-debug-able targets like static libraries, target (alias) is + enough to build the target. For executable targets, msvs need to know + the full path to start debug them. + ''' + if rebuildTargetOnly: + cmds = 'fast_start=yes rebuild='+target + else: + cmds = 'fast_start=yes' + if full_target is None: + build_target = target + else: + build_target = full_target + # project + proj = env.MSVSProject( + target = target + env['MSVSPROJECTSUFFIX'], + # this allows easy access to header files (along with source) + srcs = [env.subst(x) for x in src + inc], + incs = [env.subst('$TOP_SRCDIR/src/config.h')], + localincs = [env.subst(x) for x in inc], + resources = [env.subst(x) for x in res], + buildtarget = build_target, + cmdargs = cmds, + variant = 'Debug' + ) + Alias('msvs_projects', proj) + # + boost_src = [] + for lib in boost_libs: + boost_src += ['$TOP_SRCDIR/boost/libs/%s/src/%s' % (lib, x) for x in eval('boost_libs_%s_src_files' % lib)] + build_project('boost', src = boost_src) + # + build_project('intl', src = ['$TOP_SRCDIR/intl/%s' % x for x in intl_files], + inc = ['$TOP_SRCDIR/intl/%s' % x for x in intl_header_files]) + # + build_project('support', src = ['$TOP_SRCDIR/src/support/%s' % x for x in src_support_files], + inc = ['$TOP_SRCDIR/src/support/%s' % x for x in src_support_header_files]) + # + build_project('mathed', src = ['$TOP_SRCDIR/src/support/%s' % x for x in src_support_files], + inc = ['$TOP_SRCDIR/src/support/%s' % x for x in src_support_header_files]) + # + build_project('insets', src = ['$TOP_SRCDIR/src/insets/%s' % x for x in src_insets_files], + inc = ['$TOP_SRCDIR/src/insets/%s' % x for x in src_insets_header_files]) + # + build_project('frontends', src = ['$TOP_SRCDIR/src/frontends/%s' % x for x in src_frontends_files], + inc = ['$TOP_SRCDIR/src/frontends/%s' % x for x in src_frontends_header_files]) + # + build_project('graphics', src = ['$TOP_SRCDIR/src/graphics/%s' % x for x in src_graphics_files], + inc = ['$TOP_SRCDIR/src/graphics/%s' % x for x in src_graphics_header_files]) + # + build_project('controllers', src = ['$TOP_SRCDIR/src/frontends/controllers/%s' % x for x in src_frontends_controllers_files], + inc = ['$TOP_SRCDIR/src/frontends/controllers/%s' % x for x in src_frontends_controllers_header_files]) + # + build_project('qt2', src = ['$TOP_SRCDIR/src/frontends/qt2/%s' % x for x in src_frontends_qt2_files + src_frontends_qt2_moc_files], + inc = ['$TOP_SRCDIR/src/frontends/qt2/%s' % x for x in src_frontends_qt2_header_files], + res = ['$TOP_SRCDIR/src/frontends/qt2/ui/%s' % x for x in src_frontends_qt2_ui_files]) + # + build_project('client', src = ['$TOP_SRCDIR/src/client/%s' % x for x in src_client_files], + inc = ['$TOP_SRCDIR/src/client/%s' % x for x in src_client_header_files], + rebuildTargetOnly = False, + full_target = File(env.subst('$BUILDDIR/common/client/lyxclient$PROGSUFFIX')).abspath) + # + build_project('tex2lyx', src = ['$TOP_SRCDIR/src/tex2lyx/%s' % x for x in src_tex2lyx_files], + inc = ['$TOP_SRCDIR/src/tex2lyx/%s' % x for x in src_tex2lyx_header_files], + rebuildTargetOnly = False, + full_target = File(env.subst('$BUILDDIR/common/tex2lyx/tex2lyx$PROGSUFFIX')).abspath) + # + build_project('lyxbase', src = ['$TOP_SRCDIR/src/%s' % x for x in src_pre_files + src_post_files], + inc = ['$TOP_SRCDIR/src/%s' % x for x in src_header_files]) + # + if frontend == 'qt2': + build_project('lyx', + src = ['$TOP_SRCDIR/src/%s' % x for x in src_pre_files + src_post_files] + \ + ['$TOP_SRCDIR/src/support/%s' % x for x in src_support_files] + \ + ['$TOP_SRCDIR/src/mathed/%s' % x for x in src_mathed_files] + \ + ['$TOP_SRCDIR/src/insets/%s' % x for x in src_insets_files] + \ + ['$TOP_SRCDIR/src/frontends/%s' % x for x in src_frontends_files] + \ + ['$TOP_SRCDIR/src/graphics/%s' % x for x in src_graphics_files] + \ + ['$TOP_SRCDIR/src/frontends/controllers/%s' % x for x in src_frontends_controllers_files] + \ + ['$TOP_SRCDIR/src/frontends/qt2/%s' % x for x in src_frontends_qt2_files + src_frontends_qt2_moc_files], + inc = ['$TOP_SRCDIR/src/%s' % x for x in src_header_files] + \ + ['$TOP_SRCDIR/src/support/%s' % x for x in src_support_header_files] + \ + ['$TOP_SRCDIR/src/mathed/%s' % x for x in src_mathed_header_files] + \ + ['$TOP_SRCDIR/src/insets/%s' % x for x in src_insets_header_files] + \ + ['$TOP_SRCDIR/src/frontends/%s' % x for x in src_frontends_header_files] + \ + ['$TOP_SRCDIR/src/graphics/%s' % x for x in src_graphics_header_files] + \ + ['$TOP_SRCDIR/src/frontends/controllers/%s' % x for x in src_frontends_controllers_header_files] + \ + ['$TOP_SRCDIR/src/frontends/qt2/%s' % x for x in src_frontends_qt2_header_files], + res = ['$TOP_SRCDIR/src/frontends/qt2/ui/%s' % x for x in src_frontends_qt2_ui_files], + rebuildTargetOnly = False, + full_target = File(env.subst('$BUILDDIR/$frontend/lyx$PROGSUFFIX')).abspath) + + +if build_po: + # + # po/ + # + print 'Processing files in po...' + + import glob + # handle po files + # + # files to translate + transfiles = glob.glob(os.path.join(env.subst('$TOP_SRCDIR'), 'po', '*.po')) + # possibly *only* handle these languages + languages = None + if env.has_key('languages'): + languages = env.make_list(env['lanauges']) + # use defulat msgfmt + gmo_files = [] + if not env['MSGFMT']: + print 'msgfmt does not exist. Can not process po files' + else: + # create a builder + env['BUILDERS']['Transfiles'] = Builder(action='$MSGFMT $SOURCE -o $TARGET',suffix='.gmo',src_suffix='.po') + # + for f in transfiles: + # get filename + fname = os.path.split(f)[1] + # country code + country = fname.split('.')[0] + # + if not languages or country in languages: + gmo_files.extend(env.Transfiles(f)) + + +if 'install' in targets: + # + # this part is a bit messy right now. Since scons will provide + # --DESTDIR option soon, at least the dest_dir handling can be + # removed later. + # + # how to join dest_dir and prefix + def joinPaths(path1, path2): + ''' join path1 and path2, do not use os.path.join because + under window, c:\destdir\d:\program is invalid ''' + if path1 is None: + return os.path.normpath(path2) + # separate drive letter + (drive, path) = os.path.splitdrive(os.path.normpath(path2)) + # ignore drive letter, so c:\destdir + c:\program = c:\destdir\program + return os.path.join(os.path.normpath(path1), path[1:]) + # + # install to dest_dir/prefix + dest_dir = env.get('DESTDIR', None) + dest_prefix_dir = joinPaths(dest_dir, env.Dir(prefix).abspath) + # create the directory if needed + if not os.path.isdir(dest_prefix_dir): + try: + os.makedirs(dest_prefix_dir) + except: + pass + if not os.path.isdir(dest_prefix_dir): + print 'Can not create directory', dest_prefix_dir + Exit(3) + # + if env.has_key('exec_prefix'): + bin_dest_dir = joinPaths(dest_dir, Dir(env['exec_prefix']).abspath) + else: + bin_dest_dir = os.path.join(dest_prefix_dir, 'bin') + if add_suffix: + share_dest_dir = os.path.join(dest_prefix_dir, share_dir + program_suffix) + else: + share_dest_dir = os.path.join(dest_prefix_dir, share_dir) + man_dest_dir = os.path.join(dest_prefix_dir, man_dir) + locale_dest_dir = os.path.join(dest_prefix_dir, locale_dir) + # + import glob + # + # install executables (lyxclient may be None) + # + if add_suffix: + version_suffix = program_suffix + else: + version_suffix = '' + # + # install lyx + target_name = os.path.split(str(lyx[0]))[1].replace('lyx', 'lyx%s' % version_suffix) + target = os.path.join(bin_dest_dir, target_name) + env.InstallAs(target, lyx) + Alias('install', target) + # + # install tex2lyx + target_name = os.path.split(str(tex2lyx[0]))[1].replace('tex2lyx', 'tex2lyx%s' % version_suffix) + target = os.path.join(bin_dest_dir, target_name) + env.InstallAs(target, tex2lyx) + Alias('install', target) + # + # install lyxclient, may not exist + if client != None: + target_name = os.path.split(str(client[0]))[1].replace('client', 'client%s' % version_suffix) + target = os.path.join(bin_dest_dir, target_name) + env.InstallAs(target, client) + Alias('install', target) + # + # share/lyx + dirs = [] + for (dir,files) in [ + ('.', lib_files), + ('clipart', lib_clipart_files), + ('examples', lib_examples_files), + ('images', lib_images_files), + ('images/math', lib_images_math_files), + ('bind', lib_bind_files), + ('kbd', lib_kbd_files), + ('layouts', lib_layouts_files), + ('scripts', lib_scripts_files), + ('templates', lib_templates_files), + ('tex', lib_tex_files), + ('ui', lib_ui_files), + ('doc', lib_doc_files), + ('lyx2lyx', lib_lyx2lyx_files)]: + dirs.append(env.Install(os.path.join(share_dest_dir, dir), + [env.subst('$TOP_SRCDIR/lib/%s/%s' % (dir, file)) for file in files])) + + # lyx1.4.x does not have lyx2lyx_version.py.in + if os.path.isfile(env.subst('$TOP_SRCDIR/lib/lyx2lyx/lyx2lyx_version.py.in')): + # subst and install this file + env.substFile(share_dest_dir + '/lyx2lyx/lyx2lyx_version.py', + '$TOP_SRCDIR/lib/lyx2lyx/lyx2lyx_version.py.in') + Alias('install', share_dest_dir + '/lyx2lyx/lyx2lyx_version.py') + Alias('install', dirs) + # man + env.InstallAs(os.path.join(man_dest_dir, 'lyx' + version_suffix + '.1'), + env.subst('$TOP_SRCDIR/lyx.man')) + env.InstallAs(os.path.join(man_dest_dir, 'tex2lyx' + version_suffix + '.1'), + env.subst('$TOP_SRCDIR/src/tex2lyx/tex2lyx.man')) + env.InstallAs(os.path.join(man_dest_dir, 'lyxclient' + version_suffix + '.1'), + env.subst('$TOP_SRCDIR/src/client/lyxclient.man')) + Alias('install', [os.path.join(man_dest_dir, x + version_suffix + '.1') for + x in ['lyx', 'tex2lyx', 'lyxclient']]) + # locale files? + # ru.gmo ==> ru/LC_MESSAGES/lyxSUFFIX.mo + for gmo in gmo_files: + lan = os.path.split(str(gmo))[1].split('.')[0] + dest_file = os.path.join(locale_dest_dir, lan, 'LC_MESSAGES', 'lyx' + version_suffix + '.mo') + env.InstallAs(dest_file, gmo) + Alias('install', dest_file) + + +Default('lyx') +Alias('all', ['lyx', 'client', 'tex2lyx']) diff --git a/development/scons/scons_manifest.py b/development/scons/scons_manifest.py new file mode 100644 index 0000000000..36238e01d6 --- /dev/null +++ b/development/scons/scons_manifest.py @@ -0,0 +1,2248 @@ +from SCons.Util import Split + +intl_header_files = Split(''' + eval-plural.h + gettextP.h + gmo.h + hash-string.h + libgnuintl.h + libintl.h + loadinfo.h + localcharset.h + os2compat.h + plural-exp.h + printf-args.h + printf-parse.h + relocatable.h + vasnprintf.h + vasnwprintf.h + wprintf-parse.h + xsize.h +''') + + +intl_files = Split(''' + bindtextdom.c + dcgettext.c + dcigettext.c + dcngettext.c + dgettext.c + dngettext.c + explodename.c + finddomain.c + gettext.c + intl-compat.c + l10nflist.c + loadmsgcat.c + localcharset.c + localealias.c + localename.c + log.c + ngettext.c + osdep.c + plural-exp.c + plural.c + printf.c + relocatable.c + textdomain.c +''') + + +boost_libs_signals_src_files = Split(''' + connection.cpp + named_slot_map.cpp + signal_base.cpp + slot.cpp + trackable.cpp +''') + + +boost_libs_regex_src_files = Split(''' + c_regex_traits.cpp + c_regex_traits_common.cpp + cpp_regex_traits.cpp + cregex.cpp + fileiter.cpp + instances.cpp + posix_api.cpp + regex.cpp + regex_debug.cpp + regex_synch.cpp + w32_regex_traits.cpp + wide_posix_api.cpp + winstances.cpp +''') + + +boost_libs_filesystem_src_files = Split(''' + convenience.cpp + exception.cpp + operations_posix_windows.cpp + path_posix_windows.cpp +''') + + +boost_libs_iostreams_src_files = Split(''' + file_descriptor.cpp + mapped_file.cpp + zlib.cpp +''') + + +src_support_header_files = Split(''' + FileMonitor.h + RandomAccessList.h + convert.h + copied_ptr.h + cow_ptr.h + debugstream.h + environment.h + gzstream.h + filefilterlist.h + filename.h + filetools.h + forkedcall.h + forkedcallqueue.h + forkedcontr.h + fs_extras.h + limited_stack.h + lstrings.h + lyxalgo.h + lyxlib.h + lyxmanip.h + lyxtime.h + os.h + os_win32.h + package.h + path.h + socktools.h + std_istream.h + std_ostream.h + systemcall.h + textutils.h + translator.h + types.h + userinfo.h +''') + + +src_support_files = Split(''' + FileMonitor.C + abort.C + chdir.C + convert.C + copy.C + environment.C + filefilterlist.C + filename.C + filetools.C + forkedcall.C + forkedcallqueue.C + forkedcontr.C + fs_extras.C + getcwd.C + gzstream.C + kill.C + lstrings.C + lyxsum.C + lyxtime.C + mkdir.C + os.C + package.C + path.C + rename.C + socktools.C + systemcall.C + tempname.C + unlink.C + userinfo.C +''') + + +src_mathed_header_files = Split(''' + command_inset.h + formulamacro.h + math_amsarrayinset.h + math_arrayinset.h + math_atom.h + math_autocorrect.h + math_biginset.h + math_binominset.h + math_boldsymbolinset.h + math_boxedinset.h + math_boxinset.h + math_braceinset.h + math_casesinset.h + math_charinset.h + math_colorinset.h + math_commentinset.h + math_data.h + math_decorationinset.h + math_deliminset.h + math_dfracinset.h + math_diffinset.h + math_diminset.h + math_dotsinset.h + math_envinset.h + math_exfuncinset.h + math_exintinset.h + math_extern.h + math_factory.h + math_fboxinset.h + math_fontinset.h + math_fontoldinset.h + math_fracbase.h + math_fracinset.h + math_frameboxinset.h + math_gridinfo.h + math_gridinset.h + math_hullinset.h + math_inset.h + math_kerninset.h + math_lefteqninset.h + math_liminset.h + math_macro.h + math_macroarg.h + math_macrotable.h + math_macrotemplate.h + math_makeboxinset.h + math_mathmlstream.h + math_matrixinset.h + math_mboxinset.h + math_nestinset.h + math_numberinset.h + math_oversetinset.h + math_parinset.h + math_parser.h + math_replace.h + math_rootinset.h + math_scriptinset.h + math_sizeinset.h + math_spaceinset.h + math_splitinset.h + math_sqrtinset.h + math_stackrelinset.h + math_streamstr.h + math_stringinset.h + math_substackinset.h + math_support.h + math_symbolinset.h + math_tabularinset.h + math_tfracinset.h + math_undersetinset.h + math_unknowninset.h + math_xarrowinset.h + math_xyarrowinset.h + math_xymatrixinset.h + ref_inset.h + textpainter.h +''') + + +src_mathed_files = Split(''' + command_inset.C + math_amsarrayinset.C + math_arrayinset.C + math_atom.C + math_autocorrect.C + math_biginset.C + math_binominset.C + math_boldsymbolinset.C + math_boxedinset.C + math_boxinset.C + math_braceinset.C + math_casesinset.C + math_charinset.C + math_colorinset.C + math_commentinset.C + math_data.C + math_decorationinset.C + math_deliminset.C + math_dfracinset.C + math_diffinset.C + math_diminset.C + math_dotsinset.C + math_envinset.C + math_exfuncinset.C + math_exintinset.C + math_extern.C + math_factory.C + math_fboxinset.C + math_fontinset.C + math_fontoldinset.C + math_fracbase.C + math_fracinset.C + math_frameboxinset.C + math_gridinset.C + math_hullinset.C + math_inset.C + math_kerninset.C + math_lefteqninset.C + math_liminset.C + math_macro.C + math_macroarg.C + math_macrotable.C + math_macrotemplate.C + math_makeboxinset.C + math_mathmlstream.C + math_matrixinset.C + math_nestinset.C + math_numberinset.C + math_oversetinset.C + math_parinset.C + math_parser.C + math_rootinset.C + math_scriptinset.C + math_sizeinset.C + math_spaceinset.C + math_splitinset.C + math_sqrtinset.C + math_stackrelinset.C + math_streamstr.C + math_stringinset.C + math_substackinset.C + math_support.C + math_symbolinset.C + math_tabularinset.C + math_tfracinset.C + math_undersetinset.C + math_unknowninset.C + math_xarrowinset.C + math_xymatrixinset.C + ref_inset.C + textpainter.C +''') + + +src_insets_header_files = Split(''' + ExternalSupport.h + ExternalTemplate.h + ExternalTransforms.h + inset.h + insetbase.h + insetbibitem.h + insetbibtex.h + insetbox.h + insetbranch.h + insetcaption.h + insetcharstyle.h + insetcite.h + insetcollapsable.h + insetcommand.h + insetcommandparams.h + insetenv.h + insetert.h + insetexternal.h + insetfloat.h + insetfloatlist.h + insetfoot.h + insetfootlike.h + insetgraphics.h + insetgraphicsParams.h + insethfill.h + insetinclude.h + insetindex.h + insetlabel.h + insetlatexaccent.h + insetline.h + insetmarginal.h + insetnewline.h + insetnote.h + insetoptarg.h + insetpagebreak.h + insetquotes.h + insetref.h + insetspace.h + insetspecialchar.h + insettabular.h + insettext.h + insettheorem.h + insettoc.h + inseturl.h + insetvspace.h + insetwrap.h + mailinset.h + render_base.h + render_button.h + render_graphic.h + render_preview.h +''') + + +src_insets_files = Split(''' + ExternalSupport.C + ExternalTemplate.C + ExternalTransforms.C + inset.C + insetbase.C + insetbibitem.C + insetbibtex.C + insetbox.C + insetbranch.C + insetcaption.C + insetcharstyle.C + insetcite.C + insetcollapsable.C + insetcommand.C + insetcommandparams.C + insetenv.C + insetert.C + insetexternal.C + insetfloat.C + insetfloatlist.C + insetfoot.C + insetfootlike.C + insetgraphics.C + insetgraphicsParams.C + insethfill.C + insetinclude.C + insetindex.C + insetlabel.C + insetlatexaccent.C + insetline.C + insetmarginal.C + insetnewline.C + insetnote.C + insetoptarg.C + insetpagebreak.C + insetquotes.C + insetref.C + insetspace.C + insetspecialchar.C + insettabular.C + insettext.C + insettoc.C + inseturl.C + insetvspace.C + insetwrap.C + mailinset.C + render_button.C + render_graphic.C + render_preview.C +''') + + +src_frontends_header_files = Split(''' + Alert.h + Alert_pimpl.h + Clipboard.h + Dialogs.h + FileDialog.h + Gui.h + LyXKeySym.h + LyXKeySymFactory.h + LyXScreenFactory.h + LyXView.h + Menubar.h + Painter.h + Selection.h + Timeout.h + Toolbars.h + WorkArea.h + WorkAreaFactory.h + font_metrics.h + guiapi.h + key_state.h + lyx_gui.h + mouse_state.h + nullpainter.h + screen.h +''') + + +src_frontends_files = Split(''' + Alert.C + Dialogs.C + LyXView.C + Painter.C + Timeout.C + Toolbars.C + guiapi.C + nullpainter.C + screen.C +''') + + +src_graphics_header_files = Split(''' + GraphicsCache.h + GraphicsCacheItem.h + GraphicsConverter.h + GraphicsImage.h + GraphicsLoader.h + GraphicsParams.h + GraphicsTypes.h + LoaderQueue.h + PreviewImage.h + PreviewLoader.h + Previews.h +''') + + +src_graphics_files = Split(''' + GraphicsCache.C + GraphicsCacheItem.C + GraphicsConverter.C + GraphicsImage.C + GraphicsLoader.C + GraphicsParams.C + GraphicsTypes.C + LoaderQueue.C + PreviewImage.C + PreviewLoader.C + Previews.C +''') + + +src_frontends_controllers_header_files = Split(''' + BCView.h + ButtonController.h + ButtonPolicies.h + ControlAboutlyx.h + ControlBibtex.h + ControlBox.h + ControlBranch.h + ControlChanges.h + ControlCharacter.h + ControlCitation.h + ControlCommand.h + ControlCommandBuffer.h + ControlDocument.h + ControlERT.h + ControlErrorList.h + ControlExternal.h + ControlFloat.h + ControlGraphics.h + ControlInclude.h + ControlLog.h + ControlMath.h + ControlNote.h + ControlParagraph.h + ControlPrefs.h + ControlPrint.h + ControlRef.h + ControlSearch.h + ControlSendto.h + ControlShowFile.h + ControlSpellchecker.h + ControlTabular.h + ControlTabularCreate.h + ControlTexinfo.h + ControlThesaurus.h + ControlToc.h + ControlVSpace.h + ControlWrap.h + Dialog.h + Kernel.h + biblio.h + character.h + frnt_lang.h + helper_funcs.h + tex_helpers.h +''') + + +src_frontends_controllers_files = Split(''' + BCView.C + ButtonController.C + ButtonPolicies.C + ControlAboutlyx.C + ControlBibtex.C + ControlBox.C + ControlBranch.C + ControlChanges.C + ControlCharacter.C + ControlCitation.C + ControlCommand.C + ControlCommandBuffer.C + ControlDocument.C + ControlERT.C + ControlErrorList.C + ControlExternal.C + ControlFloat.C + ControlGraphics.C + ControlInclude.C + ControlLog.C + ControlMath.C + ControlNote.C + ControlParagraph.C + ControlPrefs.C + ControlPrint.C + ControlRef.C + ControlSearch.C + ControlSendto.C + ControlShowFile.C + ControlSpellchecker.C + ControlTabular.C + ControlTabularCreate.C + ControlTexinfo.C + ControlThesaurus.C + ControlToc.C + ControlVSpace.C + ControlWrap.C + Dialog.C + Kernel.C + biblio.C + character.C + frnt_lang.C + helper_funcs.C + tex_helpers.C +''') + + +src_frontends_qt2_ui_files = Split(''' + BiblioModuleBase.ui + BranchesModuleBase.ui + BulletsModuleBase.ui + LaTeXModuleBase.ui + LanguageModuleBase.ui + MarginsModuleBase.ui + MathsModuleBase.ui + NumberingModuleBase.ui + PageLayoutModuleBase.ui + PreambleModuleBase.ui + QAboutDialogBase.ui + QAskForTextDialog.ui + QBibitemDialogBase.ui + QBibtexAddDialogBase.ui + QBibtexDialogBase.ui + QBoxDialogBase.ui + QBranchDialogBase.ui + QChangesDialogBase.ui + QCharacterDialogBase.ui + QCitationDialogBase.ui + QCitationFindDialogBase.ui + QDelimiterDialogBase.ui + QDocumentDialogBase.ui + QERTDialogBase.ui + QErrorListDialogBase.ui + QExternalDialogBase.ui + QFloatDialogBase.ui + QGraphicsDialogBase.ui + QIncludeDialogBase.ui + QIndexDialogBase.ui + QLogDialogBase.ui + QMathDialogBase.ui + QMathMatrixDialogBase.ui + QNoteDialogBase.ui + QParagraphDialogBase.ui + QPrefAsciiModule.ui + QPrefColorsModule.ui + QPrefConvertersModule.ui + QPrefCopiersModule.ui + QPrefCygwinPathModule.ui + QPrefDateModule.ui + QPrefDisplayModule.ui + QPrefFileformatsModule.ui + QPrefIdentityModule.ui + QPrefKeyboardModule.ui + QPrefLanguageModule.ui + QPrefLatexModule.ui + QPrefPathsModule.ui + QPrefPrinterModule.ui + QPrefScreenFontsModule.ui + QPrefSpellcheckerModule.ui + QPrefUIModule.ui + QPrefsDialogBase.ui + QPrintDialogBase.ui + QRefDialogBase.ui + QSearchDialogBase.ui + QSendtoDialogBase.ui + QShowFileDialogBase.ui + QSpellcheckerDialogBase.ui + QTabularCreateDialogBase.ui + QTabularDialogBase.ui + QTexinfoDialogBase.ui + QThesaurusDialogBase.ui + QTocDialogBase.ui + QURLDialogBase.ui + QVSpaceDialogBase.ui + QWrapDialogBase.ui + TextLayoutModuleBase.ui +''') + + +src_frontends_qt2_moc_files = Split(''' + BulletsModule.C + emptytable.C + FileDialog_private.C + floatplacement.C + iconpalette.C + lengthcombo.C + panelstack.C + QAboutDialog.C + QBibitemDialog.C + QBibtexDialog.C + QBoxDialog.C + QBranchDialog.C + QBrowseBox.C + QChangesDialog.C + QCharacterDialog.C + QCitationDialog.C + QCommandBuffer.C + QCommandEdit.C + QContentPane.C + QDelimiterDialog.C + QDocumentDialog.C + QErrorListDialog.C + QERTDialog.C + QExternalDialog.C + QFloatDialog.C + QGraphicsDialog.C + QIncludeDialog.C + QIndexDialog.C + QLogDialog.C + QLPopupMenu.C + QLPrintDialog.C + QMathDialog.C + QMathMatrixDialog.C + QNoteDialog.C + QParagraphDialog.C + QPrefsDialog.C + QRefDialog.C + QSearchDialog.C + QSendtoDialog.C + qsetborder.C + QShowFileDialog.C + QSpellcheckerDialog.C + QDialogView.C + QTabularCreateDialog.C + QTabularDialog.C + QTexinfoDialog.C + QThesaurusDialog.C + QTocDialog.C + qttableview.C + QtView.C + QURLDialog.C + QVSpaceDialog.C + QWrapDialog.C + QLToolbar.C + socket_callback.C + validators.C +''') + + +src_frontends_qt2_header_files = Split(''' + BulletsModule.h + FileDialog_private.h + GuiImplementation.h + GuiSelection.h + GuiWorkArea.h + QAbout.h + QAboutDialog.h + QBibitem.h + QBibitemDialog.h + QBibtex.h + QBibtexDialog.h + QBox.h + QBoxDialog.h + QBranch.h + QBranchDialog.h + QBrowseBox.h + QChanges.h + QChangesDialog.h + QCharacter.h + QCharacterDialog.h + QCitation.h + QCitationDialog.h + QCommandBuffer.h + QCommandEdit.h + QContentPane.h + QDelimiterDialog.h + QDialogView.h + QDocument.h + QDocumentDialog.h + QERT.h + QERTDialog.h + QErrorList.h + QErrorListDialog.h + QExternal.h + QExternalDialog.h + QFloat.h + QFloatDialog.h + QGraphics.h + QGraphicsDialog.h + QInclude.h + QIncludeDialog.h + QIndex.h + QIndexDialog.h + QLImage.h + QLMenubar.h + QLPainter.h + QLPopupMenu.h + QLPrintDialog.h + QLToolbar.h + QLog.h + QLogDialog.h + QLyXKeySym.h + QMath.h + QMathDialog.h + QMathMatrixDialog.h + QNote.h + QNoteDialog.h + QParagraph.h + QParagraphDialog.h + QPrefs.h + QPrefsDialog.h + QPrint.h + QRef.h + QRefDialog.h + QSearch.h + QSearchDialog.h + QSendto.h + QSendtoDialog.h + QShowFile.h + QShowFileDialog.h + QSpellchecker.h + QSpellcheckerDialog.h + QTabular.h + QTabularCreate.h + QTabularCreateDialog.h + QTabularDialog.h + QTexinfo.h + QTexinfoDialog.h + QThesaurus.h + QThesaurusDialog.h + QToc.h + QTocDialog.h + QURL.h + QURLDialog.h + QVSpace.h + QVSpaceDialog.h + QWorkArea.h + QWrap.h + QWrapDialog.h + Qt2BC.h + QtLyXView.h + QtView.h + checkedwidgets.h + emptytable.h + floatplacement.h + iconpalette.h + lcolorcache.h + lengthcombo.h + panelstack.h + qcoloritem.h + qfont_loader.h + qfontexample.h + qlkey.h + qscreen.h + qsetborder.h + qtTimeout.h + qt_helpers.h + qttableview.h + socket_callback.h + validators.h +''') + + +src_frontends_qt2_files = Split(''' + Alert_pimpl.C + BulletsModule.C + Dialogs.C + FileDialog.C + FileDialog_private.C + LyXKeySymFactory.C + LyXScreenFactory.C + QAbout.C + QAboutDialog.C + QBibitem.C + QBibitemDialog.C + QBibtex.C + QBibtexDialog.C + QBox.C + QBoxDialog.C + QBranch.C + QBranchDialog.C + QBrowseBox.C + QChanges.C + QChangesDialog.C + QCharacter.C + QCharacterDialog.C + QCitation.C + QCitationDialog.C + QCommandBuffer.C + QCommandEdit.C + QContentPane.C + QDelimiterDialog.C + QDialogView.C + QDocument.C + QDocumentDialog.C + QERT.C + QERTDialog.C + QErrorList.C + QErrorListDialog.C + QExternal.C + QExternalDialog.C + QFloat.C + QFloatDialog.C + QGraphics.C + QGraphicsDialog.C + QInclude.C + QIncludeDialog.C + QIndex.C + QIndexDialog.C + QLImage.C + QLMenubar.C + QLPainter.C + QLPopupMenu.C + QLPrintDialog.C + QLToolbar.C + QLog.C + QLogDialog.C + QLyXKeySym.C + QMath.C + QMathDialog.C + QMathMatrixDialog.C + QNote.C + QNoteDialog.C + QParagraph.C + QParagraphDialog.C + QPrefs.C + QPrefsDialog.C + QPrint.C + QRef.C + QRefDialog.C + QSearch.C + QSearchDialog.C + QSendto.C + QSendtoDialog.C + QShowFile.C + QShowFileDialog.C + QSpellchecker.C + QSpellcheckerDialog.C + QTabular.C + QTabularCreate.C + QTabularCreateDialog.C + QTabularDialog.C + QTexinfo.C + QTexinfoDialog.C + QThesaurus.C + QThesaurusDialog.C + QToc.C + QTocDialog.C + QURL.C + QURLDialog.C + QVSpace.C + QVSpaceDialog.C + QWorkArea.C + QWrap.C + QWrapDialog.C + Qt2BC.C + QtView.C + checkedwidgets.C + emptytable.C + floatplacement.C + iconpalette.C + lcolorcache.C + lengthcombo.C + lyx_gui.C + panelstack.C + qcoloritem.C + qfont_loader.C + qfont_metrics.C + qfontexample.C + qscreen.C + qsetborder.C + qtTimeout.C + qt_helpers.C + qttableview.C + socket_callback.C + validators.C + WorkAreaFactory.C +''') + + +src_client_header_files = Split(''' + debug.h + gettext.h + messages.h +''') + + +src_client_files = Split(''' + boost.C + client.C + debug.C + gettext.C + messages.C +''') + + +src_tex2lyx_header_files = Split(''' + Spacing.h + context.h + gettext.h + lyxfont.h + tex2lyx.h + texparser.h +''') + + +src_tex2lyx_files = Split(''' + FloatList.C + Floating.C + boost.C + context.C + counters.C + gettext.C + lengthcommon.C + lyxfont.C + lyxlayout.C + lyxlex.C + lyxlex_pimpl.C + lyxtextclass.C + math.C + preamble.C + table.C + tex2lyx.C + texparser.C + text.C +''') + + +src_header_files = Split(''' + Bidi.h + BranchList.h + BufferView.h + BufferView_pimpl.h + Bullet.h + Chktex.h + CutAndPaste.h + DepTable.h + FloatList.h + Floating.h + FontIterator.h + FuncStatus.h + InsetList.h + LColor.h + LaTeX.h + LaTeXFeatures.h + LyXAction.h + MenuBackend.h + ParagraphList.h + ParagraphList_fwd.h + ParagraphParameters.h + PrinterParams.h + RowList_fwd.h + Sectioning.h + Spacing.h + SpellBase.h + Thesaurus.h + ToolbarBackend.h + Variables.h + WordLangTuple.h + aspell_local.h + author.h + box.h + buffer.h + buffer_funcs.h + bufferlist.h + bufferparams.h + bufferview_funcs.h + changes.h + chset.h + converter.h + coordcache.h + counters.h + cursor.h + cursor_slice.h + debug.h + dimension.h + dispatchresult.h + dociterator.h + encoding.h + errorlist.h + exporter.h + factory.h + format.h + funcrequest.h + gettext.h + graph.h + importer.h + insetiterator.h + intl.h + ispell.h + kbmap.h + kbsequence.h + language.h + layout.h + lengthcommon.h + lfuns.h + lyx_cb.h + lyx_main.h + lyx_sty.h + lyxfind.h + lyxfont.h + lyxfunc.h + lyxgluelength.h + lyxlayout.h + lyxlayout_ptr_fwd.h + lyxlength.h + lyxlex.h + lyxlex_pimpl.h + lyxrc.h + lyxrow.h + lyxrow_funcs.h + lyxserver.h + lyxsocket.h + lyxtext.h + lyxtextclass.h + lyxtextclasslist.h + lyxvc.h + messages.h + metricsinfo.h + mover.h + output.h + output_docbook.h + output_latex.h + output_linuxdoc.h + output_plaintext.h + outputparams.h + paper.h + paragraph.h + paragraph_funcs.h + paragraph_pimpl.h + pariterator.h + pspell.h + rowpainter.h + lastfiles.h + sgml.h + tabular.h + tex-accent.h + tex-strings.h + texrow.h + toc.h + trans.h + trans_decl.h + trans_mgr.h + undo.h + vc-backend.h + version.h + vspace.h +''') + + +src_pre_files = Split(''' + Bidi.C + BranchList.C + BufferView.C + BufferView_pimpl.C + Bullet.C + Chktex.C + CutAndPaste.C + DepTable.C + FloatList.C + Floating.C + FontIterator.C + FuncStatus.C + InsetList.C + LColor.C + LaTeX.C + LaTeXFeatures.C + LyXAction.C + MenuBackend.C + ParagraphParameters.C + Spacing.C + ToolbarBackend.C + author.C + boost.C + buffer.C + buffer_funcs.C + bufferlist.C + bufferparams.C + bufferview_funcs.C + changes.C + chset.C + converter.C + coordcache.C + counters.C + cursor.C + cursor_slice.C + debug.C + dociterator.C + encoding.C + errorlist.C + exporter.C + factory.C + format.C + funcrequest.C + gettext.C + graph.C + importer.C + insetiterator.C + intl.C + kbmap.C + kbsequence.C + language.C + lengthcommon.C + lyx_cb.C + lyx_main.C + lyx_sty.C + lyxfind.C + lyxfont.C + lyxfunc.C + lyxgluelength.C + lyxlayout.C + lyxlength.C + lyxlex.C + lyxlex_pimpl.C + lyxrc.C + lyxrow.C + lyxrow_funcs.C + lyxserver.C + lyxsocket.C + lyxtextclass.C + lyxtextclasslist.C + lyxvc.C + messages.C + metricsinfo.C + mover.C + output.C + output_docbook.C + output_latex.C + output_linuxdoc.C + output_plaintext.C + outputparams.C + paragraph.C + paragraph_funcs.C + paragraph_pimpl.C + pariterator.C + rowpainter.C + lastfiles.C + sgml.C + tex-accent.C + tex-strings.C + texrow.C + text.C + text2.C + text3.C + toc.C + trans.C + trans_mgr.C + undo.C + vc-backend.C + version.C + vspace.C +''') + + +src_post_files = Split(''' + tabular.C + dimension.C + PrinterParams.C + box.C + Thesaurus.C + SpellBase.C +''') + + +lib_files = Split(''' + lyxrc.example + CREDITS + chkconfig.ltx + external_templates + encodings + languages + symbols + syntax.default + configure.py +''') + + +# do not install, ignore +lib_image_noinst_files = Split(''' + images/README + images/font-smallcaps.xpm + images/math/ams_arrows.xbm + images/math/ams_misc.xbm + images/math/ams_nrel.xbm + images/math/ams_ops.xbm + images/math/ams_rel.xbm + images/math/arrows.xbm + images/math/bop.xbm + images/math/brel.xbm + images/math/deco.xbm + images/math/deco.xpm + images/math/delim0.xpm + images/math/delim1.xpm + images/math/delim.xbm + images/math/dots.xbm + images/math/font.xbm + images/math/frac-square.xpm + images/math/greek.xbm + images/math/misc.xbm + images/math/varsz.xbm +''') + + +lib_bind_files = Split(''' + broadway.bind + cua.bind + cyrkeys.bind + de_menus.bind + emacs.bind + fi_menus.bind + greekkeys.bind + hollywood.bind + latinkeys.bind + mac.bind + math.bind + menus.bind + pt_menus.bind + sciword.bind + sv_menus.bind + xemacs.bind + aqua.bind +''') + +lib_clipart_files = ['platypus.eps'] + + +lib_examples_files = Split(''' + Foils.lyx + ItemizeBullets.lyx + Literate.lyx + Minipage.lyx + TableExamples.lyx + aa_sample.lyx + aas_sample.lyx + amsart-test.lyx + amsbook-test.lyx + ca_splash.lyx + chess-article.lyx + chessgame.lyx + cs_splash.lyx + currency.lyx + cv.lyx + da_splash.lyx + de_ItemizeBullets.lyx + de_Lebenslauf.lyx + de_Minipage.lyx + de_TableExamples.lyx + de_Waehrungen.lyx + de_beispiel_gelyxt.lyx + de_beispiel_roh.lyx + de_decimal.lyx + de_splash.lyx + de_mathed.lyx + de_multicol.lyx + decimal.lyx + docbook_article.lyx + es_ejemplo_con_lyx.lyx + es_ejemplo_sin_lyx.lyx + es_splash.lyx + eu_adibide_gordina.lyx + eu_adibide_lyx-atua.lyx + eu_splash.lyx + example_lyxified.lyx + example_raw.lyx + fr_AlignementDecimal.lyx + fr_CV.lyx + fr_ExemplesTableaux.lyx + fr_Foils.lyx + fr_ListesPuces.lyx + fr_Minipage.lyx + fr_exemple_brut.lyx + fr_exemple_lyxifie.lyx + fr_mathed.lyx + fr_multicol.lyx + fr_splash.lyx + he_example_raw.lyx + he_he_example_lyxified.lyx + he_he_example_raw.lyx + hu_splash.lyx + iecc05.fen + iecc07.fen + iecc12.fen + it_ItemizeBullets.lyx + it_splash.lyx + landslide.lyx + linuxdoc_manpage.lyx + listerrors.lyx + mathed.lyx + multicol.lyx + nl_multicol.lyx + nl_opsommingstekens.lyx + nl_splash.lyx + nl_voorbeeld_ruw.lyx + nl_voorbeeld_verlyxt.lyx + noweb2lyx.lyx + pl_splash.lyx + pt_splash.lyx + ru_splash.lyx + script_form.lyx + sl_primer_lyxan.lyx + sl_primer_surov.lyx + sl_splash.lyx + splash.lyx + g-brief2.lyx + ro_splash.lyx +''') + + +lib_images_files = Split(''' + amssymb.xpm + banner.ppm + bookmark-goto.xpm + bookmark-save.xpm + break-line.xpm + buffer-close.xpm + buffer-export_dvi.xpm + buffer-export_latex.xpm + buffer-export_ps.xpm + buffer-export_text.xpm + buffer-new.xpm + buffer-reload.xpm + buffer-update_dvi.xpm + buffer-update_ps.xpm + buffer-view_dvi.xpm + buffer-view_ps.xpm + buffer-write-as.xpm + buffer-write.xpm + build-program.xpm + copy.xpm + cut.xpm + depth-decrement.xpm + depth-increment.xpm + dialog-preferences.xpm + dialog-show-new-inset_citation.xpm + dialog-show-new-inset_graphics.xpm + dialog-show-new-inset_include.xpm + dialog-show-new-inset_ref.xpm + dialog-show_character.xpm + dialog-show_findreplace.xpm + dialog-show_mathpanel.xpm + dialog-show_print.xpm + dialog-show_spellchecker.xpm + down.xpm + ert-insert.xpm + file-open.xpm + float-insert_figure.xpm + float-insert_table.xpm + font-bold.xpm + font-emph.xpm + font-free-apply.xpm + font-noun.xpm + font-sans.xpm + footnote-insert.xpm + index-insert.xpm + label-insert.xpm + layout-document.xpm + layout-paragraph.xpm + layout_Description.xpm + layout_Enumerate.xpm + layout_Itemize.xpm + layout_List.xpm + layout_LyX-Code.xpm + layout_Scrap.xpm + layout_Section.xpm + lyx-quit.xpm + lyx.xpm + marginalnote-insert.xpm + math-display.xpm + math-matrix.xpm + math-mode.xpm + math-subscript.xpm + math-superscript.xpm + note-insert.xpm + paste.xpm + psnfss1.xpm + psnfss2.xpm + psnfss3.xpm + psnfss4.xpm + redo.xpm + standard.xpm + tabular-feature_align-center.xpm + tabular-feature_align-left.xpm + tabular-feature_align-right.xpm + tabular-feature_append-column.xpm + tabular-feature_append-row.xpm + tabular-feature_delete-column.xpm + tabular-feature_delete-row.xpm + tabular-feature_multicolumn.xpm + tabular-feature_set-all-lines.xpm + tabular-feature_set-longtabular.xpm + tabular-feature_set-rotate-cell.xpm + tabular-feature_set-rotate-tabular.xpm + tabular-feature_toggle-line-bottom.xpm + tabular-feature_toggle-line-left.xpm + tabular-feature_toggle-line-right.xpm + tabular-feature_toggle-line-top.xpm + tabular-feature_unset-all-lines.xpm + tabular-feature_valign-bottom.xpm + tabular-feature_valign-middle.xpm + tabular-feature_valign-top.xpm + tabular-insert.xpm + thesaurus-entry.xpm + toc-view.xpm + undo.xpm + unknown.xpm + up.xpm + url-insert.xpm +''') + + +lib_images_math_files = Split(''' + Game.xpm + Im.xpm + Lleftarrow.xpm + Lsh.xpm + Re.xpm + Rsh.xpm + Vert.xpm + Vvdash.xpm + acute.xpm + aleph.xpm + alpha.xpm + amalg.xpm + angle.xpm + approx.xpm + approxeq.xpm + asymp.xpm + backepsilon.xpm + backprime.xpm + backsim.xpm + backsimeq.xpm + backslash.xpm + bar.xpm + bars.xpm + barwedge.xpm + because.xpm + beta.xpm + beth.xpm + between.xpm + bigcap.xpm + bigcirc.xpm + bigcup.xpm + bigodot.xpm + bigoplus.xpm + bigotimes.xpm + bigsqcup.xpm + bigstar.xpm + bigtriangledown.xpm + bigtriangleup.xpm + biguplus.xpm + bigvee.xpm + bigwedge.xpm + blacklozenge.xpm + blacksquare.xpm + blacktriangle.xpm + blacktriangledown.xpm + blacktriangleleft.xpm + blacktriangleright.xpm + bot.xpm + bowtie.xpm + boxdot.xpm + boxminus.xpm + boxplus.xpm + boxtimes.xpm + breve.xpm + bullet.xpm + bumpeq.xpm + bumpeq2.xpm + cap.xpm + cap2.xpm + cases.xpm + cdot.xpm + cdots.xpm + centerdot.xpm + check.xpm + chi.xpm + circ.xpm + circeq.xpm + circlearrowleft.xpm + circlearrowright.xpm + circledS.xpm + circledast.xpm + circledcirc.xpm + circleddash.xpm + clubsuit.xpm + complement.xpm + cong.xpm + coprod.xpm + cup.xpm + cup2.xpm + curlyeqprec.xpm + curlyeqsucc.xpm + curlyvee.xpm + curlywedge.xpm + curvearrowleft.xpm + curvearrowright.xpm + dagger.xpm + daleth.xpm + dashleftarrow.xpm + dashrightarrow.xpm + dashv.xpm + ddagger.xpm + ddot.xpm + ddots.xpm + delta.xpm + delta2.xpm + diagdown.xpm + diagup.xpm + diamond.xpm + diamondsuit.xpm + digamma.xpm + div.xpm + divideontimes.xpm + dot.xpm + doteq.xpm + doteqdot.xpm + dotplus.xpm + doublebarwedge.xpm + downarrow.xpm + downarrow2.xpm + downdownarrows.xpm + downharpoonleft.xpm + downharpoonright.xpm + ell.xpm + empty.xpm + emptyset.xpm + epsilon.xpm + eqcirc.xpm + eqslantgtr.xpm + eqslantless.xpm + equiv.xpm + eta.xpm + eth.xpm + exists.xpm + fallingdotseq.xpm + flat.xpm + forall.xpm + frac.xpm + frown.xpm + gamma.xpm + gamma2.xpm + geq.xpm + geqq.xpm + geqslant.xpm + gg.xpm + ggg.xpm + gimel.xpm + gnapprox.xpm + gneq.xpm + gneqq.xpm + gnsim.xpm + grave.xpm + gtrapprox.xpm + gtrdot.xpm + gtreqless.xpm + gtreqqless.xpm + gtrless.xpm + gtrsim.xpm + gvertneqq.xpm + hat.xpm + hbar.xpm + heartsuit.xpm + hookleftarrow.xpm + hookrightarrow.xpm + hslash.xpm + imath.xpm + in.xpm + infty.xpm + int.xpm + intercal.xpm + iota.xpm + jmath.xpm + kappa.xpm + lambda.xpm + lambda2.xpm + langle.xpm + lbrace.xpm + lbrace_rbrace.xpm + lbracket.xpm + lbracket_rbracket.xpm + lceil.xpm + lceil_rceil.xpm + ldots.xpm + leftarrow.xpm + leftarrow2.xpm + leftarrowtail.xpm + leftharpoondown.xpm + leftharpoonup.xpm + leftleftarrows.xpm + leftrightarrow.xpm + leftrightarrow2.xpm + leftrightarrows.xpm + leftrightharpoons.xpm + leftrightsquigarrow.xpm + leftthreetimes.xpm + leq.xpm + leqq.xpm + leqslant.xpm + lessapprox.xpm + lessdot.xpm + lesseqgtr.xpm + lesseqqgtr.xpm + lessgtr.xpm + lesssim.xpm + lfloor.xpm + lfloor_rfloor.xpm + ll.xpm + llcorner.xpm + lll.xpm + lnapprox.xpm + lneq.xpm + lneqq.xpm + lnsim.xpm + longleftarrow.xpm + longleftarrow2.xpm + longleftrightarrow.xpm + longleftrightarrow2.xpm + longmapsto.xpm + longrightarrow.xpm + longrightarrow2.xpm + looparrowleft.xpm + looparrowright.xpm + lozenge.xpm + lparen.xpm + lparen_rparen.xpm + lrcorner.xpm + ltimes.xpm + lvertneqq.xpm + mapsto.xpm + mathbb_C.xpm + mathbb_H.xpm + mathbb_N.xpm + mathbb_Q.xpm + mathbb_R.xpm + mathbb_Z.xpm + mathcal_F.xpm + mathcal_H.xpm + mathcal_L.xpm + mathcal_O.xpm + mathcircumflex.xpm + mathrm_T.xpm + measuredangle.xpm + mho.xpm + mid.xpm + models.xpm + mp.xpm + mu.xpm + multimap.xpm + nabla.xpm + natural.xpm + ncong.xpm + nearrow.xpm + neg.xpm + neq.xpm + nexists.xpm + ngeq.xpm + ngeqq.xpm + ngeqslant.xpm + ngtr.xpm + ni.xpm + nleftarrow.xpm + nleftarrow2.xpm + nleftrightarrow.xpm + nleftrightarrow2.xpm + nleq.xpm + nleqq.xpm + nleqslant.xpm + nless.xpm + nmid.xpm + notin.xpm + nparallel.xpm + nprec.xpm + npreceq.xpm + nrightarrow.xpm + nrightarrow2.xpm + nshortmid.xpm + nshortparallel.xpm + nsim.xpm + nsubseteq.xpm + nsucc.xpm + nsucceq.xpm + nsupseteq.xpm + nsupseteqq.xpm + ntriangleleft.xpm + ntrianglelefteq.xpm + ntriangleright.xpm + ntrianglerighteq.xpm + nu.xpm + nvdash.xpm + nvdash2.xpm + nvdash3.xpm + nwarrow.xpm + odot.xpm + oint.xpm + omega.xpm + omega2.xpm + ominus.xpm + oplus.xpm + oslash.xpm + otimes.xpm + overbrace.xpm + overleftarrow.xpm + overleftrightarrow.xpm + overline.xpm + overrightarrow.xpm + overset.xpm + parallel.xpm + partial.xpm + perp.xpm + phi.xpm + phi2.xpm + pi.xpm + pi2.xpm + pitchfork.xpm + pm.xpm + prec.xpm + precapprox.xpm + preccurlyeq.xpm + preceq.xpm + precnapprox.xpm + precnsim.xpm + precsim.xpm + prime.xpm + prod.xpm + propto.xpm + psi.xpm + psi2.xpm + rangle.xpm + rbrace.xpm + rbracket.xpm + rceil.xpm + rfloor.xpm + rho.xpm + rightarrow.xpm + rightarrow2.xpm + rightarrowtail.xpm + rightharpoondown.xpm + rightharpoonup.xpm + rightleftarrows.xpm + rightleftharpoons.xpm + rightrightarrows.xpm + rightsquigarrow.xpm + rightthreetimes.xpm + risingdotseq.xpm + root.xpm + rparen.xpm + rtimes.xpm + searrow.xpm + setminus.xpm + sharp.xpm + shortmid.xpm + shortparallel.xpm + sigma.xpm + sigma2.xpm + sim.xpm + simeq.xpm + slash.xpm + smallfrown.xpm + smallsetminus.xpm + smallsmile.xpm + smile.xpm + spadesuit.xpm + sphericalangle.xpm + sqcap.xpm + sqcup.xpm + sqrt.xpm + sqsubset.xpm + sqsubseteq.xpm + sqsupset.xpm + sqsupseteq.xpm + square.xpm + star.xpm + subset.xpm + subset2.xpm + subseteq.xpm + subseteqq.xpm + subsetneq.xpm + subsetneqq.xpm + succ.xpm + succapprox.xpm + succcurlyeq.xpm + succeq.xpm + succnapprox.xpm + succnsim.xpm + succsim.xpm + sum.xpm + supset.xpm + supset2.xpm + supseteq.xpm + supseteqq.xpm + supsetneq.xpm + supsetneqq.xpm + surd.xpm + swarrow.xpm + tau.xpm + textrm_Oe.xpm + textrm_AA.xpm + therefore.xpm + theta.xpm + theta2.xpm + thickapprox.xpm + thicksim.xpm + tilde.xpm + times.xpm + top.xpm + triangle.xpm + triangledown.xpm + triangleleft.xpm + trianglelefteq.xpm + triangleq.xpm + triangleright.xpm + trianglerighteq.xpm + twoheadleftarrow.xpm + twoheadrightarrow.xpm + ulcorner.xpm + underbrace.xpm + underleftarrow.xpm + underleftrightarrow.xpm + underline.xpm + underrightarrow.xpm + underscore.xpm + underset.xpm + uparrow.xpm + uparrow2.xpm + updownarrow.xpm + updownarrow2.xpm + upharpoonleft.xpm + upharpoonright.xpm + uplus.xpm + upsilon.xpm + upsilon2.xpm + upuparrows.xpm + urcorner.xpm + varepsilon.xpm + varkappa.xpm + varnothing.xpm + varphi.xpm + varpi.xpm + varpropto.xpm + varsigma.xpm + varsubsetneq.xpm + varsubsetneqq.xpm + varsupsetneq.xpm + varsupsetneqq.xpm + vartheta.xpm + vartriangle.xpm + vartriangleleft.xpm + vartriangleright.xpm + vdash.xpm + vdash2.xpm + vdash3.xpm + vdots.xpm + vec.xpm + vee.xpm + veebar.xpm + wedge.xpm + widehat.xpm + widetilde.xpm + wp.xpm + wr.xpm + xi.xpm + xi2.xpm + zeta.xpm +''') + + +lib_kbd_files = Split(''' + american-2.kmap + american.kmap + arabic.kmap + bg-bds-1251.kmap + brazil.kmap + brazil2.kmap + cp1251.cdef + czech-prg.kmap + czech.kmap + european.kmap + francais.kmap + french.kmap + german-2.kmap + german-3.kmap + german.kmap + greek.kmap + hebrew.kmap + ibm866.cdef + iso8859-1.cdef + iso8859-15.cdef + iso8859-2.cdef + iso8859-3.cdef + iso8859-4.cdef + iso8859-7.cdef + iso8859-8.cdef + iso8859-9.cdef + koi8-r.cdef + koi8-r.kmap + koi8-t.cdef + koi8-u.cdef + koi8-u.kmap + latvian.kmap + magyar-2.kmap + magyar-3.kmap + magyar.kmap + null.kmap + polish.kmap + polski.kmap + portuges.kmap + romanian.kmap + serbian.kmap + serbocroatian.kmap + sf.kmap + sg.kmap + slovak.kmap + slovene.kmap + thai-kedmanee.kmap + tis620-0.cdef + transilvanian.kmap + turkish-f.kmap + turkish.kmap + espanol.kmap +''') + + +lib_layouts_files = Split(''' + IEEEtran.layout + aa.layout + aapaper.inc + aapaper.layout + aastex.layout + aguplus.inc + amsart-plain.layout + amsart-seq.layout + amsart.layout + amsbook.layout + amsdefs.inc + amsmaths-plain.inc + amsmaths-seq.inc + amsmaths.inc + apa.layout + article.layout + book.layout + broadway.layout + chess.layout + cl2emult.layout + cv.layout + db_lyxmacros.inc + db_stdclass.inc + db_stdcharstyles.inc + db_stdcounters.inc + db_stdlayouts.inc + db_stdlists.inc + db_stdsections.inc + db_stdstarsections.inc + db_stdstruct.inc + db_stdtitle.inc + dinbrief.layout + docbook-book.layout + docbook-chapter.layout + docbook-section.layout + docbook.layout + dtk.layout + egs.layout + elsart.layout + entcs.layout + extarticle.layout + extbook.layout + extletter.layout + extreport.layout + foils.layout + g-brief-de.layout + g-brief-en.layout + heb-article.layout + heb-letter.layout + hollywood.layout + ijmpc.layout + ijmpd.layout + jgrga.layout + kluwer.layout + latex8.layout + letter.layout + linuxdoc.layout + literate-article.layout + literate-book.layout + literate-report.layout + literate-scrap.inc + llncs.layout + ltugboat.layout + lyxmacros.inc + manpage.layout + mwart.layout + mwbk.layout + mwrep.layout + paper.layout + report.layout + revtex.layout + revtex4.layout + scrartcl.layout + scrbook.layout + scrclass.inc + scrlettr.layout + scrlttr2.layout + scrreprt.layout + seminar.layout + siamltex.layout + slides.layout + spie.layout + stdclass.inc + stdcounters.inc + stdfloats.inc + stdlayouts.inc + stdletter.inc + stdlists.inc + stdsections.inc + stdstarsections.inc + stdstruct.inc + stdtitle.inc + svjog.layout + svjour.inc + svprobth.layout + agums.layout + memoir.layout + numarticle.inc + numreport.inc + numrevtex.inc + agu-dtd.layout + agu_stdclass.inc + agu_stdcounters.inc + agu_stdlists.inc + agu_stdsections.inc + agu_stdtitle.inc + g-brief2.layout + svglobal.layout +''') + + +lib_scripts_files = Split(''' + TeXFiles.py + clean_dvi.py + convertDefault.py + fen2ascii.py + fig2pdftex.py + fig2pstex.py + fig_copy.py + layout2layout.py + legacy_lyxpreview2ppm.py + listerrors + lyxpreview2bitmap.py + lyxpreview_tools.py + tex_copy.py +''') + + +lib_templates_files = Split(''' + IEEEtran.lyx + README.new_templates + aa.lyx + aastex.lyx + dinbrief.lyx + docbook_article.lyx + elsart.lyx + g-brief-de.lyx + g-brief-en.lyx + hollywood.lyx + kluwer.lyx + koma-letter2.lyx + latex8.lyx + letter.lyx + linuxdoc_article.lyx + revtex.lyx + revtex4.lyx + slides.lyx + ijmpc.lyx + ijmpd.lyx + agu_article.lyx +''') + + +lib_tex_files = Split(''' + broadway.cls + cv.cls + hollywood.cls + lyxchess.sty + lyxskak.sty + revtex.cls +''') + + +lib_ui_files = Split(''' + classic.ui + default.ui + stdmenus.ui + stdtoolbars.ui +''') + + +lib_doc_files = Split(''' + cs_Tutorial.lyx + Customization.lyx + da_Intro.lyx + de_Customization.lyx + de_Extended.lyx + de_FAQ.lyx + de_Intro.lyx + de_Tutorial.lyx + de_UserGuide.lyx + DocStyle.lyx + es_Intro.lyx + es_Tutorial.lyx + eu_Customization.lyx + eu_Extended.lyx + eu_FAQ.lyx + eu_Intro.lyx + eu_Tutorial.lyx + eu_UserGuide.lyx + Extended.lyx + FAQ.lyx + fr_Customization.lyx + fr_Extended.lyx + fr_FAQ.lyx + fr_Intro.lyx + fr_Tutorial.lyx + fr_UserGuide.lyx + he_Intro.lyx + he_Tutorial.lyx + hu_Intro.lyx + Intro.lyx + it_Customization.lyx + it_Intro.lyx + it_Tutorial.lyx + it_UserGuide.lyx + LaTeXConfig.lyx.in + nl_Intro.lyx + nl_Tutorial.lyx + nb_Intro.lyx + pl_Extended.lyx + pl_Intro.lyx + pl_Tutorial.lyx + pt_Intro.lyx + pt_Tutorial.lyx + Reference.lyx + ro_Intro.lyx + ru_FAQ.lyx + ru_Intro.lyx + ru_Tutorial.lyx + sk_Tutorial.lyx + sk_UserGuide.lyx + sl_Intro.lyx + sl_Tutorial.lyx + sv_Intro.lyx + sv_Tutorial.lyx + Tutorial.lyx + UserGuide.lyx + escher-lsd.eps + mobius.eps + platypus.eps +''') + + +lib_lyx2lyx_files = Split(''' + lyx2lyx + parser_tools.py + LyX.py + lyx_0_12.py + lyx_1_0_0.py + lyx_1_0_1.py + lyx_1_1_4.py + lyx_1_1_5.py + lyx_1_1_6fix3.py + lyx_1_1_6.py + lyx_1_2.py + lyx_1_3.py + lyx_1_4.py + profiling.py +''') + diff --git a/development/scons/scons_utils.py b/development/scons/scons_utils.py new file mode 100644 index 0000000000..3659337f27 --- /dev/null +++ b/development/scons/scons_utils.py @@ -0,0 +1,669 @@ +# vi:filetype=python:expandtab:tabstop=4:shiftwidth=4 +# +# file scons_utils.py +# +# This file is part of LyX, the document processor. +# Licence details can be found in the file COPYING. +# +# \author Bo Peng +# Full author contact details are available in file CREDITS. +# +# This file defines all the utility functions for the +# scons-based build system of lyx +# + +import os, sys, re, shutil, glob +from SCons.Util import WhereIs + + +def writeToFile(filename, lines, append = False): + " utility function: write or append lines to filename " + # create directory if needed + dir = os.path.split(filename)[0] + if dir != '' and not os.path.isdir(dir): + os.makedirs(dir) + if append: + file = open(filename, 'a') + else: + file = open(filename, 'w') + file.write(lines) + file.close() + + +def env_subst(target, source, env): + ''' subst variables in source by those in env, and output to target + source and target are scons File() objects + + %key% (not key itself) is an indication of substitution + ''' + assert len(target) == 1 + assert len(source) == 1 + target_file = file(str(target[0]), "w") + source_file = file(str(source[0]), "r") + + contents = source_file.read() + for k, v in env.items(): + try: + val = env.subst('$'+k) + # temporary fix for the \Resource backslash problem + val = val.replace('\\', '/') + # multi-line replacement + val = val.replace('\n',r'\\n\\\n') + contents = re.sub('@'+k+'@', val, contents) + contents = re.sub('%'+k+'%', val, contents) + except: + pass + target_file.write(contents + "\n") + target_file.close() + #st = os.stat(str(source[0])) + #os.chmod(str(target[0]), stat.S_IMODE(st[stat.ST_MODE]) | stat.S_IWRITE) + +# +# autoconf tests +# + +def checkPkgConfig(conf, version): + ''' Return false if pkg_config does not exist, or is too old ''' + conf.Message('Checking for pkg-config...') + ret = conf.TryAction('pkg-config --atleast-pkgconfig-version=%s' % version)[0] + conf.Result(ret) + return ret + + +def checkPackage(conf, pkg): + ''' check if pkg is under the control of conf ''' + conf.Message('Checking for package %s...' % pkg) + ret = conf.TryAction("pkg-config --print-errors --exists %s" % pkg)[0] + conf.Result(ret) + return ret + + +def checkMkdirOneArg(conf): + check_mkdir_one_arg_source = """ +#include +int main() +{ + mkdir("somedir"); +} +""" + conf.Message('Checking for the number of args for mkdir... ') + ret = conf.TryLink(check_mkdir_one_arg_source, '.c') or \ + conf.TryLink('#include ' + check_mkdir_one_arg_source, '.c') or \ + conf.TryLink('#include ' + check_mkdir_one_arg_source, '.c') + if ret: + conf.Result('one') + else: + conf.Result('two') + return ret + + +def checkCXXGlobalCstd(conf): + ''' Check the use of std::tolower or tolower ''' + check_global_cstd_source = ''' +#include +using std::tolower; +int main() +{ + return 0; +} +''' + conf.Message('Check for the use of global cstd... ') + ret = conf.TryLink(check_global_cstd_source, '.c') + conf.Result(ret) + return ret + + +def checkSelectArgType(conf): + ''' Adapted from autoconf ''' + conf.Message('Checking for arg types for select... ') + for arg234 in ['fd_set *', 'int *', 'void *']: + for arg1 in ['int', 'size_t', 'unsigned long', 'unsigned']: + for arg5 in ['struct timeval *', 'const struct timeval *']: + check_select_source = ''' +#if HAVE_SYS_SELECT_H +# include +#endif +#if HAVE_SYS_SOCKET_H +# include +#endif +extern int select (%s, %s, %s, %s, %s); +int main() +{ + return(0); +} +''' % (arg1, arg234, arg234, arg234, arg5) + ret = conf.TryLink(check_select_source, '.c') + if ret: + conf.Result(ret) + return (arg1, arg234, arg5) + conf.Result('no (use default)') + return ('int', 'int *', 'struct timeval *') + + +def checkBoostLibraries(conf, libs, lib_paths, inc_paths, version, isDebug): + ''' look for boost libraries + libs: library names + lib_paths: try these paths for boost libraries + inc_paths: try these paths for boost headers + version: required boost version + isDebug: if true, use debug libraries + ''' + conf.Message('Checking for boost library %s... ' % ', '.join(libs)) + found_lib = False + found_inc = False + lib_names = [] + lib_path = None + inc_path = None + for path in lib_paths: + # direct form: e.g. libboost_iostreams.a + # ignore isDebug + if False not in [os.path.isfile(os.path.join(path, 'libboost_%s.a' % lib)) for lib in libs]: + conf.Result('yes') + found_lib = True + lib_path = path + lib_names = libs + break + for lib in libs: + # get all the libs, then filter for the right library + files = glob.glob(os.path.join(path, 'libboost_%s-*.a' % lib)) + # check things like libboost_iostreams-gcc-mt-d-1_33_1.a + if len(files) > 0: + # runtime code includes s,g,y,d,p,n, where we should look for + # d,g,y for debug, s,p,n for release + if isDebug: + lib_files = filter(lambda x: re.search('libboost_%s-\w+-mt-[^spn]+-%s.a' % (lib, version), x), files) + else: + lib_files = filter(lambda x: re.search('libboost_%s-\w+-mt-([^dgy]+-)*%s.a' % (lib, version), x), files) + if len(lib_files) == 0: + print 'Warning: Can not find an appropriate boost library in %s.' % path + lib_files = filter(lambda x: re.search('libboost_%s-[\w-]+%s.a' % (lib, version), x), files) + if len(lib_files) > 0: + print 'Use library %s' % lib_files[0] + if len(lib_files) > 0: + # get xxx-gcc-1_33_1 from /usr/local/lib/libboost_xxx-gcc-1_33_1.a + lib_names.append(lib_files[0].split(os.sep)[-1][3:-2]) + if len(lib_names) == len(libs): + found_lib = True + lib_path = path + break + if not found_lib: + conf.Result('no') + return (None, None, None) + # check version number in boost/version.hpp + def isValidBoostDir(dir): + file = os.path.join(dir, 'boost', 'version.hpp') + version_string = '#define BOOST_LIB_VERSION "%s"' % version + return os.path.isfile(file) and version_string in open(file).read() + # check for boost header file + for path in inc_paths: + if isValidBoostDir(path): + inc_path = path + found_inc = True + else: # check path/boost_1_xx_x/boost + dirs = glob.glob(os.path.join(path, 'boost-*')) + if len(dirs) > 0 and isValidBoostDir(dirs[0]): + inc_path = dirs[0] + found_inc = True + # return result + if found_inc: + conf.Result('yes') + return (lib_names, lib_path, inc_path) + else: + conf.Result('no') + return (None, None, None) + + +def checkCommand(conf, cmd): + ''' check the existence of a command + return full path to the command, or none + ''' + conf.Message('Checking for command %s...' % cmd) + res = WhereIs(cmd) + conf.Result(res is not None) + return res + + +def checkLC_MESSAGES(conf): + ''' check the definition of LC_MESSAGES ''' + check_LC_MESSAGES = ''' +#include +int main() +{ + return LC_MESSAGES; +} +''' + conf.Message('Check for LC_MESSAGES in locale.h... ') + ret = conf.TryLink(check_LC_MESSAGES, '.c') + conf.Result(ret) + return ret + + +def checkIconvConst(conf): + ''' check the declaration of iconv ''' + check_iconv_const = ''' +#include +#include +extern +#ifdef __cplusplus +"C" +#endif +#if defined(__STDC__) || defined(__cplusplus) +#ifndef LIBICONV_DLL_EXPORTED +size_t iconv (iconv_t cd, char * *inbuf, size_t *inbytesleft, char * *outbuf, size_t *outbytesleft); +#endif +#else +size_t iconv(); +#endif + +int main() +{ + return 1; +} +''' + conf.Message('Check if the declaration of iconv needs const... ') + ret = conf.TryLink(check_iconv_const, '.c') + conf.Result(ret) + return ret + + +def createConfigFile(conf, config_file, + config_pre = '', config_post = '', + headers = [], functions = [], types = [], libs = [], + custom_tests = [], extra_items = []): + ''' create a configuration file, with options + config_file: which file to create + config_pre: first part of the config file + config_post: last part of the config file + headers: header files to check, in the form of a list of + ('file', 'HAVE_FILE', 'c'/'c++') + functions: functions to check, in the form of a list of + ('func', 'HAVE_func', 'include lines'/None) + types: types to check, in the form of a list of + ('type', 'HAVE_TYPE', 'includelines'/None) + libs: libraries to check, in the form of a list of + ('lib', 'HAVE_LIB', 'LIB_NAME'). HAVE_LIB will be set if 'lib' exists, + or any of the libs exists if 'lib' is a list of libs. + Optionally, user can provide another key LIB_NAME, that will + be set to the detected lib (or None otherwise). + custom_tests: extra tests to perform, in the form of a list of + (test (True/False), 'key', 'desc', 'true config line', 'false config line') + If the last two are ignored, '#define key 1' '/*#undef key */' + will be used. + extra_items: extra configuration lines, in the form of a list of + ('config', 'description') + Return: + The result of each test, as a dictioanry of + res['XXX'] = True/False + XXX are keys defined in each argument. + ''' + cont = config_pre + '\n' + result = {} + # add to this string, in appropriate format + def configString(lines, desc=''): + text = '' + if lines.strip() != '': + if desc != '': + text += '/* ' + desc + ' */\n' + text += lines + '\n\n' + return text + # + # headers + for header in headers: + description = "Define to 1 if you have the <%s> header file." % header[0] + if (header[2] == 'c' and conf.CheckCHeader(header[0])) or \ + (header[2] == 'cxx' and conf.CheckCXXHeader(header[0])): + result[header[1]] = True + cont += configString('#define %s 1' % header[1], desc = description) + else: + result[header[1]] = False + cont += configString('/* #undef %s */' % header[1], desc = description) + # functions + for func in functions: + description = "Define to 1 if you have the `%s' function." % func[0] + if conf.CheckFunc(func[0], header=func[2]): + result[func[1]] = True + cont += configString('#define %s 1' % func[1], desc = description) + else: + result[func[1]] = False + cont += configString('/* #undef %s */' % func[1], desc = description) + # types + for t in types: + description = "Define to 1 if you have the `%s' type." % t[0] + if conf.CheckType(t[0], includes=t[2]): + result[t[1]] = True + cont += configString('#define %s 1' % t[1], desc = description) + else: + result[t[1]] = False + cont += configString('/* #undef %s */' % t[1], desc = description) + # libraries + for lib in libs: + description = "Define to 1 if you have the `%s' library (-l%s)." % (lib[0], lib[0]) + if type(lib[0]) is type(''): + lib_list = [lib[0]] + else: + lib_list = lib[0] + # check if any of the lib exists + result[lib[1]] = False + # if user want the name of the lib detected + if len(lib) == 3: + result[lib[2]] = None + for ll in lib_list: + if conf.CheckLib(ll): + result[lib[1]] = True + if len(lib) == 3: + result[lib[2]] = ll + cont += configString('#define %s 1' % lib[1], desc = description) + break + # if not found + if not result[lib[1]]: + cont += configString('/* #undef %s */' % lib[1], desc = description) + # custom tests + for test in custom_tests: + if test[0]: + result[test[1]] = True + if len(test) == 3: + cont += configString('#define %s 1' % test[1], desc = test[2]) + else: + cont += configString(test[3], desc = test[2]) + else: + result[test[1]] = False + if len(test) == 3: + cont += configString('/* #undef %s */' % test[1], desc = test[2]) + else: + cont += configString(test[4], desc = test[2]) + # extra items (no key is returned) + for item in extra_items: + cont += configString(item[0], desc = item[1]) + # add the last part + cont += '\n' + config_post + '\n' + # write to file + writeToFile(config_file, cont) + return result + + +def installCygwinLDScript(path): + ''' Install i386pe.x-no-rdata ''' + ld_script = os.path.join(path, 'i386pe.x-no-rdata') + script = open(ld_script, 'w') + script.write('''/* specific linker script avoiding .rdata sections, for normal executables +for a reference see +http://www.cygwin.com/ml/cygwin/2004-09/msg01101.html +http://www.cygwin.com/ml/cygwin-apps/2004-09/msg00309.html +*/ +OUTPUT_FORMAT(pei-i386) +SEARCH_DIR("/usr/i686-pc-cygwin/lib"); SEARCH_DIR("/usr/lib"); SEARCH_DIR("/usr/lib/w32api"); +ENTRY(_mainCRTStartup) +SECTIONS +{ + .text __image_base__ + __section_alignment__ : + { + *(.init) + *(.text) + *(SORT(.text$*)) + *(.glue_7t) + *(.glue_7) + ___CTOR_LIST__ = .; __CTOR_LIST__ = . ; + LONG (-1);*(.ctors); *(.ctor); *(SORT(.ctors.*)); LONG (0); + ___DTOR_LIST__ = .; __DTOR_LIST__ = . ; + LONG (-1); *(.dtors); *(.dtor); *(SORT(.dtors.*)); LONG (0); + *(.fini) + /* ??? Why is .gcc_exc here? */ + *(.gcc_exc) + PROVIDE (etext = .); + *(.gcc_except_table) + } + /* The Cygwin32 library uses a section to avoid copying certain data + on fork. This used to be named ".data". The linker used + to include this between __data_start__ and __data_end__, but that + breaks building the cygwin32 dll. Instead, we name the section + ".data_cygwin_nocopy" and explictly include it after __data_end__. */ + .data BLOCK(__section_alignment__) : + { + __data_start__ = . ; + *(.data) + *(.data2) + *(SORT(.data$*)) + *(.rdata) + *(SORT(.rdata$*)) + *(.eh_frame) + ___RUNTIME_PSEUDO_RELOC_LIST__ = .; + __RUNTIME_PSEUDO_RELOC_LIST__ = .; + *(.rdata_runtime_pseudo_reloc) + ___RUNTIME_PSEUDO_RELOC_LIST_END__ = .; + __RUNTIME_PSEUDO_RELOC_LIST_END__ = .; + __data_end__ = . ; + *(.data_cygwin_nocopy) + } + .rdata BLOCK(__section_alignment__) : + { + } + .pdata BLOCK(__section_alignment__) : + { + *(.pdata) + } + .bss BLOCK(__section_alignment__) : + { + __bss_start__ = . ; + *(.bss) + *(COMMON) + __bss_end__ = . ; + } + .edata BLOCK(__section_alignment__) : + { + *(.edata) + } + /DISCARD/ : + { + *(.debug$S) + *(.debug$T) + *(.debug$F) + *(.drectve) + } + .idata BLOCK(__section_alignment__) : + { + /* This cannot currently be handled with grouped sections. + See pe.em:sort_sections. */ + SORT(*)(.idata$2) + SORT(*)(.idata$3) + /* These zeroes mark the end of the import list. */ + LONG (0); LONG (0); LONG (0); LONG (0); LONG (0); + SORT(*)(.idata$4) + SORT(*)(.idata$5) + SORT(*)(.idata$6) + SORT(*)(.idata$7) + } + .CRT BLOCK(__section_alignment__) : + { + ___crt_xc_start__ = . ; + *(SORT(.CRT$XC*)) /* C initialization */ + ___crt_xc_end__ = . ; + ___crt_xi_start__ = . ; + *(SORT(.CRT$XI*)) /* C++ initialization */ + ___crt_xi_end__ = . ; + ___crt_xl_start__ = . ; + *(SORT(.CRT$XL*)) /* TLS callbacks */ + /* ___crt_xl_end__ is defined in the TLS Directory support code */ + ___crt_xp_start__ = . ; + *(SORT(.CRT$XP*)) /* Pre-termination */ + ___crt_xp_end__ = . ; + ___crt_xt_start__ = . ; + *(SORT(.CRT$XT*)) /* Termination */ + ___crt_xt_end__ = . ; + } + .tls BLOCK(__section_alignment__) : + { + ___tls_start__ = . ; + *(.tls) + *(.tls$) + *(SORT(.tls$*)) + ___tls_end__ = . ; + } + .endjunk BLOCK(__section_alignment__) : + { + /* end is deprecated, don't use it */ + PROVIDE (end = .); + PROVIDE ( _end = .); + __end__ = .; + } + .rsrc BLOCK(__section_alignment__) : + { + *(.rsrc) + *(SORT(.rsrc$*)) + } + .reloc BLOCK(__section_alignment__) : + { + *(.reloc) + } + .stab BLOCK(__section_alignment__) (NOLOAD) : + { + *(.stab) + } + .stabstr BLOCK(__section_alignment__) (NOLOAD) : + { + *(.stabstr) + } + /* DWARF debug sections. + Symbols in the DWARF debugging sections are relative to the beginning + of the section. Unlike other targets that fake this by putting the + section VMA at 0, the PE format will not allow it. */ + /* DWARF 1.1 and DWARF 2. */ + .debug_aranges BLOCK(__section_alignment__) (NOLOAD) : + { + *(.debug_aranges) + } + .debug_pubnames BLOCK(__section_alignment__) (NOLOAD) : + { + *(.debug_pubnames) + } + /* DWARF 2. */ + .debug_info BLOCK(__section_alignment__) (NOLOAD) : + { + *(.debug_info) *(.gnu.linkonce.wi.*) + } + .debug_abbrev BLOCK(__section_alignment__) (NOLOAD) : + { + *(.debug_abbrev) + } + .debug_line BLOCK(__section_alignment__) (NOLOAD) : + { + *(.debug_line) + } + .debug_frame BLOCK(__section_alignment__) (NOLOAD) : + { + *(.debug_frame) + } + .debug_str BLOCK(__section_alignment__) (NOLOAD) : + { + *(.debug_str) + } + .debug_loc BLOCK(__section_alignment__) (NOLOAD) : + { + *(.debug_loc) + } + .debug_macinfo BLOCK(__section_alignment__) (NOLOAD) : + { + *(.debug_macinfo) + } + /* SGI/MIPS DWARF 2 extensions. */ + .debug_weaknames BLOCK(__section_alignment__) (NOLOAD) : + { + *(.debug_weaknames) + } + .debug_funcnames BLOCK(__section_alignment__) (NOLOAD) : + { + *(.debug_funcnames) + } + .debug_typenames BLOCK(__section_alignment__) (NOLOAD) : + { + *(.debug_typenames) + } + .debug_varnames BLOCK(__section_alignment__) (NOLOAD) : + { + *(.debug_varnames) + } + /* DWARF 3. */ + .debug_ranges BLOCK(__section_alignment__) (NOLOAD) : + { + *(.debug_ranges) + } +} +''') + script.close() + return(ld_script) + + +try: + # these will be used under win32 + import win32file + import win32event + import win32process + import win32security +except: + # does not matter if it fails on other systems + pass + + +class loggedSpawn: + def __init__(self, env, logfile, longarg, info): + # save the spawn system + self.env = env + self.logfile = logfile + # clear the logfile (it may not exist) + if logfile != '': + # this will overwrite existing content. + writeToFile(logfile, info, append=False) + # + self.longarg = longarg + # get hold of the old spawn? (necessary?) + self._spawn = env['SPAWN'] + + # define new SPAWN + def spawn(self, sh, escape, cmd, args, spawnenv): + # get command line + newargs = ' '.join(map(escape, args[1:])) + cmdline = cmd + " " + newargs + # + # if log is not empty, write to it + if self.logfile != '': + # this tend to be slow (?) but ensure correct output + # Note that cmdline may be long so I do not escape it + try: + # since this is not an essential operation, proceed if things go wrong here. + writeToFile(self.logfile, cmd + " " + ' '.join(args[1:]) + '\n', append=True) + except: + print "Warning: can not write to log file ", self.logfile + # + # if the command is not too long, use the old + if not self.longarg or len(cmdline) < 8000: + exit_code = self._spawn(sh, escape, cmd, args, spawnenv) + else: + sAttrs = win32security.SECURITY_ATTRIBUTES() + StartupInfo = win32process.STARTUPINFO() + for var in spawnenv: + spawnenv[var] = spawnenv[var].encode('ascii', 'replace') + # check for any special operating system commands + if cmd == 'del': + for arg in args[1:]: + win32file.DeleteFile(arg) + exit_code = 0 + else: + # otherwise execute the command. + hProcess, hThread, dwPid, dwTid = win32process.CreateProcess(None, cmdline, None, None, 1, 0, spawnenv, None, StartupInfo) + win32event.WaitForSingleObject(hProcess, win32event.INFINITE) + exit_code = win32process.GetExitCodeProcess(hProcess) + win32file.CloseHandle(hProcess); + win32file.CloseHandle(hThread); + return exit_code + + +def setLoggedSpawn(env, logfile = '', longarg=False, info=''): + ''' This function modify env and allow logging of + commands to a logfile. If the argument is too long + a win32 spawn will be used instead of the system one + ''' + # + # create a new spwn object + ls = loggedSpawn(env, logfile, longarg, info) + # replace the old SPAWN by the new function + env['SPAWN'] = ls.spawn + diff --git a/status.14x b/status.14x index 02aa019bd4..2fafb2b362 100644 --- a/status.14x +++ b/status.14x @@ -82,6 +82,8 @@ What's new - Install python files together with precompiled versions. +- A scons build system is added, details please see INSTALL.scons. + * Miscellaneous - Display latex package checking results faster during configuration.