/[ascend]/trunk/SConstruct
ViewVC logotype

Contents of /trunk/SConstruct

Parent Directory Parent Directory | Revision Log Revision Log


Revision 1598 - (show annotations) (download)
Fri Aug 17 06:44:45 2007 UTC (17 years, 2 months ago) by jpye
File size: 58392 byte(s)
All platforms will now use the lib<name>_ascend.so convention for ASCEND external libraries.
(it makes it simpler for people writing such things).
1 import sys, os, commands, platform, distutils.sysconfig, os.path, re
2
3 version = "0.9.5.113"
4
5 pyversion = "%d.%d" % (sys.version_info[0],sys.version_info[1])
6
7 #------------------------------------------------------
8 # OPTIONS
9 #
10 # Note that if you set the options via the command line, they will be
11 # remembered in the file 'options.cache'. It's a feature ;-)
12
13 opts = Options(['options.cache', 'config.py'])
14 #print "PLATFORM = ",platform.system()
15
16 default_tcl_cpppath = "$TCL/include"
17 default_tron_envvar="TRON_PATH"
18 default_conopt_envvar="CONOPT_PATH"
19
20 if platform.system()=="Windows":
21 default_tcl_lib = "tcl84"
22 default_tk_lib = "tk84"
23 default_tktable_lib = "Tktable28"
24 default_install_assets = "glade/"
25 icon_extension = '.png'
26 default_tcl = "c:\\Tcl"
27 if os.environ.get('MSYSTEM')=="MINGW32":
28 default_tcl_libpath="$TCL\\bin"
29 else:
30 default_tcl_libpath="$TCL\\lib"
31 default_rel_distdir = '.'
32 default_absolute_paths = False
33
34 default_ida_prefix = "c:\\MinGW"
35 if not os.path.exists(default_ida_prefix):
36 default_ida_prefix = None
37
38 default_conopt_prefix = "c:\\Program Files\\CONOPT"
39 default_conopt_libpath="$CONOPT_PREFIX"
40 default_conopt_cpppath="$CONOPT_PREFIX"
41 default_conopt_dlpath="$CONOPT_PREFIX"
42 default_conopt_lib="conopt3"
43
44 default_tron_prefix="c:\\Program Files\\TRON"
45 default_tron_dlpath="$TRON_PREFIX"
46 default_tron_lib="tron1"
47
48 default_prefix="c:\\MinGW"
49 default_libpath="$DEFAULT_PREFIX\\lib"
50 default_cpppath="$DEFAULT_PREFIX\\include"
51
52 if not os.path.exists(default_conopt_prefix):
53 default_conopt_prefix = None
54
55 need_libm = False
56 python_exe = sys.executable
57 default_with_scrollkeeper=False
58 pathsep = ";"
59
60 default_fortran="g77"
61 default_f2c_lib="g2c"
62
63 else:
64 default_tcl_lib = "tcl8.4"
65 default_tk_lib = "tk8.4"
66 default_tktable_lib = "Tktable2.8"
67 default_install_assets = "$INSTALL_ASCDATA/glade/"
68 icon_extension = '.svg'
69 default_tcl = '/usr'
70 default_tcl_libpath = "$TCL/lib"
71
72 if os.path.exists("/etc/debian_version"):
73 default_tcl_cpppath = "/usr/include/tcl8.4"
74
75 default_rel_distdir = '../share/ascend'
76 default_absolute_paths = True
77 default_ida_prefix="/usr"
78 default_conopt_prefix="/usr"
79 default_conopt_libpath="$CONOPT_PREFIX/lib"
80 default_conopt_cpppath="$CONOPT_PREFIX/include"
81 default_conopt_dlpath= default_conopt_libpath + ":/usr/local/lib"
82 default_conopt_lib="consub3"
83
84 default_tron_prefix="/usr"
85 default_tron_dlpath="$TRON_PREFIX/lib"
86 default_tron_lib="tron1"
87
88 default_prefix="/usr"
89 default_libpath="$DEFAULT_PREFIX/lib"
90 default_cpppath="$DEFAULT_PREFIX/include"
91
92 need_libm = True
93 if not os.path.isdir(default_tcl):
94 default_tcl = '/usr'
95 python_exe = distutils.sysconfig.EXEC_PREFIX+"/bin/python"
96 default_with_scrollkeeper=False
97 pathsep = ":"
98
99 default_fortran="gfortran"
100 default_f2c_lib="gfortran"
101
102 opts.Add(
103 'CC'
104 ,'C Compiler command'
105 ,None
106 )
107
108 opts.Add(
109 'CXX'
110 ,'C++ Compiler command'
111 ,None
112 )
113
114 opts.Add(BoolOption(
115 'GCOV'
116 , 'Whether to enable coverage testing in object code'
117 , False
118 ))
119
120 opts.Add(BoolOption(
121 'WITH_GCCVISIBILITY'
122 ,"Whether to use GCC Visibility features (only applicable if available)"
123 ,True
124 ))
125
126 opts.Add(BoolOption(
127 'WITH_SIGNALS'
128 ,"Whether to permit use of signals for flow control in the C-level code"
129 ,True
130 ))
131
132 # You can turn off building of Tcl/Tk interface
133 opts.Add(BoolOption(
134 'WITH_TCLTK'
135 ,"Set to False if you don't want to build the original Tcl/Tk GUI."
136 , True
137 ))
138
139 # You can turn off the building of the Python interface
140 opts.Add(BoolOption(
141 'WITH_PYTHON'
142 ,"Set to False if you don't want to build Python wrappers."
143 , True
144 ))
145
146 # Which solvers will we allow?
147 opts.Add(ListOption(
148 'WITH_SOLVERS'
149 ,"List of the solvers you want to build. The default is the minimum that"
150 +" works. The option 'LSOD' is provided for backwards compatibility"
151 +"; the value 'LSODE' is preferred."
152 ,["QRSLV","CMSLV","LSODE","IDA","CONOPT","LRSLV","TRON","IPOPT"]
153 ,['QRSLV','MPS','SLV','OPTSQP'
154 ,'NGSLV','CMSLV','LRSLV','MINOS','CONOPT'
155 ,'LSODE','LSOD','OPTSQP',"IDA","TRON","IPOPT"
156 ]
157 ))
158
159 # Where will the local copy of the help files be kept?
160 opts.Add(BoolOption(
161 'WITH_DOC'
162 , "Should we try to build and install help files? If not, ASCEND will access online help files"
163 , True
164 ))
165
166 opts.Add(BoolOption(
167 'WITH_DOC_BUILD'
168 , "If true, we'll attempt to build docs. Set false, we'll assume we already have then (eg from the tarball)"
169 , "$WITH_DOC"
170 ))
171
172 opts.Add(BoolOption(
173 'WITH_DOC_INSTALL'
174 , "If true, SCons will install the documentation file(s). If false, assume rpm or dpkg is going to do it."
175 , "$WITH_DOC"
176 ))
177
178 opts.Add(
179 'HELP_ROOT'
180 , "Location of the main help file"
181 , "$INSTALL_DOC/book.pdf"
182 )
183
184 # Will bintoken support be enabled?
185 opts.Add(BoolOption(
186 'WITH_BINTOKEN'
187 ,"Enable bintoken support? This means compiling models as C-code before"
188 +" running them, to increase solving speed for large models."
189 ,False
190 ))
191
192 # What should the default ASCENDLIBRARY path be?
193 # Note: users can change it by editing their ~/.ascend.ini
194 opts.Add(
195 'DEFAULT_ASCENDLIBRARY'
196 ,"Set the default value of the ASCENDLIBRARY -- the location where"
197 +" ASCEND will look for models when running ASCEND"
198 ,"$INSTALL_MODELS"
199 )
200
201 # What should the default ASCENDLIBRARY path be?
202 # Note: users can change it by editing their ~/.ascend.ini
203 opts.Add(
204 'DEFAULT_ASCENDSOLVERS'
205 ,"Set the default value of ASCENDSOLVERS -- the location where"
206 +" ASCEND will look for solver shared-library files"
207 ,"$INSTALL_SOLVERS"
208 )
209
210 # Where is SWIG?
211 opts.Add(
212 'SWIG'
213 ,"SWIG location, probably only required for MinGW and MSVC users."
214 +" Enter the location as a Windows-style path, for example"
215 +" 'c:\\msys\\1.0\\home\\john\\swigwin-1.3.29\\swig.exe'."
216 )
217
218 # Build the test suite?
219 opts.Add(BoolOption(
220 'WITH_CUNIT'
221 ,"You can disable CUnit tests with this option. This will basically stop"
222 +" SCons from parsing the SConscript files relating to the 'test'"
223 +" target, which just might make things marginally faster. Probably"
224 +" you can just ignore this option though. SCons will sniff for Cunit"
225 +" but build the tests only if you specify the 'test' target."
226 ,True
227 ))
228
229 # Build with MMIO matrix export support?
230 opts.Add(BoolOption(
231 'WITH_MMIO'
232 ,"Include support for exporting matrices in Matrix Market format"
233 ,True
234 ))
235
236 #----- default paths -----
237 opts.Add(PackageOption(
238 'DEFAULT_PREFIX'
239 ,"Where are most of the shared libraries located on your system?"
240 ,default_prefix
241 ))
242
243 #------ install location for python extensions ------
244
245 # (removed for the moment)
246
247 #------ cunit --------
248 # Where was CUNIT installed?
249 opts.Add(PackageOption(
250 'CUNIT_PREFIX'
251 ,"Where are your CUnit files?"
252 ,"$DEFAULT_PREFIX"
253 ))
254
255 # Where are the CUnit includes?
256 opts.Add(PackageOption(
257 'CUNIT_CPPPATH'
258 ,"Where are your CUnit include files?"
259 ,"$CUNIT_PREFIX/include"
260 ))
261
262 # Where are the CUnit libraries?
263 opts.Add(PackageOption(
264 'CUNIT_LIBPATH'
265 ,"Where are your CUnit libraries?"
266 ,"$CUNIT_PREFIX/lib"
267 ))
268
269 #-------- ida -------
270
271 opts.Add(PackageOption(
272 "SUNDIALS_PREFIX"
273 ,"Prefix for your IDA install (IDA ./configure --prefix)"
274 ,default_ida_prefix
275 ))
276
277 opts.Add(
278 'SUNDIALS_CPPPATH'
279 ,"Where is your ida.h?"
280 ,"$SUNDIALS_PREFIX/include"
281 )
282
283 #
284 opts.Add(
285 'SUNDIALS_LIBPATH'
286 ,"Where are your SUNDIALS libraries installed?"
287 ,"$SUNDIALS_PREFIX/lib"
288 )
289
290 opts.Add(
291 'SUNDIALS_LIBS'
292 ,"What libraries are required for SUNDIALS?"
293 ,['sundials_nvecserial','sundials_ida','m']
294 )
295
296 # ----- conopt-----
297
298 opts.Add(PackageOption(
299 "CONOPT_PREFIX"
300 ,"Prefix for your CONOPT install (CONOPT ./configure --prefix)"
301 ,default_conopt_prefix
302 ))
303
304 opts.Add(
305 "CONOPT_LIB"
306 ,"Library linked to for CONOPT"
307 ,default_conopt_lib
308 )
309
310 opts.Add(BoolOption(
311 "CONOPT_LINKED"
312 ,"Do you want to dynamically link to CONOPT (only possible if CONOPT is available at buildtime)"
313 ,False
314 ))
315
316 opts.Add(
317 'CONOPT_CPPPATH'
318 ,"Where is your conopt.h?"
319 ,default_conopt_cpppath
320 )
321
322 opts.Add(
323 'CONOPT_LIBPATH'
324 ,"Where is your CONOPT library installed?"
325 ,default_conopt_libpath
326 )
327
328 opts.Add(
329 'CONOPT_DLPATH'
330 ,"What is the default search path that ASCEND should use when dlopening the CONOPT library at runtime?"
331 ,default_conopt_dlpath
332 )
333
334 opts.Add(
335 'CONOPT_ENVVAR'
336 ,"What environment variable should be used at runtime to override the default search location for CONOPT DLL/SO?"
337 ,default_conopt_envvar
338 )
339
340 #------- IPOPT -------
341
342 opts.Add(PackageOption(
343 "IPOPT_PREFIX"
344 ,"Prefix for your IPOPT install (IPOPT ./configure --prefix)"
345 ,default_conopt_prefix
346 ))
347
348 opts.Add(
349 "IPOPT_LIBS"
350 ,"Library linked to for IPOPT"
351 ,["$F2C_LIB","blas","lapack","pthread","ipopt"]
352 )
353
354
355 opts.Add(
356 "IPOPT_LIBPATH"
357 ,"Where is your IPOPT library installed"
358 ,"$IPOPT_PREFIX/lib"
359 )
360
361 opts.Add(
362 'IPOPT_CPPPATH'
363 ,"Where is your ipopt/IpStdCInterface.h (do not include the 'ipopt' in the path)"
364 ,"$IPOPT_PREFIX/include"
365 )
366
367
368 #------- TRON -------
369
370 opts.Add(
371 'TRON_ENVVAR'
372 ,"What environment variable should be used at runtime to override the default search location for TRON DLL/SO?"
373 ,default_tron_envvar
374 )
375
376 opts.Add(
377 "TRON_LIB"
378 ,"Library linked to for TRON"
379 ,"tron"
380 )
381
382 opts.Add(
383 "TRON_PREFIX"
384 ,"Prefix for your TRON install"
385 ,default_tron_prefix
386 )
387
388 opts.Add(
389 'TRON_DLPATH'
390 ,"What is the default search path that ASCEND should use when dlopening the TRON library at runtime?"
391 ,default_tron_dlpath
392 )
393
394 #-------- f2c ------
395
396 opts.Add(
397 "F2C_LIB"
398 ,"F2C library (eg. g2c, gfortran, f2c)"
399 ,default_f2c_lib # the default is gfortran now
400 )
401
402 opts.Add(PackageOption(
403 "F2C_LIBPATH"
404 ,"Directory containing F2C library (i.e. g2c, gfortran, f2c, etc.), if not already accessible"
405 ,"off"
406 ))
407
408 opts.Add(
409 "FORTRAN"
410 ,"Fortran compiler (eg g77, gfortran)"
411 ,default_fortran
412 )
413
414 #------- tcl/tk --------
415
416 opts.Add(
417 'TCL'
418 ,'Base of Tcl distribution'
419 ,default_tcl
420 )
421
422 # Where are the Tcl includes?
423 opts.Add(
424 'TCL_CPPPATH'
425 ,"Where are your Tcl include files?"
426 ,default_tcl_cpppath
427 )
428
429 # Where are the Tcl libs?
430 opts.Add(
431 'TCL_LIBPATH'
432 ,"Where are your Tcl libraries?"
433 ,default_tcl_libpath
434 )
435
436 # What is the name of the Tcl lib?
437 opts.Add(
438 'TCL_LIB'
439 ,"Name of Tcl lib (eg 'tcl' or 'tcl83'), for full path to static library (if STATIC_TCLTK is set)"
440 ,default_tcl_lib
441 )
442
443 # Where are the Tk includes?
444 opts.Add(
445 'TK_CPPPATH'
446 ,"Where are your Tk include files?"
447 ,'$TCL_CPPPATH'
448 )
449
450 # Where are the Tk libs?
451 opts.Add(
452 'TK_LIBPATH'
453 ,"Where are your Tk libraries?"
454 ,'$TCL_LIBPATH'
455 )
456
457 # What is the name of the Tk lib?
458 opts.Add(
459 'TK_LIB'
460 ,"Name of Tk lib (eg 'tk' or 'tk83'), or full path to static library"
461 ,default_tk_lib
462 )
463
464 # Static linking to TkTable
465
466 opts.Add(BoolOption(
467 'STATIC_TCLTK'
468 ,'Set true for static linking for Tcl/Tk and TkTable. EXPERIMENTAL'
469 ,False
470 ))
471
472 opts.Add(
473 'TKTABLE_LIBPATH'
474 ,'Location of TkTable static library'
475 ,'$TCL_LIBPATH/Tktable2.8'
476 )
477
478 opts.Add(
479 'TKTABLE_LIB'
480 ,'Stem name of TkTable (eg tktable2.8, no ".so" or "lib") shared library, or full path of static tktable (/usr/lib/...)'
481 ,default_tktable_lib
482 )
483
484 opts.Add(
485 'TKTABLE_CPPPATH'
486 ,'Location of TkTable header file'
487 ,'$TCL_CPPPATH'
488 )
489
490 opts.Add(
491 'X11'
492 ,'Base X11 directory. Only used when STATIC_TCLTK is turned on. EXPERIMENTAL'
493 ,'/usr/X11R6'
494 )
495
496 opts.Add(
497 'X11_LIBPATH'
498 ,'Location of X11 lib. EXPERIMENTAL'
499 ,'$X11/lib'
500 )
501
502 opts.Add(
503 'X11_CPPPATH'
504 ,'Location of X11 includes. EXPERIMENTAL'
505 ,'$X11/include'
506 )
507
508 opts.Add(
509 'X11_LIB'
510 ,'Name of X11 lib. EXPERIMENTAL'
511 ,'X11'
512 )
513
514 #----- installed file locations (for 'scons install') -----
515
516 opts.Add(
517 'INSTALL_PREFIX'
518 ,'Root location for installed files'
519 ,'/usr/local'
520 )
521
522 opts.Add(
523 'INSTALL_BIN'
524 ,'Location to put binaries during installation'
525 ,"$INSTALL_PREFIX/bin"
526 )
527
528 opts.Add(
529 'INSTALL_LIB'
530 ,'Location to put libraries during installation'
531 ,"$INSTALL_PREFIX/lib"
532 )
533
534 opts.Add(
535 'INSTALL_SHARE'
536 ,'Common shared-file location on this system'
537 ,"$INSTALL_PREFIX/share"
538 )
539
540 opts.Add(
541 'INSTALL_ASCDATA'
542 ,"Location of ASCEND shared data (TK, python, models etc)"
543 ,"$INSTALL_SHARE/ascend"
544 )
545
546 opts.Add(
547 'INSTALL_MODELS'
548 ,"Location of ASCEND model files (.a4c,.a4l,.a4s)"
549 ,"$INSTALL_ASCDATA/models"
550 )
551
552 opts.Add(
553 'INSTALL_SOLVERS'
554 ,"Location of ASCEND solvers"
555 ,"$INSTALL_ASCDATA/solvers"
556 )
557
558 opts.Add(
559 'INSTALL_DOC'
560 ,"Location of ASCEND documentation files"
561 ,"$INSTALL_SHARE/doc/ascend-"+version
562 )
563
564 opts.Add(
565 'INSTALL_INCLUDE'
566 ,'Location to put header files during installation'
567 ,"$INSTALL_PREFIX/include"
568 )
569
570
571 opts.Add(
572 'INSTALL_ROOT'
573 ,'For use by RPM only: location of %{buildroot} during rpmbuild'
574 ,""
575 )
576
577 opts.Add(
578 'EXTLIB_SUFFIX'
579 ,"Filename suffix for ASCEND 'external libraries' (for use with IMPORT"
580 ,"_ascend$SHLIBSUFFIX"
581 )
582
583 opts.Add(
584 'EXTLIB_PREFIX'
585 ,"Filename suffix for ASCEND 'external libraries' (for use with IMPORT"
586 ,"$SHLIBPREFIX"
587 )
588
589 #----------------------
590
591 opts.Add(
592 'PYGTK_ASSETS'
593 ,'Default location for Glade assets (placed in pygtk/config.py)'
594 ,default_install_assets
595 )
596
597 opts.Add(BoolOption(
598 'DEBUG'
599 ,"Compile source with debugger symbols, eg for use with 'gdb'"
600 ,False
601 ))
602
603 opts.Add(BoolOption(
604 'MALLOC_DEBUG'
605 ,"Compile with debugging version of MALLOC. Required for full CUnit testing"
606 ,False
607 ))
608
609 #------ dmalloc --------
610 opts.Add(PackageOption(
611 'DMALLOC_PREFIX'
612 ,"Where are your dmalloc files?"
613 ,default_prefix
614 ))
615
616 opts.Add(PackageOption(
617 'DMALLOC_CPPPATH'
618 ,"Where are your dmalloc include files?"
619 ,default_cpppath
620 ))
621
622 opts.Add(PackageOption(
623 'DMALLOC_LIBPATH'
624 ,"Where are your dmalloc libraries?"
625 ,default_libpath
626 ))
627
628 opts.Add(BoolOption(
629 'WITH_DMALLOC'
630 ,"Link to the DMALLOC library (if available) for debugging of memory usage."
631 ,False
632 ))
633
634 #------ f --------
635 opts.Add(PackageOption(
636 'MFGRAPH_PREFIX'
637 ,"Where are your MFGRAPH files?"
638 ,default_prefix
639 ))
640
641 opts.Add(PackageOption(
642 'MFGRAPH_CPPPATH'
643 ,"Where are your MFGRAPH include files?"
644 ,default_cpppath
645 ))
646
647 opts.Add(PackageOption(
648 'MFGRAPH_LIBPATH'
649 ,"Where are your MFGRAPH libraries?"
650 ,default_libpath
651 ))
652
653 opts.Add(BoolOption(
654 'WITH_MFGRAPH'
655 ,"Link to the MFGRAPH library (if available, for generating incidence graphs)"
656 ,True
657 ))
658
659
660 #------ ufsparse --------
661 opts.Add(PackageOption(
662 'UFSPARSE_PREFIX'
663 ,"Where are your UFSPARSE files?"
664 ,default_prefix
665 ))
666
667 opts.Add(PackageOption(
668 'UFSPARSE_CPPPATH'
669 ,"Where are your UFSPARSE include files?"
670 ,default_cpppath
671 ))
672
673 opts.Add(PackageOption(
674 'UFSPARSE_LIBPATH'
675 ,"Where are your UFSPARSE libraries?"
676 ,default_libpath
677 ))
678
679 opts.Add(BoolOption(
680 'WITH_UFSPARSE'
681 ,"Link to the UFSPARSE library (if available, for additional sparse matrix routines)"
682 ,True
683 ))
684
685 #-----------------------
686
687 opts.Add(BoolOption(
688 'UPDATE_NO_YACC_LEX'
689 ,"Update the *_no_yacc* and *_no_lex* files in the source tree? (these files are created so that ASCEND can be compiled in the absence of those tools)"
690 ,False
691 ))
692
693 opts.Add(
694 'DISTTAR_NAME'
695 ,"Stem name of the tarball created by 'scons dist'. So for 'ascend-aaa.tar.bz2', set this to 'ascend-aaa'."
696 ,"ascend-"+version
697 )
698
699 opts.Add(
700 'RELEASE'
701 ,"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."
702 ,"0"
703 )
704
705 opts.Add(BoolOption(
706 'ABSOLUTE_PATHS'
707 ,"Whether to use absolute or relative paths in the installed Tcl/Tk interface. If you want to build an RPM, set this to false."
708 ,default_absolute_paths
709 ))
710
711 opts.Add(
712 'WIN_INSTALLER_NAME'
713 ,"Name of the installer .exe to create under Windows (minus the '.exe')"
714 ,"ascend-"+version+"-py"+pyversion+".exe"
715 )
716
717 opts.Add(BoolOption(
718 'WITH_XTERM_COLORS'
719 ,"Set to 0 if you don't want xterm colour codes in the console output"
720 ,True
721 ))
722
723 opts.Add(BoolOption(
724 'WITH_EXTFNS'
725 ,"Set to 0 if you don't want to attempt to build the external modules bundled with ASCEND"
726 ,True
727 ))
728
729 opts.Add(BoolOption(
730 'WITH_SCROLLKEEPER'
731 ,"Set to to 1 if you want to install an OMF file that can be read by scrollkeeper (eg Yelp on GNOME)"
732 ,default_with_scrollkeeper
733 ))
734
735
736 if platform.system()!="Windows":
737 opts.Add(BoolOption(
738 'WITH_GCCVISIBILITY'
739 , 'Whether to use GCC Visibility extensions when building with GCC 4.0'
740 , True
741 ))
742
743
744
745 # TODO: OTHER OPTIONS?
746 # TODO: flags for optimisation
747 # TODO: turning on/off bintoken functionality
748 # TODO: Where will the 'Makefile.bt' file be installed?
749
750 # Import the outside environment
751
752 def c_escape(str):
753 return re.sub("\\\\","/",str)
754
755 envadditional={}
756
757 tools = ['lex','yacc','fortran','swig','nsis','substinfile','disttar']
758 if platform.system()=="Windows":
759 if os.environ.get('OSTYPE')=='msys' or os.environ.get('MSYSTEM'):
760 envenv = os.environ;
761 tools += ['mingw']
762 #TODO removed 'doxygen' for SCons 0.96.93
763 envadditional['IS_MINGW']=True
764 else:
765 print "Assuming VC++ build environment (Note: MinGW is preferred)"
766 envenv = {
767 'PATH':os.environ['PATH']
768 ,'INCLUDE':os.environ['INCLUDE']
769 ,'LIB':os.environ['LIB']
770 ,'MSVS_IGNORE_IDE_PATHS':1
771 }
772 tools += ['default']
773 #TODO removed 'doxygen' for SCons 0.96.93
774 envadditional['CPPDEFINES']=['_CRT_SECURE_NO_DEPRECATE']
775 else:
776 if os.environ.get('TARGET')=='mingw':
777 envenv = os.environ
778 tools += ['crossmingw']
779 envadditional['CPPPATH']=['/usr/lib/gcc/i586-mingw32msvc/3.4.5/include','/usr/include']
780 envadditional['LIBS']=['gcc']
781 else:
782 envenv = os.environ
783 tools += ['default']
784 #TODO removed 'doxygen' for SCons 0.96.93
785
786
787 env = Environment(
788 ENV=envenv
789 , toolpath=['scons']
790 , tools=tools
791 , **envadditional
792 )
793
794 #print "PATH =",os.environ['PATH']
795 #print "PROGSUFFIX =",env['PROGSUFFIX']
796 #print "CPPPATH =",env['CPPPATH']
797
798 opts.Update(env)
799
800 if 'LSOD' in env['WITH_SOLVERS']:
801 if 'LSODE' not in env['WITH_SOLVERS']:
802 env['WITH_SOLVERS'].append('LSODE')
803 env['WITH_SOLVERS'].remove('LSOD')
804
805 opts.Save('options.cache',env)
806
807 Help(opts.GenerateHelpText(env))
808
809 with_tcltk = env.get('WITH_TCLTK')
810 without_tcltk_reason = "disabled by options/config.py"
811
812 with_python = env.get('WITH_PYTHON')
813 without_python_reason = "disabled by options/config.py"
814
815 with_cunit = env.get('WITH_CUNIT')
816 without_cunit_reason = "not requested"
817
818 with_extfns = env.get('WITH_EXTFNS')
819 without_extfn_reason = "disabled by options/config.py"
820
821 with_scrollkeeper = env.get('WITH_SCROLLKEEPER')
822 without_scrollkeeper_reason = "disabled by options/config.py"
823
824 with_dmalloc = env.get('WITH_DMALLOC')
825 without_dmalloc_reason = "disabled by options/config.py"
826
827 with_mfgraph = env.get('WITH_MFGRAPH')
828 without_mfgraph_reason = "disabled by options/config.py"
829
830 with_ufsparse = env.get('WITH_UFSPARSE')
831 without_ufsparse_reason = "disabled by options/config.py"
832
833 with_mmio = env.get('WITH_MMIO')
834 without_mmio_reason = "disabled by options/config.py"
835
836 with_signals = env.get('WITH_SIGNALS')
837 without_signals_reason = "disabled by options/config.py"
838
839 with_doc = env.get('WITH_DOC')
840
841 with_doc_build = env.get('WITH_DOC_BUILD');
842 without_doc_build_reason = "disabled by options/config.py"
843 if not with_doc:
844 with_doc_build = False
845 without_doc_build_reason = "disabled by with_doc"
846
847 with_latex2html = False
848
849 if platform.system()=="Windows":
850 with_installer=1
851 else:
852 with_installer=0
853 without_installer_reason = "only possible under Windows"
854
855 if 'LSODE' in env['WITH_SOLVERS']:
856 with_lsode=True
857 else:
858 with_lsode=False
859 without_lsode_reason = "not requested (WITH_SOLVERS)"
860
861 if 'IDA' in env['WITH_SOLVERS']:
862 with_ida=True
863 else:
864 with_ida=False
865 without_ida_reason = "not requested (WITH_SOLVERS)"
866
867
868 if 'CONOPT' in env['WITH_SOLVERS']:
869 with_conopt=True
870 else:
871 with_conopt=False
872 without_conopt_reason = "not requested (WITH_SOLVERS)"
873
874 if 'IPOPT' in env['WITH_SOLVERS']:
875 with_ipopt=True
876 else:
877 with_ipopt=False
878 without_ipopt_reason = "not requested (WITH_SOLVERS)"
879
880
881 #print "SOLVERS:",env['WITH_SOLVERS']
882 #print "WITH_BINTOKEN:",env['WITH_BINTOKEN']
883 #print "DEFAULT_ASCENDLIBRARY:",env['DEFAULT_ASCENDLIBRARY']
884
885 can_install = True
886 if platform.system()=='Windows':
887 can_install = False
888
889 env['CAN_INSTALL']=can_install
890
891 print "TCL=",env['TCL']
892 print "TCL_CPPPATH =",env['TCL_CPPPATH']
893 print "TCL_LIBPATH =",env['TCL_LIBPATH']
894 print "TCL_LIB =",env['TCL_LIB']
895 print "CC =",env['CC']
896 print "CXX =",env['CXX']
897 print "FORTRAN=",env.get('FORTRAN')
898
899 print "ABSOLUTE PATHS =",env['ABSOLUTE_PATHS']
900 print "INSTALL_ASCDATA =",env['INSTALL_ASCDATA']
901 print "INSTALL_PREFIX =",env['INSTALL_PREFIX']
902 print "INSTALL_MODELS =",env['INSTALL_MODELS']
903 print "INSTALL_SOLVERS =",env['INSTALL_SOLVERS']
904 print "DEFAULT_ASCENDLIBRARY =",env['DEFAULT_ASCENDLIBRARY']
905 print "DEFAULT_ASCENDSOLVERS =",env['DEFAULT_ASCENDSOLVERS']
906
907
908 #------------------------------------------------------
909 # SPECIAL CONFIGURATION TESTS
910
911 need_fortran = False
912
913 #----------------
914 # CC
915
916 cc_test_text = """
917 int main(void){
918 return 0;
919 }
920 """;
921
922 def CheckCC(context):
923 context.Message("Checking C compiler ('%s')... " % context.env.get('CC'))
924 is_ok = context.TryCompile(cc_test_text,".c")
925 context.Result(is_ok)
926 return is_ok
927
928 #----------------
929 # CXX
930
931 cxx_test_text = """
932 template<class X>
933 class pair{
934 public:
935 X a;
936 X b;
937 };
938
939 int main(void){
940 pair<double> P;
941 P.a = 0;
942 return 0;
943 }
944 """;
945
946 def CheckCXX(context):
947 context.Message("Checking C++ compiler ('%s')... " % context.env.get('CXX'))
948 is_ok = context.TryCompile(cc_test_text,".cpp")
949 context.Result(is_ok)
950 return is_ok
951
952
953
954 #----------------
955 # SWIG
956
957 import os,re
958
959 def get_swig_version(env):
960 cmd = env['SWIG']+' -version'
961 (cin,coutcerr) = os.popen4(cmd)
962 output = coutcerr.read()
963
964 restr = "SWIG\\s+Version\\s+(?P<maj>[0-9]+)\\.(?P<min>[0-9]+)\\.(?P<pat>[0-9]+)\\s*$"
965 expr = re.compile(restr,re.M);
966 m = expr.search(output);
967 if not m:
968 return None
969 maj = int(m.group('maj'))
970 min = int(m.group('min'))
971 pat = int(m.group('pat'))
972
973 return (maj,min,pat)
974
975
976 def CheckSwigVersion(context):
977
978 try:
979 context.Message("Checking version of SWIG... ")
980 maj,min,pat = get_swig_version(context.env)
981 except:
982 context.Result("Failed to detect version, or failed to run SWIG")
983 return 0;
984
985 context.env['SWIGVERSION']=tuple([maj,min,pat])
986
987 if maj == 1 and (
988 min > 3
989 or (min == 3 and pat >= 24)
990 ):
991 context.Result("ok, %d.%d.%d" % (maj,min,pat))
992 return 1;
993 else:
994 context.Result("too old, %d.%d.%d" % (maj,min,pat))
995 return 0;
996
997 #----------------
998 # Scrollkeeper (Linux documentation system)
999
1000 def get_scrollkeeper_omfdir(env):
1001 cmd = 'scrollkeeper-config --omfdir'
1002 (cin,coutcerr) = os.popen4(cmd)
1003 output = coutcerr.read()
1004 return output.strip()
1005
1006 def CheckScrollkeeperConfig(context):
1007 try:
1008 context.Message("Checking for scrollkeeper...")
1009 dir=get_scrollkeeper_omfdir(context.env)
1010 except:
1011 context.Result("Failed to run 'scrollkeeper-config'")
1012 return 0
1013 context.env['OMFDIR']=dir
1014 context.Result("OK, %s" % dir)
1015 return 1
1016
1017 #----------------
1018 # General purpose library-and-header test
1019
1020 class KeepContext:
1021 def __init__(self,context,varprefix,static=False):
1022 self.keep = {}
1023 for k in ['LIBS','LIBPATH','CPPPATH','LINKFLAGS']:
1024 #print "Keeping env %s = %s" % (k,context.env.get(k))
1025 self.keep[k]=context.env.get(k)
1026
1027 if context.env.has_key(varprefix+'_CPPPATH'):
1028 context.env.AppendUnique(CPPPATH=[env[varprefix+'_CPPPATH']])
1029 #print "Adding '"+str(env[varprefix+'_CPPPATH'])+"' to cpp path"
1030
1031 if static:
1032 staticlib=env[varprefix+'_LIB']
1033 #print "STATIC LIB = ",staticlib
1034 context.env.Append(
1035 LINKFLAGS=[staticlib]
1036 )
1037 else:
1038 if context.env.has_key(varprefix+'_LIBPATH'):
1039 context.env.Append(LIBPATH=[env[varprefix+'_LIBPATH']])
1040 #print "Adding '"+str(env[varprefix+'_LIBPATH'])+"' to lib path"
1041
1042 if context.env.has_key(varprefix+'_LIB'):
1043 context.env.Append(LIBS=[env[varprefix+'_LIB']])
1044 #print "Adding '"+str(env[varprefix+'_LIB'])+"' to libs"
1045 elif context.env.has_key(varprefix+'_LIBS'):
1046 context.env.AppendUnique(LIBS=env[varprefix+'_LIBS'])
1047
1048 def restore(self,context):
1049 #print "RESTORING CONTEXT"
1050 #print self.keep
1051 #print "..."
1052 for k in self.keep:
1053 if self.keep[k]==None:
1054 if context.env.has_key(k):
1055 #print "Clearing "+str(k)
1056 del context.env[k];
1057 else:
1058 #print "Restoring %s to '%s'" %(k,self.keep.get(k))
1059 context.env[k]=self.keep[k];
1060
1061 def CheckExtLib(context,libname,text,ext='.c',varprefix=None,static=False):
1062 """This method will check for variables LIBNAME_LIBPATH
1063 and LIBNAME_CPPPATH and try to compile and link the
1064 file with the provided text, linking with the
1065 library libname."""
1066
1067 if static:
1068 context.Message( 'Checking for static '+libname+'... ' )
1069 else:
1070 context.Message( 'Checking for '+libname+'... ' )
1071
1072 if varprefix==None:
1073 varprefix = libname.upper()
1074
1075 #print "LIBS is currently:",context.env.get('LIBS')
1076 keep = KeepContext(context,varprefix,static)
1077
1078 if not context.env.has_key(varprefix+'_LIB'):
1079 # if varprefix_LIB were in env, KeepContext would
1080 # have appended it already
1081 context.env.Append(LIBS=[libname])
1082
1083 is_ok = context.TryLink(text,ext)
1084
1085 #print "Link success? ",(is_ok != 0)
1086
1087 keep.restore(context)
1088
1089 # print "Restored CPPPATH="+str(context.env['CPPPATH'])
1090 # print "Restored LIBS="+str(context.env['LIBS'])
1091 # print "Restored LIBPATH="+str(context.env['LIBPATH'])
1092
1093 context.Result(is_ok)
1094 return is_ok
1095
1096 #----------------
1097 # GCC
1098
1099 gcc_test_text = """
1100 #ifndef __GNUC__
1101 # error "Not using GCC"
1102 #endif
1103
1104 int main(void){
1105 return __GNUC__;
1106 }
1107 """
1108
1109 def CheckGcc(context):
1110 context.Message("Checking for GCC... ")
1111 is_ok = context.TryCompile(gcc_test_text,".c")
1112 context.Result(is_ok)
1113 return is_ok
1114
1115 #----------------
1116 # GCC VISIBILITY feature
1117
1118 gccvisibility_test_text = """
1119 #if __GNUC__ < 4
1120 # error "Require GCC version 4 or newer"
1121 #endif
1122
1123 __attribute__ ((visibility("default"))) int x;
1124
1125 int main(void){
1126 extern int x;
1127 x = 4;
1128 }
1129 """
1130
1131 def CheckGccVisibility(context):
1132 context.Message("Checking for GCC 'visibility' capability... ")
1133 if not context.env.has_key('WITH_GCCVISIBILITY') or not env['WITH_GCCVISIBILITY']:
1134 context.Result("disabled")
1135 return 0
1136 is_ok = context.TryCompile(gccvisibility_test_text,".c")
1137 context.Result(is_ok)
1138 return is_ok
1139
1140 #----------------
1141 # YACC
1142
1143 yacc_test_text = """
1144 %{
1145 #include <stdio.h>
1146
1147 /* MSVC++ needs this before it can swallow Bison output */
1148 #ifdef _MSC_VER
1149 # define __STDC__
1150 #endif
1151 %}
1152 %token MSG
1153 %start ROOT
1154 %%
1155 ROOT:
1156 MSG { printf("HELLO"); }
1157 ;
1158 %%
1159 """
1160
1161 def CheckYacc(context):
1162 context.Message("Checking for Yacc ('%s')... " % context.env.get('YACC'))
1163 is_ok = context.TryCompile(yacc_test_text,".y")
1164 context.Result(is_ok)
1165 return is_ok
1166
1167 #----------------
1168 # LEX
1169
1170 lex_test_text = """
1171 %{
1172 #include <stdio.h>
1173 %}
1174 DIGIT [0-9]
1175 ID [a-z][a-z0-9]*
1176 %%
1177 {DIGIT}+ {
1178 printf("A digit: %s\\n",yytext);
1179 }
1180
1181 [ \\t\\n]+ /* ignore */
1182
1183 . {
1184 printf("Unrecognized guff");
1185 }
1186 %%
1187 main(){
1188 yylex();
1189 }
1190 """
1191
1192 def CheckLex(context):
1193 context.Message("Checking for Lex ('%s')... " % context.env.get('LEX'))
1194 is_ok = context.TryCompile(lex_test_text,".l")
1195 context.Result(is_ok)
1196 return is_ok
1197
1198 #----------------
1199 # CUnit test
1200
1201 cunit_test_text = """
1202 #include <CUnit/CUnit.h>
1203 int maxi(int i1, int i2){
1204 return (i1 > i2) ? i1 : i2;
1205 }
1206
1207 void test_maxi(void){
1208 CU_ASSERT(maxi(0,2) == 2);
1209 CU_ASSERT(maxi(0,-2) == 0);
1210 CU_ASSERT(maxi(2,2) == 2);
1211
1212 }
1213 int main(void){
1214 /* CU_initialize_registry() */
1215 return 0;
1216 }
1217 """
1218
1219 def CheckCUnit(context):
1220 return CheckExtLib(context,'cunit',cunit_test_text)
1221
1222 #----------------
1223 # dmalloc test
1224
1225 dmalloc_test_text = """
1226 #include <stdlib.h>
1227 #include <dmalloc.h>
1228
1229 int main(void){
1230 char *c;
1231 c = malloc(100*sizeof(char));
1232 free(c);
1233 return 0;
1234 }
1235 """
1236
1237 def CheckDMalloc(context):
1238 return CheckExtLib(context,'dmalloc',dmalloc_test_text)
1239
1240 #----------------
1241 # mfgraph test
1242
1243 mfgraph_test_text = """
1244 #include <mfgraph/mfg_draw_graph.h>
1245 int main(void){
1246 using namespace mfg;
1247 DrawGraph g;
1248 return 0;
1249 }
1250 """
1251
1252 def CheckMFGraph(context):
1253 return CheckExtLib(context,'mfgraph',mfgraph_test_text,ext=".cpp")
1254
1255 #----------------
1256 # ufsparse test
1257
1258 ufsparse_test_text = """
1259 #include <ufsparse/cs.h>
1260 int main(void){
1261 cs *A,*B,*C;
1262 C = cs_multiply(A,B);
1263 return 0;
1264 }
1265 """
1266
1267 def CheckUFSparse(context):
1268 return CheckExtLib(context
1269 ,libname='cxsparse'
1270 ,varprefix='ufsparse'
1271 ,text=ufsparse_test_text
1272 ,ext=".c"
1273 )
1274
1275 #----------------
1276 # MATH test
1277
1278 math_test_text = """
1279 #ifndef _ALL_SOURCE
1280 # define _ALL_SOURCE
1281 #endif
1282 #ifndef _XOPEN_SOURCE
1283 # define _XOPEN_SOURCE
1284 #endif
1285 #ifndef _XOPEN_SOURCE_EXTENDED
1286 # define _XOPEN_SOURCE_EXTENDED 1
1287 #endif
1288 #include <math.h>
1289 int main(void){
1290 double x = 1.0; double y = 1.0; int i = 1;
1291 acosh(x); asinh(x); atanh(x); cbrt(x); expm1(x); erf(x); erfc(x); isnan(x);
1292 j0(x); j1(x); jn(i,x); ilogb(x); logb(x); log1p(x); rint(x);
1293 y0(x); y1(x); yn(i,x);
1294 /* this part causes problems with crossmingw... */
1295 #ifdef _THREAD_SAFE
1296 gamma_r(x,&i);
1297 lgamma_r(x,&i);
1298 #else
1299 gamma(x);
1300 lgamma(x);
1301 #endif
1302 hypot(x,y); nextafter(x,y); remainder(x,y); scalb(x,y);
1303 return 0;
1304 }
1305 """
1306
1307 def CheckMath(context):
1308 context.Message('Checking for IEEE math library... ')
1309 libsave=context.env.get('LIBS');
1310 context.env.AppendUnique(LIBS=['m'])
1311 is_ok=context.TryLink(math_test_text,".c")
1312 context.Result(is_ok)
1313 if not is_ok:
1314 context.env['LIBS']=libsave
1315 return is_ok
1316
1317 #----------------
1318 # libpython test
1319
1320 libpython_test_text = """
1321 #include <Python.h>
1322 int main(void){
1323 PyObject *p;
1324 p = Py_None;
1325 return 0;
1326 }
1327 """
1328
1329 def CheckPythonLib(context):
1330 context.Message('Checking for libpython... ')
1331
1332 if platform.system()=="Windows":
1333 python_lib='python%d%d'
1334 else:
1335 python_lib='python%d.%d'
1336 python_libs = [python_lib % (sys.version_info[0],sys.version_info[1])]
1337
1338 python_cpppath = [distutils.sysconfig.get_python_inc()]
1339 cfig = distutils.sysconfig.get_config_vars()
1340
1341 lastLIBS = context.env.get('LIBS')
1342 lastLIBPATH = context.env.get('LIBPATH')
1343 lastCPPPATH = context.env.get('CPPPATH')
1344 lastLINKFLAGS = context.env.get('LINKFLAGS')
1345
1346 python_libpath = []
1347 python_linkflags = []
1348 if platform.system()=="Windows":
1349 python_libpath += [os.path.join(sys.prefix,"libs")]
1350 else:
1351 # checked on Linux and SunOS
1352 if cfig['LDLIBRARY']==cfig['LIBRARY']:
1353 sys.stdout.write("(static)")
1354 python_libpath += [cfig['LIBPL']]
1355 python_linkflags += cfig['LIBS'].split(' ')
1356
1357 context.env.AppendUnique(LIBS=python_libs)
1358 context.env.AppendUnique(LIBPATH=python_libpath)
1359 context.env.AppendUnique(CPPPATH=python_cpppath)
1360 context.env.AppendUnique(LINKFLAGS=python_linkflags)
1361 result = context.TryLink(libpython_test_text,".c");
1362
1363 context.Result(result)
1364
1365 if(result):
1366 context.env['PYTHON_LIBPATH']=python_libpath
1367 context.env['PYTHON_LIB']=python_libs
1368 context.env['PYTHON_CPPPATH']=python_cpppath
1369 context.env['PYTHON_LINKFLAGS']=python_linkflags
1370
1371 context.env['LIBS'] = lastLIBS
1372 context.env['LIBPATH'] = lastLIBPATH
1373 context.env['CPPPATH'] = lastCPPPATH
1374 context.env['LINKFLAGS'] = lastLINKFLAGS
1375
1376 return result
1377
1378 #----------------
1379 # IDA test
1380
1381 sundials_version_major_required = 2
1382 sundials_version_minor_min = 2
1383 sundials_version_minor_max = 3
1384
1385 sundials_version_text = """
1386 #include <sundials/sundials_config.h>
1387 #include <stdio.h>
1388 int main(){
1389 printf("%s",SUNDIALS_PACKAGE_VERSION);
1390 return 0;
1391 }
1392 """
1393
1394 ida_test_text = """
1395 #if SUNDIALS_VERSION_MAJOR==2 && SUNDIALS_VERSION_MINOR==2
1396 # include <sundials/sundials_config.h>
1397 # include <sundials/sundials_nvector.h>
1398 # include <nvector_serial.h>
1399 # include <ida.h>
1400 # include <ida/ida_spgmr.h>
1401 #else
1402 # include <sundials/sundials_config.h>
1403 # include <nvector/nvector_serial.h>
1404 # include <ida/ida.h>
1405 #endif
1406 int main(){
1407 void *ida_mem;
1408 ida_mem = IDACreate();
1409 return 0;
1410 }
1411 """
1412
1413 # slightly changed calling convention (IDACalcID) in newer versions of SUNDIALS,
1414 # so detect the version and act accordingly.
1415 def CheckSUNDIALS(context):
1416 keep = KeepContext(context,'SUNDIALS')
1417 context.Message("Checking for SUNDIALS... ")
1418 (is_ok,output) = context.TryRun(sundials_version_text,'.c')
1419 keep.restore(context)
1420 if not is_ok:
1421 context.Result(0)
1422 return 0
1423
1424 major,minor,patch = tuple([int(i) for i in output.split(".")])
1425 context.env['SUNDIALS_VERSION_MAJOR'] = major
1426 context.env['SUNDIALS_VERSION_MINOR'] = minor
1427 if major != sundials_version_major_required \
1428 or minor < sundials_version_minor_min \
1429 or minor > sundials_version_minor_max:
1430 context.Result(output+" (bad version)")
1431 # bad version
1432 return 0
1433
1434 # good version
1435 context.Result("%d.%d.%d, good" % (major,minor,patch))
1436
1437 return 1
1438
1439
1440 def CheckIDA(context):
1441 context.Message( 'Checking for IDA... ' )
1442
1443 keep = KeepContext(context,"SUNDIALS")
1444
1445 major = context.env['SUNDIALS_VERSION_MAJOR']
1446 minor = context.env['SUNDIALS_VERSION_MINOR']
1447
1448 cppdef = context.env.get('CPPDEFINES')
1449
1450 context.env.Append(CPPDEFINES=[
1451 ('SUNDIALS_VERSION_MAJOR',"$SUNDIALS_VERSION_MAJOR")
1452 ,('SUNDIALS_VERSION_MINOR',"$SUNDIALS_VERSION_MINOR")
1453 ])
1454
1455 context.env['SUNDIALS_CPPPATH_EXTRA']=[]
1456 if major==2 and minor==2:
1457 context.env.Append(SUNDIALS_CPPPATH_EXTRA = ["$SUNDIALS_CPPPATH/sundials"])
1458
1459 context.env.Append(CPPDEFINES=[('SUNDIALS_VERSION_MAJOR',"$SUNDIALS_VERSION_MAJOR"),('SUNDIALS_VERSION_MINOR',"$SUNDIALS_VERSION_MINOR")])
1460 context.env.AppendUnique(LIBS=context.env['SUNDIALS_LIBS'])
1461 context.env.AppendUnique(CPPPATH=context.env['SUNDIALS_CPPPATH_EXTRA'])
1462
1463 is_ok = context.TryLink(ida_test_text,".c")
1464 context.Result(is_ok)
1465
1466 if cppdef:
1467 context.env['CPPDEFINES']=cppdef
1468 else:
1469 del context.env['CPPDEFINES']
1470
1471 keep.restore(context)
1472
1473 return is_ok
1474
1475
1476 #----------------
1477 # CONOPT test
1478
1479 conopt_test_text = """
1480 #if !defined(_WIN32)
1481 # define FNAME_LCASE_DECOR
1482 #endif
1483
1484 #include <conopt.h>
1485 #include <stdlib.h>
1486 int main(){
1487 int s, *v, e;
1488 s = COIDEF_Size();
1489 v = (int *)malloc(s*sizeof(int));
1490 e = COIDEF_Ini(v);
1491 return e;
1492 }
1493 """
1494
1495 def CheckCONOPT(context):
1496 context.Message( 'Checking for CONOPT... ' )
1497
1498 keep = KeepContext(context,"CONOPT")
1499
1500 is_ok = context.TryLink(conopt_test_text,".c")
1501 context.Result(is_ok)
1502
1503 keep.restore(context)
1504
1505 return is_ok
1506
1507 #----------------
1508 # IPOPT test
1509
1510 ipopt_test_text = """
1511 #if !defined(_WIN32)
1512 # define FNAME_LCASE_DECOR
1513 #endif
1514
1515 #include <ipopt/IpStdCInterface.h>
1516 int main(){
1517 Number n;
1518 IpoptProblem nlp = 0;
1519 FreeIpoptProblem(nlp); // probably a crash if you run this
1520 return 0;
1521 }
1522 """
1523
1524 def CheckIPOPT(context):
1525 context.Message( 'Checking for IPOPT... ' )
1526
1527 keep = KeepContext(context,"IPOPT")
1528 is_ok = context.TryLink(ipopt_test_text,".c")
1529 context.Result(is_ok)
1530
1531 keep.restore(context)
1532
1533 return is_ok
1534
1535 #----------------
1536 # Tcl test
1537
1538 # TCL and TK required version 8.1, 8.2, 8.3, or 8.4:
1539 tcltk_minor_newest_acceptable = 4
1540 tcltk_major_required = 8
1541
1542 tcl_check_text = r"""
1543 #include <tcl.h>
1544 #include <stdio.h>
1545 int main(void){
1546 printf("%s",TCL_PATCH_LEVEL);
1547 return 0;
1548 }
1549 """
1550
1551 def CheckTcl(context):
1552 return CheckExtLib(context,'tcl',tcl_check_text,static=env['STATIC_TCLTK'])
1553
1554 def CheckTclVersion(context):
1555 keep = KeepContext(context,'TCL',static=env['STATIC_TCLTK'])
1556 context.Message("Checking Tcl version... ")
1557 (is_ok,output) = context.TryRun(tcl_check_text,'.c')
1558 keep.restore(context)
1559 if not is_ok:
1560 context.Result("failed to run check")
1561 return 0
1562
1563 major,minor,patch = tuple([int(i) for i in output.split(".")])
1564 if major != tcltk_major_required or minor > tcltk_minor_newest_acceptable:
1565 context.Result(output+" (bad version)")
1566 # bad version
1567 return 0
1568
1569 # good version
1570 context.Result(output+", good")
1571 return 1
1572
1573 #----------------
1574 # Tk test
1575
1576 tk_check_text = r"""
1577 #include <tk.h>
1578 #include <stdio.h>
1579 int main(void){
1580 printf("%s",TK_PATCH_LEVEL);
1581 return 0;
1582 }
1583 """
1584 def CheckTk(context):
1585 return CheckExtLib(context,'tk',tk_check_text,static=env['STATIC_TCLTK'])
1586
1587
1588 def CheckTkVersion(context):
1589 keep = KeepContext(context,'TK',static=context.env['STATIC_TCLTK'])
1590 context.Message("Checking Tk version... ")
1591 #print "LINKFLAGS =",context.env['LINKFLAGS']
1592 (is_ok,output) = context.TryRun(tk_check_text,'.c')
1593 keep.restore(context)
1594 if not is_ok:
1595 context.Result("failed to run check")
1596 return 0
1597
1598 major,minor,patch = tuple([int(i) for i in output.split(".")])
1599 if major != tcltk_major_required or minor > tcltk_minor_newest_acceptable:
1600 # bad version
1601 context.Result(output+" (bad version)")
1602 return 0
1603
1604 # good version
1605 context.Result(output+" (good)")
1606 return 1
1607
1608 #----------------
1609 # Tktable test
1610
1611 tktable_check_text = r"""
1612 #include <tkTable.h>
1613 #include <stdio.h>
1614 int main(void){
1615 Table mytable;
1616 return 0;
1617 }
1618 """
1619
1620 def CheckTkTable(context):
1621 return CheckExtLib(context,'tktable',tktable_check_text,static=env['STATIC_TCLTK'])
1622
1623 #---------------
1624 # X11 test
1625
1626 x11_check_text = r"""
1627 #include <X11/Xlib.h>
1628 #include <X11/IntrinsicP.h>
1629 #include <X11/Intrinsic.h>
1630 #include <X11/ObjectP.h>
1631 #include <X11/Object.h>
1632 int main(void){
1633 Object mything;
1634 return 0;
1635 }
1636 """
1637
1638 def CheckX11(context):
1639 return CheckExtLib(context,'X11',x11_check_text)
1640
1641 #----------------
1642 # Check that we can raise and catch sigint
1643
1644 sigint_test_text = r"""
1645 #include <signal.h>
1646 #include <setjmp.h>
1647 #include <stdlib.h>
1648 static jmp_buf g_jmpenv;
1649 void sighandler(int sig){
1650 longjmp(g_jmpenv,sig);
1651 }
1652 void testsigint(){
1653 raise(SIGINT);
1654 }
1655 int main(void){
1656 signal(SIGINT,&sighandler);
1657 switch(setjmp(g_jmpenv)){
1658 case 0:
1659 testsigint();
1660 exit(1);
1661 case SIGINT:
1662 exit(0);
1663 default:
1664 exit(2);
1665 }
1666 }
1667 """
1668
1669 def CheckSIGINT(context):
1670 context.Message("Checking SIGINT is catchable... ")
1671 (is_ok,output)=context.TryRun(sigint_test_text,".c")
1672 context.Result(is_ok)
1673 return is_ok
1674
1675 #----------------
1676 # Check that we're able to catch floating point errors
1677
1678 sigfpe_test_text = r"""
1679 #include <signal.h>
1680 #include <setjmp.h>
1681 #include <stdlib.h>
1682 #include <fenv.h>
1683 static jmp_buf g_jmpenv;
1684 void fpehandler(int sig){
1685 longjmp(g_jmpenv,sig);
1686 }
1687 int main(void){
1688 fenv_t myfenv;
1689 fegetenv(&myfenv);
1690 fesetenv(&myfenv);
1691 feenableexcept(FE_ALL_EXCEPT);
1692 signal(SIGFPE,&fpehandler);
1693 double x;
1694 switch(setjmp(g_jmpenv)){
1695 case 0:
1696 x = 1.0 / 0.0;
1697 /* failed to catch */
1698 exit(1);
1699 case SIGFPE:
1700 exit(0);
1701 }
1702 }
1703 """
1704
1705 def CheckFPE(context):
1706 context.Message("Checking C99 FPE behaviour... ")
1707 (is_ok,output) = context.TryRun(sigfpe_test_text,'.c')
1708 context.Result(is_ok)
1709 return is_ok
1710
1711 #----------------
1712 # signal reset needed?
1713
1714 sigreset_test_text = r"""
1715 #include <signal.h>
1716 #include <setjmp.h>
1717 #include <stdlib.h>
1718 #include <stdio.h>
1719 typedef void SigHandlerFn(int);
1720 static jmp_buf g_jmpenv;
1721 void sighandler(int sig){
1722 longjmp(g_jmpenv,sig);
1723 }
1724 void testsigint(){
1725 /* fprintf(stderr,"Raising SIGINT\n"); */
1726 raise(SIGINT);
1727 }
1728 int main(void){
1729 SigHandlerFn *last,*saved;
1730 saved = signal(SIGINT,&sighandler);
1731 if(saved!=SIG_DFL){
1732 fprintf(stderr,"Default handler (%p) was not correctly set\n",SIG_DFL);
1733 exit(3);
1734 }
1735 switch(setjmp(g_jmpenv)){
1736 case 0:
1737 testsigint();
1738 fprintf(stderr,"Back from SIGINT\n");
1739 exit(1);
1740 case SIGINT:
1741 break;
1742 default:
1743 exit(2);
1744 };
1745 last = signal(SIGINT,SIG_DFL);
1746 if(last!=&sighandler){
1747 printf("1");
1748 exit(0);
1749 }
1750 printf("0");
1751 exit(0);
1752 }
1753 """
1754
1755 def CheckSigReset(context):
1756 context.Message("Checking signal handler reset... ")
1757 (is_ok,output) = context.TryRun(sigreset_test_text,'.c')
1758 if not is_ok:
1759 context.Result("ERROR")
1760 return False
1761 if int(output)==1:
1762 context.Result("required");
1763 context.env['ASC_RESETNEEDED'] = True
1764 else:
1765 context.Result("not required");
1766 context.env['ASC_RESETNEEDED'] = False
1767 return is_ok
1768
1769 #----------------
1770 # LyX on this system?
1771
1772 def CheckLyx(context):
1773 context.Message("Checking for LyX... ")
1774 r = context.env.WhereIs("lyx")
1775 if r:
1776 context.Result(r)
1777 else:
1778 context.Result(0)
1779 return r
1780
1781 #----------------
1782 # Latex2HTML on this system?
1783
1784 def CheckLatex2HTML(context):
1785 context.Message("Checking for latex2html...")
1786 if context.env.WhereIs("latex2html"):
1787 r = True
1788 else:
1789 r = False
1790 context.Result(r)
1791 return r
1792
1793 #----------------
1794 # GCC Version sniffing
1795
1796 # TODO FIXME
1797
1798 gcc_version4 = False
1799
1800 #------------------------------------------------------
1801 # CONFIGURATION
1802
1803 conf = Configure(env
1804 , custom_tests = {
1805 'CheckCC' : CheckCC
1806 , 'CheckCXX' : CheckCXX
1807 , 'CheckMath' : CheckMath
1808 , 'CheckSwigVersion' : CheckSwigVersion
1809 , 'CheckPythonLib' : CheckPythonLib
1810 , 'CheckCUnit' : CheckCUnit
1811 , 'CheckDMalloc' : CheckDMalloc
1812 , 'CheckLyx' : CheckLyx
1813 , 'CheckLatex2HTML' : CheckLatex2HTML
1814 , 'CheckMFGraph' : CheckMFGraph
1815 , 'CheckUFSparse' : CheckUFSparse
1816 , 'CheckTcl' : CheckTcl
1817 , 'CheckTclVersion' : CheckTclVersion
1818 , 'CheckTk' : CheckTk
1819 , 'CheckTkVersion' : CheckTkVersion
1820 , 'CheckGcc' : CheckGcc
1821 , 'CheckGccVisibility' : CheckGccVisibility
1822 , 'CheckYacc' : CheckYacc
1823 , 'CheckLex' : CheckLex
1824 , 'CheckTkTable' : CheckTkTable
1825 , 'CheckX11' : CheckX11
1826 , 'CheckIDA' : CheckIDA
1827 , 'CheckSUNDIALS' : CheckSUNDIALS
1828 , 'CheckCONOPT' : CheckCONOPT
1829 , 'CheckIPOPT' : CheckIPOPT
1830 , 'CheckScrollkeeperConfig' : CheckScrollkeeperConfig
1831 , 'CheckFPE' : CheckFPE
1832 , 'CheckSIGINT' : CheckSIGINT
1833 , 'CheckSigReset' : CheckSigReset
1834 # , 'CheckIsNan' : CheckIsNan
1835 # , 'CheckCppUnitConfig' : CheckCppUnitConfig
1836 }
1837 # , config_h = "config.h"
1838 )
1839
1840 def sconsversioncheck():
1841
1842 # uncomment the following line to skip the version check:
1843 # return 1
1844
1845 import SCons
1846 v = SCons.__version__.split(".")
1847 if v[0] != '0':
1848 return 0
1849 if int(v[1]) >= 97:
1850 return 1
1851 if v[1] != '96':
1852 return 0
1853 micro = int(v[2])
1854 if micro == 92 or micro == 93 or micro == 96:
1855 return 1;
1856 return 0
1857
1858 if not sconsversioncheck():
1859 print "Scons version is not OK. Please try version 0.96.92 or 0.96.93,"
1860 print "or consult the developers in the case of newer versions. Modify"
1861 print "the function 'sconsversioncheck' in the file SConstruct if you"
1862 print "want to *force* SCons to continue."
1863 Exit(1)
1864
1865 # check C compiler
1866
1867 if not conf.CheckCC():
1868 print "Failed to build simple test file with your C compiler."
1869 print "Check your compiler is installed and running correctly."
1870 Exit(1)
1871
1872 if not conf.CheckCXX():
1873 print "Failed to build simple test file with your C++ compiler."
1874 print "Check your compiler is installed and running correctly."
1875 Exit(1)
1876
1877 # stdio -- just to check that compiler is behaving
1878
1879 if not conf.CheckHeader('stdio.h'):
1880 print "CPPPATH =",env.get('CPPPATH')
1881 print "Did not find 'stdio.h'! Check your compiler configuration."
1882 print ""
1883 print "You environment is printed here:"
1884 for k,v in os.environ.iteritems():
1885 print "%-30s%s" % ("%s :" % k, v)
1886 Exit(1)
1887
1888 if not conf.CheckFunc('snprintf'):
1889 print "Didn't find snprintf";
1890 exit(1)
1891
1892 # Math library
1893
1894 conf.env['HAVE_IEEE']=True
1895
1896 if need_libm and not conf.CheckMath():
1897 conf.env['HAVE_IEEE']=False
1898 print 'Did not find math library, exiting!'
1899 Exit(1)
1900
1901 # Where is 'isnan'?
1902
1903 if not conf.CheckFunc('isnan') and not conf.CheckFunc('_isnan'):
1904 print "Didn't find isnan"
1905 # Exit(1)
1906
1907 # GCC visibility
1908
1909 if conf.CheckGcc():
1910 conf.env['HAVE_GCC']=True;
1911 if env['WITH_GCCVISIBILITY'] and conf.CheckGccVisibility():
1912 conf.env['HAVE_GCCVISIBILITY']=True;
1913 conf.env.Append(CCFLAGS=['-fvisibility=hidden'])
1914 conf.env.Append(CPPDEFINES=['HAVE_GCCVISIBILITY'])
1915 conf.env.Append(CCFLAGS=['-Wall'])
1916
1917 # Catching SIGINT
1918
1919 if env['WITH_SIGNALS']:
1920 if not conf.CheckSIGINT():
1921 with_signals = False
1922 without_signals_reason = "SIGINT uncatchable"
1923
1924 # Catching SIGFPE
1925
1926 if conf.CheckFPE():
1927 conf.env['HAVE_C99FPE']=True
1928 else:
1929 conf.env['HAVE_C99FPE']=False
1930
1931 # Checking for signal reset requirement
1932
1933 if not conf.CheckSigReset():
1934 print "Unable to determine if signal reset is required"
1935 Exit(1)
1936
1937 # YACC
1938
1939 if conf.CheckYacc():
1940 conf.env['HAVE_YACC']=True
1941
1942 if conf.CheckLex():
1943 conf.env['HAVE_LEX']=True
1944
1945 # Tcl/Tk
1946
1947 if with_tcltk:
1948 if conf.CheckTcl():
1949 if conf.CheckTclVersion():
1950 if conf.CheckTk():
1951 if with_tcltk and conf.CheckTkVersion():
1952 if env['STATIC_TCLTK']:
1953 if conf.CheckTkTable():
1954 pass
1955 else:
1956 without_tcltk_reason = "TkTable not found"
1957 with_tcltk = False
1958 else:
1959 without_tcltk_reason = "Require Tk version <= 8.4. See 'scons -h'"
1960 with_tcltk = False
1961 else:
1962 without_tcltk_reason = "Tk not found."
1963 with_tcltk = False
1964 else:
1965 without_tcltk_reason = "Require Tcl <= 8.4 Tcl."
1966 with_tcltk = False
1967
1968 else:
1969 without_tcltk_reason = "Tcl not found."
1970 with_tcltk = False
1971
1972 if env['STATIC_TCLTK']:
1973 conf.CheckX11()
1974
1975 # Python... obviously we're already running python, so we just need to
1976 # check that we can link to the python library OK:
1977
1978 if not conf.CheckPythonLib():
1979 without_python_reason = 'libpython2.x not found or not linkable'
1980 with_python = False
1981 env['WITH_PYTHON']=False
1982
1983 # SWIG version
1984
1985 if with_python and not conf.CheckSwigVersion():
1986 without_python_reason = 'SWIG >= 1.3.24 is required'
1987 with_python = False
1988 env['WITH_PYTHON']=False
1989
1990 # CUnit
1991
1992 if with_cunit:
1993 if not conf.CheckCUnit():
1994 without_cunit_reason = 'CUnit not found'
1995 with_cunit = False
1996 #print "CUNIT NOT FOUND, LIBS=",conf.env.get('LIBS')
1997
1998 # DMALLOC
1999
2000 if with_dmalloc:
2001 if not conf.CheckDMalloc():
2002 without_dmalloc_reason = 'dmalloc not found'
2003 with_dmalloc = False
2004
2005 # MFGRAPH
2006
2007 if with_mfgraph:
2008 if not conf.CheckMFGraph():
2009 without_mfgraph_reason = 'mfgraph not found'
2010 with_mfgraph = False
2011 env['WITH_MFGRAPH'] = False
2012
2013 # UFSPARSE
2014
2015 if with_ufsparse:
2016 if not conf.CheckUFSparse():
2017 without_ufsparse_reason = 'mfgraph not found'
2018 with_ufsparse = False
2019 env['WITH_UFSPARSE'] = False
2020
2021 # IDA
2022
2023 if not with_ida:
2024 without_ida_reason = "Not selected (see config option WITH_SOLVERS)"
2025 elif not conf.CheckSUNDIALS():
2026 with_ida = False
2027 without_ida_reason = "SUNDIALS not found, or bad version"
2028 elif not conf.CheckIDA():
2029 with_ida = False
2030 without_ida_reason = "Unable to compile/link against SUNDIALS/IDA"
2031
2032 # CONOPT
2033
2034 if not with_conopt:
2035 without_conopt_reason = "Not selected (see config option WITH_SOLVERS)"
2036 elif not conf.CheckCONOPT():
2037 if conf.env.get('CONOPT_LINKED'):
2038 conf.env['CONOPT_LINKED'] = False
2039 # we no longer require CONOPT at buildtime in order to build support for it
2040 #with_conopt = False
2041 #without_conpt_reason = "CONOPT not found"
2042
2043 # IPOPT
2044
2045 if not with_ipopt:
2046 without_ipopt_reason = "Not selected (see config option WITH_SOLVERS)"
2047 elif not conf.CheckIPOPT():
2048 with_ipopt = False
2049 without_ipopt_reason = "IPOPT not found"
2050
2051 # BLAS
2052
2053 need_blas=False
2054
2055 if with_lsode:
2056 need_fortran = True
2057 need_blas=True
2058
2059 if need_blas:
2060 if conf.CheckLib('blas'):
2061 with_local_blas = False
2062 without_local_blas_reason = "Found BLAS installed on system"
2063 else:
2064 with_local_blas = True
2065 need_fortran = True
2066 else:
2067 with_local_blas= False;
2068 without_local_blas_reason = "BLAS not required"
2069
2070 # FORTRAN
2071
2072 if need_fortran:
2073 conf.env.Tool('fortran')
2074 detect_fortran = conf.env.Detect(['gfortran','g77'])
2075 if detect_fortran:
2076 # For some reason, g77 doesn't get detected properly on MinGW
2077 if not env.has_key('F77') and not env.has_key('FORTRAN'):
2078 print "Fixing detection of F77 on MinGW...(?)"
2079 conf.env.Replace(F77=detect_fortran)
2080 conf.env.Replace(F77COM='$F77 $F77FLAGS -c -o $TARGET $SOURCE')
2081 conf.env.Replace(F77FLAGS='')
2082 #print "F77:",conf.env['F77']
2083 #print "F77COM:",conf.env['F77COM']
2084 #print "F77FLAGS:",conf.env['F77FLAGS']
2085 fortran_builder = Builder(
2086 action='$F77COM'
2087 , suffix='.o'
2088 , src_suffix='.f'
2089 )
2090 conf.env.Append(BUILDERS={'Fortran':fortran_builder})
2091 if platform.system()=="Linux":
2092 conf.env.Append(SHFORTRANFLAGS=['-fPIC'])
2093 else:
2094 with_lsode=False;
2095 without_lsode_reason="FORTRAN-77 required but not found"
2096
2097 #else:
2098 # print "FORTRAN not required"
2099
2100 # F2C
2101
2102 if need_fortran:
2103 if platform.system()=="Windows":
2104 pass
2105 #conf.env.Append(LIBPATH='c:\mingw\lib')
2106
2107 # scrollkeeper
2108
2109 if with_scrollkeeper:
2110 if not conf.CheckScrollkeeperConfig():
2111 with_scrollkeeper=False
2112 without_scrollkeeper_reason="unable to detect scrollkeeper-config"
2113
2114 # lyx
2115
2116 if with_doc_build:
2117 if not conf.CheckLyx():
2118 with_doc_build = False
2119 without_doc_build_reason="unable to locate lyx"
2120
2121 with_latext2html = conf.CheckLatex2HTML()
2122
2123 # TODO: -D_HPUX_SOURCE is needed
2124
2125 # TODO: check size of void*
2126
2127 # TODO: detect if dynamic libraries are possible or not
2128
2129 if platform.system()=="Windows" and env.has_key('MSVS'):
2130 _found_windows_h = conf.CheckHeader('Windows.h')
2131
2132 if not _found_windows_h:
2133 print "Could not locate 'Windows.h' in CPPPATH. Check your configuration."
2134 Exit(1)
2135
2136 if with_python and not conf.CheckHeader(['basetsd.h','BaseTsd.h']):
2137 with_python = 0;
2138 without_python_reason = "Header file 'basetsd.h' not found. Install the MS Platform SDK."
2139
2140 conf.Finish()
2141
2142 #---------------------------------------
2143 # SUBSTITUTION DICTIONARY for .in files
2144
2145 release = env.get('RELEASE')
2146 if release=="0.":
2147 release="0"
2148
2149 #print "SUBSTITUTED CONOPT_LIBPATH:",c_escape(env.subst("$CONOPT_LIBPATH"))
2150
2151 subst_dict = {
2152 '@DEFAULT_ASCENDLIBRARY@':env['DEFAULT_ASCENDLIBRARY']
2153 ,'@DEFAULT_ASCENDSOLVERS@':env['DEFAULT_ASCENDSOLVERS']
2154 , '@GLADE_FILE@':'ascend.glade'
2155 , '@HELP_ROOT@':''
2156 , '@ICON_EXTENSION@':icon_extension
2157 , '@INSTALL_ASCDATA@':env['INSTALL_ASCDATA']
2158 , '@INSTALL_BIN@':env['INSTALL_BIN']
2159 , '@INSTALL_INCLUDE@':env['INSTALL_INCLUDE']
2160 , '@INSTALL_LIB@':env['INSTALL_LIB']
2161 , '@INSTALL_MODELS@':env['INSTALL_MODELS']
2162 , '@INSTALL_SOLVERS@':env['INSTALL_SOLVERS']
2163 , '@PYGTK_ASSETS@':env['PYGTK_ASSETS']
2164 , '@VERSION@':version
2165 , '@RELEASE@':release
2166 , '@DISTTAR_NAME@':env['DISTTAR_NAME']
2167 , '@WEBHELPROOT@':'http://ascendwiki.cheme.cmu.edu/Category:Documentation'
2168 , '@SHLIBSUFFIX@':env['SHLIBSUFFIX']
2169 , '@SHLIBPREFIX@':env['SHLIBPREFIX']
2170 , '@EXTLIB_SUFFIX@':env['EXTLIB_SUFFIX']
2171 , '@EXTLIB_PREFIX@':env['EXTLIB_PREFIX']
2172 , '@ASC_ENV_TK_DEFAULT@' : '$$ASCENDDIST/tcltk'
2173 , '@ASC_DISTDIR_REL_BIN@' : default_rel_distdir
2174 , '@PYTHON@' : python_exe
2175 , '@PYVERSION@' : pyversion
2176 , '@ASC_CONOPT_LIB@':env.get('CONOPT_LIB')
2177 , '@ASC_CONOPT_ENVVAR@':env.get('CONOPT_ENVVAR')
2178 , '@ASC_CONOPT_DLPATH@':c_escape(env.subst("$CONOPT_DLPATH"))
2179 , '@SOURCE_ROOT@':c_escape(os.path.abspath(str(env.Dir("#"))))
2180 , '@WITH_SOLVERS@':",".join(env.get('WITH_SOLVERS'))
2181 }
2182
2183 if env.get('WITH_DOC'):
2184 print "WITH_DOC:",env['WITH_DOC']
2185 subst_dict['@HELP_ROOT@']=env['HELP_ROOT']
2186
2187 # bool options...
2188 for k,v in {
2189 'ASC_WITH_IDA':with_ida
2190 ,'ASC_WITH_DMALLOC':with_dmalloc
2191 ,'ASC_WITH_MFGRAPH':with_mfgraph
2192 ,'ASC_WITH_UFSPARSE':with_ufsparse
2193 ,'ASC_WITH_CONOPT':with_conopt
2194 ,'ASC_LINKED_CONOPT':env.get('CONOPT_LINKED')
2195 ,'ASC_WITH_IPOPT':with_ipopt
2196 ,'ASC_WITH_LSODE':with_lsode
2197 ,'ASC_WITH_MMIO':with_mmio
2198 ,'ASC_SIGNAL_TRAPS':with_signals
2199 ,'ASC_RESETNEEDED':env.get('ASC_RESETNEEDED')
2200 ,'HAVE_C99FPE':env.get('HAVE_C99FPE')
2201 ,'HAVE_IEEE':env.get('HAVE_IEEE')
2202 ,'ASC_ABSOLUTE_PATHS':env.get('ABSOLUTE_PATHS')
2203 ,'ASC_XTERM_COLORS':env.get('WITH_XTERM_COLORS')
2204 ,'MALLOC_DEBUG':env.get('MALLOC_DEBUG')
2205 }.iteritems():
2206
2207 if v: subst_dict["/\\* #define %s @%s@ \\*/" % (k,k)]='# define %s 1 ' % k
2208
2209 if with_python:
2210 subst_dict['@ASCXX_USE_PYTHON@']="1"
2211 env['WITH_PYTHON']=1;
2212
2213 if with_latex2html:
2214 env['WITH_LATEX2HTML']=1
2215
2216 if env.has_key('HAVE_GCCVISIBILITY'):
2217 subst_dict['@HAVE_GCCVISIBILITY@'] = "1"
2218
2219 env.Append(SUBST_DICT=subst_dict)
2220
2221 #for k,v in subst_dict.iteritems():
2222 # print "%-50s%s" % ("'%s'"%k,v)
2223
2224 # REMOVED: long command-line support on Win2k
2225
2226 #------------------------------------------------------
2227 # RECIPE: SWIG scanner
2228
2229 import SCons.Script
2230
2231 SWIGScanner = SCons.Scanner.ClassicCPP(
2232 "SWIGScan"
2233 , ".i"
2234 , "CPPPATH"
2235 , '^[ \t]*[%,#][ \t]*(?:include|import)[ \t]*(<|")([^>"]+)(>|")'
2236 )
2237
2238 env.Append(SCANNERS=[SWIGScanner])
2239
2240 #------------------------------------------------------
2241 # Recipe for 'CHMOD' ACTION
2242
2243 import SCons
2244 from SCons.Script.SConscript import SConsEnvironment
2245 SConsEnvironment.Chmod = SCons.Action.ActionFactory(os.chmod,
2246 lambda dest, mode: 'Chmod("%s", 0%o)' % (dest, mode))
2247
2248 def InstallPerm(env, dest, files, perm):
2249 obj = env.Install(dest, files)
2250 for i in obj:
2251 env.AddPostAction(i, env.Chmod(str(i), perm))
2252
2253 SConsEnvironment.InstallPerm = InstallPerm
2254
2255 # define wrappers
2256 SConsEnvironment.InstallProgram = lambda env, dest, files: InstallPerm(env, dest, files, 0755)
2257 SConsEnvironment.InstallHeader = lambda env, dest, files: InstallPerm(env, dest, files, 0644)
2258 SConsEnvironment.InstallShared = lambda env, dest, files: InstallPerm(env, dest, files, 0644)
2259
2260 #------------------------------------------------------
2261 # BUILD...
2262
2263 # so that #include <modulename/headername.h> works across all modules...
2264 env.AppendUnique(CPPPATH=['#base/generic'])
2265
2266 if env['DEBUG']:
2267 env.Append(CCFLAGS=['-g'])
2268 env.Append(LINKFLAGS=['-g'])
2269
2270 if env['GCOV']:
2271 env.Append(
2272 CPPFLAGS=['-g','-fprofile-arcs','-ftest-coverage']
2273 , LIBS=['gcov']
2274 , LINKFLAGS=['-fprofile-arcs','-ftest-coverage']
2275 )
2276
2277 if with_ida:
2278 env.Append(WITH_IDA=1)
2279
2280 if with_conopt:
2281 env.Append(WITH_CONOPT=1)
2282
2283 if with_ipopt:
2284 env.Append(WITH_IPOPT=1)
2285
2286 #-------------
2287 # TCL/TK GUI
2288
2289 if with_tcltk:
2290 env.SConscript(['tcltk/generic/interface/SConscript'],'env')
2291 else:
2292 print "Skipping... Tcl/Tk bindings aren't being built:",without_tcltk_reason
2293
2294 #-------------
2295 # PYTHON INTERFACE
2296
2297 if with_python:
2298 env.SConscript(['pygtk/SConscript'],'env')
2299 else:
2300 print "Skipping... Python bindings aren't being built:",without_python_reason
2301
2302 #------------
2303 # BASE/GENERIC SUBDIRECTORIES
2304
2305 libascend_env = env.Copy()
2306
2307 dirs = ['general','utilities','compiler','system','solver','integrator','packages','linear']
2308
2309 srcs = []
2310 for d in dirs:
2311 heresrcs = libascend_env.SConscript('base/generic/'+d+'/SConscript','libascend_env')
2312 srcs += heresrcs
2313
2314 #-------------
2315 # IMPORTED CODE: LSODE, BLAS, etc
2316
2317 #if with_lsode:
2318 # srcs += env.SConscript(['lsod/SConscript'],'env')
2319 # srcs += env.SConscript(['linpack/SConscript'],'env')
2320 #else:
2321 # print "Skipping... LSODE won't be built:", without_lsode_reason
2322
2323 if with_local_blas:
2324 env['blasobjs'] = env.SConscript(['blas/SConscript'],'env')
2325 else:
2326 env['blasobjs'] = []
2327 print "Skipping... BLAS won't be built:", without_local_blas_reason
2328
2329 if not with_ida:
2330 print "Skipping... IDA won't be built:", without_ida_reason
2331
2332 if with_mmio:
2333 srcs += env.SConscript(['mmio/SConscript'],'env')
2334 else:
2335 print "Skipping... MMIO export won't be built:", without_mmio_reason
2336 #-------------
2337 # LIBASCEND -- all base/generic functionality
2338
2339 if with_dmalloc:
2340 libascend_env.Append(LIBS=['dmalloc'])
2341
2342 if with_ufsparse:
2343 libascend_env.Append(LIBS=['cxsparse'])
2344
2345 libascend = libascend_env.SharedLibrary('ascend',srcs)
2346
2347 # for use in declaring dependent shared libraries in SConscript files (eg solvers/*/SConscript)
2348 env['libascend'] = libascend
2349
2350 env.Alias('libascend',libascend)
2351
2352 #-------------
2353 # UNIT TESTS (C CODE)
2354
2355 if with_cunit:
2356 testdirs = ['general','solver','utilities','linear']
2357 testsrcs = []
2358 for testdir in testdirs:
2359 path = 'base/generic/'+testdir+'/test/'
2360 env.SConscript([path+'SConscript'],'env')
2361 testsrcs += [i.path for i in env['TESTSRCS_'+testdir.upper()]]
2362
2363 #print "TESTSRCS =",testsrcs
2364
2365 env.SConscript(['test/SConscript'],'env')
2366 env.SConscript(['base/generic/test/SConscript'],'env')
2367
2368 env.Alias('test',[env.Dir('test'),env.Dir('base/generic/test')])
2369
2370 else:
2371 print "Skipping... CUnit tests aren't being built:",without_cunit_reason
2372
2373 #-------------
2374 # EXTERNAL SOLVERS
2375
2376 env['extfns']=[]
2377
2378 env.SConscript(['solvers/SConscript'],'env')
2379
2380 #-------------
2381 # EXTERNAL FUNCTIONS
2382
2383 modeldirs = env.SConscript(['models/SConscript'],'env')
2384
2385 if not with_extfns:
2386 print "Skipping... External modules aren't being built:",without_extfns_reason
2387
2388 env.Alias('extfns',env['extfns'])
2389
2390 #------------------------------------------------------
2391 # CREATE ASCEND-CONFIG scriptlet
2392
2393 ascendconfig = env.SubstInFile('ascend-config.in')
2394
2395 #------------------------------------------------------
2396 # INSTALLATION
2397
2398 if env.get('CAN_INSTALL'):
2399
2400 dirs = ['INSTALL_BIN','INSTALL_ASCDATA','INSTALL_LIB', 'INSTALL_INCLUDE','INSTALL_DOC']
2401 install_dirs = [Dir(env.subst("$INSTALL_ROOT$"+d)) for d in dirs]
2402 install_dirs += modeldirs + [Dir(env.subst("$INSTALL_ROOT$INSTALL_SOLVERS"))]
2403
2404 # TODO: add install options
2405 env.Alias('install',install_dirs)
2406
2407 env.InstallShared(Dir(env.subst("$INSTALL_ROOT$INSTALL_LIB")),libascend)
2408
2409 env.InstallProgram(Dir(env.subst("$INSTALL_ROOT$INSTALL_BIN")),ascendconfig)
2410
2411 #------------------------------------------------------
2412 # WINDOWS INSTALLER
2413
2414 if not env.get('NSIS'):
2415 with_installer = False
2416 without_installer_reason = "NSIS not found"
2417
2418 if with_installer:
2419 env.Append(NSISDEFINES={
2420 'OUTFILE':"#dist/"+env['WIN_INSTALLER_NAME']
2421 ,"VERSION":version
2422 ,'PYVERSION':pyversion
2423 })
2424 installer = env.Installer('nsis/installer.nsi')
2425 Depends(installer,["pygtk","tcltk","ascend.dll","models","ascend-config"])
2426 env.Alias('installer',installer)
2427 else:
2428 print "Skipping... Windows installer isn't being built:",without_installer_reason
2429
2430
2431 #------------------------------------------------------
2432 # PROJECT FILE for MSVC
2433
2434 env.SConscript(['base/msvc/SConscript'],['env','libascend']);
2435
2436 #------------------------------------------------------
2437 # CREATE the SPEC file for generation of RPM packages
2438
2439 if platform.system()=="Linux":
2440 env.SubstInFile('ascend.spec.in')
2441
2442 #------------------------------------------------------
2443 # CREATE OMF FILE FOR USE WITH SCROLLKEEPER
2444
2445 #if with_scrollkeeper:
2446 # #env.SubstInFile('#/pygtk/gnome/ascend.omf.in')
2447 # #env.InstallShared(env['INSTALL_ROOT']+env['OMFDIR'],"#/pygtk/gnome/ascend.omf")
2448
2449 #------------------------------------------------------
2450 # DISTRIBUTION TAR FILE
2451
2452 env['DISTTAR_FORMAT']='bz2'
2453 env.Append(
2454 DISTTAR_EXCLUDEEXTS=['.o','.os','.so','.a','.dll','.lib','.cc','.cache','.pyc','.cvsignore','.dblite','.log','.pl','.out','.exe','.aux','.idx','.toc','.lof','.lot','.mm','.warnings','.tm2','.swp',',tmp','.gz','.bz2','.7z']
2455 , DISTTAR_EXCLUDEDIRS=['CVS','.svn','.sconf_temp', 'dist','debian']
2456 )
2457
2458 tar = env.DistTar("dist/"+env['DISTTAR_NAME']
2459 , [env.Dir('#')]
2460 )
2461
2462 env.Depends(tar,'ascend.spec')
2463 env.Depends(tar,'#doc/book.pdf')
2464
2465 #------------------------------------------------------
2466 # DEBIAN TARBALL for use with Build Service
2467
2468 import glob
2469 deb_manfiles = glob.glob('debian/*.man')
2470
2471 deb_tar = env.Tar(
2472 'dist/debian.tar.gz'
2473 ,deb_manfiles + ['debian/compat','debian/copyright','debian/dirs']
2474 ,TARFLAGS = ['cz']
2475 )
2476
2477 Alias('dist',[tar,deb_tar])
2478
2479 #------------------------------------------------------
2480 # DOCUMENTATION
2481
2482
2483 if not with_doc_build:
2484 print "Skipping... Documentation isn't being built:",without_doc_build_reason
2485
2486 #user's manual
2487 env.SConscript('doc/SConscript',['env'])
2488
2489 # doxygen documentation
2490 env.SConscript('base/doc/SConscript',['env'])
2491
2492 #------------------------------------------------------
2493 # RPM BUILD
2494
2495 # for RPM builds, 'scons dist' then 'rpmbuild -ta dist/ascend-*.tar.bz2'
2496 # (check * for the version number used to create the tarball)
2497
2498 #------------------------------------------------------
2499 # DEFAULT TARGETS
2500
2501 default_targets =['libascend','solvers']
2502 if with_tcltk:
2503 default_targets.append('tcltk')
2504 if with_python:
2505 default_targets.append('pygtk')
2506 if with_installer:
2507 default_targets.append('installer')
2508 if with_extfns:
2509 default_targets.append('extfns')
2510 if with_doc_build:
2511 default_targets.append('doc')
2512
2513 env.Default(default_targets)
2514
2515 print "Building targets:"," ".join([str(i) for i in BUILD_TARGETS])
2516
2517 # vim: set syntax=python:

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