# ===========================================================================
#
#                            PUBLIC DOMAIN NOTICE
#               National Center for Biotechnology Information
#
#  This software/database is a "United States Government Work" under the
#  terms of the United States Copyright Act.  It was written as part of
#  the author's official duties as a United States Government employee and
#  thus cannot be copyrighted.  This software/database is freely available
#  to the public for use. The National Library of Medicine and the U.S.
#  Government have not placed any restriction on its use or reproduction.
#
#  Although all reasonable efforts have been taken to ensure the accuracy
#  and reliability of the software and data, the NLM and the U.S.
#  Government do not and cannot warrant the performance or results that
#  may be obtained by using this software or data. The NLM and the U.S.
#  Government disclaim all warranties, express or implied, including
#  warranties of performance, merchantability or fitness for any particular
#  purpose.
#
#  Please cite the author in any work or product based on this material.
#
# ===========================================================================


# pick up dependencies from object directory
ifdef SRCDIR
	include $(wildcard *.d)
endif

# determine shell environment
include $(TOP)/build/Makefile.shell

# normally build shared and static external libs
LIBEXT = $(LIBX) $(SHLX)

# normally build static intermediate libs
ILIBEXT = $(LIBX)

# would normally only build dynamic library modules,
# but some tools are expecting to be able to static link
MODEXT = $(LIBX) $(SHLX)

# determine BUILD
ifeq (,$(BUILD))
	BUILD = dbg
endif

# some rules are sensitive to the type of build
BUILDTYPE = $(BUILD)

# adjust settings for build
ifeq (dbg,$(BUILD))
	DEBUG := -D_DEBUGGING
#	ILIBEXT = $(LIBX) $(SHLX)
	MODEXT = $(LIBX) $(SHLX)
endif
ifeq (rel,$(BUILD))
	DEBUG := -DNDEBUG
endif
ifeq (prof,$(BUILD))
	DEBUG := -DNDEBUG -D_PROFILING
endif

# allow for an all-static build
ifeq (stat,$(LNKG))
	STATIC = --static
	LINKAGE := -D_STATIC
	LIBEXT = $(LIBX)
	ILIBEXT = $(LIBX)
	MODEXT = $(LIBX)
	STAT_OR_DYN = static
	STATICSYSLIBS := --static-system-libs

else
	STAT_OR_DYN = dynamic
endif

LOCAL_OR_REMOTE = local


# drop all suffix rules
.SUFFIXES:

# load OS and COMP specific files
include $(TOP)/build/Makefile.$(OS)
include $(TOP)/build/Makefile.$(COMP)
include $(TOP)/build/Makefile.rules

# external schema modules
EXT_SCHEMA_MODULES = axf sraxf wgsxf vxf
UPDATE_SCHEMA_LIBS := $(addprefix -lw,$(EXT_SCHEMA_MODULES))
READONLY_SCHEMA_LIBS = $(addprefix -l,$(EXT_SCHEMA_MODULES))
ALWAYS_STATIC_SCHEMA_LIBS = $(addprefix -s,$(EXT_SCHEMA_MODULES))

# full directory paths
OLD_TARGDIR = $(OUTDIR)/$(OSFLAV)/$(BUILD)/$(TOOLSET)/$(ARCH)
TARGDIR = $(OUTDIR)/$(OSFLAV)/$(TOOLSET)/$(LNKG)/$(ARCH)/$(BUILD)
BINDIR = $(TARGDIR)/bin
ifeq (win,$(OS))
    # on Windows, place test executables next to .dlls
    TEST_BINDIR = $(BINDIR)
else
    TEST_BINDIR = $(TARGDIR)/test-bin
endif
ILIBDIR = $(TARGDIR)/ilib
LIBDIR = $(TARGDIR)/lib
MODDIR = $(TARGDIR)/mod
WMODDIR = $(TARGDIR)/wmod
OBJDIR = $(TARGDIR)/obj/$(MODULE)

# path to the ncbi sub-directory
# this is where modules and installed schema files are kept
ifeq (win,$(OS))
    # under Windows, we are always relative to binary path
	NCBIDIR = $(BINDIR)/ncbi
else
ifeq (--static,$(STATIC))
    # in static builds, we are relative to binary path
    # because the configuration library will be part of tool
	NCBIDIR = $(BINDIR)/ncbi
else
    # in dynamic builds, we are relative to library path
    # because the configuration library will live there
	NCBIDIR = $(LIBDIR)/ncbi
endif
endif

# make reissue command
MAKE_CMD = $(MAKE) BUILD=$(BUILD) TOOLSET=$(TOOLSET) COMP=$(COMP) LNKG=$(LNKG) \
    TOP=$(TOP) SRCDIR=$(SRCDIR) OUTDIR=$(OUTDIR) -C $(OBJDIR) -f $(SRCDIR)/Makefile

# directory and link creation
SUBDIRS = bin test-bin ilib lib
OUTDIRS = schema

# clean rules
stdclean:
	@ -rm -rf $(OBJDIR)
	@ rm -rf $(addsuffix .*,$(addprefix $(ILIBDIR)/,$(ALL_LIBS))) \
			$(addsuffix .*,$(addprefix $(LIBDIR)/,$(ALL_LIBS))) \
			$(addsuffix .*,$(addprefix $(MODDIR)/,$(ALL_LIBS))) \
			$(addsuffix .*,$(addprefix $(WMODDIR)/,$(ALL_LIBS))) \
			$(addsuffix *,$(addprefix $(BINDIR)/,$(ALL_TOOLS) $(ALL_LIBS))) \
			$(addsuffix *,$(addprefix $(TEST_BINDIR)/,$(ALL_TOOLS) $(TEST_TOOLS)))

