1import config.base 2 3import os 4import sys 5import re 6import pickle 7 8class Configure(config.base.Configure): 9 def __init__(self, framework): 10 config.base.Configure.__init__(self, framework) 11 self.headerPrefix = 'PETSC' 12 self.substPrefix = 'PETSC' 13 self.installed = 0 # 1 indicates that Configure itself has already compiled and installed PETSc 14 return 15 16 def __str2__(self): 17 desc = [] 18 if not self.installed: 19 desc.append('xxx=========================================================================xxx') 20 desc.append(' Configure stage complete. Now build PETSc libraries with:') 21 desc.append(' make PETSC_DIR='+self.petscdir.dir+' PETSC_ARCH='+self.arch.arch+' all') 22 desc.append('xxx=========================================================================xxx') 23 else: 24 desc.append('xxx=========================================================================xxx') 25 desc.append(' Installation complete. You do not need to run make to compile or install the software') 26 desc.append('xxx=========================================================================xxx') 27 return '\n'.join(desc)+'\n' 28 29 def setupHelp(self, help): 30 import nargs 31 help.addArgument('PETSc', '-prefix=<dir>', nargs.Arg(None, '', 'Specifiy location to install PETSc (eg. /usr/local)')) 32 help.addArgument('PETSc', '-with-prefetch=<bool>', nargs.ArgBool(None, 1,'Enable checking for prefetch instructions')) 33 help.addArgument('Windows','-with-windows-graphics=<bool>', nargs.ArgBool(None, 1,'Enable check for Windows Graphics')) 34 help.addArgument('PETSc', '-with-default-arch=<bool>', nargs.ArgBool(None, 1, 'Allow using the last configured arch without setting PETSC_ARCH')) 35 help.addArgument('PETSc','-with-single-library=<bool>', nargs.ArgBool(None, 1,'Put all PETSc code into the single -lpetsc library')) 36 help.addArgument('PETSc','-with-fortran-bindings=<bool>', nargs.ArgBool(None, 1,'Build PETSc fortran bindings in the library and corresponding module files')) 37 help.addArgument('PETSc', '-with-ios=<bool>', nargs.ArgBool(None, 0, 'Build an iPhone/iPad version of PETSc library')) 38 help.addArgument('PETSc', '-with-xsdk-defaults', nargs.ArgBool(None, 0, 'Set the following as defaults for the xSDK standard: --enable-debug=1, --enable-shared=1, --with-precision=double, --with-index-size=32, locate blas/lapack automatically')) 39 help.addArgument('PETSc', '-with-display=<x11display>', nargs.Arg(None, '', 'Specifiy DISPLAY env variable for use with matlab test)')) 40 help.addArgument('PETSc', '-with-package-scripts=<pyscripts>',nargs.ArgFileList(None,None,'Specify configure package scripts for user provided packages')) 41 return 42 43 def registerPythonFile(self,filename,directory): 44 ''' Add a python file to the framework and registers its headerprefix, ... externalpackagedir 45 directory is the directory where the file relative to the BuildSystem or config path in python notation with . ''' 46 (utilityName, ext) = os.path.splitext(filename) 47 if not utilityName.startswith('.') and not utilityName.startswith('#') and ext == '.py' and not utilityName == '__init__': 48 if directory: directory = directory+'.' 49 utilityObj = self.framework.require(directory+utilityName, self) 50 utilityObj.headerPrefix = self.headerPrefix 51 utilityObj.archProvider = self.arch 52 utilityObj.languageProvider = self.languages 53 utilityObj.installDirProvider = self.installdir 54 utilityObj.externalPackagesDirProvider = self.externalpackagesdir 55 utilityObj.precisionProvider = self.scalartypes 56 utilityObj.indexProvider = self.indexTypes 57 setattr(self, utilityName.lower(), utilityObj) 58 return utilityObj 59 return None 60 61 def setupDependencies(self, framework): 62 config.base.Configure.setupDependencies(self, framework) 63 self.programs = framework.require('config.programs', self) 64 self.setCompilers = framework.require('config.setCompilers', self) 65 self.compilers = framework.require('config.compilers', self) 66 self.arch = framework.require('PETSc.options.arch', self.setCompilers) 67 self.petscdir = framework.require('PETSc.options.petscdir', self.arch) 68 self.installdir = framework.require('PETSc.options.installDir', self) 69 self.scalartypes = framework.require('PETSc.options.scalarTypes', self) 70 self.indexTypes = framework.require('PETSc.options.indexTypes', self) 71 self.languages = framework.require('PETSc.options.languages', self.setCompilers) 72 self.indexTypes = framework.require('PETSc.options.indexTypes', self.compilers) 73 self.compilers = framework.require('config.compilers', self) 74 self.types = framework.require('config.types', self) 75 self.headers = framework.require('config.headers', self) 76 self.functions = framework.require('config.functions', self) 77 self.libraries = framework.require('config.libraries', self) 78 self.atomics = framework.require('config.atomics', self) 79 self.make = framework.require('config.packages.make', self) 80 self.blasLapack = framework.require('config.packages.BlasLapack',self) 81 self.externalpackagesdir = framework.require('PETSc.options.externalpackagesdir',self) 82 self.mpi = framework.require('config.packages.MPI',self) 83 84 for utility in sorted(os.listdir(os.path.join('config','PETSc','options'))): 85 self.registerPythonFile(utility,'PETSc.options') 86 87 for utility in sorted(os.listdir(os.path.join('config','BuildSystem','config','utilities'))): 88 self.registerPythonFile(utility,'config.utilities') 89 90 for package in sorted(os.listdir(os.path.join('config', 'BuildSystem', 'config', 'packages'))): 91 obj = self.registerPythonFile(package,'config.packages') 92 if obj: 93 obj.archProvider = self.framework.requireModule(obj.archProvider, obj) 94 obj.languageProvider = self.framework.requireModule(obj.languageProvider, obj) 95 obj.installDirProvider = self.framework.requireModule(obj.installDirProvider, obj) 96 obj.externalPackagesDirProvider = self.framework.requireModule(obj.externalPackagesDirProvider, obj) 97 obj.precisionProvider = self.framework.requireModule(obj.precisionProvider, obj) 98 obj.indexProvider = self.framework.requireModule(obj.indexProvider, obj) 99 100 # Force blaslapack and opencl to depend on scalarType so precision is set before BlasLapack is built 101 framework.require('PETSc.options.scalarTypes', self.f2cblaslapack) 102 framework.require('PETSc.options.scalarTypes', self.fblaslapack) 103 framework.require('PETSc.options.scalarTypes', self.blaslapack) 104 framework.require('PETSc.options.scalarTypes', self.opencl) 105 106 self.programs.headerPrefix = self.headerPrefix 107 self.compilers.headerPrefix = self.headerPrefix 108 self.types.headerPrefix = self.headerPrefix 109 self.headers.headerPrefix = self.headerPrefix 110 self.functions.headerPrefix = self.headerPrefix 111 self.libraries.headerPrefix = self.headerPrefix 112 113 # Register user provided package scripts 114 if 'with-package-scripts' in self.framework.argDB: 115 for script in self.framework.argDB['with-package-scripts']: 116 if os.path.splitext(script)[1] != '.py': 117 raise RuntimeError('Only python scripts compatible with configure package script format should be specified! Invalid option -with-package-scripts='+script) 118 self.framework.logPrint('User is registering a new package script: '+script) 119 dname,fname = os.path.split(script) 120 if dname: sys.path.append(dname) 121 self.registerPythonFile(fname,'') 122 123 # test for a variety of basic headers and functions 124 headersC = map(lambda name: name+'.h', ['setjmp','dos', 'endian', 'fcntl', 'float', 'io', 'limits', 'malloc', 'pwd', 'search', 'strings', 125 'unistd', 'sys/sysinfo', 'machine/endian', 'sys/param', 'sys/procfs', 'sys/resource', 126 'sys/systeminfo', 'sys/times', 'sys/utsname','string', 'stdlib', 127 'sys/socket','sys/wait','netinet/in','netdb','Direct','time','Ws2tcpip','sys/types', 128 'WindowsX', 'cxxabi','float','ieeefp','stdint','sched','pthread','inttypes','immintrin','zmmintrin']) 129 functions = ['access', '_access', 'clock', 'drand48', 'getcwd', '_getcwd', 'getdomainname', 'gethostname', 130 'gettimeofday', 'getwd', 'memalign', 'mkstemp', 'popen', 'PXFGETARG', 'rand', 'getpagesize', 131 'readlink', 'realpath', 'sigaction', 'signal', 'sigset', 'usleep', 'sleep', '_sleep', 'socket', 132 'times', 'gethostbyname', 'uname','snprintf','_snprintf','lseek','_lseek','time','fork','stricmp', 133 'strcasecmp', 'bzero', 'dlopen', 'dlsym', 'dlclose', 'dlerror','get_nprocs','sysctlbyname', 134 '_set_output_format','_mkdir'] 135 libraries1 = [(['socket', 'nsl'], 'socket'), (['fpe'], 'handle_sigfpes')] 136 self.headers.headers.extend(headersC) 137 self.functions.functions.extend(functions) 138 self.libraries.libraries.extend(libraries1) 139 140 return 141 142 def DumpPkgconfig(self): 143 ''' Create a pkg-config file ''' 144 if not os.path.exists(os.path.join(self.petscdir.dir,self.arch.arch,'lib','pkgconfig')): 145 os.makedirs(os.path.join(self.petscdir.dir,self.arch.arch,'lib','pkgconfig')) 146 fd = open(os.path.join(self.petscdir.dir,self.arch.arch,'lib','pkgconfig','PETSc.pc'),'w') 147 cflags_inc = ['-I${includedir}'] 148 if self.framework.argDB['prefix']: 149 fd.write('prefix='+self.installdir.dir+'\n') 150 else: 151 fd.write('prefix='+os.path.join(self.petscdir.dir, self.arch.arch)+'\n') 152 cflags_inc.append('-I' + os.path.join(self.petscdir.dir, 'include')) 153 fd.write('exec_prefix=${prefix}\n') 154 fd.write('includedir=${prefix}/include\n') 155 fd.write('libdir=${prefix}/lib\n') 156 157 self.setCompilers.pushLanguage('C') 158 fd.write('ccompiler='+self.setCompilers.getCompiler()+'\n') 159 fd.write('cflags_extra='+self.setCompilers.getCompilerFlags().strip()+'\n') 160 fd.write('cflags_dep='+self.compilers.dependenciesGenerationFlag.get('C','')+'\n') 161 fd.write('ldflag_rpath='+self.setCompilers.CSharedLinkerFlag+'\n') 162 self.setCompilers.popLanguage() 163 if hasattr(self.compilers, 'CXX'): 164 self.setCompilers.pushLanguage('C++') 165 fd.write('cxxcompiler='+self.setCompilers.getCompiler()+'\n') 166 fd.write('cxxflags_extra='+self.setCompilers.getCompilerFlags().strip()+'\n') 167 self.setCompilers.popLanguage() 168 if hasattr(self.compilers, 'FC'): 169 self.setCompilers.pushLanguage('FC') 170 fd.write('fcompiler='+self.setCompilers.getCompiler()+'\n') 171 fd.write('fflags_extra='+self.setCompilers.getCompilerFlags().strip()+'\n') 172 self.setCompilers.popLanguage() 173 174 fd.write('\n') 175 fd.write('Name: PETSc\n') 176 fd.write('Description: Library to solve ODEs and algebraic equations\n') 177 fd.write('Version: %s\n' % self.petscdir.version) 178 fd.write('Cflags: ' + ' '.join([self.setCompilers.CPPFLAGS] + cflags_inc) + '\n') 179 fd.write('Libs: '+self.libraries.toStringNoDupes(['-L${libdir}', self.petsclib], with_rpath=False)+'\n') 180 # Remove RPATH flags from library list. User can add them using 181 # pkg-config --variable=ldflag_rpath and pkg-config --libs-only-L 182 fd.write('Libs.private: '+self.libraries.toStringNoDupes([f for f in self.packagelibs+self.complibs if not f.startswith(self.setCompilers.CSharedLinkerFlag)], with_rpath=False)+'\n') 183 184 fd.close() 185 return 186 187 def DumpModule(self): 188 ''' Create a module file ''' 189 if not os.path.exists(os.path.join(self.petscdir.dir,self.arch.arch,'lib','petsc','conf','modules')): 190 os.makedirs(os.path.join(self.petscdir.dir,self.arch.arch,'lib','petsc','conf','modules')) 191 if not os.path.exists(os.path.join(self.petscdir.dir,self.arch.arch,'lib','petsc','conf','modules','petsc')): 192 os.makedirs(os.path.join(self.petscdir.dir,self.arch.arch,'lib','petsc','conf','modules','petsc')) 193 if self.framework.argDB['prefix']: 194 installdir = self.installdir.dir 195 installarch = '' 196 installpath = os.path.join(installdir,'bin') 197 else: 198 installdir = self.petscdir.dir 199 installarch = self.arch.arch 200 installpath = os.path.join(installdir,installarch,'bin')+':'+os.path.join(installdir,'bin') 201 fd = open(os.path.join(self.petscdir.dir,self.arch.arch,'lib','petsc','conf','modules','petsc',self.petscdir.version),'w') 202 fd.write('''\ 203#%%Module 204 205proc ModulesHelp { } { 206 puts stderr "This module sets the path and environment variables for petsc-%s" 207 puts stderr " see https://www.mcs.anl.gov/petsc/ for more information " 208 puts stderr "" 209} 210module-whatis "PETSc - Portable, Extensible Toolkit for Scientific Computation" 211 212set petsc_dir "%s" 213set petsc_arch "%s" 214 215setenv PETSC_ARCH "$petsc_arch" 216setenv PETSC_DIR "$petsc_dir" 217prepend-path PATH "%s" 218''' % (self.petscdir.version, installdir, installarch, installpath)) 219 fd.close() 220 return 221 222 def Dump(self): 223 ''' Actually put the values into the configuration files ''' 224 # eventually everything between -- should be gone 225 if self.mpi.usingMPIUni: 226 # 227 # Remove any MPI/MPICH include files that may have been put here by previous runs of ./configure 228 self.executeShellCommand('rm -rf '+os.path.join(self.petscdir.dir,self.arch.arch,'include','mpi*')+' '+os.path.join(self.petscdir.dir,self.arch.arch,'include','opa*'), log = self.log) 229 230 self.setCompilers.pushLanguage('C') 231 compiler = self.setCompilers.getCompiler() 232 if compiler.endswith('mpicc') or compiler.endswith('mpiicc'): 233 try: 234 output = self.executeShellCommand(compiler + ' -show', log = self.log)[0] 235 compiler = output.split(' ')[0] 236 self.addDefine('MPICC_SHOW','"'+output.strip().replace('\n','\\\\n')+'"') 237 except: 238 self.addDefine('MPICC_SHOW','"Unavailable"') 239 else: 240 self.addDefine('MPICC_SHOW','"Unavailable"') 241 self.setCompilers.popLanguage() 242#----------------------------------------------------------------------------------------------------- 243 244 # Sometimes we need C compiler, even if built with C++ 245 self.setCompilers.pushLanguage('C') 246 self.addMakeMacro('CC_FLAGS',self.setCompilers.getCompilerFlags()) 247 self.setCompilers.popLanguage() 248 249 # And sometimes we need a C++ compiler even when PETSc is built with C 250 if hasattr(self.compilers, 'CXX'): 251 self.setCompilers.pushLanguage('Cxx') 252 self.addDefine('HAVE_CXX','1') 253 self.addMakeMacro('CXX_FLAGS',self.setCompilers.getCompilerFlags()) 254 cxx_linker = self.setCompilers.getLinker() 255 self.addMakeMacro('CXX_LINKER',cxx_linker) 256 self.addMakeMacro('CXX_LINKER_FLAGS',self.setCompilers.getLinkerFlags()) 257 self.setCompilers.popLanguage() 258 259 # C preprocessor values 260 self.addMakeMacro('CPP_FLAGS',self.setCompilers.CPPFLAGS) 261 262 # compiler values 263 self.setCompilers.pushLanguage(self.languages.clanguage) 264 self.addMakeMacro('PCC',self.setCompilers.getCompiler()) 265 self.addMakeMacro('PCC_FLAGS',self.setCompilers.getCompilerFlags()) 266 self.setCompilers.popLanguage() 267 # .o or .obj 268 self.addMakeMacro('CC_SUFFIX','o') 269 270 # executable linker values 271 self.setCompilers.pushLanguage(self.languages.clanguage) 272 pcc_linker = self.setCompilers.getLinker() 273 self.addMakeMacro('PCC_LINKER',pcc_linker) 274 self.addMakeMacro('PCC_LINKER_FLAGS',self.setCompilers.getLinkerFlags()) 275 self.setCompilers.popLanguage() 276 # '' for Unix, .exe for Windows 277 self.addMakeMacro('CC_LINKER_SUFFIX','') 278 279 if hasattr(self.compilers, 'FC'): 280 if self.framework.argDB['with-fortran-bindings']: 281 self.addDefine('HAVE_FORTRAN','1') 282 self.setCompilers.pushLanguage('FC') 283 # need FPPFLAGS in config/setCompilers 284 self.addMakeMacro('FPP_FLAGS',self.setCompilers.CPPFLAGS) 285 286 # compiler values 287 self.addMakeMacro('FC_FLAGS',self.setCompilers.getCompilerFlags()) 288 self.setCompilers.popLanguage() 289 # .o or .obj 290 self.addMakeMacro('FC_SUFFIX','o') 291 292 # executable linker values 293 self.setCompilers.pushLanguage('FC') 294 # Cannot have NAG f90 as the linker - so use pcc_linker as fc_linker 295 fc_linker = self.setCompilers.getLinker() 296 if config.setCompilers.Configure.isNAG(fc_linker, self.log): 297 self.addMakeMacro('FC_LINKER',pcc_linker) 298 else: 299 self.addMakeMacro('FC_LINKER',fc_linker) 300 self.addMakeMacro('FC_LINKER_FLAGS',self.setCompilers.getLinkerFlags()) 301 # apple requires this shared library linker flag on SOME versions of the os 302 if self.setCompilers.getLinkerFlags().find('-Wl,-commons,use_dylibs') > -1: 303 self.addMakeMacro('DARWIN_COMMONS_USE_DYLIBS',' -Wl,-commons,use_dylibs ') 304 self.setCompilers.popLanguage() 305 306 # F90 Modules 307 if self.setCompilers.fortranModuleIncludeFlag: 308 self.addMakeMacro('FC_MODULE_FLAG', self.setCompilers.fortranModuleIncludeFlag) 309 else: # for non-f90 compilers like g77 310 self.addMakeMacro('FC_MODULE_FLAG', '-I') 311 if self.setCompilers.fortranModuleIncludeFlag: 312 self.addMakeMacro('FC_MODULE_OUTPUT_FLAG', self.setCompilers.fortranModuleOutputFlag) 313 else: 314 self.addMakeMacro('FC','') 315 316 if hasattr(self.compilers, 'CUDAC'): 317 self.setCompilers.pushLanguage('CUDA') 318 self.addMakeMacro('CUDAC_FLAGS',self.setCompilers.getCompilerFlags()) 319 self.setCompilers.popLanguage() 320 321 # shared library linker values 322 self.setCompilers.pushLanguage(self.languages.clanguage) 323 # need to fix BuildSystem to collect these separately 324 self.addMakeMacro('SL_LINKER',self.setCompilers.getLinker()) 325 self.addMakeMacro('SL_LINKER_FLAGS','${PCC_LINKER_FLAGS}') 326 self.setCompilers.popLanguage() 327 # One of 'a', 'so', 'lib', 'dll', 'dylib' (perhaps others also?) depending on the library generator and architecture 328 # Note: . is not included in this macro, consistent with AR_LIB_SUFFIX 329 if self.setCompilers.sharedLibraryExt == self.setCompilers.AR_LIB_SUFFIX: 330 self.addMakeMacro('SL_LINKER_SUFFIX', '') 331 self.addDefine('SLSUFFIX','""') 332 else: 333 self.addMakeMacro('SL_LINKER_SUFFIX', self.setCompilers.sharedLibraryExt) 334 self.addDefine('SLSUFFIX','"'+self.setCompilers.sharedLibraryExt+'"') 335 336 self.addMakeMacro('SL_LINKER_LIBS','${PETSC_EXTERNAL_LIB_BASIC}') 337 338#----------------------------------------------------------------------------------------------------- 339 340 # CONLY or CPP. We should change the PETSc makefiles to do this better 341 if self.languages.clanguage == 'C': lang = 'CONLY' 342 else: lang = 'CXXONLY' 343 self.addMakeMacro('PETSC_LANGUAGE',lang) 344 345 # real or complex 346 self.addMakeMacro('PETSC_SCALAR',self.scalartypes.scalartype) 347 # double or float 348 self.addMakeMacro('PETSC_PRECISION',self.scalartypes.precision) 349 350 if self.framework.argDB['with-batch']: 351 self.addMakeMacro('PETSC_WITH_BATCH','1') 352 353 # Test for compiler-specific macros that need to be defined. 354 if self.setCompilers.isCrayVector('CC', self.log): 355 self.addDefine('HAVE_CRAY_VECTOR','1') 356 357#----------------------------------------------------------------------------------------------------- 358 if self.functions.haveFunction('gethostbyname') and self.functions.haveFunction('socket') and self.headers.haveHeader('netinet/in.h'): 359 self.addDefine('USE_SOCKET_VIEWER','1') 360 if self.checkCompile('#include <sys/socket.h>','setsockopt(0,SOL_SOCKET,SO_REUSEADDR,0,0)'): 361 self.addDefine('HAVE_SO_REUSEADDR','1') 362 363#----------------------------------------------------------------------------------------------------- 364 # print include and lib for makefiles 365 self.framework.packages.reverse() 366 petscincludes = [os.path.join(self.petscdir.dir,'include'),os.path.join(self.petscdir.dir,self.arch.arch,'include')] 367 petscincludes_install = [os.path.join(self.installdir.dir, 'include')] if self.framework.argDB['prefix'] else petscincludes 368 includes = [] 369 self.packagelibs = [] 370 for i in self.framework.packages: 371 if i.useddirectly: 372 self.addDefine('HAVE_'+i.PACKAGE.replace('-','_'), 1) # ONLY list package if it is used directly by PETSc (and not only by another package) 373 if not isinstance(i.lib, list): 374 i.lib = [i.lib] 375 if i.linkedbypetsc: self.packagelibs.extend(i.lib) 376 self.addMakeMacro(i.PACKAGE.replace('-','_')+'_LIB', self.libraries.toStringNoDupes(i.lib)) 377 if hasattr(i,'include'): 378 if not isinstance(i.include,list): 379 i.include = [i.include] 380 includes.extend(i.include) 381 self.addMakeMacro(i.PACKAGE.replace('-','_')+'_INCLUDE',self.headers.toStringNoDupes(i.include)) 382 if self.framework.argDB['with-single-library']: 383 self.petsclib = '-lpetsc' 384 else: 385 self.petsclib = '-lpetscts -lpetscsnes -lpetscksp -lpetscdm -lpetscmat -lpetscvec -lpetscsys' 386 self.complibs = self.compilers.flibs+self.compilers.cxxlibs+self.compilers.LIBS.split() 387 self.PETSC_WITH_EXTERNAL_LIB = self.libraries.toStringNoDupes(['-L${PETSC_DIR}/${PETSC_ARCH}/lib', self.petsclib]+self.packagelibs+self.complibs) 388 self.PETSC_EXTERNAL_LIB_BASIC = self.libraries.toStringNoDupes(self.packagelibs+self.complibs) 389 390 self.addMakeMacro('PETSC_EXTERNAL_LIB_BASIC',self.PETSC_EXTERNAL_LIB_BASIC) 391 allincludes = petscincludes + includes 392 allincludes_install = petscincludes_install + includes 393 self.PETSC_CC_INCLUDES = self.headers.toStringNoDupes(allincludes) 394 self.PETSC_CC_INCLUDES_INSTALL = self.headers.toStringNoDupes(allincludes_install) 395 self.addMakeMacro('PETSC_CC_INCLUDES',self.PETSC_CC_INCLUDES) 396 self.addMakeMacro('PETSC_CC_INCLUDES_INSTALL', self.PETSC_CC_INCLUDES_INSTALL) 397 if hasattr(self.compilers, 'FC'): 398 def modinc(includes): 399 return includes if self.compilers.fortranIsF90 else [] 400 self.addMakeMacro('PETSC_FC_INCLUDES',self.headers.toStringNoDupes(allincludes,modinc(allincludes))) 401 self.addMakeMacro('PETSC_FC_INCLUDES_INSTALL',self.headers.toStringNoDupes(allincludes_install,modinc(allincludes_install))) 402 403 self.addDefine('LIB_DIR','"'+os.path.join(self.installdir.dir,'lib')+'"') 404 405 if self.framework.argDB['with-single-library']: 406 # overrides the values set in conf/variables 407 self.addMakeMacro('LIBNAME','${INSTALL_LIB_DIR}/libpetsc.${AR_LIB_SUFFIX}') 408 self.addMakeMacro('SHLIBS','libpetsc') 409 self.addMakeMacro('PETSC_LIB_BASIC','-lpetsc') 410 self.addMakeMacro('PETSC_KSP_LIB_BASIC','-lpetsc') 411 self.addMakeMacro('PETSC_TS_LIB_BASIC','-lpetsc') 412 self.addMakeMacro('PETSC_TAO_LIB_BASIC','-lpetsc') 413 self.addMakeMacro('PETSC_WITH_EXTERNAL_LIB',self.PETSC_WITH_EXTERNAL_LIB) 414 self.addDefine('USE_SINGLE_LIBRARY', '1') 415 if self.sharedlibraries.useShared: 416 self.addMakeMacro('PETSC_SYS_LIB','${C_SH_LIB_PATH} ${PETSC_WITH_EXTERNAL_LIB}') 417 self.addMakeMacro('PETSC_VEC_LIB','${C_SH_LIB_PATH} ${PETSC_WITH_EXTERNAL_LIB}') 418 self.addMakeMacro('PETSC_MAT_LIB','${C_SH_LIB_PATH} ${PETSC_WITH_EXTERNAL_LIB}') 419 self.addMakeMacro('PETSC_DM_LIB','${C_SH_LIB_PATH} ${PETSC_WITH_EXTERNAL_LIB}') 420 self.addMakeMacro('PETSC_KSP_LIB','${C_SH_LIB_PATH} ${PETSC_WITH_EXTERNAL_LIB}') 421 self.addMakeMacro('PETSC_SNES_LIB','${C_SH_LIB_PATH} ${PETSC_WITH_EXTERNAL_LIB}') 422 self.addMakeMacro('PETSC_TS_LIB','${C_SH_LIB_PATH} ${PETSC_WITH_EXTERNAL_LIB}') 423 self.addMakeMacro('PETSC_TAO_LIB','${C_SH_LIB_PATH} ${PETSC_WITH_EXTERNAL_LIB}') 424 self.addMakeMacro('PETSC_CHARACTERISTIC_LIB','${C_SH_LIB_PATH} ${PETSC_WITH_EXTERNAL_LIB}') 425 self.addMakeMacro('PETSC_LIB','${C_SH_LIB_PATH} ${PETSC_WITH_EXTERNAL_LIB}') 426 self.addMakeMacro('PETSC_CONTRIB','${C_SH_LIB_PATH} ${PETSC_WITH_EXTERNAL_LIB}') 427 else: 428 self.addMakeMacro('PETSC_SYS_LIB','${PETSC_WITH_EXTERNAL_LIB}') 429 self.addMakeMacro('PETSC_VEC_LIB','${PETSC_WITH_EXTERNAL_LIB}') 430 self.addMakeMacro('PETSC_MAT_LIB','${PETSC_WITH_EXTERNAL_LIB}') 431 self.addMakeMacro('PETSC_DM_LIB','${PETSC_WITH_EXTERNAL_LIB}') 432 self.addMakeMacro('PETSC_KSP_LIB','${PETSC_WITH_EXTERNAL_LIB}') 433 self.addMakeMacro('PETSC_SNES_LIB','${PETSC_WITH_EXTERNAL_LIB}') 434 self.addMakeMacro('PETSC_TS_LIB','${PETSC_WITH_EXTERNAL_LIB}') 435 self.addMakeMacro('PETSC_TAO_LIB','${PETSC_WITH_EXTERNAL_LIB}') 436 self.addMakeMacro('PETSC_CHARACTERISTIC_LIB','${PETSC_WITH_EXTERNAL_LIB}') 437 self.addMakeMacro('PETSC_LIB','${PETSC_WITH_EXTERNAL_LIB}') 438 self.addMakeMacro('PETSC_CONTRIB','${PETSC_WITH_EXTERNAL_LIB}') 439 440 if not os.path.exists(os.path.join(self.petscdir.dir,self.arch.arch,'lib')): 441 os.makedirs(os.path.join(self.petscdir.dir,self.arch.arch,'lib')) 442 443# add a makefile endtry for display 444 if self.framework.argDB['with-display']: 445 self.addMakeMacro('DISPLAY',self.framework.argDB['with-display']) 446 447 # add a makefile entry for configure options 448 self.addMakeMacro('CONFIGURE_OPTIONS', self.framework.getOptionsString(['configModules', 'optionsModule']).replace('\"','\\"')) 449 return 450 451 def dumpConfigInfo(self): 452 import time 453 fd = open(os.path.join(self.arch.arch,'include','petscconfiginfo.h'),'w') 454 fd.write('static const char *petscconfigureoptions = "'+self.framework.getOptionsString(['configModules', 'optionsModule']).replace('\"','\\"')+'";\n') 455 fd.close() 456 return 457 458 def dumpMachineInfo(self): 459 import platform 460 import datetime 461 import time 462 import script 463 def escape(s): 464 return s.replace('"',r'\"').replace(r'\ ',r'\\ ') 465 fd = open(os.path.join(self.arch.arch,'include','petscmachineinfo.h'),'w') 466 fd.write('static const char *petscmachineinfo = \"\\n\"\n') 467 fd.write('\"-----------------------------------------\\n\"\n') 468 buildhost = platform.node() 469 if os.environ.get('SOURCE_DATE_EPOCH'): 470 buildhost = "reproducible" 471 buildtime = datetime.datetime.utcfromtimestamp(int(os.environ.get('SOURCE_DATE_EPOCH', time.time()))) 472 fd.write('\"Libraries compiled on %s on %s \\n\"\n' % (buildtime, buildhost)) 473 fd.write('\"Machine characteristics: %s\\n\"\n' % (platform.platform())) 474 fd.write('\"Using PETSc directory: %s\\n\"\n' % (escape(self.installdir.petscDir))) 475 fd.write('\"Using PETSc arch: %s\\n\"\n' % (escape(self.installdir.petscArch))) 476 fd.write('\"-----------------------------------------\\n\";\n') 477 fd.write('static const char *petsccompilerinfo = \"\\n\"\n') 478 self.setCompilers.pushLanguage(self.languages.clanguage) 479 fd.write('\"Using C compiler: %s %s \\n\"\n' % (escape(self.setCompilers.getCompiler()), escape(self.setCompilers.getCompilerFlags()))) 480 self.setCompilers.popLanguage() 481 if hasattr(self.compilers, 'FC'): 482 self.setCompilers.pushLanguage('FC') 483 fd.write('\"Using Fortran compiler: %s %s %s\\n\"\n' % (escape(self.setCompilers.getCompiler()), escape(self.setCompilers.getCompilerFlags()), escape(self.setCompilers.CPPFLAGS))) 484 self.setCompilers.popLanguage() 485 fd.write('\"-----------------------------------------\\n\";\n') 486 fd.write('static const char *petsccompilerflagsinfo = \"\\n\"\n') 487 fd.write('\"Using include paths: %s\\n\"\n' % (escape(self.PETSC_CC_INCLUDES_INSTALL.replace('${PETSC_DIR}', self.installdir.petscDir)))) 488 fd.write('\"-----------------------------------------\\n\";\n') 489 fd.write('static const char *petsclinkerinfo = \"\\n\"\n') 490 self.setCompilers.pushLanguage(self.languages.clanguage) 491 fd.write('\"Using C linker: %s\\n\"\n' % (escape(self.setCompilers.getLinker()))) 492 self.setCompilers.popLanguage() 493 if hasattr(self.compilers, 'FC'): 494 self.setCompilers.pushLanguage('FC') 495 fd.write('\"Using Fortran linker: %s\\n\"\n' % (escape(self.setCompilers.getLinker()))) 496 self.setCompilers.popLanguage() 497 fd.write('\"Using libraries: %s%s -L%s %s %s\\n\"\n' % (escape(self.setCompilers.CSharedLinkerFlag), escape(os.path.join(self.installdir.petscDir, self.installdir.petscArch, 'lib')), escape(os.path.join(self.installdir.petscDir, self.installdir.petscArch, 'lib')), escape(self.petsclib), escape(self.PETSC_EXTERNAL_LIB_BASIC))) 498 fd.write('\"-----------------------------------------\\n\";\n') 499 fd.close() 500 return 501 502 def configurePrefetch(self): 503 '''Sees if there are any prefetch functions supported''' 504 if config.setCompilers.Configure.isSolaris(self.log) or self.framework.argDB['with-ios'] or not self.framework.argDB['with-prefetch']: 505 self.addDefine('Prefetch(a,b,c)', ' ') 506 return 507 self.pushLanguage(self.languages.clanguage) 508 if self.checkLink('#include <xmmintrin.h>', 'void *v = 0;_mm_prefetch((const char*)v,_MM_HINT_NTA);\n'): 509 # The Intel Intrinsics manual [1] specifies the prototype 510 # 511 # void _mm_prefetch(char const *a, int sel); 512 # 513 # but other vendors seem to insist on using subtly different 514 # prototypes, including void* for the pointer, and an enum for 515 # sel. These are both reasonable changes, but negatively impact 516 # portability. 517 # 518 # [1] https://software.intel.com/file/6373 519 self.addDefine('HAVE_XMMINTRIN_H', 1) 520 self.addDefine('Prefetch(a,b,c)', '_mm_prefetch((const char*)(a),(c))') 521 self.addDefine('PREFETCH_HINT_NTA', '_MM_HINT_NTA') 522 self.addDefine('PREFETCH_HINT_T0', '_MM_HINT_T0') 523 self.addDefine('PREFETCH_HINT_T1', '_MM_HINT_T1') 524 self.addDefine('PREFETCH_HINT_T2', '_MM_HINT_T2') 525 elif self.checkLink('#include <xmmintrin.h>', 'void *v = 0;_mm_prefetch(v,_MM_HINT_NTA);\n'): 526 self.addDefine('HAVE_XMMINTRIN_H', 1) 527 self.addDefine('Prefetch(a,b,c)', '_mm_prefetch((const void*)(a),(c))') 528 self.addDefine('PREFETCH_HINT_NTA', '_MM_HINT_NTA') 529 self.addDefine('PREFETCH_HINT_T0', '_MM_HINT_T0') 530 self.addDefine('PREFETCH_HINT_T1', '_MM_HINT_T1') 531 self.addDefine('PREFETCH_HINT_T2', '_MM_HINT_T2') 532 elif self.checkLink('', 'void *v = 0;__builtin_prefetch(v,0,0);\n'): 533 # From GCC docs: void __builtin_prefetch(const void *addr,int rw,int locality) 534 # 535 # The value of rw is a compile-time constant one or zero; one 536 # means that the prefetch is preparing for a write to the memory 537 # address and zero, the default, means that the prefetch is 538 # preparing for a read. The value locality must be a compile-time 539 # constant integer between zero and three. A value of zero means 540 # that the data has no temporal locality, so it need not be left 541 # in the cache after the access. A value of three means that the 542 # data has a high degree of temporal locality and should be left 543 # in all levels of cache possible. Values of one and two mean, 544 # respectively, a low or moderate degree of temporal locality. 545 # 546 # Here we adopt Intel's x86/x86-64 naming scheme for the locality 547 # hints. Using macros for these values in necessary since some 548 # compilers require an enum. 549 self.addDefine('Prefetch(a,b,c)', '__builtin_prefetch((a),(b),(c))') 550 self.addDefine('PREFETCH_HINT_NTA', '0') 551 self.addDefine('PREFETCH_HINT_T0', '3') 552 self.addDefine('PREFETCH_HINT_T1', '2') 553 self.addDefine('PREFETCH_HINT_T2', '1') 554 else: 555 self.addDefine('Prefetch(a,b,c)', ' ') 556 self.popLanguage() 557 558 def configureAtoll(self): 559 '''Checks if atoll exists''' 560 if self.checkLink('#define _POSIX_C_SOURCE 200112L\n#include <stdlib.h>','long v = atoll("25")') or self.checkLink ('#include <stdlib.h>','long v = atoll("25")'): 561 self.addDefine('HAVE_ATOLL', '1') 562 563 def configureUnused(self): 564 '''Sees if __attribute((unused)) is supported''' 565 if self.framework.argDB['with-ios']: 566 self.addDefine('UNUSED', ' ') 567 return 568 self.pushLanguage(self.languages.clanguage) 569 if self.checkLink('__attribute((unused)) static int myfunc(__attribute((unused)) void *name){ return 1;}', 'int i = 0;\nint j = myfunc(&i);\ntypedef void* atype;\n__attribute((unused)) atype a;\n'): 570 self.addDefine('UNUSED', '__attribute((unused))') 571 else: 572 self.addDefine('UNUSED', ' ') 573 self.popLanguage() 574 575 def configureIsatty(self): 576 '''Check if the Unix C function isatty() works correctly 577 Actually just assumes it does not work correctly on batch systems''' 578 if not self.framework.argDB['with-batch']: 579 self.addDefine('USE_ISATTY',1) 580 581 def configureDeprecated(self): 582 '''Check if __attribute((deprecated)) is supported''' 583 self.pushLanguage(self.languages.clanguage) 584 ## Recent versions of gcc and clang support __attribute((deprecated("string argument"))), which is very useful, but 585 ## Intel has conspired to make a supremely environment-sensitive compiler. The Intel compiler looks at the gcc 586 ## executable in the environment to determine the language compatibility that it should attempt to emulate. Some 587 ## important Cray installations have built PETSc using the Intel compiler, but with a newer gcc module loaded (e.g., 588 ## 4.7). Thus at PETSc configure time, the Intel compiler decides to support the string argument, but the gcc 589 ## found in the default user environment is older and does not support the argument. If GCC and Intel were cool 590 ## like Clang and supported __has_attribute, we could avoid configure tests entirely, but they don't. And that is 591 ## why we can't have nice things. 592 # 593 # if self.checkCompile("""__attribute((deprecated("Why you shouldn't use myfunc"))) static int myfunc(void) { return 1;}""", ''): 594 # self.addDefine('DEPRECATED_FUNCTION(why)', '__attribute((deprecated(why)))') 595 # self.addDefine('DEPRECATED_TYPEDEF(why)', '__attribute((deprecated(why)))') 596 if self.checkCompile("""__attribute((deprecated)) static int myfunc(void) { return 1;}""", ''): 597 self.addDefine('DEPRECATED_FUNCTION(why)', '__attribute((deprecated))') 598 self.addDefine('DEPRECATED_TYPEDEF(why)', '__attribute((deprecated))') 599 else: 600 self.addDefine('DEPRECATED_FUNCTION(why)', ' ') 601 self.addDefine('DEPRECATED_TYPEDEF(why)', ' ') 602 if self.checkCompile("""enum E {oldval __attribute((deprecated)), newval };""", ''): 603 self.addDefine('DEPRECATED_ENUM(why)', '__attribute((deprecated))') 604 else: 605 self.addDefine('DEPRECATED_ENUM(why)', ' ') 606 # I was unable to make a CPP macro that takes the old and new values as seperate arguments and builds the message needed by _Pragma 607 # hence the deprecation message is handled as it is 608 if self.checkCompile('#define TEST _Pragma("GCC warning \"Testing _Pragma\"") value'): 609 self.addDefine('DEPRECATED_MACRO(why)', '_Pragma(why)') 610 else: 611 self.addDefine('DEPRECATED_MACRO(why)', ' ') 612 self.popLanguage() 613 614 def configureAlign(self): 615 '''Check if __attribute(aligned) is supported''' 616 code = '''\ 617struct mystruct {int myint;} __attribute((aligned(16))); 618char assert_aligned[(sizeof(struct mystruct)==16)*2-1]; 619''' 620 self.pushLanguage(self.languages.clanguage) 621 if self.checkCompile(code): 622 self.addDefine('ATTRIBUTEALIGNED(size)', '__attribute((aligned(size)))') 623 self.addDefine('HAVE_ATTRIBUTEALIGNED', 1) 624 else: 625 self.framework.logPrint('Incorrect attribute(aligned)') 626 self.addDefine('ATTRIBUTEALIGNED(size)', ' ') 627 self.popLanguage() 628 return 629 630 def configureExpect(self): 631 '''Sees if the __builtin_expect directive is supported''' 632 self.pushLanguage(self.languages.clanguage) 633 if self.checkLink('', 'if (__builtin_expect(0,1)) return 1;'): 634 self.addDefine('HAVE_BUILTIN_EXPECT', 1) 635 self.popLanguage() 636 637 def configureFunctionName(self): 638 '''Sees if the compiler supports __func__ or a variant.''' 639 def getFunctionName(lang): 640 name = '"unknown"' 641 self.pushLanguage(lang) 642 for fname in ['__func__','__FUNCTION__','__extension__ __func__']: 643 code = "if ("+fname+"[0] != 'm') return 1;" 644 if self.checkCompile('',code) and self.checkLink('',code): 645 name = fname 646 break 647 self.popLanguage() 648 return name 649 langs = [] 650 651 self.addDefine('FUNCTION_NAME_C', getFunctionName('C')) 652 if hasattr(self.compilers, 'CXX'): 653 self.addDefine('FUNCTION_NAME_CXX', getFunctionName('Cxx')) 654 655 def configureIntptrt(self): 656 '''Determine what to use for uintptr_t''' 657 def staticAssertSizeMatchesVoidStar(inc,typename): 658 # The declaration is an error if either array size is negative. 659 # It should be okay to use an int that is too large, but it would be very unlikely for this to be the case 660 return self.checkCompile(inc, ('#define STATIC_ASSERT(cond) char negative_length_if_false[2*(!!(cond))-1]\n' 661 + 'STATIC_ASSERT(sizeof(void*) == sizeof(%s));'%typename)) 662 self.pushLanguage(self.languages.clanguage) 663 if self.checkCompile('#include <stdint.h>', 'int x; uintptr_t i = (uintptr_t)&x;'): 664 self.addDefine('UINTPTR_T', 'uintptr_t') 665 elif staticAssertSizeMatchesVoidStar('','unsigned long long'): 666 self.addDefine('UINTPTR_T', 'unsigned long long') 667 elif staticAssertSizeMatchesVoidStar('#include <stdlib.h>','size_t') or staticAssertSizeMatchesVoidStar('#include <string.h>', 'size_t'): 668 self.addDefine('UINTPTR_T', 'size_t') 669 elif staticAssertSizeMatchesVoidStar('','unsigned long'): 670 self.addDefine('UINTPTR_T', 'unsigned long') 671 elif staticAssertSizeMatchesVoidStar('','unsigned'): 672 self.addDefine('UINTPTR_T', 'unsigned') 673 else: 674 raise RuntimeError('Could not find any unsigned integer type matching void*') 675 self.popLanguage() 676 677 def configureRTLDDefault(self): 678 if self.checkCompile('#include <dlfcn.h>\n void *ptr = RTLD_DEFAULT;'): 679 self.addDefine('RTLD_DEFAULT','1') 680 return 681 682 def configureSolaris(self): 683 '''Solaris specific stuff''' 684 if os.path.isdir(os.path.join('/usr','ucblib')): 685 try: 686 flag = getattr(self.setCompilers, self.language[-1]+'SharedLinkerFlag') 687 except AttributeError: 688 flag = None 689 if flag is None: 690 self.compilers.LIBS += ' -L/usr/ucblib' 691 else: 692 self.compilers.LIBS += ' '+flag+'/usr/ucblib' 693 return 694 695 def configureLinux(self): 696 '''Linux specific stuff''' 697 # TODO: Test for this by mallocing an odd number of floats and checking the address 698 self.addDefine('HAVE_DOUBLE_ALIGN_MALLOC', 1) 699 return 700 701 def configureWin32(self): 702 '''Win32 non-cygwin specific stuff''' 703 kernel32=0 704 if self.libraries.add('Kernel32.lib','GetComputerName',prototype='#include <Windows.h>', call='GetComputerName(NULL,NULL);'): 705 self.addDefine('HAVE_WINDOWS_H',1) 706 self.addDefine('HAVE_GETCOMPUTERNAME',1) 707 kernel32=1 708 elif self.libraries.add('kernel32','GetComputerName',prototype='#include <Windows.h>', call='GetComputerName(NULL,NULL);'): 709 self.addDefine('HAVE_WINDOWS_H',1) 710 self.addDefine('HAVE_GETCOMPUTERNAME',1) 711 kernel32=1 712 if kernel32: 713 if self.framework.argDB['with-windows-graphics']: 714 self.addDefine('USE_WINDOWS_GRAPHICS',1) 715 if self.checkLink('#include <Windows.h>','LoadLibrary(0)'): 716 self.addDefine('HAVE_LOADLIBRARY',1) 717 if self.checkLink('#include <Windows.h>','GetProcAddress(0,0)'): 718 self.addDefine('HAVE_GETPROCADDRESS',1) 719 if self.checkLink('#include <Windows.h>','FreeLibrary(0)'): 720 self.addDefine('HAVE_FREELIBRARY',1) 721 if self.checkLink('#include <Windows.h>','GetLastError()'): 722 self.addDefine('HAVE_GETLASTERROR',1) 723 if self.checkLink('#include <Windows.h>','SetLastError(0)'): 724 self.addDefine('HAVE_SETLASTERROR',1) 725 if self.checkLink('#include <Windows.h>\n','QueryPerformanceCounter(0);\n'): 726 self.addDefine('USE_MICROSOFT_TIME',1) 727 if self.libraries.add('Advapi32.lib','GetUserName',prototype='#include <Windows.h>', call='GetUserName(NULL,NULL);'): 728 self.addDefine('HAVE_GET_USER_NAME',1) 729 elif self.libraries.add('advapi32','GetUserName',prototype='#include <Windows.h>', call='GetUserName(NULL,NULL);'): 730 self.addDefine('HAVE_GET_USER_NAME',1) 731 732 if not self.libraries.add('User32.lib','GetDC',prototype='#include <Windows.h>',call='GetDC(0);'): 733 self.libraries.add('user32','GetDC',prototype='#include <Windows.h>',call='GetDC(0);') 734 if not self.libraries.add('Gdi32.lib','CreateCompatibleDC',prototype='#include <Windows.h>',call='CreateCompatibleDC(0);'): 735 self.libraries.add('gdi32','CreateCompatibleDC',prototype='#include <Windows.h>',call='CreateCompatibleDC(0);') 736 737 self.types.check('int32_t', 'int') 738 if not self.checkCompile('#include <sys/types.h>\n','uid_t u;\n'): 739 self.addTypedef('int', 'uid_t') 740 self.addTypedef('int', 'gid_t') 741 if not self.checkLink('#if defined(PETSC_HAVE_UNISTD_H)\n#include <unistd.h>\n#endif\n','int a=R_OK;\n'): 742 self.framework.addDefine('R_OK', '04') 743 self.framework.addDefine('W_OK', '02') 744 self.framework.addDefine('X_OK', '01') 745 if not self.checkLink('#include <sys/stat.h>\n','int a=0;\nif (S_ISDIR(a)){}\n'): 746 self.framework.addDefine('S_ISREG(a)', '(((a)&_S_IFMT) == _S_IFREG)') 747 self.framework.addDefine('S_ISDIR(a)', '(((a)&_S_IFMT) == _S_IFDIR)') 748 if self.checkCompile('#include <Windows.h>\n','LARGE_INTEGER a;\nDWORD b=a.u.HighPart;\n'): 749 self.addDefine('HAVE_LARGE_INTEGER_U',1) 750 751 # Windows requires a Binary file creation flag when creating/opening binary files. Is a better test in order? 752 if self.checkCompile('#include <Windows.h>\n#include <fcntl.h>\n', 'int flags = O_BINARY;'): 753 self.addDefine('HAVE_O_BINARY',1) 754 755 if self.compilers.CC.find('win32fe') >= 0: 756 self.addDefine('HAVE_WINDOWS_COMPILERS',1) 757 self.addDefine('PATH_SEPARATOR','\';\'') 758 self.addDefine('DIR_SEPARATOR','\'\\\\\'') 759 self.addDefine('REPLACE_DIR_SEPARATOR','\'/\'') 760 self.addDefine('CANNOT_START_DEBUGGER',1) 761 (petscdir,error,status) = self.executeShellCommand('cygpath -w '+self.installdir.petscDir, log = self.log) 762 self.addDefine('DIR','"'+petscdir.replace('\\','\\\\')+'"') 763 (petscdir,error,status) = self.executeShellCommand('cygpath -m '+self.installdir.petscDir, log = self.log) 764 self.addMakeMacro('wPETSC_DIR',petscdir) 765 else: 766 self.addDefine('PATH_SEPARATOR','\':\'') 767 self.addDefine('REPLACE_DIR_SEPARATOR','\'\\\\\'') 768 self.addDefine('DIR_SEPARATOR','\'/\'') 769 self.addDefine('DIR','"'+self.installdir.petscDir+'"') 770 self.addMakeMacro('wPETSC_DIR',self.installdir.petscDir) 771 self.addDefine('ARCH','"'+self.installdir.petscArch+'"') 772 return 773 774#----------------------------------------------------------------------------------------------------- 775 def configureCygwinBrokenPipe(self): 776 '''Cygwin version <= 1.7.18 had issues with pipes and long commands invoked from gnu-make 777 http://cygwin.com/ml/cygwin/2013-05/msg00340.html ''' 778 if config.setCompilers.Configure.isCygwin(self.log): 779 import platform 780 import re 781 r=re.compile("([0-9]+).([0-9]+).([0-9]+)") 782 m=r.match(platform.release()) 783 major=int(m.group(1)) 784 minor=int(m.group(2)) 785 subminor=int(m.group(3)) 786 if ((major < 1) or (major == 1 and minor < 7) or (major == 1 and minor == 7 and subminor <= 18)): 787 self.addMakeMacro('PETSC_CYGWIN_BROKEN_PIPE','1') 788 return 789 790#----------------------------------------------------------------------------------------------------- 791 def configureDefaultArch(self): 792 conffile = os.path.join('lib','petsc','conf', 'petscvariables') 793 if self.framework.argDB['with-default-arch']: 794 fd = open(conffile, 'w') 795 fd.write('PETSC_ARCH='+self.arch.arch+'\n') 796 fd.write('PETSC_DIR='+self.petscdir.dir+'\n') 797 fd.write('include '+os.path.join('$(PETSC_DIR)','$(PETSC_ARCH)','lib','petsc','conf','petscvariables')+'\n') 798 fd.close() 799 self.framework.actions.addArgument('PETSc', 'Build', 'Set default architecture to '+self.arch.arch+' in '+conffile) 800 elif os.path.isfile(conffile): 801 try: 802 os.unlink(conffile) 803 except: 804 raise RuntimeError('Unable to remove file '+conffile+'. Did a different user create it?') 805 return 806 807#----------------------------------------------------------------------------------------------------- 808 def configureScript(self): 809 '''Output a script in the conf directory which will reproduce the configuration''' 810 import nargs 811 import sys 812 scriptName = os.path.join(self.arch.arch,'lib','petsc','conf', 'reconfigure-'+self.arch.arch+'.py') 813 args = dict([(nargs.Arg.parseArgument(arg)[0], arg) for arg in self.framework.clArgs]) 814 if 'with-clean' in args: 815 del args['with-clean'] 816 if 'configModules' in args: 817 if nargs.Arg.parseArgument(args['configModules'])[1] == 'PETSc.Configure': 818 del args['configModules'] 819 if 'optionsModule' in args: 820 if nargs.Arg.parseArgument(args['optionsModule'])[1] == 'config.compilerOptions': 821 del args['optionsModule'] 822 if not 'PETSC_ARCH' in args: 823 args['PETSC_ARCH'] = 'PETSC_ARCH='+str(self.arch.arch) 824 f = open(scriptName, 'w') 825 f.write('#!'+sys.executable+'\n') 826 f.write('if __name__ == \'__main__\':\n') 827 f.write(' import sys\n') 828 f.write(' import os\n') 829 f.write(' sys.path.insert(0, os.path.abspath(\'config\'))\n') 830 f.write(' import configure\n') 831 # pretty print repr(args.values()) 832 f.write(' configure_options = [\n') 833 for itm in sorted(args.values()): 834 f.write(' \''+str(itm)+'\',\n') 835 f.write(' ]\n') 836 f.write(' configure.petsc_configure(configure_options)\n') 837 f.close() 838 try: 839 os.chmod(scriptName, 0o775) 840 except OSError as e: 841 self.framework.logPrint('Unable to make reconfigure script executable:\n'+str(e)) 842 self.framework.actions.addArgument('PETSc', 'File creation', 'Created '+scriptName+' for automatic reconfiguration') 843 return 844 845 def configureInstall(self): 846 '''Setup the directories for installation''' 847 if self.framework.argDB['prefix']: 848 self.addMakeRule('print_mesg_after_build','',['-@echo "Now to install the libraries do:"',\ 849 '-@echo "'+self.installdir.installSudo+'make PETSC_DIR=${PETSC_DIR} PETSC_ARCH=${PETSC_ARCH} install"',\ 850 '-@echo "========================================="']) 851 else: 852 self.addMakeRule('print_mesg_after_build','',['-@echo "Now to check if the libraries are working do:"',\ 853 '-@echo "make PETSC_DIR=${PETSC_DIR} PETSC_ARCH=${PETSC_ARCH} check"',\ 854 '-@echo "========================================="']) 855 return 856 857 def configureGCOV(self): 858 if self.framework.argDB['with-gcov']: 859 self.addDefine('USE_GCOV','1') 860 return 861 862 def postProcessPackages(self): 863 postPackages=[] 864 for i in self.framework.packages: 865 if hasattr(i,'postProcess'): postPackages.append(i) 866 if postPackages: 867 # ctetgen needs petsc conf files. so attempt to create them early 868 self.framework.dumpConfFiles() 869 # tacky fix for dependency of Aluimia on Pflotran; requested via petsc-dev Matt provide a correct fix 870 for i in postPackages: 871 if i.name.upper() in ['PFLOTRAN']: 872 i.postProcess() 873 postPackages.remove(i) 874 for i in postPackages: i.postProcess() 875 for i in postPackages: 876 if i.installedpetsc: 877 self.installed = 1 878 break 879 return 880 881 def configure(self): 882 if not os.path.samefile(self.petscdir.dir, os.getcwd()): 883 raise RuntimeError('Wrong PETSC_DIR option specified: '+str(self.petscdir.dir) + '\n Configure invoked in: '+os.path.realpath(os.getcwd())) 884 if self.framework.argDB['prefix'] and os.path.isdir(self.framework.argDB['prefix']) and os.path.samefile(self.framework.argDB['prefix'],self.petscdir.dir): 885 raise RuntimeError('Incorrect option --prefix='+self.framework.argDB['prefix']+' specified. It cannot be same as PETSC_DIR!') 886 if self.framework.argDB['prefix'] and self.framework.argDB['prefix'].find(' ') > -1: 887 raise RuntimeError('Your --prefix '+self.framework.argDB['prefix']+' has spaces in it; this is not allowed.\n Use a --prefix that does not have spaces in it') 888 if self.framework.argDB['prefix'] and os.path.isdir(self.framework.argDB['prefix']) and os.path.samefile(self.framework.argDB['prefix'],os.path.join(self.petscdir.dir,self.arch.arch)): 889 raise RuntimeError('Incorrect option --prefix='+self.framework.argDB['prefix']+' specified. It cannot be same as PETSC_DIR/PETSC_ARCH!') 890 self.framework.header = os.path.join(self.arch.arch,'include','petscconf.h') 891 self.framework.cHeader = os.path.join(self.arch.arch,'include','petscfix.h') 892 self.framework.pkgheader = os.path.join(self.arch.arch,'include','petscpkg_version.h') 893 self.framework.makeMacroHeader = os.path.join(self.arch.arch,'lib','petsc','conf','petscvariables') 894 self.framework.makeRuleHeader = os.path.join(self.arch.arch,'lib','petsc','conf','petscrules') 895 if self.libraries.math is None: 896 raise RuntimeError('PETSc requires a functional math library. Please send configure.log to petsc-maint@mcs.anl.gov.') 897 if self.languages.clanguage == 'Cxx' and not hasattr(self.compilers, 'CXX'): 898 raise RuntimeError('Cannot set C language to C++ without a functional C++ compiler.') 899 self.executeTest(self.configureRTLDDefault) 900 self.executeTest(self.configurePrefetch) 901 self.executeTest(self.configureUnused) 902 self.executeTest(self.configureDeprecated) 903 self.executeTest(self.configureIsatty) 904 self.executeTest(self.configureExpect); 905 self.executeTest(self.configureAlign); 906 self.executeTest(self.configureFunctionName); 907 self.executeTest(self.configureIntptrt); 908 self.executeTest(self.configureSolaris) 909 self.executeTest(self.configureLinux) 910 self.executeTest(self.configureWin32) 911 self.executeTest(self.configureCygwinBrokenPipe) 912 self.executeTest(self.configureDefaultArch) 913 self.executeTest(self.configureScript) 914 self.executeTest(self.configureInstall) 915 self.executeTest(self.configureGCOV) 916 self.executeTest(self.configureAtoll) 917 918 self.Dump() 919 self.dumpConfigInfo() 920 self.dumpMachineInfo() 921 # need to save the current state of BuildSystem so that postProcess() packages can read it in and perhaps run make install 922 self.framework.storeSubstitutions(self.framework.argDB) 923 self.framework.argDB['configureCache'] = pickle.dumps(self.framework) 924 self.framework.argDB.save(force = True) 925 self.DumpPkgconfig() 926 self.DumpModule() 927 self.postProcessPackages() 928 self.framework.log.write('================================================================================\n') 929 self.logClear() 930 return 931