<commit_before>#!/bin/sh
# LambdaNative - a cross-platform Scheme framework
# Copyright (c) 2009-2013, University of British Columbia
# All rights reserved.
#
# Redistribution and use in source and binary forms, with or
# without modification, are permitted provided that the
# following conditions are met:
#
# * Redistributions of source code must retain the above
# copyright notice, this list of conditions and the following
# disclaimer.
#
# * Redistributions in binary form must reproduce the above
# copyright notice, this list of conditions and the following
# disclaimer in the documentation and/or other materials
# provided with the distribution.
#
# * Neither the name of the University of British Columbia nor
# the names of its contributors may be used to endorse or
# promote products derived from this software without specific
# prior written permission.
#
# THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND
# CONTRIBUTORS "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES,
# INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF
# MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
# DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR
# CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
# SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
# NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
# LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
# HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
# CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR
# OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
# SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.

# application building, packaging and installation

. ./config.cache

. ./SETUP

evallog=`pwd`"/eval.log"

if [ -f $evallog ]; then
  rm $evallog
fi

#########################
# general functions

# since os x doesn't have md5sum
md5summer=md5sum
if [ "X"`which md5sum 2> /dev/null` = "X" ]; then
  md5summer="md5 -r"
fi

veval()
{
  if [ $SYS_VERBOSE ]; then 
    echo "$1"
    eval $1
  else 
    echo "$1" > $evallog
    eval $1 >> $evallog 2>&1
  fi
}

vecho()
{
  if [ $SYS_VERBOSE ]; then 
    echo "$1"
  fi
}

getparam()
{
  if [ "$1" = "1" ]; then echo "$2"; fi
  if [ "$1" = "2" ]; then echo "$3"; fi
  if [ "$1" = "3" ]; then echo "$4"; fi
  if [ "$1" = "4" ]; then echo "$5"; fi
  if [ "$1" = "5" ]; then echo "$6"; fi
}

rmifexists()
{
  if [ "$1" ]; then
    if [ -e "$1" ]; then
      vecho " => removing old $1.."
      rm -rf "$1"
    fi
  fi
}

###############################
# keep track of state to reset partial builds

statefile=`pwd`"/make.state"

setstate()
{
  echo "state=$1" > $statefile
}

resetstate()
{
  state=
  if [ -f $statefile ]; then
    . $statefile
    rm $statefile
  fi
  if [ ! "X$state" = "X" ]; then
    echo " ** WARNING: previous build aborted unexpectantly in state: $state"
    case $state in
      ARTWORK)
       file=`locatefile apps/$SYS_APPNAME/artwork.eps silent`
       if [ -f $file ]; then
         touch $file
       fi
      ;;
      STRINGS)
       file="$SYS_PREFIXROOT/build/$SYS_APPNAME/strings/strings_include.scm"
       rmifexists $file
       ;;
      FONTS)
       file="$SYS_PREFIXROOT/build/$SYS_APPNAME/fonts/fonts_include.scm"
       rmifexists $file
       ;;
      TEXTURES)
       file="$SYS_PREFIXROOT/build/$SYS_APPNAME/textures/textures_include.scm"
       rmifexists $file
       ;;
    esac
  fi
} 

#################################
# abort on missing files and errors

assertfile()
{
  if [ ! -s "$1" ]; then
    if [ -f $evallog ]; then
      cat $evallog | sed '/^$/d'
    fi
    echo "ERROR: failed on file $1" 1>&2
    if [ ! "X$2" = "X" ]; then 
      echo ">> $2"
    fi
    exit 1
  fi
}

asserterror()
{
  if [ ! $1 = 0 ]; then
    if [ -f $evallog ]; then
      cat $evallog | sed '/^$/d'
    fi
    echo "ERROR: failed with exit code $1" 1>&2
    if [ ! "X$2" = "X" ]; then 
      echo ">> $2"
    fi
    exit 1
  fi
}

asserttool()
{
  for tool in $@; do
    if [ "X"`which $tool 2> /dev/null` = "X" ]; then 
      echo "ERROR: required tool $tool not found." 
      echo "Please install a package containing this tool before proceeding."
      exit 1
    else 
      vecho "  => $tool.. ok" 
    fi
  done
}

#################################
# misc file and directory support

stringhash()
{
  echo "$1" | $md5summer | cut -f 1 -d " "
}

isnewer()
{
  result=no
  if [ ! -e "$2" ]; then
    result=yes
  else
    if `test "$1" -nt "$2"`; then
      result=yes
    fi
  fi
  echo $result
}

