📄 buildiface
字号:
lib\${MPILIBNAME}f90_a_SOURCES = mpi.o mpi_constants.o mpi_sizeofs.o mpi_base.o\n";print MAKEFD "all-preamble: \$(MPIMOD).\$(MOD)\n";print MAKEFD "\# The copy line in this step makes the F90 modules available to# the mpif90 script before an install takes place# The if handles the Intel F90 compiler, which has an unusual interface# (The mpimod.pcl file should contain only a local mpimod.pc name; if# it contains a file name in another directory and that file does not # exist, the compiler may refuse to compile the file)## FIXME: We may want to edit the mpif.h to convert Fortran77-specific# items (such as an integer*8 used for file offsets) into the # corresponding Fortran 90 KIND type, to accomodate compilers that# reject non-standard features such as integer*8 (such as the Intel# Fortran compiler with -std95).# We need the MPI constants in a separate module for some of the# interface definitions (the ones that need MPI_ADDRESS_KIND or# MPI_OFFSET_KIND)";print MAKEFD "\\$(MPIMOD).\$(MOD): \$(MPICONSTMOD).\$(MOD) \$(MPISIZEOFMOD).\$(MOD) \\\t\t \$(MPIBASEMOD).\$(MOD) \$(srcdir)/mpi.f90 mpifnoext.h\n";&createModSteps( '$(srcdir)/mpi.f90' );#print MAKEFD "\tcp mpi.\$(MOD) mpi_constants.\$(MOD) mpi_base.\$(MOD) mpi_sizeofs.\$(MOD) ../../../src/include\n";## Some versions of the Intel f90 compiler require special files that # describe which modules to load.#print MAKEFD "\t\@if [ -n \"\@F90_WORK_FILES_ARG\@\" ] ; then \\\#\t cp work.pc ../../../src/include/mpimod.pc ; \\\#\t echo \"mpimod.pc\" > mpimod.pcl ; \\\#\t echo \"\${includedir}/mpimod.pc\" >> mpimod.pcl ;\\\#\t cp mpimod.pcl ../../../src/include/mpimod.pcl ; \\\#\tfi\n";print MAKEFD "\$(MPICONSTMOD).\$(MOD): \$(srcdir)/mpi_constants.f90 mpifnoext.h\n";&createModSteps( '$(srcdir)/mpi_constants.f90' );print MAKEFD "\$(MPISIZEOFMOD).\$(MOD): mpi_sizeofs.f90 mpifnoext.h\n";&createModSteps( "mpi_sizeofs.f90" );print MAKEFD "\$(MPIBASEMOD).\$(MOD): \$(srcdir)/mpi_base.f90\n";&createModSteps( '$(srcdir)/mpi_base.f90' );print MAKEFD "\# We need a free-format version of mpif.h with no external commandsmpifnoext.h: ../f77/mpif.h rm -f mpifnoext.h sed -e 's/^C/\\!/g' -e '/EXTERNAL/d' \\ -e '/DOUBLE PRECISION/d' ../f77/mpif.h > mpifnoext.h";print MAKEFD "# To ensure that f90 can be used before a make-install step, we copy# the library to the build directory (just like we do with the module files)all-postamble: if [ -s lib\${MPILIBNAME}f90.a ] ; then \\ cp -p lib\${MPILIBNAME}f90.a ../../../lib ; fi";print MAKEFD "clean-local:\n";print MAKEFD "\trm -f *.\$(MOD)\n";print MAKEFD "\trm -f mpimod.pcl mpimod.pc\n";print MAKEFD "maint-clean:\\trm -f \${mpi_sources} fproto.h\n";#print MAKEFD "install_BIN = mpif90\n";#print MAKEFD "install_ETC = mpif90.conf\n";print MAKEFD "install_INCLUDE = \$(MPIMOD).\$(MOD) \$(MPICONSTMOD).\$(MOD) \$(MPIBASEMOD).\$(MOD) \$(MPISIZEOFMOD).\$(MOD)\n";# These next two are special files needed by some versions of the Intel # compilersprint MAKEFD "optinstall_INCLUDE = mpimod.pcl mpimod.pc\n";print MAKEFD "install_LIB = lib\${MPILIBNAME}f90.a\n";#print MAKEFD "optinstall_SHLIB= lib\${MPILIBNAME}f90.so\n"; # Add the documentation#doc_sources = mpif90.txt manf90.txt print MAKEFD "# Documentation sourcesdoc_sources =DOCDESTDIRS = html:www/www1,man:man/man1,latex:doc/refmandoc_HTML_SOURCES = \${doc_sources}doc_MAN_SOURCES = \${doc_sources}doc_LATEX_SOURCES = \${doc_sources}";# ----------------------------------------------------------------------------# FIXME: Add the steps to handle the choice arguments. They should be# selected by configure from a list of possible choices, with an # enable switch used to bypass the checks. In addition, we need a way to # dynamically create subsets, given a list of routines and types/dimensions # to include. This allows users to build precisely tailored F90 modules.# ----------------------------------------------------------------------------# Since configure copies mpif90 to the bin dir, we need to remove it# in a distclean step.print MAKEFD "distclean-local:\n";print MAKEFD "\trm -f lib\${MPILIBNAME}f90.a\n";print MAKEFD "\trm -f ../../../bin/mpif90\n";print MAKEFD "\trm -f ../../../src/include/\$(MPIMOD).\$(MOD)\n";print MAKEFD "\trm -f ../../../src/include/\$(MPIBASEMOD).\$(MOD)\n";print MAKEFD "\trm -f ../../../src/include/\$(MPICONSTMOD).\$(MOD)\n";print MAKEFD "\trm -f ../../../src/include/\$(MPISIZEOFMOD).\$(MOD)\n";close( MAKEFD );&ReplaceIfDifferent( "Makefile.sm", "Makefile.sm.new" );## Still to do# make sure that we fit within the Fortran line length rules# Look into alternatives for generating a zillion files# Handle routines with more than one choice argument## ------------------------------------------------------------------------# Procedures# print_line( FD, line, count, continue, continuelen )# Print line to FD; if line size > count, output continue string and# continue. Use print_endline to finish a linesub print_line { my $FD = $_[0]; my $line = $_[1]; my $count = $_[2]; my $continue = $_[3]; my $continue_len = $_[4]; $linelen = length( $line ); #print "linelen = $linelen, print_line_len = $print_line_len\n"; if ($print_line_len + $linelen > $count) { print $FD $continue; $print_line_len = $continue_len; } print $FD $line; $print_line_len += $linelen;}sub print_endline { my $FD = $_[0]; print $FD "\n"; $print_line_len = 0;}# This routine adds to the Makefile.sm the instructions to create# a module, handling the strange requirements of some Fortran 90 compilers.# Also handles the case where the sub createModSteps { my ($srcFile) = @_; # Get a version of the source file with $(F90EXT) instead of .f90 # as the extension my $srcFileWithExt = $srcFile; $srcFileWithExt =~ s/\.f90$/\.\$(F90EXT)/;print MAKEFD "\t\@if [ -n \"\@F90_WORK_FILES_ARG\@\" ] ; then \\ rm -f mpimod.pc mpimod.pcl ; \\ echo \"mpimod.pc\" > mpimod.pcl ; \\ echo \$(F90_COMPILE_MODS) \@F90_WORK_FILES_ARG\@ -c $srcFile ; \\ \$(F90_COMPILE_MODS) \@F90_WORK_FILES_ARG\@ -c $srcFile ; \\ cp mpimod.pc ../../../src/include/mpimod.pc ; \\ cp mpimod.pcl ../../../src/include/mpimod.pcl ; \\ else \\ if [ \"\$(F90EXT)\" != \"f90\" ] ; then \\ ln -sf $srcFile $srcFileWithExt ; \\ fi ; \\ echo \$(F90_COMPILE_MODS) -c $srcFileWithExt ; \\ \$(F90_COMPILE_MODS) -c $srcFileWithExt ; \\ if [ \"\$(F90EXT)\" != \"f90\" ] ; then \\ rm -f $srcFileWithExt ; \\ fi ; \\ fi";}# Print the declarations for the given routine. sub PrintArgDecls { my ($routine,$svflag,$svArgs) = @_; my $ucname = uc($routine); my $args = $mpi_routines{$routine}; my @parms = split(/,/, $args ); # preload the svargs if requested. This is used to decide whether # an array arg is output as a scalar or a vector my %svargs = (); if ($svflag) { for my $val (split(/:/,$svArgs)) { my $loc = $val; my $count = "-1"; if ($loc =~ /(\d+)-(\d+)/) { $loc = $1; $count = $2; } $svargs{$loc} = $count; } } # Determine if we need any constants (e.g., MPI_STATUS_SIZE, # MPI_OFFSET_KIND) my %use_constants = (); my $found_constants = 0; for (my $i=0; $i<=$#parms; $i++) { $parm = $parms[$i]; # Check for special args $loc = $i+1; if (defined($special_args{"$routine-$loc"})) { $parm = $special_args{"$routine-$loc"}; } # Map the C type to the Fortran type $cparm = $parm; $cparm =~ s/\s+//g; $fparm = $parmc2f{$cparm}; # Now, does this type contain an MPI constant? if ($fparm =~ /(MPI_[A-Z_]*)/) { $use_constants{$1} = 1; $found_constants = 1; } } if ($found_constants) { print MPIBASEFD " USE MPI_CONSTANTS,ONLY:"; $sep = ""; foreach $name (keys(%use_constants)) { print MPIBASEFD "$sep$name"; $sep = ", "; $NeedConstants{$routine} .= "$name "; } print MPIBASEFD "\n"; } # Output argument types $lastParmType = "<none>"; for (my $i=0; $i<=$#parms; $i++) { $parm = $parms[$i]; # Check for special args $loc = $i+1; if (defined($special_args{"$routine-$loc"})) { $parm = $special_args{"$routine-$loc"}; } # Map the C type to the Fortran type $cparm = $parm; $cparm =~ s/\s+//g; $fparm = $parmc2f{$cparm}; if ($fparm eq "") { print STDERR "$routine: No parm type for $cparm ($parm)\n"; } # Split out the base type from the name if ($fparm =~ /(\w+.*)\s+(%name\S.*)/) { $parmType = $1; $varName = $2; if ($varName =~ /%name%/) { $varName =~ s/%name%/v$i/; } $varName =~ s/%nl%/\n /g; $parmType =~ s/%nl%/\n /g; # Here's where we might change vector to scalar args if ($svflag) { if (defined($svargs{$loc})) { # The value is the count arg for the array; later, we # can make use of that to improve the definitions if ($varName =~ /,\*/) { $varName =~ s/,\*//; } elsif ($varName =~ /\(\*\)/) { $varName =~ s/\(\*\)//; } else { print STDERR "Failed to make arg $i in $routine a scalar\n"; } } } } else { $parmType = $fparm; $varName = "v$i"; } if ($parmType ne $lastParmType) { if ($lastParmType ne "<none>" ) { print MPIBASEFD "\n"; } print MPIBASEFD " $parmType $varName"; $lastParmType = $parmType; } else { print MPIBASEFD ", $varName"; } } if ($lastParmType ne "<none>" ) { print MPIBASEFD "\n"; } print MPIBASEFD " INTEGER ierror\n";}## Replace old file with new file only if new file is different# Otherwise, remove new filename sub ReplaceIfDifferent { my ($oldfilename,$newfilename) = @_; my $rc = 1; if (-s $oldfilename) { $rc = system "cmp -s $newfilename $oldfilename"; $rc >>= 8; # Shift right to get exit status } if ($rc != 0) { # The files differ. Replace the old file # with the new one if (-s $oldfilename) { print STDERR "Replacing $oldfilename\n"; unlink $oldfilename; } else { print STDERR "Creating $oldfilename\n"; } rename $newfilename, $oldfilename || die "Could not replace $oldfilename"; } else { unlink $newfilename; }}
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -