Commit 0e708e59 authored by Byron Nikolaidis's avatar Byron Nikolaidis

Update driver to official 6.30.0244 release.

parent 556e603b
......@@ -200,7 +200,12 @@ mylog("**** SQLBindCol: stmt = %u, icol = %d\n", stmt, icol);
// - - - - - - - - -
// Returns the description of a parameter marker.
// Returns the description of a parameter marker.
// This function is listed as not being supported by SQLGetFunctions() because it is
// used to describe "parameter markers" (not bound parameters), in which case,
// the dbms should return info on the markers. Since Postgres doesn't support that,
// it is best to say this function is not supported and let the application assume a
// data type (most likely varchar).
RETCODE SQL_API SQLDescribeParam(
HSTMT hstmt,
......@@ -223,6 +228,8 @@ StatementClass *stmt = (StatementClass *) hstmt;
ipar--;
// This implementation is not very good, since it is supposed to describe
// parameter markers, not bound parameters.
if(pfSqlType)
*pfSqlType = stmt->parameters[ipar].SQLType;
......@@ -252,25 +259,50 @@ RETCODE SQL_API SQLParamOptions(
// - - - - - - - - -
// Returns the number of parameters in an SQL statement
// This function should really talk to the dbms to determine the number of
// "parameter markers" (not bound parameters) in the statement. But, since
// Postgres doesn't support that, the driver should just count the number of markers
// and return that. The reason the driver just can't say this function is unsupported
// like it does for SQLDescribeParam is that some applications don't care and try
// to call it anyway.
// If the statement does not have parameters, it should just return 0.
RETCODE SQL_API SQLNumParams(
HSTMT hstmt,
SWORD FAR *pcpar)
{
StatementClass *stmt = (StatementClass *) hstmt;
char in_quote = FALSE;
unsigned int i;
if(!stmt)
return SQL_INVALID_HANDLE;
// If the statement does not have parameters, it should just return 0.
if (pcpar)
*pcpar = 0;
else
return SQL_ERROR;
if (pcpar) {
*pcpar = stmt->parameters_allocated;
}
return SQL_SUCCESS;
if(!stmt->statement) {
// no statement has been allocated
stmt->errormsg = "SQLNumParams called with no statement ready.";
stmt->errornumber = STMT_SEQUENCE_ERROR;
return SQL_ERROR;
} else {
for(i=0; i < strlen(stmt->statement); i++) {
if(stmt->statement[i] == '?' && !in_quote)
(*pcpar)++;
else {
if (stmt->statement[i] == '\'')
in_quote = (in_quote ? FALSE : TRUE);
}
}
return SQL_SUCCESS;
}
}
/********************************************************************
......
......@@ -365,7 +365,12 @@ struct tm *tim;
// truncate the data.
// return COPY_RESULT_TRUNCATED;
*pcbValue = cbValueMax -1;
// LongVarBinary types do handle truncated multiple get calls
// through convert_lo().
if (pcbValue)
*pcbValue = cbValueMax -1;
return COPY_OK;
} else {
......
......@@ -623,6 +623,15 @@ char temp[128];
globals.unknown_sizes = atoi(temp);
// Lie about supported functions?
SQLGetPrivateProfileString(DBMS_NAME, INI_LIE, "",
temp, sizeof(temp), ODBCINST_INI);
if ( temp[0] == '\0')
globals.lie = DEFAULT_LIE;
else
globals.lie = atoi(temp);
// Readonly is stored in the driver section AND per datasource
SQLGetPrivateProfileString(DBMS_NAME, INI_READONLY, "",
temp, sizeof(temp), ODBCINST_INI);
......
......@@ -56,6 +56,7 @@
#define INI_FAKEOIDINDEX "FakeOidIndex"
#define INI_SHOWOIDCOLUMN "ShowOidColumn"
#define INI_SHOWSYSTEMTABLES "ShowSystemTables"
#define INI_LIE "Lie"
#define INI_EXTRASYSTABLEPREFIXES "ExtraSysTablePrefixes"
/* Connection Defaults */
......@@ -74,6 +75,7 @@
#define DEFAULT_FAKEOIDINDEX 0
#define DEFAULT_SHOWOIDCOLUMN 0
#define DEFAULT_SHOWSYSTEMTABLES 0 // dont show system tables
#define DEFAULT_LIE 0
#define DEFAULT_EXTRASYSTABLEPREFIXES "dd_;"
......
This diff is collapsed.
/* Module: lobj.c
*
* Description: This module contains routines related to manipulating
* large objects.
*
* Classes: none
*
* API functions: none
*
* Comments: See "notice.txt" for copyright and license information.
*
*/
#include "lobj.h"
#include "psqlodbc.h"
#include "connection.h"
Oid
lo_creat(ConnectionClass *conn, int mode)
{
LO_ARG argv[1];
int retval, result_len;
argv[0].isint = 1;
argv[0].len = 4;
argv[0].u.integer = mode;
if ( ! CC_send_function(conn, LO_CREAT, &retval, &result_len, 1, argv, 1))
return 0; // invalid oid
else
return retval;
}
int
lo_open(ConnectionClass *conn, int lobjId, int mode)
{
int fd;
int result_len;
LO_ARG argv[2];
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 ( ! CC_send_function(conn, LO_OPEN, &fd, &result_len, 1, argv, 2))
return -1;
if (fd >= 0 && lo_lseek(conn, fd, 0L, SEEK_SET) < 0)
return -1;
return fd;
}
int
lo_close(ConnectionClass *conn, int fd)
{
LO_ARG argv[1];
int retval, result_len;
argv[0].isint = 1;
argv[0].len = 4;
argv[0].u.integer = fd;
if ( ! CC_send_function(conn, LO_CLOSE, &retval, &result_len, 1, argv, 1))
return -1;
else
return retval;
}
int
lo_read(ConnectionClass *conn, int fd, char *buf, int len)
{
LO_ARG argv[2];
int result_len;
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;
if ( ! CC_send_function(conn, LO_READ, (int *) buf, &result_len, 0, argv, 2))
return -1;
else
return result_len;
}
int
lo_write(ConnectionClass *conn, int fd, char *buf, int len)
{
LO_ARG argv[2];
int retval, result_len;
if (len <= 0)
return 0;
argv[0].isint = 1;
argv[0].len = 4;
argv[0].u.integer = fd;
argv[1].isint = 0;
argv[1].len = len;
argv[1].u.ptr = (char *) buf;
if ( ! CC_send_function(conn, LO_WRITE, &retval, &result_len, 1, argv, 2))
return -1;
else
return retval;
}
int
lo_lseek(ConnectionClass *conn, int fd, int offset, int whence)
{
LO_ARG argv[3];
int retval, result_len;
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;
if ( ! CC_send_function(conn, LO_LSEEK, &retval, &result_len, 1, argv, 3))
return -1;
else
return retval;
}
int
lo_tell(ConnectionClass *conn, int fd)
{
LO_ARG argv[1];
int retval, result_len;
argv[0].isint = 1;
argv[0].len = 4;
argv[0].u.integer = fd;
if ( ! CC_send_function(conn, LO_TELL, &retval, &result_len, 1, argv, 1))
return -1;
else
return retval;
}
int
lo_unlink(ConnectionClass *conn, Oid lobjId)
{
LO_ARG argv[1];
int retval, result_len;
argv[0].isint = 1;
argv[0].len = 4;
argv[0].u.integer = lobjId;
if ( ! CC_send_function(conn, LO_UNLINK, &retval, &result_len, 1, argv, 1))
return -1;
else
return retval;
}
/* File: lobj.h
*
* Description: See "lobj.c"
*
* Comments: See "notice.txt" for copyright and license information.
*
*/
#ifndef __LOBJ_H__
#define __LOBJ_H__
#include "psqlodbc.h"
typedef struct lo_arg {
int isint;
int len;
union
{
int integer;
char *ptr;
} u;
};
#define LO_CREAT 957
#define LO_OPEN 952
#define LO_CLOSE 953
#define LO_READ 954
#define LO_WRITE 955
#define LO_LSEEK 956
#define LO_TELL 958
#define LO_UNLINK 964
#define INV_WRITE 0x00020000
#define INV_READ 0x00040000
Oid lo_creat(ConnectionClass *conn, int mode);
int lo_open(ConnectionClass *conn, int lobjId, int mode);
int lo_close(ConnectionClass *conn, int fd);
int lo_read(ConnectionClass *conn, int fd, char *buf, int len);
int lo_write(ConnectionClass *conn, int fd, char *buf, int len);
int lo_lseek(ConnectionClass *conn, int fd, int offset, int len);
int lo_tell(ConnectionClass *conn, int fd);
int lo_unlink(ConnectionClass *conn, Oid lobjId);
#endif
......@@ -163,14 +163,28 @@ char changed = FALSE;
break;
case SQL_KEYSET_SIZE:
mylog("SetStmtOption(): SQL_KEYSET_SIZE = %d\n", vParam);
if (globals.lie)
stmt->keyset_size = vParam;
else {
stmt->errornumber = STMT_NOT_IMPLEMENTED_ERROR;
stmt->errormsg = "Driver does not support keyset size option";
return SQL_ERROR;
}
break;
case SQL_CONCURRENCY:
// positioned update isn't supported so cursor concurrency is read-only
mylog("SetStmtOption(): SQL_CONCURRENCY = %d\n", vParam);
stmt->scroll_concurrency = SQL_CONCUR_READ_ONLY;
if (vParam != SQL_CONCUR_READ_ONLY)
changed = TRUE;
if (globals.lie)
stmt->scroll_concurrency = vParam;
else {
stmt->scroll_concurrency = SQL_CONCUR_READ_ONLY;
if (vParam != SQL_CONCUR_READ_ONLY)
changed = TRUE;
}
break;
case SQL_CURSOR_TYPE:
......@@ -178,25 +192,28 @@ char changed = FALSE;
// otherwise, it can only be forward or static.
mylog("SetStmtOption(): SQL_CURSOR_TYPE = %d\n", vParam);
if (globals.use_declarefetch) {
stmt->cursor_type = SQL_CURSOR_FORWARD_ONLY;
if (vParam != SQL_CURSOR_FORWARD_ONLY)
changed = TRUE;
}
if (globals.lie)
stmt->cursor_type = vParam;
else {
if (vParam == SQL_CURSOR_FORWARD_ONLY || vParam == SQL_CURSOR_STATIC)
stmt->cursor_type = vParam; // valid type
if (globals.use_declarefetch) {
stmt->cursor_type = SQL_CURSOR_FORWARD_ONLY;
if (vParam != SQL_CURSOR_FORWARD_ONLY)
changed = TRUE;
}
else {
stmt->cursor_type = SQL_CURSOR_STATIC;
changed = TRUE;
if (vParam == SQL_CURSOR_FORWARD_ONLY || vParam == SQL_CURSOR_STATIC)
stmt->cursor_type = vParam; // valid type
else {
stmt->cursor_type = SQL_CURSOR_STATIC;
changed = TRUE;
}
}
}
break;
case SQL_SIMULATE_CURSOR:
stmt->errornumber = STMT_NOT_IMPLEMENTED_ERROR;
stmt->errormsg = "Simulated positioned update/delete not supported";
stmt->errormsg = "Simulated positioned update/delete not supported. Use the cursor library.";
return SQL_ERROR;
default:
......@@ -254,6 +271,11 @@ StatementClass *stmt = (StatementClass *) hstmt;
*((SDWORD *)pvParam) = stmt->rowset_size;
break;
case SQL_KEYSET_SIZE:
mylog("GetStmtOption(): SQL_KEYSET_SIZE\n");
*((SDWORD *)pvParam) = stmt->keyset_size;
break;
case SQL_CONCURRENCY:
mylog("GetStmtOption(): SQL_CONCURRENCY\n");
*((SDWORD *)pvParam) = stmt->scroll_concurrency;
......@@ -266,7 +288,7 @@ StatementClass *stmt = (StatementClass *) hstmt;
case SQL_SIMULATE_CURSOR:
stmt->errornumber = STMT_NOT_IMPLEMENTED_ERROR;
stmt->errormsg = "Simulated positioned update/delete not supported";
stmt->errormsg = "Simulated positioned update/delete not supported. Use the cursor library.";
return SQL_ERROR;
default:
......
......@@ -88,6 +88,7 @@ typedef struct GlobalValues_
char text_as_longvarchar;
char unknowns_as_longvarchar;
char bools_as_char;
char lie;
char extra_systable_prefixes[MEDIUM_REGISTRY_LEN];
char conn_settings[LARGE_REGISTRY_LEN];
} GLOBAL_VALUES;
......
......@@ -151,6 +151,7 @@ StatementClass *rv;
rv->status = STMT_ALLOCATED;
rv->maxRows = 0; // driver returns all rows
rv->rowset_size = 1;
rv->keyset_size = 0; // fully keyset driven is the default
rv->scroll_concurrency = SQL_CONCUR_READ_ONLY;
rv->cursor_type = SQL_CURSOR_FORWARD_ONLY;
rv->errormsg = NULL;
......
......@@ -77,6 +77,7 @@ struct StatementClass_ {
int errornumber;
int maxRows;
int rowset_size;
int keyset_size;
int cursor_type;
int scroll_concurrency;
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment