#
# This file contains rules which are shared between multiple Makefiles.
#

ifndef FIRST_TIME
FIRST_TIME = false

#CURRDIR := $(TOPDIR)
#
# False targets.
#
.PHONY: dummy

#
# Special variables which should not be exported
#
unexport EXTRA_ASFLAGS
unexport EXTRA_CFLAGS
unexport EXTRA_LDFLAGS
unexport EXTRA_ARFLAGS
unexport SUBDIRS
unexport SUB_DIRS
unexport ALL_SUB_DIRS
unexport MOD_SUB_DIRS
unexport O_TARGET
unexport O_OBJS
unexport L_OBJS
unexport M_OBJS
# intermediate objects that form part of a module
unexport MI_OBJS
unexport ALL_MOBJS
# objects that export symbol tables
unexport OX_OBJS
unexport LX_OBJS
unexport MX_OBJS
unexport MIX_OBJS
unexport SYMTAB_OBJS

unexport MOD_LIST_NAME

#
# Get things started.
#
first_rule: sub_dirs
	$(MAKE) all_targets

#
# Common rules
#

%.s: %.c
	$(CC) $(CFLAGS) $(EXTRA_CFLAGS) $(CFLAGS_$@) -S $< -o $@

%.i: %.c
	$(CC) $(CFLAGS) $(EXTRA_CFLAGS) $(CFLAGS_$@) -E $< > $@

%.o: %.c
	@echo Compiling $< with: $(EXTRA_CFLAGS) $(CFLAGS_$@)
	@$(CC) $(CFLAGS) $(EXTRA_CFLAGS) $(CFLAGS_$@) -c -o $@ $<
	@ ( \
	    echo 'ifeq ($(strip $(subst $(comma),:,$(CFLAGS) $(EXTRA_CFLAGS) $(CFLAGS_$@))),$$(strip $$(subst $$(comma),:,$$(CFLAGS) $$(EXTRA_CFLAGS) $$(CFLAGS_$@))))' ; \
	    echo 'FILES_FLAGS_UP_TO_DATE += $@' ; \
	    echo 'endif' \
	) > $(dir $@)/.$(notdir $@).flags

%.o: %.s
	@echo Assembling $< with: $(ASFLAGS) $(EXTRA_CFLAGS)
	@$(AS) $(ASFLAGS) $(EXTRA_CFLAGS) -o $@ $<

ifneq ($(wildcard $(TOPDIR)/.hdepend),)
include $(TOPDIR)/.hdepend
endif

# Trap to catch unhandled fastdeps and ignore them
%/.__fastdep__:
	@echo DEBUG: !!!ERROR!!! fastdep for $@ not found

endif
#
#
#
#all_targets: $(O_TARGET) $(L_TARGET)

O_TARGET := $(addprefix $(CURRDIR),$(O_TARGET))
O_OBJS   := $(addprefix $(CURRDIR),$(O_OBJS))
OX_OBJS  := $(addprefix $(CURRDIR),$(OX_OBJS))
L_TARGET := $(addprefix $(CURRDIR),$(L_TARGET))
L_OBJS   := $(addprefix $(CURRDIR),$(L_OBJS))
LX_OBJS  := $(addprefix $(CURRDIR),$(LX_OBJS))
M_OBJS   := $(addprefix $(CURRDIR),$(M_OBJS))
MX_OBJS  := $(addprefix $(CURRDIR),$(MX_OBJS))
MI_OBJS  := $(addprefix $(CURRDIR),$(MI_OBJS))
MIX_OBJS := $(addprefix $(CURRDIR),$(MIX_OBJS))

#X := $(shell echo 'DEBUG: Dir $(CURRDIR): O_TARGET=$(O_TARGET), O_OBJS=$(O_OBJS), OX_OBJS=$(OX_OBJS), L_TARGET=$(L_TARGET), L_OBJS=$(L_OBJS), LX_OBJS=$(LX_OBJS)' >&2)
#
# Rule to compile a set of .o files into one .o file
#
ifneq ($(O_TARGET),)
ALL_O = $(OX_OBJS) $(O_OBJS)
$(O_TARGET): $(ALL_O)
	rm -f $@
ifneq "$(strip $(ALL_O))" ""
	$(LD) $(EXTRA_LDFLAGS) -r -o $@ $(filter-out dummy,$^)
else
	$(AR) rcs $@
endif
	@ ( \
	    echo 'X := $$(shell echo "==<$(strip $(subst $(comma),:,$(EXTRA_LDFLAGS) $(filter-out dummy,$^)))" >&2)' ; \
	    echo 'X := $$(shell echo "==>$$(strip $$(subst $$(comma),:,$$(EXTRA_LDFLAGS) $$(OX_OBJS) $$(O_OBJS)))" >&2)' ; \
	    echo 'ifeq ($(strip $(subst $(comma),:,$(EXTRA_LDFLAGS) $(filter-out dummy,$^))),$$(strip $$(subst $$(comma),:,$$(EXTRA_LDFLAGS) $$(OX_OBJS) $$(O_OBJS))))' ; \
	    echo 'FILES_FLAGS_UP_TO_DATE += $@' ; \
	    echo 'endif' \
	) > $(dir $@)/.$(notdir $@).flags
endif # O_TARGET

#
# Rule to compile a set of .o files into one .a file
#
ifneq ($(L_TARGET),)
$(L_TARGET): $(LX_OBJS) $(L_OBJS)
	rm -f $@
	$(AR) $(EXTRA_ARFLAGS) rcs $@ $(filter-out dummy,$^)
	( \
	    echo 'ifeq ($(strip $(subst $(comma),:,$(EXTRA_ARFLAGS) $(filter-out dummy,$^))),$$(strip $$(subst $$(comma),:,$$(EXTRA_ARFLAGS) $$(LX_OBJS) $$(L_OBJS))))' ; \
	    echo 'FILES_FLAGS_UP_TO_DATE += $@' ; \
	    echo 'endif' \
	) > $(dir $@)/.$(notdir $@).flags
endif

#
# This make dependencies quickly
#
$(CURRDIR).__fastdep__: $(patsubst %,$(CURRDIR)%/.__fastdep__,$(ALL_SUB_DIRS)) $(wildcard $(CURRDIR)*.[chS])
	$(TOPDIR)/scripts/mkdep $(wildcard $(dir $@)*.[chS] local.h.master) > $(dir $@).depend
#ifneq ($(ALL_SUB_DIRS),)
#	$(MAKE) $(patsubst %,_sfdep_%,$(ALL_SUB_DIRS)) _FASTDEP_ALL_SUB_DIRS="$(ALL_SUB_DIRS)"
#endif

#ifdef _FASTDEP_ALL_SUB_DIRS
#$(patsubst %,_sfdep_%,$(_FASTDEP_ALL_SUB_DIRS)):
#	$(MAKE) -C $(patsubst _sfdep_%,%,$@) fastdep
#endif

#
# A rule to make subdirectories
#
#sub_dirs: dummy $(patsubst %,_subdir_%,$(SUB_DIRS))
#
#ifdef SUB_DIRS
#$(patsubst %,_subdir_%,$(SUB_DIRS)) : dummy
#	$(MAKE) -C $(patsubst _subdir_%,%,$@)
#endif

CONFIG_MODULES :=

ifneq ($(CONFIG_MODULES),)
#
# A rule to make modules
#
ALL_MOBJS = $(MX_OBJS) $(M_OBJS)
ifneq "$(strip $(ALL_MOBJS))" ""
PDWN=$(shell $(CONFIG_SHELL) $(TOPDIR)/scripts/pathdown.sh)
endif

ifdef MOD_SUB_DIRS
$(patsubst %,_modsubdir_%,$(MOD_SUB_DIRS)) : dummy
	$(MAKE) -C $(patsubst _modsubdir_%,%,$@) modules
endif

ifdef MOD_IN_SUB_DIRS
$(patsubst %,_modinsubdir_%,$(MOD_IN_SUB_DIRS)) : dummy
	$(MAKE) -C $(patsubst _modinsubdir_%,%,$@) modules
endif

modules: $(ALL_MOBJS) $(MIX_OBJS) $(MI_OBJS) dummy \
	 $(patsubst %,_modsubdir_%,$(MOD_SUB_DIRS)) \
	 $(patsubst %,_modinsubdir_%,$(MOD_IN_SUB_DIRS))
ifneq "$(strip $(MOD_LIST_NAME))" ""
	rm -f $$TOPDIR/modules/$(MOD_LIST_NAME)
ifdef MOD_SUB_DIRS
	for i in $(MOD_SUB_DIRS); do \
	    echo `basename $$i`.o >> $$TOPDIR/modules/$(MOD_LIST_NAME); done
endif
ifneq "$(strip $(ALL_MOBJS))" ""
	echo $(ALL_MOBJS) >> $$TOPDIR/modules/$(MOD_LIST_NAME)
endif
ifneq "$(strip $(MOD_TO_LIST))" ""
	echo $(MOD_TO_LIST) >> $$TOPDIR/modules/$(MOD_LIST_NAME)