# removing symbolic links that point to specific builds
removelinks:
	@ test ! -h $(OUTDIR)/schema && rm -rf $(OUTDIR)/schema || true
	@ rm -f $(addprefix $(OUTDIR)/,$(addsuffix $(BITS),$(SUBDIRS)))
	@ rm -f $(addprefix $(OUTDIR)/,$(OUTDIRS))

# create all required output directories
makedirs:
	@ mkdir -p $(addprefix $(TARGDIR)/,$(SUBDIRS) obj/$(MODULE)) $(NCBIDIR)

# build version include files
vers-includes: makedirs
	@ $(MAKE_CMD) -s $(TARGDIR)/$@

ifeq (win,$(OS))

# Windows doesn't really support symbolic links
# we may add them back in when our toolkit is able to create them
rebuild-dirlinks: makedirs
	@ true
else

LNDIRS = $(addprefix ln_,$(SUBDIRS))
$(LNDIRS):
	@ ln -s $(TARGDIR)/$(subst ln_,,$@) $(OUTDIR)/$(subst ln_,,$@)$(BITS)

ifdef NOREBUILD_LINKS
rebuild-dirlinks:
	@ true
else
rebuild-dirlinks: removelinks makedirs $(LNDIRS)
	@ ln -s $(TOP)/interfaces $(OUTDIR)/schema
endif

endif

.PHONY: stdclean removelinks makedirs vers-includes rebuild-dirlinks

# configuration targets 
out:
	@ echo $(OUTDIR) > $(TOP)/build/OUTDIR.$(BUILD_OS)
	@ $(MAKE) TOP=$(TOP) -f $(TOP)/build/Makefile.env rebuild-dirlinks

CC:
	@ echo cc > $(TOP)/build/COMP.$(OS)

GCC:
	@ echo gcc > $(TOP)/build/COMP.$(OS)

ICC:
	@ echo icc > $(TOP)/build/COMP.$(OS)

VC++:
	@ echo vc++ > $(TOP)/build/COMP.$(OS)

CLANG:
	@ echo clang > $(TOP)/build/COMP.$(OS)

static:
	@ echo stat > $(TOP)/build/LNKG.$(OS)

dynamic:
	@ echo dyn > $(TOP)/build/LNKG.$(OS)

debug:
	@ echo dbg > $(TOP)/build/BUILD.$(OS)

profile: static
	@ echo prof > $(TOP)/build/BUILD.$(OS)

release:
	@ echo rel > $(TOP)/build/BUILD.$(OS)

pubtools: release static

bindir:
	@ echo "$(BINDIR)"

targdir:
	@ echo "$(TARGDIR)"

osdir:
	@ echo "$(OUTDIR)/$(OSFLAV)"

compilers:
	@ echo "$(COMPILERS)"

architectures:
	@ echo "$(ARCHITECTURES)"

architecture:
	@ echo "$(ARCH)"

config:
	@ echo "  current build is $(BUILD_OS) $(STAT_OR_DYN) $(BUILD) $(ARCH) build using $(TOOLSET) tools"
	@ echo "  output target directory is '$(TARGDIR)'"
	@ echo

.PHONY: out CC GCC ICC debug profile release bindir report_config

# includes based upon build
ITF = $(TOP)/interfaces
OSINC = $(TOP)/interfaces/os
CCINC = $(TOP)/interfaces/cc
XTINC = $(TOP)/interfaces/ext
OVERRIDEINC = $(TOP)/interfaces/override

# OS specific source and include dirs
SRCDIRS_OS = $(SRCDIR)/$(OS)
INCDIRS_OS = $(OSINC)/$(OS)

# most OS' have a parent type
ifdef OS_DAD

SRCDIRS_OS += $(SRCDIR)/$(OS_DAD)
INCDIRS_OS += $(OSINC)/$(OS_DAD)

# some OS' have a grandparent
ifdef OS_GDAD
SRCDIRS_OS += $(SRCDIR)/$(OS_GDAD)
INCDIRS_OS += $(OSINC)/$(OS_GDAD)
endif

endif

# compiler specific includes
INCDIRS_COMP = \
	$(CCINC)/$(COMP)/$(ARCH) \
	$(CCINC)/$(COMP)

# some compilers have a parent type
ifdef COMP_DAD

INCDIRS_COMP += \
	$(CCINC)/$(COMP_DAD)/$(ARCH) \
	$(CCINC)/$(COMP_DAD)

endif

VPATH = \
	$(SRCDIR)/$(COMP)/$(ARCH) \
	$(SRCDIR)/$(COMP) \
	$(SRCDIRS_OS) \
	$(SRCDIR)

INCDIRS = \
	$(addprefix -I,$(OVERRIDEINC)) \
	$(addprefix -I,$(SRCDIRS_OS)) \
	$(addprefix -I,$(SRCDIR) $(ITF)) \
	$(addprefix -I,$(INCDIRS_COMP)) \
	$(addprefix -I,$(INCDIRS_OS) $(XTINC)) \
	-I.


# defines that describe os & architecture
DLLX ?= $(SHLX)
ARCHDEFS = -D_ARCH_BITS=$(BITS) -DLIBPREFIX=$(LPFX) -DSHLIBEXT=$(DLLX)

# default tool parameters
CFLAGS	= $(DEBUG) $(DBG) $(CARCH) $(PROF) $(PED) $(LINKAGE) $(DEFINES) $(ARCHDEFS) $(MIN_DEPLOY_OS_OPT) $(INCDIRS)
CPFLAGS = $(DEBUG) $(DBG) $(CARCH) $(PROF) $(LINKAGE) $(DEFINES) $(ARCHDEFS) $(MIN_DEPLOY_OS_OPT) $(INCDIRS)
LDFLAGS = $(DBG) $(PROF) $(CARCH) $(MIN_DEPLOY_OS_OPT)
