?RCS: $Id$
?RCS:
?RCS: Copyright (c) 2001 Jarkko Hietaniemi
?RCS:
?RCS: You may distribute under the terms of either the GNU General Public
?RCS: License or the Artistic License, as specified in the README file.
?RCS:
?MAKE:run to from targetarch targetdir targetmkdir targethost targetport \
	usecrosscompile hostperl hostgenerate hostosname targetenv: \
	    src test rm echo sed mkdir cp chmod make touch
?MAKE:	-pick add $@ %<
?Y:TOP
?S:usecrosscompile:
?S:	This variable conditionally defines the USE_CROSS_COMPILE symbol,
?S:	and indicates that Perl has been cross-compiled.
?S:.
?S:run:
?S:	This variable contains the command used by Configure
?S:	to copy and execute a cross-compiled executable in the
?S:	target host.  Useful and available only during Perl build.
?S:	Empty string '' if not cross-compiling.
?S:.
?S:from:
?S:	This variable contains the command used by Configure
?S:	to copy files from the target host.  Useful and available
?S:	only during Perl build.
?S:	The string ':' if not cross-compiling.
?S:.
?S:to:
?S:	This variable contains the command used by Configure
?S:	to copy to from the target host.  Useful and available
?S:	only during Perl build.
?S:	The string ':' if not cross-compiling.
?S:.
?S:targetarch:
?S:	If cross-compiling, this variable contains the target architecture.
?S:	If not, this will be empty.
?S:.
?S:targetdir:
?S:	This variable contains a path that will be created on the target
?S:	host using targetmkdir, and then used to copy the cross-compiled
?S:	executables to. Defaults to '/tmp' if not set.
?S:.
?S:targetmkdir:
?S:	This variable contains the command used by Configure to create a
?S:	new directory on the target host.
?S:.
?S:targethost:
?S:	This variable contains the name of a separate host machine that
?S:	can be used to run compiled test programs and perl tests on.
?S:	Set to empty string if not in use.
?S:.
?S:targetport:
?S:	This variable contains the number of a network port to be used to
?S:	connect to the host in targethost, if unset defaults to 22 for ssh.
?S:.
?S:hostperl:
?S:	This variable contains the path to a miniperl binary that can be
?S:	run on the host OS when cross-compiling.  Useful and available only
?S:	during Perl build.
?S:	Empty string '' if not cross-compiling.
?S:.
?S:hostgenerate:
?S:	This variable contains the path to a generate_uudmap binary that
?S:	can be run on the host OS when cross-compiling.  Useful and
?S:	available only during Perl build.
?S:	Empty string '' if not cross-compiling.
?S:.
?S:hostosname:
?S:	This variable contains the original value of '$^O' for hostperl
?S:	when cross-compiling.  This is useful to pick the proper tools
?S:	when running build code in the host.
?S:	Empty string '' if not cross-compiling.
?S:.
?S:targetenv:
?S:	If cross-compiling, this variable can be used to modify the
?S:	environment on the target system.
?S:	However, how and where it's used, and even if it's used at all, is
?S:	entirely dependent on both the transport mechanism (targetrun) and
?S:	what the target system is.  Unless the relevant documentation says
?S:	otherwise, it is genereally not useful.
?S:.
?C:USE_CROSS_COMPILE:
?C:	This symbol, if defined, indicates that Perl is being cross-compiled.
?C:.
?C:PERL_TARGETARCH:
?C:	This symbol, if defined, indicates the target architecture
?C:	Perl has been cross-compiled to.  Undefined if not a cross-compile.
?C:.
?H:?%<:#ifndef USE_CROSS_COMPILE
?H:?%<:#$usecrosscompile	USE_CROSS_COMPILE	/**/
?H:?%<:#define	PERL_TARGETARCH	"$targetarch"	/**/
?H:?%<:#endif
?H:.
?D:targetenv=''
?D:targethost=''
?D:targetmkdir=''
?T:croak pwd exe f q cwd file xxx env
?LINT:extern usecrosscompile
?LINT:extern cc
?LINT:extern usrinc
?LINT:change ar
?LINT:change nm
?LINT:change ranlib
?LINT:change src
?LINT:extern targetenv
?LINT:extern targetport
?LINT:extern targetdir
?LINT:extern targetuser
?LINT:change targetuser
?LINT:extern targetrun
?LINT:extern targetfrom
?LINT:extern targetto
?LINT:change targetrun
?LINT:change targetfrom
?LINT:change targetto
?LINT:extern incpth
?LINT:extern libpth
?LINT:extern locincpth
?LINT:extern loclibpth
?LINT:change locincpth
?LINT:change loclibpth
?LINT:extern hostperl
?LINT:extern hostgenerate
?LINT:extern before_host
?LINT:change before_host
?LINT:extern hostosname
?LINT:extern multiarch
: Check for Cross-Compilation
?X: targethost and targetenv mainly set to allow ?S: documentation
?X:otherwise it could have been declared extern
if $test "X$targethost" = "X"; then
    targethost=""
