# -*-Makefile-*-
#
# 'make' creates mlsqlodbcw.[so|dll|dylib], the custom MarkLogic version
# of the PostgreSQL ODBC driver library psqlodbcw.
# Dependencies:
#   ../SqlClient must exist (be pulled from svn).
#   ../SqlClient/libmlq.[so|dll|dylib] must already be built.
#
# You will need to have the following packages installed to build correctly:
# unixODBC-devel (2.3.2), unixODBC (2.3.2)
# XYZZY: No, get these from ../xdmp/src
# openssl-devel (1.0.zi), openssl-libs (1.0.zi)
# 

ALTERED_ODBC_SRCS = \
	version.h \
	connection.c \
	convert.c \
	dlg_specific.h \
	dlg_wingui.c \
	info.c \
	statement.c

# 'make MLFLAGS=-DMARKLOGIC_DEBUG' will build an ODBC driver that logs
# brief client messages to stdout.
#MLFLAGS=-DMARKLOGIC_DEBUG -DUNICODE_SUPPORT
MLFLAGS=-DUNICODE_SUPPORT

SQL_DIR = ../SqlClient
SQL_INCLUDES = -I$(SQL_DIR)/src/include \
	       -I$(SQL_DIR)/src/interfaces/ecpg/include \
	       -I$(SQL_DIR)/src/interfaces/libpq
XDMP_DIR = $(shell pwd)/../xdmp/src
THIRDPARTY_DIR = $(shell pwd)/../xdmp/3rdParty
OPENSSL_VERSION = 3.3.5
OPENSSL_DIR = $(THIRDPARTY_DIR)/openssl/$(OPENSSL_VERSION)
OPENSSL_INCLUDES = -I$(OPENSSL_DIR)/include

# You only need to read this complicated comment if you plan to edit
# this file.  The intended default target is odbc-shlib (see lower),
# but that can't go here because it depends on SHLIB being defined
# first, and SHLIB's value varies per the conditional below.  Yet, we
# need to give our intended default target a gratuitous rule up here,
# or we'd pick up the default target of an intervening included
# Makefile.  Also, the default target can't be called "all," or gmake
# will also build "all" rules in included Makefiles.
default-target: odbc-shlib

MAJOR_VERSION = 12
MINOR_VERSION = 0
RPM_RELEASE = rhel
VERSION = $(MAJOR_VERSION).$(MINOR_VERSION)

PATCH_RELEASE = $(shell $(shell which cat) $(XDMP_DIR)/PATCH_VERSION)
RELEASE = $(VERSION).$(PATCH_RELEASE)
BASENAME = mlsqlodbc-$(RELEASE)

ifeq "$(shell uname -s)" "Linux"
-include Makefile.linux
INCLUDES = $(SQL_INCLUDES) $(OPENSSL_INCLUDES)
SHLIB = mlsqlodbcw.so
MAKE_EXT = linux

ARCH_RESULT := $(shell /bin/arch 2>/dev/null)
ifeq ($(ARCH_RESULT),)
  # arch might be in /usr/bin
  ARCH_RESULT := $(shell /usr/bin/arch 2>/dev/null)
endif
ifeq ($(ARCH_RESULT),)
  # uname -m does the job as well
  ARCH_RESULT := $(shell /bin/uname -m 2>/dev/null)
endif
ifeq ($(ARCH_RESULT),x86_64)
  ARCH = x86_64
else
  ARCH = i386
endif
OPENSSL_DIR = $(shell pwd)/../SqlClient/openssl/$(OPENSSL_VERSION)
MARKLOGIC_COMP = gcc$(shell gcc --version | head -1 | awk '{print $$3}' | awk -F. '{print $$1 "." $$2}')
OPENSSL_LIB_DIR = "$(OPENSSL_DIR)/$(MAKE_EXT)/$(ARCH)-$(MARKLOGIC_COMP)"
OPENSSL_LIBS = "-L$(OPENSSL_LIB_DIR)"
endif

