From 1eab86e26da7d6a18d8acc4c320d72b0df2527b7 Mon Sep 17 00:00:00 2001 From: "Thomas G. Lockhart" Date: Tue, 6 Oct 1998 05:58:41 +0000 Subject: [PATCH] Update source code to Byron's v6.30.0250 sources plus minor cleanup to get rid of unused variables. Get clean compile on Linux (Thomas and Gerald). Implement autoconf/configure for standalone builds and use the existing autoconf/configure system when in the Postgres source tree. Code tests and functions with ApplixWare-4.4.1beta on a Linux box. Changes should be backward compatible with WIN32 but still needs testing. --- src/interfaces/odbc/Config.mk | 1 - src/interfaces/odbc/GNUmakefile.in | 127 ++ src/interfaces/odbc/Makefile.global.in | 201 ++++ src/interfaces/odbc/Makefile.unx | 85 -- src/interfaces/odbc/README.Linux | 113 -- src/interfaces/odbc/TODO.txt | 16 + src/interfaces/odbc/Version.mk | 6 +- src/interfaces/odbc/acconfig.h | 2 + src/interfaces/odbc/bind.c | 33 +- src/interfaces/odbc/columninfo.c | 2 +- src/interfaces/odbc/columninfo.h | 2 +- src/interfaces/odbc/config.guess | 694 +++++++++++ src/interfaces/odbc/config.h.in | 25 + src/interfaces/odbc/config.status | 261 +++++ src/interfaces/odbc/config.sub | 930 +++++++++++++++ src/interfaces/odbc/configure | 1991 ++++++++++++++++++++++++++++++++ src/interfaces/odbc/configure.in | 317 +++++ src/interfaces/odbc/connection.c | 253 ++-- src/interfaces/odbc/connection.h | 14 +- src/interfaces/odbc/convert.c | 44 +- src/interfaces/odbc/dlg_specific.c | 218 ++-- src/interfaces/odbc/dlg_specific.h | 30 +- src/interfaces/odbc/drvconn.c | 24 +- src/interfaces/odbc/environ.c | 7 +- src/interfaces/odbc/environ.h | 4 +- src/interfaces/odbc/execute.c | 74 +- src/interfaces/odbc/gpps.c | 20 +- src/interfaces/odbc/gpps.h | 6 +- src/interfaces/odbc/info.c | 892 ++++++++------ src/interfaces/odbc/install-sh | 250 ++++ src/interfaces/odbc/iodbc.h | 6 +- src/interfaces/odbc/misc.c | 55 +- src/interfaces/odbc/misc.h | 26 +- src/interfaces/odbc/options.c | 24 +- src/interfaces/odbc/parse.c | 20 +- src/interfaces/odbc/pgtypes.c | 6 +- src/interfaces/odbc/psqlodbc.c | 16 +- src/interfaces/odbc/psqlodbc.h | 15 +- src/interfaces/odbc/psqlodbc.rc | 8 +- src/interfaces/odbc/qresult.c | 2 +- src/interfaces/odbc/qresult.h | 5 +- src/interfaces/odbc/readme.txt | 23 + src/interfaces/odbc/results.c | 153 +-- src/interfaces/odbc/socket.c | 7 +- src/interfaces/odbc/socket.h | 7 +- src/interfaces/odbc/statement.c | 48 +- src/interfaces/odbc/statement.h | 17 +- src/interfaces/odbc/tuple.c | 3 +- src/interfaces/odbc/tuple.h | 6 +- 49 files changed, 6089 insertions(+), 1000 deletions(-) create mode 100644 src/interfaces/odbc/GNUmakefile.in create mode 100644 src/interfaces/odbc/Makefile.global.in delete mode 100644 src/interfaces/odbc/Makefile.unx delete mode 100644 src/interfaces/odbc/README.Linux create mode 100644 src/interfaces/odbc/TODO.txt create mode 100644 src/interfaces/odbc/acconfig.h create mode 100755 src/interfaces/odbc/config.guess create mode 100644 src/interfaces/odbc/config.h.in create mode 100644 src/interfaces/odbc/config.status create mode 100755 src/interfaces/odbc/config.sub create mode 100755 src/interfaces/odbc/configure create mode 100644 src/interfaces/odbc/configure.in create mode 100644 src/interfaces/odbc/install-sh diff --git a/src/interfaces/odbc/Config.mk b/src/interfaces/odbc/Config.mk index e08ca2dfcc..9622ccb84e 100644 --- a/src/interfaces/odbc/Config.mk +++ b/src/interfaces/odbc/Config.mk @@ -1,4 +1,3 @@ - # # # diff --git a/src/interfaces/odbc/GNUmakefile.in b/src/interfaces/odbc/GNUmakefile.in new file mode 100644 index 0000000000..8feee81ef4 --- /dev/null +++ b/src/interfaces/odbc/GNUmakefile.in @@ -0,0 +1,127 @@ +#------------------------------------------------------------------------- +# +# Makefile.inc-- +# Build and install postgres. +# +# Copyright (c) 1994, Regents of the University of California +# +# +# IDENTIFICATION +# $Header: /cvsroot/pgsql/src/interfaces/odbc/Attic/GNUmakefile.in,v 1.1 1998/10/06 05:57:56 thomas Exp $ +# +#------------------------------------------------------------------------- +@SET_MAKE@ + +NAME = psqlodbc +SRCDIR=@srcdir@ +ODBCSRCDIR=@srcdir@ +include $(ODBCSRCDIR)/Makefile.global + +include Version.mk +PORTNAME= @PORTNAME@ + +FIND = @find@ + +# assuming gnu tar and split here +TAR = @tar@ +SPLIT = @split@ + +ifeq ($(PORTNAME), linux) + install-shlib-dep := install-shlib + shlib := lib$(NAME)$(DLSUFFIX).$(SO_MAJOR_VERSION).$(SO_MINOR_VERSION) + LDFLAGS_SL = -shared -soname lib$(NAME)$(DLSUFFIX).$(SO_MAJOR_VERSION) + LDFLAGS_SL += -Bsymbolic $(LDFLAGS) -lc -lm + CFLAGS += -I. $(CFLAGS_SL) +endif + +ifeq ($(PORTNAME), bsd) + ifdef BSD_SHLIB + install-shlib-dep := install-shlib + shlib := lib$(NAME)$(DLSUFFIX).$(SO_MAJOR_VERSION).$(SO_MINOR_VERSION) + LDFLAGS_SL = -x -Bshareable -Bforcearchive $(LDFLAGS) + CFLAGS += -I. $(CFLAGS_SL) + endif +endif + +SOURCES = *.c *.h *.in Config.mk Makefile Makefile.unx README.Linux \ + TODO.txt Version.mk config.guess config.sub configure \ + install-sh license.txt notice.txt odbcinst.ini patch \ + psqlodbc.aps psqlodbc.def psqlodbc.mak psqlodbc.mdp \ + psqlodbc.ncb psqlodbc.rc readme.txt + +OBJECTS = info.o bind.o columninfo.o connection.o convert.o drvconn.o \ + environ.o execute.o lobj.o misc.o options.o \ + pgtypes.o psqlodbc.o qresult.o results.o socket.o parse.o statement.o \ + gpps.o tuple.o tuplelist.o dlg_specific.o $(OBJX) + +CFLAGS += @DEFS@ + +all: libpsqlodbc.a $(shlib) + +libpsqlodbc.a: $(OBJECTS) + $(AR) $(AROPT) libpsqlodbc.a $(OBJS) + $(RANLIB) libpsqlodbc.a + +$(shlib): $(OBJECTS) + $(LD) $(LDFLAGS_SL) $(OBJECTS) \ + -o $(shlib) $(LIBS) + +.PHONY: beforeinstall-headers + +.PHONY: install + +install: $(HEADERDIR) $(LIBDIR) $(ODBCINST) install-headers \ + install-libpsqlodbc install-ini $(install-shlib-dep) + +$(HEADERDIR) $(LIBDIR) $(ODBCINST): + mkdir -p $@ + +install-headers: beforeinstall-headers isql.h isqlext.h iodbc.h + $(INSTALL) $(INSTLOPTS) iodbc.h $(HEADERDIR)/iodbc/iodbc.h + $(INSTALL) $(INSTLOPTS) isql.h $(HEADERDIR)/iodbc/isql.h + $(INSTALL) $(INSTLOPTS) isqlext.h $(HEADERDIR)/iodbc/isqlext.h + +beforeinstall-headers: + @if [ ! -d $(HEADERDIR)/iodbc ]; then mkdir -p $(HEADERDIR)/iodbc; fi + +install-libpsqlodbc: libpsqlodbc.a + $(INSTALL) $(INSTL_LIB_OPTS) libpsqlodbc.a $(DESTDIR)$(LIBDIR)/lib$(NAME).a + +install-shlib: $(shlib) + $(INSTALL) $(INSTL_LIB_OPTS) $(shlib) $(DESTDIR)$(LIBDIR)/$(shlib) + rm -f $(DESTDIR)$(LIBDIR)/lib$(NAME)$(DLSUFFIX) + rm -f $(DESTDIR)$(LIBDIR)/lib$(NAME)$(DLSUFFIX).$(SO_MAJOR_VERSION) + cd $(DESTDIR)$(LIBDIR) && $(LN_S) -f $(shlib) lib$(NAME)$(DLSUFFIX).$(SO_MAJOR_VERSION) + cd $(DESTDIR)$(LIBDIR) && $(LN_S) -f lib$(NAME)$(DLSUFFIX).$(SO_MAJOR_VERSION) lib$(NAME)$(DLSUFFIX) + +install-ini: odbcinst.ini + $(INSTALL) $(INSTL_LIB_OPTS) odbcinst.ini $(ODBCINST)/odbcinst.ini + +depend dep: + $(CC) -MM *.c >depend + +.PHONY: clean + +clean: + -rm -f lib$(NAME).a $(shlib) $(OBJECTS) lib$(NAME)$(DLSUFFIX) + -rm -f config.log config.cache config.status + +.PHONY: distclean + +distclean: clean + -rm -f config.h GNUmakefile Makefile.global + +.PHONY: standalone + +standalone: + -rm -f psqlodbc-$(SO_MAJOR_VERSION)$(SO_MINOR_VERSION).tar.gz + tar -cf psqlodbc-$(SO_MAJOR_VERSION)$(SO_MINOR_VERSION).tar $(SOURCES) + tar -r -C ../.. -f psqlodbc-$(SO_MAJOR_VERSION)$(SO_MINOR_VERSION).tar template + gzip psqlodbc-$(SO_MAJOR_VERSION)$(SO_MINOR_VERSION).tar + +.PHONY: integrated + +integrated: + -rm -f psqlodbc-$(SO_MAJOR_VERSION)$(SO_MINOR_VERSION)-int.tar.gz + tar -cf psqlodbc-$(SO_MAJOR_VERSION)$(SO_MINOR_VERSION)-int.tar $(SOURCES) + gzip psqlodbc-$(SO_MAJOR_VERSION)$(SO_MINOR_VERSION)-int.tar diff --git a/src/interfaces/odbc/Makefile.global.in b/src/interfaces/odbc/Makefile.global.in new file mode 100644 index 0000000000..f074cb1093 --- /dev/null +++ b/src/interfaces/odbc/Makefile.global.in @@ -0,0 +1,201 @@ +#---------------------------------------------------------------------------- +# +# Makefile.global-- +# global configuration for the Makefiles +# +# Copyright (c) 1994, Regents of the University of California +# +# +# IDENTIFICATION +# $Header: /cvsroot/pgsql/src/interfaces/odbc/Attic/Makefile.global.in,v 1.1 1998/10/06 05:57:56 thomas Exp $ +# +# NOTES +# This is derived from the main Postgres makefile. +# +# When running standalone: +# To override the default setting, create a Makefile.custom in this +# directory and put your defines there. (Makefile.custom is included +# near the end of this file). Sometimes, a variable gets set in +# Makefile.global after Makefile.custom has been included, so you can't +# simply set that variable in Makefile.custom. In those cases, there is +# often another variable (like CUSTOM_COPT) that you can set in +# Makefile.custom that influences the later setting of the true variable +# of interest (like CFLAGS) by Makefile.global. +# +# +# If you change any of these defines you probably have to +# make clean; make +# since no dependencies are created for these. (of course you can +# be crafty and check what files really depend on them and just remake +# those). +# +# Before including this file, you must set the SRCDIR variable to the +# path of the top of the Postgres source tree (the directory that +# contains this file). +# +#------------------------------------------------------------------------- + + +############################################################################## +# +# CONFIGURATION SECTION +# +# Following are settings pertaining to the postgres build and +# installation. +# of the port. +# +# Ignore LINUX_ELF if you're not using Linux. But if you are, and you're +# compiling to a.out (which means you're using the dld dynamic loading +# library), set LINUX_ELF to null in Makefile.custom. +LINUX_ELF= true +# +# Ignore BSD_SHLIB if you're not using one of the BSD ports. But if you +# are, and it's one that doesn't have shared libraries (NetBSD/vax is an +# example of this), set BSD_SHLIB to null in Makefile.custom. +BSD_SHLIB= true + +# For convenience, POSTGRESDIR is where BINDIR, and LIBDIR +# and other target destinations are rooted. Of course, each of these is +# changable separately. + +POSTGRESDIR=@prefix@ + +# Where the postgres executables live (changeable by just putting them +# somewhere else and putting that directory in your shell PATH) +BINDIR= $(POSTGRESDIR)/bin + +# Where libpsqlodbc.a gets installed. You must put it where your loader will +# look for it if you wish to use the -lpq convention. Otherwise you +# can just put the absolute pathname to the library at the end of your +# command line. + +LIBDIR= $(POSTGRESDIR)/lib + +# Where the man pages (suitable for use with "man") get installed. +POSTMANDIR= $(POSTGRESDIR)/man + +# Where the formatted documents (e.g., the reference manual) get installed. +POSTDOCDIR= $(POSTGRESDIR)/doc + +# Where the header files necessary to build frontend programs get installed. +HEADERDIR= $(POSTGRESDIR)/include + +# Where the odbcinst.ini file will be placed + +ODBCINST= $(POSTGRESDIR)@ODBCINSTDIR@ + +############################################################################## +# +# FEATURES +# +# To disable a feature, comment out the entire definition +# (that is, prepend '#', don't set it to "0" or "no"). + +############################################################################## +# +# Installation. +# +# For many ports, INSTALL is overridden below. +INSTALL= @INSTALL@ +RANLIB= @RANLIB@ + +INSTLOPTS= @INSTLOPTS@ +INSTL_EXE_OPTS= @INSTL_EXE_OPTS@ +INSTL_LIB_OPTS= @INSTL_LIB_OPTS@ + +############################################################################## +# +# For building shell scripts: +# +# For many ports, these are overridden below. + +# DASH_N is what we put before the text on an echo command when we don't +# want a trailing newline. BACKSLASH_C is what we put at the end of the +# string on a echo command when we don't want a trailing newline. On +# some systems, you do echo -n "no newline after this", while on others +# you do echo "no newline after this\c". + +DASH_N= @DASH_N@ +BACKSLASH_C= @BACKSLASH_C@ + + + +#------------------------------------------------------------- +# See the subdirectory template for default settings for these +#------------------------------------------------------------- +CC= @CC@ +AROPT= @AROPT@ +CFLAGS= -I$(ODBCSRCDIR) @CPPFLAGS@ @CFLAGS@ +CFLAGS_SL= @SHARED_LIB@ +LDFLAGS= @LDFLAGS@ @LIBS@ +DLSUFFIX= @DLSUFFIX@ +LN_S = @LN_S@ + +############################################################################## +# +# Customization. +# +# This includes local customizations. If we're being build from +# within the Postgres distribution and a Makefile.custom exists +# in the top level Postgres directory it overrides any local customization +# that might be in Makefile.custom of the odbc driver directory. These +# files don't exist in the original +# distribution so that they don't get overwritten when you upgrade. + +ifneq ($(wildcard $(SRCDIR)/Makefile.custom), ) +include $(SRCDIR)/Makefile.custom +endif + +ifneq ($(wildcard ../../Makefile.custom), ) +include ../../Makefile.custom +endif + +# This goes here so that customization in Makefile.custom is effective +############################################################################## + +ifneq ($(CUSTOM_INSTALL),) +INSTALL= $(CUSTOM_INSTALL) +endif + +# +# Flags for CC and LD. + +############################################################################## +# COPT +# +# COPT is for options that the sophisticated builder might want to vary +# from one build to the next, like options to build Postgres with debugging +# information included. COPT is meant to be set on the make command line, +# for example with the command "make COPT=-g". The value you see set here +# is the default that gets used if the builder does not give a value for +# COPT on his make command. +# +# There is a nonobvious relationship between -O (optimization) and +# -Werror (consider all warnings fatal). On some systems, if you don't +# optimize, you will always get some warnings because the system header +# files will include some unreferenced functions in the code. These are +# functions that are supposed to be inline, so there wouldn't ordinarily +# be an "unreferenced" problem, but if you don't enable optimization, no +# inlining can happen, and hence the problem. Therefore, we include +# if you override -O, you override -Werror as well. +# +# CUSTOM_COPT is something the user may set in Makefile.custom + +# Common values for COPT are: -g for debuggable binaries, -m486 if you are +# using a i486 or better. + +ifneq ($(CUSTOM_CC),) + CC= $(CUSTOM_CC) +endif + +ifneq ($(CUSTOM_COPT),) + COPT= $(CUSTOM_COPT) +endif + +ifeq ($(CC), gcc) +CFLAGS+= -Wall -Wmissing-prototypes +endif + +ifdef COPT + CFLAGS+= $(COPT) +endif diff --git a/src/interfaces/odbc/Makefile.unx b/src/interfaces/odbc/Makefile.unx deleted file mode 100644 index 6d85483662..0000000000 --- a/src/interfaces/odbc/Makefile.unx +++ /dev/null @@ -1,85 +0,0 @@ - -# .include "Version.mk" -# .include "Config.mk" -include Version.mk -include Config.mk -#============================================================================== -# Makefile -# -# UNIX Makefile to build the CLI for PostgreSQL/Postgres95 -# -#============================================================================== -# Site specific configuration (UNIX) -#============================================================================== -# -# option switches -# -# debug: select this to enable debugging of the software -#DEBUG = -D_DEBUG -# -#============================================================================== - -#---| definitions |------------------------------------------------------------ - -# NAME = cli -NAME = psqlodbc - -OBJECTS = info.o bind.o columninfo.o connection.o convert.o drvconn.o \ - environ.o execute.o lobj.o misc.o options.o \ - pgtypes.o psqlodbc.o qresult.o results.o socket.o statement.o \ - gpps.o tuple.o tuplelist.o dlg_specific.o $(OBJX) - -#CFLAGS = -c $(DEBUG) -D$(PG_ENV) -O $(PIC) $(ANSI) -I$(PG_INCLUDE) \ -# -I$(ODBC_INCLUDE) -D$(DLDAPI) $(CFLAGSX) -DHAVE_CONFIG_H \ -# -DVERSION=\"$(VERSION)$(EXTVER)\" -CFLAGS = -g -c -Wall $(DEBUG) -O $(PIC) $(ANSI) -I. -I.. \ - -I$(PG_INCLUDE) -I$(ODBC_INCLUDE) $(CFLAGSX) -DHAVE_CONFIG_H - -shlib = lib$(NAME)-$(VERSION).$(DLSUFFIX) -DESTDIR = /usr/local -LIBDIR = /lib - -#---| global dependencies |---------------------------------------------------- - -#all: $(OBJECTS) lib dll - -all: $(OBJECTS) dll - -clean: - -rm -f core *.o *~ *.core - -delete: clean - -delete_all: delete - -rm -f /usr/local/lib/lib$(NAME)_$(MSQL_ENV).a - -rm -f /usr/local/lib/lib$(NAME)_$(MSQL_ENV).$(DLSUFFIX) - -#---| local dependencies |----------------------------------------------------- -#log.o: ../SRC_LOG/log.c ../SRC_LOG/log.h -# $(CC) $(CFLAGS) -I../SRC_LOG ../SRC_LOG/log.c - -lib: - $(AR) lib$(NAME)$(PG_ENV).a $(OBJECTS) - $(RANLIB) lib$(NAME)$(PG_ENV).a - -dll: $(OBJECTS) - $(LD) $(LDFLAGS) -L$(PG_LIBPATH) $(OBJECTS) \ - -o $(shlib) $(LIBS) $(PG_LIBS) - -install-shlib: $(shlib) - $(INSTALL_DATA) $(shlib) $(DESTDIR)$(LIBDIR)/$(shlib) - rm -f $(DESTDIR)$(LIBDIR)/lib$(NAME).so - ln -sf $(shlib) $(DESTDIR)$(LIBDIR)/lib$(NAME).so - -install-headers: $(INSTHEADERS) - if [ -d $(DESTDIR)$(INCDIR)/iodbc ]; then : ; else $(MKDIR) $(DESTDIR)$(INCDIR)/iodbc; fi - $(INSTALL_DATA) $(INSTHEADERS) $(DESTDIR)$(INCDIR)/iodbc - -install-ini: odbcinst.ini - $(INSTALL_DATA) odbcinst.ini /etc - -install: install-headers install-shlib install-ini - -#============================================================================== - - diff --git a/src/interfaces/odbc/README.Linux b/src/interfaces/odbc/README.Linux deleted file mode 100644 index ecb2403d95..0000000000 --- a/src/interfaces/odbc/README.Linux +++ /dev/null @@ -1,113 +0,0 @@ - -Unix port of psqlodbc, brought to you by: - Gerald Gryschuk(ggryschuk@home.com) - -This is the first release of a port of psqlodbc to Unix(specifically Linux), -as such the installation may not be as straight forward as it could be(then -again it might be). As well the only testing of the driver has been with -the real project I'm working on, since it seems to be working there I assumed -it was ready to go out. This port works with Ke Jin's iodbc driver manager -although there is no theoretical reason why it couldn't work with other -driver managers for UNIX(I know of none though). The FreeODBC site -(http://users.ids.net/~bjepson/freeODBC/) has a link to download the current -version of iodbc(iodbc-2.12). - -This driver has been successfully compiled and tested on a RedHat 4.1 system -using both gcc 2.7.2 and egcs 1.0.2. - -INSTALLATION: - -If you have a system any where close to mine this will be easy, just -copy Makefile.lnx to Makefile then type 'make' and see what happens. Note -that if you have not enabled logging(read the file misc.h) then you -may get alot of warning messages, just ignore these, they shouldn't be -a problem. If this doesn't work, well... I don't know what to say, see if - you can figure out what's wrong,fix it and send me a message. If everything - makes o.k. you can 'make install' which will install the shared library -(in /usr/local/lib) and a WINDOWS type INI file in /etc (called odbcinst.ini, - see CONFIGURATION below). If you want to program using this driver do a -'make install-headers' which will install programming header files in -/usr/local/include/iodbc. If you don't like these install locations edit - Config.mk and change the environment variable DESTDIR(and possible DESTINCDIR - to get rid of the /iodbc) to suit your system. - -CONFIGURATION: - -The psqlodbc driver reads two Windows type INI files for configuration, -one called odbcinst.ini located in /etc which is used for system wide -configuration of the driver and one in the users home directory called -.odbc.ini, which can be used to override the system wide settings. Note that -the location of odbcinst is currently hardcoded into the source so if you -want to change this you have to change it in the source as well. This latter -file is also searched for by iodbc and is where -the DataSource definitions are placed. The format of both files is exactly -like that of a Windows INI file using key,value pairs. A DataSource definition -is started with a section name enclosed in square brackets i.e. [PostODBC]. -Comments are started using a ';' character and are restricted to being -only on seperate lines(i.e. no comments are allowed on definition lines). -The important keywords for psqlodbc are: - Driver = (location where the psqlodbc library was installed) - ex. Driver = /usr/local/lib/libpspqlodbc.so - - ServerName = hostname or ip-address of postgreSQL server - ex. ServerName = simpsons.springfield.com - or ServerName = 192.1.1.1 - - Database = name of database to connect to - ex. Database = template1 - - Port = tcp port that the postgreSQL server is listening on, note - that this need not be set as the driver defaults to the - default postgreSQL port of 5432. Of course if your server - is listening on a different port than you need to say - what it is here. - - Username = name of authorized postgreSQL user - ex. Username = homer - - Password = the password for the user named in Username. Note - that if you have password checking on in postgreSQL - you have to have this field. Unfortunately this means - storing clear text passwords in a file. If this bothers - you, well... write a dialog box routine and send it - to me. - ex. Password = Doh! - - ReadOnly = 0 or 1. Default is 1 => database IS readonly. If - set to 0, database is read-write. - ex. ReadOnly = 0 - - Protocol = 6.2 to force the use of Postgres 6.2 protocol - -The odbcinst.ini file is where sytem wide settings are kept. There are -quite a number of these, all of which have built-in defaults. Since I'm -not even sure what they are all for I won't try to describe them, check -the file dlg_specific.h for a list and some explanation. Two that I found -useful are Debug and CommLog, which can be used to tailor logging of messages -by the driver(note that you have to have defined MY_LOG and Q_LOG during -compilation of the driver, see the file misc.h for an explanation). If -you have logging On(ie. CommLog = 1 and/or Debug = 1) then logging will -occur to the files /tmp/mylog.log(Debug, only developers will be -interested) and /tmp/psqlodbc.log(end user log file). - -USE: - run an ODBC enabled application :-) . - - O.k. Well, the only ODBC compliant applications that I can - "guarantee" to work are those that are compiled using the following - headers that come with this driver, iodbc.h, isql.h and isqlext.h. - -BUGS,etc. - - If you have problems with compiling/installing or making this - package send e-mail to me at: - gerald.gryschuk@home.com or to the pgsql-interfaces mailing list - pgsql-interfaces@postgresql.org . - - Ports to different Unices are greatly appreciated and can probably be - sent to me for now(although this may change shortly). - - Bugs of a general nature should still be sent to the current - maintainer or to the interfaces list. - - diff --git a/src/interfaces/odbc/TODO.txt b/src/interfaces/odbc/TODO.txt new file mode 100644 index 0000000000..151e65fb8d --- /dev/null +++ b/src/interfaces/odbc/TODO.txt @@ -0,0 +1,16 @@ + +ODBC Driver TO-DO List +Last Updated: 9/16/98 + + +Task Added Priority %Complete? +----------------------------------------------------------------------------------- +Implement 6.4 protocol changes 09/16/98 high +Handle multi-row rowsets (SQLBindCol) 09/16/98 med +Port to 16 bit? 04/20/98 med +Handle Literal precision in parsing 07/01/98 med +Cache SQLColumns at a higher level (henv or dll) 07/02/98 med +Add lo_text type to map to LONGVARCHAR 07/09/98 low +Add encrypted password capability 06/11/98 low +Remove tuplelist structure 06/25/98 low +Support SQLTables "%" semantics 07/01/98 low diff --git a/src/interfaces/odbc/Version.mk b/src/interfaces/odbc/Version.mk index 80a3d63b82..c927772c0b 100644 --- a/src/interfaces/odbc/Version.mk +++ b/src/interfaces/odbc/Version.mk @@ -1,3 +1,5 @@ -VERSION = 0.24 -EXTVER = .2 +VERSION = 0.25 +EXTVER = .0 +SO_MAJOR_VERSION = 0 +SO_MINOR_VERSION = 25 diff --git a/src/interfaces/odbc/acconfig.h b/src/interfaces/odbc/acconfig.h new file mode 100644 index 0000000000..1008cc9793 --- /dev/null +++ b/src/interfaces/odbc/acconfig.h @@ -0,0 +1,2 @@ +/* default path for the location of the odbcinst.ini file */ +#undef ODBCINST diff --git a/src/interfaces/odbc/bind.c b/src/interfaces/odbc/bind.c index a30e4104e2..30e76af255 100644 --- a/src/interfaces/odbc/bind.c +++ b/src/interfaces/odbc/bind.c @@ -14,7 +14,7 @@ */ #ifdef HAVE_CONFIG_H -#include +#include "config.h" #endif #include "bind.h" @@ -25,7 +25,7 @@ #include #include -#ifdef HAVE_IODBC +#ifndef WIN32 #include "iodbc.h" #include "isql.h" #include "isqlext.h" @@ -49,7 +49,9 @@ RETCODE SQL_API SQLBindParameter( SDWORD FAR *pcbValue) { StatementClass *stmt = (StatementClass *) hstmt; -char *func="SQLBindParameter"; +static char *func="SQLBindParameter"; + + mylog( "%s: entering...\n", func); if( ! stmt) { SC_log_error(func, "", NULL); @@ -131,8 +133,7 @@ char *func="SQLBindParameter"; else stmt->parameters[ipar].data_at_exec = FALSE; - mylog("SQLBindParamater: ipar = %d, *pcbValue = %d, data_at_exec = %d\n", - ipar, pcbValue ? *pcbValue: -777, stmt->parameters[ipar].data_at_exec); + mylog("SQLBindParamater: ipar = %d, *pcbValue = %d, data_at_exec = %d\n", ipar, pcbValue ? *pcbValue: -777, stmt->parameters[ipar].data_at_exec); return SQL_SUCCESS; } @@ -149,8 +150,9 @@ RETCODE SQL_API SQLBindCol( SDWORD FAR *pcbValue) { StatementClass *stmt = (StatementClass *) hstmt; -Int2 numcols = 0; -char *func="SQLBindCol"; +static char *func="SQLBindCol"; + + mylog( "%s: entering...\n", func); mylog("**** SQLBindCol: stmt = %u, icol = %d\n", stmt, icol); @@ -230,7 +232,9 @@ RETCODE SQL_API SQLDescribeParam( SWORD FAR *pfNullable) { StatementClass *stmt = (StatementClass *) hstmt; -char *func = "SQLDescribeParam"; +static char *func = "SQLDescribeParam"; + + mylog( "%s: entering...\n", func); if( ! stmt) { SC_log_error(func, "", NULL); @@ -272,7 +276,9 @@ RETCODE SQL_API SQLParamOptions( UDWORD crow, UDWORD FAR *pirow) { -char *func = "SQLParamOptions"; +static char *func = "SQLParamOptions"; + + mylog( "%s: entering...\n", func); SC_log_error(func, "Function not implemented", (StatementClass *) hstmt); return SQL_ERROR; @@ -294,7 +300,9 @@ RETCODE SQL_API SQLNumParams( StatementClass *stmt = (StatementClass *) hstmt; char in_quote = FALSE; unsigned int i; -char *func = "SQLNumParams"; +static char *func = "SQLNumParams"; + + mylog( "%s: entering...\n", func); if(!stmt) { SC_log_error(func, "", NULL); @@ -357,10 +365,11 @@ int i; void extend_bindings(StatementClass *stmt, int num_columns) { +static char *func="extend_bindings"; BindInfoClass *new_bindings; int i; -mylog("in extend_bindings: stmt=%u, bindings_allocated=%d, num_columns=%d\n", stmt, stmt->bindings_allocated, num_columns); +mylog("%s: entering ... stmt=%u, bindings_allocated=%d, num_columns=%d\n", func, stmt, stmt->bindings_allocated, num_columns); /* if we have too few, allocate room for more, and copy the old */ /* entries into the new structure */ @@ -368,6 +377,8 @@ mylog("in extend_bindings: stmt=%u, bindings_allocated=%d, num_columns=%d\n", st new_bindings = create_empty_bindings(num_columns); if ( ! new_bindings) { + mylog("%s: unable to create %d new bindings from %d old bindings\n", func, num_columns, stmt->bindings_allocated); + if (stmt->bindings) { free(stmt->bindings); stmt->bindings = NULL; diff --git a/src/interfaces/odbc/columninfo.c b/src/interfaces/odbc/columninfo.c index c13d9969e9..41e6e74635 100644 --- a/src/interfaces/odbc/columninfo.c +++ b/src/interfaces/odbc/columninfo.c @@ -80,7 +80,7 @@ char new_field_name[MAX_MESSAGE_LEN+1]; CI_set_field_info(self, lf, new_field_name, new_adtid, new_adtsize); } - return SOCK_get_errcode(sock) == 0; + return (SOCK_get_errcode(sock) == 0); } diff --git a/src/interfaces/odbc/columninfo.h b/src/interfaces/odbc/columninfo.h index 8fcf2ad3c7..01c654da84 100644 --- a/src/interfaces/odbc/columninfo.h +++ b/src/interfaces/odbc/columninfo.h @@ -26,7 +26,7 @@ struct ColumnInfoClass_ { #define CI_get_fieldsize(self, col) (self->adtsize[col]) #define CI_get_display_size(self, col) (self->display_size[col]) -ColumnInfoClass *CI_Constructor(); +ColumnInfoClass *CI_Constructor(void); void CI_Destructor(ColumnInfoClass *self); void CI_free_memory(ColumnInfoClass *self); char CI_read_fields(ColumnInfoClass *self, SocketClass *sock); diff --git a/src/interfaces/odbc/config.guess b/src/interfaces/odbc/config.guess new file mode 100755 index 0000000000..a1563dabf1 --- /dev/null +++ b/src/interfaces/odbc/config.guess @@ -0,0 +1,694 @@ +#! /bin/sh +# Attempt to guess a canonical system name. +# Copyright (C) 1992, 93, 94, 95, 1996 Free Software Foundation, Inc. +# +# This file is free software; you can redistribute it and/or modify it +# under the terms of the GNU General Public License as published by +# the Free Software Foundation; either version 2 of the License, or +# (at your option) any later version. +# +# This program is distributed in the hope that it will be useful, but +# WITHOUT ANY WARRANTY; without even the implied warranty of +# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU +# General Public License for more details. +# +# You should have received a copy of the GNU General Public License +# along with this program; if not, write to the Free Software +# Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. +# +# As a special exception to the GNU General Public License, if you +# distribute this file as part of a program that contains a +# configuration script generated by Autoconf, you may include it under +# the same distribution terms that you use for the rest of that program. + +# Written by Per Bothner . +# The master version of this file is at the FSF in /home/gd/gnu/lib. +# +# This script attempts to guess a canonical system name similar to +# config.sub. If it succeeds, it prints the system name on stdout, and +# exits with 0. Otherwise, it exits with 1. +# +# The plan is that this can be called by configure scripts if you +# don't specify an explicit system type (host/target name). +# +# Only a few systems have been added to this list; please add others +# (but try to keep the structure clean). +# + +# This is needed to find uname on a Pyramid OSx when run in the BSD universe. +# (ghazi@noc.rutgers.edu 8/24/94.) +if (test -f /.attbin/uname) >/dev/null 2>&1 ; then + PATH=$PATH:/.attbin ; export PATH +fi + +UNAME_MACHINE=`(uname -m) 2>/dev/null` || UNAME_MACHINE=unknown +UNAME_RELEASE=`(uname -r) 2>/dev/null` || UNAME_RELEASE=unknown +UNAME_SYSTEM=`(uname -s) 2>/dev/null` || UNAME_SYSTEM=unknown +UNAME_VERSION=`(uname -v) 2>/dev/null` || UNAME_VERSION=unknown + +trap 'rm -f dummy.c dummy.o dummy; exit 1' 1 2 15 + +# Note: order is significant - the case branches are not exclusive. + +case "${UNAME_MACHINE}:${UNAME_SYSTEM}:${UNAME_RELEASE}:${UNAME_VERSION}" in + alpha:OSF1:*:*) + # A Vn.n version is a released version. + # A Tn.n version is a released field test version. + # A Xn.n version is an unreleased experimental baselevel. + # 1.2 uses "1.2" for uname -r. + echo alpha-dec-osf`echo ${UNAME_RELEASE} | sed -e 's/^[VTX]//'` + exit 0 ;; + 21064:Windows_NT:50:3) + echo alpha-dec-winnt3.5 + exit 0 ;; + Amiga*:UNIX_System_V:4.0:*) + echo m68k-cbm-sysv4 + exit 0;; + amiga:NetBSD:*:*) + echo m68k-cbm-netbsd${UNAME_RELEASE} + exit 0 ;; + amiga:OpenBSD:*:*) + echo m68k-cbm-openbsd${UNAME_RELEASE} + exit 0 ;; + arm:RISC*:1.[012]*:*|arm:riscix:1.[012]*:*) + echo arm-acorn-riscix${UNAME_RELEASE} + exit 0;; + Pyramid*:OSx*:*:*|MIS*:OSx*:*:*) + # akee@wpdis03.wpafb.af.mil (Earle F. Ake) contributed MIS and NILE. + if test "`(/bin/universe) 2>/dev/null`" = att ; then + echo pyramid-pyramid-sysv3 + else + echo pyramid-pyramid-bsd + fi + exit 0 ;; + NILE:*:*:dcosx) + echo pyramid-pyramid-svr4 + exit 0 ;; + sun4*:SunOS:5.*:* | tadpole*:SunOS:5.*:*) + echo sparc-sun-solaris2`echo ${UNAME_RELEASE}|sed -e 's/[^.]*//'` + exit 0 ;; + i86pc:SunOS:5.*:*) + echo i386-pc-solaris2`echo ${UNAME_RELEASE}|sed -e 's/[^.]*//'` + exit 0 ;; + sun4*:SunOS:6*:*) + # According to config.sub, this is the proper way to canonicalize + # SunOS6. Hard to guess exactly what SunOS6 will be like, but + # it's likely to be more like Solaris than SunOS4. + echo sparc-sun-solaris3`echo ${UNAME_RELEASE}|sed -e 's/[^.]*//'` + exit 0 ;; + sun4*:SunOS:*:*) + case "`/usr/bin/arch -k`" in + Series*|S4*) + UNAME_RELEASE=`uname -v` + ;; + esac + # Japanese Language versions have a version number like `4.1.3-JL'. + echo sparc-sun-sunos`echo ${UNAME_RELEASE}|sed -e 's/-/_/'` + exit 0 ;; + sun3*:SunOS:*:*) + echo m68k-sun-sunos${UNAME_RELEASE} + exit 0 ;; + aushp:SunOS:*:*) + echo sparc-auspex-sunos${UNAME_RELEASE} + exit 0 ;; + atari*:NetBSD:*:*) + echo m68k-atari-netbsd${UNAME_RELEASE} + exit 0 ;; + atari*:OpenBSD:*:*) + echo m68k-atari-openbsd${UNAME_RELEASE} + exit 0 ;; + sun3*:NetBSD:*:*) + echo m68k-sun-netbsd${UNAME_RELEASE} + exit 0 ;; + sun3*:OpenBSD:*:*) + echo m68k-sun-openbsd${UNAME_RELEASE} + exit 0 ;; + mac68k:NetBSD:*:*) + echo m68k-apple-netbsd${UNAME_RELEASE} + exit 0 ;; + mac68k:OpenBSD:*:*) + echo m68k-apple-openbsd${UNAME_RELEASE} + exit 0 ;; + powerpc:machten:*:*) + echo powerpc-apple-machten${UNAME_RELEASE} + exit 0 ;; + RISC*:Mach:*:*) + echo mips-dec-mach_bsd4.3 + exit 0 ;; + RISC*:ULTRIX:*:*) + echo mips-dec-ultrix${UNAME_RELEASE} + exit 0 ;; + VAX*:ULTRIX*:*:*) + echo vax-dec-ultrix${UNAME_RELEASE} + exit 0 ;; + mips:*:*:UMIPS | mips:*:*:RISCos) + sed 's/^ //' << EOF >dummy.c + int main (argc, argv) int argc; char **argv; { + #if defined (host_mips) && defined (MIPSEB) + #if defined (SYSTYPE_SYSV) + printf ("mips-mips-riscos%ssysv\n", argv[1]); exit (0); + #endif + #if defined (SYSTYPE_SVR4) + printf ("mips-mips-riscos%ssvr4\n", argv[1]); exit (0); + #endif + #if defined (SYSTYPE_BSD43) || defined(SYSTYPE_BSD) + printf ("mips-mips-riscos%sbsd\n", argv[1]); exit (0); + #endif + #endif + exit (-1); + } +EOF + ${CC-cc} dummy.c -o dummy \ + && ./dummy `echo "${UNAME_RELEASE}" | sed -n 's/\([0-9]*\).*/\1/p'` \ + && rm dummy.c dummy && exit 0 + rm -f dummy.c dummy + echo mips-mips-riscos${UNAME_RELEASE} + exit 0 ;; + Night_Hawk:Power_UNIX:*:*) + echo powerpc-harris-powerunix + exit 0 ;; + m88k:CX/UX:7*:*) + echo m88k-harris-cxux7 + exit 0 ;; + m88k:*:4*:R4*) + echo m88k-motorola-sysv4 + exit 0 ;; + m88k:*:3*:R3*) + echo m88k-motorola-sysv3 + exit 0 ;; + AViiON:dgux:*:*) + # DG/UX returns AViiON for all architectures + UNAME_PROCESSOR=`/usr/bin/uname -p` + if [ $UNAME_PROCESSOR = mc88100 -o $UNAME_PROCESSOR = mc88110 ] ; then + if [ ${TARGET_BINARY_INTERFACE}x = m88kdguxelfx \ + -o ${TARGET_BINARY_INTERFACE}x = m88kdguxx \ + -o ${TARGET_BINARY_INTERFACE}x = x ] ; then + echo m88k-dg-dgux${UNAME_RELEASE} + else + echo m88k-dg-dguxbcs${UNAME_RELEASE} + fi + else echo i586-dg-dgux${UNAME_RELEASE} + fi + exit 0 ;; + M88*:DolphinOS:*:*) # DolphinOS (SVR3) + echo m88k-dolphin-sysv3 + exit 0 ;; + M88*:*:R3*:*) + # Delta 88k system running SVR3 + echo m88k-motorola-sysv3 + exit 0 ;; + XD88*:*:*:*) # Tektronix XD88 system running UTekV (SVR3) + echo m88k-tektronix-sysv3 + exit 0 ;; + Tek43[0-9][0-9]:UTek:*:*) # Tektronix 4300 system running UTek (BSD) + echo m68k-tektronix-bsd + exit 0 ;; + *:IRIX*:*:*) + echo mips-sgi-irix`echo ${UNAME_RELEASE}|sed -e 's/-/_/g'` + exit 0 ;; + ????????:AIX?:[12].1:2) # AIX 2.2.1 or AIX 2.1.1 is RT/PC AIX. + echo romp-ibm-aix # uname -m gives an 8 hex-code CPU id + exit 0 ;; # Note that: echo "'`uname -s`'" gives 'AIX ' + i?86:AIX:*:*) + echo i386-ibm-aix + exit 0 ;; + *:AIX:2:3) + if grep bos325 /usr/include/stdio.h >/dev/null 2>&1; then + sed 's/^ //' << EOF >dummy.c + #include + + main() + { + if (!__power_pc()) + exit(1); + puts("powerpc-ibm-aix3.2.5"); + exit(0); + } +EOF + ${CC-cc} dummy.c -o dummy && ./dummy && rm dummy.c dummy && exit 0 + rm -f dummy.c dummy + echo rs6000-ibm-aix3.2.5 + elif grep bos324 /usr/include/stdio.h >/dev/null 2>&1; then + echo rs6000-ibm-aix3.2.4 + else + echo rs6000-ibm-aix3.2 + fi + exit 0 ;; + *:AIX:*:4) + if /usr/sbin/lsattr -EHl proc0 | grep POWER >/dev/null 2>&1; then + IBM_ARCH=rs6000 + else + IBM_ARCH=powerpc + fi + if [ -x /usr/bin/oslevel ] ; then + IBM_REV=`/usr/bin/oslevel` + else + IBM_REV=4.${UNAME_RELEASE} + fi + echo ${IBM_ARCH}-ibm-aix${IBM_REV} + exit 0 ;; + *:AIX:*:*) + echo rs6000-ibm-aix + exit 0 ;; + ibmrt:4.4BSD:*|romp-ibm:BSD:*) + echo romp-ibm-bsd4.4 + exit 0 ;; + ibmrt:*BSD:*|romp-ibm:BSD:*) # covers RT/PC NetBSD and + echo romp-ibm-bsd${UNAME_RELEASE} # 4.3 with uname added to + exit 0 ;; # report: romp-ibm BSD 4.3 + *:BOSX:*:*) + echo rs6000-bull-bosx + exit 0 ;; + DPX/2?00:B.O.S.:*:*) + echo m68k-bull-sysv3 + exit 0 ;; + 9000/[34]??:4.3bsd:1.*:*) + echo m68k-hp-bsd + exit 0 ;; + hp300:4.4BSD:*:* | 9000/[34]??:4.3bsd:2.*:*) + echo m68k-hp-bsd4.4 + exit 0 ;; + 9000/[3478]??:HP-UX:*:*) + case "${UNAME_MACHINE}" in + 9000/31? ) HP_ARCH=m68000 ;; + 9000/[34]?? ) HP_ARCH=m68k ;; + 9000/7?? | 9000/8?[1679] ) HP_ARCH=hppa1.1 ;; + 9000/8?? ) HP_ARCH=hppa1.0 ;; + esac + HPUX_REV=`echo ${UNAME_RELEASE}|sed -e 's/[^.]*.[0B]*//'` + echo ${HP_ARCH}-hp-hpux${HPUX_REV} + exit 0 ;; + 3050*:HI-UX:*:*) + sed 's/^ //' << EOF >dummy.c + #include + int + main () + { + long cpu = sysconf (_SC_CPU_VERSION); + /* The order matters, because CPU_IS_HP_MC68K erroneously returns + true for CPU_PA_RISC1_0. CPU_IS_PA_RISC returns correct + results, however. */ + if (CPU_IS_PA_RISC (cpu)) + { + switch (cpu) + { + case CPU_PA_RISC1_0: puts ("hppa1.0-hitachi-hiuxwe2"); break; + case CPU_PA_RISC1_1: puts ("hppa1.1-hitachi-hiuxwe2"); break; + case CPU_PA_RISC2_0: puts ("hppa2.0-hitachi-hiuxwe2"); break; + default: puts ("hppa-hitachi-hiuxwe2"); break; + } + } + else if (CPU_IS_HP_MC68K (cpu)) + puts ("m68k-hitachi-hiuxwe2"); + else puts ("unknown-hitachi-hiuxwe2"); + exit (0); + } +EOF + ${CC-cc} dummy.c -o dummy && ./dummy && rm dummy.c dummy && exit 0 + rm -f dummy.c dummy + echo unknown-hitachi-hiuxwe2 + exit 0 ;; + 9000/7??:4.3bsd:*:* | 9000/8?[79]:4.3bsd:*:* ) + echo hppa1.1-hp-bsd + exit 0 ;; + 9000/8??:4.3bsd:*:*) + echo hppa1.0-hp-bsd + exit 0 ;; + hp7??:OSF1:*:* | hp8?[79]:OSF1:*:* ) + echo hppa1.1-hp-osf + exit 0 ;; + hp8??:OSF1:*:*) + echo hppa1.0-hp-osf + exit 0 ;; + i?86:OSF1:*:*) + if [ -x /usr/sbin/sysversion ] ; then + echo ${UNAME_MACHINE}-unknown-osf1mk + else + echo ${UNAME_MACHINE}-unknown-osf1 + fi + exit 0 ;; + parisc*:Lites*:*:*) + echo hppa1.1-hp-lites + exit 0 ;; + C1*:ConvexOS:*:* | convex:ConvexOS:C1*:*) + echo c1-convex-bsd + exit 0 ;; + C2*:ConvexOS:*:* | convex:ConvexOS:C2*:*) + if getsysinfo -f scalar_acc + then echo c32-convex-bsd + else echo c2-convex-bsd + fi + exit 0 ;; + C34*:ConvexOS:*:* | convex:ConvexOS:C34*:*) + echo c34-convex-bsd + exit 0 ;; + C38*:ConvexOS:*:* | convex:ConvexOS:C38*:*) + echo c38-convex-bsd + exit 0 ;; + C4*:ConvexOS:*:* | convex:ConvexOS:C4*:*) + echo c4-convex-bsd + exit 0 ;; + CRAY*X-MP:*:*:*) + echo xmp-cray-unicos + exit 0 ;; + CRAY*Y-MP:*:*:*) + echo ymp-cray-unicos${UNAME_RELEASE} + exit 0 ;; + CRAY*[A-Z]90:*:*:*) + echo ${UNAME_MACHINE}-cray-unicos${UNAME_RELEASE} \ + | sed -e 's/CRAY.*\([A-Z]90\)/\1/' \ + -e y/ABCDEFGHIJKLMNOPQRSTUVWXYZ/abcdefghijklmnopqrstuvwxyz/ + exit 0 ;; + CRAY*TS:*:*:*) + echo t90-cray-unicos${UNAME_RELEASE} + exit 0 ;; + CRAY-2:*:*:*) + echo cray2-cray-unicos + exit 0 ;; + F300:UNIX_System_V:*:*) + FUJITSU_SYS=`uname -p | tr [A-Z] [a-z] | sed -e 's/\///'` + FUJITSU_REL=`echo ${UNAME_RELEASE} | sed -e 's/ /_/'` + echo "f300-fujitsu-${FUJITSU_SYS}${FUJITSU_REL}" + exit 0 ;; + F301:UNIX_System_V:*:*) + echo f301-fujitsu-uxpv`echo $UNAME_RELEASE | sed 's/ .*//'` + exit 0 ;; + hp3[0-9][05]:NetBSD:*:*) + echo m68k-hp-netbsd${UNAME_RELEASE} + exit 0 ;; + hp3[0-9][05]:OpenBSD:*:*) + echo m68k-hp-openbsd${UNAME_RELEASE} + exit 0 ;; + i?86:BSD/386:*:* | *:BSD/OS:*:*) + echo ${UNAME_MACHINE}-pc-bsdi${UNAME_RELEASE} + exit 0 ;; + *:FreeBSD:*:*) + echo ${UNAME_MACHINE}-unknown-freebsd`echo ${UNAME_RELEASE}|sed -e 's/[-(].*//'` + exit 0 ;; + *:NetBSD:*:*) + echo ${UNAME_MACHINE}-unknown-netbsd`echo ${UNAME_RELEASE}|sed -e 's/[-_].*/\./'` + exit 0 ;; + *:OpenBSD:*:*) + echo ${UNAME_MACHINE}-unknown-openbsd`echo ${UNAME_RELEASE}|sed -e 's/[-_].*/\./'` + exit 0 ;; + i*:CYGWIN*:*) + echo i386-pc-cygwin32 + exit 0 ;; + p*:CYGWIN*:*) + echo powerpcle-unknown-cygwin32 + exit 0 ;; + prep*:SunOS:5.*:*) + echo powerpcle-unknown-solaris2`echo ${UNAME_RELEASE}|sed -e 's/[^.]*//'` + exit 0 ;; + *:GNU:*:*) + echo `echo ${UNAME_MACHINE}|sed -e 's,/.*$,,'`-unknown-gnu`echo ${UNAME_RELEASE}|sed -e 's,/.*$,,'` + exit 0 ;; + *:Linux:*:*) + # The BFD linker knows what the default object file format is, so + # first see if it will tell us. + ld_help_string=`ld --help 2>&1` + if echo "$ld_help_string" | grep >/dev/null 2>&1 "supported emulations: elf_i.86"; then + echo "${UNAME_MACHINE}-pc-linux-gnu" ; exit 0 + elif echo "$ld_help_string" | grep >/dev/null 2>&1 "supported emulations: i.86linux"; then + echo "${UNAME_MACHINE}-pc-linux-gnuaout" ; exit 0 + elif echo "$ld_help_string" | grep >/dev/null 2>&1 "supported emulations: i.86coff"; then + echo "${UNAME_MACHINE}-pc-linux-gnucoff" ; exit 0 + elif echo "$ld_help_string" | grep >/dev/null 2>&1 "supported emulations: m68kelf"; then + echo "${UNAME_MACHINE}-unknown-linux-gnu" ; exit 0 + elif echo "$ld_help_string" | grep >/dev/null 2>&1 "supported emulations: m68klinux"; then + echo "${UNAME_MACHINE}-unknown-linux-gnuaout" ; exit 0 + elif echo "$ld_help_string" | grep >/dev/null 2>&1 "supported emulations: elf32ppc"; then + echo "powerpc-unknown-linux-gnu" ; exit 0 + elif test "${UNAME_MACHINE}" = "alpha" ; then + echo alpha-unknown-linux-gnu ; exit 0 + elif test "${UNAME_MACHINE}" = "sparc" ; then + echo sparc-unknown-linux-gnu ; exit 0 + else + # Either a pre-BFD a.out linker (linux-gnuoldld) or one that does not give us + # useful --help. Gcc wants to distinguish between linux-gnuoldld and linux-gnuaout. + test ! -d /usr/lib/ldscripts/. \ + && echo "${UNAME_MACHINE}-pc-linux-gnuoldld" && exit 0 + # Determine whether the default compiler is a.out or elf + cat >dummy.c </dev/null && ./dummy "${UNAME_MACHINE}" && rm dummy.c dummy && exit 0 + rm -f dummy.c dummy + fi ;; +# ptx 4.0 does uname -s correctly, with DYNIX/ptx in there. earlier versions +# are messed up and put the nodename in both sysname and nodename. + i?86:DYNIX/ptx:4*:*) + echo i386-sequent-sysv4 + exit 0 ;; + i?86:*:4.*:* | i?86:SYSTEM_V:4.*:*) + if grep Novell /usr/include/link.h >/dev/null 2>/dev/null; then + echo ${UNAME_MACHINE}-univel-sysv${UNAME_RELEASE} + else + echo ${UNAME_MACHINE}-pc-sysv${UNAME_RELEASE} + fi + exit 0 ;; + i?86:*:3.2:*) + if test -f /usr/options/cb.name; then + UNAME_REL=`sed -n 's/.*Version //p' /dev/null >/dev/null ; then + UNAME_REL=`(/bin/uname -X|egrep Release|sed -e 's/.*= //')` + (/bin/uname -X|egrep i80486 >/dev/null) && UNAME_MACHINE=i486 + (/bin/uname -X|egrep '^Machine.*Pentium' >/dev/null) \ + && UNAME_MACHINE=i586 + echo ${UNAME_MACHINE}-pc-sco$UNAME_REL + else + echo ${UNAME_MACHINE}-pc-sysv32 + fi + exit 0 ;; + Intel:Mach:3*:*) + echo i386-pc-mach3 + exit 0 ;; + paragon:*:*:*) + echo i860-intel-osf1 + exit 0 ;; + i860:*:4.*:*) # i860-SVR4 + if grep Stardent /usr/include/sys/uadmin.h >/dev/null 2>&1 ; then + echo i860-stardent-sysv${UNAME_RELEASE} # Stardent Vistra i860-SVR4 + else # Add other i860-SVR4 vendors below as they are discovered. + echo i860-unknown-sysv${UNAME_RELEASE} # Unknown i860-SVR4 + fi + exit 0 ;; + mini*:CTIX:SYS*5:*) + # "miniframe" + echo m68010-convergent-sysv + exit 0 ;; + M68*:*:R3V[567]*:*) + test -r /sysV68 && echo 'm68k-motorola-sysv' && exit 0 ;; + 3[34]??:*:4.0:3.0 | 3[34]??,*:*:4.0:3.0 | 4850:*:4.0:3.0) + OS_REL='' + test -r /etc/.relid \ + && OS_REL=.`sed -n 's/[^ ]* [^ ]* \([0-9][0-9]\).*/\1/p' < /etc/.relid` + /bin/uname -p 2>/dev/null | grep 86 >/dev/null \ + && echo i486-ncr-sysv4.3${OS_REL} && exit 0 + /bin/uname -p 2>/dev/null | /bin/grep entium >/dev/null \ + && echo i586-ncr-sysv4.3${OS_REL} && exit 0 ;; + 3[34]??:*:4.0:* | 3[34]??,*:*:4.0:*) + /bin/uname -p 2>/dev/null | grep 86 >/dev/null \ + && echo i486-ncr-sysv4 && exit 0 ;; + m68*:LynxOS:2.*:*) + echo m68k-unknown-lynxos${UNAME_RELEASE} + exit 0 ;; + mc68030:UNIX_System_V:4.*:*) + echo m68k-atari-sysv4 + exit 0 ;; + i?86:LynxOS:2.*:*) + echo i386-unknown-lynxos${UNAME_RELEASE} + exit 0 ;; + TSUNAMI:LynxOS:2.*:*) + echo sparc-unknown-lynxos${UNAME_RELEASE} + exit 0 ;; + rs6000:LynxOS:2.*:* | PowerPC:LynxOS:2.*:*) + echo rs6000-unknown-lynxos${UNAME_RELEASE} + exit 0 ;; + SM[BE]S:UNIX_SV:*:*) + echo mips-dde-sysv${UNAME_RELEASE} + exit 0 ;; + RM*:SINIX-*:*:*) + echo mips-sni-sysv4 + exit 0 ;; + *:SINIX-*:*:*) + if uname -p 2>/dev/null >/dev/null ; then + UNAME_MACHINE=`(uname -p) 2>/dev/null` + echo ${UNAME_MACHINE}-sni-sysv4 + else + echo ns32k-sni-sysv + fi + exit 0 ;; + *:UNIX_System_V:4*:FTX*) + # From Gerald Hewes . + # How about differentiating between stratus architectures? -djm + echo hppa1.1-stratus-sysv4 + exit 0 ;; + *:*:*:FTX*) + # From seanf@swdc.stratus.com. + echo i860-stratus-sysv4 + exit 0 ;; + mc68*:A/UX:*:*) + echo m68k-apple-aux${UNAME_RELEASE} + exit 0 ;; + R3000:*System_V*:*:* | R4000:UNIX_SYSV:*:*) + if [ -d /usr/nec ]; then + echo mips-nec-sysv${UNAME_RELEASE} + else + echo mips-unknown-sysv${UNAME_RELEASE} + fi + exit 0 ;; + PENTIUM:CPunix:4.0*:*) # Unisys `ClearPath HMP IX 4000' SVR4/MP effort + # says + echo i586-unisys-sysv4 + exit 0 ;; +esac + +#echo '(No uname command or uname output not recognized.)' 1>&2 +#echo "${UNAME_MACHINE}:${UNAME_SYSTEM}:${UNAME_RELEASE}:${UNAME_VERSION}" 1>&2 + +cat >dummy.c < +# include +#endif +main () +{ +#if defined (sony) +#if defined (MIPSEB) + /* BFD wants "bsd" instead of "newsos". Perhaps BFD should be changed, + I don't know.... */ + printf ("mips-sony-bsd\n"); exit (0); +#else +#include + printf ("m68k-sony-newsos%s\n", +#ifdef NEWSOS4 + "4" +#else + "" +#endif + ); exit (0); +#endif +#endif + +#if defined (__arm) && defined (__acorn) && defined (__unix) + printf ("arm-acorn-riscix"); exit (0); +#endif + +#if defined (hp300) && !defined (hpux) + printf ("m68k-hp-bsd\n"); exit (0); +#endif + +#if defined (NeXT) +#if !defined (__ARCHITECTURE__) +#define __ARCHITECTURE__ "m68k" +#endif + int version; + version=`(hostinfo | sed -n 's/.*NeXT Mach \([0-9]*\).*/\1/p') 2>/dev/null`; + printf ("%s-next-nextstep%d\n", __ARCHITECTURE__, version); + exit (0); +#endif + +#if defined (MULTIMAX) || defined (n16) +#if defined (UMAXV) + printf ("ns32k-encore-sysv\n"); exit (0); +#else +#if defined (CMU) + printf ("ns32k-encore-mach\n"); exit (0); +#else + printf ("ns32k-encore-bsd\n"); exit (0); +#endif +#endif +#endif + +#if defined (__386BSD__) + printf ("i386-pc-bsd\n"); exit (0); +#endif + +#if defined (sequent) +#if defined (i386) + printf ("i386-sequent-dynix\n"); exit (0); +#endif +#if defined (ns32000) + printf ("ns32k-sequent-dynix\n"); exit (0); +#endif +#endif + +#if defined (_SEQUENT_) + struct utsname un; + + uname(&un); + + if (strncmp(un.version, "V2", 2) == 0) { + printf ("i386-sequent-ptx2\n"); exit (0); + } + if (strncmp(un.version, "V1", 2) == 0) { /* XXX is V1 correct? */ + printf ("i386-sequent-ptx1\n"); exit (0); + } + printf ("i386-sequent-ptx\n"); exit (0); + +#endif + +#if defined (vax) +#if !defined (ultrix) + printf ("vax-dec-bsd\n"); exit (0); +#else + printf ("vax-dec-ultrix\n"); exit (0); +#endif +#endif + +#if defined (alliant) && defined (i860) + printf ("i860-alliant-bsd\n"); exit (0); +#endif + + exit (1); +} +EOF + +${CC-cc} dummy.c -o dummy 2>/dev/null && ./dummy && rm dummy.c dummy && exit 0 +rm -f dummy.c dummy + +# Apollos put the system type in the environment. + +test -d /usr/apollo && { echo ${ISP}-apollo-${SYSTYPE}; exit 0; } + +# Convex versions that predate uname can use getsysinfo(1) + +if [ -x /usr/convex/getsysinfo ] +then + case `getsysinfo -f cpu_type` in + c1*) + echo c1-convex-bsd + exit 0 ;; + c2*) + if getsysinfo -f scalar_acc + then echo c32-convex-bsd + else echo c2-convex-bsd + fi + exit 0 ;; + c34*) + echo c34-convex-bsd + exit 0 ;; + c38*) + echo c38-convex-bsd + exit 0 ;; + c4*) + echo c4-convex-bsd + exit 0 ;; + esac +fi + +#echo '(Unable to guess system type)' 1>&2 + +exit 1 diff --git a/src/interfaces/odbc/config.h.in b/src/interfaces/odbc/config.h.in new file mode 100644 index 0000000000..558b034a06 --- /dev/null +++ b/src/interfaces/odbc/config.h.in @@ -0,0 +1,25 @@ +/* config.h.in. Generated automatically from configure.in by autoheader. */ + +/* Define if you have the ANSI C header files. */ +#undef STDC_HEADERS + +/* default path for the location of the odbcinst.ini file */ +#undef ODBCINST + +/* Define if you have the stricmp function. */ +#undef HAVE_STRICMP + +/* Define if you have the header file. */ +#undef HAVE_PWD_H + +/* Define if you have the header file. */ +#undef HAVE_SYS_PARAM_H + +/* Define if you have the c library (-lc). */ +#undef HAVE_LIBC + +/* Define if you have the dl library (-ldl). */ +#undef HAVE_LIBDL + +/* Define if you have the m library (-lm). */ +#undef HAVE_LIBM diff --git a/src/interfaces/odbc/config.status b/src/interfaces/odbc/config.status new file mode 100644 index 0000000000..581b509705 --- /dev/null +++ b/src/interfaces/odbc/config.status @@ -0,0 +1,261 @@ +#! /bin/sh +# Generated automatically by configure. +# Run this file to recreate the current configuration. +# This directory was configured as follows, +# on host golem: +# +# ./configure +# +# Compiler output produced by configure, useful for debugging +# configure, is in ./config.log if it exists. + +ac_cs_usage="Usage: ./config.status [--recheck] [--version] [--help]" +for ac_option +do + case "$ac_option" in + -recheck | --recheck | --rechec | --reche | --rech | --rec | --re | --r) + echo "running ${CONFIG_SHELL-/bin/sh} ./configure --no-create --no-recursion" + exec ${CONFIG_SHELL-/bin/sh} ./configure --no-create --no-recursion ;; + -version | --version | --versio | --versi | --vers | --ver | --ve | --v) + echo "./config.status generated by autoconf version 2.12" + exit 0 ;; + -help | --help | --hel | --he | --h) + echo "$ac_cs_usage"; exit 0 ;; + *) echo "$ac_cs_usage"; exit 1 ;; + esac +done + +ac_given_srcdir=. + +trap 'rm -fr GNUmakefile Makefile.global config.h conftest*; exit 1' 1 2 15 + +# Protect against being on the right side of a sed subst in config.status. +sed 's/%@/@@/; s/@%/@@/; s/%g$/@g/; /@g$/s/[\\&%]/\\&/g; + s/@@/%@/; s/@@/@%/; s/@g$/%g/' > conftest.subs <<\CEOF +/^[ ]*VPATH[ ]*=[^:]*$/d + +s%@CFLAGS@%-O2%g +s%@CPPFLAGS@%%g +s%@CXXFLAGS@%%g +s%@DEFS@%-DHAVE_CONFIG_H%g +s%@LDFLAGS@%%g +s%@LIBS@%-ldl -lm -lc %g +s%@exec_prefix@%${prefix}%g +s%@prefix@%/usr/local/pgsql%g +s%@program_transform_name@%s,x,x,%g +s%@bindir@%${exec_prefix}/bin%g +s%@sbindir@%${exec_prefix}/sbin%g +s%@libexecdir@%${exec_prefix}/libexec%g +s%@datadir@%${prefix}/share%g +s%@sysconfdir@%${prefix}/etc%g +s%@sharedstatedir@%${prefix}/com%g +s%@localstatedir@%${prefix}/var%g +s%@libdir@%${exec_prefix}/lib%g +s%@includedir@%${prefix}/include%g +s%@oldincludedir@%/usr/include%g +s%@infodir@%${prefix}/info%g +s%@mandir@%${prefix}/man%g +s%@host@%i686-pc-linux-gnu%g +s%@host_alias@%i686-pc-linux-gnu%g +s%@host_cpu@%i686%g +s%@host_vendor@%pc%g +s%@host_os@%linux-gnu%g +s%@PORTNAME@%linux%g +s%@ODBCINSTDIR@%%g +s%@CC@%gcc%g +s%@CPP@%gcc -E%g +s%@AROPT@%crs%g +s%@SHARED_LIB@%-fpic%g +s%@DLSUFFIX@%.so%g +s%@DL_LIB@%%g +s%@INSTALL@%/usr/bin/install%g +s%@INSTLOPTS@%-c -m 444%g +s%@INSTL_LIB_OPTS@%-c -m 644%g +s%@INSTL_EXE_OPTS@%-c -m 555%g +s%@DASH_N@%-n%g +s%@BACKSLASH_C@%%g +s%@LN_S@%ln -s%g +s%@SET_MAKE@%%g +s%@RANLIB@%ranlib%g +s%@find@%/usr/bin/find%g +s%@tar@%/bin/tar%g +s%@split@%/usr/bin/split%g + +CEOF + +# Split the substitutions into bite-sized pieces for seds with +# small command number limits, like on Digital OSF/1 and HP-UX. +ac_max_sed_cmds=90 # Maximum number of lines to put in a sed script. +ac_file=1 # Number of current file. +ac_beg=1 # First line for current file. +ac_end=$ac_max_sed_cmds # Line after last line for current file. +ac_more_lines=: +ac_sed_cmds="" +while $ac_more_lines; do + if test $ac_beg -gt 1; then + sed "1,${ac_beg}d; ${ac_end}q" conftest.subs > conftest.s$ac_file + else + sed "${ac_end}q" conftest.subs > conftest.s$ac_file + fi + if test ! -s conftest.s$ac_file; then + ac_more_lines=false + rm -f conftest.s$ac_file + else + if test -z "$ac_sed_cmds"; then + ac_sed_cmds="sed -f conftest.s$ac_file" + else + ac_sed_cmds="$ac_sed_cmds | sed -f conftest.s$ac_file" + fi + ac_file=`expr $ac_file + 1` + ac_beg=$ac_end + ac_end=`expr $ac_end + $ac_max_sed_cmds` + fi +done +if test -z "$ac_sed_cmds"; then + ac_sed_cmds=cat +fi + +CONFIG_FILES=${CONFIG_FILES-"GNUmakefile Makefile.global"} +for ac_file in .. $CONFIG_FILES; do if test "x$ac_file" != x..; then + # Support "outfile[:infile[:infile...]]", defaulting infile="outfile.in". + case "$ac_file" in + *:*) ac_file_in=`echo "$ac_file"|sed 's%[^:]*:%%'` + ac_file=`echo "$ac_file"|sed 's%:.*%%'` ;; + *) ac_file_in="${ac_file}.in" ;; + esac + + # Adjust a relative srcdir, top_srcdir, and INSTALL for subdirectories. + + # Remove last slash and all that follows it. Not all systems have dirname. + ac_dir=`echo $ac_file|sed 's%/[^/][^/]*$%%'` + if test "$ac_dir" != "$ac_file" && test "$ac_dir" != .; then + # The file is in a subdirectory. + test ! -d "$ac_dir" && mkdir "$ac_dir" + ac_dir_suffix="/`echo $ac_dir|sed 's%^\./%%'`" + # A "../" for each directory in $ac_dir_suffix. + ac_dots=`echo $ac_dir_suffix|sed 's%/[^/]*%../%g'` + else + ac_dir_suffix= ac_dots= + fi + + case "$ac_given_srcdir" in + .) srcdir=. + if test -z "$ac_dots"; then top_srcdir=. + else top_srcdir=`echo $ac_dots|sed 's%/$%%'`; fi ;; + /*) srcdir="$ac_given_srcdir$ac_dir_suffix"; top_srcdir="$ac_given_srcdir" ;; + *) # Relative path. + srcdir="$ac_dots$ac_given_srcdir$ac_dir_suffix" + top_srcdir="$ac_dots$ac_given_srcdir" ;; + esac + + + echo creating "$ac_file" + rm -f "$ac_file" + configure_input="Generated automatically from `echo $ac_file_in|sed 's%.*/%%'` by configure." + case "$ac_file" in + *Makefile*) ac_comsub="1i\\ +# $configure_input" ;; + *) ac_comsub= ;; + esac + + ac_file_inputs=`echo $ac_file_in|sed -e "s%^%$ac_given_srcdir/%" -e "s%:% $ac_given_srcdir/%g"` + sed -e "$ac_comsub +s%@configure_input@%$configure_input%g +s%@srcdir@%$srcdir%g +s%@top_srcdir@%$top_srcdir%g +" $ac_file_inputs | (eval "$ac_sed_cmds") > $ac_file +fi; done +rm -f conftest.s* + +# These sed commands are passed to sed as "A NAME B NAME C VALUE D", where +# NAME is the cpp macro being defined and VALUE is the value it is being given. +# +# ac_d sets the value in "#define NAME VALUE" lines. +ac_dA='s%^\([ ]*\)#\([ ]*define[ ][ ]*\)' +ac_dB='\([ ][ ]*\)[^ ]*%\1#\2' +ac_dC='\3' +ac_dD='%g' +# ac_u turns "#undef NAME" with trailing blanks into "#define NAME VALUE". +ac_uA='s%^\([ ]*\)#\([ ]*\)undef\([ ][ ]*\)' +ac_uB='\([ ]\)%\1#\2define\3' +ac_uC=' ' +ac_uD='\4%g' +# ac_e turns "#undef NAME" without trailing blanks into "#define NAME VALUE". +ac_eA='s%^\([ ]*\)#\([ ]*\)undef\([ ][ ]*\)' +ac_eB='$%\1#\2define\3' +ac_eC=' ' +ac_eD='%g' + +if test "${CONFIG_HEADERS+set}" != set; then + CONFIG_HEADERS="config.h" +fi +for ac_file in .. $CONFIG_HEADERS; do if test "x$ac_file" != x..; then + # Support "outfile[:infile[:infile...]]", defaulting infile="outfile.in". + case "$ac_file" in + *:*) ac_file_in=`echo "$ac_file"|sed 's%[^:]*:%%'` + ac_file=`echo "$ac_file"|sed 's%:.*%%'` ;; + *) ac_file_in="${ac_file}.in" ;; + esac + + echo creating $ac_file + + rm -f conftest.frag conftest.in conftest.out + ac_file_inputs=`echo $ac_file_in|sed -e "s%^%$ac_given_srcdir/%" -e "s%:% $ac_given_srcdir/%g"` + cat $ac_file_inputs > conftest.in + + cat > conftest.frag < conftest.out + rm -f conftest.in + mv conftest.out conftest.in + + cat > conftest.frag < conftest.out + rm -f conftest.in + mv conftest.out conftest.in + + rm -f conftest.frag conftest.h + echo "/* $ac_file. Generated automatically by configure. */" > conftest.h + cat conftest.in >> conftest.h + rm -f conftest.in + if cmp -s $ac_file conftest.h 2>/dev/null; then + echo "$ac_file is unchanged" + rm -f conftest.h + else + # Remove last slash and all that follows it. Not all systems have dirname. + ac_dir=`echo $ac_file|sed 's%/[^/][^/]*$%%'` + if test "$ac_dir" != "$ac_file" && test "$ac_dir" != .; then + # The file is in a subdirectory. + test ! -d "$ac_dir" && mkdir "$ac_dir" + fi + rm -f $ac_file + mv conftest.h $ac_file + fi +fi; done + + + +exit 0 diff --git a/src/interfaces/odbc/config.sub b/src/interfaces/odbc/config.sub new file mode 100755 index 0000000000..0859eab7b8 --- /dev/null +++ b/src/interfaces/odbc/config.sub @@ -0,0 +1,930 @@ +#! /bin/sh +# Configuration validation subroutine script, version 1.1. +# Copyright (C) 1991, 92, 93, 94, 95, 1996 Free Software Foundation, Inc. +# This file is (in principle) common to ALL GNU software. +# The presence of a machine in this file suggests that SOME GNU software +# can handle that machine. It does not imply ALL GNU software can. +# +# This file is free software; you can redistribute it and/or modify +# it under the terms of the GNU General Public License as published by +# the Free Software Foundation; either version 2 of the License, or +# (at your option) any later version. +# +# This program is distributed in the hope that it will be useful, +# but WITHOUT ANY WARRANTY; without even the implied warranty of +# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +# GNU General Public License for more details. +# +# You should have received a copy of the GNU General Public License +# along with this program; if not, write to the Free Software +# Foundation, Inc., 59 Temple Place - Suite 330, +# Boston, MA 02111-1307, USA. + +# As a special exception to the GNU General Public License, if you +# distribute this file as part of a program that contains a +# configuration script generated by Autoconf, you may include it under +# the same distribution terms that you use for the rest of that program. + +# Configuration subroutine to validate and canonicalize a configuration type. +# Supply the specified configuration type as an argument. +# If it is invalid, we print an error message on stderr and exit with code 1. +# Otherwise, we print the canonical config type on stdout and succeed. + +# This file is supposed to be the same for all GNU packages +# and recognize all the CPU types, system types and aliases +# that are meaningful with *any* GNU software. +# Each package is responsible for reporting which valid configurations +# it does not support. The user should be able to distinguish +# a failure to support a valid configuration from a meaningless +# configuration. + +# The goal of this file is to map all the various variations of a given +# machine specification into a single specification in the form: +# CPU_TYPE-MANUFACTURER-OPERATING_SYSTEM +# or in some cases, the newer four-part form: +# CPU_TYPE-MANUFACTURER-KERNEL-OPERATING_SYSTEM +# It is wrong to echo any other type of specification. + +if [ x$1 = x ] +then + echo Configuration name missing. 1>&2 + echo "Usage: $0 CPU-MFR-OPSYS" 1>&2 + echo "or $0 ALIAS" 1>&2 + echo where ALIAS is a recognized configuration type. 1>&2 + exit 1 +fi + +# First pass through any local machine types. +case $1 in + *local*) + echo $1 + exit 0 + ;; + *) + ;; +esac + +# Separate what the user gave into CPU-COMPANY and OS or KERNEL-OS (if any). +# Here we must recognize all the valid KERNEL-OS combinations. +maybe_os=`echo $1 | sed 's/^\(.*\)-\([^-]*-[^-]*\)$/\2/'` +case $maybe_os in + linux-gnu*) + os=-$maybe_os + basic_machine=`echo $1 | sed 's/^\(.*\)-\([^-]*-[^-]*\)$/\1/'` + ;; + *) + basic_machine=`echo $1 | sed 's/-[^-]*$//'` + if [ $basic_machine != $1 ] + then os=`echo $1 | sed 's/.*-/-/'` + else os=; fi + ;; +esac + +### Let's recognize common machines as not being operating systems so +### that things like config.sub decstation-3100 work. We also +### recognize some manufacturers as not being operating systems, so we +### can provide default operating systems below. +case $os in + -sun*os*) + # Prevent following clause from handling this invalid input. + ;; + -dec* | -mips* | -sequent* | -encore* | -pc532* | -sgi* | -sony* | \ + -att* | -7300* | -3300* | -delta* | -motorola* | -sun[234]* | \ + -unicom* | -ibm* | -next | -hp | -isi* | -apollo | -altos* | \ + -convergent* | -ncr* | -news | -32* | -3600* | -3100* | -hitachi* |\ + -c[123]* | -convex* | -sun | -crds | -omron* | -dg | -ultra | -tti* | \ + -harris | -dolphin | -highlevel | -gould | -cbm | -ns | -masscomp | \ + -apple) + os= + basic_machine=$1 + ;; + -hiux*) + os=-hiuxwe2 + ;; + -sco5) + os=sco3.2v5 + basic_machine=`echo $1 | sed -e 's/86-.*/86-pc/'` + ;; + -sco4) + os=-sco3.2v4 + basic_machine=`echo $1 | sed -e 's/86-.*/86-pc/'` + ;; + -sco3.2.[4-9]*) + os=`echo $os | sed -e 's/sco3.2./sco3.2v/'` + basic_machine=`echo $1 | sed -e 's/86-.*/86-pc/'` + ;; + -sco3.2v[4-9]*) + # Don't forget version if it is 3.2v4 or newer. + basic_machine=`echo $1 | sed -e 's/86-.*/86-pc/'` + ;; + -sco*) + os=-sco3.2v2 + basic_machine=`echo $1 | sed -e 's/86-.*/86-pc/'` + ;; + -isc) + os=-isc2.2 + basic_machine=`echo $1 | sed -e 's/86-.*/86-pc/'` + ;; + -clix*) + basic_machine=clipper-intergraph + ;; + -isc*) + basic_machine=`echo $1 | sed -e 's/86-.*/86-pc/'` + ;; + -lynx*) + os=-lynxos + ;; + -ptx*) + basic_machine=`echo $1 | sed -e 's/86-.*/86-sequent/'` + ;; + -windowsnt*) + os=`echo $os | sed -e 's/windowsnt/winnt/'` + ;; + -psos*) + os=-psos + ;; +esac + +# Decode aliases for certain CPU-COMPANY combinations. +case $basic_machine in + # Recognize the basic CPU types without company name. + # Some are omitted here because they have special meanings below. + tahoe | i860 | m68k | m68000 | m88k | ns32k | arm \ + | arme[lb] | pyramid \ + | tron | a29k | 580 | i960 | h8300 | hppa | hppa1.0 | hppa1.1 \ + | alpha | we32k | ns16k | clipper | i370 | sh \ + | powerpc | powerpcle | 1750a | dsp16xx | mips64 | mipsel \ + | pdp11 | mips64el | mips64orion | mips64orionel \ + | sparc | sparclet | sparclite | sparc64) + basic_machine=$basic_machine-unknown + ;; + # We use `pc' rather than `unknown' + # because (1) that's what they normally are, and + # (2) the word "unknown" tends to confuse beginning users. + i[3456]86) + basic_machine=$basic_machine-pc + ;; + # Object if more than one company name word. + *-*-*) + echo Invalid configuration \`$1\': machine \`$basic_machine\' not recognized 1>&2 + exit 1 + ;; + # Recognize the basic CPU types with company name. + vax-* | tahoe-* | i[3456]86-* | i860-* | m68k-* | m68000-* | m88k-* \ + | sparc-* | ns32k-* | fx80-* | arm-* | c[123]* \ + | mips-* | pyramid-* | tron-* | a29k-* | romp-* | rs6000-* | power-* \ + | none-* | 580-* | cray2-* | h8300-* | i960-* | xmp-* | ymp-* \ + | hppa-* | hppa1.0-* | hppa1.1-* | alpha-* | we32k-* | cydra-* | ns16k-* \ + | pn-* | np1-* | xps100-* | clipper-* | orion-* | sparclite-* \ + | pdp11-* | sh-* | powerpc-* | powerpcle-* | sparc64-* | mips64-* | mipsel-* \ + | mips64el-* | mips64orion-* | mips64orionel-* | f301-*) + ;; + # Recognize the various machine names and aliases which stand + # for a CPU type and a company and sometimes even an OS. + 3b1 | 7300 | 7300-att | att-7300 | pc7300 | safari | unixpc) + basic_machine=m68000-att + ;; + 3b*) + basic_machine=we32k-att + ;; + alliant | fx80) + basic_machine=fx80-alliant + ;; + altos | altos3068) + basic_machine=m68k-altos + ;; + am29k) + basic_machine=a29k-none + os=-bsd + ;; + amdahl) + basic_machine=580-amdahl + os=-sysv + ;; + amiga | amiga-*) + basic_machine=m68k-cbm + ;; + amigados) + basic_machine=m68k-cbm + os=-amigados + ;; + amigaunix | amix) + basic_machine=m68k-cbm + os=-sysv4 + ;; + apollo68) + basic_machine=m68k-apollo + os=-sysv + ;; + aux) + basic_machine=m68k-apple + os=-aux + ;; + balance) + basic_machine=ns32k-sequent + os=-dynix + ;; + convex-c1) + basic_machine=c1-convex + os=-bsd + ;; + convex-c2) + basic_machine=c2-convex + os=-bsd + ;; + convex-c32) + basic_machine=c32-convex + os=-bsd + ;; + convex-c34) + basic_machine=c34-convex + os=-bsd + ;; + convex-c38) + basic_machine=c38-convex + os=-bsd + ;; + cray | ymp) + basic_machine=ymp-cray + os=-unicos + ;; + cray2) + basic_machine=cray2-cray + os=-unicos + ;; + [ctj]90-cray) + basic_machine=c90-cray + os=-unicos + ;; + crds | unos) + basic_machine=m68k-crds + ;; + da30 | da30-*) + basic_machine=m68k-da30 + ;; + decstation | decstation-3100 | pmax | pmax-* | pmin | dec3100 | decstatn) + basic_machine=mips-dec + ;; + delta | 3300 | motorola-3300 | motorola-delta \ + | 3300-motorola | delta-motorola) + basic_machine=m68k-motorola + ;; + delta88) + basic_machine=m88k-motorola + os=-sysv3 + ;; + dpx20 | dpx20-*) + basic_machine=rs6000-bull + os=-bosx + ;; + dpx2* | dpx2*-bull) + basic_machine=m68k-bull + os=-sysv3 + ;; + ebmon29k) + basic_machine=a29k-amd + os=-ebmon + ;; + elxsi) + basic_machine=elxsi-elxsi + os=-bsd + ;; + encore | umax | mmax) + basic_machine=ns32k-encore + ;; + fx2800) + basic_machine=i860-alliant + ;; + genix) + basic_machine=ns32k-ns + ;; + gmicro) + basic_machine=tron-gmicro + os=-sysv + ;; + h3050r* | hiux*) + basic_machine=hppa1.1-hitachi + os=-hiuxwe2 + ;; + h8300hms) + basic_machine=h8300-hitachi + os=-hms + ;; + harris) + basic_machine=m88k-harris + os=-sysv3 + ;; + hp300-*) + basic_machine=m68k-hp + ;; + hp300bsd) + basic_machine=m68k-hp + os=-bsd + ;; + hp300hpux) + basic_machine=m68k-hp + os=-hpux + ;; + hp9k2[0-9][0-9] | hp9k31[0-9]) + basic_machine=m68000-hp + ;; + hp9k3[2-9][0-9]) + basic_machine=m68k-hp + ;; + hp9k7[0-9][0-9] | hp7[0-9][0-9] | hp9k8[0-9]7 | hp8[0-9]7) + basic_machine=hppa1.1-hp + ;; + hp9k8[0-9][0-9] | hp8[0-9][0-9]) + basic_machine=hppa1.0-hp + ;; + hppa-next) + os=-nextstep3 + ;; + i370-ibm* | ibm*) + basic_machine=i370-ibm + os=-mvs + ;; +# I'm not sure what "Sysv32" means. Should this be sysv3.2? + i[3456]86v32) + basic_machine=`echo $1 | sed -e 's/86.*/86-pc/'` + os=-sysv32 + ;; + i[3456]86v4*) + basic_machine=`echo $1 | sed -e 's/86.*/86-pc/'` + os=-sysv4 + ;; + i[3456]86v) + basic_machine=`echo $1 | sed -e 's/86.*/86-pc/'` + os=-sysv + ;; + i[3456]86sol2) + basic_machine=`echo $1 | sed -e 's/86.*/86-pc/'` + os=-solaris2 + ;; + iris | iris4d) + basic_machine=mips-sgi + case $os in + -irix*) + ;; + *) + os=-irix4 + ;; + esac + ;; + isi68 | isi) + basic_machine=m68k-isi + os=-sysv + ;; + m88k-omron*) + basic_machine=m88k-omron + ;; + magnum | m3230) + basic_machine=mips-mips + os=-sysv + ;; + merlin) + basic_machine=ns32k-utek + os=-sysv + ;; + miniframe) + basic_machine=m68000-convergent + ;; + mips3*-*) + basic_machine=`echo $basic_machine | sed -e 's/mips3/mips64/'` + ;; + mips3*) + basic_machine=`echo $basic_machine | sed -e 's/mips3/mips64/'`-unknown + ;; + ncr3000) + basic_machine=i486-ncr + os=-sysv4 + ;; + news | news700 | news800 | news900) + basic_machine=m68k-sony + os=-newsos + ;; + news1000) + basic_machine=m68030-sony + os=-newsos + ;; + news-3600 | risc-news) + basic_machine=mips-sony + os=-newsos + ;; + next | m*-next ) + basic_machine=m68k-next + case $os in + -nextstep* ) + ;; + -ns2*) + os=-nextstep2 + ;; + *) + os=-nextstep3 + ;; + esac + ;; + nh3000) + basic_machine=m68k-harris + os=-cxux + ;; + nh[45]000) + basic_machine=m88k-harris + os=-cxux + ;; + nindy960) + basic_machine=i960-intel + os=-nindy + ;; + np1) + basic_machine=np1-gould + ;; + pa-hitachi) + basic_machine=hppa1.1-hitachi + os=-hiuxwe2 + ;; + paragon) + basic_machine=i860-intel + os=-osf + ;; + pbd) + basic_machine=sparc-tti + ;; + pbb) + basic_machine=m68k-tti + ;; + pc532 | pc532-*) + basic_machine=ns32k-pc532 + ;; + pentium | p5) + basic_machine=i586-intel + ;; + pentiumpro | p6) + basic_machine=i686-intel + ;; + pentium-* | p5-*) + basic_machine=i586-`echo $basic_machine | sed 's/^[^-]*-//'` + ;; + pentiumpro-* | p6-*) + basic_machine=i686-`echo $basic_machine | sed 's/^[^-]*-//'` + ;; + k5) + # We don't have specific support for AMD's K5 yet, so just call it a Pentium + basic_machine=i586-amd + ;; + nexen) + # We don't have specific support for Nexgen yet, so just call it a Pentium + basic_machine=i586-nexgen + ;; + pn) + basic_machine=pn-gould + ;; + power) basic_machine=rs6000-ibm + ;; + ppc) basic_machine=powerpc-unknown + ;; + ppc-*) basic_machine=powerpc-`echo $basic_machine | sed 's/^[^-]*-//'` + ;; + ppcle | powerpclittle | ppc-le | powerpc-little) + basic_machine=powerpcle-unknown + ;; + ppcle-* | powerpclittle-*) + basic_machine=powerpcle-`echo $basic_machine | sed 's/^[^-]*-//'` + ;; + ps2) + basic_machine=i386-ibm + ;; + rm[46]00) + basic_machine=mips-siemens + ;; + rtpc | rtpc-*) + basic_machine=romp-ibm + ;; + sequent) + basic_machine=i386-sequent + ;; + sh) + basic_machine=sh-hitachi + os=-hms + ;; + sps7) + basic_machine=m68k-bull + os=-sysv2 + ;; + spur) + basic_machine=spur-unknown + ;; + sun2) + basic_machine=m68000-sun + ;; + sun2os3) + basic_machine=m68000-sun + os=-sunos3 + ;; + sun2os4) + basic_machine=m68000-sun + os=-sunos4 + ;; + sun3os3) + basic_machine=m68k-sun + os=-sunos3 + ;; + sun3os4) + basic_machine=m68k-sun + os=-sunos4 + ;; + sun4os3) + basic_machine=sparc-sun + os=-sunos3 + ;; + sun4os4) + basic_machine=sparc-sun + os=-sunos4 + ;; + sun4sol2) + basic_machine=sparc-sun + os=-solaris2 + ;; + sun3 | sun3-*) + basic_machine=m68k-sun + ;; + sun4) + basic_machine=sparc-sun + ;; + sun386 | sun386i | roadrunner) + basic_machine=i386-sun + ;; + symmetry) + basic_machine=i386-sequent + os=-dynix + ;; + tower | tower-32) + basic_machine=m68k-ncr + ;; + udi29k) + basic_machine=a29k-amd + os=-udi + ;; + ultra3) + basic_machine=a29k-nyu + os=-sym1 + ;; + vaxv) + basic_machine=vax-dec + os=-sysv + ;; + vms) + basic_machine=vax-dec + os=-vms + ;; + vpp*|vx|vx-*) + basic_machine=f301-fujitsu + ;; + vxworks960) + basic_machine=i960-wrs + os=-vxworks + ;; + vxworks68) + basic_machine=m68k-wrs + os=-vxworks + ;; + vxworks29k) + basic_machine=a29k-wrs + os=-vxworks + ;; + xmp) + basic_machine=xmp-cray + os=-unicos + ;; + xps | xps100) + basic_machine=xps100-honeywell + ;; + none) + basic_machine=none-none + os=-none + ;; + +# Here we handle the default manufacturer of certain CPU types. It is in +# some cases the only manufacturer, in others, it is the most popular. + mips) + basic_machine=mips-mips + ;; + romp) + basic_machine=romp-ibm + ;; + rs6000) + basic_machine=rs6000-ibm + ;; + vax) + basic_machine=vax-dec + ;; + pdp11) + basic_machine=pdp11-dec + ;; + we32k) + basic_machine=we32k-att + ;; + sparc) + basic_machine=sparc-sun + ;; + cydra) + basic_machine=cydra-cydrome + ;; + orion) + basic_machine=orion-highlevel + ;; + orion105) + basic_machine=clipper-highlevel + ;; + *) + echo Invalid configuration \`$1\': machine \`$basic_machine\' not recognized 1>&2 + exit 1 + ;; +esac + +# Here we canonicalize certain aliases for manufacturers. +case $basic_machine in + *-digital*) + basic_machine=`echo $basic_machine | sed 's/digital.*/dec/'` + ;; + *-commodore*) + basic_machine=`echo $basic_machine | sed 's/commodore.*/cbm/'` + ;; + *) + ;; +esac + +# Decode manufacturer-specific aliases for certain operating systems. + +if [ x"$os" != x"" ] +then +case $os in + # First match some system type aliases + # that might get confused with valid system types. + # -solaris* is a basic system type, with this one exception. + -solaris1 | -solaris1.*) + os=`echo $os | sed -e 's|solaris1|sunos4|'` + ;; + -solaris) + os=-solaris2 + ;; + -unixware* | svr4*) + os=-sysv4 + ;; + -univel*) + os=-sysv4 + ;; + -gnu/linux*) + os=`echo $os | sed -e 's|gnu/linux|linux-gnu|'` + ;; + # First accept the basic system types. + # The portable systems comes first. + # Each alternative MUST END IN A *, to match a version number. + # -sysv* is not here because it comes later, after sysvr4. + -gnu* | -bsd* | -mach* | -minix* | -genix* | -ultrix* | -irix* \ + | -*vms* | -sco* | -esix* | -isc* | -aix* | -sunos | -sunos[34]*\ + | -hpux* | -unos* | -osf* | -luna* | -dgux* | -solaris* | -sym* \ + | -amigados* | -msdos* | -newsos* | -unicos* | -aof* | -aos* \ + | -nindy* | -vxsim* | -vxworks* | -ebmon* | -hms* | -mvs* \ + | -clix* | -riscos* | -uniplus* | -iris* | -rtu* | -xenix* \ + | -hiux* | -386bsd* | -netbsd* | -openbsd* | -freebsd* | -riscix* \ + | -lynxos* | -bosx* | -nextstep* | -cxux* | -aout* | -elf* \ + | -ptx* | -coff* | -ecoff* | -winnt* | -domain* | -vsta* \ + | -udi* | -eabi* | -lites* | -ieee* | -go32* | -aux* \ + | -cygwin32* | -pe* | -psos* | -moss* | -proelf* | -rtems* \ + | -linux-gnu* | -uxpv*) + # Remember, each alternative MUST END IN *, to match a version number. + ;; + -linux*) + os=`echo $os | sed -e 's|linux|linux-gnu|'` + ;; + -sunos5*) + os=`echo $os | sed -e 's|sunos5|solaris2|'` + ;; + -sunos6*) + os=`echo $os | sed -e 's|sunos6|solaris3|'` + ;; + -osfrose*) + os=-osfrose + ;; + -osf*) + os=-osf + ;; + -utek*) + os=-bsd + ;; + -dynix*) + os=-bsd + ;; + -acis*) + os=-aos + ;; + -ctix* | -uts*) + os=-sysv + ;; + -ns2 ) + os=-nextstep2 + ;; + # Preserve the version number of sinix5. + -sinix5.*) + os=`echo $os | sed -e 's|sinix|sysv|'` + ;; + -sinix*) + os=-sysv4 + ;; + -triton*) + os=-sysv3 + ;; + -oss*) + os=-sysv3 + ;; + -svr4) + os=-sysv4 + ;; + -svr3) + os=-sysv3 + ;; + -sysvr4) + os=-sysv4 + ;; + # This must come after -sysvr4. + -sysv*) + ;; + -xenix) + os=-xenix + ;; + -none) + ;; + *) + # Get rid of the `-' at the beginning of $os. + os=`echo $os | sed 's/[^-]*-//'` + echo Invalid configuration \`$1\': system \`$os\' not recognized 1>&2 + exit 1 + ;; +esac +else + +# Here we handle the default operating systems that come with various machines. +# The value should be what the vendor currently ships out the door with their +# machine or put another way, the most popular os provided with the machine. + +# Note that if you're going to try to match "-MANUFACTURER" here (say, +# "-sun"), then you have to tell the case statement up towards the top +# that MANUFACTURER isn't an operating system. Otherwise, code above +# will signal an error saying that MANUFACTURER isn't an operating +# system, and we'll never get to this point. + +case $basic_machine in + *-acorn) + os=-riscix1.2 + ;; + arm*-semi) + os=-aout + ;; + pdp11-*) + os=-none + ;; + *-dec | vax-*) + os=-ultrix4.2 + ;; + m68*-apollo) + os=-domain + ;; + i386-sun) + os=-sunos4.0.2 + ;; + m68000-sun) + os=-sunos3 + # This also exists in the configure program, but was not the + # default. + # os=-sunos4 + ;; + *-tti) # must be before sparc entry or we get the wrong os. + os=-sysv3 + ;; + sparc-* | *-sun) + os=-sunos4.1.1 + ;; + *-ibm) + os=-aix + ;; + *-hp) + os=-hpux + ;; + *-hitachi) + os=-hiux + ;; + i860-* | *-att | *-ncr | *-altos | *-motorola | *-convergent) + os=-sysv + ;; + *-cbm) + os=-amigados + ;; + *-dg) + os=-dgux + ;; + *-dolphin) + os=-sysv3 + ;; + m68k-ccur) + os=-rtu + ;; + m88k-omron*) + os=-luna + ;; + *-next ) + os=-nextstep + ;; + *-sequent) + os=-ptx + ;; + *-crds) + os=-unos + ;; + *-ns) + os=-genix + ;; + i370-*) + os=-mvs + ;; + *-next) + os=-nextstep3 + ;; + *-gould) + os=-sysv + ;; + *-highlevel) + os=-bsd + ;; + *-encore) + os=-bsd + ;; + *-sgi) + os=-irix + ;; + *-siemens) + os=-sysv4 + ;; + *-masscomp) + os=-rtu + ;; + f301-fujitsu) + os=-uxpv + ;; + *) + os=-none + ;; +esac +fi + +# Here we handle the case where we know the os, and the CPU type, but not the +# manufacturer. We pick the logical manufacturer. +vendor=unknown +case $basic_machine in + *-unknown) + case $os in + -riscix*) + vendor=acorn + ;; + -sunos*) + vendor=sun + ;; + -aix*) + vendor=ibm + ;; + -hpux*) + vendor=hp + ;; + -hiux*) + vendor=hitachi + ;; + -unos*) + vendor=crds + ;; + -dgux*) + vendor=dg + ;; + -luna*) + vendor=omron + ;; + -genix*) + vendor=ns + ;; + -mvs*) + vendor=ibm + ;; + -ptx*) + vendor=sequent + ;; + -vxsim* | -vxworks*) + vendor=wrs + ;; + -aux*) + vendor=apple + ;; + esac + basic_machine=`echo $basic_machine | sed "s/unknown/$vendor/"` + ;; +esac + +echo $basic_machine$os diff --git a/src/interfaces/odbc/configure b/src/interfaces/odbc/configure new file mode 100755 index 0000000000..a4a6a01537 --- /dev/null +++ b/src/interfaces/odbc/configure @@ -0,0 +1,1991 @@ +#! /bin/sh + +# Guess values for system-dependent variables and create Makefiles. +# Generated automatically using autoconf version 2.12 +# Copyright (C) 1992, 93, 94, 95, 96 Free Software Foundation, Inc. +# +# This configure script is free software; the Free Software Foundation +# gives unlimited permission to copy, distribute and modify it. + +# Defaults: +ac_help= +ac_default_prefix=/usr/local +# Any additions from configure.in: +ac_default_prefix=/usr/local +ac_help="$ac_help + --with-template=TEMPLATE + use operating system template file + see template directory" +ac_help="$ac_help + --with-odbcinst= change default directory for odbcinst.ini" + +# Initialize some variables set by options. +# The variables have the same names as the options, with +# dashes changed to underlines. +build=NONE +cache_file=./config.cache +exec_prefix=NONE +host=NONE +no_create= +nonopt=NONE +no_recursion= +prefix=NONE +program_prefix=NONE +program_suffix=NONE +program_transform_name=s,x,x, +silent= +site= +srcdir= +target=NONE +verbose= +x_includes=NONE +x_libraries=NONE +bindir='${exec_prefix}/bin' +sbindir='${exec_prefix}/sbin' +libexecdir='${exec_prefix}/libexec' +datadir='${prefix}/share' +sysconfdir='${prefix}/etc' +sharedstatedir='${prefix}/com' +localstatedir='${prefix}/var' +libdir='${exec_prefix}/lib' +includedir='${prefix}/include' +oldincludedir='/usr/include' +infodir='${prefix}/info' +mandir='${prefix}/man' + +# Initialize some other variables. +subdirs= +MFLAGS= MAKEFLAGS= +# Maximum number of lines to put in a shell here document. +ac_max_here_lines=12 + +ac_prev= +for ac_option +do + + # If the previous option needs an argument, assign it. + if test -n "$ac_prev"; then + eval "$ac_prev=\$ac_option" + ac_prev= + continue + fi + + case "$ac_option" in + -*=*) ac_optarg=`echo "$ac_option" | sed 's/[-_a-zA-Z0-9]*=//'` ;; + *) ac_optarg= ;; + esac + + # Accept the important Cygnus configure options, so we can diagnose typos. + + case "$ac_option" in + + -bindir | --bindir | --bindi | --bind | --bin | --bi) + ac_prev=bindir ;; + -bindir=* | --bindir=* | --bindi=* | --bind=* | --bin=* | --bi=*) + bindir="$ac_optarg" ;; + + -build | --build | --buil | --bui | --bu) + ac_prev=build ;; + -build=* | --build=* | --buil=* | --bui=* | --bu=*) + build="$ac_optarg" ;; + + -cache-file | --cache-file | --cache-fil | --cache-fi \ + | --cache-f | --cache- | --cache | --cach | --cac | --ca | --c) + ac_prev=cache_file ;; + -cache-file=* | --cache-file=* | --cache-fil=* | --cache-fi=* \ + | --cache-f=* | --cache-=* | --cache=* | --cach=* | --cac=* | --ca=* | --c=*) + cache_file="$ac_optarg" ;; + + -datadir | --datadir | --datadi | --datad | --data | --dat | --da) + ac_prev=datadir ;; + -datadir=* | --datadir=* | --datadi=* | --datad=* | --data=* | --dat=* \ + | --da=*) + datadir="$ac_optarg" ;; + + -disable-* | --disable-*) + ac_feature=`echo $ac_option|sed -e 's/-*disable-//'` + # Reject names that are not valid shell variable names. + if test -n "`echo $ac_feature| sed 's/[-a-zA-Z0-9_]//g'`"; then + { echo "configure: error: $ac_feature: invalid feature name" 1>&2; exit 1; } + fi + ac_feature=`echo $ac_feature| sed 's/-/_/g'` + eval "enable_${ac_feature}=no" ;; + + -enable-* | --enable-*) + ac_feature=`echo $ac_option|sed -e 's/-*enable-//' -e 's/=.*//'` + # Reject names that are not valid shell variable names. + if test -n "`echo $ac_feature| sed 's/[-_a-zA-Z0-9]//g'`"; then + { echo "configure: error: $ac_feature: invalid feature name" 1>&2; exit 1; } + fi + ac_feature=`echo $ac_feature| sed 's/-/_/g'` + case "$ac_option" in + *=*) ;; + *) ac_optarg=yes ;; + esac + eval "enable_${ac_feature}='$ac_optarg'" ;; + + -exec-prefix | --exec_prefix | --exec-prefix | --exec-prefi \ + | --exec-pref | --exec-pre | --exec-pr | --exec-p | --exec- \ + | --exec | --exe | --ex) + ac_prev=exec_prefix ;; + -exec-prefix=* | --exec_prefix=* | --exec-prefix=* | --exec-prefi=* \ + | --exec-pref=* | --exec-pre=* | --exec-pr=* | --exec-p=* | --exec-=* \ + | --exec=* | --exe=* | --ex=*) + exec_prefix="$ac_optarg" ;; + + -gas | --gas | --ga | --g) + # Obsolete; use --with-gas. + with_gas=yes ;; + + -help | --help | --hel | --he) + # Omit some internal or obsolete options to make the list less imposing. + # This message is too long to be a string in the A/UX 3.1 sh. + cat << EOF +Usage: configure [options] [host] +Options: [defaults in brackets after descriptions] +Configuration: + --cache-file=FILE cache test results in FILE + --help print this message + --no-create do not create output files + --quiet, --silent do not print \`checking...' messages + --version print the version of autoconf that created configure +Directory and file names: + --prefix=PREFIX install architecture-independent files in PREFIX + [$ac_default_prefix] + --exec-prefix=EPREFIX install architecture-dependent files in EPREFIX + [same as prefix] + --bindir=DIR user executables in DIR [EPREFIX/bin] + --sbindir=DIR system admin executables in DIR [EPREFIX/sbin] + --libexecdir=DIR program executables in DIR [EPREFIX/libexec] + --datadir=DIR read-only architecture-independent data in DIR + [PREFIX/share] + --sysconfdir=DIR read-only single-machine data in DIR [PREFIX/etc] + --sharedstatedir=DIR modifiable architecture-independent data in DIR + [PREFIX/com] + --localstatedir=DIR modifiable single-machine data in DIR [PREFIX/var] + --libdir=DIR object code libraries in DIR [EPREFIX/lib] + --includedir=DIR C header files in DIR [PREFIX/include] + --oldincludedir=DIR C header files for non-gcc in DIR [/usr/include] + --infodir=DIR info documentation in DIR [PREFIX/info] + --mandir=DIR man documentation in DIR [PREFIX/man] + --srcdir=DIR find the sources in DIR [configure dir or ..] + --program-prefix=PREFIX prepend PREFIX to installed program names + --program-suffix=SUFFIX append SUFFIX to installed program names + --program-transform-name=PROGRAM + run sed PROGRAM on installed program names +EOF + cat << EOF +Host type: + --build=BUILD configure for building on BUILD [BUILD=HOST] + --host=HOST configure for HOST [guessed] + --target=TARGET configure for TARGET [TARGET=HOST] +Features and packages: + --disable-FEATURE do not include FEATURE (same as --enable-FEATURE=no) + --enable-FEATURE[=ARG] include FEATURE [ARG=yes] + --with-PACKAGE[=ARG] use PACKAGE [ARG=yes] + --without-PACKAGE do not use PACKAGE (same as --with-PACKAGE=no) + --x-includes=DIR X include files are in DIR + --x-libraries=DIR X library files are in DIR +EOF + if test -n "$ac_help"; then + echo "--enable and --with options recognized:$ac_help" + fi + exit 0 ;; + + -host | --host | --hos | --ho) + ac_prev=host ;; + -host=* | --host=* | --hos=* | --ho=*) + host="$ac_optarg" ;; + + -includedir | --includedir | --includedi | --included | --include \ + | --includ | --inclu | --incl | --inc) + ac_prev=includedir ;; + -includedir=* | --includedir=* | --includedi=* | --included=* | --include=* \ + | --includ=* | --inclu=* | --incl=* | --inc=*) + includedir="$ac_optarg" ;; + + -infodir | --infodir | --infodi | --infod | --info | --inf) + ac_prev=infodir ;; + -infodir=* | --infodir=* | --infodi=* | --infod=* | --info=* | --inf=*) + infodir="$ac_optarg" ;; + + -libdir | --libdir | --libdi | --libd) + ac_prev=libdir ;; + -libdir=* | --libdir=* | --libdi=* | --libd=*) + libdir="$ac_optarg" ;; + + -libexecdir | --libexecdir | --libexecdi | --libexecd | --libexec \ + | --libexe | --libex | --libe) + ac_prev=libexecdir ;; + -libexecdir=* | --libexecdir=* | --libexecdi=* | --libexecd=* | --libexec=* \ + | --libexe=* | --libex=* | --libe=*) + libexecdir="$ac_optarg" ;; + + -localstatedir | --localstatedir | --localstatedi | --localstated \ + | --localstate | --localstat | --localsta | --localst \ + | --locals | --local | --loca | --loc | --lo) + ac_prev=localstatedir ;; + -localstatedir=* | --localstatedir=* | --localstatedi=* | --localstated=* \ + | --localstate=* | --localstat=* | --localsta=* | --localst=* \ + | --locals=* | --local=* | --loca=* | --loc=* | --lo=*) + localstatedir="$ac_optarg" ;; + + -mandir | --mandir | --mandi | --mand | --man | --ma | --m) + ac_prev=mandir ;; + -mandir=* | --mandir=* | --mandi=* | --mand=* | --man=* | --ma=* | --m=*) + mandir="$ac_optarg" ;; + + -nfp | --nfp | --nf) + # Obsolete; use --without-fp. + with_fp=no ;; + + -no-create | --no-create | --no-creat | --no-crea | --no-cre \ + | --no-cr | --no-c) + no_create=yes ;; + + -no-recursion | --no-recursion | --no-recursio | --no-recursi \ + | --no-recurs | --no-recur | --no-recu | --no-rec | --no-re | --no-r) + no_recursion=yes ;; + + -oldincludedir | --oldincludedir | --oldincludedi | --oldincluded \ + | --oldinclude | --oldinclud | --oldinclu | --oldincl | --oldinc \ + | --oldin | --oldi | --old | --ol | --o) + ac_prev=oldincludedir ;; + -oldincludedir=* | --oldincludedir=* | --oldincludedi=* | --oldincluded=* \ + | --oldinclude=* | --oldinclud=* | --oldinclu=* | --oldincl=* | --oldinc=* \ + | --oldin=* | --oldi=* | --old=* | --ol=* | --o=*) + oldincludedir="$ac_optarg" ;; + + -prefix | --prefix | --prefi | --pref | --pre | --pr | --p) + ac_prev=prefix ;; + -prefix=* | --prefix=* | --prefi=* | --pref=* | --pre=* | --pr=* | --p=*) + prefix="$ac_optarg" ;; + + -program-prefix | --program-prefix | --program-prefi | --program-pref \ + | --program-pre | --program-pr | --program-p) + ac_prev=program_prefix ;; + -program-prefix=* | --program-prefix=* | --program-prefi=* \ + | --program-pref=* | --program-pre=* | --program-pr=* | --program-p=*) + program_prefix="$ac_optarg" ;; + + -program-suffix | --program-suffix | --program-suffi | --program-suff \ + | --program-suf | --program-su | --program-s) + ac_prev=program_suffix ;; + -program-suffix=* | --program-suffix=* | --program-suffi=* \ + | --program-suff=* | --program-suf=* | --program-su=* | --program-s=*) + program_suffix="$ac_optarg" ;; + + -program-transform-name | --program-transform-name \ + | --program-transform-nam | --program-transform-na \ + | --program-transform-n | --program-transform- \ + | --program-transform | --program-transfor \ + | --program-transfo | --program-transf \ + | --program-trans | --program-tran \ + | --progr-tra | --program-tr | --program-t) + ac_prev=program_transform_name ;; + -program-transform-name=* | --program-transform-name=* \ + | --program-transform-nam=* | --program-transform-na=* \ + | --program-transform-n=* | --program-transform-=* \ + | --program-transform=* | --program-transfor=* \ + | --program-transfo=* | --program-transf=* \ + | --program-trans=* | --program-tran=* \ + | --progr-tra=* | --program-tr=* | --program-t=*) + program_transform_name="$ac_optarg" ;; + + -q | -quiet | --quiet | --quie | --qui | --qu | --q \ + | -silent | --silent | --silen | --sile | --sil) + silent=yes ;; + + -sbindir | --sbindir | --sbindi | --sbind | --sbin | --sbi | --sb) + ac_prev=sbindir ;; + -sbindir=* | --sbindir=* | --sbindi=* | --sbind=* | --sbin=* \ + | --sbi=* | --sb=*) + sbindir="$ac_optarg" ;; + + -sharedstatedir | --sharedstatedir | --sharedstatedi \ + | --sharedstated | --sharedstate | --sharedstat | --sharedsta \ + | --sharedst | --shareds | --shared | --share | --shar \ + | --sha | --sh) + ac_prev=sharedstatedir ;; + -sharedstatedir=* | --sharedstatedir=* | --sharedstatedi=* \ + | --sharedstated=* | --sharedstate=* | --sharedstat=* | --sharedsta=* \ + | --sharedst=* | --shareds=* | --shared=* | --share=* | --shar=* \ + | --sha=* | --sh=*) + sharedstatedir="$ac_optarg" ;; + + -site | --site | --sit) + ac_prev=site ;; + -site=* | --site=* | --sit=*) + site="$ac_optarg" ;; + + -srcdir | --srcdir | --srcdi | --srcd | --src | --sr) + ac_prev=srcdir ;; + -srcdir=* | --srcdir=* | --srcdi=* | --srcd=* | --src=* | --sr=*) + srcdir="$ac_optarg" ;; + + -sysconfdir | --sysconfdir | --sysconfdi | --sysconfd | --sysconf \ + | --syscon | --sysco | --sysc | --sys | --sy) + ac_prev=sysconfdir ;; + -sysconfdir=* | --sysconfdir=* | --sysconfdi=* | --sysconfd=* | --sysconf=* \ + | --syscon=* | --sysco=* | --sysc=* | --sys=* | --sy=*) + sysconfdir="$ac_optarg" ;; + + -target | --target | --targe | --targ | --tar | --ta | --t) + ac_prev=target ;; + -target=* | --target=* | --targe=* | --targ=* | --tar=* | --ta=* | --t=*) + target="$ac_optarg" ;; + + -v | -verbose | --verbose | --verbos | --verbo | --verb) + verbose=yes ;; + + -version | --version | --versio | --versi | --vers) + echo "configure generated by autoconf version 2.12" + exit 0 ;; + + -with-* | --with-*) + ac_package=`echo $ac_option|sed -e 's/-*with-//' -e 's/=.*//'` + # Reject names that are not valid shell variable names. + if test -n "`echo $ac_package| sed 's/[-_a-zA-Z0-9]//g'`"; then + { echo "configure: error: $ac_package: invalid package name" 1>&2; exit 1; } + fi + ac_package=`echo $ac_package| sed 's/-/_/g'` + case "$ac_option" in + *=*) ;; + *) ac_optarg=yes ;; + esac + eval "with_${ac_package}='$ac_optarg'" ;; + + -without-* | --without-*) + ac_package=`echo $ac_option|sed -e 's/-*without-//'` + # Reject names that are not valid shell variable names. + if test -n "`echo $ac_package| sed 's/[-a-zA-Z0-9_]//g'`"; then + { echo "configure: error: $ac_package: invalid package name" 1>&2; exit 1; } + fi + ac_package=`echo $ac_package| sed 's/-/_/g'` + eval "with_${ac_package}=no" ;; + + --x) + # Obsolete; use --with-x. + with_x=yes ;; + + -x-includes | --x-includes | --x-include | --x-includ | --x-inclu \ + | --x-incl | --x-inc | --x-in | --x-i) + ac_prev=x_includes ;; + -x-includes=* | --x-includes=* | --x-include=* | --x-includ=* | --x-inclu=* \ + | --x-incl=* | --x-inc=* | --x-in=* | --x-i=*) + x_includes="$ac_optarg" ;; + + -x-libraries | --x-libraries | --x-librarie | --x-librari \ + | --x-librar | --x-libra | --x-libr | --x-lib | --x-li | --x-l) + ac_prev=x_libraries ;; + -x-libraries=* | --x-libraries=* | --x-librarie=* | --x-librari=* \ + | --x-librar=* | --x-libra=* | --x-libr=* | --x-lib=* | --x-li=* | --x-l=*) + x_libraries="$ac_optarg" ;; + + -*) { echo "configure: error: $ac_option: invalid option; use --help to show usage" 1>&2; exit 1; } + ;; + + *) + if test -n "`echo $ac_option| sed 's/[-a-z0-9.]//g'`"; then + echo "configure: warning: $ac_option: invalid host type" 1>&2 + fi + if test "x$nonopt" != xNONE; then + { echo "configure: error: can only configure for one host and one target at a time" 1>&2; exit 1; } + fi + nonopt="$ac_option" + ;; + + esac +done + +if test -n "$ac_prev"; then + { echo "configure: error: missing argument to --`echo $ac_prev | sed 's/_/-/g'`" 1>&2; exit 1; } +fi + +trap 'rm -fr conftest* confdefs* core core.* *.core $ac_clean_files; exit 1' 1 2 15 + +# File descriptor usage: +# 0 standard input +# 1 file creation +# 2 errors and warnings +# 3 some systems may open it to /dev/tty +# 4 used on the Kubota Titan +# 6 checking for... messages and results +# 5 compiler messages saved in config.log +if test "$silent" = yes; then + exec 6>/dev/null +else + exec 6>&1 +fi +exec 5>./config.log + +echo "\ +This file contains any messages produced by compilers while +running configure, to aid debugging if configure makes a mistake. +" 1>&5 + +# Strip out --no-create and --no-recursion so they do not pile up. +# Also quote any args containing shell metacharacters. +ac_configure_args= +for ac_arg +do + case "$ac_arg" in + -no-create | --no-create | --no-creat | --no-crea | --no-cre \ + | --no-cr | --no-c) ;; + -no-recursion | --no-recursion | --no-recursio | --no-recursi \ + | --no-recurs | --no-recur | --no-recu | --no-rec | --no-re | --no-r) ;; + *" "*|*" "*|*[\[\]\~\#\$\^\&\*\(\)\{\}\\\|\;\<\>\?]*) + ac_configure_args="$ac_configure_args '$ac_arg'" ;; + *) ac_configure_args="$ac_configure_args $ac_arg" ;; + esac +done + +# NLS nuisances. +# Only set these to C if already set. These must not be set unconditionally +# because not all systems understand e.g. LANG=C (notably SCO). +# Fixing LC_MESSAGES prevents Solaris sh from translating var values in `set'! +# Non-C LC_CTYPE values break the ctype check. +if test "${LANG+set}" = set; then LANG=C; export LANG; fi +if test "${LC_ALL+set}" = set; then LC_ALL=C; export LC_ALL; fi +if test "${LC_MESSAGES+set}" = set; then LC_MESSAGES=C; export LC_MESSAGES; fi +if test "${LC_CTYPE+set}" = set; then LC_CTYPE=C; export LC_CTYPE; fi + +# confdefs.h avoids OS command line length limits that DEFS can exceed. +rm -rf conftest* confdefs.h +# AIX cpp loses on an empty file, so make sure it contains at least a newline. +echo > confdefs.h + +# A filename unique to this package, relative to the directory that +# configure is in, which we can look for to find out if srcdir is correct. +ac_unique_file=bind.c + +# Find the source files, if location was not specified. +if test -z "$srcdir"; then + ac_srcdir_defaulted=yes + # Try the directory containing this script, then its parent. + ac_prog=$0 + ac_confdir=`echo $ac_prog|sed 's%/[^/][^/]*$%%'` + test "x$ac_confdir" = "x$ac_prog" && ac_confdir=. + srcdir=$ac_confdir + if test ! -r $srcdir/$ac_unique_file; then + srcdir=.. + fi +else + ac_srcdir_defaulted=no +fi +if test ! -r $srcdir/$ac_unique_file; then + if test "$ac_srcdir_defaulted" = yes; then + { echo "configure: error: can not find sources in $ac_confdir or .." 1>&2; exit 1; } + else + { echo "configure: error: can not find sources in $srcdir" 1>&2; exit 1; } + fi +fi +srcdir=`echo "${srcdir}" | sed 's%\([^/]\)/*$%\1%'` + +# Prefer explicitly selected file to automatically selected ones. +if test -z "$CONFIG_SITE"; then + if test "x$prefix" != xNONE; then + CONFIG_SITE="$prefix/share/config.site $prefix/etc/config.site" + else + CONFIG_SITE="$ac_default_prefix/share/config.site $ac_default_prefix/etc/config.site" + fi +fi +for ac_site_file in $CONFIG_SITE; do + if test -r "$ac_site_file"; then + echo "loading site script $ac_site_file" + . "$ac_site_file" + fi +done + +if test -r "$cache_file"; then + echo "loading cache $cache_file" + . $cache_file +else + echo "creating cache $cache_file" + > $cache_file +fi + +ac_ext=c +# CFLAGS is not in ac_cpp because -g, -O, etc. are not valid cpp options. +ac_cpp='$CPP $CPPFLAGS' +ac_compile='${CC-cc} -c $CFLAGS $CPPFLAGS conftest.$ac_ext 1>&5' +ac_link='${CC-cc} -o conftest $CFLAGS $CPPFLAGS $LDFLAGS conftest.$ac_ext $LIBS 1>&5' +cross_compiling=$ac_cv_prog_cc_cross + +if (echo "testing\c"; echo 1,2,3) | grep c >/dev/null; then + # Stardent Vistra SVR4 grep lacks -e, says ghazi@caip.rutgers.edu. + if (echo -n testing; echo 1,2,3) | sed s/-n/xn/ | grep xn >/dev/null; then + ac_n= ac_c=' +' ac_t=' ' + else + ac_n=-n ac_c= ac_t= + fi +else + ac_n= ac_c='\c' ac_t= +fi + + + + +if test -d ../../interfaces +then + TEMPLATEDIR=../../template + if test "$prefix" = "NONE" + then + ac_default_prefix=/usr/local/pgsql + fi + ODBCINSTDIR= +else + TEMPLATEDIR=./template + if test "$prefix" = "NONE" + then + ODBCINSTDIR=/share + else + ODBCINSTDIR= + fi +fi + +echo "*** configuring psqlodbc ***" + +ac_aux_dir= +for ac_dir in $srcdir $srcdir/.. $srcdir/../..; do + if test -f $ac_dir/install-sh; then + ac_aux_dir=$ac_dir + ac_install_sh="$ac_aux_dir/install-sh -c" + break + elif test -f $ac_dir/install.sh; then + ac_aux_dir=$ac_dir + ac_install_sh="$ac_aux_dir/install.sh -c" + break + fi +done +if test -z "$ac_aux_dir"; then + { echo "configure: error: can not find install-sh or install.sh in $srcdir $srcdir/.. $srcdir/../.." 1>&2; exit 1; } +fi +ac_config_guess=$ac_aux_dir/config.guess +ac_config_sub=$ac_aux_dir/config.sub +ac_configure=$ac_aux_dir/configure # This should be Cygnus configure. + + +# Make sure we can run config.sub. +if $ac_config_sub sun4 >/dev/null 2>&1; then : +else { echo "configure: error: can not run $ac_config_sub" 1>&2; exit 1; } +fi + +echo $ac_n "checking host system type""... $ac_c" 1>&6 +echo "configure:577: checking host system type" >&5 + +host_alias=$host +case "$host_alias" in +NONE) + case $nonopt in + NONE) + if host_alias=`$ac_config_guess`; then : + else { echo "configure: error: can not guess host type; you must specify one" 1>&2; exit 1; } + fi ;; + *) host_alias=$nonopt ;; + esac ;; +esac + +host=`$ac_config_sub $host_alias` +host_cpu=`echo $host | sed 's/^\([^-]*\)-\([^-]*\)-\(.*\)$/\1/'` +host_vendor=`echo $host | sed 's/^\([^-]*\)-\([^-]*\)-\(.*\)$/\2/'` +host_os=`echo $host | sed 's/^\([^-]*\)-\([^-]*\)-\(.*\)$/\3/'` +echo "$ac_t""$host" 1>&6 + + +case "$host_os" in + solaris*) + case "$host_cpu" in + sparc) os=sparc_solaris ;; + i386) os=i386_solaris ;; + esac ;; + sunos*) os=sunos4 ;; + aux*) os=aux ;; + linux*) os=linux ;; + bsdi*) os=bsdi ;; + freebsd*|netbsd*|openbsd*) os=bsd ;; + dgux*) os=dgux ;; + aix*) os=aix ;; +nextstep*) os=nextstep ;; + ultrix*) os=ultrix4 ;; + irix*) os=irix5 ;; + hpux*) os=hpux ;; + osf*) os=alpha ;; + sco*) os=sco ;; + machten*) os=machten ;; + cygwin*) os=win ;; + sysv4.2*) + case "$host_vendor" in + univel) os=univel ;; + *) os=unknown ;; + esac ;; + sysv4*) os=svr4 ;; +*) echo "" + echo "*************************************************************" + echo "configure does not currently recognize your operating system," + echo "therefore you must do a manual configuration of:" + echo "$host_os" + echo "Please contact scrappy@hub.org to see about rectifying this, " + echo "including the above 'checking host system type...' line " + echo "*************************************************************" + echo "" + exit;; +esac + + +PORTNAME=${os} + + + +echo "checking echo setting..." +if echo '\c' | grep -s c >/dev/null 2>&1 +then + ECHO_N="echo -n" + ECHO_C="" +else + ECHO_N="echo" + ECHO_C='\c' +fi + + + + +echo $ac_n "checking setting template to""... $ac_c" 1>&6 +echo "configure:656: checking setting template to" >&5 +# Check whether --with-template or --without-template was given. +if test "${with_template+set}" = set; then + withval="$with_template" + TEMPLATE=$withval +else + host_no_ver=`echo "$host" | sed 's/[0-9.]*$//'` + GUESS=`grep "$host_no_ver" $TEMPLATEDIR/.similar | sed 's/.*=//' | tail -1` + if test "$GUESS" + then TEMPLATE="$GUESS" + else TEMPLATE=`uname -s | tr A-Z a-z` + fi + +fi + +echo "$ac_t""$TEMPLATE" 1>&6 + +if test ! -d "$TEMPLATEDIR" +then + cat << EOT +************************************************************** +You seem to be missing the template directory needed by +configure. If you just copied the source from the Postgres +distribution you should instead have issued the command +'make standalone' which would have built a distribution +containing the necessary template directory. The other +option is that your trying to build from the source +which is meant to be placed in the Postgres distribution +directory 'interfaces/odbc'. Depending on your case either get the +standalone source from the following Web site: + + www.insightdist.com/psqlodbc/ + +or issue the 'make standalone' command from the +'interfaces/odbc' directory of your Postgres Distribution, +or copy the distribution file you have to your Postgres +distribution's 'interfaces/odbc' directory and try +again. + +If neither of these is the case than please complain +kindly to the maintainers, their e-mail addresses can +be found in the Readme files. +************************************************************* +EOT + +exit +else + +if test ! -f "$TEMPLATEDIR/$TEMPLATE" +then + cat </dev/null` + fi + if test "$GUESS" + then + TEMPLATE=`echo $GUESS | sed 's/.*=//'` + fi + export TEMPLATE + ls $TEMPLATEDIR + echo "**************************************************************" + $ECHO_N "Appropriate template file { $TEMPLATE }: $ECHO_C" + read a + if test "$a." != "." + then + TEMPLATE=$a + fi + if test ! -f $TEMPLATEDIR/$TEMPLATE + then + echo "You must choose an appropriate template file." + exit + fi +fi +fi + +TEMPLATE=$TEMPLATEDIR/$TEMPLATE +export TEMPLATE +echo "" + +AROPT=`grep '^AROPT:' $TEMPLATE | awk -F: '{print $2}'` +SHARED_LIB=`grep '^SHARED_LIB:' $TEMPLATE | awk -F: '{print $2}'` +CFLAGS=`grep '^CFLAGS:' $TEMPLATE | awk -F: '{print $2}'` +SRCH_INC=`grep '^SRCH_INC:' $TEMPLATE | awk -F: '{print $2}'` +SRCH_LIB=`grep '^SRCH_LIB:' $TEMPLATE | awk -F: '{print $2}'` +DLSUFFIX=`grep '^DLSUFFIX:' $TEMPLATE | awk -F: '{print $2}'` +DL_LIB=`grep '^DL_LIB:' $TEMPLATE | awk -F: '{print $2}'` +CC=`grep '^CC:' $TEMPLATE | awk -F: '{print $2}'` +LIBS=`grep '^LIBS:' $TEMPLATE | awk -F: '{print $2}'` + + +a=$SRCH_INC +CPPFLAGS=`echo "$a" | sed 's@ *@ @g; s@^\([^ ]\)@-I\1@; s@ \([^ ]\)@ -I\1@g'` + +export CPPFLAGS +echo "- setting CPPFLAGS=$CPPFLAGS" + +a=$SRCH_LIB +LDFLAGS=`echo "$a" | sed 's@ *@ @g; s@^\([^ ]\)@-L\1@; s@ \([^ ]\)@ -L\1@g'` + +export LDFLAGS +echo "- setting LDFLAGS=$LDFLAGS" + +echo $ac_n "checking setting ODBCINST""... $ac_c" 1>&6 +echo "configure:768: checking setting ODBCINST" >&5 +# Check whether --with-odbcinst or --without-odbcinst was given. +if test "${with_odbcinst+set}" = set; then + withval="$with_odbcinst" + cat >> confdefs.h <&6 +else + cat >> confdefs.h <&6 + +fi + + +if test "X$with_odbcinst" != "X" +then + ODBCINSTDIR=$with_odbcinst +fi + + + +if test "X$with_compiler" != "X" +then + CC=$with_compiler +else + # Extract the first word of "gcc", so it can be a program name with args. +set dummy gcc; ac_word=$2 +echo $ac_n "checking for $ac_word""... $ac_c" 1>&6 +echo "configure:799: checking for $ac_word" >&5 +if eval "test \"`echo '$''{'ac_cv_prog_CC'+set}'`\" = set"; then + echo $ac_n "(cached) $ac_c" 1>&6 +else + if test -n "$CC"; then + ac_cv_prog_CC="$CC" # Let the user override the test. +else + IFS="${IFS= }"; ac_save_ifs="$IFS"; IFS="${IFS}:" + for ac_dir in $PATH; do + test -z "$ac_dir" && ac_dir=. + if test -f $ac_dir/$ac_word; then + ac_cv_prog_CC="gcc" + break + fi + done + IFS="$ac_save_ifs" +fi +fi +CC="$ac_cv_prog_CC" +if test -n "$CC"; then + echo "$ac_t""$CC" 1>&6 +else + echo "$ac_t""no" 1>&6 +fi + +if test -z "$CC"; then + # Extract the first word of "cc", so it can be a program name with args. +set dummy cc; ac_word=$2 +echo $ac_n "checking for $ac_word""... $ac_c" 1>&6 +echo "configure:828: checking for $ac_word" >&5 +if eval "test \"`echo '$''{'ac_cv_prog_CC'+set}'`\" = set"; then + echo $ac_n "(cached) $ac_c" 1>&6 +else + if test -n "$CC"; then + ac_cv_prog_CC="$CC" # Let the user override the test. +else + IFS="${IFS= }"; ac_save_ifs="$IFS"; IFS="${IFS}:" + ac_prog_rejected=no + for ac_dir in $PATH; do + test -z "$ac_dir" && ac_dir=. + if test -f $ac_dir/$ac_word; then + if test "$ac_dir/$ac_word" = "/usr/ucb/cc"; then + ac_prog_rejected=yes + continue + fi + ac_cv_prog_CC="cc" + break + fi + done + IFS="$ac_save_ifs" +if test $ac_prog_rejected = yes; then + # We found a bogon in the path, so make sure we never use it. + set dummy $ac_cv_prog_CC + shift + if test $# -gt 0; then + # We chose a different compiler from the bogus one. + # However, it has the same basename, so the bogon will be chosen + # first if we set CC to just the basename; use the full file name. + shift + set dummy "$ac_dir/$ac_word" "$@" + shift + ac_cv_prog_CC="$@" + fi +fi +fi +fi +CC="$ac_cv_prog_CC" +if test -n "$CC"; then + echo "$ac_t""$CC" 1>&6 +else + echo "$ac_t""no" 1>&6 +fi + + test -z "$CC" && { echo "configure: error: no acceptable cc found in \$PATH" 1>&2; exit 1; } +fi + +echo $ac_n "checking whether the C compiler ($CC $CFLAGS $LDFLAGS) works""... $ac_c" 1>&6 +echo "configure:876: checking whether the C compiler ($CC $CFLAGS $LDFLAGS) works" >&5 + +ac_ext=c +# CFLAGS is not in ac_cpp because -g, -O, etc. are not valid cpp options. +ac_cpp='$CPP $CPPFLAGS' +ac_compile='${CC-cc} -c $CFLAGS $CPPFLAGS conftest.$ac_ext 1>&5' +ac_link='${CC-cc} -o conftest $CFLAGS $CPPFLAGS $LDFLAGS conftest.$ac_ext $LIBS 1>&5' +cross_compiling=$ac_cv_prog_cc_cross + +cat > conftest.$ac_ext <&5; (eval $ac_link) 2>&5; } && test -s conftest; then + ac_cv_prog_cc_works=yes + # If we can't run a trivial program, we are probably using a cross compiler. + if (./conftest; exit) 2>/dev/null; then + ac_cv_prog_cc_cross=no + else + ac_cv_prog_cc_cross=yes + fi +else + echo "configure: failed program was:" >&5 + cat conftest.$ac_ext >&5 + ac_cv_prog_cc_works=no +fi +rm -fr conftest* + +echo "$ac_t""$ac_cv_prog_cc_works" 1>&6 +if test $ac_cv_prog_cc_works = no; then + { echo "configure: error: installation or configuration problem: C compiler cannot create executables." 1>&2; exit 1; } +fi +echo $ac_n "checking whether the C compiler ($CC $CFLAGS $LDFLAGS) is a cross-compiler""... $ac_c" 1>&6 +echo "configure:910: checking whether the C compiler ($CC $CFLAGS $LDFLAGS) is a cross-compiler" >&5 +echo "$ac_t""$ac_cv_prog_cc_cross" 1>&6 +cross_compiling=$ac_cv_prog_cc_cross + +echo $ac_n "checking whether we are using GNU C""... $ac_c" 1>&6 +echo "configure:915: checking whether we are using GNU C" >&5 +if eval "test \"`echo '$''{'ac_cv_prog_gcc'+set}'`\" = set"; then + echo $ac_n "(cached) $ac_c" 1>&6 +else + cat > conftest.c <&5; (eval $ac_try) 2>&5; }; } | egrep yes >/dev/null 2>&1; then + ac_cv_prog_gcc=yes +else + ac_cv_prog_gcc=no +fi +fi + +echo "$ac_t""$ac_cv_prog_gcc" 1>&6 + +if test $ac_cv_prog_gcc = yes; then + GCC=yes + ac_test_CFLAGS="${CFLAGS+set}" + ac_save_CFLAGS="$CFLAGS" + CFLAGS= + echo $ac_n "checking whether ${CC-cc} accepts -g""... $ac_c" 1>&6 +echo "configure:939: checking whether ${CC-cc} accepts -g" >&5 +if eval "test \"`echo '$''{'ac_cv_prog_cc_g'+set}'`\" = set"; then + echo $ac_n "(cached) $ac_c" 1>&6 +else + echo 'void f(){}' > conftest.c +if test -z "`${CC-cc} -g -c conftest.c 2>&1`"; then + ac_cv_prog_cc_g=yes +else + ac_cv_prog_cc_g=no +fi +rm -f conftest* + +fi + +echo "$ac_t""$ac_cv_prog_cc_g" 1>&6 + if test "$ac_test_CFLAGS" = set; then + CFLAGS="$ac_save_CFLAGS" + elif test $ac_cv_prog_cc_g = yes; then + CFLAGS="-g -O2" + else + CFLAGS="-O2" + fi +else + GCC= + test "${CFLAGS+set}" = set || CFLAGS="-g" +fi + +fi + + + +echo $ac_n "checking how to run the C preprocessor""... $ac_c" 1>&6 +echo "configure:971: checking how to run the C preprocessor" >&5 +# On Suns, sometimes $CPP names a directory. +if test -n "$CPP" && test -d "$CPP"; then + CPP= +fi +if test -z "$CPP"; then +if eval "test \"`echo '$''{'ac_cv_prog_CPP'+set}'`\" = set"; then + echo $ac_n "(cached) $ac_c" 1>&6 +else + # This must be in double quotes, not single quotes, because CPP may get + # substituted into the Makefile and "${CC-cc}" will confuse make. + CPP="${CC-cc} -E" + # On the NeXT, cc -E runs the code through the compiler's parser, + # not just through cpp. + cat > conftest.$ac_ext < +Syntax Error +EOF +ac_try="$ac_cpp conftest.$ac_ext >/dev/null 2>conftest.out" +{ (eval echo configure:992: \"$ac_try\") 1>&5; (eval $ac_try) 2>&5; } +ac_err=`grep -v '^ *+' conftest.out` +if test -z "$ac_err"; then + : +else + echo "$ac_err" >&5 + echo "configure: failed program was:" >&5 + cat conftest.$ac_ext >&5 + rm -rf conftest* + CPP="${CC-cc} -E -traditional-cpp" + cat > conftest.$ac_ext < +Syntax Error +EOF +ac_try="$ac_cpp conftest.$ac_ext >/dev/null 2>conftest.out" +{ (eval echo configure:1009: \"$ac_try\") 1>&5; (eval $ac_try) 2>&5; } +ac_err=`grep -v '^ *+' conftest.out` +if test -z "$ac_err"; then + : +else + echo "$ac_err" >&5 + echo "configure: failed program was:" >&5 + cat conftest.$ac_ext >&5 + rm -rf conftest* + CPP=/lib/cpp +fi +rm -f conftest* +fi +rm -f conftest* + ac_cv_prog_CPP="$CPP" +fi + CPP="$ac_cv_prog_CPP" +else + ac_cv_prog_CPP="$CPP" +fi +echo "$ac_t""$CPP" 1>&6 + + + + + + + + + + + +INSTALLPATH="/usr/ucb:$PATH" +for ac_prog in ginstall installbsd bsdinst scoinst install +do +# Extract the first word of "$ac_prog", so it can be a program name with args. +set dummy $ac_prog; ac_word=$2 +echo $ac_n "checking for $ac_word""... $ac_c" 1>&6 +echo "configure:1047: checking for $ac_word" >&5 +if eval "test \"`echo '$''{'ac_cv_path_INSTALL'+set}'`\" = set"; then + echo $ac_n "(cached) $ac_c" 1>&6 +else + case "$INSTALL" in + /*) + ac_cv_path_INSTALL="$INSTALL" # Let the user override the test with a path. + ;; + *) + IFS="${IFS= }"; ac_save_ifs="$IFS"; IFS="${IFS}:" + for ac_dir in $INSTALLPATH$ac_dummy; do + test -z "$ac_dir" && ac_dir=. + if test -f $ac_dir/$ac_word; then + ac_cv_path_INSTALL="$ac_dir/$ac_word" + break + fi + done + IFS="$ac_save_ifs" + ;; +esac +fi +INSTALL="$ac_cv_path_INSTALL" +if test -n "$INSTALL"; then + echo "$ac_t""$INSTALL" 1>&6 +else + echo "$ac_t""no" 1>&6 +fi + +test -n "$INSTALL" && break +done +test -n "$INSTALL" || INSTALL="NONE" + +if test $INSTALL = "NONE" +then + echo "- No Install Script found - aborting." + exit 0; +fi + +INSTLOPTS="-m 444" +INSTL_EXE_OPTS="-m 555" +INSTL_LIB_OPTS="-m 644" + +case "`basename $INSTALL`" in + install|installbsd|scoinst) + INSTLOPTS="-c $INSTLOPTS" + INSTL_EXE_OPTS="-c $INSTL_EXE_OPTS" + INSTL_LIB_OPTS="-c $INSTL_LIB_OPTS";; +esac + +echo "- Using $INSTALL" + + + + + +ECHO_N_OUT=`echo -n "" | wc -c` +ECHO_C_OUT=`echo "\c" | wc -c` +if test "$ECHO_N_OUT" -eq 0; then + DASH_N='-n' + BACKSLASH_C= +else + if test "ECHO_C_OUT" -eq 0; then + DASH_N= + BACKSLASH_C='\\\\c' + else + { echo "configure: error: "echo behaviour undetermined"" 1>&2; exit 1; } + fi +fi + + + +echo $ac_n "checking whether ln -s works""... $ac_c" 1>&6 +echo "configure:1119: checking whether ln -s works" >&5 +if eval "test \"`echo '$''{'ac_cv_prog_LN_S'+set}'`\" = set"; then + echo $ac_n "(cached) $ac_c" 1>&6 +else + rm -f conftestdata +if ln -s X conftestdata 2>/dev/null +then + rm -f conftestdata + ac_cv_prog_LN_S="ln -s" +else + ac_cv_prog_LN_S=ln +fi +fi +LN_S="$ac_cv_prog_LN_S" +if test "$ac_cv_prog_LN_S" = "ln -s"; then + echo "$ac_t""yes" 1>&6 +else + echo "$ac_t""no" 1>&6 +fi + +echo $ac_n "checking whether ${MAKE-make} sets \${MAKE}""... $ac_c" 1>&6 +echo "configure:1140: checking whether ${MAKE-make} sets \${MAKE}" >&5 +set dummy ${MAKE-make}; ac_make=`echo "$2" | sed 'y%./+-%__p_%'` +if eval "test \"`echo '$''{'ac_cv_prog_make_${ac_make}_set'+set}'`\" = set"; then + echo $ac_n "(cached) $ac_c" 1>&6 +else + cat > conftestmake <<\EOF +all: + @echo 'ac_maketemp="${MAKE}"' +EOF +# GNU make sometimes prints "make[1]: Entering...", which would confuse us. +eval `${MAKE-make} -f conftestmake 2>/dev/null | grep temp=` +if test -n "$ac_maketemp"; then + eval ac_cv_prog_make_${ac_make}_set=yes +else + eval ac_cv_prog_make_${ac_make}_set=no +fi +rm -f conftestmake +fi +if eval "test \"`echo '$ac_cv_prog_make_'${ac_make}_set`\" = yes"; then + echo "$ac_t""yes" 1>&6 + SET_MAKE= +else + echo "$ac_t""no" 1>&6 + SET_MAKE="MAKE=${MAKE-make}" +fi + +# Extract the first word of "ranlib", so it can be a program name with args. +set dummy ranlib; ac_word=$2 +echo $ac_n "checking for $ac_word""... $ac_c" 1>&6 +echo "configure:1169: checking for $ac_word" >&5 +if eval "test \"`echo '$''{'ac_cv_prog_RANLIB'+set}'`\" = set"; then + echo $ac_n "(cached) $ac_c" 1>&6 +else + if test -n "$RANLIB"; then + ac_cv_prog_RANLIB="$RANLIB" # Let the user override the test. +else + IFS="${IFS= }"; ac_save_ifs="$IFS"; IFS="${IFS}:" + for ac_dir in $PATH; do + test -z "$ac_dir" && ac_dir=. + if test -f $ac_dir/$ac_word; then + ac_cv_prog_RANLIB="ranlib" + break + fi + done + IFS="$ac_save_ifs" + test -z "$ac_cv_prog_RANLIB" && ac_cv_prog_RANLIB=":" +fi +fi +RANLIB="$ac_cv_prog_RANLIB" +if test -n "$RANLIB"; then + echo "$ac_t""$RANLIB" 1>&6 +else + echo "$ac_t""no" 1>&6 +fi + +# Extract the first word of "find", so it can be a program name with args. +set dummy find; ac_word=$2 +echo $ac_n "checking for $ac_word""... $ac_c" 1>&6 +echo "configure:1198: checking for $ac_word" >&5 +if eval "test \"`echo '$''{'ac_cv_path_find'+set}'`\" = set"; then + echo $ac_n "(cached) $ac_c" 1>&6 +else + case "$find" in + /*) + ac_cv_path_find="$find" # Let the user override the test with a path. + ;; + *) + IFS="${IFS= }"; ac_save_ifs="$IFS"; IFS="${IFS}:" + for ac_dir in $PATH; do + test -z "$ac_dir" && ac_dir=. + if test -f $ac_dir/$ac_word; then + ac_cv_path_find="$ac_dir/$ac_word" + break + fi + done + IFS="$ac_save_ifs" + ;; +esac +fi +find="$ac_cv_path_find" +if test -n "$find"; then + echo "$ac_t""$find" 1>&6 +else + echo "$ac_t""no" 1>&6 +fi + +# Extract the first word of "tar", so it can be a program name with args. +set dummy tar; ac_word=$2 +echo $ac_n "checking for $ac_word""... $ac_c" 1>&6 +echo "configure:1229: checking for $ac_word" >&5 +if eval "test \"`echo '$''{'ac_cv_path_tar'+set}'`\" = set"; then + echo $ac_n "(cached) $ac_c" 1>&6 +else + case "$tar" in + /*) + ac_cv_path_tar="$tar" # Let the user override the test with a path. + ;; + *) + IFS="${IFS= }"; ac_save_ifs="$IFS"; IFS="${IFS}:" + for ac_dir in $PATH; do + test -z "$ac_dir" && ac_dir=. + if test -f $ac_dir/$ac_word; then + ac_cv_path_tar="$ac_dir/$ac_word" + break + fi + done + IFS="$ac_save_ifs" + ;; +esac +fi +tar="$ac_cv_path_tar" +if test -n "$tar"; then + echo "$ac_t""$tar" 1>&6 +else + echo "$ac_t""no" 1>&6 +fi + +# Extract the first word of "split", so it can be a program name with args. +set dummy split; ac_word=$2 +echo $ac_n "checking for $ac_word""... $ac_c" 1>&6 +echo "configure:1260: checking for $ac_word" >&5 +if eval "test \"`echo '$''{'ac_cv_path_split'+set}'`\" = set"; then + echo $ac_n "(cached) $ac_c" 1>&6 +else + case "$split" in + /*) + ac_cv_path_split="$split" # Let the user override the test with a path. + ;; + *) + IFS="${IFS= }"; ac_save_ifs="$IFS"; IFS="${IFS}:" + for ac_dir in $PATH; do + test -z "$ac_dir" && ac_dir=. + if test -f $ac_dir/$ac_word; then + ac_cv_path_split="$ac_dir/$ac_word" + break + fi + done + IFS="$ac_save_ifs" + ;; +esac +fi +split="$ac_cv_path_split" +if test -n "$split"; then + echo "$ac_t""$split" 1>&6 +else + echo "$ac_t""no" 1>&6 +fi + + +echo $ac_n "checking for main in -lc""... $ac_c" 1>&6 +echo "configure:1290: checking for main in -lc" >&5 +ac_lib_var=`echo c'_'main | sed 'y%./+-%__p_%'` +if eval "test \"`echo '$''{'ac_cv_lib_$ac_lib_var'+set}'`\" = set"; then + echo $ac_n "(cached) $ac_c" 1>&6 +else + ac_save_LIBS="$LIBS" +LIBS="-lc $LIBS" +cat > conftest.$ac_ext <&5; (eval $ac_link) 2>&5; } && test -s conftest; then + rm -rf conftest* + eval "ac_cv_lib_$ac_lib_var=yes" +else + echo "configure: failed program was:" >&5 + cat conftest.$ac_ext >&5 + rm -rf conftest* + eval "ac_cv_lib_$ac_lib_var=no" +fi +rm -f conftest* +LIBS="$ac_save_LIBS" + +fi +if eval "test \"`echo '$ac_cv_lib_'$ac_lib_var`\" = yes"; then + echo "$ac_t""yes" 1>&6 + ac_tr_lib=HAVE_LIB`echo c | sed -e 's/[^a-zA-Z0-9_]/_/g' \ + -e 'y/abcdefghijklmnopqrstuvwxyz/ABCDEFGHIJKLMNOPQRSTUVWXYZ/'` + cat >> confdefs.h <&6 +fi + +echo $ac_n "checking for main in -lm""... $ac_c" 1>&6 +echo "configure:1333: checking for main in -lm" >&5 +ac_lib_var=`echo m'_'main | sed 'y%./+-%__p_%'` +if eval "test \"`echo '$''{'ac_cv_lib_$ac_lib_var'+set}'`\" = set"; then + echo $ac_n "(cached) $ac_c" 1>&6 +else + ac_save_LIBS="$LIBS" +LIBS="-lm $LIBS" +cat > conftest.$ac_ext <&5; (eval $ac_link) 2>&5; } && test -s conftest; then + rm -rf conftest* + eval "ac_cv_lib_$ac_lib_var=yes" +else + echo "configure: failed program was:" >&5 + cat conftest.$ac_ext >&5 + rm -rf conftest* + eval "ac_cv_lib_$ac_lib_var=no" +fi +rm -f conftest* +LIBS="$ac_save_LIBS" + +fi +if eval "test \"`echo '$ac_cv_lib_'$ac_lib_var`\" = yes"; then + echo "$ac_t""yes" 1>&6 + ac_tr_lib=HAVE_LIB`echo m | sed -e 's/[^a-zA-Z0-9_]/_/g' \ + -e 'y/abcdefghijklmnopqrstuvwxyz/ABCDEFGHIJKLMNOPQRSTUVWXYZ/'` + cat >> confdefs.h <&6 +fi + +echo $ac_n "checking for main in -ldl""... $ac_c" 1>&6 +echo "configure:1376: checking for main in -ldl" >&5 +ac_lib_var=`echo dl'_'main | sed 'y%./+-%__p_%'` +if eval "test \"`echo '$''{'ac_cv_lib_$ac_lib_var'+set}'`\" = set"; then + echo $ac_n "(cached) $ac_c" 1>&6 +else + ac_save_LIBS="$LIBS" +LIBS="-ldl $LIBS" +cat > conftest.$ac_ext <&5; (eval $ac_link) 2>&5; } && test -s conftest; then + rm -rf conftest* + eval "ac_cv_lib_$ac_lib_var=yes" +else + echo "configure: failed program was:" >&5 + cat conftest.$ac_ext >&5 + rm -rf conftest* + eval "ac_cv_lib_$ac_lib_var=no" +fi +rm -f conftest* +LIBS="$ac_save_LIBS" + +fi +if eval "test \"`echo '$ac_cv_lib_'$ac_lib_var`\" = yes"; then + echo "$ac_t""yes" 1>&6 + ac_tr_lib=HAVE_LIB`echo dl | sed -e 's/[^a-zA-Z0-9_]/_/g' \ + -e 'y/abcdefghijklmnopqrstuvwxyz/ABCDEFGHIJKLMNOPQRSTUVWXYZ/'` + cat >> confdefs.h <&6 +fi + + +echo $ac_n "checking for ANSI C header files""... $ac_c" 1>&6 +echo "configure:1420: checking for ANSI C header files" >&5 +if eval "test \"`echo '$''{'ac_cv_header_stdc'+set}'`\" = set"; then + echo $ac_n "(cached) $ac_c" 1>&6 +else + cat > conftest.$ac_ext < +#include +#include +#include +EOF +ac_try="$ac_cpp conftest.$ac_ext >/dev/null 2>conftest.out" +{ (eval echo configure:1433: \"$ac_try\") 1>&5; (eval $ac_try) 2>&5; } +ac_err=`grep -v '^ *+' conftest.out` +if test -z "$ac_err"; then + rm -rf conftest* + ac_cv_header_stdc=yes +else + echo "$ac_err" >&5 + echo "configure: failed program was:" >&5 + cat conftest.$ac_ext >&5 + rm -rf conftest* + ac_cv_header_stdc=no +fi +rm -f conftest* + +if test $ac_cv_header_stdc = yes; then + # SunOS 4.x string.h does not declare mem*, contrary to ANSI. +cat > conftest.$ac_ext < +EOF +if (eval "$ac_cpp conftest.$ac_ext") 2>&5 | + egrep "memchr" >/dev/null 2>&1; then + : +else + rm -rf conftest* + ac_cv_header_stdc=no +fi +rm -f conftest* + +fi + +if test $ac_cv_header_stdc = yes; then + # ISC 2.0.2 stdlib.h does not declare free, contrary to ANSI. +cat > conftest.$ac_ext < +EOF +if (eval "$ac_cpp conftest.$ac_ext") 2>&5 | + egrep "free" >/dev/null 2>&1; then + : +else + rm -rf conftest* + ac_cv_header_stdc=no +fi +rm -f conftest* + +fi + +if test $ac_cv_header_stdc = yes; then + # /bin/cc in Irix-4.0.5 gets non-ANSI ctype macros unless using -ansi. +if test "$cross_compiling" = yes; then + : +else + cat > conftest.$ac_ext < +#define ISLOWER(c) ('a' <= (c) && (c) <= 'z') +#define TOUPPER(c) (ISLOWER(c) ? 'A' + ((c) - 'a') : (c)) +#define XOR(e, f) (((e) && !(f)) || (!(e) && (f))) +int main () { int i; for (i = 0; i < 256; i++) +if (XOR (islower (i), ISLOWER (i)) || toupper (i) != TOUPPER (i)) exit(2); +exit (0); } + +EOF +if { (eval echo configure:1500: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest && (./conftest; exit) 2>/dev/null +then + : +else + echo "configure: failed program was:" >&5 + cat conftest.$ac_ext >&5 + rm -fr conftest* + ac_cv_header_stdc=no +fi +rm -fr conftest* +fi + +fi +fi + +echo "$ac_t""$ac_cv_header_stdc" 1>&6 +if test $ac_cv_header_stdc = yes; then + cat >> confdefs.h <<\EOF +#define STDC_HEADERS 1 +EOF + +fi + +for ac_hdr in sys/param.h pwd.h +do +ac_safe=`echo "$ac_hdr" | sed 'y%./+-%__p_%'` +echo $ac_n "checking for $ac_hdr""... $ac_c" 1>&6 +echo "configure:1527: checking for $ac_hdr" >&5 +if eval "test \"`echo '$''{'ac_cv_header_$ac_safe'+set}'`\" = set"; then + echo $ac_n "(cached) $ac_c" 1>&6 +else + cat > conftest.$ac_ext < +EOF +ac_try="$ac_cpp conftest.$ac_ext >/dev/null 2>conftest.out" +{ (eval echo configure:1537: \"$ac_try\") 1>&5; (eval $ac_try) 2>&5; } +ac_err=`grep -v '^ *+' conftest.out` +if test -z "$ac_err"; then + rm -rf conftest* + eval "ac_cv_header_$ac_safe=yes" +else + echo "$ac_err" >&5 + echo "configure: failed program was:" >&5 + cat conftest.$ac_ext >&5 + rm -rf conftest* + eval "ac_cv_header_$ac_safe=no" +fi +rm -f conftest* +fi +if eval "test \"`echo '$ac_cv_header_'$ac_safe`\" = yes"; then + echo "$ac_t""yes" 1>&6 + ac_tr_hdr=HAVE_`echo $ac_hdr | sed 'y%abcdefghijklmnopqrstuvwxyz./-%ABCDEFGHIJKLMNOPQRSTUVWXYZ___%'` + cat >> confdefs.h <&6 +fi +done + + + + +for ac_func in stricmp +do +echo $ac_n "checking for $ac_func""... $ac_c" 1>&6 +echo "configure:1569: checking for $ac_func" >&5 +if eval "test \"`echo '$''{'ac_cv_func_$ac_func'+set}'`\" = set"; then + echo $ac_n "(cached) $ac_c" 1>&6 +else + cat > conftest.$ac_ext < +/* Override any gcc2 internal prototype to avoid an error. */ +/* We use char because int might match the return type of a gcc2 + builtin and then its argument prototype would still apply. */ +char $ac_func(); + +int main() { + +/* The GNU C library defines this for functions which it implements + to always fail with ENOSYS. Some functions are actually named + something starting with __ and the normal name is an alias. */ +#if defined (__stub_$ac_func) || defined (__stub___$ac_func) +choke me +#else +$ac_func(); +#endif + +; return 0; } +EOF +if { (eval echo configure:1597: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest; then + rm -rf conftest* + eval "ac_cv_func_$ac_func=yes" +else + echo "configure: failed program was:" >&5 + cat conftest.$ac_ext >&5 + rm -rf conftest* + eval "ac_cv_func_$ac_func=no" +fi +rm -f conftest* +fi + +if eval "test \"`echo '$ac_cv_func_'$ac_func`\" = yes"; then + echo "$ac_t""yes" 1>&6 + ac_tr_func=HAVE_`echo $ac_func | tr 'abcdefghijklmnopqrstuvwxyz' 'ABCDEFGHIJKLMNOPQRSTUVWXYZ'` + cat >> confdefs.h <&6 +fi +done + + + + +trap '' 1 2 15 +cat > confcache <<\EOF +# This file is a shell script that caches the results of configure +# tests run on this system so they can be shared between configure +# scripts and configure runs. It is not useful on other systems. +# If it contains results you don't want to keep, you may remove or edit it. +# +# By default, configure uses ./config.cache as the cache file, +# creating it if it does not exist already. You can give configure +# the --cache-file=FILE option to use a different cache file; that is +# what configure does when it calls configure scripts in +# subdirectories, so they share the cache. +# Giving --cache-file=/dev/null disables caching, for debugging configure. +# config.status only pays attention to the cache file if you give it the +# --recheck option to rerun configure. +# +EOF +# The following way of writing the cache mishandles newlines in values, +# but we know of no workaround that is simple, portable, and efficient. +# So, don't put newlines in cache variables' values. +# Ultrix sh set writes to stderr and can't be redirected directly, +# and sets the high bit in the cache file unless we assign to the vars. +(set) 2>&1 | + case `(ac_space=' '; set) 2>&1` in + *ac_space=\ *) + # `set' does not quote correctly, so add quotes (double-quote substitution + # turns \\\\ into \\, and sed turns \\ into \). + sed -n \ + -e "s/'/'\\\\''/g" \ + -e "s/^\\([a-zA-Z0-9_]*_cv_[a-zA-Z0-9_]*\\)=\\(.*\\)/\\1=\${\\1='\\2'}/p" + ;; + *) + # `set' quotes correctly as required by POSIX, so do not add quotes. + sed -n -e 's/^\([a-zA-Z0-9_]*_cv_[a-zA-Z0-9_]*\)=\(.*\)/\1=${\1=\2}/p' + ;; + esac >> confcache +if cmp -s $cache_file confcache; then + : +else + if test -w $cache_file; then + echo "updating cache $cache_file" + cat confcache > $cache_file + else + echo "not updating unwritable cache $cache_file" + fi +fi +rm -f confcache + +trap 'rm -fr conftest* confdefs* core core.* *.core $ac_clean_files; exit 1' 1 2 15 + +test "x$prefix" = xNONE && prefix=$ac_default_prefix +# Let make expand exec_prefix. +test "x$exec_prefix" = xNONE && exec_prefix='${prefix}' + +# Any assignment to VPATH causes Sun make to only execute +# the first set of double-colon rules, so remove it if not needed. +# If there is a colon in the path, we need to keep it. +if test "x$srcdir" = x.; then + ac_vpsub='/^[ ]*VPATH[ ]*=[^:]*$/d' +fi + +trap 'rm -f $CONFIG_STATUS conftest*; exit 1' 1 2 15 + +DEFS=-DHAVE_CONFIG_H + +# Without the "./", some shells look in PATH for config.status. +: ${CONFIG_STATUS=./config.status} + +echo creating $CONFIG_STATUS +rm -f $CONFIG_STATUS +cat > $CONFIG_STATUS </dev/null | sed 1q`: +# +# $0 $ac_configure_args +# +# Compiler output produced by configure, useful for debugging +# configure, is in ./config.log if it exists. + +ac_cs_usage="Usage: $CONFIG_STATUS [--recheck] [--version] [--help]" +for ac_option +do + case "\$ac_option" in + -recheck | --recheck | --rechec | --reche | --rech | --rec | --re | --r) + echo "running \${CONFIG_SHELL-/bin/sh} $0 $ac_configure_args --no-create --no-recursion" + exec \${CONFIG_SHELL-/bin/sh} $0 $ac_configure_args --no-create --no-recursion ;; + -version | --version | --versio | --versi | --vers | --ver | --ve | --v) + echo "$CONFIG_STATUS generated by autoconf version 2.12" + exit 0 ;; + -help | --help | --hel | --he | --h) + echo "\$ac_cs_usage"; exit 0 ;; + *) echo "\$ac_cs_usage"; exit 1 ;; + esac +done + +ac_given_srcdir=$srcdir + +trap 'rm -fr `echo "GNUmakefile Makefile.global config.h" | sed "s/:[^ ]*//g"` conftest*; exit 1' 1 2 15 +EOF +cat >> $CONFIG_STATUS < conftest.subs <<\\CEOF +$ac_vpsub +$extrasub +s%@CFLAGS@%$CFLAGS%g +s%@CPPFLAGS@%$CPPFLAGS%g +s%@CXXFLAGS@%$CXXFLAGS%g +s%@DEFS@%$DEFS%g +s%@LDFLAGS@%$LDFLAGS%g +s%@LIBS@%$LIBS%g +s%@exec_prefix@%$exec_prefix%g +s%@prefix@%$prefix%g +s%@program_transform_name@%$program_transform_name%g +s%@bindir@%$bindir%g +s%@sbindir@%$sbindir%g +s%@libexecdir@%$libexecdir%g +s%@datadir@%$datadir%g +s%@sysconfdir@%$sysconfdir%g +s%@sharedstatedir@%$sharedstatedir%g +s%@localstatedir@%$localstatedir%g +s%@libdir@%$libdir%g +s%@includedir@%$includedir%g +s%@oldincludedir@%$oldincludedir%g +s%@infodir@%$infodir%g +s%@mandir@%$mandir%g +s%@host@%$host%g +s%@host_alias@%$host_alias%g +s%@host_cpu@%$host_cpu%g +s%@host_vendor@%$host_vendor%g +s%@host_os@%$host_os%g +s%@PORTNAME@%$PORTNAME%g +s%@ODBCINSTDIR@%$ODBCINSTDIR%g +s%@CC@%$CC%g +s%@CPP@%$CPP%g +s%@AROPT@%$AROPT%g +s%@SHARED_LIB@%$SHARED_LIB%g +s%@DLSUFFIX@%$DLSUFFIX%g +s%@DL_LIB@%$DL_LIB%g +s%@INSTALL@%$INSTALL%g +s%@INSTLOPTS@%$INSTLOPTS%g +s%@INSTL_LIB_OPTS@%$INSTL_LIB_OPTS%g +s%@INSTL_EXE_OPTS@%$INSTL_EXE_OPTS%g +s%@DASH_N@%$DASH_N%g +s%@BACKSLASH_C@%$BACKSLASH_C%g +s%@LN_S@%$LN_S%g +s%@SET_MAKE@%$SET_MAKE%g +s%@RANLIB@%$RANLIB%g +s%@find@%$find%g +s%@tar@%$tar%g +s%@split@%$split%g + +CEOF +EOF + +cat >> $CONFIG_STATUS <<\EOF + +# Split the substitutions into bite-sized pieces for seds with +# small command number limits, like on Digital OSF/1 and HP-UX. +ac_max_sed_cmds=90 # Maximum number of lines to put in a sed script. +ac_file=1 # Number of current file. +ac_beg=1 # First line for current file. +ac_end=$ac_max_sed_cmds # Line after last line for current file. +ac_more_lines=: +ac_sed_cmds="" +while $ac_more_lines; do + if test $ac_beg -gt 1; then + sed "1,${ac_beg}d; ${ac_end}q" conftest.subs > conftest.s$ac_file + else + sed "${ac_end}q" conftest.subs > conftest.s$ac_file + fi + if test ! -s conftest.s$ac_file; then + ac_more_lines=false + rm -f conftest.s$ac_file + else + if test -z "$ac_sed_cmds"; then + ac_sed_cmds="sed -f conftest.s$ac_file" + else + ac_sed_cmds="$ac_sed_cmds | sed -f conftest.s$ac_file" + fi + ac_file=`expr $ac_file + 1` + ac_beg=$ac_end + ac_end=`expr $ac_end + $ac_max_sed_cmds` + fi +done +if test -z "$ac_sed_cmds"; then + ac_sed_cmds=cat +fi +EOF + +cat >> $CONFIG_STATUS <> $CONFIG_STATUS <<\EOF +for ac_file in .. $CONFIG_FILES; do if test "x$ac_file" != x..; then + # Support "outfile[:infile[:infile...]]", defaulting infile="outfile.in". + case "$ac_file" in + *:*) ac_file_in=`echo "$ac_file"|sed 's%[^:]*:%%'` + ac_file=`echo "$ac_file"|sed 's%:.*%%'` ;; + *) ac_file_in="${ac_file}.in" ;; + esac + + # Adjust a relative srcdir, top_srcdir, and INSTALL for subdirectories. + + # Remove last slash and all that follows it. Not all systems have dirname. + ac_dir=`echo $ac_file|sed 's%/[^/][^/]*$%%'` + if test "$ac_dir" != "$ac_file" && test "$ac_dir" != .; then + # The file is in a subdirectory. + test ! -d "$ac_dir" && mkdir "$ac_dir" + ac_dir_suffix="/`echo $ac_dir|sed 's%^\./%%'`" + # A "../" for each directory in $ac_dir_suffix. + ac_dots=`echo $ac_dir_suffix|sed 's%/[^/]*%../%g'` + else + ac_dir_suffix= ac_dots= + fi + + case "$ac_given_srcdir" in + .) srcdir=. + if test -z "$ac_dots"; then top_srcdir=. + else top_srcdir=`echo $ac_dots|sed 's%/$%%'`; fi ;; + /*) srcdir="$ac_given_srcdir$ac_dir_suffix"; top_srcdir="$ac_given_srcdir" ;; + *) # Relative path. + srcdir="$ac_dots$ac_given_srcdir$ac_dir_suffix" + top_srcdir="$ac_dots$ac_given_srcdir" ;; + esac + + + echo creating "$ac_file" + rm -f "$ac_file" + configure_input="Generated automatically from `echo $ac_file_in|sed 's%.*/%%'` by configure." + case "$ac_file" in + *Makefile*) ac_comsub="1i\\ +# $configure_input" ;; + *) ac_comsub= ;; + esac + + ac_file_inputs=`echo $ac_file_in|sed -e "s%^%$ac_given_srcdir/%" -e "s%:% $ac_given_srcdir/%g"` + sed -e "$ac_comsub +s%@configure_input@%$configure_input%g +s%@srcdir@%$srcdir%g +s%@top_srcdir@%$top_srcdir%g +" $ac_file_inputs | (eval "$ac_sed_cmds") > $ac_file +fi; done +rm -f conftest.s* + +# These sed commands are passed to sed as "A NAME B NAME C VALUE D", where +# NAME is the cpp macro being defined and VALUE is the value it is being given. +# +# ac_d sets the value in "#define NAME VALUE" lines. +ac_dA='s%^\([ ]*\)#\([ ]*define[ ][ ]*\)' +ac_dB='\([ ][ ]*\)[^ ]*%\1#\2' +ac_dC='\3' +ac_dD='%g' +# ac_u turns "#undef NAME" with trailing blanks into "#define NAME VALUE". +ac_uA='s%^\([ ]*\)#\([ ]*\)undef\([ ][ ]*\)' +ac_uB='\([ ]\)%\1#\2define\3' +ac_uC=' ' +ac_uD='\4%g' +# ac_e turns "#undef NAME" without trailing blanks into "#define NAME VALUE". +ac_eA='s%^\([ ]*\)#\([ ]*\)undef\([ ][ ]*\)' +ac_eB='$%\1#\2define\3' +ac_eC=' ' +ac_eD='%g' + +if test "${CONFIG_HEADERS+set}" != set; then +EOF +cat >> $CONFIG_STATUS <> $CONFIG_STATUS <<\EOF +fi +for ac_file in .. $CONFIG_HEADERS; do if test "x$ac_file" != x..; then + # Support "outfile[:infile[:infile...]]", defaulting infile="outfile.in". + case "$ac_file" in + *:*) ac_file_in=`echo "$ac_file"|sed 's%[^:]*:%%'` + ac_file=`echo "$ac_file"|sed 's%:.*%%'` ;; + *) ac_file_in="${ac_file}.in" ;; + esac + + echo creating $ac_file + + rm -f conftest.frag conftest.in conftest.out + ac_file_inputs=`echo $ac_file_in|sed -e "s%^%$ac_given_srcdir/%" -e "s%:% $ac_given_srcdir/%g"` + cat $ac_file_inputs > conftest.in + +EOF + +# Transform confdefs.h into a sed script conftest.vals that substitutes +# the proper values into config.h.in to produce config.h. And first: +# Protect against being on the right side of a sed subst in config.status. +# Protect against being in an unquoted here document in config.status. +rm -f conftest.vals +cat > conftest.hdr <<\EOF +s/[\\&%]/\\&/g +s%[\\$`]%\\&%g +s%#define \([A-Za-z_][A-Za-z0-9_]*\) *\(.*\)%${ac_dA}\1${ac_dB}\1${ac_dC}\2${ac_dD}%gp +s%ac_d%ac_u%gp +s%ac_u%ac_e%gp +EOF +sed -n -f conftest.hdr confdefs.h > conftest.vals +rm -f conftest.hdr + +# This sed command replaces #undef with comments. This is necessary, for +# example, in the case of _POSIX_SOURCE, which is predefined and required +# on some systems where configure will not decide to define it. +cat >> conftest.vals <<\EOF +s%^[ ]*#[ ]*undef[ ][ ]*[a-zA-Z_][a-zA-Z_0-9]*%/* & */% +EOF + +# Break up conftest.vals because some shells have a limit on +# the size of here documents, and old seds have small limits too. + +rm -f conftest.tail +while : +do + ac_lines=`grep -c . conftest.vals` + # grep -c gives empty output for an empty file on some AIX systems. + if test -z "$ac_lines" || test "$ac_lines" -eq 0; then break; fi + # Write a limited-size here document to conftest.frag. + echo ' cat > conftest.frag <> $CONFIG_STATUS + sed ${ac_max_here_lines}q conftest.vals >> $CONFIG_STATUS + echo 'CEOF + sed -f conftest.frag conftest.in > conftest.out + rm -f conftest.in + mv conftest.out conftest.in +' >> $CONFIG_STATUS + sed 1,${ac_max_here_lines}d conftest.vals > conftest.tail + rm -f conftest.vals + mv conftest.tail conftest.vals +done +rm -f conftest.vals + +cat >> $CONFIG_STATUS <<\EOF + rm -f conftest.frag conftest.h + echo "/* $ac_file. Generated automatically by configure. */" > conftest.h + cat conftest.in >> conftest.h + rm -f conftest.in + if cmp -s $ac_file conftest.h 2>/dev/null; then + echo "$ac_file is unchanged" + rm -f conftest.h + else + # Remove last slash and all that follows it. Not all systems have dirname. + ac_dir=`echo $ac_file|sed 's%/[^/][^/]*$%%'` + if test "$ac_dir" != "$ac_file" && test "$ac_dir" != .; then + # The file is in a subdirectory. + test ! -d "$ac_dir" && mkdir "$ac_dir" + fi + rm -f $ac_file + mv conftest.h $ac_file + fi +fi; done + +EOF +cat >> $CONFIG_STATUS <> $CONFIG_STATUS <<\EOF + +exit 0 +EOF +chmod +x $CONFIG_STATUS +rm -fr confdefs* $ac_clean_files +test "$no_create" = yes || ${CONFIG_SHELL-/bin/sh} $CONFIG_STATUS || exit 1 + diff --git a/src/interfaces/odbc/configure.in b/src/interfaces/odbc/configure.in new file mode 100644 index 0000000000..0f53a2e9bf --- /dev/null +++ b/src/interfaces/odbc/configure.in @@ -0,0 +1,317 @@ +dnl Process this file with autoconf to produce a configure script. +AC_INIT(bind.c) +AC_PREFIX_DEFAULT(/usr/local) + +if test -d ../../interfaces +then + TEMPLATEDIR=../../template + if test "$prefix" = "NONE" + then + ac_default_prefix=/usr/local/pgsql + fi + ODBCINSTDIR= +else + TEMPLATEDIR=./template + if test "$prefix" = "NONE" + then + ODBCINSTDIR=/share + else + ODBCINSTDIR= + fi +fi + +echo "*** configuring psqlodbc ***" + +AC_CANONICAL_HOST + +case "$host_os" in + solaris*) + case "$host_cpu" in + sparc) os=sparc_solaris ;; + i386) os=i386_solaris ;; + esac ;; + sunos*) os=sunos4 ;; + aux*) os=aux ;; + linux*) os=linux ;; + bsdi*) os=bsdi ;; + freebsd*|netbsd*|openbsd*) os=bsd ;; + dgux*) os=dgux ;; + aix*) os=aix ;; +nextstep*) os=nextstep ;; + ultrix*) os=ultrix4 ;; + irix*) os=irix5 ;; + hpux*) os=hpux ;; + osf*) os=alpha ;; + sco*) os=sco ;; + machten*) os=machten ;; + cygwin*) os=win ;; + sysv4.2*) + case "$host_vendor" in + univel) os=univel ;; + *) os=unknown ;; + esac ;; + sysv4*) os=svr4 ;; +*) echo "" + echo "*************************************************************" + echo "configure does not currently recognize your operating system," + echo "therefore you must do a manual configuration of:" + echo "$host_os" + echo "Please contact scrappy@hub.org to see about rectifying this, " + echo "including the above 'checking host system type...' line " + echo "*************************************************************" + echo "" + exit;; +esac + + +PORTNAME=${os} + +AC_SUBST(PORTNAME) + +echo "checking echo setting..." +if echo '\c' | grep -s c >/dev/null 2>&1 +then + ECHO_N="echo -n" + ECHO_C="" +else + ECHO_N="echo" + ECHO_C='\c' +fi + +dnl cat </dev/null` + fi + if test "$GUESS" + then + TEMPLATE=`echo $GUESS | sed 's/.*=//'` + fi + export TEMPLATE + ls $TEMPLATEDIR + echo "**************************************************************" + $ECHO_N "Appropriate template file { $TEMPLATE }: $ECHO_C" + read a + if test "$a." != "." + then + TEMPLATE=$a + fi + if test ! -f $TEMPLATEDIR/$TEMPLATE + then + echo "You must choose an appropriate template file." + exit + fi +fi +fi + +TEMPLATE=$TEMPLATEDIR/$TEMPLATE +export TEMPLATE +echo "" + +AROPT=`grep '^AROPT:' $TEMPLATE | awk -F: '{print $2}'` +SHARED_LIB=`grep '^SHARED_LIB:' $TEMPLATE | awk -F: '{print $2}'` +CFLAGS=`grep '^CFLAGS:' $TEMPLATE | awk -F: '{print $2}'` +SRCH_INC=`grep '^SRCH_INC:' $TEMPLATE | awk -F: '{print $2}'` +SRCH_LIB=`grep '^SRCH_LIB:' $TEMPLATE | awk -F: '{print $2}'` +DLSUFFIX=`grep '^DLSUFFIX:' $TEMPLATE | awk -F: '{print $2}'` +DL_LIB=`grep '^DL_LIB:' $TEMPLATE | awk -F: '{print $2}'` +CC=`grep '^CC:' $TEMPLATE | awk -F: '{print $2}'` +LIBS=`grep '^LIBS:' $TEMPLATE | awk -F: '{print $2}'` + + +a=$SRCH_INC +CPPFLAGS=`echo "$a" | sed 's@ *@ @g; s@^\([[^ ]]\)@-I\1@; s@ \([[^ ]]\)@ -I\1@g'` + +export CPPFLAGS +echo "- setting CPPFLAGS=$CPPFLAGS" + +a=$SRCH_LIB +LDFLAGS=`echo "$a" | sed 's@ *@ @g; s@^\([[^ ]]\)@-L\1@; s@ \([[^ ]]\)@ -L\1@g'` + +export LDFLAGS +echo "- setting LDFLAGS=$LDFLAGS" + +dnl Allow for overriding the default location of the odbcinst.ini +dnl file which is normally ${prefix}/share or ${prefix} if this is +dnl being compiled inside the postgres distribution. +AC_MSG_CHECKING(setting ODBCINST) +AC_ARG_WITH( + odbcinst, + [ --with-odbcinst= change default directory for odbcinst.ini], + AC_DEFINE_UNQUOTED(ODBCINST, ${with_odbcinst}) AC_MSG_RESULT($with_odbcinst), + AC_DEFINE_UNQUOTED(ODBCINST, ${ODBCINSTDIR}) AC_MSG_RESULT(${ODBCINSTDIR}) +) + +if test "X$with_odbcinst" != "X" +then + ODBCINSTDIR=$with_odbcinst +fi + +AC_SUBST(ODBCINSTDIR) + +if test "X$with_compiler" != "X" +then + CC=$with_compiler +else + AC_PROG_CC +fi + +AC_CONFIG_HEADER(config.h) + +dnl Checks for programs. +AC_PROG_CPP + +AC_SUBST(PORTNAME) +AC_SUBST(LDFLAGS) +AC_SUBST(CPPFLAGS) +AC_SUBST(AROPT) +AC_SUBST(SHARED_LIB) +AC_SUBST(CFLAGS) +AC_SUBST(DLSUFFIX) +AC_SUBST(DL_LIB) + +INSTALLPATH="/usr/ucb:$PATH" +AC_PATH_PROGS(INSTALL, ginstall installbsd bsdinst scoinst install, NONE, $INSTALLPATH) +if test $INSTALL = "NONE" +then + echo "- No Install Script found - aborting." + exit 0; +fi + +INSTLOPTS="-m 444" +INSTL_EXE_OPTS="-m 555" +INSTL_LIB_OPTS="-m 644" + +case "`basename $INSTALL`" in + install|installbsd|scoinst) + INSTLOPTS="-c $INSTLOPTS" + INSTL_EXE_OPTS="-c $INSTL_EXE_OPTS" + INSTL_LIB_OPTS="-c $INSTL_LIB_OPTS";; +esac + +echo "- Using $INSTALL" +AC_SUBST(INSTALL) +AC_SUBST(INSTLOPTS) +AC_SUBST(INSTL_LIB_OPTS) +AC_SUBST(INSTL_EXE_OPTS) + +dnl Check the option to echo to inhibit newlines. +ECHO_N_OUT=`echo -n "" | wc -c` +ECHO_C_OUT=`echo "\c" | wc -c` +if test "$ECHO_N_OUT" -eq 0; then + DASH_N='-n' + BACKSLASH_C= +else + if test "ECHO_C_OUT" -eq 0; then + DASH_N= + BACKSLASH_C='\\\\c' + else + AC_MSG_ERROR("echo behaviour undetermined") + fi +fi +AC_SUBST(DASH_N) +AC_SUBST(BACKSLASH_C) + +AC_PROG_LN_S +AC_PROG_MAKE_SET +AC_PROG_RANLIB +AC_PATH_PROG(find, find) +AC_PATH_PROG(tar, tar) +AC_PATH_PROG(split,split) + +AC_CHECK_LIB(c, main) +AC_CHECK_LIB(m, main) +AC_CHECK_LIB(dl, main) + +dnl Checks for header files. +AC_HEADER_STDC +AC_CHECK_HEADERS(sys/param.h pwd.h) + +dnl Checks for typedefs, structures, and compiler characteristics. + +dnl Check for any "odd" conditions + +dnl Checks for library functions. +AC_CHECK_FUNCS(stricmp) + +dnl Check for X libraries + +dnl Check for X library + +AC_OUTPUT(GNUmakefile Makefile.global) diff --git a/src/interfaces/odbc/connection.c b/src/interfaces/odbc/connection.c index 8eedcf18cc..3857f73d70 100644 --- a/src/interfaces/odbc/connection.c +++ b/src/interfaces/odbc/connection.c @@ -23,7 +23,7 @@ #include #include -#ifndef UNIX +#ifdef WIN32 #include #endif @@ -39,10 +39,12 @@ RETCODE SQL_API SQLAllocConnect( { EnvironmentClass *env = (EnvironmentClass *)henv; ConnectionClass *conn; -char *func="SQLAllocConnect"; +static char *func="SQLAllocConnect"; + + mylog( "%s: entering...\n", func); conn = CC_Constructor(); - mylog("**** SQLAllocConnect: henv = %u, conn = %u\n", henv, conn); + mylog("**** %s: henv = %u, conn = %u\n", func, henv, conn); if( ! conn) { env->errormsg = "Couldn't allocate memory for Connection object."; @@ -80,7 +82,9 @@ RETCODE SQL_API SQLConnect( { ConnectionClass *conn = (ConnectionClass *) hdbc; ConnInfo *ci; -char *func = "SQLConnect"; +static char *func = "SQLConnect"; + + mylog( "%s: entering...\n", func); if ( ! conn) { CC_log_error(func, "", NULL); @@ -103,7 +107,7 @@ char *func = "SQLConnect"; /* fill in any defaults */ getDSNdefaults(ci); - qlog("conn = %u, SQLConnect(DSN='%s', UID='%s', PWD='%s')\n", conn, ci->dsn, ci->username, ci->password); + qlog("conn = %u, %s(DSN='%s', UID='%s', PWD='%s')\n", conn, func, ci->dsn, ci->username, ci->password); if ( CC_connect(conn, FALSE) <= 0) { // Error messages are filled in @@ -111,6 +115,8 @@ char *func = "SQLConnect"; return SQL_ERROR; } + mylog( "%s: returning...\n", func); + return SQL_SUCCESS; } @@ -124,6 +130,10 @@ RETCODE SQL_API SQLBrowseConnect( SWORD cbConnStrOutMax, SWORD FAR *pcbConnStrOut) { +static char *func="SQLBrowseConnect"; + + mylog( "%s: entering...\n", func); + return SQL_SUCCESS; } @@ -134,16 +144,17 @@ RETCODE SQL_API SQLDisconnect( HDBC hdbc) { ConnectionClass *conn = (ConnectionClass *) hdbc; -char *func = "SQLDisconnect"; +static char *func = "SQLDisconnect"; - mylog("**** in SQLDisconnect\n"); + + mylog( "%s: entering...\n", func); if ( ! conn) { CC_log_error(func, "", NULL); return SQL_INVALID_HANDLE; } - qlog("conn=%u, SQLDisconnect\n", conn); + qlog("conn=%u, %s\n", conn, func); if (conn->status == CONN_EXECUTING) { conn->errornumber = CONN_IN_USE; @@ -152,13 +163,13 @@ char *func = "SQLDisconnect"; return SQL_ERROR; } - mylog("SQLDisconnect: about to CC_cleanup\n"); + mylog("%s: about to CC_cleanup\n", func); /* Close the connection and free statements */ CC_cleanup(conn); - mylog("SQLDisconnect: done CC_cleanup\n"); - mylog("exit SQLDisconnect\n"); + mylog("%s: done CC_cleanup\n", func); + mylog("%s: returning...\n", func); return SQL_SUCCESS; } @@ -170,9 +181,10 @@ RETCODE SQL_API SQLFreeConnect( HDBC hdbc) { ConnectionClass *conn = (ConnectionClass *) hdbc; -char *func = "SQLFreeConnect"; +static char *func = "SQLFreeConnect"; - mylog("**** in SQLFreeConnect: hdbc=%u\n", hdbc); + mylog( "%s: entering...\n", func); + mylog("**** in %s: hdbc=%u\n", func, hdbc); if ( ! conn) { CC_log_error(func, "", NULL); @@ -189,7 +201,7 @@ char *func = "SQLFreeConnect"; CC_Destructor(conn); - mylog("exit SQLFreeConnect\n"); + mylog("%s: returning...\n", func); return SQL_SUCCESS; } @@ -201,8 +213,7 @@ char *func = "SQLFreeConnect"; * */ -ConnectionClass -*CC_Constructor() +ConnectionClass *CC_Constructor() { ConnectionClass *rv; @@ -381,10 +392,12 @@ StatementClass *stmt; } /* Check for translation dll */ +#ifdef WIN32 if ( self->translation_handle) { FreeLibrary (self->translation_handle); self->translation_handle = NULL; } +#endif mylog("exit CC_Cleanup\n"); return TRUE; @@ -394,6 +407,8 @@ int CC_set_translation (ConnectionClass *self) { +#ifdef WIN32 + if (self->translation_handle != NULL) { FreeLibrary (self->translation_handle); self->translation_handle = NULL; @@ -424,7 +439,7 @@ CC_set_translation (ConnectionClass *self) self->errormsg = "Could not find translation DLL functions."; return FALSE; } - +#endif return TRUE; } @@ -440,6 +455,9 @@ int areq = -1; int beresp; char msgbuffer[ERROR_MSG_LENGTH]; char salt[2]; +static char *func="CC_connect"; + + mylog("%s: entering...\n", func); if ( do_password) @@ -447,7 +465,8 @@ char salt[2]; else { - qlog("Global Options: fetch=%d, socket=%d, unknown_sizes=%d, max_varchar_size=%d, max_longvarchar_size=%d\n", + qlog("Global Options: Version='%s', fetch=%d, socket=%d, unknown_sizes=%d, max_varchar_size=%d, max_longvarchar_size=%d\n", + POSTGRESDRIVERVERSION, globals.fetch_max, globals.socket_buffersize, globals.unknown_sizes, @@ -477,8 +496,7 @@ char salt[2]; return 0; } - mylog("CC_connect(): DSN = '%s', server = '%s', port = '%s', database = '%s', username = '%s', password='%s'\n", - ci->dsn, ci->server, ci->port, ci->database, ci->username, ci->password); + mylog("CC_connect(): DSN = '%s', server = '%s', port = '%s', database = '%s', username = '%s', password='%s'\n", ci->dsn, ci->server, ci->port, ci->database, ci->username, ci->password); /* If the socket was closed for some reason (like a SQLDisconnect, but no SQLFreeConnect then create a socket now. @@ -668,11 +686,13 @@ char salt[2]; CC_send_settings(self); CC_lookup_lo(self); /* a hack to get the oid of our large object oid type */ -// CC_test(self); + // CC_test(self); CC_clear_error(self); /* clear any initial command errors */ self->status = CONN_CONNECTED; + mylog("%s: returning...\n", func); + return 1; } @@ -837,7 +857,7 @@ char cmdbuffer[MAX_MESSAGE_LEN+1]; // QR_set_command() dups this string so dont mylog("send_query: done sending query\n"); while(1) { - /* what type of message is comming now ? */ + /* what type of message is coming now ? */ id = SOCK_get_char(sock); if ((SOCK_get_errcode(sock) != 0) || (id == EOF)) { @@ -884,7 +904,7 @@ char cmdbuffer[MAX_MESSAGE_LEN+1]; // QR_set_command() dups this string so dont QR_set_command(res, cmdbuffer); /* (Quotation from the original comments) - since backend may produze more than one result for some commands + since backend may produce more than one result for some commands we need to poll until clear so we send an empty query, and keep reading out of the pipe until an 'I' is received @@ -1039,8 +1059,7 @@ int i; for (i = 0; i < nargs; ++i) { - mylog(" arg[%d]: len = %d, isint = %d, integer = %d, ptr = %u\n", - i, args[i].len, args[i].isint, args[i].u.integer, args[i].u.ptr); + mylog(" arg[%d]: len = %d, isint = %d, integer = %d, ptr = %u\n", i, args[i].len, args[i].isint, args[i].u.integer, args[i].u.ptr); SOCK_put_int(sock, args[i].len, 4); if (args[i].isint) @@ -1148,58 +1167,86 @@ int i; char CC_send_settings(ConnectionClass *self) { -char ini_query[MAX_MESSAGE_LEN]; +// char ini_query[MAX_MESSAGE_LEN]; ConnInfo *ci = &(self->connInfo); // QResultClass *res; HSTMT hstmt; StatementClass *stmt; RETCODE result; -SWORD cols = 0; +char status = TRUE; +char *cs, *ptr; +static char *func="CC_send_settings"; + + + mylog("%s: entering...\n", func); /* This function must use the local odbc API functions since the odbc state has not transitioned to "connected" yet. */ - result = _SQLAllocStmt( self, &hstmt); + + result = SQLAllocStmt( self, &hstmt); if((result != SQL_SUCCESS) && (result != SQL_SUCCESS_WITH_INFO)) { return FALSE; } stmt = (StatementClass *) hstmt; - ini_query[0] = '\0'; + stmt->internal = TRUE; /* ensure no BEGIN/COMMIT/ABORT stuff */ /* Set the Datestyle to the format the driver expects it to be in */ - sprintf(ini_query, "set DateStyle to 'ISO'"); + result = SQLExecDirect(hstmt, "set DateStyle to 'ISO'", SQL_NTS); + if((result != SQL_SUCCESS) && (result != SQL_SUCCESS_WITH_INFO)) + status = FALSE; + + mylog("%s: result %d, status %d from set DateStyle\n", func, result, status); /* Disable genetic optimizer based on global flag */ - if (globals.disable_optimizer) - sprintf(&ini_query[strlen(ini_query)], "%sset geqo to 'OFF'", - ini_query[0] != '\0' ? "; " : ""); + if (globals.disable_optimizer) { + result = SQLExecDirect(hstmt, "set geqo to 'OFF'", SQL_NTS); + if((result != SQL_SUCCESS) && (result != SQL_SUCCESS_WITH_INFO)) + status = FALSE; + + mylog("%s: result %d, status %d from set geqo\n", func, result, status); + + } /* Global settings */ - if (globals.conn_settings[0] != '\0') - sprintf(&ini_query[strlen(ini_query)], "%s%s", - ini_query[0] != '\0' ? "; " : "", - globals.conn_settings); + if (globals.conn_settings[0] != '\0') { + cs = strdup(globals.conn_settings); + ptr = strtok(cs, ";"); + while (ptr) { + result = SQLExecDirect(hstmt, ptr, SQL_NTS); + if((result != SQL_SUCCESS) && (result != SQL_SUCCESS_WITH_INFO)) + status = FALSE; + + mylog("%s: result %d, status %d from '%s'\n", func, result, status, ptr); + + ptr = strtok(NULL, ";"); + } + free(cs); + } + /* Per Datasource settings */ - if (ci->conn_settings[0] != '\0') - sprintf(&ini_query[strlen(ini_query)], "%s%s", - ini_query[0] != '\0' ? "; " : "", - ci->conn_settings); + if (ci->conn_settings[0] != '\0') { + cs = strdup(ci->conn_settings); + ptr = strtok(cs, ";"); + while (ptr) { + result = SQLExecDirect(hstmt, ptr, SQL_NTS); + if((result != SQL_SUCCESS) && (result != SQL_SUCCESS_WITH_INFO)) + status = FALSE; - if (ini_query[0] != '\0') { - mylog("Sending Initial Connection query: '%s'\n", ini_query); + mylog("%s: result %d, status %d from '%s'\n", func, result, status, ptr); - result = _SQLExecDirect(hstmt, ini_query, SQL_NTS); - if((result != SQL_SUCCESS) && (result != SQL_SUCCESS_WITH_INFO)) { - _SQLFreeStmt(hstmt, SQL_DROP); - return FALSE; + ptr = strtok(NULL, ";"); } - _SQLFreeStmt(hstmt, SQL_DROP); - + free(cs); } - return TRUE; + + + SQLFreeStmt(hstmt, SQL_DROP); + + return status; } /* This function is just a hack to get the oid of our Large Object oid type. @@ -1212,40 +1259,41 @@ CC_lookup_lo(ConnectionClass *self) HSTMT hstmt; StatementClass *stmt; RETCODE result; +static char *func = "CC_lookup_lo"; + + mylog( "%s: entering...\n", func); /* This function must use the local odbc API functions since the odbc state has not transitioned to "connected" yet. */ - result = _SQLAllocStmt( self, &hstmt); + result = SQLAllocStmt( self, &hstmt); if((result != SQL_SUCCESS) && (result != SQL_SUCCESS_WITH_INFO)) { return; } stmt = (StatementClass *) hstmt; - result = _SQLExecDirect(hstmt, "select oid from pg_type where typname='" \ - PG_TYPE_LO_NAME \ - "'", SQL_NTS); + result = SQLExecDirect(hstmt, "select oid from pg_type where typname='" PG_TYPE_LO_NAME "'", SQL_NTS); if((result != SQL_SUCCESS) && (result != SQL_SUCCESS_WITH_INFO)) { - _SQLFreeStmt(hstmt, SQL_DROP); + SQLFreeStmt(hstmt, SQL_DROP); return; } - result = _SQLFetch(hstmt); + result = SQLFetch(hstmt); if((result != SQL_SUCCESS) && (result != SQL_SUCCESS_WITH_INFO)) { - _SQLFreeStmt(hstmt, SQL_DROP); + SQLFreeStmt(hstmt, SQL_DROP); return; } - result = _SQLGetData(hstmt, 1, SQL_C_SLONG, &self->lobj_type, sizeof(self->lobj_type), NULL); + result = SQLGetData(hstmt, 1, SQL_C_SLONG, &self->lobj_type, sizeof(self->lobj_type), NULL); if((result != SQL_SUCCESS) && (result != SQL_SUCCESS_WITH_INFO)) { - _SQLFreeStmt(hstmt, SQL_DROP); + SQLFreeStmt(hstmt, SQL_DROP); return; } mylog("Got the large object oid: %d\n", self->lobj_type); qlog(" [ Large Object oid = %d ]\n", self->lobj_type); - result = _SQLFreeStmt(hstmt, SQL_DROP); + result = SQLFreeStmt(hstmt, SQL_DROP); } void @@ -1253,6 +1301,7 @@ CC_log_error(char *func, char *desc, ConnectionClass *self) { if (self) { qlog("CONN ERROR: func=%s, desc='%s', errnum=%d, errmsg='%s'\n", func, desc, self->errornumber, self->errormsg); + mylog("CONN ERROR: func=%s, desc='%s', errnum=%d, errmsg='%s'\n", func, desc, self->errornumber, self->errormsg); qlog(" ------------------------------------------------------------\n"); qlog(" henv=%u, conn=%u, status=%u, num_stmts=%d\n", self->henv, self, self->status, self->num_stmts); qlog(" sock=%u, stmts=%u, lobj_type=%d\n", self->sock, self->stmts, self->lobj_type); @@ -1273,43 +1322,103 @@ CC_log_error(char *func, char *desc, ConnectionClass *self) void CC_test(ConnectionClass *self) { +static char *func = "CC_test"; HSTMT hstmt1; RETCODE result; -SDWORD pcbValue; -UDWORD pcrow; -UWORD rgfRowStatus; -char name[255], type[255]; -SDWORD namelen, typelen; -SWORD cols; +char pktab[255], fktab[255], pkcol[255], fkcol[255], tgname[255]; +SDWORD pktab_len, pkcol_len, fktab_len, fkcol_len, ur_len, dr_len, tgname_len; +SWORD cols, seq; +SDWORD update_rule, delete_rule; + + mylog( "%s: entering...\n", func); result = SQLAllocStmt( self, &hstmt1); if((result != SQL_SUCCESS) && (result != SQL_SUCCESS_WITH_INFO)) { return; } - result = SQLTables(hstmt1, "", SQL_NTS, "", SQL_NTS, "", SQL_NTS, "", SQL_NTS); - qlog("SQLTables result = %d\n", result); + result = SQLPrimaryKeys(hstmt1, NULL, 0, NULL, 0, "t1", SQL_NTS); + + qlog("SQLPrimaryKeys result = %d\n", result); result = SQLNumResultCols(hstmt1, &cols); qlog("cols SQLTables result = %d\n", result); - result = SQLBindCol(hstmt1, 3, SQL_C_CHAR, name, sizeof(name), &namelen); + result = SQLBindCol(hstmt1, 3, SQL_C_CHAR, pktab, sizeof(pktab), &pktab_len); qlog("bind result = %d\n", result); - result = SQLBindCol(hstmt1, 4, SQL_C_CHAR, type, sizeof(type), &typelen); + result = SQLBindCol(hstmt1, 4, SQL_C_CHAR, pkcol, sizeof(pkcol), &pkcol_len); qlog("bind result = %d\n", result); - + + result = SQLBindCol(hstmt1, 5, SQL_C_SHORT, &seq, 0, NULL); + qlog("bind result = %d\n", result); + + result = SQLFetch(hstmt1); + qlog("SQLFetch result = %d\n", result); + while (result != SQL_NO_DATA_FOUND) { + qlog("fetch on stmt1: result = %d, pktab='%s', pkcol='%s', seq=%d\n", + result, pktab, pkcol, seq); + + result = SQLFetch(hstmt1); + } + qlog("SQLFetch result = %d\n", result); + + // Test of case #1 + result = SQLForeignKeys(hstmt1, "", SQL_NTS, "", SQL_NTS, "t1", SQL_NTS, + NULL, 0, NULL, 0, NULL, 0); + + // Test of case #2 + result = SQLForeignKeys(hstmt1, "", SQL_NTS, "", SQL_NTS, NULL, 0, + NULL, 0, NULL, 0, "ar_register", SQL_NTS); + + + // Test of case #3 + result = SQLForeignKeys(hstmt1, NULL, 0, NULL, 0, "employee", SQL_NTS, + NULL, 0, NULL, 0, "invoice", SQL_NTS); + + qlog("SQLForeignKeys result = %d\n", result); + + result = SQLNumResultCols(hstmt1, &cols); + qlog("cols SQLTables result = %d\n", result); + + result = SQLBindCol(hstmt1, 3, SQL_C_CHAR, pktab, sizeof(pktab), &pktab_len); + qlog("bind result = %d\n", result); + + result = SQLBindCol(hstmt1, 4, SQL_C_CHAR, pkcol, sizeof(pkcol), &pkcol_len); + qlog("bind result = %d\n", result); + + result = SQLBindCol(hstmt1, 7, SQL_C_CHAR, fktab, sizeof(fktab), &fktab_len); + qlog("bind result = %d\n", result); + + result = SQLBindCol(hstmt1, 8, SQL_C_CHAR, fkcol, sizeof(fkcol), &fkcol_len); + qlog("bind result = %d\n", result); + + result = SQLBindCol(hstmt1, 9, SQL_C_SHORT, &seq, 0, NULL); + qlog("bind result = %d\n", result); + + result = SQLBindCol(hstmt1, 10, SQL_C_LONG, &update_rule, 0, &ur_len); + qlog("bind result = %d\n", result); + + result = SQLBindCol(hstmt1, 11, SQL_C_LONG, &delete_rule, 0, &dr_len); + qlog("bind result = %d\n", result); + + result = SQLBindCol(hstmt1, 14, SQL_C_CHAR, tgname, sizeof(tgname), &tgname_len); + qlog("bind result = %d\n", result); + result = SQLFetch(hstmt1); qlog("SQLFetch result = %d\n", result); while (result != SQL_NO_DATA_FOUND) { - qlog("fetch on stmt1: result=%d, namelen=%d: name='%s', typelen=%d, type='%s'\n", result, namelen, name, typelen, type); + qlog("fetch on stmt1: result = %d, pktab='%s', pkcol='%s', fktab='%s', fkcol='%s', seq=%d, update_rule=%d, ur_len=%d, delete_rule=%d, dr_len=%d, tgname='%s', tgname_len=%d\n", + result, pktab, pkcol, fktab, fkcol, seq, update_rule, ur_len, delete_rule, dr_len, tgname, tgname_len); result = SQLFetch(hstmt1); } qlog("SQLFetch result = %d\n", result); + SQLFreeStmt(hstmt1, SQL_DROP); } */ + diff --git a/src/interfaces/odbc/connection.h b/src/interfaces/odbc/connection.h index 9776967f28..895e4ce826 100644 --- a/src/interfaces/odbc/connection.h +++ b/src/interfaces/odbc/connection.h @@ -11,10 +11,10 @@ #define __CONNECTION_H__ #ifdef HAVE_CONFIG_H -#include +#include "config.h" #endif -#ifdef HAVE_IODBC +#ifndef WIN32 #include "iodbc.h" #include "isql.h" #include "isqlext.h" @@ -163,6 +163,14 @@ struct col_info { }; /* Translation DLL entry points */ +#ifdef WIN32 +#define DLLHANDLE HINSTANCE +#else +#define WINAPI CALLBACK +#define DLLHANDLE void * +#define HINSTANCE void * +#endif + typedef BOOL (FAR WINAPI *DataSourceToDriverProc) (UDWORD, SWORD, PTR, @@ -222,7 +230,7 @@ struct ConnectionClass_ { /* prototypes */ -ConnectionClass *CC_Constructor(); +ConnectionClass *CC_Constructor(void); char CC_Destructor(ConnectionClass *self); int CC_cursor_count(ConnectionClass *self); char CC_cleanup(ConnectionClass *self); diff --git a/src/interfaces/odbc/convert.c b/src/interfaces/odbc/convert.c index 3c24731bd2..72cb6feb0e 100644 --- a/src/interfaces/odbc/convert.c +++ b/src/interfaces/odbc/convert.c @@ -17,13 +17,14 @@ */ #ifdef HAVE_CONFIG_H -#include +#include "config.h" #endif #include #include +#include -#ifdef HAVE_IODBC +#ifndef WIN32 #include "iodbc.h" #include "isql.h" #include "isqlext.h" @@ -42,8 +43,8 @@ #include "lobj.h" #include "connection.h" -#ifdef UNIX -#if !HAVE_STRICMP +#ifndef WIN32 +#ifndef HAVE_STRICMP #define stricmp(s1,s2) strcasecmp(s1,s2) #define strnicmp(s1,s2,n) strncasecmp(s1,s2,n) #endif @@ -69,6 +70,10 @@ char *mapFuncs[][2] = { { 0, 0 } }; +char *mapFunction(char *func); +unsigned int conv_from_octal(unsigned char *s); +unsigned int conv_from_hex(unsigned char *s); +char *conv_to_octal(unsigned char val); /******** A Guide for date/time/timestamp conversions ************** @@ -126,6 +131,7 @@ struct tm *tim; return COPY_OK; } + if (stmt->hdbc->DataSourceToDriver != NULL) { int length = strlen (value); stmt->hdbc->DataSourceToDriver (stmt->hdbc->translation_option, @@ -135,6 +141,7 @@ struct tm *tim; NULL, 0, NULL); } + /******************************************************************** First convert any specific postgres types into more useable data. @@ -393,6 +400,7 @@ struct tm *tim; } + /* This function inserts parameters into an SQL statements. It will also modify a SELECT statement for use with declare/fetch cursors. This function no longer does any dynamic memory allocation! @@ -400,7 +408,7 @@ struct tm *tim; int copy_statement_with_parameters(StatementClass *stmt) { -char *func="copy_statement_with_parameters"; +static char *func="copy_statement_with_parameters"; unsigned int opos, npos; char param_string[128], tmp[256], cbuf[TEXT_FIELD_SIZE+5]; int param_number; @@ -431,7 +439,7 @@ char in_quote = FALSE; /* If the application hasn't set a cursor name, then generate one */ if ( stmt->cursor_name[0] == '\0') - sprintf(stmt->cursor_name, "SQL_CUR%u", stmt); + sprintf(stmt->cursor_name, "SQL_CUR%p", stmt); // For selects, prepend a declare cursor to the statement if (stmt->statement_type == STMT_TYPE_SELECT && globals.use_declarefetch) { @@ -533,9 +541,7 @@ char in_quote = FALSE; param_ctype = stmt->parameters[param_number].CType; param_sqltype = stmt->parameters[param_number].SQLType; - mylog("copy_statement_with_params: from(fcType)=%d, to(fSqlType)=%d\n", - param_ctype, - param_sqltype); + mylog("copy_statement_with_params: from(fcType)=%d, to(fSqlType)=%d\n", param_ctype, param_sqltype); // replace DEFAULT with something we can use if(param_ctype == SQL_C_DEFAULT) @@ -630,8 +636,7 @@ char in_quote = FALSE; st.mm = tss->minute; st.ss = tss->second; - mylog("m=%d,d=%d,y=%d,hh=%d,mm=%d,ss=%d\n", - st.m, st.d, st.y, st.hh, st.mm, st.ss); + mylog("m=%d,d=%d,y=%d,hh=%d,mm=%d,ss=%d\n", st.m, st.d, st.y, st.hh, st.mm, st.ss); break; @@ -769,6 +774,7 @@ char in_quote = FALSE; // make sure new_statement is always null-terminated new_statement[npos] = '\0'; + if(stmt->hdbc->DriverToDataSource != NULL) { int length = strlen (new_statement); stmt->hdbc->DriverToDataSource (stmt->hdbc->translation_option, @@ -778,6 +784,7 @@ char in_quote = FALSE; NULL, 0, NULL); } + return SQL_SUCCESS; } @@ -975,6 +982,9 @@ char *p; int convert_pgbinary_to_char(char *value, char *rgbValue, int cbValueMax) { + mylog("convert_pgbinary_to_char: value = '%s'\n", value); + + strncpy_null(rgbValue, value, cbValueMax); return 0; } @@ -1029,6 +1039,9 @@ int o=0; mylog("convert_from_pgbinary: i=%d, rgbValue[%d] = %d, %c\n", i, o, rgbValue[o], rgbValue[o]); o++; } + + rgbValue[o] = '\0'; + return o; } @@ -1148,13 +1161,16 @@ int retval; stmt->lobj_fd = lo_open(stmt->hdbc, oid, INV_READ); if (stmt->lobj_fd < 0) { stmt->errornumber = STMT_EXEC_ERROR; - stmt->errormsg = "Couldnt open large object for writing."; + stmt->errormsg = "Couldnt open large object for reading."; return COPY_GENERAL_ERROR; } } - if (stmt->lobj_fd < 0) - return COPY_NO_DATA_FOUND; + if (stmt->lobj_fd < 0) { + stmt->errornumber = STMT_EXEC_ERROR; + stmt->errormsg = "Large object FD undefined for multiple read."; + return COPY_GENERAL_ERROR; + } retval = lo_read(stmt->hdbc, stmt->lobj_fd, rgbValue, cbValueMax); if (retval < 0) { diff --git a/src/interfaces/odbc/dlg_specific.c b/src/interfaces/odbc/dlg_specific.c index 316941b765..82e7e5a2b8 100644 --- a/src/interfaces/odbc/dlg_specific.c +++ b/src/interfaces/odbc/dlg_specific.c @@ -17,15 +17,15 @@ */ #ifdef HAVE_CONFIG_H -#include +#include "config.h" #endif -#ifdef UNIX +#ifndef WIN32 #include #include "gpps.h" #define SQLGetPrivateProfileString(a,b,c,d,e,f) GetPrivateProfileString(a,b,c,d,e,f) #define SQLWritePrivateProfileString(a,b,c,d) WritePrivateProfileString(a,b,c,d) -#if !HAVE_STRICMP +#ifndef HAVE_STRICMP #define stricmp(s1,s2) strcasecmp(s1,s2) #define strnicmp(s1,s2,n) strncasecmp(s1,s2,n) #endif @@ -34,9 +34,19 @@ #include "dlg_specific.h" #include "convert.h" +#ifndef BOOL +#define BOOL int +#endif +#ifndef FALSE +#define FALSE (BOOL)0 +#endif +#ifndef TRUE +#define TRUE (BOOL)1 +#endif + extern GLOBAL_VALUES globals; -#ifndef UNIX /* best to find a #ifdef for WINDOWS */ +#ifdef WIN32 void SetDlgStuff(HWND hdlg, ConnInfo *ci) { @@ -291,7 +301,7 @@ char buf[128]; return FALSE; } -#endif /* !UNIX */ +#endif /* WIN32 */ void makeConnectString(char *connect_string, ConnInfo *ci) @@ -371,16 +381,7 @@ copyAttributes(ConnInfo *ci, char *attribute, char *value) // strcpy(ci->conn_settings, value); } - mylog("copyAttributes: DSN='%s',server='%s',dbase='%s',user='%s',passwd='%s',port='%s',readonly='%s',protocol='%s', conn_settings='%s')\n", - ci->dsn, - ci->server, - ci->database, - ci->username, - ci->password, - ci->port, - ci->readonly, - ci->protocol, - ci->conn_settings); + mylog("copyAttributes: DSN='%s',server='%s',dbase='%s',user='%s',passwd='%s',port='%s',readonly='%s',protocol='%s', conn_settings='%s')\n", ci->dsn, ci->server,ci->database,ci->username,ci->password,ci->port,ci->readonly,ci->protocol,ci->conn_settings); } @@ -422,6 +423,9 @@ char encoded_conn_settings[LARGE_REGISTRY_LEN]; strcpy(DSN, INI_DSN); } + // brute-force chop off trailing blanks... + while (*(DSN+strlen(DSN)-1) == ' ') *(DSN+strlen(DSN)-1) = '\0'; + // Proceed with getting info for the given DSN. if ( ci->desc[0] == '\0' || overwrite) @@ -471,6 +475,11 @@ char encoded_conn_settings[LARGE_REGISTRY_LEN]; if ( ci->translation_option[0] == '\0' || overwrite) SQLGetPrivateProfileString(DSN, INI_TRANSLATIONOPTION, "", ci->translation_option, sizeof(ci->translation_option), ODBC_INI); + + /* Allow override of odbcinst.ini parameters here */ + getGlobalDefaults(DSN, ODBC_INI, TRUE); + + qlog("DSN info: DSN='%s',server='%s',port='%s',dbase='%s',user='%s',passwd='%s'\n", DSN, ci->server, @@ -572,165 +581,172 @@ char encoded_conn_settings[LARGE_REGISTRY_LEN]; /* This function reads the ODBCINST.INI portion of the registry and gets any driver defaults. */ -void getGlobalDefaults(void) +void getGlobalDefaults(char *section, char *filename, char override) { -char temp[128]; +char temp[256]; // Fetch Count is stored in driver section - SQLGetPrivateProfileString(DBMS_NAME, INI_FETCH, "", - temp, sizeof(temp), ODBCINST_INI); + SQLGetPrivateProfileString(section, INI_FETCH, "", + temp, sizeof(temp), filename); if ( temp[0] ) { globals.fetch_max = atoi(temp); /* sanity check if using cursors */ if (globals.fetch_max <= 0) globals.fetch_max = FETCH_MAX; } - - else + else if ( ! override) globals.fetch_max = FETCH_MAX; // Socket Buffersize is stored in driver section - SQLGetPrivateProfileString(DBMS_NAME, INI_SOCKET, "", - temp, sizeof(temp), ODBCINST_INI); + SQLGetPrivateProfileString(section, INI_SOCKET, "", + temp, sizeof(temp), filename); if ( temp[0] ) globals.socket_buffersize = atoi(temp); - else + else if ( ! override) globals.socket_buffersize = SOCK_BUFFER_SIZE; // Debug is stored in the driver section - SQLGetPrivateProfileString(DBMS_NAME, INI_DEBUG, "0", - temp, sizeof(temp), ODBCINST_INI); - globals.debug = atoi(temp); + SQLGetPrivateProfileString(section, INI_DEBUG, "", + temp, sizeof(temp), filename); + if ( temp[0] ) + globals.debug = atoi(temp); + else if ( ! override) + globals.debug = DEFAULT_DEBUG; // CommLog is stored in the driver section - SQLGetPrivateProfileString(DBMS_NAME, INI_COMMLOG, "", - temp, sizeof(temp), ODBCINST_INI); - if ( temp[0] == '\0') - globals.commlog = DEFAULT_COMMLOG; - else + SQLGetPrivateProfileString(section, INI_COMMLOG, "", + temp, sizeof(temp), filename); + if ( temp[0] ) globals.commlog = atoi(temp); + else if ( ! override) + globals.commlog = DEFAULT_COMMLOG; // Optimizer is stored in the driver section only - SQLGetPrivateProfileString(DBMS_NAME, INI_OPTIMIZER, "", - temp, sizeof(temp), ODBCINST_INI); - if ( temp[0] == '\0') - globals.disable_optimizer = DEFAULT_OPTIMIZER; - else + SQLGetPrivateProfileString(section, INI_OPTIMIZER, "", + temp, sizeof(temp), filename); + if ( temp[0] ) globals.disable_optimizer = atoi(temp); + else if ( ! override) + globals.disable_optimizer = DEFAULT_OPTIMIZER; // Recognize Unique Index is stored in the driver section only - SQLGetPrivateProfileString(DBMS_NAME, INI_UNIQUEINDEX, "", - temp, sizeof(temp), ODBCINST_INI); - if ( temp[0] == '\0') - globals.unique_index = DEFAULT_UNIQUEINDEX; - else + SQLGetPrivateProfileString(section, INI_UNIQUEINDEX, "", + temp, sizeof(temp), filename); + if ( temp[0] ) globals.unique_index = atoi(temp); + else if ( ! override) + globals.unique_index = DEFAULT_UNIQUEINDEX; // Unknown Sizes is stored in the driver section only - SQLGetPrivateProfileString(DBMS_NAME, INI_UNKNOWNSIZES, "", - temp, sizeof(temp), ODBCINST_INI); - if ( temp[0] == '\0') - globals.unknown_sizes = DEFAULT_UNKNOWNSIZES; - else + SQLGetPrivateProfileString(section, INI_UNKNOWNSIZES, "", + temp, sizeof(temp), filename); + if ( temp[0] ) globals.unknown_sizes = atoi(temp); + else if ( ! override) + globals.unknown_sizes = DEFAULT_UNKNOWNSIZES; // Lie about supported functions? - SQLGetPrivateProfileString(DBMS_NAME, INI_LIE, "", - temp, sizeof(temp), ODBCINST_INI); - if ( temp[0] == '\0') - globals.lie = DEFAULT_LIE; - else + SQLGetPrivateProfileString(section, INI_LIE, "", + temp, sizeof(temp), filename); + if ( temp[0] ) globals.lie = atoi(temp); + else if ( ! override) + globals.lie = DEFAULT_LIE; // Parse statements - SQLGetPrivateProfileString(DBMS_NAME, INI_PARSE, "", - temp, sizeof(temp), ODBCINST_INI); - if ( temp[0] == '\0') - globals.parse = DEFAULT_PARSE; - else + SQLGetPrivateProfileString(section, INI_PARSE, "", + temp, sizeof(temp), filename); + if ( temp[0] ) globals.parse = atoi(temp); + else if ( ! override) + globals.parse = DEFAULT_PARSE; // Readonly is stored in the driver section AND per datasource - SQLGetPrivateProfileString(DBMS_NAME, INI_READONLY, "", - temp, sizeof(temp), ODBCINST_INI); - if ( temp[0] == '\0') - globals.readonly = DEFAULT_READONLY; - else + SQLGetPrivateProfileString(section, INI_READONLY, "", + temp, sizeof(temp), filename); + if ( temp[0] ) globals.readonly = atoi(temp); + else if ( ! override) + globals.readonly = DEFAULT_READONLY; // UseDeclareFetch is stored in the driver section only - SQLGetPrivateProfileString(DBMS_NAME, INI_USEDECLAREFETCH, "", - temp, sizeof(temp), ODBCINST_INI); - if ( temp[0] == '\0') - globals.use_declarefetch = DEFAULT_USEDECLAREFETCH; - else + SQLGetPrivateProfileString(section, INI_USEDECLAREFETCH, "", + temp, sizeof(temp), filename); + if ( temp[0] ) globals.use_declarefetch = atoi(temp); + else if ( ! override) + globals.use_declarefetch = DEFAULT_USEDECLAREFETCH; // Max Varchar Size - SQLGetPrivateProfileString(DBMS_NAME, INI_MAXVARCHARSIZE, "", - temp, sizeof(temp), ODBCINST_INI); - if ( temp[0] == '\0') - globals.max_varchar_size = MAX_VARCHAR_SIZE; - else + SQLGetPrivateProfileString(section, INI_MAXVARCHARSIZE, "", + temp, sizeof(temp), filename); + if ( temp[0] ) globals.max_varchar_size = atoi(temp); + else if ( ! override) + globals.max_varchar_size = MAX_VARCHAR_SIZE; // Max TextField Size - SQLGetPrivateProfileString(DBMS_NAME, INI_MAXLONGVARCHARSIZE, "", - temp, sizeof(temp), ODBCINST_INI); - if ( temp[0] == '\0') - globals.max_longvarchar_size = TEXT_FIELD_SIZE; - else + SQLGetPrivateProfileString(section, INI_MAXLONGVARCHARSIZE, "", + temp, sizeof(temp), filename); + if ( temp[0] ) globals.max_longvarchar_size = atoi(temp); + else if ( ! override) + globals.max_longvarchar_size = TEXT_FIELD_SIZE; // Text As LongVarchar - SQLGetPrivateProfileString(DBMS_NAME, INI_TEXTASLONGVARCHAR, "", - temp, sizeof(temp), ODBCINST_INI); - if ( temp[0] == '\0') - globals.text_as_longvarchar = DEFAULT_TEXTASLONGVARCHAR; - else + SQLGetPrivateProfileString(section, INI_TEXTASLONGVARCHAR, "", + temp, sizeof(temp), filename); + if ( temp[0] ) globals.text_as_longvarchar = atoi(temp); + else if ( ! override) + globals.text_as_longvarchar = DEFAULT_TEXTASLONGVARCHAR; // Unknowns As LongVarchar - SQLGetPrivateProfileString(DBMS_NAME, INI_UNKNOWNSASLONGVARCHAR, "", - temp, sizeof(temp), ODBCINST_INI); - if ( temp[0] == '\0') - globals.unknowns_as_longvarchar = DEFAULT_UNKNOWNSASLONGVARCHAR; - else + SQLGetPrivateProfileString(section, INI_UNKNOWNSASLONGVARCHAR, "", + temp, sizeof(temp), filename); + if ( temp[0] ) globals.unknowns_as_longvarchar = atoi(temp); + else if ( ! override) + globals.unknowns_as_longvarchar = DEFAULT_UNKNOWNSASLONGVARCHAR; // Bools As Char - SQLGetPrivateProfileString(DBMS_NAME, INI_BOOLSASCHAR, "", - temp, sizeof(temp), ODBCINST_INI); - if ( temp[0] == '\0') - globals.bools_as_char = DEFAULT_BOOLSASCHAR; - else + SQLGetPrivateProfileString(section, INI_BOOLSASCHAR, "", + temp, sizeof(temp), filename); + if ( temp[0] ) globals.bools_as_char = atoi(temp); + else if ( ! override) + globals.bools_as_char = DEFAULT_BOOLSASCHAR; - - // Extra System Table prefixes - SQLGetPrivateProfileString(DBMS_NAME, INI_EXTRASYSTABLEPREFIXES, "@@@", - globals.extra_systable_prefixes, sizeof(globals.extra_systable_prefixes), ODBCINST_INI); - if ( ! strcmp(globals.extra_systable_prefixes, "@@@")) { + // Extra Systable prefixes + // Use @@@ to distinguish between blank extra prefixes and no key entry + SQLGetPrivateProfileString(section, INI_EXTRASYSTABLEPREFIXES, "@@@", + temp, sizeof(temp), filename); + if ( strcmp(temp, "@@@" )) + strcpy(globals.extra_systable_prefixes, temp); + else if ( ! override) strcpy(globals.extra_systable_prefixes, DEFAULT_EXTRASYSTABLEPREFIXES); - } + mylog("globals.extra_systable_prefixes = '%s'\n", globals.extra_systable_prefixes); - // ConnSettings is stored in the driver section and per datasource for override - SQLGetPrivateProfileString(DBMS_NAME, INI_CONNSETTINGS, "", - globals.conn_settings, sizeof(globals.conn_settings), ODBCINST_INI); + // Dont allow override of an override! + if ( ! override) { + // ConnSettings is stored in the driver section and per datasource for override + SQLGetPrivateProfileString(section, INI_CONNSETTINGS, "", + globals.conn_settings, sizeof(globals.conn_settings), filename); + } } diff --git a/src/interfaces/odbc/dlg_specific.h b/src/interfaces/odbc/dlg_specific.h index 7861199fe3..b4e5ef05f1 100644 --- a/src/interfaces/odbc/dlg_specific.h +++ b/src/interfaces/odbc/dlg_specific.h @@ -11,13 +11,13 @@ #define __DLG_SPECIFIC_H__ #ifdef HAVE_CONFIG_H -#include +#include "config.h" #endif #include "psqlodbc.h" #include "connection.h" -#ifndef UNIX +#ifdef WIN32 #include #include #include @@ -30,13 +30,20 @@ #define UNKNOWNS_AS_LONGEST 2 /* INI File Stuff */ -#ifdef UNIX -#define ODBC_INI ".odbc.ini" -#define ODBCINST_INI "/etc/odbcinst.ini" +#ifndef WIN32 +#define ODBC_INI ".odbc.ini" +#ifdef ODBCINST +#define xstr(s) str(s) +#define str(s) #s +#define ODBCINST_INI xstr(ODBCINST) "/odbcinst.ini" #else -#define ODBC_INI "ODBC.INI" /* ODBC initialization file */ -#define ODBCINST_INI "ODBCINST.INI" /* ODBC Installation file */ +#define ODBCINST_INI "/etc/odbcinst.ini" #endif +#else +#define ODBC_INI "ODBC.INI" /* ODBC initialization file */ +#define ODBCINST_INI "ODBCINST.INI" /* ODBC Installation file */ +#endif + #define INI_DSN DBMS_NAME /* Name of default Datasource in ini file (not used?) */ #define INI_KDESC "Description" /* Data source description */ @@ -81,13 +88,14 @@ /* Connection Defaults */ #define DEFAULT_PORT "5432" #define DEFAULT_READONLY 1 -#define DEFAULT_USEDECLAREFETCH 1 +#define DEFAULT_USEDECLAREFETCH 0 #define DEFAULT_TEXTASLONGVARCHAR 1 #define DEFAULT_UNKNOWNSASLONGVARCHAR 0 #define DEFAULT_BOOLSASCHAR 1 #define DEFAULT_OPTIMIZER 1 // disable #define DEFAULT_UNIQUEINDEX 0 // dont recognize #define DEFAULT_COMMLOG 0 // dont log +#define DEFAULT_DEBUG 0 #define DEFAULT_UNKNOWNSIZES UNKNOWNS_AS_MAX @@ -101,9 +109,9 @@ #define DEFAULT_EXTRASYSTABLEPREFIXES "dd_;" /* prototypes */ -void getGlobalDefaults(void); +void getGlobalDefaults(char *section, char *filename, char override); -#ifndef UNIX +#ifdef WIN32 void SetDlgStuff(HWND hdlg, ConnInfo *ci); void GetDlgStuff(HWND hdlg, ConnInfo *ci); @@ -115,7 +123,7 @@ int CALLBACK ds_optionsProc(HWND hdlg, WORD wMsg, WPARAM wParam, LPARAM lParam); -#endif /* ! UNIX */ +#endif /* WIN32 */ void updateGlobals(void); void writeDSNinfo(ConnInfo *ci); diff --git a/src/interfaces/odbc/drvconn.c b/src/interfaces/odbc/drvconn.c index 13dbaf28b0..7959ed998c 100644 --- a/src/interfaces/odbc/drvconn.c +++ b/src/interfaces/odbc/drvconn.c @@ -13,7 +13,7 @@ */ #ifdef HAVE_CONFIG_H -#include +#include "config.h" #endif #include @@ -22,7 +22,7 @@ #include "psqlodbc.h" #include "connection.h" -#ifdef UNIX +#ifndef WIN32 #include #include #define NEAR @@ -33,7 +33,7 @@ #include -#ifdef UNIX +#ifndef WIN32 #define stricmp(s1,s2) strcasecmp(s1,s2) #define strnicmp(s1,s2,n) strncasecmp(s1,s2,n) #else @@ -55,7 +55,7 @@ /* prototypes */ void dconn_get_connect_attributes(UCHAR FAR *connect_string, ConnInfo *ci); -#ifndef UNIX /* should be something like ifdef WINDOWS */ +#ifdef WIN32 BOOL FAR PASCAL dconn_FDriverConnectProc(HWND hdlg, UINT wMsg, WPARAM wParam, LPARAM lParam); RETCODE dconn_DoDialog(HWND hwnd, ConnInfo *ci); @@ -75,15 +75,19 @@ RETCODE SQL_API SQLDriverConnect( SWORD FAR *pcbConnStrOut, UWORD fDriverCompletion) { -char *func = "SQLDriverConnect"; +static char *func = "SQLDriverConnect"; ConnectionClass *conn = (ConnectionClass *) hdbc; ConnInfo *ci; +#ifdef WIN32 RETCODE dialog_result; +#endif char connStrIn[MAX_CONNECT_STRING]; char connStrOut[MAX_CONNECT_STRING]; int retval; char password_required = FALSE; + mylog("%s: entering...\n", func); + if ( ! conn) { CC_log_error(func, "", NULL); return SQL_INVALID_HANDLE; @@ -107,11 +111,13 @@ char password_required = FALSE; // Fill in any default parameters if they are not there. getDSNdefaults(ci); +#ifdef WIN32 dialog: +#endif ci->focus_password = password_required; switch(fDriverCompletion) { -#ifndef UNIX /* again should be ifdef WINDOWS like */ +#ifdef WIN32 case SQL_DRIVER_PROMPT: dialog_result = dconn_DoDialog(hwnd, ci); if(dialog_result != SQL_SUCCESS) { @@ -185,7 +191,7 @@ dialog: return SQL_ERROR; /* need a password but not allowed to prompt so error */ } else { -#ifndef UNIX +#ifdef WIN32 password_required = TRUE; goto dialog; #else @@ -203,7 +209,7 @@ dialog: return SQL_SUCCESS; } -#ifndef UNIX /* yet another candidate for ifdef WINDOWS */ +#ifdef WIN32 RETCODE dconn_DoDialog(HWND hwnd, ConnInfo *ci) { int dialog_result; @@ -299,7 +305,7 @@ ConnInfo *ci; return FALSE; } -#endif /* ! UNIX */ +#endif /* WIN32 */ void dconn_get_connect_attributes(UCHAR FAR *connect_string, ConnInfo *ci) { diff --git a/src/interfaces/odbc/environ.c b/src/interfaces/odbc/environ.c index 82f73e977f..f5c2798b5e 100644 --- a/src/interfaces/odbc/environ.c +++ b/src/interfaces/odbc/environ.c @@ -25,7 +25,7 @@ ConnectionClass *conns[MAX_CONNECTIONS]; RETCODE SQL_API SQLAllocEnv(HENV FAR *phenv) { -char *func = "SQLAllocEnv"; +static char *func = "SQLAllocEnv"; mylog("**** in SQLAllocEnv ** \n"); @@ -42,7 +42,7 @@ mylog("**** in SQLAllocEnv ** \n"); RETCODE SQL_API SQLFreeEnv(HENV henv) { -char *func = "SQLFreeEnv"; +static char *func = "SQLFreeEnv"; EnvironmentClass *env = (EnvironmentClass *) henv; mylog("**** in SQLFreeEnv: env = %u ** \n", env); @@ -403,8 +403,7 @@ mylog("EN_add_connection: self = %u, conn = %u\n", self, conn); conn->henv = self; conns[i] = conn; - mylog(" added at i =%d, conn->henv = %u, conns[i]->henv = %u\n", - i, conn->henv, conns[i]->henv); + mylog(" added at i =%d, conn->henv = %u, conns[i]->henv = %u\n", i, conn->henv, conns[i]->henv); return TRUE; } diff --git a/src/interfaces/odbc/environ.h b/src/interfaces/odbc/environ.h index 906e4efae1..47018e7b38 100644 --- a/src/interfaces/odbc/environ.h +++ b/src/interfaces/odbc/environ.h @@ -11,12 +11,12 @@ #define __ENVIRON_H__ #ifdef HAVE_CONFIG_H -#include +#include "config.h" #endif #include "psqlodbc.h" -#ifdef HAVE_IODBC +#ifndef WIN32 #include "iodbc.h" #include "isql.h" #include "isqlext.h" diff --git a/src/interfaces/odbc/execute.c b/src/interfaces/odbc/execute.c index 2f4f1763bc..1baaaffc71 100644 --- a/src/interfaces/odbc/execute.c +++ b/src/interfaces/odbc/execute.c @@ -14,14 +14,14 @@ */ #ifdef HAVE_CONFIG_H -#include +#include "config.h" #endif #include "psqlodbc.h" #include #include -#ifdef HAVE_IODBC +#ifndef WIN32 #include "iodbc.h" #include "isqlext.h" #else @@ -37,23 +37,16 @@ #include "lobj.h" -RETCODE SQL_API SQLExecDirect( - HSTMT hstmt, - UCHAR FAR *szSqlStr, - SDWORD cbSqlStr) -{ - return _SQLExecDirect(hstmt, szSqlStr, cbSqlStr); -} - - // Perform a Prepare on the SQL statement RETCODE SQL_API SQLPrepare(HSTMT hstmt, UCHAR FAR *szSqlStr, SDWORD cbSqlStr) { -char *func = "SQLPrepare"; +static char *func = "SQLPrepare"; StatementClass *self = (StatementClass *) hstmt; + mylog( "%s: entering...\n", func); + if ( ! self) { SC_log_error(func, "", NULL); return SQL_INVALID_HANDLE; @@ -130,13 +123,16 @@ StatementClass *self = (StatementClass *) hstmt; // Performs the equivalent of SQLPrepare, followed by SQLExecute. -RETCODE SQL_API _SQLExecDirect( +RETCODE SQL_API SQLExecDirect( HSTMT hstmt, UCHAR FAR *szSqlStr, SDWORD cbSqlStr) { StatementClass *stmt = (StatementClass *) hstmt; -char *func = "SQLExecDirect"; +RETCODE SQL_API result; +static char *func = "SQLExecDirect"; + + mylog( "%s: entering...\n", func); if ( ! stmt) { SC_log_error(func, "", NULL); @@ -156,7 +152,7 @@ char *func = "SQLExecDirect"; return SQL_ERROR; } - mylog("**** SQLExecDirect: hstmt=%u, statement='%s'\n", hstmt, stmt->statement); + mylog("**** %s: hstmt=%u, statement='%s'\n", func, hstmt, stmt->statement); stmt->prepare = FALSE; stmt->statement_type = statement_type(stmt->statement); @@ -169,23 +165,29 @@ char *func = "SQLExecDirect"; return SQL_ERROR; } - mylog("SQLExecDirect: calling SQLExecute\n"); + mylog("%s: calling SQLExecute...\n", func); + + result = SQLExecute(hstmt); - return SQLExecute(hstmt); + mylog("%s: returned %hd from SQLExecute\n", func, result); + return result; } // Execute a prepared SQL statement RETCODE SQL_API SQLExecute( HSTMT hstmt) { -char *func="SQLExecute"; +static char *func="SQLExecute"; StatementClass *stmt = (StatementClass *) hstmt; ConnectionClass *conn; int i, retval; + mylog("%s: entering...\n", func); + if ( ! stmt) { SC_log_error(func, "", NULL); + mylog("%s: NULL statement so return SQL_INVALID_HANDLE\n", func); return SQL_INVALID_HANDLE; } @@ -195,14 +197,19 @@ int i, retval; */ if ( stmt->prepare && stmt->status == STMT_PREMATURE) { stmt->status = STMT_FINISHED; - if (stmt->errormsg == NULL) + if (stmt->errormsg == NULL) { + mylog("%s: premature statement but return SQL_SUCCESS\n", func); return SQL_SUCCESS; + } else { SC_log_error(func, "", stmt); + mylog("%s: premature statement so return SQL_ERROR\n", func); return SQL_ERROR; } } + mylog("%s: clear errors...\n", func); + SC_clear_error(stmt); conn = SC_get_conn(stmt); @@ -210,6 +217,7 @@ int i, retval; stmt->errormsg = "Connection is already in use."; stmt->errornumber = STMT_SEQUENCE_ERROR; SC_log_error(func, "", stmt); + mylog("%s: problem with connection\n", func); return SQL_ERROR; } @@ -217,6 +225,7 @@ int i, retval; stmt->errornumber = STMT_NO_STMTSTRING; stmt->errormsg = "This handle does not have a SQL statement stored in it"; SC_log_error(func, "", stmt); + mylog("%s: problem with handle\n", func); return SQL_ERROR; } @@ -225,6 +234,7 @@ int i, retval; to SQLFreeStmt(SQL_CLOSE) or SQLCancel. */ if (stmt->status == STMT_FINISHED) { + mylog("%s: recycling statement (should have been done by app)...\n", func); SC_recycle_statement(stmt); } @@ -235,6 +245,7 @@ int i, retval; stmt->errornumber = STMT_STATUS_ERROR; stmt->errormsg = "The handle does not point to a statement that is ready to be executed"; SC_log_error(func, "", stmt); + mylog("%s: problem with statement\n", func); return SQL_ERROR; } @@ -258,7 +269,7 @@ int i, retval; return SQL_NEED_DATA; - mylog("SQLExecute: copying statement params: trans_status=%d, len=%d, stmt='%s'\n", conn->transact_status, strlen(stmt->statement), stmt->statement); + mylog("%s: copying statement params: trans_status=%d, len=%d, stmt='%s'\n", func, conn->transact_status, strlen(stmt->statement), stmt->statement); // Create the statement with parameters substituted. retval = copy_statement_with_parameters(stmt); @@ -282,14 +293,14 @@ RETCODE SQL_API SQLTransact( HDBC hdbc, UWORD fType) { -char *func = "SQLTransact"; -extern ConnectionClass **conns; +static char *func = "SQLTransact"; +extern ConnectionClass *conns[]; ConnectionClass *conn; QResultClass *res; char ok, *stmt_string; int lf; -mylog("**** SQLTransact: hdbc=%u, henv=%u\n", hdbc, henv); + mylog("entering %s: hdbc=%u, henv=%u\n", func, hdbc, henv); if (hdbc == SQL_NULL_HDBC && henv == SQL_NULL_HENV) { CC_log_error(func, "", NULL); @@ -357,9 +368,11 @@ mylog("**** SQLTransact: hdbc=%u, henv=%u\n", hdbc, henv); RETCODE SQL_API SQLCancel( HSTMT hstmt) // Statement to cancel. { -char *func="SQLCancel"; +static char *func="SQLCancel"; StatementClass *stmt = (StatementClass *) hstmt; + mylog( "%s: entering...\n", func); + // Check if this can handle canceling in the middle of a SQLPutData? if ( ! stmt) { SC_log_error(func, "", NULL); @@ -394,6 +407,9 @@ RETCODE SQL_API SQLNativeSql( SDWORD cbSqlStrMax, SDWORD FAR *pcbSqlStr) { +static char *func="SQLNativeSql"; + + mylog( "%s: entering...\n", func); strncpy_null(szSqlStr, szSqlStrIn, cbSqlStrMax); @@ -409,17 +425,18 @@ RETCODE SQL_API SQLParamData( HSTMT hstmt, PTR FAR *prgbValue) { -char *func = "SQLParamData"; +static char *func = "SQLParamData"; StatementClass *stmt = (StatementClass *) hstmt; int i, retval; + mylog( "%s: entering...\n", func); + if ( ! stmt) { SC_log_error(func, "", NULL); return SQL_INVALID_HANDLE; } - mylog("SQLParamData, enter: data_at_exec=%d, params_alloc=%d\n", - stmt->data_at_exec, stmt->parameters_allocated); + mylog("%s: data_at_exec=%d, params_alloc=%d\n", func, stmt->data_at_exec, stmt->parameters_allocated); if (stmt->data_at_exec < 0) { stmt->errornumber = STMT_SEQUENCE_ERROR; @@ -482,12 +499,13 @@ RETCODE SQL_API SQLPutData( PTR rgbValue, SDWORD cbValue) { -char *func = "SQLPutData"; +static char *func = "SQLPutData"; StatementClass *stmt = (StatementClass *) hstmt; int old_pos, retval; ParameterInfoClass *current_param; char *buffer; + mylog( "%s: entering...\n", func); if ( ! stmt) { SC_log_error(func, "", NULL); diff --git a/src/interfaces/odbc/gpps.c b/src/interfaces/odbc/gpps.c index 62d37e5589..5cb4502c18 100644 --- a/src/interfaces/odbc/gpps.c +++ b/src/interfaces/odbc/gpps.c @@ -13,11 +13,12 @@ #ifndef WIN32 #if HAVE_CONFIG_H -#include // produced by configure +#include "config.h" // produced by configure #endif #include #include +#include #if HAVE_PWD_H #include @@ -26,6 +27,7 @@ #include #include #include "gpps.h" +#include "misc.h" #ifndef TRUE #define TRUE ((BOOL)1) @@ -54,6 +56,7 @@ GetPrivateProfileString(char *theSection, // section name size_t aLength; char aLine[2048]; char *aValue; + char *aStart; char *aString; size_t aLineLength; size_t aReturnLength = 0; @@ -144,11 +147,15 @@ GetPrivateProfileString(char *theSection, // section name if( (aString = strchr(aLine, ']')) ) { - *aString = '\0'; + aStart = aLine + 1; + aString--; + while (isspace(*aStart)) aStart++; + while (isspace(*aString)) aString--; + *(aString+1) = '\0'; // accept as matched if NULL key or exact match - if(!theSection || !strcmp(aLine + 1, theSection)) + if(!theSection || !strcmp(aStart, theSection)) { aSectionFound = TRUE; } @@ -185,11 +192,14 @@ GetPrivateProfileString(char *theSection, // section name aValue = ""; } + aStart = aLine; + while(isspace(*aStart)) aStart++; + // strip trailing blanks from key if(aString) { - while(--aString >= aLine && *aString == ' ') + while(--aString >= aStart && *aString == ' ') { *aString = '\0'; } @@ -197,7 +207,7 @@ GetPrivateProfileString(char *theSection, // section name // see if key is matched - if(theKey == NULL || !strcmp(theKey, aLine)) + if(theKey == NULL || !strcmp(theKey, aStart)) { // matched -- first, terminate value part diff --git a/src/interfaces/odbc/gpps.h b/src/interfaces/odbc/gpps.h index 21b15f1bfd..3f9738031a 100644 --- a/src/interfaces/odbc/gpps.h +++ b/src/interfaces/odbc/gpps.h @@ -4,10 +4,10 @@ #define GPPS_H #ifdef HAVE_CONFIG_H -#include +#include "config.h" #endif -#ifdef UNIX +#ifndef WIN32 #include #include "iodbc.h" #endif @@ -34,7 +34,7 @@ WritePrivateProfileString(char *theSection, // section name } #endif -#ifdef UNIX +#ifndef WIN32 #undef DWORD #endif #endif diff --git a/src/interfaces/odbc/info.c b/src/interfaces/odbc/info.c index 376f434126..c8a1998ad8 100644 --- a/src/interfaces/odbc/info.c +++ b/src/interfaces/odbc/info.c @@ -17,17 +17,18 @@ */ #ifdef HAVE_CONFIG_H -#include +#include "config.h" #endif #include #include #include "psqlodbc.h" -#ifdef HAVE_IODBC +#ifndef WIN32 #include "iodbc.h" #include "isql.h" #include "isqlext.h" +#include /* for tolower function */ #else #include #include @@ -46,8 +47,16 @@ #include "pgtypes.h" +/* Trigger related stuff for SQLForeign Keys */ +#define TRIGGER_SHIFT 3 +#define TRIGGER_MASK 0x03 +#define TRIGGER_DELETE 0x01 +#define TRIGGER_UPDATE 0x02 + + extern GLOBAL_VALUES globals; + // - - - - - - - - - RETCODE SQL_API SQLGetInfo( @@ -57,10 +66,13 @@ RETCODE SQL_API SQLGetInfo( SWORD cbInfoValueMax, SWORD FAR *pcbInfoValue) { -char *func = "SQLGetInfo"; +static char *func = "SQLGetInfo"; ConnectionClass *conn = (ConnectionClass *) hdbc; +ConnInfo *ci; char *p; + mylog( "%s: entering...\n", func); + if ( ! conn) { CC_log_error(func, "", NULL); return SQL_INVALID_HANDLE; @@ -71,6 +83,7 @@ char *p; return SQL_INVALID_HANDLE; } + ci = &conn->connInfo; switch (fInfoType) { case SQL_ACCESSIBLE_PROCEDURES: /* ODBC 1.0 */ @@ -290,11 +303,8 @@ char *p; case SQL_IDENTIFIER_QUOTE_CHAR: /* ODBC 1.0 */ // the character used to quote "identifiers" (what are they?) - // the manual index lists 'owner names' and 'qualifiers' as - // examples of identifiers. it says return a blank for no - // quote character, we'll try that... if (pcbInfoValue) *pcbInfoValue = 1; - strncpy_null((char *)rgbInfoValue, "\"", (size_t)cbInfoValueMax); + strncpy_null((char *)rgbInfoValue, PROTOCOL_62(ci) ? " " : "\"", (size_t)cbInfoValueMax); break; case SQL_KEYWORDS: /* ODBC 2.0 */ @@ -737,13 +747,13 @@ RETCODE SQL_API SQLGetTypeInfo( HSTMT hstmt, SWORD fSqlType) { -char *func = "SQLGetTypeInfo"; +static char *func = "SQLGetTypeInfo"; StatementClass *stmt = (StatementClass *) hstmt; TupleNode *row; int i; Int4 type; - mylog("**** in SQLGetTypeInfo: fSqlType = %d\n", fSqlType); + mylog("%s: entering...fSqlType = %d\n", func, fSqlType); if( ! stmt) { SC_log_error(func, "", NULL); @@ -822,6 +832,10 @@ RETCODE SQL_API SQLGetFunctions( UWORD fFunction, UWORD FAR *pfExists) { +static char *func="SQLGetFunctions"; + + mylog( "%s: entering...\n", func); + if (fFunction == SQL_API_ALL_FUNCTIONS) { if (globals.lie) { @@ -988,7 +1002,7 @@ RETCODE SQL_API SQLTables( UCHAR FAR * szTableType, SWORD cbTableType) { -char *func = "SQLTables"; +static char *func = "SQLTables"; StatementClass *stmt = (StatementClass *) hstmt; StatementClass *tbl_stmt; TupleNode *row; @@ -1004,7 +1018,7 @@ char show_system_tables, show_regular_tables, show_views; char regular_table, view, systable; int i; -mylog("**** SQLTables(): ENTER, stmt=%u\n", stmt); +mylog("%s: entering...stmt=%u\n", func, stmt); if( ! stmt) { SC_log_error(func, "", NULL); @@ -1029,7 +1043,8 @@ mylog("**** SQLTables(): ENTER, stmt=%u\n", stmt); // Create the query to find out the tables // ********************************************************************** - strcpy(tables_query, "select relname, usename, relhasrules from pg_class, pg_user where relkind = 'r' "); + strcpy(tables_query, "select relname, usename, relhasrules from pg_class, pg_user"); + strcat(tables_query, " where relkind = 'r'"); my_strcat(tables_query, " and usename like '%.*s'", szTableOwner, cbTableOwner); my_strcat(tables_query, " and relname like '%.*s'", szTableName, cbTableName); @@ -1097,7 +1112,9 @@ mylog("**** SQLTables(): ENTER, stmt=%u\n", stmt); /* filter out large objects unconditionally (they are not system tables) and match users */ - strcat(tables_query, " and relname !~ '^xinv[0-9]+' and int4out(usesysid) = int4out(relowner) order by relname"); + strcat(tables_query, " and relname !~ '^xinv[0-9]+'"); + strcat(tables_query, " and int4out(usesysid) = int4out(relowner)"); + strcat(tables_query, "order by relname"); // ********************************************************************** @@ -1257,7 +1274,7 @@ RETCODE SQL_API SQLColumns( UCHAR FAR * szColumnName, SWORD cbColumnName) { -char *func = "SQLColumns"; +static char *func = "SQLColumns"; StatementClass *stmt = (StatementClass *) hstmt; TupleNode *row; HSTMT hcol_stmt; @@ -1265,14 +1282,13 @@ StatementClass *col_stmt; char columns_query[MAX_STATEMENT_LEN]; RETCODE result; char table_owner[MAX_INFO_STRING], table_name[MAX_INFO_STRING], field_name[MAX_INFO_STRING], field_type_name[MAX_INFO_STRING]; -Int2 field_number, field_length, mod_length, result_cols; -Int4 field_type, the_type; +Int2 field_number, result_cols; +Int4 field_type, the_type, field_length, mod_length; char not_null[MAX_INFO_STRING]; ConnInfo *ci; - -mylog("**** SQLColumns(): ENTER, stmt=%u\n", stmt); + mylog("%s: entering...stmt=%u\n", func, stmt); if( ! stmt) { SC_log_error(func, "", NULL); @@ -1309,6 +1325,8 @@ mylog("**** SQLColumns(): ENTER, stmt=%u\n", stmt); } col_stmt = (StatementClass *) hcol_stmt; + mylog("SQLColumns: hcol_stmt = %u, col_stmt = %u\n", hcol_stmt, col_stmt); + result = SQLExecDirect(hcol_stmt, columns_query, strlen(columns_query)); if((result != SQL_SUCCESS) && (result != SQL_SUCCESS_WITH_INFO)) { @@ -1349,7 +1367,7 @@ mylog("**** SQLColumns(): ENTER, stmt=%u\n", stmt); return SQL_ERROR; } - result = SQLBindCol(hcol_stmt, 4, SQL_C_DEFAULT, + result = SQLBindCol(hcol_stmt, 4, SQL_C_LONG, &field_type, 4, NULL); if((result != SQL_SUCCESS) && (result != SQL_SUCCESS_WITH_INFO)) { stmt->errormsg = col_stmt->errormsg; @@ -1369,7 +1387,7 @@ mylog("**** SQLColumns(): ENTER, stmt=%u\n", stmt); return SQL_ERROR; } - result = SQLBindCol(hcol_stmt, 6, SQL_C_DEFAULT, + result = SQLBindCol(hcol_stmt, 6, SQL_C_SHORT, &field_number, MAX_INFO_STRING, NULL); if((result != SQL_SUCCESS) && (result != SQL_SUCCESS_WITH_INFO)) { stmt->errormsg = col_stmt->errormsg; @@ -1379,7 +1397,7 @@ mylog("**** SQLColumns(): ENTER, stmt=%u\n", stmt); return SQL_ERROR; } - result = SQLBindCol(hcol_stmt, 7, SQL_C_DEFAULT, + result = SQLBindCol(hcol_stmt, 7, SQL_C_LONG, &field_length, MAX_INFO_STRING, NULL); if((result != SQL_SUCCESS) && (result != SQL_SUCCESS_WITH_INFO)) { stmt->errormsg = col_stmt->errormsg; @@ -1389,7 +1407,7 @@ mylog("**** SQLColumns(): ENTER, stmt=%u\n", stmt); return SQL_ERROR; } - result = SQLBindCol(hcol_stmt, 8, SQL_C_DEFAULT, + result = SQLBindCol(hcol_stmt, 8, SQL_C_LONG, &mod_length, MAX_INFO_STRING, NULL); if((result != SQL_SUCCESS) && (result != SQL_SUCCESS_WITH_INFO)) { stmt->errormsg = col_stmt->errormsg; @@ -1445,6 +1463,7 @@ mylog("**** SQLColumns(): ENTER, stmt=%u\n", stmt); result = SQLFetch(hcol_stmt); + /* Only show oid if option AND there are other columns AND its not being called by SQLStatistics . Always show OID if its a system table @@ -1488,6 +1507,7 @@ mylog("**** SQLColumns(): ENTER, stmt=%u\n", stmt); row = (TupleNode *)malloc(sizeof(TupleNode) + (result_cols - 1) * sizeof(TupleField)); + set_tuplefield_string(&row->tuple[0], ""); // see note in SQLTables() // set_tuplefield_string(&row->tuple[1], table_owner); @@ -1535,7 +1555,9 @@ mylog("**** SQLColumns(): ENTER, stmt=%u\n", stmt); QR_add_tuple(stmt->result, row); + result = SQLFetch(hcol_stmt); + } if(result != SQL_NO_DATA_FOUND) { stmt->errormsg = SC_create_errormsg(hcol_stmt); @@ -1597,13 +1619,13 @@ RETCODE SQL_API SQLSpecialColumns( UWORD fScope, UWORD fNullable) { -char *func = "SQLSpecialColumns"; +static char *func = "SQLSpecialColumns"; TupleNode *row; StatementClass *stmt = (StatementClass *) hstmt; ConnInfo *ci; -mylog("**** SQLSpecialColumns(): ENTER, stmt=%u\n", stmt); +mylog("%s: entering...stmt=%u\n", func, stmt); if( ! stmt) { SC_log_error(func, "", NULL); @@ -1678,7 +1700,7 @@ RETCODE SQL_API SQLStatistics( UWORD fUnique, UWORD fAccuracy) { -char *func="SQLStatistics"; +static char *func="SQLStatistics"; StatementClass *stmt = (StatementClass *) hstmt; char index_query[MAX_STATEMENT_LEN]; HSTMT hindx_stmt; @@ -1700,7 +1722,7 @@ char error = TRUE; ConnInfo *ci; char buf[256]; -mylog("**** SQLStatistics(): ENTER, stmt=%u\n", stmt); +mylog("%s: entering...stmt=%u\n", func, stmt); if( ! stmt) { SC_log_error(func, "", NULL); @@ -2013,32 +2035,72 @@ RETCODE SQL_API SQLColumnPrivileges( UCHAR FAR * szColumnName, SWORD cbColumnName) { -char *func="SQLColumnPrivileges"; +static char *func="SQLColumnPrivileges"; + + mylog("%s: entering...\n", func); + /* Neither Access or Borland care about this. */ SC_log_error(func, "Function not implemented", (StatementClass *) hstmt); return SQL_ERROR; } -RETCODE -getPrimaryKeyString(StatementClass *stmt, char *szTableName, SWORD cbTableName, char *svKey, int *nKey) + + +RETCODE SQL_API SQLPrimaryKeys( + HSTMT hstmt, + UCHAR FAR * szTableQualifier, + SWORD cbTableQualifier, + UCHAR FAR * szTableOwner, + SWORD cbTableOwner, + UCHAR FAR * szTableName, + SWORD cbTableName) { -char *func = "getPrimaryKeyString"; +static char *func = "SQLPrimaryKeys"; +StatementClass *stmt = (StatementClass *) hstmt; +TupleNode *row; +RETCODE result; +int seq = 0; HSTMT htbl_stmt; StatementClass *tbl_stmt; -RETCODE result; char tables_query[MAX_STATEMENT_LEN]; char attname[MAX_INFO_STRING]; SDWORD attname_len; -int nk = 0; - - if (nKey != NULL) - *nKey = 0; +char pktab[MAX_TABLE_LEN + 1]; +Int2 result_cols; - svKey[0] = '\0'; + mylog("%s: entering...stmt=%u\n", func, stmt); + if( ! stmt) { + SC_log_error(func, "", NULL); + return SQL_INVALID_HANDLE; + } + stmt->manual_result = TRUE; stmt->errormsg_created = TRUE; + stmt->result = QR_Constructor(); + if(!stmt->result) { + stmt->errormsg = "Couldn't allocate memory for SQLPrimaryKeys result."; + stmt->errornumber = STMT_NO_MEMORY_ERROR; + SC_log_error(func, "", stmt); + return SQL_ERROR; + } + + // the binding structure for a statement is not set up until + // a statement is actually executed, so we'll have to do this ourselves. + result_cols = 6; + extend_bindings(stmt, result_cols); + + // set the field names + QR_set_num_fields(stmt->result, result_cols); + QR_set_field_info(stmt->result, 0, "TABLE_QUALIFIER", PG_TYPE_TEXT, MAX_INFO_STRING); + QR_set_field_info(stmt->result, 1, "TABLE_OWNER", PG_TYPE_TEXT, MAX_INFO_STRING); + QR_set_field_info(stmt->result, 2, "TABLE_NAME", PG_TYPE_TEXT, MAX_INFO_STRING); + QR_set_field_info(stmt->result, 3, "COLUMN_NAME", PG_TYPE_TEXT, MAX_INFO_STRING); + QR_set_field_info(stmt->result, 4, "KEY_SEQ", PG_TYPE_INT2, 2); + QR_set_field_info(stmt->result, 5, "PK_NAME", PG_TYPE_TEXT, MAX_INFO_STRING); + + result = SQLAllocStmt( stmt->hdbc, &htbl_stmt); if((result != SQL_SUCCESS) && (result != SQL_SUCCESS_WITH_INFO)) { stmt->errornumber = STMT_NO_MEMORY_ERROR; @@ -2048,18 +2110,19 @@ int nk = 0; } tbl_stmt = (StatementClass *) htbl_stmt; - tables_query[0] = '\0'; - if ( ! my_strcat(tables_query, "select distinct on attnum a2.attname, a2.attnum from pg_attribute a1, pg_attribute a2, pg_class c, pg_index i where c.relname = '%.*s_pkey' AND c.oid = i.indexrelid AND a1.attrelid = c.oid AND a2.attrelid = c.oid AND (i.indkey[0] = a1.attnum OR i.indkey[1] = a1.attnum OR i.indkey[2] = a1.attnum OR i.indkey[3] = a1.attnum OR i.indkey[4] = a1.attnum OR i.indkey[5] = a1.attnum OR i.indkey[6] = a1.attnum OR i.indkey[7] = a1.attnum) order by a2.attnum", - szTableName, cbTableName)) { - - stmt->errormsg = "No Table specified to getPrimaryKeyString."; + pktab[0] = '\0'; + make_string(szTableName, cbTableName, pktab); + if ( pktab[0] == '\0') { + stmt->errormsg = "No Table specified to SQLPrimaryKeys."; stmt->errornumber = STMT_INTERNAL_ERROR; SC_log_error(func, "", stmt); SQLFreeStmt(htbl_stmt, SQL_DROP); return SQL_ERROR; } - mylog("getPrimaryKeyString: tables_query='%s'\n", tables_query); + sprintf(tables_query, "select distinct on attnum a2.attname, a2.attnum from pg_attribute a1, pg_attribute a2, pg_class c, pg_index i where c.relname = '%s_pkey' AND c.oid = i.indexrelid AND a1.attrelid = c.oid AND a2.attrelid = c.oid AND (i.indkey[0] = a1.attnum OR i.indkey[1] = a1.attnum OR i.indkey[2] = a1.attnum OR i.indkey[3] = a1.attnum OR i.indkey[4] = a1.attnum OR i.indkey[5] = a1.attnum OR i.indkey[6] = a1.attnum OR i.indkey[7] = a1.attnum) order by a2.attnum", pktab); + + mylog("SQLPrimaryKeys: tables_query='%s'\n", tables_query); result = SQLExecDirect(htbl_stmt, tables_query, strlen(tables_query)); if((result != SQL_SUCCESS) && (result != SQL_SUCCESS_WITH_INFO)) { @@ -2081,14 +2144,29 @@ int nk = 0; } result = SQLFetch(htbl_stmt); + while((result == SQL_SUCCESS) || (result == SQL_SUCCESS_WITH_INFO)) { - if (strlen(svKey) > 0) - strcat(svKey, "+"); - strcat(svKey, attname); + row = (TupleNode *)malloc(sizeof(TupleNode) + (result_cols - 1) * sizeof(TupleField)); + + set_tuplefield_null(&row->tuple[0]); + + // I have to hide the table owner from Access, otherwise it + // insists on referring to the table as 'owner.table'. + // (this is valid according to the ODBC SQL grammar, but + // Postgres won't support it.) + + set_tuplefield_string(&row->tuple[1], ""); + set_tuplefield_string(&row->tuple[2], pktab); + set_tuplefield_string(&row->tuple[3], attname); + set_tuplefield_int2(&row->tuple[4], (Int2) (++seq)); + set_tuplefield_null(&row->tuple[5]); + + QR_add_tuple(stmt->result, row); + + mylog(">> primaryKeys: pktab = '%s', attname = '%s', seq = %d\n", pktab, attname, seq); result = SQLFetch(htbl_stmt); - nk++; } if(result != SQL_NO_DATA_FOUND) { @@ -2101,135 +2179,6 @@ int nk = 0; SQLFreeStmt(htbl_stmt, SQL_DROP); - if (nKey != NULL) - *nKey = nk; - - mylog(">> getPrimaryKeyString: returning nKey=%d, svKey='%s'\n", nk, svKey); - return result; -} - -RETCODE -getPrimaryKeyArray(StatementClass *stmt, char *szTableName, SWORD cbTableName, char keyArray[][MAX_INFO_STRING], int *nKey) -{ -RETCODE result; -char svKey[MAX_KEYLEN], *svKeyPtr; -int i = 0; - - result = getPrimaryKeyString(stmt, szTableName, cbTableName, svKey, nKey); - if (result != SQL_SUCCESS && result != SQL_NO_DATA_FOUND) - // error passed from above - return result; - - // If no keys, return NO_DATA_FOUND - if (svKey[0] == '\0') { - mylog("!!!!!! getPrimaryKeyArray: svKey was null\n"); - return SQL_NO_DATA_FOUND; - } - - // mylog(">> primarykeyArray: nKey=%d, svKey='%s'\n", *nKey, svKey); - - svKeyPtr = strtok(svKey, "+"); - while (svKeyPtr != NULL && i < MAX_KEYPARTS) { - strcpy(keyArray[i++], svKeyPtr); - svKeyPtr = strtok(NULL, "+"); - } - - /* - for (i = 0; i < *nKey; i++) - mylog(">> keyArray[%d] = '%s'\n", i, keyArray[i]); - */ - - return result; -} - - -RETCODE SQL_API SQLPrimaryKeys( - HSTMT hstmt, - UCHAR FAR * szTableQualifier, - SWORD cbTableQualifier, - UCHAR FAR * szTableOwner, - SWORD cbTableOwner, - UCHAR FAR * szTableName, - SWORD cbTableName) -{ -char *func = "SQLPrimaryKeys"; -StatementClass *stmt = (StatementClass *) hstmt; -TupleNode *row; -RETCODE result; -char svKey[MAX_KEYLEN], *ptr; -int seq = 1, nkeys = 0; - -mylog("**** SQLPrimaryKeys(): ENTER, stmt=%u\n", stmt); - - if( ! stmt) { - SC_log_error(func, "", NULL); - return SQL_INVALID_HANDLE; - } - stmt->manual_result = TRUE; - - result = getPrimaryKeyString(stmt, szTableName, cbTableName, svKey, &nkeys); - - mylog(">> PrimaryKeys: getPrimaryKeyString() returned %d, nkeys=%d, svKey = '%s'\n", result, nkeys, svKey); - - if (result != SQL_SUCCESS && result != SQL_NO_DATA_FOUND) { - // error msg passed from above - return result; - } - - // I'm not sure if this is correct to return when there are no keys or - // if an empty result set would be better. - if (nkeys == 0) { - stmt->errornumber = STMT_INFO_ONLY; - stmt->errormsg = "No primary keys for this table."; - return SQL_SUCCESS_WITH_INFO; - } - - stmt->result = QR_Constructor(); - if(!stmt->result) { - stmt->errormsg = "Couldn't allocate memory for SQLPrimaryKeys result."; - stmt->errornumber = STMT_NO_MEMORY_ERROR; - SC_log_error(func, "", stmt); - return SQL_ERROR; - } - - - // the binding structure for a statement is not set up until - // a statement is actually executed, so we'll have to do this ourselves. - extend_bindings(stmt, 6); - - // set the field names - QR_set_num_fields(stmt->result, 6); - QR_set_field_info(stmt->result, 0, "TABLE_QUALIFIER", PG_TYPE_TEXT, MAX_INFO_STRING); - QR_set_field_info(stmt->result, 1, "TABLE_OWNER", PG_TYPE_TEXT, MAX_INFO_STRING); - QR_set_field_info(stmt->result, 2, "TABLE_NAME", PG_TYPE_TEXT, MAX_INFO_STRING); - QR_set_field_info(stmt->result, 3, "COLUMN_NAME", PG_TYPE_TEXT, MAX_INFO_STRING); - QR_set_field_info(stmt->result, 4, "KEY_SEQ", PG_TYPE_INT2, 2); - QR_set_field_info(stmt->result, 5, "PK_NAME", PG_TYPE_TEXT, MAX_INFO_STRING); - - // add the tuples - ptr = strtok(svKey, "+"); - while( ptr != NULL) { - row = (TupleNode *)malloc(sizeof(TupleNode) + (6 - 1) * sizeof(TupleField)); - - set_tuplefield_string(&row->tuple[0], ""); - - // I have to hide the table owner from Access, otherwise it - // insists on referring to the table as 'owner.table'. - // (this is valid according to the ODBC SQL grammar, but - // Postgres won't support it.) - - mylog(">> primaryKeys: ptab = '%s', seq = %d\n", ptr, seq); - - set_tuplefield_string(&row->tuple[1], ""); - set_tuplefield_string(&row->tuple[2], szTableName); - set_tuplefield_string(&row->tuple[3], ptr); - set_tuplefield_int2(&row->tuple[4], (Int2) (seq++)); - set_tuplefield_null(&row->tuple[5]); - - QR_add_tuple(stmt->result, row); - - ptr = strtok(NULL, "+"); - } // also, things need to think that this statement is finished so // the results can be retrieved. @@ -2258,24 +2207,24 @@ RETCODE SQL_API SQLForeignKeys( UCHAR FAR * szFkTableName, SWORD cbFkTableName) { -char *func = "SQLForeignKeys"; +static char *func = "SQLForeignKeys"; StatementClass *stmt = (StatementClass *) hstmt; TupleNode *row; -HSTMT htbl_stmt; +HSTMT htbl_stmt, hpkey_stmt; StatementClass *tbl_stmt; -RETCODE result; +RETCODE result, keyresult; char tables_query[MAX_STATEMENT_LEN]; -char relname[MAX_INFO_STRING], attnames[MAX_INFO_STRING], frelname[MAX_INFO_STRING]; -SDWORD relname_len, attnames_len, frelname_len; -char *pktab, *fktab; -char fkey = FALSE; -char primaryKey[MAX_KEYPARTS][MAX_INFO_STRING]; -char *attnamePtr; -int pkeys, seq; +char args[1024], tgname[MAX_INFO_STRING]; +char pktab[MAX_TABLE_LEN + 1], fktab[MAX_TABLE_LEN + 1]; +char *ptr, *pkey_ptr, *pkptr, *fkptr, *frel, *prel; +int i, k, pkeys, seq, ntabs; +SWORD nargs, rule_type, action; +char pkey[MAX_INFO_STRING]; +Int2 result_cols; + -mylog("**** SQLForeignKeys(): ENTER, stmt=%u\n", stmt); + mylog("%s: entering...stmt=%u\n", func, stmt); - memset(primaryKey, 0, sizeof(primaryKey)); if( ! stmt) { SC_log_error(func, "", NULL); @@ -2284,6 +2233,46 @@ mylog("**** SQLForeignKeys(): ENTER, stmt=%u\n", stmt); stmt->manual_result = TRUE; stmt->errormsg_created = TRUE; + stmt->result = QR_Constructor(); + if(!stmt->result) { + stmt->errormsg = "Couldn't allocate memory for SQLForeignKeys result."; + stmt->errornumber = STMT_NO_MEMORY_ERROR; + SC_log_error(func, "", stmt); + SQLFreeStmt(htbl_stmt, SQL_DROP); + return SQL_ERROR; + } + + // the binding structure for a statement is not set up until + // a statement is actually executed, so we'll have to do this ourselves. + result_cols = 14; + extend_bindings(stmt, result_cols); + + // set the field names + QR_set_num_fields(stmt->result, result_cols); + QR_set_field_info(stmt->result, 0, "PKTABLE_QUALIFIER", PG_TYPE_TEXT, MAX_INFO_STRING); + QR_set_field_info(stmt->result, 1, "PKTABLE_OWNER", PG_TYPE_TEXT, MAX_INFO_STRING); + QR_set_field_info(stmt->result, 2, "PKTABLE_NAME", PG_TYPE_TEXT, MAX_INFO_STRING); + QR_set_field_info(stmt->result, 3, "PKCOLUMN_NAME", PG_TYPE_TEXT, MAX_INFO_STRING); + QR_set_field_info(stmt->result, 4, "FKTABLE_QUALIFIER", PG_TYPE_TEXT, MAX_INFO_STRING); + QR_set_field_info(stmt->result, 5, "FKTABLE_OWNER", PG_TYPE_TEXT, MAX_INFO_STRING); + QR_set_field_info(stmt->result, 6, "FKTABLE_NAME", PG_TYPE_TEXT, MAX_INFO_STRING); + QR_set_field_info(stmt->result, 7, "FKCOLUMN_NAME", PG_TYPE_TEXT, MAX_INFO_STRING); + QR_set_field_info(stmt->result, 8, "KEY_SEQ", PG_TYPE_INT2, 2); + QR_set_field_info(stmt->result, 9, "UPDATE_RULE", PG_TYPE_INT2, 2); + QR_set_field_info(stmt->result, 10, "DELETE_RULE", PG_TYPE_INT2, 2); + QR_set_field_info(stmt->result, 11, "FK_NAME", PG_TYPE_TEXT, MAX_INFO_STRING); + QR_set_field_info(stmt->result, 12, "PK_NAME", PG_TYPE_TEXT, MAX_INFO_STRING); + QR_set_field_info(stmt->result, 13, "TRIGGER_NAME", PG_TYPE_TEXT, MAX_INFO_STRING); + + // also, things need to think that this statement is finished so + // the results can be retrieved. + stmt->status = STMT_FINISHED; + + // set up the current tuple pointer for SQLFetch + stmt->currTuple = -1; + stmt->current_col = -1; + + result = SQLAllocStmt( stmt->hdbc, &htbl_stmt); if((result != SQL_SUCCESS) && (result != SQL_SUCCESS_WITH_INFO)) { stmt->errornumber = STMT_NO_MEMORY_ERROR; @@ -2294,212 +2283,401 @@ mylog("**** SQLForeignKeys(): ENTER, stmt=%u\n", stmt); tbl_stmt = (StatementClass *) htbl_stmt; - pktab = make_string(szPkTableName, cbPkTableName, NULL); - fktab = make_string(szFkTableName, cbFkTableName, NULL); + pktab[0] = '\0'; + fktab[0] = '\0'; + + make_string(szPkTableName, cbPkTableName, pktab); + make_string(szFkTableName, cbFkTableName, fktab); - if (pktab && fktab) { - // Get the primary key of the table listed in szPkTable - result = getPrimaryKeyArray(stmt, pktab, (SWORD) strlen(pktab), primaryKey, &pkeys); - if (result != SQL_SUCCESS && result != SQL_NO_DATA_FOUND) { - // error msg passed from above + + /* Case #2 -- Get the foreign keys in the specified table (fktab) that + refer to the primary keys of other table(s). + */ + if (fktab[0] != '\0') { + + sprintf(tables_query, "select pg_trigger.tgargs, pg_trigger.tgnargs, pg_trigger.tgname from pg_proc, pg_trigger, pg_class where pg_proc.oid = pg_trigger.tgfoid and pg_trigger.tgrelid = pg_class.oid AND pg_proc.proname = 'check_primary_key' AND pg_class.relname = '%s'", + fktab); + + result = SQLExecDirect(htbl_stmt, tables_query, strlen(tables_query)); + if((result != SQL_SUCCESS) && (result != SQL_SUCCESS_WITH_INFO)) { + stmt->errormsg = SC_create_errormsg(htbl_stmt); + stmt->errornumber = tbl_stmt->errornumber; + SC_log_error(func, "", stmt); + SQLFreeStmt(htbl_stmt, SQL_DROP); + return SQL_ERROR; + } + + result = SQLBindCol(htbl_stmt, 1, SQL_C_BINARY, + args, MAX_INFO_STRING, NULL); + if((result != SQL_SUCCESS) && (result != SQL_SUCCESS_WITH_INFO)) { + stmt->errormsg = tbl_stmt->errormsg; + stmt->errornumber = tbl_stmt->errornumber; + SC_log_error(func, "", stmt); SQLFreeStmt(htbl_stmt, SQL_DROP); - free(pktab); free(fktab); - return result; + return SQL_ERROR; } - if (pkeys == 0) { - stmt->errornumber = STMT_INFO_ONLY; - stmt->errormsg = "No primary keys for this table."; + + result = SQLBindCol(htbl_stmt, 2, SQL_C_SHORT, + &nargs, 0, NULL); + if((result != SQL_SUCCESS) && (result != SQL_SUCCESS_WITH_INFO)) { + stmt->errormsg = tbl_stmt->errormsg; + stmt->errornumber = tbl_stmt->errornumber; + SC_log_error(func, "", stmt); SQLFreeStmt(htbl_stmt, SQL_DROP); - free(pktab); free(fktab); - return SQL_SUCCESS_WITH_INFO; + return SQL_ERROR; } - sprintf(tables_query, "select relname, attnames, frelname from %s where relname='%s' AND frelname='%s'", KEYS_TABLE, fktab, pktab); - free(pktab); free(fktab); - } - else if (pktab) { - // Get the primary key of the table listed in szPkTable - result = getPrimaryKeyArray(stmt, pktab, (SWORD) strlen(pktab), primaryKey, &pkeys); - if (result != SQL_SUCCESS && result != SQL_NO_DATA_FOUND) { - // error msg passed from above + result = SQLBindCol(htbl_stmt, 3, SQL_C_CHAR, + tgname, sizeof(tgname), NULL); + if((result != SQL_SUCCESS) && (result != SQL_SUCCESS_WITH_INFO)) { + stmt->errormsg = tbl_stmt->errormsg; + stmt->errornumber = tbl_stmt->errornumber; + SC_log_error(func, "", stmt); SQLFreeStmt(htbl_stmt, SQL_DROP); - free(pktab); - return result; + return SQL_ERROR; } - if (pkeys == 0) { - stmt->errornumber = STMT_INFO_ONLY; - stmt->errormsg = "No primary keys for this table."; + + result = SQLFetch(htbl_stmt); + if (result == SQL_NO_DATA_FOUND) + return SQL_SUCCESS; + + if(result != SQL_SUCCESS) { + stmt->errormsg = SC_create_errormsg(htbl_stmt); + stmt->errornumber = tbl_stmt->errornumber; + SC_log_error(func, "", stmt); SQLFreeStmt(htbl_stmt, SQL_DROP); - free(pktab); - return SQL_SUCCESS_WITH_INFO; + return SQL_ERROR; } - sprintf(tables_query, "select relname, attnames, frelname from %s where frelname='%s'", KEYS_TABLE, pktab); - free(pktab); - } - else if (fktab) { - // This query could involve multiple calls to getPrimaryKey() - // so put that off till we know what pktables we need. - fkey = TRUE; + keyresult = SQLAllocStmt( stmt->hdbc, &hpkey_stmt); + if((keyresult != SQL_SUCCESS) && (keyresult != SQL_SUCCESS_WITH_INFO)) { + stmt->errornumber = STMT_NO_MEMORY_ERROR; + stmt->errormsg = "Couldn't allocate statement for SQLForeignKeys (pkeys) result."; + SC_log_error(func, "", stmt); + return SQL_ERROR; + } - sprintf(tables_query, "select relname, attnames, frelname from %s where relname='%s'", KEYS_TABLE, fktab); - free(fktab); - } - else { - stmt->errormsg = "No tables specified to SQLForeignKeys."; - stmt->errornumber = STMT_INTERNAL_ERROR; - SC_log_error(func, "", stmt); - SQLFreeStmt(htbl_stmt, SQL_DROP); - return SQL_ERROR; - } + keyresult = SQLBindCol(hpkey_stmt, 4, SQL_C_CHAR, + pkey, sizeof(pkey), NULL); + if (keyresult != SQL_SUCCESS) { + stmt->errornumber = STMT_NO_MEMORY_ERROR; + stmt->errormsg = "Couldn't bindcol for primary keys for SQLForeignKeys result."; + SC_log_error(func, "", stmt); + SQLFreeStmt(hpkey_stmt, SQL_DROP); + return SQL_ERROR; + } - result = SQLExecDirect(htbl_stmt, tables_query, strlen(tables_query)); - if((result != SQL_SUCCESS) && (result != SQL_SUCCESS_WITH_INFO)) { - stmt->errormsg = SC_create_errormsg(htbl_stmt); - stmt->errornumber = tbl_stmt->errornumber; - SC_log_error(func, "", stmt); - SQLFreeStmt(htbl_stmt, SQL_DROP); - return SQL_ERROR; - } + while (result == SQL_SUCCESS) { - result = SQLBindCol(htbl_stmt, 1, SQL_C_CHAR, - relname, MAX_INFO_STRING, &relname_len); - if((result != SQL_SUCCESS) && (result != SQL_SUCCESS_WITH_INFO)) { - stmt->errormsg = tbl_stmt->errormsg; - stmt->errornumber = tbl_stmt->errornumber; - SC_log_error(func, "", stmt); - SQLFreeStmt(htbl_stmt, SQL_DROP); - return SQL_ERROR; - } - result = SQLBindCol(htbl_stmt, 2, SQL_C_CHAR, - attnames, MAX_INFO_STRING, &attnames_len); - if((result != SQL_SUCCESS) && (result != SQL_SUCCESS_WITH_INFO)) { - stmt->errormsg = tbl_stmt->errormsg; - stmt->errornumber = tbl_stmt->errornumber; - SC_log_error(func, "", stmt); - SQLFreeStmt(htbl_stmt, SQL_DROP); - return SQL_ERROR; - } + /* Compute the number of keyparts. */ + pkeys = nargs / 2; - result = SQLBindCol(htbl_stmt, 3, SQL_C_CHAR, - frelname, MAX_INFO_STRING, &frelname_len); - if((result != SQL_SUCCESS) && (result != SQL_SUCCESS_WITH_INFO)) { - stmt->errormsg = tbl_stmt->errormsg; - stmt->errornumber = tbl_stmt->errornumber; - SC_log_error(func, "", stmt); - SQLFreeStmt(htbl_stmt, SQL_DROP); - return SQL_ERROR; - } + mylog("Foreign Key Case#2: nargs = %d, pkeys = %d\n", nargs, pkeys); - stmt->result = QR_Constructor(); - if(!stmt->result) { - stmt->errormsg = "Couldn't allocate memory for SQLForeignKeys result."; - stmt->errornumber = STMT_NO_MEMORY_ERROR; - SC_log_error(func, "", stmt); - SQLFreeStmt(htbl_stmt, SQL_DROP); - return SQL_ERROR; - } + ptr = args; - // the binding structure for a statement is not set up until - // a statement is actually executed, so we'll have to do this ourselves. - extend_bindings(stmt, 13); + /* Get to the PK Table Name */ + for (k = 0; k < pkeys; k++) + ptr += strlen(ptr) + 1; - // set the field names - QR_set_num_fields(stmt->result, 13); - QR_set_field_info(stmt->result, 0, "PKTABLE_QUALIFIER", PG_TYPE_TEXT, MAX_INFO_STRING); - QR_set_field_info(stmt->result, 1, "PKTABLE_OWNER", PG_TYPE_TEXT, MAX_INFO_STRING); - QR_set_field_info(stmt->result, 2, "PKTABLE_NAME", PG_TYPE_TEXT, MAX_INFO_STRING); - QR_set_field_info(stmt->result, 3, "PKCOLUMN_NAME", PG_TYPE_TEXT, MAX_INFO_STRING); - QR_set_field_info(stmt->result, 4, "FKTABLE_QUALIFIER", PG_TYPE_TEXT, MAX_INFO_STRING); - QR_set_field_info(stmt->result, 5, "FKTABLE_OWNER", PG_TYPE_TEXT, MAX_INFO_STRING); - QR_set_field_info(stmt->result, 6, "FKTABLE_NAME", PG_TYPE_TEXT, MAX_INFO_STRING); - QR_set_field_info(stmt->result, 7, "FKCOLUMN_NAME", PG_TYPE_TEXT, MAX_INFO_STRING); - QR_set_field_info(stmt->result, 8, "KEY_SEQ", PG_TYPE_INT2, 2); - QR_set_field_info(stmt->result, 9, "UPDATE_RULE", PG_TYPE_INT2, 2); - QR_set_field_info(stmt->result, 10, "DELETE_RULE", PG_TYPE_INT2, 2); - QR_set_field_info(stmt->result, 11, "FK_NAME", PG_TYPE_TEXT, MAX_INFO_STRING); - QR_set_field_info(stmt->result, 12, "PK_NAME", PG_TYPE_TEXT, MAX_INFO_STRING); + prel = ptr; - // add the tuples - result = SQLFetch(htbl_stmt); + mylog("prel = '%s'\n", prel); - while((result == SQL_SUCCESS) || (result == SQL_SUCCESS_WITH_INFO)) { + /* If there is a pk table specified, then check it. */ + if (pktab[0] != '\0') { + + /* If it doesn't match, then continue */ + if ( strcmp(prel, pktab)) { + result = SQLFetch(htbl_stmt); + continue; + } + } + + keyresult = SQLPrimaryKeys(hpkey_stmt, NULL, 0, NULL, 0, prel, SQL_NTS); + if (keyresult != SQL_SUCCESS) { + stmt->errornumber = STMT_NO_MEMORY_ERROR; + stmt->errormsg = "Couldn't get primary keys for SQLForeignKeys result."; + SC_log_error(func, "", stmt); + SQLFreeStmt(hpkey_stmt, SQL_DROP); + return SQL_ERROR; + } + + + /* Check that the key listed is the primary key */ + keyresult = SQLFetch(hpkey_stmt); + for (k = 0; k < pkeys; k++) { + + ptr += strlen(ptr) + 1; + if ( keyresult != SQL_SUCCESS || strcmp(ptr, pkey)) { + pkeys = 0; + break; + } + keyresult = SQLFetch(hpkey_stmt); + } + ptr = prel; + + + + /* Set to first fk column */ + fkptr = args; + seq = 0; + + for (k = 0; k < pkeys; k++) { + + row = (TupleNode *)malloc(sizeof(TupleNode) + (result_cols - 1) * sizeof(TupleField)); + + set_tuplefield_null(&row->tuple[0]); + set_tuplefield_string(&row->tuple[1], ""); - if (fkey == TRUE) { - result = getPrimaryKeyArray(stmt, frelname, (SWORD) strlen(frelname), primaryKey, &pkeys); + set_tuplefield_string(&row->tuple[2], prel); - // mylog(">> getPrimaryKeyArray: frelname = '%s', pkeys = %d, result = %d\n", frelname, pkeys, result); + // Get to the primary key + ptr += strlen(ptr) + 1; + + mylog("prel = '%s', ptr = '%s'\n", prel, ptr); + + set_tuplefield_string(&row->tuple[3], ptr); + set_tuplefield_null(&row->tuple[4]); + set_tuplefield_string(&row->tuple[5], ""); + + set_tuplefield_string(&row->tuple[6], fktab); + set_tuplefield_string(&row->tuple[7], fkptr); + + mylog("fktab = '%s', fkptr = '%s'\n", fktab, fkptr); + + set_tuplefield_int2(&row->tuple[8], (Int2) (++seq)); + set_tuplefield_null(&row->tuple[9]); + set_tuplefield_null(&row->tuple[10]); + set_tuplefield_null(&row->tuple[11]); + set_tuplefield_null(&row->tuple[12]); + + set_tuplefield_string(&row->tuple[13], tgname); + + QR_add_tuple(stmt->result, row); + + // next foreign key + fkptr += strlen(fkptr) + 1; - // If an error occurs or for some reason there is no primary key for a - // table that is a foreign key, then skip that one. - if ((result != SQL_SUCCESS && result != SQL_NO_DATA_FOUND) || pkeys == 0) { - result = SQLFetch(htbl_stmt); - continue; } - /* - for (i = 0; i< pkeys; i++) - mylog(">> fkey: pkeys=%d, primaryKey[%d] = '%s'\n", pkeys, i, primaryKey[i]); - mylog(">> !!!!!!!!! pkeys = %d\n", pkeys); - */ + result = SQLFetch(htbl_stmt); } + } - // mylog(">> attnames='%s'\n", attnames); + /* Case #1 -- Get the foreign keys in other tables that refer to the primary key + in the specified table (pktab). i.e., Who points to me? + */ + else if (pktab[0] != '\0') { + + sprintf(tables_query, "select pg_trigger.tgargs, pg_trigger.tgnargs, pg_trigger.tgtype, pg_trigger.tgname from pg_proc, pg_trigger, pg_class where pg_proc.oid = pg_trigger.tgfoid and pg_trigger.tgrelid = pg_class.oid AND pg_proc.proname = 'check_foreign_key' AND pg_class.relname = '%s'", + pktab); + + result = SQLExecDirect(htbl_stmt, tables_query, strlen(tables_query)); + if((result != SQL_SUCCESS) && (result != SQL_SUCCESS_WITH_INFO)) { + stmt->errormsg = SC_create_errormsg(htbl_stmt); + stmt->errornumber = tbl_stmt->errornumber; + SC_log_error(func, "", stmt); + SQLFreeStmt(htbl_stmt, SQL_DROP); + return SQL_ERROR; + } - attnamePtr = strtok(attnames, "+"); - seq = 0; + result = SQLBindCol(htbl_stmt, 1, SQL_C_BINARY, + args, sizeof(args), NULL); + if((result != SQL_SUCCESS) && (result != SQL_SUCCESS_WITH_INFO)) { + stmt->errormsg = tbl_stmt->errormsg; + stmt->errornumber = tbl_stmt->errornumber; + SC_log_error(func, "", stmt); + SQLFreeStmt(htbl_stmt, SQL_DROP); + return SQL_ERROR; + } - while (attnamePtr != NULL && seq < pkeys) { + result = SQLBindCol(htbl_stmt, 2, SQL_C_SHORT, + &nargs, 0, NULL); + if((result != SQL_SUCCESS) && (result != SQL_SUCCESS_WITH_INFO)) { + stmt->errormsg = tbl_stmt->errormsg; + stmt->errornumber = tbl_stmt->errornumber; + SC_log_error(func, "", stmt); + SQLFreeStmt(htbl_stmt, SQL_DROP); + return SQL_ERROR; + } - row = (TupleNode *)malloc(sizeof(TupleNode) + (13 - 1) * sizeof(TupleField)); + result = SQLBindCol(htbl_stmt, 3, SQL_C_SHORT, + &rule_type, 0, NULL); + if((result != SQL_SUCCESS) && (result != SQL_SUCCESS_WITH_INFO)) { + stmt->errormsg = tbl_stmt->errormsg; + stmt->errornumber = tbl_stmt->errornumber; + SC_log_error(func, "", stmt); + SQLFreeStmt(htbl_stmt, SQL_DROP); + return SQL_ERROR; + } - set_tuplefield_null(&row->tuple[0]); + result = SQLBindCol(htbl_stmt, 4, SQL_C_CHAR, + tgname, sizeof(tgname), NULL); + if((result != SQL_SUCCESS) && (result != SQL_SUCCESS_WITH_INFO)) { + stmt->errormsg = tbl_stmt->errormsg; + stmt->errornumber = tbl_stmt->errornumber; + SC_log_error(func, "", stmt); + SQLFreeStmt(htbl_stmt, SQL_DROP); + return SQL_ERROR; + } - // I have to hide the table owner from Access, otherwise it - // insists on referring to the table as 'owner.table'. - // (this is valid according to the ODBC SQL grammar, but - // Postgres won't support it.) + result = SQLFetch(htbl_stmt); + if (result == SQL_NO_DATA_FOUND) + return SQL_SUCCESS; - mylog(">> foreign keys: pktab='%s' patt='%s' fktab='%s' fatt='%s' seq=%d\n", - frelname, primaryKey[seq], relname, attnamePtr, (seq+1)); + if(result != SQL_SUCCESS) { + stmt->errormsg = SC_create_errormsg(htbl_stmt); + stmt->errornumber = tbl_stmt->errornumber; + SC_log_error(func, "", stmt); + SQLFreeStmt(htbl_stmt, SQL_DROP); + return SQL_ERROR; + } - set_tuplefield_string(&row->tuple[1], ""); - set_tuplefield_string(&row->tuple[2], frelname); - set_tuplefield_string(&row->tuple[3], primaryKey[seq]); - set_tuplefield_null(&row->tuple[4]); - set_tuplefield_string(&row->tuple[5], ""); - set_tuplefield_string(&row->tuple[6], relname); - set_tuplefield_string(&row->tuple[7], attnamePtr); - set_tuplefield_int2(&row->tuple[8], (Int2) (++seq)); - set_tuplefield_null(&row->tuple[9]); - set_tuplefield_null(&row->tuple[10]); - set_tuplefield_null(&row->tuple[11]); - set_tuplefield_null(&row->tuple[12]); + keyresult = SQLAllocStmt( stmt->hdbc, &hpkey_stmt); + if((keyresult != SQL_SUCCESS) && (keyresult != SQL_SUCCESS_WITH_INFO)) { + stmt->errornumber = STMT_NO_MEMORY_ERROR; + stmt->errormsg = "Couldn't allocate statement for SQLForeignKeys (pkeys) result."; + SC_log_error(func, "", stmt); + return SQL_ERROR; + } - QR_add_tuple(stmt->result, row); + keyresult = SQLPrimaryKeys(hpkey_stmt, NULL, 0, NULL, 0, pktab, SQL_NTS); + if (keyresult != SQL_SUCCESS) { + stmt->errornumber = STMT_NO_MEMORY_ERROR; + stmt->errormsg = "Couldn't get primary keys for SQLForeignKeys result."; + SC_log_error(func, "", stmt); + SQLFreeStmt(hpkey_stmt, SQL_DROP); + return SQL_ERROR; + } - attnamePtr = strtok(NULL, "+"); + keyresult = SQLBindCol(hpkey_stmt, 4, SQL_C_CHAR, + pkey, sizeof(pkey), NULL); + if (keyresult != SQL_SUCCESS) { + stmt->errornumber = STMT_NO_MEMORY_ERROR; + stmt->errormsg = "Couldn't bindcol for primary keys for SQLForeignKeys result."; + SC_log_error(func, "", stmt); + SQLFreeStmt(hpkey_stmt, SQL_DROP); + return SQL_ERROR; } - result = SQLFetch(htbl_stmt); - } - if(result != SQL_NO_DATA_FOUND) { - stmt->errormsg = SC_create_errormsg(htbl_stmt); - stmt->errornumber = tbl_stmt->errornumber; + while (result == SQL_SUCCESS) { + // Get the number of tables + ptr = args; + ntabs = atoi(args); + ptr += strlen(ptr) + 1; + + + // Handle action (i.e., 'cascade', 'restrict', 'setnull') + switch(tolower(ptr[0])) { + case 'c': + action = SQL_CASCADE; + break; + case 'r': + action = SQL_RESTRICT; + break; + case 's': + action = SQL_SET_NULL; + break; + default: + action = -1; + break; + } + + rule_type >>= TRIGGER_SHIFT; + ptr += strlen(ptr) + 1; + + // Calculate the number of key parts + pkeys = (nargs - ( 2 + ntabs)) / (ntabs + 1); + pkey_ptr = ptr; + + + keyresult = SQLExtendedFetch(hpkey_stmt, SQL_FETCH_FIRST, -1, NULL, NULL); + if ( keyresult != SQL_SUCCESS || strcmp(pkey, ptr)) { + ntabs = 0; + } + + // Get to the last primary keypart + for (i = 1; i < pkeys; i++) { + + // If keypart doesnt match, skip this entry + if ( keyresult != SQL_SUCCESS || strcmp(pkey, ptr)) { + ntabs = 0; + break; + } + ptr += strlen(ptr) + 1; + + keyresult = SQLExtendedFetch(hpkey_stmt, SQL_FETCH_NEXT, -1, NULL, NULL); + } + + mylog("Foreign Key Case#1: nargs = %d, ntabs = %d, pkeys = %d\n", nargs, ntabs, pkeys); + + + // Get Foreign Key Tables + for (i = 0; i < ntabs; i++) { + + seq = 0; + pkptr = pkey_ptr; + + ptr += strlen(ptr) + 1; + frel = ptr; + + for (k = 0; k < pkeys; k++) { + + row = (TupleNode *)malloc(sizeof(TupleNode) + (result_cols - 1) * sizeof(TupleField)); + + set_tuplefield_null(&row->tuple[0]); + set_tuplefield_string(&row->tuple[1], ""); + + set_tuplefield_string(&row->tuple[2], pktab); + set_tuplefield_string(&row->tuple[3], pkptr); + + mylog("pktab = '%s', pkptr = '%s'\n", pktab, pkptr); + + set_tuplefield_null(&row->tuple[4]); + set_tuplefield_string(&row->tuple[5], ""); + set_tuplefield_string(&row->tuple[6], frel); + + // Get to the foreign key + ptr += strlen(ptr) + 1; + + set_tuplefield_string(&row->tuple[7], ptr); + + mylog("frel = '%s', ptr = '%s'\n", frel, ptr); + mylog("rule_type = %d, action = %d\n", rule_type, action); + + set_tuplefield_int2(&row->tuple[8], (Int2) (++seq)); + + set_nullfield_int2(&row->tuple[9], (Int2) ((rule_type & TRIGGER_UPDATE) ? action : -1)); + set_nullfield_int2(&row->tuple[10], (Int2) ((rule_type & TRIGGER_DELETE) ? action : -1)); + + set_tuplefield_null(&row->tuple[11]); + set_tuplefield_null(&row->tuple[12]); + + set_tuplefield_string(&row->tuple[13], tgname); + + QR_add_tuple(stmt->result, row); + + // next primary key + pkptr += strlen(pkptr) + 1; + + } + + } + + result = SQLFetch(htbl_stmt); + } + } + else { + stmt->errormsg = "No tables specified to SQLForeignKeys."; + stmt->errornumber = STMT_INTERNAL_ERROR; SC_log_error(func, "", stmt); SQLFreeStmt(htbl_stmt, SQL_DROP); - return SQL_ERROR; - } + return SQL_ERROR; + } SQLFreeStmt(htbl_stmt, SQL_DROP); - - // also, things need to think that this statement is finished so - // the results can be retrieved. - stmt->status = STMT_FINISHED; - - // set up the current tuple pointer for SQLFetch - stmt->currTuple = -1; - stmt->current_col = -1; + SQLFreeStmt(hpkey_stmt, SQL_DROP); mylog("SQLForeignKeys(): EXIT, stmt=%u\n", stmt); return SQL_SUCCESS; @@ -2518,7 +2696,9 @@ RETCODE SQL_API SQLProcedureColumns( UCHAR FAR * szColumnName, SWORD cbColumnName) { -char *func="SQLProcedureColumns"; +static char *func="SQLProcedureColumns"; + + mylog("%s: entering...\n", func); SC_log_error(func, "Function not implemented", (StatementClass *) hstmt); return SQL_ERROR; @@ -2533,7 +2713,9 @@ RETCODE SQL_API SQLProcedures( UCHAR FAR * szProcName, SWORD cbProcName) { -char *func="SQLProcedures"; +static char *func="SQLProcedures"; + + mylog("%s: entering...\n", func); SC_log_error(func, "Function not implemented", (StatementClass *) hstmt); return SQL_ERROR; @@ -2548,7 +2730,9 @@ RETCODE SQL_API SQLTablePrivileges( UCHAR FAR * szTableName, SWORD cbTableName) { -char *func="SQLTablePrivileges"; +static char *func="SQLTablePrivileges"; + + mylog("%s: entering...\n", func); SC_log_error(func, "Function not implemented", (StatementClass *) hstmt); return SQL_ERROR; diff --git a/src/interfaces/odbc/install-sh b/src/interfaces/odbc/install-sh new file mode 100644 index 0000000000..ebc66913e9 --- /dev/null +++ b/src/interfaces/odbc/install-sh @@ -0,0 +1,250 @@ +#! /bin/sh +# +# install - install a program, script, or datafile +# This comes from X11R5 (mit/util/scripts/install.sh). +# +# Copyright 1991 by the Massachusetts Institute of Technology +# +# Permission to use, copy, modify, distribute, and sell this software and its +# documentation for any purpose is hereby granted without fee, provided that +# the above copyright notice appear in all copies and that both that +# copyright notice and this permission notice appear in supporting +# documentation, and that the name of M.I.T. not be used in advertising or +# publicity pertaining to distribution of the software without specific, +# written prior permission. M.I.T. makes no representations about the +# suitability of this software for any purpose. It is provided "as is" +# without express or implied warranty. +# +# Calling this script install-sh is preferred over install.sh, to prevent +# `make' implicit rules from creating a file called install from it +# when there is no Makefile. +# +# This script is compatible with the BSD install script, but was written +# from scratch. It can only install one file at a time, a restriction +# shared with many OS's install programs. + + +# set DOITPROG to echo to test this script + +# Don't use :- since 4.3BSD and earlier shells don't like it. +doit="${DOITPROG-}" + + +# put in absolute paths if you don't have them in your path; or use env. vars. + +mvprog="${MVPROG-mv}" +cpprog="${CPPROG-cp}" +chmodprog="${CHMODPROG-chmod}" +chownprog="${CHOWNPROG-chown}" +chgrpprog="${CHGRPPROG-chgrp}" +stripprog="${STRIPPROG-strip}" +rmprog="${RMPROG-rm}" +mkdirprog="${MKDIRPROG-mkdir}" + +transformbasename="" +transform_arg="" +instcmd="$mvprog" +chmodcmd="$chmodprog 0755" +chowncmd="" +chgrpcmd="" +stripcmd="" +rmcmd="$rmprog -f" +mvcmd="$mvprog" +src="" +dst="" +dir_arg="" + +while [ x"$1" != x ]; do + case $1 in + -c) instcmd="$cpprog" + shift + continue;; + + -d) dir_arg=true + shift + continue;; + + -m) chmodcmd="$chmodprog $2" + shift + shift + continue;; + + -o) chowncmd="$chownprog $2" + shift + shift + continue;; + + -g) chgrpcmd="$chgrpprog $2" + shift + shift + continue;; + + -s) stripcmd="$stripprog" + shift + continue;; + + -t=*) transformarg=`echo $1 | sed 's/-t=//'` + shift + continue;; + + -b=*) transformbasename=`echo $1 | sed 's/-b=//'` + shift + continue;; + + *) if [ x"$src" = x ] + then + src=$1 + else + # this colon is to work around a 386BSD /bin/sh bug + : + dst=$1 + fi + shift + continue;; + esac +done + +if [ x"$src" = x ] +then + echo "install: no input file specified" + exit 1 +else + true +fi + +if [ x"$dir_arg" != x ]; then + dst=$src + src="" + + if [ -d $dst ]; then + instcmd=: + else + instcmd=mkdir + fi +else + +# Waiting for this to be detected by the "$instcmd $src $dsttmp" command +# might cause directories to be created, which would be especially bad +# if $src (and thus $dsttmp) contains '*'. + + if [ -f $src -o -d $src ] + then + true + else + echo "install: $src does not exist" + exit 1 + fi + + if [ x"$dst" = x ] + then + echo "install: no destination specified" + exit 1 + else + true + fi + +# If destination is a directory, append the input filename; if your system +# does not like double slashes in filenames, you may need to add some logic + + if [ -d $dst ] + then + dst="$dst"/`basename $src` + else + true + fi +fi + +## this sed command emulates the dirname command +dstdir=`echo $dst | sed -e 's,[^/]*$,,;s,/$,,;s,^$,.,'` + +# Make sure that the destination directory exists. +# this part is taken from Noah Friedman's mkinstalldirs script + +# Skip lots of stat calls in the usual case. +if [ ! -d "$dstdir" ]; then +defaultIFS=' +' +IFS="${IFS-${defaultIFS}}" + +oIFS="${IFS}" +# Some sh's can't handle IFS=/ for some reason. +IFS='%' +set - `echo ${dstdir} | sed -e 's@/@%@g' -e 's@^%@/@'` +IFS="${oIFS}" + +pathcomp='' + +while [ $# -ne 0 ] ; do + pathcomp="${pathcomp}${1}" + shift + + if [ ! -d "${pathcomp}" ] ; + then + $mkdirprog "${pathcomp}" + else + true + fi + + pathcomp="${pathcomp}/" +done +fi + +if [ x"$dir_arg" != x ] +then + $doit $instcmd $dst && + + if [ x"$chowncmd" != x ]; then $doit $chowncmd $dst; else true ; fi && + if [ x"$chgrpcmd" != x ]; then $doit $chgrpcmd $dst; else true ; fi && + if [ x"$stripcmd" != x ]; then $doit $stripcmd $dst; else true ; fi && + if [ x"$chmodcmd" != x ]; then $doit $chmodcmd $dst; else true ; fi +else + +# If we're going to rename the final executable, determine the name now. + + if [ x"$transformarg" = x ] + then + dstfile=`basename $dst` + else + dstfile=`basename $dst $transformbasename | + sed $transformarg`$transformbasename + fi + +# don't allow the sed command to completely eliminate the filename + + if [ x"$dstfile" = x ] + then + dstfile=`basename $dst` + else + true + fi + +# Make a temp file name in the proper directory. + + dsttmp=$dstdir/#inst.$$# + +# Move or copy the file name to the temp name + + $doit $instcmd $src $dsttmp && + + trap "rm -f ${dsttmp}" 0 && + +# and set any options; do chmod last to preserve setuid bits + +# If any of these fail, we abort the whole thing. If we want to +# ignore errors from any of these, just make sure not to ignore +# errors from the above "$doit $instcmd $src $dsttmp" command. + + if [ x"$chowncmd" != x ]; then $doit $chowncmd $dsttmp; else true;fi && + if [ x"$chgrpcmd" != x ]; then $doit $chgrpcmd $dsttmp; else true;fi && + if [ x"$stripcmd" != x ]; then $doit $stripcmd $dsttmp; else true;fi && + if [ x"$chmodcmd" != x ]; then $doit $chmodcmd $dsttmp; else true;fi && + +# Now rename the file to the real destination. + + $doit $rmcmd -f $dstdir/$dstfile && + $doit $mvcmd $dsttmp $dstdir/$dstfile + +fi && + + +exit 0 diff --git a/src/interfaces/odbc/iodbc.h b/src/interfaces/odbc/iodbc.h index cf0c1a9886..ab6a6015ad 100644 --- a/src/interfaces/odbc/iodbc.h +++ b/src/interfaces/odbc/iodbc.h @@ -1,7 +1,7 @@ #ifndef _IODBC_H #define _IODBC_H -# if !defined(WINDOWS) && !defined(WIN32_SYSTEM) +# if !defined(WIN32) && !defined(WIN32_SYSTEM) # define _UNIX_ # include @@ -32,7 +32,7 @@ # endif /* _UNIX_ */ -# if defined(WINDOWS) || defined(WIN32_SYSTEM) +# if defined(WIN32) || defined(WIN32_SYSTEM) # include # include @@ -55,7 +55,7 @@ # define STREQ(a, b) (_fstrcmp((char FAR*)(a), (char FAR*)(b) == 0) # endif -# endif /* WINDOWS */ +# endif /* WIN32 */ # define SYSERR (-1) diff --git a/src/interfaces/odbc/misc.c b/src/interfaces/odbc/misc.c index 68bb7ae63b..7e1501842c 100644 --- a/src/interfaces/odbc/misc.c +++ b/src/interfaces/odbc/misc.c @@ -14,12 +14,45 @@ #include #include +#include #include "psqlodbc.h" +#ifndef WIN32 +#if HAVE_PWD_H +#include +#endif +#include +#include +#else +#include /* Byron: is this where Windows keeps def. of getpid ? */ +#endif extern GLOBAL_VALUES globals; +void generate_filename(char*,char*,char*); +void +generate_filename(char* dirname,char* prefix,char* filename) +{ + int pid = 0; +#ifndef WIN32 + struct passwd *ptr = 0; + ptr = getpwuid(getuid()); +#endif + pid = getpid(); + if(dirname == 0 || filename == 0) + return; + + strcpy(filename,dirname); + strcat(filename,DIRSEPERATOR); + if(prefix != 0) + strcat(filename,prefix); +#ifndef WIN32 + strcat(filename,ptr->pw_name); +#endif + sprintf(filename,"%s%d%s",filename,pid,".log"); + return; +} #ifdef MY_LOG @@ -29,15 +62,17 @@ va_dcl { char *fmt; char *args; - -static FILE *LOGFP = 0; +char filebuf[80]; + FILE* LOGFP = globals.mylogFP; if ( globals.debug) { va_start(args); fmt = va_arg(args, char *); if (! LOGFP) { - LOGFP = fopen(MYLOGFILE, "w"); + generate_filename(MYLOGDIR,MYLOGFILE,filebuf); + LOGFP = fopen(filebuf, "w"); + globals.mylogFP = LOGFP; setbuf(LOGFP, NULL); } @@ -57,14 +92,18 @@ va_dcl { char *fmt; char *args; -static FILE *LOGFP = 0; +char filebuf[80]; +FILE* LOGFP = globals.qlogFP; if ( globals.commlog) { va_start(args); fmt = va_arg(args, char *); + if (! LOGFP) { - LOGFP = fopen(QLOGFILE, "w"); + generate_filename(QLOGDIR,QLOGFILE,filebuf); + LOGFP = fopen(filebuf, "w"); + globals.qlogFP = LOGFP; setbuf(LOGFP, NULL); } @@ -79,15 +118,15 @@ static FILE *LOGFP = 0; /* Undefine these because windows.h will redefine and cause a warning */ #ifdef HAVE_CONFIG_H -#include +#include "config.h" #endif -#ifndef UNIX +#ifdef WIN32 #undef va_start #undef va_end #endif -#ifdef HAVE_IODBC +#ifndef WIN32 #include "iodbc.h" #include "isql.h" #else diff --git a/src/interfaces/odbc/misc.h b/src/interfaces/odbc/misc.h index 584562fb08..3e17e1362a 100644 --- a/src/interfaces/odbc/misc.h +++ b/src/interfaces/odbc/misc.h @@ -11,10 +11,10 @@ #define __MISC_H__ #ifdef HAVE_CONFIG_H -#include +#include "config.h" #endif -#ifdef UNIX +#ifndef WIN32 #include "gpps.h" #define SQLGetPrivateProfileString(a,b,c,d,e,f) GetPrivateProfileString(a,b,c,d,e,f) #endif @@ -26,7 +26,7 @@ portion of the registry. You may have to manually add this key. This logfile is intended for development use, not for an end user! */ -// #define MY_LOG +#define MY_LOG /* Uncomment Q_LOG to compile in the qlog() statements (Communications log, i.e. CommLog). @@ -39,10 +39,11 @@ #ifdef MY_LOG -#ifdef UNIX -#define MYLOGFILE "/tmp/mylog.log" +#define MYLOGFILE "mylog_" +#ifndef WIN32 +#define MYLOGDIR "/tmp" #else -#define MYLOGFILE "c:\\mylog.log" +#define MYLOGDIR "c:" #endif void mylog(); /* prototype */ #else @@ -50,16 +51,23 @@ void mylog(); /* prototype */ #endif #ifdef Q_LOG -#ifdef UNIX -#define QLOGFILE "/tmp/psqlodbc.log" +#define QLOGFILE "psqlodbc_" +#ifndef WIN32 +#define QLOGDIR "/tmp" #else -#define QLOGFILE "c:\\psqlodbc.log" +#define QLOGDIR "c:" #endif void qlog(); /* prototype */ #else #define qlog // qlog #endif +#ifndef WIN32 +#define DIRSEPERATOR "/" +#else +#define DIRSEPERATOR "\\" +#endif + void remove_newlines(char *string); char *strncpy_null(char *dst, const char *src, int len); char *trim(char *string); diff --git a/src/interfaces/odbc/options.c b/src/interfaces/odbc/options.c index 9f498eac49..ec65364284 100644 --- a/src/interfaces/odbc/options.c +++ b/src/interfaces/odbc/options.c @@ -14,12 +14,12 @@ */ #ifdef HAVE_CONFIG_H -#include +#include "config.h" #endif #include "psqlodbc.h" -#ifdef HAVE_IODBC +#ifndef WIN32 #include "iodbc.h" #include "isql.h" #include "isqlext.h" @@ -43,9 +43,11 @@ RETCODE SQL_API SQLSetConnectOption( UWORD fOption, UDWORD vParam) { -char *func="SQLSetConnectOption"; +static char *func="SQLSetConnectOption"; ConnectionClass *conn = (ConnectionClass *) hdbc; + mylog("%s: entering...\n", func); + if ( ! conn) { CC_log_error(func, "", NULL); return SQL_INVALID_HANDLE; @@ -101,7 +103,7 @@ ConnectionClass *conn = (ConnectionClass *) hdbc; char option[64]; conn->errormsg = "Driver does not support setting this connect option"; conn->errornumber = CONN_UNSUPPORTED_OPTION; - sprintf(option, "fOption=%d, vParam=%d", fOption, vParam); + sprintf(option, "fOption=%d, vParam=%ld", fOption, vParam); CC_log_error(func, option, conn); return SQL_ERROR; } @@ -118,9 +120,11 @@ RETCODE SQL_API SQLGetConnectOption( UWORD fOption, PTR pvParam) { -char *func="SQLGetConnectOption"; +static char *func="SQLGetConnectOption"; ConnectionClass *conn = (ConnectionClass *) hdbc; + mylog("%s: entering...\n", func); + if (! conn) { CC_log_error(func, "", NULL); return SQL_INVALID_HANDLE; @@ -162,10 +166,12 @@ RETCODE SQL_API SQLSetStmtOption( UWORD fOption, UDWORD vParam) { -char *func="SQLSetStmtOption"; +static char *func="SQLSetStmtOption"; StatementClass *stmt = (StatementClass *) hstmt; char changed = FALSE; + mylog("%s: entering...\n", func); + // thought we could fake Access out by just returning SQL_SUCCESS // all the time, but it tries to set a huge value for SQL_MAX_LENGTH // and expects the driver to reduce it to the real value @@ -260,7 +266,7 @@ char changed = FALSE; char option[64]; stmt->errornumber = STMT_NOT_IMPLEMENTED_ERROR; stmt->errormsg = "Driver does not support setting this statement option"; - sprintf(option, "fOption=%d, vParam=%d", fOption, vParam); + sprintf(option, "fOption=%d, vParam=%ld", fOption, vParam); SC_log_error(func, option, stmt); return SQL_ERROR; } @@ -283,9 +289,11 @@ RETCODE SQL_API SQLGetStmtOption( UWORD fOption, PTR pvParam) { -char *func="SQLGetStmtOption"; +static char *func="SQLGetStmtOption"; StatementClass *stmt = (StatementClass *) hstmt; + mylog("%s: entering...\n", func); + // thought we could fake Access out by just returning SQL_SUCCESS // all the time, but it tries to set a huge value for SQL_MAX_LENGTH // and expects the driver to reduce it to the real value diff --git a/src/interfaces/odbc/parse.c b/src/interfaces/odbc/parse.c index 0a6382a493..78abaf30f0 100644 --- a/src/interfaces/odbc/parse.c +++ b/src/interfaces/odbc/parse.c @@ -20,14 +20,15 @@ #include #include +#include #include "statement.h" #include "connection.h" #include "qresult.h" #include "pgtypes.h" -#ifdef UNIX -#if !HAVE_STRICMP +#ifndef WIN32 +#ifndef HAVE_STRICMP #define stricmp(s1,s2) strcasecmp(s1,s2) #define strnicmp(s1,s2,n) strncasecmp(s1,s2,n) #endif @@ -37,6 +38,10 @@ #define TAB_INCR 8 #define COL_INCR 16 +char *getNextToken(char *s, char *token, int smax, char *delim, char *quote, char *dquote, char *numeric); +void getColInfo(COL_INFO *col_info, FIELD_INFO *fi, int k); +char searchColInfo(COL_INFO *col_info, FIELD_INFO *fi); + char * getNextToken(char *s, char *token, int smax, char *delim, char *quote, char *dquote, char *numeric) { @@ -106,7 +111,9 @@ char qc, in_escape = FALSE; break; } - if ( ispunct(s[i])) { + if ( ispunct(s[i]) && s[i] != '_') { + mylog("got ispunct: s[%d] = '%c'\n", i, s[i]); + if (out == 0) { token[out++] = s[i++]; break; @@ -205,12 +212,13 @@ char *col; char parse_statement(StatementClass *stmt) { +static char *func="parse_statement"; char token[256]; char delim, quote, dquote, numeric, unquoted; char *ptr; char in_select = FALSE, in_distinct = FALSE, in_on = FALSE, in_from = FALSE, in_where = FALSE, in_table = FALSE; char in_field = FALSE, in_expr = FALSE, in_func = FALSE, in_dot = FALSE, in_as = FALSE; -int j, i, k, n, blevel = 0; +int j, i, k = 0, n, blevel = 0; FIELD_INFO **fi; TABLE_INFO **ti; char parse; @@ -220,6 +228,8 @@ StatementClass *col_stmt; RETCODE result; + mylog("%s: entering...\n", func); + ptr = stmt->statement; fi = stmt->fi; ti = stmt->ti; @@ -227,7 +237,7 @@ RETCODE result; stmt->nfld = 0; stmt->ntab = 0; - while (ptr = getNextToken(ptr, token, sizeof(token), &delim, "e, &dquote, &numeric)) { + while ((ptr = getNextToken(ptr, token, sizeof(token), &delim, "e, &dquote, &numeric)) != NULL) { unquoted = ! ( quote || dquote ); diff --git a/src/interfaces/odbc/pgtypes.c b/src/interfaces/odbc/pgtypes.c index dae519a804..24ef584374 100644 --- a/src/interfaces/odbc/pgtypes.c +++ b/src/interfaces/odbc/pgtypes.c @@ -16,7 +16,7 @@ */ #ifdef HAVE_CONFIG_H -#include +#include "config.h" #endif #include "psqlodbc.h" @@ -26,7 +26,7 @@ #include "connection.h" #include "qresult.h" -#ifdef HAVE_IODBC +#ifndef WIN32 #include "iodbc.h" #include "isql.h" #include "isqlext.h" @@ -39,6 +39,8 @@ extern GLOBAL_VALUES globals; +Int4 getCharPrecision(StatementClass *stmt, Int4 type, int col, int handle_unknown_size_as); + /* these are the types we support. all of the pgtype_ functions should */ /* return values for each one of these. */ diff --git a/src/interfaces/odbc/psqlodbc.c b/src/interfaces/odbc/psqlodbc.c index db9a6cdc2f..5a3527c759 100644 --- a/src/interfaces/odbc/psqlodbc.c +++ b/src/interfaces/odbc/psqlodbc.c @@ -14,13 +14,13 @@ */ #ifdef HAVE_CONFIG_H -#include +#include "config.h" #endif #include "psqlodbc.h" #include "dlg_specific.h" -#ifdef HAVE_IODBC +#ifndef WIN32 #include "iodbc.h" #include "isql.h" #include "isqlext.h" @@ -33,7 +33,11 @@ GLOBAL_VALUES globals; -#ifndef UNIX /* again find a WINDOWS #ifdef */ +BOOL _init(void); +BOOL _fini(void); +RETCODE SQL_API SQLDummyOrdinal(void); + +#ifdef WIN32 HINSTANCE NEAR s_hModule; /* Saved module handle. */ /* This is where the Driver Manager attaches to this Driver */ @@ -60,7 +64,7 @@ WSADATA wsaData; return FALSE; } - getGlobalDefaults(); + getGlobalDefaults(DBMS_NAME, ODBCINST_INI, FALSE); break; case DLL_THREAD_ATTACH: @@ -84,7 +88,7 @@ WSADATA wsaData; UNREFERENCED_PARAMETER(lpReserved); } -#else /* UNIX */ +#else /* WIN32 */ #ifndef TRUE #define TRUE (BOOL)1 @@ -99,7 +103,7 @@ WSADATA wsaData; BOOL _init(void) { - getGlobalDefaults(); + getGlobalDefaults(DBMS_NAME, ODBCINST_INI, FALSE); return TRUE; } diff --git a/src/interfaces/odbc/psqlodbc.h b/src/interfaces/odbc/psqlodbc.h index aa32c779c5..05b3ee3018 100644 --- a/src/interfaces/odbc/psqlodbc.h +++ b/src/interfaces/odbc/psqlodbc.h @@ -12,10 +12,12 @@ #define __PSQLODBC_H__ #ifdef HAVE_CONFIG_H -#include +#include "config.h" #endif -#ifdef UNIX +#include /* for FILE* pointers: see GLOBAL_VALUES */ + +#ifndef WIN32 #define Int4 long int #define UInt4 unsigned int #define Int2 short @@ -67,10 +69,10 @@ typedef UInt4 Oid; /* Driver stuff */ #define DRIVERNAME "PostgreSQL ODBC" #define DBMS_NAME "PostgreSQL" -#define DBMS_VERSION "06.30.0248 PostgreSQL 6.3" -#define POSTGRESDRIVERVERSION "06.30.0248" +#define DBMS_VERSION "06.30.0250 PostgreSQL 6.3" +#define POSTGRESDRIVERVERSION "06.30.0250" -#ifndef UNIX +#ifdef WIN32 #define DRIVER_FILE_NAME "PSQLODBC.DLL" #else #define DRIVER_FILE_NAME "libpsqlodbc.so" @@ -114,6 +116,8 @@ typedef struct GlobalValues_ char parse; char extra_systable_prefixes[MEDIUM_REGISTRY_LEN]; char conn_settings[LARGE_REGISTRY_LEN]; + FILE* mylogFP; + FILE* qlogFP; } GLOBAL_VALUES; @@ -127,7 +131,6 @@ typedef struct GlobalValues_ #define MAX_VARCHAR_SIZE 254 /* maximum size of a varchar (not including null term) */ - #include "misc.h" #endif diff --git a/src/interfaces/odbc/psqlodbc.rc b/src/interfaces/odbc/psqlodbc.rc index e59af92a33..3e6cafded4 100644 --- a/src/interfaces/odbc/psqlodbc.rc +++ b/src/interfaces/odbc/psqlodbc.rc @@ -203,8 +203,8 @@ END // VS_VERSION_INFO VERSIONINFO - FILEVERSION 6,30,2,48 - PRODUCTVERSION 6,30,2,48 + FILEVERSION 6,30,2,50 + PRODUCTVERSION 6,30,2,50 FILEFLAGSMASK 0x3L #ifdef _DEBUG FILEFLAGS 0x1L @@ -222,12 +222,12 @@ BEGIN VALUE "Comments", "PostgreSQL ODBC driver for Windows 95\0" VALUE "CompanyName", "Insight Distribution Systems\0" VALUE "FileDescription", "PostgreSQL Driver\0" - VALUE "FileVersion", " 6.30.0248\0" + VALUE "FileVersion", " 6.30.0250\0" VALUE "InternalName", "psqlodbc\0" VALUE "LegalTrademarks", "ODBC(TM) is a trademark of Microsoft Corporation. Microsoft® is a registered trademark of Microsoft Corporation. Windows(TM) is a trademark of Microsoft Corporation.\0" VALUE "OriginalFilename", "psqlodbc.dll\0" VALUE "ProductName", "Microsoft Open Database Connectivity\0" - VALUE "ProductVersion", " 6.30.0248\0" + VALUE "ProductVersion", " 6.30.0250\0" END END BLOCK "VarFileInfo" diff --git a/src/interfaces/odbc/qresult.c b/src/interfaces/odbc/qresult.c index 3a8f002dc2..714063516e 100644 --- a/src/interfaces/odbc/qresult.c +++ b/src/interfaces/odbc/qresult.c @@ -501,7 +501,7 @@ ColumnInfoClass *flds; SOCK_get_n_char(sock, buffer, len); buffer[len] = '\0'; - // mylog("qresult: len=%d, buffer='%s'\n", len, buffer); + mylog("qresult: len=%d, buffer='%s'\n", len, buffer); this_tuplefield[field_lf].len = len; this_tuplefield[field_lf].value = buffer; diff --git a/src/interfaces/odbc/qresult.h b/src/interfaces/odbc/qresult.h index 132a398326..f05830d6d4 100644 --- a/src/interfaces/odbc/qresult.h +++ b/src/interfaces/odbc/qresult.h @@ -65,8 +65,7 @@ struct QResultClass_ { /* These functions are for retrieving data from the qresult */ #define QR_get_value_manual(self, tupleno, fieldno) (TL_get_fieldval(self->manual_tuples, tupleno, fieldno)) #define QR_get_value_backend(self, fieldno) (self->tupleField[fieldno].value) -#define QR_get_value_backend_row(self, tupleno, fieldno) \ - ((self->backend_tuples + (tupleno * self->num_fields))[fieldno].value) +#define QR_get_value_backend_row(self, tupleno, fieldno) ((self->backend_tuples + (tupleno * self->num_fields))[fieldno].value) /* These functions are used by both manual and backend results */ #define QR_NumResultCols(self) (CI_get_num_fields(self->fields)) @@ -93,7 +92,7 @@ struct QResultClass_ { #define QR_get_status(self) (self->status) // Core Functions -QResultClass *QR_Constructor(); +QResultClass *QR_Constructor(void); void QR_Destructor(QResultClass *self); char QR_read_tuple(QResultClass *self, char binary); int QR_next_tuple(QResultClass *self); diff --git a/src/interfaces/odbc/readme.txt b/src/interfaces/odbc/readme.txt index 377bb28bf0..e9a0553c05 100644 --- a/src/interfaces/odbc/readme.txt +++ b/src/interfaces/odbc/readme.txt @@ -70,3 +70,26 @@ But for now, it sure is fun to stick a Word document, Visio document, or avi of baby into a database column, even if you will fill up your server's hard disk after a while! + +III. Using Row Versioning feature and creating the missing equals operator + +In order to use row versioning, you must overload the int4eq function for use +with the xid type. Also, you need to create an operator to compare xid to int4. +You must do this for each database you want to use this feature on. +Here are the details: + +create function int4eq(xid,int4) + returns bool + as '' + language 'internal'; + +create operator = ( + leftarg=xid, + rightarg=int4, + procedure=int4eq, + commutator='=', + negator='<>', + restrict=eqsel, + join=eqjoinsel + ); + diff --git a/src/interfaces/odbc/results.c b/src/interfaces/odbc/results.c index 1f7418df1e..5d9dfc30fb 100644 --- a/src/interfaces/odbc/results.c +++ b/src/interfaces/odbc/results.c @@ -16,7 +16,7 @@ */ #ifdef HAVE_CONFIG_H -#include +#include "config.h" #endif #include @@ -32,7 +32,7 @@ #include -#ifdef HAVE_IODBC +#ifndef WIN32 #include "iodbc.h" #include "isqlext.h" #else @@ -42,28 +42,13 @@ extern GLOBAL_VALUES globals; -RETCODE SQL_API SQLFetch(HSTMT hstmt) -{ - return _SQLFetch(hstmt); -} - -RETCODE SQL_API SQLGetData( - HSTMT hstmt, - UWORD icol, - SWORD fCType, - PTR rgbValue, - SDWORD cbValueMax, - SDWORD FAR *pcbValue) -{ - return _SQLGetData(hstmt, icol, fCType, rgbValue, cbValueMax, pcbValue); -} RETCODE SQL_API SQLRowCount( HSTMT hstmt, SDWORD FAR *pcrow) { -char *func="SQLRowCount"; +static char *func="SQLRowCount"; StatementClass *stmt = (StatementClass *) hstmt; QResultClass *res; char *msg, *ptr; @@ -117,7 +102,7 @@ RETCODE SQL_API SQLNumResultCols( HSTMT hstmt, SWORD FAR *pccol) { -char *func="SQLNumResultCols"; +static char *func="SQLNumResultCols"; StatementClass *stmt = (StatementClass *) hstmt; QResultClass *result; char parse_ok; @@ -182,16 +167,18 @@ RETCODE SQL_API SQLDescribeCol( SWORD FAR *pibScale, SWORD FAR *pfNullable) { -char *func="SQLDescribeCol"; +static char *func="SQLDescribeCol"; /* gets all the information about a specific column */ StatementClass *stmt = (StatementClass *) hstmt; QResultClass *result; -char *col_name; -Int4 fieldtype; -int precision; +char *col_name = NULL; +Int4 fieldtype = 0; +int precision = 0; ConnInfo *ci; char parse_ok; + mylog("%s: entering...\n", func); + if ( ! stmt) { SC_log_error(func, "", NULL); return SQL_INVALID_HANDLE; @@ -201,13 +188,9 @@ char parse_ok; SC_clear_error(stmt); - if(icol < 1) { - // we do not support bookmarks - stmt->errormsg = "Bookmarks are not currently supported."; - stmt->errornumber = STMT_NOT_IMPLEMENTED_ERROR; - SC_log_error(func, "", stmt); - return SQL_ERROR; - } + /* Dont check for bookmark column. This is the responsibility + of the driver manager. + */ icol--; /* use zero based column numbers */ @@ -342,15 +325,16 @@ RETCODE SQL_API SQLColAttributes( SWORD FAR *pcbDesc, SDWORD FAR *pfDesc) { -char *func = "SQLColAttributes"; +static char *func = "SQLColAttributes"; StatementClass *stmt = (StatementClass *) hstmt; char *value; -Int4 field_type; +Int4 field_type = 0; ConnInfo *ci; int unknown_sizes; -int cols; +int cols = 0; char parse_ok; + mylog("%s: entering...\n", func); if( ! stmt) { SC_log_error(func, "", NULL); @@ -359,13 +343,10 @@ char parse_ok; ci = &(stmt->hdbc->connInfo); - if(icol < 1) { - // we do not support bookmarks - stmt->errormsg = "Bookmarks are not currently supported."; - stmt->errornumber = STMT_NOT_IMPLEMENTED_ERROR; - SC_log_error(func, "", stmt); - return SQL_ERROR; - } + /* Dont check for bookmark column. This is the responsibility + of the driver manager. For certain types of arguments, the column + number is ignored anyway, so it may be 0. + */ icol--; @@ -383,6 +364,16 @@ char parse_ok; cols = stmt->nfld; + /* Column Count is a special case. The Column number is ignored + in this case. + */ + if (fDescType == SQL_COLUMN_COUNT) { + if (pfDesc) + *pfDesc = cols; + + return SQL_SUCCESS; + } + if (stmt->parse_status != STMT_PARSE_FATAL && stmt->fi && stmt->fi[icol]) { if (icol >= cols) { @@ -411,6 +402,17 @@ char parse_ok; } cols = QR_NumResultCols(stmt->result); + + /* Column Count is a special case. The Column number is ignored + in this case. + */ + if (fDescType == SQL_COLUMN_COUNT) { + if (pfDesc) + *pfDesc = cols; + + return SQL_SUCCESS; + } + if (icol >= cols) { stmt->errornumber = STMT_INVALID_COLUMN_NUMBER_ERROR; stmt->errormsg = "Invalid column number in DescribeCol."; @@ -438,10 +440,10 @@ char parse_ok; *pfDesc = pgtype_case_sensitive(stmt, field_type); break; - case SQL_COLUMN_COUNT: - if (pfDesc) - *pfDesc = cols; - break; + /* This special case is handled above. + + case SQL_COLUMN_COUNT: + */ case SQL_COLUMN_DISPLAY_SIZE: if (pfDesc) { @@ -593,7 +595,7 @@ char parse_ok; // Returns result data for a single column in the current row. -RETCODE SQL_API _SQLGetData( +RETCODE SQL_API SQLGetData( HSTMT hstmt, UWORD icol, SWORD fCType, @@ -601,7 +603,7 @@ RETCODE SQL_API _SQLGetData( SDWORD cbValueMax, SDWORD FAR *pcbValue) { -char *func="SQLGetData"; +static char *func="SQLGetData"; QResultClass *res; StatementClass *stmt = (StatementClass *) hstmt; int num_cols, num_rows; @@ -737,10 +739,10 @@ mylog("SQLGetData: enter, stmt=%u\n", stmt); // Returns data for bound columns in the current row ("hstmt->iCursor"), // advances the cursor. -RETCODE SQL_API _SQLFetch( +RETCODE SQL_API SQLFetch( HSTMT hstmt) { -char *func = "SQLFetch"; +static char *func = "SQLFetch"; StatementClass *stmt = (StatementClass *) hstmt; QResultClass *res; int retval; @@ -750,6 +752,8 @@ char *value; ColumnInfoClass *ci; // TupleField *tupleField; +mylog("SQLFetch: stmt = %u, stmt->result= %u\n", stmt, stmt->result); + if ( ! stmt) { SC_log_error(func, "", NULL); return SQL_INVALID_HANDLE; @@ -790,8 +794,7 @@ ColumnInfoClass *ci; return SQL_ERROR; } - mylog("manual_result = %d, use_declarefetch = %d\n", - stmt->manual_result, globals.use_declarefetch); + mylog("manual_result = %d, use_declarefetch = %d\n", stmt->manual_result, globals.use_declarefetch); if ( stmt->manual_result || ! globals.use_declarefetch) { @@ -832,8 +835,7 @@ ColumnInfoClass *ci; for (lf=0; lf < num_cols; lf++) { - mylog("fetch: cols=%d, lf=%d, stmt = %u, stmt->bindings = %u, buffer[] = %u\n", - num_cols, lf, stmt, stmt->bindings, stmt->bindings[lf].buffer); + mylog("fetch: cols=%d, lf=%d, stmt = %u, stmt->bindings = %u, buffer[] = %u\n", num_cols, lf, stmt, stmt->bindings, stmt->bindings[lf].buffer); if (stmt->bindings[lf].buffer != NULL) { // this column has a binding @@ -843,8 +845,10 @@ ColumnInfoClass *ci; mylog("type = %d\n", type); - if (stmt->manual_result) + if (stmt->manual_result) { value = QR_get_value_manual(res, stmt->currTuple, lf); + mylog("manual_result\n"); + } else if (globals.use_declarefetch) value = QR_get_value_backend(res, lf); else { @@ -857,32 +861,41 @@ ColumnInfoClass *ci; mylog("copy_and_convert: retval = %d\n", retval); - // check whether the complete result was copied - if(retval == COPY_UNSUPPORTED_TYPE) { + + switch(retval) { + case COPY_OK: + break; /* OK, do next bound column */ + + case COPY_UNSUPPORTED_TYPE: stmt->errormsg = "Received an unsupported type from Postgres."; stmt->errornumber = STMT_RESTRICTED_DATA_TYPE_ERROR; SC_log_error(func, "", stmt); return SQL_ERROR; - } else if(retval == COPY_UNSUPPORTED_CONVERSION) { + case COPY_UNSUPPORTED_CONVERSION: stmt->errormsg = "Couldn't handle the necessary data type conversion."; stmt->errornumber = STMT_RESTRICTED_DATA_TYPE_ERROR; SC_log_error(func, "", stmt); return SQL_ERROR; - } else if(retval == COPY_RESULT_TRUNCATED) { - /* The result has been truncated during the copy */ - /* this will generate a SQL_SUCCESS_WITH_INFO result */ + case COPY_RESULT_TRUNCATED: stmt->errornumber = STMT_TRUNCATED; - stmt->errormsg = "A buffer was too small for the return value to fit in"; + stmt->errormsg = "The buffer was too small for the result."; return SQL_SUCCESS_WITH_INFO; - } else if(retval != COPY_OK) { + case COPY_GENERAL_ERROR: /* error msg already filled in */ + SC_log_error(func, "", stmt); + return SQL_ERROR; + + case COPY_NO_DATA_FOUND: + SC_log_error(func, "no data found", stmt); + return SQL_NO_DATA_FOUND; + + default: stmt->errormsg = "Unrecognized return value from copy_and_convert_field."; stmt->errornumber = STMT_INTERNAL_ERROR; SC_log_error(func, "", stmt); return SQL_ERROR; - } } } @@ -899,7 +912,7 @@ RETCODE SQL_API SQLExtendedFetch( UDWORD FAR *pcrow, UWORD FAR *rgfRowStatus) { -char *func = "SQLExtendedFetch"; +static char *func = "SQLExtendedFetch"; StatementClass *stmt = (StatementClass *) hstmt; int num_tuples; RETCODE result; @@ -1009,7 +1022,7 @@ RETCODE SQL_API SQLSetPos( UWORD fOption, UWORD fLock) { -char *func = "SQLSetPos"; +static char *func = "SQLSetPos"; char buf[128]; sprintf(buf, "SQLSetPos not implemented: irow=%d, fOption=%d, fLock=%d\n", irow, fOption, fLock); @@ -1026,7 +1039,7 @@ RETCODE SQL_API SQLSetScrollOptions( SDWORD crowKeyset, UWORD crowRowset) { -char *func = "SQLSetScrollOptions"; +static char *func = "SQLSetScrollOptions"; SC_log_error(func, "Function not implemented", (StatementClass *) hstmt); return SQL_ERROR; @@ -1040,12 +1053,11 @@ RETCODE SQL_API SQLSetCursorName( UCHAR FAR *szCursor, SWORD cbCursor) { -char *func="SQLSetCursorName"; +static char *func="SQLSetCursorName"; StatementClass *stmt = (StatementClass *) hstmt; int len; -mylog("SQLSetCursorName: hstmt=%u, szCursor=%u, cbCursorMax=%d\n", - hstmt, szCursor, cbCursor); +mylog("SQLSetCursorName: hstmt=%u, szCursor=%u, cbCursorMax=%d\n", hstmt, szCursor, cbCursor); if ( ! stmt) { SC_log_error(func, "", NULL); @@ -1072,11 +1084,10 @@ RETCODE SQL_API SQLGetCursorName( SWORD cbCursorMax, SWORD FAR *pcbCursor) { -char *func="SQLGetCursorName"; +static char *func="SQLGetCursorName"; StatementClass *stmt = (StatementClass *) hstmt; -mylog("SQLGetCursorName: hstmt=%u, szCursor=%u, cbCursorMax=%d, pcbCursor=%u\n", - hstmt, szCursor, cbCursorMax, pcbCursor); +mylog("SQLGetCursorName: hstmt=%u, szCursor=%u, cbCursorMax=%d, pcbCursor=%u\n", hstmt, szCursor, cbCursorMax, pcbCursor); if ( ! stmt) { SC_log_error(func, "", NULL); diff --git a/src/interfaces/odbc/socket.c b/src/interfaces/odbc/socket.c index 080989b6f0..32114ffc6d 100644 --- a/src/interfaces/odbc/socket.c +++ b/src/interfaces/odbc/socket.c @@ -13,16 +13,13 @@ */ #ifdef HAVE_CONFIG_H -#include +#include "config.h" #endif #include "socket.h" -#ifdef UNIX +#ifndef WIN32 #include -#include -#include -#include #include /* for memset */ #endif diff --git a/src/interfaces/odbc/socket.h b/src/interfaces/odbc/socket.h index a3dfb3e9e3..d57d012a48 100644 --- a/src/interfaces/odbc/socket.h +++ b/src/interfaces/odbc/socket.h @@ -11,15 +11,16 @@ #define __SOCKET_H__ #ifdef HAVE_CONFIG_H -#include +#include "config.h" #endif -#ifdef UNIX +#ifndef WIN32 #include #include #include #include #include +#include #define closesocket(xxx) close(xxx) #define SOCKETFD int #else @@ -68,7 +69,7 @@ struct SocketClass_ { /* Socket prototypes */ -SocketClass *SOCK_Constructor(); +SocketClass *SOCK_Constructor(void); void SOCK_Destructor(SocketClass *self); char SOCK_connect_to(SocketClass *self, unsigned short port, char *hostname); void SOCK_get_n_char(SocketClass *self, char *buffer, int len); diff --git a/src/interfaces/odbc/statement.c b/src/interfaces/odbc/statement.c index dc45a0dccb..db81491591 100644 --- a/src/interfaces/odbc/statement.c +++ b/src/interfaces/odbc/statement.c @@ -13,7 +13,7 @@ */ #ifdef HAVE_CONFIG_H -#include +#include "config.h" #endif #include "statement.h" @@ -25,7 +25,7 @@ #include #include -#ifdef HAVE_IODBC +#ifndef WIN32 #include "iodbc.h" #include "isql.h" #else @@ -35,8 +35,8 @@ extern GLOBAL_VALUES globals; -#ifdef UNIX -#if !HAVE_STRICMP +#ifndef WIN32 +#ifndef HAVE_STRICMP #define stricmp(s1,s2) strcasecmp(s1,s2) #define strnicmp(s1,s2,n) strncasecmp(s1,s2,n) #endif @@ -63,23 +63,12 @@ static struct { RETCODE SQL_API SQLAllocStmt(HDBC hdbc, HSTMT FAR *phstmt) { - return _SQLAllocStmt(hdbc, phstmt); -} - -RETCODE SQL_API SQLFreeStmt(HSTMT hstmt, - UWORD fOption) -{ - return _SQLFreeStmt(hstmt, fOption); -} - - -RETCODE SQL_API _SQLAllocStmt(HDBC hdbc, - HSTMT FAR *phstmt) -{ -char *func="SQLAllocStmt"; +static char *func="SQLAllocStmt"; ConnectionClass *conn = (ConnectionClass *) hdbc; StatementClass *stmt; + mylog("%s: entering...\n", func); + if( ! conn) { CC_log_error(func, "", NULL); return SQL_INVALID_HANDLE; @@ -112,13 +101,13 @@ StatementClass *stmt; } -RETCODE SQL_API _SQLFreeStmt(HSTMT hstmt, +RETCODE SQL_API SQLFreeStmt(HSTMT hstmt, UWORD fOption) { -char *func="SQLFreeStmt"; +static char *func="SQLFreeStmt"; StatementClass *stmt = (StatementClass *) hstmt; - mylog("**** enter SQLFreeStmt: hstmt=%u, fOption=%d\n", hstmt, fOption); + mylog("%s: entering...hstmt=%u, fOption=%d\n", func, hstmt, fOption); if ( ! stmt) { SC_log_error(func, "", NULL); @@ -151,8 +140,6 @@ StatementClass *stmt = (StatementClass *) hstmt; SC_unbind_cols(stmt); } else if (fOption == SQL_CLOSE) { - ConnectionClass *conn = stmt->hdbc; - /* this should discard all the results, but leave the statement */ /* itself in place (it can be executed again) */ if (!SC_recycle_statement(stmt)) { @@ -181,7 +168,7 @@ StatementClass *stmt = (StatementClass *) hstmt; */ StatementClass * -SC_Constructor() +SC_Constructor(void) { StatementClass *rv; @@ -346,6 +333,8 @@ SC_recycle_statement(StatementClass *self) { ConnectionClass *conn; +mylog("recycle statement: self= %u\n", self); + /* This would not happen */ if (self->status == STMT_EXECUTING) { self->errornumber = STMT_SEQUENCE_ERROR; @@ -540,7 +529,7 @@ char rv; RETCODE SC_execute(StatementClass *self) { -char *func="SC_execute"; +static char *func="SC_execute"; ConnectionClass *conn; QResultClass *res; char ok, was_ok, was_nonfatal; @@ -553,7 +542,7 @@ Int2 oldstatus, numcols; /* The reason is because we can't use declare/fetch cursors without starting a transaction first. */ - if ( ! CC_is_in_trans(conn) && (globals.use_declarefetch || STMT_UPDATE(self))) { + if ( ! self->internal && ! CC_is_in_trans(conn) && (globals.use_declarefetch || STMT_UPDATE(self))) { mylog(" about to begin a transaction on statement = %u\n", self); res = CC_send_query(conn, "BEGIN", NULL, NULL); @@ -618,7 +607,7 @@ Int2 oldstatus, numcols; self->result = CC_send_query(conn, self->stmt_with_params, NULL, NULL); // If we are in autocommit, we must send the commit. - if (CC_is_in_autocommit(conn) && STMT_UPDATE(self)) { + if ( ! self->internal && CC_is_in_autocommit(conn) && STMT_UPDATE(self)) { CC_send_query(conn, "COMMIT", NULL, NULL); CC_set_no_trans(conn); } @@ -671,7 +660,9 @@ Int2 oldstatus, numcols; self->errornumber = STMT_EXEC_ERROR; self->errormsg = "Error while executing the query"; } - CC_abort(conn); + + if ( ! self->internal) + CC_abort(conn); } if (self->errornumber == STMT_OK) @@ -691,6 +682,7 @@ SC_log_error(char *func, char *desc, StatementClass *self) { if (self) { qlog("STATEMENT ERROR: func=%s, desc='%s', errnum=%d, errmsg='%s'\n", func, desc, self->errornumber, self->errormsg); + mylog("STATEMENT ERROR: func=%s, desc='%s', errnum=%d, errmsg='%s'\n", func, desc, self->errornumber, self->errormsg); qlog(" ------------------------------------------------------------\n"); qlog(" hdbc=%u, stmt=%u, result=%u\n", self->hdbc, self, self->result); qlog(" manual_result=%d, prepare=%d, internal=%d\n", self->manual_result, self->prepare, self->internal); diff --git a/src/interfaces/odbc/statement.h b/src/interfaces/odbc/statement.h index 33317a51f5..52b64278c1 100644 --- a/src/interfaces/odbc/statement.h +++ b/src/interfaces/odbc/statement.h @@ -11,10 +11,10 @@ #define __STATEMENT_H__ #ifdef HAVE_CONFIG_H -#include +#include "config.h" #endif -#ifdef HAVE_IODBC +#ifndef WIN32 #include "iodbc.h" #include "isql.h" #else @@ -179,7 +179,7 @@ struct StatementClass_ { #define STMT_FREE_PARAMS_DATA_AT_EXEC_ONLY 1 /* Statement prototypes */ -StatementClass *SC_Constructor(); +StatementClass *SC_Constructor(void); char SC_Destructor(StatementClass *self); int statement_type(char *statement); char parse_statement(StatementClass *stmt); @@ -194,16 +194,5 @@ RETCODE SC_execute(StatementClass *stmt); void SC_free_params(StatementClass *self, char option); void SC_log_error(char *func, char *desc, StatementClass *self); -RETCODE SQL_API _SQLAllocStmt(HDBC hdbc, HSTMT FAR *phstmt); -RETCODE SQL_API _SQLFreeStmt(HSTMT hstmt, UWORD fOption); -RETCODE SQL_API _SQLExecDirect(HSTMT hstmt, UCHAR FAR *szSqlStr, SDWORD cbSqlStr); -RETCODE SQL_API _SQLFetch(HSTMT hstmt); -RETCODE SQL_API _SQLGetData( - HSTMT hstmt, - UWORD icol, - SWORD fCType, - PTR rgbValue, - SDWORD cbValueMax, - SDWORD FAR *pcbValue); #endif diff --git a/src/interfaces/odbc/tuple.c b/src/interfaces/odbc/tuple.c index 81e9cfe33b..802b533d83 100644 --- a/src/interfaces/odbc/tuple.c +++ b/src/interfaces/odbc/tuple.c @@ -22,7 +22,7 @@ void set_tuplefield_null(TupleField *tuple_field) { tuple_field->len = 0; - tuple_field->value = strdup(""); + tuple_field->value = NULL; // strdup(""); } void set_tuplefield_string(TupleField *tuple_field, char *string) @@ -37,6 +37,7 @@ void set_tuplefield_int2(TupleField *tuple_field, Int2 value) { char buffer[10]; + sprintf(buffer,"%d", value); tuple_field->len = strlen(buffer)+1; diff --git a/src/interfaces/odbc/tuple.h b/src/interfaces/odbc/tuple.h index 585254edc8..628d5ce449 100644 --- a/src/interfaces/odbc/tuple.h +++ b/src/interfaces/odbc/tuple.h @@ -32,9 +32,9 @@ struct TupleNode_ { but these handle automatic NULL determination and call set_tuplefield_null() if appropriate for the datatype (used by SQLGetTypeInfo). */ -#define set_nullfield_string(FLD, VAL) (VAL ? set_tuplefield_string(FLD, VAL) : set_tuplefield_null(FLD)) -#define set_nullfield_int2(FLD, VAL) (VAL != -1 ? set_tuplefield_int2(FLD, VAL) : set_tuplefield_null(FLD)) -#define set_nullfield_int4(FLD, VAL) (VAL != -1 ? set_tuplefield_int4(FLD, VAL) : set_tuplefield_null(FLD)) +#define set_nullfield_string(FLD, VAL) ((VAL) ? set_tuplefield_string(FLD, (VAL)) : set_tuplefield_null(FLD)) +#define set_nullfield_int2(FLD, VAL) ((VAL) != -1 ? set_tuplefield_int2(FLD, (VAL)) : set_tuplefield_null(FLD)) +#define set_nullfield_int4(FLD, VAL) ((VAL) != -1 ? set_tuplefield_int4(FLD, (VAL)) : set_tuplefield_null(FLD)) void set_tuplefield_null(TupleField *tuple_field); void set_tuplefield_string(TupleField *tuple_field, char *string); -- 2.11.0