fi
if $test "X$targetenv" = "X"; then
    targetenv=""
fi
case "$usecrosscompile" in
$define|true|[yY]*)
	$echo "Cross-compiling..."
	croak=''
	case "$cc" in
	*-gcc*|*-g++*) # A cross-compiling gcc, probably.
	    # arm-linux-androideabi-gcc  -> arm-linux-androideabi
	    # x86_64-w64-mingw32-gcc.exe -> x86_64-w64-mingw32
	    targetarch=`$echo $cc|$sed 's/-g[c\+][c\+].*$//'`
	    ar=`$echo $cc|$sed 's/-g[c\+][c\+]/-ar/'`
	    # leave out ld, choosing it is more complex
	    nm=`$echo $cc|$sed 's/-g[c\+][c\+]/-nm/'`
	    ranlib=`$echo $cc|$sed 's/-g[c\+][c\+]/-ranlib/'`
	    # We are in a weird spot. Just before us, some values
	    # were 'saved', to be restored after the hints are
	    # run.  This means that the changes we made to ar,
	    # nm and ranlib will get reverted.
	    # To avoid that, we hijack the saving mechanism and
	    # have it save our new values.
	    for file in ar nm ranlib; do
		eval xxx=\$$file
		eval $file=$xxx$_exe
		eval _$file=$xxx
	    done
	;;
	esac
	case "$targetarch" in
	'') echo "Targetarch not defined." >&4; croak=y ;;
	*)  echo "Using targetarch $targetarch." >&4 ;;
	esac
	case "$targethost" in
	'') echo "Targethost not defined." >&4; croak=n ;;
	*)  echo "Using targethost $targethost." >&4
	esac
	locincpth=' '
	loclibpth=' '
	case "$croak" in
	y) echo "Cannot continue, aborting." >&4; exit 1 ;;
	esac
    : compile a host miniperl and generate_uudmap, unless we got passed them
    if $test "X$hostperl" = X; then
      echo "Building host miniperl and generate_uudmap binaries" >&4
      before_host=`pwd`
      cd ..
      cd $src
      src=`pwd`
      rm -rf $src/host
      mkdir $src/host
      cd $src/host
      $src/Configure -des -Dusedevel -Dmksymlinks
      $make miniperl
      case "$hostgenerate" in
      '') $make generate_uudmap
          hostgenerate=$src/host/generate_uudmap
          ;;
       "$undef") hostgenerate=''
          ;;
      esac
      hostperl=$src/host/miniperl
      cd $before_host
    fi
    hostosname=`$hostperl -le 'print $^O'`
    ;;
*)
    usecrosscompile="$undef"
    ;;
esac