ifneq "$(WINDIR)" ""
-include Makefile.winnt
INCLUDES = $(SQL_INCLUDES)
SHLIB = mlsqlodbcw.dll
CPPFLAGS = -DMARKLOGIC
USE_LIBPQ = "yes"
$(info VERSION: $(value VSVERSION))
 ifeq ("$(VSVERSION)","12.0") 
	INSTALLER=installer.vs2013
 else
 ifeq ("$(VSVERSION)","14.0") 
	INSTALLER=installer.vs2015
 else
 ifeq ("$(VSVERSION)","15.0") 
	INSTALLER=installer.vs2017
 else
 ifeq ("$(VSVERSION)","17.0") 
	INSTALLER=installer.vs2022
 else
	INSTALLER=installer
 endif
 endif
 endif
 endif
else
  INSTALLER=installer
endif

ifeq "$(shell uname -s)" "SunOS"
-include Makefile.solaris
INCLUDES = $(SQL_INCLUDES) $(OPENSSL_INCLUDES)
SHLIB = mlsqlodbcw.so
MAKE_EXT = solaris
endif

ifeq "$(shell uname -s)" "Linux"
  PKG_NAME = $(BASENAME)-$(RPM_RELEASE).$(ARCH)
else
  PKG_NAME = $(BASENAME)-$(ARCH)
endif

ifeq "$(shell uname -s)" "Darwin"
-include Makefile.macosx
INCLUDES = $(SQL_INCLUDES)
MLFLAGS += -DMAC64
SHLIB = mlsqlodbcw.dylib
ARCH = x86_64
MAKE_EXT = macosx
#PACKAGEMAKER = ~/Downloads/Auxiliary\ Tools/PackageMaker.app/Contents/MacOS/PackageMaker
PACKAGEMAKER = pkgbuild
IDENTIFIER = com.marklogic.odbc
MACPACKAGENAME = mlsqlodbc
MACINSTALLTEMP = macosx/package/MacInstallTemp
MACINSTALLIMAGE = $(MACINSTALLTEMP)/DiskImage
MACINSTALLCONF = $(MACINSTALLTEMP)/Config
MACINSTALLRES = $(MACINSTALLTEMP)/Resources
MACINSTALLPKGROOT = $(MACINSTALLTEMP)/MarkLogicODBC
MACINSTALLBIN = $(MACINSTALLPKGROOT)/mlbin
MACINSTALLLIB = $(MACINSTALLPKGROOT)/lib
MACINSTALLTEMPLATE = $(MACINSTALLPKGROOT)/templates
DISKIMAGER = hdiutil 
MLPKG = $(MACINSTALLIMAGE)/mlsql.pkg
PACKAGEPATH = $(MACINSTALLIMAGE)/$(PKG_NAME).pkg
DISKIMAGEPATH = $(MACINSTALLIMAGE)/$(PKG_NAME).dmg
endif


