summaryrefslogtreecommitdiff
path: root/src/interfaces
diff options
context:
space:
mode:
Diffstat (limited to 'src/interfaces')
-rw-r--r--src/interfaces/libpgtcl/libpgtcl.h12
-rw-r--r--src/interfaces/libpgtcl/pgtcl.c277
-rw-r--r--src/interfaces/libpgtcl/pgtclCmds.c2054
-rw-r--r--src/interfaces/libpgtcl/pgtclCmds.h134
-rw-r--r--src/interfaces/libpgtcl/pgtclId.c260
-rw-r--r--src/interfaces/libpgtcl/pgtclId.h24
-rw-r--r--src/interfaces/libpq/fe-auth.c763
-rw-r--r--src/interfaces/libpq/fe-auth.h34
-rw-r--r--src/interfaces/libpq/fe-connect.c1686
-rw-r--r--src/interfaces/libpq/fe-connect.h12
-rw-r--r--src/interfaces/libpq/fe-exec.c3014
-rw-r--r--src/interfaces/libpq/fe-lobj.c939
-rw-r--r--src/interfaces/libpq/fe-misc.c227
-rw-r--r--src/interfaces/libpq/libpq-fe.h503
-rw-r--r--src/interfaces/libpq/pqsignal.c38
-rw-r--r--src/interfaces/libpq/pqsignal.h12
16 files changed, 5353 insertions, 4636 deletions
diff --git a/src/interfaces/libpgtcl/libpgtcl.h b/src/interfaces/libpgtcl/libpgtcl.h
index 7a5fa0364c1..4ee2848c991 100644
--- a/src/interfaces/libpgtcl/libpgtcl.h
+++ b/src/interfaces/libpgtcl/libpgtcl.h
@@ -1,12 +1,12 @@
/*-------------------------------------------------------------------------
*
* libpgtcl.h--
- * libpgtcl is a tcl package for front-ends to interface with pglite
- * It's the tcl equivalent of the old libpq C interface.
+ * libpgtcl is a tcl package for front-ends to interface with pglite
+ * It's the tcl equivalent of the old libpq C interface.
*
* Copyright (c) 1994, Regents of the University of California
*
- * $Id: libpgtcl.h,v 1.2 1996/10/30 06:18:37 scrappy Exp $
+ * $Id: libpgtcl.h,v 1.3 1997/09/07 05:03:06 momjian Exp $
*
*-------------------------------------------------------------------------
*/
@@ -16,7 +16,7 @@
#include "tcl.h"
-extern int Pgtcl_Init (Tcl_Interp *interp);
-extern int Pgtcl_SafeInit (Tcl_Interp *interp);
+extern int Pgtcl_Init(Tcl_Interp * interp);
+extern int Pgtcl_SafeInit(Tcl_Interp * interp);
-#endif /* LIBPGTCL_H */
+#endif /* LIBPGTCL_H */
diff --git a/src/interfaces/libpgtcl/pgtcl.c b/src/interfaces/libpgtcl/pgtcl.c
index 8df0c42105c..75c8ec5ddad 100644
--- a/src/interfaces/libpgtcl/pgtcl.c
+++ b/src/interfaces/libpgtcl/pgtcl.c
@@ -1,15 +1,15 @@
/*-------------------------------------------------------------------------
*
* pgtcl.c--
- *
- * libpgtcl is a tcl package for front-ends to interface with pglite
- * It's the tcl equivalent of the old libpq C interface.
+ *
+ * libpgtcl is a tcl package for front-ends to interface with pglite
+ * It's the tcl equivalent of the old libpq C interface.
*
* Copyright (c) 1994, Regents of the University of California
*
*
* IDENTIFICATION
- * $Header: /cvsroot/pgsql/src/interfaces/libpgtcl/Attic/pgtcl.c,v 1.7 1997/01/03 18:48:28 scrappy Exp $
+ * $Header: /cvsroot/pgsql/src/interfaces/libpgtcl/Attic/pgtcl.c,v 1.8 1997/09/07 05:03:09 momjian Exp $
*
*-------------------------------------------------------------------------
*/
@@ -23,8 +23,8 @@
#include "pgtclId.h"
/*
- * Pgtcl_Init
- * initialization package for the PGLITE Tcl package
+ * Pgtcl_Init
+ * initialization package for the PGLITE Tcl package
*
*/
@@ -32,153 +32,154 @@
* Tidy up forgotten postgres connection at Tcl_Exit
*/
static void
-Pgtcl_AtExit (ClientData cData)
+Pgtcl_AtExit(ClientData cData)
{
- Pg_clientData *cd = (Pg_clientData *)cData;
- Tcl_HashEntry *hent;
- Tcl_HashSearch hsearch;
- Pg_ConnectionId *connid;
- PGconn *conn;
-
- while((hent = Tcl_FirstHashEntry(&(cd->dbh_hash), &hsearch)) != NULL) {
- connid = (Pg_ConnectionId *)Tcl_GetHashValue(hent);
- conn = connid->conn;
- PgDelConnectionId(cd, connid->id);
- PQfinish(conn);
- }
-
- Tcl_DeleteHashTable(&(cd->dbh_hash));
- Tcl_DeleteHashTable(&(cd->res_hash));
- Tcl_DeleteHashTable(&(cd->notify_hash));
-
- Tcl_DeleteExitHandler(Pgtcl_AtExit, cData);
+ Pg_clientData *cd = (Pg_clientData *) cData;
+ Tcl_HashEntry *hent;
+ Tcl_HashSearch hsearch;
+ Pg_ConnectionId *connid;
+ PGconn *conn;
+
+ while ((hent = Tcl_FirstHashEntry(&(cd->dbh_hash), &hsearch)) != NULL)
+ {
+ connid = (Pg_ConnectionId *) Tcl_GetHashValue(hent);
+ conn = connid->conn;
+ PgDelConnectionId(cd, connid->id);
+ PQfinish(conn);
+ }
+
+ Tcl_DeleteHashTable(&(cd->dbh_hash));
+ Tcl_DeleteHashTable(&(cd->res_hash));
+ Tcl_DeleteHashTable(&(cd->notify_hash));
+
+ Tcl_DeleteExitHandler(Pgtcl_AtExit, cData);
}
/*
* Tidy up forgotten postgres connections on Interpreter deletion
*/
static void
-Pgtcl_Shutdown (ClientData cData, Tcl_Interp *interp)
+Pgtcl_Shutdown(ClientData cData, Tcl_Interp * interp)
{
- Pgtcl_AtExit(cData);
+ Pgtcl_AtExit(cData);
}
int
-Pgtcl_Init (Tcl_Interp *interp)
+Pgtcl_Init(Tcl_Interp * interp)
{
- Pg_clientData *cd;
-
- /* Create and initialize the client data area */
- cd = (Pg_clientData *)ckalloc(sizeof(Pg_clientData));
- Tcl_InitHashTable(&(cd->dbh_hash), TCL_STRING_KEYS);
- Tcl_InitHashTable(&(cd->res_hash), TCL_STRING_KEYS);
- Tcl_InitHashTable(&(cd->notify_hash), TCL_STRING_KEYS);
- cd->dbh_count = 0L;
- cd->res_count = 0L;
-
- /* Arrange for tidy up when interpreter is deleted or Tcl exits */
- Tcl_CallWhenDeleted(interp, Pgtcl_Shutdown, (ClientData)cd);
- Tcl_CreateExitHandler(Pgtcl_AtExit, (ClientData)cd);
-
- /* register all pgtcl commands */
- Tcl_CreateCommand(interp,
- "pg_conndefaults",
- Pg_conndefaults,
- (ClientData)cd, (Tcl_CmdDeleteProc*)NULL);
-
- Tcl_CreateCommand(interp,
- "pg_connect",
- Pg_connect,
- (ClientData)cd, (Tcl_CmdDeleteProc*)NULL);
-
- Tcl_CreateCommand(interp,
- "pg_disconnect",
- Pg_disconnect,
- (ClientData)cd, (Tcl_CmdDeleteProc*)NULL);
-
- Tcl_CreateCommand(interp,
- "pg_exec",
- Pg_exec,
- (ClientData)cd, (Tcl_CmdDeleteProc*)NULL);
-
- Tcl_CreateCommand(interp,
- "pg_select",
- Pg_select,
- (ClientData)cd, (Tcl_CmdDeleteProc*)NULL);
-
- Tcl_CreateCommand(interp,
- "pg_result",
- Pg_result,
- (ClientData)cd, (Tcl_CmdDeleteProc*)NULL);
-
- Tcl_CreateCommand(interp,
- "pg_lo_open",
- Pg_lo_open,
- (ClientData)cd, (Tcl_CmdDeleteProc*)NULL);
-
- Tcl_CreateCommand(interp,
- "pg_lo_close",
- Pg_lo_close,
- (ClientData)cd, (Tcl_CmdDeleteProc*)NULL);
-
- Tcl_CreateCommand(interp,
- "pg_lo_read",
- Pg_lo_read,
- (ClientData)cd, (Tcl_CmdDeleteProc*)NULL);
-
- Tcl_CreateCommand(interp,
- "pg_lo_write",
- Pg_lo_write,
- (ClientData)cd, (Tcl_CmdDeleteProc*)NULL);
-
- Tcl_CreateCommand(interp,
- "pg_lo_lseek",
- Pg_lo_lseek,
- (ClientData)cd, (Tcl_CmdDeleteProc*)NULL);
-
- Tcl_CreateCommand(interp,
- "pg_lo_creat",
- Pg_lo_creat,
- (ClientData)cd, (Tcl_CmdDeleteProc*)NULL);
-
- Tcl_CreateCommand(interp,
- "pg_lo_tell",
- Pg_lo_tell,
- (ClientData)cd, (Tcl_CmdDeleteProc*)NULL);
-
- Tcl_CreateCommand(interp,
- "pg_lo_unlink",
- Pg_lo_unlink,
- (ClientData)cd, (Tcl_CmdDeleteProc*)NULL);
-
- Tcl_CreateCommand(interp,
- "pg_lo_import",
- Pg_lo_import,
- (ClientData)cd, (Tcl_CmdDeleteProc*)NULL);
-
- Tcl_CreateCommand(interp,
- "pg_lo_export",
- Pg_lo_export,
- (ClientData)cd, (Tcl_CmdDeleteProc*)NULL);
-
- Tcl_CreateCommand(interp,
- "pg_listen",
- Pg_listen,
- (ClientData)cd, (Tcl_CmdDeleteProc*)NULL);
-
- Tcl_CreateCommand(interp,
- "pg_notifies",
- Pg_notifies,
- (ClientData)cd, (Tcl_CmdDeleteProc*)NULL);
-
- Tcl_PkgProvide(interp, "Pgtcl", "1.0");
-
- return TCL_OK;
+ Pg_clientData *cd;
+
+ /* Create and initialize the client data area */
+ cd = (Pg_clientData *) ckalloc(sizeof(Pg_clientData));
+ Tcl_InitHashTable(&(cd->dbh_hash), TCL_STRING_KEYS);
+ Tcl_InitHashTable(&(cd->res_hash), TCL_STRING_KEYS);
+ Tcl_InitHashTable(&(cd->notify_hash), TCL_STRING_KEYS);
+ cd->dbh_count = 0L;
+ cd->res_count = 0L;
+
+ /* Arrange for tidy up when interpreter is deleted or Tcl exits */
+ Tcl_CallWhenDeleted(interp, Pgtcl_Shutdown, (ClientData) cd);
+ Tcl_CreateExitHandler(Pgtcl_AtExit, (ClientData) cd);
+
+ /* register all pgtcl commands */
+ Tcl_CreateCommand(interp,
+ "pg_conndefaults",
+ Pg_conndefaults,
+ (ClientData) cd, (Tcl_CmdDeleteProc *) NULL);
+
+ Tcl_CreateCommand(interp,
+ "pg_connect",
+ Pg_connect,
+ (ClientData) cd, (Tcl_CmdDeleteProc *) NULL);
+
+ Tcl_CreateCommand(interp,
+ "pg_disconnect",
+ Pg_disconnect,
+ (ClientData) cd, (Tcl_CmdDeleteProc *) NULL);
+
+ Tcl_CreateCommand(interp,
+ "pg_exec",
+ Pg_exec,
+ (ClientData) cd, (Tcl_CmdDeleteProc *) NULL);
+
+ Tcl_CreateCommand(interp,
+ "pg_select",
+ Pg_select,
+ (ClientData) cd, (Tcl_CmdDeleteProc *) NULL);
+
+ Tcl_CreateCommand(interp,
+ "pg_result",
+ Pg_result,
+ (ClientData) cd, (Tcl_CmdDeleteProc *) NULL);
+
+ Tcl_CreateCommand(interp,
+ "pg_lo_open",
+ Pg_lo_open,
+ (ClientData) cd, (Tcl_CmdDeleteProc *) NULL);
+
+ Tcl_CreateCommand(interp,
+ "pg_lo_close",
+ Pg_lo_close,
+ (ClientData) cd, (Tcl_CmdDeleteProc *) NULL);
+
+ Tcl_CreateCommand(interp,
+ "pg_lo_read",
+ Pg_lo_read,
+ (ClientData) cd, (Tcl_CmdDeleteProc *) NULL);
+
+ Tcl_CreateCommand(interp,
+ "pg_lo_write",
+ Pg_lo_write,
+ (ClientData) cd, (Tcl_CmdDeleteProc *) NULL);
+
+ Tcl_CreateCommand(interp,
+ "pg_lo_lseek",
+ Pg_lo_lseek,
+ (ClientData) cd, (Tcl_CmdDeleteProc *) NULL);
+
+ Tcl_CreateCommand(interp,
+ "pg_lo_creat",
+ Pg_lo_creat,
+ (ClientData) cd, (Tcl_CmdDeleteProc *) NULL);
+
+ Tcl_CreateCommand(interp,
+ "pg_lo_tell",
+ Pg_lo_tell,
+ (ClientData) cd, (Tcl_CmdDeleteProc *) NULL);
+
+ Tcl_CreateCommand(interp,
+ "pg_lo_unlink",
+ Pg_lo_unlink,
+ (ClientData) cd, (Tcl_CmdDeleteProc *) NULL);
+
+ Tcl_CreateCommand(interp,
+ "pg_lo_import",
+ Pg_lo_import,
+ (ClientData) cd, (Tcl_CmdDeleteProc *) NULL);
+
+ Tcl_CreateCommand(interp,
+ "pg_lo_export",
+ Pg_lo_export,
+ (ClientData) cd, (Tcl_CmdDeleteProc *) NULL);
+
+ Tcl_CreateCommand(interp,
+ "pg_listen",
+ Pg_listen,
+ (ClientData) cd, (Tcl_CmdDeleteProc *) NULL);
+
+ Tcl_CreateCommand(interp,
+ "pg_notifies",
+ Pg_notifies,
+ (ClientData) cd, (Tcl_CmdDeleteProc *) NULL);
+
+ Tcl_PkgProvide(interp, "Pgtcl", "1.0");
+
+ return TCL_OK;
}
int
-Pgtcl_SafeInit (Tcl_Interp *interp)
+Pgtcl_SafeInit(Tcl_Interp * interp)
{
- return Pgtcl_Init(interp);
+ return Pgtcl_Init(interp);
}
diff --git a/src/interfaces/libpgtcl/pgtclCmds.c b/src/interfaces/libpgtcl/pgtclCmds.c
index 6ad9ca17673..834938487d4 100644
--- a/src/interfaces/libpgtcl/pgtclCmds.c
+++ b/src/interfaces/libpgtcl/pgtclCmds.c
@@ -1,13 +1,13 @@
/*-------------------------------------------------------------------------
*
* pgtclCmds.c--
- * C functions which implement pg_* tcl commands
+ * C functions which implement pg_* tcl commands
*
* Copyright (c) 1994, Regents of the University of California
*
*
* IDENTIFICATION
- * $Header: /cvsroot/pgsql/src/interfaces/libpgtcl/Attic/pgtclCmds.c,v 1.13 1997/04/02 18:16:49 scrappy Exp $
+ * $Header: /cvsroot/pgsql/src/interfaces/libpgtcl/Attic/pgtclCmds.c,v 1.14 1997/09/07 05:03:10 momjian Exp $
*
*-------------------------------------------------------------------------
*/
@@ -25,8 +25,8 @@
#include "pgtclId.h"
#ifdef TCL_ARRAYS
-#define ISOCTAL(c) (((c) >= '0') && ((c) <= '7'))
-#define DIGIT(c) ((c) - '0')
+#define ISOCTAL(c) (((c) >= '0') && ((c) <= '7'))
+#define DIGIT(c) ((c) - '0')
/*
* translate_escape() --
@@ -38,97 +38,107 @@
* just before the rest of the buffer).
*/
-static inline char*
+static inline char *
translate_escape(char *p, int isArray)
{
- register char c, *q, *s;
+ register char c,
+ *q,
+ *s;
#ifdef TCL_ARRAYS_DEBUG_ESCAPE
- printf(" escape = '%s'\n", p);
+ printf(" escape = '%s'\n", p);
#endif
- /* Address of the first character after the escape sequence */
- s = p+2;
- switch (c = *(p+1)) {
- case '0':
- case '1':
- case '2':
- case '3':
- case '4':
- case '5':
- case '6':
- case '7':
- c = DIGIT(c);
- if (ISOCTAL(*s)) {
- c = (c<<3) + DIGIT(*s++);
- }
- if (ISOCTAL(*s)) {
- c = (c<<3) + DIGIT(*s++);
- }
- *p = c;
- break;
- case 'b':
- *p = '\b';
- break;
- case 'f':
- *p = '\f';
- break;
- case 'n':
- *p = '\n';
- break;
- case 'r':
- *p = '\r';
- break;
- case 't':
- *p = '\t';
- break;
- case 'v':
- *p = '\v';
- break;
- case '\\':
- case '{':
- case '}':
- case '"':
- /*
- * Backslahes, curly braces and double-quotes are left
- * escaped if they appear inside an array. They will be
- * unescaped by Tcl in Tcl_AppendElement.
- * The buffer position is advanced by 1 so that the this
- * character is not processed again by the caller.
- */
- if (isArray) {
- return p+1;
- } else {
- *p = c;
+ /* Address of the first character after the escape sequence */
+ s = p + 2;
+ switch (c = *(p + 1))
+ {
+ case '0':
+ case '1':
+ case '2':
+ case '3':
+ case '4':
+ case '5':
+ case '6':
+ case '7':
+ c = DIGIT(c);
+ if (ISOCTAL(*s))
+ {
+ c = (c << 3) + DIGIT(*s++);
+ }
+ if (ISOCTAL(*s))
+ {
+ c = (c << 3) + DIGIT(*s++);
+ }
+ *p = c;
+ break;
+ case 'b':
+ *p = '\b';
+ break;
+ case 'f':
+ *p = '\f';
+ break;
+ case 'n':
+ *p = '\n';
+ break;
+ case 'r':
+ *p = '\r';
+ break;
+ case 't':
+ *p = '\t';
+ break;
+ case 'v':
+ *p = '\v';
+ break;
+ case '\\':
+ case '{':
+ case '}':
+ case '"':
+
+ /*
+ * Backslahes, curly braces and double-quotes are left escaped if
+ * they appear inside an array. They will be unescaped by Tcl in
+ * Tcl_AppendElement. The buffer position is advanced by 1 so that
+ * the this character is not processed again by the caller.
+ */
+ if (isArray)
+ {
+ return p + 1;
+ }
+ else
+ {
+ *p = c;
+ }
+ break;
+ case '\0':
+
+ /*
+ * This means a backslash at the end of the string. It should
+ * never happen but in that case replace the \ with a \0 but don't
+ * shift the rest of the buffer so that the caller can see the end
+ * of the string and terminate.
+ */
+ *p = c;
+ return p;
+ break;
+ default:
+
+ /*
+ * Default case, store the escaped character over the backslash
+ * and shift the buffer over itself.
+ */
+ *p = c;
}
- break;
- case '\0':
- /*
- * This means a backslash at the end of the string.
- * It should never happen but in that case replace
- * the \ with a \0 but don't shift the rest of the
- * buffer so that the caller can see the end of the
- * string and terminate.
- */
- *p = c;
- return p;
- break;
- default:
- /*
- * Default case, store the escaped character over the backslash
- * and shift the buffer over itself.
- */
- *p = c;
- }
- /* Shift the rest of the buffer over itself after the current char */
- q = p+1;
- for ( ; *s ; ) {
- *q++ = *s++;
- }
- *q = '\0';
+ /* Shift the rest of the buffer over itself after the current char */
+ q = p + 1;
+ for (; *s;)
+ {
+ *q++ = *s++;
+ }
+ *q = '\0';
#ifdef TCL_ARRAYS_DEBUG_ESCAPE
- printf(" after = '%s'\n", p);
+ printf(" after = '%s'\n", p);
#endif
- return p;
+ return p;
}
/*
@@ -139,299 +149,339 @@ translate_escape(char *p, int isArray)
* representation of a postgres array.
*/
-static char *
-tcl_value (char *value)
+static char *
+tcl_value(char *value)
{
- int literal, last;
- register char *p;
+ int literal,
+ last;
+ register char *p;
- if (!value) {
- return ((char *) NULL);
- }
+ if (!value)
+ {
+ return ((char *) NULL);
+ }
#ifdef TCL_ARRAYS_DEBUG
- printf("pq_value = '%s'\n", value);
+ printf("pq_value = '%s'\n", value);
#endif
- last = strlen(value)-1;
- if ((last >= 1) && (value[0] == '{') && (value[last] == '}')) {
- /* Looks like an array, replace ',' with spaces */
- /* Remove the outer pair of { }, the last first! */
- value[last] = '\0';
- value++;
- literal = 0;
- for (p=value; *p; p++) {
- if (!literal) {
- /* We are at the list level, look for ',' and '"' */
- switch (*p) {
- case '"': /* beginning of literal */
- literal = 1;
- break;
- case ',': /* replace the ',' with space */
- *p = ' ';
- break;
- }
- } else {
- /* We are inside a C string */
- switch (*p) {
- case '"': /* end of literal */
- literal = 0;
- break;
- case '\\':
- /*
- * escape sequence, translate it
- */
- p = translate_escape(p,1);
- break;
+ last = strlen(value) - 1;
+ if ((last >= 1) && (value[0] == '{') && (value[last] == '}'))
+ {
+ /* Looks like an array, replace ',' with spaces */
+ /* Remove the outer pair of { }, the last first! */
+ value[last] = '\0';
+ value++;
+ literal = 0;
+ for (p = value; *p; p++)
+ {
+ if (!literal)
+ {
+ /* We are at the list level, look for ',' and '"' */
+ switch (*p)
+ {
+ case '"': /* beginning of literal */
+ literal = 1;
+ break;
+ case ',': /* replace the ',' with space */
+ *p = ' ';
+ break;
+ }
+ }
+ else
+ {
+ /* We are inside a C string */
+ switch (*p)
+ {
+ case '"': /* end of literal */
+ literal = 0;
+ break;
+ case '\\':
+
+ /*
+ * escape sequence, translate it
+ */
+ p = translate_escape(p, 1);
+ break;
+ }
+ }
+ if (!*p)
+ {
+ break;
+ }
}
- }
- if (!*p) {
- break;
- }
}
- } else {
- /* Looks like a normal scalar value */
- for (p=value; *p; p++) {
- if (*p == '\\') {
- /*
- * escape sequence, translate it
- */
- p = translate_escape(p,0);
- }
- if (!*p) {
- break;
- }
+ else
+ {
+ /* Looks like a normal scalar value */
+ for (p = value; *p; p++)
+ {
+ if (*p == '\\')
+ {
+
+ /*
+ * escape sequence, translate it
+ */
+ p = translate_escape(p, 0);
+ }
+ if (!*p)
+ {
+ break;
+ }
+ }
}
- }
#ifdef TCL_ARRAYS_DEBUG
- printf("tcl_value = '%s'\n\n", value);
+ printf("tcl_value = '%s'\n\n", value);
#endif
- return (value);
+ return (value);
}
#endif
/**********************************
* pg_conndefaults
-
+
syntax:
pg_conndefaults
-
+
the return result is a list describing the possible options and their
current default values for a call to pg_connect with the new -conninfo
syntax. Each entry in the list is a sublist of the format:
- {optname label dispchar dispsize value}
-
+ {optname label dispchar dispsize value}
+
**********************************/
int
-Pg_conndefaults(ClientData cData, Tcl_Interp *interp, int argc, char **argv)
+Pg_conndefaults(ClientData cData, Tcl_Interp * interp, int argc, char **argv)
{
- PQconninfoOption *option;
- char buf[8192];
-
- Tcl_ResetResult(interp);
- for(option = PQconndefaults(); option->keyword != NULL; option++) {
- if(option->val == NULL) {
- option->val = "";
- }
- sprintf(buf, "{%s} {%s} {%s} %d {%s}",
- option->keyword,
- option->label,
- option->dispchar,
- option->dispsize,
- option->val);
- Tcl_AppendElement(interp, buf);
- }
-
- return TCL_OK;
+ PQconninfoOption *option;
+ char buf[8192];
+
+ Tcl_ResetResult(interp);
+ for (option = PQconndefaults(); option->keyword != NULL; option++)
+ {
+ if (option->val == NULL)
+ {
+ option->val = "";
+ }
+ sprintf(buf, "{%s} {%s} {%s} %d {%s}",
+ option->keyword,
+ option->label,
+ option->dispchar,
+ option->dispsize,
+ option->val);
+ Tcl_AppendElement(interp, buf);
+ }
+
+ return TCL_OK;
}
/**********************************
* pg_connect
- make a connection to a backend.
-
+ make a connection to a backend.
+
syntax:
pg_connect dbName [-host hostName] [-port portNumber] [-tty pqtty]]
-
+
the return result is either an error message or a handle for a database
connection. Handles start with the prefix "pgp"
-
+
**********************************/
int
-Pg_connect(ClientData cData, Tcl_Interp *interp, int argc, char* argv[])
+Pg_connect(ClientData cData, Tcl_Interp * interp, int argc, char *argv[])
{
- Pg_clientData *cd = (Pg_clientData *)cData;
- char *pghost = NULL;
- char *pgtty = NULL;
- char *pgport = NULL;
- char *pgoptions = NULL;
- char *dbName;
- int i;
- PGconn *conn;
-
- if (argc == 1) {
- Tcl_AppendResult(interp, "pg_connect: database name missing\n", 0);
- Tcl_AppendResult(interp, "pg_connect databaseName [-host hostName] [-port portNumber] [-tty pgtty]]\n", 0);
- Tcl_AppendResult(interp, "pg_connect -conninfo <conninfo-string>", 0);
- return TCL_ERROR;
-
- }
+ Pg_clientData *cd = (Pg_clientData *) cData;
+ char *pghost = NULL;
+ char *pgtty = NULL;
+ char *pgport = NULL;
+ char *pgoptions = NULL;
+ char *dbName;
+ int i;
+ PGconn *conn;
+
+ if (argc == 1)
+ {
+ Tcl_AppendResult(interp, "pg_connect: database name missing\n", 0);
+ Tcl_AppendResult(interp, "pg_connect databaseName [-host hostName] [-port portNumber] [-tty pgtty]]\n", 0);
+ Tcl_AppendResult(interp, "pg_connect -conninfo <conninfo-string>", 0);
+ return TCL_ERROR;
- if (!strcmp("-conninfo", argv[1])) {
- /*
- * Establish a connection using the new PQconnectdb() interface
- */
- if (argc != 3) {
- Tcl_AppendResult(interp, "pg_connect: syntax error\n", 0);
- Tcl_AppendResult(interp, "pg_connect -conninfo <conninfo-string>", 0);
- return TCL_ERROR;
}
- conn = PQconnectdb(argv[2]);
- } else {
- /*
- * Establish a connection using the old PQsetdb() interface
- */
- if (argc > 2) {
- /* parse for pg environment settings */
- i = 2;
- while (i+1 < argc) {
- if (strcmp(argv[i], "-host") == 0) {
- pghost = argv[i+1];
- i += 2;
+
+ if (!strcmp("-conninfo", argv[1]))
+ {
+
+ /*
+ * Establish a connection using the new PQconnectdb() interface
+ */
+ if (argc != 3)
+ {
+ Tcl_AppendResult(interp, "pg_connect: syntax error\n", 0);
+ Tcl_AppendResult(interp, "pg_connect -conninfo <conninfo-string>", 0);
+ return TCL_ERROR;
}
- else
- if (strcmp(argv[i], "-port") == 0) {
- pgport = argv[i+1];
- i += 2;
- }
- else
- if (strcmp(argv[i], "-tty") == 0) {
- pgtty = argv[i+1];
- i += 2;
- }
- else if (strcmp(argv[i], "-options") == 0) {
- pgoptions = argv[i+1];
- i += 2;
- }
- else {
- Tcl_AppendResult(interp, "Bad option to pg_connect : \n",
- argv[i], 0);
- Tcl_AppendResult(interp, "pg_connect databaseName [-host hostName] [-port portNumber] [-tty pgtty]]",0);
- return TCL_ERROR;
+ conn = PQconnectdb(argv[2]);
+ }
+ else
+ {
+
+ /*
+ * Establish a connection using the old PQsetdb() interface
+ */
+ if (argc > 2)
+ {
+ /* parse for pg environment settings */
+ i = 2;
+ while (i + 1 < argc)
+ {
+ if (strcmp(argv[i], "-host") == 0)
+ {
+ pghost = argv[i + 1];
+ i += 2;
+ }
+ else if (strcmp(argv[i], "-port") == 0)
+ {
+ pgport = argv[i + 1];
+ i += 2;
+ }
+ else if (strcmp(argv[i], "-tty") == 0)
+ {
+ pgtty = argv[i + 1];
+ i += 2;
+ }
+ else if (strcmp(argv[i], "-options") == 0)
+ {
+ pgoptions = argv[i + 1];
+ i += 2;
+ }
+ else
+ {
+ Tcl_AppendResult(interp, "Bad option to pg_connect : \n",
+ argv[i], 0);
+ Tcl_AppendResult(interp, "pg_connect databaseName [-host hostName] [-port portNumber] [-tty pgtty]]", 0);
+ return TCL_ERROR;
+ }
+ } /* while */
+ if ((i % 2 != 0) || i != argc)
+ {
+ Tcl_AppendResult(interp, "wrong # of arguments to pg_connect\n", argv[i], 0);
+ Tcl_AppendResult(interp, "pg_connect databaseName [-host hostName] [-port portNumber] [-tty pgtty]]", 0);
+ return TCL_ERROR;
}
- } /* while */
- if ((i % 2 != 0) || i != argc) {
- Tcl_AppendResult(interp, "wrong # of arguments to pg_connect\n", argv[i],0);
- Tcl_AppendResult(interp, "pg_connect databaseName [-host hostName] [-port portNumber] [-tty pgtty]]",0);
- return TCL_ERROR;
- }
+ }
+ dbName = argv[1];
+ conn = PQsetdb(pghost, pgport, pgoptions, pgtty, dbName);
}
- dbName = argv[1];
- conn = PQsetdb(pghost, pgport, pgoptions, pgtty, dbName);
- }
- if (conn->status == CONNECTION_OK) {
- PgSetConnectionId(cd, interp->result, conn);
- return TCL_OK;
- }
- else {
- Tcl_AppendResult(interp, "Connection to database failed\n", 0);
- Tcl_AppendResult(interp, conn->errorMessage, 0);
- PQfinish(conn);
- return TCL_ERROR;
- }
+ if (conn->status == CONNECTION_OK)
+ {
+ PgSetConnectionId(cd, interp->result, conn);
+ return TCL_OK;
+ }
+ else
+ {
+ Tcl_AppendResult(interp, "Connection to database failed\n", 0);
+ Tcl_AppendResult(interp, conn->errorMessage, 0);
+ PQfinish(conn);
+ return TCL_ERROR;
+ }
}
/**********************************
* pg_disconnect
close a backend connection
-
+
syntax:
pg_disconnect connection
-
+
The argument passed in must be a connection pointer.
-
+
**********************************/
int
-Pg_disconnect(ClientData cData, Tcl_Interp *interp, int argc, char* argv[])
+Pg_disconnect(ClientData cData, Tcl_Interp * interp, int argc, char *argv[])
{
- Pg_clientData *cd = (Pg_clientData *)cData;
- PGconn *conn;
+ Pg_clientData *cd = (Pg_clientData *) cData;
+ PGconn *conn;
- if (argc != 2) {
- Tcl_AppendResult(interp, "Wrong # of arguments\n", "pg_disconnect connection", 0);
- return TCL_ERROR;
- }
+ if (argc != 2)
+ {
+ Tcl_AppendResult(interp, "Wrong # of arguments\n", "pg_disconnect connection", 0);
+ return TCL_ERROR;
+ }
- conn = PgGetConnectionId(cd, argv[1]);
- if (conn == (PGconn *)NULL) {
- Tcl_AppendResult(interp, "First argument is not a valid connection\n", 0);
- return TCL_ERROR;
- }
-
- PgDelConnectionId(cd, argv[1]);
- PQfinish(conn);
- return TCL_OK;
+ conn = PgGetConnectionId(cd, argv[1]);
+ if (conn == (PGconn *) NULL)
+ {
+ Tcl_AppendResult(interp, "First argument is not a valid connection\n", 0);
+ return TCL_ERROR;
+ }
+
+ PgDelConnectionId(cd, argv[1]);
+ PQfinish(conn);
+ return TCL_OK;
}
/**********************************
* pg_exec
send a query string to the backend connection
-
+
syntax:
pg_exec connection query
-
+
the return result is either an error message or a handle for a query
result. Handles start with the prefix "pgp"
**********************************/
int
-Pg_exec(ClientData cData, Tcl_Interp *interp, int argc, char* argv[])
+Pg_exec(ClientData cData, Tcl_Interp * interp, int argc, char *argv[])
{
- Pg_clientData *cd = (Pg_clientData *)cData;
- PGconn *conn;
- PGresult *result;
+ Pg_clientData *cd = (Pg_clientData *) cData;
+ PGconn *conn;
+ PGresult *result;
- if (argc != 3) {
- Tcl_AppendResult(interp, "Wrong # of arguments\n",
- "pg_exec connection queryString", 0);
- return TCL_ERROR;
- }
+ if (argc != 3)
+ {
+ Tcl_AppendResult(interp, "Wrong # of arguments\n",
+ "pg_exec connection queryString", 0);
+ return TCL_ERROR;
+ }
- conn = PgGetConnectionId(cd, argv[1]);
- if (conn == (PGconn *)NULL) {
- Tcl_AppendResult(interp, "First argument is not a valid connection\n", 0);
- return TCL_ERROR;
- }
-
- result = PQexec(conn, argv[2]);
- if (result) {
- PgSetResultId(cd, interp->result, argv[1], result);
+ conn = PgGetConnectionId(cd, argv[1]);
+ if (conn == (PGconn *) NULL)
+ {
+ Tcl_AppendResult(interp, "First argument is not a valid connection\n", 0);
+ return TCL_ERROR;
+ }
+
+ result = PQexec(conn, argv[2]);
+ if (result)
+ {
+ PgSetResultId(cd, interp->result, argv[1], result);
+ return TCL_OK;
+ }
+ else
+ {
+ /* error occurred during the query */
+ Tcl_SetResult(interp, conn->errorMessage, TCL_STATIC);
+ return TCL_ERROR;
+ }
+ /* check return status of result */
return TCL_OK;
- }
- else {
- /* error occurred during the query */
- Tcl_SetResult(interp, conn->errorMessage, TCL_STATIC);
- return TCL_ERROR;
- }
- /* check return status of result */
- return TCL_OK;
}
/**********************************
* pg_result
get information about the results of a query
-
+
syntax:
- pg_result result ?option?
-
+ pg_result result ?option?
+
the options are:
- -status
+ -status
the status of the result
-conn
the connection that produced the result
@@ -451,291 +501,333 @@ Pg_exec(ClientData cData, Tcl_Interp *interp, int argc, char* argv[])
returns the number of attributes returned by the query
-getTuple tupleNumber
returns the values of the tuple in a list
- -clear
+ -clear
clear the result buffer. Do not reuse after this
**********************************/
int
-Pg_result(ClientData cData, Tcl_Interp *interp, int argc, char* argv[])
+Pg_result(ClientData cData, Tcl_Interp * interp, int argc, char *argv[])
{
- Pg_clientData *cd = (Pg_clientData *)cData;
- PGresult *result;
- char *opt;
- int i;
- int tupno;
- char prearrayInd[MAX_MESSAGE_LEN];
- char arrayInd[MAX_MESSAGE_LEN];
- char *appendstr;
- char *arrVar;
-
- if (argc != 3 && argc != 4 && argc != 5) {
- Tcl_AppendResult(interp, "Wrong # of arguments\n",0);
- goto Pg_result_errReturn;
- }
-
- result = PgGetResultId(cd, argv[1]);
- if (result == (PGresult *)NULL) {
- Tcl_AppendResult(interp, "First argument is not a valid query result\n", 0);
- return TCL_ERROR;
- }
+ Pg_clientData *cd = (Pg_clientData *) cData;
+ PGresult *result;
+ char *opt;
+ int i;
+ int tupno;
+ char prearrayInd[MAX_MESSAGE_LEN];
+ char arrayInd[MAX_MESSAGE_LEN];
+ char *appendstr;
+ char *arrVar;
+
+ if (argc != 3 && argc != 4 && argc != 5)
+ {
+ Tcl_AppendResult(interp, "Wrong # of arguments\n", 0);
+ goto Pg_result_errReturn;
+ }
+
+ result = PgGetResultId(cd, argv[1]);
+ if (result == (PGresult *) NULL)
+ {
+ Tcl_AppendResult(interp, "First argument is not a valid query result\n", 0);
+ return TCL_ERROR;
+ }
- opt = argv[2];
+ opt = argv[2];
- if (strcmp(opt, "-status") == 0) {
- Tcl_AppendResult(interp, pgresStatus[PQresultStatus(result)], 0);
- return TCL_OK;
- }
- else if (strcmp(opt, "-oid") == 0) {
- Tcl_AppendResult(interp, PQoidStatus(result), 0);
- return TCL_OK;
- }
- else if (strcmp(opt, "-conn") == 0) {
- PgGetConnByResultId(cd, interp->result, argv[1]);
- return TCL_OK;
- }
- else if (strcmp(opt, "-clear") == 0) {
- PgDelResultId(cd, argv[1]);
- PQclear(result);
- return TCL_OK;
- }
- else if (strcmp(opt, "-numTuples") == 0) {
- sprintf(interp->result, "%d", PQntuples(result));
- return TCL_OK;
- }
- else if (strcmp(opt, "-assign") == 0) {
- if (argc != 4) {
- Tcl_AppendResult(interp, "-assign option must be followed by a variable name",0);
- return TCL_ERROR;
- }
- arrVar = argv[3];
- /* this assignment assigns the table of result tuples into a giant
- array with the name given in the argument,
- the indices of the array or (tupno,attrName)*/
- for (tupno = 0; tupno<PQntuples(result); tupno++) {
- for (i=0;i<PQnfields(result);i++) {
- sprintf(arrayInd, "%d,%s", tupno, PQfname(result,i));
- Tcl_SetVar2(interp, arrVar, arrayInd,
+ if (strcmp(opt, "-status") == 0)
+ {
+ Tcl_AppendResult(interp, pgresStatus[PQresultStatus(result)], 0);
+ return TCL_OK;
+ }
+ else if (strcmp(opt, "-oid") == 0)
+ {
+ Tcl_AppendResult(interp, PQoidStatus(result), 0);
+ return TCL_OK;
+ }
+ else if (strcmp(opt, "-conn") == 0)
+ {
+ PgGetConnByResultId(cd, interp->result, argv[1]);
+ return TCL_OK;
+ }
+ else if (strcmp(opt, "-clear") == 0)
+ {
+ PgDelResultId(cd, argv[1]);
+ PQclear(result);
+ return TCL_OK;
+ }
+ else if (strcmp(opt, "-numTuples") == 0)
+ {
+ sprintf(interp->result, "%d", PQntuples(result));
+ return TCL_OK;
+ }
+ else if (strcmp(opt, "-assign") == 0)
+ {
+ if (argc != 4)
+ {
+ Tcl_AppendResult(interp, "-assign option must be followed by a variable name", 0);
+ return TCL_ERROR;
+ }
+ arrVar = argv[3];
+
+ /*
+ * this assignment assigns the table of result tuples into a giant
+ * array with the name given in the argument, the indices of the
+ * array or (tupno,attrName)
+ */
+ for (tupno = 0; tupno < PQntuples(result); tupno++)
+ {
+ for (i = 0; i < PQnfields(result); i++)
+ {
+ sprintf(arrayInd, "%d,%s", tupno, PQfname(result, i));
+ Tcl_SetVar2(interp, arrVar, arrayInd,
#ifdef TCL_ARRAYS
- tcl_value(PQgetvalue(result,tupno,i)),
+ tcl_value(PQgetvalue(result, tupno, i)),
#else
- PQgetvalue(result,tupno,i),
+ PQgetvalue(result, tupno, i),
#endif
- TCL_LEAVE_ERR_MSG);
- }
+ TCL_LEAVE_ERR_MSG);
+ }
+ }
+ Tcl_AppendResult(interp, arrVar, 0);
+ return TCL_OK;
}
- Tcl_AppendResult(interp, arrVar, 0);
- return TCL_OK;
- }
- else if (strcmp(opt, "-assignbyidx") == 0) {
- if (argc !=4 && argc != 5) {
- Tcl_AppendResult(interp, "-assignbyidx requires the array name and takes one optional argument as an append string",0);
- return TCL_ERROR;
- }
- arrVar = argv[3];
- /* this assignment assigns the table of result tuples into a giant
- array with the name given in the argument,
- the indices of the array or (tupno,attrName)*/
- if (argc == 5) {
- appendstr = argv[4];
- } else {
- appendstr = "";
- }
- for (tupno = 0; tupno<PQntuples(result); tupno++) {
- sprintf(prearrayInd,"%s",PQgetvalue(result,tupno,0));
- for (i=1;i<PQnfields(result);i++) {
- sprintf(arrayInd, "%s,%s%s", prearrayInd, PQfname(result,i),
- appendstr);
- Tcl_SetVar2(interp, arrVar, arrayInd,
- PQgetvalue(result,tupno,i),
- TCL_LEAVE_ERR_MSG);
- }
- }
- Tcl_AppendResult(interp, arrVar, 0);
- return TCL_OK;
- }
- else if (strcmp(opt, "-getTuple") == 0) {
- if (argc != 4) {
- Tcl_AppendResult(interp, "-getTuple option must be followed by a tuple number",0);
- return TCL_ERROR;
- }
- tupno = atoi(argv[3]);
-
- if (tupno >= PQntuples(result)) {
- Tcl_AppendResult(interp, "argument to getTuple cannot exceed number of tuples - 1",0);
- return TCL_ERROR;
+ else if (strcmp(opt, "-assignbyidx") == 0)
+ {
+ if (argc != 4 && argc != 5)
+ {
+ Tcl_AppendResult(interp, "-assignbyidx requires the array name and takes one optional argument as an append string", 0);
+ return TCL_ERROR;
+ }
+ arrVar = argv[3];
+
+ /*
+ * this assignment assigns the table of result tuples into a giant
+ * array with the name given in the argument, the indices of the
+ * array or (tupno,attrName)
+ */
+ if (argc == 5)
+ {
+ appendstr = argv[4];
+ }
+ else
+ {
+ appendstr = "";
+ }
+ for (tupno = 0; tupno < PQntuples(result); tupno++)
+ {
+ sprintf(prearrayInd, "%s", PQgetvalue(result, tupno, 0));
+ for (i = 1; i < PQnfields(result); i++)
+ {
+ sprintf(arrayInd, "%s,%s%s", prearrayInd, PQfname(result, i),
+ appendstr);
+ Tcl_SetVar2(interp, arrVar, arrayInd,
+ PQgetvalue(result, tupno, i),
+ TCL_LEAVE_ERR_MSG);
+ }
+ }
+ Tcl_AppendResult(interp, arrVar, 0);
+ return TCL_OK;
}
+ else if (strcmp(opt, "-getTuple") == 0)
+ {
+ if (argc != 4)
+ {
+ Tcl_AppendResult(interp, "-getTuple option must be followed by a tuple number", 0);
+ return TCL_ERROR;
+ }
+ tupno = atoi(argv[3]);
+
+ if (tupno >= PQntuples(result))
+ {
+ Tcl_AppendResult(interp, "argument to getTuple cannot exceed number of tuples - 1", 0);
+ return TCL_ERROR;
+ }
#ifdef TCL_ARRAYS
- for (i=0; i<PQnfields(result); i++) {
- Tcl_AppendElement(interp, tcl_value(PQgetvalue(result,tupno,i)));
- }
+ for (i = 0; i < PQnfields(result); i++)
+ {
+ Tcl_AppendElement(interp, tcl_value(PQgetvalue(result, tupno, i)));
+ }
#else
-/* Tcl_AppendResult(interp, PQgetvalue(result,tupno,0),NULL); */
- Tcl_AppendElement(interp, PQgetvalue(result,tupno,0));
- for (i=1;i<PQnfields(result);i++) {
-/* Tcl_AppendResult(interp, " ", PQgetvalue(result,tupno,i),NULL);*/
- Tcl_AppendElement(interp, PQgetvalue(result,tupno,i));
- }
+/* Tcl_AppendResult(interp, PQgetvalue(result,tupno,0),NULL); */
+ Tcl_AppendElement(interp, PQgetvalue(result, tupno, 0));
+ for (i = 1; i < PQnfields(result); i++)
+ {
+/* Tcl_AppendResult(interp, " ", PQgetvalue(result,tupno,i),NULL);*/
+ Tcl_AppendElement(interp, PQgetvalue(result, tupno, i));
+ }
#endif
- return TCL_OK;
- }
- else if (strcmp(opt, "-attributes") == 0) {
- Tcl_AppendResult(interp, PQfname(result,0),NULL);
- for (i=1;i<PQnfields(result);i++) {
- Tcl_AppendResult(interp, " ", PQfname(result,i), NULL);
- }
- return TCL_OK;
- }
- else if (strcmp(opt, "-lAttributes") == 0) {
- char buf[512];
- Tcl_ResetResult(interp);
- for (i = 0; i < PQnfields(result); i++) {
- sprintf(buf, "{%s} %ld %d", PQfname(result, i),
- (long) PQftype(result, i),
- PQfsize(result, i));
- Tcl_AppendElement(interp, buf);
- }
- return TCL_OK;
- }
- else if (strcmp(opt, "-numAttrs") == 0) {
- sprintf(interp->result, "%d", PQnfields(result));
- return TCL_OK;
- }
- else {
- Tcl_AppendResult(interp, "Invalid option",0);
- goto Pg_result_errReturn;
- }
-
-
- Pg_result_errReturn:
- Tcl_AppendResult(interp,
- "pg_result result ?option? where ?option is\n",
- "\t-status\n",
- "\t-conn\n",
- "\t-assign arrayVarName\n",
- "\t-assignbyidx arrayVarName ?appendstr?\n",
- "\t-numTuples\n",
- "\t-attributes\n"
- "\t-lAttributes\n"
- "\t-numAttrs\n"
- "\t-getTuple tupleNumber\n",
- "\t-clear\n",
- "\t-oid\n",
- 0);
- return TCL_ERROR;
-
+ return TCL_OK;
+ }
+ else if (strcmp(opt, "-attributes") == 0)
+ {
+ Tcl_AppendResult(interp, PQfname(result, 0), NULL);
+ for (i = 1; i < PQnfields(result); i++)
+ {
+ Tcl_AppendResult(interp, " ", PQfname(result, i), NULL);
+ }
+ return TCL_OK;
+ }
+ else if (strcmp(opt, "-lAttributes") == 0)
+ {
+ char buf[512];
+
+ Tcl_ResetResult(interp);
+ for (i = 0; i < PQnfields(result); i++)
+ {
+ sprintf(buf, "{%s} %ld %d", PQfname(result, i),
+ (long) PQftype(result, i),
+ PQfsize(result, i));
+ Tcl_AppendElement(interp, buf);
+ }
+ return TCL_OK;
+ }
+ else if (strcmp(opt, "-numAttrs") == 0)
+ {
+ sprintf(interp->result, "%d", PQnfields(result));
+ return TCL_OK;
+ }
+ else
+ {
+ Tcl_AppendResult(interp, "Invalid option", 0);
+ goto Pg_result_errReturn;
+ }
+
+
+Pg_result_errReturn:
+ Tcl_AppendResult(interp,
+ "pg_result result ?option? where ?option is\n",
+ "\t-status\n",
+ "\t-conn\n",
+ "\t-assign arrayVarName\n",
+ "\t-assignbyidx arrayVarName ?appendstr?\n",
+ "\t-numTuples\n",
+ "\t-attributes\n"
+ "\t-lAttributes\n"
+ "\t-numAttrs\n"
+ "\t-getTuple tupleNumber\n",
+ "\t-clear\n",
+ "\t-oid\n",
+ 0);
+ return TCL_ERROR;
+
}
/**********************************
* pg_lo_open
- open a large object
-
+ open a large object
+
syntax:
- pg_lo_open conn objOid mode
+ pg_lo_open conn objOid mode
where mode can be either 'r', 'w', or 'rw'
**********************/
int
-Pg_lo_open(ClientData cData, Tcl_Interp *interp, int argc, char* argv[])
+Pg_lo_open(ClientData cData, Tcl_Interp * interp, int argc, char *argv[])
{
- Pg_clientData *cd = (Pg_clientData *)cData;
- PGconn *conn;
- int lobjId;
- int mode;
- int fd;
-
- if (argc != 4) {
- Tcl_AppendResult(interp, "Wrong # of arguments\n",
- "pg_lo_open connection lobjOid mode", 0);
- return TCL_ERROR;
- }
-
- conn = PgGetConnectionId(cd, argv[1]);
- if (conn == (PGconn *)NULL) {
- Tcl_AppendResult(interp, "First argument is not a valid connection\n", 0);
- return TCL_ERROR;
- }
-
- lobjId = atoi(argv[2]);
- if (strlen(argv[3]) < 1 ||
- strlen(argv[3]) > 2)
- {
- Tcl_AppendResult(interp,"mode argument must be 'r', 'w', or 'rw'",0);
- return TCL_ERROR;
- }
- switch (argv[3][0]) {
- case 'r':
- case 'R':
- mode = INV_READ;
- break;
- case 'w':
- case 'W':
- mode = INV_WRITE;
- break;
- default:
- Tcl_AppendResult(interp,"mode argument must be 'r', 'w', or 'rw'",0);
- return TCL_ERROR;
- }
- switch (argv[3][1]) {
- case '\0':
- break;
- case 'r':
- case 'R':
- mode = mode & INV_READ;
- break;
- case 'w':
- case 'W':
- mode = mode & INV_WRITE;
- break;
- default:
- Tcl_AppendResult(interp,"mode argument must be 'r', 'w', or 'rw'",0);
- return TCL_ERROR;
- }
-
- fd = lo_open(conn,lobjId,mode);
- sprintf(interp->result,"%d",fd);
- return TCL_OK;
+ Pg_clientData *cd = (Pg_clientData *) cData;
+ PGconn *conn;
+ int lobjId;
+ int mode;
+ int fd;
+
+ if (argc != 4)
+ {
+ Tcl_AppendResult(interp, "Wrong # of arguments\n",
+ "pg_lo_open connection lobjOid mode", 0);
+ return TCL_ERROR;
+ }
+
+ conn = PgGetConnectionId(cd, argv[1]);
+ if (conn == (PGconn *) NULL)
+ {
+ Tcl_AppendResult(interp, "First argument is not a valid connection\n", 0);
+ return TCL_ERROR;
+ }
+
+ lobjId = atoi(argv[2]);
+ if (strlen(argv[3]) < 1 ||
+ strlen(argv[3]) > 2)
+ {
+ Tcl_AppendResult(interp, "mode argument must be 'r', 'w', or 'rw'", 0);
+ return TCL_ERROR;
+ }
+ switch (argv[3][0])
+ {
+ case 'r':
+ case 'R':
+ mode = INV_READ;
+ break;
+ case 'w':
+ case 'W':
+ mode = INV_WRITE;
+ break;
+ default:
+ Tcl_AppendResult(interp, "mode argument must be 'r', 'w', or 'rw'", 0);
+ return TCL_ERROR;
+ }
+ switch (argv[3][1])
+ {
+ case '\0':
+ break;
+ case 'r':
+ case 'R':
+ mode = mode & INV_READ;
+ break;
+ case 'w':
+ case 'W':
+ mode = mode & INV_WRITE;
+ break;
+ default:
+ Tcl_AppendResult(interp, "mode argument must be 'r', 'w', or 'rw'", 0);
+ return TCL_ERROR;
+ }
+
+ fd = lo_open(conn, lobjId, mode);
+ sprintf(interp->result, "%d", fd);
+ return TCL_OK;
}
/**********************************
* pg_lo_close
- close a large object
-
+ close a large object
+
syntax:
- pg_lo_close conn fd
+ pg_lo_close conn fd
**********************/
int
-Pg_lo_close(ClientData cData, Tcl_Interp *interp, int argc, char* argv[])
+Pg_lo_close(ClientData cData, Tcl_Interp * interp, int argc, char *argv[])
{
- Pg_clientData *cd = (Pg_clientData *)cData;
- PGconn *conn;
- int fd;
+ Pg_clientData *cd = (Pg_clientData *) cData;
+ PGconn *conn;
+ int fd;
- if (argc != 3) {
- Tcl_AppendResult(interp, "Wrong # of arguments\n",
- "pg_lo_close connection fd", 0);
- return TCL_ERROR;
- }
+ if (argc != 3)
+ {
+ Tcl_AppendResult(interp, "Wrong # of arguments\n",
+ "pg_lo_close connection fd", 0);
+ return TCL_ERROR;
+ }
- conn = PgGetConnectionId(cd, argv[1]);
- if (conn == (PGconn *)NULL) {
- Tcl_AppendResult(interp, "First argument is not a valid connection\n", 0);
- return TCL_ERROR;
- }
-
- fd = atoi(argv[2]);
- sprintf(interp->result,"%d",lo_close(conn,fd));
- return TCL_OK;
+ conn = PgGetConnectionId(cd, argv[1]);
+ if (conn == (PGconn *) NULL)
+ {
+ Tcl_AppendResult(interp, "First argument is not a valid connection\n", 0);
+ return TCL_ERROR;
+ }
+
+ fd = atoi(argv[2]);
+ sprintf(interp->result, "%d", lo_close(conn, fd));
+ return TCL_OK;
}
/**********************************
* pg_lo_read
- reads at most len bytes from a large object into a variable named
+ reads at most len bytes from a large object into a variable named
bufVar
-
+
syntax:
pg_lo_read conn fd bufVar len
@@ -743,98 +835,104 @@ Pg_lo_close(ClientData cData, Tcl_Interp *interp, int argc, char* argv[])
**********************/
int
-Pg_lo_read(ClientData cData, Tcl_Interp *interp, int argc, char* argv[])
+Pg_lo_read(ClientData cData, Tcl_Interp * interp, int argc, char *argv[])
{
- Pg_clientData *cd = (Pg_clientData *)cData;
- PGconn *conn;
- int fd;
- int nbytes = 0;
- char *buf;
- char *bufVar;
- int len;
-
- if (argc != 5) {
- Tcl_AppendResult(interp, "Wrong # of arguments\n",
- " pg_lo_read conn fd bufVar len", 0);
- return TCL_ERROR;
- }
+ Pg_clientData *cd = (Pg_clientData *) cData;
+ PGconn *conn;
+ int fd;
+ int nbytes = 0;
+ char *buf;
+ char *bufVar;
+ int len;
- conn = PgGetConnectionId(cd, argv[1]);
- if (conn == (PGconn *)NULL) {
- Tcl_AppendResult(interp, "First argument is not a valid connection\n", 0);
- return TCL_ERROR;
- }
-
- fd = atoi(argv[2]);
+ if (argc != 5)
+ {
+ Tcl_AppendResult(interp, "Wrong # of arguments\n",
+ " pg_lo_read conn fd bufVar len", 0);
+ return TCL_ERROR;
+ }
+
+ conn = PgGetConnectionId(cd, argv[1]);
+ if (conn == (PGconn *) NULL)
+ {
+ Tcl_AppendResult(interp, "First argument is not a valid connection\n", 0);
+ return TCL_ERROR;
+ }
- bufVar = argv[3];
+ fd = atoi(argv[2]);
- len = atoi(argv[4]);
+ bufVar = argv[3];
- if (len <= 0) {
- sprintf(interp->result,"%d",nbytes);
- return TCL_OK;
- }
- buf = malloc(sizeof(len+1));
+ len = atoi(argv[4]);
+
+ if (len <= 0)
+ {
+ sprintf(interp->result, "%d", nbytes);
+ return TCL_OK;
+ }
+ buf = malloc(sizeof(len + 1));
- nbytes = lo_read(conn,fd,buf,len);
+ nbytes = lo_read(conn, fd, buf, len);
+
+ Tcl_SetVar(interp, bufVar, buf, TCL_LEAVE_ERR_MSG);
+ sprintf(interp->result, "%d", nbytes);
+ free(buf);
+ return TCL_OK;
- Tcl_SetVar(interp,bufVar,buf,TCL_LEAVE_ERR_MSG);
- sprintf(interp->result,"%d",nbytes);
- free(buf);
- return TCL_OK;
-
}
/***********************************
Pg_lo_write
- write at most len bytes to a large object
+ write at most len bytes to a large object
syntax:
pg_lo_write conn fd buf len
***********************************/
int
-Pg_lo_write(ClientData cData, Tcl_Interp *interp, int argc, char* argv[])
+Pg_lo_write(ClientData cData, Tcl_Interp * interp, int argc, char *argv[])
{
- Pg_clientData *cd = (Pg_clientData *)cData;
- PGconn *conn;
- char *buf;
- int fd;
- int nbytes = 0;
- int len;
-
- if (argc != 5) {
- Tcl_AppendResult(interp, "Wrong # of arguments\n",
- "pg_lo_write conn fd buf len", 0);
- return TCL_ERROR;
- }
+ Pg_clientData *cd = (Pg_clientData *) cData;
+ PGconn *conn;
+ char *buf;
+ int fd;
+ int nbytes = 0;
+ int len;
- conn = PgGetConnectionId(cd, argv[1]);
- if (conn == (PGconn *)NULL) {
- Tcl_AppendResult(interp, "First argument is not a valid connection\n", 0);
- return TCL_ERROR;
- }
-
- fd = atoi(argv[2]);
+ if (argc != 5)
+ {
+ Tcl_AppendResult(interp, "Wrong # of arguments\n",
+ "pg_lo_write conn fd buf len", 0);
+ return TCL_ERROR;
+ }
+
+ conn = PgGetConnectionId(cd, argv[1]);
+ if (conn == (PGconn *) NULL)
+ {
+ Tcl_AppendResult(interp, "First argument is not a valid connection\n", 0);
+ return TCL_ERROR;
+ }
- buf = argv[3];
+ fd = atoi(argv[2]);
- len = atoi(argv[4]);
+ buf = argv[3];
- if (len <= 0) {
- sprintf(interp->result,"%d",nbytes);
- return TCL_OK;
- }
+ len = atoi(argv[4]);
- nbytes = lo_write(conn,fd,buf,len);
- sprintf(interp->result,"%d",nbytes);
- return TCL_OK;
+ if (len <= 0)
+ {
+ sprintf(interp->result, "%d", nbytes);
+ return TCL_OK;
+ }
+
+ nbytes = lo_write(conn, fd, buf, len);
+ sprintf(interp->result, "%d", nbytes);
+ return TCL_OK;
}
/***********************************
Pg_lo_lseek
- seek to a certain position in a large object
+ seek to a certain position in a large object
syntax
pg_lo_lseek conn fd offset whence
@@ -843,44 +941,54 @@ whence can be either
"SEEK_CUR", "SEEK_END", or "SEEK_SET"
***********************************/
int
-Pg_lo_lseek(ClientData cData, Tcl_Interp *interp, int argc, char* argv[])
+Pg_lo_lseek(ClientData cData, Tcl_Interp * interp, int argc, char *argv[])
{
- Pg_clientData *cd = (Pg_clientData *)cData;
- PGconn *conn;
- int fd;
- char *whenceStr;
- int offset, whence;
-
- if (argc != 5) {
- Tcl_AppendResult(interp, "Wrong # of arguments\n",
- "pg_lo_lseek conn fd offset whence", 0);
- return TCL_ERROR;
- }
+ Pg_clientData *cd = (Pg_clientData *) cData;
+ PGconn *conn;
+ int fd;
+ char *whenceStr;
+ int offset,
+ whence;
- conn = PgGetConnectionId(cd, argv[1]);
- if (conn == (PGconn *)NULL) {
- Tcl_AppendResult(interp, "First argument is not a valid connection\n", 0);
- return TCL_ERROR;
- }
-
- fd = atoi(argv[2]);
-
- offset = atoi(argv[3]);
-
- whenceStr = argv[4];
- if (strcmp(whenceStr,"SEEK_SET") == 0) {
- whence = SEEK_SET;
- } else if (strcmp(whenceStr,"SEEK_CUR") == 0) {
- whence = SEEK_CUR;
- } else if (strcmp(whenceStr,"SEEK_END") == 0) {
- whence = SEEK_END;
- } else {
- Tcl_AppendResult(interp, "the whence argument to Pg_lo_lseek must be SEEK_SET, SEEK_CUR or SEEK_END",0);
- return TCL_ERROR;
- }
-
- sprintf(interp->result,"%d",lo_lseek(conn,fd,offset,whence));
- return TCL_OK;
+ if (argc != 5)
+ {
+ Tcl_AppendResult(interp, "Wrong # of arguments\n",
+ "pg_lo_lseek conn fd offset whence", 0);
+ return TCL_ERROR;
+ }
+
+ conn = PgGetConnectionId(cd, argv[1]);
+ if (conn == (PGconn *) NULL)
+ {
+ Tcl_AppendResult(interp, "First argument is not a valid connection\n", 0);
+ return TCL_ERROR;
+ }
+
+ fd = atoi(argv[2]);
+
+ offset = atoi(argv[3]);
+
+ whenceStr = argv[4];
+ if (strcmp(whenceStr, "SEEK_SET") == 0)
+ {
+ whence = SEEK_SET;
+ }
+ else if (strcmp(whenceStr, "SEEK_CUR") == 0)
+ {
+ whence = SEEK_CUR;
+ }
+ else if (strcmp(whenceStr, "SEEK_END") == 0)
+ {
+ whence = SEEK_END;
+ }
+ else
+ {
+ Tcl_AppendResult(interp, "the whence argument to Pg_lo_lseek must be SEEK_SET, SEEK_CUR or SEEK_END", 0);
+ return TCL_ERROR;
+ }
+
+ sprintf(interp->result, "%d", lo_lseek(conn, fd, offset, whence));
+ return TCL_OK;
}
@@ -896,97 +1004,116 @@ for now, we don't support any additional storage managers.
***********************************/
int
-Pg_lo_creat(ClientData cData, Tcl_Interp *interp, int argc, char* argv[])
+Pg_lo_creat(ClientData cData, Tcl_Interp * interp, int argc, char *argv[])
{
- Pg_clientData *cd = (Pg_clientData *)cData;
- PGconn *conn;
- char *modeStr;
- char *modeWord;
- int mode;
-
- if (argc != 3) {
- Tcl_AppendResult(interp, "Wrong # of arguments\n",
- "pg_lo_creat conn mode", 0);
- return TCL_ERROR;
- }
+ Pg_clientData *cd = (Pg_clientData *) cData;
+ PGconn *conn;
+ char *modeStr;
+ char *modeWord;
+ int mode;
- conn = PgGetConnectionId(cd, argv[1]);
- if (conn == (PGconn *)NULL) {
- Tcl_AppendResult(interp, "First argument is not a valid connection\n", 0);
- return TCL_ERROR;
- }
-
- modeStr = argv[2];
-
- modeWord = strtok(modeStr,"|");
- if (strcmp(modeWord,"INV_READ") == 0) {
- mode = INV_READ;
- } else if (strcmp(modeWord,"INV_WRITE") == 0) {
- mode = INV_WRITE;
- } else if (strcmp(modeWord,"INV_ARCHIVE") == 0) {
- mode = INV_ARCHIVE;
- } else {
- Tcl_AppendResult(interp,
- "invalid mode argument to Pg_lo_creat\nmode argument must be some OR'd combination of INV_READ, INV_WRITE, and INV_ARCHIVE",
- 0);
- return TCL_ERROR;
- }
-
- while ( (modeWord = strtok((char*)NULL, "|")) != NULL) {
- if (strcmp(modeWord,"INV_READ") == 0) {
- mode |= INV_READ;
- } else if (strcmp(modeWord,"INV_WRITE") == 0) {
- mode |= INV_WRITE;
- } else if (strcmp(modeWord,"INV_ARCHIVE") == 0) {
- mode |= INV_ARCHIVE;
- } else {
- Tcl_AppendResult(interp,
- "invalid mode argument to Pg_lo_creat\nmode argument must be some OR'd combination of INV_READ, INV_WRITE, and INV_ARCHIVE",
- 0);
- return TCL_ERROR;
- }
- }
- sprintf(interp->result,"%d",lo_creat(conn,mode));
- return TCL_OK;
+ if (argc != 3)
+ {
+ Tcl_AppendResult(interp, "Wrong # of arguments\n",
+ "pg_lo_creat conn mode", 0);
+ return TCL_ERROR;
+ }
+
+ conn = PgGetConnectionId(cd, argv[1]);
+ if (conn == (PGconn *) NULL)
+ {
+ Tcl_AppendResult(interp, "First argument is not a valid connection\n", 0);
+ return TCL_ERROR;
+ }
+
+ modeStr = argv[2];
+
+ modeWord = strtok(modeStr, "|");
+ if (strcmp(modeWord, "INV_READ") == 0)
+ {
+ mode = INV_READ;
+ }
+ else if (strcmp(modeWord, "INV_WRITE") == 0)
+ {
+ mode = INV_WRITE;
+ }
+ else if (strcmp(modeWord, "INV_ARCHIVE") == 0)
+ {
+ mode = INV_ARCHIVE;
+ }
+ else
+ {
+ Tcl_AppendResult(interp,
+ "invalid mode argument to Pg_lo_creat\nmode argument must be some OR'd combination of INV_READ, INV_WRITE, and INV_ARCHIVE",
+ 0);
+ return TCL_ERROR;
+ }
+
+ while ((modeWord = strtok((char *) NULL, "|")) != NULL)
+ {
+ if (strcmp(modeWord, "INV_READ") == 0)
+ {
+ mode |= INV_READ;
+ }
+ else if (strcmp(modeWord, "INV_WRITE") == 0)
+ {
+ mode |= INV_WRITE;
+ }
+ else if (strcmp(modeWord, "INV_ARCHIVE") == 0)
+ {
+ mode |= INV_ARCHIVE;
+ }
+ else
+ {
+ Tcl_AppendResult(interp,
+ "invalid mode argument to Pg_lo_creat\nmode argument must be some OR'd combination of INV_READ, INV_WRITE, and INV_ARCHIVE",
+ 0);
+ return TCL_ERROR;
+ }
+ }
+ sprintf(interp->result, "%d", lo_creat(conn, mode));
+ return TCL_OK;
}
/***********************************
Pg_lo_tell
- returns the current seek location of the large object
+ returns the current seek location of the large object
syntax:
pg_lo_tell conn fd
***********************************/
int
-Pg_lo_tell(ClientData cData, Tcl_Interp *interp, int argc, char* argv[])
+Pg_lo_tell(ClientData cData, Tcl_Interp * interp, int argc, char *argv[])
{
- Pg_clientData *cd = (Pg_clientData *)cData;
- PGconn *conn;
- int fd;
+ Pg_clientData *cd = (Pg_clientData *) cData;
+ PGconn *conn;
+ int fd;
- if (argc != 3) {
- Tcl_AppendResult(interp, "Wrong # of arguments\n",
- "pg_lo_tell conn fd", 0);
- return TCL_ERROR;
- }
+ if (argc != 3)
+ {
+ Tcl_AppendResult(interp, "Wrong # of arguments\n",
+ "pg_lo_tell conn fd", 0);
+ return TCL_ERROR;
+ }
- conn = PgGetConnectionId(cd, argv[1]);
- if (conn == (PGconn *)NULL) {
- Tcl_AppendResult(interp, "First argument is not a valid connection\n", 0);
- return TCL_ERROR;
- }
-
- fd = atoi(argv[2]);
+ conn = PgGetConnectionId(cd, argv[1]);
+ if (conn == (PGconn *) NULL)
+ {
+ Tcl_AppendResult(interp, "First argument is not a valid connection\n", 0);
+ return TCL_ERROR;
+ }
- sprintf(interp->result,"%d",lo_tell(conn,fd));
- return TCL_OK;
+ fd = atoi(argv[2]);
+
+ sprintf(interp->result, "%d", lo_tell(conn, fd));
+ return TCL_OK;
}
/***********************************
Pg_lo_unlink
- unlink a file based on lobject id
+ unlink a file based on lobject id
syntax:
pg_lo_unlink conn lobjId
@@ -994,40 +1121,43 @@ Pg_lo_unlink
***********************************/
int
-Pg_lo_unlink(ClientData cData, Tcl_Interp *interp, int argc, char* argv[])
+Pg_lo_unlink(ClientData cData, Tcl_Interp * interp, int argc, char *argv[])
{
- Pg_clientData *cd = (Pg_clientData *)cData;
- PGconn *conn;
- int lobjId;
- int retval;
-
- if (argc != 3) {
- Tcl_AppendResult(interp, "Wrong # of arguments\n",
- "pg_lo_tell conn fd", 0);
- return TCL_ERROR;
- }
+ Pg_clientData *cd = (Pg_clientData *) cData;
+ PGconn *conn;
+ int lobjId;
+ int retval;
- conn = PgGetConnectionId(cd, argv[1]);
- if (conn == (PGconn *)NULL) {
- Tcl_AppendResult(interp, "First argument is not a valid connection\n", 0);
- return TCL_ERROR;
- }
-
- lobjId = atoi(argv[2]);
+ if (argc != 3)
+ {
+ Tcl_AppendResult(interp, "Wrong # of arguments\n",
+ "pg_lo_tell conn fd", 0);
+ return TCL_ERROR;
+ }
- retval = lo_unlink(conn,lobjId);
- if (retval == -1) {
- sprintf(interp->result,"Pg_lo_unlink of '%d' failed",lobjId);
- return TCL_ERROR;
- }
-
- sprintf(interp->result,"%d",retval);
- return TCL_OK;
+ conn = PgGetConnectionId(cd, argv[1]);
+ if (conn == (PGconn *) NULL)
+ {
+ Tcl_AppendResult(interp, "First argument is not a valid connection\n", 0);
+ return TCL_ERROR;
+ }
+
+ lobjId = atoi(argv[2]);
+
+ retval = lo_unlink(conn, lobjId);
+ if (retval == -1)
+ {
+ sprintf(interp->result, "Pg_lo_unlink of '%d' failed", lobjId);
+ return TCL_ERROR;
+ }
+
+ sprintf(interp->result, "%d", retval);
+ return TCL_OK;
}
/***********************************
Pg_lo_import
- import a Unix file into an (inversion) large objct
+ import a Unix file into an (inversion) large objct
returns the oid of that object upon success
returns InvalidOid upon failure
@@ -1037,81 +1167,87 @@ Pg_lo_import
***********************************/
int
-Pg_lo_import(ClientData cData, Tcl_Interp *interp, int argc, char* argv[])
+Pg_lo_import(ClientData cData, Tcl_Interp * interp, int argc, char *argv[])
{
- Pg_clientData *cd = (Pg_clientData *)cData;
- PGconn *conn;
- char* filename;
- Oid lobjId;
-
- if (argc != 3) {
- Tcl_AppendResult(interp, "Wrong # of arguments\n",
- "pg_lo_import conn filename", 0);
- return TCL_ERROR;
- }
+ Pg_clientData *cd = (Pg_clientData *) cData;
+ PGconn *conn;
+ char *filename;
+ Oid lobjId;
- conn = PgGetConnectionId(cd, argv[1]);
- if (conn == (PGconn *)NULL) {
- Tcl_AppendResult(interp, "First argument is not a valid connection\n", 0);
- return TCL_ERROR;
- }
-
- filename = argv[2];
+ if (argc != 3)
+ {
+ Tcl_AppendResult(interp, "Wrong # of arguments\n",
+ "pg_lo_import conn filename", 0);
+ return TCL_ERROR;
+ }
- lobjId = lo_import(conn,filename);
- if (lobjId == InvalidOid) {
- sprintf(interp->result, "Pg_lo_import of '%s' failed",filename);
- return TCL_ERROR;
- }
- sprintf(interp->result,"%d",lobjId);
- return TCL_OK;
+ conn = PgGetConnectionId(cd, argv[1]);
+ if (conn == (PGconn *) NULL)
+ {
+ Tcl_AppendResult(interp, "First argument is not a valid connection\n", 0);
+ return TCL_ERROR;
+ }
+
+ filename = argv[2];
+
+ lobjId = lo_import(conn, filename);
+ if (lobjId == InvalidOid)
+ {
+ sprintf(interp->result, "Pg_lo_import of '%s' failed", filename);
+ return TCL_ERROR;
+ }
+ sprintf(interp->result, "%d", lobjId);
+ return TCL_OK;
}
/***********************************
Pg_lo_export
- export an Inversion large object to a Unix file
-
+ export an Inversion large object to a Unix file
+
syntax:
pg_lo_export conn lobjId filename
***********************************/
int
-Pg_lo_export(ClientData cData, Tcl_Interp *interp, int argc, char* argv[])
+Pg_lo_export(ClientData cData, Tcl_Interp * interp, int argc, char *argv[])
{
- Pg_clientData *cd = (Pg_clientData *)cData;
- PGconn *conn;
- char* filename;
- Oid lobjId;
- int retval;
-
- if (argc != 4) {
- Tcl_AppendResult(interp, "Wrong # of arguments\n",
- "pg_lo_export conn lobjId filename", 0);
- return TCL_ERROR;
- }
+ Pg_clientData *cd = (Pg_clientData *) cData;
+ PGconn *conn;
+ char *filename;
+ Oid lobjId;
+ int retval;
- conn = PgGetConnectionId(cd, argv[1]);
- if (conn == (PGconn *)NULL) {
- Tcl_AppendResult(interp, "First argument is not a valid connection\n", 0);
- return TCL_ERROR;
- }
-
- lobjId = atoi(argv[2]);
- filename = argv[3];
-
- retval = lo_export(conn,lobjId,filename);
- if (retval == -1) {
- sprintf(interp->result, "Pg_lo_export %d %s failed",lobjId, filename);
- return TCL_ERROR;
- }
- return TCL_OK;
+ if (argc != 4)
+ {
+ Tcl_AppendResult(interp, "Wrong # of arguments\n",
+ "pg_lo_export conn lobjId filename", 0);
+ return TCL_ERROR;
+ }
+
+ conn = PgGetConnectionId(cd, argv[1]);
+ if (conn == (PGconn *) NULL)
+ {
+ Tcl_AppendResult(interp, "First argument is not a valid connection\n", 0);
+ return TCL_ERROR;
+ }
+
+ lobjId = atoi(argv[2]);
+ filename = argv[3];
+
+ retval = lo_export(conn, lobjId, filename);
+ if (retval == -1)
+ {
+ sprintf(interp->result, "Pg_lo_export %d %s failed", lobjId, filename);
+ return TCL_ERROR;
+ }
+ return TCL_OK;
}
/**********************************
* pg_select
send a select query string to the backend connection
-
+
syntax:
pg_select connection query var proc
@@ -1121,7 +1257,7 @@ Pg_lo_export(ClientData cData, Tcl_Interp *interp, int argc, char* argv[])
Originally I was also going to update changes but that has turned out
to be not so simple. Instead, the caller should get the OID of any
- table they want to update and update it themself in the loop. I may
+ table they want to update and update it themself in the loop. I may
try to write a simplified table lookup and update function to make
that task a little easier.
@@ -1130,41 +1266,45 @@ Pg_lo_export(ClientData cData, Tcl_Interp *interp, int argc, char* argv[])
**********************************/
int
-Pg_select(ClientData cData, Tcl_Interp *interp, int argc, char **argv)
+Pg_select(ClientData cData, Tcl_Interp * interp, int argc, char **argv)
{
- Pg_clientData *cd = (Pg_clientData *)cData;
- PGconn *conn;
- PGresult *result;
- int r;
- size_t tupno, column, ncols;
- Tcl_DString headers;
- char buffer[2048];
- struct {
- char *cname;
- int change;
- } *info;
+ Pg_clientData *cd = (Pg_clientData *) cData;
+ PGconn *conn;
+ PGresult *result;
+ int r;
+ size_t tupno,
+ column,
+ ncols;
+ Tcl_DString headers;
+ char buffer[2048];
+ struct
+ {
+ char *cname;
+ int change;
+ } *info;
if (argc != 5)
{
Tcl_AppendResult(interp, "Wrong # of arguments\n",
- "pg_select connection queryString var proc", 0);
+ "pg_select connection queryString var proc", 0);
+ return TCL_ERROR;
+ }
+
+ conn = PgGetConnectionId(cd, argv[1]);
+ if (conn == (PGconn *) NULL)
+ {
+ Tcl_AppendResult(interp, "First argument is not a valid connection\n", 0);
return TCL_ERROR;
}
- conn = PgGetConnectionId(cd, argv[1]);
- if (conn == (PGconn *)NULL) {
- Tcl_AppendResult(interp, "First argument is not a valid connection\n", 0);
- return TCL_ERROR;
- }
-
if ((result = PQexec(conn, argv[2])) == 0)
- {
+ {
/* error occurred during the query */
Tcl_SetResult(interp, conn->errorMessage, TCL_STATIC);
return TCL_ERROR;
- }
+ }
- if ((info = malloc(sizeof(*info) * (ncols = PQnfields(result)))) == NULL)
+ if ((info = malloc(sizeof(*info) * (ncols = PQnfields(result)))) == NULL)
{
Tcl_AppendResult(interp, "Not enough memory", 0);
return TCL_ERROR;
@@ -1203,10 +1343,10 @@ Pg_select(ClientData cData, Tcl_Interp *interp, int argc, char **argv)
if (r == TCL_ERROR)
{
- char msg[60];
+ char msg[60];
sprintf(msg, "\n (\"pg_select\" body line %d)",
- interp->errorLine);
+ interp->errorLine);
Tcl_AddErrorInfo(interp, msg);
}
@@ -1221,142 +1361,160 @@ Pg_select(ClientData cData, Tcl_Interp *interp, int argc, char **argv)
}
int
-Pg_listen(ClientData cData, Tcl_Interp *interp, int argc, char* argv[])
+Pg_listen(ClientData cData, Tcl_Interp * interp, int argc, char *argv[])
{
- Pg_clientData *cd = (Pg_clientData *)cData;
- int new;
- char *relname;
- char *callback = NULL;
- Tcl_HashEntry *entry;
- PGconn *conn;
- PGresult *result;
-
- if ((argc < 3) || (argc > 4)) {
- Tcl_AppendResult(interp, "wrong # args, should be \"",
- argv[0], " connection relname ?callback?\"", 0);
- return TCL_ERROR;
- }
-
- /*
- * Get the command arguments. Note that relname will copied by
- * Tcl_CreateHashEntry while callback must be allocated.
- */
- conn = (PGconn*)PgGetConnectionId(cd, argv[1]);
- if (conn == (PGconn *)NULL) {
- Tcl_AppendResult(interp, "First argument is not a valid connection\n", 0);
- return TCL_ERROR;
- }
- relname = argv[2];
- if ((argc > 3) && *argv[3]) {
- callback = (char *) ckalloc((unsigned) (strlen(argv[3])+1));
- strcpy(callback, argv[3]);
- }
-
- /*
- * Set or update a callback for a relation;
- */
- if (callback) {
- entry = Tcl_CreateHashEntry(&(cd->notify_hash), relname, &new);
- if (new) {
- /* New callback, execute a listen command on the relation */
- char *cmd = (char *) ckalloc((unsigned) (strlen(argv[2])+8));
- sprintf(cmd, "LISTEN %s", relname);
- result = PQexec(conn, cmd);
- ckfree(cmd);
- if (!result || (result->resultStatus != PGRES_COMMAND_OK)) {
- /* Error occurred during the execution of command */
- if (result) PQclear(result);
- ckfree(callback);
- Tcl_DeleteHashEntry(entry);
- Tcl_SetResult(interp, conn->errorMessage, TCL_STATIC);
+ Pg_clientData *cd = (Pg_clientData *) cData;
+ int new;
+ char *relname;
+ char *callback = NULL;
+ Tcl_HashEntry *entry;
+ PGconn *conn;
+ PGresult *result;
+
+ if ((argc < 3) || (argc > 4))
+ {
+ Tcl_AppendResult(interp, "wrong # args, should be \"",
+ argv[0], " connection relname ?callback?\"", 0);
+ return TCL_ERROR;
+ }
+
+ /*
+ * Get the command arguments. Note that relname will copied by
+ * Tcl_CreateHashEntry while callback must be allocated.
+ */
+ conn = (PGconn *) PgGetConnectionId(cd, argv[1]);
+ if (conn == (PGconn *) NULL)
+ {
+ Tcl_AppendResult(interp, "First argument is not a valid connection\n", 0);
return TCL_ERROR;
- }
- PQclear(result);
- } else {
- /* Free the old callback string */
- ckfree((char *) Tcl_GetHashValue(entry));
- }
- /* Store the new callback command */
- Tcl_SetHashValue(entry, callback);
- }
-
- /*
- * Remove a callback for a relation. There is no way to
- * un-listen a relation, simply remove the callback from
- * the notify hash table.
- */
- if (callback == NULL) {
- entry = Tcl_FindHashEntry(&(cd->notify_hash), relname);
- if (entry == NULL) {
- Tcl_AppendResult(interp, "not listening on ", relname, 0);
- return TCL_ERROR;
- }
- ckfree((char *) Tcl_GetHashValue(entry));
- Tcl_DeleteHashEntry(entry);
- }
-
- return TCL_OK;
+ }
+ relname = argv[2];
+ if ((argc > 3) && *argv[3])
+ {
+ callback = (char *) ckalloc((unsigned) (strlen(argv[3]) + 1));
+ strcpy(callback, argv[3]);
+ }
+
+ /*
+ * Set or update a callback for a relation;
+ */
+ if (callback)
+ {
+ entry = Tcl_CreateHashEntry(&(cd->notify_hash), relname, &new);
+ if (new)
+ {
+ /* New callback, execute a listen command on the relation */
+ char *cmd = (char *) ckalloc((unsigned) (strlen(argv[2]) + 8));
+
+ sprintf(cmd, "LISTEN %s", relname);
+ result = PQexec(conn, cmd);
+ ckfree(cmd);
+ if (!result || (result->resultStatus != PGRES_COMMAND_OK))
+ {
+ /* Error occurred during the execution of command */
+ if (result)
+ PQclear(result);
+ ckfree(callback);
+ Tcl_DeleteHashEntry(entry);
+ Tcl_SetResult(interp, conn->errorMessage, TCL_STATIC);
+ return TCL_ERROR;
+ }
+ PQclear(result);
+ }
+ else
+ {
+ /* Free the old callback string */
+ ckfree((char *) Tcl_GetHashValue(entry));
+ }
+ /* Store the new callback command */
+ Tcl_SetHashValue(entry, callback);
+ }
+
+ /*
+ * Remove a callback for a relation. There is no way to un-listen a
+ * relation, simply remove the callback from the notify hash table.
+ */
+ if (callback == NULL)
+ {
+ entry = Tcl_FindHashEntry(&(cd->notify_hash), relname);
+ if (entry == NULL)
+ {
+ Tcl_AppendResult(interp, "not listening on ", relname, 0);
+ return TCL_ERROR;
+ }
+ ckfree((char *) Tcl_GetHashValue(entry));
+ Tcl_DeleteHashEntry(entry);
+ }
+
+ return TCL_OK;
}
int
-Pg_notifies(ClientData cData, Tcl_Interp *interp, int argc, char* argv[])
+Pg_notifies(ClientData cData, Tcl_Interp * interp, int argc, char *argv[])
{
- Pg_clientData *cd = (Pg_clientData *)cData;
- int count;
- char buff[12];
- char *callback;
- Tcl_HashEntry *entry;
- PGconn *conn;
- PGresult *result;
- PGnotify *notify;
-
- if (argc != 2) {
- Tcl_AppendResult(interp, "wrong # args, should be \"",
- argv[0], " connection\"", 0);
- return TCL_ERROR;
- }
-
- /*
- * Get the connection argument.
- */
- conn = (PGconn*)PgGetConnectionId(cd, argv[1]);
- if (conn == (PGconn *)NULL) {
- Tcl_AppendResult(interp, "First argument is not a valid connection\n", 0);
- return TCL_ERROR;
- }
-
- /* Execute an empty command to retrieve asynchronous notifications */
- result = PQexec(conn, " ");
- if (result == NULL) {
- /* Error occurred during the execution of command */
- Tcl_SetResult(interp, conn->errorMessage, TCL_STATIC);
- return TCL_ERROR;
- }
- PQclear(result);
-
- /*
- * Loop while there are pending notifies.
- */
- for (count=0; count < 999; count++) {
- /* See if there is a pending notification */
- notify = PQnotifies(conn);
- if (notify == NULL) {
- break;
- }
- entry = Tcl_FindHashEntry(&(cd->notify_hash), notify->relname);
- if (entry != NULL) {
- callback = Tcl_GetHashValue(entry);
- if (callback) {
- Tcl_Eval(interp, callback);
- }
- }
- free(notify);
- }
-
- /*
- * Return the number of notifications processed.
- */
- sprintf(buff, "%d", count);
- Tcl_SetResult(interp, buff, TCL_VOLATILE);
- return TCL_OK;
+ Pg_clientData *cd = (Pg_clientData *) cData;
+ int count;
+ char buff[12];
+ char *callback;
+ Tcl_HashEntry *entry;
+ PGconn *conn;
+ PGresult *result;
+ PGnotify *notify;
+
+ if (argc != 2)
+ {
+ Tcl_AppendResult(interp, "wrong # args, should be \"",
+ argv[0], " connection\"", 0);
+ return TCL_ERROR;
+ }
+
+ /*
+ * Get the connection argument.
+ */
+ conn = (PGconn *) PgGetConnectionId(cd, argv[1]);
+ if (conn == (PGconn *) NULL)
+ {
+ Tcl_AppendResult(interp, "First argument is not a valid connection\n", 0);
+ return TCL_ERROR;
+ }
+
+ /* Execute an empty command to retrieve asynchronous notifications */
+ result = PQexec(conn, " ");
+ if (result == NULL)
+ {
+ /* Error occurred during the execution of command */
+ Tcl_SetResult(interp, conn->errorMessage, TCL_STATIC);
+ return TCL_ERROR;
+ }
+ PQclear(result);
+
+ /*
+ * Loop while there are pending notifies.
+ */
+ for (count = 0; count < 999; count++)
+ {
+ /* See if there is a pending notification */
+ notify = PQnotifies(conn);
+ if (notify == NULL)
+ {
+ break;
+ }
+ entry = Tcl_FindHashEntry(&(cd->notify_hash), notify->relname);
+ if (entry != NULL)
+ {
+ callback = Tcl_GetHashValue(entry);
+ if (callback)
+ {
+ Tcl_Eval(interp, callback);
+ }
+ }
+ free(notify);
+ }
+
+ /*
+ * Return the number of notifications processed.
+ */
+ sprintf(buff, "%d", count);
+ Tcl_SetResult(interp, buff, TCL_VOLATILE);
+ return TCL_OK;
}
diff --git a/src/interfaces/libpgtcl/pgtclCmds.h b/src/interfaces/libpgtcl/pgtclCmds.h
index de69ad2e14c..f1e5755641f 100644
--- a/src/interfaces/libpgtcl/pgtclCmds.h
+++ b/src/interfaces/libpgtcl/pgtclCmds.h
@@ -1,11 +1,11 @@
/*-------------------------------------------------------------------------
*
* pgtclCmds.h--
- * declarations for the C functions which implement pg_* tcl commands
+ * declarations for the C functions which implement pg_* tcl commands
*
* Copyright (c) 1994, Regents of the University of California
*
- * $Id: pgtclCmds.h,v 1.6 1997/01/03 18:48:31 scrappy Exp $
+ * $Id: pgtclCmds.h,v 1.7 1997/09/07 05:03:12 momjian Exp $
*
*-------------------------------------------------------------------------
*/
@@ -18,69 +18,89 @@
#include "libpq-fe.h"
#include "libpq/libpq-fs.h"
-typedef struct Pg_clientData_s {
- Tcl_HashTable dbh_hash;
- Tcl_HashTable res_hash;
- Tcl_HashTable notify_hash;
- long dbh_count;
- long res_count;
-} Pg_clientData;
+typedef struct Pg_clientData_s
+{
+ Tcl_HashTable dbh_hash;
+ Tcl_HashTable res_hash;
+ Tcl_HashTable notify_hash;
+ long dbh_count;
+ long res_count;
+} Pg_clientData;
-typedef struct Pg_ConnectionId_s {
- char id[32];
- PGconn *conn;
- Tcl_HashTable res_hash;
-} Pg_ConnectionId;
+typedef struct Pg_ConnectionId_s
+{
+ char id[32];
+ PGconn *conn;
+ Tcl_HashTable res_hash;
+} Pg_ConnectionId;
-typedef struct Pg_ResultId_s {
- char id[32];
- PGresult *result;
- Pg_ConnectionId *connection;
-} Pg_ResultId;
+typedef struct Pg_ResultId_s
+{
+ char id[32];
+ PGresult *result;
+ Pg_ConnectionId *connection;
+} Pg_ResultId;
/* **************************/
/* registered Tcl functions */
/* **************************/
-extern int Pg_conndefaults(
- ClientData cData, Tcl_Interp *interp, int argc, char* argv[]);
-extern int Pg_connect(
- ClientData cData, Tcl_Interp *interp, int argc, char* argv[]);
-extern int Pg_disconnect(
- ClientData cData, Tcl_Interp *interp, int argc, char* argv[]);
-extern int Pg_exec(
- ClientData cData, Tcl_Interp *interp, int argc, char* argv[]);
-extern int Pg_select(
- ClientData cData, Tcl_Interp *interp, int argc, char* argv[]);
-extern int Pg_result(
- ClientData cData, Tcl_Interp *interp, int argc, char* argv[]);
-extern int Pg_lo_open(
- ClientData cData, Tcl_Interp *interp, int argc, char* argv[]);
-extern int Pg_lo_close(
- ClientData cData, Tcl_Interp *interp, int argc, char* argv[]);
-extern int Pg_lo_read(
- ClientData cData, Tcl_Interp *interp, int argc, char* argv[]);
-extern int Pg_lo_write(
- ClientData cData, Tcl_Interp *interp, int argc, char* argv[]);
-extern int Pg_lo_lseek(
- ClientData cData, Tcl_Interp *interp, int argc, char* argv[]);
-extern int Pg_lo_creat(
- ClientData cData, Tcl_Interp *interp, int argc, char* argv[]);
-extern int Pg_lo_tell(
- ClientData cData, Tcl_Interp *interp, int argc, char* argv[]);
-extern int Pg_lo_unlink(
- ClientData cData, Tcl_Interp *interp, int argc, char* argv[]);
-extern int Pg_lo_import(
- ClientData cData, Tcl_Interp *interp, int argc, char* argv[]);
-extern int Pg_lo_export(
- ClientData cData, Tcl_Interp *interp, int argc, char* argv[]);
-extern int Pg_listen(
- ClientData cData, Tcl_Interp *interp, int argc, char* argv[]);
-extern int Pg_notifies(
- ClientData cData, Tcl_Interp *interp, int argc, char* argv[]);
+extern int
+Pg_conndefaults(
+ ClientData cData, Tcl_Interp * interp, int argc, char *argv[]);
+extern int
+Pg_connect(
+ ClientData cData, Tcl_Interp * interp, int argc, char *argv[]);
+extern int
+Pg_disconnect(
+ ClientData cData, Tcl_Interp * interp, int argc, char *argv[]);
+extern int
+Pg_exec(
+ ClientData cData, Tcl_Interp * interp, int argc, char *argv[]);
+extern int
+Pg_select(
+ ClientData cData, Tcl_Interp * interp, int argc, char *argv[]);
+extern int
+Pg_result(
+ ClientData cData, Tcl_Interp * interp, int argc, char *argv[]);
+extern int
+Pg_lo_open(
+ ClientData cData, Tcl_Interp * interp, int argc, char *argv[]);
+extern int
+Pg_lo_close(
+ ClientData cData, Tcl_Interp * interp, int argc, char *argv[]);
+extern int
+Pg_lo_read(
+ ClientData cData, Tcl_Interp * interp, int argc, char *argv[]);
+extern int
+Pg_lo_write(
+ ClientData cData, Tcl_Interp * interp, int argc, char *argv[]);
+extern int
+Pg_lo_lseek(
+ ClientData cData, Tcl_Interp * interp, int argc, char *argv[]);
+extern int
+Pg_lo_creat(
+ ClientData cData, Tcl_Interp * interp, int argc, char *argv[]);
+extern int
+Pg_lo_tell(
+ ClientData cData, Tcl_Interp * interp, int argc, char *argv[]);
+extern int
+Pg_lo_unlink(
+ ClientData cData, Tcl_Interp * interp, int argc, char *argv[]);
+extern int
+Pg_lo_import(
+ ClientData cData, Tcl_Interp * interp, int argc, char *argv[]);
+extern int
+Pg_lo_export(
+ ClientData cData, Tcl_Interp * interp, int argc, char *argv[]);
+extern int
+Pg_listen(
+ ClientData cData, Tcl_Interp * interp, int argc, char *argv[]);
+extern int
+Pg_notifies(
+ ClientData cData, Tcl_Interp * interp, int argc, char *argv[]);
-#endif /*PGTCLCMDS_H*/
-
+#endif /* PGTCLCMDS_H */
diff --git a/src/interfaces/libpgtcl/pgtclId.c b/src/interfaces/libpgtcl/pgtclId.c
index f39342c002e..d6265974b43 100644
--- a/src/interfaces/libpgtcl/pgtclId.c
+++ b/src/interfaces/libpgtcl/pgtclId.c
@@ -1,18 +1,18 @@
/*-------------------------------------------------------------------------
*
* pgtclId.c--
- * useful routines to convert between strings and pointers
- * Needed because everything in tcl is a string, but we want pointers
- * to data structures
+ * useful routines to convert between strings and pointers
+ * Needed because everything in tcl is a string, but we want pointers
+ * to data structures
*
- * ASSUMPTION: sizeof(long) >= sizeof(void*)
+ * ASSUMPTION: sizeof(long) >= sizeof(void*)
*
*
* Copyright (c) 1994, Regents of the University of California
*
*
* IDENTIFICATION
- * $Header: /cvsroot/pgsql/src/interfaces/libpgtcl/Attic/pgtclId.c,v 1.3 1996/11/11 12:14:45 scrappy Exp $
+ * $Header: /cvsroot/pgsql/src/interfaces/libpgtcl/Attic/pgtclId.c,v 1.4 1997/09/07 05:03:13 momjian Exp $
*
*-------------------------------------------------------------------------
*/
@@ -29,39 +29,40 @@
* Create the Id for a new connection and hash it
*/
void
-PgSetConnectionId(Pg_clientData *cd, char *id, PGconn *conn)
+PgSetConnectionId(Pg_clientData * cd, char *id, PGconn * conn)
{
- Tcl_HashEntry *hent;
- Pg_ConnectionId *connid;
- int hnew;
-
- connid = (Pg_ConnectionId *)ckalloc(sizeof(Pg_ConnectionId));
- connid->conn = conn;
- Tcl_InitHashTable(&(connid->res_hash), TCL_STRING_KEYS);
- sprintf(connid->id, "pgc%ld", cd->dbh_count++);
- strcpy(id, connid->id);
-
- hent = Tcl_CreateHashEntry(&(cd->dbh_hash), connid->id, &hnew);
- Tcl_SetHashValue(hent, (ClientData)connid);
+ Tcl_HashEntry *hent;
+ Pg_ConnectionId *connid;
+ int hnew;
+
+ connid = (Pg_ConnectionId *) ckalloc(sizeof(Pg_ConnectionId));
+ connid->conn = conn;
+ Tcl_InitHashTable(&(connid->res_hash), TCL_STRING_KEYS);
+ sprintf(connid->id, "pgc%ld", cd->dbh_count++);
+ strcpy(id, connid->id);
+
+ hent = Tcl_CreateHashEntry(&(cd->dbh_hash), connid->id, &hnew);
+ Tcl_SetHashValue(hent, (ClientData) connid);
}
/*
* Get back the connection from the Id
*/
-PGconn *
-PgGetConnectionId(Pg_clientData *cd, char *id)
+PGconn *
+PgGetConnectionId(Pg_clientData * cd, char *id)
{
- Tcl_HashEntry *hent;
- Pg_ConnectionId *connid;
+ Tcl_HashEntry *hent;
+ Pg_ConnectionId *connid;
- hent = Tcl_FindHashEntry(&(cd->dbh_hash), id);
- if(hent == NULL) {
- return (PGconn *)NULL;
- }
+ hent = Tcl_FindHashEntry(&(cd->dbh_hash), id);
+ if (hent == NULL)
+ {
+ return (PGconn *) NULL;
+ }
- connid = (Pg_ConnectionId *)Tcl_GetHashValue(hent);
- return connid->conn;
+ connid = (Pg_ConnectionId *) Tcl_GetHashValue(hent);
+ return connid->conn;
}
@@ -70,36 +71,39 @@ PgGetConnectionId(Pg_clientData *cd, char *id)
* close all portals the user forgot.
*/
void
-PgDelConnectionId(Pg_clientData *cd, char *id)
+PgDelConnectionId(Pg_clientData * cd, char *id)
{
- Tcl_HashEntry *hent;
- Tcl_HashEntry *hent2;
- Tcl_HashEntry *hent3;
- Tcl_HashSearch hsearch;
- Pg_ConnectionId *connid;
- Pg_ResultId *resid;
-
- hent = Tcl_FindHashEntry(&(cd->dbh_hash), id);
- if(hent == NULL) {
- return;
- }
-
- connid = (Pg_ConnectionId *)Tcl_GetHashValue(hent);
-
- hent2 = Tcl_FirstHashEntry(&(connid->res_hash), &hsearch);
- while(hent2 != NULL) {
- resid = (Pg_ResultId *)Tcl_GetHashValue(hent2);
- PQclear(resid->result);
- hent3 = Tcl_FindHashEntry(&(cd->res_hash), resid->id);
- if(hent3 != NULL) {
- Tcl_DeleteHashEntry(hent3);
+ Tcl_HashEntry *hent;
+ Tcl_HashEntry *hent2;
+ Tcl_HashEntry *hent3;
+ Tcl_HashSearch hsearch;
+ Pg_ConnectionId *connid;
+ Pg_ResultId *resid;
+
+ hent = Tcl_FindHashEntry(&(cd->dbh_hash), id);
+ if (hent == NULL)
+ {
+ return;
}
- ckfree(resid);
- hent2 = Tcl_NextHashEntry(&hsearch);
- }
- Tcl_DeleteHashTable(&(connid->res_hash));
- Tcl_DeleteHashEntry(hent);
- ckfree(connid);
+
+ connid = (Pg_ConnectionId *) Tcl_GetHashValue(hent);
+
+ hent2 = Tcl_FirstHashEntry(&(connid->res_hash), &hsearch);
+ while (hent2 != NULL)
+ {
+ resid = (Pg_ResultId *) Tcl_GetHashValue(hent2);
+ PQclear(resid->result);
+ hent3 = Tcl_FindHashEntry(&(cd->res_hash), resid->id);
+ if (hent3 != NULL)
+ {
+ Tcl_DeleteHashEntry(hent3);
+ }
+ ckfree(resid);
+ hent2 = Tcl_NextHashEntry(&hsearch);
+ }
+ Tcl_DeleteHashTable(&(connid->res_hash));
+ Tcl_DeleteHashEntry(hent);
+ ckfree(connid);
}
@@ -107,52 +111,57 @@ PgDelConnectionId(Pg_clientData *cd, char *id)
* Create a new result Id and hash it
*/
void
-PgSetResultId(Pg_clientData *cd, char *id, char *connid_c, PGresult *res)
+PgSetResultId(Pg_clientData * cd, char *id, char *connid_c, PGresult * res)
{
- Tcl_HashEntry *hent;
- Pg_ConnectionId *connid;
- Pg_ResultId *resid;
- int hnew;
-
- hent = Tcl_FindHashEntry(&(cd->dbh_hash), connid_c);
- if(hent == NULL) {
- connid = NULL;
- } else {
- connid = (Pg_ConnectionId *)Tcl_GetHashValue(hent);
- }
-
- resid = (Pg_ResultId *)ckalloc(sizeof(Pg_ResultId));
- resid->result = res;
- resid->connection = connid;
- sprintf(resid->id, "pgr%ld", cd->res_count++);
- strcpy(id, resid->id);
-
- hent = Tcl_CreateHashEntry(&(cd->res_hash), resid->id, &hnew);
- Tcl_SetHashValue(hent, (ClientData)resid);
-
- if(connid != NULL) {
- hent = Tcl_CreateHashEntry(&(connid->res_hash), resid->id, &hnew);
- Tcl_SetHashValue(hent, (ClientData)resid);
- }
+ Tcl_HashEntry *hent;
+ Pg_ConnectionId *connid;
+ Pg_ResultId *resid;
+ int hnew;
+
+ hent = Tcl_FindHashEntry(&(cd->dbh_hash), connid_c);
+ if (hent == NULL)
+ {
+ connid = NULL;
+ }
+ else
+ {
+ connid = (Pg_ConnectionId *) Tcl_GetHashValue(hent);
+ }
+
+ resid = (Pg_ResultId *) ckalloc(sizeof(Pg_ResultId));
+ resid->result = res;
+ resid->connection = connid;
+ sprintf(resid->id, "pgr%ld", cd->res_count++);
+ strcpy(id, resid->id);
+
+ hent = Tcl_CreateHashEntry(&(cd->res_hash), resid->id, &hnew);
+ Tcl_SetHashValue(hent, (ClientData) resid);
+
+ if (connid != NULL)
+ {
+ hent = Tcl_CreateHashEntry(&(connid->res_hash), resid->id, &hnew);
+ Tcl_SetHashValue(hent, (ClientData) resid);
+ }
}
/*
* Get back the result pointer from the Id
*/
-PGresult *
-PgGetResultId(Pg_clientData *cd, char *id)
+PGresult *
+PgGetResultId(Pg_clientData * cd, char *id)
{
- Tcl_HashEntry *hent;
- Pg_ResultId *resid;
+ Tcl_HashEntry *hent;
+ Pg_ResultId *resid;
- hent = Tcl_FindHashEntry(&(cd->res_hash), id);
- if(hent == NULL) {
- return (PGresult *)NULL;
- }
+ hent = Tcl_FindHashEntry(&(cd->res_hash), id);
+ if (hent == NULL)
+ {
+ return (PGresult *) NULL;
+ }
- resid = (Pg_ResultId *)Tcl_GetHashValue(hent);
- return resid->result;
+ resid = (Pg_ResultId *) Tcl_GetHashValue(hent);
+ return resid->result;
}
@@ -160,27 +169,30 @@ PgGetResultId(Pg_clientData *cd, char *id)
* Remove a result Id from the hash tables
*/
void
-PgDelResultId(Pg_clientData *cd, char *id)
+PgDelResultId(Pg_clientData * cd, char *id)
{
- Tcl_HashEntry *hent;
- Tcl_HashEntry *hent2;
- Pg_ResultId *resid;
-
- hent = Tcl_FindHashEntry(&(cd->res_hash), id);
- if(hent == NULL) {
- return;
- }
-
- resid = (Pg_ResultId *)Tcl_GetHashValue(hent);
- if (resid->connection != NULL) {
- hent2 = Tcl_FindHashEntry(&(resid->connection->res_hash), id);
- if(hent2 != NULL) {
- Tcl_DeleteHashEntry(hent2);
+ Tcl_HashEntry *hent;
+ Tcl_HashEntry *hent2;
+ Pg_ResultId *resid;
+
+ hent = Tcl_FindHashEntry(&(cd->res_hash), id);
+ if (hent == NULL)
+ {
+ return;
}
- }
- Tcl_DeleteHashEntry(hent);
- ckfree(resid);
+ resid = (Pg_ResultId *) Tcl_GetHashValue(hent);
+ if (resid->connection != NULL)
+ {
+ hent2 = Tcl_FindHashEntry(&(resid->connection->res_hash), id);
+ if (hent2 != NULL)
+ {
+ Tcl_DeleteHashEntry(hent2);
+ }
+ }
+
+ Tcl_DeleteHashEntry(hent);
+ ckfree(resid);
}
@@ -188,20 +200,20 @@ PgDelResultId(Pg_clientData *cd, char *id)
* Get the connection Id from the result Id
*/
void
-PgGetConnByResultId(Pg_clientData *cd, char *id, char *resid_c)
+PgGetConnByResultId(Pg_clientData * cd, char *id, char *resid_c)
{
- Tcl_HashEntry *hent;
- Pg_ResultId *resid;
-
- hent = Tcl_FindHashEntry(&(cd->res_hash), id);
- if(hent == NULL) {
- return;
- }
-
- resid = (Pg_ResultId *)Tcl_GetHashValue(hent);
- if (resid->connection != NULL) {
- strcpy(id, resid->connection->id);
- }
-}
+ Tcl_HashEntry *hent;
+ Pg_ResultId *resid;
+ hent = Tcl_FindHashEntry(&(cd->res_hash), id);
+ if (hent == NULL)
+ {
+ return;
+ }
+ resid = (Pg_ResultId *) Tcl_GetHashValue(hent);
+ if (resid->connection != NULL)
+ {
+ strcpy(id, resid->connection->id);
+ }
+}
diff --git a/src/interfaces/libpgtcl/pgtclId.h b/src/interfaces/libpgtcl/pgtclId.h
index 9cb431918aa..03856434d6b 100644
--- a/src/interfaces/libpgtcl/pgtclId.h
+++ b/src/interfaces/libpgtcl/pgtclId.h
@@ -1,22 +1,22 @@
/*-------------------------------------------------------------------------
*
* pgtclId.h--
- * useful routines to convert between strings and pointers
- * Needed because everything in tcl is a string, but often, pointers
- * to data structures are needed.
- *
+ * useful routines to convert between strings and pointers
+ * Needed because everything in tcl is a string, but often, pointers
+ * to data structures are needed.
+ *
*
* Copyright (c) 1994, Regents of the University of California
*
- * $Id: pgtclId.h,v 1.2 1996/10/30 06:18:42 scrappy Exp $
+ * $Id: pgtclId.h,v 1.3 1997/09/07 05:03:14 momjian Exp $
*
*-------------------------------------------------------------------------
*/
-extern void PgSetConnectionId(Pg_clientData *cd, char *id, PGconn *conn);
-extern PGconn *PgGetConnectionId(Pg_clientData *cd, char *id);
-extern void PgDelConnectionId(Pg_clientData *cd, char *id);
-extern void PgSetResultId(Pg_clientData *cd, char *id, char *connid, PGresult *res);
-extern PGresult *PgGetResultId(Pg_clientData *cd, char *id);
-extern void PgDelResultId(Pg_clientData *cd, char *id);
-extern void PgGetConnByResultId(Pg_clientData *cd, char *id, char *resid);
+extern void PgSetConnectionId(Pg_clientData * cd, char *id, PGconn * conn);
+extern PGconn *PgGetConnectionId(Pg_clientData * cd, char *id);
+extern void PgDelConnectionId(Pg_clientData * cd, char *id);
+extern void PgSetResultId(Pg_clientData * cd, char *id, char *connid, PGresult * res);
+extern PGresult *PgGetResultId(Pg_clientData * cd, char *id);
+extern void PgDelResultId(Pg_clientData * cd, char *id);
+extern void PgGetConnByResultId(Pg_clientData * cd, char *id, char *resid);
diff --git a/src/interfaces/libpq/fe-auth.c b/src/interfaces/libpq/fe-auth.c
index d058ec8ab78..433cc65ded7 100644
--- a/src/interfaces/libpq/fe-auth.c
+++ b/src/interfaces/libpq/fe-auth.c
@@ -1,34 +1,34 @@
/*-------------------------------------------------------------------------
*
* fe-auth.c--
- * The front-end (client) authorization routines
+ * The front-end (client) authorization routines
*
* Copyright (c) 1994, Regents of the University of California
*
*
* IDENTIFICATION
- * $Header: /cvsroot/pgsql/src/interfaces/libpq/fe-auth.c,v 1.8 1997/08/12 20:16:21 momjian Exp $
+ * $Header: /cvsroot/pgsql/src/interfaces/libpq/fe-auth.c,v 1.9 1997/09/07 05:03:17 momjian Exp $
*
*-------------------------------------------------------------------------
*/
/*
* INTERFACE ROUTINES
- * frontend (client) routines:
- * fe_sendauth send authentication information
- * fe_getauthname get user's name according to the client side
- * of the authentication system
- * fe_setauthsvc set frontend authentication service
- * fe_getauthsvc get current frontend authentication service
+ * frontend (client) routines:
+ * fe_sendauth send authentication information
+ * fe_getauthname get user's name according to the client side
+ * of the authentication system
+ * fe_setauthsvc set frontend authentication service
+ * fe_getauthsvc get current frontend authentication service
*
*
*
*/
#include <stdio.h>
#include <string.h>
-#include <sys/param.h> /* for MAXHOSTNAMELEN on most */
+#include <sys/param.h> /* for MAXHOSTNAMELEN on most */
#ifndef MAXHOSTNAMELEN
-#include <netdb.h> /* for MAXHOSTNAMELEN on some */
+#include <netdb.h> /* for MAXHOSTNAMELEN on some */
#endif
#include <unistd.h>
#include <sys/types.h>
@@ -47,12 +47,12 @@
*----------------------------------------------------------------
*/
-struct authsvc {
- char name[16]; /* service nickname (for command line) */
- MsgType msgtype; /* startup packet header type */
- int allowed; /* initially allowed (before command line
- * option parsing)?
- */
+struct authsvc
+{
+ char name[16]; /* service nickname (for command line) */
+ MsgType msgtype; /* startup packet header type */
+ int allowed; /* initially allowed (before command line
+ * option parsing)? */
};
/*
@@ -67,24 +67,24 @@ struct authsvc {
*/
static struct authsvc authsvcs[] = {
#ifdef KRB4
- { "krb4", STARTUP_KRB4_MSG, 1 },
- { "kerberos", STARTUP_KRB4_MSG, 1 },
-#endif /* KRB4 */
+ {"krb4", STARTUP_KRB4_MSG, 1},
+ {"kerberos", STARTUP_KRB4_MSG, 1},
+#endif /* KRB4 */
#ifdef KRB5
- { "krb5", STARTUP_KRB5_MSG, 1 },
- { "kerberos", STARTUP_KRB5_MSG, 1 },
-#endif /* KRB5 */
- { UNAUTHNAME, STARTUP_MSG,
+ {"krb5", STARTUP_KRB5_MSG, 1},
+ {"kerberos", STARTUP_KRB5_MSG, 1},
+#endif /* KRB5 */
+ {UNAUTHNAME, STARTUP_MSG,
#if defined(KRB4) || defined(KRB5)
- 0
-#else /* !(KRB4 || KRB5) */
- 1
-#endif /* !(KRB4 || KRB5) */
- },
- { "password", STARTUP_PASSWORD_MSG, 0 }
+ 0
+#else /* !(KRB4 || KRB5) */
+ 1
+#endif /* !(KRB4 || KRB5) */
+ },
+ {"password", STARTUP_PASSWORD_MSG, 0}
};
-static n_authsvcs = sizeof(authsvcs) / sizeof(struct authsvc);
+static n_authsvcs = sizeof(authsvcs) / sizeof(struct authsvc);
#ifdef KRB4
/*----------------------------------------------------------------
@@ -95,8 +95,8 @@ static n_authsvcs = sizeof(authsvcs) / sizeof(struct authsvc);
#include "krb.h"
/* for some reason, this is not defined in krb.h ... */
-extern char *tkt_string(void);
-
+extern char *tkt_string(void);
+
/*
* pg_krb4_init -- initialization performed before any Kerberos calls are made
*
@@ -104,60 +104,63 @@ extern char *tkt_string(void);
* ticket file if we want them to see a special one. (They will open the file
* themselves.)
*/
-static void pg_krb4_init()
+static void
+pg_krb4_init()
{
- char *realm;
- static init_done = 0;
-
- if (init_done)
- return;
- init_done = 1;
-
- /*
- * If the user set PGREALM, then we use a ticket file with a special
- * name: <usual-ticket-file-name>@<PGREALM-value>
- */
- if (realm = getenv("PGREALM")) {
- char tktbuf[MAXPATHLEN];
-
- (void) sprintf(tktbuf, "%s@%s", tkt_string(), realm);
- krb_set_tkt_string(tktbuf);
- }
+ char *realm;
+ static init_done = 0;
+
+ if (init_done)
+ return;
+ init_done = 1;
+
+ /*
+ * If the user set PGREALM, then we use a ticket file with a special
+ * name: <usual-ticket-file-name>@<PGREALM-value>
+ */
+ if (realm = getenv("PGREALM"))
+ {
+ char tktbuf[MAXPATHLEN];
+
+ (void) sprintf(tktbuf, "%s@%s", tkt_string(), realm);
+ krb_set_tkt_string(tktbuf);
+ }
}
/*
* pg_krb4_authname -- returns a pointer to static space containing whatever
- * name the user has authenticated to the system
+ * name the user has authenticated to the system
*
* We obtain this information by digging around in the ticket file.
*/
-static char *
-pg_krb4_authname(char* PQerrormsg)
+static char *
+pg_krb4_authname(char *PQerrormsg)
{
- char instance[INST_SZ];
- char realm[REALM_SZ];
- int status;
- static char name[SNAME_SZ+1] = "";
-
- if (name[0])
- return(name);
-
- pg_krb4_init();
-
- name[SNAME_SZ] = '\0';
- status = krb_get_tf_fullname(tkt_string(), name, instance, realm);
- if (status != KSUCCESS) {
- (void) sprintf(PQerrormsg,
- "pg_krb4_authname: krb_get_tf_fullname: %s\n",
- krb_err_txt[status]);
- return((char *) NULL);
- }
- return(name);
+ char instance[INST_SZ];
+ char realm[REALM_SZ];
+ int status;
+ static char name[SNAME_SZ + 1] = "";
+
+ if (name[0])
+ return (name);
+
+ pg_krb4_init();
+
+ name[SNAME_SZ] = '\0';
+ status = krb_get_tf_fullname(tkt_string(), name, instance, realm);
+ if (status != KSUCCESS)
+ {
+ (void) sprintf(PQerrormsg,
+ "pg_krb4_authname: krb_get_tf_fullname: %s\n",
+ krb_err_txt[status]);
+ return ((char *) NULL);
+ }
+ return (name);
}
/*
* pg_krb4_sendauth -- client routine to send authentication information to
- * the server
+ * the server
*
* This routine does not do mutual authentication, nor does it return enough
* information to do encrypted connections. But then, if we want to do
@@ -170,48 +173,50 @@ pg_krb4_authname(char* PQerrormsg)
* (canonicalized to omit all domain suffixes).
*/
static int
-pg_krb4_sendauth(const char* PQerrormsg, int sock,
- struct sockaddr_in *laddr,
- struct sockaddr_in *raddr,
- const char *hostname)
+pg_krb4_sendauth(const char *PQerrormsg, int sock,
+ struct sockaddr_in * laddr,
+ struct sockaddr_in * raddr,
+ const char *hostname)
{
- long krbopts = 0; /* one-way authentication */
- KTEXT_ST clttkt;
- int status;
- char hostbuf[MAXHOSTNAMELEN];
- const char *realm = getenv("PGREALM"); /* NULL == current realm */
-
- if (!hostname || !(*hostname)) {
- if (gethostname(hostbuf, MAXHOSTNAMELEN) < 0)
- strcpy(hostbuf, "localhost");
- hostname = hostbuf;
- }
-
- pg_krb4_init();
-
- status = krb_sendauth(krbopts,
- sock,
- &clttkt,
- PG_KRB_SRVNAM,
- hostname,
- realm,
- (u_long) 0,
- (MSG_DAT *) NULL,
- (CREDENTIALS *) NULL,
- (Key_schedule *) NULL,
- laddr,
- raddr,
- PG_KRB4_VERSION);
- if (status != KSUCCESS) {
- (void) sprintf(PQerrormsg,
- "pg_krb4_sendauth: kerberos error: %s\n",
- krb_err_txt[status]);
- return(STATUS_ERROR);
- }
- return(STATUS_OK);
+ long krbopts = 0;/* one-way authentication */
+ KTEXT_ST clttkt;
+ int status;
+ char hostbuf[MAXHOSTNAMELEN];
+ const char *realm = getenv("PGREALM"); /* NULL == current realm */
+
+ if (!hostname || !(*hostname))
+ {
+ if (gethostname(hostbuf, MAXHOSTNAMELEN) < 0)
+ strcpy(hostbuf, "localhost");
+ hostname = hostbuf;
+ }
+
+ pg_krb4_init();
+
+ status = krb_sendauth(krbopts,
+ sock,
+ &clttkt,
+ PG_KRB_SRVNAM,
+ hostname,
+ realm,
+ (u_long) 0,
+ (MSG_DAT *) NULL,
+ (CREDENTIALS *) NULL,
+ (Key_schedule *) NULL,
+ laddr,
+ raddr,
+ PG_KRB4_VERSION);
+ if (status != KSUCCESS)
+ {
+ (void) sprintf(PQerrormsg,
+ "pg_krb4_sendauth: kerberos error: %s\n",
+ krb_err_txt[status]);
+ return (STATUS_ERROR);
+ }
+ return (STATUS_OK);
}
-#endif /* KRB4 */
+#endif /* KRB4 */
#ifdef KRB5
/*----------------------------------------------------------------
@@ -223,25 +228,25 @@ pg_krb4_sendauth(const char* PQerrormsg, int sock,
/*
* pg_an_to_ln -- return the local name corresponding to an authentication
- * name
+ * name
*
* XXX Assumes that the first aname component is the user name. This is NOT
- * necessarily so, since an aname can actually be something out of your
- * worst X.400 nightmare, like
- * ORGANIZATION=U. C. Berkeley/NAME=Paul M. [email protected]
- * Note that the MIT an_to_ln code does the same thing if you don't
- * provide an aname mapping database...it may be a better idea to use
- * krb5_an_to_ln, except that it punts if multiple components are found,
- * and we can't afford to punt.
+ * necessarily so, since an aname can actually be something out of your
+ * worst X.400 nightmare, like
+ * ORGANIZATION=U. C. Berkeley/NAME=Paul M. [email protected]
+ * Note that the MIT an_to_ln code does the same thing if you don't
+ * provide an aname mapping database...it may be a better idea to use
+ * krb5_an_to_ln, except that it punts if multiple components are found,
+ * and we can't afford to punt.
*/
-static char *
+static char *
pg_an_to_ln(const char *aname)
{
- char *p;
-
- if ((p = strchr(aname, '/')) || (p = strchr(aname, '@')))
- *p = '\0';
- return(aname);
+ char *p;
+
+ if ((p = strchr(aname, '/')) || (p = strchr(aname, '@')))
+ *p = '\0';
+ return (aname);
}
@@ -251,85 +256,92 @@ pg_an_to_ln(const char *aname)
* With v5, we can no longer set the ticket (credential cache) file name;
* we now have to provide a file handle for the open (well, "resolved")
* ticket file everywhere.
- *
+ *
*/
static int
-krb5_ccache pg_krb5_init(void)
+krb5_ccache
+pg_krb5_init(void)
{
- krb5_error_code code;
- char *realm, *defname;
- char tktbuf[MAXPATHLEN];
- static krb5_ccache ccache = (krb5_ccache) NULL;
-
- if (ccache)
- return(ccache);
-
- /*
- * If the user set PGREALM, then we use a ticket file with a special
- * name: <usual-ticket-file-name>@<PGREALM-value>
- */
- if (!(defname = krb5_cc_default_name())) {
- (void) sprintf(PQerrormsg,
- "pg_krb5_init: krb5_cc_default_name failed\n");
- return((krb5_ccache) NULL);
- }
- strcpy(tktbuf, defname);
- if (realm = getenv("PGREALM")) {
- strcat(tktbuf, "@");
- strcat(tktbuf, realm);
- }
-
- if (code = krb5_cc_resolve(tktbuf, &ccache)) {
- (void) sprintf(PQerrormsg,
- "pg_krb5_init: Kerberos error %d in krb5_cc_resolve\n",
- code);
- com_err("pg_krb5_init", code, "in krb5_cc_resolve");
- return((krb5_ccache) NULL);
- }
- return(ccache);
+ krb5_error_code code;
+ char *realm,
+ *defname;
+ char tktbuf[MAXPATHLEN];
+ static krb5_ccache ccache = (krb5_ccache) NULL;
+
+ if (ccache)
+ return (ccache);
+
+ /*
+ * If the user set PGREALM, then we use a ticket file with a special
+ * name: <usual-ticket-file-name>@<PGREALM-value>
+ */
+ if (!(defname = krb5_cc_default_name()))
+ {
+ (void) sprintf(PQerrormsg,
+ "pg_krb5_init: krb5_cc_default_name failed\n");
+ return ((krb5_ccache) NULL);
+ }
+ strcpy(tktbuf, defname);
+ if (realm = getenv("PGREALM"))
+ {
+ strcat(tktbuf, "@");
+ strcat(tktbuf, realm);
+ }
+
+ if (code = krb5_cc_resolve(tktbuf, &ccache))
+ {
+ (void) sprintf(PQerrormsg,
+ "pg_krb5_init: Kerberos error %d in krb5_cc_resolve\n",
+ code);
+ com_err("pg_krb5_init", code, "in krb5_cc_resolve");
+ return ((krb5_ccache) NULL);
+ }
+ return (ccache);
}
/*
* pg_krb5_authname -- returns a pointer to static space containing whatever
- * name the user has authenticated to the system
+ * name the user has authenticated to the system
*
* We obtain this information by digging around in the ticket file.
*/
static const char *
-pg_krb5_authname(const char* PQerrormsg)
+pg_krb5_authname(const char *PQerrormsg)
{
- krb5_ccache ccache;
- krb5_principal principal;
- krb5_error_code code;
- static char *authname = (char *) NULL;
-
- if (authname)
- return(authname);
-
- ccache = pg_krb5_init(); /* don't free this */
-
- if (code = krb5_cc_get_principal(ccache, &principal)) {
- (void) sprintf(PQerrormsg,
- "pg_krb5_authname: Kerberos error %d in krb5_cc_get_principal\n",
- code);
- com_err("pg_krb5_authname", code, "in krb5_cc_get_principal");
- return((char *) NULL);
- }
- if (code = krb5_unparse_name(principal, &authname)) {
- (void) sprintf(PQerrormsg,
- "pg_krb5_authname: Kerberos error %d in krb5_unparse_name\n",
- code);
- com_err("pg_krb5_authname", code, "in krb5_unparse_name");
+ krb5_ccache ccache;
+ krb5_principal principal;
+ krb5_error_code code;
+ static char *authname = (char *) NULL;
+
+ if (authname)
+ return (authname);
+
+ ccache = pg_krb5_init(); /* don't free this */
+
+ if (code = krb5_cc_get_principal(ccache, &principal))
+ {
+ (void) sprintf(PQerrormsg,
+ "pg_krb5_authname: Kerberos error %d in krb5_cc_get_principal\n",
+ code);
+ com_err("pg_krb5_authname", code, "in krb5_cc_get_principal");
+ return ((char *) NULL);
+ }
+ if (code = krb5_unparse_name(principal, &authname))
+ {
+ (void) sprintf(PQerrormsg,
+ "pg_krb5_authname: Kerberos error %d in krb5_unparse_name\n",
+ code);
+ com_err("pg_krb5_authname", code, "in krb5_unparse_name");
+ krb5_free_principal(principal);
+ return ((char *) NULL);
+ }
krb5_free_principal(principal);
- return((char *) NULL);
- }
- krb5_free_principal(principal);
- return(pg_an_to_ln(authname));
+ return (pg_an_to_ln(authname));
}
/*
* pg_krb5_sendauth -- client routine to send authentication information to
- * the server
+ * the server
*
* This routine does not do mutual authentication, nor does it return enough
* information to do encrypted connections. But then, if we want to do
@@ -337,159 +349,173 @@ pg_krb5_authname(const char* PQerrormsg)
* anyway.
*
* Server hostnames are canonicalized v4-style, i.e., all domain suffixes
- * are simply chopped off. Hence, we are assuming that you've entered your
+ * are simply chopped off. Hence, we are assuming that you've entered your
* server instances as
- * <value-of-PG_KRB_SRVNAM>/<canonicalized-hostname>
- * in the PGREALM (or local) database. This is probably a bad assumption.
+ * <value-of-PG_KRB_SRVNAM>/<canonicalized-hostname>
+ * in the PGREALM (or local) database. This is probably a bad assumption.
*/
static int
-pg_krb5_sendauth(const char* PQerrormsg,int sock,
- struct sockaddr_in *laddr,
- struct sockaddr_in *raddr,
- const char *hostname)
+pg_krb5_sendauth(const char *PQerrormsg, int sock,
+ struct sockaddr_in * laddr,
+ struct sockaddr_in * raddr,
+ const char *hostname)
{
- char servbuf[MAXHOSTNAMELEN + 1 +
- sizeof(PG_KRB_SRVNAM)];
- const char *hostp;
- const char *realm;
- krb5_error_code code;
- krb5_principal client, server;
- krb5_ccache ccache;
- krb5_error *error = (krb5_error *) NULL;
-
- ccache = pg_krb5_init(); /* don't free this */
-
- /*
- * set up client -- this is easy, we can get it out of the ticket
- * file.
- */
- if (code = krb5_cc_get_principal(ccache, &client)) {
- (void) sprintf(PQerrormsg,
- "pg_krb5_sendauth: Kerberos error %d in krb5_cc_get_principal\n",
- code);
- com_err("pg_krb5_sendauth", code, "in krb5_cc_get_principal");
- return(STATUS_ERROR);
- }
-
- /*
- * set up server -- canonicalize as described above
- */
- strcpy(servbuf, PG_KRB_SRVNAM);
- *(hostp = servbuf + (sizeof(PG_KRB_SRVNAM) - 1)) = '/';
- if (hostname || *hostname) {
- strncpy(++hostp, hostname, MAXHOSTNAMELEN);
- } else {
- if (gethostname(++hostp, MAXHOSTNAMELEN) < 0)
- strcpy(hostp, "localhost");
- }
- if (hostp = strchr(hostp, '.'))
- *hostp = '\0';
- if (realm = getenv("PGREALM")) {
- strcat(servbuf, "@");
- strcat(servbuf, realm);
- }
- if (code = krb5_parse_name(servbuf, &server)) {
- (void) sprintf(PQerrormsg,
- "pg_krb5_sendauth: Kerberos error %d in krb5_parse_name\n",
- code);
- com_err("pg_krb5_sendauth", code, "in krb5_parse_name");
- krb5_free_principal(client);
- return(STATUS_ERROR);
- }
-
- /*
- * The only thing we want back from krb5_sendauth is an error status
- * and any error messages.
- */
- if (code = krb5_sendauth((krb5_pointer) &sock,
- PG_KRB5_VERSION,
- client,
- server,
- (krb5_flags) 0,
- (krb5_checksum *) NULL,
- (krb5_creds *) NULL,
- ccache,
- (krb5_int32 *) NULL,
- (krb5_keyblock **) NULL,
- &error,
- (krb5_ap_rep_enc_part **) NULL)) {
- if ((code == KRB5_SENDAUTH_REJECTED) && error) {
- (void) sprintf(PQerrormsg,
- "pg_krb5_sendauth: authentication rejected: \"%*s\"\n",
- error->text.length, error->text.data);
- fputs(PQerrormsg, stderr);
- pqdebug("%s", PQerrormsg);
- } else {
- (void) sprintf(PQerrormsg,
- "pg_krb5_sendauth: Kerberos error %d in krb5_sendauth\n",
- code);
- com_err("pg_krb5_sendauth", code, "in krb5_sendauth");
+ char servbuf[MAXHOSTNAMELEN + 1 +
+ sizeof(PG_KRB_SRVNAM)];
+ const char *hostp;
+ const char *realm;
+ krb5_error_code code;
+ krb5_principal client,
+ server;
+ krb5_ccache ccache;
+ krb5_error *error = (krb5_error *) NULL;
+
+ ccache = pg_krb5_init(); /* don't free this */
+
+ /*
+ * set up client -- this is easy, we can get it out of the ticket
+ * file.
+ */
+ if (code = krb5_cc_get_principal(ccache, &client))
+ {
+ (void) sprintf(PQerrormsg,
+ "pg_krb5_sendauth: Kerberos error %d in krb5_cc_get_principal\n",
+ code);
+ com_err("pg_krb5_sendauth", code, "in krb5_cc_get_principal");
+ return (STATUS_ERROR);
+ }
+
+ /*
+ * set up server -- canonicalize as described above
+ */
+ strcpy(servbuf, PG_KRB_SRVNAM);
+ *(hostp = servbuf + (sizeof(PG_KRB_SRVNAM) - 1)) = '/';
+ if (hostname || *hostname)
+ {
+ strncpy(++hostp, hostname, MAXHOSTNAMELEN);
+ }
+ else
+ {
+ if (gethostname(++hostp, MAXHOSTNAMELEN) < 0)
+ strcpy(hostp, "localhost");
+ }
+ if (hostp = strchr(hostp, '.'))
+ *hostp = '\0';
+ if (realm = getenv("PGREALM"))
+ {
+ strcat(servbuf, "@");
+ strcat(servbuf, realm);
+ }
+ if (code = krb5_parse_name(servbuf, &server))
+ {
+ (void) sprintf(PQerrormsg,
+ "pg_krb5_sendauth: Kerberos error %d in krb5_parse_name\n",
+ code);
+ com_err("pg_krb5_sendauth", code, "in krb5_parse_name");
+ krb5_free_principal(client);
+ return (STATUS_ERROR);
+ }
+
+ /*
+ * The only thing we want back from krb5_sendauth is an error status
+ * and any error messages.
+ */
+ if (code = krb5_sendauth((krb5_pointer) & sock,
+ PG_KRB5_VERSION,
+ client,
+ server,
+ (krb5_flags) 0,
+ (krb5_checksum *) NULL,
+ (krb5_creds *) NULL,
+ ccache,
+ (krb5_int32 *) NULL,
+ (krb5_keyblock **) NULL,
+ &error,
+ (krb5_ap_rep_enc_part **) NULL))
+ {
+ if ((code == KRB5_SENDAUTH_REJECTED) && error)
+ {
+ (void) sprintf(PQerrormsg,
+ "pg_krb5_sendauth: authentication rejected: \"%*s\"\n",
+ error->text.length, error->text.data);
+ fputs(PQerrormsg, stderr);
+ pqdebug("%s", PQerrormsg);
+ }
+ else
+ {
+ (void) sprintf(PQerrormsg,
+ "pg_krb5_sendauth: Kerberos error %d in krb5_sendauth\n",
+ code);
+ com_err("pg_krb5_sendauth", code, "in krb5_sendauth");
+ }
}
- }
- krb5_free_principal(client);
- krb5_free_principal(server);
- return(code ? STATUS_ERROR : STATUS_OK);
+ krb5_free_principal(client);
+ krb5_free_principal(server);
+ return (code ? STATUS_ERROR : STATUS_OK);
}
-#endif /* KRB5 */
+#endif /* KRB5 */
static int
-pg_password_sendauth(Port *port, const char *user, const char *password)
+pg_password_sendauth(Port * port, const char *user, const char *password)
{
- PacketBuf buf;
- char *tmp;
+ PacketBuf buf;
+ char *tmp;
- buf.len = htonl(sizeof(PacketBuf));
- buf.msgtype = STARTUP_PASSWORD_MSG;
- buf.data[0] = '\0';
+ buf.len = htonl(sizeof(PacketBuf));
+ buf.msgtype = STARTUP_PASSWORD_MSG;
+ buf.data[0] = '\0';
- tmp = buf.data;
- strncpy(tmp, user, strlen(user)+1);
- tmp += strlen(user)+1;
- strncpy(tmp, password, strlen(password)+1);
+ tmp = buf.data;
+ strncpy(tmp, user, strlen(user) + 1);
+ tmp += strlen(user) + 1;
+ strncpy(tmp, password, strlen(password) + 1);
- return packetSend(port, &buf, sizeof(PacketBuf), BLOCKING);
+ return packetSend(port, &buf, sizeof(PacketBuf), BLOCKING);
}
/*
* fe_sendauth -- client demux routine for outgoing authentication information
*/
int
-fe_sendauth(MsgType msgtype, Port *port, const char *hostname,
- const char *user, const char *password, const char* PQerrormsg)
+fe_sendauth(MsgType msgtype, Port * port, const char *hostname,
+ const char *user, const char *password, const char *PQerrormsg)
{
- switch (msgtype) {
+ switch (msgtype)
+ {
#ifdef KRB4
- case STARTUP_KRB4_MSG:
- if (pg_krb4_sendauth(PQerrormsg, port->sock, &port->laddr,
- &port->raddr,
- hostname) != STATUS_OK) {
- (void) sprintf(PQerrormsg,
- "fe_sendauth: krb4 authentication failed\n");
-/* fputs(PQerrormsg, stderr); */
- return(STATUS_ERROR);
- }
- break;
+ case STARTUP_KRB4_MSG:
+ if (pg_krb4_sendauth(PQerrormsg, port->sock, &port->laddr,
+ &port->raddr,
+ hostname) != STATUS_OK)
+ {
+ (void) sprintf(PQerrormsg,
+ "fe_sendauth: krb4 authentication failed\n");
+/* fputs(PQerrormsg, stderr); */
+ return (STATUS_ERROR);
+ }
+ break;
#endif
#ifdef KRB5
- case STARTUP_KRB5_MSG:
- if (pg_krb5_sendauth(PQerrormsg,port->sock, &port->laddr,
- &port->raddr,
- hostname) != STATUS_OK) {
- (void) sprintf(PQerrormsg,
- "fe_sendauth: krb5 authentication failed\n");
- return(STATUS_ERROR);
- }
- break;
+ case STARTUP_KRB5_MSG:
+ if (pg_krb5_sendauth(PQerrormsg, port->sock, &port->laddr,
+ &port->raddr,
+ hostname) != STATUS_OK)
+ {
+ (void) sprintf(PQerrormsg,
+ "fe_sendauth: krb5 authentication failed\n");
+ return (STATUS_ERROR);
+ }
+ break;
#endif
- case STARTUP_MSG:
- break;
- case STARTUP_PASSWORD_MSG:
- pg_password_sendauth(port, user, password);
- default:
- break;
- }
- return(STATUS_OK);
+ case STARTUP_MSG:
+ break;
+ case STARTUP_PASSWORD_MSG:
+ pg_password_sendauth(port, user, password);
+ default:
+ break;
+ }
+ return (STATUS_OK);
}
/*
@@ -499,74 +525,77 @@ fe_sendauth(MsgType msgtype, Port *port, const char *hostname,
* Set/return the authentication service currently selected for use by the
* frontend. (You can only use one in the frontend, obviously.)
*/
-static pg_authsvc = -1;
+static pg_authsvc = -1;
void
-fe_setauthsvc(const char *name, char* PQerrormsg)
+fe_setauthsvc(const char *name, char *PQerrormsg)
{
- int i;
-
- for (i = 0; i < n_authsvcs; ++i)
- if (!strcmp(name, authsvcs[i].name)) {
- pg_authsvc = i;
- break;
+ int i;
+
+ for (i = 0; i < n_authsvcs; ++i)
+ if (!strcmp(name, authsvcs[i].name))
+ {
+ pg_authsvc = i;
+ break;
+ }
+ if (i == n_authsvcs)
+ {
+ (void) sprintf(PQerrormsg,
+ "fe_setauthsvc: invalid name: %s, ignoring...\n",
+ name);
}
- if (i == n_authsvcs) {
- (void) sprintf(PQerrormsg,
- "fe_setauthsvc: invalid name: %s, ignoring...\n",
- name);
- }
- return;
+ return;
}
MsgType
-fe_getauthsvc(char* PQerrormsg)
+fe_getauthsvc(char *PQerrormsg)
{
- if (pg_authsvc < 0 || pg_authsvc >= n_authsvcs)
- fe_setauthsvc(DEFAULT_CLIENT_AUTHSVC,PQerrormsg);
- return(authsvcs[pg_authsvc].msgtype);
+ if (pg_authsvc < 0 || pg_authsvc >= n_authsvcs)
+ fe_setauthsvc(DEFAULT_CLIENT_AUTHSVC, PQerrormsg);
+ return (authsvcs[pg_authsvc].msgtype);
}
/*
* fe_getauthname -- returns a pointer to dynamic space containing whatever
- * name the user has authenticated to the system
+ * name the user has authenticated to the system
* if there is an error, return the error message in PQerrormsg
*/
-char*
-fe_getauthname(char* PQerrormsg)
+char *
+fe_getauthname(char *PQerrormsg)
{
- char *name = (char *) NULL;
- char *authn = (char *) NULL;
- MsgType authsvc;
-
- authsvc = fe_getauthsvc(PQerrormsg);
- switch ((int) authsvc) {
+ char *name = (char *) NULL;
+ char *authn = (char *) NULL;
+ MsgType authsvc;
+
+ authsvc = fe_getauthsvc(PQerrormsg);
+ switch ((int) authsvc)
+ {
#ifdef KRB4
- case STARTUP_KRB4_MSG:
- name = pg_krb4_authname(PQerrormsg);
- break;
+ case STARTUP_KRB4_MSG:
+ name = pg_krb4_authname(PQerrormsg);
+ break;
#endif
#ifdef KRB5
- case STARTUP_KRB5_MSG:
- name = pg_krb5_authname(PQerrormsg);
- break;
+ case STARTUP_KRB5_MSG:
+ name = pg_krb5_authname(PQerrormsg);
+ break;
#endif
- case STARTUP_MSG:
- {
- struct passwd *pw = getpwuid(geteuid());
- if (pw) name = pw->pw_name;
+ case STARTUP_MSG:
+ {
+ struct passwd *pw = getpwuid(geteuid());
+
+ if (pw)
+ name = pw->pw_name;
+ }
+ break;
+ default:
+ (void) sprintf(PQerrormsg,
+ "fe_getauthname: invalid authentication system: %d\n",
+ authsvc);
+ break;
}
- break;
- default:
- (void) sprintf(PQerrormsg,
- "fe_getauthname: invalid authentication system: %d\n",
- authsvc);
- break;
- }
-
- if(name && (authn = (char *) malloc(strlen(name) + 1)))
- strcpy(authn, name);
- return(authn);
-}
-
+ if (name && (authn = (char *) malloc(strlen(name) + 1)))
+ strcpy(authn, name);
+ return (authn);
+}
diff --git a/src/interfaces/libpq/fe-auth.h b/src/interfaces/libpq/fe-auth.h
index 646f93df37a..6ca83fe4e89 100644
--- a/src/interfaces/libpq/fe-auth.h
+++ b/src/interfaces/libpq/fe-auth.h
@@ -1,17 +1,17 @@
/*-------------------------------------------------------------------------
*
* fe-auth.h
- *
- * Definitions for network authentication routines
+ *
+ * Definitions for network authentication routines
*
* Copyright (c) 1994, Regents of the University of California
*
- * $Id: fe-auth.h,v 1.3 1997/03/12 21:23:04 scrappy Exp $
+ * $Id: fe-auth.h,v 1.4 1997/09/07 05:03:21 momjian Exp $
*
*-------------------------------------------------------------------------
*/
#ifndef FE_AUTH_H
-#define FE_AUTH_H
+#define FE_AUTH_H
/*----------------------------------------------------------------
* Common routines and definitions
@@ -19,22 +19,22 @@
*/
/* what we call "no authentication system" */
-#define UNAUTHNAME "unauth"
+#define UNAUTHNAME "unauth"
/* what a frontend uses by default */
#if !defined(KRB4) && !defined(KRB5)
-#define DEFAULT_CLIENT_AUTHSVC UNAUTHNAME
-#else /* KRB4 || KRB5 */
-#define DEFAULT_CLIENT_AUTHSVC "kerberos"
-#endif /* KRB4 || KRB5 */
-
-extern int fe_sendauth(MsgType msgtype, Port *port, const char *hostname,
- const char *user, const char *password,
- const char* PQerromsg);
-extern void fe_setauthsvc(const char *name, char* PQerrormsg);
+#define DEFAULT_CLIENT_AUTHSVC UNAUTHNAME
+#else /* KRB4 || KRB5 */
+#define DEFAULT_CLIENT_AUTHSVC "kerberos"
+#endif /* KRB4 || KRB5 */
-#define PG_KRB4_VERSION "PGVER4.1" /* at most KRB_SENDAUTH_VLEN chars */
-#define PG_KRB5_VERSION "PGVER5.1"
+extern int
+fe_sendauth(MsgType msgtype, Port * port, const char *hostname,
+ const char *user, const char *password,
+ const char *PQerromsg);
+extern void fe_setauthsvc(const char *name, char *PQerrormsg);
-#endif /* FE_AUTH_H */
+#define PG_KRB4_VERSION "PGVER4.1" /* at most KRB_SENDAUTH_VLEN chars */
+#define PG_KRB5_VERSION "PGVER5.1"
+#endif /* FE_AUTH_H */
diff --git a/src/interfaces/libpq/fe-connect.c b/src/interfaces/libpq/fe-connect.c
index cb9b10d8704..1b6a1c1243d 100644
--- a/src/interfaces/libpq/fe-connect.c
+++ b/src/interfaces/libpq/fe-connect.c
@@ -1,13 +1,13 @@
/*-------------------------------------------------------------------------
*
* fe-connect.c--
- * functions related to setting up a connection to the backend
+ * functions related to setting up a connection to the backend
*
* Copyright (c) 1994, Regents of the University of California
*
*
* IDENTIFICATION
- * $Header: /cvsroot/pgsql/src/interfaces/libpq/fe-connect.c,v 1.38 1997/09/05 00:09:43 momjian Exp $
+ * $Header: /cvsroot/pgsql/src/interfaces/libpq/fe-connect.c,v 1.39 1997/09/07 05:03:24 momjian Exp $
*
*-------------------------------------------------------------------------
*/
@@ -24,10 +24,11 @@
#include <netinet/tcp.h>
#include <errno.h>
#include <signal.h>
-#include <ctype.h> /* for isspace() */
+#include <ctype.h> /* for isspace() */
#include "postgres.h"
-#include "libpq/pqcomm.h" /* for decls of MsgType, PacketBuf, StartupInfo */
+#include "libpq/pqcomm.h" /* for decls of MsgType, PacketBuf,
+ * StartupInfo */
#include "fe-auth.h"
#include "fe-connect.h"
#include "libpq-fe.h"
@@ -38,14 +39,14 @@
/* use a local version instead of the one found in pqpacket.c */
-static ConnStatusType connectDB(PGconn *conn);
+static ConnStatusType connectDB(PGconn * conn);
-static void startup2PacketBuf(StartupInfo* s, PacketBuf* res);
-static void freePGconn(PGconn *conn);
-static void closePGconn(PGconn *conn);
-static int conninfo_parse(const char *conninfo, char *errorMessage);
-static char *conninfo_getval(char *keyword);
-static void conninfo_free(void);
+static void startup2PacketBuf(StartupInfo * s, PacketBuf * res);
+static void freePGconn(PGconn * conn);
+static void closePGconn(PGconn * conn);
+static int conninfo_parse(const char *conninfo, char *errorMessage);
+static char *conninfo_getval(char *keyword);
+static void conninfo_free(void);
#define NOTIFYLIST_INITIAL_SIZE 10
#define NOTIFYLIST_GROWBY 10
@@ -65,60 +66,66 @@ static void conninfo_free(void);
* The Label and Disp-Char entries are provided for applications that
* want to use PQconndefaults() to create a generic database connection
* dialog. Disp-Char is defined as follows:
- * "" Normal input field
+ * "" Normal input field
* ----------
*/
static PQconninfoOption PQconninfoOptions[] = {
-/* ----------------------------------------------------------------- */
-/* Option-name Environment-Var Compiled-in Current value */
-/* Label Disp-Char */
-/* ----------------- --------------- --------------- --------------- */
- { "authtype", "PGAUTHTYPE", DefaultAuthtype, NULL,
- "Database-Authtype", "", 20 },
+/* ----------------------------------------------------------------- */
+/* Option-name Environment-Var Compiled-in Current value */
+/* Label Disp-Char */
+/* ----------------- --------------- --------------- --------------- */
+ {"authtype", "PGAUTHTYPE", DefaultAuthtype, NULL,
+ "Database-Authtype", "", 20},
- { "user", "PGUSER", NULL, NULL,
- "Database-User", "", 20 },
+ {"user", "PGUSER", NULL, NULL,
+ "Database-User", "", 20},
- { "password", "PGPASSWORD", DefaultPassword, NULL,
- "Database-Password", "", 20 },
+ {"password", "PGPASSWORD", DefaultPassword, NULL,
+ "Database-Password", "", 20},
- { "dbname", "PGDATABASE", NULL, NULL,
- "Database-Name", "", 20 },
+ {"dbname", "PGDATABASE", NULL, NULL,
+ "Database-Name", "", 20},
- { "host", "PGHOST", DefaultHost, NULL,
- "Database-Host", "", 40 },
+ {"host", "PGHOST", DefaultHost, NULL,
+ "Database-Host", "", 40},
- { "port", "PGPORT", DEF_PGPORT, NULL,
- "Database-Port", "", 6 },
+ {"port", "PGPORT", DEF_PGPORT, NULL,
+ "Database-Port", "", 6},
- { "tty", "PGTTY", DefaultTty, NULL,
- "Backend-Debug-TTY", "D", 40 },
+ {"tty", "PGTTY", DefaultTty, NULL,
+ "Backend-Debug-TTY", "D", 40},
- { "options", "PGOPTIONS", DefaultOption, NULL,
- "Backend-Debug-Options", "D", 40 },
-/* ----------------- --------------- --------------- --------------- */
- { NULL, NULL, NULL, NULL,
- NULL, NULL, 0 }
+ {"options", "PGOPTIONS", DefaultOption, NULL,
+ "Backend-Debug-Options", "D", 40},
+/* ----------------- --------------- --------------- --------------- */
+ {NULL, NULL, NULL, NULL,
+ NULL, NULL, 0}
};
struct EnvironmentOptions
+{
+ const char *envName,
+ *pgName;
+} EnvironmentOptions[] =
+
+{
{
- const char *envName, *pgName;
- } EnvironmentOptions[] =
+ "PG_DATESTYLE", "datestyle"
+ },
{
- { "PG_DATESTYLE", "datestyle" },
- { NULL }
- };
-
+ NULL
+ }
+};
+
/* ----------------
- * PQconnectdb
- *
+ * PQconnectdb
+ *
* establishes a connectin to a postgres backend through the postmaster
* using connection information in a string.
*
* The conninfo string is a list of
*
- * option = value
+ * option = value
*
* definitions. Value might be a single value containing no whitespaces
* or a single quoted string. If a single quote should appear everywhere
@@ -126,547 +133,624 @@ struct EnvironmentOptions
*
* Returns a PGconn* which is needed for all subsequent libpq calls
* if the status field of the connection returned is CONNECTION_BAD,
- * then some fields may be null'ed out instead of having valid values
+ * then some fields may be null'ed out instead of having valid values
* ----------------
*/
-PGconn*
+PGconn *
PQconnectdb(const char *conninfo)
{
- PGconn *conn;
- PQconninfoOption *option;
- char errorMessage[ERROR_MSG_LENGTH];
-
- /* ----------
- * Allocate memory for the conn structure
- * ----------
- */
- conn = (PGconn*)malloc(sizeof(PGconn));
- if (conn == NULL) {
- fprintf(stderr,
- "FATAL: PQsetdb() -- unable to allocate memory for a PGconn");
- return (PGconn*)NULL;
- }
- memset((char *)conn, 0, sizeof(PGconn));
-
- /* ----------
- * Parse the conninfo string and get the fallback resources
- * ----------
- */
- if(conninfo_parse(conninfo, errorMessage) < 0) {
- conn->status = CONNECTION_BAD;
- strcpy(conn->errorMessage, errorMessage);
- conninfo_free();
- return conn;
- }
+ PGconn *conn;
+ PQconninfoOption *option;
+ char errorMessage[ERROR_MSG_LENGTH];
- /* ----------
- * Check that we have all connection parameters
- * ----------
- */
- for(option = PQconninfoOptions; option->keyword != NULL; option++) {
- if(option->val != NULL) continue; /* Value was in conninfo */
+ /* ----------
+ * Allocate memory for the conn structure
+ * ----------
+ */
+ conn = (PGconn *) malloc(sizeof(PGconn));
+ if (conn == NULL)
+ {
+ fprintf(stderr,
+ "FATAL: PQsetdb() -- unable to allocate memory for a PGconn");
+ return (PGconn *) NULL;
+ }
+ memset((char *) conn, 0, sizeof(PGconn));
/* ----------
- * No value was found for this option. Return an error.
+ * Parse the conninfo string and get the fallback resources
* ----------
*/
- conn->status = CONNECTION_BAD;
- sprintf(conn->errorMessage,
- "ERROR: PQconnectdb(): Cannot determine a value for option '%s'.\n",
- option->keyword);
- strcat(conn->errorMessage,
- "Option not specified in conninfo string");
- if(option->environ) {
- strcat(conn->errorMessage,
- ", environment variable ");
- strcat(conn->errorMessage, option->environ);
- strcat(conn->errorMessage, "\nnot set");
+ if (conninfo_parse(conninfo, errorMessage) < 0)
+ {
+ conn->status = CONNECTION_BAD;
+ strcpy(conn->errorMessage, errorMessage);
+ conninfo_free();
+ return conn;
}
- strcat(conn->errorMessage, " and no compiled in default value.\n");
+
+ /* ----------
+ * Check that we have all connection parameters
+ * ----------
+ */
+ for (option = PQconninfoOptions; option->keyword != NULL; option++)
+ {
+ if (option->val != NULL)
+ continue; /* Value was in conninfo */
+
+ /* ----------
+ * No value was found for this option. Return an error.
+ * ----------
+ */
+ conn->status = CONNECTION_BAD;
+ sprintf(conn->errorMessage,
+ "ERROR: PQconnectdb(): Cannot determine a value for option '%s'.\n",
+ option->keyword);
+ strcat(conn->errorMessage,
+ "Option not specified in conninfo string");
+ if (option->environ)
+ {
+ strcat(conn->errorMessage,
+ ", environment variable ");
+ strcat(conn->errorMessage, option->environ);
+ strcat(conn->errorMessage, "\nnot set");
+ }
+ strcat(conn->errorMessage, " and no compiled in default value.\n");
+ conninfo_free();
+ return conn;
+ }
+
+ /* ----------
+ * Setup the conn structure
+ * ----------
+ */
+ conn->lobjfuncs = (PGlobjfuncs *) NULL;
+ conn->Pfout = NULL;
+ conn->Pfin = NULL;
+ conn->Pfdebug = NULL;
+ conn->port = NULL;
+ conn->notifyList = DLNewList();
+
+ conn->pghost = strdup(conninfo_getval("host"));
+ conn->pgport = strdup(conninfo_getval("port"));
+ conn->pgtty = strdup(conninfo_getval("tty"));
+ conn->pgoptions = strdup(conninfo_getval("options"));
+ conn->pguser = strdup(conninfo_getval("user"));
+ conn->pgpass = strdup(conninfo_getval("password"));
+ conn->pgauth = strdup(conninfo_getval("authtype"));
+ conn->dbName = strdup(conninfo_getval("dbname"));
+
+ /* ----------
+ * Free the connection info - all is in conn now
+ * ----------
+ */
conninfo_free();
+
+ /*
+ * try to set the auth service if one was specified
+ */
+ if (conn->pgauth)
+ {
+ fe_setauthsvc(conn->pgauth, conn->errorMessage);
+ }
+
+ /* ----------
+ * Connect to the database
+ * ----------
+ */
+ conn->status = connectDB(conn);
+ if (conn->status == CONNECTION_OK)
+ {
+ PGresult *res;
+
+ /*
+ * Send a blank query to make sure everything works; in
+ * particular, that the database exists.
+ */
+ res = PQexec(conn, " ");
+ if (res == NULL || res->resultStatus != PGRES_EMPTY_QUERY)
+ {
+ /* PQexec has put error message in conn->errorMessage */
+ closePGconn(conn);
+ }
+ PQclear(res);
+ }
+
return conn;
- }
-
- /* ----------
- * Setup the conn structure
- * ----------
- */
- conn->lobjfuncs = (PGlobjfuncs *) NULL;
- conn->Pfout = NULL;
- conn->Pfin = NULL;
- conn->Pfdebug = NULL;
- conn->port = NULL;
- conn->notifyList = DLNewList();
-
- conn->pghost = strdup(conninfo_getval("host"));
- conn->pgport = strdup(conninfo_getval("port"));
- conn->pgtty = strdup(conninfo_getval("tty"));
- conn->pgoptions = strdup(conninfo_getval("options"));
- conn->pguser = strdup(conninfo_getval("user"));
- conn->pgpass = strdup(conninfo_getval("password"));
- conn->pgauth = strdup(conninfo_getval("authtype"));
- conn->dbName = strdup(conninfo_getval("dbname"));
-
- /* ----------
- * Free the connection info - all is in conn now
- * ----------
- */
- conninfo_free();
-
- /*
- * try to set the auth service if one was specified
- */
- if(conn->pgauth) {
- fe_setauthsvc(conn->pgauth, conn->errorMessage);
- }
-
- /* ----------
- * Connect to the database
- * ----------
- */
- conn->status = connectDB(conn);
- if (conn->status == CONNECTION_OK) {
- PGresult *res;
- /* Send a blank query to make sure everything works; in particular, that
- the database exists.
- */
- res = PQexec(conn," ");
- if (res == NULL || res->resultStatus != PGRES_EMPTY_QUERY) {
- /* PQexec has put error message in conn->errorMessage */
- closePGconn(conn);
- }
- PQclear(res);
- }
-
- return conn;
}
/* ----------------
- * PQconndefaults
- *
+ * PQconndefaults
+ *
* Parse an empty string like PQconnectdb() would do and return the
* address of the connection options structure. Using this function
* an application might determine all possible options and their
* current default values.
* ----------------
*/
-PQconninfoOption*
+PQconninfoOption *
PQconndefaults(void)
{
- char errorMessage[ERROR_MSG_LENGTH];
+ char errorMessage[ERROR_MSG_LENGTH];
- conninfo_parse("", errorMessage);
- return PQconninfoOptions;
+ conninfo_parse("", errorMessage);
+ return PQconninfoOptions;
}
/* ----------------
- * PQsetdb
- *
+ * PQsetdb
+ *
* establishes a connection to a postgres backend through the postmaster
* at the specified host and port.
*
* returns a PGconn* which is needed for all subsequent libpq calls
* if the status field of the connection returned is CONNECTION_BAD,
- * then some fields may be null'ed out instead of having valid values
+ * then some fields may be null'ed out instead of having valid values
*
- * Uses these environment variables:
+ * Uses these environment variables:
*
- * PGHOST identifies host to which to connect if <pghost> argument
- * is NULL or a null string.
+ * PGHOST identifies host to which to connect if <pghost> argument
+ * is NULL or a null string.
*
- * PGPORT identifies TCP port to which to connect if <pgport> argument
- * is NULL or a null string.
+ * PGPORT identifies TCP port to which to connect if <pgport> argument
+ * is NULL or a null string.
*
- * PGTTY identifies tty to which to send messages if <pgtty> argument
- * is NULL or a null string.
+ * PGTTY identifies tty to which to send messages if <pgtty> argument
+ * is NULL or a null string.
*
- * PGOPTIONS identifies connection options if <pgoptions> argument is
- * NULL or a null string.
+ * PGOPTIONS identifies connection options if <pgoptions> argument is
+ * NULL or a null string.
*
- * PGUSER Postgres username to associate with the connection.
+ * PGUSER Postgres username to associate with the connection.
*
- * PGPASSWORD The user's password.
+ * PGPASSWORD The user's password.
*
- * PGDATABASE name of database to which to connect if <pgdatabase>
- * argument is NULL or a null string
+ * PGDATABASE name of database to which to connect if <pgdatabase>
+ * argument is NULL or a null string
*
- * None of the above need be defined. There are defaults for all of them.
+ * None of the above need be defined. There are defaults for all of them.
*
* ----------------
*/
-PGconn*
-PQsetdb(const char *pghost, const char* pgport, const char* pgoptions, const char* pgtty, const char* dbName)
+PGconn *
+PQsetdb(const char *pghost, const char *pgport, const char *pgoptions, const char *pgtty, const char *dbName)
{
- PGconn *conn;
- char *tmp;
- char errorMessage[ERROR_MSG_LENGTH];
- /* An error message from some service we call. */
- bool error;
- /* We encountered an error that prevents successful completion */
- int i;
-
- conn = (PGconn*)malloc(sizeof(PGconn));
-
- if (conn == NULL)
- fprintf(stderr,
- "FATAL: PQsetdb() -- unable to allocate memory for a PGconn");
- else {
- conn->lobjfuncs = (PGlobjfuncs *) NULL;
- conn->Pfout = NULL;
- conn->Pfin = NULL;
- conn->Pfdebug = NULL;
- conn->port = NULL;
- conn->notifyList = DLNewList();
-
- if (!pghost || pghost[0] == '\0') {
- if (!(tmp = getenv("PGHOST"))) {
- tmp = DefaultHost;
- }
- conn->pghost = strdup(tmp);
- } else
- conn->pghost = strdup(pghost);
-
- if (!pgport || pgport[0] == '\0') {
- if (!(tmp = getenv("PGPORT"))) {
- tmp = DEF_PGPORT;
- }
- conn->pgport = strdup(tmp);
- } else
- conn->pgport = strdup(pgport);
-
- if (!pgtty || pgtty[0] == '\0') {
- if (!(tmp = getenv("PGTTY"))) {
- tmp = DefaultTty;
- }
- conn->pgtty = strdup(tmp);
- } else
- conn->pgtty = strdup(pgtty);
-
- if (!pgoptions || pgoptions[0] == '\0') {
- if (!(tmp = getenv("PGOPTIONS"))) {
- tmp = DefaultOption;
- }
- conn->pgoptions = strdup(tmp);
- } else
- conn->pgoptions = strdup(pgoptions);
-
- if ((tmp = getenv("PGUSER"))) {
- error = FALSE;
- conn->pguser = strdup(tmp);
- } else {
- tmp = fe_getauthname(errorMessage);
- if (tmp == 0) {
- error = TRUE;
- sprintf(conn->errorMessage,
- "FATAL: PQsetdb: Unable to determine a Postgres username!\n");
- } else {
- error = FALSE;
- conn->pguser = tmp;
- }
- }
-
- if((tmp = getenv("PGPASSWORD"))) {
- conn->pgpass = strdup(tmp);
- } else {
- conn->pgpass = 0;
- }
-
- if (!error) {
- if (((tmp = (char *)dbName) && (dbName[0] != '\0')) ||
- ((tmp = getenv("PGDATABASE")))) {
- conn->dbName = strdup(tmp);
- } else conn->dbName = strdup(conn->pguser);
- for(i = 0; conn->dbName[i]; i++)
- if (isupper(conn->dbName[i]))
- conn->dbName[i] = tolower(conn->dbName[i]);
- } else conn->dbName = NULL;
-
- if (error) conn->status = CONNECTION_BAD;
- else {
- conn->status = connectDB(conn);
- /* Puts message in conn->errorMessage */
- if (conn->status == CONNECTION_OK) {
- PGresult *res;
- /* Send a blank query to make sure everything works;
- in particular, that the database exists.
- */
- res = PQexec(conn," ");
- if (res == NULL || res->resultStatus != PGRES_EMPTY_QUERY) {
- /* PQexec has put error message in conn->errorMessage */
- closePGconn(conn);
- }
- PQclear(res);
- }
- }
- }
- return conn;
+ PGconn *conn;
+ char *tmp;
+ char errorMessage[ERROR_MSG_LENGTH];
+
+ /* An error message from some service we call. */
+ bool error;
+
+ /* We encountered an error that prevents successful completion */
+ int i;
+
+ conn = (PGconn *) malloc(sizeof(PGconn));
+
+ if (conn == NULL)
+ fprintf(stderr,
+ "FATAL: PQsetdb() -- unable to allocate memory for a PGconn");
+ else
+ {
+ conn->lobjfuncs = (PGlobjfuncs *) NULL;
+ conn->Pfout = NULL;
+ conn->Pfin = NULL;
+ conn->Pfdebug = NULL;
+ conn->port = NULL;
+ conn->notifyList = DLNewList();
+
+ if (!pghost || pghost[0] == '\0')
+ {
+ if (!(tmp = getenv("PGHOST")))
+ {
+ tmp = DefaultHost;
+ }
+ conn->pghost = strdup(tmp);
+ }
+ else
+ conn->pghost = strdup(pghost);
+
+ if (!pgport || pgport[0] == '\0')
+ {
+ if (!(tmp = getenv("PGPORT")))
+ {
+ tmp = DEF_PGPORT;
+ }
+ conn->pgport = strdup(tmp);
+ }
+ else
+ conn->pgport = strdup(pgport);
+
+ if (!pgtty || pgtty[0] == '\0')
+ {
+ if (!(tmp = getenv("PGTTY")))
+ {
+ tmp = DefaultTty;
+ }
+ conn->pgtty = strdup(tmp);
+ }
+ else
+ conn->pgtty = strdup(pgtty);
+
+ if (!pgoptions || pgoptions[0] == '\0')
+ {
+ if (!(tmp = getenv("PGOPTIONS")))
+ {
+ tmp = DefaultOption;
+ }
+ conn->pgoptions = strdup(tmp);
+ }
+ else
+ conn->pgoptions = strdup(pgoptions);
+
+ if ((tmp = getenv("PGUSER")))
+ {
+ error = FALSE;
+ conn->pguser = strdup(tmp);
+ }
+ else
+ {
+ tmp = fe_getauthname(errorMessage);
+ if (tmp == 0)
+ {
+ error = TRUE;
+ sprintf(conn->errorMessage,
+ "FATAL: PQsetdb: Unable to determine a Postgres username!\n");
+ }
+ else
+ {
+ error = FALSE;
+ conn->pguser = tmp;
+ }
+ }
+
+ if ((tmp = getenv("PGPASSWORD")))
+ {
+ conn->pgpass = strdup(tmp);
+ }
+ else
+ {
+ conn->pgpass = 0;
+ }
+
+ if (!error)
+ {
+ if (((tmp = (char *) dbName) && (dbName[0] != '\0')) ||
+ ((tmp = getenv("PGDATABASE"))))
+ {
+ conn->dbName = strdup(tmp);
+ }
+ else
+ conn->dbName = strdup(conn->pguser);
+ for (i = 0; conn->dbName[i]; i++)
+ if (isupper(conn->dbName[i]))
+ conn->dbName[i] = tolower(conn->dbName[i]);
+ }
+ else
+ conn->dbName = NULL;
+
+ if (error)
+ conn->status = CONNECTION_BAD;
+ else
+ {
+ conn->status = connectDB(conn);
+ /* Puts message in conn->errorMessage */
+ if (conn->status == CONNECTION_OK)
+ {
+ PGresult *res;
+
+ /*
+ * Send a blank query to make sure everything works; in
+ * particular, that the database exists.
+ */
+ res = PQexec(conn, " ");
+ if (res == NULL || res->resultStatus != PGRES_EMPTY_QUERY)
+ {
+ /* PQexec has put error message in conn->errorMessage */
+ closePGconn(conn);
+ }
+ PQclear(res);
+ }
+ }
+ }
+ return conn;
}
-
+
/*
* connectDB -
- * make a connection to the backend so it is ready to receive queries.
+ * make a connection to the backend so it is ready to receive queries.
* return CONNECTION_OK if successful, CONNECTION_BAD if not.
*
*/
-static ConnStatusType
-connectDB(PGconn *conn)
+static ConnStatusType
+connectDB(PGconn * conn)
{
- struct hostent *hp;
-
- StartupInfo startup;
- PacketBuf pacBuf;
- int status;
- MsgType msgtype;
- int laddrlen = sizeof(struct sockaddr);
- Port *port = conn->port;
- int portno;
-
- /*
- *
- * Initialize the startup packet.
- *
- * This data structure is used for the seq-packet protocol. It
- * describes the frontend-backend connection.
- *
- *
- */
- strncpy(startup.user,conn->pguser,sizeof(startup.user));
- strncpy(startup.database,conn->dbName,sizeof(startup.database));
- strncpy(startup.tty,conn->pgtty,sizeof(startup.tty));
- if (conn->pgoptions) {
- strncpy(startup.options,conn->pgoptions, sizeof(startup.options));
- }
- else
- startup.options[0]='\0';
- startup.execFile[0]='\0'; /* not used */
-
- /*
- *
- * Open a connection to postmaster/backend.
- *
- */
- port = (Port *) malloc(sizeof(Port));
- memset((char *) port, 0, sizeof(Port));
-
- if (!(hp = gethostbyname(conn->pghost)) || hp->h_addrtype != AF_INET) {
- (void) sprintf(conn->errorMessage,
- "connectDB() -- unknown hostname: %s\n",
- conn->pghost);
- goto connect_errReturn;
- }
- memset((char *) &port->raddr, 0, sizeof(port->raddr));
- memmove((char *) &(port->raddr.sin_addr),
- (char *) hp->h_addr,
- hp->h_length);
- port->raddr.sin_family = AF_INET;
- portno = atoi(conn->pgport);
- port->raddr.sin_port = htons((unsigned short)(portno));
-
- /* connect to the server */
- if ((port->sock = socket(AF_INET, SOCK_STREAM, 0)) < 0) {
- (void) sprintf(conn->errorMessage,
- "connectDB() -- socket() failed: errno=%d\n%s\n",
- errno, strerror(errno));
- goto connect_errReturn;
- }
- if (connect(port->sock, (struct sockaddr *)&port->raddr,
- sizeof(port->raddr)) < 0) {
- (void) sprintf(conn->errorMessage,
- "connectDB() failed: Is the postmaster running at '%s' on port '%s'?\n",
- conn->pghost,conn->pgport);
- goto connect_errReturn;
- }
- {
- struct protoent *pe;
- int on=1;
-
- pe = getprotobyname ("TCP");
- if ( pe == NULL )
- {
- (void) sprintf(conn->errorMessage,
- "connectDB(): getprotobyname failed\n");
- goto connect_errReturn;
+ struct hostent *hp;
+
+ StartupInfo startup;
+ PacketBuf pacBuf;
+ int status;
+ MsgType msgtype;
+ int laddrlen = sizeof(struct sockaddr);
+ Port *port = conn->port;
+ int portno;
+
+ /*
+ * Initialize the startup packet.
+ *
+ * This data structure is used for the seq-packet protocol. It describes
+ * the frontend-backend connection.
+ *
+ *
+ */
+ strncpy(startup.user, conn->pguser, sizeof(startup.user));
+ strncpy(startup.database, conn->dbName, sizeof(startup.database));
+ strncpy(startup.tty, conn->pgtty, sizeof(startup.tty));
+ if (conn->pgoptions)
+ {
+ strncpy(startup.options, conn->pgoptions, sizeof(startup.options));
+ }
+ else
+ startup.options[0] = '\0';
+ startup.execFile[0] = '\0'; /* not used */
+
+ /*
+ * Open a connection to postmaster/backend.
+ *
+ */
+ port = (Port *) malloc(sizeof(Port));
+ memset((char *) port, 0, sizeof(Port));
+
+ if (!(hp = gethostbyname(conn->pghost)) || hp->h_addrtype != AF_INET)
+ {
+ (void) sprintf(conn->errorMessage,
+ "connectDB() -- unknown hostname: %s\n",
+ conn->pghost);
+ goto connect_errReturn;
+ }
+ memset((char *) &port->raddr, 0, sizeof(port->raddr));
+ memmove((char *) &(port->raddr.sin_addr),
+ (char *) hp->h_addr,
+ hp->h_length);
+ port->raddr.sin_family = AF_INET;
+ portno = atoi(conn->pgport);
+ port->raddr.sin_port = htons((unsigned short) (portno));
+
+ /* connect to the server */
+ if ((port->sock = socket(AF_INET, SOCK_STREAM, 0)) < 0)
+ {
+ (void) sprintf(conn->errorMessage,
+ "connectDB() -- socket() failed: errno=%d\n%s\n",
+ errno, strerror(errno));
+ goto connect_errReturn;
+ }
+ if (connect(port->sock, (struct sockaddr *) & port->raddr,
+ sizeof(port->raddr)) < 0)
+ {
+ (void) sprintf(conn->errorMessage,
+ "connectDB() failed: Is the postmaster running at '%s' on port '%s'?\n",
+ conn->pghost, conn->pgport);
+ goto connect_errReturn;
+ }
+ {
+ struct protoent *pe;
+ int on = 1;
+
+ pe = getprotobyname("TCP");
+ if (pe == NULL)
+ {
+ (void) sprintf(conn->errorMessage,
+ "connectDB(): getprotobyname failed\n");
+ goto connect_errReturn;
+ }
+ if (setsockopt(port->sock, pe->p_proto, TCP_NODELAY,
+ &on, sizeof(on)) < 0)
+ {
+ (void) sprintf(conn->errorMessage,
+ "connectDB(): setsockopt failed\n");
+ goto connect_errReturn;
+ }
+ }
+
+ /* fill in the client address */
+ if (getsockname(port->sock, (struct sockaddr *) & port->laddr,
+ &laddrlen) < 0)
+ {
+ (void) sprintf(conn->errorMessage,
+ "connectDB() -- getsockname() failed: errno=%d\n%s\n",
+ errno, strerror(errno));
+ goto connect_errReturn;
+ }
+
+ /* by this point, connection has been opened */
+ msgtype = fe_getauthsvc(conn->errorMessage);
+
+/* pacBuf = startup2PacketBuf(&startup);*/
+ startup2PacketBuf(&startup, &pacBuf);
+ pacBuf.msgtype = (MsgType) htonl(msgtype);
+ status = packetSend(port, &pacBuf, sizeof(PacketBuf), BLOCKING);
+
+ if (status == STATUS_ERROR)
+ {
+ sprintf(conn->errorMessage,
+ "connectDB() -- couldn't send complete packet: errno=%d\n%s\n", errno, strerror(errno));
+ goto connect_errReturn;
}
- if ( setsockopt (port->sock, pe->p_proto, TCP_NODELAY,
- &on, sizeof (on)) < 0 )
- {
- (void) sprintf(conn->errorMessage,
- "connectDB(): setsockopt failed\n");
- goto connect_errReturn;
+
+ /* authenticate as required */
+ if (fe_sendauth(msgtype, port, conn->pghost,
+ conn->pguser, conn->pgpass,
+ conn->errorMessage) != STATUS_OK)
+ {
+ (void) sprintf(conn->errorMessage,
+ "connectDB() -- authentication failed with %s\n",
+ conn->pghost);
+ goto connect_errReturn;
}
- }
-
- /* fill in the client address */
- if (getsockname(port->sock, (struct sockaddr *) &port->laddr,
- &laddrlen) < 0) {
- (void) sprintf(conn->errorMessage,
- "connectDB() -- getsockname() failed: errno=%d\n%s\n",
- errno, strerror(errno));
- goto connect_errReturn;
- }
-
- /* by this point, connection has been opened */
- msgtype = fe_getauthsvc(conn->errorMessage);
-
-/* pacBuf = startup2PacketBuf(&startup);*/
- startup2PacketBuf(&startup, &pacBuf);
- pacBuf.msgtype = (MsgType) htonl(msgtype);
- status = packetSend(port, &pacBuf, sizeof(PacketBuf), BLOCKING);
-
- if (status == STATUS_ERROR)
+
+ /* free the password so it's not hanging out in memory forever */
+ if (conn->pgpass)
{
- sprintf(conn->errorMessage,
- "connectDB() -- couldn't send complete packet: errno=%d\n%s\n", errno,strerror(errno));
- goto connect_errReturn;
+ free(conn->pgpass);
}
- /* authenticate as required*/
- if (fe_sendauth(msgtype, port, conn->pghost,
- conn->pguser, conn->pgpass,
- conn->errorMessage) != STATUS_OK) {
- (void) sprintf(conn->errorMessage,
- "connectDB() -- authentication failed with %s\n",
- conn->pghost);
- goto connect_errReturn;
- }
-
- /* free the password so it's not hanging out in memory forever */
- if(conn->pgpass) {
- free(conn->pgpass);
- }
-
- /* set up the socket file descriptors */
- conn->Pfout = fdopen(port->sock, "w");
- conn->Pfin = fdopen(dup(port->sock), "r");
- if (!conn->Pfout || !conn->Pfin) {
- (void) sprintf(conn->errorMessage,
- "connectDB() -- fdopen() failed: errno=%d\n%s\n",
- errno, strerror(errno));
- goto connect_errReturn;
- }
-
- conn->port = port;
-
- {
+ /* set up the socket file descriptors */
+ conn->Pfout = fdopen(port->sock, "w");
+ conn->Pfin = fdopen(dup(port->sock), "r");
+ if (!conn->Pfout || !conn->Pfin)
+ {
+ (void) sprintf(conn->errorMessage,
+ "connectDB() -- fdopen() failed: errno=%d\n%s\n",
+ errno, strerror(errno));
+ goto connect_errReturn;
+ }
+
+ conn->port = port;
+
+ {
struct EnvironmentOptions *eo;
- char setQuery[80]; /* mjl: size okay? XXX */
-
- for(eo = EnvironmentOptions; eo->envName; eo++)
+ char setQuery[80]; /* mjl: size okay? XXX */
+
+ for (eo = EnvironmentOptions; eo->envName; eo++)
+ {
+ const char *val;
+
+ if ((val = getenv(eo->envName)))
{
- const char *val;
-
- if((val = getenv(eo->envName)))
- {
- PGresult *res;
-
+ PGresult *res;
+
sprintf(setQuery, "SET %s TO '%.60s'", eo->pgName, val);
res = PQexec(conn, setQuery);
PQclear(res); /* Don't care? */
- }
}
}
- return CONNECTION_OK;
+ }
+ return CONNECTION_OK;
connect_errReturn:
- /* Igor/6/3/97 - We need to free it here...otherwise the function
- returns without setting conn->port to port. Because of that
- any way of referencing this variable will be lost and it's allocated
- memory will not be freed. */
- free(port); /* PURIFY */
- return CONNECTION_BAD;
+ /*
+ * Igor/6/3/97 - We need to free it here...otherwise the function
+ * returns without setting conn->port to port. Because of that any way
+ * of referencing this variable will be lost and it's allocated memory
+ * will not be freed.
+ */
+ free(port); /* PURIFY */
+ return CONNECTION_BAD;
}
/*
* freePGconn
- * - free the PGconn data structure
+ * - free the PGconn data structure
*
*/
-static void
-freePGconn(PGconn *conn)
+static void
+freePGconn(PGconn * conn)
{
- if (!conn) return;
- if (conn->pghost) free(conn->pghost);
- if (conn->pgtty) free(conn->pgtty);
- if (conn->pgoptions) free(conn->pgoptions);
- if (conn->pgport) free(conn->pgport);
- if (conn->dbName) free(conn->dbName);
- if (conn->pguser) free(conn->pguser);
- if (conn->notifyList) DLFreeList(conn->notifyList);
- if (conn->port) free(conn->port);
- free(conn);
+ if (!conn)
+ return;
+ if (conn->pghost)
+ free(conn->pghost);
+ if (conn->pgtty)
+ free(conn->pgtty);
+ if (conn->pgoptions)
+ free(conn->pgoptions);
+ if (conn->pgport)
+ free(conn->pgport);
+ if (conn->dbName)
+ free(conn->dbName);
+ if (conn->pguser)
+ free(conn->pguser);
+ if (conn->notifyList)
+ DLFreeList(conn->notifyList);
+ if (conn->port)
+ free(conn->port);
+ free(conn);
}
/*
closePGconn
- - properly close a connection to the backend
+ - properly close a connection to the backend
*/
static void
-closePGconn(PGconn *conn)
+closePGconn(PGconn * conn)
{
/* GH: What to do for !USE_POSIX_SIGNALS ? */
#if defined(USE_POSIX_SIGNALS)
- struct sigaction ignore_action;
- /* This is used as a constant, but not declared as such because the
- sigaction structure is defined differently on different systems */
- struct sigaction oldaction;
-
- /* If connection is already gone, that's cool. No reason for kernel
- to kill us when we try to write to it. So ignore SIGPIPE signals.
- */
- ignore_action.sa_handler = SIG_IGN;
- sigemptyset(&ignore_action.sa_mask);
- ignore_action.sa_flags = 0;
- sigaction(SIGPIPE, (struct sigaction *) &ignore_action, &oldaction);
-
- fputs("X\0", conn->Pfout);
- fflush(conn->Pfout);
- sigaction(SIGPIPE, &oldaction, NULL);
+ struct sigaction ignore_action;
+
+ /*
+ * This is used as a constant, but not declared as such because the
+ * sigaction structure is defined differently on different systems
+ */
+ struct sigaction oldaction;
+
+ /*
+ * If connection is already gone, that's cool. No reason for kernel
+ * to kill us when we try to write to it. So ignore SIGPIPE signals.
+ */
+ ignore_action.sa_handler = SIG_IGN;
+ sigemptyset(&ignore_action.sa_mask);
+ ignore_action.sa_flags = 0;
+ sigaction(SIGPIPE, (struct sigaction *) & ignore_action, &oldaction);
+
+ fputs("X\0", conn->Pfout);
+ fflush(conn->Pfout);
+ sigaction(SIGPIPE, &oldaction, NULL);
#else
- signal(SIGPIPE, SIG_IGN);
- fputs("X\0", conn->Pfout);
- fflush(conn->Pfout);
- signal(SIGPIPE, SIG_DFL);
+ signal(SIGPIPE, SIG_IGN);
+ fputs("X\0", conn->Pfout);
+ fflush(conn->Pfout);
+ signal(SIGPIPE, SIG_DFL);
#endif
- if (conn->Pfout) fclose(conn->Pfout);
- if (conn->Pfin) fclose(conn->Pfin);
- if (conn->Pfdebug) fclose(conn->Pfdebug);
- conn->status = CONNECTION_BAD; /* Well, not really _bad_ - just absent */
+ if (conn->Pfout)
+ fclose(conn->Pfout);
+ if (conn->Pfin)
+ fclose(conn->Pfin);
+ if (conn->Pfdebug)
+ fclose(conn->Pfdebug);
+ conn->status = CONNECTION_BAD; /* Well, not really _bad_ - just
+ * absent */
}
/*
PQfinish:
- properly close a connection to the backend
- also frees the PGconn data structure so it shouldn't be re-used
- after this
+ properly close a connection to the backend
+ also frees the PGconn data structure so it shouldn't be re-used
+ after this
*/
void
-PQfinish(PGconn *conn)
+PQfinish(PGconn * conn)
{
- if (!conn) {
- fprintf(stderr,"PQfinish() -- pointer to PGconn is null\n");
- } else {
- if (conn->status == CONNECTION_OK)
- closePGconn(conn);
- freePGconn(conn);
- }
+ if (!conn)
+ {
+ fprintf(stderr, "PQfinish() -- pointer to PGconn is null\n");
+ }
+ else
+ {
+ if (conn->status == CONNECTION_OK)
+ closePGconn(conn);
+ freePGconn(conn);
+ }
}
/* PQreset :
resets the connection to the backend
- closes the existing connection and makes a new one
+ closes the existing connection and makes a new one
*/
void
-PQreset(PGconn *conn)
+PQreset(PGconn * conn)
{
- if (!conn) {
- fprintf(stderr,"PQreset() -- pointer to PGconn is null\n");
- } else {
- closePGconn(conn);
- conn->status = connectDB(conn);
- }
+ if (!conn)
+ {
+ fprintf(stderr, "PQreset() -- pointer to PGconn is null\n");
+ }
+ else
+ {
+ closePGconn(conn);
+ conn->status = connectDB(conn);
+ }
}
/*
@@ -679,29 +763,30 @@ PQreset(PGconn *conn)
*
* RETURNS: STATUS_ERROR if the write fails, STATUS_OK otherwise.
* SIDE_EFFECTS: may block.
- * NOTES: Non-blocking writes would significantly complicate
- * buffer management. For now, we're not going to do it.
+ * NOTES: Non-blocking writes would significantly complicate
+ * buffer management. For now, we're not going to do it.
*
*/
int
-packetSend(Port *port,
- PacketBuf *buf,
- PacketLen len,
- bool nonBlocking)
+packetSend(Port * port,
+ PacketBuf * buf,
+ PacketLen len,
+ bool nonBlocking)
{
- PacketLen totalLen;
- int addrLen = sizeof(struct sockaddr_in);
-
- totalLen = len;
-
- len = sendto(port->sock, (Addr) buf, totalLen, /* flags */ 0,
- (struct sockaddr *)&(port->raddr), addrLen);
-
- if (len < totalLen) {
- return(STATUS_ERROR);
- }
-
- return(STATUS_OK);
+ PacketLen totalLen;
+ int addrLen = sizeof(struct sockaddr_in);
+
+ totalLen = len;
+
+ len = sendto(port->sock, (Addr) buf, totalLen, /* flags */ 0,
+ (struct sockaddr *) & (port->raddr), addrLen);
+
+ if (len < totalLen)
+ {
+ return (STATUS_ERROR);
+ }
+
+ return (STATUS_OK);
}
/*
@@ -709,359 +794,412 @@ packetSend(Port *port,
*
* this is just like StartupInfo2Packet(), defined in backend/libpq/pqpacket.c
* but we repeat it here so we don't have to link in libpq.a
- *
+ *
* converts a StartupInfo structure to a PacketBuf
*/
static void
-startup2PacketBuf(StartupInfo* s, PacketBuf* res)
+startup2PacketBuf(StartupInfo * s, PacketBuf * res)
{
- char* tmp;
-
-/* res = (PacketBuf*)malloc(sizeof(PacketBuf)); */
- res->len = htonl(sizeof(PacketBuf));
- /* use \n to delimit the strings */
- res->data[0] = '\0';
-
- tmp= res->data;
-
- strncpy(tmp, s->database, sizeof(s->database));
- tmp += sizeof(s->database);
- strncpy(tmp, s->user, sizeof(s->user));
- tmp += sizeof(s->user);
- strncpy(tmp, s->options, sizeof(s->options));
- tmp += sizeof(s->options);
- strncpy(tmp, s->execFile, sizeof(s->execFile));
- tmp += sizeof(s->execFile);
- strncpy(tmp, s->tty, sizeof(s->tty));
+ char *tmp;
+
+/* res = (PacketBuf*)malloc(sizeof(PacketBuf)); */
+ res->len = htonl(sizeof(PacketBuf));
+ /* use \n to delimit the strings */
+ res->data[0] = '\0';
+
+ tmp = res->data;
+
+ strncpy(tmp, s->database, sizeof(s->database));
+ tmp += sizeof(s->database);
+ strncpy(tmp, s->user, sizeof(s->user));
+ tmp += sizeof(s->user);
+ strncpy(tmp, s->options, sizeof(s->options));
+ tmp += sizeof(s->options);
+ strncpy(tmp, s->execFile, sizeof(s->execFile));
+ tmp += sizeof(s->execFile);
+ strncpy(tmp, s->tty, sizeof(s->tty));
}
/* ----------------
* Conninfo parser routine
* ----------------
*/
-static int conninfo_parse(const char *conninfo, char *errorMessage)
+static int
+conninfo_parse(const char *conninfo, char *errorMessage)
{
- char *pname;
- char *pval;
- char *buf;
- char *tmp;
- char *cp;
- char *cp2;
- PQconninfoOption *option;
- char errortmp[ERROR_MSG_LENGTH];
-
- conninfo_free();
-
- if((buf = strdup(conninfo)) == NULL) {
- strcpy(errorMessage,
- "FATAL: cannot allocate memory for copy of conninfo string\n");
- return -1;
- }
- cp = buf;
-
- while(*cp) {
- /* Skip blanks before the parameter name */
- if(isspace(*cp)) {
- cp++;
- continue;
+ char *pname;
+ char *pval;
+ char *buf;
+ char *tmp;
+ char *cp;
+ char *cp2;
+ PQconninfoOption *option;
+ char errortmp[ERROR_MSG_LENGTH];
+
+ conninfo_free();
+
+ if ((buf = strdup(conninfo)) == NULL)
+ {
+ strcpy(errorMessage,
+ "FATAL: cannot allocate memory for copy of conninfo string\n");
+ return -1;
}
+ cp = buf;
- /* Get the parameter name */
- pname = cp;
- while(*cp) {
- if(*cp == '=') {
- break;
- }
- if(isspace(*cp)) {
- *cp++ = '\0';
- while(*cp) {
- if(!isspace(*cp)) {
- break;
- }
- cp++;
+ while (*cp)
+ {
+ /* Skip blanks before the parameter name */
+ if (isspace(*cp))
+ {
+ cp++;
+ continue;
}
- break;
- }
- cp++;
- }
- /* Check that there is a following '=' */
- if(*cp != '=') {
- sprintf(errorMessage,
- "ERROR: PQconnectdb() - Missing '=' after '%s' in conninfo\n",
- pname);
- free(buf);
- return -1;
- }
- *cp++ = '\0';
-
- /* Skip blanks after the '=' */
- while(*cp) {
- if(!isspace(*cp)) {
- break;
- }
- cp++;
- }
+ /* Get the parameter name */
+ pname = cp;
+ while (*cp)
+ {
+ if (*cp == '=')
+ {
+ break;
+ }
+ if (isspace(*cp))
+ {
+ *cp++ = '\0';
+ while (*cp)
+ {
+ if (!isspace(*cp))
+ {
+ break;
+ }
+ cp++;
+ }
+ break;
+ }
+ cp++;
+ }
- pval = cp;
+ /* Check that there is a following '=' */
+ if (*cp != '=')
+ {
+ sprintf(errorMessage,
+ "ERROR: PQconnectdb() - Missing '=' after '%s' in conninfo\n",
+ pname);
+ free(buf);
+ return -1;
+ }
+ *cp++ = '\0';
- if(*cp != '\'') {
- cp2 = pval;
- while(*cp) {
- if(isspace(*cp)) {
- *cp++ = '\0';
- break;
+ /* Skip blanks after the '=' */
+ while (*cp)
+ {
+ if (!isspace(*cp))
+ {
+ break;
+ }
+ cp++;
}
- if(*cp == '\\') {
- cp++;
- if(*cp != '\0') {
- *cp2++ = *cp++;
- }
- } else {
- *cp2++ = *cp++;
+
+ pval = cp;
+
+ if (*cp != '\'')
+ {
+ cp2 = pval;
+ while (*cp)
+ {
+ if (isspace(*cp))
+ {
+ *cp++ = '\0';
+ break;
+ }
+ if (*cp == '\\')
+ {
+ cp++;
+ if (*cp != '\0')
+ {
+ *cp2++ = *cp++;
+ }
+ }
+ else
+ {
+ *cp2++ = *cp++;
+ }
+ }
+ *cp2 = '\0';
}
- }
- *cp2 = '\0';
- } else {
- cp2 = pval;
- cp++;
- for(;;) {
- if(*cp == '\0') {
- sprintf(errorMessage,
- "ERROR: PQconnectdb() - unterminated quoted string in conninfo\n");
- free(buf);
- return -1;
+ else
+ {
+ cp2 = pval;
+ cp++;
+ for (;;)
+ {
+ if (*cp == '\0')
+ {
+ sprintf(errorMessage,
+ "ERROR: PQconnectdb() - unterminated quoted string in conninfo\n");
+ free(buf);
+ return -1;
+ }
+ if (*cp == '\\')
+ {
+ cp++;
+ if (*cp != '\0')
+ {
+ *cp2++ = *cp++;
+ }
+ continue;
+ }
+ if (*cp == '\'')
+ {
+ *cp2 = '\0';
+ cp++;
+ break;
+ }
+ *cp2++ = *cp++;
+ }
}
- if(*cp == '\\') {
- cp++;
- if(*cp != '\0') {
- *cp2++ = *cp++;
- }
- continue;
+
+ /* ----------
+ * Now we have the name and the value. Search
+ * for the param record.
+ * ----------
+ */
+ for (option = PQconninfoOptions; option->keyword != NULL; option++)
+ {
+ if (!strcmp(option->keyword, pname))
+ {
+ break;
+ }
}
- if(*cp == '\'') {
- *cp2 = '\0';
- cp++;
- break;
+ if (option->keyword == NULL)
+ {
+ sprintf(errorMessage,
+ "ERROR: PQconnectdb() - unknown option '%s'\n",
+ pname);
+ free(buf);
+ return -1;
}
- *cp2++ = *cp++;
- }
- }
- /* ----------
- * Now we have the name and the value. Search
- * for the param record.
- * ----------
- */
- for(option = PQconninfoOptions; option->keyword != NULL; option++) {
- if(!strcmp(option->keyword, pname)) {
- break;
- }
- }
- if(option->keyword == NULL) {
- sprintf(errorMessage,
- "ERROR: PQconnectdb() - unknown option '%s'\n",
- pname);
- free(buf);
- return -1;
+ /* ----------
+ * Store the value
+ * ----------
+ */
+ option->val = strdup(pval);
}
- /* ----------
- * Store the value
- * ----------
- */
- option->val = strdup(pval);
- }
-
- free(buf);
-
- /* ----------
- * Get the fallback resources for parameters not specified
- * in the conninfo string.
- * ----------
- */
- for(option = PQconninfoOptions; option->keyword != NULL; option++) {
- if(option->val != NULL) continue; /* Value was in conninfo */
+ free(buf);
/* ----------
- * Try to get the environment variable fallback
+ * Get the fallback resources for parameters not specified
+ * in the conninfo string.
* ----------
*/
- if(option->environ != NULL) {
- if((tmp = getenv(option->environ)) != NULL) {
- option->val = strdup(tmp);
- continue;
- }
- }
+ for (option = PQconninfoOptions; option->keyword != NULL; option++)
+ {
+ if (option->val != NULL)
+ continue; /* Value was in conninfo */
+
+ /* ----------
+ * Try to get the environment variable fallback
+ * ----------
+ */
+ if (option->environ != NULL)
+ {
+ if ((tmp = getenv(option->environ)) != NULL)
+ {
+ option->val = strdup(tmp);
+ continue;
+ }
+ }
- /* ----------
- * No environment variable specified or this one isn't set -
- * try compiled in
- * ----------
- */
- if(option->compiled != NULL) {
- option->val = strdup(option->compiled);
- continue;
- }
+ /* ----------
+ * No environment variable specified or this one isn't set -
+ * try compiled in
+ * ----------
+ */
+ if (option->compiled != NULL)
+ {
+ option->val = strdup(option->compiled);
+ continue;
+ }
- /* ----------
- * Special handling for user
- * ----------
- */
- if(!strcmp(option->keyword, "user")) {
- tmp = fe_getauthname(errortmp);
- if (tmp) {
- option->val = strdup(tmp);
- }
- }
+ /* ----------
+ * Special handling for user
+ * ----------
+ */
+ if (!strcmp(option->keyword, "user"))
+ {
+ tmp = fe_getauthname(errortmp);
+ if (tmp)
+ {
+ option->val = strdup(tmp);
+ }
+ }
- /* ----------
- * Special handling for dbname
- * ----------
- */
- if(!strcmp(option->keyword, "dbname")) {
- tmp = conninfo_getval("user");
- if (tmp) {
- option->val = strdup(tmp);
- }
+ /* ----------
+ * Special handling for dbname
+ * ----------
+ */
+ if (!strcmp(option->keyword, "dbname"))
+ {
+ tmp = conninfo_getval("user");
+ if (tmp)
+ {
+ option->val = strdup(tmp);
+ }
+ }
}
- }
- return 0;
+ return 0;
}
-static char*
+static char *
conninfo_getval(char *keyword)
{
- PQconninfoOption *option;
+ PQconninfoOption *option;
- for(option = PQconninfoOptions; option->keyword != NULL; option++) {
- if (!strcmp(option->keyword, keyword)) {
- return option->val;
+ for (option = PQconninfoOptions; option->keyword != NULL; option++)
+ {
+ if (!strcmp(option->keyword, keyword))
+ {
+ return option->val;
+ }
}
- }
- return NULL;
+ return NULL;
}
static void
conninfo_free()
{
- PQconninfoOption *option;
+ PQconninfoOption *option;
- for(option = PQconninfoOptions; option->keyword != NULL; option++) {
- if(option->val != NULL) {
- free(option->val);
- option->val = NULL;
+ for (option = PQconninfoOptions; option->keyword != NULL; option++)
+ {
+ if (option->val != NULL)
+ {
+ free(option->val);
+ option->val = NULL;
+ }
}
- }
}
/* =========== accessor functions for PGconn ========= */
-char*
-PQdb(PGconn* conn)
+char *
+PQdb(PGconn * conn)
{
- if (!conn) {
- fprintf(stderr,"PQdb() -- pointer to PGconn is null\n");
- return (char *)NULL;
- }
- return conn->dbName;
+ if (!conn)
+ {
+ fprintf(stderr, "PQdb() -- pointer to PGconn is null\n");
+ return (char *) NULL;
+ }
+ return conn->dbName;
}
-char*
-PQuser(PGconn* conn)
+char *
+PQuser(PGconn * conn)
{
- if (!conn) {
- fprintf(stderr,"PQuser() -- pointer to PGconn is null\n");
- return (char *)NULL;
- }
- return conn->pguser;
+ if (!conn)
+ {
+ fprintf(stderr, "PQuser() -- pointer to PGconn is null\n");
+ return (char *) NULL;
+ }
+ return conn->pguser;
}
-char*
-PQhost(PGconn* conn)
+char *
+PQhost(PGconn * conn)
{
- if (!conn) {
- fprintf(stderr,"PQhost() -- pointer to PGconn is null\n");
- return (char *)NULL;
- }
+ if (!conn)
+ {
+ fprintf(stderr, "PQhost() -- pointer to PGconn is null\n");
+ return (char *) NULL;
+ }
- return conn->pghost;
+ return conn->pghost;
}
-char*
-PQoptions(PGconn* conn)
+char *
+PQoptions(PGconn * conn)
{
- if (!conn) {
- fprintf(stderr,"PQoptions() -- pointer to PGconn is null\n");
- return (char *)NULL;
- }
- return conn->pgoptions;
+ if (!conn)
+ {
+ fprintf(stderr, "PQoptions() -- pointer to PGconn is null\n");
+ return (char *) NULL;
+ }
+ return conn->pgoptions;
}
-char*
-PQtty(PGconn* conn)
+char *
+PQtty(PGconn * conn)
{
- if (!conn) {
- fprintf(stderr,"PQtty() -- pointer to PGconn is null\n");
- return (char *)NULL;
- }
- return conn->pgtty;
+ if (!conn)
+ {
+ fprintf(stderr, "PQtty() -- pointer to PGconn is null\n");
+ return (char *) NULL;
+ }
+ return conn->pgtty;
}
-char*
-PQport(PGconn* conn)
+char *
+PQport(PGconn * conn)
{
- if (!conn) {
- fprintf(stderr,"PQport() -- pointer to PGconn is null\n");
- return (char *)NULL;
- }
- return conn->pgport;
+ if (!conn)
+ {
+ fprintf(stderr, "PQport() -- pointer to PGconn is null\n");
+ return (char *) NULL;
+ }
+ return conn->pgport;
}
ConnStatusType
-PQstatus(PGconn* conn)
+PQstatus(PGconn * conn)
{
- if (!conn) {
- fprintf(stderr,"PQstatus() -- pointer to PGconn is null\n");
- return CONNECTION_BAD;
- }
- return conn->status;
+ if (!conn)
+ {
+ fprintf(stderr, "PQstatus() -- pointer to PGconn is null\n");
+ return CONNECTION_BAD;
+ }
+ return conn->status;
}
-char*
-PQerrorMessage(PGconn* conn)
+char *
+PQerrorMessage(PGconn * conn)
{
- if (!conn) {
- fprintf(stderr,"PQerrorMessage() -- pointer to PGconn is null\n");
- return (char *)NULL;
- }
- return conn->errorMessage;
+ if (!conn)
+ {
+ fprintf(stderr, "PQerrorMessage() -- pointer to PGconn is null\n");
+ return (char *) NULL;
+ }
+ return conn->errorMessage;
}
void
-PQtrace(PGconn *conn, FILE* debug_port)
+PQtrace(PGconn * conn, FILE * debug_port)
{
- if (conn == NULL ||
- conn->status == CONNECTION_BAD) {
- return;
- }
- PQuntrace(conn);
- conn->Pfdebug = debug_port;
+ if (conn == NULL ||
+ conn->status == CONNECTION_BAD)
+ {
+ return;
+ }
+ PQuntrace(conn);
+ conn->Pfdebug = debug_port;
}
-void
-PQuntrace(PGconn *conn)
+void
+PQuntrace(PGconn * conn)
{
- if (conn == NULL ||
- conn->status == CONNECTION_BAD) {
- return;
- }
- if (conn->Pfdebug) {
- fflush(conn->Pfdebug);
- fclose(conn->Pfdebug);
- conn->Pfdebug = NULL;
- }
+ if (conn == NULL ||
+ conn->status == CONNECTION_BAD)
+ {
+ return;
+ }
+ if (conn->Pfdebug)
+ {
+ fflush(conn->Pfdebug);
+ fclose(conn->Pfdebug);
+ conn->Pfdebug = NULL;
+ }
}
diff --git a/src/interfaces/libpq/fe-connect.h b/src/interfaces/libpq/fe-connect.h
index ffa746473d3..5bd38084488 100644
--- a/src/interfaces/libpq/fe-connect.h
+++ b/src/interfaces/libpq/fe-connect.h
@@ -2,28 +2,28 @@
*
* fe-connect.h
*
- * Definitions related to setting up a connection to the backend
+ * Definitions related to setting up a connection to the backend
*
* Copyright (c) 1994, Regents of the University of California
*
- * $Id: fe-connect.h,v 1.1 1997/03/16 19:06:04 scrappy Exp $
+ * $Id: fe-connect.h,v 1.2 1997/09/07 05:03:26 momjian Exp $
*
*-------------------------------------------------------------------------
*/
#ifndef FE_CONNECT_H
-#define FE_CONNECT_H
+#define FE_CONNECT_H
/*----------------------------------------------------------------
* Common routines and definitions
*----------------------------------------------------------------
*/
-extern int packetSend(Port *port, PacketBuf *buf, PacketLen len, bool nonBlocking);
+extern int packetSend(Port * port, PacketBuf * buf, PacketLen len, bool nonBlocking);
-#endif /* FE_CONNECT_H */
+#endif /* FE_CONNECT_H */
#ifndef FE_CONNECT_H
#define FE_CONNECT_H
-int packetSend(Port *port, PacketBuf *buf, PacketLen len, bool nonBlocking);
+int packetSend(Port * port, PacketBuf * buf, PacketLen len, bool nonBlocking);
#endif
diff --git a/src/interfaces/libpq/fe-exec.c b/src/interfaces/libpq/fe-exec.c
index 771e8c66e2b..be8913e7bf7 100644
--- a/src/interfaces/libpq/fe-exec.c
+++ b/src/interfaces/libpq/fe-exec.c
@@ -1,13 +1,13 @@
/*-------------------------------------------------------------------------
*
* fe-exec.c--
- * functions related to sending a query down to the backend
+ * functions related to sending a query down to the backend
*
* Copyright (c) 1994, Regents of the University of California
*
*
* IDENTIFICATION
- * $Header: /cvsroot/pgsql/src/interfaces/libpq/fe-exec.c,v 1.35 1997/09/05 00:09:47 momjian Exp $
+ * $Header: /cvsroot/pgsql/src/interfaces/libpq/fe-exec.c,v 1.36 1997/09/07 05:03:28 momjian Exp $
*
*-------------------------------------------------------------------------
*/
@@ -23,19 +23,22 @@
#include "libpq-fe.h"
#include <sys/ioctl.h>
#ifndef HAVE_TERMIOS_H
-# include <sys/termios.h>
+#include <sys/termios.h>
#else
-# include <termios.h>
+#include <termios.h>
#endif
#ifdef TIOCGWINSZ
-struct winsize screen_size;
+struct winsize screen_size;
+
#else
-struct winsize {
- int ws_row;
- int ws_col;
-} screen_size;
+struct winsize
+{
+ int ws_row;
+ int ws_col;
+} screen_size;
+
#endif
/* the rows array in a PGresGroup has to grow to accommodate the rows */
@@ -43,325 +46,358 @@ struct winsize {
#define TUPARR_GROW_BY 100
/* keep this in same order as ExecStatusType in pgtclCmds.h */
-const char* pgresStatus[] = {
- "PGRES_EMPTY_QUERY",
- "PGRES_COMMAND_OK",
- "PGRES_TUPLES_OK",
- "PGRES_BAD_RESPONSE",
- "PGRES_NONFATAL_ERROR",
- "PGRES_FATAL_ERROR"
+const char *pgresStatus[] = {
+ "PGRES_EMPTY_QUERY",
+ "PGRES_COMMAND_OK",
+ "PGRES_TUPLES_OK",
+ "PGRES_BAD_RESPONSE",
+ "PGRES_NONFATAL_ERROR",
+ "PGRES_FATAL_ERROR"
};
-static PGresult* makePGresult(PGconn *conn, char *pname);
-static void addTuple(PGresult *res, PGresAttValue *tup);
-static PGresAttValue* getTuple(PGconn *conn, PGresult *res, int binary);
-static PGresult* makeEmptyPGresult(PGconn *conn, ExecStatusType status);
-static void fill(int length, int max, char filler, FILE *fp);
-static char* do_header(FILE *fout, PQprintOpt *po, const int nFields,
- int fieldMax[], char *fieldNames[], unsigned char fieldNotNum[],
- const int fs_len, PGresult *res);
+static PGresult *makePGresult(PGconn * conn, char *pname);
+static void addTuple(PGresult * res, PGresAttValue * tup);
+static PGresAttValue *getTuple(PGconn * conn, PGresult * res, int binary);
+static PGresult *makeEmptyPGresult(PGconn * conn, ExecStatusType status);
+static void fill(int length, int max, char filler, FILE * fp);
+static char *
+do_header(FILE * fout, PQprintOpt * po, const int nFields,
+ int fieldMax[], char *fieldNames[], unsigned char fieldNotNum[],
+ const int fs_len, PGresult * res);
/*
* PQclear -
- * free's the memory associated with a PGresult
+ * free's the memory associated with a PGresult
*
*/
void
-PQclear(PGresult* res)
+PQclear(PGresult * res)
{
- int i,j;
-
- if (!res)
- return;
-
- /* free all the rows */
- for (i=0;i<res->ntups;i++) {
- for (j=0;j<res->numAttributes;j++) {
- if (res->tuples[i][j].value)
- free(res->tuples[i][j].value);
- }
- if (res->tuples[i]) free(res->tuples[i]);
- }
- if (res->tuples) free(res->tuples);
-
- /* free all the attributes */
- for (i=0;i<res->numAttributes;i++) {
- if (res->attDescs[i].name)
- free(res->attDescs[i].name);
- }
- if (res->attDescs) free(res->attDescs);
-
- /* free the structure itself */
- free(res);
+ int i,
+ j;
+
+ if (!res)
+ return;
+
+ /* free all the rows */
+ for (i = 0; i < res->ntups; i++)
+ {
+ for (j = 0; j < res->numAttributes; j++)
+ {
+ if (res->tuples[i][j].value)
+ free(res->tuples[i][j].value);
+ }
+ if (res->tuples[i])
+ free(res->tuples[i]);
+ }
+ if (res->tuples)
+ free(res->tuples);
+
+ /* free all the attributes */
+ for (i = 0; i < res->numAttributes; i++)
+ {
+ if (res->attDescs[i].name)
+ free(res->attDescs[i].name);
+ }
+ if (res->attDescs)
+ free(res->attDescs);
+
+ /* free the structure itself */
+ free(res);
}
/*
* PGresult -
- * returns a newly allocated, initialized PGresult
+ * returns a newly allocated, initialized PGresult
*
*/
-static PGresult*
-makeEmptyPGresult(PGconn *conn, ExecStatusType status)
+static PGresult *
+makeEmptyPGresult(PGconn * conn, ExecStatusType status)
{
- PGresult *result;
-
- result = (PGresult*)malloc(sizeof(PGresult));
-
- result->conn = conn;
- result->ntups = 0;
- result->numAttributes = 0;
- result->attDescs = NULL;
- result->tuples = NULL;
- result->tupArrSize = 0;
- result->resultStatus = status;
- result->cmdStatus[0] = '\0';
- result->binary = 0;
- return result;
+ PGresult *result;
+
+ result = (PGresult *) malloc(sizeof(PGresult));
+
+ result->conn = conn;
+ result->ntups = 0;
+ result->numAttributes = 0;
+ result->attDescs = NULL;
+ result->tuples = NULL;
+ result->tupArrSize = 0;
+ result->resultStatus = status;
+ result->cmdStatus[0] = '\0';
+ result->binary = 0;
+ return result;
}
/*
* getTuple -
- * get the next row from the stream
+ * get the next row from the stream
*
- * the CALLER is responsible from freeing the PGresAttValue returned
+ * the CALLER is responsible from freeing the PGresAttValue returned
*/
-static PGresAttValue*
-getTuple(PGconn *conn, PGresult* result, int binary)
+static PGresAttValue *
+getTuple(PGconn * conn, PGresult * result, int binary)
{
- char bitmap[MAX_FIELDS]; /* the backend sends us a bitmap of */
- /* which attributes are null */
- int bitmap_index = 0;
- int i;
- int nbytes; /* the number of bytes in bitmap */
- char bmap; /* One byte of the bitmap */
- int bitcnt = 0; /* number of bits examined in current byte */
- int vlen; /* length of the current field value */
- FILE *pfin = conn->Pfin;
- FILE *pfdebug = conn->Pfdebug;
-
- PGresAttValue* tup;
-
- int nfields = result->numAttributes;
-
- result->binary = binary;
-
- tup = (PGresAttValue*) malloc(nfields * sizeof(PGresAttValue));
-
- nbytes = nfields / BYTELEN;
- if ( (nfields % BYTELEN) > 0)
- nbytes++;
-
- if (pqGetnchar(bitmap, nbytes, pfin, pfdebug) == 1){
- sprintf(conn->errorMessage,
- "Error reading null-values bitmap from row data stream\n");
- return NULL;
- }
-
- bmap = bitmap[bitmap_index];
-
- for (i=0;i<nfields;i++) {
- if (!(bmap & 0200)) {
- /* if the field value is absent, make it '\0' */
- tup[i].value = (char*)malloc(1);
- tup[i].value[0] = '\0';
- tup[i].len = NULL_LEN;
- }
- else {
- /* get the value length (the first four bytes are for length) */
- pqGetInt(&vlen, VARHDRSZ, pfin, pfdebug);
- if (binary == 0) {
- vlen = vlen - VARHDRSZ;
- }
- if (vlen < 0)
- vlen = 0;
- tup[i].len = vlen;
- tup[i].value = (char*) malloc(vlen + 1);
- /* read in the value; */
- if (vlen > 0)
- pqGetnchar((char*)(tup[i].value), vlen, pfin, pfdebug);
- tup[i].value[vlen] = '\0';
- }
- /* get the appropriate bitmap */
- bitcnt++;
- if (bitcnt == BYTELEN) {
- bitmap_index++;
- bmap = bitmap[bitmap_index];
- bitcnt = 0;
- } else
- bmap <<= 1;
- }
-
- return tup;
+ char bitmap[MAX_FIELDS]; /* the backend sends us a bitmap
+ * of */
+
+ /* which attributes are null */
+ int bitmap_index = 0;
+ int i;
+ int nbytes; /* the number of bytes in bitmap */
+ char bmap; /* One byte of the bitmap */
+ int bitcnt = 0; /* number of bits examined in current byte */
+ int vlen; /* length of the current field value */
+ FILE *pfin = conn->Pfin;
+ FILE *pfdebug = conn->Pfdebug;
+
+ PGresAttValue *tup;
+
+ int nfields = result->numAttributes;
+
+ result->binary = binary;
+
+ tup = (PGresAttValue *) malloc(nfields * sizeof(PGresAttValue));
+
+ nbytes = nfields / BYTELEN;
+ if ((nfields % BYTELEN) > 0)
+ nbytes++;
+
+ if (pqGetnchar(bitmap, nbytes, pfin, pfdebug) == 1)
+ {
+ sprintf(conn->errorMessage,
+ "Error reading null-values bitmap from row data stream\n");
+ return NULL;
+ }
+
+ bmap = bitmap[bitmap_index];
+
+ for (i = 0; i < nfields; i++)
+ {
+ if (!(bmap & 0200))
+ {
+ /* if the field value is absent, make it '\0' */
+ tup[i].value = (char *) malloc(1);
+ tup[i].value[0] = '\0';
+ tup[i].len = NULL_LEN;
+ }
+ else
+ {
+ /* get the value length (the first four bytes are for length) */
+ pqGetInt(&vlen, VARHDRSZ, pfin, pfdebug);
+ if (binary == 0)
+ {
+ vlen = vlen - VARHDRSZ;
+ }
+ if (vlen < 0)
+ vlen = 0;
+ tup[i].len = vlen;
+ tup[i].value = (char *) malloc(vlen + 1);
+ /* read in the value; */
+ if (vlen > 0)
+ pqGetnchar((char *) (tup[i].value), vlen, pfin, pfdebug);
+ tup[i].value[vlen] = '\0';
+ }
+ /* get the appropriate bitmap */
+ bitcnt++;
+ if (bitcnt == BYTELEN)
+ {
+ bitmap_index++;
+ bmap = bitmap[bitmap_index];
+ bitcnt = 0;
+ }
+ else
+ bmap <<= 1;
+ }
+
+ return tup;
}
/*
* addTuple
- * add a row to the PGresult structure, growing it if necessary
- * to accommodate
+ * add a row to the PGresult structure, growing it if necessary
+ * to accommodate
*
*/
-static void
-addTuple(PGresult* res, PGresAttValue* tup)
+static void
+addTuple(PGresult * res, PGresAttValue * tup)
{
- if (res->ntups == res->tupArrSize) {
- /* grow the array */
- res->tupArrSize += TUPARR_GROW_BY;
-
- if (res->ntups == 0)
- res->tuples = (PGresAttValue**)
- malloc(res->tupArrSize * sizeof(PGresAttValue*));
- else
- /* we can use realloc because shallow copying of the structure is okay */
- res->tuples = (PGresAttValue**)
- realloc(res->tuples, res->tupArrSize * sizeof(PGresAttValue*));
- }
-
- res->tuples[res->ntups] = tup;
- res->ntups++;
+ if (res->ntups == res->tupArrSize)
+ {
+ /* grow the array */
+ res->tupArrSize += TUPARR_GROW_BY;
+
+ if (res->ntups == 0)
+ res->tuples = (PGresAttValue **)
+ malloc(res->tupArrSize * sizeof(PGresAttValue *));
+ else
+
+ /*
+ * we can use realloc because shallow copying of the structure
+ * is okay
+ */
+ res->tuples = (PGresAttValue **)
+ realloc(res->tuples, res->tupArrSize * sizeof(PGresAttValue *));
+ }
+
+ res->tuples[res->ntups] = tup;
+ res->ntups++;
}
/*
* PGresult
- * fill out the PGresult structure with result rows from the backend
- * this is called after query has been successfully run and we have
- * a portal name
+ * fill out the PGresult structure with result rows from the backend
+ * this is called after query has been successfully run and we have
+ * a portal name
*
- * ASSUMPTION: we assume only *1* row group is returned from the backend
+ * ASSUMPTION: we assume only *1* row group is returned from the backend
*
- * the CALLER is reponsible for free'ing the new PGresult allocated here
+ * the CALLER is reponsible for free'ing the new PGresult allocated here
*
*/
-static PGresult*
-makePGresult(PGconn* conn, char* pname)
+static PGresult *
+makePGresult(PGconn * conn, char *pname)
{
- PGresult* result;
- int id;
- int nfields;
- int i;
- int done = 0;
-
- PGresAttValue* newTup;
-
- FILE* pfin = conn->Pfin;
- FILE* pfdebug = conn->Pfdebug;
-
- result = makeEmptyPGresult(conn, PGRES_TUPLES_OK);
-
- /* makePGresult() should only be called when the */
- /* id of the stream is 'T' to start with */
-
- /* the next two bytes are the number of fields */
- if (pqGetInt(&nfields, 2, pfin, pfdebug) == 1) {
- sprintf(conn->errorMessage,
- "could not get the number of fields from the 'T' message\n");
- goto makePGresult_badResponse_return;
- }
- else
- result->numAttributes = nfields;
-
- /* allocate space for the attribute descriptors */
- if (nfields > 0) {
- result->attDescs = (PGresAttDesc*) malloc(nfields * sizeof(PGresAttDesc));
- }
-
- /* get type info */
- for (i=0;i<nfields;i++) {
- char typName[MAX_MESSAGE_LEN];
- int adtid;
- int adtsize;
-
- if ( pqGets(typName, MAX_MESSAGE_LEN, pfin, pfdebug) ||
- pqGetInt(&adtid, 4, pfin, pfdebug) ||
- pqGetInt(&adtsize, 2, pfin, pfdebug)) {
- sprintf(conn->errorMessage,
- "error reading type information from the 'T' message\n");
- goto makePGresult_badResponse_return;
- }
- result->attDescs[i].name = malloc(strlen(typName)+1);
- strcpy(result->attDescs[i].name,typName);
- result->attDescs[i].adtid = adtid;
- result->attDescs[i].adtsize = adtsize; /* casting from int to int2 here */
- }
-
- id = pqGetc(pfin,pfdebug);
-
- /* process the data stream until we're finished */
- while(!done) {
- switch (id) {
- case 'T': /* a new row group */
- sprintf(conn->errorMessage,
- "makePGresult() -- "
- "is not equipped to handle multiple row groups.\n");
- goto makePGresult_badResponse_return;
- case 'B': /* a row in binary format */
- case 'D': /* a row in ASCII format */
- newTup = getTuple(conn, result, (id == 'B'));
- if (newTup == NULL)
- goto makePGresult_badResponse_return;
- addTuple(result,newTup);
- break;
- case 'C': /* end of portal row stream */
- {
- char command[MAX_MESSAGE_LEN];
- pqGets(command,MAX_MESSAGE_LEN, pfin, pfdebug); /* read command tag */
- done = 1;
- }
- break;
- case 'E': /* errors */
- if (pqGets(conn->errorMessage, ERROR_MSG_LENGTH, pfin, pfdebug) == 1) {
- sprintf(conn->errorMessage,
- "Error return detected from backend, "
- "but error message cannot be read");
- }
- result->resultStatus = PGRES_FATAL_ERROR;
- return result;
- break;
- case 'N': /* notices from the backend */
- if (pqGets(conn->errorMessage, ERROR_MSG_LENGTH, pfin, pfdebug) == 1) {
- sprintf(conn->errorMessage,
- "Notice return detected from backend, "
- "but error message cannot be read");
- } else
- /* XXXX send Notices to stderr for now */
- fprintf(stderr, "%s\n", conn->errorMessage);
- break;
- default: /* uh-oh
- this should never happen but frequently does when the
- backend dumps core */
- sprintf(conn->errorMessage,
- "FATAL: unrecognized data from the backend. "
- "It probably dumped core.\n");
- fprintf(stderr, conn->errorMessage);
- result->resultStatus = PGRES_FATAL_ERROR;
- return result;
- break;
- }
- if (!done)
- id = getc(pfin);
- } /* while (1) */
-
- result->resultStatus = PGRES_TUPLES_OK;
- return result;
+ PGresult *result;
+ int id;
+ int nfields;
+ int i;
+ int done = 0;
+
+ PGresAttValue *newTup;
+
+ FILE *pfin = conn->Pfin;
+ FILE *pfdebug = conn->Pfdebug;
+
+ result = makeEmptyPGresult(conn, PGRES_TUPLES_OK);
+
+ /* makePGresult() should only be called when the */
+ /* id of the stream is 'T' to start with */
+
+ /* the next two bytes are the number of fields */
+ if (pqGetInt(&nfields, 2, pfin, pfdebug) == 1)
+ {
+ sprintf(conn->errorMessage,
+ "could not get the number of fields from the 'T' message\n");
+ goto makePGresult_badResponse_return;
+ }
+ else
+ result->numAttributes = nfields;
+
+ /* allocate space for the attribute descriptors */
+ if (nfields > 0)
+ {
+ result->attDescs = (PGresAttDesc *) malloc(nfields * sizeof(PGresAttDesc));
+ }
+
+ /* get type info */
+ for (i = 0; i < nfields; i++)
+ {
+ char typName[MAX_MESSAGE_LEN];
+ int adtid;
+ int adtsize;
+
+ if (pqGets(typName, MAX_MESSAGE_LEN, pfin, pfdebug) ||
+ pqGetInt(&adtid, 4, pfin, pfdebug) ||
+ pqGetInt(&adtsize, 2, pfin, pfdebug))
+ {
+ sprintf(conn->errorMessage,
+ "error reading type information from the 'T' message\n");
+ goto makePGresult_badResponse_return;
+ }
+ result->attDescs[i].name = malloc(strlen(typName) + 1);
+ strcpy(result->attDescs[i].name, typName);
+ result->attDescs[i].adtid = adtid;
+ result->attDescs[i].adtsize = adtsize; /* casting from int to
+ * int2 here */
+ }
+
+ id = pqGetc(pfin, pfdebug);
+
+ /* process the data stream until we're finished */
+ while (!done)
+ {
+ switch (id)
+ {
+ case 'T': /* a new row group */
+ sprintf(conn->errorMessage,
+ "makePGresult() -- "
+ "is not equipped to handle multiple row groups.\n");
+ goto makePGresult_badResponse_return;
+ case 'B': /* a row in binary format */
+ case 'D': /* a row in ASCII format */
+ newTup = getTuple(conn, result, (id == 'B'));
+ if (newTup == NULL)
+ goto makePGresult_badResponse_return;
+ addTuple(result, newTup);
+ break;
+ case 'C': /* end of portal row stream */
+ {
+ char command[MAX_MESSAGE_LEN];
+
+ pqGets(command, MAX_MESSAGE_LEN, pfin, pfdebug); /* read command tag */
+ done = 1;
+ }
+ break;
+ case 'E': /* errors */
+ if (pqGets(conn->errorMessage, ERROR_MSG_LENGTH, pfin, pfdebug) == 1)
+ {
+ sprintf(conn->errorMessage,
+ "Error return detected from backend, "
+ "but error message cannot be read");
+ }
+ result->resultStatus = PGRES_FATAL_ERROR;
+ return result;
+ break;
+ case 'N': /* notices from the backend */
+ if (pqGets(conn->errorMessage, ERROR_MSG_LENGTH, pfin, pfdebug) == 1)
+ {
+ sprintf(conn->errorMessage,
+ "Notice return detected from backend, "
+ "but error message cannot be read");
+ }
+ else
+ /* XXXX send Notices to stderr for now */
+ fprintf(stderr, "%s\n", conn->errorMessage);
+ break;
+ default: /* uh-oh this should never happen but
+ * frequently does when the backend dumps
+ * core */
+ sprintf(conn->errorMessage,
+ "FATAL: unrecognized data from the backend. "
+ "It probably dumped core.\n");
+ fprintf(stderr, conn->errorMessage);
+ result->resultStatus = PGRES_FATAL_ERROR;
+ return result;
+ break;
+ }
+ if (!done)
+ id = getc(pfin);
+ } /* while (1) */
+
+ result->resultStatus = PGRES_TUPLES_OK;
+ return result;
makePGresult_badResponse_return:
- result->resultStatus = PGRES_BAD_RESPONSE;
- return result;
+ result->resultStatus = PGRES_BAD_RESPONSE;
+ return result;
}
/*
- * Assuming that we just sent a query to the backend, read the backend's
+ * Assuming that we just sent a query to the backend, read the backend's
* response from stream <pfin> and respond accordingly.
*
* If <pfdebug> is non-null, write to that stream whatever we receive
* (it's a debugging trace).
- *
+ *
* Return as <result> a pointer to a proper final PGresult structure,
* newly allocated, for the query based on the response we get. If the
* response we get indicates that the query didn't execute, return a
@@ -370,450 +406,522 @@ makePGresult_badResponse_return:
*/
static void
-process_response_from_backend(FILE *pfin, FILE *pfout, FILE *pfdebug,
- PGconn *conn,
- PGresult **result_p, char * const reason) {
-
- int id;
- /* The protocol character received from the backend. The protocol
- character is the first character in the backend's response to our
- query. It defines the nature of the response.
- */
- PGnotify *newNotify;
- bool done;
- /* We're all done with the query and ready to return the result. */
- int emptiesSent;
- /* Number of empty queries we have sent in order to flush out multiple
- responses, less the number of corresponding responses we have
- received.
- */
- int errors;
- /* If an error is received, we must still drain out the empty
- queries sent. So we need another flag.
- */
- char cmdStatus[MAX_MESSAGE_LEN];
- char pname[MAX_MESSAGE_LEN]; /* portal name */
-
- /* loop because multiple messages, especially NOTICES,
- can come back from the backend. NOTICES are output directly to stderr
- */
-
- emptiesSent = 0; /* No empty queries sent yet */
- errors = 0; /* No errors received yet */
- pname[0] = '\0';
-
- done = false; /* initial value */
- while (!done) {
- /* read the result id */
- id = pqGetc(pfin, pfdebug);
- if (id == EOF) {
- /* hmm, no response from the backend-end, that's bad */
- (void) sprintf(reason,
- "PQexec() -- Request was sent to backend, but backend "
- "closed the channel before "
- "responding. This probably means the backend "
- "terminated abnormally before or while processing "
- "the request.\n");
- conn->status = CONNECTION_BAD; /* No more connection to backend */
- *result_p = (PGresult*)NULL;
- done = true;
- } else {
- switch (id) {
- case 'A':
- newNotify = (PGnotify*)malloc(sizeof(PGnotify));
- pqGetInt(&(newNotify->be_pid), 4, pfin, pfdebug);
- pqGets(newNotify->relname, NAMEDATALEN, pfin, pfdebug);
- DLAddTail(conn->notifyList, DLNewElem(newNotify));
- /* async messages are piggy'ed back on other messages,
- so we stay in the while loop for other messages */
- break;
- case 'C': /* portal query command, no rows returned */
- if (pqGets(cmdStatus, MAX_MESSAGE_LEN, pfin, pfdebug) == 1) {
- sprintf(reason,
- "PQexec() -- query command completed, "
- "but return message from backend cannot be read.");
- *result_p = (PGresult*)NULL;
- done = true;
- } else {
- /*
- * since backend may produce more than one result for some
- * commands need to poll until clear
- * send an empty query down, and keep reading out of the pipe
- * until an 'I' is received.
- */
- pqPuts("Q ", pfout, pfdebug); /* send an empty query */
- /*
- * Increment a flag and process messages in the usual way because
- * there may be async notifications pending. DZ - 31-8-1996
- */
- emptiesSent++;
- }
- break;
- case 'E': /* error return */
- if (pqGets(conn->errorMessage, ERROR_MSG_LENGTH, pfin, pfdebug) == 1) {
- (void) sprintf(reason,
- "PQexec() -- error return detected from backend, "
- "but attempt to read the error message failed.");
- }
- *result_p = (PGresult*)NULL;
- errors++;
- if (emptiesSent == 0) {
- done = true;
- }
- break;
- case 'I': { /* empty query */
- /* read and throw away the closing '\0' */
- int c;
- if ((c = pqGetc(pfin,pfdebug)) != '\0') {
- fprintf(stderr,"error!, unexpected character %c following 'I'\n", c);
- }
- if (emptiesSent) {
- if (--emptiesSent == 0) { /* is this the last one? */
- /*
- * If this is the result of a portal query command set the
- * command status and message accordingly. DZ - 31-8-1996
- */
- if (!errors) {
- *result_p = makeEmptyPGresult(conn,PGRES_COMMAND_OK);
- strncpy((*result_p)->cmdStatus, cmdStatus, CMDSTATUS_LEN-1);
- } else {
- *result_p = (PGresult*)NULL;
- }
- done = true;
- }
- }
- else {
- if (!errors) {
- *result_p = makeEmptyPGresult(conn, PGRES_EMPTY_QUERY);
- } else {
- *result_p = (PGresult*)NULL;
- }
- done = true;
- }
- }
- break;
- case 'N': /* notices from the backend */
- if (pqGets(reason, ERROR_MSG_LENGTH, pfin, pfdebug) == 1) {
- sprintf(reason,
- "PQexec() -- Notice detected from backend, "
- "but attempt to read the notice failed.");
- *result_p = (PGresult*)NULL;
- done = true;
- } else
- /* Should we really be doing this? These notices are not important
- enough for us to presume to put them on stderr. Maybe the caller
- should decide whether to put them on stderr or not. BJH 96.12.27
- */
- fprintf(stderr,"%s", reason);
- break;
- case 'P': /* synchronous (normal) portal */
- pqGets(pname, MAX_MESSAGE_LEN, pfin, pfdebug); /* read in portal name*/
- break;
- case 'T': /* actual row results: */
- *result_p = makePGresult(conn, pname);
- done = true;
- break;
- case 'D': /* copy command began successfully */
- *result_p = makeEmptyPGresult(conn, PGRES_COPY_IN);
- done = true;
- break;
- case 'B': /* copy command began successfully */
- *result_p = makeEmptyPGresult(conn, PGRES_COPY_OUT);
- done = true;
- break;
- default:
- sprintf(reason,
- "unknown protocol character '%c' read from backend. "
- "(The protocol character is the first character the "
- "backend sends in response to a query it receives).\n",
- id);
- *result_p = (PGresult*)NULL;
- done = true;
- } /* switch on protocol character */
- } /* if character was received */
- } /* while not done */
+process_response_from_backend(FILE * pfin, FILE * pfout, FILE * pfdebug,
+ PGconn * conn,
+ PGresult ** result_p, char *const reason)
+{
+
+ int id;
+
+ /*
+ * The protocol character received from the backend. The protocol
+ * character is the first character in the backend's response to our
+ * query. It defines the nature of the response.
+ */
+ PGnotify *newNotify;
+ bool done;
+
+ /* We're all done with the query and ready to return the result. */
+ int emptiesSent;
+
+ /*
+ * Number of empty queries we have sent in order to flush out multiple
+ * responses, less the number of corresponding responses we have
+ * received.
+ */
+ int errors;
+
+ /*
+ * If an error is received, we must still drain out the empty queries
+ * sent. So we need another flag.
+ */
+ char cmdStatus[MAX_MESSAGE_LEN];
+ char pname[MAX_MESSAGE_LEN]; /* portal name */
+
+ /*
+ * loop because multiple messages, especially NOTICES, can come back
+ * from the backend. NOTICES are output directly to stderr
+ */
+
+ emptiesSent = 0; /* No empty queries sent yet */
+ errors = 0; /* No errors received yet */
+ pname[0] = '\0';
+
+ done = false; /* initial value */
+ while (!done)
+ {
+ /* read the result id */
+ id = pqGetc(pfin, pfdebug);
+ if (id == EOF)
+ {
+ /* hmm, no response from the backend-end, that's bad */
+ (void) sprintf(reason,
+ "PQexec() -- Request was sent to backend, but backend "
+ "closed the channel before "
+ "responding. This probably means the backend "
+ "terminated abnormally before or while processing "
+ "the request.\n");
+ conn->status = CONNECTION_BAD; /* No more connection to
+ * backend */
+ *result_p = (PGresult *) NULL;
+ done = true;
+ }
+ else
+ {
+ switch (id)
+ {
+ case 'A':
+ newNotify = (PGnotify *) malloc(sizeof(PGnotify));
+ pqGetInt(&(newNotify->be_pid), 4, pfin, pfdebug);
+ pqGets(newNotify->relname, NAMEDATALEN, pfin, pfdebug);
+ DLAddTail(conn->notifyList, DLNewElem(newNotify));
+
+ /*
+ * async messages are piggy'ed back on other messages, so
+ * we stay in the while loop for other messages
+ */
+ break;
+ case 'C': /* portal query command, no rows returned */
+ if (pqGets(cmdStatus, MAX_MESSAGE_LEN, pfin, pfdebug) == 1)
+ {
+ sprintf(reason,
+ "PQexec() -- query command completed, "
+ "but return message from backend cannot be read.");
+ *result_p = (PGresult *) NULL;
+ done = true;
+ }
+ else
+ {
+
+ /*
+ * since backend may produce more than one result for
+ * some commands need to poll until clear send an
+ * empty query down, and keep reading out of the pipe
+ * until an 'I' is received.
+ */
+ pqPuts("Q ", pfout, pfdebug); /* send an empty query */
+
+ /*
+ * Increment a flag and process messages in the usual
+ * way because there may be async notifications
+ * pending. DZ - 31-8-1996
+ */
+ emptiesSent++;
+ }
+ break;
+ case 'E': /* error return */
+ if (pqGets(conn->errorMessage, ERROR_MSG_LENGTH, pfin, pfdebug) == 1)
+ {
+ (void) sprintf(reason,
+ "PQexec() -- error return detected from backend, "
+ "but attempt to read the error message failed.");
+ }
+ *result_p = (PGresult *) NULL;
+ errors++;
+ if (emptiesSent == 0)
+ {
+ done = true;
+ }
+ break;
+ case 'I':
+ { /* empty query */
+ /* read and throw away the closing '\0' */
+ int c;
+
+ if ((c = pqGetc(pfin, pfdebug)) != '\0')
+ {
+ fprintf(stderr, "error!, unexpected character %c following 'I'\n", c);
+ }
+ if (emptiesSent)
+ {
+ if (--emptiesSent == 0)
+ { /* is this the last one? */
+
+ /*
+ * If this is the result of a portal query
+ * command set the command status and message
+ * accordingly. DZ - 31-8-1996
+ */
+ if (!errors)
+ {
+ *result_p = makeEmptyPGresult(conn, PGRES_COMMAND_OK);
+ strncpy((*result_p)->cmdStatus, cmdStatus, CMDSTATUS_LEN - 1);
+ }
+ else
+ {
+ *result_p = (PGresult *) NULL;
+ }
+ done = true;
+ }
+ }
+ else
+ {
+ if (!errors)
+ {
+ *result_p = makeEmptyPGresult(conn, PGRES_EMPTY_QUERY);
+ }
+ else
+ {
+ *result_p = (PGresult *) NULL;
+ }
+ done = true;
+ }
+ }
+ break;
+ case 'N': /* notices from the backend */
+ if (pqGets(reason, ERROR_MSG_LENGTH, pfin, pfdebug) == 1)
+ {
+ sprintf(reason,
+ "PQexec() -- Notice detected from backend, "
+ "but attempt to read the notice failed.");
+ *result_p = (PGresult *) NULL;
+ done = true;
+ }
+ else
+
+ /*
+ * Should we really be doing this? These notices are
+ * not important enough for us to presume to put them
+ * on stderr. Maybe the caller should decide whether
+ * to put them on stderr or not. BJH 96.12.27
+ */
+ fprintf(stderr, "%s", reason);
+ break;
+ case 'P': /* synchronous (normal) portal */
+ pqGets(pname, MAX_MESSAGE_LEN, pfin, pfdebug); /* read in portal name */
+ break;
+ case 'T': /* actual row results: */
+ *result_p = makePGresult(conn, pname);
+ done = true;
+ break;
+ case 'D': /* copy command began successfully */
+ *result_p = makeEmptyPGresult(conn, PGRES_COPY_IN);
+ done = true;
+ break;
+ case 'B': /* copy command began successfully */
+ *result_p = makeEmptyPGresult(conn, PGRES_COPY_OUT);
+ done = true;
+ break;
+ default:
+ sprintf(reason,
+ "unknown protocol character '%c' read from backend. "
+ "(The protocol character is the first character the "
+ "backend sends in response to a query it receives).\n",
+ id);
+ *result_p = (PGresult *) NULL;
+ done = true;
+ } /* switch on protocol character */
+ } /* if character was received */
+ } /* while not done */
}
/*
* PQexec
- * send a query to the backend and package up the result in a Pgresult
+ * send a query to the backend and package up the result in a Pgresult
*
- * if the query failed, return NULL, conn->errorMessage is set to
+ * if the query failed, return NULL, conn->errorMessage is set to
* a relevant message
- * if query is successful, a new PGresult is returned
+ * if query is successful, a new PGresult is returned
* the use is responsible for freeing that structure when done with it
*
*/
-PGresult*
-PQexec(PGconn* conn, const char* query)
+PGresult *
+PQexec(PGconn * conn, const char *query)
{
- PGresult *result;
- char buffer[MAX_MESSAGE_LEN];
-
- if (!conn) return NULL;
- if (!query) {
- sprintf(conn->errorMessage, "PQexec() -- query pointer is null.");
- return NULL;
- }
-
- /*clear the error string */
- conn->errorMessage[0] = '\0';
-
- /* check to see if the query string is too long */
- if (strlen(query) > MAX_MESSAGE_LEN) {
- sprintf(conn->errorMessage, "PQexec() -- query is too long. "
- "Maximum length is %d\n", MAX_MESSAGE_LEN -2 );
- return NULL;
- }
-
- /* Don't try to send if we know there's no live connection. */
- if (conn->status != CONNECTION_OK) {
- sprintf(conn->errorMessage, "PQexec() -- There is no connection "
- "to the backend.\n");
- return NULL;
- }
-
- /* the frontend-backend protocol uses 'Q' to designate queries */
- sprintf(buffer,"Q%s",query);
-
- /* send the query to the backend; */
- if (pqPuts(buffer, conn->Pfout, conn->Pfdebug) == 1) {
- (void) sprintf(conn->errorMessage,
- "PQexec() -- while sending query: %s\n"
- "-- fprintf to Pfout failed: errno=%d\n%s\n",
- query, errno, strerror(errno));
- return NULL;
- }
-
- process_response_from_backend(conn->Pfin, conn->Pfout, conn->Pfdebug, conn,
- &result, conn->errorMessage);
- return(result);
+ PGresult *result;
+ char buffer[MAX_MESSAGE_LEN];
+
+ if (!conn)
+ return NULL;
+ if (!query)
+ {
+ sprintf(conn->errorMessage, "PQexec() -- query pointer is null.");
+ return NULL;
+ }
+
+ /* clear the error string */
+ conn->errorMessage[0] = '\0';
+
+ /* check to see if the query string is too long */
+ if (strlen(query) > MAX_MESSAGE_LEN)
+ {
+ sprintf(conn->errorMessage, "PQexec() -- query is too long. "
+ "Maximum length is %d\n", MAX_MESSAGE_LEN - 2);
+ return NULL;
+ }
+
+ /* Don't try to send if we know there's no live connection. */
+ if (conn->status != CONNECTION_OK)
+ {
+ sprintf(conn->errorMessage, "PQexec() -- There is no connection "
+ "to the backend.\n");
+ return NULL;
+ }
+
+ /* the frontend-backend protocol uses 'Q' to designate queries */
+ sprintf(buffer, "Q%s", query);
+
+ /* send the query to the backend; */
+ if (pqPuts(buffer, conn->Pfout, conn->Pfdebug) == 1)
+ {
+ (void) sprintf(conn->errorMessage,
+ "PQexec() -- while sending query: %s\n"
+ "-- fprintf to Pfout failed: errno=%d\n%s\n",
+ query, errno, strerror(errno));
+ return NULL;
+ }
+
+ process_response_from_backend(conn->Pfin, conn->Pfout, conn->Pfdebug, conn,
+ &result, conn->errorMessage);
+ return (result);
}
/*
* PQnotifies
- * returns a PGnotify* structure of the latest async notification
+ * returns a PGnotify* structure of the latest async notification
* that has not yet been handled
*
- * returns NULL, if there is currently
+ * returns NULL, if there is currently
* no unhandled async notification from the backend
*
* the CALLER is responsible for FREE'ing the structure returned
*/
-PGnotify*
-PQnotifies(PGconn *conn)
+PGnotify *
+PQnotifies(PGconn * conn)
{
- Dlelem *e;
-
- if (!conn) return NULL;
-
- if (conn->status != CONNECTION_OK)
- return NULL;
- /* RemHead returns NULL if list is empy */
- e = DLRemHead(conn->notifyList);
- if (e)
- return (PGnotify*)DLE_VAL(e);
- else
- return NULL;
+ Dlelem *e;
+
+ if (!conn)
+ return NULL;
+
+ if (conn->status != CONNECTION_OK)
+ return NULL;
+ /* RemHead returns NULL if list is empy */
+ e = DLRemHead(conn->notifyList);
+ if (e)
+ return (PGnotify *) DLE_VAL(e);
+ else
+ return NULL;
}
/*
* PQgetline - gets a newline-terminated string from the backend.
- *
+ *
* Chiefly here so that applications can use "COPY <rel> to stdout"
- * and read the output string. Returns a null-terminated string in s.
+ * and read the output string. Returns a null-terminated string in s.
*
* PQgetline reads up to maxlen-1 characters (like fgets(3)) but strips
* the terminating \n (like gets(3)).
*
* RETURNS:
- * EOF if it is detected or invalid arguments are given
- * 0 if EOL is reached (i.e., \n has been read)
- * (this is required for backward-compatibility -- this
- * routine used to always return EOF or 0, assuming that
- * the line ended within maxlen bytes.)
- * 1 in other cases
+ * EOF if it is detected or invalid arguments are given
+ * 0 if EOL is reached (i.e., \n has been read)
+ * (this is required for backward-compatibility -- this
+ * routine used to always return EOF or 0, assuming that
+ * the line ended within maxlen bytes.)
+ * 1 in other cases
*/
int
-PQgetline(PGconn *conn, char *s, int maxlen)
+PQgetline(PGconn * conn, char *s, int maxlen)
{
- int c = '\0';
-
- if (!conn) return EOF;
-
- if (!conn->Pfin || !s || maxlen <= 1)
- return(EOF);
-
- for (; maxlen > 1 &&
- (c = pqGetc(conn->Pfin, conn->Pfdebug)) != '\n' &&
- c != EOF;
- --maxlen) {
- *s++ = c;
- }
- *s = '\0';
-
- if (c == EOF) {
- return(EOF); /* error -- reached EOF before \n */
- } else if (c == '\n') {
- return(0); /* done with this line */
- }
- return(1); /* returning a full buffer */
+ int c = '\0';
+
+ if (!conn)
+ return EOF;
+
+ if (!conn->Pfin || !s || maxlen <= 1)
+ return (EOF);
+
+ for (; maxlen > 1 &&
+ (c = pqGetc(conn->Pfin, conn->Pfdebug)) != '\n' &&
+ c != EOF;
+ --maxlen)
+ {
+ *s++ = c;
+ }
+ *s = '\0';
+
+ if (c == EOF)
+ {
+ return (EOF); /* error -- reached EOF before \n */
+ }
+ else if (c == '\n')
+ {
+ return (0); /* done with this line */
+ }
+ return (1); /* returning a full buffer */
}
/*
* PQputline -- sends a string to the backend.
- *
+ *
* Chiefly here so that applications can use "COPY <rel> from stdin".
*
*/
void
-PQputline(PGconn *conn, const char *s)
+PQputline(PGconn * conn, const char *s)
{
- if (conn && (conn->Pfout)) {
- (void) fputs(s, conn->Pfout);
- fflush(conn->Pfout);
- }
+ if (conn && (conn->Pfout))
+ {
+ (void) fputs(s, conn->Pfout);
+ fflush(conn->Pfout);
+ }
}
/*
* PQendcopy
- * called while waiting for the backend to respond with success/failure
- * to a "copy".
+ * called while waiting for the backend to respond with success/failure
+ * to a "copy".
*
* RETURNS:
- * 0 on success
- * 1 on failure
+ * 0 on success
+ * 1 on failure
*/
int
-PQendcopy(PGconn *conn)
+PQendcopy(PGconn * conn)
{
- FILE *pfin, *pfdebug;
- bool valid = true;
-
- if (!conn) return (int)NULL;
-
- pfin = conn->Pfin;
- pfdebug = conn->Pfdebug;
-
- if ( pqGetc(pfin,pfdebug) == 'C')
- {
- char command[MAX_MESSAGE_LEN];
- pqGets(command,MAX_MESSAGE_LEN, pfin, pfdebug); /* read command tag */
- }
- else valid = false;
-
- if ( valid )
- return (0);
- else {
- sprintf(conn->errorMessage,
- "Error return detected from backend, "
- "but attempt to read the message failed.");
- fprintf(stderr,"resetting connection\n");
- PQreset(conn);
- return(1);
- }
+ FILE *pfin,
+ *pfdebug;
+ bool valid = true;
+
+ if (!conn)
+ return (int) NULL;
+
+ pfin = conn->Pfin;
+ pfdebug = conn->Pfdebug;
+
+ if (pqGetc(pfin, pfdebug) == 'C')
+ {
+ char command[MAX_MESSAGE_LEN];
+
+ pqGets(command, MAX_MESSAGE_LEN, pfin, pfdebug); /* read command tag */
+ }
+ else
+ valid = false;
+
+ if (valid)
+ return (0);
+ else
+ {
+ sprintf(conn->errorMessage,
+ "Error return detected from backend, "
+ "but attempt to read the message failed.");
+ fprintf(stderr, "resetting connection\n");
+ PQreset(conn);
+ return (1);
+ }
}
/* simply send out max-length number of filler characters to fp */
static void
-fill (int length, int max, char filler, FILE *fp)
+fill(int length, int max, char filler, FILE * fp)
{
- int count;
- char filltmp[2];
-
- filltmp[0] = filler;
- filltmp[1] = 0;
- count = max - length;
- while (count-- >= 0)
- {
- fprintf(fp, "%s", filltmp);
- }
- }
+ int count;
+ char filltmp[2];
+
+ filltmp[0] = filler;
+ filltmp[1] = 0;
+ count = max - length;
+ while (count-- >= 0)
+ {
+ fprintf(fp, "%s", filltmp);
+ }
+}
/*
* PQdisplayTuples()
* kept for backward compatibility
*/
void
-PQdisplayTuples(PGresult *res,
- FILE *fp, /* where to send the output */
- int fillAlign, /* pad the fields with spaces */
- const char *fieldSep, /* field separator */
- int printHeader, /* display headers? */
- int quiet
- )
+PQdisplayTuples(PGresult * res,
+ FILE * fp, /* where to send the output */
+ int fillAlign, /* pad the fields with spaces */
+ const char *fieldSep, /* field separator */
+ int printHeader,/* display headers? */
+ int quiet
+)
{
#define DEFAULT_FIELD_SEP " "
- int i, j;
- int nFields;
- int nTuples;
- int fLength[MAX_FIELDS];
-
- if (fieldSep == NULL)
- fieldSep = DEFAULT_FIELD_SEP;
-
- /* Get some useful info about the results */
- nFields = PQnfields(res);
- nTuples = PQntuples(res);
-
- if (fp == NULL)
- fp = stdout;
-
- /* Zero the initial field lengths */
- for (j=0 ; j < nFields; j++) {
- fLength[j] = strlen(PQfname(res,j));
- }
- /* Find the max length of each field in the result */
- /* will be somewhat time consuming for very large results */
- if (fillAlign) {
- for (i=0; i < nTuples; i++) {
- for (j=0 ; j < nFields; j++) {
- if (PQgetlength(res,i,j) > fLength[j])
- fLength[j] = PQgetlength(res,i,j);
- }
- }
- }
-
- if (printHeader) {
- /* first, print out the attribute names */
- for (i=0; i < nFields; i++) {
- fputs(PQfname(res,i), fp);
- if (fillAlign)
- fill (strlen (PQfname(res,i)), fLength[i], ' ', fp);
- fputs(fieldSep,fp);
- }
- fprintf(fp, "\n");
-
- /* Underline the attribute names */
- for (i=0; i < nFields; i++) {
- if (fillAlign)
- fill (0, fLength[i], '-', fp);
- fputs(fieldSep,fp);
- }
- fprintf(fp, "\n");
- }
-
- /* next, print out the instances */
- for (i=0; i < nTuples; i++) {
- for (j=0 ; j < nFields; j++) {
- fprintf(fp, "%s", PQgetvalue(res,i,j));
- if (fillAlign)
- fill (strlen (PQgetvalue(res,i,j)), fLength[j], ' ', fp);
- fputs(fieldSep,fp);
- }
- fprintf(fp, "\n");
- }
-
- if (!quiet)
- fprintf (fp, "\nQuery returned %d row%s.\n",PQntuples(res),
- (PQntuples(res) == 1) ? "" : "s");
-
- fflush(fp);
+ int i,
+ j;
+ int nFields;
+ int nTuples;
+ int fLength[MAX_FIELDS];
+
+ if (fieldSep == NULL)
+ fieldSep = DEFAULT_FIELD_SEP;
+
+ /* Get some useful info about the results */
+ nFields = PQnfields(res);
+ nTuples = PQntuples(res);
+
+ if (fp == NULL)
+ fp = stdout;
+
+ /* Zero the initial field lengths */
+ for (j = 0; j < nFields; j++)
+ {
+ fLength[j] = strlen(PQfname(res, j));
+ }
+ /* Find the max length of each field in the result */
+ /* will be somewhat time consuming for very large results */
+ if (fillAlign)
+ {
+ for (i = 0; i < nTuples; i++)
+ {
+ for (j = 0; j < nFields; j++)
+ {
+ if (PQgetlength(res, i, j) > fLength[j])
+ fLength[j] = PQgetlength(res, i, j);
+ }
+ }
+ }
+
+ if (printHeader)
+ {
+ /* first, print out the attribute names */
+ for (i = 0; i < nFields; i++)
+ {
+ fputs(PQfname(res, i), fp);
+ if (fillAlign)
+ fill(strlen(PQfname(res, i)), fLength[i], ' ', fp);
+ fputs(fieldSep, fp);
+ }
+ fprintf(fp, "\n");
+
+ /* Underline the attribute names */
+ for (i = 0; i < nFields; i++)
+ {
+ if (fillAlign)
+ fill(0, fLength[i], '-', fp);
+ fputs(fieldSep, fp);
+ }
+ fprintf(fp, "\n");
+ }
+
+ /* next, print out the instances */
+ for (i = 0; i < nTuples; i++)
+ {
+ for (j = 0; j < nFields; j++)
+ {
+ fprintf(fp, "%s", PQgetvalue(res, i, j));
+ if (fillAlign)
+ fill(strlen(PQgetvalue(res, i, j)), fLength[j], ' ', fp);
+ fputs(fieldSep, fp);
+ }
+ fprintf(fp, "\n");
+ }
+
+ if (!quiet)
+ fprintf(fp, "\nQuery returned %d row%s.\n", PQntuples(res),
+ (PQntuples(res) == 1) ? "" : "s");
+
+ fflush(fp);
}
@@ -825,260 +933,311 @@ PQdisplayTuples(PGresult *res,
*
*/
void
-PQprintTuples(PGresult *res,
- FILE* fout, /* output stream */
- int PrintAttNames,/* print attribute names or not*/
- int TerseOutput, /* delimiter bars or not?*/
- int colWidth /* width of column, if 0, use variable width */
- )
+PQprintTuples(PGresult * res,
+ FILE * fout, /* output stream */
+ int PrintAttNames,/* print attribute names or not */
+ int TerseOutput, /* delimiter bars or not? */
+ int colWidth /* width of column, if 0, use variable
+ * width */
+)
{
- int nFields;
- int nTups;
- int i,j;
- char formatString[80];
-
- char *tborder = NULL;
-
- nFields = PQnfields(res);
- nTups = PQntuples(res);
-
- if (colWidth > 0) {
- sprintf(formatString,"%%s %%-%ds",colWidth);
- } else
- sprintf(formatString,"%%s %%s");
-
- if ( nFields > 0 ) { /* only print rows with at least 1 field. */
-
- if (!TerseOutput)
- {
- int width;
- width = nFields * 14;
- tborder = malloc (width+1);
- for (i = 0; i <= width; i++)
- tborder[i] = '-';
- tborder[i] = '\0';
- fprintf(fout,"%s\n",tborder);
- }
-
- for (i=0; i < nFields; i++) {
- if (PrintAttNames) {
- fprintf(fout,formatString,
- TerseOutput ? "" : "|",
- PQfname(res, i));
- }
- }
-
- if (PrintAttNames) {
- if (TerseOutput)
- fprintf(fout,"\n");
- else
- fprintf(fout, "|\n%s\n",tborder);
- }
-
- for (i = 0; i < nTups; i++) {
- for (j = 0; j < nFields; j++) {
- char *pval = PQgetvalue(res,i,j);
- fprintf(fout, formatString,
- TerseOutput ? "" : "|",
- pval ? pval : "");
- }
- if (TerseOutput)
- fprintf(fout,"\n");
- else
- fprintf(fout, "|\n%s\n",tborder);
- }
- }
+ int nFields;
+ int nTups;
+ int i,
+ j;
+ char formatString[80];
+
+ char *tborder = NULL;
+
+ nFields = PQnfields(res);
+ nTups = PQntuples(res);
+
+ if (colWidth > 0)
+ {
+ sprintf(formatString, "%%s %%-%ds", colWidth);
+ }
+ else
+ sprintf(formatString, "%%s %%s");
+
+ if (nFields > 0)
+ { /* only print rows with at least 1 field. */
+
+ if (!TerseOutput)
+ {
+ int width;
+
+ width = nFields * 14;
+ tborder = malloc(width + 1);
+ for (i = 0; i <= width; i++)
+ tborder[i] = '-';
+ tborder[i] = '\0';
+ fprintf(fout, "%s\n", tborder);
+ }
+
+ for (i = 0; i < nFields; i++)
+ {
+ if (PrintAttNames)
+ {
+ fprintf(fout, formatString,
+ TerseOutput ? "" : "|",
+ PQfname(res, i));
+ }
+ }
+
+ if (PrintAttNames)
+ {
+ if (TerseOutput)
+ fprintf(fout, "\n");
+ else
+ fprintf(fout, "|\n%s\n", tborder);
+ }
+
+ for (i = 0; i < nTups; i++)
+ {
+ for (j = 0; j < nFields; j++)
+ {
+ char *pval = PQgetvalue(res, i, j);
+
+ fprintf(fout, formatString,
+ TerseOutput ? "" : "|",
+ pval ? pval : "");
+ }
+ if (TerseOutput)
+ fprintf(fout, "\n");
+ else
+ fprintf(fout, "|\n%s\n", tborder);
+ }
+ }
}
static void
-do_field(PQprintOpt *po, PGresult *res,
- const int i, const int j, char *buf, const int fs_len,
- char *fields[],
- const int nFields, char *fieldNames[],
- unsigned char fieldNotNum[], int fieldMax[],
- const int fieldMaxLen, FILE *fout
- ) {
-
- char *pval, *p, *o;
- int plen;
- bool skipit;
-
- plen=PQgetlength(res,i,j);
- pval=PQgetvalue(res,i,j);
-
- if (plen < 1 || !pval || !*pval) {
- if (po->align || po->expanded) skipit = true;
- else {
- skipit = false;
- goto efield;
- }
- } else skipit = false;
-
- if (!skipit) {
- for (p=pval, o=buf; *p; *(o++)=*(p++)) {
- if ((fs_len==1 && (*p==*(po->fieldSep))) || *p=='\\' || *p=='\n')
- *(o++)='\\';
- if (po->align && (*pval=='E' || *pval=='e' ||
- !((*p>='0' && *p<='9') ||
- *p=='.' ||
- *p=='E' ||
- *p=='e' ||
- *p==' ' ||
- *p=='-')))
- fieldNotNum[j]=1;
- }
- *o='\0';
- if (!po->expanded && (po->align || po->html3)) {
- int n=strlen(buf);
- if (n>fieldMax[j])
- fieldMax[j]=n;
- if (!(fields[i*nFields+j]=(char *)malloc(n+1))) {
- perror("malloc");
- exit(1);
- }
- strcpy(fields[i*nFields+j], buf);
- } else {
- if (po->expanded) {
- if (po->html3)
- fprintf(fout,
- "<tr><td align=left><b>%s</b></td>"
- "<td align=%s>%s</td></tr>\n",
- fieldNames[j],
- fieldNotNum[j] ? "left": "right",
- buf);
- else {
- if (po->align)
- fprintf(fout,
- "%-*s%s %s\n",
- fieldMaxLen-fs_len, fieldNames[j], po->fieldSep,
- buf);
- else
- fprintf(fout, "%s%s%s\n", fieldNames[j], po->fieldSep, buf);
- }
- } else {
- if (!po->html3) {
- fputs(buf, fout);
- efield:
- if ((j+1)<nFields)
- fputs(po->fieldSep, fout);
- else
- fputc('\n', fout);
- }
- }
- }
- }
+do_field(PQprintOpt * po, PGresult * res,
+ const int i, const int j, char *buf, const int fs_len,
+ char *fields[],
+ const int nFields, char *fieldNames[],
+ unsigned char fieldNotNum[], int fieldMax[],
+ const int fieldMaxLen, FILE * fout
+)
+{
+
+ char *pval,
+ *p,
+ *o;
+ int plen;
+ bool skipit;
+
+ plen = PQgetlength(res, i, j);
+ pval = PQgetvalue(res, i, j);
+
+ if (plen < 1 || !pval || !*pval)
+ {
+ if (po->align || po->expanded)
+ skipit = true;
+ else
+ {
+ skipit = false;
+ goto efield;
+ }
+ }
+ else
+ skipit = false;
+
+ if (!skipit)
+ {
+ for (p = pval, o = buf; *p; *(o++) = *(p++))
+ {
+ if ((fs_len == 1 && (*p == *(po->fieldSep))) || *p == '\\' || *p == '\n')
+ *(o++) = '\\';
+ if (po->align && (*pval == 'E' || *pval == 'e' ||
+ !((*p >= '0' && *p <= '9') ||
+ *p == '.' ||
+ *p == 'E' ||
+ *p == 'e' ||
+ *p == ' ' ||
+ *p == '-')))
+ fieldNotNum[j] = 1;
+ }
+ *o = '\0';
+ if (!po->expanded && (po->align || po->html3))
+ {
+ int n = strlen(buf);
+
+ if (n > fieldMax[j])
+ fieldMax[j] = n;
+ if (!(fields[i * nFields + j] = (char *) malloc(n + 1)))
+ {
+ perror("malloc");
+ exit(1);
+ }
+ strcpy(fields[i * nFields + j], buf);
+ }
+ else
+ {
+ if (po->expanded)
+ {
+ if (po->html3)
+ fprintf(fout,
+ "<tr><td align=left><b>%s</b></td>"
+ "<td align=%s>%s</td></tr>\n",
+ fieldNames[j],
+ fieldNotNum[j] ? "left" : "right",
+ buf);
+ else
+ {
+ if (po->align)
+ fprintf(fout,
+ "%-*s%s %s\n",
+ fieldMaxLen - fs_len, fieldNames[j], po->fieldSep,
+ buf);
+ else
+ fprintf(fout, "%s%s%s\n", fieldNames[j], po->fieldSep, buf);
+ }
+ }
+ else
+ {
+ if (!po->html3)
+ {
+ fputs(buf, fout);
+ efield:
+ if ((j + 1) < nFields)
+ fputs(po->fieldSep, fout);
+ else
+ fputc('\n', fout);
+ }
+ }
+ }
+ }
}
-static char*
-do_header(FILE *fout, PQprintOpt *po, const int nFields, int fieldMax[],
- char *fieldNames[], unsigned char fieldNotNum[],
- const int fs_len, PGresult *res) {
-
- int j; /* for loop index */
- char *border=NULL;
-
- if (po->html3)
- fputs("<tr>", fout);
- else {
- int j; /* for loop index */
- int tot=0;
- int n=0;
- char *p=NULL;
- for (; n < nFields; n++)
- tot+=fieldMax[n]+fs_len+(po->standard? 2: 0);
- if (po->standard)
- tot+=fs_len*2+2;
- border=malloc(tot+1);
- if (!border) {
- perror("malloc");
- exit(1);
- }
- p=border;
- if (po->standard) {
- char *fs=po->fieldSep;
- while (*fs++)
- *p++='+';
- }
- for (j=0; j < nFields; j++) {
- int len;
- for (len=fieldMax[j] + (po->standard? 2:0) ; len--; *p++='-');
- if (po->standard || (j+1)<nFields) {
- char *fs=po->fieldSep;
- while (*fs++)
- *p++='+';
- }
- }
- *p='\0';
- if (po->standard)
- fprintf(fout, "%s\n", border);
- }
- if (po->standard)
- fputs(po->fieldSep, fout);
- for (j=0; j < nFields; j++) {
- char *s=PQfname(res, j);
- if (po->html3) {
- fprintf(fout, "<th align=%s>%s</th>",
- fieldNotNum[j]? "left": "right", fieldNames[j]);
- } else {
- int n=strlen(s);
- if (n>fieldMax[j])
- fieldMax[j]=n;
- if (po->standard)
- fprintf(fout,
- fieldNotNum[j] ? " %-*s ": " %*s ",
- fieldMax[j], s);
- else
- fprintf(fout, fieldNotNum[j] ? "%-*s": "%*s", fieldMax[j], s);
- if (po->standard || (j+1)<nFields)
- fputs(po->fieldSep, fout);
- }
- }
- if (po->html3)
- fputs("</tr>\n", fout);
- else
- fprintf(fout, "\n%s\n", border);
- return border;
+static char *
+do_header(FILE * fout, PQprintOpt * po, const int nFields, int fieldMax[],
+ char *fieldNames[], unsigned char fieldNotNum[],
+ const int fs_len, PGresult * res)
+{
+
+ int j; /* for loop index */
+ char *border = NULL;
+
+ if (po->html3)
+ fputs("<tr>", fout);
+ else
+ {
+ int j; /* for loop index */
+ int tot = 0;
+ int n = 0;
+ char *p = NULL;
+
+ for (; n < nFields; n++)
+ tot += fieldMax[n] + fs_len + (po->standard ? 2 : 0);
+ if (po->standard)
+ tot += fs_len * 2 + 2;
+ border = malloc(tot + 1);
+ if (!border)
+ {
+ perror("malloc");
+ exit(1);
+ }
+ p = border;
+ if (po->standard)
+ {
+ char *fs = po->fieldSep;
+
+ while (*fs++)
+ *p++ = '+';
+ }
+ for (j = 0; j < nFields; j++)
+ {
+ int len;
+
+ for (len = fieldMax[j] + (po->standard ? 2 : 0); len--; *p++ = '-');
+ if (po->standard || (j + 1) < nFields)
+ {
+ char *fs = po->fieldSep;
+
+ while (*fs++)
+ *p++ = '+';
+ }
+ }
+ *p = '\0';
+ if (po->standard)
+ fprintf(fout, "%s\n", border);
+ }
+ if (po->standard)
+ fputs(po->fieldSep, fout);
+ for (j = 0; j < nFields; j++)
+ {
+ char *s = PQfname(res, j);
+
+ if (po->html3)
+ {
+ fprintf(fout, "<th align=%s>%s</th>",
+ fieldNotNum[j] ? "left" : "right", fieldNames[j]);
+ }
+ else
+ {
+ int n = strlen(s);
+
+ if (n > fieldMax[j])
+ fieldMax[j] = n;
+ if (po->standard)
+ fprintf(fout,
+ fieldNotNum[j] ? " %-*s " : " %*s ",
+ fieldMax[j], s);
+ else
+ fprintf(fout, fieldNotNum[j] ? "%-*s" : "%*s", fieldMax[j], s);
+ if (po->standard || (j + 1) < nFields)
+ fputs(po->fieldSep, fout);
+ }
+ }
+ if (po->html3)
+ fputs("</tr>\n", fout);
+ else
+ fprintf(fout, "\n%s\n", border);
+ return border;
}
static void
-output_row(FILE *fout, PQprintOpt *po, const int nFields, char *fields[],
- unsigned char fieldNotNum[], int fieldMax[], char *border,
- const int row_index) {
-
- int field_index; /* for loop index */
-
- if (po->html3)
- fputs("<tr>", fout);
- else if (po->standard)
- fputs(po->fieldSep, fout);
- for (field_index = 0; field_index < nFields; field_index++) {
- char *p=fields[row_index*nFields+field_index];
- if (po->html3)
- fprintf(fout, "<td align=%s>%s</td>",
- fieldNotNum[field_index]? "left": "right", p? p: "");
- else {
- fprintf(fout,
- fieldNotNum[field_index] ?
- (po->standard ? " %-*s ": "%-*s") :
- (po->standard ? " %*s ": "%*s"),
- fieldMax[field_index],
- p ? p: "");
- if (po->standard || field_index+1 < nFields)
- fputs(po->fieldSep, fout);
- }
- if (p)
- free(p);
- }
- if (po->html3)
- fputs("</tr>", fout);
- else
- if (po->standard)
- fprintf(fout, "\n%s", border);
- fputc('\n', fout);
+output_row(FILE * fout, PQprintOpt * po, const int nFields, char *fields[],
+ unsigned char fieldNotNum[], int fieldMax[], char *border,
+ const int row_index)
+{
+
+ int field_index;/* for loop index */
+
+ if (po->html3)
+ fputs("<tr>", fout);
+ else if (po->standard)
+ fputs(po->fieldSep, fout);
+ for (field_index = 0; field_index < nFields; field_index++)
+ {
+ char *p = fields[row_index * nFields + field_index];
+
+ if (po->html3)
+ fprintf(fout, "<td align=%s>%s</td>",
+ fieldNotNum[field_index] ? "left" : "right", p ? p : "");
+ else
+ {
+ fprintf(fout,
+ fieldNotNum[field_index] ?
+ (po->standard ? " %-*s " : "%-*s") :
+ (po->standard ? " %*s " : "%*s"),
+ fieldMax[field_index],
+ p ? p : "");
+ if (po->standard || field_index + 1 < nFields)
+ fputs(po->fieldSep, fout);
+ }
+ if (p)
+ free(p);
+ }
+ if (po->html3)
+ fputs("</tr>", fout);
+ else if (po->standard)
+ fprintf(fout, "\n%s", border);
+ fputc('\n', fout);
}
@@ -1097,591 +1256,672 @@ output_row(FILE *fout, PQprintOpt *po, const int nFields, char *fields[],
*/
void
-PQprint(FILE *fout,
- PGresult *res,
- PQprintOpt *po
- )
+PQprint(FILE * fout,
+ PGresult * res,
+ PQprintOpt * po
+)
{
- int nFields;
-
- nFields = PQnfields(res);
-
- if ( nFields > 0 ) { /* only print rows with at least 1 field. */
- int i,j;
- int nTups;
- int *fieldMax=NULL; /* in case we don't use them */
- unsigned char *fieldNotNum=NULL;
- char *border=NULL;
- char **fields=NULL;
- char **fieldNames;
- int fieldMaxLen=0;
- int numFieldName;
- int fs_len=strlen(po->fieldSep);
- int total_line_length = 0;
- int usePipe = 0;
- char *pagerenv;
- char buf[8192*2+1];
-
- nTups = PQntuples(res);
- if (!(fieldNames=(char **)calloc(nFields, sizeof (char *)))) {
- perror("calloc");
- exit(1);
- }
- if (!(fieldNotNum=(unsigned char *)calloc(nFields, 1))) {
- perror("calloc");
- exit(1);
- }
- if (!(fieldMax=(int *)calloc(nFields, sizeof(int)))) {
- perror("calloc");
- exit(1);
- }
- for (numFieldName=0;
- po->fieldName && po->fieldName[numFieldName];
- numFieldName++)
- ;
- for (j=0; j < nFields; j++) {
- int len;
- char *s =
- (j<numFieldName && po->fieldName[j][0])?
- po->fieldName[j]: PQfname(res, j);
- fieldNames[j]=s;
- len=s ? strlen(s): 0;
- fieldMax[j] = len;
- len+=fs_len;
- if (len>fieldMaxLen)
- fieldMaxLen=len;
- total_line_length += len;
- }
-
- total_line_length += nFields * strlen(po->fieldSep) + 1;
-
- if (fout == NULL)
- fout = stdout;
- if (po->pager && fout == stdout &&
- isatty(fileno(stdin)) &&
- isatty(fileno(stdout))) {
- /* try to pipe to the pager program if possible */
+ int nFields;
+
+ nFields = PQnfields(res);
+
+ if (nFields > 0)
+ { /* only print rows with at least 1 field. */
+ int i,
+ j;
+ int nTups;
+ int *fieldMax = NULL; /* in case we don't use
+ * them */
+ unsigned char *fieldNotNum = NULL;
+ char *border = NULL;
+ char **fields = NULL;
+ char **fieldNames;
+ int fieldMaxLen = 0;
+ int numFieldName;
+ int fs_len = strlen(po->fieldSep);
+ int total_line_length = 0;
+ int usePipe = 0;
+ char *pagerenv;
+ char buf[8192 * 2 + 1];
+
+ nTups = PQntuples(res);
+ if (!(fieldNames = (char **) calloc(nFields, sizeof(char *))))
+ {
+ perror("calloc");
+ exit(1);
+ }
+ if (!(fieldNotNum = (unsigned char *) calloc(nFields, 1)))
+ {
+ perror("calloc");
+ exit(1);
+ }
+ if (!(fieldMax = (int *) calloc(nFields, sizeof(int))))
+ {
+ perror("calloc");
+ exit(1);
+ }
+ for (numFieldName = 0;
+ po->fieldName && po->fieldName[numFieldName];
+ numFieldName++)
+ ;
+ for (j = 0; j < nFields; j++)
+ {
+ int len;
+ char *s =
+ (j < numFieldName && po->fieldName[j][0]) ?
+ po->fieldName[j] : PQfname(res, j);
+
+ fieldNames[j] = s;
+ len = s ? strlen(s) : 0;
+ fieldMax[j] = len;
+ len += fs_len;
+ if (len > fieldMaxLen)
+ fieldMaxLen = len;
+ total_line_length += len;
+ }
+
+ total_line_length += nFields * strlen(po->fieldSep) + 1;
+
+ if (fout == NULL)
+ fout = stdout;
+ if (po->pager && fout == stdout &&
+ isatty(fileno(stdin)) &&
+ isatty(fileno(stdout)))
+ {
+ /* try to pipe to the pager program if possible */
#ifdef TIOCGWINSZ
- if (ioctl(fileno(stdout),TIOCGWINSZ,&screen_size) == -1 ||
- screen_size.ws_col == 0 ||
- screen_size.ws_row == 0) {
+ if (ioctl(fileno(stdout), TIOCGWINSZ, &screen_size) == -1 ||
+ screen_size.ws_col == 0 ||
+ screen_size.ws_row == 0)
+ {
#endif
- screen_size.ws_row = 24;
- screen_size.ws_col = 80;
+ screen_size.ws_row = 24;
+ screen_size.ws_col = 80;
#ifdef TIOCGWINSZ
- }
+ }
#endif
- pagerenv=getenv("PAGER");
- if (pagerenv != NULL &&
- pagerenv[0] != '\0' &&
- !po->html3 &&
- ((po->expanded &&
- nTups * (nFields+1) >= screen_size.ws_row) ||
- (!po->expanded &&
- nTups * (total_line_length / screen_size.ws_col + 1) *
- ( 1 + (po->standard != 0)) >=
- screen_size.ws_row -
- (po->header != 0) *
- (total_line_length / screen_size.ws_col + 1) * 2
- - (po->header != 0) *2 /* row count and newline */
- ))) {
- fout = popen(pagerenv, "w");
- if (fout) {
- usePipe = 1;
- pqsignal(SIGPIPE, SIG_IGN);
- } else
- fout = stdout;
- }
- }
-
- if (!po->expanded && (po->align || po->html3)) {
- if (!(fields=(char **)calloc(nFields*(nTups+1), sizeof(char *)))) {
- perror("calloc");
- exit(1);
- }
- } else
- if (po->header && !po->html3) {
- if (po->expanded) {
- if (po->align)
- fprintf(fout, "%-*s%s Value\n",
- fieldMaxLen-fs_len, "Field", po->fieldSep);
- else
- fprintf(fout, "%s%sValue\n", "Field", po->fieldSep);
- } else {
- int len=0;
- for (j=0; j < nFields; j++) {
- char *s=fieldNames[j];
- fputs(s, fout);
- len+=strlen(s)+fs_len;
- if ((j+1)<nFields)
- fputs(po->fieldSep, fout);
- }
- fputc('\n', fout);
- for (len-=fs_len; len--; fputc('-', fout));
- fputc('\n', fout);
- }
- }
- if (po->expanded && po->html3) {
- if (po->caption)
- fprintf(fout, "<centre><h2>%s</h2></centre>\n", po->caption);
- else
- fprintf(fout,
- "<centre><h2>"
- "Query retrieved %d rows * %d fields"
- "</h2></centre>\n",
- nTups, nFields);
- }
- for (i = 0; i < nTups; i++) {
- if (po->expanded) {
- if (po->html3)
- fprintf(fout,
- "<table %s><caption align=high>%d</caption>\n",
- po->tableOpt? po->tableOpt: "", i);
- else
- fprintf(fout, "-- RECORD %d --\n", i);
- }
- for (j = 0; j < nFields; j++)
- do_field(po, res, i, j, buf, fs_len, fields, nFields,
- fieldNames, fieldNotNum,
- fieldMax, fieldMaxLen, fout);
- if (po->html3 && po->expanded)
- fputs("</table>\n", fout);
- }
- if (!po->expanded && (po->align || po->html3)) {
- if (po->html3) {
- if (po->header) {
- if (po->caption)
- fprintf(fout,
- "<table %s><caption align=high>%s</caption>\n",
- po->tableOpt? po->tableOpt: "",
- po->caption);
- else
- fprintf(fout,
- "<table %s><caption align=high>"
- "Retrieved %d rows * %d fields"
- "</caption>\n",
- po->tableOpt? po->tableOpt: "", nTups, nFields);
- } else
- fprintf(fout, "<table %s>", po->tableOpt? po->tableOpt: "");
- }
- if (po->header)
- border = do_header(fout, po, nFields, fieldMax, fieldNames,
- fieldNotNum, fs_len, res);
- for (i = 0; i < nTups; i++)
- output_row(fout, po, nFields, fields,
- fieldNotNum, fieldMax, border, i);
- free(fields);
- if (border)
- free(border);
- }
- if (po->header && !po->html3)
- fprintf (fout, "(%d row%s)\n\n",PQntuples(res),
- (PQntuples(res) == 1) ? "" : "s");
- free(fieldMax);
- free(fieldNotNum);
- free(fieldNames);
- if (usePipe) {
- pclose(fout);
- pqsignal(SIGPIPE, SIG_DFL);
- }
- if (po->html3 && !po->expanded)
- fputs("</table>\n", fout);
- }
+ pagerenv = getenv("PAGER");
+ if (pagerenv != NULL &&
+ pagerenv[0] != '\0' &&
+ !po->html3 &&
+ ((po->expanded &&
+ nTups * (nFields + 1) >= screen_size.ws_row) ||
+ (!po->expanded &&
+ nTups * (total_line_length / screen_size.ws_col + 1) *
+ (1 + (po->standard != 0)) >=
+ screen_size.ws_row -
+ (po->header != 0) *
+ (total_line_length / screen_size.ws_col + 1) * 2
+ - (po->header != 0) * 2 /* row count and newline */
+ )))
+ {
+ fout = popen(pagerenv, "w");
+ if (fout)
+ {
+ usePipe = 1;
+ pqsignal(SIGPIPE, SIG_IGN);
+ }
+ else
+ fout = stdout;
+ }
+ }
+
+ if (!po->expanded && (po->align || po->html3))
+ {
+ if (!(fields = (char **) calloc(nFields * (nTups + 1), sizeof(char *))))
+ {
+ perror("calloc");
+ exit(1);
+ }
+ }
+ else if (po->header && !po->html3)
+ {
+ if (po->expanded)
+ {
+ if (po->align)
+ fprintf(fout, "%-*s%s Value\n",
+ fieldMaxLen - fs_len, "Field", po->fieldSep);
+ else
+ fprintf(fout, "%s%sValue\n", "Field", po->fieldSep);
+ }
+ else
+ {
+ int len = 0;
+
+ for (j = 0; j < nFields; j++)
+ {
+ char *s = fieldNames[j];
+
+ fputs(s, fout);
+ len += strlen(s) + fs_len;
+ if ((j + 1) < nFields)
+ fputs(po->fieldSep, fout);
+ }
+ fputc('\n', fout);
+ for (len -= fs_len; len--; fputc('-', fout));
+ fputc('\n', fout);
+ }
+ }
+ if (po->expanded && po->html3)
+ {
+ if (po->caption)
+ fprintf(fout, "<centre><h2>%s</h2></centre>\n", po->caption);
+ else
+ fprintf(fout,
+ "<centre><h2>"
+ "Query retrieved %d rows * %d fields"
+ "</h2></centre>\n",
+ nTups, nFields);
+ }
+ for (i = 0; i < nTups; i++)
+ {
+ if (po->expanded)
+ {
+ if (po->html3)
+ fprintf(fout,
+ "<table %s><caption align=high>%d</caption>\n",
+ po->tableOpt ? po->tableOpt : "", i);
+ else
+ fprintf(fout, "-- RECORD %d --\n", i);
+ }
+ for (j = 0; j < nFields; j++)
+ do_field(po, res, i, j, buf, fs_len, fields, nFields,
+ fieldNames, fieldNotNum,
+ fieldMax, fieldMaxLen, fout);
+ if (po->html3 && po->expanded)
+ fputs("</table>\n", fout);
+ }
+ if (!po->expanded && (po->align || po->html3))
+ {
+ if (po->html3)
+ {
+ if (po->header)
+ {
+ if (po->caption)
+ fprintf(fout,
+ "<table %s><caption align=high>%s</caption>\n",
+ po->tableOpt ? po->tableOpt : "",
+ po->caption);
+ else
+ fprintf(fout,
+ "<table %s><caption align=high>"
+ "Retrieved %d rows * %d fields"
+ "</caption>\n",
+ po->tableOpt ? po->tableOpt : "", nTups, nFields);
+ }
+ else
+ fprintf(fout, "<table %s>", po->tableOpt ? po->tableOpt : "");
+ }
+ if (po->header)
+ border = do_header(fout, po, nFields, fieldMax, fieldNames,
+ fieldNotNum, fs_len, res);
+ for (i = 0; i < nTups; i++)
+ output_row(fout, po, nFields, fields,
+ fieldNotNum, fieldMax, border, i);
+ free(fields);
+ if (border)
+ free(border);
+ }
+ if (po->header && !po->html3)
+ fprintf(fout, "(%d row%s)\n\n", PQntuples(res),
+ (PQntuples(res) == 1) ? "" : "s");
+ free(fieldMax);
+ free(fieldNotNum);
+ free(fieldNames);
+ if (usePipe)
+ {
+ pclose(fout);
+ pqsignal(SIGPIPE, SIG_DFL);
+ }
+ if (po->html3 && !po->expanded)
+ fputs("</table>\n", fout);
+ }
}
/* ----------------
- * PQfn - Send a function call to the POSTGRES backend.
+ * PQfn - Send a function call to the POSTGRES backend.
*
- * conn : backend connection
- * fnid : function id
- * result_buf : pointer to result buffer (&int if integer)
- * result_len : length of return value.
- * actual_result_len: actual length returned. (differs from result_len
- * for varlena structures.)
- * result_type : If the result is an integer, this must be 1,
- * otherwise this should be 0
- * args : pointer to a NULL terminated arg array.
- * (length, if integer, and result-pointer)
- * nargs : # of arguments in args array.
+ * conn : backend connection
+ * fnid : function id
+ * result_buf : pointer to result buffer (&int if integer)
+ * result_len : length of return value.
+ * actual_result_len: actual length returned. (differs from result_len
+ * for varlena structures.)
+ * result_type : If the result is an integer, this must be 1,
+ * otherwise this should be 0
+ * args : pointer to a NULL terminated arg array.
+ * (length, if integer, and result-pointer)
+ * nargs : # of arguments in args array.
*
* RETURNS
- * NULL on failure. PQerrormsg will be set.
- * "G" if there is a return value.
- * "V" if there is no return value.
+ * NULL on failure. PQerrormsg will be set.
+ * "G" if there is a return value.
+ * "V" if there is no return value.
* ----------------
*/
-PGresult*
-PQfn(PGconn *conn,
- int fnid,
- int *result_buf,
- int *actual_result_len,
- int result_is_int,
- PQArgBlock *args,
- int nargs)
+PGresult *
+PQfn(PGconn * conn,
+ int fnid,
+ int *result_buf,
+ int *actual_result_len,
+ int result_is_int,
+ PQArgBlock * args,
+ int nargs)
{
- FILE *pfin, *pfout, *pfdebug;
- int id;
- int i;
-
- if (!conn) return NULL;
-
- pfin = conn->Pfin;
- pfout = conn->Pfout;
- pfdebug = conn->Pfdebug;
-
- /* clear the error string */
- conn->errorMessage[0] = '\0';
-
- pqPuts("F ",pfout,pfdebug); /* function */
- pqPutInt(fnid, 4, pfout, pfdebug); /* function id */
- pqPutInt(nargs, 4, pfout, pfdebug); /* # of args */
-
- for (i = 0; i < nargs; ++i) { /* len.int4 + contents */
- pqPutInt(args[i].len, 4, pfout, pfdebug);
- if (args[i].isint) {
- pqPutInt(args[i].u.integer, 4, pfout, pfdebug);
- } else {
- pqPutnchar((char *)args[i].u.ptr, args[i].len, pfout, pfdebug);
- }
- }
- pqFlush(pfout, pfdebug);
-
- id = pqGetc(pfin, pfdebug);
- if (id != 'V') {
- if (id == 'E') {
- pqGets(conn->errorMessage,ERROR_MSG_LENGTH,pfin,pfdebug);
- } else
- sprintf(conn->errorMessage,
- "PQfn: expected a 'V' from the backend. Got '%c' instead",
- id);
- return makeEmptyPGresult(conn,PGRES_FATAL_ERROR);
- }
-
- id = pqGetc(pfin, pfdebug);
- for (;;) {
- int c;
- switch (id) {
- case 'G': /* function returned properly */
- pqGetInt(actual_result_len,4,pfin,pfdebug);
- if (result_is_int) {
- pqGetInt(result_buf,4,pfin,pfdebug);
- } else {
- pqGetnchar((char *) result_buf, *actual_result_len,
- pfin, pfdebug);
- }
- c = pqGetc(pfin, pfdebug); /* get the last '0'*/
- return makeEmptyPGresult(conn,PGRES_COMMAND_OK);
- case 'E':
- sprintf(conn->errorMessage,
- "PQfn: returned an error");
- return makeEmptyPGresult(conn,PGRES_FATAL_ERROR);
- case 'N':
- /* print notice and go back to processing return values */
- if (pqGets(conn->errorMessage, ERROR_MSG_LENGTH, pfin, pfdebug)
- == 1) {
- sprintf(conn->errorMessage,
- "Notice return detected from backend, but message "
- "cannot be read");
- } else
- fprintf(stderr, "%s\n", conn->errorMessage);
- /* keep iterating */
- break;
- case '0': /* no return value */
- return makeEmptyPGresult(conn,PGRES_COMMAND_OK);
- default:
- /* The backend violates the protocol. */
- sprintf(conn->errorMessage,
- "FATAL: PQfn: protocol error: id=%x\n", id);
- return makeEmptyPGresult(conn,PGRES_FATAL_ERROR);
- }
- }
+ FILE *pfin,
+ *pfout,
+ *pfdebug;
+ int id;
+ int i;
+
+ if (!conn)
+ return NULL;
+
+ pfin = conn->Pfin;
+ pfout = conn->Pfout;
+ pfdebug = conn->Pfdebug;
+
+ /* clear the error string */
+ conn->errorMessage[0] = '\0';
+
+ pqPuts("F ", pfout, pfdebug); /* function */
+ pqPutInt(fnid, 4, pfout, pfdebug); /* function id */
+ pqPutInt(nargs, 4, pfout, pfdebug); /* # of args */
+
+ for (i = 0; i < nargs; ++i)
+ { /* len.int4 + contents */
+ pqPutInt(args[i].len, 4, pfout, pfdebug);
+ if (args[i].isint)
+ {
+ pqPutInt(args[i].u.integer, 4, pfout, pfdebug);
+ }
+ else
+ {
+ pqPutnchar((char *) args[i].u.ptr, args[i].len, pfout, pfdebug);
+ }
+ }
+ pqFlush(pfout, pfdebug);
+
+ id = pqGetc(pfin, pfdebug);
+ if (id != 'V')
+ {
+ if (id == 'E')
+ {
+ pqGets(conn->errorMessage, ERROR_MSG_LENGTH, pfin, pfdebug);
+ }
+ else
+ sprintf(conn->errorMessage,
+ "PQfn: expected a 'V' from the backend. Got '%c' instead",
+ id);
+ return makeEmptyPGresult(conn, PGRES_FATAL_ERROR);
+ }
+
+ id = pqGetc(pfin, pfdebug);
+ for (;;)
+ {
+ int c;
+
+ switch (id)
+ {
+ case 'G': /* function returned properly */
+ pqGetInt(actual_result_len, 4, pfin, pfdebug);
+ if (result_is_int)
+ {
+ pqGetInt(result_buf, 4, pfin, pfdebug);
+ }
+ else
+ {
+ pqGetnchar((char *) result_buf, *actual_result_len,
+ pfin, pfdebug);
+ }
+ c = pqGetc(pfin, pfdebug); /* get the last '0' */
+ return makeEmptyPGresult(conn, PGRES_COMMAND_OK);
+ case 'E':
+ sprintf(conn->errorMessage,
+ "PQfn: returned an error");
+ return makeEmptyPGresult(conn, PGRES_FATAL_ERROR);
+ case 'N':
+ /* print notice and go back to processing return values */
+ if (pqGets(conn->errorMessage, ERROR_MSG_LENGTH, pfin, pfdebug)
+ == 1)
+ {
+ sprintf(conn->errorMessage,
+ "Notice return detected from backend, but message "
+ "cannot be read");
+ }
+ else
+ fprintf(stderr, "%s\n", conn->errorMessage);
+ /* keep iterating */
+ break;
+ case '0': /* no return value */
+ return makeEmptyPGresult(conn, PGRES_COMMAND_OK);
+ default:
+ /* The backend violates the protocol. */
+ sprintf(conn->errorMessage,
+ "FATAL: PQfn: protocol error: id=%x\n", id);
+ return makeEmptyPGresult(conn, PGRES_FATAL_ERROR);
+ }
+ }
}
/* ====== accessor funcs for PGresult ======== */
-ExecStatusType
-PQresultStatus(PGresult* res)
-{
- if (!res) {
- fprintf(stderr, "PQresultStatus() -- pointer to PQresult is null");
- return PGRES_NONFATAL_ERROR;
- }
+ExecStatusType
+PQresultStatus(PGresult * res)
+{
+ if (!res)
+ {
+ fprintf(stderr, "PQresultStatus() -- pointer to PQresult is null");
+ return PGRES_NONFATAL_ERROR;
+ }
- return res->resultStatus;
+ return res->resultStatus;
}
-int
-PQntuples(PGresult *res)
+int
+PQntuples(PGresult * res)
{
- if (!res) {
- fprintf(stderr, "PQntuples() -- pointer to PQresult is null");
- return (int)NULL;
- }
- return res->ntups;
+ if (!res)
+ {
+ fprintf(stderr, "PQntuples() -- pointer to PQresult is null");
+ return (int) NULL;
+ }
+ return res->ntups;
}
int
-PQnfields(PGresult *res)
+PQnfields(PGresult * res)
{
- if (!res) {
- fprintf(stderr, "PQnfields() -- pointer to PQresult is null");
- return (int)NULL;
- }
- return res->numAttributes;
+ if (!res)
+ {
+ fprintf(stderr, "PQnfields() -- pointer to PQresult is null");
+ return (int) NULL;
+ }
+ return res->numAttributes;
}
/*
returns NULL if the field_num is invalid
*/
-char*
-PQfname(PGresult *res, int field_num)
+char *
+PQfname(PGresult * res, int field_num)
{
- if (!res) {
- fprintf(stderr, "PQfname() -- pointer to PQresult is null");
- return NULL;
- }
-
- if (field_num > (res->numAttributes - 1)) {
- fprintf(stderr,
- "PQfname: ERROR! name of field %d(of %d) is not available",
- field_num, res->numAttributes -1);
- return NULL;
- }
- if (res->attDescs) {
- return res->attDescs[field_num].name;
- } else
- return NULL;
+ if (!res)
+ {
+ fprintf(stderr, "PQfname() -- pointer to PQresult is null");
+ return NULL;
+ }
+
+ if (field_num > (res->numAttributes - 1))
+ {
+ fprintf(stderr,
+ "PQfname: ERROR! name of field %d(of %d) is not available",
+ field_num, res->numAttributes - 1);
+ return NULL;
+ }
+ if (res->attDescs)
+ {
+ return res->attDescs[field_num].name;
+ }
+ else
+ return NULL;
}
/*
returns -1 on a bad field name
*/
int
-PQfnumber(PGresult *res, const char* field_name)
+PQfnumber(PGresult * res, const char *field_name)
{
- int i;
+ int i;
- if (!res) {
- fprintf(stderr, "PQfnumber() -- pointer to PQresult is null");
- return -1;
- }
+ if (!res)
+ {
+ fprintf(stderr, "PQfnumber() -- pointer to PQresult is null");
+ return -1;
+ }
- if (field_name == NULL ||
- field_name[0] == '\0' ||
- res->attDescs == NULL)
- return -1;
+ if (field_name == NULL ||
+ field_name[0] == '\0' ||
+ res->attDescs == NULL)
+ return -1;
- for (i=0;i<res->numAttributes;i++) {
- if ( strcasecmp(field_name, res->attDescs[i].name) == 0 )
- return i;
- }
- return -1;
+ for (i = 0; i < res->numAttributes; i++)
+ {
+ if (strcasecmp(field_name, res->attDescs[i].name) == 0)
+ return i;
+ }
+ return -1;
}
Oid
-PQftype(PGresult *res, int field_num)
+PQftype(PGresult * res, int field_num)
{
- if (!res) {
- fprintf(stderr, "PQftype() -- pointer to PQresult is null");
- return InvalidOid;
- }
-
- if (field_num > (res->numAttributes - 1)) {
- fprintf(stderr,
- "PQftype: ERROR! type of field %d(of %d) is not available",
- field_num, res->numAttributes -1);
- }
- if (res->attDescs) {
- return res->attDescs[field_num].adtid;
- } else
- return InvalidOid;
+ if (!res)
+ {
+ fprintf(stderr, "PQftype() -- pointer to PQresult is null");
+ return InvalidOid;
+ }
+
+ if (field_num > (res->numAttributes - 1))
+ {
+ fprintf(stderr,
+ "PQftype: ERROR! type of field %d(of %d) is not available",
+ field_num, res->numAttributes - 1);
+ }
+ if (res->attDescs)
+ {
+ return res->attDescs[field_num].adtid;
+ }
+ else
+ return InvalidOid;
}
int2
-PQfsize(PGresult *res, int field_num)
+PQfsize(PGresult * res, int field_num)
{
- if (!res) {
- fprintf(stderr, "PQfsize() -- pointer to PQresult is null");
- return (int2)NULL;
- }
-
- if (field_num > (res->numAttributes - 1)) {
- fprintf(stderr,
- "PQfsize: ERROR! size of field %d(of %d) is not available",
- field_num, res->numAttributes -1);
- }
- if (res->attDescs) {
- return res->attDescs[field_num].adtsize;
- } else
- return 0;
+ if (!res)
+ {
+ fprintf(stderr, "PQfsize() -- pointer to PQresult is null");
+ return (int2) NULL;
+ }
+
+ if (field_num > (res->numAttributes - 1))
+ {
+ fprintf(stderr,
+ "PQfsize: ERROR! size of field %d(of %d) is not available",
+ field_num, res->numAttributes - 1);
+ }
+ if (res->attDescs)
+ {
+ return res->attDescs[field_num].adtsize;
+ }
+ else
+ return 0;
}
-char* PQcmdStatus(PGresult *res) {
- if (!res) {
- fprintf(stderr, "PQcmdStatus() -- pointer to PQresult is null");
- return NULL;
- }
- return res->cmdStatus;
+char *
+PQcmdStatus(PGresult * res)
+{
+ if (!res)
+ {
+ fprintf(stderr, "PQcmdStatus() -- pointer to PQresult is null");
+ return NULL;
+ }
+ return res->cmdStatus;
}
/*
PQoidStatus -
- if the last command was an INSERT, return the oid string
- if not, return ""
+ if the last command was an INSERT, return the oid string
+ if not, return ""
*/
-static char oidStatus[32] = {0};
-const char* PQoidStatus (PGresult *res)
+static char oidStatus[32] = {0};
+const char *
+PQoidStatus(PGresult * res)
{
- if (!res)
- {
- fprintf (stderr, "PQoidStatus () -- pointer to PQresult is null");
- return NULL;
- }
-
- oidStatus[0] = 0;
- if ( !res->cmdStatus )
- return oidStatus;
-
- if ( strncmp (res->cmdStatus, "INSERT", 6) == 0 )
- {
- char *p = res->cmdStatus + 7;
- char *e;
-
- for (e = p; *e != ' ' && *e; ) e++;
- sprintf (oidStatus, "%.*s", e - p, p);
- }
- return oidStatus;
+ if (!res)
+ {
+ fprintf(stderr, "PQoidStatus () -- pointer to PQresult is null");
+ return NULL;
+ }
+
+ oidStatus[0] = 0;
+ if (!res->cmdStatus)
+ return oidStatus;
+
+ if (strncmp(res->cmdStatus, "INSERT", 6) == 0)
+ {
+ char *p = res->cmdStatus + 7;
+ char *e;
+
+ for (e = p; *e != ' ' && *e;)
+ e++;
+ sprintf(oidStatus, "%.*s", e - p, p);
+ }
+ return oidStatus;
}
/*
PQcmdTuples -
- if the last command was an INSERT/UPDATE/DELETE, return number
- of inserted/affected tuples, if not, return ""
+ if the last command was an INSERT/UPDATE/DELETE, return number
+ of inserted/affected tuples, if not, return ""
*/
-const char* PQcmdTuples (PGresult *res)
+const char *
+PQcmdTuples(PGresult * res)
{
- if (!res)
- {
- fprintf (stderr, "PQcmdTuples () -- pointer to PQresult is null");
- return NULL;
- }
-
- if ( !res->cmdStatus )
- return "";
-
- if ( strncmp (res->cmdStatus, "INSERT", 6) == 0 ||
- strncmp (res->cmdStatus, "DELETE", 6) == 0 ||
- strncmp (res->cmdStatus, "UPDATE", 6) == 0 )
- {
- char *p = res->cmdStatus + 6;
-
- if ( *p == 0 )
- {
- fprintf (stderr, "PQcmdTuples (%s) -- short input from server",
- res->cmdStatus);
- return NULL;
- }
- p++;
- if ( *(res->cmdStatus) != 'I' ) /* UPDATE/DELETE */
- return (p);
- while ( *p != ' ' && *p ) p++; /* INSERT: skip oid */
- if ( *p == 0 )
- {
- fprintf (stderr, "PQcmdTuples (INSERT) -- there's no # of tuples");
- return NULL;
- }
- p++;
- return (p);
- }
- return "";
+ if (!res)
+ {
+ fprintf(stderr, "PQcmdTuples () -- pointer to PQresult is null");
+ return NULL;
+ }
+
+ if (!res->cmdStatus)
+ return "";
+
+ if (strncmp(res->cmdStatus, "INSERT", 6) == 0 ||
+ strncmp(res->cmdStatus, "DELETE", 6) == 0 ||
+ strncmp(res->cmdStatus, "UPDATE", 6) == 0)
+ {
+ char *p = res->cmdStatus + 6;
+
+ if (*p == 0)
+ {
+ fprintf(stderr, "PQcmdTuples (%s) -- short input from server",
+ res->cmdStatus);
+ return NULL;
+ }
+ p++;
+ if (*(res->cmdStatus) != 'I') /* UPDATE/DELETE */
+ return (p);
+ while (*p != ' ' && *p)
+ p++; /* INSERT: skip oid */
+ if (*p == 0)
+ {
+ fprintf(stderr, "PQcmdTuples (INSERT) -- there's no # of tuples");
+ return NULL;
+ }
+ p++;
+ return (p);
+ }
+ return "";
}
/*
PQgetvalue:
- return the value of field 'field_num' of row 'tup_num'
+ return the value of field 'field_num' of row 'tup_num'
- If res is binary, then the value returned is NOT a null-terminated
- ASCII string, but the binary representation in the server's native
- format.
+ If res is binary, then the value returned is NOT a null-terminated
+ ASCII string, but the binary representation in the server's native
+ format.
- if res is not binary, a null-terminated ASCII string is returned.
+ if res is not binary, a null-terminated ASCII string is returned.
*/
-char*
-PQgetvalue(PGresult *res, int tup_num, int field_num)
+char *
+PQgetvalue(PGresult * res, int tup_num, int field_num)
{
- if (!res) {
- fprintf(stderr, "PQgetvalue: pointer to PQresult is null\n");
- return NULL;
- } else if (tup_num > (res->ntups - 1)) {
- fprintf(stderr,
- "PQgetvalue: There is no row %d in the query results. "
- "The highest numbered row is %d.\n",
- tup_num, res->ntups - 1);
- return NULL;
- } else if (field_num > (res->numAttributes - 1)) {
- fprintf(stderr,
- "PQgetvalue: There is no field %d in the query results. "
- "The highest numbered field is %d.\n",
- field_num, res->numAttributes - 1);
- return NULL;
- }
-
- return res->tuples[tup_num][field_num].value;
+ if (!res)
+ {
+ fprintf(stderr, "PQgetvalue: pointer to PQresult is null\n");
+ return NULL;
+ }
+ else if (tup_num > (res->ntups - 1))
+ {
+ fprintf(stderr,
+ "PQgetvalue: There is no row %d in the query results. "
+ "The highest numbered row is %d.\n",
+ tup_num, res->ntups - 1);
+ return NULL;
+ }
+ else if (field_num > (res->numAttributes - 1))
+ {
+ fprintf(stderr,
+ "PQgetvalue: There is no field %d in the query results. "
+ "The highest numbered field is %d.\n",
+ field_num, res->numAttributes - 1);
+ return NULL;
+ }
+
+ return res->tuples[tup_num][field_num].value;
}
/* PQgetlength:
- returns the length of a field value in bytes. If res is binary,
- i.e. a result of a binary portal, then the length returned does
- NOT include the size field of the varlena.
+ returns the length of a field value in bytes. If res is binary,
+ i.e. a result of a binary portal, then the length returned does
+ NOT include the size field of the varlena.
*/
int
-PQgetlength(PGresult *res, int tup_num, int field_num)
+PQgetlength(PGresult * res, int tup_num, int field_num)
{
- if (!res) {
- fprintf(stderr, "PQgetlength() -- pointer to PQresult is null");
- return (int)NULL;
- }
-
- if (tup_num > (res->ntups - 1 )||
- field_num > (res->numAttributes - 1)) {
- fprintf(stderr,
- "PQgetlength: ERROR! field %d(of %d) of row %d(of %d) "
- "is not available",
- field_num, res->numAttributes - 1, tup_num, res->ntups);
- }
-
- if (res->tuples[tup_num][field_num].len != NULL_LEN)
- return res->tuples[tup_num][field_num].len;
- else
- return 0;
- }
+ if (!res)
+ {
+ fprintf(stderr, "PQgetlength() -- pointer to PQresult is null");
+ return (int) NULL;
+ }
+
+ if (tup_num > (res->ntups - 1) ||
+ field_num > (res->numAttributes - 1))
+ {
+ fprintf(stderr,
+ "PQgetlength: ERROR! field %d(of %d) of row %d(of %d) "
+ "is not available",
+ field_num, res->numAttributes - 1, tup_num, res->ntups);
+ }
+
+ if (res->tuples[tup_num][field_num].len != NULL_LEN)
+ return res->tuples[tup_num][field_num].len;
+ else
+ return 0;
+}
/* PQgetisnull:
- returns the null status of a field value.
+ returns the null status of a field value.
*/
int
-PQgetisnull(PGresult *res, int tup_num, int field_num)
+PQgetisnull(PGresult * res, int tup_num, int field_num)
{
- if (!res) {
- fprintf(stderr, "PQgetisnull() -- pointer to PQresult is null");
- return (int)NULL;
- }
-
- if (tup_num > (res->ntups - 1 )||
- field_num > (res->numAttributes - 1)) {
- fprintf(stderr,
- "PQgetisnull: ERROR! field %d(of %d) of row %d(of %d) "
- "is not available",
- field_num, res->numAttributes - 1, tup_num, res->ntups);
- }
-
- if (res->tuples[tup_num][field_num].len == NULL_LEN)
- return 1;
- else
- return 0;
+ if (!res)
+ {
+ fprintf(stderr, "PQgetisnull() -- pointer to PQresult is null");
+ return (int) NULL;
+ }
+
+ if (tup_num > (res->ntups - 1) ||
+ field_num > (res->numAttributes - 1))
+ {
+ fprintf(stderr,
+ "PQgetisnull: ERROR! field %d(of %d) of row %d(of %d) "
+ "is not available",
+ field_num, res->numAttributes - 1, tup_num, res->ntups);
+ }
+
+ if (res->tuples[tup_num][field_num].len == NULL_LEN)
+ return 1;
+ else
+ return 0;
}
diff --git a/src/interfaces/libpq/fe-lobj.c b/src/interfaces/libpq/fe-lobj.c
index 9b566cea339..1636edc7f42 100644
--- a/src/interfaces/libpq/fe-lobj.c
+++ b/src/interfaces/libpq/fe-lobj.c
@@ -1,13 +1,13 @@
/*-------------------------------------------------------------------------
*
* fe-lobj.c--
- * Front-end large object interface
+ * Front-end large object interface
*
* Copyright (c) 1994, Regents of the University of California
*
*
* IDENTIFICATION
- * $Header: /cvsroot/pgsql/src/interfaces/libpq/fe-lobj.c,v 1.7 1997/05/06 07:19:04 thomas Exp $
+ * $Header: /cvsroot/pgsql/src/interfaces/libpq/fe-lobj.c,v 1.8 1997/09/07 05:03:34 momjian Exp $
*
*-------------------------------------------------------------------------
*/
@@ -21,207 +21,227 @@
#include "libpq-fe.h"
#include "libpq/libpq-fs.h"
-#define LO_BUFSIZE 1024
+#define LO_BUFSIZE 1024
-static int lo_initialize(PGconn *conn);
+static int lo_initialize(PGconn * conn);
/*
* lo_open
- * opens an existing large object
+ * opens an existing large object
*
* returns the file descriptor for use in later lo_* calls
* return -1 upon failure.
*/
int
-lo_open(PGconn* conn, Oid lobjId, int mode)
+lo_open(PGconn * conn, Oid lobjId, int mode)
{
- int fd;
- int result_len;
- PQArgBlock argv[2];
- PGresult *res;
-
- argv[0].isint = 1;
- argv[0].len = 4;
- argv[0].u.integer = lobjId;
-
- argv[1].isint = 1;
- argv[1].len = 4;
- argv[1].u.integer = mode;
-
- if(conn->lobjfuncs == (PGlobjfuncs *)NULL) {
- if(lo_initialize(conn) < 0) {
- return -1;
- }
- }
-
- res = PQfn(conn, conn->lobjfuncs->fn_lo_open,&fd,&result_len,1,argv,2);
- if (PQresultStatus(res) == PGRES_COMMAND_OK) {
- PQclear(res);
+ int fd;
+ int result_len;
+ PQArgBlock argv[2];
+ PGresult *res;
+
+ argv[0].isint = 1;
+ argv[0].len = 4;
+ argv[0].u.integer = lobjId;
+
+ argv[1].isint = 1;
+ argv[1].len = 4;
+ argv[1].u.integer = mode;
+
+ if (conn->lobjfuncs == (PGlobjfuncs *) NULL)
+ {
+ if (lo_initialize(conn) < 0)
+ {
+ return -1;
+ }
+ }
+
+ res = PQfn(conn, conn->lobjfuncs->fn_lo_open, &fd, &result_len, 1, argv, 2);
+ if (PQresultStatus(res) == PGRES_COMMAND_OK)
+ {
+ PQclear(res);
- /* have to do this to reset offset in shared fd cache */
- /* but only if fd is valid */
- if (fd >= 0 && lo_lseek(conn, fd, 0L, SEEK_SET) < 0)
- return -1;
- return fd;
- } else
- return -1;
+ /* have to do this to reset offset in shared fd cache */
+ /* but only if fd is valid */
+ if (fd >= 0 && lo_lseek(conn, fd, 0L, SEEK_SET) < 0)
+ return -1;
+ return fd;
+ }
+ else
+ return -1;
}
/*
* lo_close
- * closes an existing large object
+ * closes an existing large object
*
* returns 0 upon success
* returns -1 upon failure.
*/
int
-lo_close(PGconn *conn, int fd)
+lo_close(PGconn * conn, int fd)
{
- PQArgBlock argv[1];
- PGresult *res;
- int retval;
- int result_len;
-
- if(conn->lobjfuncs == (PGlobjfuncs *)NULL) {
- if(lo_initialize(conn) < 0) {
- return -1;
- }
- }
-
- argv[0].isint = 1;
- argv[0].len = 4;
- argv[0].u.integer = fd;
- res = PQfn(conn, conn->lobjfuncs->fn_lo_close,
- &retval,&result_len,1,argv,1);
- if (PQresultStatus(res) == PGRES_COMMAND_OK) {
- PQclear(res);
- return retval;
- } else
- return -1;
+ PQArgBlock argv[1];
+ PGresult *res;
+ int retval;
+ int result_len;
+
+ if (conn->lobjfuncs == (PGlobjfuncs *) NULL)
+ {
+ if (lo_initialize(conn) < 0)
+ {
+ return -1;
+ }
+ }
+
+ argv[0].isint = 1;
+ argv[0].len = 4;
+ argv[0].u.integer = fd;
+ res = PQfn(conn, conn->lobjfuncs->fn_lo_close,
+ &retval, &result_len, 1, argv, 1);
+ if (PQresultStatus(res) == PGRES_COMMAND_OK)
+ {
+ PQclear(res);
+ return retval;
+ }
+ else
+ return -1;
}
/*
* lo_read
- * read len bytes of the large object into buf
+ * read len bytes of the large object into buf
*
* returns the length of bytes read.
* the CALLER must have allocated enough space to hold the result returned
*/
int
-lo_read(PGconn *conn, int fd, char *buf, int len)
+lo_read(PGconn * conn, int fd, char *buf, int len)
{
- PQArgBlock argv[2];
- PGresult *res;
- int result_len;
-
- if(conn->lobjfuncs == (PGlobjfuncs *)NULL) {
- if(lo_initialize(conn) < 0) {
- return -1;
- }
- }
-
- argv[0].isint = 1;
- argv[0].len = 4;
- argv[0].u.integer = fd;
-
- argv[1].isint = 1;
- argv[1].len = 4;
- argv[1].u.integer = len;
-
- res = PQfn(conn, conn->lobjfuncs->fn_lo_read,
- (int*)buf,&result_len,0,argv,2);
- if (PQresultStatus(res) == PGRES_COMMAND_OK) {
- PQclear(res);
- return result_len;
- } else
- return -1;
+ PQArgBlock argv[2];
+ PGresult *res;
+ int result_len;
+
+ if (conn->lobjfuncs == (PGlobjfuncs *) NULL)
+ {
+ if (lo_initialize(conn) < 0)
+ {
+ return -1;
+ }
+ }
+
+ argv[0].isint = 1;
+ argv[0].len = 4;
+ argv[0].u.integer = fd;
+
+ argv[1].isint = 1;
+ argv[1].len = 4;
+ argv[1].u.integer = len;
+
+ res = PQfn(conn, conn->lobjfuncs->fn_lo_read,
+ (int *) buf, &result_len, 0, argv, 2);
+ if (PQresultStatus(res) == PGRES_COMMAND_OK)
+ {
+ PQclear(res);
+ return result_len;
+ }
+ else
+ return -1;
}
/*
* lo_write
- * write len bytes of buf into the large object fd
+ * write len bytes of buf into the large object fd
*
*/
int
-lo_write(PGconn *conn, int fd, char *buf, int len)
+lo_write(PGconn * conn, int fd, char *buf, int len)
{
- PQArgBlock argv[2];
- PGresult *res;
- int result_len;
- int retval;
-
- if(conn->lobjfuncs == (PGlobjfuncs *)NULL) {
- if(lo_initialize(conn) < 0) {
- return -1;
- }
- }
-
- if (len <= 0)
- return 0;
+ PQArgBlock argv[2];
+ PGresult *res;
+ int result_len;
+ int retval;
+
+ if (conn->lobjfuncs == (PGlobjfuncs *) NULL)
+ {
+ if (lo_initialize(conn) < 0)
+ {
+ return -1;
+ }
+ }
- argv[0].isint = 1;
- argv[0].len = 4;
- argv[0].u.integer = fd;
+ if (len <= 0)
+ return 0;
- argv[1].isint = 0;
- argv[1].len = len;
- argv[1].u.ptr = (int*)buf;
+ argv[0].isint = 1;
+ argv[0].len = 4;
+ argv[0].u.integer = fd;
- res = PQfn(conn, conn->lobjfuncs->fn_lo_write,
- &retval,&result_len,1,argv,2);
- if (PQresultStatus(res) == PGRES_COMMAND_OK) {
- PQclear(res);
- return retval;
- } else
- return -1;
+ argv[1].isint = 0;
+ argv[1].len = len;
+ argv[1].u.ptr = (int *) buf;
+
+ res = PQfn(conn, conn->lobjfuncs->fn_lo_write,
+ &retval, &result_len, 1, argv, 2);
+ if (PQresultStatus(res) == PGRES_COMMAND_OK)
+ {
+ PQclear(res);
+ return retval;
+ }
+ else
+ return -1;
}
/*
* lo_lseek
- * change the current read or write location on a large object
+ * change the current read or write location on a large object
* currently, only L_SET is a legal value for whence
*
*/
int
-lo_lseek(PGconn *conn, int fd, int offset, int whence)
+lo_lseek(PGconn * conn, int fd, int offset, int whence)
{
- PQArgBlock argv[3];
- PGresult *res;
- int retval;
- int result_len;
-
- if(conn->lobjfuncs == (PGlobjfuncs *)NULL) {
- if(lo_initialize(conn) < 0) {
- return -1;
- }
- }
-
- argv[0].isint = 1;
- argv[0].len = 4;
- argv[0].u.integer = fd;
-
- argv[1].isint = 1;
- argv[1].len = 4;
- argv[1].u.integer = offset;
-
- argv[2].isint = 1;
- argv[2].len = 4;
- argv[2].u.integer = whence;
-
- res = PQfn(conn, conn->lobjfuncs->fn_lo_lseek,
- &retval,&result_len,1,argv,3);
- if (PQresultStatus(res) == PGRES_COMMAND_OK) {
- PQclear(res);
- return retval;
- } else
- return -1;
+ PQArgBlock argv[3];
+ PGresult *res;
+ int retval;
+ int result_len;
+
+ if (conn->lobjfuncs == (PGlobjfuncs *) NULL)
+ {
+ if (lo_initialize(conn) < 0)
+ {
+ return -1;
+ }
+ }
+
+ argv[0].isint = 1;
+ argv[0].len = 4;
+ argv[0].u.integer = fd;
+
+ argv[1].isint = 1;
+ argv[1].len = 4;
+ argv[1].u.integer = offset;
+
+ argv[2].isint = 1;
+ argv[2].len = 4;
+ argv[2].u.integer = whence;
+
+ res = PQfn(conn, conn->lobjfuncs->fn_lo_lseek,
+ &retval, &result_len, 1, argv, 3);
+ if (PQresultStatus(res) == PGRES_COMMAND_OK)
+ {
+ PQclear(res);
+ return retval;
+ }
+ else
+ return -1;
}
/*
* lo_creat
- * create a new large object
+ * create a new large object
* the mode is a bitmask describing different attributes of the new object
*
* returns the oid of the large object created or
@@ -229,209 +249,233 @@ lo_lseek(PGconn *conn, int fd, int offset, int whence)
*/
Oid
-lo_creat(PGconn *conn, int mode)
+lo_creat(PGconn * conn, int mode)
{
- PQArgBlock argv[1];
- PGresult *res;
- int retval;
- int result_len;
-
- if(conn->lobjfuncs == (PGlobjfuncs *)NULL) {
- if(lo_initialize(conn) < 0) {
- return -1;
- }
- }
-
- argv[0].isint = 1;
- argv[0].len = 4;
- argv[0].u.integer = mode;
- res = PQfn(conn, conn->lobjfuncs->fn_lo_creat,
- &retval,&result_len,1,argv,1);
- if (PQresultStatus(res) == PGRES_COMMAND_OK) {
- PQclear(res);
- return (Oid)retval;
- } else
- return InvalidOid;
+ PQArgBlock argv[1];
+ PGresult *res;
+ int retval;
+ int result_len;
+
+ if (conn->lobjfuncs == (PGlobjfuncs *) NULL)
+ {
+ if (lo_initialize(conn) < 0)
+ {
+ return -1;
+ }
+ }
+
+ argv[0].isint = 1;
+ argv[0].len = 4;
+ argv[0].u.integer = mode;
+ res = PQfn(conn, conn->lobjfuncs->fn_lo_creat,
+ &retval, &result_len, 1, argv, 1);
+ if (PQresultStatus(res) == PGRES_COMMAND_OK)
+ {
+ PQclear(res);
+ return (Oid) retval;
+ }
+ else
+ return InvalidOid;
}
/*
* lo_tell
- * returns the current seek location of the large object
+ * returns the current seek location of the large object
*
*/
int
-lo_tell(PGconn *conn, int fd)
+lo_tell(PGconn * conn, int fd)
{
- int retval;
- PQArgBlock argv[1];
- PGresult *res;
- int result_len;
-
- if(conn->lobjfuncs == (PGlobjfuncs *)NULL) {
- if(lo_initialize(conn) < 0) {
- return -1;
- }
- }
-
- argv[0].isint = 1;
- argv[0].len = 4;
- argv[0].u.integer = fd;
-
- res = PQfn(conn, conn->lobjfuncs->fn_lo_tell,
- &retval,&result_len,1,argv,1);
- if (PQresultStatus(res) == PGRES_COMMAND_OK) {
- PQclear(res);
- return retval;
- } else
- return -1;
+ int retval;
+ PQArgBlock argv[1];
+ PGresult *res;
+ int result_len;
+
+ if (conn->lobjfuncs == (PGlobjfuncs *) NULL)
+ {
+ if (lo_initialize(conn) < 0)
+ {
+ return -1;
+ }
+ }
+
+ argv[0].isint = 1;
+ argv[0].len = 4;
+ argv[0].u.integer = fd;
+
+ res = PQfn(conn, conn->lobjfuncs->fn_lo_tell,
+ &retval, &result_len, 1, argv, 1);
+ if (PQresultStatus(res) == PGRES_COMMAND_OK)
+ {
+ PQclear(res);
+ return retval;
+ }
+ else
+ return -1;
}
/*
* lo_unlink
- * delete a file
+ * delete a file
*
*/
int
-lo_unlink(PGconn *conn, Oid lobjId)
+lo_unlink(PGconn * conn, Oid lobjId)
{
- PQArgBlock argv[1];
- PGresult *res;
- int result_len;
- int retval;
-
- if(conn->lobjfuncs == (PGlobjfuncs *)NULL) {
- if(lo_initialize(conn) < 0) {
- return -1;
- }
- }
-
- argv[0].isint = 1;
- argv[0].len = 4;
- argv[0].u.integer = lobjId;
-
- res = PQfn(conn, conn->lobjfuncs->fn_lo_unlink,
- &retval,&result_len,1,argv,1);
- if (PQresultStatus(res) == PGRES_COMMAND_OK) {
- PQclear(res);
- return retval;
- } else
- return -1;
+ PQArgBlock argv[1];
+ PGresult *res;
+ int result_len;
+ int retval;
+
+ if (conn->lobjfuncs == (PGlobjfuncs *) NULL)
+ {
+ if (lo_initialize(conn) < 0)
+ {
+ return -1;
+ }
+ }
+
+ argv[0].isint = 1;
+ argv[0].len = 4;
+ argv[0].u.integer = lobjId;
+
+ res = PQfn(conn, conn->lobjfuncs->fn_lo_unlink,
+ &retval, &result_len, 1, argv, 1);
+ if (PQresultStatus(res) == PGRES_COMMAND_OK)
+ {
+ PQclear(res);
+ return retval;
+ }
+ else
+ return -1;
}
/*
* lo_import -
- * imports a file as an (inversion) large object.
- * returns the oid of that object upon success,
+ * imports a file as an (inversion) large object.
+ * returns the oid of that object upon success,
* returns InvalidOid upon failure
*
*/
Oid
-lo_import(PGconn *conn, char* filename)
+lo_import(PGconn * conn, char *filename)
{
- int fd;
- int nbytes, tmp;
- char buf[LO_BUFSIZE];
- Oid lobjOid;
- int lobj;
-
- /*
- * open the file to be read in
- */
- fd = open(filename, O_RDONLY, 0666);
- if (fd < 0) { /* error */
- sprintf(conn->errorMessage,
- "lo_import: can't open unix file\"%s\"\n", filename);
- return InvalidOid;
- }
-
- /*
- * create an inversion "object"
- */
- lobjOid = lo_creat(conn, INV_READ|INV_WRITE);
- if (lobjOid == InvalidOid) {
- sprintf(conn->errorMessage,
- "lo_import: can't create inv object for \"%s\"", filename);
- return InvalidOid;
- }
-
- lobj = lo_open(conn, lobjOid, INV_WRITE);
- if (lobj == -1) {
- sprintf(conn->errorMessage,
- "lo_import: could not open inv object oid %d",lobjOid);
- return InvalidOid;
- }
- /*
- * read in from the Unix file and write to the inversion file
- */
- while ((nbytes = read(fd, buf, LO_BUFSIZE)) > 0) {
- tmp = lo_write(conn,lobj, buf, nbytes);
- if (tmp < nbytes) {
- sprintf(conn->errorMessage,
- "lo_import: error while reading \"%s\"",filename);
- return InvalidOid;
- }
- }
-
- (void) close(fd);
- (void) lo_close(conn, lobj);
-
- return lobjOid;
+ int fd;
+ int nbytes,
+ tmp;
+ char buf[LO_BUFSIZE];
+ Oid lobjOid;
+ int lobj;
+
+ /*
+ * open the file to be read in
+ */
+ fd = open(filename, O_RDONLY, 0666);
+ if (fd < 0)
+ { /* error */
+ sprintf(conn->errorMessage,
+ "lo_import: can't open unix file\"%s\"\n", filename);
+ return InvalidOid;
+ }
+
+ /*
+ * create an inversion "object"
+ */
+ lobjOid = lo_creat(conn, INV_READ | INV_WRITE);
+ if (lobjOid == InvalidOid)
+ {
+ sprintf(conn->errorMessage,
+ "lo_import: can't create inv object for \"%s\"", filename);
+ return InvalidOid;
+ }
+
+ lobj = lo_open(conn, lobjOid, INV_WRITE);
+ if (lobj == -1)
+ {
+ sprintf(conn->errorMessage,
+ "lo_import: could not open inv object oid %d", lobjOid);
+ return InvalidOid;
+ }
+
+ /*
+ * read in from the Unix file and write to the inversion file
+ */
+ while ((nbytes = read(fd, buf, LO_BUFSIZE)) > 0)
+ {
+ tmp = lo_write(conn, lobj, buf, nbytes);
+ if (tmp < nbytes)
+ {
+ sprintf(conn->errorMessage,
+ "lo_import: error while reading \"%s\"", filename);
+ return InvalidOid;
+ }
+ }
+
+ (void) close(fd);
+ (void) lo_close(conn, lobj);
+
+ return lobjOid;
}
/*
* lo_export -
- * exports an (inversion) large object.
+ * exports an (inversion) large object.
* returns -1 upon failure, 1 otherwise
*/
int
-lo_export(PGconn *conn, Oid lobjId, char *filename)
+lo_export(PGconn * conn, Oid lobjId, char *filename)
{
- int fd;
- int nbytes, tmp;
- char buf[LO_BUFSIZE];
- int lobj;
-
- /*
- * create an inversion "object"
- */
- lobj = lo_open(conn, lobjId, INV_READ);
- if (lobj == -1) {
- sprintf(conn->errorMessage,
- "lo_export: can't open inv object %d",lobjId);
- return -1;
- }
-
- /*
- * open the file to be written to
- */
- fd = open(filename, O_CREAT|O_WRONLY, 0666);
- if (fd < 0) { /* error */
- sprintf(conn->errorMessage,
- "lo_export: can't open unix file\"%s\"",filename);
- return 0;
- }
+ int fd;
+ int nbytes,
+ tmp;
+ char buf[LO_BUFSIZE];
+ int lobj;
+
+ /*
+ * create an inversion "object"
+ */
+ lobj = lo_open(conn, lobjId, INV_READ);
+ if (lobj == -1)
+ {
+ sprintf(conn->errorMessage,
+ "lo_export: can't open inv object %d", lobjId);
+ return -1;
+ }
+
+ /*
+ * open the file to be written to
+ */
+ fd = open(filename, O_CREAT | O_WRONLY, 0666);
+ if (fd < 0)
+ { /* error */
+ sprintf(conn->errorMessage,
+ "lo_export: can't open unix file\"%s\"", filename);
+ return 0;
+ }
- /*
- * read in from the Unix file and write to the inversion file
- */
- while ((nbytes = lo_read(conn, lobj, buf, LO_BUFSIZE)) > 0) {
- tmp = write(fd, buf, nbytes);
- if (tmp < nbytes) {
- sprintf(conn->errorMessage,
- "lo_export: error while writing \"%s\"",
- filename);
- return -1;
+ /*
+ * read in from the Unix file and write to the inversion file
+ */
+ while ((nbytes = lo_read(conn, lobj, buf, LO_BUFSIZE)) > 0)
+ {
+ tmp = write(fd, buf, nbytes);
+ if (tmp < nbytes)
+ {
+ sprintf(conn->errorMessage,
+ "lo_export: error while writing \"%s\"",
+ filename);
+ return -1;
+ }
}
- }
- (void) lo_close(conn,lobj);
- (void) close(fd);
+ (void) lo_close(conn, lobj);
+ (void) close(fd);
- return 1;
+ return 1;
}
@@ -443,31 +487,33 @@ lo_export(PGconn *conn, Oid lobjId, char *filename)
* functions that are required for large object operations.
* ----------------
*/
-static int lo_initialize(PGconn *conn)
+static int
+lo_initialize(PGconn * conn)
{
- PGresult *res;
- PGlobjfuncs *lobjfuncs;
- int n;
- char *fname;
- Oid foid;
-
- /* ----------------
- * Allocate the structure to hold the functions OID's
- * ----------------
- */
- lobjfuncs = (PGlobjfuncs *)malloc(sizeof(PGlobjfuncs));
- if (lobjfuncs == (PGlobjfuncs *)NULL) {
- strcpy(conn->errorMessage,
- "FATAL: malloc() failed in lo_initialize()\n");
- return -1;
- }
- memset((char *)lobjfuncs, 0, sizeof(PGlobjfuncs));
-
- /* ----------------
- * Execute the query to get all the functions at once
- * ----------------
- */
- res = PQexec(conn, "select proname, oid from pg_proc \
+ PGresult *res;
+ PGlobjfuncs *lobjfuncs;
+ int n;
+ char *fname;
+ Oid foid;
+
+ /* ----------------
+ * Allocate the structure to hold the functions OID's
+ * ----------------
+ */
+ lobjfuncs = (PGlobjfuncs *) malloc(sizeof(PGlobjfuncs));
+ if (lobjfuncs == (PGlobjfuncs *) NULL)
+ {
+ strcpy(conn->errorMessage,
+ "FATAL: malloc() failed in lo_initialize()\n");
+ return -1;
+ }
+ memset((char *) lobjfuncs, 0, sizeof(PGlobjfuncs));
+
+ /* ----------------
+ * Execute the query to get all the functions at once
+ * ----------------
+ */
+ res = PQexec(conn, "select proname, oid from pg_proc \
where proname = 'lo_open' \
or proname = 'lo_close' \
or proname = 'lo_creat' \
@@ -476,114 +522,131 @@ static int lo_initialize(PGconn *conn)
or proname = 'lo_tell' \
or proname = 'loread' \
or proname = 'lowrite'");
- if (res == (PGresult *)NULL) {
- free(lobjfuncs);
- return -1;
- }
+ if (res == (PGresult *) NULL)
+ {
+ free(lobjfuncs);
+ return -1;
+ }
+
+ if (res->resultStatus != PGRES_TUPLES_OK)
+ {
+ free(lobjfuncs);
+ PQclear(res);
+ strcpy(conn->errorMessage,
+ "ERROR: SELECT didn't return data in lo_initialize()\n");
+ return -1;
+ }
+
+ /* ----------------
+ * Examine the result and put the OID's into the struct
+ * ----------------
+ */
+ for (n = 0; n < PQntuples(res); n++)
+ {
+ fname = PQgetvalue(res, n, 0);
+ foid = (Oid) atoi(PQgetvalue(res, n, 1));
+ if (!strcmp(fname, "lo_open"))
+ {
+ lobjfuncs->fn_lo_open = foid;
+ }
+ else if (!strcmp(fname, "lo_close"))
+ {
+ lobjfuncs->fn_lo_close = foid;
+ }
+ else if (!strcmp(fname, "lo_creat"))
+ {
+ lobjfuncs->fn_lo_creat = foid;
+ }
+ else if (!strcmp(fname, "lo_unlink"))
+ {
+ lobjfuncs->fn_lo_unlink = foid;
+ }
+ else if (!strcmp(fname, "lo_lseek"))
+ {
+ lobjfuncs->fn_lo_lseek = foid;
+ }
+ else if (!strcmp(fname, "lo_tell"))
+ {
+ lobjfuncs->fn_lo_tell = foid;
+ }
+ else if (!strcmp(fname, "loread"))
+ {
+ lobjfuncs->fn_lo_read = foid;
+ }
+ else if (!strcmp(fname, "lowrite"))
+ {
+ lobjfuncs->fn_lo_write = foid;
+ }
+ }
- if (res->resultStatus != PGRES_TUPLES_OK) {
- free(lobjfuncs);
PQclear(res);
- strcpy(conn->errorMessage,
- "ERROR: SELECT didn't return data in lo_initialize()\n");
- return -1;
- }
-
- /* ----------------
- * Examine the result and put the OID's into the struct
- * ----------------
- */
- for(n = 0; n < PQntuples(res); n++) {
- fname = PQgetvalue(res, n, 0);
- foid = (Oid)atoi(PQgetvalue(res, n, 1));
- if(!strcmp(fname, "lo_open")) {
- lobjfuncs->fn_lo_open = foid;
- } else
- if(!strcmp(fname, "lo_close")) {
- lobjfuncs->fn_lo_close = foid;
- } else
- if(!strcmp(fname, "lo_creat")) {
- lobjfuncs->fn_lo_creat = foid;
- } else
- if(!strcmp(fname, "lo_unlink")) {
- lobjfuncs->fn_lo_unlink = foid;
- } else
- if(!strcmp(fname, "lo_lseek")) {
- lobjfuncs->fn_lo_lseek = foid;
- } else
- if(!strcmp(fname, "lo_tell")) {
- lobjfuncs->fn_lo_tell = foid;
- } else
- if(!strcmp(fname, "loread")) {
- lobjfuncs->fn_lo_read = foid;
- } else
- if(!strcmp(fname, "lowrite")) {
- lobjfuncs->fn_lo_write = foid;
- }
- }
-
- PQclear(res);
-
- /* ----------------
- * Finally check that we really got all large object
- * interface functions.
- * ----------------
- */
- if(lobjfuncs->fn_lo_open == 0) {
- strcpy(conn->errorMessage,
- "ERROR: Cannot determine OID for function lo_open\n");
- free(lobjfuncs);
- return -1;
- }
- if(lobjfuncs->fn_lo_close == 0) {
- strcpy(conn->errorMessage,
- "ERROR: Cannot determine OID for function lo_close\n");
- free(lobjfuncs);
- return -1;
- }
- if(lobjfuncs->fn_lo_creat == 0) {
- strcpy(conn->errorMessage,
- "ERROR: Cannot determine OID for function lo_creat\n");
- free(lobjfuncs);
- return -1;
- }
- if(lobjfuncs->fn_lo_unlink == 0) {
- strcpy(conn->errorMessage,
- "ERROR: Cannot determine OID for function lo_unlink\n");
- free(lobjfuncs);
- return -1;
- }
- if(lobjfuncs->fn_lo_lseek == 0) {
- strcpy(conn->errorMessage,
- "ERROR: Cannot determine OID for function lo_lseek\n");
- free(lobjfuncs);
- return -1;
- }
- if(lobjfuncs->fn_lo_tell == 0) {
- strcpy(conn->errorMessage,
- "ERROR: Cannot determine OID for function lo_tell\n");
- free(lobjfuncs);
- return -1;
- }
- if(lobjfuncs->fn_lo_read == 0) {
- strcpy(conn->errorMessage,
- "ERROR: Cannot determine OID for function loread\n");
- free(lobjfuncs);
- return -1;
- }
- if(lobjfuncs->fn_lo_write == 0) {
- strcpy(conn->errorMessage,
- "ERROR: Cannot determine OID for function lowrite\n");
- free(lobjfuncs);
- return -1;
- }
-
- /* ----------------
- * Put the structure into the connection control
- * ----------------
- */
- conn->lobjfuncs = lobjfuncs;
- return 0;
-}
+ /* ----------------
+ * Finally check that we really got all large object
+ * interface functions.
+ * ----------------
+ */
+ if (lobjfuncs->fn_lo_open == 0)
+ {
+ strcpy(conn->errorMessage,
+ "ERROR: Cannot determine OID for function lo_open\n");
+ free(lobjfuncs);
+ return -1;
+ }
+ if (lobjfuncs->fn_lo_close == 0)
+ {
+ strcpy(conn->errorMessage,
+ "ERROR: Cannot determine OID for function lo_close\n");
+ free(lobjfuncs);
+ return -1;
+ }
+ if (lobjfuncs->fn_lo_creat == 0)
+ {
+ strcpy(conn->errorMessage,
+ "ERROR: Cannot determine OID for function lo_creat\n");
+ free(lobjfuncs);
+ return -1;
+ }
+ if (lobjfuncs->fn_lo_unlink == 0)
+ {
+ strcpy(conn->errorMessage,
+ "ERROR: Cannot determine OID for function lo_unlink\n");
+ free(lobjfuncs);
+ return -1;
+ }
+ if (lobjfuncs->fn_lo_lseek == 0)
+ {
+ strcpy(conn->errorMessage,
+ "ERROR: Cannot determine OID for function lo_lseek\n");
+ free(lobjfuncs);
+ return -1;
+ }
+ if (lobjfuncs->fn_lo_tell == 0)
+ {
+ strcpy(conn->errorMessage,
+ "ERROR: Cannot determine OID for function lo_tell\n");
+ free(lobjfuncs);
+ return -1;
+ }
+ if (lobjfuncs->fn_lo_read == 0)
+ {
+ strcpy(conn->errorMessage,
+ "ERROR: Cannot determine OID for function loread\n");
+ free(lobjfuncs);
+ return -1;
+ }
+ if (lobjfuncs->fn_lo_write == 0)
+ {
+ strcpy(conn->errorMessage,
+ "ERROR: Cannot determine OID for function lowrite\n");
+ free(lobjfuncs);
+ return -1;
+ }
+ /* ----------------
+ * Put the structure into the connection control
+ * ----------------
+ */
+ conn->lobjfuncs = lobjfuncs;
+ return 0;
+}
diff --git a/src/interfaces/libpq/fe-misc.c b/src/interfaces/libpq/fe-misc.c
index 62062184ca8..b7e8a1b1c69 100644
--- a/src/interfaces/libpq/fe-misc.c
+++ b/src/interfaces/libpq/fe-misc.c
@@ -1,17 +1,17 @@
/*-------------------------------------------------------------------------
*
- * FILE
- * fe-misc.c
+ * FILE
+ * fe-misc.c
*
- * DESCRIPTION
- * miscellaneous useful functions
- * these routines are analogous to the ones in libpq/pqcomm.c
+ * DESCRIPTION
+ * miscellaneous useful functions
+ * these routines are analogous to the ones in libpq/pqcomm.c
*
* Copyright (c) 1994, Regents of the University of California
*
*
* IDENTIFICATION
- * $Header: /cvsroot/pgsql/src/interfaces/libpq/fe-misc.c,v 1.5 1997/03/16 18:51:29 scrappy Exp $
+ * $Header: /cvsroot/pgsql/src/interfaces/libpq/fe-misc.c,v 1.6 1997/09/07 05:03:35 momjian Exp $
*
*-------------------------------------------------------------------------
*/
@@ -29,80 +29,84 @@
if debug is set, also echo the character fetched
*/
-int pqGetc(FILE* fin, FILE* debug)
+int
+pqGetc(FILE * fin, FILE * debug)
{
- int c;
+ int c;
- c = getc(fin);
+ c = getc(fin);
- if (debug && c != EOF)
- fprintf(debug, "From backend> %c\n", c);
-
- return c;
+ if (debug && c != EOF)
+ fprintf(debug, "From backend> %c\n", c);
+
+ return c;
}
/* --------------------------------------------------------------------- */
/* pqPutnchar:
- send a string of exactly len length into stream f
+ send a string of exactly len length into stream f
returns 1 if there was an error, 0 otherwise.
*/
-int pqPutnchar(const char* s, int len, FILE *f, FILE *debug)
+int
+pqPutnchar(const char *s, int len, FILE * f, FILE * debug)
{
- if (f == NULL)
- return 1;
+ if (f == NULL)
+ return 1;
- if(debug)
- fprintf(debug, "To backend> %s\n", s);
+ if (debug)
+ fprintf(debug, "To backend> %s\n", s);
- if(fwrite(s, 1, len, f) != len)
- return 1;
+ if (fwrite(s, 1, len, f) != len)
+ return 1;
- return 0;
+ return 0;
}
/* --------------------------------------------------------------------- */
/* pqGetnchar:
- get a string of exactly len length from stream f
+ get a string of exactly len length from stream f
*/
-int pqGetnchar(char* s, int len, FILE *f, FILE *debug)
+int
+pqGetnchar(char *s, int len, FILE * f, FILE * debug)
{
- int cnt;
+ int cnt;
+
+ if (f == NULL)
+ return 1;
- if (f == NULL)
- return 1;
-
- cnt = fread(s, 1, len, f);
- s[cnt] = '\0';
- /* mjl: actually needs up to len+1 bytes, is this okay? XXX */
+ cnt = fread(s, 1, len, f);
+ s[cnt] = '\0';
+ /* mjl: actually needs up to len+1 bytes, is this okay? XXX */
- if (debug)
- fprintf(debug, "From backend (%d)> %s\n", len, s);
+ if (debug)
+ fprintf(debug, "From backend (%d)> %s\n", len, s);
- return 0;
+ return 0;
}
/* --------------------------------------------------------------------- */
/* pqGets:
get a string of up to length len from stream f
*/
-int pqGets(char* s, int len, FILE *f, FILE *debug)
+int
+pqGets(char *s, int len, FILE * f, FILE * debug)
{
- int c;
- const char *str = s;
+ int c;
+ const char *str = s;
+
+ if (f == NULL)
+ return 1;
- if (f == NULL)
- return 1;
-
- while (len-- && (c = getc(f)) != EOF && c)
- *s++ = c;
- *s = '\0';
- /* mjl: actually needs up to len+1 bytes, is this okay? XXX */
+ while (len-- && (c = getc(f)) != EOF && c)
+ *s++ = c;
+ *s = '\0';
+ /* mjl: actually needs up to len+1 bytes, is this okay? XXX */
- if (debug)
- fprintf(debug, "From backend> \"%s\"\n", str);
+ if (debug)
+ fprintf(debug, "From backend> \"%s\"\n", str);
- return 0;
+ return 0;
}
/* --------------------------------------------------------------------- */
@@ -111,84 +115,91 @@ int pqGets(char* s, int len, FILE *f, FILE *debug)
for host endianness.
returns 0 if successful, 1 otherwise
*/
-int pqPutInt(const int integer, int bytes, FILE* f, FILE *debug)
+int
+pqPutInt(const int integer, int bytes, FILE * f, FILE * debug)
{
- int retval = 0;
-
- switch(bytes)
- {
- case 2:
- retval = pqPutShort(integer, f);
- break;
- case 4:
- retval = pqPutLong(integer, f);
- break;
- default:
- fprintf(stderr, "** int size %d not supported\n", bytes);
- retval = 1;
- }
-
- if (debug) fprintf(debug, "To backend (%d#)> %d\n", bytes, integer);
-
- return retval;
+ int retval = 0;
+
+ switch (bytes)
+ {
+ case 2:
+ retval = pqPutShort(integer, f);
+ break;
+ case 4:
+ retval = pqPutLong(integer, f);
+ break;
+ default:
+ fprintf(stderr, "** int size %d not supported\n", bytes);
+ retval = 1;
+ }
+
+ if (debug)
+ fprintf(debug, "To backend (%d#)> %d\n", bytes, integer);
+
+ return retval;
}
/* --------------------------------------------------------------------- */
-/* pgGetInt
+/* pgGetInt
read a 2 or 4 byte integer from the stream and swab it around
to compensate for different endianness
- returns 0 if successful
+ returns 0 if successful
*/
-int pqGetInt(int* result, int bytes, FILE* f, FILE *debug)
+int
+pqGetInt(int *result, int bytes, FILE * f, FILE * debug)
{
- int retval = 0;
-
- switch(bytes)
- {
- case 2:
- retval = pqGetShort(result, f);
- break;
- case 4:
- retval = pqGetLong(result, f);
- break;
- default:
- fprintf(stderr, "** int size %d not supported\n", bytes);
- retval = 1;
- }
-
- if (debug)
- fprintf(debug,"From backend (#%d)> %d\n", bytes, *result);
-
- return retval;
+ int retval = 0;
+
+ switch (bytes)
+ {
+ case 2:
+ retval = pqGetShort(result, f);
+ break;
+ case 4:
+ retval = pqGetLong(result, f);
+ break;
+ default:
+ fprintf(stderr, "** int size %d not supported\n", bytes);
+ retval = 1;
+ }
+
+ if (debug)
+ fprintf(debug, "From backend (#%d)> %d\n", bytes, *result);
+
+ return retval;
}
/* --------------------------------------------------------------------- */
-int pqPuts(const char* s, FILE *f, FILE *debug)
+int
+pqPuts(const char *s, FILE * f, FILE * debug)
{
- if (f == NULL)
- return 1;
-
- if (fputs(s, f) == EOF)
- return 1;
-
- fputc('\0', f); /* important to send an ending \0 since backend expects it */
- fflush(f);
-
- if (debug) {
- fprintf(debug, "To backend> %s\n", s);
- }
-
- return 0;
+ if (f == NULL)
+ return 1;
+
+ if (fputs(s, f) == EOF)
+ return 1;
+
+ fputc('\0', f); /* important to send an ending \0 since
+ * backend expects it */
+ fflush(f);
+
+ if (debug)
+ {
+ fprintf(debug, "To backend> %s\n", s);
+ }
+
+ return 0;
}
/* --------------------------------------------------------------------- */
-void pqFlush(FILE *f, FILE *debug)
+void
+pqFlush(FILE * f, FILE * debug)
{
- if (f)
- fflush(f);
+ if (f)
+ fflush(f);
- if (debug)
- fflush(debug);
+ if (debug)
+ fflush(debug);
}
/* --------------------------------------------------------------------- */
diff --git a/src/interfaces/libpq/libpq-fe.h b/src/interfaces/libpq/libpq-fe.h
index fdd29fe42d2..3013d5a2bfc 100644
--- a/src/interfaces/libpq/libpq-fe.h
+++ b/src/interfaces/libpq/libpq-fe.h
@@ -1,12 +1,12 @@
/*-------------------------------------------------------------------------
*
* libpq-fe.h--
- * This file contains definitions for structures and
- * externs for functions used by frontend postgres applications.
+ * This file contains definitions for structures and
+ * externs for functions used by frontend postgres applications.
*
* Copyright (c) 1994, Regents of the University of California
*
- * $Id: libpq-fe.h,v 1.20 1997/08/27 09:05:24 vadim Exp $
+ * $Id: libpq-fe.h,v 1.21 1997/09/07 05:03:36 momjian Exp $
*
*-------------------------------------------------------------------------
*/
@@ -15,41 +15,47 @@
#define LIBPQ_FE_H
#ifdef __cplusplus
-extern "C" {
+extern "C"
+{
#endif
#include <stdio.h>
/* ----------------
- * include stuff common to fe and be
+ * include stuff common to fe and be
* ----------------
*/
#include "postgres_ext.h"
#include "libpq/pqcomm.h"
#include "lib/dllist.h"
-typedef enum {CONNECTION_OK,
- CONNECTION_BAD} ConnStatusType;
-
-typedef enum {
- PGRES_EMPTY_QUERY = 0,
- PGRES_COMMAND_OK, /* a query command that doesn't return */
- /* anything was executed properly by the backend */
- PGRES_TUPLES_OK, /* a query command that returns tuples */
- /* was executed properly by the backend, PGresult */
- /* contains the resulttuples */
- PGRES_COPY_OUT,
- PGRES_COPY_IN,
- PGRES_BAD_RESPONSE, /* an unexpected response was recv'd from the backend */
- PGRES_NONFATAL_ERROR,
- PGRES_FATAL_ERROR
-
-} ExecStatusType;
+ typedef enum
+ {
+ CONNECTION_OK,
+ CONNECTION_BAD
+ } ConnStatusType;
+
+ typedef enum
+ {
+ PGRES_EMPTY_QUERY = 0,
+ PGRES_COMMAND_OK, /* a query command that doesn't return */
+ /* anything was executed properly by the backend */
+ PGRES_TUPLES_OK, /* a query command that returns tuples */
+ /* was executed properly by the backend, PGresult */
+ /* contains the resulttuples */
+ PGRES_COPY_OUT,
+ PGRES_COPY_IN,
+ PGRES_BAD_RESPONSE, /* an unexpected response was recv'd from
+ * the backend */
+ PGRES_NONFATAL_ERROR,
+ PGRES_FATAL_ERROR
+
+ } ExecStatusType;
/* string descriptions of the ExecStatusTypes */
-extern const char* pgresStatus[];
+ extern const char *pgresStatus[];
-/*
- * POSTGRES backend dependent Constants.
+/*
+ * POSTGRES backend dependent Constants.
*/
/* ERROR_MSG_LENGTH should really be the same as ELOG_MAXLEN in utils/elog.h*/
@@ -60,236 +66,273 @@ extern const char* pgresStatus[];
/* ----------------
* PQArgBlock --
- * Information (pointer to array of this structure) required
- * for the PQfn() call.
+ * Information (pointer to array of this structure) required
+ * for the PQfn() call.
* ----------------
*/
-typedef struct {
- int len;
- int isint;
- union {
- int *ptr; /* can't use void (dec compiler barfs) */
- int integer;
- } u;
-} PQArgBlock;
-
-typedef struct pgresAttDesc {
- char* name; /* type name */
- Oid adtid; /* type id */
- short adtsize; /* type size */
-} PGresAttDesc;
+ typedef struct
+ {
+ int len;
+ int isint;
+ union
+ {
+ int *ptr;/* can't use void (dec compiler barfs) */
+ int integer;
+ } u;
+ } PQArgBlock;
+
+ typedef struct pgresAttDesc
+ {
+ char *name; /* type name */
+ Oid adtid; /* type id */
+ short adtsize;/* type size */
+ } PGresAttDesc;
/* use char* for Attribute values,
ASCII tuples are guaranteed to be null-terminated
For binary tuples, the first four bytes of the value is the size,
- and the bytes afterwards are the value. The binary value is
+ and the bytes afterwards are the value. The binary value is
not guaranteed to be null-terminated. In fact, it can have embedded nulls*/
-#define NULL_LEN (-1) /* pg_result len for NULL value */
-
-typedef struct pgresAttValue {
- int len; /* length in bytes of the value */
- char *value; /* actual value */
-} PGresAttValue;
-
-typedef struct pgNotify {
- char relname[NAMEDATALEN]; /* name of relation containing data */
- int be_pid; /* process id of backend */
-} PGnotify;
-
-typedef struct pgLobjfuncs {
- Oid fn_lo_open; /* OID of backend function lo_open */
- Oid fn_lo_close; /* OID of backend function lo_close */
- Oid fn_lo_creat; /* OID of backend function lo_creat */
- Oid fn_lo_unlink; /* OID of backend function lo_unlink */
- Oid fn_lo_lseek; /* OID of backend function lo_lseek */
- Oid fn_lo_tell; /* OID of backend function lo_tell */
- Oid fn_lo_read; /* OID of backend function LOread */
- Oid fn_lo_write; /* OID of backend function LOwrite */
-} PGlobjfuncs;
+#define NULL_LEN (-1) /* pg_result len for NULL value */
+
+ typedef struct pgresAttValue
+ {
+ int len; /* length in bytes of the value */
+ char *value; /* actual value */
+ } PGresAttValue;
+
+ typedef struct pgNotify
+ {
+ char relname[NAMEDATALEN]; /* name of relation
+ * containing data */
+ int be_pid; /* process id of backend */
+ } PGnotify;
+
+ typedef struct pgLobjfuncs
+ {
+ Oid fn_lo_open; /* OID of backend function lo_open */
+ Oid fn_lo_close; /* OID of backend function
+ * lo_close */
+ Oid fn_lo_creat; /* OID of backend function
+ * lo_creat */
+ Oid fn_lo_unlink; /* OID of backend function
+ * lo_unlink */
+ Oid fn_lo_lseek; /* OID of backend function
+ * lo_lseek */
+ Oid fn_lo_tell; /* OID of backend function lo_tell */
+ Oid fn_lo_read; /* OID of backend function LOread */
+ Oid fn_lo_write; /* OID of backend function LOwrite */
+ } PGlobjfuncs;
/* PGconn encapsulates a connection to the backend */
-typedef struct pg_conn{
- char *pghost; /* the machine on which the server is running */
- char *pgtty; /* tty on which the backend messages is displayed */
- char *pgport; /* the communication port with the backend */
- char *pgoptions; /* options to start the backend with */
- char *dbName; /* database name */
- ConnStatusType status;
- char errorMessage[ERROR_MSG_LENGTH];
- /* pipes for be/fe communication */
- FILE *Pfin;
- FILE *Pfout;
- FILE *Pfdebug;
- void *port; /* really a Port* */
- int asyncNotifyWaiting;
- Dllist* notifyList;
- char *pguser; /* Postgres username of user who is connected */
- char *pgpass;
- char *pgauth;
- PGlobjfuncs *lobjfuncs; /* Backend function OID's for large object access */
-} PGconn;
+ typedef struct pg_conn
+ {
+ char *pghost; /* the machine on which the server is
+ * running */
+ char *pgtty; /* tty on which the backend messages is
+ * displayed */
+ char *pgport; /* the communication port with the backend */
+ char *pgoptions; /* options to start the backend
+ * with */
+ char *dbName; /* database name */
+ ConnStatusType status;
+ char errorMessage[ERROR_MSG_LENGTH];
+ /* pipes for be/fe communication */
+ FILE *Pfin;
+ FILE *Pfout;
+ FILE *Pfdebug;
+ void *port; /* really a Port* */
+ int asyncNotifyWaiting;
+ Dllist *notifyList;
+ char *pguser; /* Postgres username of user who is
+ * connected */
+ char *pgpass;
+ char *pgauth;
+ PGlobjfuncs *lobjfuncs; /* Backend function OID's for
+ * large object access */
+ } PGconn;
#define CMDSTATUS_LEN 40
/* PGresult encapsulates the result of a query */
/* unlike the old libpq, we assume that queries only return in one group */
-typedef struct pg_result{
- int ntups;
- int numAttributes;
- PGresAttDesc *attDescs;
- PGresAttValue* *tuples; /* each PGresTuple is an array of PGresAttValue's */
- int tupArrSize; /* size of tuples array allocated */
- ExecStatusType resultStatus;
- char cmdStatus[CMDSTATUS_LEN]; /* cmd status from the last insert query*/
- int binary; /* binary tuple values if binary == 1, otherwise ASCII */
- PGconn* conn;
-} PGresult;
-
-typedef char pqbool;
- /* We can't use the conventional "bool", because we are designed to be
- included in a user's program, and user may already have that type
- defined. Pqbool, on the other hand, is unlikely to be used.
- */
-
-struct _PQprintOpt {
- pqbool header; /* print output field headings and row count */
- pqbool align; /* fill align the fields */
- pqbool standard; /* old brain dead format */
- pqbool html3; /* output html tables */
- pqbool expanded; /* expand tables */
- pqbool pager; /* use pager for output if needed */
- char *fieldSep; /* field separator */
- char *tableOpt; /* insert to HTML <table ...> */
- char *caption; /* HTML <caption> */
- char **fieldName; /* null terminated array of repalcement field names */
-};
-
-typedef struct _PQprintOpt PQprintOpt;
+ typedef struct pg_result
+ {
+ int ntups;
+ int numAttributes;
+ PGresAttDesc *attDescs;
+ PGresAttValue **tuples;/* each PGresTuple is an array of
+ * PGresAttValue's */
+ int tupArrSize; /* size of tuples array allocated */
+ ExecStatusType resultStatus;
+ char cmdStatus[CMDSTATUS_LEN]; /* cmd status from the
+ * last insert query */
+ int binary; /* binary tuple values if binary == 1,
+ * otherwise ASCII */
+ PGconn *conn;
+ } PGresult;
+
+ typedef char pqbool;
+
+ /*
+ * We can't use the conventional "bool", because we are designed to be
+ * included in a user's program, and user may already have that type
+ * defined. Pqbool, on the other hand, is unlikely to be used.
+ */
+
+ struct _PQprintOpt
+ {
+ pqbool header; /* print output field headings and row
+ * count */
+ pqbool align; /* fill align the fields */
+ pqbool standard; /* old brain dead format */
+ pqbool html3; /* output html tables */
+ pqbool expanded; /* expand tables */
+ pqbool pager; /* use pager for output if needed */
+ char *fieldSep; /* field separator */
+ char *tableOpt; /* insert to HTML <table ...> */
+ char *caption;/* HTML <caption> */
+ char **fieldName; /* null terminated array of
+ * repalcement field names */
+ };
+
+ typedef struct _PQprintOpt PQprintOpt;
/* ----------------
* Structure for the conninfo parameter definitions of PQconnectdb()
* ----------------
*/
-struct _PQconninfoOption {
- char *keyword; /* The keyword of the option */
- char *environ; /* Fallback environment variable name */
- char *compiled; /* Fallback compiled in default value */
- char *val; /* Options value */
- char *label; /* Label for field in connect dialog */
- char *dispchar; /* Character to display for this field */
- /* in a connect dialog. Values are: */
- /* "" Display entered value as is */
- /* "*" Password field - hide value */
- /* "D" Debug options - don't */
- /* create a field by default */
- int dispsize; /* Field size in characters for dialog */
-};
-
-typedef struct _PQconninfoOption PQconninfoOption;
-
-/* === in fe-connect.c === */
- /* make a new client connection to the backend */
-extern PGconn* PQconnectdb(const char* conninfo);
-extern PQconninfoOption *PQconndefaults(void);
-extern PGconn* PQsetdb(const char* pghost, const char* pgport, const char* pgoptions,
- const char* pgtty, const char* dbName);
- /* close the current connection and free the PGconn data structure */
-extern void PQfinish(PGconn* conn);
- /* close the current connection and restablish a new one with the same
- parameters */
-extern void PQreset(PGconn* conn);
-
-extern char* PQdb(PGconn* conn);
-extern char* PQuser(PGconn* conn);
-extern char* PQhost(PGconn* conn);
-extern char* PQoptions(PGconn* conn);
-extern char* PQport(PGconn* conn);
-extern char* PQtty(PGconn* conn);
-extern ConnStatusType PQstatus(PGconn* conn);
-extern char* PQerrorMessage(PGconn* conn);
-extern void PQtrace(PGconn *conn, FILE* debug_port);
-extern void PQuntrace(PGconn *conn);
+ struct _PQconninfoOption
+ {
+ char *keyword;/* The keyword of the option */
+ char *environ;/* Fallback environment variable name */
+ char *compiled; /* Fallback compiled in default
+ * value */
+ char *val; /* Options value */
+ char *label; /* Label for field in connect dialog */
+ char *dispchar; /* Character to display for this
+ * field */
+ /* in a connect dialog. Values are: */
+ /* "" Display entered value as is */
+ /* "*" Password field - hide value */
+ /* "D" Debug options - don't */
+ /* create a field by default */
+ int dispsize; /* Field size in characters for
+ * dialog */
+ };
+
+ typedef struct _PQconninfoOption PQconninfoOption;
+
+/* === in fe-connect.c === */
+ /* make a new client connection to the backend */
+ extern PGconn *PQconnectdb(const char *conninfo);
+ extern PQconninfoOption *PQconndefaults(void);
+ extern PGconn *PQsetdb(const char *pghost, const char *pgport, const char *pgoptions,
+ const char *pgtty, const char *dbName);
+ /* close the current connection and free the PGconn data structure */
+ extern void PQfinish(PGconn * conn);
+
+ /*
+ * close the current connection and restablish a new one with the same
+ * parameters
+ */
+ extern void PQreset(PGconn * conn);
+
+ extern char *PQdb(PGconn * conn);
+ extern char *PQuser(PGconn * conn);
+ extern char *PQhost(PGconn * conn);
+ extern char *PQoptions(PGconn * conn);
+ extern char *PQport(PGconn * conn);
+ extern char *PQtty(PGconn * conn);
+ extern ConnStatusType PQstatus(PGconn * conn);
+ extern char *PQerrorMessage(PGconn * conn);
+ extern void PQtrace(PGconn * conn, FILE * debug_port);
+ extern void PQuntrace(PGconn * conn);
/* === in fe-exec.c === */
-extern PGresult* PQexec(PGconn* conn, const char* query);
-extern int PQgetline(PGconn *conn, char* string, int length);
-extern int PQendcopy(PGconn *conn);
-extern void PQputline(PGconn *conn, const char* string);
-extern ExecStatusType PQresultStatus(PGresult* res);
-extern int PQntuples(PGresult *res);
-extern int PQnfields(PGresult *res);
-extern char* PQfname(PGresult *res, int field_num);
-extern int PQfnumber(PGresult *res, const char* field_name);
-extern Oid PQftype(PGresult *res, int field_num);
-extern short PQfsize(PGresult *res, int field_num);
-extern char* PQcmdStatus(PGresult *res);
-extern const char* PQoidStatus(PGresult *res);
-extern const char* PQcmdTuples(PGresult *res);
-extern char* PQgetvalue(PGresult *res, int tup_num, int field_num);
-extern int PQgetlength(PGresult *res, int tup_num, int field_num);
-extern int PQgetisnull(PGresult *res, int tup_num, int field_num);
-extern void PQclear(PGresult* res);
+ extern PGresult *PQexec(PGconn * conn, const char *query);
+ extern int PQgetline(PGconn * conn, char *string, int length);
+ extern int PQendcopy(PGconn * conn);
+ extern void PQputline(PGconn * conn, const char *string);
+ extern ExecStatusType PQresultStatus(PGresult * res);
+ extern int PQntuples(PGresult * res);
+ extern int PQnfields(PGresult * res);
+ extern char *PQfname(PGresult * res, int field_num);
+ extern int PQfnumber(PGresult * res, const char *field_name);
+ extern Oid PQftype(PGresult * res, int field_num);
+ extern short PQfsize(PGresult * res, int field_num);
+ extern char *PQcmdStatus(PGresult * res);
+ extern const char *PQoidStatus(PGresult * res);
+ extern const char *PQcmdTuples(PGresult * res);
+ extern char *PQgetvalue(PGresult * res, int tup_num, int field_num);
+ extern int PQgetlength(PGresult * res, int tup_num, int field_num);
+ extern int PQgetisnull(PGresult * res, int tup_num, int field_num);
+ extern void PQclear(PGresult * res);
/* PQdisplayTuples() is a better version of PQprintTuples() */
-extern void PQdisplayTuples(PGresult *res,
- FILE *fp, /* where to send the output */
- int fillAlign, /* pad the fields with spaces */
- const char *fieldSep, /* field separator */
- int printHeader, /* display headers? */
- int quiet);
-extern void PQprintTuples(PGresult* res,
- FILE* fout, /* output stream */
- int printAttName,/* print attribute names or not*/
- int terseOutput, /* delimiter bars or not?*/
- int width /* width of column,
- if 0, use variable width */
- );
-extern void PQprint(FILE* fout, /* output stream */
- PGresult* res,
- PQprintOpt *ps /* option structure */
- );
-extern PGnotify* PQnotifies(PGconn *conn);
-extern PGresult* PQfn(PGconn* conn,
- int fnid,
- int *result_buf,
- int *result_len,
- int result_is_int,
- PQArgBlock *args,
- int nargs);
+ extern void PQdisplayTuples(PGresult * res,
+ FILE * fp, /* where to send the
+ * output */
+ int fillAlign, /* pad the fields with
+ * spaces */
+ const char *fieldSep, /* field separator */
+ int printHeader, /* display headers? */
+ int quiet);
+ extern void PQprintTuples(PGresult * res,
+ FILE * fout, /* output stream */
+ int printAttName, /* print attribute names
+ * or not */
+ int terseOutput, /* delimiter bars or
+ * not? */
+ int width /* width of column, if
+ * 0, use variable width */
+ );
+ extern void PQprint(FILE * fout, /* output stream */
+ PGresult * res,
+ PQprintOpt * ps /* option structure */
+ );
+ extern PGnotify *PQnotifies(PGconn * conn);
+ extern PGresult *PQfn(PGconn * conn,
+ int fnid,
+ int *result_buf,
+ int *result_len,
+ int result_is_int,
+ PQArgBlock * args,
+ int nargs);
/* === in fe-auth.c === */
-extern MsgType fe_getauthsvc(char* PQerrormsg);
-extern void fe_setauthsvc(const char *name, char* PQerrormsg);
-extern char *fe_getauthname(char* PQerrormsg);
+ extern MsgType fe_getauthsvc(char *PQerrormsg);
+ extern void fe_setauthsvc(const char *name, char *PQerrormsg);
+ extern char *fe_getauthname(char *PQerrormsg);
/* === in fe-misc.c === */
/* pqGets and pqPuts gets and sends strings to the file stream
- returns 0 if successful
- if debug is non-null, debugging output is sent to that stream
+ returns 0 if successful
+ if debug is non-null, debugging output is sent to that stream
*/
-extern int pqGets(char* s, int maxlen, FILE* stream, FILE* debug);
-extern int pqGetnchar(char* s, int maxlen, FILE* stream, FILE* debug);
-extern int pqPutnchar(const char* s, int maxlen, FILE* stream, FILE* debug);
-extern int pqPuts(const char* s, FILE* stream, FILE* debug );
-extern int pqGetc(FILE* stream, FILE *debug);
+ extern int pqGets(char *s, int maxlen, FILE * stream, FILE * debug);
+ extern int pqGetnchar(char *s, int maxlen, FILE * stream, FILE * debug);
+ extern int pqPutnchar(const char *s, int maxlen, FILE * stream, FILE * debug);
+ extern int pqPuts(const char *s, FILE * stream, FILE * debug);
+ extern int pqGetc(FILE * stream, FILE * debug);
/* get a n-byte integer from the stream into result */
/* returns 0 if successful */
-extern int pqGetInt(int* result, int bytes, FILE* stream, FILE *debug );
+ extern int pqGetInt(int *result, int bytes, FILE * stream, FILE * debug);
/* put a n-byte integer into the stream */
/* returns 0 if successful */
-extern int pqPutInt(const int n, int bytes, FILE* stream, FILE *debug );
-extern void pqFlush(FILE* stream, FILE* debug);
+ extern int pqPutInt(const int n, int bytes, FILE * stream, FILE * debug);
+ extern void pqFlush(FILE * stream, FILE * debug);
/* === in fe-lobj.c === */
-int lo_open(PGconn* conn, Oid lobjId, int mode);
-int lo_close(PGconn *conn, int fd);
-int lo_read(PGconn *conn, int fd, char *buf, int len);
-int lo_write(PGconn *conn, int fd, char *buf, int len);
-int lo_lseek(PGconn *conn, int fd, int offset, int whence);
-Oid lo_creat(PGconn *conn, int mode);
-int lo_tell(PGconn *conn, int fd);
-int lo_unlink(PGconn *conn, Oid lobjId);
-Oid lo_import(PGconn *conn, char *filename);
-int lo_export(PGconn *conn, Oid lobjId, char *filename);
+ int lo_open(PGconn * conn, Oid lobjId, int mode);
+ int lo_close(PGconn * conn, int fd);
+ int lo_read(PGconn * conn, int fd, char *buf, int len);
+ int lo_write(PGconn * conn, int fd, char *buf, int len);
+ int lo_lseek(PGconn * conn, int fd, int offset, int whence);
+ Oid lo_creat(PGconn * conn, int mode);
+ int lo_tell(PGconn * conn, int fd);
+ int lo_unlink(PGconn * conn, Oid lobjId);
+ Oid lo_import(PGconn * conn, char *filename);
+ int lo_export(PGconn * conn, Oid lobjId, char *filename);
/* max length of message to send */
#define MAX_MESSAGE_LEN 8193
@@ -299,25 +342,25 @@ int lo_export(PGconn *conn, Oid lobjId, char *filename);
/* fall back options if they are not specified by arguments or defined
by environment variables */
-#define DefaultHost "localhost"
-#define DefaultTty ""
+#define DefaultHost "localhost"
+#define DefaultTty ""
#define DefaultOption ""
-#define DefaultAuthtype ""
-#define DefaultPassword ""
+#define DefaultAuthtype ""
+#define DefaultPassword ""
-typedef void *TUPLE;
+ typedef void *TUPLE;
#define palloc malloc
#define pfree free
#if defined(sunos4)
-extern char *sys_errlist[];
+ extern char *sys_errlist[];
#define strerror(A) (sys_errlist[(A)])
-#endif /* sunos4 */
+#endif /* sunos4 */
#ifdef __cplusplus
};
-#endif
-#endif /* LIBPQ_FE_H */
+#endif
+#endif /* LIBPQ_FE_H */
diff --git a/src/interfaces/libpq/pqsignal.c b/src/interfaces/libpq/pqsignal.c
index a177012051a..c004704ba45 100644
--- a/src/interfaces/libpq/pqsignal.c
+++ b/src/interfaces/libpq/pqsignal.c
@@ -1,18 +1,18 @@
/*-------------------------------------------------------------------------
*
* pqsignal.c--
- * reliable BSD-style signal(2) routine stolen from RWW who stole it
- * from Stevens...
+ * reliable BSD-style signal(2) routine stolen from RWW who stole it
+ * from Stevens...
*
* Copyright (c) 1994, Regents of the University of California
*
*
* IDENTIFICATION
- * $Header: /cvsroot/pgsql/src/interfaces/libpq/pqsignal.c,v 1.3 1996/12/26 22:08:30 momjian Exp $
+ * $Header: /cvsroot/pgsql/src/interfaces/libpq/pqsignal.c,v 1.4 1997/09/07 05:03:37 momjian Exp $
*
* NOTES
- * This shouldn't be in libpq, but the monitor and some other
- * things need it...
+ * This shouldn't be in libpq, but the monitor and some other
+ * things need it...
*
*-------------------------------------------------------------------------
*/
@@ -26,18 +26,20 @@ pqsigfunc
pqsignal(int signo, pqsigfunc func)
{
#if !defined(USE_POSIX_SIGNALS)
- return signal(signo, func);
+ return signal(signo, func);
#else
- struct sigaction act, oact;
-
- act.sa_handler = func;
- sigemptyset(&act.sa_mask);
- act.sa_flags = 0;
- if (signo != SIGALRM) {
- act.sa_flags |= SA_RESTART;
- }
- if (sigaction(signo, &act, &oact) < 0)
- return(SIG_ERR);
- return(oact.sa_handler);
-#endif /* !USE_POSIX_SIGNALS */
+ struct sigaction act,
+ oact;
+
+ act.sa_handler = func;
+ sigemptyset(&act.sa_mask);
+ act.sa_flags = 0;
+ if (signo != SIGALRM)
+ {
+ act.sa_flags |= SA_RESTART;
+ }
+ if (sigaction(signo, &act, &oact) < 0)
+ return (SIG_ERR);
+ return (oact.sa_handler);
+#endif /* !USE_POSIX_SIGNALS */
}
diff --git a/src/interfaces/libpq/pqsignal.h b/src/interfaces/libpq/pqsignal.h
index 4d57549443f..e2f6d7a973b 100644
--- a/src/interfaces/libpq/pqsignal.h
+++ b/src/interfaces/libpq/pqsignal.h
@@ -1,16 +1,16 @@
/*-------------------------------------------------------------------------
*
* pqsignal.h--
- * prototypes for the reliable BSD-style signal(2) routine.
+ * prototypes for the reliable BSD-style signal(2) routine.
*
*
* Copyright (c) 1994, Regents of the University of California
*
- * $Id: pqsignal.h,v 1.2 1996/12/26 22:08:34 momjian Exp $
+ * $Id: pqsignal.h,v 1.3 1997/09/07 05:03:39 momjian Exp $
*
* NOTES
- * This shouldn't be in libpq, but the monitor and some other
- * things need it...
+ * This shouldn't be in libpq, but the monitor and some other
+ * things need it...
*
*-------------------------------------------------------------------------
*/
@@ -19,8 +19,8 @@
#include "c.h"
-typedef void (*pqsigfunc)(int);
+typedef void (*pqsigfunc) (int);
extern pqsigfunc pqsignal(int signo, pqsigfunc func);
-#endif /* PQSIGNAL_H */
+#endif /* PQSIGNAL_H */