endif
endif
ifneq "$(strip $(ALL_MOBJS))" ""
	echo $(PDWN)
	cd $$TOPDIR/modules; for i in $(ALL_MOBJS); do \
	    ln -sf ../$(PDWN)/$$i $$i; done
endif

endif
#
# A rule to do nothing
#
dummy:

#
# This is useful for testing
#
#script:
#	$(SCRIPT)

#
# This sets version suffixes on exported symbols
# Uses SYMTAB_OBJS
# Separate the object into "normal" objects and "exporting" objects
# Exporting objects are: all objects that define symbol tables
#
ifneq ($(CONFIG_MODULES),)

SYMTAB_OBJS = $(LX_OBJS) $(OX_OBJS) $(MX_OBJS) $(MIX_OBJS)

ifdef CONFIG_MODVERSIONS
ifneq "$(strip $(SYMTAB_OBJS))" ""

MODINCL = $(TOPDIR)/include/linux/modules

# The -w option (enable warnings) for genksyms will return here in 2.1
# So where has it gone?
#
# Added the SMP separator to stop module accidents between uniprocessor
# and SMP Intel boxes - AC - from bits by Michael Chastain
#

ifdef CONFIG_SMP
	genksyms_smp_prefix := -p smp_
else
	genksyms_smp_prefix := 
endif

#
#	Differ 1 and 2Gig kernels to avoid module misload errors
#

ifdef CONFIG_2GB
ifdef CONFIG_SMP
	genksyms_smp_prefix := -p smp2gig_
else
	genksyms_smp_prefix := -p 2gig_
endif
endif

$(MODINCL)/%.ver: %.c
	@if [ ! -r $(MODINCL)/$*.stamp -o $(MODINCL)/$*.stamp -ot $< ]; then \
		echo '$(CC) $(CFLAGS) -E -D__GENKSYMS__ $<'; \
		echo '| $(GENKSYMS) $(genksyms_smp_prefix) -k $(VERSION).$(PATCHLEVEL).$(SUBLEVEL) > $@.tmp'; \
		$(CC) $(CFLAGS) -E -D__GENKSYMS__ $< \
		| $(GENKSYMS) $(genksyms_smp_prefix) -k $(VERSION).$(PATCHLEVEL).$(SUBLEVEL) > $@.tmp; \
		if [ -r $@ ] && cmp -s $@ $@.tmp; then echo $@ is unchanged; rm -f $@.tmp; \
		else echo mv $@.tmp $@; mv -f $@.tmp $@; fi; \
	fi; touch $(MODINCL)/$*.stamp

$(addprefix $(MODINCL)/,$(notdir $(SYMTAB_OBJS:.o=.ver))): $(TOPDIR)/include/linux/autoconf.h

$(TOPDIR)/include/linux/modversions.h: $(addprefix $(MODINCL)/,$(SYMTAB_OBJS:.o=.ver))
	@echo updating $(TOPDIR)/include/linux/modversions.h
	@(echo "#ifndef _LINUX_MODVERSIONS_H";\
	  echo "#define _LINUX_MODVERSIONS_H"; \
	  echo "#include <linux/modsetver.h>"; \
	  cd $(TOPDIR)/include/linux/modules; \
	  for f in *.ver; do \
	    if [ -f $$f ]; then echo "#include <linux/modules/$${f}>"; fi; \
	  done; \
	  echo "#endif"; \
	) > $@

dep fastdep: $(TOPDIR)/include/linux/modversions.h

endif # SYMTAB_OBJS 

$(M_OBJS): $(TOPDIR)/include/linux/modversions.h
ifdef MAKING_MODULES
$(O_OBJS) $(L_OBJS): $(TOPDIR)/include/linux/modversions.h
endif

else

$(TOPDIR)/include/linux/modversions.h:
	@echo "#include <linux/modsetver.h>" > $@

endif # CONFIG_MODVERSIONS

ifneq "$(strip $(SYMTAB_OBJS))" ""
$(SYMTAB_OBJS): $(TOPDIR)/include/linux/modversions.h $(SYMTAB_OBJS:.o=.c)
	@echo Compiling $(@:.o=.c) with: $(EXTRA_CFLAGS) $(CFLAGS_$@) -DEXPORT_SYMTAB
	@$(CC) $(CFLAGS) $(EXTRA_CFLAGS) $(CFLAGS_$@) -DEXPORT_SYMTAB -c $(@:.o=.c)
	@ ( \
	    echo 'ifeq ($(strip $(subst $(comma),:,$(CFLAGS) $(EXTRA_CFLAGS) $(CFLAGS_$@) -DEXPORT_SYMTAB)),$$(strip $$(subst $$(comma),:,$$(CFLAGS) $$(EXTRA_CFLAGS) $$(CFLAGS_$@) -DEXPORT_SYMTAB)))' ; \
	    echo 'FILES_FLAGS_UP_TO_DATE += $@' ; \
	    echo 'endif' \
	) > $(dir $@)/.$(notdir $@).flags