newersourceindir()
{
  result="no"
  tgt="$2"
  dir=`dirname $1`
  srcfiles=`ls -1 $dir/*.scm` 
  for src in $srcfiles; do
    if `test "$src" -nt "$tgt"`; then
      result="yes"
    fi
  done
  echo $result
}

newerindir()
{
  result="no"
  if [ ! -e "$2" ]; then
    result=yes
  else
    tgt="$2"
    if [ -d $1 ]; then
      dir=$1
    else
      dir=`dirname $1`
    fi
    srcfiles=`ls -1 $dir/*`
    for src in $srcfiles; do
      if `test "$src" -nt "$tgt"`; then
        result="yes"
      fi
    done
  fi
  echo $result
}

locatetest()
{
  here=`pwd`
  file=
  dirs=$(echo "$SYS_PATH" | tr ":" "\n")
  for dir in $dirs; do
    tmp="$dir/$2"
    if [ ! "X$tmp" = "X" ]; then
      if [ $1 $tmp ]; then
        if [ "X$file" = "X" ]; then
          file=$tmp
        else
          if [ ! "X$3" = "Xsilent" ]; then
             echo "WARNING: $file shadows $tmp" 1>&2
          fi
        fi
      fi
    fi 
  done
  if [ "X$file" = "X" ]; then
    if [ ! "X$3" = "Xsilent" ]; then
      echo "WARNING: [$2] not found" 1>&2
    fi
  fi
  if [ ! -e $file ]; then
    if [ ! "X$3" = "Xsilent" ]; then
      echo "WARNING: [$2] not found" 1>&2
    fi
  fi
  cd "$here"
  echo $file
}

locatedir()
{
  locatetest "-d" $@
}

locatefile()
{
  locatetest "-f" $@
}

wildcard_dir()
{
  find $1 -maxdepth 0 -print |sort -r| head -n 1
}

#################################
# autoconf-like parameter substitution

ac_sedsub=

ac_subst()
{
  newcmd="echo \"s|@${1}@|\$${1}|g;\""
  newsub=`eval $newcmd`
  ac_sedsub="${ac_sedsub}${newsub}"
}

ac_output()
{
  infile=`echo "${1}" | sed 's/\.in$//'`.in
  if [ "X$2" = "X" ]; then
    outfile=$1
  else 
    outfile=$2
  fi
  assertfile $infile
  cat $infile | sed "$ac_sedsub" > $outfile
  assertfile $outfile
}

#################################
# misc source code checks

has_module()
{
  res=no
  modfile=`locatefile apps/$SYS_APPNAME/MODULES`
  if [ -f "$modfile" ]; then
    if [ ! "X"`cat "$modfile" | grep "$1" | cut -c 1` = "X" ]; then
       res=yes
    fi
  fi 
  echo $res
}

is_gui_app()
{
  res=`has_module ln_glcore`
  if [ "$res" = "no" ]; then
    res=`has_module glcore`
  fi
  echo "$res"
}

is_standalone_app()
{
  neg=`has_module eventloop`
  if [ $neg = no ]; then
    neg=yes
  else
    neg=no
  fi
  echo $neg
}

###########################
# general compiler functions

compile()
{
  if [ $SYS_MODE = "debug" ]; then
    opts="(declare (block)(not safe)(debug)(debug-location))"
    optc="-g -Wall -Wno-unused-variable -Wno-unused-label -Wno-unused-parameter"
  else 
    opts="(declare (block)(not safe))"
    optc="-O2 -Wall -Wno-unused-variable -Wno-unused-label -Wno-unused-parameter"
  fi
  src="$1"
  ctgt="$2"
  otgt="$3"
  defs="$4"
  path=`dirname $src`
  here=`pwd`
  cd $path
  rmifexists "$ctgt"
  echo " => $src.." 
  veval "$SYS_GSC -prelude \"$opts\" -c -o $ctgt $src"
  assertfile "$ctgt"
  rmifexists "$otgt"
  veval "$SYS_ENV $SYS_CC $SYS_CPPFLAGS $SYS_CFLAGS $defs -c -o $otgt $ctgt -I$SYS_PREFIX/include"
  assertfile "$otgt"
  cd $here
}