: Define -Dtargethost=somecomputer to run compiled tests on another machine
case "$targethost" in
    '') echo "Checking for cross-compile" >&4
    case "$usecrosscompile$multiarch" in
       *$define*) echo "Skipping the try tests in the rest of Configure as no targethost was defined when cross-compiling" >&4
         if [ -f Makefile ]; then
           echo " "
           echo "Now you must ensure config.sh, config.h and the generated headers exist and run a $make."
         else
           echo "Configure done."
         fi
       exit 0
       ;;
     *) echo "No targethost for running compiler tests against defined, running locally" >&4
        run=''
        to=:
        from=:
        ;;
    esac
    ;;
    *) echo "Using targethost $targethost." >&4
	case "$src" in
	/*) run=$src/Cross/run
	    targetmkdir=$src/Cross/mkdir
	    to=$src/Cross/to
	    from=$src/Cross/from
	    ;;
	*)  pwd=`$test -f ../Configure & cd ..; pwd`
	    run=$pwd/Cross/run
	    targetmkdir=$pwd/Cross/mkdir
	    to=$pwd/Cross/to
	    from=$pwd/Cross/from
	    ;;
	esac
	case "$targetrun" in
	'') targetrun=ssh ;;
	esac
	case "$targetto" in
	'') targetto=scp ;;
	esac
	case "$targetfrom" in
	'') targetfrom=scp ;;
	esac
	run=$run-$targetrun
	to=$to-$targetto
	from=$from-$targetfrom
	case "$targetdir" in
	'')  targetdir=/tmp
	     echo "Guessing targetdir $targetdir." >&4
	     ;;
	esac
	case "$targetuser" in
	'')  targetuser=root
	     echo "Guessing targetuser $targetuser." >&4
	     ;;
	esac
	case "$targetport" in
	'')  targetport=22
	     echo "Guessing targetport $targetport." >&4
	     ;;
	esac
	case "$targetfrom" in
	scp)	q=-q ;;
	*)	q='' ;;
	esac
	case "$targetrun" in
	ssh|rsh)
	    cat >$run <<EOF
#!/bin/sh
env=''
case "\$1" in
-cwd)
  shift
  cwd=\$1
  shift
  ;;
esac
case "\$1" in
-env)
  shift
  env=\$1
  shift
  ;;
esac
case "\$cwd" in
'') cwd=$targetdir ;;
esac
exe=\$1
shift
$to \$exe
$targetrun -p $targetport -l $targetuser $targethost "cd \$cwd && \$env \$exe \$@"
EOF
	    ;;
	adb)
	    $touch $run
	    ;;
	*)  echo "Unknown targetrun '$targetrun'" >&4
	    exit 1
	    ;;
	esac
	case "$targetmkdir" in
	*/Cross/mkdir)
	    cat >$targetmkdir <<EOF
#!/bin/sh
$targetrun -p $targetport -l $targetuser $targethost "mkdir -p \$@"
EOF
	    $chmod a+rx $targetmkdir
	    ;;
	*)  echo "Unknown targetmkdir '$targetmkdir'" >&4
	    exit 1
	    ;;
	esac
	case "$targetto" in
	scp|rcp)
	    cat >$to <<EOF
#!/bin/sh
for f in \$@
do
  case "\$f" in
  /*)
    $targetmkdir \`dirname \$f\`
    $targetto -P $targetport -r $q \$f $targetuser@$targethost:\$f           2>/dev/null  || exit 1
    ;;
  *)
    $targetmkdir $targetdir/\`dirname \$f\`
    $targetto -P $targetport -r $q \$f $targetuser@$targethost:$targetdir/\$f 2>/dev/null || exit 1
    ;;
  esac
done
exit 0
EOF
	    ;;
	cp) cat >$to <<EOF
#!/bin/sh
for f in \$@
do
  case "\$f" in
  /*)
    $mkdir -p $targetdir/\`dirname \$f\`
    $cp \$f $targetdir/\$f || exit 1
    ;;
  *)
    $targetmkdir $targetdir/\`dirname \$f\`
    $cp \$f $targetdir/\$f || exit 1
    ;;
  esac
done
exit 0
EOF
	    ;;
	*)  echo "Unknown targetto '$targetto'" >&4
	    exit 1
	    ;;
	esac
	case "$targetfrom" in
	scp|rcp)
	  cat >$from <<EOF
#!/bin/sh
for f in \$@
do
  $rm -f \$f
  $targetfrom -P $targetport $q $targetuser@$targethost:$targetdir/\$f . || exit 1
done
exit 0
EOF
	    ;;
	cp) cat >$from <<EOF
#!/bin/sh
for f in \$@
do
  $rm -f \$f
  cp $targetdir/\$f . || exit 1
done
exit 0
EOF
	    ;;
	*)  echo "Unknown targetfrom '$targetfrom'" >&4
	    exit 1
	    ;;
	esac
	if $test ! -f $run; then
	    echo "Target 'run' script '$run' not found." >&4
	else
	    $chmod a+rx $run
	fi
	if $test ! -f $to; then
	    echo "Target 'to' script '$to' not found." >&4
	else
	    $chmod a+rx $to
	fi
	if $test ! -f $from; then
	    echo "Target 'from' script '$from' not found." >&4
	else
	    $chmod a+rx $from
	fi
	if $test ! -f $run -o ! -f $to -o ! -f $from; then
	    exit 1
	fi
	cat >&4 <<EOF
Using '$run' for remote execution,
and '$from' and '$to'
for remote file transfer.
EOF
	;;
*)	run=''
	to=:
	from=:
	usecrosscompile="$undef"
	targetarch=''
	;;
esac

