From d88ed1c5b846f6d829411929de9acbc8d83b9933 Mon Sep 17 00:00:00 2001 From: eknauel Date: Thu, 25 Apr 2002 08:51:11 +0000 Subject: [PATCH] - fixed silly +1/-1 offset bug in odbc_sql_bin_parameter_exec_out - fixed matching of SQL types in odbc_sql_bin_parameter_exec_out - added new functions for sql-time<->SQL_TIME_STRUCT conversion - added new functions for sql-date<->SQL_DATE_STRUCT conversion - added new functions for sql-timestamp<->SQL_TIMESTAMP_STRUCT conversion - use functions for sql-time/sql-date/sql-timestamp conversion - print more debug information in odbc_sql_bin_parameter_exec_out - added function odbc_sql_execute_direct - added function odbc_sql_get_data, check_sql_get_data_result - added function odbc_sql_fetch - odbc_debug_msgs: do not print native_error - renamed function odbc_set_env_attr to odbc_sql_set_env_attr --- scsh/odbc/odbc.c | 424 +++++++++++++++++++++++++++++++++++++++-------- scsh/odbc/odbc.h | 46 ++++- 2 files changed, 399 insertions(+), 71 deletions(-) diff --git a/scsh/odbc/odbc.c b/scsh/odbc/odbc.c index 017d384..bf63935 100644 --- a/scsh/odbc/odbc.c +++ b/scsh/odbc/odbc.c @@ -1109,49 +1109,52 @@ s48_value odbc_sql_bind_parameter_exec_out(s48_value stmt_handle, SQLRETURN retval; unsigned int i; + ODBC_DEBUG_PRINTF("odbc_sql_bind_parameter_exec_out\n"); sh = (SQLHSTMT) s48_extract_integer(stmt_handle); /* bind parameters */ - for (i = 1; i < S48_VECTOR_LENGTH(param_vals); i++) { + for (i = 0; i < S48_VECTOR_LENGTH(param_vals); i++) { + + ODBC_DEBUG_PRINTF_ARG1("Binding parameter %d", i); value_type = (SQLSMALLINT) s48_extract_integer(S48_CAR(S48_CDR(S48_VECTOR_REF(param_vals, i)))); param_type = (SQLSMALLINT) s48_extract_integer(S48_CDR(S48_CDR(S48_VECTOR_REF(param_vals, i)))); - + switch (value_type) { case SQL_C_CHAR: case SQL_C_BINARY: - { + { SQLCHAR *value; SQLUINTEGER val_len; - + + ODBC_DEBUG_PRINTF("value_type is string\n"); value = (SQLCHAR *) s48_extract_string(S48_CAR(S48_VECTOR_REF(param_vals, i))); val_len = (SQLUINTEGER) S48_STRING_LENGTH(S48_CAR(S48_VECTOR_REF(param_vals, i))); - retval = SQLBindParameter(sh, (SQLUSMALLINT) i, + retval = SQLBindParameter(sh, (SQLUSMALLINT) (i+1), SQL_PARAM_OUTPUT, value_type, param_type, val_len, 0, value, 0, (void *)SQL_NTS); break; } - case SQL_C_SSHORT: - case SQL_C_USHORT: - case SQL_C_SLONG: - case SQL_C_ULONG: + case SQL_C_SHORT: + case SQL_C_LONG: { SQLINTEGER value; SQLINTEGER cb_val; + ODBC_DEBUG_PRINTF("value_type integer\n"); cb_val = 0; value = (SQLINTEGER) s48_extract_integer(S48_CAR(S48_VECTOR_REF(param_vals, i))); - retval = SQLBindParameter(sh, (SQLUSMALLINT) i, + retval = SQLBindParameter(sh, (SQLUSMALLINT) (i+1), SQL_PARAM_OUTPUT, value_type, param_type, 0, 0, @@ -1169,7 +1172,7 @@ s48_value odbc_sql_bind_parameter_exec_out(s48_value stmt_handle, value = (SQLCHAR) s48_extract_char(S48_CAR(S48_VECTOR_REF(param_vals, i))); - retval = SQLBindParameter(sh, (SQLUSMALLINT) i, + retval = SQLBindParameter(sh, (SQLUSMALLINT) (i+1), SQL_PARAM_OUTPUT, value_type, param_type, 0, 0, @@ -1181,11 +1184,12 @@ s48_value odbc_sql_bind_parameter_exec_out(s48_value stmt_handle, SQLREAL value; SQLINTEGER cb_val; + ODBC_DEBUG_PRINTF("value_type is float\n"); cb_val = 0; value = (SQLREAL) S48_UNSAFE_EXTRACT_DOUBLE(S48_CAR(S48_VECTOR_REF(param_vals, i))); - retval = SQLBindParameter(sh, (SQLUSMALLINT) i, + retval = SQLBindParameter(sh, (SQLUSMALLINT) (i+1), SQL_PARAM_OUTPUT, value_type, param_type, 0, 0, @@ -1197,11 +1201,12 @@ s48_value odbc_sql_bind_parameter_exec_out(s48_value stmt_handle, SQLDOUBLE value; SQLINTEGER cb_val; + ODBC_DEBUG_PRINTF("value_type is double\n"); cb_val = 0; value = (SQLDOUBLE) S48_UNSAFE_EXTRACT_DOUBLE(S48_CAR(S48_VECTOR_REF(param_vals, i))); - retval = SQLBindParameter(sh, (SQLUSMALLINT) i, + retval = SQLBindParameter(sh, (SQLUSMALLINT) (i+1), SQL_PARAM_OUTPUT, value_type, param_type, 0, 0, @@ -1213,20 +1218,11 @@ s48_value odbc_sql_bind_parameter_exec_out(s48_value stmt_handle, SQL_DATE_STRUCT value; SQLINTEGER cb_val; + ODBC_DEBUG_PRINTF("value_type is date\n"); cb_val = 0; - value.year = (SQLSMALLINT) - s48_extract_integer(S48_RECORD_REF(S48_CAR(S48_VECTOR_REF(param_vals, i)), - SR_SQL_DATE_YEAR)); + sql_date_record_to_struct(param_vals, &value); - value.month = (SQLUSMALLINT) - s48_extract_integer(S48_RECORD_REF(S48_CAR(S48_VECTOR_REF(param_vals, i)), - SR_SQL_DATE_MONTH)); - - value.day = (SQLUSMALLINT) - s48_extract_integer(S48_RECORD_REF(S48_CAR(S48_VECTOR_REF(param_vals, i)), - SR_SQL_DATE_DAY)); - - retval = SQLBindParameter(sh, (SQLUSMALLINT) i, + retval = SQLBindParameter(sh, (SQLUSMALLINT) (i+1), SQL_PARAM_OUTPUT, value_type, param_type, 0, 0, @@ -1238,20 +1234,11 @@ s48_value odbc_sql_bind_parameter_exec_out(s48_value stmt_handle, SQL_TIME_STRUCT value; SQLINTEGER cb_val; + ODBC_DEBUG_PRINTF("value_type is time\n"); cb_val = 0; - value.hour = (SQLSMALLINT) - s48_extract_integer(S48_RECORD_REF(S48_CAR(S48_VECTOR_REF(param_vals, i)), - SR_SQL_TIME_HOUR)); + sql_time_record_to_struct(param_vals, &value); - value.minute = (SQLSMALLINT) - s48_extract_integer(S48_RECORD_REF(S48_CAR(S48_VECTOR_REF(param_vals, i)), - SR_SQL_TIME_MINUTE)); - - value.second = (SQLSMALLINT) - s48_extract_integer(S48_RECORD_REF(S48_CAR(S48_VECTOR_REF(param_vals, i)), - SR_SQL_TIME_SECOND)); - - retval = SQLBindParameter(sh, (SQLUSMALLINT) i, + retval = SQLBindParameter(sh, (SQLUSMALLINT) (i+1), SQL_PARAM_OUTPUT, value_type, param_type, 0, 0, @@ -1263,36 +1250,11 @@ s48_value odbc_sql_bind_parameter_exec_out(s48_value stmt_handle, SQL_TIMESTAMP_STRUCT value; SQLINTEGER cb_val; + ODBC_DEBUG_PRINTF("value_type is timestamp\n"); cb_val = 0; - value.year = (SQLSMALLINT) - s48_extract_integer(S48_RECORD_REF(S48_CAR(S48_VECTOR_REF(param_vals, i)), - SR_SQL_TIMESTAMP_YEAR)); + sql_timestamp_record_to_struct(param_vals, &value); - value.month = (SQLUSMALLINT) - s48_extract_integer(S48_RECORD_REF(S48_CAR(S48_VECTOR_REF(param_vals, i)), - SR_SQL_TIMESTAMP_MONTH)); - - value.day = (SQLUSMALLINT) - s48_extract_integer(S48_RECORD_REF(S48_CAR(S48_VECTOR_REF(param_vals, i)), - SR_SQL_TIMESTAMP_DAY)); - - value.hour = (SQLUSMALLINT) - s48_extract_integer(S48_RECORD_REF(S48_CAR(S48_VECTOR_REF(param_vals, i)), - SR_SQL_TIMESTAMP_HOUR)); - - value.minute = (SQLUSMALLINT) - s48_extract_integer(S48_RECORD_REF(S48_CAR(S48_VECTOR_REF(param_vals, i)), - SR_SQL_TIMESTAMP_MINUTE)); - - value.second = (SQLUSMALLINT) - s48_extract_integer(S48_RECORD_REF(S48_CAR(S48_VECTOR_REF(param_vals, i)), - SR_SQL_TIMESTAMP_SECOND)); - - value.fraction = (SQLUINTEGER) - s48_extract_integer(S48_RECORD_REF(S48_CAR(S48_VECTOR_REF(param_vals, i)), - SR_SQL_TIMESTAMP_FRACTION)); - - retval = SQLBindParameter(sh, (SQLUSMALLINT) i, + retval = SQLBindParameter(sh, (SQLUSMALLINT) (i+1), SQL_PARAM_OUTPUT, value_type, param_type, 0, 0, @@ -1328,6 +1290,8 @@ s48_value odbc_sql_bind_parameter_exec_out(s48_value stmt_handle, } } + ODBC_DEBUG_PRINTF("All parameters bound\n"); + /* check the return value of SQLBindParameter */ if (retval != SQL_SUCCESS) { switch (retval) @@ -1352,6 +1316,8 @@ s48_value odbc_sql_bind_parameter_exec_out(s48_value stmt_handle, } } /* for */ + ODBC_DEBUG_PRINTF("Executing statement\n"); + /* execute statement */ retval = SQLExecute(sh); @@ -1402,6 +1368,8 @@ s48_value odbc_sql_execute(s48_value stmt_handle) SQLHSTMT sh; SQLRETURN retval; + ODBC_DEBUG_PRINTF("odbc_sql_execute\n"); + sh = (SQLHSTMT) s48_extract_integer(stmt_handle); retval = SQLExecute(sh); @@ -1436,6 +1404,63 @@ s48_value odbc_sql_execute(s48_value stmt_handle) } } +s48_value odbc_sql_execute_direct(s48_value stmt_handle, + s48_value stmt) +{ + + SQLHSTMT sh; + SQLCHAR *query; + SQLRETURN retval; + + ODBC_DEBUG_PRINTF("odbc_sql_execute_direct\n"); + + sh = (SQLHSTMT) s48_extract_integer(stmt_handle); + query = (SQLCHAR *) s48_extract_string(stmt); + + retval = SQLExecDirect(sh, query, S48_STRING_LENGTH(stmt)); + + switch (retval) + { + case SQL_SUCCESS: + { + return S48_TRUE; + } + case SQL_SUCCESS_WITH_INFO: + { + ODBC_DEBUG_DIAGREC(SQL_HANDLE_STMT, sh); + return S48_TRUE; + } + case SQL_ERROR: + { + ODBC_DEBUG_DIAGREC(SQL_HANDLE_STMT, sh); + ODBC_RAISE_EXCEPTION("SQLExecDirect returned SQL_ERROR"); + break; + } + case SQL_NEED_DATA: + { + return SQL_NEED_DATA; + } + case SQL_STILL_EXECUTING: + { + ODBC_RAISE_EXCEPTION("SQLExecDirect returned SQL_STILL_EXECUTING, not implemented yet"); + break; + } + case SQL_NO_DATA: + { + return SQL_NO_DATA; + } + case SQL_INVALID_HANDLE: + { + ODBC_RAISE_EXCEPTION("SQLExecDirect got invalid handle"); + break; + } + default: + { + ODBC_RAISE_EXCEPTION("SQLExecDirect returned unknown error code"); + break; + } + } +} /* * @@ -1445,6 +1470,143 @@ s48_value odbc_sql_execute(s48_value stmt_handle) * */ +s48_value odbc_sql_get_data(s48_value stmt_handle, + s48_value column_number, + s48_value target_type) +{ + + SQLHSTMT sh; + SQLUSMALLINT cn; + SQLSMALLINT tt; + SQLRETURN retval; + + ODBC_DEBUG_PRINTF("odbc_sql_get_data\n"); + + sh = (SQLHSTMT) s48_extract_integer(stmt_handle); + cn = (SQLUSMALLINT) s48_extract_integer(column_number); + tt = (SQLSMALLINT) s48_extract_integer(target_type); + + + switch (tt) + { + case SQL_C_CHAR: + case SQL_C_BINARY: + { + SQLCHAR str[ODBC_GET_DATA_MAX_STR_LEN]; + SQLINTEGER str_len; + + retval = SQLGetData(sh, cn, tt, + str, ODBC_GET_DATA_MAX_STR_LEN-1, + &str_len); + check_sql_get_data_result(retval, sh); + return s48_enter_string((char *) str); + } + case SQL_C_SSHORT: + case SQL_C_USHORT: + case SQL_C_SLONG: + case SQL_C_ULONG: + { + long int i; + SQLINTEGER rest; + + retval = SQLGetData(sh, cn, tt, + &i, sizeof(long int), &rest); + check_sql_get_data_result(retval, sh); + return s48_enter_integer(i); + } + } +} + +void check_sql_get_data_result(SQLRETURN retval, SQLHSTMT stmt_handle) +{ + + switch (retval) + { + case SQL_SUCCESS: + { + return; + } + case SQL_SUCCESS_WITH_INFO: + { + ODBC_DEBUG_DIAGREC(SQL_HANDLE_STMT, stmt_handle); + return; + } + case SQL_NO_DATA: + { + ODBC_DEBUG_DIAGREC(SQL_HANDLE_STMT, stmt_handle); + ODBC_RAISE_EXCEPTION("SQLGetData returned SQL_NO_DATA"); + break; + } + case SQL_STILL_EXECUTING: + { + ODBC_RAISE_EXCEPTION("SQLGetData returned SQL_STILL_EXECUTING, not yet implemented"); + break; + } + case SQL_ERROR: + { + ODBC_DEBUG_DIAGREC(SQL_HANDLE_STMT, stmt_handle); + ODBC_RAISE_EXCEPTION("SQLGetData returned SQL_ERROR"); + break; + } + case SQL_INVALID_HANDLE: + { + ODBC_RAISE_EXCEPTION("SQLGetData got invalid handle"); + break; + } + } +} + +s48_value odbc_sql_fetch(s48_value stmt_handle) +{ + + SQLHSTMT sh; + SQLRETURN retval; + + ODBC_DEBUG_PRINTF("odbc_sql_fetch\n"); + + sh = (SQLHSTMT) s48_extract_integer(stmt_handle); + + retval = SQLFetch(sh); + + switch (retval) + { + case SQL_SUCCESS: + { + return S48_TRUE; + } + case SQL_SUCCESS_WITH_INFO: + { + ODBC_DEBUG_DIAGREC(SQL_HANDLE_STMT, sh); + return S48_TRUE; + } + case SQL_NO_DATA: + { + return SQL_NO_DATA; + } + case SQL_STILL_EXECUTING: + { + ODBC_RAISE_EXCEPTION("SQLFetch returned SQL_STILL_EXECUTING, not yet implemented"); + break; + } + case SQL_ERROR: + { + ODBC_DEBUG_DIAGREC(SQL_HANDLE_STMT, sh); + ODBC_RAISE_EXCEPTION("SQLFetch returned SQL_ERROR"); + break; + } + case SQL_INVALID_HANDLE: + { + ODBC_RAISE_EXCEPTION("SQLFetch got invalid handle"); + break; + } + default: + { + ODBC_RAISE_EXCEPTION("SQLFetch returned unknown error code"); + break; + } + } +} + /* * * PART 8 @@ -1703,8 +1865,8 @@ void odbc_debug_msgs(SQLSMALLINT handle_type, SQLHANDLE handle) retval = SQLGetDiagRec(handle_type, handle, i, sql_state, - native_error, - message, ERROR_MSG_BUFFER_LEN, + &native_error, + message, ERROR_MSG_BUFFER_LEN-1, &message_len); if (retval == SQL_NO_DATA) @@ -1726,17 +1888,136 @@ void odbc_debug_msgs(SQLSMALLINT handle_type, SQLHANDLE handle) if (retval == SQL_SUCCESS) { printf("\nODBC status record %d:\n", i); printf("SQL state: %s\n", (char *)sql_state); - printf("native error msg: %s\n", (char *)native_error); - printf("error msg: %s\n", message); + /* TODO: + * Need to find out how to printf the + * native_error here + */ + printf("error msg: %s\n", message); } i++; } } #endif + +/* convert Scheme sql-date record to SQL_DATE_STRUCT */ +void sql_date_record_to_struct(s48_value sql_date, SQL_DATE_STRUCT *ds) +{ + ds->year = (SQLSMALLINT) + s48_extract_integer(S48_RECORD_REF(sql_date, SR_SQL_DATE_YEAR)); + ds->month = (SQLUSMALLINT) + s48_extract_integer(S48_RECORD_REF(sql_date, SR_SQL_DATE_MONTH)); + ds->day = (SQLUSMALLINT) + s48_extract_integer(S48_RECORD_REF(sql_date, SR_SQL_DATE_DAY)); +} +/* convert SQL_DATE_STRUCT to Scheme sql-date record */ +s48_value struct_to_sql_date_record(SQL_DATE_STRUCT *ds) +{ + s48_value sql_date; + + sql_date = s48_make_record(sql_date_record_type); + + S48_RECORD_SET(sql_date, SR_SQL_DATE_YEAR, + s48_enter_integer(ds->year)); + S48_RECORD_SET(sql_date, SR_SQL_DATE_MONTH, + s48_enter_integer(ds->month)); + S48_RECORD_SET(sql_date, SR_SQL_DATE_DAY, + s48_enter_integer(ds->day)); + + return sql_date; +} + +/* convert Scheme sql-time record to SQL_TIME_STRUCT */ +void sql_time_record_to_struct(s48_value sql_time, SQL_TIME_STRUCT *ts) +{ + ts->hour = (SQLUSMALLINT) + s48_extract_integer(S48_RECORD_REF(sql_time, SR_SQL_TIME_HOUR)); + + ts->minute = (SQLUSMALLINT) + s48_extract_integer(S48_RECORD_REF(sql_time, SR_SQL_TIME_MINUTE)); + + ts->second = (SQLUSMALLINT) + s48_extract_integer(S48_RECORD_REF(sql_time, SR_SQL_TIME_SECOND)); +} + +/* convert SQL_TIME_STRUCT to Scheme sql-time record */ +s48_value struct_to_sql_time_record(SQL_TIME_STRUCT *ts) +{ + s48_value sql_time; + + sql_time = s48_make_record(sql_time_record_type); + + S48_RECORD_SET(sql_time, SR_SQL_TIME_HOUR, + s48_extract_integer(ts->hour)); + + S48_RECORD_SET(sql_time, SR_SQL_TIME_MINUTE, + s48_extract_integer(ts->minute)); + + S48_RECORD_SET(sql_time, SR_SQL_TIME_SECOND, + s48_extract_integer(ts->second)); + + return sql_time; +} + +/* convert Scheme sql-timestamp record to SQL_TIMESTAMP_STRUCT */ +void sql_timestamp_record_to_struct(s48_value sql_timestamp, + SQL_TIMESTAMP_STRUCT *ts) +{ + ts->year = (SQLSMALLINT) + s48_extract_integer(S48_RECORD_REF(sql_timestamp, SR_SQL_TIMESTAMP_YEAR)); + + ts->month = (SQLUSMALLINT) + s48_extract_integer(S48_RECORD_REF(sql_timestamp, SR_SQL_TIMESTAMP_MONTH)); + + ts->day = (SQLUSMALLINT) + s48_extract_integer(S48_RECORD_REF(sql_timestamp, SR_SQL_TIMESTAMP_DAY)); + + ts->hour = (SQLUSMALLINT) + s48_extract_integer(S48_RECORD_REF(sql_timestamp, SR_SQL_TIMESTAMP_HOUR)); + + ts->minute = (SQLUSMALLINT) + s48_extract_integer(S48_RECORD_REF(sql_timestamp, SR_SQL_TIMESTAMP_MINUTE)); + + ts->second = (SQLUSMALLINT) + s48_extract_integer(S48_RECORD_REF(sql_timestamp, SR_SQL_TIMESTAMP_SECOND)); + + ts->fraction = (SQLUINTEGER) + s48_extract_integer(S48_RECORD_REF(sql_timestamp, SR_SQL_TIMESTAMP_FRACTION)); +} + +/* convert SQL_TIMESTAMP_STRUCT to Scheme sql-timestamp record */ +s48_value struct_to_sql_timestamp_record(SQL_TIMESTAMP_STRUCT *ts) +{ + s48_value sql_timestamp; + + sql_timestamp = s48_make_record(sql_timestamp_record_type); + + S48_RECORD_SET(sql_timestamp, SR_SQL_TIMESTAMP_YEAR, + s48_extract_integer(ts->year)); + + S48_RECORD_SET(sql_timestamp, SR_SQL_TIMESTAMP_MONTH, + s48_extract_integer(ts->month)); + + S48_RECORD_SET(sql_timestamp, SR_SQL_TIMESTAMP_DAY, + s48_extract_integer(ts->day)); + + S48_RECORD_SET(sql_timestamp, SR_SQL_TIMESTAMP_HOUR, + s48_extract_integer(ts->hour)); + + S48_RECORD_SET(sql_timestamp, SR_SQL_TIMESTAMP_MINUTE, + s48_extract_integer(ts->minute)); + + S48_RECORD_SET(sql_timestamp, SR_SQL_TIMESTAMP_SECOND, + s48_extract_integer(ts->second)); + + S48_RECORD_SET(sql_timestamp, SR_SQL_TIMESTAMP_FRACTION, + s48_extract_integer(ts->fraction)); + + return sql_timestamp; +} void s48_init_odbc(void) { @@ -1771,11 +2052,15 @@ void s48_init_odbc(void) /* PART 5 */ S48_EXPORT_FUNCTION(odbc_sql_prepare); + S48_EXPORT_FUNCTION(odbc_sql_bind_parameter_exec_out); /* PART 6 */ S48_EXPORT_FUNCTION(odbc_sql_execute); + S48_EXPORT_FUNCTION(odbc_sql_execute_direct); /* PART 7 */ + S48_EXPORT_FUNCTION(odbc_sql_get_data); + S48_EXPORT_FUNCTION(odbc_sql_fetch); /* PART 8 */ @@ -1788,4 +2073,3 @@ void s48_init_odbc(void) S48_EXPORT_FUNCTION(odbc_sql_disconnect); S48_EXPORT_FUNCTION(odbc_sql_free_handle); } - diff --git a/scsh/odbc/odbc.h b/scsh/odbc/odbc.h index dd8d5c0..ecbdd49 100644 --- a/scsh/odbc/odbc.h +++ b/scsh/odbc/odbc.h @@ -11,6 +11,7 @@ #define ODBC_GET_INFO_MAX_LEN 255 #define ODBC_GET_CONNECT_ATTR_MAX_LEN 255 #define ODBC_GET_STMT_ATTR_MAX_LEN 255 +#define ODBC_GET_DATA_MAX_STR_LEN 255 #define ODBC_DEBUG_MSGS 1 @@ -24,23 +25,33 @@ #ifdef ODBC_DEBUG_MSGS #define ODBC_DEBUG_PRINTF(str) printf(str); +#define ODBC_DEBUG_PRINTF_ARG1(str, arg) printf(str, arg); +#define ODBC_DEBUG_PRINTF_ARG2(str, arg1, arg2) printf(str, arg1, arg2); #else #define ODBC_DEBUG_PRINTF(str) ; +#define ODBC_DEBUG_PRINTF_ARG1(str, arg) ; +#define ODBC_DEBUG_PRINTF_ARG2(str, arg1, arg2) ; #endif /* offsets for scheme records */ /* corresponds to sql-date */ +static s48_value sql_date_record_type = S48_FALSE; + #define SR_SQL_DATE_YEAR 0 #define SR_SQL_DATE_MONTH 1 #define SR_SQL_DATE_DAY 2 /* corresponds to sql-time */ +static s48_value sql_time_record_type = S48_FALSE; + #define SR_SQL_TIME_HOUR 0 #define SR_SQL_TIME_MINUTE 1 #define SR_SQL_TIME_SECOND 2 /* corresponds to sql-timestamp */ +static s48_value sql_timestamp_record_type = S48_FALSE; + #define SR_SQL_TIMESTAMP_YEAR 0 #define SR_SQL_TIMESTAMP_MONTH 1 #define SR_SQL_TIMESTAMP_DAY 2 @@ -70,7 +81,7 @@ s48_value odbc_alloc_environment_handle(); /* given a valid environment handle (type SQLHENV) this function * sets the environment attributes. This needs to be done before * allocating a connection handle */ -void odbc_set_env_attr(SQLHENV env_handle); +void odbc_sql_set_env_attr(SQLHENV env_handle); /* Given a valid environment handle get a connection handle */ s48_value odbc_alloc_connection_handle(s48_value env_handle); @@ -176,6 +187,9 @@ s48_value odbc_sql_get_stmt_attr_string(s48_value stmt_handle, /* Prepare a SQL statement for execution */ s48_value odbc_sql_prepare(s48_value stmt_handle, s48_value stmt_txt); +s48_value odbc_sql_bind_parameter_exec_out(s48_value stmt_handle, + s48_value param_vals); + /* * * PART 6 @@ -185,6 +199,8 @@ s48_value odbc_sql_prepare(s48_value stmt_handle, s48_value stmt_txt); */ s48_value odbc_sql_execute(s48_value stmt_handle); +s48_value odbc_sql_execute_direct(s48_value stmt_handle, s48_value stmt); + /* * * PART 7 @@ -193,6 +209,15 @@ s48_value odbc_sql_execute(s48_value stmt_handle); * */ +s48_value odbc_sql_get_data(s48_value stmt_handle, + s48_value column_number, + s48_value target_type); + +void check_sql_get_data_result(SQLRETURN retval, SQLHSTMT stmt_handle); + +s48_value odbc_sql_fetch(s48_value stmt_handle); + + /* * * PART 8 @@ -249,5 +274,24 @@ s48_value odbc_sql_free_handle(s48_value handle_type, s48_value handle); void odbc_debug_msgs(SQLSMALLINT handle_type, SQLHANDLE handle); #endif +/* convert Scheme sql-date record to SQL_DATE_STRUCT */ +void sql_date_record_to_struct(s48_value sql_date, SQL_DATE_STRUCT *ds); + +/* convert SQL_DATE_STRUCT to Scheme sql-date record */ +s48_value struct_to_sql_date_record(SQL_DATE_STRUCT *ds); + +/* convert Scheme sql-time record to SQL_TIME_STRUCT */ +void sql_time_record_to_struct(s48_value sql_time, SQL_TIME_STRUCT *ts); + +/* convert SQL_TIME_STRUCT to Scheme sql-time record */ +s48_value struct_to_sql_time_record(SQL_TIME_STRUCT *ts); + +/* convert SQL_TIME_STRUCT to Scheme sql-time record */ +s48_value struct_to_sql_time_record(SQL_TIME_STRUCT *ts); + +/* convert Scheme sql-timestamp record to SQL_TIMESTAMP_STRUCT */ +void sql_timestamp_record_to_struct(s48_value sql_timestamp, + SQL_TIMESTAMP_STRUCT *ts); + void s48_init_odbc(void);