compile_payload()
{
  name=$1
  srcs="$2"
  csrcs=
  libs="$3"
  objs=
  defs="-D___SINGLE_HOST -D___LIBRARY -D___PRIMAL"
  echo "==> creating payload needed for $name.."
  mkdir -p "$SYS_PREFIX/build"
  dirty=
  for src in $srcs; do
    chsh=`stringhash "$src"`
    ctgt="$SYS_PREFIX/build/$chsh.c"
    csrcs="$csrcs $ctgt"
    otgt=`echo "$ctgt" | sed 's/c$/o/'`
    objs="$objs $otgt"
    flag=
    if [ ! -f "$otgt" ]; then
      flag=yes
    else 
      if [ `newersourceindir "$src" "$otgt"` = "yes" ]; then
        flag=yes
      fi
    fi
    if [ $flag ]; then
      dirty=yes
      compile "$src" "$ctgt" "$otgt" "$defs"
    fi
  done
  lctgt=`echo "$ctgt" | sed 's/\.c$/\_\.c/'`
  lotgt=`echo "$lctgt" | sed 's/c$/o/'`
  if [ ! -f "$lotgt" ]; then
    dirty=yes
  fi
  if [ $dirty ]; then
    echo " => creating gsc link.."
    vecho "$SYS_GSC -link $csrcs"
    $SYS_GSC -link $csrcs 
    assertfile $lctgt
    veval "$SYS_ENV $SYS_CC $SYS_CPPFLAGS $SYS_CFLAGS $defs -o $lotgt -c $lctgt -I$SYS_PREFIX/include"
    assertfile $lotgt
  fi
  objs="$objs $lotgt"
  hookhash=`stringhash "apps/$SYS_APPNAME/hook.c"`
  hctgt="$SYS_PREFIX/build/$hookhash.c"
  hotgt=`echo "$hctgt" | sed 's/c$/o/'`
  if [ ! -f "$hotgt" ]; then
    dirty=yes
  fi
  if [ $dirty ]; then
    echo " => generating hook.."
    linker=`echo $chsh"__"`
cat > $hctgt  << _EOF
// automatically generated. Do not edit.
#include <stdlib.h>
#include <CONFIG.h>
#define ___VERSION 407000
#include <gambit.h>
#define LINKER ____20_$linker
___BEGIN_C_LINKAGE
extern ___mod_or_lnk LINKER (___global_state_struct*);
___END_C_LINKAGE
___setup_params_struct setup_params;
int debug_settings = ___DEBUG_SETTINGS_INITIAL;
#ifdef STANDALONE
char *cmd_arg0=0;
char *cmd_arg1=0;
int main(int argc, char *argv[])
{
  cmd_arg0=argv[0];
  if (argc>1) cmd_arg1=argv[1];
  ___setup_params_reset (&setup_params);
  setup_params.version = ___VERSION;
  setup_params.linker = LINKER;
  debug_settings = (debug_settings & ~___DEBUG_SETTINGS_REPL_MASK) | 
  (___DEBUG_SETTINGS_REPL_STDIO << ___DEBUG_SETTINGS_REPL_SHIFT);
  setup_params.debug_settings = debug_settings;
  ___setup(&setup_params);
  ___cleanup();
  return 0;
}
#else 
void ffi_event(int t, int x, int y)
{
  static int lock=0;
  static int gambitneedsinit=1;
  if (lock) { return; } else { lock=1; }
  if (gambitneedsinit) {
      ___setup_params_reset (&setup_params);
      setup_params.version = ___VERSION;
      setup_params.linker = LINKER;
      debug_settings = (debug_settings & ~___DEBUG_SETTINGS_REPL_MASK) | 
        (___DEBUG_SETTINGS_REPL_STDIO << ___DEBUG_SETTINGS_REPL_SHIFT);
      setup_params.debug_settings = debug_settings;
      ___setup(&setup_params);
      gambitneedsinit=0;
  }
  if (!gambitneedsinit) scm_event(t,x,y);
  if (t==EVENT_TERMINATE) { ___cleanup(); exit(0); }
  lock=0;
}
#endif
_EOF
    if [ `is_standalone_app` = "yes" ]; then
      defs="$defs -DSTANDALONE"
    fi
    veval "$SYS_ENV $SYS_CC $SYS_CPPFLAGS $SYS_CFLAGS $defs -c -o $hotgt $hctgt -I$SYS_PREFIX/include"
    assertfile $hotgt
  fi
  objs="$objs $hotgt"
  for lib in $libs; do
   objs=`ls -1 $SYS_PREFIX/build/$lib/*.o`" $objs"
  done
  tgtlib="$SYS_PREFIX/lib/libpayload.a"
  echo " => assembling payload.."
  sobjs=
  for obj in $objs; do
    sobjs="$sobjs $obj"
  done
  rmifexists "$tgtlib"
  vecho "$SYS_AR rc $tgtlib $sobjs"
  $SYS_AR rc $tgtlib $sobjs  2> /dev/null
  vecho "$SYS_RANLIB $tgtlib"
  $SYS_RANLIB $tgtlib 2> /dev/null
  assertfile "$tgtlib"
}

