*BSD News Article 23099


Return to BSD News archive

Xref: sserve comp.os.386bsd.development:1349 comp.os.386bsd.misc:1340
Path: sserve!newshost.anu.edu.au!munnari.oz.au!constellation!osuunx.ucc.okstate.edu!moe.ksu.ksu.edu!vixen.cso.uiuc.edu!howland.reston.ans.net!pipex!uknet!mcsun!Germany.EU.net!sunmbx.netmbx.de!mailgzrz.TU-Berlin.DE!cs.tu-berlin.de!wosch
From: wosch@cs.tu-berlin.de (Wolfram Schneider)
Newsgroups: comp.os.386bsd.development,comp.os.386bsd.misc
Subject: fastclean - fast kernel recompile
Followup-To: comp.os.386bsd.misc
Date: 31 Oct 1993 21:35:04 GMT
Organization: Technische Universitaet Berlin, Deutschland
Lines: 181
Message-ID: <2b1b2b$fik@news.cs.tu-berlin.de>
NNTP-Posting-Host: ole.cs.tu-berlin.de
Mime-Version: 1.0
Content-Type: text/plain; charset=ISO-8859-1
Content-Transfer-Encoding: 8bit


----------------------------------------------------------------------
#!/bin/sh
#
# Author: Wolfram Schneider <wosch@cs.tu-berlin.de>
#
#
# This script minimizes the time to recompile the kernel.
#
# Normaly you do: 
#    edit options in file FOO
#    config FOO
#    cd /sys/compile/FOO
#    make depend
#    make clean (or make link)
#    make
# make clean delete *all* object Files. 
#
# fastclean delete only files, which have new cpp(1) macros
# To do now:
#    edit options in file FOO
#    config FOO
#    cd /sys/compile/FOO
#    make depend
#    fastclean      <==
#    make
#
#
# BUGS: 
# 	- do not interrupt fastclean. 
#	- you must run fastclean *befor* you compile the kernel
#	- first you must built a whole kernel (with fastclean) 
#	- fastclean is slowly like 'make depend' (2-3 min on my machine)
#	- many files are depended from machine/*.h and ../../sys/*.h
#	  and the macros in this header files (see at end of script)
#	- my English is bad
#	- ????
#
# FEATURES:
#	- kernel recompile is 3-6 x faster than build the whole kernel :-))
#


tmp=/tmp/depend$$
dependdir=FASTCLEAN
dependfile=.depend
define=$dependdir/MACRO
sensitivity=$dependdir/SENSITIVITY
depence=$dependdir/DEPENCE

trap 'rm -f ${tmp}* $define; exit 0' 1 2 3 5 10 15
trap 'rm -f ${tmp}* exit 0' 0

usage='
echo "usage: fastclean [-c|clean] [-e|extraclean]" >&2
exit 1
'

case "$1" in 
	clean|-c*) rm -f $define; exit 0;; 
	extraclean|-e*) rm -rf $dependdir; exit 0;; 
	"");;
	*) eval "$usage";;
esac

case "`pwd`" in
  */sys/compile/*/$dependdir) echo "Please do 'cd ..'"; exit 2;;
  */sys/compile/*) ;;
  *) echo "You are not in /sys/compile/<KERNEL_CONFIG>"
     exit 1
  ;;
esac

if [ -d $dependdir ]; then :
else
  if  mkdir $dependdir; then :
  else
    echo "Cannot create directory: $dependdir"
    exit 1
  fi
fi

if [ -f Makefile -a -r Makefile ]; then :
else
  echo "./Makefile does not exist, please run 'config <KERNEL_CONFIG>' in"
  echo "/sys/i386/config"
  exit 1
fi

if [ -f $dependfile -a $dependfile ]; then :
else
  echo "File $dependfile does not exist, please run 'make depend'"
  exit 1
fi

##################################
echo "Warning: do not interrupt!!! Please wait 2-3 min"
##################################

# read cpp(1) macros
egrep '^IDENT|^COPTS' Makefile |
	sed -e 's|^[A-Z]*=||' -e 's|\${[A-Z]*}||g' | 
	awk '{for (i=1;i<=NF;i++) print $i}' | 
	sed 's|^-[DU]||' | egrep -v '^i386$|^KERNEL$' |
        sed 'p
	     s/=.*//' |
	sort -u | awk '{print "^#if.*[ \t]" $1}' > $tmp.depend


# new macros?
if [ -f $define ]; then
  if cmp $tmp.depend $define >/dev/null; then
    echo "Nothing changes. OK."
    exit 0
  else
    echo "Detected new cpp(1) macros"
    cp $tmp.depend $define
  fi
else 
  cp $tmp.depend $define
fi


#
# main
#

# make list of cpp(1) macros for each object file
awk '{bla=gsub("\\\\", "", $0); 
	if (bla==0) print $0; else printf $0;}' $dependfile |
while read obj yank rest
do

  egrep -h  -f $define $rest >$tmp.$obj

  # object file is obsolete?
  if [ -f $dependdir/$obj ]; then	
    if cmp $dependdir/$obj $tmp.$obj >/dev/null; then :
    else
      cp $tmp.$obj $dependdir/$obj
      echo "rm -f $obj" >> $tmp.remove
    fi
  else
    cp $tmp.$obj $dependdir/$obj
    echo "rm -f $obj" >> $tmp.remove
  fi

done

if [ -s $tmp.remove ]; then
  mv $tmp.remove $dependdir/REMOVED
  count=`ls *.o 2>/dev/null | wc -l` && count=`echo $count`
  if [ $count -eq 0 ]; then
    echo "Whole kernel building :-("
  else
    sh -x $dependdir/REMOVED
    removed=`wc -l < $dependdir/REMOVED` && removed=`echo $removed`
    perc=`expr 100 \* $removed / $count`
    echo "Object files: Total: $count Removed: $removed Percent: $perc"
  fi
else
  echo "Nothings to remove"
  exit 0
fi


# optional: sensitivity of '#if '
#
# cd $dependdir
# for obj in *.o; do sort -u $obj; done |sort |uniq -c|sort -nr  > $sensitivity
# head -15 $sensitivity
#
#
# optional: depence from header files
#
# tr ' ' '\12' < .depend |egrep -v '[:\]|\.o$|^$'|
# 			  sort|uniq -c | sort -nr > $depence
# 
----------------------------------------------------------------------

Wolfram