#!gmake -R

#  @file
#
#  @brief
#  Toplevel Makefile
#
#  This is the toplevel Makefile of the Kelvin project.
#
#  @author Peter Ellsiepen
#
#  CVSId: "@(#)$Id$"

PROJECT_BASE ?= $(shell expr $(CURDIR) : '\(.*/devel\).*' )

#--- project subdirectories ---------------------------------------------------

# default value of SUBDIRS = all indirect sub-directories containing a Makefile

#--- mark this as the project's toplevel Makefile -----------------------------

PROJECT_TOPLEVEL	= true

#--- include standard toplevel makefile includes ------------------------------

include $(PROJECT_BASE)/mak/common.mak
include $(PROJECT_BASE)/mak/toplevel.mak

#--- sub-directory dependencies -----------------------------------------------

#$(call subdir_depend,Loader,VdKernel)

#--- targets for build --------------------------------------------------------

.PHONY: tarball package

export FILELIST

tarball package: FILELIST = $(BASEDIRABSOLUTE)/VirtualDesign2.idb
tarball package: DEBUG=$(OPTIM_MARK)
tarball package: install

tarball:
	echo "Creation of tar-gz-package not yet implemented."

package:
	echo "Creation of system package not yet implemented."

#--- special directories and filenames ----------------------------------------

# output directory for doxygen
DOXYGENDIR			= $(BASEDIR)/docs

ifeq ($(DOXYGEN),)
$(warning Variable DOXYGEN not set, using default (doxygen))
DOXYGEN				= doxygen
endif

#--- determine scratch directory in home --------------------------------------

HOMESCRATCHDIR		:= $(shell \
	if [[ -d $(HOME)/scratch ]]; then scratch=scratch; \
    elif [[ -d $(HOME)/Scratch ]]; then scratch=Scratch; \
    elif [[ -d $(HOME)/SCRATCH ]]; then scratch=SCRATCH; \
    else \
		echo; \
		exit; \
	fi; \
	objdir1=`basename $(CURDIR)`; \
	objdir2=`dirname $(CURDIR)`; \
	objdir2=`basename $$objdir2`; \
	echo $(HOME)/$${scratch}/$${objdir2}/$${objdir1}; )

#--- special clean targets ----------------------------------------------------

.PHONY: initclean_l distclean_l

initclean distclean: %: %_l