##################################
# extract object files from static library

explode_library()
{
  libname=$1
  libfile="$SYS_PREFIX/lib/$libname.a"
  libdir="$SYS_PREFIX/build/$libname"
  assertfile $libfile
  if [ `isnewer $libfile $libdir` = "yes" ]; then
    rmifexists "$libdir"
    echo " => exploding library $libname.."
    mkdir -p "$libdir"
    here=`pwd`
    cd "$libdir"
    $SYS_AR -x $libfile
    cd "$here"
  fi
}

###################################
# artwork & texture generation

make_artwork()
{
  setstate ARTWORK
  echo "==> creating artwork needed for $SYS_APPNAME.."
  objsrc=`locatefile "apps/$SYS_APPNAME/artwork.obj" silent`
  epssrc=`locatefile "apps/$SYS_APPNAME/artwork.eps" silent`
  if [ "X$epssrc" = "X" ]; then
    assertfile $objsrc
    epssrc=`echo $objsrc | sed 's/obj$/eps/'`
  fi
  if [ `isnewer $objsrc $epssrc` = "yes" ]; then
    if [ ! "X$objsrc" = "X" ]; then
      assertfile $objsrc
      echo " => generating eps artwork.."
      tgif -print -stdout -eps -color $objsrc > $epssrc
    fi
  fi
  assertfile $epssrc
  mkdir -p "$SYS_PREFIX/build"
  mkdir -p "$SYS_PREFIXROOT/build/$SYS_APPNAME"
  pngsrc="$SYS_PREFIXROOT/build/$SYS_APPNAME/artwork.png"
  tmpfile="$SYS_PREFIXROOT/build/$SYS_APPNAME/tmp.png"
  if [ `isnewer $epssrc $pngsrc` = "yes" ]; then
    echo " => generating master pixmap.."
    veval "gs -r600 -dNOPAUSE -sDEVICE=png16m -dEPSCrop -sOutputFile=$tmpfile $epssrc quit.ps"
    assertfile $tmpfile
    veval "convert $tmpfile -trim -transparent \"#00ff00\" $pngsrc"
    rm $tmpfile
  fi
  assertfile $pngsrc
# the crazy list of artwork sizes:
# 1024: iTunes
# 512:  google play
# 144: 	retina ipad
# 128:  macosx
# 114: 	retina iphone
# 96:  	Retina iPad spotlight, android launcher
# 72:   ipad, android launcher
# 58:	iphone 4 settings
# 57:   iphone
# 48:   iPad Spotlight, android launcher, macosx
# 36:   android launcher
# 32:   macosx
# 29: 	iphone settings
# 16:   macosx
  sizes="1024 512 144 128 114 96 72 58 57 48 36 32 29 16"
  for s in $sizes; do
    tgt="$SYS_PREFIXROOT/build/$SYS_APPNAME/artwork-$s.png"
    if [ `isnewer $epssrc $tgt` = "yes" ]; then
      echo " => generating "$s"x"$s" pixmap.."
      convert $pngsrc -resize $s"x"$s $tgt
      assertfile $tgt
    fi
  done
  # create a dummy splash image to get full screen on retina displays
  tgt="$SYS_PREFIXROOT/build/$SYS_APPNAME/retina.png"
  if [ ! -f "$tgt" ]; then
    echo " => generating retina default image.."
    convert -size 640x1136 xc:black $tgt
  fi
  assertfile $tgt
  setstate
}