endif

endif # CONFIG_MODULES


#
# include dependency files if they exist
#
ifneq ($(wildcard $(CURRDIR).depend),)
include $(CURRDIR).depend
endif

#
# Find files whose flags have changed and force recompilation.
# For safety, this works in the converse direction:
#   every file is forced, except those whose flags are positively up-to-date.
#
FILES_FLAGS_UP_TO_DATE :=

# For use in expunging commas from flags, which mung our checking.
comma = ,

FILES_FLAGS_EXIST := $(wildcard $(CURRDIR).*.flags)
ifneq ($(FILES_FLAGS_EXIST),)
include $(FILES_FLAGS_EXIST)
endif

#X := $(shell echo 'DEBUG: FILES_FLAGS_EXIST=$(FILES_FLAGS_EXIST)' >&2)
#X := $(shell echo 'DEBUG: FILES_FLAGS_UP_TO_DATE=$(FILES_FLAGS_UP_TO_DATE)' >&2)

FILES_FLAGS_CHANGED := $(strip \
    $(filter-out $(FILES_FLAGS_UP_TO_DATE), \
	$(O_TARGET) $(O_OBJS) $(OX_OBJS) \
	$(L_TARGET) $(L_OBJS) $(LX_OBJS) \
	$(M_OBJS) $(MX_OBJS) \
	$(MI_OBJS) $(MIX_OBJS) \
	))

# A kludge: .S files don't get flag dependencies (yet),
#   because that will involve changing a lot of Makefiles.
FILES_FLAGS_CHANGED := $(strip \
    $(filter-out $(patsubst %.S, %.o, $(wildcard $(CURRDIR)*.S)), \
    $(FILES_FLAGS_CHANGED)))

#X := $(shell echo 'DEBUG: FILES_FLAGS_CHANGED=$(FILES_FLAGS_CHANGED)' >&2)

ifneq ($(FILES_FLAGS_CHANGED),)
$(FILES_FLAGS_CHANGED): dummy
endif

#X := $(shell echo "DEBUG: SUB_DIRS='$(SUB_DIRS)', CURRDIR='$(CURRDIR)'" >&2 )

ifneq ($(CURRDIR),)
$(patsubst ./%,%,$(CURRDIR))_SUB_DIRS := $(SUB_DIRS)
else
./_SUB_DIRS := $(SUB_DIRS)
endif

ifneq ($(SUB_DIRS),)
$(CURRDIR).subdirs.make: ./Rules.make 
	@echo 'DEBUG: Building $(dir $@).subdirs.make (DIRSTACK=$(DIRSTACK), SUB_DIRS=$($(dir $@)_SUB_DIRS))'
	@( echo 'DIRSTACK := $(dir $@) $$(DIRSTACK)' ; \
	  for i in $($(dir $@)_SUB_DIRS) ; do \
	    echo 'SUB_DIRS :=' ; \
	    echo "CURRDIR := $(patsubst ./%,%,$(dir $@))$$i/" ; \
	    echo "include $(dir $@)$$i/Makefile" ; \
	  done ; \
	  echo 'DIRSTACK := $$(wordlist 2, 10, $$(DIRSTACK))' ; \
	) > $@
#	@echo "DEBUG: target = $@" >&2
#	  echo 'x $(dir $@)_SUB_DIRS' >&2 ; \
#	cat $@
else
$(CURRDIR).subdirs.make: ./Rules.make
	@touch $@
#	@echo 'DEBUG: Building empty $(dir $@).subdirs.make (DIRSTACK=$(DIRSTACK), SUB_DIRS=$($(dir $@)_SUB_DIRS))'
endif

O_TARGET :=
O_OBJS :=
OX_OBJS :=
L_TARGET :=
L_OBJS :=
LX_OBJS :=
M_OBJS :=
MX_OBJS :=
MI_OBJS :=
MIX_OBJS :=
MOD_LIST_NAME :=
ALL_SUB_DIRS :=

ifneq ($(SUB_DIRS),'')
ifndef $(CURRDIR)_DONE_ALREADY
$(CURRDIR)_DONE_ALREADY := 1
#X := $(shell echo "DEBUG: Including '$(CURRDIR).subdirs.make'" >&2 )
include $(CURRDIR).subdirs.make
endif
endif




