/[ascend]/trunk/SConstruct
ViewVC logotype

Annotation of /trunk/SConstruct

Parent Directory Parent Directory | Revision Log Revision Log


Revision 748 - (hide annotations) (download)
Tue Jul 11 05:54:26 2006 UTC (14 years, 2 months ago) by johnpye
File size: 35099 byte(s)
Lot of svn ignore tagging.
Little more work on DSG model.
1 johnpye 393 import os, commands, platform, distutils.sysconfig, os.path
2 johnpye 385
3 johnpye 748 version = "0.9.5.95"
4 johnpye 439
5 johnpye 385 #------------------------------------------------------
6     # OPTIONS
7 johnpye 392 #
8     # Note that if you set the options via the command line, they will be
9     # remembered in the file 'options.cache'. It's a feature ;-)
10 johnpye 385
11     opts = Options(['options.cache', 'config.py'])
12 johnpye 464 #print "PLATFORM = ",platform.system()
13 johnpye 385
14 johnpye 464 if platform.system()=="Windows":
15 johnpye 631 default_tcl_lib = "tcl84"
16     default_tk_lib = "tk84"
17 johnpye 464 default_tktable_lib = "Tktable28"
18 johnpye 499 default_install_assets = "glade/"
19     icon_extension = '.png'
20 johnpye 521 default_tcl = "c:\\Tcl"
21 johnpye 643 if os.environ.get('MSYSTEM')=="MINGW32":
22 johnpye 642 default_tcl_libpath="$TCL\\bin"
23     else:
24     default_tcl_libpath="$TCL\\lib"
25 johnpye 627 default_rel_distdir = '.'
26 johnpye 628 default_absolute_paths = False
27 johnpye 739
28     default_ida_prefix = "c:\\MinGW"
29     if not os.path.exists(default_ida_prefix):
30     default_ida_prefix = None
31    
32 johnpye 673 need_libm = False
33 johnpye 683 python_exe = "c:\\Python24\\python.exe"
34 johnpye 464 else:
35 johnpye 673 default_tcl_lib = "tcl8.4"
36     default_tk_lib = "tk8.4"
37 johnpye 464 default_tktable_lib = "Tktable2.8"
38 johnpye 628 default_install_assets = "$INSTALL_ASCDATA/glade/"
39 johnpye 499 icon_extension = '.svg'
40 johnpye 684 default_tcl = '/usr'
41 johnpye 541 default_tcl_libpath = "$TCL/lib"
42 johnpye 627 default_rel_distdir = '../share/ascend'
43 johnpye 628 default_absolute_paths = True
44 johnpye 673 default_ida_prefix="/usr/local"
45     need_libm = True
46 johnpye 551 if not os.path.isdir(default_tcl):
47     default_tcl = '/usr'
48 johnpye 683 python_exe = distutils.sysconfig.EXEC_PREFIX+"/bin/python"
49 johnpye 551
50 johnpye 562 opts.Add(
51     'CC'
52     ,'C Compiler command'
53     ,None
54     )
55    
56     opts.Add(
57     'CXX'
58     ,'C++ Compiler command'
59     ,None
60     )
61    
62 johnpye 591 opts.Add(BoolOption(
63     'GCOV'
64 johnpye 593 , 'Whether to enable coverage testing in object code'
65     , False
66 johnpye 591 ))
67    
68 johnpye 385 # Package linking option
69 johnpye 386 opts.Add(EnumOption(
70     'PACKAGE_LINKING'
71 johnpye 385 , 'Style of linking for external libraries'
72     , 'DYNAMIC_PACKAGES'
73 johnpye 386 , ['DYNAMIC_PACKAGES', 'STATIC_PACKAGES', 'NO_PACKAGES']
74     ))
75 johnpye 385
76 johnpye 526 opts.Add(BoolOption(
77     'WITH_GCCVISIBILITY'
78     ,"Whether to use GCC Visibility features (only applicable if available)"
79     ,True
80     ))
81    
82 johnpye 392 # You can turn off building of Tcl/Tk interface
83 johnpye 386 opts.Add(BoolOption(
84 johnpye 542 'WITH_TCLTK'
85 johnpye 673 ,"Set to False if you don't want to build the original Tcl/Tk GUI."
86 johnpye 542 , True
87 johnpye 386 ))
88    
89 johnpye 392 # You can turn off the building of the Python interface
90 johnpye 387 opts.Add(BoolOption(
91 johnpye 542 'WITH_PYTHON'
92 johnpye 673 ,"Set to False if you don't want to build Python wrappers."
93 johnpye 542 , True
94 johnpye 387 ))
95    
96 johnpye 392 # Which solvers will we allow?
97     opts.Add(ListOption(
98     'WITH_SOLVERS'
99 johnpye 393 ,"List of the solvers you want to build. The default is the minimum that"
100     +" works."
101 johnpye 673 ,["QRSLV","CMSLV","LSOD","IDA"]
102 johnpye 392 ,['QRSLV','MPS','SLV','OPTSQP'
103     ,'NGSLV','CMSLV','LRSLV','MINOS','CONOPT'
104 johnpye 673 ,'LSOD','OPTSQP',"IDA"
105 johnpye 392 ]
106     ))
107    
108 johnpye 393 # Where will the local copy of the help files be kept?
109     opts.Add(PackageOption(
110     'WITH_LOCAL_HELP'
111     , "Directory containing the local copy of the help files (optional)"
112     , "no"
113     ))
114    
115     # Will bintoken support be enabled?
116     opts.Add(BoolOption(
117     'WITH_BINTOKEN'
118     ,"Enable bintoken support? This means compiling models as C-code before"
119     +" running them, to increase solving speed for large models."
120     ,False
121     ))
122    
123 johnpye 398 # What should the default ASCENDLIBRARY path be?
124     # Note: users can change it by editing their ~/.ascend.ini
125 johnpye 393 opts.Add(
126     'DEFAULT_ASCENDLIBRARY'
127     ,"Set the default value of the ASCENDLIBRARY -- the location where"
128     +" ASCEND will look for models when running ASCEND"
129 johnpye 628 ,"$INSTALL_ASCDATA/models"
130 johnpye 393 )
131    
132 johnpye 398 # Where is SWIG?
133     opts.Add(
134     'SWIG'
135     ,"SWIG location, probably only required for MinGW and MSVC users."
136     +" Enter the location as a Windows-style path, for example"
137 johnpye 404 +" 'c:\\msys\\1.0\\home\\john\\swigwin-1.3.29\\swig.exe'."
138 johnpye 398 )
139    
140 johnpye 400 # Build the test suite?
141     opts.Add(BoolOption(
142 johnpye 593 'WITH_CUNIT'
143 johnpye 665 ,"You can disable CUnit tests with this option. This will basically stop"
144     +" SCons from parsing the SConscript files relating to the 'test'"
145     +" target, which just might make things marginally faster. Probably"
146     +" you can just ignore this option though. SCons will sniff for Cunit"
147     +" but build the tests only if you specify the 'test' target."
148     ,True
149 johnpye 400 ))
150 johnpye 393
151 johnpye 400 # Where are the CUnit includes?
152     opts.Add(PackageOption(
153     'CUNIT_CPPPATH'
154     ,"Where are your CUnit include files?"
155 johnpye 459 ,'off'
156 johnpye 400 ))
157 johnpye 392
158 johnpye 404 # Where are the CUnit libraries?
159 johnpye 400 opts.Add(PackageOption(
160     'CUNIT_LIBPATH'
161 johnpye 404 ,"Where are your CUnit libraries?"
162 johnpye 459 ,'off'
163 johnpye 400 ))
164    
165 johnpye 673 opts.Add(PackageOption(
166     "IDA_PREFIX"
167     ,"Prefix for your IDA install (IDA ./configure --prefix)"
168     ,default_ida_prefix
169     ))
170 johnpye 521
171 johnpye 534 opts.Add(
172 johnpye 673 'IDA_CPPPATH'
173     ,"Where is your ida.h?"
174     ,"$IDA_PREFIX/include"
175     )
176    
177     opts.Add(
178     'IDA_LIBPATH'
179     ,"Where are your SUNDIALS libraries installed?"
180     ,"$IDA_PREFIX/lib"
181     )
182    
183     opts.Add(
184     "IDA_LIB"
185     ,"What libraries to link to for use of IDA (comma-separated). Note that"
186     +" you will need to include the math library in this list (for now)."
187     ,'sundials_ida,sundials_nvecserial,m'
188     )
189    
190     opts.Add(
191     "F2C_LIB"
192     ,"F2C library (eg. g2c, gfortran, f2c)"
193     ,"g2c"
194     )
195    
196     opts.Add(PackageOption(
197     "F2C_LIBPATH"
198     ,"Directory containing F2C library (i.e. g2c, gfortran, f2c, etc.), if not already accessible"
199     ,"off"
200     ))
201    
202     opts.Add(
203 johnpye 521 'TCL'
204     ,'Base of Tcl distribution'
205     ,default_tcl
206 johnpye 534 )
207 johnpye 521
208 johnpye 404 # Where are the Tcl includes?
209 johnpye 534 opts.Add(
210 johnpye 404 'TCL_CPPPATH'
211     ,"Where are your Tcl include files?"
212 johnpye 521 ,"$TCL/include"
213 johnpye 534 )
214 johnpye 404
215     # Where are the Tcl libs?
216 johnpye 534 opts.Add(
217 johnpye 404 'TCL_LIBPATH'
218     ,"Where are your Tcl libraries?"
219 johnpye 541 ,default_tcl_libpath
220 johnpye 534 )
221 johnpye 404
222 johnpye 428 # What is the name of the Tcl lib?
223     opts.Add(
224     'TCL_LIB'
225 johnpye 561 ,"Name of Tcl lib (eg 'tcl' or 'tcl83'), for full path to static library (if STATIC_TCLTK is set)"
226 johnpye 464 ,default_tcl_lib
227 johnpye 428 )
228    
229 johnpye 405 # Where are the Tk includes?
230 johnpye 534 opts.Add(
231 johnpye 405 'TK_CPPPATH'
232     ,"Where are your Tk include files?"
233 johnpye 464 ,'$TCL_CPPPATH'
234 johnpye 534 )
235 johnpye 404
236 johnpye 405 # Where are the Tk libs?
237 johnpye 534 opts.Add(
238 johnpye 405 'TK_LIBPATH'
239     ,"Where are your Tk libraries?"
240 johnpye 464 ,'$TCL_LIBPATH'
241 johnpye 534 )
242 johnpye 405
243 johnpye 428 # What is the name of the Tk lib?
244     opts.Add(
245     'TK_LIB'
246 johnpye 521 ,"Name of Tk lib (eg 'tk' or 'tk83'), or full path to static library"
247 johnpye 464 ,default_tk_lib
248 johnpye 435 )
249    
250 johnpye 460 # Static linking to TkTable
251    
252     opts.Add(BoolOption(
253 johnpye 521 'STATIC_TCLTK'
254 johnpye 554 ,'Set true for static linking for Tcl/Tk and TkTable. EXPERIMENTAL'
255 johnpye 460 ,False
256     ))
257    
258 johnpye 464 opts.Add(
259 johnpye 460 'TKTABLE_LIBPATH'
260     ,'Location of TkTable static library'
261 johnpye 464 ,'$TCL_LIBPATH/Tktable2.8'
262     )
263 johnpye 460
264 johnpye 435 opts.Add(
265 johnpye 460 'TKTABLE_LIB'
266 johnpye 521 ,'Stem name of TkTable (eg tktable2.8, no ".so" or "lib") shared library, or full path of static tktable (/usr/lib/...)'
267 johnpye 464 ,default_tktable_lib
268 johnpye 460 )
269    
270     opts.Add(
271 johnpye 521 'TKTABLE_CPPPATH'
272     ,'Location of TkTable header file'
273     ,'$TCL_CPPPATH'
274     )
275    
276     opts.Add(
277     'X11'
278 johnpye 554 ,'Base X11 directory. Only used when STATIC_TCLTK is turned on. EXPERIMENTAL'
279 johnpye 521 ,'/usr/X11R6'
280     )
281    
282     opts.Add(
283     'X11_LIBPATH'
284 johnpye 554 ,'Location of X11 lib. EXPERIMENTAL'
285 johnpye 521 ,'$X11/lib'
286     )
287    
288     opts.Add(
289     'X11_CPPPATH'
290 johnpye 554 ,'Location of X11 includes. EXPERIMENTAL'
291 johnpye 521 ,'$X11/include'
292     )
293    
294     opts.Add(
295     'X11_LIB'
296 johnpye 554 ,'Name of X11 lib. EXPERIMENTAL'
297 johnpye 521 ,'X11'
298     )
299    
300     opts.Add(
301 johnpye 435 'INSTALL_PREFIX'
302     ,'Root location for installed files'
303 johnpye 449 ,'/usr/local'
304 johnpye 428 )
305    
306 johnpye 435 opts.Add(
307     'INSTALL_BIN'
308     ,'Location to put binaries during installation'
309     ,"$INSTALL_PREFIX/bin"
310     )
311    
312     opts.Add(
313 johnpye 463 'INSTALL_LIB'
314 johnpye 683 ,'Location to put libraries during installation'
315 johnpye 463 ,"$INSTALL_PREFIX/lib"
316     )
317    
318     opts.Add(
319 ben.allan 624 'INSTALL_SHARE'
320 johnpye 628 ,'Common shared-file location on this system'
321     ,"$INSTALL_PREFIX/share"
322 johnpye 435 )
323    
324 johnpye 628
325 johnpye 435 opts.Add(
326 johnpye 628 'INSTALL_ASCDATA'
327     ,"Location of ASCEND shared data (TK, python, models etc)"
328     ,"$INSTALL_SHARE/ascend"
329     )
330    
331     opts.Add(
332 johnpye 435 'INSTALL_INCLUDE'
333     ,'Location to put header files during installation'
334     ,"$INSTALL_PREFIX/include"
335     )
336    
337 johnpye 448 opts.Add(
338 johnpye 455 'PYGTK_ASSETS'
339 johnpye 532 ,'Default location for Glade assets (placed in pygtk/config.py)'
340 johnpye 455 ,default_install_assets
341     )
342    
343 johnpye 508 opts.Add(BoolOption(
344     'DEBUG'
345     ,"Compile source with debugger symbols, eg for use with 'gdb'"
346     ,False
347     ))
348    
349 johnpye 597 opts.Add(BoolOption(
350     'MALLOC_DEBUG'
351     ,"Compile with debugging version of MALLOC. Required for full CUnit testing"
352     ,False
353     ))
354    
355 johnpye 455 opts.Add(
356 johnpye 448 'INSTALL_ROOT'
357     ,'For use by RPM only: location of %{buildroot} during rpmbuild'
358     ,""
359     )
360    
361 johnpye 563 opts.Add(
362     'DISTTAR_NAME'
363     ,"Stem name of the tarball created by 'scons dist'. So for 'ascend-aaa.tar.bz2', set this to 'ascend-aaa'."
364     ,"ascend-"+version
365     )
366    
367 johnpye 656 opts.Add(
368     'RELEASE'
369     ,"Release number for use in RPM spec file. This should always start with a zero for releases made by the ASCEND group, in order that third parties can make 'patch' releases of higher version numbers."
370     ,"0"
371     )
372    
373 johnpye 605 opts.Add(BoolOption(
374 johnpye 628 'ABSOLUTE_PATHS'
375 johnpye 605 ,"Whether to use absolute or relative paths in the installed Tcl/Tk interface. If you want to build an RPM, set this to false."
376 johnpye 628 ,default_absolute_paths
377 johnpye 605 ))
378    
379 johnpye 578 opts.Add(
380     'WIN_INSTALLER_NAME'
381     ,"Name of the installer .exe to create under Windows (minus the '.exe')"
382     ,"ascend-"+version
383     )
384    
385 johnpye 594 opts.Add(BoolOption(
386     'WITH_XTERM_COLORS'
387     ,"Set to 0 if you don't want xterm colour codes in the console output"
388     ,True
389     ))
390    
391 johnpye 546 if platform.system()!="Windows":
392     opts.Add(BoolOption(
393     'WITH_GCCVISIBILITY'
394     , 'Whether to use GCC Visibility extensions when building with GCC 4.0'
395     , True
396     ))
397    
398 johnpye 392 # TODO: OTHER OPTIONS?
399     # TODO: flags for optimisation
400 johnpye 393 # TODO: turning on/off bintoken functionality
401 johnpye 427 # TODO: Where will the 'Makefile.bt' file be installed?
402 johnpye 393
403 johnpye 498 # Import the outside environment
404    
405 johnpye 569 if os.environ.get('OSTYPE')=='msys':
406 johnpye 552 env = Environment(
407     ENV=os.environ
408 johnpye 578 , tools=['mingw','lex','yacc','fortran','swig','disttar','nsis']
409 johnpye 552 , toolpath=['scons']
410     )
411 johnpye 529 env['IS_MINGW']=True
412 johnpye 740
413     elif platform.system()=="Windows":
414     env = Environment(
415     ENV={
416     'PATH':os.environ['PATH']
417     ,'INCLUDE':os.environ['INCLUDE']
418     ,'LIB':os.environ['LIB']
419     ,'MSVS_IGNORE_IDE_PATHS':1
420     }
421     , tools = ['default','lex','yacc','fortran','swig','disttar','nsis']
422     , toolpath = ['scons']
423     )
424     env.Append(CPPDEFINES=['_CRT_SECURE_NO_DEPRECATE'])
425 johnpye 498 else:
426 johnpye 552 env = Environment(
427     ENV=os.environ
428 johnpye 740 , tools=['default','lex','yacc','fortran','swig','disttar','nsis']
429 johnpye 552 , toolpath=['scons']
430     )
431 johnpye 498
432 johnpye 385 opts.Update(env)
433     opts.Save('options.cache',env)
434    
435     Help(opts.GenerateHelpText(env))
436    
437 johnpye 551 with_tcltk = env.get('WITH_TCLTK')
438 johnpye 427 without_tcltk_reason = "disabled by options/config.py"
439 johnpye 386
440 johnpye 551 with_python = env.get('WITH_PYTHON')
441 johnpye 427 without_python_reason = "disabled by options/config.py"
442 johnpye 387
443 johnpye 593 with_cunit = env.get('WITH_CUNIT')
444 johnpye 427 without_cunit_reason = "not requested"
445 johnpye 400
446 johnpye 631 if platform.system()=="Windows":
447     with_installer=1
448     else:
449     with_installer=0
450     without_installer_reason = "only possible under Windows"
451    
452 johnpye 673 if 'LSOD' in env['WITH_SOLVERS']:
453     with_lsode=True
454     else:
455     with_lsode=False
456     without_lsode_reason = "not requested (WITH_SOLVERS)"
457    
458     if 'IDA' in env['WITH_SOLVERS']:
459     with_ida=True
460     else:
461     with_ida=False
462     without_ida_reason = "not requested (WITH_SOLVERS)"
463    
464    
465 johnpye 464 #print "SOLVERS:",env['WITH_SOLVERS']
466     #print "WITH_BINTOKEN:",env['WITH_BINTOKEN']
467     #print "DEFAULT_ASCENDLIBRARY:",env['DEFAULT_ASCENDLIBRARY']
468 johnpye 393
469 johnpye 463 can_install = True
470     if platform.system()=='Windows':
471     can_install = False
472    
473     env['CAN_INSTALL']=can_install
474    
475 johnpye 721 env['INSTALL_MODELS']=env['INSTALL_ASCDATA']+"/models/"
476    
477 johnpye 521 print "TCL_CPPPATH =",env['TCL_CPPPATH']
478     print "TCL_LIBPATH =",env['TCL_LIBPATH']
479     print "TCL_LIB =",env['TCL_LIB']
480 johnpye 562 print "CC =",env['CC']
481     print "CXX =",env['CXX']
482 johnpye 673 print "FORTRAN=",env.get('FORTRAN')
483 johnpye 393
484 johnpye 628 print "ABSOLUTE PATHS =",env['ABSOLUTE_PATHS']
485 johnpye 385 #------------------------------------------------------
486 johnpye 398 # SPECIAL CONFIGURATION TESTS
487    
488 johnpye 463 need_fortran = False
489    
490 johnpye 400 #----------------
491     # SWIG
492    
493 johnpye 398 import os,re
494    
495 johnpye 413 def get_swig_version(env):
496 johnpye 403 cmd = env['SWIG']+' -version'
497 johnpye 427 (cin,coutcerr) = os.popen4(cmd)
498 johnpye 403 output = coutcerr.read()
499 johnpye 398
500 johnpye 403 restr = "SWIG\\s+Version\\s+(?P<maj>[0-9]+)\\.(?P<min>[0-9]+)\\.(?P<pat>[0-9]+)\\s*$"
501     expr = re.compile(restr,re.M);
502 johnpye 398 m = expr.search(output);
503     if not m:
504 johnpye 413 return None
505 johnpye 398 maj = int(m.group('maj'))
506     min = int(m.group('min'))
507     pat = int(m.group('pat'))
508 johnpye 413
509     return (maj,min,pat)
510 johnpye 398
511 johnpye 413
512     def CheckSwigVersion(context):
513    
514     try:
515     context.Message("Checking version of SWIG... ")
516     maj,min,pat = get_swig_version(context.env)
517     except:
518     context.Result("Failed to detect version, or failed to run SWIG")
519     return 0;
520    
521 johnpye 478 context.env['SWIGVERSION']=tuple([maj,min,pat])
522    
523 johnpye 398 if maj == 1 and (
524 johnpye 400 min > 3
525     or (min == 3 and pat >= 24)
526 johnpye 398 ):
527     context.Result("ok, %d.%d.%d" % (maj,min,pat))
528     return 1;
529 johnpye 401 else:
530     context.Result("too old, %d.%d.%d" % (maj,min,pat))
531     return 0;
532 johnpye 398
533 johnpye 400 #----------------
534     # General purpose library-and-header test
535    
536 johnpye 404 class KeepContext:
537 johnpye 521 def __init__(self,context,varprefix,static=False):
538 johnpye 404 self.keep = {}
539 johnpye 521 for k in ['LIBS','LIBPATH','CPPPATH','LINKFLAGS']:
540 johnpye 705 #print "Keeping env %s = %s" % (k,context.env.get(k))
541     self.keep[k]=context.env.get(k)
542 johnpye 404
543     if context.env.has_key(varprefix+'_CPPPATH'):
544 johnpye 743 context.env.AppendUnique(CPPPATH=[env[varprefix+'_CPPPATH']])
545 johnpye 428 #print "Adding '"+str(cpppath_add)+"' to cpp path"
546    
547 johnpye 521 if static:
548     staticlib=env[varprefix+'_LIB']
549     #print "STATIC LIB = ",staticlib
550     context.env.Append(
551     LINKFLAGS=[staticlib]
552     )
553     else:
554     if context.env.has_key(varprefix+'_LIBPATH'):
555     context.env.Append(LIBPATH=[env[varprefix+'_LIBPATH']])
556     #print "Adding '"+str(libpath_add)+"' to lib path"
557 johnpye 428
558 johnpye 521 if context.env.has_key(varprefix+'_LIB'):
559     context.env.Append(LIBS=[env[varprefix+'_LIB']])
560 johnpye 705 #print "Adding '"+str(env[varprefix+'_LIB'])+"' to libs"
561 johnpye 404
562     def restore(self,context):
563 johnpye 464 #print "RESTORING CONTEXT"
564     #print self.keep
565     #print "..."
566 johnpye 404 for k in self.keep:
567 johnpye 463 if self.keep[k]==None:
568 johnpye 521 if context.env.has_key(k):
569     #print "Clearing "+str(k)
570     del context.env[k];
571 johnpye 463 else:
572 johnpye 705 #print "Restoring %s to '%s'" %(k,self.keep.get(k))
573 johnpye 463 context.env[k]=self.keep[k];
574 johnpye 404
575 johnpye 521 def CheckExtLib(context,libname,text,ext='.c',varprefix=None,static=False):
576 johnpye 400 """This method will check for variables LIBNAME_LIBPATH
577     and LIBNAME_CPPPATH and try to compile and link the
578     file with the provided text, linking with the
579     library libname."""
580    
581 johnpye 521 if static:
582     context.Message( 'Checking for static '+libname+'... ' )
583     else:
584     context.Message( 'Checking for '+libname+'... ' )
585    
586 johnpye 400 if varprefix==None:
587     varprefix = libname.upper()
588    
589 johnpye 705 #print "LIBS is currently:",context.env.get('LIBS')
590 johnpye 521 keep = KeepContext(context,varprefix,static)
591 johnpye 400
592 johnpye 428 if not context.env.has_key(varprefix+'_LIB'):
593 johnpye 463 # if varprefix_LIB were in env, KeepContext would
594     # have appended it already
595 johnpye 705 context.env.Append(LIBS=[libname])
596 johnpye 428
597 johnpye 404 is_ok = context.TryLink(text,ext)
598 johnpye 428
599 johnpye 521 #print "Link success? ",(is_ok != 0)
600 johnpye 400
601 johnpye 405 keep.restore(context)
602 johnpye 400
603 johnpye 428 # print "Restored CPPPATH="+str(context.env['CPPPATH'])
604 johnpye 705 # print "Restored LIBS="+str(context.env['LIBS'])
605 johnpye 428 # print "Restored LIBPATH="+str(context.env['LIBPATH'])
606    
607 johnpye 404 context.Result(is_ok)
608     return is_ok
609    
610     #----------------
611 johnpye 502 # GCC
612    
613     gcc_test_text = """
614     #ifndef __GNUC__
615     # error "Not using GCC"
616     #endif
617    
618     int main(void){
619     return __GNUC__;
620     }
621     """
622    
623     def CheckGcc(context):
624     context.Message("Checking for GCC... ")
625     is_ok = context.TryCompile(gcc_test_text,".c")
626     context.Result(is_ok)
627     return is_ok
628    
629     #----------------
630 johnpye 500 # GCC VISIBILITY feature
631    
632     gccvisibility_test_text = """
633     #if __GNUC__ < 4
634     # error "Require GCC version 4 or newer"
635     #endif
636    
637     __attribute__ ((visibility("default"))) int x;
638    
639     int main(void){
640     extern int x;
641     x = 4;
642     }
643     """
644    
645     def CheckGccVisibility(context):
646     context.Message("Checking for GCC 'visibility' capability... ")
647 johnpye 546 if not context.env.has_key('WITH_GCCVISIBILITY') or not env['WITH_GCCVISIBILITY']:
648     context.Result("disabled")
649     return 0
650 johnpye 500 is_ok = context.TryCompile(gccvisibility_test_text,".c")
651     context.Result(is_ok)
652     return is_ok
653 johnpye 502
654 johnpye 500 #----------------
655 johnpye 502 # YACC
656    
657     yacc_test_text = """
658 johnpye 646 %{
659     #include <stdio.h>
660 johnpye 741
661     /* MSVC++ needs this before it can swallow Bison output */
662     #ifdef _MSC_VER
663     # define __STDC__
664     #endif
665 johnpye 646 %}
666     %token MSG
667 johnpye 502 %start ROOT
668 johnpye 646 %%
669     ROOT:
670     MSG { printf("HELLO"); }
671     ;
672     %%
673 johnpye 502 """
674    
675     def CheckYacc(context):
676 johnpye 644 context.Message("Checking for Yacc ('%s')... " % context.env.get('YACC'))
677 johnpye 502 is_ok = context.TryCompile(yacc_test_text,".y")
678     context.Result(is_ok)
679     return is_ok
680    
681     #----------------
682 johnpye 404 # CUnit test
683    
684 johnpye 400 cunit_test_text = """
685 johnpye 451 #include <CUnit/CUnit.h>
686 johnpye 400 int maxi(int i1, int i2){
687     return (i1 > i2) ? i1 : i2;
688     }
689    
690     void test_maxi(void){
691     CU_ASSERT(maxi(0,2) == 2);
692     CU_ASSERT(maxi(0,-2) == 0);
693     CU_ASSERT(maxi(2,2) == 2);
694    
695     }
696     int main(void){
697     /* CU_initialize_registry() */
698 johnpye 404 return 0;
699 johnpye 400 }
700     """
701    
702     def CheckCUnit(context):
703 johnpye 451 return CheckExtLib(context,'cunit',cunit_test_text)
704 johnpye 400
705 johnpye 404 #----------------
706 johnpye 673 # MATH test
707    
708     math_test_text = """
709 johnpye 705 #ifndef _ALL_SOURCE
710     # define _ALL_SOURCE
711     #endif
712     #ifndef _XOPEN_SOURCE
713     # define _XOPEN_SOURCE
714     #endif
715     #ifndef _XOPEN_SOURCE_EXTENDED
716     # define _XOPEN_SOURCE_EXTENDED 1
717     #endif
718 johnpye 673 #include <math.h>
719     int main(void){
720 johnpye 705 double x = 1.0; double y = 1.0; int i = 1;
721     acosh(x); asinh(x); atanh(x); cbrt(x); expm1(x); erf(x); erfc(x); isnan(x);
722     j0(x); j1(x); jn(i,x); ilogb(x); logb(x); log1p(x); rint(x);
723     y0(x); y1(x); yn(i,x);
724     #ifdef _THREAD_SAFE
725     gamma_r(x,&i);
726     lgamma_r(x,&i);
727     #else
728     gamma(x);
729     lgamma(x);
730     #endif
731     hypot(x,y); nextafter(x,y); remainder(x,y); scalb(x,y);
732 johnpye 673 return 0;
733     }
734     """
735    
736     def CheckMath(context):
737 johnpye 705 context.Message('Checking for IEE math library... ')
738     libsave=context.env.get('LIBS');
739     context.env.AppendUnique(LIBS=['m'])
740     is_ok=context.TryLink(math_test_text,".c")
741     context.Result(is_ok)
742     if not is_ok:
743     context.env['LIBS']=libsave
744     return is_ok
745    
746 johnpye 673 #----------------
747     # IDA test
748    
749     ida_test_text = """
750     #include <ida.h>
751     #include <nvector_serial.h>
752     #include <ida_spgmr.h>
753     int main(){
754     void *ida_mem;
755     ida_mem = IDACreate();
756     }
757     """
758    
759     def CheckIDA(context):
760     context.Message( 'Checking for IDA (SUNDIALS)... ' )
761    
762     # add SUNDIALS subdirectories as well (what a pain)
763     if context.env.get('IDA_CPPPATH'):
764     extra = [context.env['IDA_CPPPATH']+"/ida",context.env['IDA_CPPPATH']+"/sundials"]
765 johnpye 743 context.env.AppendUnique(CPPPATH=extra)
766 johnpye 673
767     if ',' in context.env.get('IDA_LIB'):
768     context.env['IDA_LIB']=context.env['IDA_LIB'].split(',')
769     #print "IDA_LIB NOW =",context.env['IDA_LIB']
770     else:
771     print "NO COMMA IN IDA_LIB:",context.env['IDA_LIB']
772    
773     keep = KeepContext(context,"IDA")
774    
775     is_ok = context.TryLink(ida_test_text,".c")
776     context.Result(is_ok)
777    
778     keep.restore(context)
779    
780     if is_ok:
781     context.env.Append(IDA_CPPPATH_EXTRA=extra)
782    
783     return is_ok
784    
785     #----------------
786 johnpye 405 # Tcl test
787 johnpye 404
788 johnpye 561 # TCL and TK required version 8.1, 8.2, 8.3, or 8.4:
789     tcltk_minor_newest_acceptable = 4
790     tcltk_major_required = 8
791    
792 johnpye 404 tcl_check_text = r"""
793     #include <tcl.h>
794     #include <stdio.h>
795     int main(void){
796     printf("%s",TCL_PATCH_LEVEL);
797     return 0;
798     }
799     """
800    
801     def CheckTcl(context):
802 johnpye 521 return CheckExtLib(context,'tcl',tcl_check_text,static=env['STATIC_TCLTK'])
803 johnpye 405
804     def CheckTclVersion(context):
805 johnpye 521 keep = KeepContext(context,'TCL',static=env['STATIC_TCLTK'])
806 johnpye 405 context.Message("Checking Tcl version... ")
807     (is_ok,output) = context.TryRun(tcl_check_text,'.c')
808 johnpye 404 keep.restore(context)
809     if not is_ok:
810 johnpye 405 context.Result("failed to run check")
811 johnpye 404 return 0
812 johnpye 405
813 wangym 511 major,minor,patch = tuple([int(i) for i in output.split(".")])
814 johnpye 561 if major != tcltk_major_required or minor > tcltk_minor_newest_acceptable:
815 johnpye 428 context.Result(output+" (bad version)")
816 johnpye 405 # bad version
817     return 0
818    
819     # good version
820 johnpye 552 context.Result(output+", good")
821 johnpye 404 return 1
822    
823 johnpye 405 #----------------
824 johnpye 463 # Tk test
825 johnpye 405
826     tk_check_text = r"""
827     #include <tk.h>
828     #include <stdio.h>
829     int main(void){
830     printf("%s",TK_PATCH_LEVEL);
831     return 0;
832     }
833     """
834     def CheckTk(context):
835 johnpye 673 return CheckExtLib(context,'tk',tk_check_text,static=env['STATIC_TCLTK'])
836 johnpye 405
837 johnpye 428
838 johnpye 405 def CheckTkVersion(context):
839 johnpye 521 keep = KeepContext(context,'TK',static=context.env['STATIC_TCLTK'])
840 johnpye 405 context.Message("Checking Tk version... ")
841 johnpye 521 #print "LINKFLAGS =",context.env['LINKFLAGS']
842 johnpye 405 (is_ok,output) = context.TryRun(tk_check_text,'.c')
843 johnpye 404 keep.restore(context)
844     if not is_ok:
845     context.Result("failed to run check")
846     return 0
847    
848 wangym 511 major,minor,patch = tuple([int(i) for i in output.split(".")])
849 johnpye 561 if major != tcltk_major_required or minor > tcltk_minor_newest_acceptable:
850 johnpye 404 # bad version
851 johnpye 561 context.Result(output+" (bad version)")
852 johnpye 404 return 0
853 johnpye 400
854 johnpye 404 # good version
855 johnpye 561 context.Result(output+" (good)")
856 johnpye 404 return 1
857 johnpye 485
858     #----------------
859 johnpye 521 # Tktable test
860    
861     tktable_check_text = r"""
862     #include <tkTable.h>
863     #include <stdio.h>
864     int main(void){
865     Table mytable;
866     return 0;
867     }
868     """
869    
870     def CheckTkTable(context):
871     return CheckExtLib(context,'tktable',tktable_check_text,static=env['STATIC_TCLTK'])
872    
873     #---------------
874     # X11 test
875    
876     x11_check_text = r"""
877     #include <X11/Xlib.h>
878     #include <X11/IntrinsicP.h>
879     #include <X11/Intrinsic.h>
880     #include <X11/ObjectP.h>
881     #include <X11/Object.h>
882     int main(void){
883     Object mything;
884     return 0;
885     }
886     """
887    
888     def CheckX11(context):
889     return CheckExtLib(context,'X11',x11_check_text)
890    
891     #----------------
892 johnpye 485 # GCC Version sniffing
893    
894     # TODO FIXME
895    
896     gcc_version4 = False
897    
898 johnpye 398 #------------------------------------------------------
899 johnpye 385 # CONFIGURATION
900    
901     conf = Configure(env
902     , custom_tests = {
903 johnpye 673 'CheckMath' : CheckMath
904     , 'CheckSwigVersion' : CheckSwigVersion
905 johnpye 400 , 'CheckCUnit' : CheckCUnit
906 johnpye 404 , 'CheckTcl' : CheckTcl
907     , 'CheckTclVersion' : CheckTclVersion
908 johnpye 405 , 'CheckTk' : CheckTk
909     , 'CheckTkVersion' : CheckTkVersion
910 johnpye 502 , 'CheckGcc' : CheckGcc
911 johnpye 500 , 'CheckGccVisibility' : CheckGccVisibility
912 johnpye 502 , 'CheckYacc' : CheckYacc
913 johnpye 521 , 'CheckTkTable' : CheckTkTable
914     , 'CheckX11' : CheckX11
915 johnpye 673 , 'CheckIDA' : CheckIDA
916 johnpye 400 # , 'CheckIsNan' : CheckIsNan
917     # , 'CheckCppUnitConfig' : CheckCppUnitConfig
918 johnpye 385 }
919 johnpye 459 # , config_h = "config.h"
920 johnpye 385 )
921    
922 johnpye 740 # stdio -- just to check that compiler is behaving
923 johnpye 398
924 johnpye 740 if not conf.CheckHeader('stdio.h'):
925     print "Did not find 'stdio.h'! Check your compiler configuration."
926     Exit(1)
927    
928 johnpye 385 # Math library
929    
930 johnpye 673 if need_libm:
931     if not conf.CheckMath():
932     print 'Did not find math library, exiting!'
933     Exit(1)
934     #pass
935 johnpye 427
936 johnpye 385 # Where is 'isnan'?
937    
938 johnpye 740 if not conf.CheckFunc('isnan') and not conf.CheckFunc('_isnan'):
939 johnpye 385 print "Didn't find isnan"
940 johnpye 414 # Exit(1)
941 johnpye 385
942 johnpye 500 # GCC visibility
943    
944 johnpye 502 if conf.CheckGcc():
945     conf.env['HAVE_GCC']=True;
946 johnpye 526 if env['WITH_GCCVISIBILITY'] and conf.CheckGccVisibility():
947 johnpye 509 conf.env['HAVE_GCCVISIBILITY']=True;
948     conf.env.Append(CCFLAGS=['-fvisibility=hidden'])
949     conf.env.Append(CPPDEFINES=['HAVE_GCCVISIBILITY'])
950 johnpye 709 conf.env.Append(CCFLAGS=['-Wall'])
951 johnpye 500
952 johnpye 502 # YACC
953    
954 johnpye 506 if not conf.CheckYacc():
955     print "YACC NOT FOUND OR NOT WORKING"
956     else:
957 johnpye 502 conf.env['HAVE_YACC']=True
958    
959     conf.env['HAVE_LEX']=True
960    
961 johnpye 387 # Tcl/Tk
962 johnpye 386
963 johnpye 586 if with_tcltk:
964     if conf.CheckTcl():
965     if conf.CheckTclVersion():
966     if conf.CheckTk():
967     if with_tcltk and conf.CheckTkVersion():
968     if env['STATIC_TCLTK']:
969     if conf.CheckTkTable():
970     pass
971     else:
972     without_tcltk_reason = "TkTable not found"
973     with_tcltk = False
974     else:
975     without_tcltk_reason = "Require Tk version <= 8.4. See 'scons -h'"
976     with_tcltk = False
977 johnpye 521 else:
978 johnpye 586 without_tcltk_reason = "Tk not found."
979 johnpye 551 with_tcltk = False
980 johnpye 428 else:
981 johnpye 586 without_tcltk_reason = "Require Tcl <= 8.4 Tcl."
982 johnpye 551 with_tcltk = False
983 johnpye 586
984 johnpye 428 else:
985 johnpye 586 without_tcltk_reason = "Tcl not found."
986 johnpye 551 with_tcltk = False
987 johnpye 386
988 johnpye 521 if env['STATIC_TCLTK']:
989     conf.CheckX11()
990    
991 johnpye 395 # Python... obviously we're already running python, so we just need to
992     # check that we can link to the python library OK:
993    
994 johnpye 391 if platform.system()=="Windows":
995 johnpye 395 python_lib='python24'
996 johnpye 391 else:
997 johnpye 395 python_lib='python2.4'
998 johnpye 391
999 johnpye 395 # SWIG version
1000    
1001 johnpye 413 if not conf.CheckSwigVersion():
1002     without_python_reason = 'SWIG >= 1.3.24 is required'
1003     with_python = False
1004    
1005 johnpye 400 # CUnit
1006    
1007 johnpye 593 if with_cunit:
1008 johnpye 404 if not conf.CheckCUnit():
1009 johnpye 427 without_cunit_reason = 'CUnit not found'
1010 johnpye 665 with_cunit = False
1011 johnpye 705 #print "CUNIT NOT FOUND, LIBS=",conf.env.get('LIBS')
1012 johnpye 427
1013 johnpye 673 # IDA
1014    
1015     if not with_ida:
1016     without_ida_reason = "Not selected (see config option WITH_SOLVERS)"
1017     elif not conf.CheckIDA():
1018     with_ida = False
1019     without_ida_reason = "IDA not found"
1020    
1021 johnpye 427 # BLAS
1022    
1023 johnpye 459 need_blas=False
1024 johnpye 673
1025     if with_lsode:
1026     need_fortran = True
1027 johnpye 459 need_blas=True
1028 johnpye 673
1029 johnpye 459 if need_blas:
1030     if conf.CheckLib('blas'):
1031     with_local_blas = False
1032     without_local_blas_reason = "Found BLAS installed on system"
1033     else:
1034     with_local_blas = True
1035     need_fortran = True
1036 johnpye 673 else:
1037     with_local_blas= False;
1038     without_local_blas_reason = "BLAS not required"
1039 johnpye 427
1040     # FORTRAN
1041    
1042     if need_fortran:
1043 johnpye 629 conf.env.Tool('fortran')
1044     detect_fortran = conf.env.Detect(['g77','f77','gfortran'])
1045 johnpye 427 if detect_fortran:
1046     # For some reason, g77 doesn't get detected properly on MinGW
1047 johnpye 673 if not env.has_key('F77') and not env.has_key('FORTRAN'):
1048 johnpye 427 conf.env.Replace(F77=detect_fortran)
1049     conf.env.Replace(F77COM='$F77 $F77FLAGS -c -o $TARGET $SOURCE')
1050     conf.env.Replace(F77FLAGS='')
1051 johnpye 428 #print "F77:",conf.env['F77']
1052     #print "F77COM:",conf.env['F77COM']
1053     #print "F77FLAGS:",conf.env['F77FLAGS']
1054 johnpye 427 fortran_builder = Builder(
1055     action='$F77COM'
1056     , suffix='.o'
1057     , src_suffix='.f'
1058     )
1059     conf.env.Append(BUILDERS={'Fortran':fortran_builder})
1060     else:
1061 johnpye 673 with_lsode=False;
1062     without_lsode_reason="FORTRAN-77 required but not found"
1063 johnpye 629
1064 johnpye 464 #else:
1065     # print "FORTRAN not required"
1066 johnpye 400
1067 johnpye 673 # F2C
1068    
1069     if need_fortran:
1070     if platform.system()=="Windows":
1071     conf.env.Append(LIBPATH='c:\mingw\lib')
1072    
1073    
1074 johnpye 385 # TODO: -D_HPUX_SOURCE is needed
1075    
1076     # TODO: check size of void*
1077    
1078 johnpye 393 # TODO: detect if dynamic libraries are possible or not
1079    
1080 johnpye 427 if platform.system()=="Windows" and env.has_key('MSVS'):
1081 johnpye 740 _found_windows_h = conf.CheckHeader('Windows.h')
1082    
1083     if not _found_windows_h:
1084 johnpye 741 print "Could not locate 'Windows.h' in CPPPATH. Check your configuration."
1085 johnpye 740 Exit(1)
1086 johnpye 741
1087 johnpye 534 if with_python and not conf.CheckHeader(['basetsd.h','BaseTsd.h']):
1088 johnpye 427 with_python = 0;
1089     without_python_reason = "Header file 'basetsd.h' not found. Install the MS Platform SDK."
1090    
1091     conf.env.Append(CPPDEFINES=env['PACKAGE_LINKING'])
1092    
1093 johnpye 395 conf.Finish()
1094    
1095     env.Append(PYTHON_LIBPATH=[distutils.sysconfig.PREFIX+"/libs"])
1096     env.Append(PYTHON_LIB=[python_lib])
1097     env.Append(PYTHON_CPPPATH=[distutils.sysconfig.get_python_inc()])
1098    
1099 johnpye 507 #---------------------------------------
1100     # SUBSTITUTION DICTIONARY for .in files
1101    
1102 johnpye 658 release = env.get('RELEASE')
1103     if release=="0.":
1104     release="0"
1105    
1106 johnpye 507 subst_dict = {
1107     '@DEFAULT_ASCENDLIBRARY@':env['DEFAULT_ASCENDLIBRARY']
1108     , '@GLADE_FILE@':'ascend.glade'
1109     , '@HELP_ROOT@':''
1110     , '@ICON_EXTENSION@':icon_extension
1111 johnpye 628 , '@INSTALL_ASCDATA@':env['INSTALL_ASCDATA']
1112 johnpye 507 , '@INSTALL_BIN@':env['INSTALL_BIN']
1113     , '@INSTALL_INCLUDE@':env['INSTALL_INCLUDE']
1114 johnpye 683 , '@INSTALL_LIB@':env['INSTALL_LIB']
1115 johnpye 721 , '@INSTALL_MODELS@':env['INSTALL_MODELS']
1116 johnpye 507 , '@PYGTK_ASSETS@':env['PYGTK_ASSETS']
1117     , '@VERSION@':version
1118 johnpye 658 , '@RELEASE@':release
1119 johnpye 563 , '@DISTTAR_NAME@':env['DISTTAR_NAME']
1120 johnpye 507 , '@WEBHELPROOT@':'http://pye.dyndns.org/ascend/manual/'
1121 johnpye 508 , '@ASC_SHLIBSUFFIX@':env['SHLIBSUFFIX']
1122     , '@ASC_SHLIBPREFIX@':env['SHLIBPREFIX']
1123 johnpye 589 , '@ASC_ENV_TK_DEFAULT@' : '$$ASCENDDIST/tcltk'
1124 johnpye 627 , '@ASC_DISTDIR_REL_BIN@' : default_rel_distdir
1125 johnpye 683 , '@PYTHON@' : python_exe
1126 johnpye 507 }
1127    
1128 johnpye 594 if env.get('WITH_LOCAL_HELP'):
1129 johnpye 507 print "WITH_LOCAL_HELP:",env['WITH_LOCAL_HELP']
1130     subst_dict['@HELP_ROOT@']=env['WITH_LOCAL_HELP']
1131    
1132 johnpye 597 # bool options...
1133 johnpye 673 for k,v in {
1134     'ABSOLUTE_PATHS' : 'ASC_ABSOLUTE_PATHS'
1135     ,'WITH_XTERM_COLORS' : 'ASC_XTERM_COLORS'
1136     ,'MALLOC_DEBUG' : 'MALLOC_DEBUG'
1137 johnpye 605 }.iteritems():
1138 johnpye 597 if env.get(k):
1139 johnpye 673 # subst_dict['@'+v+'@']='1'
1140     subst_dict["/\\* #define "+v+' @'+v+"@ \\*/"]='# define '+v+' 1 '
1141 johnpye 594
1142 johnpye 673 if with_ida:
1143     subst_dict["/\\* #define ASC_WITH_IDA @ASC_WITH_IDA@ \\*/"]='#define ASC_WITH_IDA '
1144    
1145     if with_lsode:
1146     subst_dict["/\\* #define ASC_WITH_LSODE @ASC_WITH_LSODE@ \\*/"]='#define ASC_WITH_LSODE '
1147    
1148 johnpye 507 if with_python:
1149     subst_dict['@ASCXX_USE_PYTHON@']="1"
1150 johnpye 673 env['WITH_PYTHON']=1;
1151 johnpye 507
1152     if env.has_key('HAVE_GCCVISIBILITY'):
1153     subst_dict['@HAVE_GCCVISIBILITY@'] = "1"
1154    
1155     env.Append(SUBST_DICT=subst_dict)
1156    
1157 johnpye 385 #------------------------------------------------------
1158 johnpye 558 # RECIPE: SWIG scanner
1159    
1160     import SCons.Script
1161    
1162     SWIGScanner = SCons.Scanner.ClassicCPP(
1163     "SWIGScan"
1164     , ".i"
1165     , "CPPPATH"
1166     , '^[ \t]*[%,#][ \t]*(?:include|import)[ \t]*(<|")([^>"]+)(>|")'
1167     )
1168    
1169     env.Append(SCANNERS=[SWIGScanner])
1170    
1171     #------------------------------------------------------
1172 johnpye 393 # RECIPE: 'SubstInFile', used in pygtk SConscript
1173    
1174     import re
1175 johnpye 395 from SCons.Script import * # the usual scons stuff you get in a SConscript
1176 johnpye 393
1177 johnpye 395 def TOOL_SUBST(env):
1178     """Adds SubstInFile builder, which substitutes the keys->values of SUBST_DICT
1179     from the source to the target.
1180     The values of SUBST_DICT first have any construction variables expanded
1181     (its keys are not expanded).
1182     If a value of SUBST_DICT is a python callable function, it is called and
1183     the result is expanded as the value.
1184     If there's more than one source and more than one target, each target gets
1185     substituted from the corresponding source.
1186 johnpye 393 """
1187 johnpye 395 env.Append(TOOLS = 'SUBST')
1188     def do_subst_in_file(targetfile, sourcefile, dict):
1189     """Replace all instances of the keys of dict with their values.
1190     For example, if dict is {'%VERSION%': '1.2345', '%BASE%': 'MyProg'},
1191     then all instances of %VERSION% in the file will be replaced with 1.2345 etc.
1192     """
1193     try:
1194     f = open(sourcefile, 'rb')
1195     contents = f.read()
1196     f.close()
1197     except:
1198     raise SCons.Errors.UserError, "Can't read source file %s"%sourcefile
1199     for (k,v) in dict.items():
1200     contents = re.sub(k, v, contents)
1201     try:
1202     f = open(targetfile, 'wb')
1203     f.write(contents)
1204     f.close()
1205     except:
1206     raise SCons.Errors.UserError, "Can't write target file %s"%targetfile
1207     return 0 # success
1208 johnpye 393
1209 johnpye 395 def subst_in_file(target, source, env):
1210     if not env.has_key('SUBST_DICT'):
1211     raise SCons.Errors.UserError, "SubstInFile requires SUBST_DICT to be set."
1212     d = dict(env['SUBST_DICT']) # copy it
1213     for (k,v) in d.items():
1214     if callable(v):
1215     d[k] = env.subst(v())
1216     elif SCons.Util.is_String(v):
1217     d[k]=env.subst(v)
1218     else:
1219     raise SCons.Errors.UserError, "SubstInFile: key %s: %s must be a string or callable"%(k, repr(v))
1220     for (t,s) in zip(target, source):
1221     return do_subst_in_file(str(t), str(s), d)
1222 johnpye 393
1223 johnpye 395 def subst_in_file_string(target, source, env):
1224     """This is what gets printed on the console."""
1225     return '\n'.join(['Substituting vars from %s into %s'%(str(s), str(t))
1226     for (t,s) in zip(target, source)])
1227 johnpye 393
1228 johnpye 395 def subst_emitter(target, source, env):
1229     """Add dependency from substituted SUBST_DICT to target.
1230     Returns original target, source tuple unchanged.
1231     """
1232     d = env['SUBST_DICT'].copy() # copy it
1233     for (k,v) in d.items():
1234     if callable(v):
1235     d[k] = env.subst(v())
1236     elif SCons.Util.is_String(v):
1237     d[k]=env.subst(v)
1238     Depends(target, SCons.Node.Python.Value(d))
1239     return target, source
1240 johnpye 393
1241 johnpye 395 subst_action=SCons.Action.Action(subst_in_file, subst_in_file_string)
1242     env['BUILDERS']['SubstInFile'] = Builder(action=subst_action, emitter=subst_emitter)
1243    
1244     TOOL_SUBST(env)
1245    
1246 johnpye 393 #------------------------------------------------------
1247 johnpye 463 # Recipe for 'CHMOD' ACTION
1248 johnpye 439
1249     import SCons
1250     from SCons.Script.SConscript import SConsEnvironment
1251     SConsEnvironment.Chmod = SCons.Action.ActionFactory(os.chmod,
1252     lambda dest, mode: 'Chmod("%s", 0%o)' % (dest, mode))
1253    
1254     def InstallPerm(env, dest, files, perm):
1255     obj = env.Install(dest, files)
1256     for i in obj:
1257     env.AddPostAction(i, env.Chmod(str(i), perm))
1258    
1259     SConsEnvironment.InstallPerm = InstallPerm
1260    
1261     # define wrappers
1262     SConsEnvironment.InstallProgram = lambda env, dest, files: InstallPerm(env, dest, files, 0755)
1263 johnpye 578 SConsEnvironment.InstallHeader = lambda env, dest, files: InstallPerm(env, dest, files, 0644)
1264 johnpye 629 SConsEnvironment.InstallShared = lambda env, dest, files: InstallPerm(env, dest, files, 0644)
1265 johnpye 463
1266 johnpye 439 #------------------------------------------------------
1267 johnpye 463 # BUILD...
1268 johnpye 385
1269 johnpye 463 # so that #include <modulename/headername.h> works across all modules...
1270 johnpye 743 env.AppendUnique(CPPPATH=['#base/generic'])
1271 johnpye 385
1272 johnpye 508 if env['DEBUG']:
1273     env.Append(CCFLAGS=['-g'])
1274    
1275 johnpye 591 if env['GCOV']:
1276     env.Append(
1277     CPPFLAGS=['-g','-fprofile-arcs','-ftest-coverage']
1278     , LIBS=['gcov']
1279     , LINKFLAGS=['-fprofile-arcs','-ftest-coverage']
1280     )
1281    
1282 johnpye 673 if with_ida:
1283     env.Append(WITH_IDA=1)
1284    
1285 johnpye 463 #-------------
1286     # TCL/TK GUI
1287 johnpye 385
1288 johnpye 551 if with_tcltk:
1289 johnpye 569 env.SConscript(['tcltk/generic/interface/SConscript'],'env')
1290 johnpye 391 else:
1291 johnpye 405 print "Skipping... Tcl/Tk GUI isn't being built:",without_tcltk_reason
1292 johnpye 386
1293 johnpye 463 #-------------
1294     # PYTHON INTERFACE
1295    
1296 johnpye 387 if with_python:
1297 johnpye 532 env.SConscript(['pygtk/SConscript'],'env')
1298 johnpye 391 else:
1299 johnpye 413 print "Skipping... Python GUI isn't being built:",without_python_reason
1300 johnpye 400
1301 johnpye 463 #------------
1302     # BASE/GENERIC SUBDIRECTORIES
1303    
1304 johnpye 673 libascend_env = env.Copy()
1305    
1306 johnpye 463 dirs = ['general','utilities','compiler','solver','packages']
1307    
1308     srcs = []
1309     for d in dirs:
1310 johnpye 673 heresrcs = libascend_env.SConscript('base/generic/'+d+'/SConscript','libascend_env')
1311 johnpye 463 srcs += heresrcs
1312    
1313     #-------------
1314 johnpye 673 # IMPORTED CODE: LSODE, BLAS, etc
1315    
1316     if with_lsode:
1317     srcs += env.SConscript(['lsod/SConscript'],'env')
1318     srcs += env.SConscript(['linpack/SConscript'],'env')
1319     else:
1320     print "Skipping... LSODE won't be built:", without_lsode_reason
1321    
1322     if with_local_blas:
1323     srcs += env.SConscript(['blas/SConscript'],'env')
1324     else:
1325     print "Skipping... BLAS won't be built:", without_local_blas_reason
1326    
1327     if not with_ida:
1328     print "Skipping... IDA won't be built:", without_ida_reason
1329    
1330     #-------------
1331 johnpye 463 # LIBASCEND -- all base/generic functionality
1332    
1333 johnpye 673 libascend = libascend_env.SharedLibrary('ascend',srcs)
1334 johnpye 463
1335 johnpye 673 env.Alias('libascend',libascend)
1336    
1337 johnpye 463 #-------------
1338     # UNIT TESTS
1339    
1340 johnpye 593 if with_cunit:
1341 johnpye 400 testdirs = ['general','solver','utilities']
1342 johnpye 593 testsrcs = []
1343 johnpye 400 for testdir in testdirs:
1344     path = 'base/generic/'+testdir+'/test/'
1345     env.SConscript([path+'SConscript'],'env')
1346 johnpye 593 testsrcs += [i.path for i in env['TESTSRCS_'+testdir.upper()]]
1347    
1348     #print "TESTSRCS =",testsrcs
1349    
1350 johnpye 400 env.SConscript(['test/SConscript'],'env')
1351     env.SConscript(['base/generic/test/SConscript'],'env')
1352 johnpye 593
1353     env.Alias('test',[env.Dir('test'),env.Dir('base/generic/test')])
1354 johnpye 400
1355     else:
1356 johnpye 427 print "Skipping... CUnit tests aren't being built:",without_cunit_reason
1357 johnpye 400
1358 johnpye 463 #------------------------------------------------------
1359 johnpye 683 # CREATE ASCEND-CONFIG scriptlet
1360    
1361     ascendconfig = env.SubstInFile('ascend-config.in')
1362    
1363     #------------------------------------------------------
1364 johnpye 463 # INSTALLATION
1365 johnpye 427
1366 johnpye 552 if env.get('CAN_INSTALL'):
1367 johnpye 463 # the models directory only needs to be processed for installation, no other processing required.
1368     env.SConscript(['models/SConscript'],'env')
1369 johnpye 427
1370 johnpye 721 dirs = ['INSTALL_BIN','INSTALL_ASCDATA','INSTALL_LIB', 'INSTALL_INCLUDE']
1371 johnpye 463 install_dirs = [env['INSTALL_ROOT']+env[d] for d in dirs]
1372 johnpye 449
1373 johnpye 463 # TODO: add install options
1374     env.Alias('install',install_dirs)
1375 johnpye 400
1376 johnpye 629 env.InstallShared(env['INSTALL_ROOT']+env['INSTALL_LIB'],libascend)
1377 johnpye 435
1378 johnpye 683 env.InstallProgram(env['INSTALL_ROOT']+env['INSTALL_BIN'],ascendconfig)
1379    
1380 johnpye 438 #------------------------------------------------------
1381 johnpye 631 # WINDOWS INSTALLER
1382     # For the windows installer, please see pygtk/SConscript
1383    
1384     if with_installer:
1385     pass
1386     else:
1387     print "Skipping... Windows installer isn't being built:",without_installer_reason
1388    
1389     #------------------------------------------------------
1390 johnpye 673 # PROJECT FILE for MSVC
1391    
1392     env.SConscript(['base/msvc/SConscript'],['env','libascend']);
1393    
1394     #------------------------------------------------------
1395 johnpye 438 # CREATE the SPEC file for generation of RPM packages
1396    
1397 johnpye 463 if platform.system()=="Linux":
1398     env.SubstInFile('ascend.spec.in')
1399 johnpye 552
1400     #------------------------------------------------------
1401     # DISTRIBUTION TAR FILE
1402    
1403 johnpye 554 env['DISTTAR_FORMAT']='bz2'
1404 johnpye 556 env.Append(
1405 johnpye 566 DISTTAR_EXCLUDEEXTS=['.o','.os','.so','.a','.dll','.cc','.cache','.pyc','.cvsignore','.dblite','.log','.pl']
1406 johnpye 561 , DISTTAR_EXCLUDEDIRS=['CVS','.svn','.sconf_temp', 'dist']
1407 johnpye 556 )
1408 johnpye 554
1409 johnpye 563 tar = env.DistTar("dist/"+env['DISTTAR_NAME']
1410 johnpye 556 , [env.Dir('#')]
1411 johnpye 554 )
1412    
1413 johnpye 680 env.Depends(tar,'ascend.spec')
1414    
1415 johnpye 554 #------------------------------------------------------
1416     # RPM BUILD
1417    
1418     #if platform.system()=="Linux":
1419     # pass
1420    
1421     #------------------------------------------------------
1422     # DEFAULT TARGETS
1423    
1424 johnpye 673 default_targets =['libascend']
1425 johnpye 629 if with_tcltk:
1426     default_targets.append('tcltk')
1427     if with_python:
1428     default_targets.append('pygtk')
1429 johnpye 631 if with_installer:
1430     default_targets.append('installer')
1431 johnpye 554
1432 johnpye 629 env.Default(default_targets)
1433    
1434     print "Building targets:"," ".join([str(i) for i in BUILD_TARGETS])
1435    
1436 johnpye 705 # vim: set syntax=python:
1437    

john.pye@anu.edu.au
ViewVC Help
Powered by ViewVC 1.1.22