make_textures()
{
  setstate TEXTURES
  echo "==> creating textures needed for $SYS_APPNAME.."
  srcdir=`locatedir apps/$SYS_APPNAME/textures silent`
  if [ "X" == "X$srcdir" ]; then 
    return 
  fi
  tgtdir=$SYS_PREFIXROOT/build/$SYS_APPNAME/textures
  mkdir -p $tgtdir
  incfile=$tgtdir/textures_include.scm
  images=`ls -1 "$srcdir"/*.png 2> /dev/null`
  dirty="no"
  empty=yes
  for imgfile in $images; do
    empty=no
    if [ `isnewer $imgfile $incfile` = "yes" ]; then
      dirty="yes" <commit_msg>make.sh  String comparison in make_textures had wrong operator.<commit_after>#!/bin/sh
# LambdaNative - a cross-platform Scheme framework
# Copyright (c) 2009-2013, University of British Columbia
# All rights reserved.
#
# Redistribution and use in source and binary forms, with or
# without modification, are permitted provided that the
# following conditions are met:
#
# * Redistributions of source code must retain the above
# copyright notice, this list of conditions and the following
# disclaimer.
#
# * Redistributions in binary form must reproduce the above
# copyright notice, this list of conditions and the following
# disclaimer in the documentation and/or other materials
# provided with the distribution.
#
# * Neither the name of the University of British Columbia nor
# the names of its contributors may be used to endorse or
# promote products derived from this software without specific
# prior written permission.
#
# THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND
# CONTRIBUTORS "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES,
# INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF
# MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
# DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR
# CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
# SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
# NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
# LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
# HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
# CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR
# OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
# SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.

# application building, packaging and installation

. ./config.cache

. ./SETUP

evallog=`pwd`"/eval.log"

if [ -f $evallog ]; then
  rm $evallog
fi

#########################
# general functions

# since os x doesn't have md5sum
md5summer=md5sum
if [ "X"`which md5sum 2> /dev/null` = "X" ]; then
  md5summer="md5 -r"
fi

veval()
{
  if [ $SYS_VERBOSE ]; then 
    echo "$1"
    eval $1
  else 
    echo "$1" > $evallog
    eval $1 >> $evallog 2>&1
  fi
}

vecho()
{
  if [ $SYS_VERBOSE ]; then 
    echo "$1"
  fi
}

getparam()
{
  if [ "$1" = "1" ]; then echo "$2"; fi
  if [ "$1" = "2" ]; then echo "$3"; fi
  if [ "$1" = "3" ]; then echo "$4"; fi
  if [ "$1" = "4" ]; then echo "$5"; fi
  if [ "$1" = "5" ]; then echo "$6"; fi
}

rmifexists()
{
  if [ "$1" ]; then
    if [ -e "$1" ]; then
      vecho " => removing old $1.."
      rm -rf "$1"
    fi
  fi
}

###############################
# keep track of state to reset partial builds

statefile=`pwd`"/make.state"

setstate()
{
  echo "state=$1" > $statefile
}

resetstate()
{
  state=
  if [ -f $statefile ]; then
    . $statefile
    rm $statefile
  fi
  if [ ! "X$state" = "X" ]; then
    echo " ** WARNING: previous build aborted unexpectantly in state: $state"
    case $state in
      ARTWORK)
       file=`locatefile apps/$SYS_APPNAME/artwork.eps silent`
       if [ -f $file ]; then
         touch $file
       fi
      ;;
      STRINGS)
       file="$SYS_PREFIXROOT/build/$SYS_APPNAME/strings/strings_include.scm"
       rmifexists $file
       ;;
      FONTS)
       file="$SYS_PREFIXROOT/build/$SYS_APPNAME/fonts/fonts_include.scm"
       rmifexists $file
       ;;
      TEXTURES)
       file="$SYS_PREFIXROOT/build/$SYS_APPNAME/textures/textures_include.scm"
       rmifexists $file
       ;;
    esac
  fi
} 

#################################
# abort on missing files and errors

assertfile()
{
  if [ ! -s "$1" ]; then
    if [ -f $evallog ]; then
      cat $evallog | sed '/^$/d'
    fi
    echo "ERROR: failed on file $1" 1>&2
    if [ ! "X$2" = "X" ]; then 
      echo ">> $2"
    fi
    exit 1
  fi
}

asserterror()
{
  if [ ! $1 = 0 ]; then
    if [ -f $evallog ]; then
      cat $evallog | sed '/^$/d'
    fi
    echo "ERROR: failed with exit code $1" 1>&2
    if [ ! "X$2" = "X" ]; then 
      echo ">> $2"
    fi
    exit 1
  fi
}

asserttool()
{
  for tool in $@; do
    if [ "X"`which $tool 2> /dev/null` = "X" ]; then 
      echo "ERROR: required tool $tool not found." 
      echo "Please install a package containing this tool before proceeding."
      exit 1
    else 
      vecho "  => $tool.. ok" 
    fi
  done
}

#################################
# misc file and directory support

stringhash()
{
  echo "$1" | $md5summer | cut -f 1 -d " "
}

isnewer()
{
  result=no
  if [ ! -e "$2" ]; then
    result=yes
  else
    if `test "$1" -nt "$2"`; then
      result=yes
    fi
  fi
  echo $result
}

newersourceindir()
{
  result="no"
  tgt="$2"
  dir=`dirname $1`
  srcfiles=`ls -1 $dir/*.scm` 
  for src in $srcfiles; do
    if `test "$src" -nt "$tgt"`; then
      result="yes"
    fi
  done
  echo $result
}