ifneq "$(WINDIR)" ""
# 'make' fails randomly on 'cannot open program database
# 'c:...\sqlclient\src\port\vc90.idb'; just try repeatedly.
odbc-shlib: clean64
	-@for i in 1 2 3 4 5 6 7 8 9 10;\
	do  if [ ! -f $(ARCH)/$(MLDLL) ];\
	    then	$(MAKE) ALL;\
	    fi;\
	done
	$(MAKE) ALL
	cp $(ARCH)/$(MLDLL) .
	cp $(ARCH)/$(XADLL) .
	cp $(ARCH)/$(DTCDLL) .
	cp $(ARCH)/*.lib .
	cp $(ARCH)/*.exp .
 ifeq ("$(VSVERSION)","9.0")
	cp $(ARCH)/*.manifest .
 endif
else
odbc-shlib: $(SHLIB)
endif

ifneq "$(WINDIR)" ""
# 'make' fails randomly on 'cannot open program database
# 'c:...\sqlclient\src\port\vc90.idb'; just try repeatedly.
allwin32: clean32
	-@for i in 1 2 3 4 5 6 7 8 9 10;\
	do  if [ ! -f i686/$(MLDLL) ];\
	    then	$(MAKE) ARCH=i686 ALL;\
	    fi;\
	done
	$(MAKE) ARCH=i686 ALL
	cp i686/$(MLDLL) .
	cp i686/$(XADLL) .
	cp i686/$(DTCDLL) .
	cp i686/*.lib .
	cp i686/*.exp .
  ifeq ("$(VSVERSION)","9.0")
	cp i686/*.manifest .
  endif
endif

$(SHLIB): $(ALTERED_ODBC_SRCS) odbcmlsql_setup.c config.status
# WAS	    LDFLAGS="-L$(SQL_DIR) -L$(UNIXODBC_DIR)/lib/$(MAKE_EXT)"
#	    CPPFLAGS="-DMARKLOGIC -DSQLCOLATTRIBUTE_SQLLEN
#	    LDFLAGS="-L$(SQL_DIR) $(OPENSSL_LIBS)" 
#		LD_LIBRARY_PATH=$(OPENSSL_LIB_DIR) 
	$(MAKE) \
	    CPPFLAGS="-DMARKLOGIC -DSQLCOLATTRIBUTE_SQLLEN $(INCLUDES) $(MLFLAGS)" \
		LDFLAGS="-L$(SQL_DIR)" \
	    LIBS="-lmlq -lpthread -lodbcinst" \
	    ml
	cp .libs/$@ .

with-static-client-lib: $(ALTERED_ODBC_SRCS) odbcmlsql_setup.c config.status
	$(MAKE) \
	    CPPFLAGS="-DMARKLOGIC -DSQLCOLATTRIBUTE_SQLLEN \
                      $(INCLUDES) $(MLFLAGS)" \
	    LDFLAGS="-L$(SQL_DIR)" \
	    LIBS="$(SQL_DIR)/src/interfaces/libpq/libmlq.a \
		  -lssl -lpthread -lodbcinst" \
	ml
	cp .libs/$@ .

touch:
	touch $(ALTERED_ODBC_SRCS)

debug-client:
	$(MAKE) touch
	$(MAKE) odbc-shlib MLFLAGS=-DMARKLOGIC_DEBUG

ifeq "$(WINDIR)" ""
config.status:
##	export LDFLAGS="-L$(SQL_DIR) -L$(UNIXODBC_DIR)/lib/$(MAKE_EXT)"; 
#	export LDFLAGS="-L$(SQL_DIR) $(OPENSSL_LIBS)"; \
#	export LD_LIBRARY_PATH=$(OPENSSL_LIB_DIR); \
#	./configure
	touch ./config.status
endif

ifneq "$(WINDIR)" ""
msi: ../SqlClient/amd64/libmlq.dll
	@if [ ! -f "amd64/$(SHLIB)" ];\
	then $(MAKE) odbc-shlib;\
	fi
	cp ../SqlClient/amd64/libmlq.dll ./amd64
	cp ../SqlClient/amd64/mlsql.exe ./amd64

  ifeq ("$(VSVERSION)","9.0")
	cp ../SqlClient/amd64/libmlq.dll.manifest ./amd64
  endif
	cd $(INSTALLER);\
	./Make.bat $(VERSION)
	cp $(INSTALLER)/mlsqlodbc.msi ./$(PKG_NAME).msi

package:
	@if [ "$(ARCH)" = "i686" ];\
	then	$(MAKE) msi32;\
		$(MAKE) zip32;\
	else	$(MAKE) msi;\
		$(MAKE) zip;\
	fi

tarz:
	@if [ ! -f $(PKG_NAME).msi ];\
	then	if [ "$(ARCH)" = "i686" ];\
		then	$(MAKE) msi32;\
		else	$(MAKE) msi;\
		fi;\
	fi
	tar cvzf $(PKG_NAME).tar.gz readme.txt $(PKG_NAME).msi

tarz32:
	$(MAKE) tarz ARCH=i686

zip:
	@if [ ! -f $(PKG_NAME).msi ];\
	then	if [ "$(ARCH)" = "i686" ];\
		then	$(MAKE) msi32;\
		else	$(MAKE) msi;\
		fi;\
	fi
ifneq "$(@shell which zip)" "/usr/bin/zip"
	jar cvMf $(PKG_NAME).zip readme.txt $(PKG_NAME).msi
else
	zip -r $(PKG_NAME).zip readme.txt $(PKG_NAME).msi
endif

zip32:
	$(MAKE) zip ARCH=i686
endif

ifeq "$(shell uname -s)" "Linux"
package-setup: ../SqlClient/libmlq.so ../SqlClient/mlsql
	@if [ ! -f "$(SHLIB)" ];\
	then $(MAKE) odbc-shlib;\
	fi
	$(RM) $(RMFLAGS) -r linux/package spec .rpmmacros .rpmrc
	umask 022; mkdir -p linux/package/RPMS/$(ARCH) linux/package/root/opt/MarkLogic/lib/odbc linux/package/root/opt/MarkLogic/odbc/ssl linux/package/root/opt/MarkLogic/bin linux/package/root/opt/MarkLogic/templates
	cp -fp ../SqlClient/libmlq.so linux/package/root/opt/MarkLogic/lib/odbc/
	cp -fp ../SqlClient/mlsql linux/package/root/opt/MarkLogic/bin/
	cp -fpP $(OPENSSL_LIB_DIR)/libssl* linux/package/root/opt/MarkLogic/lib/odbc/
	cp -fpP $(OPENSSL_LIB_DIR)/libcrypto* linux/package/root/opt/MarkLogic/lib/odbc/
	cp -fp $(OPENSSL_DIR)/linux/ssl/*.cnf linux/package/root/opt/MarkLogic/odbc/ssl/
	cp -fp mlodbcinst linux/package/root/opt/MarkLogic/bin/
	cp -fp mlsqlodbcw.so linux/package/root/opt/MarkLogic/lib/odbc/
	cp -fp linux/templates/mlsql_driver.template linux/package/root/opt/MarkLogic/templates/
	cp -fp linux/templates/mlsql.template linux/package/root/opt/MarkLogic/templates/
	cp -fp NOTICE-ODBCDRIVER.txt linux/package/root/opt/MarkLogic/

package: export PATH := $(RPM_BUILD_PATH)
package: package-setup spec .rpmmacros .rpmrc
	$(RM) $(RMFLAGS) $(PKG_NAME).rpm
	rpmbuild --version
	HOME=linux/package rpmbuild --bb --buildroot `pwd`/linux/package/root --dbpath `pwd`/linux/package spec
	rpm -Kv linux/package/RPMS/$(ARCH)/$(PKG_NAME).rpm
	cp linux/package/RPMS/$(ARCH)/$(PKG_NAME).rpm .

spec: linux/$(INSTALLER)/mkspec
	$(RM) $(RMFLAGS) $@
	./linux/$(INSTALLER)/mkspec $(RELEASE) $(RPM_RELEASE) >$@
	cp $@ linux/package

.rpmmacros: linux/$(INSTALLER)/mkrpmmacros
	$(RM) $(RMFLAGS) $@
	./linux/$(INSTALLER)/mkrpmmacros >$@
	cp $@ linux/package

.rpmrc: linux/$(INSTALLER)/mkrpmrc
	$(RM) $(RMFLAGS) $@
	./linux/$(INSTALLER)/mkrpmrc >$@
	cp $@ linux/package

clean-rpm:
	$(RM) $(RMFLAGS) spec .rpmmacros .rpmrc $(PKG_NAME).rpm
	$(RM) $(RMFLAGS) -r linux/package
endif

ifneq "$(WINDIR)" ""
msi32: ../SqlClient/i686/libmlq.dll
	@if [ ! -f "i686/$(SHLIB)" ];\
	then $(MAKE) allwin32;\
	fi
	cp ../SqlClient/i686/libmlq.dll ./i686
	cp ../SqlClient/i686/mlsql.exe ./i686	
 ifeq ("$(VSVERSION)","9.0")
	cp ../SqlClient/i686/libmlq.dll.manifest ./i686
 endif
	cd $(INSTALLER);\
	./Make32.bat $(VERSION)
	cp $(INSTALLER)/mlsqlodbc_32.msi ./$(PKG_NAME).msi
endif

ifneq "$(WINDIR)" ""
clean-msi-64:
	cd $(INSTALLER);\
	rm -f mlsqlodbc.msi;\
	rm -f mlsqlodbc.wixpdb;\
	rm -f mlsqlodbc.wixobj;\
	rm -f mlsqlodbc.msm;\
	rm -f mlsqlodbcm.wixobj

clean-msi-32:
	cd $(INSTALLER);\
	rm -f mlsqlodbc_32.msi;\
	rm -f mlsqlodbc_32.wixpdb;\
	rm -f mlsqlodbc_32.wixobj;\
	rm -f mlsqlodbc_32.msm;\
	rm -f mlsqlodbcm_32.wixobj

clean-msi: clean-msi-64 clean-msi-32
endif

ifneq "$(WINDIR)" ""
clean-base:
	rm -f *.obj
	rm -f *.lib
	rm -f *.exp
	rm -f $(MLDLL).manifest
	rm -f $(XADLL).manifest
	rm -f $(DTCDLL).manifest

clean32: clean-msi-32 clean-base
	if [ -d i686 ];\
	then	$(MAKE) CLEAN ARCH=i686;\
	fi

clean64: clean-msi-32 clean-base
	if [ -d amd64 ];\
	then	$(MAKE) CLEAN ARCH=amd64;\
	fi

clean: clean-msi clean-base
	if [ -d i686 ];\
	then	$(MAKE) CLEAN ARCH=i686;\
	fi
	if [ -d amd64 ];\
	then	$(MAKE) CLEAN ARCH=amd64;\
	fi
else
clean-base:
	rm -f $(SHLIB) mlsqlodbcw.la ./.libs/*.o *.lo

clean: clean-base clean-rpm
	rm -f config.status
endif

# Clean and make all, but skip running 'configure'
noconfig: clean-base
	$(MAKE) $(SHLIB)

# Make all, without clean (or 'configure')
ifneq "$(WINDIR)" ""
finish:
	-@for i in 1 2 3 4 5 6 7 8;\
	do  if [ ! -f $(ARCH)/$(MLDLL) ];\
	    then	$(MAKE) ALL;\
	    fi;\
	done
	$(MAKE) ALL
	cp $(ARCH)/$(MLDLL) .
	cp $(ARCH)/$(XADLL) .
	cp $(ARCH)/$(DTCDLL) .
	cp $(ARCH)/*.lib .
	cp $(ARCH)/*.exp .
	cp $(ARCH)/*.manifest .
else
finish: $(SHLIB)
endif

ifeq "$(shell uname -s)" "Darwin"
package-setup: ../SqlClient/libmlq.dylib ../SqlClient/mlsql
	@if [ ! -f "$(SHLIB)" ];\
	then $(MAKE) odbc-shlib;\
	fi
	$(RM) -r $(MACINSTALLPKGROOT) $(MACINSTALLIMAGE)
	umask 022; mkdir -p $(MACINSTALLTEMP) $(MACINSTALLPKGROOT) $(MACINSTALLIMAGE) $(MACINSTALLLIB) $(MACINSTALLBIN) $(MACINSTALLTEMPLATE)
	cp -fp mlsqlodbcw.dylib $(MACINSTALLLIB)
	cp -fp $(SQL_DIR)/libmlq.dylib $(MACINSTALLLIB)
	cp -fp $(SQL_DIR)/mlsql $(MACINSTALLBIN)
	cp -fp mlodbcinst $(MACINSTALLBIN)
	cp -fp macosx/templates/mlsql_driver.template $(MACINSTALLTEMPLATE)
	cp -fp macosx/templates/mlsql.template $(MACINSTALLTEMPLATE)
	cp -fp NOTICE-ODBCDRIVER.txt $(MACINSTALLPKGROOT)

package-make: package-setup
	#$(PACKAGEMAKER) -build -p $(PACKAGEPATH) -f $(MACINSTALLPKGROOT) \
		-i $(MACINSTALLCONF)/Info.plist -r $(MACINSTALLRES)
	$(PACKAGEMAKER) --root $(MACINSTALLPKGROOT) --version 1 --scripts $(MACINSTALLRES) --identifier $(IDENTIFIER) --install-location /Users/Shared/MarkLogicInstall $(MLPKG)
	cp $(MACINSTALLTEMP)/distribution.xml $(MACINSTALLIMAGE)
	productbuild --distribution $(MACINSTALLIMAGE)/distribution.xml --resources $(MACINSTALLRES) --package-path $(MACINSTALLIMAGE) $(PACKAGEPATH)
	chmod -R 755 $(MACINSTALLIMAGE)
	$(RM) -r $(DISKIMAGEPATH)
	-$(DISKIMAGER) create -imagekey zlib-level=9 \
		-srcfolder $(PACKAGEPATH) -volname $(MACPACKAGENAME) \
		$(DISKIMAGEPATH)
package: package-make
	cp -fp $(DISKIMAGEPATH) .

clean-rpm: 
	$(RM) $(RMFLAGS) $(PKG_NAME).dmg $(DISKIMAGEPATH)
	$(RM) $(RMFLAGS) -r $(MACINSTALLPKGROOT) $(MACINSTALLIMAGE)
endif