initclean_l:
	$(RMR) $(BINDIR_VD2)
	$(RMR) $(LIBDIR_VD2)
	$(RMR) $(PLGDIR_VD2)
	$(RMR) $(BINDIR_VDSE)
	$(RMR) $(LIBDIR_VDSE)
	$(RMR) $(PLGDIR_VDSE)
	$(RMR) $(BINDIR_IDEAL)
	$(RMR) $(LIBDIR_IDEAL)
	$(RMR) $(PLGDIR_IDEAL)
	@-for d in $(INSTDIR)/{bin,conf,vd2,vdse,ideal}/* \
			  $(INSTDIR)/{bin,conf,vd2,vdse,ideal}; do \
		if [[ -d $$d ]]; then \
			(rmdir $$d 2>/dev/null && echo rmdir $$d) || $(ERRIGNORE); \
		fi; \
	 done

distclean_l: initclean_l docclean
ifneq ($(HOMESCRATCHDIR),)
	@if [[ -d $(HOMESCRATCHDIR) ]]; then \
		echo $(RMR) $(HOMESCRATCHDIR); \
		$(RMR) $(HOMESCRATCHDIR); \
	fi
endif
	@if [[ -d scratch || -L scratch ]]; then \
		echo $(RMR) scratch; \
		$(RMR) scratch; \
	fi

#--- special init targets -----------------------------------------------------

.PHONY:    init_l    initscratch_l \
		dbginit_l dbginitscratch_l \
	    optinit_l optinitscratch_l

init optinit dbginit initscratch optinitscratch dbginitscratch: %: %_l

init_l: $(BINDIR) $(LIBDIR) $(PLGDIR) $(INCDIR) $(CNFDIR) $(DOXYGENDIR)

initscratch_l: init_l scratch

dbginit_l: DEBUG = $(DEBUG_MARK)
dbginit_l: $(BINDIR) $(LIBDIR) $(PLGDIR) $(INCDIR) $(CNFDIR) $(DOXYGENDIR)

dbginitscratch_l: dbginit_l scratch

optinit_l: DEBUG = $(DEBUG_MARK)
optinit_l: $(BINDIR) $(LIBDIR) $(PLGDIR) $(INCDIR) $(CNFDIR) $(DOXYGENDIR)

optinitscratch_l: optinit_l scratch

$(BINDIR) $(LIBDIR) $(PLGDIR) $(INCDIR) $(CNFDIR) $(DOXYGENDIR):
	mkdir -p $@

# For the init-targets, make sure that the sub-directories are made *after* the
# toplevel directory, even in parallel makes.

# Well, the following would be nice but does not work since the *init*_r targets
# are no final targets but depend on the SUBDIR_TARGETS themselves ... :-(
#
#init optinit dbginit initscratch optinitscratch dbginitscratch: %_r: %_l
#
# Thus, we have to state all init dependencies explicitly 
# (see toplevel.mak for the definition of SUBDIR_TARGETS).

$(filter %.init   , $(SUBDIR_TARGETS)):    %.init:    init_l
$(filter %.dbginit, $(SUBDIR_TARGETS)): %.dbginit: dbginit_l
$(filter %.optinit, $(SUBDIR_TARGETS)): %.optinit: optinit_l

$(filter %.initscratch   , $(SUBDIR_TARGETS)):    %.initscratch:    initscratch_l
$(filter %.dbginitscratch, $(SUBDIR_TARGETS)): %.dbginitscratch: dbginitscratch_l
$(filter %.optinitscratch, $(SUBDIR_TARGETS)): %.optinitscratch: optinitscratch_l

#--- create tags & cscope database (for vim) ----------------------------------

TAGS_SUBDIRS := $(SUBDIRS)
tags:
	@echo Creating common tags file for directories
	@echo " $(TAGS_SUBDIRS) .."
	@$(CTAGS) -R --c-types=+C --totals $(TAGS_SUBDIRS) 

CSCOPE_OSGDIRS := Action Base Field FieldContainer Image Loader Log Nodes \
				  State Window
CSCOPE_DIRS := $(addprefix $(BASEDIRABSOLUTE)/, $(SUBDIRS) ) \
			   $(addprefix $(BASEDIRABSOLUTE)/../OpenSG/, $(CSCOPE_OSGDIRS) )
cscope:
	@echo Creating common cscope file for directories
	@echo " $(CSCOPE_DIRS) ..."
	@cscope -u -b -q -f ../cscope.db -s $(shell echo $(CSCOPE_DIRS) | tr " " ",")
	
#--- special targets for scratch dir handling ---------------------------------

#  Create link scratch -> ~/scratch/...,
#  where '...' are the last two directories in PWD.
#  (This allows to have multiple versions of the project to be checked out.)
#
#  @see also: target distclean_l

scratch:
	@if [[ -L scratch ]]; then \
		echo; \
		echo It seems like ./scratch is a link to a non-existent directory.; \
		echo Please re-create the directory where ./scratch is pointing to,; \
		echo or remove ./scratch.; \
		echo; \
		exit 1; \
	fi
ifeq ($(HOMESCRATCHDIR),)
	@echo "Could not find scratch directory in home\!"; \
	exit 1
else
	@if [[ ! -d $(HOMESCRATCHDIR) ]]; then \
		mkdir -p $(HOMESCRATCHDIR); \
	fi; \
	$(LNS) $(HOMESCRATCHDIR) scratch
endif

#--- doc ----------------------------------------------------------------------

.PHONY: html  man  latex  doc \
		htmlg mang latexg docg \
		docclean

# Note: generating doc is only useful from the topmost makefile 
#	    in order to get correct references 

doc:
	@echo -n "Generating HTML documentation in docs ... "
	@doxygen $(BASEDIR)/doxygen.cfg
	@echo "done."
# keep the doxygen.cfg, so we have a chance to find out what went wrong,
# if something went wrong [GZ]

docclean:
	$(RMR) $(DOXYGENDIR)

#--- end of file --------------------------------------------------------------