newerindir()
{
  result="no"
  if [ ! -e "$2" ]; then
    result=yes
  else
    tgt="$2"
    if [ -d $1 ]; then
      dir=$1
    else
      dir=`dirname $1`
    fi
    srcfiles=`ls -1 $dir/*`
    for src in $srcfiles; do
      if `test "$src" -nt "$tgt"`; then
        result="yes"
      fi
    done
  fi
  echo $result
}

locatetest()
{
  here=`pwd`
  file=
  dirs=$(echo "$SYS_PATH" | tr ":" "\n")
  for dir in $dirs; do
    tmp="$dir/$2"
    if [ ! "X$tmp" = "X" ]; then
      if [ $1 $tmp ]; then
        if [ "X$file" = "X" ]; then
          file=$tmp
        else
          if [ ! "X$3" = "Xsilent" ]; then
             echo "WARNING: $file shadows $tmp" 1>&2
          fi
        fi
      fi
    fi 
  done
  if [ "X$file" = "X" ]; then
    if [ ! "X$3" = "Xsilent" ]; then
      echo "WARNING: [$2] not found" 1>&2
    fi
  fi
  if [ ! -e $file ]; then
    if [ ! "X$3" = "Xsilent" ]; then
      echo "WARNING: [$2] not found" 1>&2
    fi
  fi
  cd "$here"
  echo $file
}

locatedir()
{
  locatetest "-d" $@
}

locatefile()
{
  locatetest "-f" $@
}

wildcard_dir()
{
  find $1 -maxdepth 0 -print |sort -r| head -n 1
}

#################################
# autoconf-like parameter substitution

ac_sedsub=

ac_subst()
{
  newcmd="echo \"s|@${1}@|\$${1}|g;\""
  newsub=`eval $newcmd`
  ac_sedsub="${ac_sedsub}${newsub}"
}

ac_output()
{
  infile=`echo "${1}" | sed 's/\.in$//'`.in
  if [ "X$2" = "X" ]; then
    outfile=$1
  else 
    outfile=$2
  fi
  assertfile $infile
  cat $infile | sed "$ac_sedsub" > $outfile
  assertfile $outfile
}

#################################
# misc source code checks

has_module()
{
  res=no
  modfile=`locatefile apps/$SYS_APPNAME/MODULES`
  if [ -f "$modfile" ]; then
    if [ ! "X"`cat "$modfile" | grep "$1" | cut -c 1` = "X" ]; then
       res=yes
    fi
  fi 
  echo $res
}

is_gui_app()
{
  res=`has_module ln_glcore`
  if [ "$res" = "no" ]; then
    res=`has_module glcore`
  fi
  echo "$res"
}

is_standalone_app()
{
  neg=`has_module eventloop`
  if [ $neg = no ]; then
    neg=yes
  else
    neg=no
  fi
  echo $neg
}

###########################
# general compiler functions

compile()
{
  if [ $SYS_MODE = "debug" ]; then
    opts="(declare (block)(not safe)(debug)(debug-location))"
    optc="-g -Wall -Wno-unused-variable -Wno-unused-label -Wno-unused-parameter"
  else 
    opts="(declare (block)(not safe))"
    optc="-O2 -Wall -Wno-unused-variable -Wno-unused-label -Wno-unused-parameter"
  fi
  src="$1"
  ctgt="$2"
  otgt="$3"
  defs="$4"
  path=`dirname $src`
  here=`pwd`
  cd $path
  rmifexists "$ctgt"
  echo " => $src.." 
  veval "$SYS_GSC -prelude \"$opts\" -c -o $ctgt $src"
  assertfile "$ctgt"
  rmifexists "$otgt"
  veval "$SYS_ENV $SYS_CC $SYS_CPPFLAGS $SYS_CFLAGS $defs -c -o $otgt $ctgt -I$SYS_PREFIX/include"
  assertfile "$otgt"
  cd $here
}

