Merge commit 'charm/charm' into charm
[charm.git] / build
1 #!/bin/sh
2
3 # Silly shorthand, used for source reorganization
4 src="src/arch"
5
6 more=0
7
8 syntax() {
9   echo ''
10   echo 'Usage: build <target> <version> <options> [charmc-options ...]'
11   echo ''
12   echo '<targets>: converse charm++ LIBS AMPI FEM bigemulator pose jade msa'
13   echo '<targets>: doc ps-doc pdf-doc html-doc'
14   if test $more = 1
15   then
16   echo ''
17   echo '  charm++         compile Charm++ core only'
18   echo '  AMPI            compile Adaptive MPI on top of Charm++'
19   echo '  FEM             compile FEM framework'
20   echo '  LIBS            compile additional parallel libraries with Charm++ core'
21   echo '  bigemulator     build additional BigSim libraries'
22   echo '  pose            build POSE parallel discrete event simulator'
23   echo '  jade            build Jade compiler (auto-builds charm++, msa)'
24   echo '  msa             build Multiphase Shared Arrays(MSA) library'
25   echo '  Tau             build the TAU tracing library for generating TAU performance data' 
26   echo '  ChaNGa          compile Charm++ core and necessary libraries for ChaNGa'
27   echo ''
28   fi
29   echo '<versions>: ' 
30   ( cd $src ; ls -1 | egrep -v '(^CVS)|(^shmem$)|(^mpi$)|(^sim$)|(^net$)|(^multicore$)|(^elan$)|(^util$)|(^common$)|(^uth$)|(^conv-mach-fix.sh$)|(^win32$)|(^win64$)|(^paragon$)|(^vmi$)|(^lapi$)|(^cell$)|(^template$)|(^cuda$)' | pr -3 -t )
31   echo ''
32   echo '<options>: compiler and platform specific options'
33   echo 'cc cc64 cxx kcc pgcc acc icc ecc gcc3 gcc4 mpcc pathscale'
34   echo 'help smp gm tcp vmi scyld clustermatic bigemulator ooc syncft mlogft papi'
35   echo 'pthreads lam'
36   echo '--incdir --libdir --basedir --no-build-shared --destination --suffix -j'
37   if test $more = 1
38   then
39   echo ''
40   echo 'For platform specific options, use help option:'
41   echo '  help            platform specific help, e.g. ./build charm++ net-linux help'
42   echo ''
43   echo 'Choose a compiler (only one option is allowed from this section):'
44   echo '  cc, cc64        For Sun WorkShop C++ 32/64 bit compilers'
45   echo '  cxx             DIGITAL C++ compiler (DEC Alpha)'
46   echo '  kcc             KAI C++ compiler'
47   echo "  pgcc            Portland Group's C++ compiler"
48   echo '  acc             HP aCC compiler'
49   echo '  icc             Intel C/C++ compiler for Linux IA32'
50   echo '  ecc             Intel C/C++ compiler for Linux IA64'
51   echo '  gcc3            use gcc3 - GNU GCC/G++ version 3'
52   echo '  gcc4            use gcc4 - GNU GCC/G++ version 4 (only mpi-crayxt3)'
53   echo '  mpcc            SUN Solaris C++ compiler for MPI'
54   echo '  pathscale       use pathscale compiler suite'
55   echo ''
56   echo 'Choose a fortran compile (only one option is allowed from this section):'
57   echo '  g95             G95 at http://ww.g95.org'
58   echo '  absoft          Absoft fortran compiler'
59   echo "  pgf90           Portland Group\'s Fortran compiler"
60   echo '  ifc             Intel Fortran compiler (older versions)'
61   echo '  ifort           Intel Fortran compiler (newer versions)'
62   echo ''
63   echo 'Platform specific options (choose multiple if apply):'
64   echo '  lam             Use LAM MPI'
65   echo '  smp             support for SMP, multithreaded charm on each node'
66   echo '  mpt             use SGI Message Passing Toolkit (only for mpi version)'
67   echo '  gm              use Myrinet for communication'
68   echo '  tcp             use TCP sockets for communication (only for net version)'
69   echo '  ibverbs         use the Infiniband OpenIB layer for communication (only for net-linux-amd64 currently)'
70   echo "  vmi             use NCSA's VMI for communication (only for mpi version)"
71   echo '  scyld           compile for Scyld Beowulf cluster based on bproc'
72   echo '  clustermatic    compile for Clustermatic (support version 3 and 4) '
73   echo '  pthreads        compile with pthreads Converse threads'
74   echo ''
75   echo 'Advanced options:'
76   echo '  bigemulator     compile for BigSim simulator'
77   echo '  ooc             compile with out of core support'
78   echo '  syncft          compile with Charm++ fault tolerance support'
79   echo '  mlogft          compile with Charm++ message logging fault tolerance support'
80   echo '  papi            compile with PAPI performance counter support (if any)'
81   echo ''
82   echo "Charm++ dynamic libraries:"
83   echo "  --build-shared     build Charm++ dynamic libraries (.so) (default)"
84   echo "  --no-build-shared  don't build Charm++'s shared libraries"
85   echo ''
86   echo 'Miscellaneous options:'
87   echo '  --incdir=DIR       specify additional include path for compiler'
88   echo '  --libdir=DIR       specify additional lib path for compiler'
89   echo '  --basedir=DIR      shortcut for the above two - DIR/include and DIR/lib'
90   echo '  -j[N]              parallel make, N is the number of paralle make jobs'
91   echo "  --with-romio       build AMPI with ROMIO library"
92   echo "  --destination=DIR  build Charm++ inside DIR, by default the destination is <version>"
93   echo "  --suffix=DIR       append DIR to the destination directory of the Charm++ build"
94   echo "  --tau-makefile=FILE Specify which TAU stub makefile to use"
95   fi
96   echo ''
97   echo '<charmc-options>: normal compiler options e.g. -g -O -save -verbose'
98   if test $more = 1
99   then
100   echo ''
101   echo 'Examples:'
102   echo "1. display all supported options for net-linux using 'help':"
103   echo '  ./build charm++ net-linux help'
104   echo '2. compile Charm++ on Linux with optimizations:'
105   echo '  ./build charm++ net-linux -O -DCMK_OPTIMIZE'
106   echo '3. compile Charm++ for Linux clustermatic Beowulf cluster with Intel compiler:'
107   echo '  ./build charm++ net-linux clustermatic icc -O'
108   echo '4. compile Charm++ for IA64 Linux cluster with MPICH-GM:'
109   echo '  ./build charm++ mpi-linux-ia64 gm -O'
110   echo '5. compile Charm++ for Windows with VC++ (Cygwin required):'
111   echo '  ./build charm++ net-win32 -O'
112   echo '6. compile on IBM SP with MPI using parallel gmake, 4 jobs simultaneously:'
113   echo '  MAKE=gmake  ./build charm++ mpi-sp -j4 -O            # sh'
114   echo '  setenv MAKE gmake;  ./build charm++ mpi-sp -j4 -O    # csh'
115   echo '7. compile Charm++ with MPI that is installed at /usr/local/mpich:'
116   echo '  ./build charm++ mpi-linux --incdir /usr/local/mpich/include --libdir /usr/local/mpich/lib -O'
117   echo '   or in short,'
118   echo '  ./build charm++ mpi-linux --basedir /usr/local/mpich -O'
119   echo '  ./build Tau --tau-makefile=/usr/local/packages/TAU/x86_64/lib/Makefile.tau-mpi'
120   echo ''
121   echo 'Note: This script:'
122   echo ' 1. Creates directories <destination> and <destination>/tmp'
123   echo ' 2. Copies src/scripts/Makefile into <destination>/tmp'
124   echo ' 3. Does a "make basics" in <destination>/tmp.'
125   echo ' 3. Does a "make -jN <target> <version> OPTS=<charmc-options>" in <destination>/tmp.'
126   echo "That's all build does.  The rest is handled by the Makefile."
127   echo ''
128   echo 'Thank you for using Charm++, please send questions or comments to '
129   echo 'Parallel Programming Lab at University of Illinois at Urbana-Champaign'
130   echo '(email: charm@cs.uiuc.edu).'
131
132   else
133   echo ''
134   echo "To get more detailed help, run ./build --help"
135   fi
136 }
137
138 Echo() {
139     [ "x$QUIET" = "x--quiet" ] || echo $*
140 }
141
142 printOption() {
143   for prefix in cc conv-mach
144   do
145     str="Supported compilers:"
146     [ "$prefix" = "conv-mach" ] && str="Supported options:"
147     opts=""
148     for dir in $OPT_DIRS
149     do
150 #         echo "Checking for $prefix in $dir"
151           files=`cd $dir; ls $prefix-*.h 2>/dev/null`
152           opts="$opts "`echo $files | sed 's/'$prefix'-\([^.]*\).h/\1/g'`
153     done 
154     tmp=.tmp.$$
155     rm -f $tmp; touch $tmp
156     for o in $opts
157     do
158       echo $o >> $tmp
159     done
160     opts=`sort $tmp | uniq`
161     rm -f $tmp
162     echo $str $opts
163   done
164   exit 1
165 }
166
167 CheckDir() {
168   for d in $*
169   do
170     if test ! -d $d
171     then
172       echo Error: cannot find $d!
173       exit 1
174     fi
175   done
176 }
177
178 TestIfCompiler() {
179   for dir in $OPT_DIRS
180   do
181     [ -f $dir/cc-$1.sh ] && return 1
182   done  
183   return 0
184 }
185
186 TestIfOption() {
187   for dir in $OPT_DIRS
188   do
189     [ -f $dir/conv-mach-$1.h ] && return 1 
190   done
191   
192   echo "Error> option: $1 is not supported in this version!"; 
193   printOption
194 }
195
196
197 # start
198
199 MAKEOPTS=""
200 OPTS=""
201 BOPTS=""
202 MORE=""
203 COMPILER=""
204 BASEDIR=
205 LIBDIR=
206 INCDIR=
207 ARCH=
208 BUILD_SHARED=
209 WITH_ROMIO=
210 BUILD_EMULATOR=0
211 DESTINATION=""
212 DESTINATION_SUFFIX=""
213 TAU_MAKEFILE=""
214 QUIET=""
215
216 [ "$1" = '--help' -o "$1" = '-h' ] && more=1 && syntax | more && exit 1
217 [ $# -lt 2 ] && ./smart-build.pl && exit 1
218 PROGRAM=$1
219 shift
220 VERSION=$1; BASEVERSION=$1; 
221 if test -f $src/$BASEVERSION/vdir_link
222 then
223   BASEVERSION=`cat $src/$BASEVERSION/vdir_link`
224 fi
225 ARCH=`echo $1 | sed -e 's@-.*@@'`
226 shift
227
228 #echo $src
229 #echo $BASEVERSION
230 #echo $ARCH
231
232 OPT_DIRS="$src/$BASEVERSION $src/$ARCH $src/common"
233
234 while [ ! $# -eq 0 ]
235 do
236   case "$1" in
237     "--basedir")
238                 shift; 
239                 for dir in $1
240                 do
241                   CheckDir $dir/include $dir/lib
242                   LIBDIR="$LIBDIR -L$dir/lib";
243                   INCDIR="$INCDIR -I$dir/include"
244                 done
245                 shift
246                 ;;
247     --basedir=*)
248                 basedir=`echo $1 | awk -F= '{print $2}'`
249                 for dir in $basedir
250                 do
251                   CheckDir $dir/include $dir/lib
252                   LIBDIR="$LIBDIR -L$dir/lib";
253                   INCDIR="$INCDIR -I$dir/include"
254                 done
255                 shift
256                 ;;
257     "--libdir")
258                 shift; CheckDir $1
259                 for dir in $1
260                 do
261                   LIBDIR="$LIBDIR -L$dir"; 
262                 done
263                 shift
264                 ;;
265     --libdir=*)
266                 libdir=`echo $1 | awk -F= '{print $2}'`
267                 CheckDir $libdir
268                 for dir in $libdir
269                 do
270                   LIBDIR="$LIBDIR -L$dir"; 
271                 done
272                 shift
273                 ;;
274     "--incdir")
275                 shift; CheckDir $1
276                 for dir in $1
277                 do
278                   INCDIR="$INCDIR -I$dir"; 
279                 done
280                 shift
281                 ;;
282     --incdir=*)
283                 incdir=`echo $1 | awk -F= '{print $2}'`
284                 CheckDir $incdir
285                 for dir in $incdir
286                 do
287                   INCDIR="$INCDIR -I$dir"; 
288                 done
289                 shift
290                 ;;
291     --no-build-shared|-nobs|--no-shared)
292                 BUILD_SHARED="-nobs"; shift
293                 ;;
294     --with-romio)
295                 WITH_ROMIO="true"; shift
296                 ;;
297     --build-shared|-bs)
298                 # obsolete, do nothing
299                 shift
300                 ;;
301     --destination)
302                 shift
303                 DESTINATION="$1"
304                 shift
305                 ;;
306     --destination=*)
307                 DESTINATION="`echo $1 | awk -F= '{print $2}'`"
308                 shift
309                 ;;
310     --suffix)
311                 shift
312                 DESTINATION_SUFFIX="$1"
313                 shift
314                 ;;
315     --suffix=*)
316                 DESTINATION_SUFFIX="`echo $1 | awk -F= '{print $2}'`"
317                 shift
318                 ;;
319     --tau-makefile)
320                 TAU_MAKEFILE=$1
321                 shift
322                 ;;
323     --tau-makefile=*)
324                 TAU_MAKEFILE=`echo $1 | awk -F= '{print $2}'`
325                 shift
326                 ;;
327     --quiet)
328                 MAKEOPTS="$MAKEOPTS --quiet"
329                 QUIET="--quiet"
330                 shift;
331                 ;;
332     -j*)
333                 PMAKENUM=`echo $1 | awk -Fj '{print $2}'`
334                 MAKEOPTS="$MAKEOPTS -j $PMAKENUM"
335                 shift;
336                 ;;
337     -*) 
338 # We hit a real compiler option (like -g, or -Dfoo),
339 # so just copy over all remaining options
340           while [ ! $# -eq 0 ]
341           do
342             OPTS="$OPTS $1"; shift
343           done
344           ;;
345     "help")
346         printOption
347         ;;
348     *)
349 # This has to be a build-time option (like "smp", "gcc3", or "kcc")
350         TestIfCompiler $1
351         if [ $? -eq 1 ] 
352         then
353 # It specifies a compiler:
354           if [ ! -z "$COMPILER" ] 
355           then
356               echo "Error> Tried to specify two compilers: $COMPILER and $1"
357               printOption
358           fi
359           COMPILER=$1
360         else
361 # It specifies some other option:
362           TestIfOption $1
363           BOPTS="$BOPTS $1"
364           [ $1 =  "bigemulator" ] && BUILD_EMULATOR=1
365         fi
366         shift
367         ;;
368   esac
369 done
370
371 [ "x$VERSION" = "x" ] && syntax && exit 1
372
373 if [ -z "$MAKE" ] 
374 then
375   # prefer gmake
376   MAKE=`which gmake 2>/dev/null`
377   [ -z "$MAKE" -o ! -x "$MAKE" ] && MAKE='make'
378 fi
379
380 if [ ! -f $src/$BASEVERSION/conv-mach.h ] 
381 then
382   if [ "x_$BASEVERSION" = "x_net-rs6k" ]
383   then
384     echo "Error> build net-aix-ppc instead of net-rs6k!" 
385   else
386     echo "Error> build can not find arch: $BASEVERSION!" 
387   fi
388   exit 1
389 fi
390
391 #generate VERSION name combining all the build-time options.
392 if [ -n "$BOPTS" -o -n "$COMPILER" ]
393 then
394   echo "Selected Compiler: $COMPILER"
395   echo "Selected Options: $BOPTS"
396   SORTED=`echo $BOPTS | awk  '{ for (i = 1; i <= NF; ++i) print $i }' | sort`
397   BOPTS_WITHCOMPILER=`echo $SORTED $COMPILER`
398   for i in $BOPTS_WITHCOMPILER
399   do
400     VERSION=$VERSION-$i
401   done
402 fi
403
404 #echo "|$DESTINATION|$DESTINATION_SUFFIX|"
405
406 if [ -z "$DESTINATION" ]
407 then
408   DESTINATION="$VERSION"
409 fi
410
411 if [ -n "$DESTINATION_SUFFIX" ]
412 then
413   DESTINATION="$DESTINATION-$DESTINATION_SUFFIX"
414 fi
415
416 [ -d $DESTINATION ] || Echo "Creating dir: $DESTINATION"
417 [ -d $DESTINATION ] || mkdir $DESTINATION
418 [ -d $DESTINATION/tmp ] || Echo "Creating dir: $DESTINATION/tmp"
419 [ -d $DESTINATION/tmp ] || mkdir $DESTINATION/tmp
420
421 Echo "Copying src/scripts/Makefile to $DESTINATION/tmp"
422 rm -f $DESTINATION/tmp/Makefile
423 rm -f $DESTINATION/tmp/Make.depends
424 rm -f $DESTINATION/tmp/Make.lb
425 rm -f $DESTINATION/tmp/Make.machine
426
427
428 # Create the bin, lib, include, etc. links:
429 WINNAME=`echo $VERSION | awk -F- '{print $2}'`
430 if [ "x_$WINNAME" = "x_win32" -o "x_$WINNAME" = "x_win64" ]
431 then
432 #Win32/64 version needs special compilers and *copied* (not linked)
433 # source files.
434         echo "Copying compilers for $WINNAME into cygwin /bin directory"
435         cp -f $src/$WINNAME/unix2nt* /bin
436         cp $src/win32/system_ln $DESTINATION/tmp
437         cp $src/win32/unistd.h $DESTINATION/tmp
438         echo "Compiling createlink.cpp ..."
439         (cd $src/win32; unix2nt_cc  -c createlink.cpp -o createlink.o -D_WIN32_WINNT=0x0500; unix2nt_cc createlink.o)
440         if test ! -x $src/win32/createlink.exe
441         then
442                 echo "VC++ is not properly installed!"
443                 exit 1
444         fi
445         echo "Copying $src/win32/createlink.exe to /bin directory"
446         cp $src/win32/createlink.exe /bin
447         chmod +x $DESTINATION/tmp/system_ln
448 else
449         cat > $DESTINATION/tmp/system_ln <<EOF
450 #!/bin/sh
451 ln -f -s \$@
452 EOF
453   chmod +x $DESTINATION/tmp/system_ln
454   for newdir in `echo bin lib lib_so include tmp`
455   do
456     Echo "Soft-linking over $newdir"
457     if [ -r $newdir ]
458     then
459       rm -fr $newdir || exit 1
460     fi
461     $DESTINATION/tmp/system_ln $DESTINATION/$newdir $newdir
462   done
463   rm -f VERSION
464   $DESTINATION/tmp/system_ln $DESTINATION/include/VERSION VERSION
465 fi
466
467 $DESTINATION/tmp/system_ln "../../src/scripts/Make.depends" $DESTINATION/tmp/Make.depends
468 $DESTINATION/tmp/system_ln "../../src/ck-ldb/Make.lb" $DESTINATION/tmp/Make.lb
469 $DESTINATION/tmp/system_ln "../../src/scripts/Makefile" $DESTINATION/tmp/Makefile
470 $DESTINATION/tmp/system_ln "../../src/scripts/Make.tau" $DESTINATION/tmp/Make.tau
471 touch $DESTINATION/tmp/Makefile.machine
472
473 ConvUsr="$DESTINATION/tmp/conv-mach-pre.sh"
474 Echo "Generating $ConvUsr"
475 echo > $ConvUsr
476 if test -n "$LIBDIR" 
477 then
478   echo 'USER_OPTS_LD="$USER_OPTS_LD '$LIBDIR'"' >> $ConvUsr
479   echo 'USER_OPTS_LDXX="$USER_OPTS_LDXX '$LIBDIR'"' >> $ConvUsr
480 fi
481 if test -n "$INCDIR" 
482 then
483   echo 'USER_OPTS_CC="$USER_OPTS_CC '$INCDIR'"' >> $ConvUsr
484   echo 'USER_OPTS_CXX="$USER_OPTS_CXX '$INCDIR'"' >> $ConvUsr
485 fi
486 chmod +x $ConvUsr
487
488 # Create conv-mach-opt headers with special build-time options
489 ConvHeader="$DESTINATION/tmp/conv-mach-opt.h"
490 ConvSh="$DESTINATION/tmp/conv-mach-opt.sh"
491 if [ ! -f $ConvSh -o ! -f $ConvHeader ]
492 then
493   Echo "Generating $ConvHeader, conv-mach-opt.sh"
494   echo '/* Build-time options header, automatically generated by charm/build*/'> $ConvHeader
495   echo '# Built-time options header, automatically generated by charm/build'> $ConvSh
496   echo '[ -z "$CHARMINC" ] && CHARMINC="."' >> $ConvSh
497 fi
498 if test -n "$COMPILER"
499 then
500       i="$COMPILER"
501       echo '#include "'cc-$i.h'"' >> $ConvHeader
502       echo '. $CHARMINC/'"cc-$i.sh" >> $ConvSh
503 fi
504 if test -n "$BOPTS"
505 then
506     for i in $BOPTS
507     do
508       echo '#include "'conv-mach-$i.h'"' >> $ConvHeader
509       echo '. $CHARMINC/'"conv-mach-$i.sh" >> $ConvSh
510     done
511 fi
512
513 if test  -n "$BUILD_SHARED" 
514 then
515     echo "CMK_NO_BUILD_SHARED=true" >> $ConvSh
516 fi
517
518 if test  -n "$WITH_ROMIO" 
519 then
520     echo "CMK_AMPI_WITH_ROMIO=\"true\"" >> $ConvSh
521 fi
522
523
524 # build with Tau
525 WITH_TAU=0
526 if [ "$PROGRAM" = "Tau" ]
527 then
528         Echo "TAU>>>> makefile config option: $TAU_MAKEFILE"
529         if [ -n "$TAU_MAKEFILE" -a -f $TAU_MAKEFILE ]
530         then
531           #Setting up TAU trace library:
532           Echo "TAU>>>> configuring with this TAU makefile: $TAU_MAKEFILE"
533
534           WITH_TAU=1
535         else
536           Echo "TAU>>>> ERROR could not find Makefile: $TAU_MAKEFILE, ignored"
537           TAU_MAKEFILE=""
538         fi
539 fi
540 [ -z "$TAU_MAKEFILE" ] && TAU_MAKEFILE="Make.tau"
541 SED_CHARMC="s@TAU_MAKEFILE=\(.*\)@TAU_MAKEFILE=$TAU_MAKEFILE@"
542
543 sed -e $SED_CHARMC src/scripts/Makefile > .Makefile.$$ && cp .Makefile.$$ src/scripts/Makefile && rm -f  .Makefile.$$
544 sed -e $SED_CHARMC src/scripts/charmc > .charmc.$$ && cp .charmc.$$ src/scripts/charmc && rm -f .charmc.$$
545
546 if test $WITH_TAU -eq 1
547 then
548     echo "#define CMK_WITH_TAU               1" >> $ConvHeader
549     echo "#define pthread_create             tau_pthread_create" >> $ConvHeader
550     echo "#define pthread_exit               tau_pthread_exit" >> $ConvHeader
551
552     echo "CMK_WITH_TAU=\"true\"" >> $ConvSh
553 fi
554
555
556 echo $BASEVERSION > $DESTINATION/tmp/.vdir
557 echo $VERSION | sed -e 's@-.*@@' > $DESTINATION/tmp/.gdir
558
559 if test $BUILD_EMULATOR = 1
560 then
561   PROGRAM="$PROGRAM bigsim"
562 fi
563
564 printError()
565 {
566         Echo "-------------------------------------------------"
567         Echo "Charm++ NOT BUILT. Either cd into $DESTINATION/tmp and try"
568         Echo "to resolve the problems yourself, visit"
569         Echo "    http://charm.cs.uiuc.edu/"
570         Echo "for more information. Otherwise, email the developers at charm@cs.uiuc.edu"
571         exit $MAKEEXIT
572 }
573
574 Echo "Performing '$MAKE $MAKEOPTS basics OPTS="$OPTS" QUIET="$QUIET"' in $VERSION/tmp"
575 cd $DESTINATION/tmp 
576 $MAKE $MAKEOPTS basics OPTS="$OPTS $BUILD_SHARED" QUIET="$QUIET"
577 MAKEEXIT=$?
578 [ $MAKEEXIT -ne 0 ] && printError
579
580 Echo "Performing '$MAKE $MAKEOPTS $PROGRAM OPTS="$OPTS" QUIET="$QUIET"' in $VERSION/tmp"
581 $MAKE $MAKEOPTS $PROGRAM OPTS="$OPTS $BUILD_SHARED" QUIET="$QUIET"
582 MAKEEXIT=$?
583 if [ $MAKEEXIT -eq 0 ]
584 then
585         Echo "-------------------------------------------------"
586         Echo "$PROGRAM built successfully."
587         Echo "Next, try out a sample program like" \
588              "tests/charm++/simplearrayhello"
589 else
590         printError
591 fi