compile_payload()
{
  name=$1
  srcs="$2"
  csrcs=
  libs="$3"
  objs=
  defs="-D___SINGLE_HOST -D___LIBRARY -D___PRIMAL"
  echo "==> creating payload needed for $name.."
  mkdir -p "$SYS_PREFIX/build"
  dirty=
  for src in $srcs; do
    chsh=`stringhash "$src"`
    ctgt="$SYS_PREFIX/build/$chsh.c"
    csrcs="$csrcs $ctgt"
    otgt=`echo "$ctgt" | sed 's/c$/o/'`
    objs="$objs $otgt"
    flag=
    if [ ! -f "$otgt" ]; then
      flag=yes
    else 
      if [ `newersourceindir "$src" "$otgt"` = "yes" ]; then
        flag=yes
      fi
    fi
    if [ $flag ]; then
      dirty=yes
      compile "$src" "$ctgt" "$otgt" "$defs"
    fi
  done
  lctgt=`echo "$ctgt" | sed 's/\.c$/\_\.c/'`
  lotgt=`echo "$lctgt" | sed 's/c$/o/'`
  if [ ! -f "$lotgt" ]; then
    dirty=yes
  fi
  if [ $dirty ]; then
    echo " => creating gsc link.."
    vecho "$SYS_GSC -link $csrcs"
    $SYS_GSC -link $csrcs 
    assertfile $lctgt
    veval "$SYS_ENV $SYS_CC $SYS_CPPFLAGS $SYS_CFLAGS $defs -o $lotgt -c $lctgt -I$SYS_PREFIX/include"
    assertfile $lotgt
  fi
  objs="$objs $lotgt"
  hookhash=`stringhash "apps/$SYS_APPNAME/hook.c"`
  hctgt="$SYS_PREFIX/build/$hookhash.c"
  hotgt=`echo "$hctgt" | sed 's/c$/o/'`
  if [ ! -f "$hotgt" ]; then
    dirty=yes
  fi
  if [ $dirty ]; then
    echo " => generating hook.."
    linker=`echo $chsh"__"`
cat > $hctgt  << _EOF
// automatically generated. Do not edit.
#include <stdlib.h>
#include <CONFIG.h>
#define ___VERSION 407000
#include <gambit.h>
#define LINKER ____20_$linker
___BEGIN_C_LINKAGE
extern ___mod_or_lnk LINKER (___global_state_struct*);
___END_C_LINKAGE
___setup_params_struct setup_params;
int debug_settings = ___DEBUG_SETTINGS_INITIAL;
#ifdef STANDALONE
char *cmd_arg0=0;
char *cmd_arg1=0;
int main(int argc, char *argv[])
{
  cmd_arg0=argv[0];
  if (argc>1) cmd_arg1=argv[1];
  ___setup_params_reset (&setup_params);
  setup_params.version = ___VERSION;
  setup_params.linker = LINKER;
  debug_settings = (debug_settings & ~___DEBUG_SETTINGS_REPL_MASK) | 
  (___DEBUG_SETTINGS_REPL_STDIO << ___DEBUG_SETTINGS_REPL_SHIFT);
  setup_params.debug_settings = debug_settings;
  ___setup(&setup_params);
  ___cleanup();
  return 0;
}
#else 
void ffi_event(int t, int x, int y)
{
  static int lock=0;
  static int gambitneedsinit=1;
  if (lock) { return; } else { lock=1; }
  if (gambitneedsinit) {
      ___setup_params_reset (&setup_params);
      setup_params.version = ___VERSION;
      setup_params.linker = LINKER;
      debug_settings = (debug_settings & ~___DEBUG_SETTINGS_REPL_MASK) | 
        (___DEBUG_SETTINGS_REPL_STDIO << ___DEBUG_SETTINGS_REPL_SHIFT);
      setup_params.debug_settings = debug_settings;
      ___setup(&setup_params);
      gambitneedsinit=0;
  }
  if (!gambitneedsinit) scm_event(t,x,y);
  if (t==EVENT_TERMINATE) { ___cleanup(); exit(0); }
  lock=0;
}
#endif
_EOF
    if [ `is_standalone_app` = "yes" ]; then
      defs="$defs -DSTANDALONE"
    fi
    veval "$SYS_ENV $SYS_CC $SYS_CPPFLAGS $SYS_CFLAGS $defs -c -o $hotgt $hctgt -I$SYS_PREFIX/include"
    assertfile $hotgt
  fi
  objs="$objs $hotgt"
  for lib in $libs; do
   objs=`ls -1 $SYS_PREFIX/build/$lib/*.o`" $objs"
  done
  tgtlib="$SYS_PREFIX/lib/libpayload.a"
  echo " => assembling payload.."
  sobjs=
  for obj in $objs; do
    sobjs="$sobjs $obj"
  done
  rmifexists "$tgtlib"
  vecho "$SYS_AR rc $tgtlib $sobjs"
  $SYS_AR rc $tgtlib $sobjs  2> /dev/null
  vecho "$SYS_RANLIB $tgtlib"
  $SYS_RANLIB $tgtlib 2> /dev/null
  assertfile "$tgtlib"
}

##################################
# extract object files from static library

explode_library()
{
  libname=$1
  libfile="$SYS_PREFIX/lib/$libname.a"
  libdir="$SYS_PREFIX/build/$libname"
  assertfile $libfile
  if [ `isnewer $libfile $libdir` = "yes" ]; then
    rmifexists "$libdir"
    echo " => exploding library $libname.."
    mkdir -p "$libdir"
    here=`pwd`
    cd "$libdir"
    $SYS_AR -x $libfile
    cd "$here"
  fi
}

###################################
# artwork & texture generation

make_artwork()
{
  setstate ARTWORK
  echo "==> creating artwork needed for $SYS_APPNAME.."
  objsrc=`locatefile "apps/$SYS_APPNAME/artwork.obj" silent`
  epssrc=`locatefile "apps/$SYS_APPNAME/artwork.eps" silent`
  if [ "X$epssrc" = "X" ]; then
    assertfile $objsrc
    epssrc=`echo $objsrc | sed 's/obj$/eps/'`
  fi
  if [ `isnewer $objsrc $epssrc` = "yes" ]; then
    if [ ! "X$objsrc" = "X" ]; then
      assertfile $objsrc
      echo " => generating eps artwork.."
      tgif -print -stdout -eps -color $objsrc > $epssrc
    fi
  fi
  assertfile $epssrc
  mkdir -p "$SYS_PREFIX/build"
  mkdir -p "$SYS_PREFIXROOT/build/$SYS_APPNAME"
  pngsrc="$SYS_PREFIXROOT/build/$SYS_APPNAME/artwork.png"
  tmpfile="$SYS_PREFIXROOT/build/$SYS_APPNAME/tmp.png"
  if [ `isnewer $epssrc $pngsrc` = "yes" ]; then
    echo " => generating master pixmap.."
    veval "gs -r600 -dNOPAUSE -sDEVICE=png16m -dEPSCrop -sOutputFile=$tmpfile $epssrc quit.ps"
    assertfile $tmpfile
    veval "convert $tmpfile -trim -transparent \"#00ff00\" $pngsrc"
    rm $tmpfile
  fi
  assertfile $pngsrc
# the crazy list of artwork sizes:
# 1024: iTunes
# 512:  google play
# 144: 	retina ipad
# 128:  macosx
# 114: 	retina iphone
# 96:  	Retina iPad spotlight, android launcher
# 72:   ipad, android launcher
# 58:	iphone 4 settings
# 57:   iphone
# 48:   iPad Spotlight, android launcher, macosx
# 36:   android launcher
# 32:   macosx
# 29: 	iphone settings
# 16:   macosx
  sizes="1024 512 144 128 114 96 72 58 57 48 36 32 29 16"
  for s in $sizes; do
    tgt="$SYS_PREFIXROOT/build/$SYS_APPNAME/artwork-$s.png"
    if [ `isnewer $epssrc $tgt` = "yes" ]; then
      echo " => generating "$s"x"$s" pixmap.."
      convert $pngsrc -resize $s"x"$s $tgt
      assertfile $tgt
    fi
  done
  # create a dummy splash image to get full screen on retina displays
  tgt="$SYS_PREFIXROOT/build/$SYS_APPNAME/retina.png"
  if [ ! -f "$tgt" ]; then
    echo " => generating retina default image.."
    convert -size 640x1136 xc:black $tgt
  fi
  assertfile $tgt
  setstate
}

make_textures()
{
  setstate TEXTURES
  echo "==> creating textures needed for $SYS_APPNAME.."
  srcdir=`locatedir apps/$SYS_APPNAME/textures silent`
  if [ "X" = "X$srcdir" ]; then 
    return 
  fi
  tgtdir=$SYS_PREFIXROOT/build/$SYS_APPNAME/textures
  mkdir -p $tgtdir
  incfile=$tgtdir/textures_include.scm
  images=`ls -1 "$srcdir"/*.png 2> /dev/null`
  dirty="no"
  empty=yes
  for imgfile in $images; do
    empty=no
    if [ `isnewer $imgfile $incfile` = "yes" ]; then
      dirty="yes" 
{'fraction_non_alphanumeric': 0.16125836016844192, 'fraction_numerical': 0.015641034714604197, 'mean_word_length': 3.01249467556439, 'pattern_counts': {'":': 2, '<': 21, '<?xml version=': 0, '>': 83, 'https://': 0, 'lorem ipsum': 0, 'www.': 0, 'xml': 0}, 'pii_count': 0, 'substrings_counts': 0, 'word_list_counts': {'cursed_substrings.json': 0, 'profanity_word_list.json': 0, 'sexual_word_list.json': 0, 'zh_pornsignals.json': 0}}
{'dir': 'git-commits-cleaned', 'id': '7157624', 'n_tokens_mistral': 11095, 'n_tokens_neox': 10540, 'n_words': 2915}